Skip to content

Commit

Permalink
[GR-33259] Allow runtimes to enter leave an individual language insta…
Browse files Browse the repository at this point in the history
…nce.

PullRequest: graal/9614
  • Loading branch information
chumer committed Aug 26, 2021
2 parents c7f6914 + 3a34701 commit bc7e837
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,7 @@
import org.graalvm.options.OptionValues;

import com.oracle.truffle.api.CompilerDirectives.CompilationFinal;
import com.oracle.truffle.api.TruffleLanguage;
import com.oracle.truffle.api.TruffleLogger;
import com.oracle.truffle.api.nodes.RootNode;
import com.oracle.truffle.api.source.Source;
Expand Down Expand Up @@ -439,4 +440,20 @@ public void mergeLoadedSources(Source[] sources) {
GraalRuntimeAccessor.SOURCE.mergeLoadedSources(sources);
}

@SuppressWarnings("static-method")
public Object enterLanguage(TruffleLanguage<?> language) {
return GraalRuntimeAccessor.ENGINE.enterLanguageFromRuntime(language);
}

@SuppressWarnings("static-method")
public void leaveLanguage(TruffleLanguage<?> language, Object prev) {
GraalRuntimeAccessor.ENGINE.leaveLanguageFromRuntime(language, prev);
}

@SuppressWarnings("static-method")
public TruffleLanguage<?> getLanguage(OptimizedCallTarget target) {
RootNode root = target.getRootNode();
return GraalRuntimeAccessor.NODES.getLanguage(root);
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -615,6 +615,10 @@ public abstract <T, G> Iterator<T> mergeHostGuestFrames(Object instrumentEnv, St

public abstract Object getHostContext(Object valueContext);

public abstract Object enterLanguageFromRuntime(TruffleLanguage<?> language);

public abstract void leaveLanguageFromRuntime(TruffleLanguage<?> language, Object prev);

}

public abstract static class LanguageSupport extends Support {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -345,6 +345,18 @@ public Object getHostContext(Object polyglotContext) {
return ((PolyglotContextImpl) polyglotContext).getHostContextImpl();
}

@Override
public Object enterLanguageFromRuntime(TruffleLanguage<?> language) {
PolyglotLanguageInstance instance = (PolyglotLanguageInstance) EngineAccessor.LANGUAGE.getPolyglotLanguageInstance(language);
return PolyglotFastThreadLocals.enterLanguage(instance);
}

@Override
public void leaveLanguageFromRuntime(TruffleLanguage<?> language, Object prev) {
PolyglotLanguageInstance instance = (PolyglotLanguageInstance) EngineAccessor.LANGUAGE.getPolyglotLanguageInstance(language);
PolyglotFastThreadLocals.leaveLanguage(instance, prev);
}

@Override
public TruffleContext getCurrentCreatorTruffleContext() {
PolyglotContextImpl context = PolyglotFastThreadLocals.getContext(null);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,20 @@ static Object[] createFastThreadLocals(PolyglotThreadInfo thread) {
return data;
}

private static Object[] createFastThreadLocalsForLanguage(PolyglotLanguageInstance instance) {
Object[] data = new Object[LANGUAGE_START + (instance.language.engine.languages.length * LANGUAGE_ELEMENTS)];
data[THREAD_INDEX] = null; // not available if only engine is entered
data[CONTEXT_INDEX] = null; // not available if only engine is entered

// we take the first language we find. should we fail maybe if there is more than one?
data[getLanguageIndex(instance) + LANGUAGE_SPI_OFFSET] = instance.spi;
return data;
}

private static int getLanguageIndex(PolyglotLanguageInstance instance) {
return LANGUAGE_START + (instance.language.cache.getStaticIndex() * LANGUAGE_ELEMENTS);
}

@SuppressWarnings({"unchecked"})
public static <C extends TruffleLanguage<?>> LanguageReference<C> createLanguageReference(Node legacyNode, Class<? extends TruffleLanguage<?>> language) {
LanguageReference<C> ref = createLanguageReference(language);
Expand Down Expand Up @@ -141,6 +155,17 @@ public static void leave(Object[] prev) {
IMPL.set(prev);
}

public static Object enterLanguage(PolyglotLanguageInstance language) {
Object[] prev = IMPL.get();
IMPL.set(createFastThreadLocalsForLanguage(language));
return prev;
}

public static void leaveLanguage(PolyglotLanguageInstance instance, Object prev) {
assert IMPL.get()[getLanguageIndex(instance) + LANGUAGE_SPI_OFFSET] != null : "language not entered";
IMPL.set((Object[]) prev);
}

public static void cleanup(Object[] threadLocals) {
Arrays.fill(threadLocals, null);
}
Expand Down Expand Up @@ -224,12 +249,12 @@ static void notifyLanguageCreated(PolyglotLanguageContext languageContext) {
}

private static void updateLanguageObjects(Object[] data, PolyglotLanguageContext languageContext) {
int index = languageContext.language.cache.getStaticIndex();
int languageIndex = LANGUAGE_START + (index * LANGUAGE_ELEMENTS);
PolyglotLanguageInstance instance = languageContext.getLanguageInstance();
int languageIndex = getLanguageIndex(instance);
assert languageIndex + LANGUAGE_ELEMENTS - 1 < data.length : "unexpected fast thread local state";

data[languageIndex + LANGUAGE_CONTEXT_OFFSET] = languageContext.getContextImpl();
data[languageIndex + LANGUAGE_SPI_OFFSET] = languageContext.getLanguageInstance().spi;
data[languageIndex + LANGUAGE_SPI_OFFSET] = instance.spi;
}

/*
Expand Down

0 comments on commit bc7e837

Please sign in to comment.