Wed, 17 Jul 2013 14:04:01 +0100
8012242: Lambda compatibility and checked exceptions
Summary: Inference variables in 'throws' clause with no constraints should be inferred as RuntimeException
Reviewed-by: jjg, vromero
1 /*
2 * Copyright (c) 2009, 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. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
26 package com.sun.tools.javac.code;
28 import javax.lang.model.element.Element;
29 import javax.lang.model.element.ElementKind;
30 import javax.lang.model.type.TypeKind;
32 import com.sun.tools.javac.code.Attribute;
33 import com.sun.tools.javac.code.Attribute.TypeCompound;
34 import com.sun.tools.javac.code.Flags;
35 import com.sun.tools.javac.code.Kinds;
36 import com.sun.tools.javac.code.Type.AnnotatedType;
37 import com.sun.tools.javac.code.Type.ArrayType;
38 import com.sun.tools.javac.code.Type.CapturedType;
39 import com.sun.tools.javac.code.Type.ClassType;
40 import com.sun.tools.javac.code.Type.ErrorType;
41 import com.sun.tools.javac.code.Type.ForAll;
42 import com.sun.tools.javac.code.Type.MethodType;
43 import com.sun.tools.javac.code.Type.PackageType;
44 import com.sun.tools.javac.code.Type.TypeVar;
45 import com.sun.tools.javac.code.Type.UndetVar;
46 import com.sun.tools.javac.code.Type.Visitor;
47 import com.sun.tools.javac.code.Type.WildcardType;
48 import com.sun.tools.javac.code.TypeAnnotationPosition.TypePathEntry;
49 import com.sun.tools.javac.code.TypeAnnotationPosition.TypePathEntryKind;
50 import com.sun.tools.javac.code.TypeTag;
51 import com.sun.tools.javac.code.Symbol.VarSymbol;
52 import com.sun.tools.javac.code.Symbol.MethodSymbol;
53 import com.sun.tools.javac.comp.Annotate;
54 import com.sun.tools.javac.comp.Annotate.Annotator;
55 import com.sun.tools.javac.tree.JCTree;
56 import com.sun.tools.javac.tree.JCTree.JCBlock;
57 import com.sun.tools.javac.tree.JCTree.JCClassDecl;
58 import com.sun.tools.javac.tree.JCTree.JCExpression;
59 import com.sun.tools.javac.tree.JCTree.JCLambda;
60 import com.sun.tools.javac.tree.JCTree.JCMethodDecl;
61 import com.sun.tools.javac.tree.JCTree.JCNewClass;
62 import com.sun.tools.javac.tree.JCTree.JCTypeApply;
63 import com.sun.tools.javac.tree.JCTree.JCVariableDecl;
64 import com.sun.tools.javac.tree.TreeScanner;
65 import com.sun.tools.javac.tree.JCTree.*;
66 import com.sun.tools.javac.util.Assert;
67 import com.sun.tools.javac.util.List;
68 import com.sun.tools.javac.util.ListBuffer;
69 import com.sun.tools.javac.util.Log;
70 import com.sun.tools.javac.util.Names;
72 /**
73 * Contains operations specific to processing type annotations.
74 * This class has two functions:
75 * separate declaration from type annotations and insert the type
76 * annotations to their types;
77 * and determine the TypeAnnotationPositions for all type annotations.
78 */
79 public class TypeAnnotations {
80 // Class cannot be instantiated.
81 private TypeAnnotations() {}
83 /**
84 * Separate type annotations from declaration annotations and
85 * determine the correct positions for type annotations.
86 * This version only visits types in signatures and should be
87 * called from MemberEnter.
88 * The method takes the Annotate object as parameter and
89 * adds an Annotator to the correct Annotate queue for
90 * later processing.
91 */
92 public static void organizeTypeAnnotationsSignatures(final Symtab syms, final Names names,
93 final Log log, final JCClassDecl tree, Annotate annotate) {
94 annotate.afterRepeated( new Annotator() {
95 @Override
96 public void enterAnnotation() {
97 new TypeAnnotationPositions(syms, names, log, true).scan(tree);
98 }
99 } );
100 }
102 /**
103 * This version only visits types in bodies, that is, field initializers,
104 * top-level blocks, and method bodies, and should be called from Attr.
105 */
106 public static void organizeTypeAnnotationsBodies(Symtab syms, Names names, Log log, JCClassDecl tree) {
107 new TypeAnnotationPositions(syms, names, log, false).scan(tree);
108 }
110 public enum AnnotationType { DECLARATION, TYPE, BOTH };
112 /**
113 * Determine whether an annotation is a declaration annotation,
114 * a type annotation, or both.
115 */
116 public static AnnotationType annotationType(Symtab syms, Names names,
117 Attribute.Compound a, Symbol s) {
118 Attribute.Compound atTarget =
119 a.type.tsym.attribute(syms.annotationTargetType.tsym);
120 if (atTarget == null) {
121 return inferTargetMetaInfo(a, s);
122 }
123 Attribute atValue = atTarget.member(names.value);
124 if (!(atValue instanceof Attribute.Array)) {
125 Assert.error("annotationType(): bad @Target argument " + atValue +
126 " (" + atValue.getClass() + ")");
127 return AnnotationType.DECLARATION; // error recovery
128 }
129 Attribute.Array arr = (Attribute.Array) atValue;
130 boolean isDecl = false, isType = false;
131 for (Attribute app : arr.values) {
132 if (!(app instanceof Attribute.Enum)) {
133 Assert.error("annotationType(): unrecognized Attribute kind " + app +
134 " (" + app.getClass() + ")");
135 isDecl = true;
136 continue;
137 }
138 Attribute.Enum e = (Attribute.Enum) app;
139 if (e.value.name == names.TYPE) {
140 if (s.kind == Kinds.TYP)
141 isDecl = true;
142 } else if (e.value.name == names.FIELD) {
143 if (s.kind == Kinds.VAR &&
144 s.owner.kind != Kinds.MTH)
145 isDecl = true;
146 } else if (e.value.name == names.METHOD) {
147 if (s.kind == Kinds.MTH &&
148 !s.isConstructor())
149 isDecl = true;
150 } else if (e.value.name == names.PARAMETER) {
151 if (s.kind == Kinds.VAR &&
152 s.owner.kind == Kinds.MTH &&
153 (s.flags() & Flags.PARAMETER) != 0)
154 isDecl = true;
155 } else if (e.value.name == names.CONSTRUCTOR) {
156 if (s.kind == Kinds.MTH &&
157 s.isConstructor())
158 isDecl = true;
159 } else if (e.value.name == names.LOCAL_VARIABLE) {
160 if (s.kind == Kinds.VAR &&
161 s.owner.kind == Kinds.MTH &&
162 (s.flags() & Flags.PARAMETER) == 0)
163 isDecl = true;
164 } else if (e.value.name == names.ANNOTATION_TYPE) {
165 if (s.kind == Kinds.TYP &&
166 (s.flags() & Flags.ANNOTATION) != 0)
167 isDecl = true;
168 } else if (e.value.name == names.PACKAGE) {
169 if (s.kind == Kinds.PCK)
170 isDecl = true;
171 } else if (e.value.name == names.TYPE_USE) {
172 if (s.kind == Kinds.TYP ||
173 s.kind == Kinds.VAR ||
174 (s.kind == Kinds.MTH && !s.isConstructor() &&
175 !s.type.getReturnType().hasTag(TypeTag.VOID)) ||
176 (s.kind == Kinds.MTH && s.isConstructor()))
177 isType = true;
178 } else if (e.value.name == names.TYPE_PARAMETER) {
179 /* Irrelevant in this case */
180 // TYPE_PARAMETER doesn't aid in distinguishing between
181 // Type annotations and declaration annotations on an
182 // Element
183 } else {
184 Assert.error("annotationType(): unrecognized Attribute name " + e.value.name +
185 " (" + e.value.name.getClass() + ")");
186 isDecl = true;
187 }
188 }
189 if (isDecl && isType) {
190 return AnnotationType.BOTH;
191 } else if (isType) {
192 return AnnotationType.TYPE;
193 } else {
194 return AnnotationType.DECLARATION;
195 }
196 }
198 /** Infer the target annotation kind, if none is give.
199 * We only infer declaration annotations.
200 */
201 private static AnnotationType inferTargetMetaInfo(Attribute.Compound a, Symbol s) {
202 return AnnotationType.DECLARATION;
203 }
206 private static class TypeAnnotationPositions extends TreeScanner {
208 private final Symtab syms;
209 private final Names names;
210 private final Log log;
211 private final boolean sigOnly;
213 private TypeAnnotationPositions(Symtab syms, Names names, Log log, boolean sigOnly) {
214 this.syms = syms;
215 this.names = names;
216 this.log = log;
217 this.sigOnly = sigOnly;
218 }
220 /*
221 * When traversing the AST we keep the "frames" of visited
222 * trees in order to determine the position of annotations.
223 */
224 private ListBuffer<JCTree> frames = ListBuffer.lb();
226 protected void push(JCTree t) { frames = frames.prepend(t); }
227 protected JCTree pop() { return frames.next(); }
228 // could this be frames.elems.tail.head?
229 private JCTree peek2() { return frames.toList().tail.head; }
231 @Override
232 public void scan(JCTree tree) {
233 push(tree);
234 super.scan(tree);
235 pop();
236 }
238 /**
239 * Separates type annotations from declaration annotations.
240 * This step is needed because in certain locations (where declaration
241 * and type annotations can be mixed, e.g. the type of a field)
242 * we never build an JCAnnotatedType. This step finds these
243 * annotations and marks them as if they were part of the type.
244 */
245 private void separateAnnotationsKinds(JCTree typetree, Type type, Symbol sym,
246 TypeAnnotationPosition pos) {
247 /*
248 System.out.printf("separateAnnotationsKinds(typetree: %s, type: %s, symbol: %s, pos: %s%n",
249 typetree, type, sym, pos);
250 */
251 List<Attribute.Compound> annotations = sym.getRawAttributes();
252 ListBuffer<Attribute.Compound> declAnnos = new ListBuffer<Attribute.Compound>();
253 ListBuffer<Attribute.TypeCompound> typeAnnos = new ListBuffer<Attribute.TypeCompound>();
255 for (Attribute.Compound a : annotations) {
256 switch (annotationType(syms, names, a, sym)) {
257 case DECLARATION:
258 declAnnos.append(a);
259 break;
260 case BOTH: {
261 declAnnos.append(a);
262 Attribute.TypeCompound ta = toTypeCompound(a, pos);
263 typeAnnos.append(ta);
264 break;
265 }
266 case TYPE: {
267 Attribute.TypeCompound ta = toTypeCompound(a, pos);
268 typeAnnos.append(ta);
269 break;
270 }
271 }
272 }
274 sym.resetAnnotations();
275 sym.setDeclarationAttributes(declAnnos.toList());
277 if (typeAnnos.isEmpty()) {
278 return;
279 }
281 List<Attribute.TypeCompound> typeAnnotations = typeAnnos.toList();
283 if (type == null) {
284 // When type is null, put the type annotations to the symbol.
285 // This is used for constructor return annotations, for which
286 // no appropriate type exists.
287 sym.appendUniqueTypeAttributes(typeAnnotations);
288 return;
289 }
291 // type is non-null and annotations are added to that type
292 type = typeWithAnnotations(typetree, type, typeAnnotations, log);
294 if (sym.getKind() == ElementKind.METHOD) {
295 sym.type.asMethodType().restype = type;
296 } else if (sym.getKind() == ElementKind.PARAMETER) {
297 sym.type = type;
298 if (sym.getQualifiedName().equals(names._this)) {
299 sym.owner.type.asMethodType().recvtype = type;
300 // note that the typeAnnotations will also be added to the owner below.
301 } else {
302 MethodType methType = sym.owner.type.asMethodType();
303 List<VarSymbol> params = ((MethodSymbol)sym.owner).params;
304 List<Type> oldArgs = methType.argtypes;
305 ListBuffer<Type> newArgs = new ListBuffer<Type>();
306 while (params.nonEmpty()) {
307 if (params.head == sym) {
308 newArgs.add(type);
309 } else {
310 newArgs.add(oldArgs.head);
311 }
312 oldArgs = oldArgs.tail;
313 params = params.tail;
314 }
315 methType.argtypes = newArgs.toList();
316 }
317 } else {
318 sym.type = type;
319 }
321 sym.appendUniqueTypeAttributes(typeAnnotations);
323 if (sym.getKind() == ElementKind.PARAMETER ||
324 sym.getKind() == ElementKind.LOCAL_VARIABLE ||
325 sym.getKind() == ElementKind.RESOURCE_VARIABLE ||
326 sym.getKind() == ElementKind.EXCEPTION_PARAMETER) {
327 // Make sure all type annotations from the symbol are also
328 // on the owner.
329 sym.owner.appendUniqueTypeAttributes(sym.getRawTypeAttributes());
330 }
331 }
333 // This method has a similar purpose as
334 // {@link com.sun.tools.javac.parser.JavacParser.insertAnnotationsToMostInner(JCExpression, List<JCTypeAnnotation>, boolean)}
335 // We found a type annotation in a declaration annotation position,
336 // for example, on the return type.
337 // Such an annotation is _not_ part of an JCAnnotatedType tree and we therefore
338 // need to set its position explicitly.
339 // The method returns a copy of type that contains these annotations.
340 //
341 // As a side effect the method sets the type annotation position of "annotations".
342 // Note that it is assumed that all annotations share the same position.
343 private static Type typeWithAnnotations(final JCTree typetree, final Type type,
344 final List<Attribute.TypeCompound> annotations, Log log) {
345 // System.out.printf("typeWithAnnotations(typetree: %s, type: %s, annotations: %s)%n",
346 // typetree, type, annotations);
347 if (annotations.isEmpty()) {
348 return type;
349 }
350 if (type.hasTag(TypeTag.ARRAY)) {
351 Type toreturn;
352 Type.ArrayType tomodify;
353 Type.ArrayType arType;
354 {
355 Type touse = type;
356 if (type.isAnnotated()) {
357 Type.AnnotatedType atype = (Type.AnnotatedType)type;
358 toreturn = new Type.AnnotatedType(atype.underlyingType);
359 ((Type.AnnotatedType)toreturn).typeAnnotations = atype.typeAnnotations;
360 touse = atype.underlyingType;
361 arType = (Type.ArrayType) touse;
362 tomodify = new Type.ArrayType(null, arType.tsym);
363 ((Type.AnnotatedType)toreturn).underlyingType = tomodify;
364 } else {
365 arType = (Type.ArrayType) touse;
366 tomodify = new Type.ArrayType(null, arType.tsym);
367 toreturn = tomodify;
368 }
369 }
370 JCArrayTypeTree arTree = arrayTypeTree(typetree);
372 ListBuffer<TypePathEntry> depth = ListBuffer.lb();
373 depth = depth.append(TypePathEntry.ARRAY);
374 while (arType.elemtype.hasTag(TypeTag.ARRAY)) {
375 if (arType.elemtype.isAnnotated()) {
376 Type.AnnotatedType aelemtype = (Type.AnnotatedType) arType.elemtype;
377 Type.AnnotatedType newAT = new Type.AnnotatedType(aelemtype.underlyingType);
378 tomodify.elemtype = newAT;
379 newAT.typeAnnotations = aelemtype.typeAnnotations;
380 arType = (Type.ArrayType) aelemtype.underlyingType;
381 tomodify = new Type.ArrayType(null, arType.tsym);
382 newAT.underlyingType = tomodify;
383 } else {
384 arType = (Type.ArrayType) arType.elemtype;
385 tomodify.elemtype = new Type.ArrayType(null, arType.tsym);
386 tomodify = (Type.ArrayType) tomodify.elemtype;
387 }
388 arTree = arrayTypeTree(arTree.elemtype);
389 depth = depth.append(TypePathEntry.ARRAY);
390 }
391 Type arelemType = typeWithAnnotations(arTree.elemtype, arType.elemtype, annotations, log);
392 tomodify.elemtype = arelemType;
393 {
394 // All annotations share the same position; modify the first one.
395 Attribute.TypeCompound a = annotations.get(0);
396 TypeAnnotationPosition p = a.position;
397 p.location = p.location.prependList(depth.toList());
398 }
399 typetree.type = toreturn;
400 return toreturn;
401 } else if (type.hasTag(TypeTag.TYPEVAR)) {
402 // Nothing to do for type variables.
403 return type;
404 } else if (type.getKind() == TypeKind.UNION) {
405 // There is a TypeKind, but no TypeTag.
406 JCTypeUnion tutree = (JCTypeUnion) typetree;
407 JCExpression fst = tutree.alternatives.get(0);
408 Type res = typeWithAnnotations(fst, fst.type, annotations, log);
409 fst.type = res;
410 // TODO: do we want to set res as first element in uct.alternatives?
411 // UnionClassType uct = (com.sun.tools.javac.code.Type.UnionClassType)type;
412 // Return the un-annotated union-type.
413 return type;
414 } else {
415 Type enclTy = type;
416 Element enclEl = type.asElement();
417 JCTree enclTr = typetree;
419 while (enclEl != null &&
420 enclEl.getKind() != ElementKind.PACKAGE &&
421 enclTy != null &&
422 enclTy.getKind() != TypeKind.NONE &&
423 enclTy.getKind() != TypeKind.ERROR &&
424 (enclTr.getKind() == JCTree.Kind.MEMBER_SELECT ||
425 enclTr.getKind() == JCTree.Kind.PARAMETERIZED_TYPE ||
426 enclTr.getKind() == JCTree.Kind.ANNOTATED_TYPE)) {
427 // Iterate also over the type tree, not just the type: the type is already
428 // completely resolved and we cannot distinguish where the annotation
429 // belongs for a nested type.
430 if (enclTr.getKind() == JCTree.Kind.MEMBER_SELECT) {
431 // only change encl in this case.
432 enclTy = enclTy.getEnclosingType();
433 enclEl = enclEl.getEnclosingElement();
434 enclTr = ((JCFieldAccess)enclTr).getExpression();
435 } else if (enclTr.getKind() == JCTree.Kind.PARAMETERIZED_TYPE) {
436 enclTr = ((JCTypeApply)enclTr).getType();
437 } else {
438 // only other option because of while condition
439 enclTr = ((JCAnnotatedType)enclTr).getUnderlyingType();
440 }
441 }
443 /** We are trying to annotate some enclosing type,
444 * but nothing more exists.
445 */
446 if (enclTy != null &&
447 enclTy.getKind() == TypeKind.NONE &&
448 (enclTr.getKind() == JCTree.Kind.IDENTIFIER ||
449 enclTr.getKind() == JCTree.Kind.MEMBER_SELECT ||
450 enclTr.getKind() == JCTree.Kind.PARAMETERIZED_TYPE ||
451 enclTr.getKind() == JCTree.Kind.ANNOTATED_TYPE)) {
452 // TODO: also if it's "java. @A lang.Object", that is,
453 // if it's on a package?
454 log.error(enclTr.pos(), "cant.annotate.nested.type", enclTr.toString());
455 return type;
456 }
458 // At this point we have visited the part of the nested
459 // type that is written in the source code.
460 // Now count from here to the actual top-level class to determine
461 // the correct nesting.
463 // The genericLocation for the annotation.
464 ListBuffer<TypePathEntry> depth = ListBuffer.lb();
466 Type topTy = enclTy;
467 while (enclEl != null &&
468 enclEl.getKind() != ElementKind.PACKAGE &&
469 topTy != null &&
470 topTy.getKind() != TypeKind.NONE &&
471 topTy.getKind() != TypeKind.ERROR) {
472 topTy = topTy.getEnclosingType();
473 enclEl = enclEl.getEnclosingElement();
475 if (topTy != null && topTy.getKind() != TypeKind.NONE) {
476 // Only count enclosing types.
477 depth = depth.append(TypePathEntry.INNER_TYPE);
478 }
479 }
481 if (depth.nonEmpty()) {
482 // Only need to change the annotation positions
483 // if they are on an enclosed type.
484 // All annotations share the same position; modify the first one.
485 Attribute.TypeCompound a = annotations.get(0);
486 TypeAnnotationPosition p = a.position;
487 p.location = p.location.appendList(depth.toList());
488 }
490 Type ret = typeWithAnnotations(type, enclTy, annotations);
491 typetree.type = ret;
492 return ret;
493 }
494 }
496 private static JCArrayTypeTree arrayTypeTree(JCTree typetree) {
497 if (typetree.getKind() == JCTree.Kind.ARRAY_TYPE) {
498 return (JCArrayTypeTree) typetree;
499 } else if (typetree.getKind() == JCTree.Kind.ANNOTATED_TYPE) {
500 return (JCArrayTypeTree) ((JCAnnotatedType)typetree).underlyingType;
501 } else {
502 Assert.error("Could not determine array type from type tree: " + typetree);
503 return null;
504 }
505 }
507 /** Return a copy of the first type that only differs by
508 * inserting the annotations to the left-most/inner-most type
509 * or the type given by stopAt.
510 *
511 * We need the stopAt parameter to know where on a type to
512 * put the annotations.
513 * If we have nested classes Outer > Middle > Inner, and we
514 * have the source type "@A Middle.Inner", we will invoke
515 * this method with type = Outer.Middle.Inner,
516 * stopAt = Middle.Inner, and annotations = @A.
517 *
518 * @param type The type to copy.
519 * @param stopAt The type to stop at.
520 * @param annotations The annotations to insert.
521 * @return A copy of type that contains the annotations.
522 */
523 private static Type typeWithAnnotations(final Type type,
524 final Type stopAt,
525 final List<Attribute.TypeCompound> annotations) {
526 Visitor<Type, List<TypeCompound>> visitor =
527 new Type.Visitor<Type, List<Attribute.TypeCompound>>() {
528 @Override
529 public Type visitClassType(ClassType t, List<TypeCompound> s) {
530 // assert that t.constValue() == null?
531 if (t == stopAt ||
532 t.getEnclosingType() == Type.noType) {
533 return new AnnotatedType(s, t);
534 } else {
535 ClassType ret = new ClassType(t.getEnclosingType().accept(this, s),
536 t.typarams_field, t.tsym);
537 ret.all_interfaces_field = t.all_interfaces_field;
538 ret.allparams_field = t.allparams_field;
539 ret.interfaces_field = t.interfaces_field;
540 ret.rank_field = t.rank_field;
541 ret.supertype_field = t.supertype_field;
542 return ret;
543 }
544 }
546 @Override
547 public Type visitAnnotatedType(AnnotatedType t, List<TypeCompound> s) {
548 return new AnnotatedType(t.typeAnnotations, t.underlyingType.accept(this, s));
549 }
551 @Override
552 public Type visitWildcardType(WildcardType t, List<TypeCompound> s) {
553 return new AnnotatedType(s, t);
554 }
556 @Override
557 public Type visitArrayType(ArrayType t, List<TypeCompound> s) {
558 ArrayType ret = new ArrayType(t.elemtype.accept(this, s), t.tsym);
559 return ret;
560 }
562 @Override
563 public Type visitMethodType(MethodType t, List<TypeCompound> s) {
564 // Impossible?
565 return t;
566 }
568 @Override
569 public Type visitPackageType(PackageType t, List<TypeCompound> s) {
570 // Impossible?
571 return t;
572 }
574 @Override
575 public Type visitTypeVar(TypeVar t, List<TypeCompound> s) {
576 return new AnnotatedType(s, t);
577 }
579 @Override
580 public Type visitCapturedType(CapturedType t, List<TypeCompound> s) {
581 return new AnnotatedType(s, t);
582 }
584 @Override
585 public Type visitForAll(ForAll t, List<TypeCompound> s) {
586 // Impossible?
587 return t;
588 }
590 @Override
591 public Type visitUndetVar(UndetVar t, List<TypeCompound> s) {
592 // Impossible?
593 return t;
594 }
596 @Override
597 public Type visitErrorType(ErrorType t, List<TypeCompound> s) {
598 return new AnnotatedType(s, t);
599 }
601 @Override
602 public Type visitType(Type t, List<TypeCompound> s) {
603 return new AnnotatedType(s, t);
604 }
605 };
607 return type.accept(visitor, annotations);
608 }
610 private static Attribute.TypeCompound toTypeCompound(Attribute.Compound a, TypeAnnotationPosition p) {
611 // It is safe to alias the position.
612 return new Attribute.TypeCompound(a, p);
613 }
616 /* This is the beginning of the second part of organizing
617 * type annotations: determine the type annotation positions.
618 */
620 private void resolveFrame(JCTree tree, JCTree frame,
621 List<JCTree> path, TypeAnnotationPosition p) {
622 /*
623 System.out.println("Resolving tree: " + tree + " kind: " + tree.getKind());
624 System.out.println(" Framing tree: " + frame + " kind: " + frame.getKind());
625 */
627 // Note that p.offset is set in
628 // com.sun.tools.javac.jvm.Gen.setTypeAnnotationPositions(int)
630 switch (frame.getKind()) {
631 case TYPE_CAST:
632 JCTypeCast frameTC = (JCTypeCast) frame;
633 p.type = TargetType.CAST;
634 if (frameTC.clazz.hasTag(Tag.TYPEINTERSECTION)) {
635 // This case was already handled by INTERSECTION_TYPE
636 } else {
637 p.type_index = 0;
638 }
639 p.pos = frame.pos;
640 return;
642 case INSTANCE_OF:
643 p.type = TargetType.INSTANCEOF;
644 p.pos = frame.pos;
645 return;
647 case NEW_CLASS:
648 JCNewClass frameNewClass = (JCNewClass) frame;
649 if (frameNewClass.def != null) {
650 // Special handling for anonymous class instantiations
651 JCClassDecl frameClassDecl = frameNewClass.def;
652 if (frameClassDecl.extending == tree) {
653 p.type = TargetType.CLASS_EXTENDS;
654 p.type_index = -1;
655 } else if (frameClassDecl.implementing.contains(tree)) {
656 p.type = TargetType.CLASS_EXTENDS;
657 p.type_index = frameClassDecl.implementing.indexOf(tree);
658 } else {
659 // In contrast to CLASS below, typarams cannot occur here.
660 Assert.error("Could not determine position of tree " + tree +
661 " within frame " + frame);
662 }
663 } else if (frameNewClass.typeargs.contains(tree)) {
664 p.type = TargetType.CONSTRUCTOR_INVOCATION_TYPE_ARGUMENT;
665 p.type_index = frameNewClass.typeargs.indexOf(tree);
666 } else {
667 p.type = TargetType.NEW;
668 }
669 p.pos = frame.pos;
670 return;
672 case NEW_ARRAY:
673 p.type = TargetType.NEW;
674 p.pos = frame.pos;
675 return;
677 case ANNOTATION_TYPE:
678 case CLASS:
679 case ENUM:
680 case INTERFACE:
681 p.pos = frame.pos;
682 if (((JCClassDecl)frame).extending == tree) {
683 p.type = TargetType.CLASS_EXTENDS;
684 p.type_index = -1;
685 } else if (((JCClassDecl)frame).implementing.contains(tree)) {
686 p.type = TargetType.CLASS_EXTENDS;
687 p.type_index = ((JCClassDecl)frame).implementing.indexOf(tree);
688 } else if (((JCClassDecl)frame).typarams.contains(tree)) {
689 p.type = TargetType.CLASS_TYPE_PARAMETER;
690 p.parameter_index = ((JCClassDecl)frame).typarams.indexOf(tree);
691 } else {
692 Assert.error("Could not determine position of tree " + tree +
693 " within frame " + frame);
694 }
695 return;
697 case METHOD: {
698 JCMethodDecl frameMethod = (JCMethodDecl) frame;
699 p.pos = frame.pos;
700 if (frameMethod.thrown.contains(tree)) {
701 p.type = TargetType.THROWS;
702 p.type_index = frameMethod.thrown.indexOf(tree);
703 } else if (frameMethod.restype == tree) {
704 p.type = TargetType.METHOD_RETURN;
705 } else if (frameMethod.typarams.contains(tree)) {
706 p.type = TargetType.METHOD_TYPE_PARAMETER;
707 p.parameter_index = frameMethod.typarams.indexOf(tree);
708 } else {
709 Assert.error("Could not determine position of tree " + tree +
710 " within frame " + frame);
711 }
712 return;
713 }
715 case PARAMETERIZED_TYPE: {
716 List<JCTree> newPath = path.tail;
718 if (((JCTypeApply)frame).clazz == tree) {
719 // generic: RAW; noop
720 } else if (((JCTypeApply)frame).arguments.contains(tree)) {
721 JCTypeApply taframe = (JCTypeApply) frame;
722 int arg = taframe.arguments.indexOf(tree);
723 p.location = p.location.prepend(new TypePathEntry(TypePathEntryKind.TYPE_ARGUMENT, arg));
725 Type typeToUse;
726 if (newPath.tail != null && newPath.tail.head.hasTag(Tag.NEWCLASS)) {
727 // If we are within an anonymous class instantiation, use its type,
728 // because it contains a correctly nested type.
729 typeToUse = newPath.tail.head.type;
730 } else {
731 typeToUse = taframe.type;
732 }
734 locateNestedTypes(typeToUse, p);
735 } else {
736 Assert.error("Could not determine type argument position of tree " + tree +
737 " within frame " + frame);
738 }
740 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
741 return;
742 }
744 case MEMBER_REFERENCE: {
745 JCMemberReference mrframe = (JCMemberReference) frame;
747 if (mrframe.expr == tree) {
748 switch (mrframe.mode) {
749 case INVOKE:
750 p.type = TargetType.METHOD_REFERENCE;
751 break;
752 case NEW:
753 p.type = TargetType.CONSTRUCTOR_REFERENCE;
754 break;
755 default:
756 Assert.error("Unknown method reference mode " + mrframe.mode +
757 " for tree " + tree + " within frame " + frame);
758 }
759 p.pos = frame.pos;
760 } else if (mrframe.typeargs != null &&
761 mrframe.typeargs.contains(tree)) {
762 int arg = mrframe.typeargs.indexOf(tree);
763 p.type_index = arg;
764 switch (mrframe.mode) {
765 case INVOKE:
766 p.type = TargetType.METHOD_REFERENCE_TYPE_ARGUMENT;
767 break;
768 case NEW:
769 p.type = TargetType.CONSTRUCTOR_REFERENCE_TYPE_ARGUMENT;
770 break;
771 default:
772 Assert.error("Unknown method reference mode " + mrframe.mode +
773 " for tree " + tree + " within frame " + frame);
774 }
775 p.pos = frame.pos;
776 } else {
777 Assert.error("Could not determine type argument position of tree " + tree +
778 " within frame " + frame);
779 }
780 return;
781 }
783 case ARRAY_TYPE: {
784 ListBuffer<TypePathEntry> index = ListBuffer.lb();
785 index = index.append(TypePathEntry.ARRAY);
786 List<JCTree> newPath = path.tail;
787 while (true) {
788 JCTree npHead = newPath.tail.head;
789 if (npHead.hasTag(JCTree.Tag.TYPEARRAY)) {
790 newPath = newPath.tail;
791 index = index.append(TypePathEntry.ARRAY);
792 } else if (npHead.hasTag(JCTree.Tag.ANNOTATED_TYPE)) {
793 newPath = newPath.tail;
794 } else {
795 break;
796 }
797 }
798 p.location = p.location.prependList(index.toList());
799 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
800 return;
801 }
803 case TYPE_PARAMETER:
804 if (path.tail.tail.head.hasTag(JCTree.Tag.CLASSDEF)) {
805 JCClassDecl clazz = (JCClassDecl)path.tail.tail.head;
806 p.type = TargetType.CLASS_TYPE_PARAMETER_BOUND;
807 p.parameter_index = clazz.typarams.indexOf(path.tail.head);
808 p.bound_index = ((JCTypeParameter)frame).bounds.indexOf(tree);
809 if (((JCTypeParameter)frame).bounds.get(0).type.isInterface()) {
810 // Account for an implicit Object as bound 0
811 p.bound_index += 1;
812 }
813 } else if (path.tail.tail.head.hasTag(JCTree.Tag.METHODDEF)) {
814 JCMethodDecl method = (JCMethodDecl)path.tail.tail.head;
815 p.type = TargetType.METHOD_TYPE_PARAMETER_BOUND;
816 p.parameter_index = method.typarams.indexOf(path.tail.head);
817 p.bound_index = ((JCTypeParameter)frame).bounds.indexOf(tree);
818 if (((JCTypeParameter)frame).bounds.get(0).type.isInterface()) {
819 // Account for an implicit Object as bound 0
820 p.bound_index += 1;
821 }
822 } else {
823 Assert.error("Could not determine position of tree " + tree +
824 " within frame " + frame);
825 }
826 p.pos = frame.pos;
827 return;
829 case VARIABLE:
830 VarSymbol v = ((JCVariableDecl)frame).sym;
831 p.pos = frame.pos;
832 switch (v.getKind()) {
833 case LOCAL_VARIABLE:
834 p.type = TargetType.LOCAL_VARIABLE;
835 break;
836 case FIELD:
837 p.type = TargetType.FIELD;
838 break;
839 case PARAMETER:
840 if (v.getQualifiedName().equals(names._this)) {
841 // TODO: Intro a separate ElementKind?
842 p.type = TargetType.METHOD_RECEIVER;
843 } else {
844 p.type = TargetType.METHOD_FORMAL_PARAMETER;
845 p.parameter_index = methodParamIndex(path, frame);
846 }
847 break;
848 case EXCEPTION_PARAMETER:
849 p.type = TargetType.EXCEPTION_PARAMETER;
850 break;
851 case RESOURCE_VARIABLE:
852 p.type = TargetType.RESOURCE_VARIABLE;
853 break;
854 default:
855 Assert.error("Found unexpected type annotation for variable: " + v + " with kind: " + v.getKind());
856 }
857 if (v.getKind() != ElementKind.FIELD) {
858 v.owner.appendUniqueTypeAttributes(v.getRawTypeAttributes());
859 }
860 return;
862 case ANNOTATED_TYPE: {
863 if (frame == tree) {
864 // This is only true for the first annotated type we see.
865 // For any other annotated types along the path, we do
866 // not care about inner types.
867 JCAnnotatedType atypetree = (JCAnnotatedType) frame;
868 final Type utype = atypetree.underlyingType.type;
869 if (utype == null) {
870 // This might happen during DeferredAttr;
871 // we will be back later.
872 return;
873 }
874 Symbol tsym = utype.tsym;
875 if (tsym.getKind().equals(ElementKind.TYPE_PARAMETER) ||
876 utype.getKind().equals(TypeKind.WILDCARD) ||
877 utype.getKind().equals(TypeKind.ARRAY)) {
878 // Type parameters, wildcards, and arrays have the declaring
879 // class/method as enclosing elements.
880 // There is actually nothing to do for them.
881 } else {
882 locateNestedTypes(utype, p);
883 }
884 }
885 List<JCTree> newPath = path.tail;
886 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
887 return;
888 }
890 case UNION_TYPE: {
891 List<JCTree> newPath = path.tail;
892 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
893 return;
894 }
896 case INTERSECTION_TYPE: {
897 JCTypeIntersection isect = (JCTypeIntersection)frame;
898 p.type_index = isect.bounds.indexOf(tree);
899 List<JCTree> newPath = path.tail;
900 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
901 return;
902 }
904 case METHOD_INVOCATION: {
905 JCMethodInvocation invocation = (JCMethodInvocation)frame;
906 if (!invocation.typeargs.contains(tree)) {
907 Assert.error("{" + tree + "} is not an argument in the invocation: " + invocation);
908 }
909 p.type = TargetType.METHOD_INVOCATION_TYPE_ARGUMENT;
910 p.pos = invocation.pos;
911 p.type_index = invocation.typeargs.indexOf(tree);
912 return;
913 }
915 case EXTENDS_WILDCARD:
916 case SUPER_WILDCARD: {
917 // Annotations in wildcard bounds
918 p.location = p.location.prepend(TypePathEntry.WILDCARD);
919 List<JCTree> newPath = path.tail;
920 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
921 return;
922 }
924 case MEMBER_SELECT: {
925 List<JCTree> newPath = path.tail;
926 resolveFrame(newPath.head, newPath.tail.head, newPath, p);
927 return;
928 }
930 default:
931 Assert.error("Unresolved frame: " + frame + " of kind: " + frame.getKind() +
932 "\n Looking for tree: " + tree);
933 return;
934 }
935 }
937 private static void locateNestedTypes(Type type, TypeAnnotationPosition p) {
938 // The number of "steps" to get from the full type to the
939 // left-most outer type.
940 ListBuffer<TypePathEntry> depth = ListBuffer.lb();
942 Type encl = type.getEnclosingType();
943 while (encl != null &&
944 encl.getKind() != TypeKind.NONE &&
945 encl.getKind() != TypeKind.ERROR) {
946 depth = depth.append(TypePathEntry.INNER_TYPE);
947 encl = encl.getEnclosingType();
948 }
949 if (depth.nonEmpty()) {
950 p.location = p.location.prependList(depth.toList());
951 }
952 }
954 private static int methodParamIndex(List<JCTree> path, JCTree param) {
955 List<JCTree> curr = path;
956 while (curr.head.getTag() != Tag.METHODDEF &&
957 curr.head.getTag() != Tag.LAMBDA) {
958 curr = curr.tail;
959 }
960 if (curr.head.getTag() == Tag.METHODDEF) {
961 JCMethodDecl method = (JCMethodDecl)curr.head;
962 return method.params.indexOf(param);
963 } else if (curr.head.getTag() == Tag.LAMBDA) {
964 JCLambda lambda = (JCLambda)curr.head;
965 return lambda.params.indexOf(param);
966 } else {
967 Assert.error("methodParamIndex expected to find method or lambda for param: " + param);
968 return -1;
969 }
970 }
972 // Each class (including enclosed inner classes) is visited separately.
973 // This flag is used to prevent from visiting inner classes.
974 private boolean isInClass = false;
976 @Override
977 public void visitClassDef(JCClassDecl tree) {
978 if (isInClass)
979 return;
980 isInClass = true;
982 if (sigOnly) {
983 scan(tree.mods);
984 scan(tree.typarams);
985 scan(tree.extending);
986 scan(tree.implementing);
987 }
988 scan(tree.defs);
989 }
991 /**
992 * Resolve declaration vs. type annotations in methods and
993 * then determine the positions.
994 */
995 @Override
996 public void visitMethodDef(final JCMethodDecl tree) {
997 if (tree.sym == null) {
998 // Something most be wrong, e.g. a class not found.
999 // Quietly ignore. (See test FailOver15.java)
1000 return;
1001 }
1002 if (sigOnly) {
1003 if (!tree.mods.annotations.isEmpty()) {
1004 // Nothing to do for separateAnnotationsKinds if
1005 // there are no annotations of either kind.
1006 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1007 pos.type = TargetType.METHOD_RETURN;
1008 if (tree.sym.isConstructor()) {
1009 pos.pos = tree.pos;
1010 // Use null to mark that the annotations go with the symbol.
1011 separateAnnotationsKinds(tree, null, tree.sym, pos);
1012 } else {
1013 pos.pos = tree.restype.pos;
1014 separateAnnotationsKinds(tree.restype, tree.sym.type.getReturnType(),
1015 tree.sym, pos);
1016 }
1017 }
1018 if (tree.recvparam != null && tree.recvparam.sym != null &&
1019 !tree.recvparam.mods.annotations.isEmpty()) {
1020 // Nothing to do for separateAnnotationsKinds if
1021 // there are no annotations of either kind.
1022 // TODO: make sure there are no declaration annotations.
1023 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1024 pos.type = TargetType.METHOD_RECEIVER;
1025 pos.pos = tree.recvparam.vartype.pos;
1026 separateAnnotationsKinds(tree.recvparam.vartype, tree.recvparam.sym.type,
1027 tree.recvparam.sym, pos);
1028 }
1029 int i = 0;
1030 for (JCVariableDecl param : tree.params) {
1031 if (!param.mods.annotations.isEmpty()) {
1032 // Nothing to do for separateAnnotationsKinds if
1033 // there are no annotations of either kind.
1034 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1035 pos.type = TargetType.METHOD_FORMAL_PARAMETER;
1036 pos.parameter_index = i;
1037 pos.pos = param.vartype.pos;
1038 separateAnnotationsKinds(param.vartype, param.sym.type, param.sym, pos);
1039 }
1040 ++i;
1041 }
1042 }
1044 push(tree);
1045 // super.visitMethodDef(tree);
1046 if (sigOnly) {
1047 scan(tree.mods);
1048 scan(tree.restype);
1049 scan(tree.typarams);
1050 scan(tree.recvparam);
1051 scan(tree.params);
1052 scan(tree.thrown);
1053 } else {
1054 scan(tree.defaultValue);
1055 scan(tree.body);
1056 }
1057 pop();
1058 }
1060 /* Store a reference to the current lambda expression, to
1061 * be used by all type annotations within this expression.
1062 */
1063 private JCLambda currentLambda = null;
1065 public void visitLambda(JCLambda tree) {
1066 JCLambda prevLambda = currentLambda;
1067 try {
1068 currentLambda = tree;
1070 int i = 0;
1071 for (JCVariableDecl param : tree.params) {
1072 if (!param.mods.annotations.isEmpty()) {
1073 // Nothing to do for separateAnnotationsKinds if
1074 // there are no annotations of either kind.
1075 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1076 pos.type = TargetType.METHOD_FORMAL_PARAMETER;
1077 pos.parameter_index = i;
1078 pos.pos = param.vartype.pos;
1079 pos.onLambda = tree;
1080 separateAnnotationsKinds(param.vartype, param.sym.type, param.sym, pos);
1081 }
1082 ++i;
1083 }
1085 push(tree);
1086 scan(tree.body);
1087 scan(tree.params);
1088 pop();
1089 } finally {
1090 currentLambda = prevLambda;
1091 }
1092 }
1094 /**
1095 * Resolve declaration vs. type annotations in variable declarations and
1096 * then determine the positions.
1097 */
1098 @Override
1099 public void visitVarDef(final JCVariableDecl tree) {
1100 if (tree.mods.annotations.isEmpty()) {
1101 // Nothing to do for separateAnnotationsKinds if
1102 // there are no annotations of either kind.
1103 } else if (tree.sym == null) {
1104 // Something is wrong already. Quietly ignore.
1105 } else if (tree.sym.getKind() == ElementKind.PARAMETER) {
1106 // Parameters are handled in visitMethodDef or visitLambda.
1107 } else if (tree.sym.getKind() == ElementKind.FIELD) {
1108 if (sigOnly) {
1109 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1110 pos.type = TargetType.FIELD;
1111 pos.pos = tree.pos;
1112 separateAnnotationsKinds(tree.vartype, tree.sym.type, tree.sym, pos);
1113 }
1114 } else if (tree.sym.getKind() == ElementKind.LOCAL_VARIABLE) {
1115 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1116 pos.type = TargetType.LOCAL_VARIABLE;
1117 pos.pos = tree.pos;
1118 pos.onLambda = currentLambda;
1119 separateAnnotationsKinds(tree.vartype, tree.sym.type, tree.sym, pos);
1120 } else if (tree.sym.getKind() == ElementKind.EXCEPTION_PARAMETER) {
1121 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1122 pos.type = TargetType.EXCEPTION_PARAMETER;
1123 pos.pos = tree.pos;
1124 pos.onLambda = currentLambda;
1125 separateAnnotationsKinds(tree.vartype, tree.sym.type, tree.sym, pos);
1126 } else if (tree.sym.getKind() == ElementKind.RESOURCE_VARIABLE) {
1127 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1128 pos.type = TargetType.RESOURCE_VARIABLE;
1129 pos.pos = tree.pos;
1130 pos.onLambda = currentLambda;
1131 separateAnnotationsKinds(tree.vartype, tree.sym.type, tree.sym, pos);
1132 } else if (tree.sym.getKind() == ElementKind.ENUM_CONSTANT) {
1133 // No type annotations can occur here.
1134 } else {
1135 // There is nothing else in a variable declaration that needs separation.
1136 Assert.error("Unhandled variable kind: " + tree + " of kind: " + tree.sym.getKind());
1137 }
1139 push(tree);
1140 // super.visitVarDef(tree);
1141 scan(tree.mods);
1142 scan(tree.vartype);
1143 if (!sigOnly) {
1144 scan(tree.init);
1145 }
1146 pop();
1147 }
1149 @Override
1150 public void visitBlock(JCBlock tree) {
1151 // Do not descend into top-level blocks when only interested
1152 // in the signature.
1153 if (!sigOnly) {
1154 scan(tree.stats);
1155 }
1156 }
1158 @Override
1159 public void visitAnnotatedType(JCAnnotatedType tree) {
1160 push(tree);
1161 findPosition(tree, tree, tree.annotations);
1162 pop();
1163 super.visitAnnotatedType(tree);
1164 }
1166 @Override
1167 public void visitTypeParameter(JCTypeParameter tree) {
1168 findPosition(tree, peek2(), tree.annotations);
1169 super.visitTypeParameter(tree);
1170 }
1172 @Override
1173 public void visitNewClass(JCNewClass tree) {
1174 if (tree.def != null &&
1175 !tree.def.mods.annotations.isEmpty()) {
1176 JCClassDecl classdecl = tree.def;
1177 TypeAnnotationPosition pos = new TypeAnnotationPosition();
1178 pos.type = TargetType.CLASS_EXTENDS;
1179 pos.pos = tree.pos;
1180 if (classdecl.extending == tree.clazz) {
1181 pos.type_index = -1;
1182 } else if (classdecl.implementing.contains(tree.clazz)) {
1183 pos.type_index = classdecl.implementing.indexOf(tree.clazz);
1184 } else {
1185 // In contrast to CLASS elsewhere, typarams cannot occur here.
1186 Assert.error("Could not determine position of tree " + tree);
1187 }
1188 Type before = classdecl.sym.type;
1189 separateAnnotationsKinds(classdecl, tree.clazz.type, classdecl.sym, pos);
1191 // classdecl.sym.type now contains an annotated type, which
1192 // is not what we want there.
1193 // TODO: should we put this type somewhere in the superclass/interface?
1194 classdecl.sym.type = before;
1195 }
1197 scan(tree.encl);
1198 scan(tree.typeargs);
1199 scan(tree.clazz);
1200 scan(tree.args);
1202 // The class body will already be scanned.
1203 // scan(tree.def);
1204 }
1206 @Override
1207 public void visitNewArray(JCNewArray tree) {
1208 findPosition(tree, tree, tree.annotations);
1209 int dimAnnosCount = tree.dimAnnotations.size();
1210 ListBuffer<TypePathEntry> depth = ListBuffer.lb();
1212 // handle annotations associated with dimensions
1213 for (int i = 0; i < dimAnnosCount; ++i) {
1214 TypeAnnotationPosition p = new TypeAnnotationPosition();
1215 p.pos = tree.pos;
1216 p.onLambda = currentLambda;
1217 p.type = TargetType.NEW;
1218 if (i != 0) {
1219 depth = depth.append(TypePathEntry.ARRAY);
1220 p.location = p.location.appendList(depth.toList());
1221 }
1223 setTypeAnnotationPos(tree.dimAnnotations.get(i), p);
1224 }
1226 // handle "free" annotations
1227 // int i = dimAnnosCount == 0 ? 0 : dimAnnosCount - 1;
1228 // TODO: is depth.size == i here?
1229 JCExpression elemType = tree.elemtype;
1230 depth = depth.append(TypePathEntry.ARRAY);
1231 while (elemType != null) {
1232 if (elemType.hasTag(JCTree.Tag.ANNOTATED_TYPE)) {
1233 JCAnnotatedType at = (JCAnnotatedType)elemType;
1234 TypeAnnotationPosition p = new TypeAnnotationPosition();
1235 p.type = TargetType.NEW;
1236 p.pos = tree.pos;
1237 p.onLambda = currentLambda;
1238 locateNestedTypes(elemType.type, p);
1239 p.location = p.location.prependList(depth.toList());
1240 setTypeAnnotationPos(at.annotations, p);
1241 elemType = at.underlyingType;
1242 } else if (elemType.hasTag(JCTree.Tag.TYPEARRAY)) {
1243 depth = depth.append(TypePathEntry.ARRAY);
1244 elemType = ((JCArrayTypeTree)elemType).elemtype;
1245 } else if (elemType.hasTag(JCTree.Tag.SELECT)) {
1246 elemType = ((JCFieldAccess)elemType).selected;
1247 } else {
1248 break;
1249 }
1250 }
1251 scan(tree.elems);
1252 }
1254 private void findPosition(JCTree tree, JCTree frame, List<JCAnnotation> annotations) {
1255 if (!annotations.isEmpty()) {
1256 /*
1257 System.out.println("Finding pos for: " + annotations);
1258 System.out.println(" tree: " + tree + " kind: " + tree.getKind());
1259 System.out.println(" frame: " + frame + " kind: " + frame.getKind());
1260 */
1261 TypeAnnotationPosition p = new TypeAnnotationPosition();
1262 p.onLambda = currentLambda;
1263 resolveFrame(tree, frame, frames.toList(), p);
1264 setTypeAnnotationPos(annotations, p);
1265 }
1266 }
1268 private static void setTypeAnnotationPos(List<JCAnnotation> annotations,
1269 TypeAnnotationPosition position) {
1270 for (JCAnnotation anno : annotations) {
1271 // attribute might be null during DeferredAttr;
1272 // we will be back later.
1273 if (anno.attribute != null) {
1274 ((Attribute.TypeCompound) anno.attribute).position = position;
1275 }
1276 }
1277 }
1279 @Override
1280 public String toString() {
1281 return super.toString() + ": sigOnly: " + sigOnly;
1282 }
1283 }
1284 }