aboutsummaryrefslogtreecommitdiff
path: root/src/lombok/eclipse/handlers
diff options
context:
space:
mode:
authorReinier Zwitserloot <reinier@tipit.to>2009-11-25 07:32:49 +0100
committerReinier Zwitserloot <reinier@tipit.to>2009-11-25 07:32:49 +0100
commit1a0e611a9c5e1ee518670647ce1a44beae559b44 (patch)
treee5ef8f671bc6688f486e874d4e2e1a7813e4f0b2 /src/lombok/eclipse/handlers
parent7fd947ea40c25dad9ee543ebc4b92de9a2e05efc (diff)
downloadlombok-1a0e611a9c5e1ee518670647ce1a44beae559b44.tar.gz
lombok-1a0e611a9c5e1ee518670647ce1a44beae559b44.tar.bz2
lombok-1a0e611a9c5e1ee518670647ce1a44beae559b44.zip
Refactored the source folders.
Diffstat (limited to 'src/lombok/eclipse/handlers')
-rw-r--r--src/lombok/eclipse/handlers/EclipseHandlerUtil.java385
-rw-r--r--src/lombok/eclipse/handlers/HandleCleanup.java200
-rw-r--r--src/lombok/eclipse/handlers/HandleData.java243
-rw-r--r--src/lombok/eclipse/handlers/HandleEqualsAndHashCode.java718
-rw-r--r--src/lombok/eclipse/handlers/HandleGetter.java154
-rw-r--r--src/lombok/eclipse/handlers/HandlePrintAST.java57
-rw-r--r--src/lombok/eclipse/handlers/HandleSetter.java172
-rw-r--r--src/lombok/eclipse/handlers/HandleSneakyThrows.java224
-rw-r--r--src/lombok/eclipse/handlers/HandleSynchronized.java132
-rw-r--r--src/lombok/eclipse/handlers/HandleToString.java304
-rw-r--r--src/lombok/eclipse/handlers/package-info.java26
11 files changed, 0 insertions, 2615 deletions
diff --git a/src/lombok/eclipse/handlers/EclipseHandlerUtil.java b/src/lombok/eclipse/handlers/EclipseHandlerUtil.java
deleted file mode 100644
index 2f676d09..00000000
--- a/src/lombok/eclipse/handlers/EclipseHandlerUtil.java
+++ /dev/null
@@ -1,385 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.Eclipse.fromQualifiedName;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.regex.Pattern;
-
-import lombok.AccessLevel;
-import lombok.core.TransformationsUtil;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.AbstractVariableDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.AllocationExpression;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.ConstructorDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.EqualExpression;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.IfStatement;
-import org.eclipse.jdt.internal.compiler.ast.MarkerAnnotation;
-import org.eclipse.jdt.internal.compiler.ast.NullLiteral;
-import org.eclipse.jdt.internal.compiler.ast.OperatorIds;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.StringLiteral;
-import org.eclipse.jdt.internal.compiler.ast.ThrowStatement;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-
-/**
- * Container for static utility methods useful to handlers written for eclipse.
- */
-public class EclipseHandlerUtil {
- private EclipseHandlerUtil() {
- //Prevent instantiation
- }
-
- /**
- * Checks if the given type reference represents a primitive type.
- */
- public static boolean isPrimitive(TypeReference ref) {
- if (ref.dimensions() > 0) return false;
- return TransformationsUtil.PRIMITIVE_TYPE_NAME_PATTERN.matcher(Eclipse.toQualifiedName(ref.getTypeName())).matches();
- }
-
- /**
- * Turns an {@code AccessLevel} instance into the flag bit used by eclipse.
- */
- public static int toEclipseModifier(AccessLevel value) {
- switch (value) {
- case MODULE:
- case PACKAGE:
- return 0;
- default:
- case PUBLIC:
- return ClassFileConstants.AccPublic;
- case PROTECTED:
- return ClassFileConstants.AccProtected;
- case PRIVATE:
- return ClassFileConstants.AccPrivate;
- }
- }
-
- /**
- * Checks if an eclipse-style array-of-array-of-characters to represent a fully qualified name ('foo.bar.baz'), matches a plain
- * string containing the same fully qualified name with dots in the string.
- */
- public static boolean nameEquals(char[][] typeName, String string) {
- StringBuilder sb = new StringBuilder();
- boolean first = true;
- for (char[] elem : typeName) {
- if (first) first = false;
- else sb.append('.');
- sb.append(elem);
- }
-
- return string.contentEquals(sb);
- }
-
- /** Serves as return value for the methods that check for the existence of fields and methods. */
- public enum MemberExistsResult {
- NOT_EXISTS, EXISTS_BY_USER, EXISTS_BY_LOMBOK;
- }
-
- /**
- * Checks if there is a field with the provided name.
- *
- * @param fieldName the field name to check for.
- * @param node Any node that represents the Type (TypeDeclaration) to look in, or any child node thereof.
- */
- public static MemberExistsResult fieldExists(String fieldName, EclipseNode node) {
- while (node != null && !(node.get() instanceof TypeDeclaration)) {
- node = node.up();
- }
-
- if (node != null && node.get() instanceof TypeDeclaration) {
- TypeDeclaration typeDecl = (TypeDeclaration)node.get();
- if (typeDecl.fields != null) for (FieldDeclaration def : typeDecl.fields) {
- char[] fName = def.name;
- if (fName == null) continue;
- if (fieldName.equals(new String(fName))) {
- EclipseNode existing = node.getNodeFor(def);
- if (existing == null || !existing.isHandled()) return MemberExistsResult.EXISTS_BY_USER;
- return MemberExistsResult.EXISTS_BY_LOMBOK;
- }
- }
- }
-
- return MemberExistsResult.NOT_EXISTS;
- }
-
- /**
- * Checks if there is a method with the provided name. In case of multiple methods (overloading), only
- * the first method decides if EXISTS_BY_USER or EXISTS_BY_LOMBOK is returned.
- *
- * @param methodName the method name to check for.
- * @param node Any node that represents the Type (TypeDeclaration) to look in, or any child node thereof.
- */
- public static MemberExistsResult methodExists(String methodName, EclipseNode node) {
- while (node != null && !(node.get() instanceof TypeDeclaration)) {
- node = node.up();
- }
-
- if (node != null && node.get() instanceof TypeDeclaration) {
- TypeDeclaration typeDecl = (TypeDeclaration)node.get();
- if (typeDecl.methods != null) for (AbstractMethodDeclaration def : typeDecl.methods) {
- char[] mName = def.selector;
- if (mName == null) continue;
- if (methodName.equals(new String(mName))) {
- EclipseNode existing = node.getNodeFor(def);
- if (existing == null || !existing.isHandled()) return MemberExistsResult.EXISTS_BY_USER;
- return MemberExistsResult.EXISTS_BY_LOMBOK;
- }
- }
- }
-
- return MemberExistsResult.NOT_EXISTS;
- }
-
- /**
- * Checks if there is a (non-default) constructor. In case of multiple constructors (overloading), only
- * the first constructor decides if EXISTS_BY_USER or EXISTS_BY_LOMBOK is returned.
- *
- * @param node Any node that represents the Type (TypeDeclaration) to look in, or any child node thereof.
- */
- public static MemberExistsResult constructorExists(EclipseNode node) {
- while (node != null && !(node.get() instanceof TypeDeclaration)) {
- node = node.up();
- }
-
- if (node != null && node.get() instanceof TypeDeclaration) {
- TypeDeclaration typeDecl = (TypeDeclaration)node.get();
- if (typeDecl.methods != null) for (AbstractMethodDeclaration def : typeDecl.methods) {
- if (def instanceof ConstructorDeclaration) {
- if ((def.bits & ASTNode.IsDefaultConstructor) != 0) continue;
- EclipseNode existing = node.getNodeFor(def);
- if (existing == null || !existing.isHandled()) return MemberExistsResult.EXISTS_BY_USER;
- return MemberExistsResult.EXISTS_BY_LOMBOK;
- }
- }
- }
-
- return MemberExistsResult.NOT_EXISTS;
- }
-
- /**
- * Returns the constructor that's already been generated by lombok.
- * Provide any node that represents the type (TypeDeclaration) to look in, or any child node thereof.
- */
- public static EclipseNode getExistingLombokConstructor(EclipseNode node) {
- while (node != null && !(node.get() instanceof TypeDeclaration)) {
- node = node.up();
- }
-
- if (node == null) return null;
-
- if (node.get() instanceof TypeDeclaration) {
- for (AbstractMethodDeclaration def : ((TypeDeclaration)node.get()).methods) {
- if (def instanceof ConstructorDeclaration) {
- if ((def.bits & ASTNode.IsDefaultConstructor) != 0) continue;
- EclipseNode existing = node.getNodeFor(def);
- if (existing.isHandled()) return existing;
- }
- }
- }
-
- return null;
- }
-
- /**
- * Returns the method that's already been generated by lombok with the given name.
- * Provide any node that represents the type (TypeDeclaration) to look in, or any child node thereof.
- */
- public static EclipseNode getExistingLombokMethod(String methodName, EclipseNode node) {
- while (node != null && !(node.get() instanceof TypeDeclaration)) {
- node = node.up();
- }
-
- if (node == null) return null;
-
- if (node.get() instanceof TypeDeclaration) {
- for (AbstractMethodDeclaration def : ((TypeDeclaration)node.get()).methods) {
- char[] mName = def.selector;
- if (mName == null) continue;
- if (methodName.equals(new String(mName))) {
- EclipseNode existing = node.getNodeFor(def);
- if (existing.isHandled()) return existing;
- }
- }
- }
-
- return null;
- }
-
- /**
- * Inserts a field into an existing type. The type must represent a {@code TypeDeclaration}.
- */
- public static void injectField(EclipseNode type, FieldDeclaration field) {
- TypeDeclaration parent = (TypeDeclaration) type.get();
-
- if (parent.fields == null) {
- parent.fields = new FieldDeclaration[1];
- parent.fields[0] = field;
- } else {
- FieldDeclaration[] newArray = new FieldDeclaration[parent.fields.length + 1];
- System.arraycopy(parent.fields, 0, newArray, 0, parent.fields.length);
- newArray[parent.fields.length] = field;
- parent.fields = newArray;
- }
-
- type.add(field, Kind.FIELD).recursiveSetHandled();
- }
-
- /**
- * Inserts a method into an existing type. The type must represent a {@code TypeDeclaration}.
- */
- public static void injectMethod(EclipseNode type, AbstractMethodDeclaration method) {
- TypeDeclaration parent = (TypeDeclaration) type.get();
-
- if (parent.methods == null) {
- parent.methods = new AbstractMethodDeclaration[1];
- parent.methods[0] = method;
- } else {
- boolean injectionComplete = false;
- if (method instanceof ConstructorDeclaration) {
- for (int i = 0 ; i < parent.methods.length ; i++) {
- if (parent.methods[i] instanceof ConstructorDeclaration &&
- (parent.methods[i].bits & ASTNode.IsDefaultConstructor) != 0) {
- EclipseNode tossMe = type.getNodeFor(parent.methods[i]);
- parent.methods[i] = method;
- if (tossMe != null) tossMe.up().removeChild(tossMe);
- injectionComplete = true;
- break;
- }
- }
- }
- if (!injectionComplete) {
- AbstractMethodDeclaration[] newArray = new AbstractMethodDeclaration[parent.methods.length + 1];
- System.arraycopy(parent.methods, 0, newArray, 0, parent.methods.length);
- newArray[parent.methods.length] = method;
- parent.methods = newArray;
- }
- }
-
- type.add(method, Kind.METHOD).recursiveSetHandled();
- }
-
- /**
- * Searches the given field node for annotations and returns each one that matches the provided regular expression pattern.
- *
- * Only the simple name is checked - the package and any containing class are ignored.
- */
- public static Annotation[] findAnnotations(FieldDeclaration field, Pattern namePattern) {
- List<Annotation> result = new ArrayList<Annotation>();
- if (field.annotations == null) return new Annotation[0];
- for (Annotation annotation : field.annotations) {
- TypeReference typeRef = annotation.type;
- if (typeRef != null && typeRef.getTypeName()!= null) {
- char[][] typeName = typeRef.getTypeName();
- String suspect = new String(typeName[typeName.length - 1]);
- if (namePattern.matcher(suspect).matches()) {
- result.add(annotation);
- }
- }
- }
- return result.toArray(new Annotation[0]);
- }
-
- /**
- * Generates a new statement that checks if the given variable is null, and if so, throws a {@code NullPointerException} with the
- * variable name as message.
- */
- public static Statement generateNullCheck(AbstractVariableDeclaration variable, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
-
- if (isPrimitive(variable.type)) return null;
- AllocationExpression exception = new AllocationExpression();
- Eclipse.setGeneratedBy(exception, source);
- exception.type = new QualifiedTypeReference(fromQualifiedName("java.lang.NullPointerException"), new long[]{p, p, p});
- Eclipse.setGeneratedBy(exception.type, source);
- exception.arguments = new Expression[] { new StringLiteral(variable.name, pS, pE, 0)};
- Eclipse.setGeneratedBy(exception.arguments[0], source);
- ThrowStatement throwStatement = new ThrowStatement(exception, pS, pE);
- Eclipse.setGeneratedBy(throwStatement, source);
-
- SingleNameReference varName = new SingleNameReference(variable.name, p);
- Eclipse.setGeneratedBy(varName, source);
- NullLiteral nullLiteral = new NullLiteral(pS, pE);
- Eclipse.setGeneratedBy(nullLiteral, source);
- EqualExpression equalExpression = new EqualExpression(varName, nullLiteral, OperatorIds.EQUAL_EQUAL);
- equalExpression.sourceStart = pS; equalExpression.sourceEnd = pE;
- Eclipse.setGeneratedBy(equalExpression, source);
- IfStatement ifStatement = new IfStatement(equalExpression, throwStatement, 0, 0);
- Eclipse.setGeneratedBy(ifStatement, source);
- return ifStatement;
- }
-
- /**
- * Create an annotation of the given name, and is marked as being generated by the given source.
- */
- public static MarkerAnnotation makeMarkerAnnotation(char[][] name, ASTNode source) {
- long pos = (long)source.sourceStart << 32 | source.sourceEnd;
- TypeReference typeRef = new QualifiedTypeReference(name, new long[] {pos, pos, pos});
- Eclipse.setGeneratedBy(typeRef, source);
- MarkerAnnotation ann = new MarkerAnnotation(typeRef, (int)(pos >> 32));
- ann.declarationSourceEnd = ann.sourceEnd = ann.statementEnd = (int)pos;
- Eclipse.setGeneratedBy(ann, source);
- return ann;
- }
-
- /**
- * Given a list of field names and a node referring to a type, finds each name in the list that does not match a field within the type.
- */
- public static List<Integer> createListOfNonExistentFields(List<String> list, EclipseNode type, boolean excludeStandard, boolean excludeTransient) {
- boolean[] matched = new boolean[list.size()];
-
- for (EclipseNode child : type.down()) {
- if (list.isEmpty()) break;
- if (child.getKind() != Kind.FIELD) continue;
- if (excludeStandard) {
- if ((((FieldDeclaration)child.get()).modifiers & ClassFileConstants.AccStatic) != 0) continue;
- if (child.getName().startsWith("$")) continue;
- }
- if (excludeTransient && (((FieldDeclaration)child.get()).modifiers & ClassFileConstants.AccTransient) != 0) continue;
- int idx = list.indexOf(child.getName());
- if (idx > -1) matched[idx] = true;
- }
-
- List<Integer> problematic = new ArrayList<Integer>();
- for (int i = 0 ; i < list.size() ; i++) {
- if (!matched[i]) problematic.add(i);
- }
-
- return problematic;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleCleanup.java b/src/lombok/eclipse/handlers/HandleCleanup.java
deleted file mode 100644
index d296e96b..00000000
--- a/src/lombok/eclipse/handlers/HandleCleanup.java
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import java.util.Arrays;
-
-import lombok.Cleanup;
-import lombok.core.AnnotationValues;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Assignment;
-import org.eclipse.jdt.internal.compiler.ast.Block;
-import org.eclipse.jdt.internal.compiler.ast.CaseStatement;
-import org.eclipse.jdt.internal.compiler.ast.CastExpression;
-import org.eclipse.jdt.internal.compiler.ast.LocalDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.MemberValuePair;
-import org.eclipse.jdt.internal.compiler.ast.MessageSend;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.SwitchStatement;
-import org.eclipse.jdt.internal.compiler.ast.TryStatement;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.Cleanup} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleCleanup implements EclipseAnnotationHandler<Cleanup> {
- public boolean handle(AnnotationValues<Cleanup> annotation, Annotation ast, EclipseNode annotationNode) {
- String cleanupName = annotation.getInstance().value();
- if (cleanupName.length() == 0) {
- annotationNode.addError("cleanupName cannot be the empty string.");
- return true;
- }
-
- if (annotationNode.up().getKind() != Kind.LOCAL) {
- annotationNode.addError("@Cleanup is legal only on local variable declarations.");
- return true;
- }
-
- LocalDeclaration decl = (LocalDeclaration)annotationNode.up().get();
-
- if (decl.initialization == null) {
- annotationNode.addError("@Cleanup variable declarations need to be initialized.");
- return true;
- }
-
- EclipseNode ancestor = annotationNode.up().directUp();
- ASTNode blockNode = ancestor.get();
-
- final boolean isSwitch;
- final Statement[] statements;
- if (blockNode instanceof AbstractMethodDeclaration) {
- isSwitch = false;
- statements = ((AbstractMethodDeclaration)blockNode).statements;
- } else if (blockNode instanceof Block) {
- isSwitch = false;
- statements = ((Block)blockNode).statements;
- } else if (blockNode instanceof SwitchStatement) {
- isSwitch = true;
- statements = ((SwitchStatement)blockNode).statements;
- } else {
- annotationNode.addError("@Cleanup is legal only on a local variable declaration inside a block.");
- return true;
- }
-
- if (statements == null) {
- annotationNode.addError("LOMBOK BUG: Parent block does not contain any statements.");
- return true;
- }
-
- int start = 0;
- for (; start < statements.length ; start++) {
- if (statements[start] == decl) break;
- }
-
- if (start == statements.length) {
- annotationNode.addError("LOMBOK BUG: Can't find this local variable declaration inside its parent.");
- return true;
- }
-
- start++; //We start with try{} *AFTER* the var declaration.
-
- int end;
- if (isSwitch) {
- end = start + 1;
- for (; end < statements.length ; end++) {
- if (statements[end] instanceof CaseStatement) {
- break;
- }
- }
- } else end = statements.length;
-
- //At this point:
- // start-1 = Local Declaration marked with @Cleanup
- // start = first instruction that needs to be wrapped into a try block
- // end = last intruction of the scope -OR- last instruction before the next case label in switch statements.
- // hence:
- // [start, end) = statements for the try block.
-
- Statement[] tryBlock = new Statement[end - start];
- System.arraycopy(statements, start, tryBlock, 0, end-start);
- //Remove the stuff we just dumped into the tryBlock, and then leave room for the try node.
- int newStatementsLength = statements.length - (end-start); //Remove room for every statement moved into try block...
- newStatementsLength += 1; //But add room for the TryStatement node itself.
- Statement[] newStatements = new Statement[newStatementsLength];
- System.arraycopy(statements, 0, newStatements, 0, start); //copy all statements before the try block verbatim.
- System.arraycopy(statements, end, newStatements, start+1, statements.length - end); //For switch statements.
-
- doAssignmentCheck(annotationNode, tryBlock, decl.name);
-
- TryStatement tryStatement = new TryStatement();
- Eclipse.setGeneratedBy(tryStatement, ast);
- tryStatement.tryBlock = new Block(0);
- tryStatement.tryBlock.statements = tryBlock;
- newStatements[start] = tryStatement;
-
- Statement[] finallyBlock = new Statement[1];
- MessageSend unsafeClose = new MessageSend();
- Eclipse.setGeneratedBy(unsafeClose, ast);
- unsafeClose.sourceStart = ast.sourceStart;
- unsafeClose.sourceEnd = ast.sourceEnd;
- SingleNameReference receiver = new SingleNameReference(decl.name, 0);
- Eclipse.setGeneratedBy(receiver, ast);
- unsafeClose.receiver = receiver;
- long nameSourcePosition = (long)ast.sourceStart << 32 | ast.sourceEnd;
- if (ast.memberValuePairs() != null) for (MemberValuePair pair : ast.memberValuePairs()) {
- if (pair.name != null && new String(pair.name).equals("value")) {
- nameSourcePosition = (long)pair.value.sourceStart << 32 | pair.value.sourceEnd;
- break;
- }
- }
- unsafeClose.nameSourcePosition = nameSourcePosition;
- unsafeClose.selector = cleanupName.toCharArray();
- finallyBlock[0] = unsafeClose;
- tryStatement.finallyBlock = new Block(0);
- Eclipse.setGeneratedBy(tryStatement.finallyBlock, ast);
- tryStatement.finallyBlock.statements = finallyBlock;
-
- tryStatement.catchArguments = null;
- tryStatement.catchBlocks = null;
-
- if (blockNode instanceof AbstractMethodDeclaration) {
- ((AbstractMethodDeclaration)blockNode).statements = newStatements;
- } else if (blockNode instanceof Block) {
- ((Block)blockNode).statements = newStatements;
- } else if (blockNode instanceof SwitchStatement) {
- ((SwitchStatement)blockNode).statements = newStatements;
- }
-
- ancestor.rebuild();
-
- return true;
- }
-
- private void doAssignmentCheck(EclipseNode node, Statement[] tryBlock, char[] varName) {
- for (Statement statement : tryBlock) doAssignmentCheck0(node, statement, varName);
- }
-
- private void doAssignmentCheck0(EclipseNode node, Statement statement, char[] varName) {
- if (statement instanceof Assignment)
- doAssignmentCheck0(node, ((Assignment)statement).expression, varName);
- else if (statement instanceof LocalDeclaration)
- doAssignmentCheck0(node, ((LocalDeclaration)statement).initialization, varName);
- else if (statement instanceof CastExpression)
- doAssignmentCheck0(node, ((CastExpression)statement).expression, varName);
- else if (statement instanceof SingleNameReference) {
- if (Arrays.equals(((SingleNameReference)statement).token, varName)) {
- EclipseNode problemNode = node.getNodeFor(statement);
- if (problemNode != null) problemNode.addWarning(
- "You're assigning an auto-cleanup variable to something else. This is a bad idea.");
- }
- }
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleData.java b/src/lombok/eclipse/handlers/HandleData.java
deleted file mode 100644
index 8c4e07ce..00000000
--- a/src/lombok/eclipse/handlers/HandleData.java
+++ /dev/null
@@ -1,243 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.Eclipse.*;
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-
-import java.lang.reflect.Modifier;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
-import lombok.AccessLevel;
-import lombok.Data;
-import lombok.core.AnnotationValues;
-import lombok.core.TransformationsUtil;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-import lombok.eclipse.handlers.EclipseHandlerUtil.MemberExistsResult;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.AllocationExpression;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Argument;
-import org.eclipse.jdt.internal.compiler.ast.Assignment;
-import org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.ConstructorDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.ExplicitConstructorCall;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.FieldReference;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.ParameterizedSingleTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.ReturnStatement;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.ThisReference;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.TypeParameter;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.Data} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleData implements EclipseAnnotationHandler<Data> {
- public boolean handle(AnnotationValues<Data> annotation, Annotation ast, EclipseNode annotationNode) {
- Data ann = annotation.getInstance();
- EclipseNode typeNode = annotationNode.up();
-
- TypeDeclaration typeDecl = null;
- if (typeNode.get() instanceof TypeDeclaration) typeDecl = (TypeDeclaration) typeNode.get();
- int modifiers = typeDecl == null ? 0 : typeDecl.modifiers;
- boolean notAClass = (modifiers &
- (ClassFileConstants.AccInterface | ClassFileConstants.AccAnnotation | ClassFileConstants.AccEnum)) != 0;
-
- if (typeDecl == null || notAClass) {
- annotationNode.addError("@Data is only supported on a class.");
- return false;
- }
-
- List<EclipseNode> nodesForConstructor = new ArrayList<EclipseNode>();
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() != Kind.FIELD) continue;
- FieldDeclaration fieldDecl = (FieldDeclaration) child.get();
- //Skip fields that start with $
- if (fieldDecl.name.length > 0 && fieldDecl.name[0] == '$') continue;
- //Skip static fields.
- if ((fieldDecl.modifiers & ClassFileConstants.AccStatic) != 0) continue;
- boolean isFinal = (fieldDecl.modifiers & ClassFileConstants.AccFinal) != 0;
- boolean isNonNull = findAnnotations(fieldDecl, TransformationsUtil.NON_NULL_PATTERN).length != 0;
- if ((isFinal || isNonNull) && fieldDecl.initialization == null) nodesForConstructor.add(child);
- new HandleGetter().generateGetterForField(child, annotationNode.get());
- if (!isFinal) new HandleSetter().generateSetterForField(child, annotationNode.get());
- }
-
- new HandleToString().generateToStringForType(typeNode, annotationNode);
- new HandleEqualsAndHashCode().generateEqualsAndHashCodeForType(typeNode, annotationNode);
-
- //Careful: Generate the public static constructor (if there is one) LAST, so that any attempt to
- //'find callers' on the annotation node will find callers of the constructor, which is by far the
- //most useful of the many methods built by @Data. This trick won't work for the non-static constructor,
- //for whatever reason, though you can find callers of that one by focusing on the class name itself
- //and hitting 'find callers'.
-
- if (constructorExists(typeNode) == MemberExistsResult.NOT_EXISTS) {
- ConstructorDeclaration constructor = createConstructor(
- ann.staticConstructor().length() == 0, typeNode, nodesForConstructor, ast);
- injectMethod(typeNode, constructor);
- }
-
- if (ann.staticConstructor().length() > 0) {
- if (methodExists("of", typeNode) == MemberExistsResult.NOT_EXISTS) {
- MethodDeclaration staticConstructor = createStaticConstructor(
- ann.staticConstructor(), typeNode, nodesForConstructor, ast);
- injectMethod(typeNode, staticConstructor);
- }
- }
-
- return false;
- }
-
- private ConstructorDeclaration createConstructor(boolean isPublic,
- EclipseNode type, Collection<EclipseNode> fields, ASTNode source) {
- long p = (long)source.sourceStart << 32 | source.sourceEnd;
-
- ConstructorDeclaration constructor = new ConstructorDeclaration(
- ((CompilationUnitDeclaration) type.top().get()).compilationResult);
- Eclipse.setGeneratedBy(constructor, source);
-
- constructor.modifiers = EclipseHandlerUtil.toEclipseModifier(isPublic ? AccessLevel.PUBLIC : AccessLevel.PRIVATE);
- constructor.annotations = null;
- constructor.selector = ((TypeDeclaration)type.get()).name;
- constructor.constructorCall = new ExplicitConstructorCall(ExplicitConstructorCall.ImplicitSuper);
- Eclipse.setGeneratedBy(constructor.constructorCall, source);
- constructor.thrownExceptions = null;
- constructor.typeParameters = null;
- constructor.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG;
- constructor.bodyStart = constructor.declarationSourceStart = constructor.sourceStart = source.sourceStart;
- constructor.bodyEnd = constructor.declarationSourceEnd = constructor.sourceEnd = source.sourceEnd;
- constructor.arguments = null;
-
- List<Argument> args = new ArrayList<Argument>();
- List<Statement> assigns = new ArrayList<Statement>();
- List<Statement> nullChecks = new ArrayList<Statement>();
-
- for (EclipseNode fieldNode : fields) {
- FieldDeclaration field = (FieldDeclaration) fieldNode.get();
- FieldReference thisX = new FieldReference(("this." + new String(field.name)).toCharArray(), p);
- Eclipse.setGeneratedBy(thisX, source);
- thisX.receiver = new ThisReference((int)(p >> 32), (int)p);
- Eclipse.setGeneratedBy(thisX.receiver, source);
- thisX.token = field.name;
-
- SingleNameReference assignmentNameRef = new SingleNameReference(field.name, p);
- Eclipse.setGeneratedBy(assignmentNameRef, source);
- Assignment assignment = new Assignment(thisX, assignmentNameRef, (int)p);
- Eclipse.setGeneratedBy(assignment, source);
- assigns.add(assignment);
- long fieldPos = (((long)field.sourceStart) << 32) | field.sourceEnd;
- Argument argument = new Argument(field.name, fieldPos, copyType(field.type, source), Modifier.FINAL);
- Eclipse.setGeneratedBy(argument, source);
- Annotation[] nonNulls = findAnnotations(field, TransformationsUtil.NON_NULL_PATTERN);
- Annotation[] nullables = findAnnotations(field, TransformationsUtil.NULLABLE_PATTERN);
- if (nonNulls.length != 0) {
- Statement nullCheck = generateNullCheck(field, source);
- if (nullCheck != null) nullChecks.add(nullCheck);
- }
- Annotation[] copiedAnnotations = copyAnnotations(nonNulls, nullables, source);
- if (copiedAnnotations.length != 0) argument.annotations = copiedAnnotations;
- args.add(argument);
- }
-
- nullChecks.addAll(assigns);
- constructor.statements = nullChecks.isEmpty() ? null : nullChecks.toArray(new Statement[nullChecks.size()]);
- constructor.arguments = args.isEmpty() ? null : args.toArray(new Argument[args.size()]);
- return constructor;
- }
-
- private MethodDeclaration createStaticConstructor(String name, EclipseNode type, Collection<EclipseNode> fields, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
-
- MethodDeclaration constructor = new MethodDeclaration(
- ((CompilationUnitDeclaration) type.top().get()).compilationResult);
- Eclipse.setGeneratedBy(constructor, source);
-
- constructor.modifiers = EclipseHandlerUtil.toEclipseModifier(AccessLevel.PUBLIC) | Modifier.STATIC;
- TypeDeclaration typeDecl = (TypeDeclaration) type.get();
- if (typeDecl.typeParameters != null && typeDecl.typeParameters.length > 0) {
- TypeReference[] refs = new TypeReference[typeDecl.typeParameters.length];
- int idx = 0;
- for (TypeParameter param : typeDecl.typeParameters) {
- TypeReference typeRef = new SingleTypeReference(param.name, (long)param.sourceStart << 32 | param.sourceEnd);
- Eclipse.setGeneratedBy(typeRef, source);
- refs[idx++] = typeRef;
- }
- constructor.returnType = new ParameterizedSingleTypeReference(typeDecl.name, refs, 0, p);
- } else constructor.returnType = new SingleTypeReference(((TypeDeclaration)type.get()).name, p);
- Eclipse.setGeneratedBy(constructor.returnType, source);
- constructor.annotations = null;
- constructor.selector = name.toCharArray();
- constructor.thrownExceptions = null;
- constructor.typeParameters = copyTypeParams(((TypeDeclaration)type.get()).typeParameters, source);
- constructor.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG;
- constructor.bodyStart = constructor.declarationSourceStart = constructor.sourceStart = source.sourceStart;
- constructor.bodyEnd = constructor.declarationSourceEnd = constructor.sourceEnd = source.sourceEnd;
-
- List<Argument> args = new ArrayList<Argument>();
- List<Expression> assigns = new ArrayList<Expression>();
- AllocationExpression statement = new AllocationExpression();
- statement.sourceStart = pS; statement.sourceEnd = pE;
- Eclipse.setGeneratedBy(statement, source);
- statement.type = copyType(constructor.returnType, source);
-
- for (EclipseNode fieldNode : fields) {
- FieldDeclaration field = (FieldDeclaration) fieldNode.get();
- long fieldPos = (((long)field.sourceStart) << 32) | field.sourceEnd;
- SingleNameReference nameRef = new SingleNameReference(field.name, fieldPos);
- Eclipse.setGeneratedBy(nameRef, source);
- assigns.add(nameRef);
-
- Argument argument = new Argument(field.name, fieldPos, copyType(field.type, source), 0);
- Eclipse.setGeneratedBy(argument, source);
-
- Annotation[] copiedAnnotations = copyAnnotations(
- findAnnotations(field, TransformationsUtil.NON_NULL_PATTERN),
- findAnnotations(field, TransformationsUtil.NULLABLE_PATTERN), source);
- if (copiedAnnotations.length != 0) argument.annotations = copiedAnnotations;
- args.add(new Argument(field.name, fieldPos, copyType(field.type, source), Modifier.FINAL));
- }
-
- statement.arguments = assigns.isEmpty() ? null : assigns.toArray(new Expression[assigns.size()]);
- constructor.arguments = args.isEmpty() ? null : args.toArray(new Argument[args.size()]);
- constructor.statements = new Statement[] { new ReturnStatement(statement, (int)(p >> 32), (int)p) };
- Eclipse.setGeneratedBy(constructor.statements[0], source);
- return constructor;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleEqualsAndHashCode.java b/src/lombok/eclipse/handlers/HandleEqualsAndHashCode.java
deleted file mode 100644
index 7c0980c8..00000000
--- a/src/lombok/eclipse/handlers/HandleEqualsAndHashCode.java
+++ /dev/null
@@ -1,718 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-
-import static lombok.eclipse.Eclipse.copyTypes;
-
-import java.lang.reflect.Modifier;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Argument;
-import org.eclipse.jdt.internal.compiler.ast.Assignment;
-import org.eclipse.jdt.internal.compiler.ast.BinaryExpression;
-import org.eclipse.jdt.internal.compiler.ast.CastExpression;
-import org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.ConditionalExpression;
-import org.eclipse.jdt.internal.compiler.ast.EqualExpression;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FalseLiteral;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.FieldReference;
-import org.eclipse.jdt.internal.compiler.ast.IfStatement;
-import org.eclipse.jdt.internal.compiler.ast.IntLiteral;
-import org.eclipse.jdt.internal.compiler.ast.LocalDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.MessageSend;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.NameReference;
-import org.eclipse.jdt.internal.compiler.ast.NullLiteral;
-import org.eclipse.jdt.internal.compiler.ast.OperatorIds;
-import org.eclipse.jdt.internal.compiler.ast.ParameterizedSingleTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.Reference;
-import org.eclipse.jdt.internal.compiler.ast.ReturnStatement;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.SuperReference;
-import org.eclipse.jdt.internal.compiler.ast.ThisReference;
-import org.eclipse.jdt.internal.compiler.ast.TrueLiteral;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.eclipse.jdt.internal.compiler.ast.UnaryExpression;
-import org.eclipse.jdt.internal.compiler.ast.Wildcard;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-import org.eclipse.jdt.internal.compiler.lookup.TypeConstants;
-import org.eclipse.jdt.internal.compiler.lookup.TypeIds;
-import org.mangosdk.spi.ProviderFor;
-
-import lombok.AccessLevel;
-import lombok.EqualsAndHashCode;
-import lombok.core.AnnotationValues;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-/**
- * Handles the {@code EqualsAndHashCode} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleEqualsAndHashCode implements EclipseAnnotationHandler<EqualsAndHashCode> {
- private static final Set<String> BUILT_IN_TYPES = Collections.unmodifiableSet(new HashSet<String>(Arrays.asList(
- "byte", "short", "int", "long", "char", "boolean", "double", "float")));
-
- private void checkForBogusFieldNames(EclipseNode type, AnnotationValues<EqualsAndHashCode> annotation) {
- if (annotation.isExplicit("exclude")) {
- for (int i : createListOfNonExistentFields(Arrays.asList(annotation.getInstance().exclude()), type, true, true)) {
- annotation.setWarning("exclude", "This field does not exist, or would have been excluded anyway.", i);
- }
- }
- if (annotation.isExplicit("of")) {
- for (int i : createListOfNonExistentFields(Arrays.asList(annotation.getInstance().of()), type, false, false)) {
- annotation.setWarning("of", "This field does not exist.", i);
- }
- }
- }
-
- public void generateEqualsAndHashCodeForType(EclipseNode typeNode, EclipseNode errorNode) {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() == Kind.ANNOTATION) {
- if (Eclipse.annotationTypeMatches(EqualsAndHashCode.class, child)) {
- //The annotation will make it happen, so we can skip it.
- return;
- }
- }
- }
-
- generateMethods(typeNode, errorNode, null, null, null, false);
- }
-
- @Override public boolean handle(AnnotationValues<EqualsAndHashCode> annotation,
- Annotation ast, EclipseNode annotationNode) {
- EqualsAndHashCode ann = annotation.getInstance();
- List<String> excludes = Arrays.asList(ann.exclude());
- List<String> includes = Arrays.asList(ann.of());
- EclipseNode typeNode = annotationNode.up();
-
- checkForBogusFieldNames(typeNode, annotation);
-
- Boolean callSuper = ann.callSuper();
- if (!annotation.isExplicit("callSuper")) callSuper = null;
- if (!annotation.isExplicit("exclude")) excludes = null;
- if (!annotation.isExplicit("of")) includes = null;
-
- if (excludes != null && includes != null) {
- excludes = null;
- annotation.setWarning("exclude", "exclude and of are mutually exclusive; the 'exclude' parameter will be ignored.");
- }
-
- return generateMethods(typeNode, annotationNode, excludes, includes, callSuper, true);
- }
-
- public boolean generateMethods(EclipseNode typeNode, EclipseNode errorNode, List<String> excludes, List<String> includes,
- Boolean callSuper, boolean whineIfExists) {
- assert excludes == null || includes == null;
-
- TypeDeclaration typeDecl = null;
-
- if (typeNode.get() instanceof TypeDeclaration) typeDecl = (TypeDeclaration) typeNode.get();
- int modifiers = typeDecl == null ? 0 : typeDecl.modifiers;
- boolean notAClass = (modifiers &
- (ClassFileConstants.AccInterface | ClassFileConstants.AccAnnotation | ClassFileConstants.AccEnum)) != 0;
-
- if (typeDecl == null || notAClass) {
- errorNode.addError("@EqualsAndHashCode is only supported on a class.");
- return false;
- }
-
- boolean implicitCallSuper = callSuper == null;
-
- if (callSuper == null) {
- try {
- callSuper = ((Boolean)EqualsAndHashCode.class.getMethod("callSuper").getDefaultValue()).booleanValue();
- } catch (Exception ignore) {
- throw new InternalError("Lombok bug - this cannot happen - can't find callSuper field in EqualsAndHashCode annotation.");
- }
- }
-
- boolean isDirectDescendantOfObject = true;
-
- if (typeDecl.superclass != null) {
- String p = typeDecl.superclass.toString();
- isDirectDescendantOfObject = p.equals("Object") || p.equals("java.lang.Object");
- }
-
- if (isDirectDescendantOfObject && callSuper) {
- errorNode.addError("Generating equals/hashCode with a supercall to java.lang.Object is pointless.");
- return true;
- }
-
- if (!isDirectDescendantOfObject && !callSuper && implicitCallSuper) {
- errorNode.addWarning("Generating equals/hashCode implementation but without a call to superclass, even though this class does not extend java.lang.Object. If this is intentional, add '@EqualsAndHashCode(callSuper=false)' to your type.");
- }
-
- List<EclipseNode> nodesForEquality = new ArrayList<EclipseNode>();
- if (includes != null) {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() != Kind.FIELD) continue;
- FieldDeclaration fieldDecl = (FieldDeclaration) child.get();
- if (includes.contains(new String(fieldDecl.name))) nodesForEquality.add(child);
- }
- } else {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() != Kind.FIELD) continue;
- FieldDeclaration fieldDecl = (FieldDeclaration) child.get();
- //Skip static fields.
- if ((fieldDecl.modifiers & ClassFileConstants.AccStatic) != 0) continue;
- //Skip transient fields.
- if ((fieldDecl.modifiers & ClassFileConstants.AccTransient) != 0) continue;
- //Skip excluded fields.
- if (excludes != null && excludes.contains(new String(fieldDecl.name))) continue;
- //Skip fields that start with $.
- if (fieldDecl.name.length > 0 && fieldDecl.name[0] == '$') continue;
- nodesForEquality.add(child);
- }
- }
-
- switch (methodExists("hashCode", typeNode)) {
- case NOT_EXISTS:
- MethodDeclaration hashCode = createHashCode(typeNode, nodesForEquality, callSuper, errorNode.get());
- injectMethod(typeNode, hashCode);
- break;
- case EXISTS_BY_LOMBOK:
- break;
- default:
- case EXISTS_BY_USER:
- if (whineIfExists) {
- errorNode.addWarning("Not generating hashCode(): A method with that name already exists");
- }
- break;
- }
-
- switch (methodExists("equals", typeNode)) {
- case NOT_EXISTS:
- MethodDeclaration equals = createEquals(typeNode, nodesForEquality, callSuper, errorNode.get());
- injectMethod(typeNode, equals);
- break;
- case EXISTS_BY_LOMBOK:
- break;
- default:
- case EXISTS_BY_USER:
- if (whineIfExists) {
- errorNode.addWarning("Not generating equals(Object other): A method with that name already exists");
- }
- break;
- }
-
- return true;
- }
-
- private MethodDeclaration createHashCode(EclipseNode type, Collection<EclipseNode> fields, boolean callSuper, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
-
- MethodDeclaration method = new MethodDeclaration(
- ((CompilationUnitDeclaration) type.top().get()).compilationResult);
- Eclipse.setGeneratedBy(method, source);
-
- method.modifiers = EclipseHandlerUtil.toEclipseModifier(AccessLevel.PUBLIC);
- method.returnType = TypeReference.baseTypeReference(TypeIds.T_int, 0);
- Eclipse.setGeneratedBy(method.returnType, source);
- method.annotations = new Annotation[] {makeMarkerAnnotation(TypeConstants.JAVA_LANG_OVERRIDE, source)};
- method.selector = "hashCode".toCharArray();
- method.thrownExceptions = null;
- method.typeParameters = null;
- method.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG;
- method.bodyStart = method.declarationSourceStart = method.sourceStart = source.sourceStart;
- method.bodyEnd = method.declarationSourceEnd = method.sourceEnd = source.sourceEnd;
- method.arguments = null;
-
- List<Statement> statements = new ArrayList<Statement>();
- List<Expression> intoResult = new ArrayList<Expression>();
-
- final char[] PRIME = "PRIME".toCharArray();
- final char[] RESULT = "result".toCharArray();
- final boolean isEmpty = fields.isEmpty();
-
- /* final int PRIME = 31; */ {
- /* Without fields, PRIME isn't used, and that would trigger a 'local variable not used' warning. */
- if (!isEmpty || callSuper) {
- LocalDeclaration primeDecl = new LocalDeclaration(PRIME, pS, pE);
- Eclipse.setGeneratedBy(primeDecl, source);
- primeDecl.modifiers |= Modifier.FINAL;
- primeDecl.type = TypeReference.baseTypeReference(TypeIds.T_int, 0);
- primeDecl.type.sourceStart = pS; primeDecl.type.sourceEnd = pE;
- Eclipse.setGeneratedBy(primeDecl.type, source);
- primeDecl.initialization = new IntLiteral("31".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(primeDecl.initialization, source);
- statements.add(primeDecl);
- }
- }
-
- /* int result = 1; */ {
- LocalDeclaration resultDecl = new LocalDeclaration(RESULT, pS, pE);
- Eclipse.setGeneratedBy(resultDecl, source);
- resultDecl.initialization = new IntLiteral("1".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(resultDecl.initialization, source);
- resultDecl.type = TypeReference.baseTypeReference(TypeIds.T_int, 0);
- resultDecl.type.sourceStart = pS; resultDecl.type.sourceEnd = pE;
- Eclipse.setGeneratedBy(resultDecl.type, source);
- statements.add(resultDecl);
- }
-
- if (callSuper) {
- MessageSend callToSuper = new MessageSend();
- Eclipse.setGeneratedBy(callToSuper, source);
- callToSuper.sourceStart = pS; callToSuper.sourceEnd = pE;
- callToSuper.receiver = new SuperReference(pS, pE);
- Eclipse.setGeneratedBy(callToSuper.receiver, source);
- callToSuper.selector = "hashCode".toCharArray();
- intoResult.add(callToSuper);
- }
-
- int tempCounter = 0;
- for (EclipseNode field : fields) {
- FieldDeclaration f = (FieldDeclaration) field.get();
- char[] token = f.type.getLastToken();
- if (f.type.dimensions() == 0 && token != null) {
- if (Arrays.equals(TypeConstants.FLOAT, token)) {
- /* Float.floatToIntBits(fieldName) */
- MessageSend floatToIntBits = new MessageSend();
- floatToIntBits.sourceStart = pS; floatToIntBits.sourceEnd = pE;
- Eclipse.setGeneratedBy(floatToIntBits, source);
- floatToIntBits.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA_LANG_FLOAT);
- floatToIntBits.selector = "floatToIntBits".toCharArray();
- floatToIntBits.arguments = new Expression[] { generateFieldReference(f.name, source) };
- intoResult.add(floatToIntBits);
- } else if (Arrays.equals(TypeConstants.DOUBLE, token)) {
- /* longToIntForHashCode(Double.doubleToLongBits(fieldName)) */
- MessageSend doubleToLongBits = new MessageSend();
- doubleToLongBits.sourceStart = pS; doubleToLongBits.sourceEnd = pE;
- Eclipse.setGeneratedBy(doubleToLongBits, source);
- doubleToLongBits.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA_LANG_DOUBLE);
- doubleToLongBits.selector = "doubleToLongBits".toCharArray();
- doubleToLongBits.arguments = new Expression[] { generateFieldReference(f.name, source) };
- final char[] tempName = ("temp" + ++tempCounter).toCharArray();
- LocalDeclaration tempVar = new LocalDeclaration(tempName, pS, pE);
- Eclipse.setGeneratedBy(tempVar, source);
- tempVar.initialization = doubleToLongBits;
- tempVar.type = TypeReference.baseTypeReference(TypeIds.T_long, 0);
- tempVar.type.sourceStart = pS; tempVar.type.sourceEnd = pE;
- Eclipse.setGeneratedBy(tempVar.type, source);
- tempVar.modifiers = Modifier.FINAL;
- statements.add(tempVar);
- SingleNameReference copy1 = new SingleNameReference(tempName, p);
- Eclipse.setGeneratedBy(copy1, source);
- SingleNameReference copy2 = new SingleNameReference(tempName, p);
- Eclipse.setGeneratedBy(copy2, source);
- intoResult.add(longToIntForHashCode(copy1, copy2, source));
- } else if (Arrays.equals(TypeConstants.BOOLEAN, token)) {
- /* booleanField ? 1231 : 1237 */
- IntLiteral int1231 = new IntLiteral("1231".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(int1231, source);
- IntLiteral int1237 = new IntLiteral("1237".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(int1237, source);
- ConditionalExpression int1231or1237 = new ConditionalExpression(
- generateFieldReference(f.name, source), int1231, int1237);
- Eclipse.setGeneratedBy(int1231or1237, source);
- intoResult.add(int1231or1237);
- } else if (Arrays.equals(TypeConstants.LONG, token)) {
- intoResult.add(longToIntForHashCode(generateFieldReference(f.name, source), generateFieldReference(f.name, source), source));
- } else if (BUILT_IN_TYPES.contains(new String(token))) {
- intoResult.add(generateFieldReference(f.name, source));
- } else /* objects */ {
- /* this.fieldName == null ? 0 : this.fieldName.hashCode() */
- MessageSend hashCodeCall = new MessageSend();
- hashCodeCall.sourceStart = pS; hashCodeCall.sourceEnd = pE;
- Eclipse.setGeneratedBy(hashCodeCall, source);
- hashCodeCall.receiver = generateFieldReference(f.name, source);
- hashCodeCall.selector = "hashCode".toCharArray();
- NullLiteral nullLiteral = new NullLiteral(pS, pE);
- Eclipse.setGeneratedBy(nullLiteral, source);
- EqualExpression objIsNull = new EqualExpression(
- generateFieldReference(f.name, source), nullLiteral, OperatorIds.EQUAL_EQUAL);
- Eclipse.setGeneratedBy(objIsNull, source);
- IntLiteral int0 = new IntLiteral("0".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(int0, source);
- ConditionalExpression nullOrHashCode = new ConditionalExpression(objIsNull, int0, hashCodeCall);
- nullOrHashCode.sourceStart = pS; nullOrHashCode.sourceEnd = pE;
- Eclipse.setGeneratedBy(nullOrHashCode, source);
- intoResult.add(nullOrHashCode);
- }
- } else if (f.type.dimensions() > 0 && token != null) {
- /* Arrays.deepHashCode(array) //just hashCode for simple arrays */
- MessageSend arraysHashCodeCall = new MessageSend();
- arraysHashCodeCall.sourceStart = pS; arraysHashCodeCall.sourceEnd = pE;
- Eclipse.setGeneratedBy(arraysHashCodeCall, source);
- arraysHashCodeCall.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA, TypeConstants.UTIL, "Arrays".toCharArray());
- if (f.type.dimensions() > 1 || !BUILT_IN_TYPES.contains(new String(token))) {
- arraysHashCodeCall.selector = "deepHashCode".toCharArray();
- } else {
- arraysHashCodeCall.selector = "hashCode".toCharArray();
- }
- arraysHashCodeCall.arguments = new Expression[] { generateFieldReference(f.name, source) };
- intoResult.add(arraysHashCodeCall);
- }
- }
-
- /* fold each intoResult entry into:
- result = result * PRIME + (item); */ {
- for (Expression ex : intoResult) {
- SingleNameReference resultRef = new SingleNameReference(RESULT, p);
- Eclipse.setGeneratedBy(resultRef, source);
- SingleNameReference primeRef = new SingleNameReference(PRIME, p);
- Eclipse.setGeneratedBy(primeRef, source);
- BinaryExpression multiplyByPrime = new BinaryExpression(resultRef, primeRef, OperatorIds.MULTIPLY);
- multiplyByPrime.sourceStart = pS; multiplyByPrime.sourceEnd = pE;
- Eclipse.setGeneratedBy(multiplyByPrime, source);
- BinaryExpression addItem = new BinaryExpression(multiplyByPrime, ex, OperatorIds.PLUS);
- addItem.sourceStart = pS; addItem.sourceEnd = pE;
- Eclipse.setGeneratedBy(addItem, source);
- resultRef = new SingleNameReference(RESULT, p);
- Eclipse.setGeneratedBy(resultRef, source);
- Assignment assignment = new Assignment(resultRef, addItem, pE);
- assignment.sourceStart = pS; assignment.sourceEnd = pE;
- Eclipse.setGeneratedBy(assignment, source);
- statements.add(assignment);
- }
- }
-
- /* return result; */ {
- SingleNameReference resultRef = new SingleNameReference(RESULT, p);
- Eclipse.setGeneratedBy(resultRef, source);
- ReturnStatement returnStatement = new ReturnStatement(resultRef, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
- statements.add(returnStatement);
- }
- method.statements = statements.toArray(new Statement[statements.size()]);
- return method;
- }
-
- private MethodDeclaration createEquals(EclipseNode type, Collection<EclipseNode> fields, boolean callSuper, ASTNode source) {
- int pS = source.sourceStart; int pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
-
- MethodDeclaration method = new MethodDeclaration(
- ((CompilationUnitDeclaration) type.top().get()).compilationResult);
- Eclipse.setGeneratedBy(method, source);
- method.modifiers = EclipseHandlerUtil.toEclipseModifier(AccessLevel.PUBLIC);
- method.returnType = TypeReference.baseTypeReference(TypeIds.T_boolean, 0);
- method.returnType.sourceStart = pS; method.returnType.sourceEnd = pE;
- Eclipse.setGeneratedBy(method.returnType, source);
- method.annotations = new Annotation[] {makeMarkerAnnotation(TypeConstants.JAVA_LANG_OVERRIDE, source)};
- method.selector = "equals".toCharArray();
- method.thrownExceptions = null;
- method.typeParameters = null;
- method.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG;
- method.bodyStart = method.declarationSourceStart = method.sourceStart = source.sourceStart;
- method.bodyEnd = method.declarationSourceEnd = method.sourceEnd = source.sourceEnd;
- TypeReference objectRef = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, new long[] { p, p, p });
- Eclipse.setGeneratedBy(objectRef, source);
- method.arguments = new Argument[] {new Argument(new char[] { 'o' }, 0, objectRef, Modifier.FINAL)};
- method.arguments[0].sourceStart = pS; method.arguments[0].sourceEnd = pE;
- Eclipse.setGeneratedBy(method.arguments[0], source);
-
- List<Statement> statements = new ArrayList<Statement>();
-
- /* if (o == this) return true; */ {
- SingleNameReference oRef = new SingleNameReference(new char[] { 'o' }, p);
- Eclipse.setGeneratedBy(oRef, source);
- ThisReference thisRef = new ThisReference(pS, pE);
- Eclipse.setGeneratedBy(thisRef, source);
- EqualExpression otherEqualsThis = new EqualExpression(oRef, thisRef, OperatorIds.EQUAL_EQUAL);
- Eclipse.setGeneratedBy(otherEqualsThis, source);
-
- TrueLiteral trueLiteral = new TrueLiteral(pS, pE);
- Eclipse.setGeneratedBy(trueLiteral, source);
- ReturnStatement returnTrue = new ReturnStatement(trueLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnTrue, source);
- IfStatement ifOtherEqualsThis = new IfStatement(otherEqualsThis, returnTrue, pS, pE);
- Eclipse.setGeneratedBy(ifOtherEqualsThis, source);
- statements.add(ifOtherEqualsThis);
- }
-
- /* if (o == null) return false; */ {
- SingleNameReference oRef = new SingleNameReference(new char[] { 'o' }, p);
- Eclipse.setGeneratedBy(oRef, source);
- NullLiteral nullLiteral = new NullLiteral(pS, pE);
- Eclipse.setGeneratedBy(nullLiteral, source);
- EqualExpression otherEqualsNull = new EqualExpression(oRef, nullLiteral, OperatorIds.EQUAL_EQUAL);
- Eclipse.setGeneratedBy(otherEqualsNull, source);
-
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnFalse = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnFalse, source);
- IfStatement ifOtherEqualsNull = new IfStatement(otherEqualsNull, returnFalse, pS, pE);
- Eclipse.setGeneratedBy(ifOtherEqualsNull, source);
- statements.add(ifOtherEqualsNull);
- }
-
- /* if (o.getClass() != getClass()) return false; */ {
- MessageSend otherGetClass = new MessageSend();
- otherGetClass.sourceStart = pS; otherGetClass.sourceEnd = pE;
- Eclipse.setGeneratedBy(otherGetClass, source);
- otherGetClass.receiver = new SingleNameReference(new char[] { 'o' }, p);
- Eclipse.setGeneratedBy(otherGetClass.receiver, source);
- otherGetClass.selector = "getClass".toCharArray();
- MessageSend thisGetClass = new MessageSend();
- thisGetClass.sourceStart = pS; thisGetClass.sourceEnd = pE;
- Eclipse.setGeneratedBy(thisGetClass, source);
- thisGetClass.receiver = new ThisReference(pS, pE);
- Eclipse.setGeneratedBy(thisGetClass.receiver, source);
- thisGetClass.selector = "getClass".toCharArray();
- EqualExpression classesNotEqual = new EqualExpression(otherGetClass, thisGetClass, OperatorIds.NOT_EQUAL);
- Eclipse.setGeneratedBy(classesNotEqual, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnFalse = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnFalse, source);
- IfStatement ifClassesNotEqual = new IfStatement(classesNotEqual, returnFalse, pS, pE);
- Eclipse.setGeneratedBy(ifClassesNotEqual, source);
- statements.add(ifClassesNotEqual);
- }
-
- char[] otherN = "other".toCharArray();
-
- /* if (!super.equals(o)) return false; */
- if (callSuper) {
- MessageSend callToSuper = new MessageSend();
- callToSuper.sourceStart = pS; callToSuper.sourceEnd = pE;
- Eclipse.setGeneratedBy(callToSuper, source);
- callToSuper.receiver = new SuperReference(pS, pE);
- Eclipse.setGeneratedBy(callToSuper.receiver, source);
- callToSuper.selector = "equals".toCharArray();
- SingleNameReference oRef = new SingleNameReference(new char[] { 'o' }, p);
- Eclipse.setGeneratedBy(oRef, source);
- callToSuper.arguments = new Expression[] {oRef};
- Expression superNotEqual = new UnaryExpression(callToSuper, OperatorIds.NOT);
- Eclipse.setGeneratedBy(superNotEqual, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnFalse = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnFalse, source);
- IfStatement ifSuperEquals = new IfStatement(superNotEqual, returnFalse, pS, pE);
- Eclipse.setGeneratedBy(ifSuperEquals, source);
- statements.add(ifSuperEquals);
- }
-
- TypeDeclaration typeDecl = (TypeDeclaration)type.get();
- /* MyType<?> other = (MyType<?>) o; */ {
- if (!fields.isEmpty()) {
- LocalDeclaration other = new LocalDeclaration(otherN, pS, pE);
- Eclipse.setGeneratedBy(other, source);
- char[] typeName = typeDecl.name;
- Expression targetType;
- if (typeDecl.typeParameters == null || typeDecl.typeParameters.length == 0) {
- targetType = new SingleNameReference(((TypeDeclaration)type.get()).name, p);
- Eclipse.setGeneratedBy(targetType, source);
- other.type = new SingleTypeReference(typeName, p);
- Eclipse.setGeneratedBy(other.type, source);
- } else {
- TypeReference[] typeArgs = new TypeReference[typeDecl.typeParameters.length];
- for (int i = 0; i < typeArgs.length; i++) {
- typeArgs[i] = new Wildcard(Wildcard.UNBOUND);
- typeArgs[i].sourceStart = pS; typeArgs[i].sourceEnd = pE;
- Eclipse.setGeneratedBy(typeArgs[i], source);
- }
- targetType = new ParameterizedSingleTypeReference(typeName, typeArgs, 0, p);
- Eclipse.setGeneratedBy(targetType, source);
- other.type = new ParameterizedSingleTypeReference(typeName, copyTypes(typeArgs, source), 0, p);
- Eclipse.setGeneratedBy(other.type, source);
- }
- NameReference oRef = new SingleNameReference(new char[] { 'o' }, p);
- Eclipse.setGeneratedBy(oRef, source);
- other.initialization = new CastExpression(oRef, targetType);
- Eclipse.setGeneratedBy(other.initialization, source);
- statements.add(other);
- }
- }
-
- for (EclipseNode field : fields) {
- FieldDeclaration f = (FieldDeclaration) field.get();
- char[] token = f.type.getLastToken();
- if (f.type.dimensions() == 0 && token != null) {
- if (Arrays.equals(TypeConstants.FLOAT, token)) {
- statements.add(generateCompareFloatOrDouble(otherN, "Float".toCharArray(), f.name, source));
- } else if (Arrays.equals(TypeConstants.DOUBLE, token)) {
- statements.add(generateCompareFloatOrDouble(otherN, "Double".toCharArray(), f.name, source));
- } else if (BUILT_IN_TYPES.contains(new String(token))) {
- NameReference fieldRef = new SingleNameReference(f.name, p);
- Eclipse.setGeneratedBy(fieldRef, source);
- EqualExpression fieldsNotEqual = new EqualExpression(fieldRef,
- generateQualifiedNameRef(source, otherN, f.name), OperatorIds.NOT_EQUAL);
- Eclipse.setGeneratedBy(fieldsNotEqual, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnStatement = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
- IfStatement ifStatement = new IfStatement(fieldsNotEqual, returnStatement, pS, pE);
- Eclipse.setGeneratedBy(ifStatement, source);
- statements.add(ifStatement);
- } else /* objects */ {
- NameReference fieldNameRef = new SingleNameReference(f.name, p);
- Eclipse.setGeneratedBy(fieldNameRef, source);
- NullLiteral nullLiteral = new NullLiteral(pS, pE);
- Eclipse.setGeneratedBy(nullLiteral, source);
- EqualExpression fieldIsNull = new EqualExpression(fieldNameRef, nullLiteral, OperatorIds.EQUAL_EQUAL);
- nullLiteral = new NullLiteral(pS, pE);
- Eclipse.setGeneratedBy(nullLiteral, source);
- EqualExpression otherFieldIsntNull = new EqualExpression(
- generateQualifiedNameRef(source, otherN, f.name),
- nullLiteral, OperatorIds.NOT_EQUAL);
- MessageSend equalsCall = new MessageSend();
- equalsCall.sourceStart = pS; equalsCall.sourceEnd = pE;
- Eclipse.setGeneratedBy(equalsCall, source);
- equalsCall.receiver = new SingleNameReference(f.name, p);
- Eclipse.setGeneratedBy(equalsCall.receiver, source);
- equalsCall.selector = "equals".toCharArray();
- equalsCall.arguments = new Expression[] { generateQualifiedNameRef(source, otherN, f.name) };
- UnaryExpression fieldsNotEqual = new UnaryExpression(equalsCall, OperatorIds.NOT);
- fieldsNotEqual.sourceStart = pS; fieldsNotEqual.sourceEnd = pE;
- Eclipse.setGeneratedBy(fieldsNotEqual, source);
- ConditionalExpression fullEquals = new ConditionalExpression(fieldIsNull, otherFieldIsntNull, fieldsNotEqual);
- fullEquals.sourceStart = pS; fullEquals.sourceEnd = pE;
- Eclipse.setGeneratedBy(fullEquals, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnStatement = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
- IfStatement ifStatement = new IfStatement(fullEquals, returnStatement, pS, pE);
- Eclipse.setGeneratedBy(ifStatement, source);
- statements.add(ifStatement);
- }
- } else if (f.type.dimensions() > 0 && token != null) {
- MessageSend arraysEqualCall = new MessageSend();
- arraysEqualCall.sourceStart = pS; arraysEqualCall.sourceEnd = pE;
- Eclipse.setGeneratedBy(arraysEqualCall, source);
- arraysEqualCall.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA, TypeConstants.UTIL, "Arrays".toCharArray());
- if (f.type.dimensions() > 1 || !BUILT_IN_TYPES.contains(new String(token))) {
- arraysEqualCall.selector = "deepEquals".toCharArray();
- } else {
- arraysEqualCall.selector = "equals".toCharArray();
- }
- NameReference fieldNameRef = new SingleNameReference(f.name, p);
- Eclipse.setGeneratedBy(fieldNameRef, source);
- arraysEqualCall.arguments = new Expression[] { fieldNameRef, generateQualifiedNameRef(source, otherN, f.name) };
- UnaryExpression arraysNotEqual = new UnaryExpression(arraysEqualCall, OperatorIds.NOT);
- arraysNotEqual.sourceStart = pS; arraysNotEqual.sourceEnd = pE;
- Eclipse.setGeneratedBy(arraysNotEqual, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnStatement = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
- IfStatement ifStatement = new IfStatement(arraysNotEqual, returnStatement, pS, pE);
- Eclipse.setGeneratedBy(ifStatement, source);
- statements.add(ifStatement);
- }
- }
-
- /* return true; */ {
- TrueLiteral trueLiteral = new TrueLiteral(pS, pE);
- Eclipse.setGeneratedBy(trueLiteral, source);
- ReturnStatement returnStatement = new ReturnStatement(trueLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
- statements.add(returnStatement);
- }
- method.statements = statements.toArray(new Statement[statements.size()]);
- return method;
- }
-
- private IfStatement generateCompareFloatOrDouble(char[] otherN, char[] floatOrDouble, char[] fieldName, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
- /* if (Float.compare(fieldName, other.fieldName) != 0) return false */
- MessageSend floatCompare = new MessageSend();
- floatCompare.sourceStart = pS; floatCompare.sourceEnd = pE;
- Eclipse.setGeneratedBy(floatCompare, source);
- floatCompare.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA, TypeConstants.LANG, floatOrDouble);
- floatCompare.selector = "compare".toCharArray();
- NameReference fieldNameRef = new SingleNameReference(fieldName, p);
- Eclipse.setGeneratedBy(fieldNameRef, source);
- floatCompare.arguments = new Expression[] {fieldNameRef, generateQualifiedNameRef(source, otherN, fieldName)};
- IntLiteral int0 = new IntLiteral(new char[] {'0'}, pS, pE);
- Eclipse.setGeneratedBy(int0, source);
- EqualExpression ifFloatCompareIsNot0 = new EqualExpression(floatCompare, int0, OperatorIds.NOT_EQUAL);
- ifFloatCompareIsNot0.sourceStart = pS; ifFloatCompareIsNot0.sourceEnd = pE;
- Eclipse.setGeneratedBy(ifFloatCompareIsNot0, source);
- FalseLiteral falseLiteral = new FalseLiteral(pS, pE);
- Eclipse.setGeneratedBy(falseLiteral, source);
- ReturnStatement returnFalse = new ReturnStatement(falseLiteral, pS, pE);
- Eclipse.setGeneratedBy(returnFalse, source);
- IfStatement ifStatement = new IfStatement(ifFloatCompareIsNot0, returnFalse, pS, pE);
- Eclipse.setGeneratedBy(ifStatement, source);
- return ifStatement;
- }
-
- /** Give 2 clones! */
- private Expression longToIntForHashCode(Reference ref1, Reference ref2, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- /* (int)(ref >>> 32 ^ ref) */
- IntLiteral int32 = new IntLiteral("32".toCharArray(), pS, pE);
- Eclipse.setGeneratedBy(int32, source);
- BinaryExpression higherBits = new BinaryExpression(ref1, int32, OperatorIds.UNSIGNED_RIGHT_SHIFT);
- Eclipse.setGeneratedBy(higherBits, source);
- BinaryExpression xorParts = new BinaryExpression(ref2, higherBits, OperatorIds.XOR);
- Eclipse.setGeneratedBy(xorParts, source);
- TypeReference intRef = TypeReference.baseTypeReference(TypeIds.T_int, 0);
- intRef.sourceStart = pS; intRef.sourceEnd = pE;
- Eclipse.setGeneratedBy(intRef, source);
- CastExpression expr = new CastExpression(xorParts, intRef);
- expr.sourceStart = pS; expr.sourceEnd = pE;
- Eclipse.setGeneratedBy(expr, source);
- return expr;
- }
-
- private Reference generateFieldReference(char[] fieldName, ASTNode source) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
- FieldReference thisX = new FieldReference(("this." + new String(fieldName)).toCharArray(), p);
- Eclipse.setGeneratedBy(thisX, source);
- thisX.receiver = new ThisReference(pS, pE);
- Eclipse.setGeneratedBy(thisX.receiver, source);
- thisX.token = fieldName;
- return thisX;
- }
-
- private NameReference generateQualifiedNameRef(ASTNode source, char[]... varNames) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
-
- NameReference ref;
-
- if (varNames.length > 1) ref = new QualifiedNameReference(varNames, new long[varNames.length], pS, pE);
- else ref = new SingleNameReference(varNames[0], p);
- Eclipse.setGeneratedBy(ref, source);
- return ref;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleGetter.java b/src/lombok/eclipse/handlers/HandleGetter.java
deleted file mode 100644
index 4a9930e3..00000000
--- a/src/lombok/eclipse/handlers/HandleGetter.java
+++ /dev/null
@@ -1,154 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.Eclipse.*;
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-import lombok.AccessLevel;
-import lombok.Getter;
-import lombok.core.AnnotationValues;
-import lombok.core.TransformationsUtil;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.ReturnStatement;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.Getter} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleGetter implements EclipseAnnotationHandler<Getter> {
- /**
- * Generates a getter on the stated field.
- *
- * Used by {@link HandleData}.
- *
- * The difference between this call and the handle method is as follows:
- *
- * If there is a {@code lombok.Getter} annotation on the field, it is used and the
- * same rules apply (e.g. warning if the method already exists, stated access level applies).
- * If not, the getter is still generated if it isn't already there, though there will not
- * be a warning if its already there. The default access level is used.
- */
- public void generateGetterForField(EclipseNode fieldNode, ASTNode pos) {
- for (EclipseNode child : fieldNode.down()) {
- if (child.getKind() == Kind.ANNOTATION) {
- if (annotationTypeMatches(Getter.class, child)) {
- //The annotation will make it happen, so we can skip it.
- return;
- }
- }
- }
-
- createGetterForField(AccessLevel.PUBLIC, fieldNode, fieldNode, pos, false);
- }
-
- public boolean handle(AnnotationValues<Getter> annotation, Annotation ast, EclipseNode annotationNode) {
- EclipseNode fieldNode = annotationNode.up();
- AccessLevel level = annotation.getInstance().value();
- if (level == AccessLevel.NONE) return true;
-
- return createGetterForField(level, fieldNode, annotationNode, annotationNode.get(), true);
- }
-
- private boolean createGetterForField(AccessLevel level,
- EclipseNode fieldNode, EclipseNode errorNode, ASTNode source, boolean whineIfExists) {
- if (fieldNode.getKind() != Kind.FIELD) {
- errorNode.addError("@Getter is only supported on a field.");
- return true;
- }
-
- FieldDeclaration field = (FieldDeclaration) fieldNode.get();
- TypeReference fieldType = copyType(field.type, source);
- String fieldName = new String(field.name);
- boolean isBoolean = nameEquals(fieldType.getTypeName(), "boolean") && fieldType.dimensions() == 0;
- String getterName = TransformationsUtil.toGetterName(fieldName, isBoolean);
-
- int modifier = toEclipseModifier(level) | (field.modifiers & ClassFileConstants.AccStatic);
-
- for (String altName : TransformationsUtil.toAllGetterNames(fieldName, isBoolean)) {
- switch (methodExists(altName, fieldNode)) {
- case EXISTS_BY_LOMBOK:
- return true;
- case EXISTS_BY_USER:
- if (whineIfExists) {
- String altNameExpl = "";
- if (!altName.equals(getterName)) altNameExpl = String.format(" (%s)", altName);
- errorNode.addWarning(
- String.format("Not generating %s(): A method with that name already exists%s", getterName, altNameExpl));
- }
- return true;
- default:
- case NOT_EXISTS:
- //continue scanning the other alt names.
- }
- }
-
- MethodDeclaration method = generateGetter((TypeDeclaration) fieldNode.up().get(), field, getterName, modifier, source);
- Annotation[] copiedAnnotations = copyAnnotations(
- findAnnotations(field, TransformationsUtil.NON_NULL_PATTERN),
- findAnnotations(field, TransformationsUtil.NULLABLE_PATTERN), source);
- if (copiedAnnotations.length != 0) {
- method.annotations = copiedAnnotations;
- }
-
- injectMethod(fieldNode.up(), method);
-
- return true;
- }
-
- private MethodDeclaration generateGetter(TypeDeclaration parent, FieldDeclaration field, String name,
- int modifier, ASTNode source) {
- MethodDeclaration method = new MethodDeclaration(parent.compilationResult);
- Eclipse.setGeneratedBy(method, source);
- method.modifiers = modifier;
- method.returnType = copyType(field.type, source);
- method.annotations = null;
- method.arguments = null;
- method.selector = name.toCharArray();
- method.binding = null;
- method.thrownExceptions = null;
- method.typeParameters = null;
- method.bits |= ECLIPSE_DO_NOT_TOUCH_FLAG;
- Expression fieldExpression = new SingleNameReference(field.name, ((long)field.declarationSourceStart << 32) | field.declarationSourceEnd);
- Eclipse.setGeneratedBy(fieldExpression, source);
- Statement returnStatement = new ReturnStatement(fieldExpression, field.sourceStart, field.sourceEnd);
- Eclipse.setGeneratedBy(returnStatement, source);
- method.bodyStart = method.declarationSourceStart = method.sourceStart = source.sourceStart;
- method.bodyEnd = method.declarationSourceEnd = method.sourceEnd = source.sourceEnd;
- method.statements = new Statement[] { returnStatement };
- return method;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandlePrintAST.java b/src/lombok/eclipse/handlers/HandlePrintAST.java
deleted file mode 100644
index 580a54a2..00000000
--- a/src/lombok/eclipse/handlers/HandlePrintAST.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.PrintStream;
-
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.mangosdk.spi.ProviderFor;
-
-import lombok.Lombok;
-import lombok.core.AnnotationValues;
-import lombok.core.PrintAST;
-import lombok.eclipse.EclipseASTVisitor;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-/**
- * Handles the {@code lombok.core.PrintAST} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandlePrintAST implements EclipseAnnotationHandler<PrintAST> {
- public boolean handle(AnnotationValues<PrintAST> annotation, Annotation ast, EclipseNode annotationNode) {
- if (!annotationNode.isCompleteParse()) return false;
-
- PrintStream stream = System.out;
- String fileName = annotation.getInstance().outfile();
- if (fileName.length() > 0) try {
- stream = new PrintStream(new File(fileName));
- } catch (FileNotFoundException e) {
- Lombok.sneakyThrow(e);
- }
-
- annotationNode.up().traverse(new EclipseASTVisitor.Printer(annotation.getInstance().printContent(), stream));
- return true;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleSetter.java b/src/lombok/eclipse/handlers/HandleSetter.java
deleted file mode 100644
index 9bd10af3..00000000
--- a/src/lombok/eclipse/handlers/HandleSetter.java
+++ /dev/null
@@ -1,172 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.Eclipse.*;
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-
-import java.lang.reflect.Modifier;
-
-import lombok.AccessLevel;
-import lombok.Setter;
-import lombok.core.AnnotationValues;
-import lombok.core.TransformationsUtil;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Argument;
-import org.eclipse.jdt.internal.compiler.ast.Assignment;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.FieldReference;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.NameReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.ThisReference;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-import org.eclipse.jdt.internal.compiler.lookup.TypeIds;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.Setter} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleSetter implements EclipseAnnotationHandler<Setter> {
- /**
- * Generates a setter on the stated field.
- *
- * Used by {@link HandleData}.
- *
- * The difference between this call and the handle method is as follows:
- *
- * If there is a {@code lombok.Setter} annotation on the field, it is used and the
- * same rules apply (e.g. warning if the method already exists, stated access level applies).
- * If not, the setter is still generated if it isn't already there, though there will not
- * be a warning if its already there. The default access level is used.
- */
- public void generateSetterForField(EclipseNode fieldNode, ASTNode pos) {
- for (EclipseNode child : fieldNode.down()) {
- if (child.getKind() == Kind.ANNOTATION) {
- if (annotationTypeMatches(Setter.class, child)) {
- //The annotation will make it happen, so we can skip it.
- return;
- }
- }
- }
-
- createSetterForField(AccessLevel.PUBLIC, fieldNode, fieldNode, pos, false);
- }
-
- public boolean handle(AnnotationValues<Setter> annotation, Annotation ast, EclipseNode annotationNode) {
- EclipseNode fieldNode = annotationNode.up();
- if (fieldNode.getKind() != Kind.FIELD) return false;
- AccessLevel level = annotation.getInstance().value();
- if (level == AccessLevel.NONE) return true;
-
- return createSetterForField(level, fieldNode, annotationNode, annotationNode.get(), true);
- }
-
- private boolean createSetterForField(AccessLevel level,
- EclipseNode fieldNode, EclipseNode errorNode, ASTNode pos, boolean whineIfExists) {
- if (fieldNode.getKind() != Kind.FIELD) {
- errorNode.addError("@Setter is only supported on a field.");
- return true;
- }
-
- FieldDeclaration field = (FieldDeclaration) fieldNode.get();
- String setterName = TransformationsUtil.toSetterName(new String(field.name));
-
- int modifier = toEclipseModifier(level) | (field.modifiers & ClassFileConstants.AccStatic);
-
- switch (methodExists(setterName, fieldNode)) {
- case EXISTS_BY_LOMBOK:
- return true;
- case EXISTS_BY_USER:
- if (whineIfExists) errorNode.addWarning(
- String.format("Not generating %s(%s %s): A method with that name already exists",
- setterName, field.type, new String(field.name)));
- return true;
- default:
- case NOT_EXISTS:
- //continue with creating the setter
- }
-
- MethodDeclaration method = generateSetter((TypeDeclaration) fieldNode.up().get(), field, setterName, modifier, pos);
-
- injectMethod(fieldNode.up(), method);
-
- return true;
- }
-
- private MethodDeclaration generateSetter(TypeDeclaration parent, FieldDeclaration field, String name,
- int modifier, ASTNode source) {
-
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
- MethodDeclaration method = new MethodDeclaration(parent.compilationResult);
- Eclipse.setGeneratedBy(method, source);
- method.modifiers = modifier;
- method.returnType = TypeReference.baseTypeReference(TypeIds.T_void, 0);
- method.returnType.sourceStart = pS; method.returnType.sourceEnd = pE;
- Eclipse.setGeneratedBy(method.returnType, source);
- method.annotations = null;
- Argument param = new Argument(field.name, p, copyType(field.type, source), Modifier.FINAL);
- param.sourceStart = pS; param.sourceEnd = pE;
- Eclipse.setGeneratedBy(param, source);
- method.arguments = new Argument[] { param };
- method.selector = name.toCharArray();
- method.binding = null;
- method.thrownExceptions = null;
- method.typeParameters = null;
- method.bits |= ECLIPSE_DO_NOT_TOUCH_FLAG;
- FieldReference thisX = new FieldReference(field.name, p);
- Eclipse.setGeneratedBy(thisX, source);
- thisX.receiver = new ThisReference(source.sourceStart, source.sourceEnd);
- Eclipse.setGeneratedBy(thisX.receiver, source);
- NameReference fieldNameRef = new SingleNameReference(field.name, p);
- Eclipse.setGeneratedBy(fieldNameRef, source);
- Assignment assignment = new Assignment(thisX, fieldNameRef, (int)p);
- assignment.sourceStart = pS; assignment.sourceEnd = pE;
- Eclipse.setGeneratedBy(assignment, source);
- method.bodyStart = method.declarationSourceStart = method.sourceStart = source.sourceStart;
- method.bodyEnd = method.declarationSourceEnd = method.sourceEnd = source.sourceEnd;
-
- Annotation[] nonNulls = findAnnotations(field, TransformationsUtil.NON_NULL_PATTERN);
- Annotation[] nullables = findAnnotations(field, TransformationsUtil.NULLABLE_PATTERN);
- if (nonNulls.length == 0) {
- method.statements = new Statement[] { assignment };
- } else {
- Statement nullCheck = generateNullCheck(field, source);
- if (nullCheck != null) method.statements = new Statement[] { nullCheck, assignment };
- else method.statements = new Statement[] { assignment };
- }
- Annotation[] copiedAnnotations = copyAnnotations(nonNulls, nullables, source);
- if (copiedAnnotations.length != 0) param.annotations = copiedAnnotations;
- return method;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleSneakyThrows.java b/src/lombok/eclipse/handlers/HandleSneakyThrows.java
deleted file mode 100644
index 38f22b2a..00000000
--- a/src/lombok/eclipse/handlers/HandleSneakyThrows.java
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import java.lang.reflect.Modifier;
-import java.util.ArrayList;
-import java.util.List;
-
-import lombok.SneakyThrows;
-import lombok.core.AnnotationValues;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.Argument;
-import org.eclipse.jdt.internal.compiler.ast.ArrayInitializer;
-import org.eclipse.jdt.internal.compiler.ast.Block;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.MemberValuePair;
-import org.eclipse.jdt.internal.compiler.ast.MessageSend;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.SingleTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.ThrowStatement;
-import org.eclipse.jdt.internal.compiler.ast.TryStatement;
-import org.eclipse.jdt.internal.compiler.ast.TypeReference;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.HandleSneakyThrows} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleSneakyThrows implements EclipseAnnotationHandler<SneakyThrows> {
- private static class DeclaredException {
- final String exceptionName;
- final ASTNode node;
-
- DeclaredException(String exceptionName, ASTNode node) {
- this.exceptionName = exceptionName;
- this.node = node;
- }
-
- public long getPos() {
- return (long)node.sourceStart << 32 | node.sourceEnd;
- }
- }
-
- @Override public boolean handle(AnnotationValues<SneakyThrows> annotation, Annotation source, EclipseNode annotationNode) {
- List<String> exceptionNames = annotation.getRawExpressions("value");
- List<DeclaredException> exceptions = new ArrayList<DeclaredException>();
-
- MemberValuePair[] memberValuePairs = source.memberValuePairs();
- if (memberValuePairs == null || memberValuePairs.length == 0) {
- exceptions.add(new DeclaredException("java.lang.Throwable", source));
- } else {
- Expression arrayOrSingle = memberValuePairs[0].value;
- final Expression[] exceptionNameNodes;
- if (arrayOrSingle instanceof ArrayInitializer) {
- exceptionNameNodes = ((ArrayInitializer)arrayOrSingle).expressions;
- } else exceptionNameNodes = new Expression[] { arrayOrSingle };
-
- if (exceptionNames.size() != exceptionNameNodes.length) {
- annotationNode.addError(
- "LOMBOK BUG: The number of exception classes in the annotation isn't the same pre- and post- guessing.");
- }
-
- int idx = 0;
- for (String exceptionName : exceptionNames) {
- if (exceptionName.endsWith(".class")) exceptionName = exceptionName.substring(0, exceptionName.length() - 6);
- exceptions.add(new DeclaredException(exceptionName, exceptionNameNodes[idx++]));
- }
- }
-
-
- EclipseNode owner = annotationNode.up();
- switch (owner.getKind()) {
-// case FIELD:
-// return handleField(annotationNode, (FieldDeclaration)owner.get(), exceptions);
- case METHOD:
- return handleMethod(annotationNode, (AbstractMethodDeclaration)owner.get(), exceptions);
- default:
- annotationNode.addError("@SneakyThrows is legal only on methods and constructors.");
- return true;
- }
- }
-
-// private boolean handleField(Node annotation, FieldDeclaration field, List<DeclaredException> exceptions) {
-// if (field.initialization == null) {
-// annotation.addError("@SneakyThrows can only be used on fields with an initialization statement.");
-// return true;
-// }
-//
-// Expression expression = field.initialization;
-// Statement[] content = new Statement[] {new Assignment(
-// new SingleNameReference(field.name, 0), expression, 0)};
-// field.initialization = null;
-//
-// for (DeclaredException exception : exceptions) {
-// content = new Statement[] { buildTryCatchBlock(content, exception) };
-// }
-//
-// Block block = new Block(0);
-// block.statements = content;
-//
-// Node typeNode = annotation.up().up();
-//
-// Initializer initializer = new Initializer(block, field.modifiers & Modifier.STATIC);
-// initializer.sourceStart = expression.sourceStart;
-// initializer.sourceEnd = expression.sourceEnd;
-// initializer.declarationSourceStart = expression.sourceStart;
-// initializer.declarationSourceEnd = expression.sourceEnd;
-// injectField(typeNode, initializer);
-//
-// typeNode.rebuild();
-//
-// return true;
-// }
-
- private boolean handleMethod(EclipseNode annotation, AbstractMethodDeclaration method, List<DeclaredException> exceptions) {
- if (method.isAbstract()) {
- annotation.addError("@SneakyThrows can only be used on concrete methods.");
- return true;
- }
-
- if (method.statements == null) return false;
-
- Statement[] contents = method.statements;
-
- for (DeclaredException exception : exceptions) {
- contents = new Statement[] { buildTryCatchBlock(contents, exception, exception.node) };
- }
-
- method.statements = contents;
- annotation.up().rebuild();
-
- return true;
- }
-
- private Statement buildTryCatchBlock(Statement[] contents, DeclaredException exception, ASTNode source) {
- long p = exception.getPos();
- int pS = (int)(p >> 32), pE = (int)p;
-
- TryStatement tryStatement = new TryStatement();
- Eclipse.setGeneratedBy(tryStatement, source);
- tryStatement.tryBlock = new Block(0);
- tryStatement.tryBlock.sourceStart = pS; tryStatement.tryBlock.sourceEnd = pE;
- Eclipse.setGeneratedBy(tryStatement.tryBlock, source);
- tryStatement.tryBlock.statements = contents;
- TypeReference typeReference;
- if (exception.exceptionName.indexOf('.') == -1) {
- typeReference = new SingleTypeReference(exception.exceptionName.toCharArray(), p);
- typeReference.statementEnd = pE;
- } else {
- String[] x = exception.exceptionName.split("\\.");
- char[][] elems = new char[x.length][];
- long[] poss = new long[x.length];
- int start = pS;
- for (int i = 0; i < x.length; i++) {
- elems[i] = x[i].trim().toCharArray();
- int end = start + x[i].length();
- poss[i] = (long)start << 32 | end;
- start = end + 1;
- }
- typeReference = new QualifiedTypeReference(elems, poss);
- }
- Eclipse.setGeneratedBy(typeReference, source);
-
- Argument catchArg = new Argument("$ex".toCharArray(), p, typeReference, Modifier.FINAL);
- Eclipse.setGeneratedBy(catchArg, source);
- catchArg.declarationSourceEnd = catchArg.declarationEnd = catchArg.sourceEnd = pE;
- catchArg.declarationSourceStart = catchArg.modifiersSourceStart = catchArg.sourceStart = pS;
-
- tryStatement.catchArguments = new Argument[] { catchArg };
-
- MessageSend sneakyThrowStatement = new MessageSend();
- Eclipse.setGeneratedBy(sneakyThrowStatement, source);
- sneakyThrowStatement.receiver = new QualifiedNameReference(new char[][] { "lombok".toCharArray(), "Lombok".toCharArray() }, new long[] { p, p }, pS, pE);
- Eclipse.setGeneratedBy(sneakyThrowStatement.receiver, source);
- sneakyThrowStatement.receiver.statementEnd = pE;
- sneakyThrowStatement.selector = "sneakyThrow".toCharArray();
- SingleNameReference exRef = new SingleNameReference("$ex".toCharArray(), p);
- Eclipse.setGeneratedBy(exRef, source);
- exRef.statementEnd = pE;
- sneakyThrowStatement.arguments = new Expression[] { exRef };
- sneakyThrowStatement.nameSourcePosition = p;
- sneakyThrowStatement.sourceStart = pS;
- sneakyThrowStatement.sourceEnd = sneakyThrowStatement.statementEnd = pE;
- Statement rethrowStatement = new ThrowStatement(sneakyThrowStatement, pS, pE);
- Eclipse.setGeneratedBy(rethrowStatement, source);
- Block block = new Block(0);
- block.sourceStart = pS;
- block.sourceEnd = pE;
- Eclipse.setGeneratedBy(block, source);
- block.statements = new Statement[] { rethrowStatement };
- tryStatement.catchBlocks = new Block[] { block };
- tryStatement.sourceStart = pS;
- tryStatement.sourceEnd = pE;
- return tryStatement;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleSynchronized.java b/src/lombok/eclipse/handlers/HandleSynchronized.java
deleted file mode 100644
index fde36192..00000000
--- a/src/lombok/eclipse/handlers/HandleSynchronized.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-
-import java.lang.reflect.Modifier;
-
-import lombok.Synchronized;
-import lombok.core.AnnotationValues;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-import lombok.eclipse.handlers.EclipseHandlerUtil.MemberExistsResult;
-
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.ArrayAllocationExpression;
-import org.eclipse.jdt.internal.compiler.ast.Block;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.FieldReference;
-import org.eclipse.jdt.internal.compiler.ast.IntLiteral;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.SynchronizedStatement;
-import org.eclipse.jdt.internal.compiler.ast.ThisReference;
-import org.eclipse.jdt.internal.compiler.lookup.TypeConstants;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code lombok.Synchronized} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleSynchronized implements EclipseAnnotationHandler<Synchronized> {
- private static final char[] INSTANCE_LOCK_NAME = "$lock".toCharArray();
- private static final char[] STATIC_LOCK_NAME = "$LOCK".toCharArray();
-
- @Override public boolean handle(AnnotationValues<Synchronized> annotation, Annotation source, EclipseNode annotationNode) {
- int p1 = source.sourceStart -1;
- int p2 = source.sourceStart -2;
- long pos = (((long)p1) << 32) | p2;
- EclipseNode methodNode = annotationNode.up();
- if (methodNode == null || methodNode.getKind() != Kind.METHOD || !(methodNode.get() instanceof MethodDeclaration)) {
- annotationNode.addError("@Synchronized is legal only on methods.");
- return true;
- }
-
- MethodDeclaration method = (MethodDeclaration)methodNode.get();
- if (method.isAbstract()) {
- annotationNode.addError("@Synchronized is legal only on concrete methods.");
- return true;
- }
-
- char[] lockName = annotation.getInstance().value().toCharArray();
- boolean autoMake = false;
- if (lockName.length == 0) {
- autoMake = true;
- lockName = method.isStatic() ? STATIC_LOCK_NAME : INSTANCE_LOCK_NAME;
- }
-
- if (fieldExists(new String(lockName), methodNode) == MemberExistsResult.NOT_EXISTS) {
- if (!autoMake) {
- annotationNode.addError("The field " + new String(lockName) + " does not exist.");
- return true;
- }
- FieldDeclaration fieldDecl = new FieldDeclaration(lockName, 0, -1);
- Eclipse.setGeneratedBy(fieldDecl, source);
- fieldDecl.declarationSourceEnd = -1;
-
- fieldDecl.modifiers = (method.isStatic() ? Modifier.STATIC : 0) | Modifier.FINAL | Modifier.PRIVATE;
-
- //We use 'new Object[0];' because quite unlike 'new Object();', empty arrays *ARE* serializable!
- ArrayAllocationExpression arrayAlloc = new ArrayAllocationExpression();
- Eclipse.setGeneratedBy(arrayAlloc, source);
- arrayAlloc.dimensions = new Expression[] { new IntLiteral(new char[] { '0' }, 0, 0) };
- Eclipse.setGeneratedBy(arrayAlloc.dimensions[0], source);
- arrayAlloc.type = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, new long[] { 0, 0, 0 });
- Eclipse.setGeneratedBy(arrayAlloc.type, source);
- fieldDecl.type = new QualifiedTypeReference(TypeConstants.JAVA_LANG_OBJECT, new long[] { 0, 0, 0 });
- Eclipse.setGeneratedBy(fieldDecl.type, source);
- fieldDecl.initialization = arrayAlloc;
- injectField(annotationNode.up().up(), fieldDecl);
- }
-
- if (method.statements == null) return false;
-
- Block block = new Block(0);
- Eclipse.setGeneratedBy(block, source);
- block.statements = method.statements;
- Expression lockVariable;
- if (method.isStatic()) lockVariable = new QualifiedNameReference(new char[][] {
- methodNode.up().getName().toCharArray(), lockName }, new long[] { pos, pos }, p1, p2);
- else {
- lockVariable = new FieldReference(lockName, pos);
- ThisReference thisReference = new ThisReference(p1, p2);
- Eclipse.setGeneratedBy(thisReference, source);
- ((FieldReference)lockVariable).receiver = thisReference;
- }
- Eclipse.setGeneratedBy(lockVariable, source);
-
- method.statements = new Statement[] {
- new SynchronizedStatement(lockVariable, block, 0, 0)
- };
- Eclipse.setGeneratedBy(method.statements[0], source);
-
- methodNode.rebuild();
-
- return true;
- }
-}
diff --git a/src/lombok/eclipse/handlers/HandleToString.java b/src/lombok/eclipse/handlers/HandleToString.java
deleted file mode 100644
index d5a4c398..00000000
--- a/src/lombok/eclipse/handlers/HandleToString.java
+++ /dev/null
@@ -1,304 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.handlers;
-
-import static lombok.eclipse.handlers.EclipseHandlerUtil.*;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-import lombok.AccessLevel;
-import lombok.ToString;
-import lombok.core.AnnotationValues;
-import lombok.core.AST.Kind;
-import lombok.eclipse.Eclipse;
-import lombok.eclipse.EclipseAnnotationHandler;
-import lombok.eclipse.EclipseNode;
-
-import org.eclipse.jdt.internal.compiler.ast.ASTNode;
-import org.eclipse.jdt.internal.compiler.ast.Annotation;
-import org.eclipse.jdt.internal.compiler.ast.BinaryExpression;
-import org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.Expression;
-import org.eclipse.jdt.internal.compiler.ast.FieldDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.FieldReference;
-import org.eclipse.jdt.internal.compiler.ast.MessageSend;
-import org.eclipse.jdt.internal.compiler.ast.MethodDeclaration;
-import org.eclipse.jdt.internal.compiler.ast.NameReference;
-import org.eclipse.jdt.internal.compiler.ast.OperatorIds;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference;
-import org.eclipse.jdt.internal.compiler.ast.QualifiedTypeReference;
-import org.eclipse.jdt.internal.compiler.ast.ReturnStatement;
-import org.eclipse.jdt.internal.compiler.ast.SingleNameReference;
-import org.eclipse.jdt.internal.compiler.ast.Statement;
-import org.eclipse.jdt.internal.compiler.ast.StringLiteral;
-import org.eclipse.jdt.internal.compiler.ast.SuperReference;
-import org.eclipse.jdt.internal.compiler.ast.ThisReference;
-import org.eclipse.jdt.internal.compiler.ast.TypeDeclaration;
-import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants;
-import org.eclipse.jdt.internal.compiler.lookup.TypeConstants;
-import org.mangosdk.spi.ProviderFor;
-
-/**
- * Handles the {@code ToString} annotation for eclipse.
- */
-@ProviderFor(EclipseAnnotationHandler.class)
-public class HandleToString implements EclipseAnnotationHandler<ToString> {
- private void checkForBogusFieldNames(EclipseNode type, AnnotationValues<ToString> annotation) {
- if (annotation.isExplicit("exclude")) {
- for (int i : createListOfNonExistentFields(Arrays.asList(annotation.getInstance().exclude()), type, true, false)) {
- annotation.setWarning("exclude", "This field does not exist, or would have been excluded anyway.", i);
- }
- }
- if (annotation.isExplicit("of")) {
- for (int i : createListOfNonExistentFields(Arrays.asList(annotation.getInstance().of()), type, false, false)) {
- annotation.setWarning("of", "This field does not exist.", i);
- }
- }
- }
-
- public void generateToStringForType(EclipseNode typeNode, EclipseNode errorNode) {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() == Kind.ANNOTATION) {
- if (Eclipse.annotationTypeMatches(ToString.class, child)) {
- //The annotation will make it happen, so we can skip it.
- return;
- }
- }
- }
-
- boolean includeFieldNames = true;
- try {
- includeFieldNames = ((Boolean)ToString.class.getMethod("includeFieldNames").getDefaultValue()).booleanValue();
- } catch (Exception ignore) {}
- generateToString(typeNode, errorNode, null, null, includeFieldNames, null, false);
- }
-
- public boolean handle(AnnotationValues<ToString> annotation, Annotation ast, EclipseNode annotationNode) {
- ToString ann = annotation.getInstance();
- List<String> excludes = Arrays.asList(ann.exclude());
- List<String> includes = Arrays.asList(ann.of());
- EclipseNode typeNode = annotationNode.up();
- Boolean callSuper = ann.callSuper();
-
- if (!annotation.isExplicit("callSuper")) callSuper = null;
- if (!annotation.isExplicit("exclude")) excludes = null;
- if (!annotation.isExplicit("of")) includes = null;
-
- if (excludes != null && includes != null) {
- excludes = null;
- annotation.setWarning("exclude", "exclude and of are mutually exclusive; the 'exclude' parameter will be ignored.");
- }
-
- checkForBogusFieldNames(typeNode, annotation);
-
- return generateToString(typeNode, annotationNode, excludes, includes, ann.includeFieldNames(), callSuper, true);
- }
-
- public boolean generateToString(EclipseNode typeNode, EclipseNode errorNode, List<String> excludes, List<String> includes,
- boolean includeFieldNames, Boolean callSuper, boolean whineIfExists) {
- TypeDeclaration typeDecl = null;
-
- if (typeNode.get() instanceof TypeDeclaration) typeDecl = (TypeDeclaration) typeNode.get();
- int modifiers = typeDecl == null ? 0 : typeDecl.modifiers;
- boolean notAClass = (modifiers &
- (ClassFileConstants.AccInterface | ClassFileConstants.AccAnnotation | ClassFileConstants.AccEnum)) != 0;
-
- if (typeDecl == null || notAClass) {
- errorNode.addError("@ToString is only supported on a class.");
- return false;
- }
-
- if (callSuper == null) {
- try {
- callSuper = ((Boolean)ToString.class.getMethod("callSuper").getDefaultValue()).booleanValue();
- } catch (Exception ignore) {}
- }
-
- List<EclipseNode> nodesForToString = new ArrayList<EclipseNode>();
- if (includes != null) {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() != Kind.FIELD) continue;
- FieldDeclaration fieldDecl = (FieldDeclaration) child.get();
- if (includes.contains(new String(fieldDecl.name))) nodesForToString.add(child);
- }
- } else {
- for (EclipseNode child : typeNode.down()) {
- if (child.getKind() != Kind.FIELD) continue;
- FieldDeclaration fieldDecl = (FieldDeclaration) child.get();
- //Skip static fields.
- if ((fieldDecl.modifiers & ClassFileConstants.AccStatic) != 0) continue;
- //Skip excluded fields.
- if (excludes != null && excludes.contains(new String(fieldDecl.name))) continue;
- //Skip fields that start with $
- if (fieldDecl.name.length > 0 && fieldDecl.name[0] == '$') continue;
- nodesForToString.add(child);
- }
- }
-
- switch (methodExists("toString", typeNode)) {
- case NOT_EXISTS:
- MethodDeclaration toString = createToString(typeNode, nodesForToString, includeFieldNames, callSuper, errorNode.get());
- injectMethod(typeNode, toString);
- return true;
- case EXISTS_BY_LOMBOK:
- return true;
- default:
- case EXISTS_BY_USER:
- if (whineIfExists) {
- errorNode.addWarning("Not generating toString(): A method with that name already exists");
- }
- return true;
- }
- }
-
- private MethodDeclaration createToString(EclipseNode type, Collection<EclipseNode> fields,
- boolean includeFieldNames, boolean callSuper, ASTNode source) {
- TypeDeclaration typeDeclaration = (TypeDeclaration)type.get();
- char[] rawTypeName = typeDeclaration.name;
- String typeName = rawTypeName == null ? "" : new String(rawTypeName);
- char[] suffix = ")".toCharArray();
- String infixS = ", ";
- char[] infix = infixS.toCharArray();
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
- final int PLUS = OperatorIds.PLUS;
-
- char[] prefix;
-
- if (callSuper) {
- prefix = (typeName + "(super=").toCharArray();
- } else if (fields.isEmpty()) {
- prefix = (typeName + "()").toCharArray();
- } else if (includeFieldNames) {
- prefix = (typeName + "(" + new String(((FieldDeclaration)fields.iterator().next().get()).name) + "=").toCharArray();
- } else {
- prefix = (typeName + "(").toCharArray();
- }
-
- boolean first = true;
- Expression current = new StringLiteral(prefix, pS, pE, 0);
- Eclipse.setGeneratedBy(current, source);
-
- if (callSuper) {
- MessageSend callToSuper = new MessageSend();
- callToSuper.sourceStart = pS; callToSuper.sourceEnd = pE;
- Eclipse.setGeneratedBy(callToSuper, source);
- callToSuper.receiver = new SuperReference(pS, pE);
- Eclipse.setGeneratedBy(callToSuper, source);
- callToSuper.selector = "toString".toCharArray();
- current = new BinaryExpression(current, callToSuper, PLUS);
- Eclipse.setGeneratedBy(current, source);
- first = false;
- }
-
- for (EclipseNode field : fields) {
- FieldDeclaration f = (FieldDeclaration)field.get();
- if (f.name == null || f.type == null) continue;
-
- Expression ex;
- if (f.type.dimensions() > 0) {
- MessageSend arrayToString = new MessageSend();
- arrayToString.sourceStart = pS; arrayToString.sourceEnd = pE;
- arrayToString.receiver = generateQualifiedNameRef(source, TypeConstants.JAVA, TypeConstants.UTIL, "Arrays".toCharArray());
- arrayToString.arguments = new Expression[] { new SingleNameReference(f.name, p) };
- Eclipse.setGeneratedBy(arrayToString.arguments[0], source);
- if (f.type.dimensions() > 1 || !BUILT_IN_TYPES.contains(new String(f.type.getLastToken()))) {
- arrayToString.selector = "deepToString".toCharArray();
- } else {
- arrayToString.selector = "toString".toCharArray();
- }
- ex = arrayToString;
- } else {
- FieldReference thisX = new FieldReference(f.name, p);
- thisX.receiver = new ThisReference(source.sourceStart, source.sourceEnd);
- Eclipse.setGeneratedBy(thisX.receiver, source);
- ex = thisX;
- }
- Eclipse.setGeneratedBy(ex, source);
-
- if (first) {
- current = new BinaryExpression(current, ex, PLUS);
- current.sourceStart = pS; current.sourceEnd = pE;
- Eclipse.setGeneratedBy(current, source);
- first = false;
- continue;
- }
-
- StringLiteral fieldNameLiteral;
- if (includeFieldNames) {
- char[] namePlusEqualsSign = (infixS + new String(f.name) + "=").toCharArray();
- fieldNameLiteral = new StringLiteral(namePlusEqualsSign, pS, pE, 0);
- } else {
- fieldNameLiteral = new StringLiteral(infix, pS, pE, 0);
- }
- Eclipse.setGeneratedBy(fieldNameLiteral, source);
- current = new BinaryExpression(current, fieldNameLiteral, PLUS);
- Eclipse.setGeneratedBy(current, source);
- current = new BinaryExpression(current, ex, PLUS);
- Eclipse.setGeneratedBy(current, source);
- }
- if (!first) {
- StringLiteral suffixLiteral = new StringLiteral(suffix, pS, pE, 0);
- Eclipse.setGeneratedBy(suffixLiteral, source);
- current = new BinaryExpression(current, suffixLiteral, PLUS);
- Eclipse.setGeneratedBy(current, source);
- }
-
- ReturnStatement returnStatement = new ReturnStatement(current, pS, pE);
- Eclipse.setGeneratedBy(returnStatement, source);
-
- MethodDeclaration method = new MethodDeclaration(((CompilationUnitDeclaration) type.top().get()).compilationResult);
- Eclipse.setGeneratedBy(method, source);
- method.modifiers = toEclipseModifier(AccessLevel.PUBLIC);
- method.returnType = new QualifiedTypeReference(TypeConstants.JAVA_LANG_STRING, new long[] {p, p, p});
- Eclipse.setGeneratedBy(method.returnType, source);
- method.annotations = new Annotation[] {makeMarkerAnnotation(TypeConstants.JAVA_LANG_OVERRIDE, source)};
- method.arguments = null;
- method.selector = "toString".toCharArray();
- method.thrownExceptions = null;
- method.typeParameters = null;
- method.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG;
- method.bodyStart = method.declarationSourceStart = method.sourceStart = source.sourceStart;
- method.bodyEnd = method.declarationSourceEnd = method.sourceEnd = source.sourceEnd;
- method.statements = new Statement[] { returnStatement };
- return method;
- }
-
- private static final Set<String> BUILT_IN_TYPES = Collections.unmodifiableSet(new HashSet<String>(Arrays.asList(
- "byte", "short", "int", "long", "char", "boolean", "double", "float")));
-
- private NameReference generateQualifiedNameRef(ASTNode source, char[]... varNames) {
- int pS = source.sourceStart, pE = source.sourceEnd;
- long p = (long)pS << 32 | pE;
- NameReference ref;
- if (varNames.length > 1) ref = new QualifiedNameReference(varNames, new long[varNames.length], pS, pE);
- else ref = new SingleNameReference(varNames[0], p);
- Eclipse.setGeneratedBy(ref, source);
- return ref;
- }
-}
diff --git a/src/lombok/eclipse/handlers/package-info.java b/src/lombok/eclipse/handlers/package-info.java
deleted file mode 100644
index 062b73b3..00000000
--- a/src/lombok/eclipse/handlers/package-info.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright © 2009 Reinier Zwitserloot and Roel Spilker.
- *
- * 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.
- */
-
-/**
- * Contains the classes that implement the transformations for all of lombok's various features on the eclipse platform.
- */
-package lombok.eclipse.handlers;