changeset 22068:fec8f8a61f6c

Introducing FindContextNode
author Jaroslav Tulach <jaroslav.tulach@oracle.com>
date Thu, 06 Aug 2015 17:22:35 +0200
parents e206ebd965f2
children d683f82dac22
files truffle/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/vm/ImplicitExplicitExportTest.java truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/TruffleLanguage.java truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/Accessor.java truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/FindContextNode.java truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/SLLanguage.java truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/nodes/expression/SLFunctionLiteralNode.java
diffstat 6 files changed, 90 insertions(+), 16 deletions(-) [+]
line wrap: on
line diff
--- a/truffle/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/vm/ImplicitExplicitExportTest.java	Thu Aug 06 08:33:18 2015 +0200
+++ b/truffle/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/vm/ImplicitExplicitExportTest.java	Thu Aug 06 17:22:35 2015 +0200
@@ -163,7 +163,8 @@
         }
 
         private Object importExport(Source code) {
-            Ctx ctx = findContext();
+            final Node node = createFindContextNode();
+            Ctx ctx = findContext(node, null);
             Properties p = new Properties();
             try (Reader r = code.getReader()) {
                 p.load(r);
--- a/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/TruffleLanguage.java	Thu Aug 06 08:33:18 2015 +0200
+++ b/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/TruffleLanguage.java	Thu Aug 06 17:22:35 2015 +0200
@@ -28,6 +28,7 @@
 import java.lang.annotation.*;
 
 import com.oracle.truffle.api.debug.*;
+import com.oracle.truffle.api.frame.VirtualFrame;
 import com.oracle.truffle.api.impl.*;
 import com.oracle.truffle.api.instrument.*;
 import com.oracle.truffle.api.nodes.Node;
@@ -174,19 +175,17 @@
     protected abstract DebugSupportProvider getDebugSupport();
 
     /**
-     * Finds the currently executing context for this language and current thread. Obtains data
-     * previously created by {@link #createContext(com.oracle.truffle.api.TruffleLanguage.Env)}
-     * method.
-     *
-     * @return the context associated with current execution
-     * @throws IllegalStateException if no context is associated with the execution
      */
     @SuppressWarnings({"rawtypes", "unchecked"})
-    protected final C findContext() {
-        final Class<? extends TruffleLanguage> c = getClass();
-        final Env env = API.findLanguage(null, c);
-        assert env.langCtx.lang == this;
-        return (C) env.langCtx.ctx;
+    protected final Node createFindContextNode() {
+        final Class<? extends TruffleLanguage<?>> c = (Class<? extends TruffleLanguage<?>>) getClass();
+        return new FindContextNode(c);
+    }
+    
+    public final C findContext(Node n, VirtualFrame frame) {
+        FindContextNode fcn = (FindContextNode) n;
+        assert fcn.type() == getClass();
+        return (C) fcn.executeFindContext(frame);
     }
 
     private static final class LangCtx<C> {
@@ -319,6 +318,11 @@
         }
 
         @Override
+        protected Object findContext(Env env) {
+            return env.langCtx.ctx;
+        }
+
+        @Override
         protected ToolSupportProvider getToolSupport(TruffleLanguage<?> l) {
             return l.getToolSupport();
         }
--- a/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/Accessor.java	Thu Aug 06 08:33:18 2015 +0200
+++ b/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/Accessor.java	Thu Aug 06 17:22:35 2015 +0200
@@ -35,6 +35,8 @@
 import com.oracle.truffle.api.nodes.RootNode;
 import com.oracle.truffle.api.source.*;
 import com.oracle.truffle.api.vm.*;
+import java.lang.ref.Reference;
+import java.lang.ref.WeakReference;
 
 /**
  * Communication between TruffleVM and TruffleLanguage API/SPI.
@@ -181,9 +183,17 @@
         return SPI.findLanguage(vm, languageClass);
     }
 
+    private static Reference<TruffleVM> previousVM = new WeakReference<>(null);
+    private static Assumption oneVM = Truffle.getRuntime().createAssumption();
     protected Closeable executionStart(TruffleVM vm, Debugger[] fillIn, Source s) {
         final Closeable debugClose = DEBUG.executionStart(vm, fillIn, s);
         final TruffleVM prev = CURRENT_VM.get();
+        if (!(vm == previousVM.get())) {
+            previousVM = new WeakReference<>(vm);
+            oneVM.invalidate();
+            oneVM = Truffle.getRuntime().createAssumption();
+            
+        }
         CURRENT_VM.set(vm);
         class ContextCloseable implements Closeable {
             @Override
@@ -198,6 +208,16 @@
     protected void dispatchEvent(TruffleVM vm, Object event) {
         SPI.dispatchEvent(vm, event);
     }
+    
+    static Assumption oneVMAssumption() {
+        return oneVM;
+    }
+    
+    @SuppressWarnings("unchecked")
+    static <C> C findContext(Class<? extends TruffleLanguage<C>> type) {
+        Env env = SPI.findLanguage(CURRENT_VM.get(), type);
+        return (C) API.findContext(env);
+    }
 
     /**
      * Don't call me. I am here only to let NetBeans debug any Truffle project.
@@ -207,4 +227,8 @@
     public static void main(String... args) {
         throw new IllegalStateException();
     }
+
+    protected Object findContext(Env env) {
+        return API.findContext(env);
+    }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/FindContextNode.java	Thu Aug 06 17:22:35 2015 +0200
@@ -0,0 +1,30 @@
+package com.oracle.truffle.api.impl;
+
+import com.oracle.truffle.api.Assumption;
+import com.oracle.truffle.api.CompilerDirectives;
+import com.oracle.truffle.api.TruffleLanguage;
+import com.oracle.truffle.api.frame.VirtualFrame;
+import com.oracle.truffle.api.nodes.Node;
+
+public final class FindContextNode<C> extends Node {
+    private final Class<TruffleLanguage<C>> type;
+    private @CompilerDirectives.CompilationFinal C context; 
+    private @CompilerDirectives.CompilationFinal Assumption oneVM;
+
+    public FindContextNode(Class<TruffleLanguage<C>> type) {
+        this.type = type;
+    }
+
+    public C executeFindContext(VirtualFrame frame) {
+        if (context != null && oneVM.isValid()) {
+            return context;
+        }
+        CompilerDirectives.transferToInterpreterAndInvalidate();
+        oneVM = Accessor.oneVMAssumption();
+        return context = Accessor.findContext(type);
+    }
+
+    public Class<? extends TruffleLanguage> type() {
+        return type;
+    }
+}
--- a/truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/SLLanguage.java	Thu Aug 06 08:33:18 2015 +0200
+++ b/truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/SLLanguage.java	Thu Aug 06 17:22:35 2015 +0200
@@ -402,7 +402,8 @@
                 if (failed[0] != null) {
                     throw new IllegalStateException(failed[0]);
                 }
-                SLContext fillIn = getContext();
+                Node n = createFindContextNode();
+                SLContext fillIn = findContext(n, null);
                 final SLFunctionRegistry functionRegistry = fillIn.getFunctionRegistry();
                 for (SLFunction f : c.getFunctionRegistry().getFunctions()) {
                     RootCallTarget callTarget = f.getCallTarget();
@@ -491,8 +492,8 @@
         }
     }
 
-    public SLContext getContext() {
-        return findContext();
+    public Node createFindContextNode0() {
+        return createFindContextNode();
     }
 
     private final class SLDebugProvider implements DebugSupportProvider {
--- a/truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/nodes/expression/SLFunctionLiteralNode.java	Thu Aug 06 08:33:18 2015 +0200
+++ b/truffle/com.oracle.truffle.sl/src/com/oracle/truffle/sl/nodes/expression/SLFunctionLiteralNode.java	Thu Aug 06 17:22:35 2015 +0200
@@ -41,6 +41,7 @@
 package com.oracle.truffle.sl.nodes.expression;
 
 import com.oracle.truffle.api.*;
+import com.oracle.truffle.api.CompilerDirectives.CompilationFinal;
 import com.oracle.truffle.api.frame.*;
 import com.oracle.truffle.api.nodes.*;
 import com.oracle.truffle.api.source.*;
@@ -57,14 +58,27 @@
 @NodeInfo(shortName = "func")
 public final class SLFunctionLiteralNode extends SLExpressionNode {
     private final String value;
+    private final Node contextNode;
+    @CompilationFinal private SLFunction cachedFunction;
+    @CompilationFinal private SLContext cachedContext;
+
+    
 
     public SLFunctionLiteralNode(SourceSection src, String value) {
         super(src);
         this.value = value;
+        contextNode = SLLanguage.INSTANCE.createFindContextNode0();
+        adoptChildren();
     }
 
     @Override
     public SLFunction executeGeneric(VirtualFrame frame) {
-        return SLLanguage.INSTANCE.getContext().getFunctionRegistry().lookup(value);
+        SLContext context = SLLanguage.INSTANCE.findContext(contextNode, frame);
+        if (context != cachedContext) {
+            CompilerDirectives.transferToInterpreterAndInvalidate();
+            this.cachedContext = context;
+            this.cachedFunction = context.getFunctionRegistry().lookup(value);
+        }
+        return cachedFunction;
     }
 }