changeset 2769:106b3075768e

Fix annotations on uses of a type variable
author jfranck
date Mon, 12 Jan 2015 12:41:41 +0100
parents 79e9ccb2ab25
children cdfdea4426ad
files src/jdk.compiler/share/classes/com/sun/tools/javac/code/TypeAnnotations.java test/tools/javac/processing/model/type/BasicAnnoTests.java
diffstat 2 files changed, 87 insertions(+), 33 deletions(-) [+]
line wrap: on
line diff
--- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/TypeAnnotations.java	Fri Jan 09 15:44:16 2015 +0100
+++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/TypeAnnotations.java	Mon Jan 12 12:41:41 2015 +0100
@@ -401,8 +401,7 @@
                 return rewriteArrayType((ArrayType)type, annotations, pos);
 
             if (type.hasTag(TypeTag.TYPEVAR)) {
-                // Nothing to do for type variables.
-                return type;
+                return type.annotatedType(onlyTypeAnnotations);
             } else if (type.getKind() == TypeKind.UNION) {
                 // There is a TypeKind, but no TypeTag.
                 JCTypeUnion tutree = (JCTypeUnion)typetree;
--- a/test/tools/javac/processing/model/type/BasicAnnoTests.java	Fri Jan 09 15:44:16 2015 +0100
+++ b/test/tools/javac/processing/model/type/BasicAnnoTests.java	Mon Jan 12 12:41:41 2015 +0100
@@ -38,6 +38,7 @@
 import java.lang.annotation.Target;
 import java.util.ArrayList;
 
+import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.NavigableMap;
@@ -59,6 +60,7 @@
 import javax.lang.model.type.TypeMirror;
 import javax.lang.model.type.TypeVariable;
 import javax.lang.model.type.WildcardType;
+import javax.lang.model.util.SimpleTypeVisitor6;
 import javax.lang.model.util.Types;
 import javax.tools.Diagnostic.Kind;
 
@@ -133,6 +135,7 @@
         Element elem;
         NavigableMap<Integer, AnnotationMirror> toBeFound;
         int count = 0;
+        Set<TypeMirror> seen = new HashSet<>();
 
         TestTypeScanner(Element elem, List<AnnotationMirror> tests, Types types) {
             super(types);
@@ -165,41 +168,53 @@
         Void scan(TypeMirror t, Void ignore) {
             if (t == null)
                 return DEFAULT_VALUE;
-            if (verbose)
-                out.println("scan " + count + ": " + t);
-            if (toBeFound.size() > 0) {
-                if (toBeFound.firstKey().equals(count)) {
-                    AnnotationMirror test = toBeFound.pollFirstEntry().getValue();
-                    String annoType = getAnnoType(test);
-                    AnnotationMirror anno = getAnnotation(t, annoType);
-                    if (anno == null) {
-                        error(elem, "annotation not found on " + count + ": " + t);
+
+            if (!seen.contains(t)) {
+                try {
+                    seen.add(t);
+                    if (verbose)
+                        out.println("scan " + count + ": " + t);
+                    if (toBeFound.size() > 0) {
+                        if (toBeFound.firstKey().equals(count)) {
+                            AnnotationMirror test = toBeFound.pollFirstEntry().getValue();
+                            String annoType = getAnnoType(test);
+                            AnnotationMirror anno = getAnnotation(t, annoType);
+                            if (anno == null) {
+                                error(elem, "annotation not found on " + count + ": " + t);
+                            } else {
+                                String v = getValue(anno, "value").toString();
+                                if (v.equals(getExpect(test))) {
+                                    out.println("found " + anno + " as expected");
+                                } else {
+                                    error(elem, "Unexpected value: " + v + ", expected: " + getExpect(test));
+                                }
+                            }
+                        } else if (count > toBeFound.firstKey()) {
+                            rescue();
+                        } else {
+                            List<? extends AnnotationMirror> annos = t.getAnnotationMirrors();
+                            if (annos.size() > 0) {
+                                for (AnnotationMirror a : annos)
+                                    error(elem, "annotation " + a + " found on " + count + ": " + t);
+                            }
+                        }
                     } else {
-                        String v = getValue(anno, "value").toString();
-                        if (v.equals(getExpect(test))) {
-                            out.println("found " + anno + " as expected");
-                        } else {
-                            error(elem, "Unexpected value: " + v + ", expected: " + getExpect(test));
+                        List<? extends AnnotationMirror> annos = t.getAnnotationMirrors();
+                        if (annos.size() > 0) {
+                            for (AnnotationMirror a : annos)
+                                error(elem, "annotation " + a + " found on " + count + ": " + t);
                         }
                     }
-                } else if (count > toBeFound.firstKey()) {
-                    rescue();
-                } else {
-                    List<? extends AnnotationMirror> annos = t.getAnnotationMirrors();
-                    if (annos.size() > 0) {
-                        for (AnnotationMirror a : annos)
-                            error(elem, "annotation " + a + " found on " + count + ": " + t);
-                    }
-                }
-            } else {
-                List<? extends AnnotationMirror> annos = t.getAnnotationMirrors();
-                if (annos.size() > 0) {
-                    for (AnnotationMirror a : annos)
-                        error(elem, "annotation " + a + " found on " + count + ": " + t);
+                    count++;
+                    return super.scan(t, ignore);
+
+                } finally {
+                    seen.remove(t);
                 }
             }
-            count++;
-            return super.scan(t, ignore);
+
+            return DEFAULT_VALUE;
+
         }
 
         private void rescue() {
@@ -517,4 +532,44 @@
 
     @Test(posn=1, annoType=TA.class, expect="23")
     public Set<@TA(23) ? super Object> f9;
-}
+
+    // Test type use annotations on uses of type variables
+    @Test(posn=5, annoType = TA.class, expect = "25")
+    @Test(posn=5, annoType = TB.class, expect = "26")
+    <T> void m6(@TA(25) @TB(26) T t) { }
+
+    class Inner7<T> {
+        @Test(posn=0, annoType = TA.class, expect = "30")
+        @Test(posn=0, annoType = TB.class, expect = "31")
+        @TA(30) @TB(31) T f;
+    }
+
+    // Test type use annotations on uses of type variables
+    @Test(posn=5, annoType = TB.class, expect = "41")
+    <@TA(40) T> void m7(@TB(41) T t) { }
+
+    class Inner8<@TA(50) T> {
+        @Test(posn=0, annoType = TB.class, expect = "51")
+        @TB(51) T f;
+    }
+
+    // Test type use annotations on uses of Class types
+    @Test(posn=5, annoType = TA.class, expect = "60")
+    @Test(posn=5, annoType = TB.class, expect = "61")
+    <T> void m60(@TA(60) @TB(61) String t) { }
+
+    class Inner70<T> {
+        @Test(posn=0, annoType = TA.class, expect = "70")
+        @Test(posn=0, annoType = TB.class, expect = "71")
+        @TA(70) @TB(71) String f;
+    }
+
+    // Test type use annotations on uses of type variables
+    @Test(posn=5, annoType = TB.class, expect = "81")
+    <@TA(80) T> void m80(@TB(81) String t) { }
+
+    class Inner90<@TA(90) T> {
+        @Test(posn=0, annoType = TB.class, expect = "91")
+        @TB(91) String f;
+    }
+}
\ No newline at end of file