RepeatingTypeAnnotations.java revision 2628:8df25ec8c930
1/*
2 * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24/*
25 * @test
26 * @bug 8005220
27 * @summary javap must display repeating annotations
28 * @ignore 8057687 emit correct byte code an attributes for type annotations
29 */
30import java.io.*;
31import java.util.*;
32
33/**
34 * This class extends the abstract {@link Tester} test-driver, and
35 * encapusulates a number of test-case classes (i.e. classes extending
36 * this class and annotated with {@code TestCase}).
37 * <p>
38 * By default (no argument), this test runs all test-cases, except
39 * if annotated with {@code ignore}.
40 * <p>
41 * Individual test cases can be executed using a run action.
42 * <p>
43 * Example: @run main RepeatingTypeAnnotations RepeatingTypeAnnotations$TC4
44 * <p>
45 * Note: when specific test-cases are run, additional debug output is
46 * produced to help debugging. Test annotated with {@code ignore}
47 * can be executed explicitly.
48 */
49public class RepeatingTypeAnnotations extends Tester {
50
51    /**
52     * Main method instantiates test and run test-cases.
53     */
54    public static void main(String... args) throws Exception {
55        Tester tester = new RepeatingTypeAnnotations();
56        tester.run(args);
57    }
58
59    /**
60     * Testcases are classes extending {@code RepeatingTypeAnnotations},
61     * and calling {@link setSrc}, followed by one or more invocations
62     * of {@link verify} in the body of the constructor.
63     */
64    public RepeatingTypeAnnotations() {
65        setSrc(new TestSource(template));
66    }
67
68    /**
69     * Common template for test cases. The line TESTCASE is
70     * replaced with the specific lines of individual tests.
71     */
72    private static final String[] template = {
73        "import java.lang.annotation.*;",
74        "class Test {",
75        "    @Repeatable(As.class)",
76        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
77        "    @Retention(RetentionPolicy.CLASS)",
78        "    @interface A {",
79        "        Class f() default int.class;",
80        "    }",
81
82        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
83        "    @Retention(RetentionPolicy.CLASS)",
84        "    @interface As { A[] value(); }",
85
86        "    @Repeatable(Bs.class)",
87        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
88        "    @Retention(RetentionPolicy.CLASS)",
89        "    @interface B {",
90        "        Class f() default int.class;",
91        "    }",
92
93        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
94        "    @Retention(RetentionPolicy.CLASS)",
95        "    @interface Bs { B[] value(); }",
96
97        "    @Repeatable(Cs.class)",
98        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
99        "    @Retention(RetentionPolicy.RUNTIME)",
100        "    @interface C {",
101        "        Class f() default int.class;",
102        "    }",
103
104        "    @Target({ElementType.TYPE_USE, ElementType.TYPE_PARAMETER})",
105        "    @Retention(RetentionPolicy.RUNTIME)",
106        "    @interface Cs { C[] value(); }",
107        "TESTCASE",
108        "}"
109    };
110
111    /*
112     * The test cases covers annotation in the following locations:
113     * - static and non-static fields
114     * - local variables
115     * - constructor and method return type and parameter types
116     * - casts in class and method contexts.
117     * For the above locations the test-cases covers:
118     * - single annotation type
119     * - two annotation types with same retention
120     * - two annotation types with different retention
121     * - three annotation types, two of same retention, one different.
122     */
123
124    @TestCase
125    public static class TC1 extends RepeatingTypeAnnotations {
126        public TC1() {
127            setSrc(" /* TC1 */ ",
128                   "    static String so = \"hello world\";",
129                   "    public @A @A @A Object o = (@A @A @A String) Test.so;");
130            verify("RuntimeInvisibleTypeAnnotations",
131                   "0: #25(#26=[@#27(),@#27(),@#27()]): FIELD",
132                   "0: #25(#26=[@#27(),@#27(),@#27()]): CAST, offset=5, type_index=0");
133        }
134    }
135
136    @TestCase
137    public static class TC2 extends RepeatingTypeAnnotations {
138        public TC2() {
139            setSrc(" /* TC2 */ ",
140                   "    static String so = \"hello world\";",
141                   "    public @A @B @A Object o = (@B @A @B String) Test.so;");
142            verify("RuntimeInvisibleTypeAnnotations",
143                   "0: #25(#26=[@#27(),@#27()]): FIELD",
144                   "1: #28(): FIELD",
145                   "0: #36(#26=[@#28(),@#28()]): CAST, offset=5, type_index=0",
146                   "1: #27(): CAST, offset=5, type_index=0");
147        }
148    }
149
150    @TestCase
151    public static class TC3 extends RepeatingTypeAnnotations {
152        public TC3() {
153            setSrc(" /* TC3 */ ",
154                   "    static String so = \"hello world\";",
155                   "    public @A @A @C Object o = (@B @C @B String) Test.so;");
156            verify("RuntimeVisibleTypeAnnotations",
157                   "RuntimeInvisibleTypeAnnotations",
158                   "0: #25(): FIELD",
159                   "0: #27(#28=[@#29(),@#29()]): FIELD",
160                   "0: #25(): CAST, offset=5, type_index=0",
161                   "0: #37(#28=[@#38(),@#38()]): CAST, offset=5, type_index=0");
162        }
163    }
164
165    @TestCase
166    public static class TC4 extends RepeatingTypeAnnotations {
167        public TC4() {
168            setSrc(" /* TC4 */ ",
169                   "    static String so = \"hello world\";",
170                   "    public @A @B @C Object o = (@C @B @A String) Test.so;");
171            verify("RuntimeInvisibleTypeAnnotations",
172                   "RuntimeVisibleTypeAnnotations",
173                   "0: #25(): FIELD",
174                   "0: #27(): FIELD",
175                   "1: #28(): FIELD",
176                   "0: #25(): CAST, offset=5, type_index=0",
177                   "0: #28(): CAST, offset=5, type_index=0",
178                   "1: #27(): CAST, offset=5, type_index=0");
179        }
180    }
181
182    @TestCase
183    public static class TC5 extends RepeatingTypeAnnotations {
184        public TC5() {
185            setSrc(" /* TC5 */ ",
186                   "    static String so = \"hello world\";",
187                   "    public static @A @A @A Object o = (@B @B @B String) Test.so;");
188            verify("RuntimeInvisibleTypeAnnotations",
189                   "0: #25(#26=[@#27(),@#27(),@#27()]): FIELD",
190                   "0: #36(#26=[@#37(),@#37(),@#37()]): CAST, offset=5, type_index=0");
191        }
192    }
193
194    @TestCase
195    public static class TC6 extends RepeatingTypeAnnotations {
196        public TC6() {
197            setSrc(" /* TC6 */ ",
198                   "    static String so = \"hello world\";",
199                   "    public static @A @B @A Object o = (@B @A @B String) Test.so;");
200            verify("RuntimeInvisibleTypeAnnotations",
201                   "0: #25(#26=[@#27(),@#27()]): FIELD",
202                   "1: #28(): FIELD",
203                   "0: #37(#26=[@#28(),@#28()]): CAST, offset=5, type_index=0",
204                   "1: #27(): CAST, offset=5, type_index=0");
205        }
206    }
207
208    @TestCase
209    public static class TC7 extends RepeatingTypeAnnotations {
210        public TC7() {
211            setSrc(" /* TC7 */ ",
212                   "    static String so = \"hello world\";",
213                   "    public static @A @A @C Object o = (@B @C @B String) Test.so;");
214            verify("RuntimeVisibleTypeAnnotations",
215                   "RuntimeInvisibleTypeAnnotations",
216                   "0: #25(): FIELD",
217                   "0: #27(#28=[@#29(),@#29()]): FIELD",
218                   "0: #25(): CAST, offset=5, type_index=0",
219                   "0: #38(#28=[@#39(),@#39()]): CAST, offset=5, type_index=0");
220        }
221    }
222
223    @TestCase
224    public static class TC8 extends RepeatingTypeAnnotations {
225        public TC8() {
226            setSrc(" /* TC8 */ ",
227                   "    static String so = \"hello world\";",
228                   "    public static @A @B @C Object o = (@C @B @A String) Test.so;");
229
230            verify("RuntimeVisibleTypeAnnotations",
231                   "RuntimeInvisibleTypeAnnotations",
232                   "0: #25(): FIELD",
233                   "0: #27(): FIELD",
234                   "1: #28(): FIELD",
235                   "0: #25(): CAST, offset=5, type_index=0",
236                   "0: #28(): CAST, offset=5, type_index=0",
237                   "1: #27(): CAST, offset=5, type_index=0");
238        }
239    }
240
241    @TestCase
242    public static class TC9 extends RepeatingTypeAnnotations {
243        public TC9() {
244            setSrc(" /* TC9 */ ",
245                   "    public Test(@A @A @A Object o, @A int i, long l) {",
246                   "        @A @A @A String ls = (@B @B @B String) o;",
247                   "    }");
248            verify("RuntimeInvisibleTypeAnnotations",
249                   "0: #34(#35=[@#36(),@#36(),@#36()]): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
250                   "1: #37(#35=[@#38(),@#38(),@#38()]): CAST, offset=4, type_index=0",
251                   "RuntimeInvisibleTypeAnnotations",
252                   "0: #36(): METHOD_FORMAL_PARAMETER, param_index=1",
253                   "1: #34(#35=[@#36(),@#36(),@#36()]): METHOD_FORMAL_PARAMETER, param_index=0");
254        }
255    }
256
257    @TestCase
258    public static class TC10 extends RepeatingTypeAnnotations {
259        public TC10() {
260            setSrc(" /* TC10 */ ",
261                   "    public Test(@A @A @B Object o, @A @B int i, long l) {",
262                   "        @A @A @B String ls = (@B @A @B String) o;",
263                   "    }");
264            verify("RuntimeInvisibleTypeAnnotations",
265                   "0: #34(#35=[@#36(),@#36()]): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
266                   "1: #37(): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
267                   "2: #38(#35=[@#37(),@#37()]): CAST, offset=4, type_index=0",
268                   "3: #36(): CAST, offset=4, type_index=0",
269                   "RuntimeInvisibleTypeAnnotations",
270                   "0: #36(): METHOD_FORMAL_PARAMETER, param_index=1",
271                   "1: #37(): METHOD_FORMAL_PARAMETER, param_index=1",
272                   "2: #34(#35=[@#36(),@#36()]): METHOD_FORMAL_PARAMETER, param_index=0",
273                   "3: #37(): METHOD_FORMAL_PARAMETER, param_index=0");
274        }
275    }
276
277    @TestCase
278    public static class TC11 extends RepeatingTypeAnnotations {
279        public TC11() {
280            setSrc(" /* TC11 */ ",
281                   "    public Test(@C @C @A Object o, @A @B int i, long l) {",
282                   "        @C @C @A String ls = (@A @A @C String) o;",
283                   "    }");
284            verify("RuntimeVisibleTypeAnnotations",
285                   "RuntimeInvisibleTypeAnnotations",
286                   "0: #34(#35=[@#36(),@#36()]): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
287                   "1: #36(): CAST, offset=4, type_index=0",
288                   "0: #38(): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
289                   "1: #39(#35=[@#38(),@#38()]): CAST, offset=4, type_index=0",
290                   "0: #34(#35=[@#36(),@#36()]): METHOD_FORMAL_PARAMETER, param_index=0",
291                   "0: #38(): METHOD_FORMAL_PARAMETER, param_index=1",
292                   "1: #40(): METHOD_FORMAL_PARAMETER, param_index=1",
293                   "2: #38(): METHOD_FORMAL_PARAMETER, param_index=0");
294        }
295    }
296
297    @TestCase
298    public static class TC12 extends RepeatingTypeAnnotations {
299        public TC12() {
300            setSrc(" /* TC12 */ ",
301                   "    public Test(@A @B @C Object o, @A @C int i, long l) {",
302                   "        @A @B @C String ls = (@C @A @B String) o;",
303                   "    }");
304            verify("RuntimeVisibleTypeAnnotations",
305                   "0: #34(): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
306                   "1: #34(): CAST, offset=4, type_index=0",
307                   "RuntimeInvisibleTypeAnnotations",
308                   "0: #36(): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
309                   "1: #37(): LOCAL_VARIABLE, {start_pc=10, length=1, index=5}",
310                   "2: #36(): CAST, offset=4, type_index=0",
311                   "3: #37(): CAST, offset=4, type_index=0",
312                   "0: #34(): METHOD_FORMAL_PARAMETER, param_index=0",
313                   "1: #34(): METHOD_FORMAL_PARAMETER, param_index=1",
314                   "0: #36(): METHOD_FORMAL_PARAMETER, param_index=0",
315                   "1: #37(): METHOD_FORMAL_PARAMETER, param_index=0",
316                   "2: #36(): METHOD_FORMAL_PARAMETER, param_index=1");
317        }
318    }
319
320    @TestCase
321    public static class TC13 extends RepeatingTypeAnnotations {
322        public TC13() {
323            setSrc(" /* TC13 */ ",
324                   "    public @A @A @A String foo(@A @A @A Object o, @A int i, long l) {",
325                   "        @A @A @A String ls = (@B @B @B String) o;",
326                   "        return (@A @A @A String) o;",
327                   "    }");
328            verify("RuntimeInvisibleTypeAnnotations",
329                   "0: #36(#37=[@#38(),@#38(),@#38()]): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
330                   "1: #39(#37=[@#40(),@#40(),@#40()]): CAST, offset=0, type_index=0",
331                   "2: #36(#37=[@#38(),@#38(),@#38()]): CAST, offset=6, type_index=0",
332                    "RuntimeInvisibleTypeAnnotations",
333                   "0: #38(): METHOD_FORMAL_PARAMETER, param_index=1",
334                   "1: #36(#37=[@#38(),@#38(),@#38()]): METHOD_FORMAL_PARAMETER, param_index=0",
335                   "2: #36(#37=[@#38(),@#38(),@#38()]): METHOD_RETURN"
336                   );
337        }
338    }
339
340    @TestCase
341    public static class TC14 extends RepeatingTypeAnnotations {
342        public TC14() {
343            setSrc(" /* TC14 */ ",
344                   "    public @A @B @B String foo(@A @A @B Object o, @A @B int i, long l) {",
345                   "        @A @A @B String ls = (@B @A @B String) o;",
346                   "        return (@A @B @B String) o;",
347                   "    }");
348           verify(
349                    "RuntimeInvisibleTypeAnnotations:",
350                  "0: #36(#37=[@#38(),@#38()]): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
351                  "1: #39(): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
352                  "2: #40(#37=[@#39(),@#39()]): CAST, offset=0, type_index=0",
353                  "3: #38(): CAST, offset=0, type_index=0",
354                  "4: #38(): CAST, offset=6, type_index=0",
355                  "5: #40(#37=[@#39(),@#39()]): CAST, offset=6, type_index=0",
356                    "RuntimeInvisibleTypeAnnotations:",
357                  "0: #38(): METHOD_FORMAL_PARAMETER, param_index=1",
358                  "1: #39(): METHOD_FORMAL_PARAMETER, param_index=1",
359                  "2: #36(#37=[@#38(),@#38()]): METHOD_FORMAL_PARAMETER, param_index=0",
360                  "3: #39(): METHOD_FORMAL_PARAMETER, param_index=0",
361                  "4: #38(): METHOD_RETURN",
362                  "5: #40(#37=[@#39(),@#39()]): METHOD_RETURN"
363                 );
364        }
365    }
366
367    @TestCase
368    public static class TC15 extends RepeatingTypeAnnotations {
369        public TC15() {
370            setSrc(" /* TC15 */ ",
371                   "    public @A @A @C String foo(@C @C @A Object o, @A @B int i, long l) {",
372                   "        @C @C @A String ls = (@A @A @C String) o;",
373                   "        return (@C @B @B String) o;",
374                   "    }");
375            verify(
376                    "RuntimeVisibleTypeAnnotations:",
377                   "0: #36(#37=[@#38(),@#38()]): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
378                   "1: #38(): CAST, offset=0, type_index=0",
379                   "2: #38(): CAST, offset=6, type_index=0",
380                    "RuntimeInvisibleTypeAnnotations:",
381                   "0: #40(): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
382                   "1: #41(#37=[@#40(),@#40()]): CAST, offset=0, type_index=0",
383                   "2: #42(#37=[@#43(),@#43()]): CAST, offset=6, type_index=0",
384                    "RuntimeVisibleTypeAnnotations:",
385                   "0: #36(#37=[@#38(),@#38()]): METHOD_FORMAL_PARAMETER, param_index=0",
386                   "1: #38(): METHOD_RETURN",
387                    "RuntimeInvisibleTypeAnnotations:",
388                   "0: #40(): METHOD_FORMAL_PARAMETER, param_index=1",
389                   "1: #43(): METHOD_FORMAL_PARAMETER, param_index=1",
390                   "2: #40(): METHOD_FORMAL_PARAMETER, param_index=0",
391                   "3: #41(#37=[@#40(),@#40()]): METHOD_RETURN"
392                    );
393        }
394    }
395
396    @TestCase
397    public static class TC16 extends RepeatingTypeAnnotations {
398        public TC16() {
399            setSrc(" /* TC16 */ ",
400                   "    public @A @B @C String foo(@A @B @C Object o, @A @C int i, long l) {",
401                   "        @A @B @C String ls = (@C @A @B String) o;",
402                   "        return (@B @A @C String) o;",
403                   "    }");
404            verify(
405                    "RuntimeVisibleTypeAnnotations:",
406                   "0: #36(): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
407                   "1: #36(): CAST, offset=0, type_index=0",
408                   "2: #36(): CAST, offset=6, type_index=0",
409                    "RuntimeInvisibleTypeAnnotations:",
410                   "0: #38(): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
411                   "1: #39(): LOCAL_VARIABLE, {start_pc=6, length=5, index=5}",
412                   "2: #38(): CAST, offset=0, type_index=0",
413                   "3: #39(): CAST, offset=0, type_index=0",
414                   "4: #39(): CAST, offset=6, type_index=0",
415                   "5: #38(): CAST, offset=6, type_index=0",
416                    "RuntimeVisibleTypeAnnotations:",
417                   "0: #36(): METHOD_FORMAL_PARAMETER, param_index=0",
418                   "1: #36(): METHOD_FORMAL_PARAMETER, param_index=1",
419                   "2: #36(): METHOD_RETURN",
420                    "RuntimeInvisibleTypeAnnotations:",
421                   "0: #38(): METHOD_FORMAL_PARAMETER, param_index=0",
422                   "1: #39(): METHOD_FORMAL_PARAMETER, param_index=0",
423                   "2: #38(): METHOD_FORMAL_PARAMETER, param_index=1",
424                   "3: #38(): METHOD_RETURN",
425                   "4: #39(): METHOD_RETURN"
426                  );
427        }
428    }
429}
430