📄 javacelements.java
字号:
* symbol, and returns its RHS. Does not scan nested JCAnnotations. */ private JCExpression scanForAssign(final MethodSymbol sym, final JCTree tree) { class TS extends TreeScanner { JCExpression result = null; public void scan(JCTree t) { if (t != null && result == null) t.accept(this); } public void visitAnnotation(JCAnnotation t) { if (t == tree) scan(t.args); } public void visitAssign(JCAssign t) { if (t.lhs.getTag() == JCTree.IDENT) { JCIdent ident = (JCIdent) t.lhs; if (ident.sym == sym) result = t.rhs; } } } TS scanner = new TS(); tree.accept(scanner); return scanner.result; } /** * Returns the tree node corresponding to this element, or null * if none can be found. */ public JCTree getTree(Element e) { Pair<JCTree, ?> treeTop = getTreeAndTopLevel(e); return (treeTop != null) ? treeTop.fst : null; } public String getDocComment(Element e) { // Our doc comment is contained in a map in our toplevel, // indexed by our tree. Find our enter environment, which gives // us our toplevel. It also gives us a tree that contains our // tree: walk it to find our tree. This is painful. Pair<JCTree, JCCompilationUnit> treeTop = getTreeAndTopLevel(e); if (treeTop == null) return null; JCTree tree = treeTop.fst; JCCompilationUnit toplevel = treeTop.snd; if (toplevel.docComments == null) return null; return toplevel.docComments.get(tree); } public PackageElement getPackageOf(Element e) { return cast(Symbol.class, e).packge(); } public boolean isDeprecated(Element e) { Symbol sym = cast(Symbol.class, e); return (sym.flags() & Flags.DEPRECATED) != 0; } public Name getBinaryName(TypeElement type) { return cast(TypeSymbol.class, type).flatName(); } public Map<MethodSymbol, Attribute> getElementValuesWithDefaults( AnnotationMirror a) { Attribute.Compound anno = cast(Attribute.Compound.class, a); DeclaredType annotype = a.getAnnotationType(); Map<MethodSymbol, Attribute> valmap = anno.getElementValues(); for (ExecutableElement ex : methodsIn(annotype.asElement().getEnclosedElements())) { MethodSymbol meth = (MethodSymbol) ex; Attribute defaultValue = meth.getDefaultValue(); if (defaultValue != null && !valmap.containsKey(meth)) { valmap.put(meth, defaultValue); } } return valmap; } /** * {@inheritDoc} */ public FilteredMemberList getAllMembers(TypeElement element) { Symbol sym = cast(Symbol.class, element); Scope scope = sym.members().dupUnshared(); List<Type> closure = types.closure(sym.asType()); for (Type t : closure) addMembers(scope, t); return new FilteredMemberList(scope); } // where private void addMembers(Scope scope, Type type) { members: for (Scope.Entry e = type.asElement().members().elems; e != null; e = e.sibling) { Scope.Entry overrider = scope.lookup(e.sym.getSimpleName()); while (overrider.scope != null) { if (overrider.sym.kind == e.sym.kind && (overrider.sym.flags() & Flags.SYNTHETIC) == 0) { if (overrider.sym.getKind() == ElementKind.METHOD && overrides((ExecutableElement)overrider.sym, (ExecutableElement)e.sym, (TypeElement)type.asElement())) { continue members; } } overrider = overrider.next(); } boolean derived = e.sym.getEnclosingElement() != scope.owner; ElementKind kind = e.sym.getKind(); boolean initializer = kind == ElementKind.CONSTRUCTOR || kind == ElementKind.INSTANCE_INIT || kind == ElementKind.STATIC_INIT; if (!derived || (!initializer && e.sym.isInheritedIn(scope.owner, types))) scope.enter(e.sym); } } /** * Returns all annotations of an element, whether * inherited or directly present. * * @param e the element being examined * @return all annotations of the element */ public List<Attribute.Compound> getAllAnnotationMirrors(Element e) { Symbol sym = cast(Symbol.class, e); List<Attribute.Compound> annos = sym.getAnnotationMirrors(); while (sym.getKind() == ElementKind.CLASS) { Type sup = ((ClassSymbol) sym).getSuperclass(); if (sup.tag != TypeTags.CLASS || sup.isErroneous() || sup.tsym == syms.objectType.tsym) { break; } sym = sup.tsym; List<Attribute.Compound> oldAnnos = annos; for (Attribute.Compound anno : sym.getAnnotationMirrors()) { if (isInherited(anno.type) && !containsAnnoOfType(oldAnnos, anno.type)) { annos = annos.prepend(anno); } } } return annos; } /** * Tests whether an annotation type is @Inherited. */ private boolean isInherited(Type annotype) { for (Attribute.Compound anno : annotype.tsym.getAnnotationMirrors()) { if (anno.type.tsym == syms.inheritedType.tsym) return true; } return false; } /** * Tests whether a list of annotations contains an annotation * of a given type. */ private static boolean containsAnnoOfType(List<Attribute.Compound> annos, Type type) { for (Attribute.Compound anno : annos) { if (anno.type.tsym == type.tsym) return true; } return false; } public boolean hides(Element hiderEl, Element hideeEl) { Symbol hider = cast(Symbol.class, hiderEl); Symbol hidee = cast(Symbol.class, hideeEl); // Fields only hide fields; methods only methods; types only types. // Names must match. Nothing hides itself (just try it). if (hider == hidee || hider.kind != hidee.kind || hider.name != hidee.name) { return false; } // Only static methods can hide other methods. // Methods only hide methods with matching signatures. if (hider.kind == Kinds.MTH) { if (!hider.isStatic() || !types.isSubSignature(hider.type, hidee.type)) { return false; } } // Hider must be in a subclass of hidee's class. // Note that if M1 hides M2, and M2 hides M3, and M3 is accessible // in M1's class, then M1 and M2 both hide M3. ClassSymbol hiderClass = hider.owner.enclClass(); ClassSymbol hideeClass = hidee.owner.enclClass(); if (hiderClass == null || hideeClass == null || !hiderClass.isSubClass(hideeClass, types)) { return false; } // Hidee must be accessible in hider's class. // The method isInheritedIn is poorly named: it checks only access. return hidee.isInheritedIn(hiderClass, types); } public boolean overrides(ExecutableElement riderEl, ExecutableElement rideeEl, TypeElement typeEl) { MethodSymbol rider = cast(MethodSymbol.class, riderEl); MethodSymbol ridee = cast(MethodSymbol.class, rideeEl); ClassSymbol origin = cast(ClassSymbol.class, typeEl); return rider.name == ridee.name && // not reflexive as per JLS rider != ridee && // we don't care if ridee is static, though that wouldn't // compile !rider.isStatic() && // Symbol.overrides assumes the following ridee.isMemberOf(origin, types) && // check access and signatures; don't check return types rider.overrides(ridee, origin, types, false); } public String getConstantExpression(Object value) { return Constants.format(value); } /** * Print a representation of the elements to the given writer in * the specified order. The main purpose of this method is for * diagnostics. The exact format of the output is <em>not</em> * specified and is subject to change. * * @param w the writer to print the output to * @param elements the elements to print */ public void printElements(java.io.Writer w, Element... elements) { for (Element element : elements) (new PrintingProcessor.PrintingElementVisitor(w, this)).visit(element).flush(); } public Name getName(CharSequence cs) { return Name.fromString(names, cs.toString()); } /** * Returns the tree node and compilation unit corresponding to this * element, or null if they can't be found. */ private Pair<JCTree, JCCompilationUnit> getTreeAndTopLevel(Element e) { Symbol sym = cast(Symbol.class, e); Env<AttrContext> enterEnv = getEnterEnv(sym); if (enterEnv == null) return null; JCTree tree = TreeInfo.declarationFor(sym, enterEnv.tree); if (tree == null || enterEnv.toplevel == null) return null; return new Pair<JCTree,JCCompilationUnit>(tree, enterEnv.toplevel); } /** * Returns the best approximation for the tree node and compilation unit * corresponding to the given element, annotation and value. * If the element is null, null is returned. * If the annotation is null or cannot be found, the tree node and * compilation unit for the element is returned. * If the annotation value is null or cannot be found, the tree node and * compilation unit for the annotation is returned. */ public Pair<JCTree, JCCompilationUnit> getTreeAndTopLevel( Element e, AnnotationMirror a, AnnotationValue v) { if (e == null) return null; Pair<JCTree, JCCompilationUnit> elemTreeTop = getTreeAndTopLevel(e); if (elemTreeTop == null) return null; if (a == null) return elemTreeTop; JCTree annoTree = matchAnnoToTree(a, e, elemTreeTop.fst); if (annoTree == null) return elemTreeTop; // 6388543: if v != null, we should search within annoTree to find // the tree matching v. For now, we ignore v and return the tree of // the annotation. return new Pair<JCTree, JCCompilationUnit>(annoTree, elemTreeTop.snd); } /** * Returns a symbol's enter environment, or null if it has none. */ private Env<AttrContext> getEnterEnv(Symbol sym) { // Get enclosing class of sym, or sym itself if it is a class // or package. TypeSymbol ts = (sym.kind != Kinds.PCK) ? sym.enclClass() : (PackageSymbol) sym; return (ts != null) ? enter.getEnv(ts) : null; } /** * Returns an object cast to the specified type. * @throws NullPointerException if the object is {@code null} * @throws IllegalArgumentException if the object is of the wrong type */ private static <T> T cast(Class<T> clazz, Object o) { if (! clazz.isInstance(o)) throw new IllegalArgumentException(o.toString()); return clazz.cast(o); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -