diff options
9 files changed, 281 insertions, 10 deletions
diff --git a/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java b/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java index 7f144c17..96dea22d 100644 --- a/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java +++ b/src/core/lombok/eclipse/handlers/EclipseHandlerUtil.java @@ -1013,9 +1013,17 @@ public class EclipseHandlerUtil { parent.fields = new FieldDeclaration[1]; parent.fields[0] = field; } else { - FieldDeclaration[] newArray = new FieldDeclaration[parent.fields.length + 1]; - System.arraycopy(parent.fields, 0, newArray, 1, parent.fields.length); - newArray[0] = field; + int size = parent.fields.length; + FieldDeclaration[] newArray = new FieldDeclaration[size + 1]; + System.arraycopy(parent.fields, 0, newArray, 0, size); + int index = 0; + for (; index < size; index++) { + FieldDeclaration f = newArray[index]; + if (isEnumConstant(f) || isGenerated(f)) continue; + break; + } + System.arraycopy(newArray, index, newArray, index + 1, size - index); + newArray[index] = field; parent.fields = newArray; } @@ -1028,6 +1036,10 @@ public class EclipseHandlerUtil { type.add(field, Kind.FIELD); } + private static boolean isEnumConstant(final FieldDeclaration field) { + return ((field.initialization instanceof AllocationExpression) && (((AllocationExpression) field.initialization).enumConstant == field)); + } + /** * Inserts a method into an existing type. The type must represent a {@code TypeDeclaration}. */ diff --git a/src/core/lombok/javac/handlers/JavacHandlerUtil.java b/src/core/lombok/javac/handlers/JavacHandlerUtil.java index 00090be9..fc9435d8 100644 --- a/src/core/lombok/javac/handlers/JavacHandlerUtil.java +++ b/src/core/lombok/javac/handlers/JavacHandlerUtil.java @@ -532,11 +532,35 @@ public class JavacHandlerUtil { JCClassDecl type = (JCClassDecl) typeNode.get(); if (addSuppressWarnings) addSuppressWarningsAll(field.mods, typeNode, field.pos, getGeneratedBy(field)); - type.defs = type.defs.append(field); + + List<JCTree> insertAfter = null; + List<JCTree> insertBefore = type.defs; + while (insertBefore.tail != null) { + if (insertBefore.head instanceof JCVariableDecl) { + JCVariableDecl f = (JCVariableDecl) insertBefore.head; + if (isEnumConstant(f) || isGenerated(f)) { + insertAfter = insertBefore; + insertBefore = insertBefore.tail; + continue; + } + } + break; + } + List<JCTree> fieldEntry = List.<JCTree>of(field); + fieldEntry.tail = insertBefore; + if (insertAfter == null) { + type.defs = fieldEntry; + } else { + insertAfter.tail = fieldEntry; + } typeNode.add(field, Kind.FIELD); } + private static boolean isEnumConstant(final JCVariableDecl field) { + return (field.mods.flags & Flags.ENUM) != 0; + } + /** * Adds the given new method declaration to the provided type AST Node. * Can also inject constructors. diff --git a/test/transform/resource/after-delombok/InjectField.java b/test/transform/resource/after-delombok/InjectField.java new file mode 100644 index 00000000..a9b4b1c4 --- /dev/null +++ b/test/transform/resource/after-delombok/InjectField.java @@ -0,0 +1,59 @@ +import java.util.logging.Level; + +enum InjectField1 { + A, + B; + + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField1.class.getName()); + @java.lang.SuppressWarnings("all") + private final java.lang.Object $lock = new java.lang.Object[0]; + @java.lang.SuppressWarnings("all") + private static final java.lang.Object $LOCK = new java.lang.Object[0]; + + private static final String LOG_MESSAGE = "static initializer"; + + private String fieldA; + + static { + log.log(Level.FINE, LOG_MESSAGE); + } + + private String fieldB; + + void generateLockField() { + synchronized (this.$lock) { + System.out.println("lock field"); + } + } + + static void generateStaticLockField() { + synchronized (InjectField1.$LOCK) { + System.out.println("static lock field"); + } + } +} + +class InjectField2 { + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField2.class.getName()); + @java.lang.SuppressWarnings("all") + private final java.lang.Object $lock = new java.lang.Object[0]; + + private static final String LOG_MESSAGE = "static initializer"; + + static { + log.log(Level.FINE, LOG_MESSAGE); + } + + void generateLockField() { + synchronized (this.$lock) { + System.out.println("lock field"); + } + } +} + +class InjectField3 { + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField3.class.getName()); + static { + log.log(Level.FINE, "static initializer"); + } +}
\ No newline at end of file diff --git a/test/transform/resource/after-delombok/SynchronizedPlain.java b/test/transform/resource/after-delombok/SynchronizedPlain.java index 695a3089..1a065085 100644 --- a/test/transform/resource/after-delombok/SynchronizedPlain.java +++ b/test/transform/resource/after-delombok/SynchronizedPlain.java @@ -1,4 +1,6 @@ class SynchronizedPlain1 { + @java.lang.SuppressWarnings("all") + private final java.lang.Object $lock = new java.lang.Object[0]; void test() { synchronized (this.$lock) { System.out.println("one"); @@ -9,10 +11,10 @@ class SynchronizedPlain1 { System.out.println("two"); } } - @java.lang.SuppressWarnings("all") - private final java.lang.Object $lock = new java.lang.Object[0]; } class SynchronizedPlain2 { + @java.lang.SuppressWarnings("all") + private static final java.lang.Object $LOCK = new java.lang.Object[0]; static void test() { synchronized (SynchronizedPlain2.$LOCK) { System.out.println("three"); @@ -23,6 +25,4 @@ class SynchronizedPlain2 { System.out.println("four"); } } - @java.lang.SuppressWarnings("all") - private static final java.lang.Object $LOCK = new java.lang.Object[0]; }
\ No newline at end of file diff --git a/test/transform/resource/after-ecj/InjectField.java b/test/transform/resource/after-ecj/InjectField.java new file mode 100644 index 00000000..83d9e5fa --- /dev/null +++ b/test/transform/resource/after-ecj/InjectField.java @@ -0,0 +1,63 @@ +import java.util.logging.Level; +import lombok.extern.java.Log; +import lombok.Synchronized; +@Log enum InjectField1 { + A(), + B(), + private final java.lang.Object $lock = new java.lang.Object[0]; + private static final java.lang.Object $LOCK = new java.lang.Object[0]; + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField1.class.getName()); + private static final String LOG_MESSAGE = "static initializer"; + private String fieldA; + static { + log.log(Level.FINE, LOG_MESSAGE); + } + private String fieldB; + <clinit>() { + } + InjectField1() { + super(); + } + @Synchronized void generateLockField() { + synchronized (this.$lock) + { + System.out.println("lock field"); + } + } + static @Synchronized void generateStaticLockField() { + synchronized (InjectField1.$LOCK) + { + System.out.println("static lock field"); + } + } +} +@Log class InjectField2 { + private final java.lang.Object $lock = new java.lang.Object[0]; + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField2.class.getName()); + private static final String LOG_MESSAGE = "static initializer"; + static { + log.log(Level.FINE, LOG_MESSAGE); + } + <clinit>() { + } + InjectField2() { + super(); + } + @Synchronized void generateLockField() { + synchronized (this.$lock) + { + System.out.println("lock field"); + } + } +} +@Log class InjectField3 { + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField3.class.getName()); + static { + log.log(Level.FINE, "static initializer"); + } + <clinit>() { + } + InjectField3() { + super(); + } +} diff --git a/test/transform/resource/after-ecj/LoggerSlf4jTypes.java b/test/transform/resource/after-ecj/LoggerSlf4jTypes.java index faa77cd7..95ed1ebf 100644 --- a/test/transform/resource/after-ecj/LoggerSlf4jTypes.java +++ b/test/transform/resource/after-ecj/LoggerSlf4jTypes.java @@ -11,8 +11,8 @@ } } @lombok.extern.slf4j.Slf4j enum LoggerSlf4jTypesEnumWithElement { - private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LoggerSlf4jTypesEnumWithElement.class); FOO(), + private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LoggerSlf4jTypesEnumWithElement.class); <clinit>() { } LoggerSlf4jTypesEnumWithElement() { diff --git a/test/transform/resource/after-eclipse/InjectField.java b/test/transform/resource/after-eclipse/InjectField.java new file mode 100644 index 00000000..83d9e5fa --- /dev/null +++ b/test/transform/resource/after-eclipse/InjectField.java @@ -0,0 +1,63 @@ +import java.util.logging.Level; +import lombok.extern.java.Log; +import lombok.Synchronized; +@Log enum InjectField1 { + A(), + B(), + private final java.lang.Object $lock = new java.lang.Object[0]; + private static final java.lang.Object $LOCK = new java.lang.Object[0]; + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField1.class.getName()); + private static final String LOG_MESSAGE = "static initializer"; + private String fieldA; + static { + log.log(Level.FINE, LOG_MESSAGE); + } + private String fieldB; + <clinit>() { + } + InjectField1() { + super(); + } + @Synchronized void generateLockField() { + synchronized (this.$lock) + { + System.out.println("lock field"); + } + } + static @Synchronized void generateStaticLockField() { + synchronized (InjectField1.$LOCK) + { + System.out.println("static lock field"); + } + } +} +@Log class InjectField2 { + private final java.lang.Object $lock = new java.lang.Object[0]; + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField2.class.getName()); + private static final String LOG_MESSAGE = "static initializer"; + static { + log.log(Level.FINE, LOG_MESSAGE); + } + <clinit>() { + } + InjectField2() { + super(); + } + @Synchronized void generateLockField() { + synchronized (this.$lock) + { + System.out.println("lock field"); + } + } +} +@Log class InjectField3 { + private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(InjectField3.class.getName()); + static { + log.log(Level.FINE, "static initializer"); + } + <clinit>() { + } + InjectField3() { + super(); + } +} diff --git a/test/transform/resource/after-eclipse/LoggerSlf4jTypes.java b/test/transform/resource/after-eclipse/LoggerSlf4jTypes.java index faa77cd7..95ed1ebf 100644 --- a/test/transform/resource/after-eclipse/LoggerSlf4jTypes.java +++ b/test/transform/resource/after-eclipse/LoggerSlf4jTypes.java @@ -11,8 +11,8 @@ } } @lombok.extern.slf4j.Slf4j enum LoggerSlf4jTypesEnumWithElement { - private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LoggerSlf4jTypesEnumWithElement.class); FOO(), + private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LoggerSlf4jTypesEnumWithElement.class); <clinit>() { } LoggerSlf4jTypesEnumWithElement() { diff --git a/test/transform/resource/before/InjectField.java b/test/transform/resource/before/InjectField.java new file mode 100644 index 00000000..e81cbc5a --- /dev/null +++ b/test/transform/resource/before/InjectField.java @@ -0,0 +1,50 @@ +import java.util.logging.Level; +import lombok.extern.java.Log; +import lombok.Synchronized; + +@Log +enum InjectField1 { + A, + B; + + private static final String LOG_MESSAGE = "static initializer"; + + private String fieldA; + + static { + log.log(Level.FINE, LOG_MESSAGE); + } + + private String fieldB; + + @Synchronized + void generateLockField() { + System.out.println("lock field"); + } + + @Synchronized + static void generateStaticLockField() { + System.out.println("static lock field"); + } +} + +@Log +class InjectField2 { + private static final String LOG_MESSAGE = "static initializer"; + + static { + log.log(Level.FINE, LOG_MESSAGE); + } + + @Synchronized + void generateLockField() { + System.out.println("lock field"); + } +} + +@Log +class InjectField3 { + static { + log.log(Level.FINE, "static initializer"); + } +}
\ No newline at end of file |