diff options
author | Manoj Palat | 2013-06-10 18:10:09 +0000 |
---|---|---|
committer | Markus Keller | 2013-06-10 18:10:09 +0000 |
commit | 80351fb8a54757084b1b27c49cb8b0584bf78834 (patch) | |
tree | c6c187441d3917e4f751f121782319ba63e0c4f8 | |
parent | 26e96a017b590b444a246c8fba814dc78fd85b77 (diff) | |
download | eclipse.jdt.core-80351fb8a54757084b1b27c49cb8b0584bf78834.tar.gz eclipse.jdt.core-80351fb8a54757084b1b27c49cb8b0584bf78834.tar.xz eclipse.jdt.core-80351fb8a54757084b1b27c49cb8b0584bf78834.zip |
Bug 399794: [1.8][dom ast] Add a new node type for the compiler node ReferenceExpression
20 files changed, 2227 insertions, 24 deletions
diff --git a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTConverter18Test.java b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTConverter18Test.java index 5a36264243..bd45f05508 100644 --- a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTConverter18Test.java +++ b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTConverter18Test.java @@ -1662,6 +1662,224 @@ public class ASTConverter18Test extends ConverterTestSetup { } /** + * https://bugs.eclipse.org/bugs/show_bug.cgi?id=399794 + * ReferenceExpression Family Tests + * + * @throws JavaModelException + */ + public void test399794() throws JavaModelException { + this.workingCopy = getWorkingCopy("/Converter18/src/test399794/X.java", + true/* resolve */); + String contents = "package test399794;" + + "import java.lang.annotation.*;\n " + + "interface I {\n" + + " Object copy(int [] ia);\n" + + "}\n" + + "interface J {\n" + + " void foo(int x);\n" + + "}\n" + + "class XX {\n" + + " public void foo(int x) {}\n" + + "}\n" + + "\n" + + "class Y {\n" + + " static class Z {\n" + + " public static void foo(int x) {\n" + + " System.out.print(x);\n" + + " }\n" + + " }\n" + + " public void foo(int x) {\n" + + " System.out.print(x);\n" + + " }\n" + + " public <T> void foo(T t){t.hashCode();}\n" + + "}\n" + + "\n" + + "public class X extends XX {\n" + + " @SuppressWarnings(\"unused\")\n" + + " public void bar(String [] args) {\n" + + " Y y = new Y();\n" + + " I i = @Marker int []::<String>clone;\n" + + " J j = Y.@Marker Z :: foo;\n" + + " J j1 = Y.@Marker Z :: <String> foo;\n" + + " J jdash = @Marker W<@Marker Integer> :: <String> new ;\n" + + " J jj = y :: foo;\n" + + " J jx = super :: foo;\n" + + " class Z {\n" + + " void foo() {\n" + + " J jz = X.super :: foo;\n" + + " }\n" + + " }\n" + + " }\n" + + " public static void main (String [] args) {}\n" + + "}\n" + + "class W<T> extends Y {\n" + + " public W(T x) {}\n" + + "}\n" + + "\n" + + "@Target (ElementType.TYPE_USE)\n" + + "@interface Marker {}"; + + CompilationUnit cu = (CompilationUnit) buildAST(contents, this.workingCopy); + TypeDeclaration typeDeclaration = (TypeDeclaration) getASTNode(cu, 4); + MethodDeclaration method = typeDeclaration.getMethods()[0]; + List statements = method.getBody().statements(); + assertTrue(statements.size() == 8); + int fCount = 1; + + // type method reference with primitive type with type arguments + VariableDeclarationStatement statement = (VariableDeclarationStatement) statements.get(fCount++); + VariableDeclarationFragment fragment = (VariableDeclarationFragment) statement.fragments().get(0); + Expression expression = fragment.getInitializer(); + assertTrue(expression instanceof TypeMethodReference); + TypeMethodReference typeMethodReference = (TypeMethodReference) expression; + checkSourceRange(typeMethodReference, "@Marker int []::<String>clone", contents); + ITypeBinding typeBinding = typeMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + IMethodBinding methodBinding = typeMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + Type type = typeMethodReference.getType(); + checkSourceRange(type, "@Marker int []", contents); + List typeArguments = typeMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 1); + type = (Type) typeArguments.get(0); + checkSourceRange(type, "String", contents); + assertTrue(type.isSimpleType()); + SimpleName name = typeMethodReference.getName(); + checkSourceRange(name, "clone", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + // type method reference with qualified type without type arguments + statement = (VariableDeclarationStatement) statements.get(fCount++); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof TypeMethodReference); + typeMethodReference = (TypeMethodReference) expression; + checkSourceRange(typeMethodReference, "Y.@Marker Z :: foo", contents); + typeBinding = typeMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = typeMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + type = typeMethodReference.getType(); + assertTrue(type.isQualifiedType()); + checkSourceRange(type, "Y.@Marker Z", contents); + typeArguments = typeMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 0); + name = typeMethodReference.getName(); + checkSourceRange(name, "foo", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + // type method reference with qualified type with type arguments + statement = (VariableDeclarationStatement) statements.get(fCount++); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof TypeMethodReference); + typeMethodReference = (TypeMethodReference) expression; + checkSourceRange(typeMethodReference, "Y.@Marker Z :: <String> foo", contents); + typeBinding = typeMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = typeMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + type = typeMethodReference.getType(); + assertTrue(type.isQualifiedType()); + checkSourceRange(type, "Y.@Marker Z", contents); + typeArguments = typeMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 1); + type = (Type) typeArguments.get(0); + assertTrue(type.isSimpleType()); + checkSourceRange(type, "String", contents); + name = typeMethodReference.getName(); + checkSourceRange(name, "foo", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + // creation method reference + statement = (VariableDeclarationStatement) statements.get(fCount++); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof CreationReference); + CreationReference creationReference = (CreationReference) expression; + checkSourceRange(creationReference, "@Marker W<@Marker Integer> :: <String> new ", contents); + typeBinding = creationReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = creationReference.resolveMethodBinding(); + assertNotNull(methodBinding); + Expression lhs = creationReference.getExpression(); + checkSourceRange(lhs, "@Marker W<@Marker Integer> ", contents); + typeArguments = creationReference.typeArguments(); + assertTrue(typeArguments.size() == 1); + type = (Type) typeArguments.get(0); + assertTrue(type.isSimpleType()); + checkSourceRange(type, "String", contents); + + // expression method reference + statement = (VariableDeclarationStatement) statements.get(fCount++); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof ExpressionMethodReference); + ExpressionMethodReference expressionMethodReference = (ExpressionMethodReference) expression; + checkSourceRange(expressionMethodReference, "y :: foo", contents); + typeBinding = expressionMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = expressionMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + lhs = expressionMethodReference.getExpression(); + checkSourceRange(lhs, "y", contents); + typeArguments = expressionMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 0); + name = expressionMethodReference.getName(); + checkSourceRange(name, "foo", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + // super method reference without qualifier + statement = (VariableDeclarationStatement) statements.get(fCount++); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof SuperMethodReference); + SuperMethodReference superMethodReference = (SuperMethodReference) expression; + checkSourceRange(superMethodReference, "super :: foo", contents); + typeBinding = superMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = superMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + assertNull(superMethodReference.getQualifier()); + typeArguments = superMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 0); + name = superMethodReference.getName(); + checkSourceRange(name, "foo", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + // super method reference with qualifier + TypeDeclarationStatement typeDeclarationStatement = (TypeDeclarationStatement) statements.get(fCount); + typeDeclaration = (TypeDeclaration) typeDeclarationStatement.getDeclaration(); + method = typeDeclaration.getMethods()[0]; + statements = method.getBody().statements(); + assertTrue(statements.size() == 1); + statement = (VariableDeclarationStatement) statements.get(0); + fragment = (VariableDeclarationFragment) statement.fragments().get(0); + expression = fragment.getInitializer(); + assertTrue(expression instanceof SuperMethodReference); + superMethodReference = (SuperMethodReference) expression; + checkSourceRange(superMethodReference, "X.super :: foo", contents); + typeBinding = superMethodReference.resolveTypeBinding(); + assertNotNull(typeBinding); + methodBinding = superMethodReference.resolveMethodBinding(); + assertNotNull(methodBinding); + name = (SimpleName) superMethodReference.getQualifier(); + checkSourceRange(name, "X", contents); + typeArguments = superMethodReference.typeArguments(); + assertTrue(typeArguments.size() == 0); + name = superMethodReference.getName(); + checkSourceRange(name, "foo", contents); + typeBinding = name.resolveTypeBinding(); + assertNotNull(typeBinding); + + } + + /** * https://bugs.eclipse.org/bugs/show_bug.cgi?id=399793 * * @throws JavaModelException diff --git a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTMatcherTest.java b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTMatcherTest.java index 4ec77591d4..65f2f544f6 100644 --- a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTMatcherTest.java +++ b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTMatcherTest.java @@ -504,6 +504,9 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T public boolean match(SuperMethodInvocation node, Object other) { return standardBody(node, other, this.superMatch ? super.match(node, other) : false); } + public boolean match(SuperMethodReference node, Object other) { + return standardBody(node, other, this.superMatch ? super.match(node, other) : false); + } public boolean match(SwitchCase node, Object other) { return standardBody(node, other, this.superMatch ? super.match(node, other) : false); } @@ -564,6 +567,15 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T public boolean match(LambdaExpression node, Object other) { return standardBody(node, other, this.superMatch ? super.match(node, other) : false); } + public boolean match(CreationReference node, Object other) { + return standardBody(node, other, this.superMatch ? super.match(node, other) : false); + } + public boolean match(ExpressionMethodReference node, Object other) { + return standardBody(node, other, this.superMatch ? super.match(node, other) : false); + } + public boolean match(TypeMethodReference node, Object other) { + return standardBody(node, other, this.superMatch ? super.match(node, other) : false); + } public boolean match(IntersectionType node, Object other) { return standardBody(node, other, this.superMatch ? super.match(node, other) : false); } @@ -870,6 +882,15 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T x1.setLabel(this.N1); basicMatch(x1); } + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=399794 + public void testCreationReference() { + if (this.ast.apiLevel() < AST.JLS8) { + return; + } + CreationReference x1 = this.ast.newCreationReference(this.E1); + basicMatch(x1); + } + public void testDoStatement() { DoStatement x1 = this.ast.newDoStatement(); x1.setExpression(this.E1); @@ -925,6 +946,15 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T x1.bodyDeclarations().add(this.FD2); basicMatch(x1); } + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=399794 + public void testExpressionMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) { + return; + } + ExpressionMethodReference x1 = this.ast.newExpressionMethodReference(this.E1, this.N1); + basicMatch(x1); + } + public void testExpressionStatement() { ExpressionStatement x1 = this.ast.newExpressionStatement(this.E1); basicMatch(x1); @@ -1157,6 +1187,14 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T x1.arguments().add(this.E2); basicMatch(x1); } + public void testSuperMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) { + return; + } + SuperMethodReference x1 = this.ast.newSuperMethodReference(this.N2); + x1.setQualifier(this.N1); + basicMatch(x1); + } public void testSwitchCase() { SwitchCase x1 = this.ast.newSwitchCase(); x1.setExpression(this.E1); @@ -1589,6 +1627,15 @@ public class ASTMatcherTest extends org.eclipse.jdt.core.tests.junit.extension.T basicMatch(x1); } + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=399794 + public void testTypeMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) { + return; + } + TypeMethodReference x1 = this.ast.newTypeMethodReference(this.T1, this.N1); + basicMatch(x1); + } + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=399793 public void testLambdaExpressions1() { if (this.ast.apiLevel() < AST.JLS8) { diff --git a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTStructuralPropertyTest.java b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTStructuralPropertyTest.java index c236a0b2d5..2bf4b8720c 100644 --- a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTStructuralPropertyTest.java +++ b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTStructuralPropertyTest.java @@ -328,7 +328,7 @@ public class ASTStructuralPropertyTest extends org.eclipse.jdt.core.tests.junit. maxNodeType = 84; break; case AST.JLS8: - maxNodeType = 88; + maxNodeType = 92; break; default: fail(); @@ -372,7 +372,7 @@ public class ASTStructuralPropertyTest extends org.eclipse.jdt.core.tests.junit. // oops - guess that's not valid } } - assertEquals("Wrong last known type", 88, hi); // last known one + assertEquals("Wrong last known type", 92, hi); // last known one assertEquals("Wrong number of distinct types", hi, classes.size()); // all classes are distinct } } diff --git a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTTest.java b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTTest.java index 52c8dd2924..6eb30a992b 100644 --- a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTTest.java +++ b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTTest.java @@ -8785,6 +8785,10 @@ public class ASTTest extends org.eclipse.jdt.core.tests.junit.extension.TestCase ASTNode.LAMBDA_EXPRESSION, ASTNode.INTERSECTION_TYPE, ASTNode.PACKAGE_QUALIFIED_TYPE, + ASTNode.CREATION_REFERENCE, + ASTNode.EXPRESSION_METHOD_REFERENCE, + ASTNode.SUPER_METHOD_REFERENCE, + ASTNode.TYPE_METHOD_REFERENCE }; // assert that nodeType values are correct: diff --git a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTVisitorTest.java b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTVisitorTest.java index ff0db3a211..4961c091a3 100644 --- a/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTVisitorTest.java +++ b/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/dom/ASTVisitorTest.java @@ -712,6 +712,22 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T ASTVisitorTest.this.b.append("*/)"); //$NON-NLS-1$ } + public boolean visit(CreationReference node) { + ASTVisitorTest.this.b.append("(eCR"); //$NON-NLS-1$ + return isVisitingChildren(); + } + public void endVisit(CreationReference node) { + ASTVisitorTest.this.b.append("eCR)"); //$NON-NLS-1$ + } + + public boolean visit(ExpressionMethodReference node) { + ASTVisitorTest.this.b.append("(eEMR"); //$NON-NLS-1$ + return isVisitingChildren(); + } + public void endVisit(ExpressionMethodReference node) { + ASTVisitorTest.this.b.append("eEMR)"); //$NON-NLS-1$ + } + public boolean visit(LineComment node) { ASTVisitorTest.this.b.append("(//"); //$NON-NLS-1$ return isVisitingChildren(); @@ -892,6 +908,14 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T ASTVisitorTest.this.b.append("eSM)"); //$NON-NLS-1$ } + public boolean visit(SuperMethodReference node) { + ASTVisitorTest.this.b.append("(eSMR"); //$NON-NLS-1$ + return isVisitingChildren(); + } + public void endVisit(SuperMethodReference node) { + ASTVisitorTest.this.b.append("eSMR)"); //$NON-NLS-1$ + } + public boolean visit(SwitchCase node) { ASTVisitorTest.this.b.append("(sSC"); //$NON-NLS-1$ return isVisitingChildren(); @@ -964,6 +988,14 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T ASTVisitorTest.this.b.append("eTL)"); //$NON-NLS-1$ } + public boolean visit(TypeMethodReference node) { + ASTVisitorTest.this.b.append("(eTMR"); //$NON-NLS-1$ + return isVisitingChildren(); + } + public void endVisit(TypeMethodReference node) { + ASTVisitorTest.this.b.append("eTMR)"); //$NON-NLS-1$ + } + public boolean visit(TypeParameter node) { ASTVisitorTest.this.b.append("(tTP"); //$NON-NLS-1$ return isVisitingChildren(); @@ -1416,6 +1448,18 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T String result = this.b.toString(); assertTrue(result.equals("[(sCN"+this.N1S+"sCN)]")); //$NON-NLS-1$ //$NON-NLS-2$ } + + public void testCreationReference() { + if (this.ast.apiLevel() < AST.JLS8) + return; + CreationReference x1 = this.ast.newCreationReference(this.E1); + TestVisitor v1 = new TestVisitor(); + this.b.setLength(0); + x1.accept(v1); + String result = this.b.toString(); + assertTrue(result.equals("[(eCR"+this.E1S+"eCR)]")); //$NON-NLS-1$ //$NON-NLS-2$ + } + public void testDoStatement() { DoStatement x1 = this.ast.newDoStatement(); x1.setExpression(this.E1); @@ -1476,6 +1520,17 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T String result = this.b.toString(); assertTrue(result.equals("[(ED"+this.JD1S+this.MOD1S+this.MOD2S+this.N1S+this.T1S+this.T2S+this.EC1S+this.EC2S+this.FD1S+this.FD2S+"ED)]")); //$NON-NLS-1$ //$NON-NLS-2$ } + public void testExpressionMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) + return; + ExpressionMethodReference x1 = this.ast.newExpressionMethodReference(this.E1, this.N1); + TestVisitor v1 = new TestVisitor(); + this.b.setLength(0); + x1.accept(v1); + String result = this.b.toString(); + assertTrue(result.equals("[(eEMR"+this.E1S+this.N1S+"eEMR)]")); //$NON-NLS-1$ //$NON-NLS-2$ + } + public void testExpressionStatement() { ExpressionStatement x1 = this.ast.newExpressionStatement(this.E1); TestVisitor v1 = new TestVisitor(); @@ -2009,6 +2064,18 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T assertTrue(result.equals("[(eSM"+this.N1S+this.PT1S+this.N2S+this.E1S+this.E2S+"eSM)]")); //$NON-NLS-1$ //$NON-NLS-2$ } } + public void testSuperMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) { + return; + } + SuperMethodReference x1 = this.ast.newSuperMethodReference(this.N2); + x1.setQualifier(this.N1); + TestVisitor v1 = new TestVisitor(); + this.b.setLength(0); + x1.accept(v1); + String result = this.b.toString(); + assertTrue(result.equals("[(eSMR"+this.N1S+this.N2S+"eSMR)]")); //$NON-NLS-1$ //$NON-NLS-2$ + } public void testSwitchCase() { SwitchCase x1 = this.ast.newSwitchCase(); x1.setExpression(this.E1); @@ -2155,6 +2222,17 @@ public class ASTVisitorTest extends org.eclipse.jdt.core.tests.junit.extension.T String result = this.b.toString(); assertTrue(result.equals("[(eTL"+this.T1S+"eTL)]")); //$NON-NLS-1$ //$NON-NLS-2$ } + public void testTypeMethodReference() { + if (this.ast.apiLevel() < AST.JLS8) + return; + TypeMethodReference x1 = this.ast.newTypeMethodReference(this.T1, this.N1); + TestVisitor v1 = new TestVisitor(); + this.b.setLength(0); + x1.accept(v1); + String result = this.b.toString(); + assertTrue(result.equals("[(eTMR"+this.T1S+this.N1S+"eTMR)]")); //$NON-NLS-1$ //$NON-NLS-2$ + } + /** @deprecated using deprecated code */ public void testSingleVariableDeclaration() { SingleVariableDeclaration x1 = this.ast.newSingleVariableDeclaration(); diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/AST.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/AST.java index 660201e952..86ae7910d2 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/AST.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/AST.java @@ -1346,6 +1346,20 @@ public final class AST { } /** + * Creates an unparented creation reference node owned by this AST. + * + * @param expression expression for the left hand side of CreationReference + * @return a new unparented reference expression node + * @exception UnsupportedOperationException if this operation is used in a JLS2, JLS3 or JLS4 AST + * @since 3.9 BETA_JAVA8 + */ + public CreationReference newCreationReference(Expression expression) { + CreationReference result = new CreationReference(this); + result.setExpression(expression); + return result; + } + + /** * Creates a new unparented do statement node owned by this AST. * By default, the expression is unspecified (but legal), and * the body statement is an empty block. @@ -1413,6 +1427,22 @@ public final class AST { } /** + * Creates an unparented expression method reference node owned by this AST. + * + * @param expression expression for the left hand side of ExpressionMethodReference + * @param name name of the method in the ExpressionMethodReference + * @return a new unparented reference expression node + * @exception UnsupportedOperationException if this operation is used in a JLS2, JLS3 or JLS4 AST + * @since 3.9 BETA_JAVA8 + */ + public ExpressionMethodReference newExpressionMethodReference(Expression expression, SimpleName name) { + ExpressionMethodReference result = new ExpressionMethodReference(this); + result.setExpression(expression); + result.setName(name); + return result; + } + + /** * Creates a new unparented expression statement node owned by this AST, * for the given expression. * <p> @@ -2244,6 +2274,21 @@ public final class AST { } /** + * Creates and returns a new unparented super method reference node + * owned by this AST. By default, the expression and field are both + * unspecified, but legal, names. + * + * @param name name of the method referenced + * @return a new unparented super method reference node + * @since 3.9 BETA_JAVA8 + */ + public SuperMethodReference newSuperMethodReference(SimpleName name) { + SuperMethodReference result = new SuperMethodReference(this); + result.setName(name); + return result; + } + + /** * Creates a new unparented switch case statement node owned by * this AST. By default, the expression is unspecified, but legal. * @@ -2424,6 +2469,22 @@ public final class AST { } /** + * Creates an unparented Type method reference node owned by this AST. + * + * @param type type for the left hand side of TypeMethodReference + * @param name name of the method in the TypeMethodReference + * @return a new unparented type method reference node + * @exception UnsupportedOperationException if this operation is used in a JLS2, JLS3 or JLS4 AST + * @since 3.9 BETA_JAVA8 + */ + public TypeMethodReference newTypeMethodReference(Type type, SimpleName name) { + TypeMethodReference result = new TypeMethodReference(this); + result.setType(type); + result.setName(name); + return result; + } + + /** * Creates and returns a new unparented type parameter type node with an * unspecified type variable name and an empty list of type bounds. * diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTConverter.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTConverter.java index 2e48221b89..e59773bfe9 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTConverter.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTConverter.java @@ -46,11 +46,13 @@ 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; @@ -1761,6 +1763,9 @@ class ASTConverter { 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; } @@ -2180,13 +2185,7 @@ class ASTConverter { public Expression convert(org.eclipse.jdt.internal.compiler.ast.LambdaExpression lambda) { if (this.ast.apiLevel < AST.JLS8) { - 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(lambda.sourceStart, lambda.sourceEnd - lambda.sourceStart + 1); - return nullLiteral; + return createFakeNullLiteral(lambda); } final LambdaExpression lambdaExpression = new LambdaExpression(this.ast); if (this.resolveBindings) { @@ -2534,6 +2533,72 @@ class ASTConverter { return null; // cannot be reached } + public Expression convert(org.eclipse.jdt.internal.compiler.ast.ReferenceExpression reference) { + if (this.ast.apiLevel < AST.JLS8) { + 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() < start) {// check for new + retrieveInitAndSetPositions(start, reference.sourceEnd, name); + if (!name.getIdentifier().equals("<init>")) { //$NON-NLS-1$ + NullLiteral nullLiteral = new NullLiteral(this.ast); + nullLiteral.setFlags(nullLiteral.getFlags() | ASTNode.MALFORMED); + result = nullLiteral; + } else { + CreationReference creationReference = new CreationReference(this.ast); + creationReference.setExpression(convert(lhs)); + 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); @@ -3893,6 +3958,21 @@ class ASTConverter { 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 */ @@ -4183,8 +4263,8 @@ class ASTConverter { } protected void recordNodes(ASTNode node, org.eclipse.jdt.internal.compiler.ast.ASTNode oldASTNode) { - // Do not record the fake literal node created in lieu of LambdaExpressions at JLS levels < 8, as it would lead to CCE down the road. - if (oldASTNode instanceof org.eclipse.jdt.internal.compiler.ast.LambdaExpression && node instanceof NullLiteral) { + // 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); @@ -4716,6 +4796,29 @@ class ASTConverter { } /** + * 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. diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTMatcher.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTMatcher.java index 76ad87be2b..39c601e6f9 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTMatcher.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTMatcher.java @@ -700,6 +700,31 @@ public class ASTMatcher { * @return <code>true</code> if the subtree matches, or * <code>false</code> if they do not match or the other object has a * different node type or is <code>null</code> + * @since 3.9 BETA_JAVA8 + */ + public boolean match(CreationReference node, Object other) { + if (!(other instanceof CreationReference)) { + return false; + } + CreationReference o = (CreationReference) other; + return ( + safeSubtreeMatch(node.getExpression(), o.getExpression()) + && safeSubtreeListMatch(node.typeArguments(), o.typeArguments())); + } + + /** + * Returns whether the given node and the other object match. + * <p> + * The default implementation provided by this class tests whether the + * other object is a node of the same type with structurally isomorphic + * child subtrees. Subclasses may override this method as needed. + * </p> + * + * @param node the node + * @param other the other object, or <code>null</code> + * @return <code>true</code> if the subtree matches, or + * <code>false</code> if they do not match or the other object has a + * different node type or is <code>null</code> */ public boolean match(DoStatement node, Object other) { if (!(other instanceof DoStatement)) { @@ -832,6 +857,32 @@ public class ASTMatcher { * @return <code>true</code> if the subtree matches, or * <code>false</code> if they do not match or the other object has a * different node type or is <code>null</code> + * @since 3.9 BETA_JAVA8 + */ + public boolean match(ExpressionMethodReference node, Object other) { + if (!(other instanceof ExpressionMethodReference)) { + return false; + } + ExpressionMethodReference o = (ExpressionMethodReference) other; + return ( + safeSubtreeMatch(node.getExpression(), o.getExpression()) + && safeSubtreeListMatch(node.typeArguments(), o.typeArguments()) + && safeSubtreeMatch(node.getName(), o.getName())); + } + + /** + * Returns whether the given node and the other object match. + * <p> + * The default implementation provided by this class tests whether the + * other object is a node of the same type with structurally isomorphic + * child subtrees. Subclasses may override this method as needed. + * </p> + * + * @param node the node + * @param other the other object, or <code>null</code> + * @return <code>true</code> if the subtree matches, or + * <code>false</code> if they do not match or the other object has a + * different node type or is <code>null</code> */ public boolean match(ExpressionStatement node, Object other) { if (!(other instanceof ExpressionStatement)) { @@ -2022,6 +2073,32 @@ public class ASTMatcher { * @return <code>true</code> if the subtree matches, or * <code>false</code> if they do not match or the other object has a * different node type or is <code>null</code> + * + * @since 3.9 BETA_JAVA8 + */ + public boolean match(SuperMethodReference node, Object other) { + if (!(other instanceof SuperMethodReference)) { + return false; + } + SuperMethodReference o = (SuperMethodReference) other; + return (safeSubtreeMatch(node.getQualifier(), o.getQualifier()) + && safeSubtreeListMatch(node.typeArguments(), o.typeArguments()) + && safeSubtreeMatch(node.getName(), o.getName())); + } + + /** + * Returns whether the given node and the other object match. + * <p> + * The default implementation provided by this class tests whether the + * other object is a node of the same type with structurally isomorphic + * child subtrees. Subclasses may override this method as needed. + * </p> + * + * @param node the node + * @param other the other object, or <code>null</code> + * @return <code>true</code> if the subtree matches, or + * <code>false</code> if they do not match or the other object has a + * different node type or is <code>null</code> */ public boolean match(SwitchCase node, Object other) { if (!(other instanceof SwitchCase)) { @@ -2306,6 +2383,32 @@ public class ASTMatcher { * @return <code>true</code> if the subtree matches, or * <code>false</code> if they do not match or the other object has a * different node type or is <code>null</code> + * @since 3.9 BETA_JAVA8 + */ + public boolean match(TypeMethodReference node, Object other) { + if (!(other instanceof TypeMethodReference)) { + return false; + } + TypeMethodReference o = (TypeMethodReference) other; + return ( + safeSubtreeMatch(node.getType(), o.getType()) + && safeSubtreeListMatch(node.typeArguments(), o.typeArguments()) + && safeSubtreeMatch(node.getName(), o.getName())); + } + + /** + * Returns whether the given node and the other object match. + * <p> + * The default implementation provided by this class tests whether the + * other object is a node of the same type with structurally isomorphic + * child subtrees. Subclasses may override this method as needed. + * </p> + * + * @param node the node + * @param other the other object, or <code>null</code> + * @return <code>true</code> if the subtree matches, or + * <code>false</code> if they do not match or the other object has a + * different node type or is <code>null</code> * @since 3.1 */ public boolean match(TypeParameter node, Object other) { diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTNode.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTNode.java index 6bba4f50fe..5885d339e1 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTNode.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTNode.java @@ -868,6 +868,38 @@ public abstract class ASTNode { public static final int PACKAGE_QUALIFIED_TYPE = 88; /** + * Node type constant indicating a node of type + * <code>CreationReference</code>. + * @see CreationReference + * @since 3.9 BETA_JAV8 + */ + public static final int CREATION_REFERENCE = 89; + + /** + * Node type constant indicating a node of type + * <code>ExpressionMethodReference</code>. + * @see ExpressionMethodReference + * @since 3.9 BETA_JAV8 + */ + public static final int EXPRESSION_METHOD_REFERENCE = 90; + + /** + * Node type constant indicating a node of type + * <code>SuperMethhodReference</code>. + * @see SuperMethodReference + * @since 3.9 BETA_JAV8 + */ + public static final int SUPER_METHOD_REFERENCE = 91; + + /** + * Node type constant indicating a node of type + * <code>TypeMethodReference</code>. + * @see TypeMethodReference + * @since 3.9 BETA_JAV8 + */ + public static final int TYPE_METHOD_REFERENCE = 92; + + /** * Returns the node class for the corresponding node type. * * @param nodeType AST node type @@ -921,6 +953,8 @@ public abstract class ASTNode { return ConstructorInvocation.class; case CONTINUE_STATEMENT : return ContinueStatement.class; + case CREATION_REFERENCE : + return CreationReference.class; case UNION_TYPE : return UnionType.class; case DO_STATEMENT : @@ -933,6 +967,8 @@ public abstract class ASTNode { return EnumConstantDeclaration.class; case ENUM_DECLARATION : return EnumDeclaration.class; + case EXPRESSION_METHOD_REFERENCE : + return ExpressionMethodReference.class; case EXPRESSION_STATEMENT : return ExpressionStatement.class; case EXTRA_DIMENSION: @@ -1021,6 +1057,8 @@ public abstract class ASTNode { return SuperFieldAccess.class; case SUPER_METHOD_INVOCATION : return SuperMethodInvocation.class; + case SUPER_METHOD_REFERENCE : + return SuperMethodReference.class; case SWITCH_CASE: return SwitchCase.class; case SWITCH_STATEMENT : @@ -1041,6 +1079,8 @@ public abstract class ASTNode { return TypeDeclaration.class; case TYPE_DECLARATION_STATEMENT : return TypeDeclarationStatement.class; + case TYPE_METHOD_REFERENCE : + return TypeMethodReference.class; case TYPE_LITERAL : return TypeLiteral.class; case TYPE_PARAMETER : diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTVisitor.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTVisitor.java index 681e325d6a..b4ffbaf425 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTVisitor.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ASTVisitor.java @@ -535,6 +535,23 @@ public abstract class ASTVisitor { * Visits the given type-specific AST node. * <p> * The default implementation does nothing and return true. + * Subclasses may re-implement. + * </p> + * + * @param node the node to visit + * @return <code>true</code> if the children of this node should be + * visited, and <code>false</code> if the children of this node should + * be skipped + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(CreationReference node) { + return true; + } + + /** + * Visits the given type-specific AST node. + * <p> + * The default implementation does nothing and return true. * Subclasses may reimplement. * </p> * @@ -618,6 +635,23 @@ public abstract class ASTVisitor { * Visits the given type-specific AST node. * <p> * The default implementation does nothing and return true. + * Subclasses may re-implement. + * </p> + * + * @param node the node to visit + * @return <code>true</code> if the children of this node should be + * visited, and <code>false</code> if the children of this node should + * be skipped + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(ExpressionMethodReference node) { + return true; + } + + /** + * Visits the given type-specific AST node. + * <p> + * The default implementation does nothing and return true. * Subclasses may reimplement. * </p> * @@ -1367,6 +1401,23 @@ public abstract class ASTVisitor { * @return <code>true</code> if the children of this node should be * visited, and <code>false</code> if the children of this node should * be skipped + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(SuperMethodReference node) { + return true; + } + + /** + * Visits the given type-specific AST node. + * <p> + * The default implementation does nothing and return true. + * Subclasses may reimplement. + * </p> + * + * @param node the node to visit + * @return <code>true</code> if the children of this node should be + * visited, and <code>false</code> if the children of this node should + * be skipped */ public boolean visit(SwitchCase node) { return true; @@ -1547,6 +1598,24 @@ public abstract class ASTVisitor { * @return <code>true</code> if the children of this node should be * visited, and <code>false</code> if the children of this node should * be skipped + * + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(TypeMethodReference node) { + return true; + } + + /** + * Visits the given type-specific AST node. + * <p> + * The default implementation does nothing and return true. + * Subclasses may reimplement. + * </p> + * + * @param node the node to visit + * @return <code>true</code> if the children of this node should be + * visited, and <code>false</code> if the children of this node should + * be skipped * @since 3.1 */ public boolean visit(TypeParameter node) { @@ -1918,6 +1987,19 @@ public abstract class ASTVisitor { * </p> * * @param node the node to visit + * @since 3.9 BETA_JAVA8 + */ + public void endVisit(CreationReference node) { + // default implementation: do nothing + } + + /** + * End of visit the given type-specific AST node. + * <p> + * The default implementation does nothing. Subclasses may reimplement. + * </p> + * + * @param node the node to visit */ public void endVisit(DoStatement node) { // default implementation: do nothing @@ -1981,6 +2063,19 @@ public abstract class ASTVisitor { * </p> * * @param node the node to visit + * @since 3.9 BETA_JAVA8 + */ + public void endVisit(ExpressionMethodReference node) { + // default implementation: do nothing + } + + /** + * End of visit the given type-specific AST node. + * <p> + * The default implementation does nothing. Subclasses may reimplement. + * </p> + * + * @param node the node to visit */ public void endVisit(ExpressionStatement node) { // default implementation: do nothing @@ -2516,6 +2611,19 @@ public abstract class ASTVisitor { * </p> * * @param node the node to visit + * @since 3.9 BETA_JAVA8 + */ + public void endVisit(SuperMethodReference node) { + // default implementation: do nothing + } + + /** + * End of visit the given type-specific AST node. + * <p> + * The default implementation does nothing. Subclasses may reimplement. + * </p> + * + * @param node the node to visit */ public void endVisit(SwitchCase node) { // default implementation: do nothing @@ -2649,6 +2757,20 @@ public abstract class ASTVisitor { * </p> * * @param node the node to visit + * + * @since 3.9 BETA_JAVA8 + */ + public void endVisit(TypeMethodReference node) { + // default implementation: do nothing + } + + /** + * End of visit the given type-specific AST node. + * <p> + * The default implementation does nothing. Subclasses may reimplement. + * </p> + * + * @param node the node to visit * @since 3.1 */ public void endVisit(TypeParameter node) { diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/BindingResolver.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/BindingResolver.java index 71274a3789..de79a4cffd 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/BindingResolver.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/BindingResolver.java @@ -581,6 +581,28 @@ class BindingResolver { } /** + * Resolves the given method reference and returns the binding for it. + * <p> + * The implementation of <code>MethodReference.resolveMethodBinding</code> + * forwards to this method. How the method resolves is often a function of + * the context in which the method reference node is embedded as well as + * the method reference subtree itself. + * </p> + * <p> + * The default implementation of this method returns <code>null</code>. + * Subclasses may reimplement. + * </p> + * + * @param methodReference the method reference of interest + * @return the binding for the given method reference, or + * <code>null</code> if no binding is available + * @since 3.9 BETA_JAVA8 + */ + IMethodBinding resolveMethod(MethodReference methodReference) { + return null; + } + + /** * Resolves the given Lambda Expression and returns the binding for it. * <p> * The implementation of <code>LambdaExpression.resolveMethodBinding</code> diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/CreationReference.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/CreationReference.java new file mode 100644 index 0000000000..548afe7351 --- /dev/null +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/CreationReference.java @@ -0,0 +1,261 @@ +/******************************************************************************* + * Copyright (c) 2013 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 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +package org.eclipse.jdt.core.dom; + +import java.util.ArrayList; +import java.util.List; + +/** + * Creation reference expression AST node type (added in JLS8 API). + * + * <pre> + * CreationReference: + * Expression <b>::</b> + * [ <b><</b> Type { <b>,</b> Type } <b>></b> ] + * <b>new</b> + * </pre> + * + * @since 3.9 BETA_JAVA8 + * @noinstantiate This class is not intended to be instantiated by clients. + */ +public class CreationReference extends MethodReference { + + /** + * The "expression" structural property of this node type (child type: {@link Expression}). + */ + public static final ChildPropertyDescriptor EXPRESSION_PROPERTY = + new ChildPropertyDescriptor(CreationReference.class, "expression", Expression.class, MANDATORY, CYCLE_RISK); //$NON-NLS-1$ + + /** + * The "typeArguments" structural property of this node type (element type: {@link Type}) + */ + public static final ChildListPropertyDescriptor TYPE_ARGUMENTS_PROPERTY = + internalTypeArgumentsFactory(CreationReference.class); + + /** + * A list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}), + * or null if uninitialized. + */ + private static final List PROPERTY_DESCRIPTORS_8_0; + + static { + List propertyList = new ArrayList(4); + createPropertyList(CreationReference.class, propertyList); + addProperty(EXPRESSION_PROPERTY, propertyList); + addProperty(TYPE_ARGUMENTS_PROPERTY, propertyList); + PROPERTY_DESCRIPTORS_8_0 = reapPropertyList(propertyList); + } + + /** + * Returns a list of structural property descriptors for this node type. + * Clients must not modify the result. + * + * @param apiLevel the API level; one of the AST.JLS* constants + * @return a list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}) + */ + public static List propertyDescriptors(int apiLevel) { + return PROPERTY_DESCRIPTORS_8_0; + } + + /** + * The expression; lazily initialized; defaults to an unspecified, + * legal expression (a simple name). + */ + private Expression expression = null; + + /** + * Creates a new AST node for an CreationReference declaration owned + * by the given AST. + * <p> + * N.B. This constructor is package-private; all subclasses must be + * declared in the same package; clients are unable to declare + * additional subclasses. + * </p> + * + * @param ast the AST that is to own this node + */ + CreationReference(AST ast) { + super(ast); + unsupportedIn2_3_4(); + } + + /* (omit javadoc for this method) + * Method declared on MethodReference. + */ + final ChildListPropertyDescriptor internalTypeArgumentsProperty() { + return TYPE_ARGUMENTS_PROPERTY; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalStructuralPropertiesForType(int apiLevel) { + return propertyDescriptors(apiLevel); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final ASTNode internalGetSetChildProperty(ChildPropertyDescriptor property, boolean get, ASTNode child) { + if (property == EXPRESSION_PROPERTY) { + if (get) { + return getExpression(); + } else { + setExpression((Expression) child); + return null; + } + } + // allow default implementation to flag the error + return super.internalGetSetChildProperty(property, get, child); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalGetChildListProperty(ChildListPropertyDescriptor property) { + if (property == TYPE_ARGUMENTS_PROPERTY) { + return typeArguments(); + } + // allow default implementation to flag the error + return super.internalGetChildListProperty(property); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final int getNodeType0() { + return CREATION_REFERENCE; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + ASTNode clone0(AST target) { + CreationReference result = new CreationReference(target); + result.setSourceRange(getStartPosition(), getLength()); + result.setExpression( + (Expression) ASTNode.copySubtree(target, getExpression())); + result.typeArguments().addAll(ASTNode.copySubtrees(target, typeArguments())); + return result; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final boolean subtreeMatch0(ASTMatcher matcher, Object other) { + // dispatch to correct overloaded match method + return matcher.match(this, other); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + void accept0(ASTVisitor visitor) { + boolean visitChildren = visitor.visit(this); + if (visitChildren) { + // visit children in normal left to right reading order + acceptChild(visitor, getExpression()); + acceptChildren(visitor, this.typeArguments); + } + visitor.endVisit(this); + } + + /** + * Returns the expression of this Creation Reference expression, or + * <code>null</code> if there is none. + * + * @return the expression node, or <code>null</code> if there is none + */ + public Expression getExpression() { + if (this.expression == null) { + // lazy init must be thread-safe for readers + synchronized (this) { + if (this.expression == null) { + preLazyInit(); + this.expression = new SimpleName(this.ast); + postLazyInit(this.expression, EXPRESSION_PROPERTY); + } + } + } + return this.expression; + } + + /** + * Sets the expression of this Creation Reference. + * + * @param expression the expression node, or <code>null</code> if + * there is none + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * <li>a cycle in would be created</li> + * </ul> + */ + public void setExpression(Expression expression) { + if (expression == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.expression; + preReplaceChild(oldChild, expression, EXPRESSION_PROPERTY); + this.expression = expression; + postReplaceChild(oldChild, expression, EXPRESSION_PROPERTY); + } + + /** + * Returns the live ordered list of type arguments of this Creation Reference. + * + * @return the live list of type arguments + * (element type: {@link Type}) + */ + public List typeArguments() { + return this.typeArguments; + } + + /** + * Resolves and returns the binding for the method reference by this + * expression. + * <p> + * Note that bindings are generally unavailable unless requested when the + * AST is being built. + * </p> + * + * @return the method binding, or <code>null</code> if the binding cannot + * be resolved + */ + public IMethodBinding resolveMethodBinding() { + return this.ast.getBindingResolver().resolveMethod(this); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int memSize() { + // treat Code as free + return BASE_NODE_SIZE + 2 * 4; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int treeSize() { + return + memSize() + + (this.expression == null ? 0 : getExpression().treeSize()) + + (this.typeArguments == null ? 0 : this.typeArguments.listSize()); + } +}
\ No newline at end of file diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultASTVisitor.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultASTVisitor.java index 029f3ccd0f..c8bffe5a7e 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultASTVisitor.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultASTVisitor.java @@ -92,6 +92,9 @@ class DefaultASTVisitor extends ASTVisitor { public void endVisit(ContinueStatement node) { endVisitNode(node); } + public void endVisit(CreationReference node) { + endVisitNode(node); + } public void endVisit(DoStatement node) { endVisitNode(node); } @@ -107,6 +110,9 @@ class DefaultASTVisitor extends ASTVisitor { public void endVisit(EnumDeclaration node) { endVisitNode(node); } + public void endVisit(ExpressionMethodReference node) { + endVisitNode(node); + } public void endVisit(ExpressionStatement node) { endVisitNode(node); } @@ -239,7 +245,9 @@ class DefaultASTVisitor extends ASTVisitor { public void endVisit(SuperMethodInvocation node) { endVisitNode(node); } - + public void endVisit(SuperMethodReference node) { + endVisitNode(node); + } public void endVisit(SwitchCase node) { endVisitNode(node); } @@ -274,6 +282,9 @@ class DefaultASTVisitor extends ASTVisitor { public void endVisit(TypeLiteral node) { endVisitNode(node); } + public void endVisit(TypeMethodReference node) { + endVisitNode(node); + } public void endVisit(TypeParameter node) { endVisitNode(node); } @@ -363,6 +374,9 @@ class DefaultASTVisitor extends ASTVisitor { public boolean visit(ContinueStatement node) { return visitNode(node); } + public boolean visit(CreationReference node) { + return visitNode(node); + } public boolean visit(DoStatement node) { return visitNode(node); } @@ -378,6 +392,9 @@ class DefaultASTVisitor extends ASTVisitor { public boolean visit(EnumDeclaration node) { return visitNode(node); } + public boolean visit(ExpressionMethodReference node) { + return visitNode(node); + } public boolean visit(ExpressionStatement node) { return visitNode(node); } @@ -520,6 +537,10 @@ class DefaultASTVisitor extends ASTVisitor { return visitNode(node); } + public boolean visit(SuperMethodReference node) { + return visitNode(node); + } + public boolean visit(SwitchCase node) { return visitNode(node); } @@ -564,6 +585,10 @@ class DefaultASTVisitor extends ASTVisitor { return visitNode(node); } + public boolean visit(TypeMethodReference node) { + return visitNode(node); + } + public boolean visit(TypeParameter node) { return visitNode(node); } diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultBindingResolver.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultBindingResolver.java index 49f5856f1c..4f266a1cb0 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultBindingResolver.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DefaultBindingResolver.java @@ -709,6 +709,10 @@ class DefaultBindingResolver extends BindingResolver { case ASTNode.INFIX_EXPRESSION : case ASTNode.INSTANCEOF_EXPRESSION : case ASTNode.LAMBDA_EXPRESSION: + case ASTNode.CREATION_REFERENCE: + case ASTNode.EXPRESSION_METHOD_REFERENCE: + case ASTNode.TYPE_METHOD_REFERENCE: + case ASTNode.SUPER_METHOD_REFERENCE : case ASTNode.FIELD_ACCESS : case ASTNode.SUPER_FIELD_ACCESS : case ASTNode.ARRAY_ACCESS : @@ -875,15 +879,15 @@ class DefaultBindingResolver extends BindingResolver { /* * Method declared on BindingResolver. */ - synchronized IMethodBinding resolveMethod(MethodDeclaration method) { - Object oldNode = this.newAstToOldAst.get(method); - if (oldNode instanceof AbstractMethodDeclaration) { - AbstractMethodDeclaration methodDeclaration = (AbstractMethodDeclaration) oldNode; - IMethodBinding methodBinding = getMethodBinding(methodDeclaration.binding); + synchronized IMethodBinding resolveMethod(LambdaExpression lambda) { + Object oldNode = this.newAstToOldAst.get(lambda); + if (oldNode instanceof org.eclipse.jdt.internal.compiler.ast.LambdaExpression) { + org.eclipse.jdt.internal.compiler.ast.LambdaExpression lambdaExpression = (org.eclipse.jdt.internal.compiler.ast.LambdaExpression) oldNode; + IMethodBinding methodBinding = getMethodBinding(lambdaExpression.binding); if (methodBinding == null) { return null; } - this.bindingsToAstNodes.put(methodBinding, method); + this.bindingsToAstNodes.put(methodBinding, lambda); String key = methodBinding.getKey(); if (key != null) { this.bindingTables.bindingKeysToBindings.put(key, methodBinding); @@ -895,15 +899,15 @@ class DefaultBindingResolver extends BindingResolver { /* * Method declared on BindingResolver. */ - synchronized IMethodBinding resolveMethod(LambdaExpression lambda) { - Object oldNode = this.newAstToOldAst.get(lambda); - if (oldNode instanceof org.eclipse.jdt.internal.compiler.ast.LambdaExpression) { - org.eclipse.jdt.internal.compiler.ast.LambdaExpression lambdaExpression = (org.eclipse.jdt.internal.compiler.ast.LambdaExpression) oldNode; - IMethodBinding methodBinding = getMethodBinding(lambdaExpression.binding); + synchronized IMethodBinding resolveMethod(MethodDeclaration method) { + Object oldNode = this.newAstToOldAst.get(method); + if (oldNode instanceof AbstractMethodDeclaration) { + AbstractMethodDeclaration methodDeclaration = (AbstractMethodDeclaration) oldNode; + IMethodBinding methodBinding = getMethodBinding(methodDeclaration.binding); if (methodBinding == null) { return null; } - this.bindingsToAstNodes.put(methodBinding, lambda); + this.bindingsToAstNodes.put(methodBinding, method); String key = methodBinding.getKey(); if (key != null) { this.bindingTables.bindingKeysToBindings.put(key, methodBinding); @@ -926,6 +930,26 @@ class DefaultBindingResolver extends BindingResolver { /* * Method declared on BindingResolver. */ + synchronized IMethodBinding resolveMethod(MethodReference methodReference) { + Object oldNode = this.newAstToOldAst.get(methodReference); + if (oldNode instanceof org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) { + org.eclipse.jdt.internal.compiler.ast.ReferenceExpression referenceExpression = (org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) oldNode; + IMethodBinding methodBinding = getMethodBinding(referenceExpression.binding); + if (methodBinding == null) { + return null; + } + this.bindingsToAstNodes.put(methodBinding, methodReference); + String key = methodBinding.getKey(); + if (key != null) { + this.bindingTables.bindingKeysToBindings.put(key, methodBinding); + } + return methodBinding; + } + return null; + } + /* + * Method declared on BindingResolver. + */ synchronized IMethodBinding resolveMethod(SuperMethodInvocation method) { Object oldNode = this.newAstToOldAst.get(method); if (oldNode instanceof MessageSend) { @@ -1140,6 +1164,11 @@ class DefaultBindingResolver extends BindingResolver { IMethodBinding method = getMethodBinding(memberValuePair.binding); if (method == null) return null; return method.getReturnType(); + } else if (node instanceof org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) { + org.eclipse.jdt.internal.compiler.ast.ReferenceExpression referenceExpression = (org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) node; + IMethodBinding method = getMethodBinding(referenceExpression.binding); + if (method == null) return null; + return method.getReturnType(); } return null; } @@ -1400,6 +1429,9 @@ class DefaultBindingResolver extends BindingResolver { } else if (node instanceof org.eclipse.jdt.internal.compiler.ast.MemberValuePair) { org.eclipse.jdt.internal.compiler.ast.MemberValuePair memberValuePair = (org.eclipse.jdt.internal.compiler.ast.MemberValuePair) node; return getMethodBinding(memberValuePair.binding); + } else if (node instanceof org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) { + org.eclipse.jdt.internal.compiler.ast.ReferenceExpression referenceExpression = (org.eclipse.jdt.internal.compiler.ast.ReferenceExpression) node; + return getMethodBinding(referenceExpression.binding); } return null; } diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/Expression.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/Expression.java index 6fd76fa9cc..a5b6dabb37 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/Expression.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/Expression.java @@ -31,11 +31,14 @@ package org.eclipse.jdt.core.dom; * {@link CharacterLiteral}, * {@link ClassInstanceCreation}, * {@link ConditionalExpression}, + * {@link CreationReference}, + * {@link ExpressionMethodReference}, * {@link FieldAccess}, * {@link InfixExpression}, * {@link InstanceofExpression}, * {@link LambdaExpression}, * {@link MethodInvocation}, + * {@link MethodReference}, * {@link Name}, * {@link NullLiteral}, * {@link NumberLiteral}, @@ -45,8 +48,10 @@ package org.eclipse.jdt.core.dom; * {@link StringLiteral}, * {@link SuperFieldAccess}, * {@link SuperMethodInvocation}, + * {@link SuperMethodReference}, * {@link ThisExpression}, * {@link TypeLiteral}, + * {@link TypeMethodReference}, * {@link VariableDeclarationExpression} * </pre> * </p> diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ExpressionMethodReference.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ExpressionMethodReference.java new file mode 100644 index 0000000000..b1f39588fe --- /dev/null +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/ExpressionMethodReference.java @@ -0,0 +1,296 @@ +/******************************************************************************* + * Copyright (c) 2013 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 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +package org.eclipse.jdt.core.dom; + +import java.util.ArrayList; +import java.util.List; + +/** + * Expression method reference AST node type (added in JLS8 API). + * <pre> + * ExpressionMethodReference: + * Expression <b>::</b> + * [ <b><</b> Type { <b>,</b> Type } <b>></b> ] + * Identifier + * </pre> + * + * @since 3.9 BETA_JAVA8 + * @noinstantiate This class is not intended to be instantiated by clients. + */ +public class ExpressionMethodReference extends MethodReference { + + /** + * The "expression" structural property of this node type (child type: {@link Expression}). + */ + public static final ChildPropertyDescriptor EXPRESSION_PROPERTY = + new ChildPropertyDescriptor(ExpressionMethodReference.class, "expression", Expression.class, MANDATORY, CYCLE_RISK); //$NON-NLS-1$ + + /** + * The "typeArguments" structural property of this node type (element type: {@link Type}) + */ + public static final ChildListPropertyDescriptor TYPE_ARGUMENTS_PROPERTY = + internalTypeArgumentsFactory(ExpressionMethodReference.class); + + /** + * The "name" structural property of this node type (child type: {@link SimpleName}. + */ + public static final ChildPropertyDescriptor NAME_PROPERTY = + new ChildPropertyDescriptor(ExpressionMethodReference.class, "name", SimpleName.class, MANDATORY, NO_CYCLE_RISK); //$NON-NLS-1$ + + /** + * A list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}), + * or null if uninitialized. + */ + private static final List PROPERTY_DESCRIPTORS_8_0; + + static { + List propertyList = new ArrayList(4); + createPropertyList(ExpressionMethodReference.class, propertyList); + addProperty(EXPRESSION_PROPERTY, propertyList); + addProperty(TYPE_ARGUMENTS_PROPERTY, propertyList); + addProperty(NAME_PROPERTY, propertyList); + PROPERTY_DESCRIPTORS_8_0 = reapPropertyList(propertyList); + } + + /** + * Returns a list of structural property descriptors for this node type. + * Clients must not modify the result. + * + * @param apiLevel the API level; one of the AST.JLS* constants + * @return a list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}) + */ + public static List propertyDescriptors(int apiLevel) { + return PROPERTY_DESCRIPTORS_8_0; + } + + /** + * The expression; defaults to null. + */ + private Expression expression = null; + + /** + * The method name; lazily initialized; defaults to an unspecified, + * legal Java method name. + */ + private SimpleName methodName = null; + + /** + * Creates a new AST node for an ExpressionMethodReference declaration owned + * by the given AST. + * <p> + * N.B. This constructor is package-private; all subclasses must be + * declared in the same package; clients are unable to declare + * additional subclasses. + * </p> + * + * @param ast the AST that is to own this node + */ + ExpressionMethodReference(AST ast) { + super(ast); + unsupportedIn2_3_4(); + } + + /* (omit javadoc for this method) + * Method declared on MethodReference. + */ + final ChildListPropertyDescriptor internalTypeArgumentsProperty() { + return TYPE_ARGUMENTS_PROPERTY; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalStructuralPropertiesForType(int apiLevel) { + return propertyDescriptors(apiLevel); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final ASTNode internalGetSetChildProperty(ChildPropertyDescriptor property, boolean get, ASTNode child) { + if (property == NAME_PROPERTY) { + if (get) { + return getName(); + } else { + setName((SimpleName) child); + return null; + } + } + if (property == EXPRESSION_PROPERTY) { + if (get) { + return getExpression(); + } else { + setExpression((Expression) child); + return null; + } + } + // allow default implementation to flag the error + return super.internalGetSetChildProperty(property, get, child); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalGetChildListProperty(ChildListPropertyDescriptor property) { + if (property == TYPE_ARGUMENTS_PROPERTY) { + return typeArguments(); + } + // allow default implementation to flag the error + return super.internalGetChildListProperty(property); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final int getNodeType0() { + return EXPRESSION_METHOD_REFERENCE; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + ASTNode clone0(AST target) { + ExpressionMethodReference result = new ExpressionMethodReference(target); + result.setSourceRange(getStartPosition(), getLength()); + result.setExpression( + (Expression) ASTNode.copySubtree(target, getExpression())); + result.typeArguments().addAll(ASTNode.copySubtrees(target, typeArguments())); + result.setName((SimpleName) getName().clone(target)); + return result; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final boolean subtreeMatch0(ASTMatcher matcher, Object other) { + // dispatch to correct overloaded match method + return matcher.match(this, other); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + void accept0(ASTVisitor visitor) { + boolean visitChildren = visitor.visit(this); + if (visitChildren) { + // visit children in normal left to right reading order + acceptChild(visitor, getExpression()); + acceptChildren(visitor, this.typeArguments); + acceptChild(visitor, getName()); + } + visitor.endVisit(this); + } + + /** + * Returns the expression of this expression method reference expression + * + * @return the expression node + */ + public Expression getExpression() { + return this.expression; + } + + /** + * Sets the expression of this expression method reference. + * + * @param expression the expression node + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * <li>a cycle in would be created</li> + * </ul> + */ + public void setExpression(Expression expression) { + if (expression == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.expression; + preReplaceChild(oldChild, expression, EXPRESSION_PROPERTY); + this.expression = expression; + postReplaceChild(oldChild, expression, EXPRESSION_PROPERTY); + } + + /** + * Returns the live ordered list of type arguments of this expression method reference + * + * @return the live list of type arguments + * (element type: {@link Type}) + */ + public List typeArguments() { + return this.typeArguments; + } + + /** + * Returns the name of the method referenced in this expression. + * + * @return the method name node + */ + public SimpleName getName() { + if (this.methodName == null) { + // lazy init must be thread-safe for readers + synchronized (this) { + if (this.methodName == null) { + preLazyInit(); + this.methodName = new SimpleName(this.ast); + postLazyInit(this.methodName, NAME_PROPERTY); + } + } + } + return this.methodName; + } + + /** + * Sets the name of the method referenced in this expression to the + * given name. + * + * @param name the new method name + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * </ul> + */ + public void setName(SimpleName name) { + if (name == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.methodName; + preReplaceChild(oldChild, name, NAME_PROPERTY); + this.methodName = name; + postReplaceChild(oldChild, name, NAME_PROPERTY); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int memSize() { + // treat Code as free + return BASE_NODE_SIZE + 3 * 4; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int treeSize() { + return + memSize() + + (this.expression == null ? 0 : getExpression().treeSize()) + + (this.typeArguments == null ? 0 : this.typeArguments.listSize()) + + (this.methodName == null ? 0 : getName().treeSize()); + } +}
\ No newline at end of file diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/MethodReference.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/MethodReference.java new file mode 100644 index 0000000000..2cf929e307 --- /dev/null +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/MethodReference.java @@ -0,0 +1,111 @@ +/******************************************************************************* + * Copyright (c) 2013 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 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +package org.eclipse.jdt.core.dom; + +import java.util.List; + +/** + * Abstract base class of all AST node types that represent a method reference + * expression (added in JLS8 API). + * <p> + * <pre> + * MethodReference: + * CreationReference + * ExpressionMethodReference + * SuperMethodReference + * TypeMethodReference + * </pre> + * </p> + * + * @see CreationReference + * @see ExpressionMethodReference + * @see SuperMethodReference + * @see TypeMethodReference + * @since 3.9 BETA_JAVA8 + */ +public abstract class MethodReference extends Expression { + + /** + * The type arguments (element type: {@link Type}). + * Defaults to an empty list (see constructor). + */ + ASTNode.NodeList typeArguments; + + /** + * Creates and returns a structural property descriptor for the "typeArguments" + * property declared on the given concrete node type (element type: {@link Type}). + * + * @return the property descriptor + */ + static final ChildListPropertyDescriptor internalTypeArgumentsFactory(Class nodeClass) { + return new ChildListPropertyDescriptor(nodeClass, "typeArguments", Type.class, NO_CYCLE_RISK); //$NON-NLS-1$ + } + + /** + * Returns the structural property descriptor for the "typeArguments" property + * of this node (element type: {@link Type}). + * + * @return the property descriptor + */ + abstract ChildListPropertyDescriptor internalTypeArgumentsProperty(); + + /** + * Returns the structural property descriptor for the "typeArguments" property + * of this node (element type: {@link Type}). + * + * @return the property descriptor + */ + public final ChildListPropertyDescriptor getTypeArgumentsProperty() { + return internalTypeArgumentsProperty(); + } + + /** + * Creates a new AST node for a method reference owned by the given AST. + * <p> + * N.B. This constructor is package-private. + * </p> + * + * @param ast the AST that is to own this node + */ + MethodReference(AST ast) { + super(ast); + this.typeArguments = new ASTNode.NodeList(getTypeArgumentsProperty()); + } + + /** + * Returns the live ordered list of type arguments of this method reference. + * + * @return the live list of type arguments + * (element type: {@link Type}) + */ + public List typeArguments() { + return this.typeArguments; + } + + /** + * Resolves and returns the binding for the method referenced by this + * method reference expression. + * <p> + * Note that bindings are generally unavailable unless requested when the + * AST is being built. + * </p> + * + * @return the method binding, or <code>null</code> if the binding cannot + * be resolved + */ + public IMethodBinding resolveMethodBinding() { + return this.ast.getBindingResolver().resolveMethod(this); + } +} diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/SuperMethodReference.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/SuperMethodReference.java new file mode 100644 index 0000000000..9725848472 --- /dev/null +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/SuperMethodReference.java @@ -0,0 +1,291 @@ +/******************************************************************************* + * Copyright (c) 2013 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 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +package org.eclipse.jdt.core.dom; + +import java.util.ArrayList; +import java.util.List; + +/** + * Super method reference AST node type (added in JLS8 API). + * + * <pre> + * SuperMethodReference: + * [ ClassName <b>.</b> ] <b>super</b> <b>::</b> + * [ <b><</b> Type { <b>,</b> Type } <b>></b> ] + * Identifier + * </pre> + * + * @since 3.9 BETA_JAVA8 + * @noinstantiate This class is not intended to be instantiated by clients + */ +public class SuperMethodReference extends MethodReference { + + /** + * The "qualifier" structural property of this node type (child type: {@link Name}). + */ + public static final ChildPropertyDescriptor QUALIFIER_PROPERTY = + new ChildPropertyDescriptor(SuperMethodReference.class, "qualifier", Name.class, OPTIONAL, NO_CYCLE_RISK); //$NON-NLS-1$ + + /** + * The "typeArguments" structural property of this node type (element type: {@link Type}) + */ + public static final ChildListPropertyDescriptor TYPE_ARGUMENTS_PROPERTY = + internalTypeArgumentsFactory(SuperMethodReference.class); + + /** + * The "name" structural property of this node type (child type: {@link SimpleName}). + */ + public static final ChildPropertyDescriptor NAME_PROPERTY = + new ChildPropertyDescriptor(SuperMethodReference.class, "name", SimpleName.class, MANDATORY, NO_CYCLE_RISK); //$NON-NLS-1$ + + /** + * A list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}), + * or null if uninitialized. + */ + private static final List PROPERTY_DESCRIPTORS_8_0; + + static { + List propertyList = new ArrayList(4); + createPropertyList(SuperMethodReference.class, propertyList); + addProperty(QUALIFIER_PROPERTY, propertyList); + addProperty(TYPE_ARGUMENTS_PROPERTY, propertyList); + addProperty(NAME_PROPERTY, propertyList); + PROPERTY_DESCRIPTORS_8_0 = reapPropertyList(propertyList); + } + + /** + * Returns a list of structural property descriptors for this node type. + * Clients must not modify the result. + * + * @param apiLevel the API level; one of the + * <code>AST.JLS*</code> constants + * @return a list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}) + */ + public static List propertyDescriptors(int apiLevel) { + return PROPERTY_DESCRIPTORS_8_0; + } + + /** + * The optional qualifier; <code>null</code> for none; defaults to none. + */ + private Name optionalQualifier = null; + + /** + * The method name; lazily initialized; defaults to a unspecified, + * legal Java method name. + */ + private SimpleName methodName = null; + /** + * Creates a new AST node for a super method reference owned + * by the given AST. By default, there is no qualifier. + * <p> + * N.B. This constructor is package-private; all subclasses must be + * declared in the same package; clients are unable to declare + * additional subclasses. + * </p> + * + * @param ast the AST that is to own this node + */ + SuperMethodReference(AST ast) { + super(ast); + unsupportedIn2_3_4(); + } + + /* (omit javadoc for this method) + * Method declared on MethodReference. + */ + final ChildListPropertyDescriptor internalTypeArgumentsProperty() { + return TYPE_ARGUMENTS_PROPERTY; + } + + final List internalStructuralPropertiesForType(int apiLevel) { + return propertyDescriptors(apiLevel); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final ASTNode internalGetSetChildProperty(ChildPropertyDescriptor property, boolean get, ASTNode child) { + if (property == QUALIFIER_PROPERTY) { + if (get) { + return getQualifier(); + } else { + setQualifier((Name) child); + return null; + } + } + if (property == NAME_PROPERTY) { + if (get) { + return getName(); + } else { + setName((SimpleName) child); + return null; + } + } + // allow default implementation to flag the error + return super.internalGetSetChildProperty(property, get, child); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalGetChildListProperty(ChildListPropertyDescriptor property) { + if (property == TYPE_ARGUMENTS_PROPERTY) { + return typeArguments(); + } + // allow default implementation to flag the error + return super.internalGetChildListProperty(property); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final int getNodeType0() { + return SUPER_METHOD_REFERENCE; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + ASTNode clone0(AST target) { + SuperMethodReference result = new SuperMethodReference(target); + result.setSourceRange(getStartPosition(), getLength()); + result.setName((SimpleName) getName().clone(target)); + result.setQualifier((Name) ASTNode.copySubtree(target, getQualifier())); + result.typeArguments().addAll(ASTNode.copySubtrees(target, typeArguments())); + return result; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final boolean subtreeMatch0(ASTMatcher matcher, Object other) { + // dispatch to correct overloaded match method + return matcher.match(this, other); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + void accept0(ASTVisitor visitor) { + boolean visitChildren = visitor.visit(this); + if (visitChildren) { + // visit children in normal left to right reading order + acceptChild(visitor, getQualifier()); + acceptChildren(visitor, this.typeArguments); + acceptChild(visitor, getName()); + } + visitor.endVisit(this); + } + + /** + * Returns the qualifier of this "super" method reference, or + * <code>null</code> if there is none. + * + * @return the qualifier name node, or <code>null</code> if there is none + */ + public Name getQualifier() { + return this.optionalQualifier; + } + + /** + * Sets the qualifier of this "super" method reference expression. + * + * @param name the qualifier name node, or <code>null</code> if + * there is none + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * </ul> + */ + public void setQualifier(Name name) { + ASTNode oldChild = this.optionalQualifier; + preReplaceChild(oldChild, name, QUALIFIER_PROPERTY); + this.optionalQualifier = name; + postReplaceChild(oldChild, name, QUALIFIER_PROPERTY); + } + + /** + * Returns the live ordered list of type arguments of this super method reference. + * + * @return the live list of type arguments + * (element type: {@link Type}) + */ + public List typeArguments() { + return this.typeArguments; + } + + /** + * Returns the name of the method referenced in this expression. + * + * @return the method name node + */ + public SimpleName getName() { + if (this.methodName == null) { + // lazy init must be thread-safe for readers + synchronized (this) { + if (this.methodName == null) { + preLazyInit(); + this.methodName = new SimpleName(this.ast); + postLazyInit(this.methodName, NAME_PROPERTY); + } + } + } + return this.methodName; + } + + /** + * Sets the name of the method referenced in this expression to the + * given name. + * + * @param name the new method name + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * </ul> + */ + public void setName(SimpleName name) { + if (name == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.methodName; + preReplaceChild(oldChild, name, NAME_PROPERTY); + this.methodName = name; + postReplaceChild(oldChild, name, NAME_PROPERTY); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int memSize() { + // treat Code as free + return BASE_NODE_SIZE + 3 * 4; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int treeSize() { + return + memSize() + + (this.optionalQualifier == null ? 0 : getQualifier().treeSize()) + + (this.typeArguments == null ? 0 : this.typeArguments.listSize()) + + (this.methodName == null ? 0 : getName().treeSize()); + } +}
\ No newline at end of file diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/TypeMethodReference.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/TypeMethodReference.java new file mode 100644 index 0000000000..25158e528d --- /dev/null +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/TypeMethodReference.java @@ -0,0 +1,311 @@ +/******************************************************************************* + * Copyright (c) 2013 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 + * + * This is an implementation of an early-draft specification developed under the Java + * Community Process (JCP) and is made available for testing and evaluation purposes + * only. The code is not compatible with any specification of the JCP. + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +package org.eclipse.jdt.core.dom; + +import java.util.ArrayList; +import java.util.List; + +/** + * Type method reference expression AST node type (added in JLS8 API). + * <pre> + * TypeMethodReference: + * Type <b>::</b> + * [ <b><</b> Type { <b>,</b> Type } <b>></b> ] + * Identifier + * </pre> + * + * @since 3.9 BETA_JAVA8 + * @noinstantiate This class is not intended to be instantiated by clients. + */ +public class TypeMethodReference extends MethodReference { + + /** + * The "type" structural property of this node type (child type: {@link Type}). + */ + public static final ChildPropertyDescriptor TYPE_PROPERTY = + new ChildPropertyDescriptor(TypeMethodReference.class, "type", Type.class, MANDATORY, NO_CYCLE_RISK); //$NON-NLS-1$ + + /** + * The "typeArguments" structural property of this node type (element type: {@link Type}) + */ + public static final ChildListPropertyDescriptor TYPE_ARGUMENTS_PROPERTY = + internalTypeArgumentsFactory(TypeMethodReference.class); + + /** + * The "name" structural property of this node type (child type: {@link SimpleName}. + */ + public static final ChildPropertyDescriptor NAME_PROPERTY = + new ChildPropertyDescriptor(TypeMethodReference.class, "name", SimpleName.class, MANDATORY, NO_CYCLE_RISK); //$NON-NLS-1$ + + /** + * A list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}), + * or null if uninitialized. + */ + private static final List PROPERTY_DESCRIPTORS_8_0; + + static { + List propertyList = new ArrayList(4); + createPropertyList(TypeMethodReference.class, propertyList); + addProperty(TYPE_PROPERTY, propertyList); + addProperty(TYPE_ARGUMENTS_PROPERTY, propertyList); + addProperty(NAME_PROPERTY, propertyList); + PROPERTY_DESCRIPTORS_8_0 = reapPropertyList(propertyList); + } + + /** + * Returns a list of structural property descriptors for this node type. + * Clients must not modify the result. + * + * @param apiLevel the API level; one of the AST.JLS* constants + * @return a list of property descriptors (element type: + * {@link StructuralPropertyDescriptor}) + */ + public static List propertyDescriptors(int apiLevel) { + return PROPERTY_DESCRIPTORS_8_0; + } + + /** + * The type; defaults to null. + */ + private Type type = null; + + /** + * The method name; lazily initialized; defaults to an unspecified, + * legal Java method name. + */ + private SimpleName methodName = null; + + /** + * Creates a new AST node for an TypeMethodReference declaration owned + * by the given AST. + * <p> + * N.B. This constructor is package-private; all subclasses must be + * declared in the same package; clients are unable to declare + * additional subclasses. + * </p> + * + * @param ast the AST that is to own this node + */ + TypeMethodReference(AST ast) { + super(ast); + unsupportedIn2_3_4(); + } + + /* (omit javadoc for this method) + * Method declared on MethodReference. + */ + final ChildListPropertyDescriptor internalTypeArgumentsProperty() { + return TYPE_ARGUMENTS_PROPERTY; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalStructuralPropertiesForType(int apiLevel) { + return propertyDescriptors(apiLevel); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final ASTNode internalGetSetChildProperty(ChildPropertyDescriptor property, boolean get, ASTNode child) { + if (property == NAME_PROPERTY) { + if (get) { + return getName(); + } else { + setName((SimpleName) child); + return null; + } + } + if (property == TYPE_PROPERTY) { + if (get) { + return getType(); + } else { + setType((Type) child); + return null; + } + } + // allow default implementation to flag the error + return super.internalGetSetChildProperty(property, get, child); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final List internalGetChildListProperty(ChildListPropertyDescriptor property) { + if (property == TYPE_ARGUMENTS_PROPERTY) { + return typeArguments(); + } + // allow default implementation to flag the error + return super.internalGetChildListProperty(property); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final int getNodeType0() { + return TYPE_METHOD_REFERENCE; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + ASTNode clone0(AST target) { + TypeMethodReference result = new TypeMethodReference(target); + result.setSourceRange(getStartPosition(), getLength()); + result.setName((SimpleName) getName().clone(target)); + result.setType( + (Type) ASTNode.copySubtree(target, getType())); + result.typeArguments().addAll(ASTNode.copySubtrees(target, typeArguments())); + return result; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + final boolean subtreeMatch0(ASTMatcher matcher, Object other) { + // dispatch to correct overloaded match method + return matcher.match(this, other); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + void accept0(ASTVisitor visitor) { + boolean visitChildren = visitor.visit(this); + if (visitChildren) { + // visit children in normal left to right reading order + acceptChild(visitor, getType()); + acceptChildren(visitor, this.typeArguments); + acceptChild(visitor, getName()); + } + visitor.endVisit(this); + } + + /** + * Returns the type of this type method reference expression + * + * @return the type node + */ + public Type getType() { + return this.type; + } + + /** + * Sets the type of this type method reference. + * + * @param type type of this method reference + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * <li>a cycle in would be created</li> + * </ul> + */ + public void setType(Type type) { + if (type == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.type; + preReplaceChild(oldChild, type, TYPE_PROPERTY); + this.type = type; + postReplaceChild(oldChild, type, TYPE_PROPERTY); + } + + /** + * Returns the live ordered list of type arguments of this type method reference + * + * @return the live list of type arguments + * (element type: {@link Type}) + */ + public List typeArguments() { + return this.typeArguments; + } + + /** + * Returns the name of the method referenced in this expression. + * + * @return the method name node + */ + public SimpleName getName() { + if (this.methodName == null) { + // lazy init must be thread-safe for readers + synchronized (this) { + if (this.methodName == null) { + preLazyInit(); + this.methodName = new SimpleName(this.ast); + postLazyInit(this.methodName, NAME_PROPERTY); + } + } + } + return this.methodName; + } + + /** + * Sets the name of the method referenced in this expression to the + * given name. + * + * @param name the new method name + * @exception IllegalArgumentException if: + * <ul> + * <li>the node belongs to a different AST</li> + * <li>the node already has a parent</li> + * </ul> + */ + public void setName(SimpleName name) { + if (name == null) { + throw new IllegalArgumentException(); + } + ASTNode oldChild = this.methodName; + preReplaceChild(oldChild, name, NAME_PROPERTY); + this.methodName = name; + postReplaceChild(oldChild, name, NAME_PROPERTY); + } + + /** + * Resolves and returns the binding for the method referenced by this + * expression. + * <p> + * Note that bindings are generally unavailable unless requested when the + * AST is being built. + * </p> + * + * @return the method binding, or <code>null</code> if the binding cannot + * be resolved + */ + public IMethodBinding resolveMethodBinding() { + return this.ast.getBindingResolver().resolveMethod(this); + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int memSize() { + // treat Code as free + return BASE_NODE_SIZE + 3 * 4; + } + + /* (omit javadoc for this method) + * Method declared on ASTNode. + */ + int treeSize() { + return + memSize() + + (this.type == null ? 0 : getType().treeSize()) + + (this.typeArguments == null ? 0 : this.typeArguments.listSize()) + + (this.methodName == null ? 0 : getName().treeSize()); + } +}
\ No newline at end of file diff --git a/org.eclipse.jdt.core/dom/org/eclipse/jdt/internal/core/dom/NaiveASTFlattener.java b/org.eclipse.jdt.core/dom/org/eclipse/jdt/internal/core/dom/NaiveASTFlattener.java index ecd82da382..cf0563c941 100644 --- a/org.eclipse.jdt.core/dom/org/eclipse/jdt/internal/core/dom/NaiveASTFlattener.java +++ b/org.eclipse.jdt.core/dom/org/eclipse/jdt/internal/core/dom/NaiveASTFlattener.java @@ -202,6 +202,27 @@ public class NaiveASTFlattener extends ASTVisitor { } } + /** + * reference node helper function that is common to all + * the difference reference nodes. + * + * @param typeArguments list of type arguments + */ + private void visitReferenceTypeArguments(List typeArguments) { + this.buffer.append("::");//$NON-NLS-1$ + if (!typeArguments.isEmpty()) { + this.buffer.append('<'); + for (Iterator it = typeArguments.iterator(); it.hasNext(); ) { + Type t = (Type) it.next(); + t.accept(this); + if (it.hasNext()) { + this.buffer.append(','); + } + } + this.buffer.append('>'); + } + } + private void visitTypeAnnotations(AnnotatableType node) { if (node.getAST().apiLevel() >= AST.JLS8) { visitAnnotationsList(node.annotations()); @@ -578,6 +599,18 @@ public class NaiveASTFlattener extends ASTVisitor { } /* + * @see ASTVisitor#visit(CreationReference) + * + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(CreationReference node) { + node.getExpression().accept(this); + visitReferenceTypeArguments(node.typeArguments()); + this.buffer.append("new");//$NON-NLS-1$ + return false; + } + + /* * @see ASTVisitor#visit(DoStatement) */ public boolean visit(DoStatement node) { @@ -689,6 +722,18 @@ public class NaiveASTFlattener extends ASTVisitor { } /* + * @see ASTVisitor#visit(ExpressionMethodReference) + * + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(ExpressionMethodReference node) { + node.getExpression().accept(this); + visitReferenceTypeArguments(node.typeArguments()); + node.getName().accept(this); + return false; + } + + /* * @see ASTVisitor#visit(ExpressionStatement) */ public boolean visit(ExpressionStatement node) { @@ -1479,6 +1524,22 @@ public class NaiveASTFlattener extends ASTVisitor { } /* + * @see ASTVisitor#visit(SuperMethodReference) + * + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(SuperMethodReference node) { + if (node.getQualifier() != null) { + node.getQualifier().accept(this); + this.buffer.append('.'); + } + this.buffer.append("super");//$NON-NLS-1$ + visitReferenceTypeArguments(node.typeArguments()); + node.getName().accept(this); + return false; + } + + /* * @see ASTVisitor#visit(SwitchCase) */ public boolean visit(SwitchCase node) { @@ -1735,6 +1796,18 @@ public class NaiveASTFlattener extends ASTVisitor { } /* + * @see ASTVisitor#visit(TypeMethodReference) + * + * @since 3.9 BETA_JAVA8 + */ + public boolean visit(TypeMethodReference node) { + node.getType().accept(this); + visitReferenceTypeArguments(node.typeArguments()); + node.getName().accept(this); + return false; + } + + /* * @see ASTVisitor#visit(TypeParameter) * @since 3.1 */ |