Search in sources :

Example 1 with EspressoThreadLocalState

use of com.oracle.truffle.espresso.runtime.EspressoThreadLocalState in project graal by oracle.

the class ClassRegistry method createKlass.

@SuppressWarnings("try")
private ObjectKlass createKlass(Meta meta, ParserKlass parserKlass, Symbol<Type> type, Symbol<Type> superKlassType, ClassDefinitionInfo info) {
    EspressoThreadLocalState threadLocalState = meta.getContext().getLanguage().getThreadLocalState();
    TypeStack chain = threadLocalState.getTypeStack();
    ObjectKlass superKlass = null;
    ObjectKlass[] superInterfaces = null;
    LinkedKlass[] linkedInterfaces = null;
    chain.push(type);
    try {
        if (superKlassType != null) {
            if (chain.contains(superKlassType)) {
                throw meta.throwException(meta.java_lang_ClassCircularityError);
            }
            superKlass = loadKlassRecursively(meta, superKlassType, true);
        }
        final Symbol<Type>[] superInterfacesTypes = parserKlass.getSuperInterfaces();
        linkedInterfaces = superInterfacesTypes.length == 0 ? LinkedKlass.EMPTY_ARRAY : new LinkedKlass[superInterfacesTypes.length];
        superInterfaces = superInterfacesTypes.length == 0 ? ObjectKlass.EMPTY_ARRAY : new ObjectKlass[superInterfacesTypes.length];
        for (int i = 0; i < superInterfacesTypes.length; ++i) {
            if (chain.contains(superInterfacesTypes[i])) {
                throw meta.throwException(meta.java_lang_ClassCircularityError);
            }
            ObjectKlass interf = loadKlassRecursively(meta, superInterfacesTypes[i], false);
            superInterfaces[i] = interf;
            linkedInterfaces[i] = interf.getLinkedKlass();
        }
    } finally {
        chain.pop();
    }
    if (getContext().getJavaVersion().java16OrLater() && superKlass != null) {
        if (superKlass.isFinalFlagSet()) {
            throw meta.throwExceptionWithMessage(meta.java_lang_IncompatibleClassChangeError, "class " + type + " is a subclass of final class " + superKlassType);
        }
    }
    ObjectKlass klass;
    try (DebugCloseable define = KLASS_DEFINE.scope(context.getTimers())) {
        // FIXME(peterssen): Do NOT create a LinkedKlass every time, use a global cache.
        ContextDescription description = new ContextDescription(context.getLanguage(), context.getJavaVersion());
        LinkedKlass linkedKlass = LinkedKlass.create(description, parserKlass, superKlass == null ? null : superKlass.getLinkedKlass(), linkedInterfaces);
        klass = new ObjectKlass(context, linkedKlass, superKlass, superInterfaces, getClassLoader(), info);
    }
    if (superKlass != null) {
        if (!Klass.checkAccess(superKlass, klass)) {
            throw meta.throwExceptionWithMessage(meta.java_lang_IllegalAccessError, "class " + type + " cannot access its superclass " + superKlassType);
        }
        if (!superKlass.permittedSubclassCheck(klass)) {
            throw meta.throwExceptionWithMessage(meta.java_lang_IncompatibleClassChangeError, "class " + type + " is not a permitted subclass of class " + superKlassType);
        }
    }
    for (ObjectKlass interf : superInterfaces) {
        if (interf != null) {
            if (!Klass.checkAccess(interf, klass)) {
                throw meta.throwExceptionWithMessage(meta.java_lang_IllegalAccessError, "class " + type + " cannot access its superinterface " + interf.getType());
            }
            if (!interf.permittedSubclassCheck(klass)) {
                throw meta.throwExceptionWithMessage(meta.java_lang_IncompatibleClassChangeError, "class " + type + " is not a permitted subclass of interface " + superKlassType);
            }
        }
    }
    return klass;
}
Also used : EspressoThreadLocalState(com.oracle.truffle.espresso.runtime.EspressoThreadLocalState) Symbol(com.oracle.truffle.espresso.descriptors.Symbol) DebugCloseable(com.oracle.truffle.espresso.perf.DebugCloseable)

Aggregations

Symbol (com.oracle.truffle.espresso.descriptors.Symbol)1 DebugCloseable (com.oracle.truffle.espresso.perf.DebugCloseable)1 EspressoThreadLocalState (com.oracle.truffle.espresso.runtime.EspressoThreadLocalState)1