aboutsummaryrefslogtreecommitdiff
path: root/src/core/lombok/eclipse
diff options
context:
space:
mode:
authorRoel Spilker <r.spilker@gmail.com>2013-03-26 02:42:14 +0100
committerRoel Spilker <r.spilker@gmail.com>2013-03-26 02:42:14 +0100
commit9630fc96e8382d68505a4cb8ab2ae08aec48e776 (patch)
tree10a6e50e5d6001cb2dfa6abbf04be870e665f3ff /src/core/lombok/eclipse
parent7a50b9a6345de2826a6fc314c8d31e9bfd3fca32 (diff)
downloadlombok-9630fc96e8382d68505a4cb8ab2ae08aec48e776.tar.gz
lombok-9630fc96e8382d68505a4cb8ab2ae08aec48e776.tar.bz2
lombok-9630fc96e8382d68505a4cb8ab2ae08aec48e776.zip
Massive performance improvements, and a few potentially breaking changes for other lombok plugin developers.
Diffstat (limited to 'src/core/lombok/eclipse')
-rw-r--r--src/core/lombok/eclipse/EclipseAST.java23
-rw-r--r--src/core/lombok/eclipse/EclipseImportList.java131
-rw-r--r--src/core/lombok/eclipse/HandlerLibrary.java41
-rw-r--r--src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java2
4 files changed, 158 insertions, 39 deletions
diff --git a/src/core/lombok/eclipse/EclipseAST.java b/src/core/lombok/eclipse/EclipseAST.java
index 8ab42140..d1f4ff06 100644
--- a/src/core/lombok/eclipse/EclipseAST.java
+++ b/src/core/lombok/eclipse/EclipseAST.java
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2009-2010 The Project Lombok Authors.
+ * Copyright (C) 2009-2013 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -30,6 +30,7 @@ import java.util.List;
import lombok.Lombok;
import lombok.core.AST;
+import lombok.core.ImmutableList;
import org.eclipse.jdt.internal.compiler.ast.ASTNode;
import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
@@ -55,7 +56,7 @@ public class EclipseAST extends AST<EclipseAST, EclipseNode, ASTNode> {
* @param ast The compilation unit, which serves as the top level node in the tree to be built.
*/
public EclipseAST(CompilationUnitDeclaration ast) {
- super(toFileName(ast), packageDeclaration(ast), imports(ast));
+ super(toFileName(ast), packageDeclaration(ast), new EclipseImportList(ast));
this.compilationUnitDeclaration = ast;
setTop(buildCompilationUnit(ast));
this.completeParse = isComplete(ast);
@@ -67,18 +68,6 @@ public class EclipseAST extends AST<EclipseAST, EclipseNode, ASTNode> {
return pkg == null ? null : Eclipse.toQualifiedName(pkg.getImportName());
}
- private static Collection<String> imports(CompilationUnitDeclaration cud) {
- List<String> imports = new ArrayList<String>();
- if (cud.imports == null) return imports;
- for (ImportReference imp : cud.imports) {
- if (imp == null) continue;
- String qualifiedName = Eclipse.toQualifiedName(imp.getImportName());
- if ((imp.bits & ASTNode.OnDemand) != 0) qualifiedName += ".*";
- imports.add(qualifiedName);
- }
- return imports;
- }
-
/**
* Runs through the entire AST, starting at the compilation unit, calling the provided visitor's visit methods
* for each node, depth first.
@@ -88,8 +77,10 @@ public class EclipseAST extends AST<EclipseAST, EclipseNode, ASTNode> {
}
void traverseChildren(EclipseASTVisitor visitor, EclipseNode node) {
- for (EclipseNode child : node.down()) {
- child.traverse(visitor);
+ ImmutableList<EclipseNode> children = node.down();
+ int len = children.size();
+ for (int i = 0; i < len; i++) {
+ children.get(i).traverse(visitor);
}
}
diff --git a/src/core/lombok/eclipse/EclipseImportList.java b/src/core/lombok/eclipse/EclipseImportList.java
new file mode 100644
index 00000000..264ed91f
--- /dev/null
+++ b/src/core/lombok/eclipse/EclipseImportList.java
@@ -0,0 +1,131 @@
+/*
+ * Copyright (C) 2013 The Project Lombok Authors.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+package lombok.eclipse;
+
+import static lombok.eclipse.Eclipse.*;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+
+import org.eclipse.jdt.internal.compiler.ast.ASTNode;
+import org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration;
+import org.eclipse.jdt.internal.compiler.ast.ImportReference;
+
+import lombok.core.ImportList;
+
+public class EclipseImportList implements ImportList {
+ private ImportReference[] imports;
+ private ImportReference pkg;
+
+ public EclipseImportList(CompilationUnitDeclaration cud) {
+ this.pkg = cud.currentPackage;
+ this.imports = cud.imports;
+ }
+
+ @Override public String getFullyQualifiedNameForSimpleName(String unqualified) {
+ if (imports != null) {
+ outer:
+ for (ImportReference imp : imports) {
+ if ((imp.bits & ASTNode.OnDemand) != 0) continue;
+ char[][] tokens = imp.tokens;
+ char[] token = tokens.length == 0 ? new char[0] : tokens[tokens.length - 1];
+ int len = token.length;
+ if (len != unqualified.length()) continue;
+ for (int i = 0; i < len; i++) if (token[i] != unqualified.charAt(i)) continue outer;
+ return toQualifiedName(tokens);
+ }
+ }
+ return null;
+ }
+
+ @Override public boolean hasStarImport(String packageName) {
+ if (isEqual(packageName, pkg)) return true;
+ if ("java.lang".equals(packageName)) return true;
+ if (imports != null) for (ImportReference imp : imports) {
+ if ((imp.bits & ASTNode.OnDemand) == 0) continue;
+ if (imp.isStatic()) continue;
+ if (isEqual(packageName, imp)) return true;
+ }
+ return false;
+ }
+
+ private static boolean isEqual(String packageName, ImportReference pkgOrStarImport) {
+ if (pkgOrStarImport == null || pkgOrStarImport.tokens == null || pkgOrStarImport.tokens.length == 0) return packageName.isEmpty();
+ int pos = 0;
+ int len = packageName.length();
+ for (int i = 0; i < pkgOrStarImport.tokens.length; i++) {
+ if (i != 0) {
+ if (pos >= len) return false;
+ if (packageName.charAt(pos++) != '.') return false;
+ }
+ for (int j = 0; j < pkgOrStarImport.tokens[i].length; j++) {
+ if (pos >= len) return false;
+ if (packageName.charAt(pos++) != pkgOrStarImport.tokens[i][j]) return false;
+ }
+ }
+ return true;
+ }
+
+ @Override public Collection<String> applyNameToStarImports(String startsWith, String name) {
+ List<String> out = Collections.emptyList();
+
+ if (pkg != null && pkg.tokens != null && pkg.tokens.length != 0) {
+ char[] first = pkg.tokens[0];
+ int len = first.length;
+ boolean match = true;
+ if (startsWith.length() == len) {
+ for (int i = 0; match && i < len; i++) {
+ if (startsWith.charAt(i) != first[i]) match = false;
+ }
+ if (match) out.add(toQualifiedName(pkg.tokens) + "." + name);
+ }
+ }
+
+ if (imports != null) {
+ outer:
+ for (ImportReference imp : imports) {
+ if ((imp.bits & ASTNode.OnDemand) == 0) continue;
+ if (imp.isStatic()) continue;
+ if (imp.tokens == null || imp.tokens.length == 0) continue;
+ char[] firstToken = imp.tokens[0];
+ if (firstToken.length != startsWith.length()) continue;
+ for (int i = 0; i < firstToken.length; i++) if (startsWith.charAt(i) != firstToken[i]) continue outer;
+ String fqn = toQualifiedName(imp.tokens) + "." + name;
+ if (out.isEmpty()) out = Collections.singletonList(fqn);
+ else if (out.size() == 1) {
+ out = new ArrayList<String>(out);
+ out.add(fqn);
+ } else {
+ out.add(fqn);
+ }
+ }
+ }
+ return out;
+ }
+
+ @Override public String applyUnqualifiedNameToPackage(String unqualified) {
+ if (pkg == null || pkg.tokens == null || pkg.tokens.length == 0) return unqualified;
+ return toQualifiedName(pkg.tokens) + "." + unqualified;
+ }
+}
diff --git a/src/core/lombok/eclipse/HandlerLibrary.java b/src/core/lombok/eclipse/HandlerLibrary.java
index 56744793..242e923c 100644
--- a/src/core/lombok/eclipse/HandlerLibrary.java
+++ b/src/core/lombok/eclipse/HandlerLibrary.java
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2009-2012 The Project Lombok Authors.
+ * Copyright (C) 2009-2013 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -218,30 +218,27 @@ public class HandlerLibrary {
* @param annotation 'node.get()' - convenience parameter.
*/
public void handleAnnotation(CompilationUnitDeclaration ast, EclipseNode annotationNode, org.eclipse.jdt.internal.compiler.ast.Annotation annotation, long priority) {
- String pkgName = annotationNode.getPackageDeclaration();
- Collection<String> imports = annotationNode.getImportStatements();
-
- TypeResolver resolver = new TypeResolver(pkgName, imports);
+ TypeResolver resolver = new TypeResolver(annotationNode.getImportList());
TypeReference rawType = annotation.type;
if (rawType == null) return;
- for (String fqn : resolver.findTypeMatches(annotationNode, typeLibrary, toQualifiedName(annotation.type.getTypeName()))) {
- AnnotationHandlerContainer<?> container = annotationHandlers.get(fqn);
- if (container == null) continue;
- if (priority != container.getPriority()) continue;
-
- if (!annotationNode.isCompleteParse() && container.deferUntilPostDiet()) {
- if (needsHandling(annotation)) container.preHandle(annotation, annotationNode);
- continue;
- }
-
- try {
- if (checkAndSetHandled(annotation)) container.handle(annotation, annotationNode);
- } catch (AnnotationValueDecodeFail fail) {
- fail.owner.setError(fail.getMessage(), fail.idx);
- } catch (Throwable t) {
- error(ast, String.format("Lombok annotation handler %s failed", container.handler.getClass()), t);
- }
+ String fqn = resolver.typeRefToFullyQualifiedName(annotationNode, typeLibrary, toQualifiedName(annotation.type.getTypeName()));
+ if (fqn == null) return;
+ AnnotationHandlerContainer<?> container = annotationHandlers.get(fqn);
+ if (container == null) return;
+ if (priority != container.getPriority()) return;
+
+ if (!annotationNode.isCompleteParse() && container.deferUntilPostDiet()) {
+ if (needsHandling(annotation)) container.preHandle(annotation, annotationNode);
+ return;
+ }
+
+ try {
+ if (checkAndSetHandled(annotation)) container.handle(annotation, annotationNode);
+ } catch (AnnotationValueDecodeFail fail) {
+ fail.owner.setError(fail.getMessage(), fail.idx);
+ } catch (Throwable t) {
+ error(ast, String.format("Lombok annotation handler %s failed", container.handler.getClass()), t);
}
}
diff --git a/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java b/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java
index 78780522..d47b6715 100644
--- a/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java
+++ b/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java
@@ -290,7 +290,7 @@ public class EclipseHandlerUtil {
if (!lastPartA.equals(lastPartB)) return false;
String typeName = toQualifiedName(typeRef.getTypeName());
- TypeResolver resolver = new TypeResolver(node.getPackageDeclaration(), node.getImportStatements());
+ TypeResolver resolver = new TypeResolver(node.getImportList());
return resolver.typeMatches(node, type.getName(), typeName);
}