BasicAnnoTests.java revision 2877:62e285806e83
1275970Scy/* 2275970Scy * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved. 3275970Scy * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4275970Scy * 5275970Scy * This code is free software; you can redistribute it and/or modify it 6275970Scy * under the terms of the GNU General Public License version 2 only, as 7275970Scy * published by the Free Software Foundation. 8275970Scy * 9275970Scy * This code is distributed in the hope that it will be useful, but WITHOUT 10275970Scy * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11275970Scy * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12275970Scy * version 2 for more details (a copy is included in the LICENSE file that 13275970Scy * accompanied this code). 14275970Scy * 15275970Scy * You should have received a copy of the GNU General Public License version 16275970Scy * 2 along with this work; if not, write to the Free Software Foundation, 17275970Scy * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18275970Scy * 19275970Scy * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20275970Scy * or visit www.oracle.com if you need additional information or have any 21275970Scy * questions. 22275970Scy */ 23275970Scy 24275970Scy/* 25275970Scy * @test 26275970Scy * @bug 8013852 8031744 27275970Scy * @summary Annotations on types 28275970Scy * @library /tools/javac/lib 29275970Scy * @build JavacTestingAbstractProcessor DPrinter BasicAnnoTests 30275970Scy * @compile/process -processor BasicAnnoTests -proc:only BasicAnnoTests.java 31275970Scy */ 32275970Scy 33275970Scyimport java.io.PrintWriter; 34275970Scyimport java.io.Serializable; 35275970Scyimport java.lang.annotation.Annotation; 36275970Scyimport java.lang.annotation.ElementType; 37275970Scyimport java.lang.annotation.Repeatable; 38275970Scyimport java.lang.annotation.Target; 39275970Scyimport java.util.ArrayList; 40275970Scy 41275970Scyimport java.util.HashSet; 42275970Scyimport java.util.List; 43275970Scyimport java.util.Map; 44275970Scyimport java.util.NavigableMap; 45275970Scyimport java.util.Set; 46275970Scyimport java.util.TreeMap; 47275970Scy 48275970Scyimport javax.annotation.processing.ProcessingEnvironment; 49275970Scyimport javax.annotation.processing.RoundEnvironment; 50275970Scyimport javax.lang.model.AnnotatedConstruct; 51275970Scyimport javax.lang.model.element.AnnotationMirror; 52275970Scyimport javax.lang.model.element.AnnotationValue; 53275970Scyimport javax.lang.model.element.Element; 54275970Scyimport javax.lang.model.element.ExecutableElement; 55275970Scyimport javax.lang.model.element.TypeElement; 56275970Scyimport javax.lang.model.type.ArrayType; 57275970Scyimport javax.lang.model.type.DeclaredType; 58275970Scyimport javax.lang.model.type.ExecutableType; 59275970Scyimport javax.lang.model.type.IntersectionType; 60275970Scyimport javax.lang.model.type.TypeMirror; 61275970Scyimport javax.lang.model.type.TypeVariable; 62275970Scyimport javax.lang.model.type.WildcardType; 63275970Scyimport javax.lang.model.util.Types; 64275970Scyimport javax.tools.Diagnostic.Kind; 65275970Scy 66275970Scyimport com.sun.tools.javac.code.Attribute; 67275970Scyimport com.sun.tools.javac.code.Symbol; 68275970Scyimport com.sun.tools.javac.processing.JavacProcessingEnvironment; 69275970Scyimport com.sun.tools.javac.util.Name; 70275970Scy 71275970Scyimport static com.sun.tools.javac.code.Attribute.Array; 72275970Scyimport static com.sun.tools.javac.code.Attribute.Constant; 73275970Scyimport static com.sun.tools.javac.code.Attribute.Compound; 74275970Scy 75275970Scy/** 76275970Scy * The test scans this file looking for test cases annotated with @Test. 77275970Scy */ 78275970Scypublic class BasicAnnoTests extends JavacTestingAbstractProcessor { 79275970Scy DPrinter dprinter; 80275970Scy PrintWriter out; 81275970Scy boolean verbose = true; 82275970Scy 83275970Scy @Override 84275970Scy public void init(ProcessingEnvironment pEnv) { 85275970Scy super.init(pEnv); 86275970Scy dprinter = new DPrinter(((JavacProcessingEnvironment) pEnv).getContext()); 87275970Scy out = dprinter.out; 88275970Scy } 89275970Scy 90275970Scy @Override 91275970Scy public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) { 92275970Scy TestElementScanner s = new TestElementScanner(); 93275970Scy for (Element e: roundEnv.getRootElements()) { 94275970Scy s.scan(e, null); 95275970Scy } 96275970Scy return true; 97275970Scy } 98275970Scy 99275970Scy void error(Element e, String msg) { 100275970Scy messager.printMessage(Kind.ERROR, msg, e); 101275970Scy errors++; 102275970Scy } 103275970Scy 104275970Scy int errors; 105275970Scy 106275970Scy /** 107275970Scy * Scan an element looking for declarations annotated with @Test. 108275970Scy * Run a TestTypeScanner on the annotations that are found. 109275970Scy */ 110275970Scy class TestElementScanner extends ElementScanner<Void,Void> { 111275970Scy public Void scan(Element elem, Void ignore) { 112275970Scy List<AnnotationMirror> tests = new ArrayList<>(); 113275970Scy AnnotationMirror test = getAnnotation(elem, Test.class.getName().replace('$', '.')); 114275970Scy if (test != null) { 115275970Scy tests.add(test); 116275970Scy } 117275970Scy tests.addAll(getAnnotations(elem, Tests.class.getName().replace('$', '.'))); 118275970Scy 119275970Scy if (tests.size() > 0) { 120275970Scy out.println("Test: " + elem + " " + test); 121275970Scy TestTypeScanner s = new TestTypeScanner(elem, tests, types); 122275970Scy s.test(elem.asType()); 123275970Scy out.println(); 124275970Scy } 125275970Scy return super.scan(elem, ignore); 126275970Scy } 127275970Scy } 128275970Scy 129275970Scy /** 130275970Scy * Scan the type of an element, looking for an annotation 131275970Scy * to match the expected annotation specified in the @Test annotation. 132275970Scy */ 133275970Scy class TestTypeScanner extends TypeScanner<Void, Void> { 134275970Scy Element elem; 135275970Scy NavigableMap<Integer, AnnotationMirror> toBeFound; 136275970Scy int count = 0; 137275970Scy Set<TypeMirror> seen = new HashSet<>(); 138275970Scy 139275970Scy TestTypeScanner(Element elem, List<AnnotationMirror> tests, Types types) { 140275970Scy super(types); 141275970Scy this.elem = elem; 142275970Scy 143275970Scy NavigableMap<Integer, AnnotationMirror> testByPos = new TreeMap<>(); 144275970Scy for (AnnotationMirror test : tests) { 145275970Scy for (int pos : getPosn(test)) { 146275970Scy testByPos.put(pos, test); 147275970Scy } 148275970Scy } 149275970Scy this.toBeFound = testByPos; 150275970Scy } 151275970Scy 152275970Scy public void test(TypeMirror t) { 153275970Scy scan(t, null); 154275970Scy } 155275970Scy 156275970Scy @Override 157275970Scy Void scan(TypeMirror t, Void ignore) { 158275970Scy if (t == null) 159275970Scy return DEFAULT_VALUE; 160275970Scy 161275970Scy if (!seen.contains(t)) { 162275970Scy try { 163275970Scy seen.add(t); 164275970Scy if (verbose) 165275970Scy out.println("scan " + count + ": " + t); 166275970Scy if (toBeFound.size() > 0) { 167275970Scy if (toBeFound.firstKey().equals(count)) { 168275970Scy AnnotationMirror test = toBeFound.pollFirstEntry().getValue(); 169275970Scy String annoType = getAnnoType(test); 170275970Scy AnnotationMirror anno = getAnnotation(t, annoType); 171275970Scy if (anno == null) { 172275970Scy error(elem, "annotation not found on " + count + ": " + t); 173275970Scy } else { 174275970Scy String v = getValue(anno, "value").toString(); 175275970Scy if (v.equals(getExpect(test))) { 176275970Scy out.println("found " + anno + " as expected"); 177275970Scy } else { 178275970Scy error(elem, "Unexpected value: " + v + ", expected: " + getExpect(test)); 179275970Scy } 180275970Scy } 181275970Scy } else if (count > toBeFound.firstKey()) { 182275970Scy rescue(); 183275970Scy } else { 184275970Scy List<? extends AnnotationMirror> annos = t.getAnnotationMirrors(); 185275970Scy if (annos.size() > 0) { 186275970Scy for (AnnotationMirror a : annos) 187275970Scy error(elem, "annotation " + a + " found on " + count + ": " + t); 188275970Scy } 189275970Scy } 190275970Scy } else { 191275970Scy List<? extends AnnotationMirror> annos = t.getAnnotationMirrors(); 192275970Scy if (annos.size() > 0) { 193275970Scy for (AnnotationMirror a : annos) 194275970Scy error(elem, "annotation " + a + " found on " + count + ": " + t); 195275970Scy } 196275970Scy } 197275970Scy count++; 198275970Scy return super.scan(t, ignore); 199275970Scy 200275970Scy } finally { 201275970Scy seen.remove(t); 202275970Scy } 203275970Scy } 204275970Scy 205275970Scy return DEFAULT_VALUE; 206275970Scy 207275970Scy } 208275970Scy 209275970Scy private void rescue() { 210275970Scy while (toBeFound.size() > 0 && toBeFound.firstKey() >= count) 211275970Scy toBeFound.pollFirstEntry(); 212275970Scy } 213275970Scy } 214275970Scy 215275970Scy /** Get the position value from an element annotated with a @Test annotation mirror. */ 216275970Scy static int[] getPosn(Element elem) { 217275970Scy return elem.getAnnotation(Test.class).posn(); 218275970Scy } 219275970Scy 220275970Scy /** Get the position value from a @Test annotation mirror. */ 221275970Scy static Integer[] getPosn(AnnotationMirror test) { 222275970Scy AnnotationValue v = getValue(test, "posn"); 223275970Scy Object value = v.getValue(); 224275970Scy Integer i = 0; 225275970Scy if (value instanceof Constant) { 226275970Scy i = (Integer)((Constant)value).getValue(); 227275970Scy Integer[] res = new Integer[1]; 228275970Scy res[0] = i; 229275970Scy return res; 230275970Scy } else if (value instanceof List) { 231275970Scy List<Constant> l = (List<Constant>)value; 232275970Scy Integer[] res = new Integer[l.size()]; 233275970Scy for (int c = 0; c < l.size(); c++) { 234275970Scy res[c] = (Integer)l.get(c).getValue(); 235275970Scy } 236275970Scy return res; 237275970Scy } 238275970Scy return null; 239275970Scy } 240275970Scy 241275970Scy /** Get the expect value from an @Test annotation mirror. */ 242275970Scy static String getExpect(AnnotationMirror test) { 243275970Scy AnnotationValue v = getValue(test, "expect"); 244275970Scy return (String) v.getValue(); 245275970Scy } 246275970Scy 247275970Scy /** Get the annoType value from an @Test annotation mirror. */ 248275970Scy static String getAnnoType(AnnotationMirror test) { 249275970Scy AnnotationValue v = getValue(test, "annoType"); 250275970Scy TypeMirror m = (TypeMirror) v.getValue(); 251275970Scy return m.toString(); 252275970Scy } 253275970Scy 254275970Scy /** 255275970Scy * Get a specific annotation mirror from an annotated construct. 256275970Scy */ 257275970Scy static AnnotationMirror getAnnotation(AnnotatedConstruct e, String name) { 258275970Scy for (AnnotationMirror m: e.getAnnotationMirrors()) { 259275970Scy TypeElement te = (TypeElement) m.getAnnotationType().asElement(); 260275970Scy if (te.getQualifiedName().contentEquals(name)) { 261275970Scy return m; 262275970Scy } 263275970Scy } 264275970Scy return null; 265275970Scy } 266275970Scy 267275970Scy static List<AnnotationMirror> getAnnotations(Element e, String name) { 268275970Scy Name valueName = ((Symbol)e).getSimpleName().table.names.value; 269275970Scy List<AnnotationMirror> res = new ArrayList<>(); 270275970Scy 271275970Scy for (AnnotationMirror m : e.getAnnotationMirrors()) { 272275970Scy TypeElement te = (TypeElement) m.getAnnotationType().asElement(); 273275970Scy if (te.getQualifiedName().contentEquals(name)) { 274275970Scy Compound theAnno = (Compound)m; 275275970Scy Array valueArray = (Array)theAnno.member(valueName); 276275970Scy for (Attribute a : valueArray.getValue()) { 277275970Scy AnnotationMirror theMirror = (AnnotationMirror) a; 278275970Scy 279275970Scy res.add(theMirror); 280275970Scy } 281275970Scy } 282275970Scy } 283275970Scy return res; 284275970Scy } 285275970Scy 286275970Scy /** 287275970Scy * Get a specific value from an annotation mirror. 288275970Scy */ 289275970Scy static AnnotationValue getValue(AnnotationMirror anno, String name) { 290275970Scy Map<? extends ExecutableElement, ? extends AnnotationValue> map = anno.getElementValues(); 291275970Scy for (Map.Entry<? extends ExecutableElement, ? extends AnnotationValue> e: map.entrySet()) { 292275970Scy if (e.getKey().getSimpleName().contentEquals(name)) { 293275970Scy return e.getValue(); 294275970Scy } 295275970Scy } 296275970Scy return null; 297275970Scy } 298275970Scy 299275970Scy /** 300275970Scy * The Language Model API does not provide a type scanner, so provide 301275970Scy * one sufficient for our needs. 302275970Scy */ 303275970Scy static class TypeScanner<R, P> extends SimpleTypeVisitor<R, P> { 304275970Scy private Types types; 305275970Scy 306275970Scy public TypeScanner(Types types) { 307275970Scy super(); 308275970Scy this.types = types; 309275970Scy } 310275970Scy 311275970Scy @Override 312275970Scy public R visitArray(ArrayType t, P p) { 313275970Scy scan(t.getComponentType(), p); 314275970Scy return super.visitArray(t, p); 315275970Scy } 316275970Scy 317275970Scy @Override 318275970Scy public R visitExecutable(ExecutableType t, P p) { 319275970Scy //out.println(" type parameters: " + t.getTypeVariables()); 320275970Scy scan(t.getTypeVariables(), p); 321275970Scy //out.println(" return: " + t.getReturnType()); 322275970Scy scan(t.getReturnType(), p); 323275970Scy //out.println(" receiver: " + t.getReceiverTypes()); 324275970Scy scan(t.getReceiverType()); 325275970Scy //out.println(" params: " + t.getParameterTypes()); 326275970Scy scan(t.getParameterTypes(), p); 327275970Scy //out.println(" throws: " + t.getThrownTypes()); 328275970Scy scan(t.getThrownTypes(), p); 329275970Scy return super.visitExecutable(t, p); 330275970Scy } 331275970Scy 332275970Scy @Override 333275970Scy public R visitDeclared(DeclaredType t, P p) { 334275970Scy scan(t.getTypeArguments(), p); 335275970Scy // don't scan enclosing 336275970Scy scan(types.directSupertypes(t), p); 337275970Scy return super.visitDeclared(t, p); 338275970Scy } 339275970Scy 340275970Scy @Override 341275970Scy public R visitIntersection(IntersectionType t, P p) { 342275970Scy scan(t.getBounds(), p); 343275970Scy return super.visitIntersection(t, p); 344275970Scy } 345275970Scy 346275970Scy @Override 347275970Scy public R visitTypeVariable(TypeVariable t, P p) { 348275970Scy scan(t.getLowerBound(), p); 349275970Scy scan(t.getUpperBound(), p); 350275970Scy return super.visitTypeVariable(t, p); 351275970Scy } 352275970Scy 353275970Scy @Override 354275970Scy public R visitWildcard(WildcardType t, P p) { 355275970Scy scan(t.getExtendsBound(), p); 356275970Scy scan(t.getSuperBound(), p); 357275970Scy return super.visitWildcard(t, p); 358275970Scy } 359275970Scy 360275970Scy R scan(TypeMirror t) { 361275970Scy return scan(t, null); 362275970Scy } 363275970Scy 364275970Scy R scan(TypeMirror t, P p) { 365275970Scy return (t == null) ? DEFAULT_VALUE : t.accept(this, p); 366275970Scy } 367275970Scy 368275970Scy R scan(Iterable<? extends TypeMirror> iter, P p) { 369275970Scy if (iter == null) 370275970Scy return DEFAULT_VALUE; 371275970Scy R result = DEFAULT_VALUE; 372275970Scy for (TypeMirror t: iter) 373275970Scy result = scan(t, p); 374275970Scy return result; 375275970Scy } 376275970Scy } 377275970Scy 378275970Scy /** Annotation to identify test cases. */ 379275970Scy @Repeatable(Tests.class) 380275970Scy @interface Test { 381275970Scy /** Where to look for the annotation, expressed as a scan index. */ 382275970Scy int[] posn(); 383275970Scy /** The annotation to look for. */ 384275970Scy Class<? extends Annotation> annoType(); 385275970Scy /** The string representation of the annotation's value. */ 386275970Scy String expect(); 387275970Scy } 388275970Scy 389275970Scy @interface Tests { 390275970Scy Test[] value(); 391275970Scy } 392275970Scy 393275970Scy /** Type annotation to use in test cases. */ 394275970Scy @Target(ElementType.TYPE_USE) 395275970Scy public @interface TA { 396275970Scy int value(); 397275970Scy } 398275970Scy @Target(ElementType.TYPE_USE) 399275970Scy public @interface TB { 400275970Scy int value(); 401275970Scy } 402275970Scy 403275970Scy // Test cases 404275970Scy 405275970Scy // TODO: add more cases for arrays 406275970Scy // all annotated 407275970Scy // all but one annotated 408275970Scy // vary position of one not annotated 409275970Scy // only one annotated 410275970Scy // vary position of one annotated 411275970Scy // the three above with the corner case of the ambiguos decl + type anno added 412275970Scy 413275970Scy @Test(posn=0, annoType=TA.class, expect="1") 414275970Scy public @TA(1) int f1; 415275970Scy 416275970Scy @Test(posn=0, annoType=TA.class, expect="11") 417275970Scy @TA(11) public int f11; 418275970Scy 419275970Scy @Test(posn=1, annoType=TA.class, expect="111") 420275970Scy @TA(111) public int [] f111; 421275970Scy 422275970Scy @Test(posn=1, annoType=TA.class, expect="1120") 423275970Scy @Test(posn=0, annoType=TB.class, expect="1121") 424275970Scy @TA(1120) public int @TB(1121) [] f112; 425275970Scy 426275970Scy @Test(posn=0, annoType=TB.class, expect="11211") 427275970Scy @Test(posn=1, annoType=TA.class, expect="11200") 428275970Scy public @TA(11200) int @TB(11211) [] f112b; 429275970Scy 430275970Scy @Test(posn=1, annoType=TB.class, expect="1131") 431275970Scy @Test(posn=2, annoType=TA.class, expect="1130") 432275970Scy @TA(1130) public int [] @TB(1131) [] f113; 433275970Scy 434275970Scy @Test(posn=5, annoType=TA.class, expect="12") 435275970Scy public @TA(12) int [] [] [] [] [] f12; 436275970Scy 437275970Scy @Test(posn=6, annoType=TA.class, expect="13") 438275970Scy public @TA(13) int [] [] [] [] [] [] f13; 439275970Scy 440275970Scy @Test(posn=7, annoType=TA.class, expect="14") 441275970Scy @TA(14) public int [] [] [] [] [] [] [] f14; 442275970Scy 443275970Scy @Test(posn=6, annoType=TA.class, expect="150") 444275970Scy @Test(posn=7, annoType=TB.class, expect="151") 445275970Scy @TB(151) public int [] [] [] [] [] [] @TA(150) [] f15; 446275970Scy 447275970Scy @Test(posn=0, annoType=TB.class, expect="1511") 448275970Scy @Test(posn=3, annoType=TA.class, expect="1512") 449275970Scy @Test(posn=6, annoType=TA.class, expect="150") 450275970Scy @Test(posn=7, annoType=TB.class, expect="151") 451275970Scy @TB(151) public int @TB(1511) [] [] [] @TA(1512) [] [] [] @TA(150) [] f15b; 452275970Scy 453275970Scy @Test(posn=0, annoType=TB.class, expect="1521") 454275970Scy @Test(posn=3, annoType=TA.class, expect="1522") 455275970Scy @Test(posn=6, annoType=TA.class, expect="152") 456275970Scy public int @TB(1521) [] [] [] @TA(1522) [] [] [] @TA(152) [] f15c; 457275970Scy 458275970Scy @Test(posn=5, annoType=TA.class, expect="160") 459275970Scy @Test(posn=6, annoType=TB.class, expect="161") 460275970Scy public int [] [] [] [] [] @TA(160) [] @TB(161) [] f16; 461275970Scy 462275970Scy @Test(posn=0, annoType=TA.class, expect="2") 463275970Scy public int @TA(2) [] f2; 464275970Scy 465275970Scy @Test(posn=0, annoType=TB.class, expect="33") 466275970Scy @Test(posn=1, annoType=TA.class, expect="3") 467275970Scy public @TA(3) int @TB(33) [] f3; 468275970Scy 469275970Scy @Test(posn=2, annoType=TA.class, expect="4") 470275970Scy public int m1(@TA(4) float a) throws Exception { return 0; } 471275970Scy 472275970Scy @Test(posn=1, annoType=TA.class, expect="5") 473275970Scy public @TA(5) int m2(float a) throws Exception { return 0; } 474275970Scy 475275970Scy @Test(posn=3, annoType=TA.class, expect="6") 476275970Scy public int m3(float a) throws @TA(6) Exception { return 0; } 477275970Scy 478275970Scy // Also tests that a decl anno on a typevar doesn't show up on the Type 479275970Scy @Test(posn=7, annoType=TA.class, expect="8") 480275970Scy public <@TA(7) M> M m4(@TA(8) float a) throws Exception { return null; } 481275970Scy 482275970Scy // Also tests that a decl anno on a typevar doesn't show up on the Type 483275970Scy @Test(posn=4, annoType=TA.class, expect="10") 484275970Scy public class Inner1<@TA(9) S> extends @TA(10) Object implements Cloneable {} 485275970Scy 486275970Scy // Also tests that a decl anno on a typevar doesn't show up on the Type 487275970Scy @Test(posn=5, annoType=TA.class, expect="12") 488275970Scy public class Inner2<@TA(11) S> extends Object implements @TA(12) Cloneable {} 489275970Scy 490275970Scy @Test(posn={3,6}, annoType=TA.class, expect="13") 491275970Scy public <M extends @TA(13) Object> M m5(float a) { return null; } 492275970Scy 493275970Scy @Test(posn=3, annoType=TA.class, expect="14") 494275970Scy public class Inner3<QQQ extends @TA(14) Map> {} 495275970Scy 496275970Scy @Test(posn=4, annoType=TA.class, expect="15") 497275970Scy public class Inner4<T extends @TA(15) Object & Cloneable & Serializable> {} 498275970Scy 499275970Scy @Test(posn=5, annoType=TA.class, expect="16") 500275970Scy public class Inner5<T extends Object & @TA(16) Cloneable & Serializable> {} 501275970Scy 502275970Scy @Test(posn=7, annoType=TA.class, expect="17") 503275970Scy public class Inner6<T extends Object & Cloneable & @TA(17) Serializable> {} 504275970Scy 505275970Scy // Test annotated bounds 506275970Scy 507275970Scy @Test(posn=1, annoType=TA.class, expect="18") 508275970Scy public Set<@TA(18) ? extends Object> f4; 509275970Scy 510275970Scy @Test(posn=2, annoType=TA.class, expect="19") 511275970Scy public Set<? extends @TA(19) Object> f5; 512275970Scy 513275970Scy @Test(posn=3, annoType=TA.class, expect="20") 514275970Scy public Set<? extends Set<@TA(20) ? extends Object>> f6; 515275970Scy 516275970Scy @Test(posn=4, annoType=TA.class, expect="21") 517275970Scy public Set<? extends Set<? extends @TA(21) Object>> f7; 518275970Scy 519275970Scy @Test(posn=1, annoType=TA.class, expect="22") 520275970Scy public Set<@TA(22) ?> f8; 521275970Scy 522275970Scy @Test(posn=1, annoType=TA.class, expect="23") 523275970Scy public Set<@TA(23) ? super Object> f9; 524275970Scy 525275970Scy // Test type use annotations on uses of type variables 526275970Scy @Test(posn=5, annoType = TA.class, expect = "25") 527275970Scy @Test(posn=5, annoType = TB.class, expect = "26") 528275970Scy <T> void m6(@TA(25) @TB(26) T t) { } 529275970Scy 530275970Scy class Inner7<T> { 531275970Scy @Test(posn=0, annoType = TA.class, expect = "30") 532275970Scy @Test(posn=0, annoType = TB.class, expect = "31") 533275970Scy @TA(30) @TB(31) T f; 534275970Scy } 535275970Scy 536275970Scy // Test type use annotations on uses of type variables 537275970Scy @Test(posn=5, annoType = TB.class, expect = "41") 538275970Scy <@TA(40) T> void m7(@TB(41) T t) { } 539275970Scy 540275970Scy class Inner8<@TA(50) T> { 541275970Scy @Test(posn=0, annoType = TB.class, expect = "51") 542275970Scy @TB(51) T f; 543275970Scy } 544275970Scy 545275970Scy // Test type use annotations on uses of Class types 546275970Scy @Test(posn=5, annoType = TA.class, expect = "60") 547275970Scy @Test(posn=5, annoType = TB.class, expect = "61") 548275970Scy <T> void m60(@TA(60) @TB(61) String t) { } 549275970Scy 550275970Scy class Inner70<T> { 551275970Scy @Test(posn=0, annoType = TA.class, expect = "70") 552275970Scy @Test(posn=0, annoType = TB.class, expect = "71") 553275970Scy @TA(70) @TB(71) String f; 554275970Scy } 555275970Scy 556275970Scy // Test type use annotations on uses of type variables 557275970Scy @Test(posn=5, annoType = TB.class, expect = "81") 558275970Scy <@TA(80) T> void m80(@TB(81) String t) { } 559275970Scy 560275970Scy class Inner90<@TA(90) T> { 561275970Scy @Test(posn=0, annoType = TB.class, expect = "91") 562275970Scy @TB(91) String f; 563275970Scy } 564275970Scy 565275970Scy // Recursive bound 566275970Scy @Test(posn=4, annoType = TB.class, expect = "100") 567275970Scy class Inner100<T extends Inner100<@TB(100) T>> { 568275970Scy } 569275970Scy} 570275970Scy