changeset 15210:201f6858a4f3

Restructure the interaction between OptimizedCallTarget and GraalTruffleRuntime.
author Thomas Wuerthinger <thomas.wuerthinger@oracle.com>
date Thu, 17 Apr 2014 16:25:08 +0200
parents 039d8902bdb8
children 59f71608aa9a
files graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotOptimizedCallTarget.java graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotTruffleRuntime.java graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/GraalTruffleRuntime.java graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallTarget.java graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompiler.java graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java
diffstat 6 files changed, 92 insertions(+), 120 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotOptimizedCallTarget.java	Thu Apr 17 13:17:25 2014 +0200
+++ b/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotOptimizedCallTarget.java	Thu Apr 17 16:25:08 2014 +0200
@@ -26,8 +26,6 @@
 import static com.oracle.graal.truffle.TruffleCompilerOptions.*;
 import static com.oracle.graal.truffle.OptimizedCallTargetLog.*;
 
-import java.util.concurrent.*;
-
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.hotspot.meta.*;
 import com.oracle.graal.truffle.*;
@@ -39,13 +37,12 @@
  */
 public final class HotSpotOptimizedCallTarget extends OptimizedCallTarget {
 
-    protected final TruffleCompiler compiler;
-    private Future<InstalledCode> installedCodeTask;
+    protected final GraalTruffleRuntime runtime;
     private SpeculationLog speculationLog = new HotSpotSpeculationLog();
 
-    HotSpotOptimizedCallTarget(RootNode rootNode, TruffleCompiler compiler, int invokeCounter, int compilationThreshold, boolean compilationEnabled) {
+    HotSpotOptimizedCallTarget(RootNode rootNode, GraalTruffleRuntime runtime, int invokeCounter, int compilationThreshold, boolean compilationEnabled) {
         super(rootNode, invokeCounter, compilationThreshold, compilationEnabled, TruffleUseTimeForCompilationDecision.getValue() ? new TimedCompilationPolicy() : new DefaultCompilationPolicy());
-        this.compiler = compiler;
+        this.runtime = runtime;
     }
 
     @Override
@@ -104,9 +101,7 @@
     }
 
     private void cancelInstalledTask(Node oldNode, Node newNode, CharSequence reason) {
-        Future<InstalledCode> task = this.installedCodeTask;
-        if (task != null) {
-            task.cancel(true);
+        if (this.runtime.cancelInstalledTask(this)) {
             logOptimizingUnqueued(this, oldNode, newNode, reason);
             compilationProfile.reportInvalidated();
         }
@@ -131,51 +126,30 @@
         return executeHelper(args);
     }
 
-    private boolean isCompiling() {
-        Future<InstalledCode> codeTask = this.installedCodeTask;
-        if (codeTask != null) {
-            if (codeTask.isCancelled() || codeTask.isDone()) {
-                // System.out.println("done or cancelled => set null " + codeTask.isCancelled());
-                return false;
-            }
-            return true;
-        }
-        return false;
-    }
-
     @Override
     public void compile() {
-        if (!isCompiling()) {
+        if (!runtime.isCompiling(this)) {
             performInlining();
             logOptimizingQueued(this);
-            this.installedCodeTask = compiler.compile(this);
-            if (!TruffleBackgroundCompilation.getValue()) {
-                receiveInstalledCode();
-            }
+            runtime.compile(this, TruffleBackgroundCompilation.getValue());
         }
     }
 
     @Override
-    public void exceptionWhileCompiling(Throwable t) {
-        compilationEnabled = false;
-        logOptimizingFailed(this, t.getMessage());
-        if (t instanceof BailoutException) {
-            // Bailout => move on.
+    public void compilationFinished(Throwable t) {
+        if (t == null) {
+            // Compilation was successful.
         } else {
-            if (TruffleCompilationExceptionsAreFatal.getValue()) {
-                t.printStackTrace(OUT);
-                System.exit(-1);
+            compilationEnabled = false;
+            logOptimizingFailed(this, t.getMessage());
+            if (t instanceof BailoutException) {
+                // Bailout => move on.
+            } else {
+                if (TruffleCompilationExceptionsAreFatal.getValue()) {
+                    t.printStackTrace(OUT);
+                    System.exit(-1);
+                }
             }
         }
     }
-
-    private void receiveInstalledCode() {
-        try {
-            // Force task completion.
-            installedCodeTask.get();
-        } catch (InterruptedException | ExecutionException e) {
-            exceptionWhileCompiling(e.getCause());
-        }
-    }
-
 }
--- a/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotTruffleRuntime.java	Thu Apr 17 13:17:25 2014 +0200
+++ b/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/HotSpotTruffleRuntime.java	Thu Apr 17 16:25:08 2014 +0200
@@ -27,12 +27,14 @@
 import static com.oracle.graal.truffle.TruffleCompilerOptions.*;
 
 import java.util.*;
+import java.util.concurrent.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.code.CallingConvention.Type;
 import com.oracle.graal.api.code.stack.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.api.runtime.*;
+import com.oracle.graal.compiler.*;
 import com.oracle.graal.compiler.target.*;
 import com.oracle.graal.debug.*;
 import com.oracle.graal.debug.Debug.Scope;
@@ -44,6 +46,7 @@
 import com.oracle.graal.phases.common.*;
 import com.oracle.graal.phases.tiers.*;
 import com.oracle.graal.phases.util.*;
+import com.oracle.graal.printer.*;
 import com.oracle.graal.runtime.*;
 import com.oracle.graal.truffle.*;
 import com.oracle.truffle.api.*;
@@ -61,11 +64,13 @@
         return new HotSpotTruffleRuntime();
     }
 
-    private TruffleCompiler truffleCompiler;
+    private TruffleCompilerImpl truffleCompiler;
     private Replacements truffleReplacements;
     private StackIntrospection stackIntrospection;
     private ArrayList<String> includes;
     private ArrayList<String> excludes;
+    private Map<OptimizedCallTarget, Future<?>> compilations = new IdentityHashMap<>();
+    private final ThreadPoolExecutor compileQueue;
 
     private final ResolvedJavaMethod[] callNodeMethod;
     private final ResolvedJavaMethod[] callTargetMethod;
@@ -77,6 +82,20 @@
         callNodeMethod = new ResolvedJavaMethod[]{getGraalProviders().getMetaAccess().lookupJavaMethod(HotSpotFrameInstance.CallNodeFrame.METHOD)};
         callTargetMethod = new ResolvedJavaMethod[]{getGraalProviders().getMetaAccess().lookupJavaMethod(HotSpotFrameInstance.CallTargetFrame.METHOD)};
         anyFrameMethod = new ResolvedJavaMethod[]{callNodeMethod[0], callTargetMethod[0]};
+
+        // Create compilation queue.
+        CompilerThreadFactory factory = new CompilerThreadFactory("TruffleCompilerThread", new CompilerThreadFactory.DebugConfigAccess() {
+            public GraalDebugConfig getDebugConfig() {
+                if (Debug.isEnabled()) {
+                    GraalDebugConfig debugConfig = DebugEnvironment.initialize(TTY.out().out());
+                    debugConfig.dumpHandlers().add(new TruffleTreeDumpHandler());
+                    return debugConfig;
+                } else {
+                    return null;
+                }
+            }
+        });
+        compileQueue = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), factory);
     }
 
     public String getName() {
@@ -84,10 +103,7 @@
     }
 
     public RootCallTarget createCallTarget(RootNode rootNode) {
-        if (truffleCompiler == null) {
-            truffleCompiler = new TruffleCompilerImpl();
-        }
-        return new HotSpotOptimizedCallTarget(rootNode, truffleCompiler, TruffleMinInvokeThreshold.getValue(), TruffleCompilationThreshold.getValue(), acceptForCompilation(rootNode));
+        return new HotSpotOptimizedCallTarget(rootNode, this, TruffleMinInvokeThreshold.getValue(), TruffleCompilationThreshold.getValue(), acceptForCompilation(rootNode));
     }
 
     public DirectCallNode createDirectCallNode(CallTarget target) {
@@ -264,4 +280,48 @@
             return null;
         }
     }
