| /******************************************************************************* |
| * Copyright (c) 2000, 2018 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| * Stephan Herrmann - Contribution for |
| * bug 393719 - [compiler] inconsistent warnings on iteration variables |
| *******************************************************************************/ |
| |
| package org.eclipse.jdt.core.dom; |
| |
| import java.util.Comparator; |
| import java.util.HashSet; |
| import java.util.Iterator; |
| import java.util.List; |
| import java.util.Map; |
| import java.util.Set; |
| import java.util.TreeSet; |
| |
| import org.eclipse.core.runtime.IProgressMonitor; |
| import org.eclipse.core.runtime.OperationCanceledException; |
| import org.eclipse.jdt.core.JavaCore; |
| import org.eclipse.jdt.core.compiler.CategorizedProblem; |
| import org.eclipse.jdt.core.compiler.CharOperation; |
| import org.eclipse.jdt.core.compiler.IProblem; |
| import org.eclipse.jdt.core.compiler.InvalidInputException; |
| import org.eclipse.jdt.core.dom.Modifier.ModifierKeyword; |
| import org.eclipse.jdt.core.dom.ModuleModifier.ModuleModifierKeyword; |
| import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration; |
| import org.eclipse.jdt.internal.compiler.ast.AbstractVariableDeclaration; |
| import org.eclipse.jdt.internal.compiler.ast.Argument; |
| import org.eclipse.jdt.internal.compiler.ast.FieldReference; |
| import org.eclipse.jdt.internal.compiler.ast.ForeachStatement; |
| import org.eclipse.jdt.internal.compiler.ast.IntersectionCastTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.JavadocArgumentExpression; |
| import org.eclipse.jdt.internal.compiler.ast.JavadocFieldReference; |
| import org.eclipse.jdt.internal.compiler.ast.JavadocMessageSend; |
| import org.eclipse.jdt.internal.compiler.ast.LocalDeclaration; |
| import org.eclipse.jdt.internal.compiler.ast.MessageSend; |
| import org.eclipse.jdt.internal.compiler.ast.ModuleReference; |
| import org.eclipse.jdt.internal.compiler.ast.NameReference; |
| import org.eclipse.jdt.internal.compiler.ast.OperatorIds; |
| import org.eclipse.jdt.internal.compiler.ast.ParameterizedQualifiedTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.ParameterizedSingleTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.QualifiedAllocationExpression; |
| import org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference; |
| import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.Receiver; |
| import org.eclipse.jdt.internal.compiler.ast.SingleNameReference; |
| import org.eclipse.jdt.internal.compiler.ast.SingleTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.StringLiteralConcatenation; |
| import org.eclipse.jdt.internal.compiler.ast.SuperReference; |
| import org.eclipse.jdt.internal.compiler.ast.TypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.UnionTypeReference; |
| import org.eclipse.jdt.internal.compiler.ast.Wildcard; |
| import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants; |
| import org.eclipse.jdt.internal.compiler.impl.CompilerOptions; |
| import org.eclipse.jdt.internal.compiler.lookup.BlockScope; |
| import org.eclipse.jdt.internal.compiler.lookup.ExtraCompilerModifiers; |
| import org.eclipse.jdt.internal.compiler.lookup.TypeConstants; |
| import org.eclipse.jdt.internal.compiler.parser.RecoveryScanner; |
| import org.eclipse.jdt.internal.compiler.parser.Scanner; |
| import org.eclipse.jdt.internal.compiler.parser.TerminalTokens; |
| import org.eclipse.jdt.internal.core.dom.SourceRangeVerifier; |
| import org.eclipse.jdt.internal.core.util.Util; |
| |
| /** |
| * Internal class for converting internal compiler ASTs into public ASTs. |
| */ |
| @SuppressWarnings({ "rawtypes", "unchecked" }) |
| class ASTConverter { |
| |
| protected AST ast; |
| private ASTNode referenceContext; |
| protected Comment[] commentsTable; |
| char[] compilationUnitSource; |
| int compilationUnitSourceLength; |
| protected DocCommentParser docParser; |
| // comments |
| protected boolean insideComments; |
| protected IProgressMonitor monitor; |
| protected Set pendingNameScopeResolution; |
| protected Set pendingThisExpressionScopeResolution; |
| protected boolean resolveBindings; |
| Scanner scanner; |
| private DefaultCommentMapper commentMapper; |
| |
| public ASTConverter(Map<String, String> options, boolean resolveBindings, IProgressMonitor monitor) { |
| this.resolveBindings = resolveBindings; |
| this.referenceContext = null; |
| String sourceModeSetting = options.get(JavaCore.COMPILER_SOURCE); |
| long sourceLevel = CompilerOptions.versionToJdkLevel(sourceModeSetting); |
| if (sourceLevel == 0) { |
| // unknown sourceModeSetting |
| sourceLevel = ClassFileConstants.JDK1_3; |
| } |
| this.scanner = new Scanner( |
| true /*comment*/, |
| false /*whitespace*/, |
| false /*nls*/, |
| sourceLevel /*sourceLevel*/, |
| null /*taskTags*/, |
| null/*taskPriorities*/, |
| true/*taskCaseSensitive*/); |
| this.monitor = monitor; |
| this.insideComments = JavaCore.ENABLED.equals(options.get(JavaCore.COMPILER_DOC_COMMENT_SUPPORT)); |
| } |
| |
| protected void adjustSourcePositionsForParent(org.eclipse.jdt.internal.compiler.ast.Expression expression) { |
| int start = expression.sourceStart; |
| int end = expression.sourceEnd; |
| int leftParentCount = 1; |
| int rightParentCount = 0; |
| this.scanner.resetTo(start, end); |
| try { |
| int token = this.scanner.getNextToken(); |
| expression.sourceStart = this.scanner.currentPosition; |
| boolean stop = false; |
| while (!stop && ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF)) { |
| switch(token) { |
| case TerminalTokens.TokenNameLPAREN: |
| leftParentCount++; |
| break; |
| case TerminalTokens.TokenNameRPAREN: |
| rightParentCount++; |
| if (rightParentCount == leftParentCount) { |
| // we found the matching parenthesis |
| stop = true; |
| } |
| } |
| } |
| expression.sourceEnd = this.scanner.startPosition - 1; |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| |
| protected void buildBodyDeclarations( |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration, |
| AbstractTypeDeclaration typeDecl, |
| boolean isInterface) { |
| // add body declaration in the lexical order |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration[] members = typeDeclaration.memberTypes; |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration[] fields = typeDeclaration.fields; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration[] methods = typeDeclaration.methods; |
| |
| int fieldsLength = fields == null? 0 : fields.length; |
| int methodsLength = methods == null? 0 : methods.length; |
| int membersLength = members == null ? 0 : members.length; |
| int fieldsIndex = 0; |
| int methodsIndex = 0; |
| int membersIndex = 0; |
| |
| while ((fieldsIndex < fieldsLength) |
| || (membersIndex < membersLength) |
| || (methodsIndex < methodsLength)) { |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration nextFieldDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration nextMethodDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration nextMemberDeclaration = null; |
| |
| int position = Integer.MAX_VALUE; |
| int nextDeclarationType = -1; |
| if (fieldsIndex < fieldsLength) { |
| nextFieldDeclaration = fields[fieldsIndex]; |
| if (nextFieldDeclaration.declarationSourceStart < position) { |
| position = nextFieldDeclaration.declarationSourceStart; |
| nextDeclarationType = 0; // FIELD |
| } |
| } |
| if (methodsIndex < methodsLength) { |
| nextMethodDeclaration = methods[methodsIndex]; |
| if (nextMethodDeclaration.declarationSourceStart < position) { |
| position = nextMethodDeclaration.declarationSourceStart; |
| nextDeclarationType = 1; // METHOD |
| } |
| } |
| if (membersIndex < membersLength) { |
| nextMemberDeclaration = members[membersIndex]; |
| if (nextMemberDeclaration.declarationSourceStart < position) { |
| position = nextMemberDeclaration.declarationSourceStart; |
| nextDeclarationType = 2; // MEMBER |
| } |
| } |
| switch (nextDeclarationType) { |
| case 0 : |
| if (nextFieldDeclaration.getKind() == AbstractVariableDeclaration.ENUM_CONSTANT) { |
| typeDecl.bodyDeclarations().add(convert(nextFieldDeclaration)); |
| } else { |
| checkAndAddMultipleFieldDeclaration(fields, fieldsIndex, typeDecl.bodyDeclarations()); |
| } |
| fieldsIndex++; |
| break; |
| case 1 : |
| methodsIndex++; |
| if (!nextMethodDeclaration.isDefaultConstructor() && !nextMethodDeclaration.isClinit()) { |
| typeDecl.bodyDeclarations().add(convert(isInterface, nextMethodDeclaration)); |
| } |
| break; |
| case 2 : |
| membersIndex++; |
| ASTNode node = convert(nextMemberDeclaration); |
| if (node == null) { |
| typeDecl.setFlags(typeDecl.getFlags() | ASTNode.MALFORMED); |
| } else { |
| typeDecl.bodyDeclarations().add(node); |
| } |
| } |
| } |
| // Convert javadoc |
| convert(typeDeclaration.javadoc, typeDecl); |
| } |
| |
| protected void buildBodyDeclarations(org.eclipse.jdt.internal.compiler.ast.TypeDeclaration enumDeclaration2, EnumDeclaration enumDeclaration) { |
| // add body declaration in the lexical order |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration[] members = enumDeclaration2.memberTypes; |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration[] fields = enumDeclaration2.fields; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration[] methods = enumDeclaration2.methods; |
| |
| int fieldsLength = fields == null? 0 : fields.length; |
| int methodsLength = methods == null? 0 : methods.length; |
| int membersLength = members == null ? 0 : members.length; |
| int fieldsIndex = 0; |
| int methodsIndex = 0; |
| int membersIndex = 0; |
| |
| while ((fieldsIndex < fieldsLength) |
| || (membersIndex < membersLength) |
| || (methodsIndex < methodsLength)) { |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration nextFieldDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration nextMethodDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration nextMemberDeclaration = null; |
| |
| int position = Integer.MAX_VALUE; |
| int nextDeclarationType = -1; |
| if (fieldsIndex < fieldsLength) { |
| nextFieldDeclaration = fields[fieldsIndex]; |
| if (nextFieldDeclaration.declarationSourceStart < position) { |
| position = nextFieldDeclaration.declarationSourceStart; |
| nextDeclarationType = 0; // FIELD |
| } |
| } |
| if (methodsIndex < methodsLength) { |
| nextMethodDeclaration = methods[methodsIndex]; |
| if (nextMethodDeclaration.declarationSourceStart < position) { |
| position = nextMethodDeclaration.declarationSourceStart; |
| nextDeclarationType = 1; // METHOD |
| } |
| } |
| if (membersIndex < membersLength) { |
| nextMemberDeclaration = members[membersIndex]; |
| if (nextMemberDeclaration.declarationSourceStart < position) { |
| position = nextMemberDeclaration.declarationSourceStart; |
| nextDeclarationType = 2; // MEMBER |
| } |
| } |
| switch (nextDeclarationType) { |
| case 0 : |
| if (nextFieldDeclaration.getKind() == AbstractVariableDeclaration.ENUM_CONSTANT) { |
| enumDeclaration.enumConstants().add(convert(nextFieldDeclaration)); |
| } else { |
| checkAndAddMultipleFieldDeclaration(fields, fieldsIndex, enumDeclaration.bodyDeclarations()); |
| } |
| fieldsIndex++; |
| break; |
| case 1 : |
| methodsIndex++; |
| if (!nextMethodDeclaration.isDefaultConstructor() && !nextMethodDeclaration.isClinit()) { |
| enumDeclaration.bodyDeclarations().add(convert(false, nextMethodDeclaration)); |
| } |
| break; |
| case 2 : |
| membersIndex++; |
| enumDeclaration.bodyDeclarations().add(convert(nextMemberDeclaration)); |
| break; |
| } |
| } |
| convert(enumDeclaration2.javadoc, enumDeclaration); |
| } |
| |
| protected void buildBodyDeclarations(org.eclipse.jdt.internal.compiler.ast.TypeDeclaration expression, AnonymousClassDeclaration anonymousClassDeclaration) { |
| // add body declaration in the lexical order |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration[] members = expression.memberTypes; |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration[] fields = expression.fields; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration[] methods = expression.methods; |
| |
| int fieldsLength = fields == null? 0 : fields.length; |
| int methodsLength = methods == null? 0 : methods.length; |
| int membersLength = members == null ? 0 : members.length; |
| int fieldsIndex = 0; |
| int methodsIndex = 0; |
| int membersIndex = 0; |
| |
| while ((fieldsIndex < fieldsLength) |
| || (membersIndex < membersLength) |
| || (methodsIndex < methodsLength)) { |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration nextFieldDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration nextMethodDeclaration = null; |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration nextMemberDeclaration = null; |
| |
| int position = Integer.MAX_VALUE; |
| int nextDeclarationType = -1; |
| if (fieldsIndex < fieldsLength) { |
| nextFieldDeclaration = fields[fieldsIndex]; |
| if (nextFieldDeclaration.declarationSourceStart < position) { |
| position = nextFieldDeclaration.declarationSourceStart; |
| nextDeclarationType = 0; // FIELD |
| } |
| } |
| if (methodsIndex < methodsLength) { |
| nextMethodDeclaration = methods[methodsIndex]; |
| if (nextMethodDeclaration.declarationSourceStart < position) { |
| position = nextMethodDeclaration.declarationSourceStart; |
| nextDeclarationType = 1; // METHOD |
| } |
| } |
| if (membersIndex < membersLength) { |
| nextMemberDeclaration = members[membersIndex]; |
| if (nextMemberDeclaration.declarationSourceStart < position) { |
| position = nextMemberDeclaration.declarationSourceStart; |
| nextDeclarationType = 2; // MEMBER |
| } |
| } |
| switch (nextDeclarationType) { |
| case 0 : |
| if (nextFieldDeclaration.getKind() == AbstractVariableDeclaration.ENUM_CONSTANT) { |
| anonymousClassDeclaration.bodyDeclarations().add(convert(nextFieldDeclaration)); |
| } else { |
| checkAndAddMultipleFieldDeclaration(fields, fieldsIndex, anonymousClassDeclaration.bodyDeclarations()); |
| } |
| fieldsIndex++; |
| break; |
| case 1 : |
| methodsIndex++; |
| if (!nextMethodDeclaration.isDefaultConstructor() && !nextMethodDeclaration.isClinit()) { |
| anonymousClassDeclaration.bodyDeclarations().add(convert(false, nextMethodDeclaration)); |
| } |
| break; |
| case 2 : |
| membersIndex++; |
| ASTNode node = convert(nextMemberDeclaration); |
| if (node == null) { |
| anonymousClassDeclaration.setFlags(anonymousClassDeclaration.getFlags() | ASTNode.MALFORMED); |
| } else { |
| anonymousClassDeclaration.bodyDeclarations().add(node); |
| } |
| } |
| } |
| } |
| |
| private void checkAndSetMalformed(ASTNode spannedNode, ASTNode spanningNode) { |
| if ((spannedNode.getFlags() & ASTNode.MALFORMED) != 0) { |
| spanningNode.setFlags(spanningNode.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| |
| /** |
| * Internal access method to SingleVariableDeclaration#setExtraDimensions() for avoiding deprecated warnings |
| * |
| * @param node |
| * @param dimensions |
| * @deprecated |
| */ |
| private static void internalSetExtraDimensions(SingleVariableDeclaration node, int dimensions) { |
| node.setExtraDimensions(dimensions); |
| } |
| /** |
| * Internal access method to VariableDeclarationFragment#setExtraDimensions() for avoiding deprecated warnings |
| * |
| * @param node |
| * @param dimensions |
| * @deprecated |
| */ |
| private static void internalSetExtraDimensions(VariableDeclarationFragment node, int dimensions) { |
| node.setExtraDimensions(dimensions); |
| } |
| /** |
| * Internal access method to MethodDeclaration#setExtraDimension() for avoiding deprecated warnings |
| * |
| * @param node |
| * @param dimensions |
| * @deprecated |
| */ |
| private static void internalSetExtraDimensions(MethodDeclaration node, int dimensions) { |
| node.setExtraDimensions(dimensions); |
| } |
| /** |
| * Internal access method to MethodDeclaration#thrownExceptions() for avoiding deprecated warnings |
| * |
| * @param node |
| * @deprecated |
| */ |
| private static List internalThownExceptions(MethodDeclaration node) { |
| return node.thrownExceptions(); |
| } |
| |
| /** |
| * @param compilationUnit |
| * @param comments |
| */ |
| void buildCommentsTable(CompilationUnit compilationUnit, int[][] comments) { |
| // Build comment table |
| this.commentsTable = new Comment[comments.length]; |
| int nbr = 0; |
| for (int i = 0; i < comments.length; i++) { |
| Comment comment = createComment(comments[i]); |
| if (comment != null) { |
| comment.setAlternateRoot(compilationUnit); |
| this.commentsTable[nbr++] = comment; |
| } |
| } |
| // Resize table if necessary |
| if (nbr<comments.length) { |
| Comment[] newCommentsTable = new Comment[nbr]; |
| System.arraycopy(this.commentsTable, 0, newCommentsTable, 0, nbr); |
| this.commentsTable = newCommentsTable; |
| } |
| compilationUnit.setCommentTable(this.commentsTable); |
| } |
| |
| protected void checkAndAddMultipleFieldDeclaration(org.eclipse.jdt.internal.compiler.ast.FieldDeclaration[] fields, int index, List bodyDeclarations) { |
| if (fields[index] instanceof org.eclipse.jdt.internal.compiler.ast.Initializer) { |
| org.eclipse.jdt.internal.compiler.ast.Initializer oldInitializer = (org.eclipse.jdt.internal.compiler.ast.Initializer) fields[index]; |
| Initializer initializer = new Initializer(this.ast); |
| initializer.setBody(convert(oldInitializer.block)); |
| setModifiers(initializer, oldInitializer); |
| initializer.setSourceRange(oldInitializer.declarationSourceStart, oldInitializer.sourceEnd - oldInitializer.declarationSourceStart + 1); |
| // The javadoc comment is now got from list store in compilation unit declaration |
| convert(oldInitializer.javadoc, initializer); |
| bodyDeclarations.add(initializer); |
| return; |
| } |
| if (index > 0 && fields[index - 1].declarationSourceStart == fields[index].declarationSourceStart) { |
| // we have a multiple field declaration |
| // We retrieve the existing fieldDeclaration to add the new VariableDeclarationFragment |
| FieldDeclaration fieldDeclaration = (FieldDeclaration) bodyDeclarations.get(bodyDeclarations.size() - 1); |
| fieldDeclaration.fragments().add(convertToVariableDeclarationFragment(fields[index])); |
| } else { |
| // we can create a new FieldDeclaration |
| bodyDeclarations.add(convertToFieldDeclaration(fields[index])); |
| } |
| } |
| |
| protected void checkAndAddMultipleLocalDeclaration(org.eclipse.jdt.internal.compiler.ast.Statement[] stmts, int index, List blockStatements) { |
| if (index > 0 |
| && stmts[index - 1] instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.LocalDeclaration local1 = (org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) stmts[index - 1]; |
| org.eclipse.jdt.internal.compiler.ast.LocalDeclaration local2 = (org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) stmts[index]; |
| if (local1.declarationSourceStart == local2.declarationSourceStart) { |
| // we have a multiple local declarations |
| // We retrieve the existing VariableDeclarationStatement to add the new VariableDeclarationFragment |
| VariableDeclarationStatement variableDeclarationStatement = (VariableDeclarationStatement) blockStatements.get(blockStatements.size() - 1); |
| variableDeclarationStatement.fragments().add(convertToVariableDeclarationFragment((org.eclipse.jdt.internal.compiler.ast.LocalDeclaration)stmts[index])); |
| } else { |
| // we can create a new FieldDeclaration |
| blockStatements.add(convertToVariableDeclarationStatement((org.eclipse.jdt.internal.compiler.ast.LocalDeclaration)stmts[index])); |
| } |
| } else { |
| // we can create a new FieldDeclaration |
| blockStatements.add(convertToVariableDeclarationStatement((org.eclipse.jdt.internal.compiler.ast.LocalDeclaration)stmts[index])); |
| } |
| } |
| |
| protected void checkCanceled() { |
| if (this.monitor != null && this.monitor.isCanceled()) |
| throw new OperationCanceledException(); |
| } |
| |
| private int checkLength(int start, int end) { |
| int len = end - start + 1; |
| return len > 0 ? len : 0; |
| } |
| protected void completeRecord(ArrayType arrayType, org.eclipse.jdt.internal.compiler.ast.ASTNode astNode) { |
| ArrayType array = arrayType; |
| this.recordNodes(arrayType, astNode); |
| if (this.ast.apiLevel() >= AST.JLS8_INTERNAL) { |
| this.recordNodes(arrayType.getElementType(), astNode); |
| return; |
| } |
| int dimensions = array.getDimensions(); |
| for (int i = 0; i < dimensions; i++) { |
| Type componentType = componentType(array); |
| this.recordNodes(componentType, astNode); |
| if (componentType.isArrayType()) { |
| array = (ArrayType) componentType; |
| } |
| } |
| } |
| |
| /** |
| * @deprecated |
| */ |
| private Type componentType(ArrayType array) { |
| return array.getComponentType(); |
| } |
| |
| public ASTNode convert(boolean isInterface, org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration methodDeclaration) { |
| checkCanceled(); |
| if (methodDeclaration instanceof org.eclipse.jdt.internal.compiler.ast.AnnotationMethodDeclaration) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.AnnotationMethodDeclaration) methodDeclaration); |
| } |
| MethodDeclaration methodDecl = new MethodDeclaration(this.ast); |
| ASTNode oldReferenceContext = this.referenceContext; |
| this.referenceContext = methodDecl; |
| setModifiers(methodDecl, methodDeclaration); |
| boolean isConstructor = methodDeclaration.isConstructor(); |
| methodDecl.setConstructor(isConstructor); |
| final SimpleName methodName = new SimpleName(this.ast); |
| methodName.internalSetIdentifier(new String(methodDeclaration.selector)); |
| int start = methodDeclaration.sourceStart; |
| int end = retrieveIdentifierEndPosition(start, methodDeclaration.sourceEnd); |
| if (end < start) |
| end = start + methodDeclaration.selector.length;// naive recovery with method name |
| methodName.setSourceRange(start, end - start + 1); |
| methodDecl.setName(methodName); |
| org.eclipse.jdt.internal.compiler.ast.TypeReference[] thrownExceptions = methodDeclaration.thrownExceptions; |
| int methodHeaderEnd = methodDeclaration.sourceEnd; |
| int thrownExceptionsLength = thrownExceptions == null ? 0 : thrownExceptions.length; |
| if (thrownExceptionsLength > 0) { |
| if (this.ast.apiLevel() < AST.JLS8_INTERNAL) { |
| Name thrownException; |
| int i = 0; |
| do { |
| TypeReference typeRef = thrownExceptions[i++]; |
| thrownException = convert(typeRef); |
| if (typeRef.annotations != null && typeRef.annotations.length > 0) { |
| thrownException.setFlags(thrownException.getFlags() | ASTNode.MALFORMED); |
| } |
| internalThownExceptions(methodDecl).add(thrownException); |
| } while (i < thrownExceptionsLength); |
| methodHeaderEnd = thrownException.getStartPosition() + thrownException.getLength(); |
| } else { |
| Type thrownExceptionType; |
| int i = 0; |
| do { |
| thrownExceptionType = convertType(thrownExceptions[i++]); |
| methodDecl.thrownExceptionTypes().add(thrownExceptionType); |
| } while (i < thrownExceptionsLength); |
| methodHeaderEnd = thrownExceptionType.getStartPosition() + thrownExceptionType.getLength(); |
| } |
| } |
| |
| if (methodDeclaration.receiver != null) { |
| if(this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| convertAndSetReceiver(methodDeclaration, methodDecl); |
| } else { |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| org.eclipse.jdt.internal.compiler.ast.Argument[] parameters = methodDeclaration.arguments; |
| int parametersLength = parameters == null ? 0 : parameters.length; |
| if (parametersLength > 0) { |
| SingleVariableDeclaration parameter; |
| int i = 0; |
| do { |
| parameter = convert(parameters[i++]); |
| methodDecl.parameters().add(parameter); |
| } while (i < parametersLength); |
| if (thrownExceptionsLength == 0) { |
| methodHeaderEnd = parameter.getStartPosition() + parameter.getLength(); |
| } |
| } |
| org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall explicitConstructorCall = null; |
| if (isConstructor) { |
| if (isInterface) { |
| // interface cannot have a constructor |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| org.eclipse.jdt.internal.compiler.ast.ConstructorDeclaration constructorDeclaration = (org.eclipse.jdt.internal.compiler.ast.ConstructorDeclaration) methodDeclaration; |
| explicitConstructorCall = constructorDeclaration.constructorCall; |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| // set the return type to VOID |
| PrimitiveType returnType = new PrimitiveType(this.ast); |
| returnType.setPrimitiveTypeCode(PrimitiveType.VOID); |
| returnType.setSourceRange(methodDeclaration.sourceStart, 0); |
| methodDecl.internalSetReturnType(returnType); |
| break; |
| default : |
| methodDecl.setReturnType2(null); |
| } |
| } else if (methodDeclaration instanceof org.eclipse.jdt.internal.compiler.ast.MethodDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.MethodDeclaration method = (org.eclipse.jdt.internal.compiler.ast.MethodDeclaration) methodDeclaration; |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeReference = method.returnType; |
| if (typeReference != null) { |
| Type returnType = convertType(typeReference); |
| // get the positions of the right parenthesis |
| int rightParenthesisPosition = retrieveEndOfRightParenthesisPosition(end, method.bodyEnd); |
| int extraDimensions = typeReference.extraDimensions(); |
| if (this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| setExtraAnnotatedDimensions(rightParenthesisPosition, method.bodyEnd, typeReference, |
| methodDecl.extraDimensions(), extraDimensions); |
| } else { |
| internalSetExtraDimensions(methodDecl, extraDimensions); |
| } |
| setTypeForMethodDeclaration(methodDecl, returnType, extraDimensions); |
| } else { |
| // no return type for a method that is not a constructor |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| break; |
| default : |
| methodDecl.setReturnType2(null); |
| } |
| } |
| } |
| int declarationSourceStart = methodDeclaration.declarationSourceStart; |
| int bodyEnd = methodDeclaration.bodyEnd; |
| methodDecl.setSourceRange(declarationSourceStart, checkLength(declarationSourceStart, bodyEnd)); |
| int declarationSourceEnd = methodDeclaration.declarationSourceEnd; |
| int rightBraceOrSemiColonPositionStart = bodyEnd == declarationSourceEnd ? bodyEnd : bodyEnd + 1; |
| int closingPosition = retrieveRightBraceOrSemiColonPosition(rightBraceOrSemiColonPositionStart, declarationSourceEnd); |
| if (closingPosition != -1) { |
| int startPosition = methodDecl.getStartPosition(); |
| methodDecl.setSourceRange(startPosition, closingPosition - startPosition + 1); |
| |
| org.eclipse.jdt.internal.compiler.ast.Statement[] statements = methodDeclaration.statements; |
| |
| start = retrieveStartBlockPosition(methodHeaderEnd, methodDeclaration.bodyStart); |
| if (start == -1) start = methodDeclaration.bodyStart; // use recovery position for body start |
| end = retrieveRightBrace(methodDeclaration.bodyEnd + 1, declarationSourceEnd); |
| Block block = null; |
| if (start != -1 && end != -1) { |
| /* |
| * start or end can be equal to -1 if we have an interface's method. |
| */ |
| block = new Block(this.ast); |
| block.setSourceRange(start, closingPosition - start + 1); |
| methodDecl.setBody(block); |
| } |
| if (block != null && (statements != null || explicitConstructorCall != null)) { |
| if (explicitConstructorCall != null && explicitConstructorCall.accessMode != org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall.ImplicitSuper) { |
| block.statements().add(convert(explicitConstructorCall)); |
| } |
| int statementsLength = statements == null ? 0 : statements.length; |
| for (int i = 0; i < statementsLength; i++) { |
| if (statements[i] instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| checkAndAddMultipleLocalDeclaration(statements, i, block.statements()); |
| } else { |
| final Statement statement = convert(statements[i]); |
| if (statement != null) { |
| block.statements().add(statement); |
| } |
| } |
| } |
| } |
| if (block != null) { |
| if ((methodDeclaration.modifiers & (ClassFileConstants.AccAbstract | ClassFileConstants.AccNative)) != 0 |
| || (isInterface && (this.ast.apiLevel < AST.JLS8_INTERNAL || |
| (methodDeclaration.modifiers & (ClassFileConstants.AccStatic | ExtraCompilerModifiers.AccDefaultMethod | |
| (this.ast.apiLevel > AST.JLS8_INTERNAL ? ClassFileConstants.AccPrivate : 0))) == 0))) { |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| } else { |
| // syntax error in this method declaration |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| if (!methodDeclaration.isNative() && !methodDeclaration.isAbstract()) { |
| start = retrieveStartBlockPosition(methodHeaderEnd, bodyEnd); |
| if (start == -1) start = methodDeclaration.bodyStart; // use recovery position for body start |
| end = methodDeclaration.bodyEnd; |
| // try to get the best end position |
| CategorizedProblem[] problems = methodDeclaration.compilationResult().problems; |
| if (problems != null) { |
| for (int i = 0, max = methodDeclaration.compilationResult().problemCount; i < max; i++) { |
| CategorizedProblem currentProblem = problems[i]; |
| if (currentProblem.getSourceStart() == start && currentProblem.getID() == IProblem.ParsingErrorInsertToComplete) { |
| end = currentProblem.getSourceEnd(); |
| break; |
| } |
| } |
| } |
| int startPosition = methodDecl.getStartPosition(); |
| methodDecl.setSourceRange(startPosition, checkLength(startPosition, end)); |
| if (start != -1 && end != -1) { |
| /* |
| * start or end can be equal to -1 if we have an interface's method. |
| */ |
| Block block = new Block(this.ast); |
| block.setSourceRange(start, checkLength(start, end)); |
| methodDecl.setBody(block); |
| } |
| } |
| } |
| |
| org.eclipse.jdt.internal.compiler.ast.TypeParameter[] typeParameters = methodDeclaration.typeParameters(); |
| if (typeParameters != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = typeParameters.length; i < max; i++) { |
| methodDecl.typeParameters().add(convert(typeParameters[i])); |
| } |
| } |
| } |
| |
| // The javadoc comment is now got from list store in compilation unit declaration |
| convert(methodDeclaration.javadoc, methodDecl); |
| if (this.resolveBindings) { |
| recordNodes(methodDecl, methodDeclaration); |
| recordNodes(methodName, methodDeclaration); |
| methodDecl.resolveBinding(); |
| } |
| this.referenceContext = oldReferenceContext; |
| return methodDecl; |
| } |
| |
| public ClassInstanceCreation convert(org.eclipse.jdt.internal.compiler.ast.AllocationExpression expression) { |
| ClassInstanceCreation classInstanceCreation = new ClassInstanceCreation(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(classInstanceCreation, expression); |
| } |
| if (expression.typeArguments != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| classInstanceCreation.setFlags(classInstanceCreation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = expression.typeArguments.length; i < max; i++) { |
| classInstanceCreation.typeArguments().add(convertType(expression.typeArguments[i])); |
| } |
| } |
| } |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| classInstanceCreation.internalSetName(convert(expression.type)); |
| break; |
| default : |
| classInstanceCreation.setType(convertType(expression.type)); |
| } |
| classInstanceCreation.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = expression.arguments; |
| if (arguments != null) { |
| int length = arguments.length; |
| for (int i = 0; i < length; i++) { |
| classInstanceCreation.arguments().add(convert(arguments[i])); |
| } |
| } |
| return classInstanceCreation; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.AND_AND_Expression expression) { |
| InfixExpression infixExpression = new InfixExpression(this.ast); |
| infixExpression.setOperator(InfixExpression.Operator.CONDITIONAL_AND); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| final int expressionOperatorID = (expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT; |
| if (expression.left instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((expression.left.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) { |
| // create an extended string literal equivalent => use the extended operands list |
| infixExpression.extendedOperands().add(convert(expression.right)); |
| org.eclipse.jdt.internal.compiler.ast.Expression leftOperand = expression.left; |
| org.eclipse.jdt.internal.compiler.ast.Expression rightOperand = null; |
| do { |
| rightOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).right; |
| if ((((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID |
| && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) |
| || ((rightOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID) |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0))) { |
| List extendedOperands = infixExpression.extendedOperands(); |
| InfixExpression temp = new InfixExpression(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| Expression leftSide = convert(leftOperand); |
| temp.setLeftOperand(leftSide); |
| temp.setSourceRange(leftSide.getStartPosition(), leftSide.getLength()); |
| int size = extendedOperands.size(); |
| for (int i = 0; i < size - 1; i++) { |
| Expression expr = temp; |
| temp = new InfixExpression(this.ast); |
| |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setLeftOperand(expr); |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| temp.setSourceRange(expr.getStartPosition(), expr.getLength()); |
| } |
| infixExpression = temp; |
| for (int i = 0; i < size; i++) { |
| Expression extendedOperand = (Expression) extendedOperands.remove(size - 1 - i); |
| temp.setRightOperand(extendedOperand); |
| int startPosition = temp.getLeftOperand().getStartPosition(); |
| temp.setSourceRange(startPosition, extendedOperand.getStartPosition() + extendedOperand.getLength() - startPosition); |
| if (temp.getLeftOperand().getNodeType() == ASTNode.INFIX_EXPRESSION) { |
| temp = (InfixExpression) temp.getLeftOperand(); |
| } |
| } |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| return infixExpression; |
| } |
| infixExpression.extendedOperands().add(0, convert(rightOperand)); |
| leftOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).left; |
| } while (leftOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)); |
| Expression leftExpression = convert(leftOperand); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand((Expression)infixExpression.extendedOperands().remove(0)); |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| return infixExpression; |
| } |
| Expression leftExpression = convert(expression.left); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand(convert(expression.right)); |
| infixExpression.setOperator(InfixExpression.Operator.CONDITIONAL_AND); |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| return infixExpression; |
| } |
| |
| private AnnotationTypeDeclaration convertToAnnotationDeclaration(org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration) { |
| checkCanceled(); |
| if (this.scanner.sourceLevel < ClassFileConstants.JDK1_5) return null; |
| AnnotationTypeDeclaration typeDecl = this.ast.newAnnotationTypeDeclaration(); |
| setModifiers(typeDecl, typeDeclaration); |
| final SimpleName typeName = new SimpleName(this.ast); |
| typeName.internalSetIdentifier(new String(typeDeclaration.name)); |
| typeName.setSourceRange(typeDeclaration.sourceStart, typeDeclaration.sourceEnd - typeDeclaration.sourceStart + 1); |
| typeDecl.setName(typeName); |
| typeDecl.setSourceRange(typeDeclaration.declarationSourceStart, typeDeclaration.bodyEnd - typeDeclaration.declarationSourceStart + 1); |
| |
| buildBodyDeclarations(typeDeclaration, typeDecl, false); |
| // The javadoc comment is now got from list store in compilation unit declaration |
| if (this.resolveBindings) { |
| recordNodes(typeDecl, typeDeclaration); |
| recordNodes(typeName, typeDeclaration); |
| typeDecl.resolveBinding(); |
| } |
| return typeDecl; |
| } |
| |
| public ASTNode convert(org.eclipse.jdt.internal.compiler.ast.AnnotationMethodDeclaration annotationTypeMemberDeclaration) { |
| checkCanceled(); |
| if (this.ast.apiLevel == AST.JLS2_INTERNAL) { |
| return null; |
| } |
| AnnotationTypeMemberDeclaration annotationTypeMemberDeclaration2 = new AnnotationTypeMemberDeclaration(this.ast); |
| setModifiers(annotationTypeMemberDeclaration2, annotationTypeMemberDeclaration); |
| final SimpleName methodName = new SimpleName(this.ast); |
| methodName.internalSetIdentifier(new String(annotationTypeMemberDeclaration.selector)); |
| int start = annotationTypeMemberDeclaration.sourceStart; |
| int end = retrieveIdentifierEndPosition(start, annotationTypeMemberDeclaration.sourceEnd); |
| methodName.setSourceRange(start, end - start + 1); |
| annotationTypeMemberDeclaration2.setName(methodName); |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeReference = annotationTypeMemberDeclaration.returnType; |
| if (typeReference != null) { |
| Type returnType = convertType(typeReference); |
| setTypeForMethodDeclaration(annotationTypeMemberDeclaration2, returnType, 0); |
| } |
| int declarationSourceStart = annotationTypeMemberDeclaration.declarationSourceStart; |
| int declarationSourceEnd = annotationTypeMemberDeclaration.bodyEnd; |
| annotationTypeMemberDeclaration2.setSourceRange(declarationSourceStart, declarationSourceEnd - declarationSourceStart + 1); |
| // The javadoc comment is now got from list store in compilation unit declaration |
| convert(annotationTypeMemberDeclaration.javadoc, annotationTypeMemberDeclaration2); |
| org.eclipse.jdt.internal.compiler.ast.Expression memberValue = annotationTypeMemberDeclaration.defaultValue; |
| if (memberValue != null) { |
| annotationTypeMemberDeclaration2.setDefault(convert(memberValue)); |
| } |
| if (this.resolveBindings) { |
| recordNodes(annotationTypeMemberDeclaration2, annotationTypeMemberDeclaration); |
| recordNodes(methodName, annotationTypeMemberDeclaration); |
| annotationTypeMemberDeclaration2.resolveBinding(); |
| } |
| return annotationTypeMemberDeclaration2; |
| } |
| |
| private void convertAndSetReceiver(AbstractMethodDeclaration method, MethodDeclaration methodDecl) { |
| Receiver receiver = method.receiver; |
| if (receiver.qualifyingName != null) { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(receiver.qualifyingName.getName()[0])); |
| int start = receiver.qualifyingName.sourceStart; |
| int nameEnd = receiver.qualifyingName.sourceEnd; |
| name.setSourceRange(start, nameEnd - start + 1); |
| methodDecl.setReceiverQualifier(name); |
| if (this.resolveBindings) { |
| recordNodes(name, receiver); |
| } |
| } |
| Type type = convertType(receiver.type); |
| methodDecl.setReceiverType(type); |
| if (receiver.modifiers != 0) { |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| if (this.resolveBindings) { |
| recordNodes(type, receiver); |
| type.resolveBinding(); |
| } |
| } |
| |
| public SingleVariableDeclaration convert(org.eclipse.jdt.internal.compiler.ast.Argument argument) { |
| SingleVariableDeclaration variableDecl = new SingleVariableDeclaration(this.ast); |
| setModifiers(variableDecl, argument); |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(argument.name)); |
| if (argument instanceof Receiver) { |
| name.setFlags(name.getFlags() | ASTNode.MALFORMED); |
| } |
| int start = argument.sourceStart; |
| int nameEnd = argument.sourceEnd; |
| name.setSourceRange(start, nameEnd - start + 1); |
| variableDecl.setName(name); |
| final int typeSourceEnd = argument.type.sourceEnd; |
| TypeReference typeReference = argument.type; |
| final int extraDimensions = typeReference.extraDimensions(); |
| if (this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| setExtraAnnotatedDimensions(nameEnd + 1, typeSourceEnd, typeReference, |
| variableDecl.extraDimensions(), extraDimensions); |
| } else { |
| internalSetExtraDimensions(variableDecl, extraDimensions); |
| } |
| final boolean isVarArgs = argument.isVarArgs(); |
| if (isVarArgs && extraDimensions == 0) { |
| // remove the ellipsis from the type source end |
| argument.type.sourceEnd = retrieveEllipsisStartPosition(argument.type.sourceStart, typeSourceEnd); |
| } |
| Type type = convertType(argument.type); |
| int typeEnd = type.getStartPosition() + type.getLength() - 1; |
| int rightEnd = Math.max(typeEnd, argument.declarationSourceEnd); |
| /* |
| * There is extra work to do to set the proper type positions |
| * See PR http://bugs.eclipse.org/bugs/show_bug.cgi?id=23284 |
| */ |
| if (isVarArgs) { |
| Dimension lastDimension = null; |
| if (this.ast.apiLevel() >= AST.JLS8_INTERNAL) { |
| if (type.isArrayType()) { // should always be true |
| List dimensions = ((ArrayType) type).dimensions(); |
| if (!dimensions.isEmpty()) { |
| lastDimension = (Dimension) dimensions.get(dimensions.size() - 1); |
| } |
| } |
| } |
| setTypeForSingleVariableDeclaration(variableDecl, type, extraDimensions + 1); |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=391898 |
| if (this.ast.apiLevel() >= AST.JLS8_INTERNAL) { |
| if (lastDimension != null) { // should always be true |
| List annotations = lastDimension.annotations(); |
| Iterator iter = annotations.iterator(); |
| while (iter.hasNext()) { |
| Annotation annotation = (Annotation) iter.next(); |
| annotation.setParent(null, null); |
| variableDecl.varargsAnnotations().add(annotation); |
| } |
| } |
| } |
| if (extraDimensions != 0) { |
| variableDecl.setFlags(variableDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| } else { |
| setTypeForSingleVariableDeclaration(variableDecl, type, extraDimensions); |
| } |
| variableDecl.setSourceRange(argument.declarationSourceStart, rightEnd - argument.declarationSourceStart + 1); |
| |
| if (isVarArgs) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| variableDecl.setFlags(variableDecl.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| variableDecl.setVarargs(true); |
| } |
| } |
| if (this.resolveBindings) { |
| recordNodes(name, argument); |
| recordNodes(variableDecl, argument); |
| variableDecl.resolveBinding(); |
| } |
| return variableDecl; |
| } |
| |
| |
| public Annotation convert(org.eclipse.jdt.internal.compiler.ast.Annotation annotation) { |
| if (annotation instanceof org.eclipse.jdt.internal.compiler.ast.SingleMemberAnnotation) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.SingleMemberAnnotation) annotation); |
| } else if (annotation instanceof org.eclipse.jdt.internal.compiler.ast.MarkerAnnotation) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.MarkerAnnotation) annotation); |
| } else { |
| return convert((org.eclipse.jdt.internal.compiler.ast.NormalAnnotation) annotation); |
| } |
| } |
| |
| public ArrayCreation convert(org.eclipse.jdt.internal.compiler.ast.ArrayAllocationExpression expression) { |
| ArrayCreation arrayCreation = new ArrayCreation(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(arrayCreation, expression); |
| } |
| arrayCreation.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| org.eclipse.jdt.internal.compiler.ast.Expression[] dimensions = expression.dimensions; |
| |
| int dimensionsLength = dimensions.length; |
| for (int i = 0; i < dimensionsLength; i++) { |
| if (dimensions[i] != null) { |
| Expression dimension = convert(dimensions[i]); |
| if (this.resolveBindings) { |
| recordNodes(dimension, dimensions[i]); |
| } |
| arrayCreation.dimensions().add(dimension); |
| } |
| } |
| Type type = convertType(expression.type); |
| if (this.resolveBindings) { |
| recordNodes(type, expression.type); |
| } |
| ArrayType arrayType = null; |
| if (type.isArrayType()) { |
| arrayType = (ArrayType) type; |
| if (expression.annotationsOnDimensions != null) { |
| if (this.ast.apiLevel() < AST.JLS8_INTERNAL) { |
| arrayType.setFlags(arrayType.getFlags() | ASTNode.MALFORMED); |
| } else { |
| setTypeAnnotationsAndSourceRangeOnArray(arrayType, expression.annotationsOnDimensions); |
| } |
| } |
| } else { |
| arrayType = convertToArray(type, type.getStartPosition(), -1, dimensionsLength, expression.annotationsOnDimensions); |
| } |
| arrayCreation.setType(arrayType); |
| if (this.resolveBindings) { |
| completeRecord(arrayType, expression); |
| } |
| if (expression.initializer != null) { |
| arrayCreation.setInitializer(convert(expression.initializer)); |
| } |
| return arrayCreation; |
| } |
| |
| public ArrayInitializer convert(org.eclipse.jdt.internal.compiler.ast.ArrayInitializer expression) { |
| ArrayInitializer arrayInitializer = new ArrayInitializer(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(arrayInitializer, expression); |
| } |
| arrayInitializer.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| org.eclipse.jdt.internal.compiler.ast.Expression[] expressions = expression.expressions; |
| if (expressions != null) { |
| int length = expressions.length; |
| for (int i = 0; i < length; i++) { |
| Expression expr = convert(expressions[i]); |
| if (this.resolveBindings) { |
| recordNodes(expr, expressions[i]); |
| } |
| arrayInitializer.expressions().add(expr); |
| } |
| } |
| return arrayInitializer; |
| } |
| |
| public ArrayAccess convert(org.eclipse.jdt.internal.compiler.ast.ArrayReference reference) { |
| ArrayAccess arrayAccess = new ArrayAccess(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(arrayAccess, reference); |
| } |
| arrayAccess.setSourceRange(reference.sourceStart, reference.sourceEnd - reference.sourceStart + 1); |
| arrayAccess.setArray(convert(reference.receiver)); |
| arrayAccess.setIndex(convert(reference.position)); |
| return arrayAccess; |
| } |
| |
| public AssertStatement convert(org.eclipse.jdt.internal.compiler.ast.AssertStatement statement) { |
| AssertStatement assertStatement = new AssertStatement(this.ast); |
| final Expression assertExpression = convert(statement.assertExpression); |
| Expression searchingNode = assertExpression; |
| assertStatement.setExpression(assertExpression); |
| org.eclipse.jdt.internal.compiler.ast.Expression exceptionArgument = statement.exceptionArgument; |
| if (exceptionArgument != null) { |
| final Expression exceptionMessage = convert(exceptionArgument); |
| assertStatement.setMessage(exceptionMessage); |
| searchingNode = exceptionMessage; |
| } |
| int start = statement.sourceStart; |
| int sourceEnd = retrieveSemiColonPosition(searchingNode); |
| if (sourceEnd == -1) { |
| sourceEnd = searchingNode.getStartPosition() + searchingNode.getLength() - 1; |
| assertStatement.setSourceRange(start, sourceEnd - start + 1); |
| } else { |
| assertStatement.setSourceRange(start, sourceEnd - start + 1); |
| } |
| return assertStatement; |
| } |
| |
| public Assignment convert(org.eclipse.jdt.internal.compiler.ast.Assignment expression) { |
| Assignment assignment = new Assignment(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(assignment, expression); |
| } |
| Expression lhs = convert(expression.lhs); |
| assignment.setLeftHandSide(lhs); |
| assignment.setOperator(Assignment.Operator.ASSIGN); |
| Expression rightHandSide = convert(expression.expression); |
| assignment.setRightHandSide(rightHandSide); |
| int start = lhs.getStartPosition(); |
| int end = rightHandSide.getStartPosition() + rightHandSide.getLength() - 1; |
| assignment.setSourceRange(start, end - start + 1); |
| return assignment; |
| } |
| |
| /* |
| * Internal use only |
| * Used to convert class body declarations |
| */ |
| public TypeDeclaration convert(org.eclipse.jdt.internal.compiler.ast.ASTNode[] nodes) { |
| final TypeDeclaration typeDecl = new TypeDeclaration(this.ast); |
| ASTNode oldReferenceContext = this.referenceContext; |
| this.referenceContext = typeDecl; |
| typeDecl.setInterface(false); |
| int nodesLength = nodes.length; |
| for (int i = 0; i < nodesLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.ASTNode node = nodes[i]; |
| if (node instanceof org.eclipse.jdt.internal.compiler.ast.Initializer) { |
| org.eclipse.jdt.internal.compiler.ast.Initializer oldInitializer = (org.eclipse.jdt.internal.compiler.ast.Initializer) node; |
| Initializer initializer = new Initializer(this.ast); |
| initializer.setBody(convert(oldInitializer.block)); |
| setModifiers(initializer, oldInitializer); |
| initializer.setSourceRange(oldInitializer.declarationSourceStart, oldInitializer.sourceEnd - oldInitializer.declarationSourceStart + 1); |
| // setJavaDocComment(initializer); |
| // initializer.setJavadoc(convert(oldInitializer.javadoc)); |
| convert(oldInitializer.javadoc, initializer); |
| typeDecl.bodyDeclarations().add(initializer); |
| } else if (node instanceof org.eclipse.jdt.internal.compiler.ast.FieldDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.FieldDeclaration fieldDeclaration = (org.eclipse.jdt.internal.compiler.ast.FieldDeclaration) node; |
| if (i > 0 |
| && (nodes[i - 1] instanceof org.eclipse.jdt.internal.compiler.ast.FieldDeclaration) |
| && ((org.eclipse.jdt.internal.compiler.ast.FieldDeclaration)nodes[i - 1]).declarationSourceStart == fieldDeclaration.declarationSourceStart) { |
| // we have a multiple field declaration |
| // We retrieve the existing fieldDeclaration to add the new VariableDeclarationFragment |
| FieldDeclaration currentFieldDeclaration = (FieldDeclaration) typeDecl.bodyDeclarations().get(typeDecl.bodyDeclarations().size() - 1); |
| currentFieldDeclaration.fragments().add(convertToVariableDeclarationFragment(fieldDeclaration)); |
| } else { |
| // we can create a new FieldDeclaration |
| typeDecl.bodyDeclarations().add(convertToFieldDeclaration(fieldDeclaration)); |
| } |
| } else if(node instanceof org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration) { |
| AbstractMethodDeclaration nextMethodDeclaration = (AbstractMethodDeclaration) node; |
| if (!nextMethodDeclaration.isDefaultConstructor() && !nextMethodDeclaration.isClinit()) { |
| typeDecl.bodyDeclarations().add(convert(false, nextMethodDeclaration)); |
| } |
| } else if(node instanceof org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration nextMemberDeclaration = (org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) node; |
| ASTNode nextMemberDeclarationNode = convert(nextMemberDeclaration); |
| if (nextMemberDeclarationNode == null) { |
| typeDecl.setFlags(typeDecl.getFlags() | ASTNode.MALFORMED); |
| } else { |
| typeDecl.bodyDeclarations().add(nextMemberDeclarationNode); |
| } |
| } |
| } |
| this.referenceContext = oldReferenceContext; |
| return typeDecl; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.BinaryExpression expression) { |
| InfixExpression infixExpression = new InfixExpression(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| |
| int expressionOperatorID = (expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT; |
| infixExpression.setOperator(getOperatorFor(expressionOperatorID)); |
| |
| if (expression.left instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((expression.left.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) { |
| // create an extended string literal equivalent => use the extended operands list |
| infixExpression.extendedOperands().add(convert(expression.right)); |
| org.eclipse.jdt.internal.compiler.ast.Expression leftOperand = expression.left; |
| org.eclipse.jdt.internal.compiler.ast.Expression rightOperand = null; |
| do { |
| rightOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).right; |
| if ((((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID |
| && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) |
| || ((rightOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID) |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0))) { |
| List extendedOperands = infixExpression.extendedOperands(); |
| InfixExpression temp = new InfixExpression(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| Expression leftSide = convert(leftOperand); |
| temp.setLeftOperand(leftSide); |
| temp.setSourceRange(leftSide.getStartPosition(), leftSide.getLength()); |
| int size = extendedOperands.size(); |
| for (int i = 0; i < size - 1; i++) { |
| Expression expr = temp; |
| temp = new InfixExpression(this.ast); |
| |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setLeftOperand(expr); |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| temp.setSourceRange(expr.getStartPosition(), expr.getLength()); |
| } |
| infixExpression = temp; |
| for (int i = 0; i < size; i++) { |
| Expression extendedOperand = (Expression) extendedOperands.remove(size - 1 - i); |
| temp.setRightOperand(extendedOperand); |
| int startPosition = temp.getLeftOperand().getStartPosition(); |
| temp.setSourceRange(startPosition, extendedOperand.getStartPosition() + extendedOperand.getLength() - startPosition); |
| if (temp.getLeftOperand().getNodeType() == ASTNode.INFIX_EXPRESSION) { |
| temp = (InfixExpression) temp.getLeftOperand(); |
| } |
| } |
| setInfixSourcePositions(infixExpression, infixExpression.getLeftOperand().getStartPosition()); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| return infixExpression; |
| } |
| infixExpression.extendedOperands().add(0, convert(rightOperand)); |
| leftOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).left; |
| } while (leftOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)); |
| Expression leftExpression = convert(leftOperand); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand((Expression)infixExpression.extendedOperands().remove(0)); |
| int startPosition = leftExpression.getStartPosition(); |
| setInfixSourcePositions(infixExpression, startPosition); |
| return infixExpression; |
| } else if (expression.left instanceof StringLiteralConcatenation |
| && ((expression.left.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0) |
| && (OperatorIds.PLUS == expressionOperatorID)) { |
| StringLiteralConcatenation literal = (StringLiteralConcatenation) expression.left; |
| final org.eclipse.jdt.internal.compiler.ast.Expression[] stringLiterals = literal.literals; |
| infixExpression.setLeftOperand(convert(stringLiterals[0])); |
| infixExpression.setRightOperand(convert(stringLiterals[1])); |
| for (int i = 2; i < literal.counter; i++) { |
| infixExpression.extendedOperands().add(convert(stringLiterals[i])); |
| } |
| infixExpression.extendedOperands().add(convert(expression.right)); |
| int startPosition = literal.sourceStart; |
| setInfixSourcePositions(infixExpression, startPosition); |
| return infixExpression; |
| } |
| Expression leftExpression = convert(expression.left); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand(convert(expression.right)); |
| int startPosition = leftExpression.getStartPosition(); |
| setInfixSourcePositions(infixExpression, startPosition); |
| return infixExpression; |
| } |
| |
| public Block convert(org.eclipse.jdt.internal.compiler.ast.Block statement) { |
| Block block = new Block(this.ast); |
| if (statement.sourceEnd > 0) { |
| block.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Statement[] statements = statement.statements; |
| if (statements != null) { |
| int statementsLength = statements.length; |
| for (int i = 0; i < statementsLength; i++) { |
| if (statements[i] instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| checkAndAddMultipleLocalDeclaration(statements, i, block.statements()); |
| } else { |
| Statement statement2 = convert(statements[i]); |
| if (statement2 != null) { |
| block.statements().add(statement2); |
| } |
| } |
| } |
| } |
| return block; |
| } |
| |
| public BreakStatement convert(org.eclipse.jdt.internal.compiler.ast.BreakStatement statement) { |
| BreakStatement breakStatement = new BreakStatement(this.ast); |
| breakStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| if (statement.label != null) { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(statement.label)); |
| retrieveIdentifierAndSetPositions(statement.sourceStart, statement.sourceEnd, name); |
| breakStatement.setLabel(name); |
| } |
| return breakStatement; |
| } |
| |
| |
| public SwitchCase convert(org.eclipse.jdt.internal.compiler.ast.CaseStatement statement) { |
| SwitchCase switchCase = new SwitchCase(this.ast); |
| org.eclipse.jdt.internal.compiler.ast.Expression constantExpression = statement.constantExpression; |
| if (constantExpression == null) { |
| switchCase.setExpression(null); |
| } else { |
| switchCase.setExpression(convert(constantExpression)); |
| } |
| switchCase.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| retrieveColonPosition(switchCase); |
| return switchCase; |
| } |
| |
| public CastExpression convert(org.eclipse.jdt.internal.compiler.ast.CastExpression expression) { |
| CastExpression castExpression = new CastExpression(this.ast); |
| castExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| TypeReference type = expression.type; |
| trimWhiteSpacesAndComments(type); |
| castExpression.setType(convertType(type)); |
| castExpression.setExpression(convert(expression.expression)); |
| if (this.resolveBindings) { |
| recordNodes(castExpression, expression); |
| } |
| return castExpression; |
| } |
| |
| public CharacterLiteral convert(org.eclipse.jdt.internal.compiler.ast.CharLiteral expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| CharacterLiteral literal = new CharacterLiteral(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.internalSetEscapedValue(new String(this.compilationUnitSource, sourceStart, length)); |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.ClassLiteralAccess expression) { |
| TypeLiteral typeLiteral = new TypeLiteral(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(typeLiteral, expression); |
| } |
| typeLiteral.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| typeLiteral.setType(convertType(expression.type)); |
| return typeLiteral; |
| } |
| |
| public CompilationUnit convert(org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration unit, char[] source) { |
| try { |
| if(unit.compilationResult.recoveryScannerData != null) { |
| RecoveryScanner recoveryScanner = new RecoveryScanner(this.scanner, unit.compilationResult.recoveryScannerData.removeUnused()); |
| this.scanner = recoveryScanner; |
| this.docParser.scanner = this.scanner; |
| } |
| this.compilationUnitSource = source; |
| this.compilationUnitSourceLength = source.length; |
| this.scanner.setSource(source, unit.compilationResult); |
| CompilationUnit compilationUnit = new CompilationUnit(this.ast); |
| compilationUnit.setStatementsRecoveryData(unit.compilationResult.recoveryScannerData); |
| |
| // Parse comments |
| int[][] comments = unit.comments; |
| if (comments != null) { |
| buildCommentsTable(compilationUnit, comments); |
| } |
| |
| // handle the package declaration immediately |
| // There is no node corresponding to the package declaration |
| if (this.resolveBindings) { |
| recordNodes(compilationUnit, unit); |
| } |
| if (unit.currentPackage != null) { |
| PackageDeclaration packageDeclaration = convertPackage(unit); |
| compilationUnit.setPackage(packageDeclaration); |
| } |
| org.eclipse.jdt.internal.compiler.ast.ImportReference[] imports = unit.imports; |
| if (imports != null) { |
| int importLength = imports.length; |
| for (int i = 0; i < importLength; i++) { |
| compilationUnit.imports().add(convertImport(imports[i])); |
| } |
| } |
| |
| org.eclipse.jdt.internal.compiler.ast.ModuleDeclaration mod = unit.moduleDeclaration; |
| if (mod != null) { |
| ASTNode declaration = convertToModuleDeclaration(mod); |
| if (declaration == null) { |
| compilationUnit.setFlags(compilationUnit.getFlags() | ASTNode.MALFORMED); |
| } else { |
| compilationUnit.setModule((ModuleDeclaration) declaration); |
| } |
| } else { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration[] types = unit.types; |
| if (types != null) { |
| int typesLength = types.length; |
| for (int i = 0; i < typesLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration declaration = types[i]; |
| if (CharOperation.equals(declaration.name, TypeConstants.PACKAGE_INFO_NAME)) { |
| continue; |
| } |
| ASTNode type = convert(declaration); |
| if (type == null) { |
| compilationUnit.setFlags(compilationUnit.getFlags() | ASTNode.MALFORMED); |
| } else { |
| if (type instanceof ModuleDeclaration) |
| compilationUnit.setModule((ModuleDeclaration) type); |
| else |
| compilationUnit.types().add(type); |
| } |
| } |
| } |
| } |
| compilationUnit.setSourceRange(unit.sourceStart, unit.sourceEnd - unit.sourceStart + 1); |
| |
| int problemLength = unit.compilationResult.problemCount; |
| if (problemLength != 0) { |
| CategorizedProblem[] resizedProblems = null; |
| final CategorizedProblem[] problems = unit.compilationResult.getProblems(); |
| final int realProblemLength=problems.length; |
| if (realProblemLength == problemLength) { |
| resizedProblems = problems; |
| } else { |
| System.arraycopy(problems, 0, (resizedProblems = new CategorizedProblem[realProblemLength]), 0, realProblemLength); |
| } |
| ASTSyntaxErrorPropagator syntaxErrorPropagator = new ASTSyntaxErrorPropagator(resizedProblems); |
| compilationUnit.accept(syntaxErrorPropagator); |
| ASTRecoveryPropagator recoveryPropagator = |
| new ASTRecoveryPropagator(resizedProblems, unit.compilationResult.recoveryScannerData); |
| compilationUnit.accept(recoveryPropagator); |
| compilationUnit.setProblems(resizedProblems); |
| } |
| if (this.resolveBindings) { |
| lookupForScopes(); |
| } |
| compilationUnit.initCommentMapper(this.scanner); |
| if (SourceRangeVerifier.DEBUG) { |
| String bugs = new SourceRangeVerifier().process(compilationUnit); |
| if (bugs != null) { |
| StringBuffer message = new StringBuffer("Bad AST node structure:"); //$NON-NLS-1$ |
| String lineDelimiter = Util.findLineSeparator(source); |
| if (lineDelimiter == null) lineDelimiter = System.getProperty("line.separator");//$NON-NLS-1$ |
| message.append(lineDelimiter); |
| message.append(bugs.replaceAll("\n", lineDelimiter)); //$NON-NLS-1$ |
| message.append(lineDelimiter); |
| message.append("----------------------------------- SOURCE BEGIN -------------------------------------"); //$NON-NLS-1$ |
| message.append(lineDelimiter); |
| message.append(source); |
| message.append(lineDelimiter); |
| message.append("----------------------------------- SOURCE END -------------------------------------"); //$NON-NLS-1$ |
| Util.log(new IllegalStateException("Bad AST node structure"), message.toString()); //$NON-NLS-1$ |
| if (SourceRangeVerifier.DEBUG_THROW) { |
| throw new IllegalStateException(message.toString()); |
| } |
| } |
| } |
| return compilationUnit; |
| } catch(IllegalArgumentException e) { |
| StringBuffer message = new StringBuffer("Exception occurred during compilation unit conversion:"); //$NON-NLS-1$ |
| String lineDelimiter = Util.findLineSeparator(source); |
| if (lineDelimiter == null) lineDelimiter = System.getProperty("line.separator");//$NON-NLS-1$ |
| message.append(lineDelimiter); |
| message.append("----------------------------------- SOURCE BEGIN -------------------------------------"); //$NON-NLS-1$ |
| message.append(lineDelimiter); |
| message.append(source); |
| message.append(lineDelimiter); |
| message.append("----------------------------------- SOURCE END -------------------------------------"); //$NON-NLS-1$ |
| Util.log(e, message.toString()); |
| throw e; |
| } |
| } |
| |
| public Assignment convert(org.eclipse.jdt.internal.compiler.ast.CompoundAssignment expression) { |
| Assignment assignment = new Assignment(this.ast); |
| Expression lhs = convert(expression.lhs); |
| assignment.setLeftHandSide(lhs); |
| int start = lhs.getStartPosition(); |
| assignment.setSourceRange(start, expression.sourceEnd - start + 1); |
| switch (expression.operator) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.PLUS : |
| assignment.setOperator(Assignment.Operator.PLUS_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MINUS : |
| assignment.setOperator(Assignment.Operator.MINUS_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MULTIPLY : |
| assignment.setOperator(Assignment.Operator.TIMES_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.DIVIDE : |
| assignment.setOperator(Assignment.Operator.DIVIDE_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.AND : |
| assignment.setOperator(Assignment.Operator.BIT_AND_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.OR : |
| assignment.setOperator(Assignment.Operator.BIT_OR_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.XOR : |
| assignment.setOperator(Assignment.Operator.BIT_XOR_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.REMAINDER : |
| assignment.setOperator(Assignment.Operator.REMAINDER_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.LEFT_SHIFT : |
| assignment.setOperator(Assignment.Operator.LEFT_SHIFT_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.RIGHT_SHIFT : |
| assignment.setOperator(Assignment.Operator.RIGHT_SHIFT_SIGNED_ASSIGN); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.UNSIGNED_RIGHT_SHIFT : |
| assignment.setOperator(Assignment.Operator.RIGHT_SHIFT_UNSIGNED_ASSIGN); |
| break; |
| } |
| assignment.setRightHandSide(convert(expression.expression)); |
| if (this.resolveBindings) { |
| recordNodes(assignment, expression); |
| } |
| return assignment; |
| } |
| |
| public ConditionalExpression convert(org.eclipse.jdt.internal.compiler.ast.ConditionalExpression expression) { |
| ConditionalExpression conditionalExpression = new ConditionalExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(conditionalExpression, expression); |
| } |
| conditionalExpression.setExpression(convert(expression.condition)); |
| conditionalExpression.setThenExpression(convert(expression.valueIfTrue)); |
| Expression elseExpression = convert(expression.valueIfFalse); |
| conditionalExpression.setElseExpression(elseExpression); |
| conditionalExpression.setSourceRange(expression.sourceStart, elseExpression.getStartPosition() + elseExpression.getLength() - expression.sourceStart); |
| return conditionalExpression; |
| } |
| |
| public ContinueStatement convert(org.eclipse.jdt.internal.compiler.ast.ContinueStatement statement) { |
| ContinueStatement continueStatement = new ContinueStatement(this.ast); |
| continueStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| if (statement.label != null) { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(statement.label)); |
| retrieveIdentifierAndSetPositions(statement.sourceStart, statement.sourceEnd, name); |
| continueStatement.setLabel(name); |
| } |
| return continueStatement; |
| } |
| |
| public DoStatement convert(org.eclipse.jdt.internal.compiler.ast.DoStatement statement) { |
| DoStatement doStatement = new DoStatement(this.ast); |
| doStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| doStatement.setExpression(convert(statement.condition)); |
| final Statement action = convert(statement.action); |
| if (action == null) return null; |
| doStatement.setBody(action); |
| return doStatement; |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.DoubleLiteral expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| public EmptyStatement convert(org.eclipse.jdt.internal.compiler.ast.EmptyStatement statement) { |
| EmptyStatement emptyStatement = new EmptyStatement(this.ast); |
| emptyStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| return emptyStatement; |
| } |
| |
| // field is an enum constant |
| public EnumConstantDeclaration convert(org.eclipse.jdt.internal.compiler.ast.FieldDeclaration enumConstant) { |
| checkCanceled(); |
| EnumConstantDeclaration enumConstantDeclaration = new EnumConstantDeclaration(this.ast); |
| final SimpleName typeName = new SimpleName(this.ast); |
| typeName.internalSetIdentifier(new String(enumConstant.name)); |
| typeName.setSourceRange(enumConstant.sourceStart, enumConstant.sourceEnd - enumConstant.sourceStart + 1); |
| enumConstantDeclaration.setName(typeName); |
| int declarationSourceStart = enumConstant.declarationSourceStart; |
| int declarationSourceEnd = enumConstant.declarationSourceEnd; |
| final org.eclipse.jdt.internal.compiler.ast.Expression initialization = enumConstant.initialization; |
| if (initialization != null) { |
| if (initialization instanceof QualifiedAllocationExpression) { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration anonymousType = ((QualifiedAllocationExpression) initialization).anonymousType; |
| if (anonymousType != null) { |
| AnonymousClassDeclaration anonymousClassDeclaration = new AnonymousClassDeclaration(this.ast); |
| int start = retrieveStartBlockPosition(anonymousType.sourceEnd, anonymousType.bodyEnd); |
| int end = retrieveRightBrace(anonymousType.bodyEnd +1, declarationSourceEnd); |
| if (end == -1) end = anonymousType.bodyEnd; |
| anonymousClassDeclaration.setSourceRange(start, end - start + 1); |
| enumConstantDeclaration.setAnonymousClassDeclaration(anonymousClassDeclaration); |
| buildBodyDeclarations(anonymousType, anonymousClassDeclaration); |
| if (this.resolveBindings) { |
| recordNodes(anonymousClassDeclaration, anonymousType); |
| anonymousClassDeclaration.resolveBinding(); |
| } |
| enumConstantDeclaration.setSourceRange(declarationSourceStart, end - declarationSourceStart + 1); |
| } |
| } else { |
| enumConstantDeclaration.setSourceRange(declarationSourceStart, declarationSourceEnd - declarationSourceStart + 1); |
| } |
| final org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = ((org.eclipse.jdt.internal.compiler.ast.AllocationExpression) initialization).arguments; |
| if (arguments != null) { |
| for (int i = 0, max = arguments.length; i < max; i++) { |
| enumConstantDeclaration.arguments().add(convert(arguments[i])); |
| } |
| } |
| } else { |
| enumConstantDeclaration.setSourceRange(declarationSourceStart, declarationSourceEnd - declarationSourceStart + 1); |
| } |
| setModifiers(enumConstantDeclaration, enumConstant); |
| if (this.resolveBindings) { |
| recordNodes(enumConstantDeclaration, enumConstant); |
| recordNodes(typeName, enumConstant); |
| enumConstantDeclaration.resolveVariable(); |
| } |
| convert(enumConstant.javadoc, enumConstantDeclaration); |
| return enumConstantDeclaration; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.EqualExpression expression) { |
| InfixExpression infixExpression = new InfixExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(infixExpression, expression); |
| } |
| Expression leftExpression = convert(expression.left); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand(convert(expression.right)); |
| int startPosition = leftExpression.getStartPosition(); |
| setInfixSourcePositions(infixExpression, startPosition); |
| switch ((expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.EQUAL_EQUAL : |
| infixExpression.setOperator(InfixExpression.Operator.EQUALS); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.NOT_EQUAL : |
| infixExpression.setOperator(InfixExpression.Operator.NOT_EQUALS); |
| } |
| return infixExpression; |
| |
| } |
| |
| public Statement convert(org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall statement) { |
| Statement newStatement; |
| int sourceStart = statement.sourceStart; |
| if (statement.isSuperAccess() || statement.isSuper()) { |
| SuperConstructorInvocation superConstructorInvocation = new SuperConstructorInvocation(this.ast); |
| if (statement.qualification != null) { |
| superConstructorInvocation.setExpression(convert(statement.qualification)); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = statement.arguments; |
| if (arguments != null) { |
| int length = arguments.length; |
| for (int i = 0; i < length; i++) { |
| superConstructorInvocation.arguments().add(convert(arguments[i])); |
| } |
| } |
| if (statement.typeArguments != null) { |
| if (sourceStart > statement.typeArgumentsSourceStart) { |
| sourceStart = statement.typeArgumentsSourceStart; |
| } |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| superConstructorInvocation.setFlags(superConstructorInvocation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = statement.typeArguments.length; i < max; i++) { |
| superConstructorInvocation.typeArguments().add(convertType(statement.typeArguments[i])); |
| } |
| break; |
| } |
| } |
| newStatement = superConstructorInvocation; |
| } else { |
| ConstructorInvocation constructorInvocation = new ConstructorInvocation(this.ast); |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = statement.arguments; |
| if (arguments != null) { |
| int length = arguments.length; |
| for (int i = 0; i < length; i++) { |
| constructorInvocation.arguments().add(convert(arguments[i])); |
| } |
| } |
| if (statement.typeArguments != null) { |
| if (sourceStart > statement.typeArgumentsSourceStart) { |
| sourceStart = statement.typeArgumentsSourceStart; |
| } |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| constructorInvocation.setFlags(constructorInvocation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = statement.typeArguments.length; i < max; i++) { |
| constructorInvocation.typeArguments().add(convertType(statement.typeArguments[i])); |
| } |
| break; |
| } |
| } |
| if (statement.qualification != null) { |
| // this is an error |
| constructorInvocation.setFlags(constructorInvocation.getFlags() | ASTNode.MALFORMED); |
| } |
| newStatement = constructorInvocation; |
| } |
| newStatement.setSourceRange(sourceStart, statement.sourceEnd - sourceStart + 1); |
| if (this.resolveBindings) { |
| recordNodes(newStatement, statement); |
| } |
| return newStatement; |
| } |
| |
| private ModulePackageAccess getPackageVisibilityStatement( |
| org.eclipse.jdt.internal.compiler.ast.PackageVisibilityStatement pvsStmt, ModulePackageAccess stmt) { |
| int sourceEnd = pvsStmt.declarationSourceEnd; |
| if (pvsStmt.declarationEnd > sourceEnd) sourceEnd = pvsStmt.declarationEnd; // TODO: working around a compiler issue |
| Name name = getImportName(pvsStmt.pkgRef); |
| stmt.setName(name); |
| if (this.resolveBindings) { |
| recordNodes(name, pvsStmt.pkgRef); |
| } |
| int tmp = sourceEnd; |
| if (pvsStmt.targets != null && pvsStmt.targets.length > 0) { |
| List<Name> modules = stmt.modules(); |
| for (ModuleReference moduleRef : pvsStmt.getTargetedModules()) { |
| Name target = getName(moduleRef, CharOperation.splitOn('.', moduleRef.moduleName), moduleRef.sourcePositions); |
| modules.add(target); |
| if (tmp < moduleRef.sourceEnd) tmp = moduleRef.sourceEnd; |
| if (this.resolveBindings) { |
| this.recordNodes(target, moduleRef); |
| } |
| |
| } |
| } |
| if (tmp > sourceEnd) sourceEnd = tmp; |
| stmt.setSourceRange(pvsStmt.declarationSourceStart, sourceEnd - pvsStmt.declarationSourceStart + 1); |
| return stmt; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.Expression expression) { |
| if ((expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) != 0) { |
| return convertToParenthesizedExpression(expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.Annotation) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.Annotation) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.CastExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.CastExpression) expression); |
| } |
| // switch between all types of expression |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ArrayAllocationExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ArrayAllocationExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedAllocationExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.QualifiedAllocationExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.AllocationExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.AllocationExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ArrayInitializer) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ArrayInitializer) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.PrefixExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.PrefixExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.PostfixExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.PostfixExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.CompoundAssignment) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.CompoundAssignment) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.Assignment) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.Assignment) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ClassLiteralAccess) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ClassLiteralAccess) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.FalseLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.FalseLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.TrueLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.TrueLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.NullLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.NullLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.CharLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.CharLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.DoubleLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.DoubleLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.FloatLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.FloatLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.IntLiteralMinValue) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.IntLiteralMinValue) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.IntLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.IntLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.LongLiteralMinValue) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.LongLiteralMinValue) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.LongLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.LongLiteral) expression); |
| } |
| if (expression instanceof StringLiteralConcatenation) { |
| return convert((StringLiteralConcatenation) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ExtendedStringLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ExtendedStringLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.StringLiteral) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.StringLiteral) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.AND_AND_Expression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.AND_AND_Expression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.OR_OR_Expression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.OR_OR_Expression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.EqualExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.EqualExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.InstanceOfExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.InstanceOfExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.UnaryExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.UnaryExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ConditionalExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ConditionalExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.MessageSend) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.MessageSend) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.Reference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.Reference) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.TypeReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.TypeReference) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.LambdaExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.LambdaExpression) expression); |
| } |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) expression); |
| } |
| return null; |
| } |
| |
| public StringLiteral convert(org.eclipse.jdt.internal.compiler.ast.ExtendedStringLiteral expression) { |
| expression.computeConstant(); |
| StringLiteral literal = new StringLiteral(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setLiteralValue(expression.constant.stringValue()); |
| literal.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return literal; |
| } |
| |
| public BooleanLiteral convert(org.eclipse.jdt.internal.compiler.ast.FalseLiteral expression) { |
| final BooleanLiteral literal = new BooleanLiteral(this.ast); |
| literal.setBooleanValue(false); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return literal; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.FieldReference reference) { |
| if (reference.receiver.isSuper()) { |
| final SuperFieldAccess superFieldAccess = new SuperFieldAccess(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(superFieldAccess, reference); |
| } |
| if (reference.receiver instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) { |
| Name qualifier = convert((org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) reference.receiver); |
| superFieldAccess.setQualifier(qualifier); |
| if (this.resolveBindings) { |
| recordNodes(qualifier, reference.receiver); |
| } |
| } |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(reference.token)); |
| int sourceStart = (int)(reference.nameSourcePosition>>>32); |
| int length = (int)(reference.nameSourcePosition & 0xFFFFFFFF) - sourceStart + 1; |
| simpleName.setSourceRange(sourceStart, length); |
| superFieldAccess.setName(simpleName); |
| if (this.resolveBindings) { |
| recordNodes(simpleName, reference); |
| } |
| superFieldAccess.setSourceRange(reference.receiver.sourceStart, reference.sourceEnd - reference.receiver.sourceStart + 1); |
| return superFieldAccess; |
| } else { |
| final FieldAccess fieldAccess = new FieldAccess(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(fieldAccess, reference); |
| } |
| Expression receiver = convert(reference.receiver); |
| fieldAccess.setExpression(receiver); |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(reference.token)); |
| int sourceStart = (int)(reference.nameSourcePosition>>>32); |
| int length = (int)(reference.nameSourcePosition & 0xFFFFFFFF) - sourceStart + 1; |
| simpleName.setSourceRange(sourceStart, length); |
| fieldAccess.setName(simpleName); |
| if (this.resolveBindings) { |
| recordNodes(simpleName, reference); |
| } |
| fieldAccess.setSourceRange(receiver.getStartPosition(), reference.sourceEnd - receiver.getStartPosition() + 1); |
| return fieldAccess; |
| } |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.FloatLiteral expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| public Statement convert(ForeachStatement statement) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| return createFakeEmptyStatement(statement); |
| default : |
| EnhancedForStatement enhancedForStatement = new EnhancedForStatement(this.ast); |
| enhancedForStatement.setParameter(convertToSingleVariableDeclaration(statement.elementVariable)); |
| org.eclipse.jdt.internal.compiler.ast.Expression collection = statement.collection; |
| if (collection == null) return null; |
| enhancedForStatement.setExpression(convert(collection)); |
| final Statement action = convert(statement.action); |
| if (action == null) return null; |
| enhancedForStatement.setBody(action); |
| int start = statement.sourceStart; |
| int end = statement.sourceEnd; |
| enhancedForStatement.setSourceRange(start, end - start + 1); |
| return enhancedForStatement; |
| } |
| } |
| |
| public ForStatement convert(org.eclipse.jdt.internal.compiler.ast.ForStatement statement) { |
| ForStatement forStatement = new ForStatement(this.ast); |
| forStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| org.eclipse.jdt.internal.compiler.ast.Statement[] initializations = statement.initializations; |
| if (initializations != null) { |
| // we know that we have at least one initialization |
| if (initializations[0] instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.LocalDeclaration initialization = (org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) initializations[0]; |
| VariableDeclarationExpression variableDeclarationExpression = convertToVariableDeclarationExpression(initialization); |
| int initializationsLength = initializations.length; |
| for (int i = 1; i < initializationsLength; i++) { |
| initialization = (org.eclipse.jdt.internal.compiler.ast.LocalDeclaration)initializations[i]; |
| variableDeclarationExpression.fragments().add(convertToVariableDeclarationFragment(initialization)); |
| } |
| if (initializationsLength != 1) { |
| int start = variableDeclarationExpression.getStartPosition(); |
| int end = ((org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) initializations[initializationsLength - 1]).declarationSourceEnd; |
| variableDeclarationExpression.setSourceRange(start, end - start + 1); |
| } |
| forStatement.initializers().add(variableDeclarationExpression); |
| } else { |
| int initializationsLength = initializations.length; |
| for (int i = 0; i < initializationsLength; i++) { |
| Expression initializer = convertToExpression(initializations[i]); |
| if (initializer != null) { |
| forStatement.initializers().add(initializer); |
| } else { |
| forStatement.setFlags(forStatement.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| } |
| } |
| if (statement.condition != null) { |
| forStatement.setExpression(convert(statement.condition)); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Statement[] increments = statement.increments; |
| if (increments != null) { |
| int incrementsLength = increments.length; |
| for (int i = 0; i < incrementsLength; i++) { |
| forStatement.updaters().add(convertToExpression(increments[i])); |
| } |
| } |
| final Statement action = convert(statement.action); |
| if (action == null) return null; |
| forStatement.setBody(action); |
| return forStatement; |
| } |
| |
| public IfStatement convert(org.eclipse.jdt.internal.compiler.ast.IfStatement statement) { |
| IfStatement ifStatement = new IfStatement(this.ast); |
| ifStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| ifStatement.setExpression(convert(statement.condition)); |
| final Statement thenStatement = convert(statement.thenStatement); |
| if (thenStatement == null) return null; |
| ifStatement.setThenStatement(thenStatement); |
| org.eclipse.jdt.internal.compiler.ast.Statement statement2 = statement.elseStatement; |
| if (statement2 != null) { |
| final Statement elseStatement = convert(statement2); |
| if (elseStatement != null) { |
| ifStatement.setElseStatement(elseStatement); |
| } |
| } |
| return ifStatement; |
| } |
| |
| public InstanceofExpression convert(org.eclipse.jdt.internal.compiler.ast.InstanceOfExpression expression) { |
| InstanceofExpression instanceOfExpression = new InstanceofExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(instanceOfExpression, expression); |
| } |
| Expression leftExpression = convert(expression.expression); |
| instanceOfExpression.setLeftOperand(leftExpression); |
| final Type convertType = convertType(expression.type); |
| instanceOfExpression.setRightOperand(convertType); |
| int startPosition = leftExpression.getStartPosition(); |
| int sourceEnd = convertType.getStartPosition() + convertType.getLength() - 1; |
| instanceOfExpression.setSourceRange(startPosition, sourceEnd - startPosition + 1); |
| return instanceOfExpression; |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.IntLiteral expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| final NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.IntLiteralMinValue expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| interface IGetJavaDoc { |
| Javadoc getJavaDoc(); |
| } |
| interface ISetJavaDoc { |
| void setJavadoc(Javadoc javadoc); |
| } |
| public void convert(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc, IGetJavaDoc getJ, ISetJavaDoc setJ) { |
| if (getJ.getJavaDoc() == null) { |
| Javadoc docComment = convert(javadoc); |
| if (docComment != null) |
| setJ.setJavadoc(docComment); |
| } |
| } |
| private Javadoc convert(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc) { |
| Javadoc docComment = null; |
| if (javadoc != null) { |
| if (this.commentMapper == null || !this.commentMapper.hasSameTable(this.commentsTable)) { |
| this.commentMapper = new DefaultCommentMapper(this.commentsTable); |
| } |
| Comment comment = this.commentMapper.getComment(javadoc.sourceStart); |
| if (comment != null && comment.isDocComment() && comment.getParent() == null) { |
| docComment = (Javadoc) comment; |
| if (this.resolveBindings) { |
| recordNodes(docComment, javadoc); |
| // resolve member and method references binding |
| Iterator tags = docComment.tags().listIterator(); |
| while (tags.hasNext()) { |
| recordNodes(javadoc, (TagElement) tags.next()); |
| } |
| } |
| } |
| } |
| return docComment; |
| } |
| public void convert(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc, BodyDeclaration bodyDeclaration) { |
| convert(javadoc, bodyDeclaration::getJavadoc, bodyDeclaration::setJavadoc); |
| } |
| public void convert(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc, ModuleDeclaration moduleDeclaration) { |
| convert(javadoc, moduleDeclaration::getJavadoc, moduleDeclaration::setJavadoc); |
| } |
| |
| public void convert(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc, PackageDeclaration packageDeclaration) { |
| if (this.ast.apiLevel == AST.JLS2_INTERNAL) return; |
| convert(javadoc, packageDeclaration::getJavadoc, packageDeclaration::setJavadoc); |
| } |
| |
| public LabeledStatement convert(org.eclipse.jdt.internal.compiler.ast.LabeledStatement statement) { |
| LabeledStatement labeledStatement = new LabeledStatement(this.ast); |
| final int sourceStart = statement.sourceStart; |
| labeledStatement.setSourceRange(sourceStart, statement.sourceEnd - sourceStart + 1); |
| Statement body = convert(statement.statement); |
| if (body == null) return null; |
| labeledStatement.setBody(body); |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(statement.label)); |
| name.setSourceRange(sourceStart, statement.labelEnd - sourceStart + 1); |
| labeledStatement.setLabel(name); |
| return labeledStatement; |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.LongLiteral expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| final NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| public NumberLiteral convert(org.eclipse.jdt.internal.compiler.ast.LongLiteralMinValue expression) { |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| final NumberLiteral literal = new NumberLiteral(this.ast); |
| literal.internalSetToken(new String(this.compilationUnitSource, sourceStart, length)); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(sourceStart, length); |
| removeLeadingAndTrailingCommentsFromLiteral(literal); |
| return literal; |
| } |
| |
| public Expression convert(MessageSend expression) { |
| // will return a MethodInvocation or a SuperMethodInvocation or |
| Expression expr; |
| int sourceStart = expression.sourceStart; |
| if (expression.isSuperAccess()) { |
| // returns a SuperMethodInvocation |
| final SuperMethodInvocation superMethodInvocation = new SuperMethodInvocation(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(superMethodInvocation, expression); |
| } |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(expression.selector)); |
| int nameSourceStart = (int) (expression.nameSourcePosition >>> 32); |
| int nameSourceLength = ((int) expression.nameSourcePosition) - nameSourceStart + 1; |
| name.setSourceRange(nameSourceStart, nameSourceLength); |
| if (this.resolveBindings) { |
| recordNodes(name, expression); |
| } |
| superMethodInvocation.setName(name); |
| // expression.receiver is either a QualifiedSuperReference or a SuperReference |
| // so the casting cannot fail |
| if (expression.receiver instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) { |
| Name qualifier = convert((org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) expression.receiver); |
| superMethodInvocation.setQualifier(qualifier); |
| if (this.resolveBindings) { |
| recordNodes(qualifier, expression.receiver); |
| } |
| if (qualifier != null) { |
| sourceStart = qualifier.getStartPosition(); |
| } |
| } |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = expression.arguments; |
| if (arguments != null) { |
| int argumentsLength = arguments.length; |
| for (int i = 0; i < argumentsLength; i++) { |
| Expression expri = convert(arguments[i]); |
| if (this.resolveBindings) { |
| recordNodes(expri, arguments[i]); |
| } |
| superMethodInvocation.arguments().add(expri); |
| } |
| } |
| final TypeReference[] typeArguments = expression.typeArguments; |
| if (typeArguments != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| superMethodInvocation.setFlags(superMethodInvocation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = typeArguments.length; i < max; i++) { |
| superMethodInvocation.typeArguments().add(convertType(typeArguments[i])); |
| } |
| break; |
| } |
| } |
| expr = superMethodInvocation; |
| } else { |
| // returns a MethodInvocation |
| final MethodInvocation methodInvocation = new MethodInvocation(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(methodInvocation, expression); |
| } |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(expression.selector)); |
| int nameSourceStart = (int) (expression.nameSourcePosition >>> 32); |
| int nameSourceLength = ((int) expression.nameSourcePosition) - nameSourceStart + 1; |
| name.setSourceRange(nameSourceStart, nameSourceLength); |
| methodInvocation.setName(name); |
| if (this.resolveBindings) { |
| recordNodes(name, expression); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = expression.arguments; |
| if (arguments != null) { |
| int argumentsLength = arguments.length; |
| for (int i = 0; i < argumentsLength; i++) { |
| Expression expri = convert(arguments[i]); |
| if (this.resolveBindings) { |
| recordNodes(expri, arguments[i]); |
| } |
| methodInvocation.arguments().add(expri); |
| } |
| } |
| Expression qualifier = null; |
| org.eclipse.jdt.internal.compiler.ast.Expression receiver = expression.receiver; |
| if (receiver instanceof MessageSend) { |
| if ((receiver.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) != 0) { |
| qualifier = convertToParenthesizedExpression(receiver); |
| } else { |
| qualifier = convert((MessageSend) receiver); |
| } |
| } else { |
| qualifier = convert(receiver); |
| } |
| if (qualifier instanceof Name && this.resolveBindings) { |
| recordNodes(qualifier, receiver); |
| } |
| methodInvocation.setExpression(qualifier); |
| if (qualifier != null) { |
| sourceStart = qualifier.getStartPosition(); |
| } |
| final TypeReference[] typeArguments = expression.typeArguments; |
| if (typeArguments != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodInvocation.setFlags(methodInvocation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = typeArguments.length; i < max; i++) { |
| methodInvocation.typeArguments().add(convertType(typeArguments[i])); |
| } |
| break; |
| } |
| } |
| expr = methodInvocation; |
| } |
| expr.setSourceRange(sourceStart, expression.sourceEnd - sourceStart + 1); |
| return expr; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.LambdaExpression lambda) { |
| if (this.ast.apiLevel < AST.JLS8_INTERNAL) { |
| return createFakeNullLiteral(lambda); |
| } |
| final LambdaExpression lambdaExpression = new LambdaExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(lambdaExpression, lambda); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Argument[] arguments = lambda.arguments(); |
| if (arguments != null) { |
| int argumentsLength = arguments.length; |
| for (int i = 0; i < argumentsLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.Argument argument = arguments[i]; |
| if (argument.type == null) { |
| VariableDeclarationFragment variableDeclarationFragment = new VariableDeclarationFragment(this.ast); |
| SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(argument.name)); |
| int start = argument.sourceStart; |
| int end = argument.sourceEnd; |
| simpleName.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(simpleName, argument); |
| recordNodes(variableDeclarationFragment, argument); |
| variableDeclarationFragment.resolveBinding(); |
| } |
| variableDeclarationFragment.setName(simpleName); |
| variableDeclarationFragment.setSourceRange(start, end - start + 1); |
| lambdaExpression.parameters().add(variableDeclarationFragment); |
| } else { |
| SingleVariableDeclaration singleVariableDeclaration = convert(argument); |
| lambdaExpression.parameters().add(singleVariableDeclaration); |
| } |
| } |
| } |
| final org.eclipse.jdt.internal.compiler.ast.Statement body = lambda.body(); |
| if (body instanceof org.eclipse.jdt.internal.compiler.ast.Expression) { |
| lambdaExpression.setBody(convert((org.eclipse.jdt.internal.compiler.ast.Expression) body)); |
| } else { |
| lambdaExpression.setBody(convert((org.eclipse.jdt.internal.compiler.ast.Block) body)); |
| } |
| int sourceStart = lambda.sourceStart; |
| lambdaExpression.setSourceRange(sourceStart, lambda.sourceEnd - sourceStart + 1); |
| lambdaExpression.setParentheses(lambda.hasParentheses); |
| return lambdaExpression; |
| } |
| |
| public MarkerAnnotation convert(org.eclipse.jdt.internal.compiler.ast.MarkerAnnotation annotation) { |
| final MarkerAnnotation markerAnnotation = new MarkerAnnotation(this.ast); |
| setTypeNameForAnnotation(annotation, markerAnnotation); |
| int start = annotation.sourceStart; |
| int end = annotation.declarationSourceEnd; |
| markerAnnotation.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(markerAnnotation, annotation); |
| markerAnnotation.resolveAnnotationBinding(); |
| } |
| return markerAnnotation; |
| } |
| |
| public MemberValuePair convert(org.eclipse.jdt.internal.compiler.ast.MemberValuePair memberValuePair) { |
| final MemberValuePair pair = new MemberValuePair(this.ast); |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(memberValuePair.name)); |
| int start = memberValuePair.sourceStart; |
| int end = memberValuePair.sourceEnd; |
| simpleName.setSourceRange(start, end - start + 1); |
| pair.setName(simpleName); |
| final Expression value = convert(memberValuePair.value); |
| pair.setValue(value); |
| start = memberValuePair.sourceStart; |
| end = value.getStartPosition() + value.getLength() - 1; |
| pair.setSourceRange(start, end - start + 1); |
| |
| if (memberValuePair.value instanceof SingleNameReference && |
| ((SingleNameReference)memberValuePair.value).token == RecoveryScanner.FAKE_IDENTIFIER) { |
| pair.setFlags(pair.getFlags() | ASTNode.RECOVERED); |
| } |
| |
| if (this.resolveBindings) { |
| recordNodes(simpleName, memberValuePair); |
| recordNodes(pair, memberValuePair); |
| } |
| return pair; |
| } |
| |
| public Name convert(org.eclipse.jdt.internal.compiler.ast.NameReference reference) { |
| if (reference instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference) reference); |
| } else { |
| return convert((org.eclipse.jdt.internal.compiler.ast.SingleNameReference) reference); |
| } |
| } |
| |
| public InfixExpression convert(StringLiteralConcatenation expression) { |
| expression.computeConstant(); |
| final InfixExpression infixExpression = new InfixExpression(this.ast); |
| infixExpression.setOperator(InfixExpression.Operator.PLUS); |
| org.eclipse.jdt.internal.compiler.ast.Expression[] stringLiterals = expression.literals; |
| infixExpression.setLeftOperand(convert(stringLiterals[0])); |
| infixExpression.setRightOperand(convert(stringLiterals[1])); |
| for (int i = 2; i < expression.counter; i++) { |
| infixExpression.extendedOperands().add(convert(stringLiterals[i])); |
| } |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| infixExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return infixExpression; |
| } |
| |
| public NormalAnnotation convert(org.eclipse.jdt.internal.compiler.ast.NormalAnnotation annotation) { |
| final NormalAnnotation normalAnnotation = new NormalAnnotation(this.ast); |
| setTypeNameForAnnotation(annotation, normalAnnotation); |
| |
| int start = annotation.sourceStart; |
| int end = annotation.declarationSourceEnd; |
| |
| org.eclipse.jdt.internal.compiler.ast.MemberValuePair[] memberValuePairs = annotation.memberValuePairs; |
| if (memberValuePairs != null) { |
| for (int i = 0, max = memberValuePairs.length; i < max; i++) { |
| MemberValuePair memberValuePair = convert(memberValuePairs[i]); |
| int memberValuePairEnd = memberValuePair.getStartPosition() + memberValuePair.getLength() - 1; |
| if (end == memberValuePairEnd) { |
| normalAnnotation.setFlags(normalAnnotation.getFlags() | ASTNode.RECOVERED); |
| } |
| normalAnnotation.values().add(memberValuePair); |
| } |
| } |
| |
| normalAnnotation.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(normalAnnotation, annotation); |
| normalAnnotation.resolveAnnotationBinding(); |
| } |
| return normalAnnotation; |
| } |
| |
| public NullLiteral convert(org.eclipse.jdt.internal.compiler.ast.NullLiteral expression) { |
| final NullLiteral literal = new NullLiteral(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return literal; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.OR_OR_Expression expression) { |
| InfixExpression infixExpression = new InfixExpression(this.ast); |
| infixExpression.setOperator(InfixExpression.Operator.CONDITIONAL_OR); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| final int expressionOperatorID = (expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT; |
| if (expression.left instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((expression.left.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) { |
| // create an extended string literal equivalent => use the extended operands list |
| infixExpression.extendedOperands().add(convert(expression.right)); |
| org.eclipse.jdt.internal.compiler.ast.Expression leftOperand = expression.left; |
| org.eclipse.jdt.internal.compiler.ast.Expression rightOperand = null; |
| do { |
| rightOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).right; |
| if ((((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID |
| && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)) |
| || ((rightOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) != expressionOperatorID) |
| && ((rightOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0))) { |
| List extendedOperands = infixExpression.extendedOperands(); |
| InfixExpression temp = new InfixExpression(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| Expression leftSide = convert(leftOperand); |
| temp.setLeftOperand(leftSide); |
| temp.setSourceRange(leftSide.getStartPosition(), leftSide.getLength()); |
| int size = extendedOperands.size(); |
| for (int i = 0; i < size - 1; i++) { |
| Expression expr = temp; |
| temp = new InfixExpression(this.ast); |
| |
| if (this.resolveBindings) { |
| this.recordNodes(temp, expression); |
| } |
| temp.setLeftOperand(expr); |
| temp.setOperator(getOperatorFor(expressionOperatorID)); |
| temp.setSourceRange(expr.getStartPosition(), expr.getLength()); |
| } |
| infixExpression = temp; |
| for (int i = 0; i < size; i++) { |
| Expression extendedOperand = (Expression) extendedOperands.remove(size - 1 - i); |
| temp.setRightOperand(extendedOperand); |
| int startPosition = temp.getLeftOperand().getStartPosition(); |
| temp.setSourceRange(startPosition, extendedOperand.getStartPosition() + extendedOperand.getLength() - startPosition); |
| if (temp.getLeftOperand().getNodeType() == ASTNode.INFIX_EXPRESSION) { |
| temp = (InfixExpression) temp.getLeftOperand(); |
| } |
| } |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| if (this.resolveBindings) { |
| this.recordNodes(infixExpression, expression); |
| } |
| return infixExpression; |
| } |
| infixExpression.extendedOperands().add(0, convert(rightOperand)); |
| leftOperand = ((org.eclipse.jdt.internal.compiler.ast.BinaryExpression) leftOperand).left; |
| } while (leftOperand instanceof org.eclipse.jdt.internal.compiler.ast.BinaryExpression && ((leftOperand.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) == 0)); |
| Expression leftExpression = convert(leftOperand); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand((Expression)infixExpression.extendedOperands().remove(0)); |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| return infixExpression; |
| } |
| Expression leftExpression = convert(expression.left); |
| infixExpression.setLeftOperand(leftExpression); |
| infixExpression.setRightOperand(convert(expression.right)); |
| infixExpression.setOperator(InfixExpression.Operator.CONDITIONAL_OR); |
| setInfixSourcePositions(infixExpression, expression.sourceStart); |
| return infixExpression; |
| } |
| |
| private void setInfixSourcePositions(InfixExpression infixExpression, int sourceStart) { |
| int n = infixExpression.extendedOperands().size(); |
| Expression rightMostExp = n <= 0 ? infixExpression.getRightOperand() : (Expression) infixExpression.extendedOperands().get(n - 1); |
| int rightSourceEnd = rightMostExp.getStartPosition() + rightMostExp.getLength() - 1; |
| int infixSourceEnd = infixExpression.getStartPosition() + infixExpression.getLength() - 1; |
| infixSourceEnd = rightSourceEnd > infixSourceEnd ? rightSourceEnd : infixSourceEnd; |
| infixExpression.setSourceRange(sourceStart, infixSourceEnd - sourceStart + 1); |
| } |
| |
| public PostfixExpression convert(org.eclipse.jdt.internal.compiler.ast.PostfixExpression expression) { |
| final PostfixExpression postfixExpression = new PostfixExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(postfixExpression, expression); |
| } |
| postfixExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| postfixExpression.setOperand(convert(expression.lhs)); |
| switch (expression.operator) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.PLUS : |
| postfixExpression.setOperator(PostfixExpression.Operator.INCREMENT); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MINUS : |
| postfixExpression.setOperator(PostfixExpression.Operator.DECREMENT); |
| break; |
| } |
| return postfixExpression; |
| } |
| |
| public PrefixExpression convert(org.eclipse.jdt.internal.compiler.ast.PrefixExpression expression) { |
| final PrefixExpression prefixExpression = new PrefixExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(prefixExpression, expression); |
| } |
| prefixExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| prefixExpression.setOperand(convert(expression.lhs)); |
| switch (expression.operator) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.PLUS : |
| prefixExpression.setOperator(PrefixExpression.Operator.INCREMENT); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MINUS : |
| prefixExpression.setOperator(PrefixExpression.Operator.DECREMENT); |
| break; |
| } |
| return prefixExpression; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.QualifiedAllocationExpression allocation) { |
| final ClassInstanceCreation classInstanceCreation = new ClassInstanceCreation(this.ast); |
| if (allocation.enclosingInstance != null) { |
| classInstanceCreation.setExpression(convert(allocation.enclosingInstance)); |
| } |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| classInstanceCreation.internalSetName(convert(allocation.type)); |
| break; |
| default : |
| classInstanceCreation.setType(convertType(allocation.type)); |
| } |
| org.eclipse.jdt.internal.compiler.ast.Expression[] arguments = allocation.arguments; |
| if (arguments != null) { |
| int length = arguments.length; |
| for (int i = 0; i < length; i++) { |
| Expression argument = convert(arguments[i]); |
| if (this.resolveBindings) { |
| recordNodes(argument, arguments[i]); |
| } |
| classInstanceCreation.arguments().add(argument); |
| } |
| } |
| if (allocation.typeArguments != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| classInstanceCreation.setFlags(classInstanceCreation.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = allocation.typeArguments.length; i < max; i++) { |
| classInstanceCreation.typeArguments().add(convertType(allocation.typeArguments[i])); |
| } |
| } |
| } |
| if (allocation.anonymousType != null) { |
| int declarationSourceStart = allocation.sourceStart; |
| classInstanceCreation.setSourceRange(declarationSourceStart, allocation.anonymousType.bodyEnd - declarationSourceStart + 1); |
| final AnonymousClassDeclaration anonymousClassDeclaration = new AnonymousClassDeclaration(this.ast); |
| int start = retrieveStartBlockPosition(allocation.anonymousType.sourceEnd, allocation.anonymousType.bodyEnd); |
| anonymousClassDeclaration.setSourceRange(start, allocation.anonymousType.bodyEnd - start + 1); |
| classInstanceCreation.setAnonymousClassDeclaration(anonymousClassDeclaration); |
| buildBodyDeclarations(allocation.anonymousType, anonymousClassDeclaration); |
| if (this.resolveBindings) { |
| recordNodes(classInstanceCreation, allocation.anonymousType); |
| recordNodes(anonymousClassDeclaration, allocation.anonymousType); |
| anonymousClassDeclaration.resolveBinding(); |
| } |
| return classInstanceCreation; |
| } else { |
| final int start = allocation.sourceStart; |
| classInstanceCreation.setSourceRange(start, allocation.sourceEnd - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(classInstanceCreation, allocation); |
| } |
| return classInstanceCreation; |
| } |
| } |
| |
| public Name convert(org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference nameReference) { |
| return setQualifiedNameNameAndSourceRanges(nameReference.tokens, nameReference.sourcePositions, nameReference); |
| } |
| |
| public Name convert(org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference reference) { |
| return convert(reference.qualification); |
| } |
| |
| public ThisExpression convert(org.eclipse.jdt.internal.compiler.ast.QualifiedThisReference reference) { |
| final ThisExpression thisExpression = new ThisExpression(this.ast); |
| thisExpression.setSourceRange(reference.sourceStart, reference.sourceEnd - reference.sourceStart + 1); |
| thisExpression.setQualifier(convert(reference.qualification)); |
| if (this.resolveBindings) { |
| recordNodes(thisExpression, reference); |
| recordPendingThisExpressionScopeResolution(thisExpression); |
| } |
| return thisExpression; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.Reference reference) { |
| if (reference instanceof org.eclipse.jdt.internal.compiler.ast.NameReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.NameReference) reference); |
| } |
| if (reference instanceof org.eclipse.jdt.internal.compiler.ast.ThisReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ThisReference) reference); |
| } |
| if (reference instanceof org.eclipse.jdt.internal.compiler.ast.ArrayReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ArrayReference) reference); |
| } |
| if (reference instanceof org.eclipse.jdt.internal.compiler.ast.FieldReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.FieldReference) reference); |
| } |
| return null; // cannot be reached |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.ReferenceExpression reference) { |
| if (this.ast.apiLevel < AST.JLS8_INTERNAL) { |
| return createFakeNullLiteral(reference); |
| } |
| Expression result = null; |
| org.eclipse.jdt.internal.compiler.ast.Expression lhs = reference.lhs; |
| org.eclipse.jdt.internal.compiler.ast.TypeReference[] arguments = reference.typeArguments; |
| int start = arguments != null && arguments.length > 0 ? arguments[arguments.length - 1].sourceEnd + 1 : reference.lhs.sourceEnd + 1; |
| final SimpleName name = new SimpleName(this.ast); |
| retrieveIdentifierAndSetPositions(start, reference.sourceEnd, name); |
| name.internalSetIdentifier(new String(reference.selector)); |
| if (this.resolveBindings) { |
| recordNodes(name, reference); |
| } |
| List typeArguments = null; |
| if (name.getStartPosition() == -1 && name.getIdentifier().equals("<init>")) { // check for "new" //$NON-NLS-1$ |
| retrieveInitAndSetPositions(start, reference.sourceEnd, name); |
| Type type = null; |
| if (lhs instanceof TypeReference) { |
| type = convertType((TypeReference) lhs); |
| } else if (lhs instanceof NameReference) { |
| Name typeName = convert((NameReference) lhs); |
| SimpleType simpleType = new SimpleType(this.ast); |
| simpleType.setName(typeName); |
| if (this.resolveBindings) { |
| recordNodes(simpleType, lhs); |
| } |
| simpleType.setSourceRange(lhs.sourceStart, lhs.sourceEnd - lhs.sourceStart + 1); |
| type = simpleType; |
| } |
| CreationReference creationReference = new CreationReference(this.ast); |
| creationReference.setType(type); |
| typeArguments = creationReference.typeArguments(); |
| result = creationReference; |
| } else if (lhs instanceof TypeReference) { |
| TypeMethodReference typeMethodReference = new TypeMethodReference(this.ast); |
| typeMethodReference.setType(convertType((TypeReference) lhs)); |
| typeMethodReference.setName(name); |
| typeArguments = typeMethodReference.typeArguments(); |
| result = typeMethodReference; |
| } else if (lhs instanceof SuperReference) { |
| SuperMethodReference superMethodReference = new SuperMethodReference(this.ast); |
| superMethodReference.setName(name); |
| typeArguments = superMethodReference.typeArguments(); |
| result = superMethodReference; |
| } else if (lhs instanceof QualifiedSuperReference) { |
| SuperMethodReference superMethodReference = new SuperMethodReference(this.ast); |
| superMethodReference.setQualifier(convert((QualifiedSuperReference)lhs)); |
| superMethodReference.setName(name); |
| typeArguments = superMethodReference.typeArguments(); |
| result = superMethodReference; |
| } else { |
| ExpressionMethodReference expressionMethodReference = new ExpressionMethodReference(this.ast); |
| expressionMethodReference.setExpression(convert(lhs)); |
| typeArguments = expressionMethodReference.typeArguments(); |
| expressionMethodReference.setName(name); |
| result = expressionMethodReference; |
| } |
| if (typeArguments != null && arguments != null) { |
| int argumentsLength = arguments.length; |
| for (int i = 0; i < argumentsLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.TypeReference argument = arguments[i]; |
| typeArguments.add(convertType(argument)); |
| } |
| } |
| if (this.resolveBindings) { |
| recordNodes(result, reference); |
| } |
| int sourceStart = reference.sourceStart; |
| result.setSourceRange(sourceStart, reference.sourceEnd - sourceStart + 1); |
| return result; |
| } |
| |
| public ReturnStatement convert(org.eclipse.jdt.internal.compiler.ast.ReturnStatement statement) { |
| final ReturnStatement returnStatement = new ReturnStatement(this.ast); |
| returnStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| if (statement.expression != null) { |
| returnStatement.setExpression(convert(statement.expression)); |
| } |
| return returnStatement; |
| } |
| |
| public SingleMemberAnnotation convert(org.eclipse.jdt.internal.compiler.ast.SingleMemberAnnotation annotation) { |
| final SingleMemberAnnotation singleMemberAnnotation = new SingleMemberAnnotation(this.ast); |
| setTypeNameForAnnotation(annotation, singleMemberAnnotation); |
| singleMemberAnnotation.setValue(convert(annotation.memberValue)); |
| int start = annotation.sourceStart; |
| int end = annotation.declarationSourceEnd; |
| singleMemberAnnotation.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(singleMemberAnnotation, annotation); |
| singleMemberAnnotation.resolveAnnotationBinding(); |
| } |
| return singleMemberAnnotation; |
| } |
| |
| public SimpleName convert(org.eclipse.jdt.internal.compiler.ast.SingleNameReference nameReference) { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(nameReference.token)); |
| if (this.resolveBindings) { |
| recordNodes(name, nameReference); |
| } |
| name.setSourceRange(nameReference.sourceStart, nameReference.sourceEnd - nameReference.sourceStart + 1); |
| return name; |
| } |
| |
| public Statement convert(org.eclipse.jdt.internal.compiler.ast.Statement statement) { |
| if (statement instanceof ForeachStatement) { |
| return convert((ForeachStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.LocalDeclaration localDeclaration = (org.eclipse.jdt.internal.compiler.ast.LocalDeclaration)statement; |
| return convertToVariableDeclarationStatement(localDeclaration); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.AssertStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.AssertStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.Block) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.Block) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.BreakStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.BreakStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.ContinueStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ContinueStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.CaseStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.CaseStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.DoStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.DoStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.EmptyStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.EmptyStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.ForStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ForStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.IfStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.IfStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.LabeledStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.LabeledStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.ReturnStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ReturnStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.SwitchStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.SwitchStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.SynchronizedStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.SynchronizedStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.ThrowStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.ThrowStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.TryStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.TryStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) { |
| ASTNode result = convert((org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) statement); |
| if (result == null || !(result instanceof TypeDeclaration)) { |
| return createFakeEmptyStatement(statement); |
| } |
| // annotation and enum type declarations are not returned by the parser inside method bodies |
| TypeDeclaration typeDeclaration = (TypeDeclaration) result; |
| TypeDeclarationStatement typeDeclarationStatement = new TypeDeclarationStatement(this.ast); |
| typeDeclarationStatement.setDeclaration(typeDeclaration); |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| TypeDeclaration typeDecl = typeDeclarationStatement.internalGetTypeDeclaration(); |
| typeDeclarationStatement.setSourceRange(typeDecl.getStartPosition(), typeDecl.getLength()); |
| break; |
| default : |
| AbstractTypeDeclaration typeDeclAST3 = typeDeclarationStatement.getDeclaration(); |
| typeDeclarationStatement.setSourceRange(typeDeclAST3.getStartPosition(), typeDeclAST3.getLength()); |
| break; |
| } |
| return typeDeclarationStatement; |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.WhileStatement) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.WhileStatement) statement); |
| } |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.Expression) { |
| org.eclipse.jdt.internal.compiler.ast.Expression statement2 = (org.eclipse.jdt.internal.compiler.ast.Expression) statement; |
| final Expression expr = convert(statement2); |
| final ExpressionStatement stmt = new ExpressionStatement(this.ast); |
| stmt.setExpression(expr); |
| int sourceStart = expr.getStartPosition(); |
| int sourceEnd = statement2.statementEnd; |
| stmt.setSourceRange(sourceStart, sourceEnd - sourceStart + 1); |
| return stmt; |
| } |
| return createFakeEmptyStatement(statement); |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.StringLiteral expression) { |
| if (expression instanceof StringLiteralConcatenation) { |
| return convert((StringLiteralConcatenation) expression); |
| } |
| int length = expression.sourceEnd - expression.sourceStart + 1; |
| int sourceStart = expression.sourceStart; |
| StringLiteral literal = new StringLiteral(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.internalSetEscapedValue(new String(this.compilationUnitSource, sourceStart, length)); |
| literal.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return literal; |
| } |
| |
| public SwitchStatement convert(org.eclipse.jdt.internal.compiler.ast.SwitchStatement statement) { |
| SwitchStatement switchStatement = new SwitchStatement(this.ast); |
| switchStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| switchStatement.setExpression(convert(statement.expression)); |
| org.eclipse.jdt.internal.compiler.ast.Statement[] statements = statement.statements; |
| if (statements != null) { |
| int statementsLength = statements.length; |
| for (int i = 0; i < statementsLength; i++) { |
| if (statements[i] instanceof org.eclipse.jdt.internal.compiler.ast.LocalDeclaration) { |
| checkAndAddMultipleLocalDeclaration(statements, i, switchStatement.statements()); |
| } else { |
| final Statement currentStatement = convert(statements[i]); |
| if (currentStatement != null) { |
| switchStatement.statements().add(currentStatement); |
| } |
| } |
| } |
| } |
| return switchStatement; |
| } |
| |
| public SynchronizedStatement convert(org.eclipse.jdt.internal.compiler.ast.SynchronizedStatement statement) { |
| SynchronizedStatement synchronizedStatement = new SynchronizedStatement(this.ast); |
| synchronizedStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| synchronizedStatement.setBody(convert(statement.block)); |
| synchronizedStatement.setExpression(convert(statement.expression)); |
| return synchronizedStatement; |
| } |
| |
| public Expression convert(org.eclipse.jdt.internal.compiler.ast.ThisReference reference) { |
| if (reference.isImplicitThis()) { |
| // There is no source associated with an implicit this |
| return null; |
| } else if (reference instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.QualifiedSuperReference) reference); |
| } else if (reference instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedThisReference) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.QualifiedThisReference) reference); |
| } else { |
| ThisExpression thisExpression = new ThisExpression(this.ast); |
| thisExpression.setSourceRange(reference.sourceStart, reference.sourceEnd - reference.sourceStart + 1); |
| if (this.resolveBindings) { |
| recordNodes(thisExpression, reference); |
| recordPendingThisExpressionScopeResolution(thisExpression); |
| } |
| return thisExpression; |
| } |
| } |
| |
| public ThrowStatement convert(org.eclipse.jdt.internal.compiler.ast.ThrowStatement statement) { |
| final ThrowStatement throwStatement = new ThrowStatement(this.ast); |
| throwStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| throwStatement.setExpression(convert(statement.exception)); |
| return throwStatement; |
| } |
| |
| public BooleanLiteral convert(org.eclipse.jdt.internal.compiler.ast.TrueLiteral expression) { |
| final BooleanLiteral literal = new BooleanLiteral(this.ast); |
| literal.setBooleanValue(true); |
| if (this.resolveBindings) { |
| this.recordNodes(literal, expression); |
| } |
| literal.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return literal; |
| } |
| |
| public TryStatement convert(org.eclipse.jdt.internal.compiler.ast.TryStatement statement) { |
| final TryStatement tryStatement = new TryStatement(this.ast); |
| tryStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| int resourcesLength = statement.resources.length; |
| if (resourcesLength > 0) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| // convert it to a simple try statement tagged as MALFORMED |
| tryStatement.setFlags(tryStatement.getFlags() | ASTNode.MALFORMED); |
| break; |
| case AST.JLS4_INTERNAL: |
| case AST.JLS8_INTERNAL: |
| for (int i = 0; i < resourcesLength; i++) { |
| if (!(statement.resources[i] instanceof LocalDeclaration)) { |
| tryStatement.setFlags(tryStatement.getFlags() | ASTNode.MALFORMED); |
| break; |
| } |
| LocalDeclaration localDeclaration = (LocalDeclaration)statement.resources[i]; |
| VariableDeclarationExpression variableDeclarationExpression = convertToVariableDeclarationExpression(localDeclaration); |
| int start = variableDeclarationExpression.getStartPosition(); |
| int end = localDeclaration.declarationEnd; |
| variableDeclarationExpression.setSourceRange(start, end - start + 1); |
| tryStatement.resources().add(variableDeclarationExpression); |
| } |
| break; |
| default: |
| for (int i = 0; i < resourcesLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.Statement resource = statement.resources[i]; |
| if (resource instanceof LocalDeclaration) { |
| LocalDeclaration localDeclaration = (LocalDeclaration)resource; |
| VariableDeclarationExpression variableDeclarationExpression = convertToVariableDeclarationExpression(localDeclaration); |
| int start = variableDeclarationExpression.getStartPosition(); |
| int end = localDeclaration.declarationEnd; |
| variableDeclarationExpression.setSourceRange(start, end - start + 1); |
| tryStatement.resources().add(variableDeclarationExpression); |
| } else if (resource instanceof NameReference) { |
| tryStatement.resources().add(convert((NameReference) resource)); |
| } else if (resource instanceof FieldReference) { |
| tryStatement.resources().add(convert((FieldReference) resource)); |
| } else { |
| tryStatement.setFlags(tryStatement.getFlags() | ASTNode.MALFORMED); |
| break; |
| } |
| } |
| break; |
| } |
| } |
| tryStatement.setBody(convert(statement.tryBlock)); |
| org.eclipse.jdt.internal.compiler.ast.Argument[] catchArguments = statement.catchArguments; |
| if (catchArguments != null) { |
| int catchArgumentsLength = catchArguments.length; |
| org.eclipse.jdt.internal.compiler.ast.Block[] catchBlocks = statement.catchBlocks; |
| int start = statement.tryBlock.sourceEnd; |
| for (int i = 0; i < catchArgumentsLength; i++) { |
| CatchClause catchClause = new CatchClause(this.ast); |
| int catchClauseSourceStart = retrieveStartingCatchPosition(start, catchArguments[i].sourceStart); |
| catchClause.setSourceRange(catchClauseSourceStart, catchBlocks[i].sourceEnd - catchClauseSourceStart + 1); |
| catchClause.setBody(convert(catchBlocks[i])); |
| catchClause.setException(convert(catchArguments[i])); |
| tryStatement.catchClauses().add(catchClause); |
| start = catchBlocks[i].sourceEnd; |
| } |
| } |
| if (statement.finallyBlock != null) { |
| tryStatement.setFinally(convert(statement.finallyBlock)); |
| } |
| return tryStatement; |
| } |
| |
| public ASTNode convert(org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration) { |
| int kind = org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.kind(typeDeclaration.modifiers); |
| switch (kind) { |
| case org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.ENUM_DECL : |
| if (this.ast.apiLevel == AST.JLS2_INTERNAL) { |
| return null; |
| } else { |
| return convertToEnumDeclaration(typeDeclaration); |
| } |
| case org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.ANNOTATION_TYPE_DECL : |
| if (this.ast.apiLevel == AST.JLS2_INTERNAL) { |
| return null; |
| } else { |
| return convertToAnnotationDeclaration(typeDeclaration); |
| } |
| } |
| |
| checkCanceled(); |
| TypeDeclaration typeDecl = new TypeDeclaration(this.ast); |
| ASTNode oldReferenceContext = this.referenceContext; |
| this.referenceContext = typeDecl; |
| if (typeDeclaration.modifiersSourceStart != -1) { |
| setModifiers(typeDecl, typeDeclaration); |
| } |
| boolean isInterface = kind == org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.INTERFACE_DECL; |
| typeDecl.setInterface(isInterface); |
| final SimpleName typeName = new SimpleName(this.ast); |
| typeName.internalSetIdentifier(new String(typeDeclaration.name)); |
| typeName.setSourceRange(typeDeclaration.sourceStart, typeDeclaration.sourceEnd - typeDeclaration.sourceStart + 1); |
| typeDecl.setName(typeName); |
| typeDecl.setSourceRange(typeDeclaration.declarationSourceStart, typeDeclaration.bodyEnd - typeDeclaration.declarationSourceStart + 1); |
| |
| // need to set the superclass and super interfaces here since we cannot distinguish them at |
| // the type references level. |
| if (typeDeclaration.superclass != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| typeDecl.internalSetSuperclass(convert(typeDeclaration.superclass)); |
| break; |
| default : |
| typeDecl.setSuperclassType(convertType(typeDeclaration.superclass)); |
| break; |
| } |
| } |
| |
| org.eclipse.jdt.internal.compiler.ast.TypeReference[] superInterfaces = typeDeclaration.superInterfaces; |
| if (superInterfaces != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| for (int index = 0, length = superInterfaces.length; index < length; index++) { |
| typeDecl.internalSuperInterfaces().add(convert(superInterfaces[index])); |
| } |
| break; |
| default : |
| for (int index = 0, length = superInterfaces.length; index < length; index++) { |
| typeDecl.superInterfaceTypes().add(convertType(superInterfaces[index])); |
| } |
| } |
| } |
| org.eclipse.jdt.internal.compiler.ast.TypeParameter[] typeParameters = typeDeclaration.typeParameters; |
| if (typeParameters != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| typeDecl.setFlags(typeDecl.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| for (int index = 0, length = typeParameters.length; index < length; index++) { |
| typeDecl.typeParameters().add(convert(typeParameters[index])); |
| } |
| } |
| } |
| buildBodyDeclarations(typeDeclaration, typeDecl, isInterface); |
| if (this.resolveBindings) { |
| recordNodes(typeDecl, typeDeclaration); |
| recordNodes(typeName, typeDeclaration); |
| typeDecl.resolveBinding(); |
| } |
| this.referenceContext = oldReferenceContext; |
| return typeDecl; |
| } |
| |
| public TypeParameter convert(org.eclipse.jdt.internal.compiler.ast.TypeParameter typeParameter) { |
| final TypeParameter typeParameter2 = new TypeParameter(this.ast); |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(typeParameter.name)); |
| int start = typeParameter.sourceStart; |
| int end = typeParameter.sourceEnd; |
| simpleName.setSourceRange(start, end - start + 1); |
| typeParameter2.setName(simpleName); |
| int annotationsStart = start; |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = typeParameter.annotations; |
| if (annotations != null) { |
| if (annotations[0] != null) |
| annotationsStart = annotations[0].sourceStart; |
| annotateTypeParameter(typeParameter2, typeParameter.annotations); |
| } |
| final TypeReference superType = typeParameter.type; |
| end = typeParameter.declarationSourceEnd; |
| if (superType != null) { |
| Type type = convertType(superType); |
| typeParameter2.typeBounds().add(type); |
| end = type.getStartPosition() + type.getLength() - 1; |
| } |
| TypeReference[] bounds = typeParameter.bounds; |
| if (bounds != null) { |
| Type type = null; |
| for (int index = 0, length = bounds.length; index < length; index++) { |
| type = convertType(bounds[index]); |
| typeParameter2.typeBounds().add(type); |
| end = type.getStartPosition() + type.getLength() - 1; |
| } |
| } |
| start = annotationsStart < typeParameter.declarationSourceStart ? annotationsStart : typeParameter.declarationSourceStart; |
| end = retrieveClosingAngleBracketPosition(end); |
| typeParameter2.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordName(simpleName, typeParameter); |
| recordNodes(typeParameter2, typeParameter); |
| typeParameter2.resolveBinding(); |
| } |
| return typeParameter2; |
| } |
| |
| public Name convert(org.eclipse.jdt.internal.compiler.ast.TypeReference typeReference) { |
| char[][] typeName = typeReference.getTypeName(); |
| int length = typeName.length; |
| if (length > 1) { |
| // QualifiedName |
| org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference qualifiedTypeReference = (org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference) typeReference; |
| final long[] positions = qualifiedTypeReference.sourcePositions; |
| return setQualifiedNameNameAndSourceRanges(typeName, positions, typeReference); |
| } else { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(typeName[0])); |
| name.setSourceRange(typeReference.sourceStart, typeReference.sourceEnd - typeReference.sourceStart + 1); |
| name.index = 1; |
| if (this.resolveBindings) { |
| recordNodes(name, typeReference); |
| } |
| return name; |
| } |
| } |
| |
| public PrefixExpression convert(org.eclipse.jdt.internal.compiler.ast.UnaryExpression expression) { |
| final PrefixExpression prefixExpression = new PrefixExpression(this.ast); |
| if (this.resolveBindings) { |
| this.recordNodes(prefixExpression, expression); |
| } |
| prefixExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| prefixExpression.setOperand(convert(expression.expression)); |
| switch ((expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.OperatorSHIFT) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.PLUS : |
| prefixExpression.setOperator(PrefixExpression.Operator.PLUS); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MINUS : |
| prefixExpression.setOperator(PrefixExpression.Operator.MINUS); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.NOT : |
| prefixExpression.setOperator(PrefixExpression.Operator.NOT); |
| break; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.TWIDDLE : |
| prefixExpression.setOperator(PrefixExpression.Operator.COMPLEMENT); |
| } |
| return prefixExpression; |
| } |
| |
| public WhileStatement convert(org.eclipse.jdt.internal.compiler.ast.WhileStatement statement) { |
| final WhileStatement whileStatement = new WhileStatement(this.ast); |
| whileStatement.setSourceRange(statement.sourceStart, statement.sourceEnd - statement.sourceStart + 1); |
| whileStatement.setExpression(convert(statement.condition)); |
| final Statement action = convert(statement.action); |
| if (action == null) return null; |
| whileStatement.setBody(action); |
| return whileStatement; |
| } |
| |
| public ImportDeclaration convertImport(org.eclipse.jdt.internal.compiler.ast.ImportReference importReference) { |
| final ImportDeclaration importDeclaration = new ImportDeclaration(this.ast); |
| Name name = getImportName(importReference); |
| importDeclaration.setName(name); |
| final boolean onDemand = (importReference.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.OnDemand) != 0; |
| importDeclaration.setSourceRange(importReference.declarationSourceStart, importReference.declarationEnd - importReference.declarationSourceStart + 1); |
| importDeclaration.setOnDemand(onDemand); |
| int modifiers = importReference.modifiers; |
| if (modifiers != ClassFileConstants.AccDefault) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| importDeclaration.setFlags(importDeclaration.getFlags() | ASTNode.MALFORMED); |
| break; |
| default : |
| if (modifiers == ClassFileConstants.AccStatic) { |
| importDeclaration.setStatic(true); |
| } else { |
| importDeclaration.setFlags(importDeclaration.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| } |
| if (this.resolveBindings) { |
| recordNodes(importDeclaration, importReference); |
| } |
| return importDeclaration; |
| } |
| |
| public Name getImportName(org.eclipse.jdt.internal.compiler.ast.ImportReference importReference) { |
| return getName(importReference, importReference.tokens, importReference.sourcePositions); |
| } |
| |
| private Name getName(org.eclipse.jdt.internal.compiler.ast.ASTNode node, final char[][] tokens, |
| final long[] positions) { |
| Name name; |
| int length = tokens != null ? tokens.length : 0; |
| if (length > 1) { |
| name = setQualifiedNameNameAndSourceRanges(tokens, positions, node); |
| } else { |
| name = new SimpleName(this.ast); |
| ((SimpleName)name).internalSetIdentifier(new String(tokens[0])); |
| final int start = (int)(positions[0]>>>32); |
| final int end = (int)(positions[0] & 0xFFFFFFFF); |
| name.setSourceRange(start, end - start + 1); |
| name.index = 1; |
| if (this.resolveBindings) { |
| recordNodes(name, node); |
| } |
| } |
| return name; |
| } |
| |
| public PackageDeclaration convertPackage(org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration compilationUnitDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.ImportReference importReference = compilationUnitDeclaration.currentPackage; |
| final PackageDeclaration packageDeclaration = new PackageDeclaration(this.ast); |
| final char[][] tokens = importReference.tokens; |
| final int length = importReference.tokens.length; |
| long[] positions = importReference.sourcePositions; |
| if (length > 1) { |
| packageDeclaration.setName(setQualifiedNameNameAndSourceRanges(tokens, positions, importReference)); |
| } else { |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(tokens[0])); |
| int start = (int)(positions[0]>>>32); |
| int end = (int)(positions[length - 1] & 0xFFFFFFFF); |
| name.setSourceRange(start, end - start + 1); |
| name.index = 1; |
| packageDeclaration.setName(name); |
| if (this.resolveBindings) { |
| recordNodes(name, compilationUnitDeclaration); |
| } |
| } |
| packageDeclaration.setSourceRange(importReference.declarationSourceStart, importReference.declarationEnd - importReference.declarationSourceStart + 1); |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = importReference.annotations; |
| if (annotations != null) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| packageDeclaration.setFlags(packageDeclaration.getFlags() & ASTNode.MALFORMED); |
| break; |
| default : |
| for (int i = 0, max = annotations.length; i < max; i++) { |
| packageDeclaration.annotations().add(convert(annotations[i])); |
| } |
| } |
| } |
| if (this.resolveBindings) { |
| recordNodes(packageDeclaration, importReference); |
| } |
| // Set javadoc |
| convert(compilationUnitDeclaration.javadoc, packageDeclaration); |
| return packageDeclaration; |
| } |
| |
| private ArrayType convertToArray(Type elementType, int sourceStart, int length, int dimensions, org.eclipse.jdt.internal.compiler.ast.Annotation[][] annotationsOnDimensions) { |
| ArrayType arrayType = this.ast.newArrayType(elementType, dimensions); |
| if (length > 0) arrayType.setSourceRange(sourceStart, length); |
| if (this.ast.apiLevel() < AST.JLS8_INTERNAL) { |
| if (annotationsOnDimensions != null) { |
| arrayType.setFlags(arrayType.getFlags() | ASTNode.MALFORMED); |
| } |
| ArrayType subarrayType = arrayType; |
| int index = dimensions - 1; |
| int arrayEnd = retrieveProperRightBracketPosition(dimensions, sourceStart); |
| while (index > 0) { |
| subarrayType = (ArrayType) componentType(subarrayType); |
| int end = retrieveProperRightBracketPosition(index, sourceStart); |
| subarrayType.setSourceRange(sourceStart, end - sourceStart + 1); |
| index--; |
| } |
| if (length < arrayEnd - sourceStart) arrayType.setSourceRange(sourceStart, arrayEnd - sourceStart + 1); |
| return arrayType; |
| } |
| |
| setTypeAnnotationsAndSourceRangeOnArray(arrayType, annotationsOnDimensions); |
| return arrayType; |
| } |
| |
| private EnumDeclaration convertToEnumDeclaration(org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration) { |
| checkCanceled(); |
| // enum declaration cannot be built if the source is not >= 1.5, since enum is then seen as an identifier |
| final EnumDeclaration enumDeclaration2 = new EnumDeclaration(this.ast); |
| setModifiers(enumDeclaration2, typeDeclaration); |
| final SimpleName typeName = new SimpleName(this.ast); |
| typeName.internalSetIdentifier(new String(typeDeclaration.name)); |
| typeName.setSourceRange(typeDeclaration.sourceStart, typeDeclaration.sourceEnd - typeDeclaration.sourceStart + 1); |
| enumDeclaration2.setName(typeName); |
| enumDeclaration2.setSourceRange(typeDeclaration.declarationSourceStart, typeDeclaration.bodyEnd - typeDeclaration.declarationSourceStart + 1); |
| |
| org.eclipse.jdt.internal.compiler.ast.TypeReference[] superInterfaces = typeDeclaration.superInterfaces; |
| if (superInterfaces != null) { |
| for (int index = 0, length = superInterfaces.length; index < length; index++) { |
| enumDeclaration2.superInterfaceTypes().add(convertType(superInterfaces[index])); |
| } |
| } |
| buildBodyDeclarations(typeDeclaration, enumDeclaration2); |
| if (this.resolveBindings) { |
| recordNodes(enumDeclaration2, typeDeclaration); |
| recordNodes(typeName, typeDeclaration); |
| enumDeclaration2.resolveBinding(); |
| } |
| return enumDeclaration2; |
| } |
| public Expression convertToExpression(org.eclipse.jdt.internal.compiler.ast.Statement statement) { |
| if (statement instanceof org.eclipse.jdt.internal.compiler.ast.Expression) { |
| return convert((org.eclipse.jdt.internal.compiler.ast.Expression) statement); |
| } else { |
| return null; |
| } |
| } |
| |
| protected FieldDeclaration convertToFieldDeclaration(org.eclipse.jdt.internal.compiler.ast.FieldDeclaration fieldDecl) { |
| VariableDeclarationFragment variableDeclarationFragment = convertToVariableDeclarationFragment(fieldDecl); |
| final FieldDeclaration fieldDeclaration = new FieldDeclaration(this.ast); |
| fieldDeclaration.fragments().add(variableDeclarationFragment); |
| if (this.resolveBindings) { |
| recordNodes(variableDeclarationFragment, fieldDecl); |
| variableDeclarationFragment.resolveBinding(); |
| } |
| fieldDeclaration.setSourceRange(fieldDecl.declarationSourceStart, fieldDecl.declarationEnd - fieldDecl.declarationSourceStart + 1); |
| Type type = convertType(fieldDecl.type); |
| setTypeForField(fieldDeclaration, type, variableDeclarationFragment.getExtraDimensions()); |
| setModifiers(fieldDeclaration, fieldDecl); |
| convert(fieldDecl.javadoc, fieldDeclaration); |
| return fieldDeclaration; |
| } |
| |
| /** |
| * If there is a parsing error causing a recovered module the source positions may be updated only partially. |
| * See bug 518843 for a case where this issue occurred. This method provide a safety net with |
| * source positions updated even in case of a recovery - if there is no recovery, the source positions will |
| * be retained in-tact identical to the compile time ast module node. |
| */ |
| private int getKnownEnd(ModuleDeclaration md, int sourceEnd, int declSourceEnd) { |
| int end = retrieveRightBrace(md.getStartPosition() + 1, this.compilationUnitSourceLength); |
| end = end > sourceEnd ? end : sourceEnd; |
| end = end > declSourceEnd ? end : declSourceEnd; |
| return end; |
| } |
| public ModuleDeclaration convertToModuleDeclaration(org.eclipse.jdt.internal.compiler.ast.ModuleDeclaration moduleDeclaration) { |
| checkCanceled(); |
| if (this.scanner.sourceLevel < ClassFileConstants.JDK9 |
| || this.ast.apiLevel < AST.JLS9_INTERNAL) return null; |
| ModuleDeclaration moduleDecl = this.ast.newModuleDeclaration(); |
| // TODO |
| //convert(moduleDeclaration.javadoc, moduleDecl); |
| setAnnotations(moduleDecl, moduleDeclaration); // only annotations |
| moduleDecl.setOpen(moduleDeclaration.isOpen()); |
| Name moduleName = getName(moduleDeclaration, CharOperation.splitOn('.', moduleDeclaration.moduleName), moduleDeclaration.sourcePositions); |
| moduleDecl.setName(moduleName); |
| |
| List<ModuleDirective> stmts = moduleDecl.moduleStatements(); |
| TreeSet<ModuleDirective> tSet = new TreeSet<> (new Comparator() { |
| public int compare(Object o1, Object o2) { |
| int p1 = ((ModuleDirective) o1).getStartPosition(); |
| int p2 = ((ModuleDirective) o2).getStartPosition(); |
| return p1 < p2 ? -1 : p1 == p2 ? 0 : 1; |
| } |
| }); |
| for (int i = 0; i < moduleDeclaration.exportsCount; ++i) { |
| tSet.add(getPackageVisibilityStatement(moduleDeclaration.exports[i], new ExportsDirective(this.ast))); |
| } |
| for (int i = 0; i < moduleDeclaration.opensCount; ++i) { |
| tSet.add(getPackageVisibilityStatement(moduleDeclaration.opens[i], new OpensDirective(this.ast))); |
| } |
| for (int i = 0; i < moduleDeclaration.requiresCount; ++i) { |
| org.eclipse.jdt.internal.compiler.ast.RequiresStatement req = moduleDeclaration.requires[i]; |
| ModuleReference moduleRef = req.module; |
| RequiresDirective stmt = new RequiresDirective(this.ast); |
| Name name = getName(moduleRef, CharOperation.splitOn('.', moduleRef.moduleName), moduleRef.sourcePositions); |
| stmt.setName(name); |
| if (this.resolveBindings) { |
| recordNodes(name, moduleRef); |
| } |
| |
| setModuleModifiers(req, stmt); |
| stmt.setSourceRange(req.declarationSourceStart, req.declarationEnd - req.declarationSourceStart + 1); |
| tSet.add(stmt); |
| } |
| for (int i = 0; i < moduleDeclaration.usesCount; ++i) { |
| org.eclipse.jdt.internal.compiler.ast.UsesStatement usesStatement = moduleDeclaration.uses[i]; |
| UsesDirective stmt = new UsesDirective(this.ast); |
| TypeReference usesRef = usesStatement.serviceInterface; |
| Name name = convert(usesRef); |
| stmt.setName(name); |
| stmt.setSourceRange(usesStatement.declarationSourceStart, usesStatement.declarationSourceEnd - usesStatement.declarationSourceStart + 1); |
| tSet.add(stmt); |
| } |
| for (int i = 0; i < moduleDeclaration.servicesCount; ++i) { |
| org.eclipse.jdt.internal.compiler.ast.ProvidesStatement pStmt = moduleDeclaration.services[i]; |
| ProvidesDirective stmt = new ProvidesDirective(this.ast); |
| stmt.setName(convert(pStmt.serviceInterface)); |
| TypeReference[] impls = pStmt.implementations; |
| for (TypeReference impl : impls) { |
| stmt.implementations().add(convert(impl)); |
| } |
| stmt.setSourceRange(pStmt.declarationSourceStart, pStmt.declarationSourceEnd - pStmt.declarationSourceStart + 1); |
| tSet.add(stmt); |
| } |
| // The javadoc comment is now got from list store in compilation unit declaration |
| if (this.resolveBindings) { |
| recordNodes(moduleDecl, moduleDeclaration); |
| recordNodes(moduleName, moduleDeclaration); |
| moduleDecl.resolveBinding(); |
| } |
| stmts.addAll(tSet); |
| int end = getKnownEnd(moduleDecl, moduleDeclaration.sourceEnd, moduleDeclaration.declarationSourceEnd); |
| moduleDecl.setSourceRange(moduleDeclaration.declarationSourceStart, end - moduleDeclaration.declarationSourceStart + 1); |
| return moduleDecl; |
| } |
| |
| private void setModuleModifiers(org.eclipse.jdt.internal.compiler.ast.RequiresStatement req, RequiresDirective stmt) { |
| boolean fakeInModule = this.scanner.fakeInModule; |
| this.scanner.fakeInModule = true; |
| this.scanner.resetTo(req.declarationSourceStart, req.sourceEnd); |
| try { |
| int token; |
| ModuleModifier modifier; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModuleModifier(ModuleModifier.ModuleModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransitive: |
| modifier = createModuleModifier(ModuleModifier.ModuleModifierKeyword.TRANSITIVE_KEYWORD); |
| break; |
| default : |
| continue; |
| } |
| if (modifier != null) { |
| stmt.modifiers().add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } finally { |
| this.scanner.fakeInModule = fakeInModule; |
| } |
| } |
| |
| public ParenthesizedExpression convertToParenthesizedExpression(org.eclipse.jdt.internal.compiler.ast.Expression expression) { |
| final ParenthesizedExpression parenthesizedExpression = new ParenthesizedExpression(this.ast); |
| if (this.resolveBindings) { |
| recordNodes(parenthesizedExpression, expression); |
| } |
| parenthesizedExpression.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| adjustSourcePositionsForParent(expression); |
| trimWhiteSpacesAndComments(expression); |
| // decrement the number of parenthesis |
| int numberOfParenthesis = (expression.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK) >> org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedSHIFT; |
| expression.bits &= ~org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedMASK; |
| expression.bits |= (numberOfParenthesis - 1) << org.eclipse.jdt.internal.compiler.ast.ASTNode.ParenthesizedSHIFT; |
| parenthesizedExpression.setExpression(convert(expression)); |
| return parenthesizedExpression; |
| } |
| |
| protected VariableDeclarationExpression convertToVariableDeclarationExpression(org.eclipse.jdt.internal.compiler.ast.LocalDeclaration localDeclaration) { |
| final VariableDeclarationFragment variableDeclarationFragment = convertToVariableDeclarationFragment(localDeclaration); |
| final VariableDeclarationExpression variableDeclarationExpression = new VariableDeclarationExpression(this.ast); |
| variableDeclarationExpression.fragments().add(variableDeclarationFragment); |
| if (this.resolveBindings) { |
| recordNodes(variableDeclarationFragment, localDeclaration); |
| } |
| variableDeclarationExpression.setSourceRange(localDeclaration.declarationSourceStart, localDeclaration.declarationSourceEnd - localDeclaration.declarationSourceStart + 1); |
| Type type = convertType(localDeclaration.type); |
| setTypeForVariableDeclarationExpression(variableDeclarationExpression, type, variableDeclarationFragment.getExtraDimensions()); |
| if (localDeclaration.modifiersSourceStart != -1) { |
| setModifiers(variableDeclarationExpression, localDeclaration); |
| } |
| return variableDeclarationExpression; |
| } |
| |
| protected SingleVariableDeclaration convertToSingleVariableDeclaration(LocalDeclaration localDeclaration) { |
| final SingleVariableDeclaration variableDecl = new SingleVariableDeclaration(this.ast); |
| setModifiers(variableDecl, localDeclaration); |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(localDeclaration.name)); |
| int start = localDeclaration.sourceStart; |
| int nameEnd = localDeclaration.sourceEnd; |
| name.setSourceRange(start, nameEnd - start + 1); |
| variableDecl.setName(name); |
| TypeReference typeReference = localDeclaration.type; |
| final int extraDimensions = typeReference.extraDimensions(); |
| if (this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| setExtraAnnotatedDimensions(nameEnd + 1, localDeclaration.declarationSourceEnd, typeReference, |
| variableDecl.extraDimensions(), extraDimensions); |
| } else { |
| internalSetExtraDimensions(variableDecl, extraDimensions); |
| } |
| Type type = convertType(localDeclaration.type); |
| int typeEnd = type.getStartPosition() + type.getLength() - 1; |
| // https://bugs.eclipse.org/393719 - [compiler] inconsistent warnings on iteration variables |
| // compiler considers collectionExpression as within the declarationSourceEnd, DOM AST must use the shorter range to avoid overlap |
| int sourceEnd = ((localDeclaration.bits & org.eclipse.jdt.internal.compiler.ast.ASTNode.IsForeachElementVariable) != 0) |
| ? localDeclaration.sourceEnd : localDeclaration.declarationSourceEnd; |
| int rightEnd = Math.max(typeEnd, sourceEnd); |
| /* |
| * There is extra work to do to set the proper type positions |
| * See PR http://bugs.eclipse.org/bugs/show_bug.cgi?id=23284 |
| */ |
| setTypeForSingleVariableDeclaration(variableDecl, type, extraDimensions); |
| variableDecl.setSourceRange(localDeclaration.declarationSourceStart, rightEnd - localDeclaration.declarationSourceStart + 1); |
| if (this.resolveBindings) { |
| recordNodes(name, localDeclaration); |
| recordNodes(variableDecl, localDeclaration); |
| variableDecl.resolveBinding(); |
| } |
| return variableDecl; |
| } |
| |
| private Dimension convertToDimensions(int start, int end, org.eclipse.jdt.internal.compiler.ast.Annotation[] annotation) { |
| int length = annotation == null ? 0 : annotation.length; |
| Dimension dimension = this.ast.newDimension(); |
| for (int i = 0; i < length; i++) { |
| Annotation annot = convert(annotation[i]); |
| dimension.annotations().add(annot); |
| } |
| retrieveDimensionAndSetPositions(start, end, dimension); |
| return dimension; |
| } |
| |
| protected VariableDeclarationFragment convertToVariableDeclarationFragment(org.eclipse.jdt.internal.compiler.ast.FieldDeclaration fieldDeclaration) { |
| final VariableDeclarationFragment variableDeclarationFragment = new VariableDeclarationFragment(this.ast); |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(fieldDeclaration.name)); |
| name.setSourceRange(fieldDeclaration.sourceStart, fieldDeclaration.sourceEnd - fieldDeclaration.sourceStart + 1); |
| variableDeclarationFragment.setName(name); |
| int start = fieldDeclaration.sourceEnd; |
| int end = start; |
| TypeReference typeReference = fieldDeclaration.type; |
| int extraDimensions = typeReference.extraDimensions(); |
| if (this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| setExtraAnnotatedDimensions(fieldDeclaration.sourceEnd + 1, fieldDeclaration.declarationSourceEnd, |
| typeReference, variableDeclarationFragment.extraDimensions(), extraDimensions); |
| } else { |
| internalSetExtraDimensions(variableDeclarationFragment, extraDimensions); |
| } |
| if (fieldDeclaration.initialization != null) { |
| final Expression expression = convert(fieldDeclaration.initialization); |
| variableDeclarationFragment.setInitializer(expression); |
| start = expression.getStartPosition() + expression.getLength(); |
| end = start - 1; |
| } else { |
| // we need to do it even if extendedDimension is null in case of syntax error in an array initializer |
| // need the exclusive range for retrieveEndOfPotentialExtendedDimensions |
| int possibleEnd = retrieveEndOfPotentialExtendedDimensions(start + 1, fieldDeclaration.sourceEnd, fieldDeclaration.declarationSourceEnd); |
| if (possibleEnd == Integer.MIN_VALUE) { |
| end = fieldDeclaration.declarationSourceEnd; |
| variableDeclarationFragment.setFlags(variableDeclarationFragment.getFlags() | ASTNode.MALFORMED); |
| } if (possibleEnd < 0) { |
| end = -possibleEnd; |
| variableDeclarationFragment.setFlags(variableDeclarationFragment.getFlags() | ASTNode.MALFORMED); |
| } else { |
| end = possibleEnd; |
| } |
| } |
| variableDeclarationFragment.setSourceRange(fieldDeclaration.sourceStart, end - fieldDeclaration.sourceStart + 1); |
| if (this.resolveBindings) { |
| recordNodes(name, fieldDeclaration); |
| recordNodes(variableDeclarationFragment, fieldDeclaration); |
| variableDeclarationFragment.resolveBinding(); |
| } |
| return variableDeclarationFragment; |
| } |
| |
| protected VariableDeclarationFragment convertToVariableDeclarationFragment(org.eclipse.jdt.internal.compiler.ast.LocalDeclaration localDeclaration) { |
| final VariableDeclarationFragment variableDeclarationFragment = new VariableDeclarationFragment(this.ast); |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(localDeclaration.name)); |
| name.setSourceRange(localDeclaration.sourceStart, localDeclaration.sourceEnd - localDeclaration.sourceStart + 1); |
| variableDeclarationFragment.setName(name); |
| int start = localDeclaration.sourceEnd; |
| org.eclipse.jdt.internal.compiler.ast.Expression initialization = localDeclaration.initialization; |
| TypeReference typeReference = localDeclaration.type; |
| int extraDimension = typeReference.extraDimensions(); |
| if (this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| setExtraAnnotatedDimensions(localDeclaration.sourceEnd + 1, this.compilationUnitSourceLength, |
| typeReference, variableDeclarationFragment.extraDimensions(), extraDimension); |
| } else { |
| internalSetExtraDimensions(variableDeclarationFragment, extraDimension); |
| } |
| |
| boolean hasInitialization = initialization != null; |
| int end; |
| if (hasInitialization) { |
| final Expression expression = convert(initialization); |
| variableDeclarationFragment.setInitializer(expression); |
| start = expression.getStartPosition() + expression.getLength(); |
| end = start - 1; |
| } else { |
| // we need to do it even if extendedDimension is null in case of syntax error in an array initializer |
| // start + 1 because we need the exclusive range for retrieveEndOfPotentialExtendedDimensions |
| int possibleEnd = retrieveEndOfPotentialExtendedDimensions(start + 1, localDeclaration.sourceEnd, localDeclaration.declarationSourceEnd); |
| if (possibleEnd == Integer.MIN_VALUE) { |
| end = start; |
| variableDeclarationFragment.setFlags(variableDeclarationFragment.getFlags() | ASTNode.MALFORMED); |
| } else if (possibleEnd < 0) { |
| end = -possibleEnd; |
| variableDeclarationFragment.setFlags(variableDeclarationFragment.getFlags() | ASTNode.MALFORMED); |
| } else { |
| end = possibleEnd; |
| } |
| } |
| variableDeclarationFragment.setSourceRange(localDeclaration.sourceStart, end - localDeclaration.sourceStart + 1); |
| if (this.resolveBindings) { |
| recordNodes(variableDeclarationFragment, localDeclaration); |
| recordNodes(name, localDeclaration); |
| variableDeclarationFragment.resolveBinding(); |
| } |
| return variableDeclarationFragment; |
| } |
| |
| protected void setExtraAnnotatedDimensions(int start, int end, TypeReference type, final List extraAnnotatedDimensions, int extraDimension) { |
| if (extraDimension > 0) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation[][] annotationsOnDims = type.getAnnotationsOnDimensions(true); |
| int length = (annotationsOnDims == null) ? 0 : annotationsOnDims.length; |
| for (int i = (length - extraDimension); i < length; i++) { |
| Dimension dim = convertToDimensions(start, end, (annotationsOnDims == null) ? null : annotationsOnDims[i]); |
| extraAnnotatedDimensions.add(dim); |
| start = dim.getStartPosition() + dim.getLength(); |
| } |
| } |
| } |
| |
| private void setTypeAnnotationsOnDimension(Dimension currentDimension, org.eclipse.jdt.internal.compiler.ast.Annotation[][] annotationsOnDimensions, int dimension) { |
| if (annotationsOnDimensions == null) return; |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = annotationsOnDimensions[dimension]; |
| if (annotations != null) { |
| for (int j = 0, length = annotations.length; j < length; j++) { |
| Annotation annotation = convert(annotations[j]); |
| currentDimension.annotations().add(annotation); |
| } |
| } |
| } |
| |
| private void setTypeAnnotationsAndSourceRangeOnArray(ArrayType arrayType, org.eclipse.jdt.internal.compiler.ast.Annotation[][] annotationsOnDimensions) { |
| List dimensions = arrayType.dimensions(); |
| Type elementType = arrayType.getElementType(); |
| |
| // Object[] a |
| // ^ |
| int start = elementType.getStartPosition(); |
| |
| // Object[] a |
| // ^ |
| int startArray = start + elementType.getLength(); |
| |
| // Object[] a |
| // ^ |
| int end = retrieveProperRightBracketPosition(dimensions.size(), startArray); |
| if (end == -1) { |
| end = startArray - 1; |
| } |
| arrayType.setSourceRange(start, end - start + 1); |
| |
| start = startArray; |
| for (int i = 0; i < dimensions.size(); i++) { |
| Dimension currentDimension = (Dimension) dimensions.get(i); |
| setTypeAnnotationsOnDimension(currentDimension, annotationsOnDimensions, i); |
| retrieveDimensionAndSetPositions(start, end, currentDimension); |
| start = currentDimension.getStartPosition() + currentDimension.getLength(); |
| } |
| } |
| |
| protected VariableDeclarationStatement convertToVariableDeclarationStatement(org.eclipse.jdt.internal.compiler.ast.LocalDeclaration localDeclaration) { |
| final VariableDeclarationFragment variableDeclarationFragment = convertToVariableDeclarationFragment(localDeclaration); |
| final VariableDeclarationStatement variableDeclarationStatement = new VariableDeclarationStatement(this.ast); |
| variableDeclarationStatement.fragments().add(variableDeclarationFragment); |
| variableDeclarationStatement.setSourceRange(localDeclaration.declarationSourceStart, localDeclaration.declarationSourceEnd - localDeclaration.declarationSourceStart + 1); |
| Type type = convertType(localDeclaration.type); |
| setTypeForVariableDeclarationStatement(variableDeclarationStatement, type, variableDeclarationFragment.getExtraDimensions()); |
| if (this.resolveBindings) { |
| recordNodes(variableDeclarationFragment, localDeclaration); |
| if (this.ast.apiLevel() >= AST.JLS10_INTERNAL && type.isVar()) { |
| Name varName = ((SimpleType) type).getName(); |
| recordNodes(varName, localDeclaration); |
| } |
| } |
| if (localDeclaration.modifiersSourceStart != -1) { |
| setModifiers(variableDeclarationStatement, localDeclaration); |
| } |
| return variableDeclarationStatement; |
| } |
| |
| private int annotateType(AnnotatableType type, org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations) { |
| int annotationsEnd = 0; |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| case AST.JLS4_INTERNAL: |
| type.setFlags(type.getFlags() | ASTNode.MALFORMED); |
| break; |
| default: |
| if (annotations == null) break; |
| int start = type.getStartPosition(); |
| int length = type.getLength(); |
| int annotationsLength = annotations.length; |
| for (int i = 0; i < annotationsLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation typeAnnotation = annotations[i]; |
| if (typeAnnotation != null) { |
| Annotation annotation = convert(typeAnnotation); |
| type.annotations().add(annotation); |
| annotationsEnd = annotation.getStartPosition() + annotation.getLength(); |
| } |
| } |
| int annotationsStart; |
| if (annotations[0] != null && (annotationsStart = annotations[0].sourceStart) < start && annotationsStart > 0) { |
| length += start - annotationsStart; |
| start = annotationsStart; |
| } |
| type.setSourceRange(start, length); |
| } |
| return annotationsEnd; |
| } |
| private void annotateTypeParameter(TypeParameter typeParameter, org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| case AST.JLS4_INTERNAL: |
| typeParameter.setFlags(typeParameter.getFlags() | ASTNode.MALFORMED); |
| break; |
| default: |
| int annotationsLength = annotations.length; |
| for (int i = 0; i < annotationsLength; i++) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation typeAnnotation = annotations[i]; |
| if (typeAnnotation != null) { |
| Annotation annotation = convert(typeAnnotation); |
| typeParameter.modifiers().add(annotation); |
| } |
| } |
| } |
| } |
| |
| public Type convertType(TypeReference typeReference) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations; |
| if (typeReference instanceof Wildcard) { |
| final Wildcard wildcard = (Wildcard) typeReference; |
| final WildcardType wildcardType = new WildcardType(this.ast); |
| if (wildcard.bound != null) { |
| final Type bound = convertType(wildcard.bound); |
| wildcardType.setBound(bound, wildcard.kind == Wildcard.EXTENDS); |
| int start = wildcard.sourceStart; |
| wildcardType.setSourceRange(start, bound.getStartPosition() + bound.getLength() - start); |
| } else { |
| final int start = wildcard.sourceStart; |
| final int end = wildcard.sourceEnd; |
| wildcardType.setSourceRange(start, end - start + 1); |
| } |
| if (this.resolveBindings) { |
| recordNodes(wildcardType, typeReference); |
| } |
| if (typeReference.annotations != null && (annotations = typeReference.annotations[0]) != null) { |
| annotateType(wildcardType, annotations); |
| } |
| return wildcardType; |
| } |
| Type type = null; |
| int sourceStart = typeReference.sourceStart; |
| int length = 0; |
| int dimensions = typeReference.dimensions(); |
| if (typeReference instanceof org.eclipse.jdt.internal.compiler.ast.SingleTypeReference) { |
| annotations = typeReference.annotations != null ? typeReference.annotations[0] : null; |
| int annotationsEnd = annotations != null ? annotations[annotations.length - 1].declarationSourceEnd + 1 : -1; |
| // this is either an ArrayTypeReference or a SingleTypeReference |
| char[] name = ((org.eclipse.jdt.internal.compiler.ast.SingleTypeReference) typeReference).getTypeName()[0]; |
| length = typeReference.sourceEnd - typeReference.sourceStart + 1; |
| // need to find out if this is an array type of primitive types or not |
| if (isPrimitiveType(name)) { |
| int[] positions = retrieveEndOfElementTypeNamePosition(sourceStart < annotationsEnd ? annotationsEnd : sourceStart, sourceStart + length); |
| int end = positions[1]; |
| if (end == -1) { |
| end = sourceStart + length - 1; |
| } |
| final PrimitiveType primitiveType = new PrimitiveType(this.ast); |
| primitiveType.setPrimitiveTypeCode(getPrimitiveTypeCode(name)); |
| primitiveType.setSourceRange(sourceStart, end - sourceStart + 1); |
| type = primitiveType; |
| if (typeReference.annotations != null && (annotations = typeReference.annotations[0]) != null) { |
| annotateType(primitiveType, annotations); |
| } |
| } else if (typeReference instanceof ParameterizedSingleTypeReference) { |
| ParameterizedSingleTypeReference parameterizedSingleTypeReference = (ParameterizedSingleTypeReference) typeReference; |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(name)); |
| int[] positions = retrieveEndOfElementTypeNamePosition(sourceStart < annotationsEnd ? annotationsEnd : sourceStart, sourceStart + length); |
| int end = positions[1]; |
| if (end == -1) { |
| end = sourceStart + length - 1; |
| } |
| if (positions[0] != -1) { |
| simpleName.setSourceRange(positions[0], end - positions[0] + 1); |
| } else { |
| simpleName.setSourceRange(sourceStart, end - sourceStart + 1); |
| } |
| |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| SimpleType simpleType = new SimpleType(this.ast); |
| simpleType.setName(simpleName); |
| simpleType.setFlags(simpleType.getFlags() | ASTNode.MALFORMED); |
| simpleType.setSourceRange(sourceStart, end - sourceStart + 1); |
| type = simpleType; |
| if (this.resolveBindings) { |
| this.recordNodes(simpleName, typeReference); |
| } |
| break; |
| default : |
| simpleType = new SimpleType(this.ast); |
| simpleType.setName(simpleName); |
| simpleType.setSourceRange(simpleName.getStartPosition(), simpleName.getLength()); |
| if (typeReference.annotations != null && (annotations = typeReference.annotations[0]) != null) { |
| annotateType(simpleType, annotations); |
| } |
| int newSourceStart = simpleType.getStartPosition(); |
| if (newSourceStart > 0 && newSourceStart < sourceStart) |
| sourceStart = newSourceStart; |
| final ParameterizedType parameterizedType = new ParameterizedType(this.ast); |
| parameterizedType.setType(simpleType); |
| type = parameterizedType; |
| TypeReference[] typeArguments = parameterizedSingleTypeReference.typeArguments; |
| if (typeArguments != null) { |
| Type type2 = null; |
| for (int i = 0, max = typeArguments.length; i < max; i++) { |
| type2 = convertType(typeArguments[i]); |
| ((ParameterizedType) type).typeArguments().add(type2); |
| end = type2.getStartPosition() + type2.getLength() - 1; |
| } |
| end = retrieveClosingAngleBracketPosition(end + 1); |
| type.setSourceRange(sourceStart, end - sourceStart + 1); |
| } else { |
| type.setSourceRange(sourceStart, end - sourceStart + 1); |
| } |
| if (this.resolveBindings) { |
| this.recordNodes(simpleName, typeReference); |
| this.recordNodes(simpleType, typeReference); |
| } |
| } |
| } else { |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(name)); |
| // we need to search for the starting position of the first brace in order to set the proper length |
| // PR http://dev.eclipse.org/bugs/show_bug.cgi?id=10759 |
| int[] positions = retrieveEndOfElementTypeNamePosition(sourceStart < annotationsEnd ? annotationsEnd : sourceStart, sourceStart + length); |
| int end = positions[1]; |
| if (end == -1) { |
| end = sourceStart + length - 1; |
| } |
| if (positions[0] != -1) { |
| simpleName.setSourceRange(positions[0], end - positions[0] + 1); |
| } else { |
| simpleName.setSourceRange(sourceStart, end - sourceStart + 1); |
| } |
| final SimpleType simpleType = new SimpleType(this.ast); |
| simpleType.setName(simpleName); |
| type = simpleType; |
| type.setSourceRange(sourceStart, end - sourceStart + 1); |
| type = simpleType; |
| if (this.resolveBindings) { |
| this.recordNodes(simpleName, typeReference); |
| } |
| if (typeReference.annotations != null && (annotations = typeReference.annotations[0]) != null) { |
| annotateType(simpleType, annotations); |
| } |
| } |
| if (dimensions != 0) { |
| type = convertToArray(type, sourceStart, length, dimensions, typeReference.getAnnotationsOnDimensions(true)); |
| if (this.resolveBindings) { |
| // store keys for inner types |
| completeRecord((ArrayType) type, typeReference); |
| } |
| } |
| } else { |
| if (typeReference instanceof ParameterizedQualifiedTypeReference) { |
| ParameterizedQualifiedTypeReference parameterizedQualifiedTypeReference = (ParameterizedQualifiedTypeReference) typeReference; |
| char[][] tokens = parameterizedQualifiedTypeReference.tokens; |
| TypeReference[][] typeArguments = parameterizedQualifiedTypeReference.typeArguments; |
| org.eclipse.jdt.internal.compiler.ast.Annotation[][] typeAnnotations = parameterizedQualifiedTypeReference.annotations; |
| TypeReference[] arguments = null; |
| int lenth = tokens.length; |
| int firstTypeIndex = lenth - 1; |
| long[] positions = parameterizedQualifiedTypeReference.sourcePositions; |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : { |
| char[][] name = ((org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference) typeReference).getTypeName(); |
| int nameLength = name.length; |
| sourceStart = (int)(positions[0]>>>32); |
| length = (int)(positions[nameLength - 1] & 0xFFFFFFFF) - sourceStart + 1; |
| Name qualifiedName = this.setQualifiedNameNameAndSourceRanges(name, positions, typeReference); |
| final SimpleType simpleType = new SimpleType(this.ast); |
| simpleType.setName(qualifiedName); |
| simpleType.setSourceRange(sourceStart, length); |
| simpleType.setFlags(simpleType.getFlags() | ASTNode.MALFORMED); |
| type = simpleType; |
| } |
| break; |
| default : |
| boolean isTypeArgumentBased = false; |
| for (int i = 0; i < lenth; ++i) { |
| if (typeArguments != null && typeArguments[i] != null) { |
| firstTypeIndex = i; |
| isTypeArgumentBased = true; |
| break; |
| } |
| if (typeAnnotations != null && typeAnnotations[i] != null) { |
| firstTypeIndex = i; |
| isTypeArgumentBased = false; |
| break; |
| } |
| } |
| int start = (int) (positions[0] >>> 32); |
| int end = (int) positions[firstTypeIndex]; |
| |
| Type currentType = createBaseType(typeReference, positions, typeAnnotations, tokens, lenth, firstTypeIndex, isTypeArgumentBased); |
| int indexOfEnclosingType = 1; |
| if (typeArguments != null && (arguments = typeArguments[firstTypeIndex]) != null) { |
| int arglen = arguments.length; |
| ParameterizedType parameterizedType = new ParameterizedType(this.ast); |
| parameterizedType.index = indexOfEnclosingType; |
| parameterizedType.setType(currentType); |
| if (this.resolveBindings) { |
| recordNodes(parameterizedType, typeReference); |
| } |
| Type type2 = null; |
| for (int i = 0; i < arglen; ++i ) { |
| type2 = convertType(arguments[i]); |
| parameterizedType.typeArguments().add(type2); |
| } |
| end = type2 != null ? type2.getStartPosition() + type2.getLength() - 1 : end; |
| end = retrieveClosingAngleBracketPosition(end + 1); |
| int baseStart = currentType.getStartPosition(); |
| start = start <= baseStart ? start : baseStart; |
| parameterizedType.setSourceRange(start, end - start + 1); |
| currentType = parameterizedType; |
| } |
| |
| for (int i = firstTypeIndex + 1; i < lenth; ++i) { |
| SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.setIdentifier(new String(tokens[i])); |
| simpleName.index = i + 1; |
| start = (int) (positions[i] >>> 32); |
| end = (int) positions[i]; |
| simpleName.setSourceRange(start, end - start + 1); |
| recordPendingNameScopeResolution(simpleName); |
| QualifiedType qualifiedType = new QualifiedType(this.ast); |
| qualifiedType.setQualifier(currentType); |
| qualifiedType.setName(simpleName); |
| start = currentType.getStartPosition(); |
| end = simpleName.getStartPosition() + simpleName.getLength() - 1; |
| qualifiedType.setSourceRange(start, end - start + 1); |
| if (typeAnnotations != null && (annotations = typeAnnotations[i]) != null) { |
| int nextPosition = annotateType(qualifiedType, annotations); |
| if (simpleName.getStartPosition() < nextPosition && nextPosition <= end) { |
| simpleName.setSourceRange(nextPosition, end - nextPosition + 1); |
| trimWhiteSpacesAndComments(simpleName); |
| } |
| } |
| if (this.resolveBindings) { |
| recordNodes(simpleName, typeReference); |
| recordNodes(qualifiedType, typeReference); |
| } |
| currentType = qualifiedType; |
| indexOfEnclosingType++; |
| |
| if (typeArguments != null && (arguments = typeArguments[i]) != null) { |
| int arglen = arguments.length; |
| qualifiedType.index = indexOfEnclosingType; |
| ParameterizedType parameterizedType = new ParameterizedType(this.ast); |
| parameterizedType.index = indexOfEnclosingType; |
| parameterizedType.setType(currentType); |
| if (this.resolveBindings) { |
| recordNodes(parameterizedType, typeReference); |
| } |
| Type type2 = null; |
| for (int j = 0; j < arglen; ++j ) { |
| type2 = convertType(arguments[j]); |
| parameterizedType.typeArguments().add(type2); |
| } |
| end = type2 != null ? type2.getStartPosition() + type2.getLength() - 1 : end; |
| end = retrieveClosingAngleBracketPosition(end + 1); |
| parameterizedType.setSourceRange(start, end - start + 1); |
| currentType = parameterizedType; |
| } else { |
| qualifiedType.index = indexOfEnclosingType; |
| } |
| } |
| type = currentType; |
| } |
| } else if (typeReference instanceof org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference) { |
| QualifiedTypeReference qualifiedTypeReference = (QualifiedTypeReference) typeReference; |
| long[] positions = ((org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference) typeReference).sourcePositions; |
| org.eclipse.jdt.internal.compiler.ast.Annotation [][] typeAnnotations = typeReference.annotations; |
| char [][] tokens = qualifiedTypeReference.tokens; |
| int lenth = tokens.length; |
| int firstTypeIndex = lenth; |
| |
| if (typeAnnotations != null) { |
| for (int i = 0; i < lenth; ++i) { |
| if (typeAnnotations[i] != null) { |
| firstTypeIndex = i; |
| break; |
| } |
| } |
| } |
| Type currentType = createBaseType(typeReference, positions, typeAnnotations, tokens, lenth, firstTypeIndex, false); |
| for (int i = firstTypeIndex + 1; i < lenth; ++i) { |
| currentType = createQualifiedType(typeReference, positions, typeAnnotations, tokens, i, currentType); |
| } |
| type = currentType; |
| } else if (typeReference instanceof UnionTypeReference){ |
| TypeReference[] typeReferences = ((org.eclipse.jdt.internal.compiler.ast.UnionTypeReference) typeReference).typeReferences; |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| // recovery |
| type = this.convertType(typeReferences[0]); |
| int start = typeReference.sourceStart; |
| int endPosition = typeReference.sourceEnd; |
| length = endPosition - start + 1; |
| type.setSourceRange(start, length); |
| type.setFlags(type.getFlags() | ASTNode.MALFORMED); |
| break; |
| default: |
| // union type reference |
| final UnionType unionType = new UnionType(this.ast); |
| for (int i = 0, max = typeReferences.length; i < max; i++) { |
| unionType.types().add(this.convertType(typeReferences[i])); |
| } |
| type = unionType; |
| List types = unionType.types(); |
| int size = types.size(); |
| start = ((Type) types.get(0)).getStartPosition(); |
| Type lastType = (Type) types.get(size - 1); |
| endPosition = lastType.getStartPosition() + lastType.getLength(); |
| length = endPosition - start; /* + 1 - 1 == 0 */ |
| type.setSourceRange(start, length); |
| } |
| } else if (typeReference instanceof IntersectionCastTypeReference) { |
| TypeReference[] typeReferences = ((IntersectionCastTypeReference) typeReference).typeReferences; |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| case AST.JLS4_INTERNAL : |
| type = this.convertType(typeReferences[0]); |
| int start = typeReference.sourceStart; |
| int endPosition = typeReference.sourceEnd; |
| length = endPosition - start + 1; |
| type.setSourceRange(start, length); |
| type.setFlags(type.getFlags() | ASTNode.MALFORMED); |
| break; |
| default: |
| // intersection type reference |
| final IntersectionType castType = new IntersectionType(this.ast); |
| for (int i = 0, max = typeReferences.length; i < max; i++) { |
| castType.types().add(this.convertType(typeReferences[i])); |
| } |
| type = castType; |
| List types = castType.types(); |
| int size = types.size(); |
| start = ((Type) types.get(0)).getStartPosition(); |
| Type lastType = (Type) types.get(size - 1); |
| endPosition = lastType.getStartPosition() + lastType.getLength(); |
| length = endPosition - start; |
| type.setSourceRange(start, length); |
| } |
| } |
| |
| length = typeReference.sourceEnd - sourceStart + 1; |
| if (dimensions != 0) { |
| type = convertToArray(type, sourceStart, length, dimensions, typeReference.getAnnotationsOnDimensions(true)); |
| if (this.resolveBindings) { |
| completeRecord((ArrayType) type, typeReference); |
| } |
| } |
| } |
| if (this.resolveBindings) { |
| this.recordNodes(type, typeReference); |
| } |
| boolean sawDiamond = false; |
| if (typeReference instanceof ParameterizedSingleTypeReference) { |
| ParameterizedSingleTypeReference pstr = (ParameterizedSingleTypeReference) typeReference; |
| if (pstr.typeArguments == TypeReference.NO_TYPE_ARGUMENTS) { |
| sawDiamond = true; |
| } |
| } else if (typeReference instanceof ParameterizedQualifiedTypeReference) { |
| ParameterizedQualifiedTypeReference pqtr = (ParameterizedQualifiedTypeReference) typeReference; |
| for (int i = 0, len = pqtr.typeArguments.length; i < len; i++) { |
| if (pqtr.typeArguments[i] == TypeReference.NO_TYPE_ARGUMENTS) { |
| sawDiamond = true; |
| break; |
| } |
| } |
| } |
| if (sawDiamond) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| case AST.JLS3_INTERNAL : |
| type.setFlags(type.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| return type; |
| } |
| |
| private Type createBaseType(TypeReference typeReference, long[] positions, |
| org.eclipse.jdt.internal.compiler.ast.Annotation[][] typeAnnotations, char[][] tokens, int lenth, |
| int firstTypeIndex, boolean isTypeArgumentBased) { |
| Type currentType; |
| Name name = null; |
| if (firstTypeIndex == 0) { |
| name = createSimpleName(typeReference, positions, tokens, 0 ); |
| currentType = createSimpleType(name, typeReference, positions, 0, 0); |
| setSourceRangeAnnotationsAndRecordNodes(typeReference, (SimpleType) currentType, positions, typeAnnotations, 0, 0, name.index > 0 ? name.index - 1 : 0); |
| } else if (firstTypeIndex == lenth) {//Just a QualifiedName |
| name = setQualifiedNameNameAndSourceRanges(tokens, positions, firstTypeIndex - 1, typeReference); |
| currentType = createSimpleType(name, typeReference, positions, 0, firstTypeIndex - 1); |
| } else if (isTypeArgumentBased && (typeAnnotations == null || typeAnnotations[firstTypeIndex] == null)) { |
| name = setQualifiedNameNameAndSourceRanges(tokens, positions, firstTypeIndex, typeReference); |
| currentType = createSimpleType(name, typeReference, positions, 0, firstTypeIndex); |
| } else { |
| if (firstTypeIndex == 1) { |
| name = createSimpleName(typeReference, positions, tokens, 0 ); |
| } else { |
| name = setQualifiedNameNameAndSourceRanges(tokens, positions, firstTypeIndex - 1, typeReference); |
| } |
| |
| boolean createNameQualifiedType = typeAnnotations != null && typeAnnotations[firstTypeIndex] != null; |
| if (createNameQualifiedType && this.ast.apiLevel >= AST.JLS8_INTERNAL) { |
| NameQualifiedType nameQualifiedType = new NameQualifiedType(this.ast); |
| nameQualifiedType.setQualifier(name); |
| nameQualifiedType.setName(createSimpleName(typeReference, positions, tokens, firstTypeIndex)); |
| setSourceRangeAnnotationsAndRecordNodes(typeReference, nameQualifiedType, positions, typeAnnotations, firstTypeIndex, 0, firstTypeIndex); |
| currentType = nameQualifiedType; |
| } else { |
| SimpleType simpleType = this.ast.newSimpleType(name); |
| setSourceRangeAnnotationsAndRecordNodes(typeReference, simpleType, positions, typeAnnotations, 0, 0, name.index > 0 ? name.index - 1 : 0); |
| currentType = createQualifiedType(typeReference, positions, typeAnnotations, tokens, firstTypeIndex, simpleType); |
| if (createNameQualifiedType) |
| currentType.setFlags(currentType.getFlags() | ASTNode.MALFORMED); |
| } |
| } |
| return currentType; |
| } |
| |
| private QualifiedType createQualifiedType(TypeReference typeReference, long[] positions, |
| org.eclipse.jdt.internal.compiler.ast.Annotation[][] typeAnnotations, char[][] tokens, int index, |
| Type qualifier) { |
| SimpleName simpleName = createSimpleName(typeReference, positions, tokens, index); |
| QualifiedType qualifiedType = new QualifiedType(this.ast); |
| qualifiedType.setQualifier(qualifier); |
| qualifiedType.setName(simpleName); |
| int start = qualifier.getStartPosition(); |
| int end = simpleName.getStartPosition() + simpleName.getLength() - 1; |
| setSourceRangeAnnotationsAndRecordNodes(typeReference, qualifiedType, typeAnnotations, index, start, end); |
| return qualifiedType; |
| } |
| |
| private SimpleType createSimpleType(Name name, TypeReference typeReference, long[] positions, |
| int startIndex, int endIndex) { |
| SimpleType simpleType = new SimpleType(this.ast); |
| simpleType.setName(name); |
| int start = (int)(positions[startIndex] >>> 32); |
| int end = (int)positions[endIndex]; |
| simpleType.setSourceRange(start, end - start + 1); |
| if (this.resolveBindings) { |
| recordNodes(simpleType, typeReference); |
| } |
| return simpleType; |
| } |
| |
| private void setSourceRangeAnnotationsAndRecordNodes(TypeReference typeReference, AnnotatableType annotatableType, |
| org.eclipse.jdt.internal.compiler.ast.Annotation[][] typeAnnotations, int index, int start, int end) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations; |
| int length = end - start + 1; |
| annotatableType.setSourceRange(start, length); |
| if (typeAnnotations != null && (annotations = typeAnnotations[index]) != null) { |
| annotateType(annotatableType, annotations); |
| } |
| if (this.resolveBindings) { |
| recordNodes(annotatableType, typeReference); |
| } |
| } |
| |
| private void setSourceRangeAnnotationsAndRecordNodes(TypeReference typeReference, AnnotatableType annotatableType, |
| long[] positions, org.eclipse.jdt.internal.compiler.ast.Annotation[][] typeAnnotations, int index, int startIndex, int endIndex) { |
| int start = (int) (positions[startIndex] >>> 32); |
| int end = (int) positions[endIndex]; |
| setSourceRangeAnnotationsAndRecordNodes(typeReference, annotatableType, typeAnnotations, index, start, end); |
| } |
| |
| private SimpleName createSimpleName(TypeReference typeReference, long[] positions, char[][] tokens, int index) { |
| final SimpleName simpleName = new SimpleName(this.ast); |
| simpleName.internalSetIdentifier(new String(tokens[index])); |
| recordPendingNameScopeResolution(simpleName); |
| int start = (int) (positions[index] >>> 32); |
| int end = (int) positions[index]; |
| simpleName.setSourceRange(start, end - start + 1); |
| simpleName.index = index + 1; |
| if (this.resolveBindings) { |
| recordNodes(simpleName, typeReference); |
| } |
| return simpleName; |
| } |
| |
| protected Comment createComment(int[] positions) { |
| // Create comment node |
| Comment comment = null; |
| int start = positions[0]; |
| int end = positions[1]; |
| if (positions[1]>0) { // Javadoc comments have positive end position |
| Javadoc docComment = this.docParser.parse(positions); |
| if (docComment == null) return null; |
| comment = docComment; |
| } else { |
| end = -end; |
| if (positions[0] == 0) { // we cannot know without testing chars again |
| if (this.docParser.scanner.source[1] == '/') { |
| comment = new LineComment(this.ast); |
| } else { |
| comment = new BlockComment(this.ast); |
| } |
| } |
| else if (positions[0]>0) { // Block comment have positive start position |
| comment = new BlockComment(this.ast); |
| } else { // Line comment have negative start and end position |
| start = -start; |
| comment = new LineComment(this.ast); |
| } |
| comment.setSourceRange(start, end - start); |
| } |
| return comment; |
| } |
| |
| protected Statement createFakeEmptyStatement(org.eclipse.jdt.internal.compiler.ast.Statement statement) { |
| if (statement == null) return null; |
| EmptyStatement emptyStatement = new EmptyStatement(this.ast); |
| emptyStatement.setFlags(emptyStatement.getFlags() | ASTNode.MALFORMED); |
| int start = statement.sourceStart; |
| int end = statement.sourceEnd; |
| emptyStatement.setSourceRange(start, end - start + 1); |
| return emptyStatement; |
| } |
| |
| /** |
| * Warning: Callers of this method must ensure that the fake literal node is not recorded in |
| * {@link #recordNodes(ASTNode, org.eclipse.jdt.internal.compiler.ast.ASTNode)}, see bug 403444! |
| */ |
| protected Expression createFakeNullLiteral(org.eclipse.jdt.internal.compiler.ast.FunctionalExpression expression) { |
| if (this.referenceContext != null) { |
| this.referenceContext.setFlags(this.referenceContext.getFlags() | ASTNode.MALFORMED); |
| } |
| NullLiteral nullLiteral = new NullLiteral(this.ast); |
| nullLiteral.setFlags(nullLiteral.getFlags() | ASTNode.MALFORMED); |
| nullLiteral.setSourceRange(expression.sourceStart, expression.sourceEnd - expression.sourceStart + 1); |
| return nullLiteral; |
| } |
| |
| /** |
| * @return a new modifier |
| */ |
| private Modifier createModifier(ModifierKeyword keyword) { |
| final Modifier modifier = new Modifier(this.ast); |
| modifier.setKeyword(keyword); |
| int start = this.scanner.getCurrentTokenStartPosition(); |
| int end = this.scanner.getCurrentTokenEndPosition(); |
| modifier.setSourceRange(start, end - start + 1); |
| return modifier; |
| } |
| |
| /** |
| * @return a new module modifier |
| */ |
| private ModuleModifier createModuleModifier(ModuleModifierKeyword keyword) { |
| final ModuleModifier modifier = new ModuleModifier(this.ast); |
| modifier.setKeyword(keyword); |
| int start = this.scanner.getCurrentTokenStartPosition(); |
| int end = this.scanner.getCurrentTokenEndPosition(); |
| modifier.setSourceRange(start, end - start + 1); |
| return modifier; |
| } |
| |
| protected InfixExpression.Operator getOperatorFor(int operatorID) { |
| switch (operatorID) { |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.EQUAL_EQUAL : |
| return InfixExpression.Operator.EQUALS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.LESS_EQUAL : |
| return InfixExpression.Operator.LESS_EQUALS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.GREATER_EQUAL : |
| return InfixExpression.Operator.GREATER_EQUALS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.NOT_EQUAL : |
| return InfixExpression.Operator.NOT_EQUALS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.LEFT_SHIFT : |
| return InfixExpression.Operator.LEFT_SHIFT; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.RIGHT_SHIFT : |
| return InfixExpression.Operator.RIGHT_SHIFT_SIGNED; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.UNSIGNED_RIGHT_SHIFT : |
| return InfixExpression.Operator.RIGHT_SHIFT_UNSIGNED; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.OR_OR : |
| return InfixExpression.Operator.CONDITIONAL_OR; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.AND_AND : |
| return InfixExpression.Operator.CONDITIONAL_AND; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.PLUS : |
| return InfixExpression.Operator.PLUS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MINUS : |
| return InfixExpression.Operator.MINUS; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.REMAINDER : |
| return InfixExpression.Operator.REMAINDER; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.XOR : |
| return InfixExpression.Operator.XOR; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.AND : |
| return InfixExpression.Operator.AND; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.MULTIPLY : |
| return InfixExpression.Operator.TIMES; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.OR : |
| return InfixExpression.Operator.OR; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.DIVIDE : |
| return InfixExpression.Operator.DIVIDE; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.GREATER : |
| return InfixExpression.Operator.GREATER; |
| case org.eclipse.jdt.internal.compiler.ast.OperatorIds.LESS : |
| return InfixExpression.Operator.LESS; |
| } |
| return null; |
| } |
| |
| protected PrimitiveType.Code getPrimitiveTypeCode(char[] name) { |
| switch(name[0]) { |
| case 'i' : |
| if (name.length == 3 && name[1] == 'n' && name[2] == 't') { |
| return PrimitiveType.INT; |
| } |
| break; |
| case 'l' : |
| if (name.length == 4 && name[1] == 'o' && name[2] == 'n' && name[3] == 'g') { |
| return PrimitiveType.LONG; |
| } |
| break; |
| case 'd' : |
| if (name.length == 6 |
| && name[1] == 'o' |
| && name[2] == 'u' |
| && name[3] == 'b' |
| && name[4] == 'l' |
| && name[5] == 'e') { |
| return PrimitiveType.DOUBLE; |
| } |
| break; |
| case 'f' : |
| if (name.length == 5 |
| && name[1] == 'l' |
| && name[2] == 'o' |
| && name[3] == 'a' |
| && name[4] == 't') { |
| return PrimitiveType.FLOAT; |
| } |
| break; |
| case 'b' : |
| if (name.length == 4 |
| && name[1] == 'y' |
| && name[2] == 't' |
| && name[3] == 'e') { |
| return PrimitiveType.BYTE; |
| } else |
| if (name.length == 7 |
| && name[1] == 'o' |
| && name[2] == 'o' |
| && name[3] == 'l' |
| && name[4] == 'e' |
| && name[5] == 'a' |
| && name[6] == 'n') { |
| return PrimitiveType.BOOLEAN; |
| } |
| break; |
| case 'c' : |
| if (name.length == 4 |
| && name[1] == 'h' |
| && name[2] == 'a' |
| && name[3] == 'r') { |
| return PrimitiveType.CHAR; |
| } |
| break; |
| case 's' : |
| if (name.length == 5 |
| && name[1] == 'h' |
| && name[2] == 'o' |
| && name[3] == 'r' |
| && name[4] == 't') { |
| return PrimitiveType.SHORT; |
| } |
| break; |
| case 'v' : |
| if (name.length == 4 |
| && name[1] == 'o' |
| && name[2] == 'i' |
| && name[3] == 'd') { |
| return PrimitiveType.VOID; |
| } |
| } |
| return null; // cannot be reached |
| } |
| |
| protected boolean isPrimitiveType(char[] name) { |
| switch(name[0]) { |
| case 'i' : |
| if (name.length == 3 && name[1] == 'n' && name[2] == 't') { |
| return true; |
| } |
| return false; |
| case 'l' : |
| if (name.length == 4 && name[1] == 'o' && name[2] == 'n' && name[3] == 'g') { |
| return true; |
| } |
| return false; |
| case 'd' : |
| if (name.length == 6 |
| && name[1] == 'o' |
| && name[2] == 'u' |
| && name[3] == 'b' |
| && name[4] == 'l' |
| && name[5] == 'e') { |
| return true; |
| } |
| return false; |
| case 'f' : |
| if (name.length == 5 |
| && name[1] == 'l' |
| && name[2] == 'o' |
| && name[3] == 'a' |
| && name[4] == 't') { |
| return true; |
| } |
| return false; |
| case 'b' : |
| if (name.length == 4 |
| && name[1] == 'y' |
| && name[2] == 't' |
| && name[3] == 'e') { |
| return true; |
| } else |
| if (name.length == 7 |
| && name[1] == 'o' |
| && name[2] == 'o' |
| && name[3] == 'l' |
| && name[4] == 'e' |
| && name[5] == 'a' |
| && name[6] == 'n') { |
| return true; |
| } |
| return false; |
| case 'c' : |
| if (name.length == 4 |
| && name[1] == 'h' |
| && name[2] == 'a' |
| && name[3] == 'r') { |
| return true; |
| } |
| return false; |
| case 's' : |
| if (name.length == 5 |
| && name[1] == 'h' |
| && name[2] == 'o' |
| && name[3] == 'r' |
| && name[4] == 't') { |
| return true; |
| } |
| return false; |
| case 'v' : |
| if (name.length == 4 |
| && name[1] == 'o' |
| && name[2] == 'i' |
| && name[3] == 'd') { |
| return true; |
| } |
| return false; |
| } |
| return false; |
| } |
| private void lookupForScopes() { |
| if (this.pendingNameScopeResolution != null) { |
| for (Iterator iterator = this.pendingNameScopeResolution.iterator(); iterator.hasNext(); ) { |
| Name name = (Name) iterator.next(); |
| this.ast.getBindingResolver().recordScope(name, lookupScope(name)); |
| } |
| } |
| if (this.pendingThisExpressionScopeResolution != null) { |
| for (Iterator iterator = this.pendingThisExpressionScopeResolution.iterator(); iterator.hasNext(); ) { |
| ThisExpression thisExpression = (ThisExpression) iterator.next(); |
| this.ast.getBindingResolver().recordScope(thisExpression, lookupScope(thisExpression)); |
| } |
| } |
| |
| } |
| |
| private BlockScope lookupScope(ASTNode node) { |
| ASTNode currentNode = node; |
| while(currentNode != null |
| &&!(currentNode instanceof MethodDeclaration) |
| && !(currentNode instanceof Initializer) |
| && !(currentNode instanceof FieldDeclaration) |
| && !(currentNode instanceof AbstractTypeDeclaration)) { |
| currentNode = currentNode.getParent(); |
| } |
| if (currentNode == null) { |
| return null; |
| } |
| if (currentNode instanceof Initializer) { |
| Initializer initializer = (Initializer) currentNode; |
| while(!(currentNode instanceof AbstractTypeDeclaration)) { |
| currentNode = currentNode.getParent(); |
| } |
| if (currentNode instanceof TypeDeclaration |
| || currentNode instanceof EnumDeclaration |
| || currentNode instanceof AnnotationTypeDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDecl = (org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) this.ast.getBindingResolver().getCorrespondingNode(currentNode); |
| if ((initializer.getModifiers() & Modifier.STATIC) != 0) { |
| return typeDecl.staticInitializerScope; |
| } else { |
| return typeDecl.initializerScope; |
| } |
| } |
| } else if (currentNode instanceof FieldDeclaration) { |
| FieldDeclaration fieldDeclaration = (FieldDeclaration) currentNode; |
| while(!(currentNode instanceof AbstractTypeDeclaration)) { |
| currentNode = currentNode.getParent(); |
| } |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDecl = (org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) this.ast.getBindingResolver().getCorrespondingNode(currentNode); |
| if ((fieldDeclaration.getModifiers() & Modifier.STATIC) != 0) { |
| return typeDecl.staticInitializerScope; |
| } else { |
| return typeDecl.initializerScope; |
| } |
| } else if (currentNode instanceof AbstractTypeDeclaration) { |
| org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDecl = (org.eclipse.jdt.internal.compiler.ast.TypeDeclaration) this.ast.getBindingResolver().getCorrespondingNode(currentNode); |
| return typeDecl.initializerScope; |
| } |
| AbstractMethodDeclaration abstractMethodDeclaration = (AbstractMethodDeclaration) this.ast.getBindingResolver().getCorrespondingNode(currentNode); |
| return abstractMethodDeclaration.scope; |
| } |
| |
| protected void recordName(Name name, org.eclipse.jdt.internal.compiler.ast.ASTNode compilerNode) { |
| if (compilerNode != null) { |
| recordNodes(name, compilerNode); |
| if (compilerNode instanceof org.eclipse.jdt.internal.compiler.ast.TypeReference) { |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeRef = (org.eclipse.jdt.internal.compiler.ast.TypeReference) compilerNode; |
| if (name.isQualifiedName()) { |
| SimpleName simpleName = null; |
| while (name.isQualifiedName()) { |
| simpleName = ((QualifiedName) name).getName(); |
| recordNodes(simpleName, typeRef); |
| name = ((QualifiedName) name).getQualifier(); |
| recordNodes(name, typeRef); |
| } |
| } |
| } |
| } |
| } |
| |
| protected void recordNodes(ASTNode node, org.eclipse.jdt.internal.compiler.ast.ASTNode oldASTNode) { |
| // Do not record the fake literal node created in lieu of functional expressions at JLS levels < 8, as it would lead to CCE down the road. |
| if (oldASTNode instanceof org.eclipse.jdt.internal.compiler.ast.FunctionalExpression && node instanceof NullLiteral) { |
| return; |
| } |
| this.ast.getBindingResolver().store(node, oldASTNode); |
| } |
| |
| protected void recordNodes(org.eclipse.jdt.internal.compiler.ast.Javadoc javadoc, TagElement tagElement) { |
| Iterator fragments = tagElement.fragments().listIterator(); |
| while (fragments.hasNext()) { |
| ASTNode node = (ASTNode) fragments.next(); |
| if (node.getNodeType() == ASTNode.MEMBER_REF) { |
| MemberRef memberRef = (MemberRef) node; |
| Name name = memberRef.getName(); |
| // get compiler node and record nodes |
| int start = name.getStartPosition(); |
| org.eclipse.jdt.internal.compiler.ast.ASTNode compilerNode = javadoc.getNodeStartingAt(start); |
| if (compilerNode!= null) { |
| recordNodes(name, compilerNode); |
| recordNodes(node, compilerNode); |
| } |
| // Replace qualifier to have all nodes recorded |
| if (memberRef.getQualifier() != null) { |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeRef = null; |
| if (compilerNode instanceof JavadocFieldReference) { |
| org.eclipse.jdt.internal.compiler.ast.Expression expression = ((JavadocFieldReference)compilerNode).receiver; |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.TypeReference) { |
| typeRef = (org.eclipse.jdt.internal.compiler.ast.TypeReference) expression; |
| } |
| } |
| else if (compilerNode instanceof JavadocMessageSend) { |
| org.eclipse.jdt.internal.compiler.ast.Expression expression = ((JavadocMessageSend)compilerNode).receiver; |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.TypeReference) { |
| typeRef = (org.eclipse.jdt.internal.compiler.ast.TypeReference) expression; |
| } |
| } |
| if (typeRef != null) { |
| recordName(memberRef.getQualifier(), typeRef); |
| } |
| } |
| } else if (node.getNodeType() == ASTNode.METHOD_REF) { |
| MethodRef methodRef = (MethodRef) node; |
| Name name = methodRef.getName(); |
| // get method name start position |
| int start = methodRef.getStartPosition(); |
| this.scanner.resetTo(start, start + name.getStartPosition()+name.getLength()); |
| int token; |
| try { |
| nextToken: while((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF && token != TerminalTokens.TokenNameLPAREN) { |
| if (token == TerminalTokens.TokenNameERROR && this.scanner.currentCharacter == '#') { |
| start = this.scanner.getCurrentTokenEndPosition()+1; |
| break nextToken; |
| } |
| } |
| } |
| catch(InvalidInputException e) { |
| // ignore |
| } |
| // get compiler node and record nodes |
| org.eclipse.jdt.internal.compiler.ast.ASTNode compilerNode = javadoc.getNodeStartingAt(start); |
| // record nodes |
| if (compilerNode != null) { |
| recordNodes(methodRef, compilerNode); |
| // get type ref |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeRef = null; |
| if (compilerNode instanceof org.eclipse.jdt.internal.compiler.ast.JavadocAllocationExpression) { |
| typeRef = ((org.eclipse.jdt.internal.compiler.ast.JavadocAllocationExpression)compilerNode).type; |
| if (typeRef != null) recordNodes(name, compilerNode); |
| } |
| else if (compilerNode instanceof org.eclipse.jdt.internal.compiler.ast.JavadocMessageSend) { |
| org.eclipse.jdt.internal.compiler.ast.Expression expression = ((org.eclipse.jdt.internal.compiler.ast.JavadocMessageSend)compilerNode).receiver; |
| if (expression instanceof org.eclipse.jdt.internal.compiler.ast.TypeReference) { |
| typeRef = (org.eclipse.jdt.internal.compiler.ast.TypeReference) expression; |
| } |
| recordNodes(name, compilerNode); |
| } |
| // record name and qualifier |
| if (typeRef != null && methodRef.getQualifier() != null) { |
| recordName(methodRef.getQualifier(), typeRef); |
| } |
| } |
| // Resolve parameters |
| Iterator parameters = methodRef.parameters().listIterator(); |
| while (parameters.hasNext()) { |
| MethodRefParameter param = (MethodRefParameter) parameters.next(); |
| org.eclipse.jdt.internal.compiler.ast.Expression expression = (org.eclipse.jdt.internal.compiler.ast.Expression) javadoc.getNodeStartingAt(param.getStartPosition()); |
| if (expression != null) { |
| recordNodes(param, expression); |
| if (expression instanceof JavadocArgumentExpression) { |
| JavadocArgumentExpression argExpr = (JavadocArgumentExpression) expression; |
| org.eclipse.jdt.internal.compiler.ast.TypeReference typeRef = argExpr.argument.type; |
| if (this.ast.apiLevel >= AST.JLS3_INTERNAL) { |
| param.setVarargs(argExpr.argument.isVarArgs()); |
| } |
| recordNodes(param.getType(), typeRef); |
| if (param.getType().isSimpleType()) { |
| recordName(((SimpleType)param.getType()).getName(), typeRef); |
| } else if (param.getType().isArrayType()) { |
| Type type = ((ArrayType) param.getType()).getElementType(); |
| recordNodes(type, typeRef); |
| if (type.isSimpleType()) { |
| recordName(((SimpleType)type).getName(), typeRef); |
| } |
| } |
| } |
| } |
| } |
| } else if (node.getNodeType() == ASTNode.SIMPLE_NAME || |
| node.getNodeType() == ASTNode.QUALIFIED_NAME) { |
| org.eclipse.jdt.internal.compiler.ast.ASTNode compilerNode = javadoc.getNodeStartingAt(node.getStartPosition()); |
| recordName((Name) node, compilerNode); |
| } else if (node.getNodeType() == ASTNode.TAG_ELEMENT) { |
| // resolve member and method references binding |
| recordNodes(javadoc, (TagElement) node); |
| } |
| } |
| } |
| |
| protected void recordPendingNameScopeResolution(Name name) { |
| if (this.pendingNameScopeResolution == null) { |
| this.pendingNameScopeResolution = new HashSet(); |
| } |
| this.pendingNameScopeResolution.add(name); |
| } |
| |
| protected void recordPendingThisExpressionScopeResolution(ThisExpression thisExpression) { |
| if (this.pendingThisExpressionScopeResolution == null) { |
| this.pendingThisExpressionScopeResolution = new HashSet(); |
| } |
| this.pendingThisExpressionScopeResolution.add(thisExpression); |
| } |
| |
| /** |
| * Remove whitespaces and comments before and after the expression. |
| */ |
| private void trimWhiteSpacesAndComments(org.eclipse.jdt.internal.compiler.ast.Expression expression) { |
| int[] positions = trimWhiteSpacesAndComments(expression.sourceStart, expression.sourceEnd); |
| expression.sourceStart = positions[0]; |
| expression.sourceEnd = positions[1]; |
| } |
| private void trimWhiteSpacesAndComments(ASTNode node) { |
| int start = node.getStartPosition(); |
| int end = start + node.getLength() - 1; |
| int[] positions = trimWhiteSpacesAndComments(start, end); |
| start = positions[0]; |
| end = positions[1]; |
| node.setSourceRange(start, end - start + 1); |
| } |
| private int [] trimWhiteSpacesAndComments(int start, int end) { |
| int [] positions = new int[]{start, end}; |
| int token; |
| int trimLeftPosition = start; |
| int trimRightPosition = end; |
| boolean first = true; |
| Scanner removeBlankScanner = this.ast.scanner; |
| try { |
| removeBlankScanner.setSource(this.compilationUnitSource); |
| removeBlankScanner.resetTo(start, end); |
| while (true) { |
| token = removeBlankScanner.getNextToken(); |
| switch (token) { |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| if (first) { |
| trimLeftPosition = removeBlankScanner.currentPosition; |
| } |
| break; |
| case TerminalTokens.TokenNameWHITESPACE : |
| if (first) { |
| trimLeftPosition = removeBlankScanner.currentPosition; |
| } |
| break; |
| case TerminalTokens.TokenNameEOF : |
| positions[0] = trimLeftPosition; |
| positions[1] = trimRightPosition; |
| return positions; |
| default : |
| /* |
| * if we find something else than a whitespace or a comment, |
| * then we reset the trimRigthPosition to the expression |
| * source end. |
| */ |
| trimRightPosition = removeBlankScanner.currentPosition - 1; |
| first = false; |
| } |
| } |
| } catch (InvalidInputException e){ |
| // ignore |
| } |
| return positions; |
| } |
| |
| /** |
| * Remove potential trailing comment by settings the source end on the closing parenthesis |
| */ |
| protected void removeLeadingAndTrailingCommentsFromLiteral(ASTNode node) { |
| int start = node.getStartPosition(); |
| this.scanner.resetTo(start, start + node.getLength()); |
| int token; |
| int startPosition = -1; |
| try { |
| while((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameIntegerLiteral : |
| case TerminalTokens.TokenNameFloatingPointLiteral : |
| case TerminalTokens.TokenNameLongLiteral : |
| case TerminalTokens.TokenNameDoubleLiteral : |
| case TerminalTokens.TokenNameCharacterLiteral : |
| if (startPosition == -1) { |
| startPosition = this.scanner.startPosition; |
| } |
| int end = this.scanner.currentPosition; |
| node.setSourceRange(startPosition, end - startPosition); |
| return; |
| case TerminalTokens.TokenNameMINUS : |
| startPosition = this.scanner.startPosition; |
| break; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| |
| /** |
| * This method is used to retrieve the end position of the block. |
| * @return the dimension found, -1 if none |
| */ |
| protected int retrieveClosingAngleBracketPosition(int start) { |
| this.scanner.resetTo(start, this.compilationUnitSourceLength); |
| this.scanner.returnOnlyGreater = true; |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameGREATER: |
| return this.scanner.currentPosition - 1; |
| case TerminalTokens.TokenNameLESS: |
| // TokenNameLESS can only be found if the current type has a diamond, start is located before the '<' |
| continue; |
| default: |
| return start; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| this.scanner.returnOnlyGreater = false; |
| return start; |
| } |
| |
| /** |
| * This method is used to set the right end position for expression |
| * statement. The actual AST nodes don't include the trailing semicolon. |
| * This method fixes the length of the corresponding node. |
| */ |
| protected void retrieveColonPosition(ASTNode node) { |
| int start = node.getStartPosition(); |
| int length = node.getLength(); |
| int end = start + length; |
| this.scanner.resetTo(end, this.compilationUnitSourceLength); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameCOLON: |
| node.setSourceRange(start, this.scanner.currentPosition - start); |
| return; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| /** |
| * This method is used to retrieve the start position of the Ellipsis |
| */ |
| protected int retrieveEllipsisStartPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameELLIPSIS: |
| return this.scanner.startPosition - 1; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| |
| } |
| |
| protected int retrieveSemiColonPosition(Expression node) { |
| int start = node.getStartPosition(); |
| int length = node.getLength(); |
| int end = start + length; |
| this.scanner.resetTo(end, this.compilationUnitSourceLength); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameSEMICOLON: |
| return this.scanner.currentPosition - 1; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| /** |
| * This method is used to retrieve the start and end position of a name or primitive type token. |
| * |
| * @return int[] a single dimensional array, with two elements, for the start and end positions of the name respectively |
| */ |
| protected int[] retrieveEndOfElementTypeNamePosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| int count = 0; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameLPAREN: |
| ++count; |
| break; |
| case TerminalTokens.TokenNameRPAREN: |
| --count; |
| break; |
| case TerminalTokens.TokenNameIdentifier: |
| case TerminalTokens.TokenNamebyte: |
| case TerminalTokens.TokenNamechar: |
| case TerminalTokens.TokenNamedouble: |
| case TerminalTokens.TokenNamefloat: |
| case TerminalTokens.TokenNameint: |
| case TerminalTokens.TokenNamelong: |
| case TerminalTokens.TokenNameshort: |
| case TerminalTokens.TokenNameboolean: |
| if (count > 0) break; |
| return new int[]{this.scanner.startPosition, this.scanner.currentPosition - 1}; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return new int[]{-1, -1}; |
| } |
| |
| /** |
| * This method is used to retrieve the position after the right parenthesis. |
| * @return int the position found |
| */ |
| protected int retrieveEndOfRightParenthesisPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| int count = 0; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameRPAREN: |
| count--; |
| if (count <= 0) return this.scanner.currentPosition; |
| break; |
| case TerminalTokens.TokenNameLPAREN: |
| count++; |
| //$FALL-THROUGH$ |
| default: |
| break; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| protected void retrieveDimensionAndSetPositions(int start, int end, Dimension dim) { |
| this.scanner.resetTo(start, end); |
| int token; |
| int count = 0, lParenCount = 0; |
| boolean startSet = false; |
| try { |
| while((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| if (token != TerminalTokens.TokenNameWHITESPACE) { |
| if (!startSet) { |
| start = this.scanner.startPosition; |
| startSet = true; |
| } |
| switch(token) { |
| case TerminalTokens.TokenNameRBRACKET: |
| if (lParenCount > 0) break; |
| --count; |
| if (count > 0) break; |
| int endDim = this.scanner.currentPosition - 1; |
| dim.setSourceRange(start, endDim - start + 1); |
| return; |
| case TerminalTokens.TokenNameLBRACKET: |
| if (lParenCount > 0) break; |
| count++; |
| break; |
| case TerminalTokens.TokenNameLPAREN: |
| lParenCount++; |
| break; |
| case TerminalTokens.TokenNameRPAREN: |
| --lParenCount; |
| break; |
| default: |
| break; |
| } |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| protected void retrieveIdentifierAndSetPositions(int start, int end, Name name) { |
| this.scanner.resetTo(start, end); |
| int token; |
| try { |
| while((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| if (token == TerminalTokens.TokenNameIdentifier) { |
| int startName = this.scanner.startPosition; |
| int endName = this.scanner.currentPosition - 1; |
| name.setSourceRange(startName, endName - startName + 1); |
| return; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| |
| /** |
| * This method is used to retrieve the start position of the block. |
| * @return int the dimension found, -1 if none |
| */ |
| protected int retrieveIdentifierEndPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameIdentifier://110 |
| return this.scanner.getCurrentTokenEndPosition(); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| /** |
| * retrieves the start and and of new and set the positions of the name |
| * @param start position to start search |
| * @param end position to end search |
| * @param name object where these positions will be updated. |
| */ |
| protected void retrieveInitAndSetPositions(int start, int end, Name name) { |
| this.scanner.resetTo(start, end); |
| int token; |
| try { |
| while((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| if (token == TerminalTokens.TokenNamenew) { |
| int startName = this.scanner.startPosition; |
| int endName = this.scanner.currentPosition; |
| name.setSourceRange(startName, endName - startName); |
| return; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| |
| /** |
| * This method is used to retrieve position before the next comma or semi-colon. |
| * @param initializerEnd the given initializer end exclusive |
| * @return int the position found. |
| */ |
| protected int retrieveEndOfPotentialExtendedDimensions(int initializerEnd, int nameEnd, int end) { |
| this.scanner.resetTo(initializerEnd, end); |
| boolean hasTokens = false; |
| int balance = 0; |
| int pos = initializerEnd > nameEnd ? initializerEnd - 1 : nameEnd; |
| try { |
| int token, lParenCount = 0; |
| boolean hasAnnotations = false; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| hasTokens = true; |
| if (hasAnnotations) { |
| if (token == TerminalTokens.TokenNameLPAREN) ++lParenCount; |
| else if (token == TerminalTokens.TokenNameRPAREN) { |
| --lParenCount; |
| continue; |
| } |
| if (lParenCount > 0) continue; |
| } |
| switch(token) { |
| case TerminalTokens.TokenNameAT: |
| hasAnnotations = true; |
| break; |
| case TerminalTokens.TokenNameLBRACE : |
| case TerminalTokens.TokenNameLBRACKET : |
| balance++; |
| break; |
| case TerminalTokens.TokenNameRBRACKET : |
| case TerminalTokens.TokenNameRBRACE : |
| balance --; |
| pos = this.scanner.currentPosition - 1; |
| break; |
| case TerminalTokens.TokenNameCOMMA : |
| if (balance == 0) return pos; |
| // case where a missing closing brace doesn't close an array initializer |
| pos = this.scanner.currentPosition - 1; |
| break; |
| case TerminalTokens.TokenNameSEMICOLON : |
| if (balance == 0) return pos; |
| return -pos; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| // no token, we simply return pos as the right position |
| return hasTokens ? Integer.MIN_VALUE : pos; |
| } |
| |
| protected int retrieveProperRightBracketPosition(int bracketNumber, int start, int end) { |
| this.scanner.resetTo(start, this.compilationUnitSourceLength); |
| try { |
| int token, count = 0, lParentCount = 0, balance = 0; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameLPAREN: |
| ++lParentCount; |
| break; |
| case TerminalTokens.TokenNameRPAREN: |
| --lParentCount; |
| break; |
| case TerminalTokens.TokenNameLBRACKET: |
| ++balance; |
| break; |
| case TerminalTokens.TokenNameELLIPSIS: |
| ++balance; // special case for varargs - simulate lbracket found |
| //$FALL-THROUGH$ |
| case TerminalTokens.TokenNameRBRACKET: |
| --balance; |
| if (lParentCount > 0) break; |
| if (balance > 0) break; |
| count++; |
| if (count == bracketNumber) { |
| return this.scanner.currentPosition - 1; |
| } |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| protected int retrieveProperRightBracketPosition(int bracketNumber, int start) { |
| return retrieveProperRightBracketPosition(bracketNumber, start, this.compilationUnitSourceLength); |
| } |
| |
| /** |
| * This method is used to retrieve position before the next right brace or semi-colon. |
| * @return int the position found. |
| */ |
| protected int retrieveRightBraceOrSemiColonPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameRBRACE : |
| return this.scanner.currentPosition - 1; |
| case TerminalTokens.TokenNameSEMICOLON : |
| return this.scanner.currentPosition - 1; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| /** |
| * This method is used to retrieve position before the next right brace or semi-colon. |
| * @return int the position found. |
| */ |
| protected int retrieveRightBrace(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameRBRACE : |
| return this.scanner.currentPosition - 1; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| /** |
| * This method is used to retrieve the start position of the block. |
| * @return int the dimension found, -1 if none |
| */ |
| protected int retrieveStartBlockPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNameLBRACE://110 |
| return this.scanner.startPosition; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| /** |
| * This method is used to retrieve the starting position of the catch keyword. |
| * @return int the dimension found, -1 if none |
| */ |
| protected int retrieveStartingCatchPosition(int start, int end) { |
| this.scanner.resetTo(start, end); |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| switch(token) { |
| case TerminalTokens.TokenNamecatch://225 |
| return this.scanner.startPosition; |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| return -1; |
| } |
| |
| public void setAST(AST ast) { |
| this.ast = ast; |
| this.docParser = new DocCommentParser(this.ast, this.scanner, this.insideComments); |
| } |
| |
| protected void setModifiers(AnnotationTypeDeclaration typeDecl, org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration) { |
| this.scanner.resetTo(typeDeclaration.declarationSourceStart, typeDeclaration.sourceStart); |
| this.setModifiers(typeDecl, typeDeclaration.annotations, typeDeclaration.sourceStart); |
| } |
| |
| protected void setModifiers(AnnotationTypeMemberDeclaration annotationTypeMemberDecl, org.eclipse.jdt.internal.compiler.ast.AnnotationMethodDeclaration annotationTypeMemberDeclaration) { |
| this.scanner.resetTo(annotationTypeMemberDeclaration.declarationSourceStart, annotationTypeMemberDeclaration.sourceStart); |
| this.setModifiers(annotationTypeMemberDecl, annotationTypeMemberDeclaration.annotations, annotationTypeMemberDeclaration.sourceStart); |
| } |
| |
| /** |
| * @param bodyDeclaration |
| */ |
| protected void setModifiers(BodyDeclaration bodyDeclaration, org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations, int modifiersEnd) { |
| setModifiers(bodyDeclaration.modifiers(), annotations, modifiersEnd); |
| } |
| protected void setModifiers(List modifiers, org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations, int modifiersEnd) { |
| this.scanner.tokenizeWhiteSpace = false; |
| try { |
| int token; |
| int indexInAnnotations = 0; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| IExtendedModifier modifier = null; |
| switch(token) { |
| case TerminalTokens.TokenNameabstract: |
| modifier = createModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamepublic: |
| modifier = createModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModifier(Modifier.ModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprotected: |
| modifier = createModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprivate: |
| modifier = createModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamefinal: |
| modifier = createModifier(Modifier.ModifierKeyword.FINAL_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamenative: |
| modifier = createModifier(Modifier.ModifierKeyword.NATIVE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamesynchronized: |
| modifier = createModifier(Modifier.ModifierKeyword.SYNCHRONIZED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransient: |
| modifier = createModifier(Modifier.ModifierKeyword.TRANSIENT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamevolatile: |
| modifier = createModifier(Modifier.ModifierKeyword.VOLATILE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestrictfp: |
| modifier = createModifier(Modifier.ModifierKeyword.STRICTFP_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamedefault: |
| modifier = createModifier(Modifier.ModifierKeyword.DEFAULT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameAT : |
| // we have an annotation |
| if (annotations != null && indexInAnnotations < annotations.length) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation annotation = annotations[indexInAnnotations++]; |
| modifier = convert(annotation); |
| this.scanner.resetTo(annotation.declarationSourceEnd + 1, modifiersEnd); |
| } |
| break; |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| break; |
| default : |
| // there is some syntax errors in source code |
| break; |
| } |
| if (modifier != null) { |
| modifiers.add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| |
| protected void setModifiers(EnumDeclaration enumDeclaration, org.eclipse.jdt.internal.compiler.ast.TypeDeclaration enumDeclaration2) { |
| this.scanner.resetTo(enumDeclaration2.declarationSourceStart, enumDeclaration2.sourceStart); |
| this.setModifiers(enumDeclaration, enumDeclaration2.annotations, enumDeclaration2.sourceStart); |
| } |
| |
| protected void setModifiers(EnumConstantDeclaration enumConstantDeclaration, org.eclipse.jdt.internal.compiler.ast.FieldDeclaration fieldDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| enumConstantDeclaration.internalSetModifiers(fieldDeclaration.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (fieldDeclaration.annotations != null) { |
| enumConstantDeclaration.setFlags(enumConstantDeclaration.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(fieldDeclaration.declarationSourceStart, fieldDeclaration.sourceStart); |
| this.setModifiers(enumConstantDeclaration, fieldDeclaration.annotations, fieldDeclaration.sourceStart); |
| } |
| } |
| |
| /** |
| * @param fieldDeclaration |
| * @param fieldDecl |
| */ |
| protected void setModifiers(FieldDeclaration fieldDeclaration, org.eclipse.jdt.internal.compiler.ast.FieldDeclaration fieldDecl) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| fieldDeclaration.internalSetModifiers(fieldDecl.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (fieldDecl.annotations != null) { |
| fieldDeclaration.setFlags(fieldDeclaration.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(fieldDecl.declarationSourceStart, fieldDecl.sourceStart); |
| this.setModifiers(fieldDeclaration, fieldDecl.annotations, fieldDecl.sourceStart); |
| } |
| } |
| |
| /** |
| * @param initializer |
| * @param oldInitializer |
| */ |
| protected void setModifiers(Initializer initializer, org.eclipse.jdt.internal.compiler.ast.Initializer oldInitializer) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL: |
| initializer.internalSetModifiers(oldInitializer.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (oldInitializer.annotations != null) { |
| initializer.setFlags(initializer.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(oldInitializer.declarationSourceStart, oldInitializer.bodyStart); |
| this.setModifiers(initializer, oldInitializer.annotations, oldInitializer.bodyStart); |
| } |
| } |
| /** |
| * @param methodDecl |
| * @param methodDeclaration |
| */ |
| protected void setModifiers(MethodDeclaration methodDecl, AbstractMethodDeclaration methodDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDecl.internalSetModifiers(methodDeclaration.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (methodDeclaration.annotations != null) { |
| methodDecl.setFlags(methodDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(methodDeclaration.declarationSourceStart, methodDeclaration.sourceStart); |
| this.setModifiers(methodDecl, methodDeclaration.annotations, methodDeclaration.sourceStart); |
| } |
| } |
| |
| protected void setAnnotations(ModuleDeclaration moduleDecl, org.eclipse.jdt.internal.compiler.ast.ModuleDeclaration moduleDeclaration) { |
| this.scanner.resetTo(moduleDeclaration.declarationSourceStart, moduleDeclaration.sourceStart); |
| this.setModifiers(moduleDecl.annotations(), moduleDeclaration.annotations, moduleDeclaration.sourceStart); |
| } |
| /** |
| * @param variableDecl |
| * @param argument |
| */ |
| protected void setModifiers(SingleVariableDeclaration variableDecl, Argument argument) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| variableDecl.internalSetModifiers(argument.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (argument.annotations != null) { |
| variableDecl.setFlags(variableDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(argument.declarationSourceStart, argument.sourceStart); |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = argument.annotations; |
| int indexInAnnotations = 0; |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| IExtendedModifier modifier = null; |
| switch(token) { |
| case TerminalTokens.TokenNameabstract: |
| modifier = createModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamepublic: |
| modifier = createModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModifier(Modifier.ModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprotected: |
| modifier = createModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprivate: |
| modifier = createModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamefinal: |
| modifier = createModifier(Modifier.ModifierKeyword.FINAL_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamenative: |
| modifier = createModifier(Modifier.ModifierKeyword.NATIVE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamesynchronized: |
| modifier = createModifier(Modifier.ModifierKeyword.SYNCHRONIZED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransient: |
| modifier = createModifier(Modifier.ModifierKeyword.TRANSIENT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamevolatile: |
| modifier = createModifier(Modifier.ModifierKeyword.VOLATILE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestrictfp: |
| modifier = createModifier(Modifier.ModifierKeyword.STRICTFP_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameAT : |
| // we have an annotation |
| if (annotations != null && indexInAnnotations < annotations.length) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation annotation = annotations[indexInAnnotations++]; |
| modifier = convert(annotation); |
| this.scanner.resetTo(annotation.declarationSourceEnd + 1, this.compilationUnitSourceLength); |
| } |
| break; |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| break; |
| default : |
| return; |
| } |
| if (modifier != null) { |
| variableDecl.modifiers().add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| } |
| |
| protected void setModifiers(SingleVariableDeclaration variableDecl, LocalDeclaration localDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| variableDecl.internalSetModifiers(localDeclaration.modifiers & ExtraCompilerModifiers.AccJustFlag); |
| if (localDeclaration.annotations != null) { |
| variableDecl.setFlags(variableDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(localDeclaration.declarationSourceStart, localDeclaration.sourceStart); |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = localDeclaration.annotations; |
| int indexInAnnotations = 0; |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| IExtendedModifier modifier = null; |
| switch(token) { |
| case TerminalTokens.TokenNameabstract: |
| modifier = createModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamepublic: |
| modifier = createModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModifier(Modifier.ModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprotected: |
| modifier = createModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprivate: |
| modifier = createModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamefinal: |
| modifier = createModifier(Modifier.ModifierKeyword.FINAL_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamenative: |
| modifier = createModifier(Modifier.ModifierKeyword.NATIVE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamesynchronized: |
| modifier = createModifier(Modifier.ModifierKeyword.SYNCHRONIZED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransient: |
| modifier = createModifier(Modifier.ModifierKeyword.TRANSIENT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamevolatile: |
| modifier = createModifier(Modifier.ModifierKeyword.VOLATILE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestrictfp: |
| modifier = createModifier(Modifier.ModifierKeyword.STRICTFP_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameAT : |
| // we have an annotation |
| if (annotations != null && indexInAnnotations < annotations.length) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation annotation = annotations[indexInAnnotations++]; |
| modifier = convert(annotation); |
| this.scanner.resetTo(annotation.declarationSourceEnd + 1, this.compilationUnitSourceLength); |
| } |
| break; |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| break; |
| default : |
| return; |
| } |
| if (modifier != null) { |
| variableDecl.modifiers().add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| } |
| |
| /** |
| * @param typeDecl |
| * @param typeDeclaration |
| */ |
| protected void setModifiers(TypeDeclaration typeDecl, org.eclipse.jdt.internal.compiler.ast.TypeDeclaration typeDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| int modifiers = typeDeclaration.modifiers; |
| modifiers &= ~ClassFileConstants.AccInterface; // remove AccInterface flags |
| modifiers &= ExtraCompilerModifiers.AccJustFlag; |
| typeDecl.internalSetModifiers(modifiers); |
| if (typeDeclaration.annotations != null) { |
| typeDecl.setFlags(typeDecl.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(typeDeclaration.declarationSourceStart, typeDeclaration.sourceStart); |
| this.setModifiers(typeDecl, typeDeclaration.annotations, typeDeclaration.sourceStart); |
| } |
| } |
| |
| /** |
| * @param variableDeclarationExpression |
| * @param localDeclaration |
| */ |
| protected void setModifiers(VariableDeclarationExpression variableDeclarationExpression, LocalDeclaration localDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| int modifiers = localDeclaration.modifiers & ExtraCompilerModifiers.AccJustFlag; |
| modifiers &= ~ExtraCompilerModifiers.AccBlankFinal; |
| variableDeclarationExpression.internalSetModifiers(modifiers); |
| if (localDeclaration.annotations != null) { |
| variableDeclarationExpression.setFlags(variableDeclarationExpression.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(localDeclaration.declarationSourceStart, localDeclaration.sourceStart); |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = localDeclaration.annotations; |
| int indexInAnnotations = 0; |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| IExtendedModifier modifier = null; |
| switch(token) { |
| case TerminalTokens.TokenNameabstract: |
| modifier = createModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamepublic: |
| modifier = createModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModifier(Modifier.ModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprotected: |
| modifier = createModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprivate: |
| modifier = createModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamefinal: |
| modifier = createModifier(Modifier.ModifierKeyword.FINAL_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamenative: |
| modifier = createModifier(Modifier.ModifierKeyword.NATIVE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamesynchronized: |
| modifier = createModifier(Modifier.ModifierKeyword.SYNCHRONIZED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransient: |
| modifier = createModifier(Modifier.ModifierKeyword.TRANSIENT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamevolatile: |
| modifier = createModifier(Modifier.ModifierKeyword.VOLATILE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestrictfp: |
| modifier = createModifier(Modifier.ModifierKeyword.STRICTFP_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameAT : |
| // we have an annotation |
| if (annotations != null && indexInAnnotations < annotations.length) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation annotation = annotations[indexInAnnotations++]; |
| modifier = convert(annotation); |
| this.scanner.resetTo(annotation.declarationSourceEnd + 1, this.compilationUnitSourceLength); |
| } |
| break; |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| break; |
| default : |
| return; |
| } |
| if (modifier != null) { |
| variableDeclarationExpression.modifiers().add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| } |
| |
| /** |
| * @param variableDeclarationStatement |
| * @param localDeclaration |
| */ |
| protected void setModifiers(VariableDeclarationStatement variableDeclarationStatement, LocalDeclaration localDeclaration) { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| int modifiers = localDeclaration.modifiers & ExtraCompilerModifiers.AccJustFlag; |
| modifiers &= ~ExtraCompilerModifiers.AccBlankFinal; |
| variableDeclarationStatement.internalSetModifiers(modifiers); |
| if (localDeclaration.annotations != null) { |
| variableDeclarationStatement.setFlags(variableDeclarationStatement.getFlags() | ASTNode.MALFORMED); |
| } |
| break; |
| default : |
| this.scanner.resetTo(localDeclaration.declarationSourceStart, localDeclaration.sourceStart); |
| org.eclipse.jdt.internal.compiler.ast.Annotation[] annotations = localDeclaration.annotations; |
| int indexInAnnotations = 0; |
| try { |
| int token; |
| while ((token = this.scanner.getNextToken()) != TerminalTokens.TokenNameEOF) { |
| IExtendedModifier modifier = null; |
| switch(token) { |
| case TerminalTokens.TokenNameabstract: |
| modifier = createModifier(Modifier.ModifierKeyword.ABSTRACT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamepublic: |
| modifier = createModifier(Modifier.ModifierKeyword.PUBLIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestatic: |
| modifier = createModifier(Modifier.ModifierKeyword.STATIC_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprotected: |
| modifier = createModifier(Modifier.ModifierKeyword.PROTECTED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameprivate: |
| modifier = createModifier(Modifier.ModifierKeyword.PRIVATE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamefinal: |
| modifier = createModifier(Modifier.ModifierKeyword.FINAL_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamenative: |
| modifier = createModifier(Modifier.ModifierKeyword.NATIVE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamesynchronized: |
| modifier = createModifier(Modifier.ModifierKeyword.SYNCHRONIZED_KEYWORD); |
| break; |
| case TerminalTokens.TokenNametransient: |
| modifier = createModifier(Modifier.ModifierKeyword.TRANSIENT_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamevolatile: |
| modifier = createModifier(Modifier.ModifierKeyword.VOLATILE_KEYWORD); |
| break; |
| case TerminalTokens.TokenNamestrictfp: |
| modifier = createModifier(Modifier.ModifierKeyword.STRICTFP_KEYWORD); |
| break; |
| case TerminalTokens.TokenNameAT : |
| // we have an annotation |
| if (annotations != null && indexInAnnotations < annotations.length) { |
| org.eclipse.jdt.internal.compiler.ast.Annotation annotation = annotations[indexInAnnotations++]; |
| modifier = convert(annotation); |
| this.scanner.resetTo(annotation.declarationSourceEnd + 1, this.compilationUnitSourceLength); |
| } |
| break; |
| case TerminalTokens.TokenNameCOMMENT_BLOCK : |
| case TerminalTokens.TokenNameCOMMENT_LINE : |
| case TerminalTokens.TokenNameCOMMENT_JAVADOC : |
| break; |
| default : |
| return; |
| } |
| if (modifier != null) { |
| variableDeclarationStatement.modifiers().add(modifier); |
| } |
| } |
| } catch(InvalidInputException e) { |
| // ignore |
| } |
| } |
| } |
| |
| protected QualifiedName setQualifiedNameNameAndSourceRanges(char[][] typeName, long[] positions, org.eclipse.jdt.internal.compiler.ast.ASTNode node) { |
| int length = typeName.length; |
| final SimpleName firstToken = new SimpleName(this.ast); |
| firstToken.internalSetIdentifier(new String(typeName[0])); |
| firstToken.index = 1; |
| int start0 = (int)(positions[0]>>>32); |
| int start = start0; |
| int end = (int)(positions[0] & 0xFFFFFFFF); |
| firstToken.setSourceRange(start, end - start + 1); |
| final SimpleName secondToken = new SimpleName(this.ast); |
| secondToken.internalSetIdentifier(new String(typeName[1])); |
| secondToken.index = 2; |
| start = (int)(positions[1]>>>32); |
| end = (int)(positions[1] & 0xFFFFFFFF); |
| secondToken.setSourceRange(start, end - start + 1); |
| QualifiedName qualifiedName = new QualifiedName(this.ast); |
| qualifiedName.setQualifier(firstToken); |
| qualifiedName.setName(secondToken); |
| if (this.resolveBindings) { |
| recordNodes(qualifiedName, node); |
| recordPendingNameScopeResolution(qualifiedName); |
| recordNodes(firstToken, node); |
| recordNodes(secondToken, node); |
| recordPendingNameScopeResolution(firstToken); |
| recordPendingNameScopeResolution(secondToken); |
| } |
| qualifiedName.index = 2; |
| qualifiedName.setSourceRange(start0, end - start0 + 1); |
| SimpleName newPart = null; |
| for (int i = 2; i < length; i++) { |
| newPart = new SimpleName(this.ast); |
| newPart.internalSetIdentifier(new String(typeName[i])); |
| newPart.index = i + 1; |
| start = (int)(positions[i]>>>32); |
| end = (int)(positions[i] & 0xFFFFFFFF); |
| newPart.setSourceRange(start, end - start + 1); |
| QualifiedName qualifiedName2 = new QualifiedName(this.ast); |
| qualifiedName2.setQualifier(qualifiedName); |
| qualifiedName2.setName(newPart); |
| qualifiedName = qualifiedName2; |
| qualifiedName.index = newPart.index; |
| qualifiedName.setSourceRange(start0, end - start0 + 1); |
| if (this.resolveBindings) { |
| recordNodes(qualifiedName, node); |
| recordNodes(newPart, node); |
| recordPendingNameScopeResolution(qualifiedName); |
| recordPendingNameScopeResolution(newPart); |
| } |
| } |
| QualifiedName name = qualifiedName; |
| if (this.resolveBindings) { |
| recordNodes(name, node); |
| recordPendingNameScopeResolution(name); |
| } |
| return name; |
| } |
| |
| protected QualifiedName setQualifiedNameNameAndSourceRanges(char[][] typeName, long[] positions, int endingIndex, org.eclipse.jdt.internal.compiler.ast.TypeReference node) { |
| int length = endingIndex + 1; |
| final SimpleName firstToken = new SimpleName(this.ast); |
| firstToken.internalSetIdentifier(new String(typeName[0])); |
| firstToken.index = 1; |
| int start0 = (int)(positions[0]>>>32); |
| int start = start0; |
| int end = (int) positions[0]; |
| firstToken.setSourceRange(start, end - start + 1); |
| final SimpleName secondToken = new SimpleName(this.ast); |
| secondToken.internalSetIdentifier(new String(typeName[1])); |
| secondToken.index = 2; |
| start = (int)(positions[1]>>>32); |
| end = (int) positions[1]; |
| secondToken.setSourceRange(start, end - start + 1); |
| QualifiedName qualifiedName = new QualifiedName(this.ast); |
| qualifiedName.setQualifier(firstToken); |
| qualifiedName.setName(secondToken); |
| if (this.resolveBindings) { |
| recordNodes(qualifiedName, node); |
| recordPendingNameScopeResolution(qualifiedName); |
| recordNodes(firstToken, node); |
| recordNodes(secondToken, node); |
| recordPendingNameScopeResolution(firstToken); |
| recordPendingNameScopeResolution(secondToken); |
| } |
| qualifiedName.index = 2; |
| qualifiedName.setSourceRange(start0, end - start0 + 1); |
| SimpleName newPart = null; |
| for (int i = 2; i < length; i++) { |
| newPart = new SimpleName(this.ast); |
| newPart.internalSetIdentifier(new String(typeName[i])); |
| newPart.index = i + 1; |
| start = (int)(positions[i]>>>32); |
| end = (int) positions[i]; |
| newPart.setSourceRange(start, end - start + 1); |
| QualifiedName qualifiedName2 = new QualifiedName(this.ast); |
| qualifiedName2.setQualifier(qualifiedName); |
| qualifiedName2.setName(newPart); |
| qualifiedName = qualifiedName2; |
| qualifiedName.index = newPart.index; |
| qualifiedName.setSourceRange(start0, end - start0 + 1); |
| if (this.resolveBindings) { |
| recordNodes(qualifiedName, node); |
| recordNodes(newPart, node); |
| recordPendingNameScopeResolution(qualifiedName); |
| recordPendingNameScopeResolution(newPart); |
| } |
| } |
| if (newPart == null && this.resolveBindings) { |
| recordNodes(qualifiedName, node); |
| recordPendingNameScopeResolution(qualifiedName); |
| } |
| return qualifiedName; |
| } |
| |
| protected void setTypeNameForAnnotation(org.eclipse.jdt.internal.compiler.ast.Annotation compilerAnnotation, Annotation annotation) { |
| TypeReference typeReference = compilerAnnotation.type; |
| if (typeReference instanceof QualifiedTypeReference) { |
| QualifiedTypeReference qualifiedTypeReference = (QualifiedTypeReference) typeReference; |
| char[][] tokens = qualifiedTypeReference.tokens; |
| long[] positions = qualifiedTypeReference.sourcePositions; |
| // QualifiedName |
| annotation.setTypeName(setQualifiedNameNameAndSourceRanges(tokens, positions, typeReference)); |
| } else { |
| SingleTypeReference singleTypeReference = (SingleTypeReference) typeReference; |
| final SimpleName name = new SimpleName(this.ast); |
| name.internalSetIdentifier(new String(singleTypeReference.token)); |
| int start = singleTypeReference.sourceStart; |
| int end = singleTypeReference.sourceEnd; |
| name.setSourceRange(start, end - start + 1); |
| name.index = 1; |
| annotation.setTypeName(name); |
| if (this.resolveBindings) { |
| recordNodes(name, typeReference); |
| } |
| } |
| } |
| |
| protected void setTypeForField(FieldDeclaration fieldDeclaration, Type type, int extraDimension) { |
| if (extraDimension != 0) { |
| if (type.isArrayType()) { |
| ArrayType arrayType = (ArrayType) type; |
| int remainingDimensions = arrayType.getDimensions() - extraDimension; |
| if (remainingDimensions == 0) { |
| // the dimensions are after the name so the type of the fieldDeclaration is a simpleType |
| Type elementType = arrayType.getElementType(); |
| // cut the child loose from its parent (without creating garbage) |
| elementType.setParent(null, null); |
| this.ast.getBindingResolver().updateKey(type, elementType); |
| fieldDeclaration.setType(elementType); |
| } else { |
| ArrayType subarrayType = extractSubArrayType(arrayType, remainingDimensions, extraDimension); |
| fieldDeclaration.setType(subarrayType); |
| this.ast.getBindingResolver().updateKey(type, subarrayType); |
| } |
| checkAndSetMalformed(type, fieldDeclaration); |
| } else { |
| fieldDeclaration.setType(type); |
| } |
| } else { |
| if (type.isArrayType() && (this.ast.apiLevel() < AST.JLS8_INTERNAL)) { |
| // update positions of the component types of the array type |
| int dimensions = ((ArrayType) type).getDimensions(); |
| updateInnerPositions(type, dimensions); |
| } |
| fieldDeclaration.setType(type); |
| } |
| } |
| |
| /** extracts the subArrayType for a given declaration for AST levels less |
| * @param arrayType parent type |
| * @param remainingDimensions |
| * @param dimensionsToRemove |
| * @return an ArrayType |
| */ |
| private ArrayType extractSubArrayType(ArrayType arrayType, int remainingDimensions, int dimensionsToRemove) { |
| ArrayType subArrayType = arrayType; |
| int start = subArrayType.getStartPosition(); |
| if (this.ast.apiLevel() < AST.JLS8_INTERNAL) { |
| while (dimensionsToRemove > 0 ) { |
| subArrayType = (ArrayType) componentType(subArrayType); |
| dimensionsToRemove--; |
| } |
| updateInnerPositions(subArrayType, remainingDimensions); |
| } else { |
| List dimensions = subArrayType.dimensions(); |
| while (dimensionsToRemove > 0 ) { |
| dimensions.remove(dimensions.size() - 1); |
| dimensionsToRemove--; |
| } |
| } |
| int end = retrieveProperRightBracketPosition(remainingDimensions, start); |
| subArrayType.setSourceRange(start, end - start + 1); |
| // cut the child loose from its parent (without creating garbage) |
| subArrayType.setParent(null, null); |
| return subArrayType; |
| } |
| |
| protected void setTypeForMethodDeclaration(MethodDeclaration methodDeclaration, Type type, int extraDimension) { |
| if (extraDimension != 0) { |
| if (type.isArrayType()) { |
| ArrayType arrayType = (ArrayType) type; |
| int remainingDimensions = arrayType.getDimensions() - extraDimension; |
| if (remainingDimensions == 0) { |
| // the dimensions are after the name so the type of the fieldDeclaration is a simpleType |
| Type elementType = arrayType.getElementType(); |
| // cut the child loose from its parent (without creating garbage) |
| elementType.setParent(null, null); |
| this.ast.getBindingResolver().updateKey(type, elementType); |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDeclaration.internalSetReturnType(elementType); |
| break; |
| default : |
| methodDeclaration.setReturnType2(elementType); |
| break; |
| } |
| } else { |
| ArrayType subarrayType = extractSubArrayType(arrayType, remainingDimensions, extraDimension); |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDeclaration.internalSetReturnType(subarrayType); |
| break; |
| default : |
| methodDeclaration.setReturnType2(subarrayType); |
| break; |
| } |
| this.ast.getBindingResolver().updateKey(type, subarrayType); |
| } |
| checkAndSetMalformed(type, methodDeclaration); |
| } else { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDeclaration.internalSetReturnType(type); |
| break; |
| default : |
| methodDeclaration.setReturnType2(type); |
| break; |
| } |
| } |
| } else { |
| switch(this.ast.apiLevel) { |
| case AST.JLS2_INTERNAL : |
| methodDeclaration.internalSetReturnType(type); |
| break; |
| default : |
| methodDeclaration.setReturnType2(type); |
| break; |
| } |
| } |
| } |
| |
| protected void setTypeForMethodDeclaration(AnnotationTypeMemberDeclaration annotationTypeMemberDeclaration, Type type, int extraDimension) { |
| annotationTypeMemberDeclaration.setType(type); |
| } |
| |
| protected void setTypeForSingleVariableDeclaration(SingleVariableDeclaration singleVariableDeclaration, Type type, int extraDimension) { |
| if (extraDimension != 0) { |
| if (type.isArrayType()) { |
| ArrayType arrayType = (ArrayType) type; |
| int remainingDimensions = arrayType.getDimensions() - extraDimension; |
| if (remainingDimensions == 0) { |
| // the dimensions are after the name so the type of the fieldDeclaration is a simpleType |
| Type elementType = arrayType.getElementType(); |
| // cut the child loose from its parent (without creating garbage) |
| elementType.setParent(null, null); |
| this.ast.getBindingResolver().updateKey(type, elementType); |
| singleVariableDeclaration.setType(elementType); |
| } else { |
| ArrayType subarrayType = extractSubArrayType(arrayType, remainingDimensions, extraDimension); |
| this.ast.getBindingResolver().updateKey(type, subarrayType); |
| singleVariableDeclaration.setType(subarrayType); |
| } |
| checkAndSetMalformed(type, singleVariableDeclaration); |
| |
| } else { |
| singleVariableDeclaration.setType(type); |
| } |
| } else { |
| singleVariableDeclaration.setType(type); |
| } |
| } |
| |
| protected void setTypeForVariableDeclarationExpression(VariableDeclarationExpression variableDeclarationExpression, Type type, int extraDimension) { |
| if (extraDimension != 0) { |
| if (type.isArrayType()) { |
| ArrayType arrayType = (ArrayType) type; |
| int remainingDimensions = arrayType.getDimensions() - extraDimension; |
| if (remainingDimensions == 0) { |
| // the dimensions are after the name so the type of the fieldDeclaration is a simpleType |
| Type elementType = arrayType.getElementType(); |
| // cut the child loose from its parent (without creating garbage) |
| elementType.setParent(null, null); |
| this.ast.getBindingResolver().updateKey(type, elementType); |
| variableDeclarationExpression.setType(elementType); |
| } else { |
| ArrayType subarrayType = extractSubArrayType(arrayType, remainingDimensions, extraDimension); |
| variableDeclarationExpression.setType(subarrayType); |
| this.ast.getBindingResolver().updateKey(type, subarrayType); |
| } |
| checkAndSetMalformed(type, variableDeclarationExpression); |
| } else { |
| variableDeclarationExpression.setType(type); |
| } |
| } else { |
| variableDeclarationExpression.setType(type); |
| } |
| } |
| |
| protected void setTypeForVariableDeclarationStatement(VariableDeclarationStatement variableDeclarationStatement, Type type, int extraDimension) { |
| if (extraDimension != 0) { |
| if (type.isArrayType()) { |
| ArrayType arrayType = (ArrayType) type; |
| int remainingDimensions = arrayType.getDimensions() - extraDimension; |
| if (remainingDimensions == 0) { |
| // the dimensions are after the name so the type of the fieldDeclaration is a simpleType |
| Type elementType = arrayType.getElementType(); |
| // cut the child loose from its parent (without creating garbage) |
| elementType.setParent(null, null); |
| this.ast.getBindingResolver().updateKey(type, elementType); |
| variableDeclarationStatement.setType(elementType); |
| } else { |
| ArrayType subarrayType = extractSubArrayType(arrayType, remainingDimensions, extraDimension); |
| variableDeclarationStatement.setType(subarrayType); |
| this.ast.getBindingResolver().updateKey(type, subarrayType); |
| } |
| checkAndSetMalformed(type, variableDeclarationStatement); |
| } else { |
| variableDeclarationStatement.setType(type); |
| } |
| } else { |
| variableDeclarationStatement.setType(type); |
| } |
| } |
| |
| protected void updateInnerPositions(Type type, int dimensions) { |
| if (dimensions > 1) { |
| // need to set positions for intermediate array type see 42839 |
| int start = type.getStartPosition(); |
| Type currentComponentType = componentType(((ArrayType) type)); |
| int searchedDimension = dimensions - 1; |
| int rightBracketEndPosition = start; |
| while (currentComponentType.isArrayType()) { |
| rightBracketEndPosition = retrieveProperRightBracketPosition(searchedDimension, start); |
| currentComponentType.setSourceRange(start, rightBracketEndPosition - start + 1); |
| currentComponentType = componentType(((ArrayType) currentComponentType)); |
| searchedDimension--; |
| } |
| } |
| } |
| } |