changeset 2275:0b7e49fa5f26

Fix for "AssertionError at com.sun.tools.javac.code.Type$AnnotatedType.<init>" bug report from Feb. 25 2013 by Steve Sides. There must be a nicer fix, but I didn't find it without breaking other tests.
author wmdietl
date Fri, 01 Mar 2013 11:07:16 -0800
parents 20cb3559e19c
children cc7184b9aa57
files src/share/classes/com/sun/tools/javac/code/TypeAnnotations.java
diffstat 1 files changed, 36 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/src/share/classes/com/sun/tools/javac/code/TypeAnnotations.java	Thu Feb 28 14:36:32 2013 -0800
+++ b/src/share/classes/com/sun/tools/javac/code/TypeAnnotations.java	Fri Mar 01 11:07:16 2013 -0800
@@ -272,6 +272,10 @@
             sym.annotations.reset();
             sym.annotations.setDeclarationAttributes(declAnnos.toList());
 
+            if (typeAnnos.isEmpty()) {
+                return;
+            }
+
             List<Attribute.TypeCompound> typeAnnotations = typeAnnos.toList();
 
             if (type == null) {
@@ -282,6 +286,11 @@
                 return;
             }
 
+            if (leftmostTypeAnnotationsEqual(type, typeAnnotations)) {
+                // TODO: hackish - see comment with called method.
+                return;
+            }
+
             // type is non-null and annotations are added to that type
             type = typeWithAnnotations(typetree, type, typeAnnotations, log);
 
@@ -307,6 +316,33 @@
             }
         }
 
+        // For a class declarations within an anonymous class
+        // declaration the body has been visited before.
+        // Don't try to annotate the type again, which would crash.
+        // This happens for type annotations that are also declaration
+        // annotations - they will appear in sym.getRawAttributes()
+        // and then because they are kind BOTH will be type and
+        // declaration annotations.
+        // TODO: find a nicer solution - not visiting the declaration twice.
+        // However, I didn't manage without breaking other test cases.
+        private static boolean leftmostTypeAnnotationsEqual(Type type, List<Attribute.TypeCompound> typeAnnotations) {
+            Type leftmost = type;
+            while (true) {
+                if (leftmost.getKind() == TypeKind.ARRAY) {
+                    leftmost = leftmost.unannotatedType();
+                    leftmost = ((ArrayType)leftmost).getComponentType();
+                } else if (leftmost.getKind() == TypeKind.DECLARED &&
+                        leftmost.getEnclosingType() != null &&
+                        leftmost.getEnclosingType().getKind() == TypeKind.DECLARED) {
+                    leftmost = leftmost.getEnclosingType();
+                } else {
+                    break;
+                }
+            }
+            // Comparing the length is enough to notice duplicate calls.
+            return leftmost.getAnnotationMirrors().length() == typeAnnotations.length();
+        }
+
         // This method has a similar purpose as
         // {@link com.sun.tools.javac.parser.JavacParser.insertAnnotationsToMostInner(JCExpression, List<JCTypeAnnotation>, boolean)}
         // We found a type annotation in a declaration annotation position,