+
+    public void compile(OptimizedCallTarget optimizedCallTarget, boolean mayBeAsynchronous) {
+        if (truffleCompiler == null) {
+            truffleCompiler = new TruffleCompilerImpl();
+        }
+        Runnable r = new Runnable() {
+            @Override
+            public void run() {
+                try (Scope s = Debug.scope("Truffle", new TruffleDebugJavaMethod(optimizedCallTarget))) {
+                    truffleCompiler.compileMethodImpl(optimizedCallTarget);
+                    optimizedCallTarget.compilationFinished(null);
+                } catch (Throwable e) {
+                    optimizedCallTarget.compilationFinished(e);
+                }
+            }
+        };
+        if (mayBeAsynchronous) {
+            Future<?> future = compileQueue.submit(r);
+            this.compilations.put(optimizedCallTarget, future);
+        } else {
+            r.run();
+        }
+    }
+
+    public boolean cancelInstalledTask(OptimizedCallTarget optimizedCallTarget) {
+        Future<?> codeTask = this.compilations.get(optimizedCallTarget);
+        if (codeTask != null && isCompiling(optimizedCallTarget)) {
+            this.compilations.remove(codeTask);
+            return codeTask.cancel(true);
+        }
+        return false;
+    }
+
+    public boolean isCompiling(OptimizedCallTarget optimizedCallTarget) {
+        Future<?> codeTask = this.compilations.get(optimizedCallTarget);
+        if (codeTask != null) {
+            if (codeTask.isCancelled() || codeTask.isDone()) {
+                this.compilations.remove(optimizedCallTarget);
+                return false;
+            }
+            return true;
+        }
+        return false;
+    }
 }
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/GraalTruffleRuntime.java	Thu Apr 17 13:17:25 2014 +0200
+++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/GraalTruffleRuntime.java	Thu Apr 17 16:25:08 2014 +0200
@@ -28,4 +28,10 @@
 public interface GraalTruffleRuntime extends TruffleRuntime {
 
     Replacements getReplacements();
+
+    void compile(OptimizedCallTarget optimizedCallTarget, boolean mayBeAsynchronous);
+
+    boolean cancelInstalledTask(OptimizedCallTarget optimizedCallTarget);
+
+    boolean isCompiling(OptimizedCallTarget optimizedCallTarget);
 }
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallTarget.java	Thu Apr 17 13:17:25 2014 +0200
+++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallTarget.java	Thu Apr 17 16:25:08 2014 +0200
@@ -188,6 +188,6 @@
 
     }
 
-    public abstract void exceptionWhileCompiling(Throwable e);
+    public abstract void compilationFinished(Throwable e);
 
 }
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompiler.java	Thu Apr 17 13:17:25 2014 +0200
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,36 +0,0 @@
-/*
- * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-package com.oracle.graal.truffle;
-
-import java.util.concurrent.*;
-
-import com.oracle.graal.api.code.*;
-
-/**
- * Interface of the Truffle compiler producing an {@link InstalledCode} object from the partial
- * evaluation starting with the AST represented by the given {@link OptimizedCallTarget} node.
- */
-public interface TruffleCompiler {
-
-    Future<InstalledCode> compile(OptimizedCallTarget node);
-}
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java	Thu Apr 17 13:17:25 2014 +0200
+++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java	Thu Apr 17 16:25:08 2014 +0200
@@ -27,14 +27,11 @@
 import static com.oracle.graal.truffle.TruffleCompilerOptions.*;
 
 import java.util.*;
-import java.util.concurrent.*;
-
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.code.Assumptions.Assumption;
 import com.oracle.graal.api.code.CallingConvention.Type;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.api.runtime.*;
-import com.oracle.graal.compiler.*;
 import com.oracle.graal.compiler.target.*;
 import com.oracle.graal.debug.*;
 import com.oracle.graal.debug.Debug.Scope;
@@ -55,7 +52,7 @@
 /**
  * Implementation of the Truffle compiler using Graal.
  */
-public class TruffleCompilerImpl implements TruffleCompiler {
+public class TruffleCompilerImpl {
 
     private final Providers providers;
     private final Suites suites;
@@ -64,7 +61,6 @@
     private final GraphBuilderConfiguration config;
     private final RuntimeProvider runtime;
     private final TruffleCache truffleCache;
-    private final ThreadPoolExecutor compileQueue;
 
     private static final Class<?>[] SKIPPED_EXCEPTION_CLASSES = new Class[]{UnexpectedResultException.class, SlowPathException.class, ArithmeticException.class};
 
@@ -78,20 +74,6 @@
         this.providers = backend.getProviders().copyWith(truffleReplacements);
         this.suites = backend.getSuites().getDefaultSuites();
 
-        // Create compilation queue.
-        CompilerThreadFactory factory = new CompilerThreadFactory("TruffleCompilerThread", new CompilerThreadFactory.DebugConfigAccess() {
-            public GraalDebugConfig getDebugConfig() {
-                if (Debug.isEnabled()) {
-                    GraalDebugConfig debugConfig = DebugEnvironment.initialize(TTY.out().out());
-                    debugConfig.dumpHandlers().add(new TruffleTreeDumpHandler());
-                    return debugConfig;
-                } else {
-                    return null;
-                }
-            }
-        });
-        compileQueue = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), factory);
-
         ResolvedJavaType[] skippedExceptionTypes = getSkippedExceptionTypes(providers.getMetaAccess());
         GraphBuilderConfiguration eagerConfig = GraphBuilderConfiguration.getEagerDefault();
         eagerConfig.setSkippedExceptionTypes(skippedExceptionTypes);
@@ -115,25 +97,11 @@
         return skippedExceptionTypes;
     }
 
-    public Future<InstalledCode> compile(final OptimizedCallTarget compilable) {
-        return compileQueue.submit(new Callable<InstalledCode>() {
-            @Override
-            public InstalledCode call() {
-                try (Scope s = Debug.scope("Truffle", new TruffleDebugJavaMethod(compilable))) {
-                    return compileMethodImpl(compilable);
-                } catch (Throwable e) {
-                    compilable.exceptionWhileCompiling(e);
-                    return null;
-                }
-            }
-        });
-    }
-
     public static final DebugTimer PartialEvaluationTime = Debug.timer("PartialEvaluationTime");
     public static final DebugTimer CompilationTime = Debug.timer("CompilationTime");
     public static final DebugTimer CodeInstallationTime = Debug.timer("CodeInstallation");
 
-    private InstalledCode compileMethodImpl(final OptimizedCallTarget compilable) {
+    public InstalledCode compileMethodImpl(final OptimizedCallTarget compilable) {
         final StructuredGraph graph;
 
         if (TraceTruffleCompilation.getValue()) {