⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 resolve.java

📁 java编译器gjc源码 java编译环境
💻 JAVA
📖 第 1 页 / 共 4 页
字号:
            case WRONG_MTH:
                return wrongMethods;

            default:
                return bestSoFar;

            }
        }
        if (!isAccessible(env, site, sym)) {
            return (bestSoFar.kind == ABSENT_MTH) ? new AccessError(sym) : bestSoFar;
        }
        return (bestSoFar.kind > AMBIGUOUS) ? sym :
                mostSpecific(sym, bestSoFar, env, site);
    }

    Symbol mostSpecific(Symbol m1, Symbol m2, Env env, Type site) {
        switch (m2.kind) {
        case MTH:
            if (m1 == m2)
                return m1;
            Type mt1 = site.memberType(m1);
            boolean m1SignatureMoreSpecific =
                    instantiate(env, site, m2, mt1.argtypes()) != null;
            Type mt2 = site.memberType(m2);
            boolean m2SignatureMoreSpecific =
                    instantiate(env, site, m1, mt2.argtypes()) != null;
            if (m1SignatureMoreSpecific && m2SignatureMoreSpecific) {
                if (methodsInherited(m1.owner, m2.owner))
                    return m1;
                if (methodsInherited(m2.owner, m1.owner))
                    return m2;
                boolean m1Abstract = (m1.flags() & ABSTRACT) != 0;
                if (!m1Abstract)
                    return m1;
                boolean m2Abstract = (m2.flags() & ABSTRACT) != 0;
                if (!m2Abstract)
                    return m2;
                Symbol result = mt1.restype().isSubType(mt2.restype()) ? m1 : m2;
                result = result.clone(result.owner);
                result.type = (Type) result.type.clone();
                result.type.setThrown(Check.intersect(mt1.thrown(), mt2.thrown()));
                return result;
            }
            if (m1SignatureMoreSpecific)
                return m1;
            if (m2SignatureMoreSpecific)
                return m2;
            return new AmbiguityError(m1, m2);

        case AMBIGUOUS:
            AmbiguityError e = (AmbiguityError) m2;
            Symbol err1 = mostSpecific(m1, e.sym1, env, site);
            Symbol err2 = mostSpecific(m1, e.sym2, env, site);
            if (err1 == err2)
                return err1;
            if (err1 == e.sym1 && err2 == e.sym2)
                return m2;
            return new AmbiguityError(err1, err2);

        default:
            throw new AssertionError();

        }
    }

    private boolean methodsInherited(Symbol subclass, Symbol superclass) {
        return subclass.isSubClass(superclass) &&
                !((subclass.flags() & INTERFACE) != 0 &&
                superclass.type == syms.objectType);
    }

    /**
      * Find best qualified method matching given name, type and value parameters.
      *  @param env       The current environment.
      *  @param site      The original type from where the selection takes place.
      *  @param name      The method's name.
      *  @param argtypes  The method's value parameters.
      */
    Symbol findMethod(Env env, Type site, Name name, List argtypes) {
        return findMethod(env, site, name, argtypes, site.tsym.type, true,
                methodNotFound);
    }

    private Symbol findMethod(Env env, Type site, Name name, List argtypes,
            Type intype, boolean abstractok, Symbol bestSoFar) {
        for (Type ct = intype; ct.tag == CLASS; ct = ct.supertype()) {
            ClassSymbol c = (ClassSymbol) ct.tsym;
            if ((c.flags() & (ABSTRACT | INTERFACE)) == 0)
                abstractok = false;
            for (Scope.Entry e = c.members().lookup(name); e.scope != null;
                    e = e.next()) {
                if (e.sym.kind == MTH && (e.sym.flags_field & SYNTHETIC) == 0) {
                    bestSoFar = selectBest(env, site, argtypes, e.sym, bestSoFar);
                }
            }
            if (abstractok) {
                for (List l = c.type.interfaces(); l.nonEmpty(); l = l.tail) {
                    bestSoFar = findMethod(env, site, name, argtypes, (Type) l.head,
                            abstractok, bestSoFar);
                }
            }
        }
        return bestSoFar;
    }

    /**
      * Find unqualified method matching given name, type and value parameters.
      *  @param env       The current environment.
      *  @param name      The method's name.
      *  @param argtypes  The method's value parameters.
      */
    Symbol findFun(Env env, Name name, List argtypes) {
        Symbol bestSoFar = methodNotFound;
        Symbol sym;
        Env env1 = env;
        boolean staticOnly = false;
        while (env1.outer != null) {
            if (isStatic(env1))
                staticOnly = true;
            sym = findMethod(env1, env1.enclClass.sym.type, name, argtypes);
            if (sym.kind <= AMBIGUOUS || sym.kind == WRONG_MTHS ||
                    sym.kind == WRONG_MTH) {
                if (staticOnly && sym.kind == MTH && sym.owner.kind == TYP &&
                        (sym.flags() & STATIC) == 0)
                    return new StaticError(sym);
                else
                    return sym;
            } else if (sym.kind < bestSoFar.kind) {
                bestSoFar = sym;
            }
            if ((env1.enclClass.sym.flags() & STATIC) != 0)
                staticOnly = true;
            env1 = env1.outer;
        }
        sym = findMethod(env, syms.predefClass.type, name, argtypes);
        if (sym.kind <= AMBIGUOUS)
            return sym;
        else
            return bestSoFar;
    }

    /**
      * Load toplevel or member class with given fully qualified name and
      *  verify that it is accessible.
      *  @param env       The current environment.
      *  @param name      The fully qualified name of the class to be loaded.
      */
    Symbol loadClass(Env env, Name name) {
        try {
            ClassSymbol c = reader.loadClass(name);
            if (isAccessible(env, c))
                return c;
            else
                return new AccessError(c);
        } catch (ClassReader.BadClassFile err) {
            throw err;
        }
        catch (CompletionFailure ex) {
            return typeNotFound;
        }
    }

    /**
      * Find qualified member type.
      *  @param env       The current environment.
      *  @param site      The original type from where the selection takes place.
      *  @param name      The type's name.
      *  @param c         The class to search for the member type. This is always
      *                   a superclass or implemented interface of site's class.
      */
    Symbol findMemberType(Env env, Type site, Name name, TypeSymbol c) {
        Symbol bestSoFar = typeNotFound;
        Symbol sym;
        Scope.Entry e = c.members().lookup(name);
        while (e.scope != null) {
            if (e.sym.kind == TYP) {
                return isAccessible(env, site, e.sym) ? e.sym :
                        new AccessError(e.sym);
            }
            e = e.next();
        }
        Type st = c.type.supertype();
        if (st != null && st.tag == CLASS) {
            sym = findMemberType(env, site, name, st.tsym);
            if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
        }
        for (List l = c.type.interfaces();
                bestSoFar.kind != AMBIGUOUS && l.nonEmpty(); l = l.tail) {
            sym = findMemberType(env, site, name, ((Type) l.head).tsym);
            if (bestSoFar.kind < AMBIGUOUS && sym.kind < AMBIGUOUS &&
                    sym.owner != bestSoFar.owner)
                bestSoFar = new AmbiguityError(bestSoFar, sym);
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
        }
        return bestSoFar;
    }

    /**
      * Find a global type in given scope and load corresponding class.
      *  @param env       The current environment.
      *  @param scope     The scope in which to look for the type.
      *  @param name      The type's name.
      */
    Symbol findGlobalType(Env env, Scope scope, Name name) {
        Symbol bestSoFar = typeNotFound;
        Scope.Entry e = scope.lookup(name);
        while (e.scope != null) {
            if (e.scope.owner == e.sym.owner) {
                Symbol sym = loadClass(env, e.sym.flatName());
                if (bestSoFar.kind == TYP && sym.kind == TYP && bestSoFar != sym)
                    return new AmbiguityError(bestSoFar, sym);
                else if (sym.kind < bestSoFar.kind)
                    bestSoFar = sym;
            }
            e = e.next();
        }
        return bestSoFar;
    }

    /**
      * Find an unqualified type symbol.
      *  @param env       The current environment.
      *  @param name      The type's name.
      */
    Symbol findType(Env env, Name name) {
        Symbol bestSoFar = typeNotFound;
        Symbol sym;
        Env env1 = env;
        boolean staticOnly = false;
        while (env1.outer != null) {
            if (isStatic(env1))
                staticOnly = true;
            Scope.Entry e = ((AttrContext) env1.info).scope.lookup(name);
            while (e.scope != null) {
                if (e.sym.kind == TYP) {
                    return e.sym;
                }
                e = e.next();
            }
            sym = findMemberType(env1, env1.enclClass.sym.type, name,
                    env1.enclClass.sym);
            if (staticOnly && sym.kind == TYP && sym.type.tag == CLASS &&
                    sym.type.outer().isParameterized())
                return new StaticError(sym);
            else if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
            long flags = env1.enclClass.sym.flags();
            if ((flags & STATIC) != 0)
                staticOnly = true;
            env1 = env1.outer;
        }
        if (env.tree.tag != Tree.IMPORT) {
            sym = findGlobalType(env, env.toplevel.namedImportScope, name);
            if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
            sym = findGlobalType(env, env.toplevel.packge.members(), name);
            if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
            sym = findGlobalType(env, env.toplevel.starImportScope, name);
            if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
        }
        return bestSoFar;
    }

    /**
      * Find an unqualified identifier which matches a specified kind set.
      *  @param env       The current environment.
      *  @param name      The indentifier's name.
      *  @param kind      Indicates the possible symbol kinds
      *                   (a subset of VAL, TYP, PCK).
      */
    Symbol findIdent(Env env, Name name, int kind) {
        Symbol bestSoFar = typeNotFound;
        Symbol sym;
        if ((kind & VAR) != 0) {
            sym = findVar(env, name);
            if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
        }
        if ((kind & TYP) != 0) {
            sym = findType(env, name);
            if (sym.kind <= AMBIGUOUS)
                return sym;
            else if (sym.kind < bestSoFar.kind)
                bestSoFar = sym;
        }
        if ((kind & PCK) != 0)
            return reader.enterPackage(name);
        else
            return bestSoFar;
    }

    /**
      * Find an identifier in a package which matches a specified kind set.
      *  @param env       The current environment.
      *  @param name      The identifier's name.
      *  @param kind      Indicates the possible symbol kinds
      *                   (a nonempty subset of TYP, PCK).
      */
    Symbol findIdentInPackage(Env env, TypeSymbol pck, Name name, int kind) {
        Name fullname = TypeSymbol.formFullName(name, pck);
        Symbol bestSoFar = typeNotFound;
        PackageSymbol pack = null;
        if ((kind & PCK) != 0) {
            pack = reader.enterPackage(fullname);
            if (pack.exists())
                return pack;
        }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -