# HG changeset patch # User Christian Humer # Date 1390994343 -3600 # Node ID 44bcfc983adb4e010f6a1662814756a2e43a84df # Parent 030e75d4d7dcdb6c50e556ce8d891ee36f6631f6# Parent 8cd953e97e2dfcb3647384f7774685059eece5ee Merge. diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.asm.ptx/src/com/oracle/graal/asm/ptx/PTXAssembler.java --- a/graal/com.oracle.graal.asm.ptx/src/com/oracle/graal/asm/ptx/PTXAssembler.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.asm.ptx/src/com/oracle/graal/asm/ptx/PTXAssembler.java Wed Jan 29 12:19:03 2014 +0100 @@ -397,13 +397,17 @@ } // Checkstyle: stop method name check - public final void bra(String tgt, int pred) { + /* + * Emit conditional branch to target 'tgt' guarded by predicate register 'pred' whose state is + * tested to be 'predCheck'. + */ + public final void bra(String tgt, int pred, boolean predCheck) { assert pred >= 0; if (tgt.equals("?")) { Thread.dumpStack(); } - emitString("@%p" + pred + " " + "bra" + " " + tgt + ";"); + emitString("@" + (predCheck ? "%p" : "!%p") + pred + " " + "bra" + " " + tgt + ";"); } public final void bra(String src) { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.compiler.hsail.test.infra/src/com/oracle/graal/compiler/hsail/test/infra/GraalKernelTester.java --- a/graal/com.oracle.graal.compiler.hsail.test.infra/src/com/oracle/graal/compiler/hsail/test/infra/GraalKernelTester.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.compiler.hsail.test.infra/src/com/oracle/graal/compiler/hsail/test/infra/GraalKernelTester.java Wed Jan 29 12:19:03 2014 +0100 @@ -27,33 +27,46 @@ * This class extends KernelTester and provides a base class * for which the HSAIL code comes from the Graal compiler. */ +import static com.oracle.graal.hotspot.HotSpotGraalRuntime.*; import static com.oracle.graal.phases.GraalOptions.*; import java.io.*; import java.lang.reflect.*; +import org.junit.*; + import com.oracle.graal.api.code.*; +import com.oracle.graal.api.meta.*; +import com.oracle.graal.compiler.target.*; import com.oracle.graal.debug.*; import com.oracle.graal.graph.*; import com.oracle.graal.hotspot.hsail.*; import com.oracle.graal.hotspot.meta.*; +import com.oracle.graal.hsail.*; import com.oracle.graal.options.*; - -import com.oracle.graal.phases.GraalOptions; -import static com.oracle.graal.options.OptionValue.OverrideScope; +import com.oracle.graal.options.OptionValue.OverrideScope; +import com.oracle.graal.phases.*; public abstract class GraalKernelTester extends KernelTester { - HSAILCompilationResult hsailCompResult; + private static HSAILHotSpotBackend getHSAILBackend() { + Backend backend = runtime().getBackend(HSAIL.class); + Assume.assumeTrue(backend instanceof HSAILHotSpotBackend); + return (HSAILHotSpotBackend) backend; + } + + ExternalCompilationResult hsailCode; private boolean showHsailSource = false; private boolean saveInFile = false; @Override public String getCompiledHSAILSource(Method method) { - if (hsailCompResult == null) { - hsailCompResult = HSAILCompilationResult.getHSAILCompilationResult(method); + if (hsailCode == null) { + HSAILHotSpotBackend backend = getHSAILBackend(); + ResolvedJavaMethod javaMethod = backend.getProviders().getMetaAccess().lookupJavaMethod(method); + hsailCode = backend.compileKernel(javaMethod, false); } - String hsailSource = hsailCompResult.getHSAILCode(); + String hsailSource = hsailCode.getCodeString(); if (showHsailSource) { logger.severe(hsailSource); } @@ -86,8 +99,8 @@ @Override protected void dispatchKernelOkra(int range, Object... args) { - HSAILCompilationResult hcr = HSAILCompilationResult.getHSAILCompilationResult(testMethod); - HotSpotNmethod code = (HotSpotNmethod) hcr.getInstalledCode(); + HSAILHotSpotBackend backend = getHSAILBackend(); + HotSpotNmethod code = backend.compileAndInstallKernel(testMethod); if (code != null) { try { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/BasicHSAILTest.java --- a/graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/BasicHSAILTest.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/BasicHSAILTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -22,14 +22,17 @@ */ package com.oracle.graal.compiler.hsail.test; +import java.lang.reflect.*; + import org.junit.*; +import com.oracle.graal.api.code.*; +import com.oracle.graal.compiler.target.*; import com.oracle.graal.compiler.test.*; import com.oracle.graal.debug.*; import com.oracle.graal.debug.Debug.Scope; import com.oracle.graal.hotspot.hsail.*; import com.oracle.graal.hsail.*; -import com.oracle.graal.nodes.*; /** * Test class for small Java methods compiled to HSAIL kernels. @@ -332,11 +335,18 @@ out[gid] = val; } + @Override + protected HSAILHotSpotBackend getBackend() { + Backend backend = super.getBackend(); + Assume.assumeTrue(backend instanceof HSAILHotSpotBackend); + return (HSAILHotSpotBackend) backend; + } + private void test(final String snippet) { try (Scope s = Debug.scope("HSAILCodeGen")) { - StructuredGraph graph = parse(snippet); - HSAILCompilationResult compResult = HSAILCompilationResult.getHSAILCompilationResult(graph); - Debug.log("HSAIL code generated for %s:%n%s", snippet, compResult.getHSAILCode()); + Method method = getMethod(snippet); + ExternalCompilationResult hsailCode = getBackend().compileKernel(getMetaAccess().lookupJavaMethod(method), false); + Debug.log("HSAIL code generated for %s:%n%s", snippet, hsailCode.getCodeString()); } catch (Throwable e) { throw Debug.handle(e); } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/StaticMethod16InArraysTest.java --- a/graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/StaticMethod16InArraysTest.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.compiler.hsail.test/src/com/oracle/graal/compiler/hsail/test/StaticMethod16InArraysTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -62,6 +62,7 @@ * there are registers. */ @Test(expected = java.lang.ClassCastException.class) + @Ignore("until GPU backends can co-exist") public void test() { DebugConfig debugConfig = DebugScope.getConfig(); DebugConfig noInterceptConfig = new DelegatingDebugConfig(debugConfig) { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.compiler.ptx.test/src/com/oracle/graal/compiler/ptx/test/ControlPTXTest.java --- a/graal/com.oracle.graal.compiler.ptx.test/src/com/oracle/graal/compiler/ptx/test/ControlPTXTest.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.compiler.ptx.test/src/com/oracle/graal/compiler/ptx/test/ControlPTXTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -26,18 +26,26 @@ public class ControlPTXTest extends PTXTest { - @Ignore("[CUDA] *** Error (status=702): Synchronize kernel") @Test - public void testControl() { + public void testControl1() { test("testLoop", 42); test("testSwitchDefault1I", 3); test("testSwitch1I", 2); test("testIfElse1I", 222); test("testIfElse2I", 19, 64); + } - test("testIntegerTestBranch2I", 0xff00, 0x00ff); + @Test + public void testControl2() { compileKernel("testStatic"); compileKernel("testCall"); + } + + @Ignore("[CUDA] Check for malformed PTX kernel or incorrect PTX compilation options") + @Test + public void testControl3() { + // test("testIntegerTestBranch2I", 0xff00, 0x00ff); + compileKernel("testIntegerTestBranch2I"); compileKernel("testLookupSwitch1I"); } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ShortCircuitNodeTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ShortCircuitNodeTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -0,0 +1,65 @@ +/* + * Copyright (c) 2011, 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.compiler.test; + +import org.junit.*; + +import com.oracle.graal.compiler.test.ea.EATestBase.TestClassInt; + +public class ShortCircuitNodeTest extends GraalCompilerTest { + + @Test + public void test1() { + // only executeActual, to avoid creating profiling information + executeActual(getMethod("test1Snippet"), 1, 2); + } + + public static final TestClassInt field = null; + public static TestClassInt field2 = null; + + @SuppressWarnings("unused") + public static void test1Snippet(int a, int b) { + /* + * if a ShortCircuitOrNode is created for the check inside test2, then faulty handling of + * guards can create a cycle in the graph. + */ + int v; + if (a == 1) { + if (b != 1) { + int i = field.x; + } + field2 = null; + v = 0; + } else { + v = 1; + } + + if (test2(v, b)) { + int i = field.x; + } + } + + public static boolean test2(int a, int b) { + return a != 0 || b != 1; + } +} diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/ForEachToGraal.java --- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/ForEachToGraal.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/ForEachToGraal.java Wed Jan 29 12:19:03 2014 +0100 @@ -23,10 +23,24 @@ package com.oracle.graal.hotspot.hsail; +import static com.oracle.graal.hotspot.HotSpotGraalRuntime.*; + +import java.lang.reflect.*; +import java.util.*; + import com.oracle.graal.api.code.*; +import com.oracle.graal.api.meta.*; import com.oracle.graal.compiler.hsail.*; +import com.oracle.graal.compiler.target.*; import com.oracle.graal.debug.*; +import com.oracle.graal.graph.iterators.*; import com.oracle.graal.hotspot.meta.*; +import com.oracle.graal.hsail.*; +import com.oracle.graal.java.*; +import com.oracle.graal.nodes.*; +import com.oracle.graal.nodes.java.*; +import com.oracle.graal.phases.*; +import com.oracle.graal.phases.util.*; /** * Implements compile and dispatch of Java code containing lambda constructs. Currently only used by @@ -34,18 +48,53 @@ */ public class ForEachToGraal implements CompileAndDispatch { - private static HSAILCompilationResult getCompiledLambda(Class consumerClass) { - return HSAILCompilationResult.getCompiledLambda(consumerClass); + private static HSAILHotSpotBackend getHSAILBackend() { + Backend backend = runtime().getBackend(HSAIL.class); + return (HSAILHotSpotBackend) backend; } - // Implementations of the CompileAndDispatch interface. + /** + * Gets a compiled and installed kernel for the lambda called by the {@code accept(int value)} + * method in a class implementing {@code java.util.function.IntConsumer}. + * + * @param intConsumerClass a class implementing {@code java.util.function.IntConsumer} + * @return a {@link HotSpotNmethod} handle to the compiled and installed kernel + */ + private static HotSpotNmethod getCompiledLambda(Class intConsumerClass) { + Method acceptMethod = null; + for (Method m : intConsumerClass.getMethods()) { + if (m.getName().equals("accept") && Arrays.equals(new Class[]{int.class}, m.getParameterTypes())) { + assert acceptMethod == null : "found more than one implementation of accept(int) in " + intConsumerClass; + acceptMethod = m; + } + } + + HSAILHotSpotBackend backend = getHSAILBackend(); + Providers providers = backend.getProviders(); + StructuredGraph graph = new StructuredGraph(((HotSpotMetaAccessProvider) providers.getMetaAccess()).lookupJavaMethod(acceptMethod)); + new GraphBuilderPhase.Instance(providers.getMetaAccess(), GraphBuilderConfiguration.getDefault(), OptimisticOptimizations.ALL).apply(graph); + NodeIterable calls = graph.getNodes(MethodCallTargetNode.class); + assert calls.count() == 1; + ResolvedJavaMethod lambdaMethod = calls.first().targetMethod(); + assert lambdaMethod.getName().startsWith("lambda$"); + Debug.log("target ... " + lambdaMethod); + + if (lambdaMethod == null) { + Debug.log("Did not find call in accept()"); + return null; + } + + ExternalCompilationResult hsailCode = backend.compileKernel(lambdaMethod, true); + return backend.installKernel(lambdaMethod, hsailCode); + } + @Override public Object createKernel(Class consumerClass) { try { return getCompiledLambda(consumerClass); } catch (Throwable e) { - // Note: Graal throws Errors. We want to revert to regular Java in these cases. - Debug.log("WARNING:Graal compilation failed."); + // If Graal compilation throws an exception, we want to revert to regular Java + Debug.log("WARNING: Graal compilation failed"); e.printStackTrace(); return null; } @@ -53,16 +102,14 @@ @Override public boolean dispatchKernel(Object kernel, int jobSize, Object[] args) { - // kernel is an HSAILCompilationResult - HotSpotNmethod code = (HotSpotNmethod) ((HSAILCompilationResult) kernel).getInstalledCode(); - + HotSpotNmethod code = (HotSpotNmethod) kernel; if (code != null) { try { // No return value from HSAIL kernels code.executeParallel(jobSize, 0, 0, args); return true; } catch (InvalidInstalledCodeException iice) { - Debug.log("WARNING:Invalid installed code at exec time." + iice); + Debug.log("WARNING: Invalid installed code at exec time." + iice); iice.printStackTrace(); return false; } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILCompilationResult.java --- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILCompilationResult.java Tue Jan 28 19:37:26 2014 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,182 +0,0 @@ -/* - * Copyright (c) 2009, 2012, 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.hotspot.hsail; - -import static com.oracle.graal.compiler.GraalCompiler.*; -import static com.oracle.graal.hotspot.HotSpotGraalRuntime.*; - -import java.lang.reflect.*; - -import com.oracle.graal.api.code.*; -import com.oracle.graal.api.code.CallingConvention.Type; -import com.oracle.graal.api.meta.*; -import com.oracle.graal.api.runtime.*; -import com.oracle.graal.debug.*; -import com.oracle.graal.graph.*; -import com.oracle.graal.graph.iterators.*; -import com.oracle.graal.hotspot.*; -import com.oracle.graal.hotspot.bridge.*; -import com.oracle.graal.hotspot.meta.*; -import com.oracle.graal.hsail.*; -import com.oracle.graal.java.*; -import com.oracle.graal.lir.asm.*; -import com.oracle.graal.nodes.*; -import com.oracle.graal.nodes.java.*; -import com.oracle.graal.phases.*; -import com.oracle.graal.phases.common.*; -import com.oracle.graal.phases.tiers.*; -import com.oracle.graal.phases.util.*; -import com.oracle.graal.runtime.*; - -/** - * Class that represents a HSAIL compilation result. Includes the compiled HSAIL code. - */ -public class HSAILCompilationResult extends ExternalCompilationResult { - - private static final long serialVersionUID = -4178700465275724625L; - - private static CompilerToGPU toGPU = HotSpotGraalRuntime.runtime().getCompilerToGPU(); - private static boolean validDevice = toGPU.deviceInit(); - - // The installedCode is the executable representation of the kernel in the code cache - private InstalledCode installedCode; - - public void setInstalledCode(InstalledCode newCode) { - installedCode = newCode; - } - - public InstalledCode getInstalledCode() { - return installedCode; - } - - static final HSAILHotSpotBackend backend; - static { - // Look for installed HSAIL backend - RuntimeProvider runtime = Graal.getRequiredCapability(RuntimeProvider.class); - HSAILHotSpotBackend b = (HSAILHotSpotBackend) runtime.getBackend(HSAIL.class); - if (b == null) { - // Fall back to a new instance - b = new HSAILHotSpotBackendFactory().createBackend(runtime(), runtime().getHostBackend()); - b.completeInitialization(); - } - backend = b; - } - - public static HSAILCompilationResult getHSAILCompilationResult(Method meth) { - HotSpotMetaAccessProvider metaAccess = backend.getProviders().getMetaAccess(); - ResolvedJavaMethod javaMethod = metaAccess.lookupJavaMethod(meth); - return getHSAILCompilationResult(javaMethod); - } - - public static HSAILCompilationResult getHSAILCompilationResult(ResolvedJavaMethod javaMethod) { - HotSpotMetaAccessProvider metaAccess = backend.getProviders().getMetaAccess(); - StructuredGraph graph = new StructuredGraph(javaMethod); - new GraphBuilderPhase.Instance(metaAccess, GraphBuilderConfiguration.getEagerDefault(), OptimisticOptimizations.ALL).apply(graph); - return getHSAILCompilationResult(graph); - } - - public static HSAILCompilationResult getCompiledLambda(Class consumerClass) { - /** - * Find the accept() method in the IntConsumer, then use Graal API to find the target lambda - * that accept will call. - */ - Method[] icMethods = consumerClass.getMethods(); - Method acceptMethod = null; - for (Method m : icMethods) { - if (m.getName().equals("accept") && acceptMethod == null) { - acceptMethod = m; - break; - } - } - - Providers providers = backend.getProviders(); - HotSpotMetaAccessProvider metaAccess = (HotSpotMetaAccessProvider) providers.getMetaAccess(); - ResolvedJavaMethod rm = metaAccess.lookupJavaMethod(acceptMethod); - StructuredGraph graph = new StructuredGraph(rm); - new GraphBuilderPhase.Instance(providers.getMetaAccess(), GraphBuilderConfiguration.getDefault(), OptimisticOptimizations.ALL).apply(graph); - NodeIterable nin = graph.getNodes(); - ResolvedJavaMethod lambdaMethod = null; - for (Node n : nin) { - if (n instanceof MethodCallTargetNode) { - lambdaMethod = ((MethodCallTargetNode) n).targetMethod(); - Debug.log("target ... " + lambdaMethod); - break; - } - } - if (lambdaMethod == null) { - // Did not find call in Consumer.accept. - Debug.log("Should not Reach here, did not find call in accept()"); - return null; - } - // Now that we have the target lambda, compile it. - HSAILCompilationResult hsailCompResult = HSAILCompilationResult.getHSAILCompilationResult(lambdaMethod); - return hsailCompResult; - } - - public static HSAILCompilationResult getHSAILCompilationResult(StructuredGraph graph) { - Debug.dump(graph, "Graph"); - Providers providers = backend.getProviders(); - TargetDescription target = providers.getCodeCache().getTarget(); - PhaseSuite graphBuilderSuite = backend.getSuites().getDefaultGraphBuilderSuite().copy(); - graphBuilderSuite.appendPhase(new NonNullParametersPhase()); - CallingConvention cc = CodeUtil.getCallingConvention(providers.getCodeCache(), Type.JavaCallee, graph.method(), false); - SuitesProvider suitesProvider = backend.getSuites(); - try { - HSAILCompilationResult compResult = compileGraph(graph, cc, graph.method(), providers, backend, target, null, graphBuilderSuite, OptimisticOptimizations.NONE, getProfilingInfo(graph), - null, suitesProvider.getDefaultSuites(), true, new HSAILCompilationResult(), CompilationResultBuilderFactory.Default); - if ((validDevice) && (compResult.getTargetCode() != null)) { - long kernel = toGPU.generateKernel(compResult.getTargetCode(), graph.method().getName()); - - if (kernel == 0) { - throw new GraalInternalError("Failed to compile kernel."); - } - - ((ExternalCompilationResult) compResult).setEntryPoint(kernel); - HotSpotResolvedJavaMethod compiledMethod = (HotSpotResolvedJavaMethod) graph.method(); - InstalledCode installedCode = ((HotSpotCodeCacheProvider) providers.getCodeCache()).addExternalMethod(compiledMethod, compResult); - compResult.setInstalledCode(installedCode); - } - return compResult; - } catch (InvalidInstalledCodeException e) { - e.printStackTrace(); - return null; - } catch (GraalInternalError e) { - String partialCode = backend.getPartialCodeString(); - if (partialCode != null && !partialCode.equals("")) { - Debug.log("-------------------\nPartial Code Generation:\n--------------------"); - Debug.log(partialCode); - Debug.log("-------------------\nEnd of Partial Code Generation\n--------------------"); - } - throw e; - } - } - - protected HSAILCompilationResult() { - } - - public String getHSAILCode() { - return new String(getTargetCode(), 0, getTargetCodeSize()); - } - -} diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackend.java --- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackend.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackend.java Wed Jan 29 12:19:03 2014 +0100 @@ -23,25 +23,34 @@ package com.oracle.graal.hotspot.hsail; import static com.oracle.graal.api.code.CallingConvention.Type.*; +import static com.oracle.graal.api.code.CodeUtil.*; import static com.oracle.graal.api.code.ValueUtil.*; +import static com.oracle.graal.compiler.GraalCompiler.*; import java.lang.reflect.*; import java.util.*; import com.oracle.graal.api.code.*; +import com.oracle.graal.api.code.CallingConvention.Type; import com.oracle.graal.api.meta.*; import com.oracle.graal.asm.*; import com.oracle.graal.asm.hsail.*; import com.oracle.graal.compiler.gen.*; import com.oracle.graal.debug.*; +import com.oracle.graal.debug.Debug.Scope; +import com.oracle.graal.graph.*; import com.oracle.graal.hotspot.*; import com.oracle.graal.hotspot.meta.*; import com.oracle.graal.hsail.*; +import com.oracle.graal.java.*; import com.oracle.graal.lir.*; import com.oracle.graal.lir.asm.*; import com.oracle.graal.lir.hsail.*; import com.oracle.graal.nodes.*; -import com.oracle.graal.nodes.spi.Replacements; +import com.oracle.graal.nodes.spi.*; +import com.oracle.graal.phases.*; +import com.oracle.graal.phases.common.*; +import com.oracle.graal.phases.tiers.*; import com.oracle.graal.replacements.hsail.*; /** @@ -85,6 +94,60 @@ } /** + * Compiles and installs a given method to a GPU binary. + */ + public HotSpotNmethod compileAndInstallKernel(Method method) { + ResolvedJavaMethod javaMethod = getProviders().getMetaAccess().lookupJavaMethod(method); + return installKernel(javaMethod, compileKernel(javaMethod, true)); + } + + /** + * Compiles a given method to HSAIL code. + * + * @param makeBinary specifies whether a GPU binary should also be generated for the HSAIL code. + * If true, the returned value is guaranteed to have a non-zero + * {@linkplain ExternalCompilationResult#getEntryPoint() entry point}. + * @return the HSAIL code compiled from {@code method}'s bytecode + */ + public ExternalCompilationResult compileKernel(ResolvedJavaMethod method, boolean makeBinary) { + StructuredGraph graph = new StructuredGraph(method); + HotSpotProviders providers = getProviders(); + new GraphBuilderPhase.Instance(providers.getMetaAccess(), GraphBuilderConfiguration.getEagerDefault(), OptimisticOptimizations.ALL).apply(graph); + PhaseSuite graphBuilderSuite = providers.getSuites().getDefaultGraphBuilderSuite(); + graphBuilderSuite.appendPhase(new NonNullParametersPhase()); + CallingConvention cc = getCallingConvention(providers.getCodeCache(), Type.JavaCallee, graph.method(), false); + Suites suites = providers.getSuites().getDefaultSuites(); + ExternalCompilationResult hsailCode = compileGraph(graph, cc, method, providers, this, this.getTarget(), null, graphBuilderSuite, OptimisticOptimizations.NONE, getProfilingInfo(graph), + new SpeculationLog(), suites, true, new ExternalCompilationResult(), CompilationResultBuilderFactory.Default); + + if (makeBinary) { + try (Scope ds = Debug.scope("GeneratingKernelBinary")) { + long kernel = getRuntime().getCompilerToGPU().generateKernel(hsailCode.getTargetCode(), method.getName()); + if (kernel == 0) { + throw new GraalInternalError("Failed to compile HSAIL kernel"); + } + hsailCode.setEntryPoint(kernel); + } catch (Throwable e) { + throw Debug.handle(e); + } + } + return hsailCode; + } + + /** + * Installs the {@linkplain ExternalCompilationResult#getEntryPoint() GPU binary} associated + * with some given HSAIL code in the code cache and returns a {@link HotSpotNmethod} handle to + * the installed code. + * + * @param hsailCode HSAIL compilation result for which a GPU binary has been generated + * @return a handle to the binary as installed in the HotSpot code cache + */ + public final HotSpotNmethod installKernel(ResolvedJavaMethod method, ExternalCompilationResult hsailCode) { + assert hsailCode.getEntryPoint() != 0L; + return getProviders().getCodeCache().addExternalMethod(method, hsailCode); + } + + /** * Use the HSAIL register set when the compilation target is HSAIL. */ @Override diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackendFactory.java --- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackendFactory.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackendFactory.java Wed Jan 29 12:19:03 2014 +0100 @@ -28,6 +28,7 @@ import com.oracle.graal.hotspot.*; import com.oracle.graal.hotspot.meta.*; import com.oracle.graal.hsail.*; +import com.oracle.graal.java.*; import com.oracle.graal.nodes.spi.*; import com.oracle.graal.phases.tiers.*; import com.oracle.graal.phases.util.*; @@ -51,7 +52,7 @@ Providers p = new Providers(metaAccess, codeCache, constantReflection, foreignCalls, lowerer, null); Replacements replacements = new HSAILHotSpotReplacementsImpl(p, assumptions, codeCache.getTarget(), host.getReplacements()); HotSpotDisassemblerProvider disassembler = host.getDisassembler(); - SuitesProvider suites = host.getSuites(); + SuitesProvider suites = new DefaultSuitesProvider(); HotSpotProviders providers = new HotSpotProviders(metaAccess, codeCache, constantReflection, foreignCalls, lowerer, replacements, disassembler, suites, registers); return new HSAILHotSpotBackend(runtime, providers); diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotBackend.java --- a/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotBackend.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotBackend.java Wed Jan 29 12:19:03 2014 +0100 @@ -155,7 +155,8 @@ } private boolean canOffloadToGPU(ResolvedJavaMethod method) { - return method.getName().contains("lambda$") & method.isSynthetic(); + HotSpotVMConfig config = getRuntime().getConfig(); + return config.gpuOffload && method.getName().contains("lambda$") & method.isSynthetic(); } }; } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java Wed Jan 29 12:19:03 2014 +0100 @@ -39,12 +39,19 @@ private static final long serialVersionUID = -4744897993263044184L; - private static boolean containsString(String[] array, String item) { - if (array == null) { - return false; + /** + * Determines if the current architecture is included in a given architecture set specification. + * + * @param currentArch + * @param archsSpecification specifies a set of architectures. A zero length value implies all + * architectures. + */ + private static boolean isRequired(String currentArch, String[] archsSpecification) { + if (archsSpecification.length == 0) { + return true; } - for (String arch : array) { - if (arch.equals(item)) { + for (String arch : archsSpecification) { + if (arch.equals(currentArch)) { return true; } } @@ -90,7 +97,7 @@ String type = annotation.type(); VMFields.Field entry = vmFields.get(name); if (entry == null) { - if (annotation.optional() || !containsString(annotation.archs(), currentArch)) { + if (annotation.optional() || !isRequired(currentArch, annotation.archs())) { continue; } throw new IllegalArgumentException("field not found: " + name); @@ -135,11 +142,10 @@ String name = annotation.name(); AbstractConstant entry = vmConstants.get(name); if (entry == null) { - if (!containsString(annotation.archs(), currentArch)) { + if (!isRequired(currentArch, annotation.archs())) { continue; - } else { - throw new IllegalArgumentException("constant not found: " + name); } + throw new IllegalArgumentException("constant not found: " + name); } setField(f, entry.getValue()); } else if (f.isAnnotationPresent(HotSpotVMFlag.class)) { @@ -147,11 +153,11 @@ String name = annotation.name(); Flags.Flag entry = flags.get(name); if (entry == null) { - if (annotation.optional() || !containsString(annotation.archs(), currentArch)) { + if (!isRequired(currentArch, annotation.archs())) { continue; - } else { - throw new IllegalArgumentException("flag not found: " + name); } + throw new IllegalArgumentException("flag not found: " + name); + } setField(f, entry.getValue()); } @@ -712,6 +718,7 @@ @HotSpotVMFlag(name = "PrintInlining") @Stable public boolean printInlining; @HotSpotVMFlag(name = "GraalUseFastLocking") @Stable public boolean useFastLocking; @HotSpotVMFlag(name = "ForceUnreachable") @Stable public boolean forceUnreachable; + @HotSpotVMFlag(name = "GPUOffload") @Stable public boolean gpuOffload; @HotSpotVMFlag(name = "UseTLAB") @Stable public boolean useTLAB; @HotSpotVMFlag(name = "UseBiasedLocking") @Stable public boolean useBiasedLocking; @@ -832,8 +839,6 @@ @HotSpotVMField(name = "JavaThread::_vm_result", type = "oop", get = HotSpotVMField.Type.OFFSET) @Stable public int threadObjectResultOffset; @HotSpotVMField(name = "JavaThread::_graal_counters[0]", type = "jlong", get = HotSpotVMField.Type.OFFSET, optional = true) @Stable public int graalCountersThreadOffset; - @HotSpotVMConstant(name = "GRAAL_COUNTERS_SIZE") @Stable public int graalCountersSize; - /** * This field is used to pass exception objects into and out of the runtime system during * exception handling for compiled code. @@ -1267,6 +1272,8 @@ @Stable public long arithmeticTanAddress; @Stable public long loadAndClearExceptionAddress; + @Stable public int graalCountersSize; + @HotSpotVMConstant(name = "Deoptimization::Reason_none") @Stable public int deoptReasonNone; @HotSpotVMConstant(name = "Deoptimization::Reason_null_check") @Stable public int deoptReasonNullCheck; @HotSpotVMConstant(name = "Deoptimization::Reason_range_check") @Stable public int deoptReasonRangeCheck; diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConstant.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConstant.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConstant.java Wed Jan 29 12:19:03 2014 +0100 @@ -32,7 +32,8 @@ /** * List of architectures where this constant is required. Names are derived from - * {@link HotSpotVMConfig#getHostArchitectureName()}. + * {@link HotSpotVMConfig#getHostArchitectureName()}. An empty list implies that the constant is + * required on all architectures. */ String[] archs() default {}; diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMField.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMField.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMField.java Wed Jan 29 12:19:03 2014 +0100 @@ -40,7 +40,8 @@ /** * List of architectures where this constant is required. Names are derived from - * {@link HotSpotVMConfig#getHostArchitectureName()}. + * {@link HotSpotVMConfig#getHostArchitectureName()}. An empty list implies that the constant is + * required on all architectures. */ String[] archs() default {}; diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMFlag.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMFlag.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMFlag.java Wed Jan 29 12:19:03 2014 +0100 @@ -32,7 +32,8 @@ /** * List of architectures where this constant is required. Names are derived from - * {@link HotSpotVMConfig#getHostArchitectureName()}. + * {@link HotSpotVMConfig#getHostArchitectureName()}. An empty list implies that the constant is + * required on all architectures. */ String[] archs() default {}; diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/debug/BenchmarkCounters.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/debug/BenchmarkCounters.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/debug/BenchmarkCounters.java Wed Jan 29 12:19:03 2014 +0100 @@ -107,7 +107,7 @@ public static int getIndex(DynamicCounterNode counter) { if (!enabled) { - throw new GraalInternalError("counter nodes shouldn't exist when counters are not enabled"); + throw new GraalInternalError("counter nodes shouldn't exist when counters are not enabled: " + counter.getGroup() + ", " + counter.getName()); } String name = counter.getName(); String group = counter.getGroup(); @@ -332,12 +332,15 @@ if (index >= config.graalCountersSize) { throw new GraalInternalError("too many counters, reduce number of counters or increase GRAAL_COUNTERS_SIZE (current value: " + config.graalCountersSize + ")"); } - ConstantLocationNode location = ConstantLocationNode.create(LocationIdentity.ANY_LOCATION, Kind.Long, config.graalCountersThreadOffset + Unsafe.ARRAY_LONG_INDEX_SCALE * index, graph); - ReadNode read = graph.add(new ReadNode(thread, location, StampFactory.forKind(Kind.Long), BarrierType.NONE, false)); + ConstantLocationNode arrayLocation = ConstantLocationNode.create(LocationIdentity.ANY_LOCATION, Kind.Long, config.graalCountersThreadOffset, graph); + ReadNode readArray = graph.add(new ReadNode(thread, arrayLocation, StampFactory.forKind(wordKind), BarrierType.NONE, false)); + ConstantLocationNode location = ConstantLocationNode.create(LocationIdentity.ANY_LOCATION, Kind.Long, Unsafe.ARRAY_LONG_INDEX_SCALE * index, graph); + ReadNode read = graph.add(new ReadNode(readArray, location, StampFactory.forKind(Kind.Long), BarrierType.NONE, false)); IntegerAddNode add = graph.unique(new IntegerAddNode(Kind.Long, read, counter.getIncrement())); - WriteNode write = graph.add(new WriteNode(thread, add, location, BarrierType.NONE, false)); + WriteNode write = graph.add(new WriteNode(readArray, add, location, BarrierType.NONE, false)); graph.addBeforeFixed(counter, thread); + graph.addBeforeFixed(counter, readArray); graph.addBeforeFixed(counter, read); graph.addBeforeFixed(counter, write); } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaField.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaField.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaField.java Wed Jan 29 12:19:03 2014 +0100 @@ -198,9 +198,9 @@ Object object = receiver.asObject(); // Canonicalization may attempt to process an unsafe read before - // processing a guard (e.g. a type check) for this read - // so we need to type check the object being read - if (isInObject(object)) { + // processing a guard (e.g. a null check or a type check) for this read + // so we need to check the object being read + if (object != null && isInObject(object)) { if (Modifier.isFinal(getModifiers())) { Constant value = readValue(receiver); if (assumeNonStaticFinalFieldsAsFinal(object.getClass()) || !value.isDefaultForKind()) { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod.java Wed Jan 29 12:19:03 2014 +0100 @@ -157,10 +157,18 @@ return getMetaspaceMethodConstant(); } + /** + * Gets the complete set of modifiers for this method which includes the JVM specification + * modifiers as well as the HotSpot internal modifiers. + */ + public int getAllModifiers() { + HotSpotVMConfig config = runtime().getConfig(); + return unsafe.getInt(metaspaceMethod + config.methodAccessFlagsOffset); + } + @Override public int getModifiers() { - HotSpotVMConfig config = runtime().getConfig(); - return unsafe.getInt(metaspaceMethod + config.methodAccessFlagsOffset) & Modifier.methodModifiers(); + return getAllModifiers() & Modifier.methodModifiers(); } @Override @@ -424,27 +432,23 @@ return javaMethod == null ? null : javaMethod.getAnnotation(annotationClass); } + private static final int SYNTHETIC; + static { + try { + // Unfortunately, Modifier.SYNTHETIC is not public so we have + // to jump though hoops to get it. + Field field = Modifier.class.getDeclaredField("SYNTHETIC"); + field.setAccessible(true); + SYNTHETIC = field.getInt(null); + } catch (IllegalArgumentException | IllegalAccessException | NoSuchFieldException | SecurityException e) { + throw GraalInternalError.shouldNotReachHere(e.toString()); + } + } + @Override public boolean isSynthetic() { - if (isConstructor()) { - Constructor javaConstructor = toJavaConstructor(); - return javaConstructor == null ? false : javaConstructor.isSynthetic(); - } - - // Cannot use toJava() as it ignores the return type - HotSpotSignature sig = getSignature(); - JavaType[] sigTypes = MetaUtil.signatureToTypes(sig, null); - MetaAccessProvider metaAccess = runtime().getHostProviders().getMetaAccess(); - for (Method method : holder.mirror().getDeclaredMethods()) { - if (method.getName().equals(name)) { - if (metaAccess.lookupJavaType(method.getReturnType()).equals(sig.getReturnType(holder))) { - if (matches(metaAccess, sigTypes, method.getParameterTypes())) { - return method.isSynthetic(); - } - } - } - } - return false; + int modifiers = getAllModifiers(); + return (SYNTHETIC & modifiers) != 0; } public boolean isDefault() { @@ -476,18 +480,6 @@ return result; } - private static boolean matches(MetaAccessProvider metaAccess, JavaType[] sigTypes, Class[] parameterTypes) { - if (parameterTypes.length == sigTypes.length) { - for (int i = 0; i < parameterTypes.length; i++) { - if (!metaAccess.lookupJavaType(parameterTypes[i]).equals(sigTypes[i])) { - return false; - } - } - return true; - } - return false; - } - private Method toJava() { try { return holder.mirror().getDeclaredMethod(name, signatureToTypes()); diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/phases/OnStackReplacementPhase.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/phases/OnStackReplacementPhase.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/phases/OnStackReplacementPhase.java Wed Jan 29 12:19:03 2014 +0100 @@ -78,10 +78,7 @@ ProxyNode proxy = (ProxyNode) usage; proxy.replaceAndDelete(proxy.value()); } - FixedNode next = osr.next(); - osr.setNext(null); - ((FixedWithNextNode) osr.predecessor()).setNext(next); - GraphUtil.killWithUnusedFloatingInputs(osr); + GraphUtil.removeFixedWithUnusedInputs(osr); Debug.dump(graph, "OnStackReplacement loop peeling result"); } while (true); diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java --- a/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java Wed Jan 29 12:19:03 2014 +0100 @@ -1711,7 +1711,11 @@ ResolvedJavaType resolvedCatchType = (ResolvedJavaType) catchType; for (ResolvedJavaType skippedType : graphBuilderConfig.getSkippedExceptionTypes()) { if (skippedType.isAssignableFrom(resolvedCatchType)) { - append(new DeoptimizeNode(InvalidateReprofile, UnreachedCode)); + Block nextBlock = block.successors.size() == 1 ? unwindBlock(block.deoptBci) : block.successors.get(1); + ValueNode exception = frameState.stackAt(0); + FixedNode trueSuccessor = currentGraph.add(new DeoptimizeNode(InvalidateReprofile, UnreachedCode)); + FixedNode nextDispatch = createTarget(nextBlock, frameState); + append(new IfNode(currentGraph.unique(new InstanceOfNode((ResolvedJavaType) catchType, exception, null)), trueSuccessor, nextDispatch, 0)); return; } } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.lir.ptx/src/com/oracle/graal/lir/ptx/PTXControlFlow.java --- a/graal/com.oracle.graal.lir.ptx/src/com/oracle/graal/lir/ptx/PTXControlFlow.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.lir.ptx/src/com/oracle/graal/lir/ptx/PTXControlFlow.java Wed Jan 29 12:19:03 2014 +0100 @@ -86,9 +86,9 @@ @Override public void emitCode(CompilationResultBuilder crb, PTXMacroAssembler masm) { if (crb.isSuccessorEdge(trueDestination)) { - masm.bra(masm.nameOf(falseDestination.label()), predRegNum); + masm.bra(masm.nameOf(falseDestination.label()), predRegNum, false); } else { - masm.bra(masm.nameOf(trueDestination.label())); + masm.bra(masm.nameOf(trueDestination.label()), predRegNum, true); if (!crb.isSuccessorEdge(falseDestination)) { masm.jmp(falseDestination.label()); } @@ -238,7 +238,7 @@ default: throw new GraalInternalError("switch only supported for int, long and object"); } - masm.bra(masm.nameOf(target), predRegNum); + masm.bra(masm.nameOf(target), predRegNum, true); } }; strategy.run(closure); @@ -281,7 +281,7 @@ // Jump to default target if index is not within the jump table if (defaultTarget != null) { - masm.bra(masm.nameOf(defaultTarget.label()), predRegNum); + masm.bra(masm.nameOf(defaultTarget.label()), predRegNum, true); } // address of jump table diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/LoopBeginNode.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/LoopBeginNode.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/LoopBeginNode.java Wed Jan 29 12:19:03 2014 +0100 @@ -31,6 +31,7 @@ import com.oracle.graal.graph.spi.*; import com.oracle.graal.nodes.extended.*; import com.oracle.graal.nodes.spi.*; +import com.oracle.graal.nodes.util.*; public class LoopBeginNode extends MergeNode implements IterableNodeType, LIRLowerable { @@ -184,7 +185,11 @@ public void removeExits() { for (LoopExitNode loopexit : loopExits().snapshot()) { loopexit.removeProxies(); + FrameState stateAfter = loopexit.stateAfter(); graph().replaceFixedWithFixed(loopexit, graph().add(new BeginNode())); + if (stateAfter != null && stateAfter.isAlive() && stateAfter.usages().isEmpty()) { + GraphUtil.killWithUnusedFloatingInputs(stateAfter); + } } } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadFieldNode.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadFieldNode.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadFieldNode.java Wed Jan 29 12:19:03 2014 +0100 @@ -74,6 +74,9 @@ return phi; } } + if (!isStatic() && object().isNullConstant()) { + return graph().add(new DeoptimizeNode(DeoptimizationAction.None, DeoptimizationReason.NullCheckException)); + } return this; } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/MonitorEnterNode.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/MonitorEnterNode.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/MonitorEnterNode.java Wed Jan 29 12:19:03 2014 +0100 @@ -23,6 +23,7 @@ package com.oracle.graal.nodes.java; import com.oracle.graal.api.meta.*; +import com.oracle.graal.graph.*; import com.oracle.graal.nodes.*; import com.oracle.graal.nodes.extended.*; import com.oracle.graal.nodes.spi.*; @@ -30,7 +31,7 @@ /** * The {@code MonitorEnterNode} represents the acquisition of a monitor. */ -public final class MonitorEnterNode extends AccessMonitorNode implements Virtualizable, Lowerable, MonitorEnter, MemoryCheckpoint.Single { +public final class MonitorEnterNode extends AccessMonitorNode implements Virtualizable, Lowerable, IterableNodeType, MonitorEnter, MemoryCheckpoint.Single { /** * Creates a new MonitorEnterNode. diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/util/GraphUtil.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/util/GraphUtil.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/util/GraphUtil.java Wed Jan 29 12:19:03 2014 +0100 @@ -137,6 +137,13 @@ } } + public static void removeFixedWithUnusedInputs(FixedWithNextNode fixed) { + FixedNode next = fixed.next(); + fixed.setNext(null); + fixed.replaceAtPredecessor(next); + killWithUnusedFloatingInputs(fixed); + } + public static void checkRedundantPhi(PhiNode phiNode) { if (phiNode.isDeleted() || phiNode.valueCount() == 1) { return; diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/LockEliminationPhase.java --- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/LockEliminationPhase.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/LockEliminationPhase.java Wed Jan 29 12:19:03 2014 +0100 @@ -36,19 +36,8 @@ if (next instanceof MonitorEnterNode) { MonitorEnterNode monitorEnterNode = (MonitorEnterNode) next; if (monitorEnterNode.object() == node.object()) { - FixedNode monitorEnterSuccessor = monitorEnterNode.next(); - monitorEnterNode.setNext(null); - ((FixedWithNextNode) node.predecessor()).setNext(monitorEnterSuccessor); - FrameState stateAfterFirst = node.stateAfter(); - FrameState stateAfterSecond = monitorEnterNode.stateAfter(); - node.safeDelete(); - monitorEnterNode.safeDelete(); - if (stateAfterFirst.usages().isEmpty()) { - GraphUtil.killWithUnusedFloatingInputs(stateAfterFirst); - } - if (stateAfterSecond.usages().isEmpty()) { - GraphUtil.killWithUnusedFloatingInputs(stateAfterSecond); - } + GraphUtil.removeFixedWithUnusedInputs(monitorEnterNode); + GraphUtil.removeFixedWithUnusedInputs(node); } } } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/GraphOrder.java --- a/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/GraphOrder.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/GraphOrder.java Wed Jan 29 12:19:03 2014 +0100 @@ -55,7 +55,7 @@ if (input instanceof FrameState && node instanceof StateSplit && input == ((StateSplit) node).stateAfter()) { // nothing to do - after frame states are known, allowed cycles } else { - assert false : "cycle detected: " + node + " -> " + input; + assert false : "unexpected cycle detected at input " + node + " -> " + input; } } } @@ -81,7 +81,7 @@ private static void visitForward(ArrayList nodes, NodeBitMap visited, Node node, boolean floatingOnly) { if (node != null && !visited.isMarked(node)) { - assert !floatingOnly || !(node instanceof FixedNode) : "unexpected reference to fixed node: " + node; + assert !floatingOnly || !(node instanceof FixedNode) : "unexpected reference to fixed node: " + node + " (this indicates an unexpected cycle)"; visited.mark(node); FrameState stateAfter = null; if (node instanceof StateSplit) { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/SnippetTemplate.java --- a/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/SnippetTemplate.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/SnippetTemplate.java Wed Jan 29 12:19:03 2014 +0100 @@ -569,11 +569,7 @@ LoopTransformations.fullUnroll(loop, phaseContext, new CanonicalizerPhase(true)); new CanonicalizerPhase(true).applyIncremental(snippetCopy, phaseContext, mark); } - FixedNode explodeLoopNext = explodeLoop.next(); - explodeLoop.clearSuccessors(); - explodeLoop.replaceAtPredecessor(explodeLoopNext); - explodeLoop.replaceAtUsages(null); - GraphUtil.killCFG(explodeLoop); + GraphUtil.removeFixedWithUnusedInputs(explodeLoop); exploded = true; } } while (exploded); diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/nodes/MacroNode.java --- a/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/nodes/MacroNode.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/nodes/MacroNode.java Wed Jan 29 12:19:03 2014 +0100 @@ -24,8 +24,6 @@ import static java.lang.reflect.Modifier.*; -import java.lang.reflect.*; - import com.oracle.graal.api.meta.*; import com.oracle.graal.debug.*; import com.oracle.graal.debug.Debug.Scope; @@ -47,6 +45,7 @@ private final int bci; private final ResolvedJavaMethod targetMethod; private final JavaType returnType; + private final InvokeKind invokeKind; protected MacroNode(Invoke invoke) { super(invoke.asNode().stamp(), invoke.stateAfter()); @@ -55,6 +54,7 @@ this.bci = invoke.bci(); this.targetMethod = methodCallTarget.targetMethod(); this.returnType = methodCallTarget.returnType(); + this.invokeKind = methodCallTarget.invokeKind(); } public int getBci() { @@ -148,17 +148,21 @@ } } - private InvokeNode replaceWithInvoke() { + protected InvokeNode replaceWithInvoke() { InvokeNode invoke = createInvoke(); graph().replaceFixedWithFixed(this, invoke); return invoke; } protected InvokeNode createInvoke() { - InvokeKind invokeKind = Modifier.isStatic(targetMethod.getModifiers()) ? InvokeKind.Static : InvokeKind.Special; MethodCallTargetNode callTarget = graph().add(new MethodCallTargetNode(invokeKind, targetMethod, arguments.toArray(new ValueNode[arguments.size()]), returnType)); InvokeNode invoke = graph().add(new InvokeNode(callTarget, bci)); - invoke.setStateAfter(stateAfter()); + if (stateAfter() != null) { + invoke.setStateAfter(stateAfter().duplicate()); + if (kind() != Kind.Void) { + invoke.stateAfter().replaceFirstInput(this, invoke); + } + } return invoke; } diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/ControlFlowExceptionPartialEvaluationTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/ControlFlowExceptionPartialEvaluationTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -0,0 +1,102 @@ +/* + * Copyright (c) 2014, 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.test; + +import org.junit.*; + +import com.oracle.graal.truffle.test.nodes.*; +import com.oracle.truffle.api.frame.*; +import com.oracle.truffle.api.nodes.*; + +@Ignore("Currently ignored due to problems with code coverage tools.") +public class ControlFlowExceptionPartialEvaluationTest extends PartialEvaluationTest { + + public static Object constant42() { + return 42; + } + + @Test + public void catchControlFlowException() { + FrameDescriptor fd = new FrameDescriptor(); + AbstractTestNode result = new CatchControlFlowExceptionTestNode(new ThrowControlFlowExceptionTestNode()); + assertPartialEvalEquals("constant42", new RootTestNode(fd, "catchControlFlowException", result)); + } + + @Test + public void catchSlowPathAndControlFlowException() { + FrameDescriptor fd = new FrameDescriptor(); + AbstractTestNode result = new CatchSlowPathAndControlFlowExceptionTestNode(new ThrowControlFlowExceptionTestNode()); + assertPartialEvalEquals("constant42", new RootTestNode(fd, "catchSlowPathAndControlFlowException", result)); + } + + public static class ThrowControlFlowExceptionTestNode extends AbstractTestNode { + + @Override + public int execute(VirtualFrame frame) { + throw new ControlFlowException(); + } + } + + public static class CatchControlFlowExceptionTestNode extends AbstractTestNode { + + @Child private AbstractTestNode child; + + public CatchControlFlowExceptionTestNode(AbstractTestNode child) { + this.child = adoptChild(child); + } + + @Override + public int execute(VirtualFrame frame) { + try { + return child.execute(frame); + } catch (ControlFlowException e) { + return 42; + } + } + } + + public static class CatchSlowPathAndControlFlowExceptionTestNode extends AbstractTestNode { + + @Child private AbstractTestNode child; + + public CatchSlowPathAndControlFlowExceptionTestNode(AbstractTestNode child) { + this.child = adoptChild(child); + } + + @Override + public int execute(VirtualFrame frame) { + try { + return executeChild(frame); + } catch (SlowPathException spe) { + return -1; + } catch (ControlFlowException e) { + return 42; + } + } + + @SuppressWarnings("unused") + private int executeChild(VirtualFrame frame) throws SlowPathException { + return child.execute(frame); + } + } +} diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java --- a/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java Wed Jan 29 12:19:03 2014 +0100 @@ -27,7 +27,6 @@ import org.junit.*; import com.oracle.graal.api.code.*; -import com.oracle.graal.api.runtime.*; import com.oracle.graal.compiler.test.*; import com.oracle.graal.debug.*; import com.oracle.graal.debug.Debug.Scope; @@ -39,9 +38,7 @@ import com.oracle.graal.phases.*; 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.graal.virtual.phases.ea.*; import com.oracle.truffle.api.*; @@ -50,15 +47,12 @@ public class PartialEvaluationTest extends GraalCompilerTest { private static final long UNROLL_LIMIT = 100; - private final PartialEvaluator partialEvaluator; + private final TruffleCompilerImpl truffleCompiler; public PartialEvaluationTest() { // Make sure Truffle runtime is initialized. Assert.assertTrue(Truffle.getRuntime() instanceof GraalTruffleRuntime); - Replacements truffleReplacements = ((GraalTruffleRuntime) Truffle.getRuntime()).getReplacements(); - Providers providers = getProviders().copyWith(truffleReplacements); - TruffleCache truffleCache = new TruffleCache(providers, GraphBuilderConfiguration.getDefault(), TruffleCompilerImpl.Optimizations); - this.partialEvaluator = new PartialEvaluator(Graal.getRequiredCapability(RuntimeProvider.class), providers, truffleCache); + this.truffleCompiler = new TruffleCompilerImpl(); DebugEnvironment.initialize(System.out); } @@ -70,7 +64,7 @@ protected InstalledCode assertPartialEvalEquals(String methodName, RootNode root, Arguments arguments) { Assumptions assumptions = new Assumptions(true); StructuredGraph actual = partialEval(root, arguments, assumptions, true); - InstalledCode result = new TruffleCompilerImpl().compileMethodHelper(actual, GraphBuilderConfiguration.getDefault(), assumptions, root.toString(), getSpeculationLog()); + InstalledCode result = truffleCompiler.compileMethodHelper(actual, assumptions, root.toString(), getSpeculationLog()); StructuredGraph expected = parseForComparison(methodName); removeFrameStates(actual); Assert.assertEquals(getCanonicalGraphString(expected, true), getCanonicalGraphString(actual, true)); @@ -102,7 +96,7 @@ try (Scope s = Debug.scope("TruffleCompilation", new TruffleDebugJavaMethod(compilable))) { - StructuredGraph resultGraph = partialEvaluator.createGraph(compilable, assumptions); + StructuredGraph resultGraph = truffleCompiler.getPartialEvaluator().createGraph(compilable, assumptions); CanonicalizerPhase canonicalizer = new CanonicalizerPhase(canonicalizeReads); PhaseContext context = new PhaseContext(getProviders(), assumptions); diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Wed Jan 29 12:19:03 2014 +0100 @@ -68,16 +68,16 @@ private final Providers providers; private final ResolvedJavaMethod executeHelperMethod; private final CanonicalizerPhase canonicalizer; - private final ResolvedJavaType[] skippedExceptionTypes; + private final GraphBuilderConfiguration config; private Set constantReceivers; private final GraphCache cache; private final TruffleCache truffleCache; - public PartialEvaluator(RuntimeProvider runtime, Providers providers, TruffleCache truffleCache) { + public PartialEvaluator(RuntimeProvider runtime, Providers providers, TruffleCache truffleCache, GraphBuilderConfiguration config) { this.providers = providers; CustomCanonicalizer customCanonicalizer = new PartialEvaluatorCanonicalizer(providers.getMetaAccess(), providers.getConstantReflection()); this.canonicalizer = new CanonicalizerPhase(!ImmutableCode.getValue(), customCanonicalizer); - this.skippedExceptionTypes = TruffleCompilerImpl.getSkippedExceptionTypes(providers.getMetaAccess()); + this.config = config; this.cache = runtime.getGraphCache(); this.truffleCache = truffleCache; try { @@ -98,9 +98,6 @@ constantReceivers = new HashSet<>(); } - final GraphBuilderConfiguration config = GraphBuilderConfiguration.getDefault(); - config.setSkippedExceptionTypes(skippedExceptionTypes); - final StructuredGraph graph = new StructuredGraph(executeHelperMethod); try (Scope s = Debug.scope("createGraph", graph)) { diff -r 030e75d4d7dc -r 44bcfc983adb graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java Tue Jan 28 19:37:26 2014 +0100 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCompilerImpl.java Wed Jan 29 12:19:03 2014 +0100 @@ -36,7 +36,6 @@ import com.oracle.graal.api.meta.*; import com.oracle.graal.api.runtime.*; import com.oracle.graal.compiler.*; -import com.oracle.graal.compiler.CompilerThreadFactory.*; import com.oracle.graal.compiler.target.*; import com.oracle.graal.debug.*; import com.oracle.graal.debug.Debug.Scope; @@ -65,7 +64,7 @@ private final Suites suites; private final PartialEvaluator partialEvaluator; private final Backend backend; - private final ResolvedJavaType[] skippedExceptionTypes; + private final GraphBuilderConfiguration config; private final RuntimeProvider runtime; private final TruffleCache truffleCache; private final ThreadPoolExecutor compileQueue; @@ -81,10 +80,9 @@ Replacements truffleReplacements = ((GraalTruffleRuntime) Truffle.getRuntime()).getReplacements(); this.providers = backend.getProviders().copyWith(truffleReplacements); this.suites = backend.getSuites().getDefaultSuites(); - this.skippedExceptionTypes = getSkippedExceptionTypes(providers.getMetaAccess()); // Create compilation queue. - CompilerThreadFactory factory = new CompilerThreadFactory("TruffleCompilerThread", new DebugConfigAccess() { + CompilerThreadFactory factory = new CompilerThreadFactory("TruffleCompilerThread", new CompilerThreadFactory.DebugConfigAccess() { public GraalDebugConfig getDebugConfig() { if (Debug.isEnabled()) { GraalDebugConfig debugConfig = DebugEnvironment.initialize(TTY.out().out()); @@ -97,18 +95,21 @@ }); compileQueue = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue(), factory); - final GraphBuilderConfiguration config = GraphBuilderConfiguration.getEagerDefault(); - config.setSkippedExceptionTypes(skippedExceptionTypes); - this.truffleCache = new TruffleCache(providers, config, TruffleCompilerImpl.Optimizations); + ResolvedJavaType[] skippedExceptionTypes = getSkippedExceptionTypes(providers.getMetaAccess()); + GraphBuilderConfiguration eagerConfig = GraphBuilderConfiguration.getEagerDefault(); + eagerConfig.setSkippedExceptionTypes(skippedExceptionTypes); + this.truffleCache = new TruffleCache(providers, eagerConfig, TruffleCompilerImpl.Optimizations); - this.partialEvaluator = new PartialEvaluator(runtime, providers, truffleCache); + this.config = GraphBuilderConfiguration.getDefault(); + this.config.setSkippedExceptionTypes(skippedExceptionTypes); + this.partialEvaluator = new PartialEvaluator(runtime, providers, truffleCache, config); if (Debug.isEnabled()) { DebugEnvironment.initialize(System.out); } } - static ResolvedJavaType[] getSkippedExceptionTypes(MetaAccessProvider metaAccess) { + private static ResolvedJavaType[] getSkippedExceptionTypes(MetaAccessProvider metaAccess) { ResolvedJavaType[] skippedExceptionTypes = new ResolvedJavaType[SKIPPED_EXCEPTION_CLASSES.length]; for (int i = 0; i < SKIPPED_EXCEPTION_CLASSES.length; i++) { skippedExceptionTypes[i] = metaAccess.lookupJavaType(SKIPPED_EXCEPTION_CLASSES[i]); @@ -135,8 +136,6 @@ private InstalledCode compileMethodImpl(final OptimizedCallTarget compilable) { final StructuredGraph graph; - final GraphBuilderConfiguration config = GraphBuilderConfiguration.getDefault(); - config.setSkippedExceptionTypes(skippedExceptionTypes); GraphCache graphCache = runtime.getGraphCache(); if (graphCache != null) { graphCache.removeStaleGraphs(); @@ -156,7 +155,7 @@ } long timePartialEvaluationFinished = System.nanoTime(); int nodeCountPartialEval = graph.getNodeCount(); - InstalledCode compiledMethod = compileMethodHelper(graph, config, assumptions, compilable.toString(), compilable.getSpeculationLog()); + InstalledCode compiledMethod = compileMethodHelper(graph, assumptions, compilable.toString(), compilable.getSpeculationLog()); long timeCompilationFinished = System.nanoTime(); int nodeCountLowered = graph.getNodeCount(); @@ -210,7 +209,7 @@ } } - public InstalledCode compileMethodHelper(StructuredGraph graph, GraphBuilderConfiguration config, Assumptions assumptions, String name, SpeculationLog speculationLog) { + public InstalledCode compileMethodHelper(StructuredGraph graph, Assumptions assumptions, String name, SpeculationLog speculationLog) { try (Scope s = Debug.scope("TruffleFinal")) { Debug.dump(graph, "After TruffleTier"); } catch (Throwable e) { @@ -222,7 +221,7 @@ CodeCacheProvider codeCache = providers.getCodeCache(); CallingConvention cc = getCallingConvention(codeCache, Type.JavaCallee, graph.method(), false); CompilationResult compilationResult = new CompilationResult(name); - result = compileGraph(graph, cc, graph.method(), providers, backend, codeCache.getTarget(), null, createGraphBuilderSuite(config), OptimisticOptimizations.ALL, getProfilingInfo(graph), + result = compileGraph(graph, cc, graph.method(), providers, backend, codeCache.getTarget(), null, createGraphBuilderSuite(), OptimisticOptimizations.ALL, getProfilingInfo(graph), speculationLog, suites, false, compilationResult, CompilationResultBuilderFactory.Default); } catch (Throwable e) { throw Debug.handle(e); @@ -261,7 +260,7 @@ return installedCode; } - private PhaseSuite createGraphBuilderSuite(GraphBuilderConfiguration config) { + private PhaseSuite createGraphBuilderSuite() { PhaseSuite suite = backend.getSuites().getDefaultGraphBuilderSuite().copy(); ListIterator> iterator = suite.findPhase(GraphBuilderPhase.class); iterator.remove(); @@ -279,4 +278,8 @@ } } } + + public PartialEvaluator getPartialEvaluator() { + return partialEvaluator; + } } diff -r 030e75d4d7dc -r 44bcfc983adb mxtool/mx.py --- a/mxtool/mx.py Tue Jan 28 19:37:26 2014 +0100 +++ b/mxtool/mx.py Wed Jan 29 12:19:03 2014 +0100 @@ -1565,6 +1565,9 @@ return cmp(self.value, other.value) + def __hash__(self): + return self.value.__hash__() + """ A version specification as defined in JSR-56 """ @@ -2742,10 +2745,7 @@ slm.open('sourceLookupDirector') slm.open('sourceContainers', {'duplicates' : 'false'}) - # Every Java program depends on the JRE - memento = XMLDoc().element('classpathContainer', {'path' : 'org.eclipse.jdt.launching.JRE_CONTAINER'}).xml(standalone='no') - slm.element('classpathContainer', {'memento' : memento, 'typeId':'org.eclipse.jdt.launching.sourceContainer.classpathContainer'}) - + javaCompliance = None for dep in deps: if dep.isLibrary(): if hasattr(dep, 'eclipse.container'): @@ -2757,6 +2757,15 @@ else: memento = XMLDoc().element('javaProject', {'name' : dep.name}).xml(standalone='no') slm.element('container', {'memento' : memento, 'typeId':'org.eclipse.jdt.launching.sourceContainer.javaProject'}) + if javaCompliance is None or dep.javaCompliance < javaCompliance: + javaCompliance = dep.javaCompliance + + if javaCompliance: + memento = XMLDoc().element('classpathContainer', {'path' : 'org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-' + str(javaCompliance)}).xml(standalone='no') + slm.element('classpathContainer', {'memento' : memento, 'typeId':'org.eclipse.jdt.launching.sourceContainer.classpathContainer'}) + else: + memento = XMLDoc().element('classpathContainer', {'path' : 'org.eclipse.jdt.launching.JRE_CONTAINER'}).xml(standalone='no') + slm.element('classpathContainer', {'memento' : memento, 'typeId':'org.eclipse.jdt.launching.sourceContainer.classpathContainer'}) slm.close('sourceContainers') slm.close('sourceLookupDirector') @@ -2933,7 +2942,7 @@ out.element('classpathentry', {'kind' : 'src', 'path' : 'src_gen'}) files.append(genDir) - # Every Java program depends on the JRE + # Every Java program depends on a JRE out.element('classpathentry', {'kind' : 'con', 'path' : 'org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-' + str(p.javaCompliance)}) if exists(join(p.dir, 'plugin.xml')): # eclipse plugin project diff -r 030e75d4d7dc -r 44bcfc983adb src/share/vm/graal/graalCompilerToVM.cpp --- a/src/share/vm/graal/graalCompilerToVM.cpp Tue Jan 28 19:37:26 2014 +0100 +++ b/src/share/vm/graal/graalCompilerToVM.cpp Wed Jan 29 12:19:03 2014 +0100 @@ -553,7 +553,7 @@ //------------------------------------------------------------------------------------------------ set_int("graalCountersThreadOffset", in_bytes(JavaThread::graal_counters_offset())); - set_int("graalCountersSize", (jint) GRAAL_COUNTERS_SIZE); + set_int("graalCountersSize", (jint) GraalCounterSize); #undef set_boolean #undef set_int @@ -816,7 +816,7 @@ C2V_END C2V_VMENTRY(jlongArray, collectCounters, (JNIEnv *env, jobject)) - typeArrayOop arrayOop = oopFactory::new_longArray(GRAAL_COUNTERS_SIZE, CHECK_NULL); + typeArrayOop arrayOop = oopFactory::new_longArray(GraalCounterSize, CHECK_NULL); JavaThread::collect_counters(arrayOop); return (jlongArray) JNIHandles::make_local(arrayOop); C2V_END diff -r 030e75d4d7dc -r 44bcfc983adb src/share/vm/graal/graalGlobals.hpp --- a/src/share/vm/graal/graalGlobals.hpp Tue Jan 28 19:37:26 2014 +0100 +++ b/src/share/vm/graal/graalGlobals.hpp Wed Jan 29 12:19:03 2014 +0100 @@ -55,6 +55,12 @@ product(intx, TraceGraal, 0, \ "Trace level for Graal") \ \ + product(intx, GraalCounterSize, 0, \ + "Reserved size for benchmark counters") \ + \ + product(bool, GraalCountersExcludeCompiler, true, \ + "Exclude Graal compiler threads from benchmark counters") \ + \ product(bool, GraalDeferredInitBarriers, true, \ "Defer write barriers of young objects") \ \ diff -r 030e75d4d7dc -r 44bcfc983adb src/share/vm/runtime/thread.cpp --- a/src/share/vm/runtime/thread.cpp Tue Jan 28 19:37:26 2014 +0100 +++ b/src/share/vm/runtime/thread.cpp Wed Jan 29 12:19:03 2014 +0100 @@ -1418,31 +1418,27 @@ #ifdef GRAAL -#if GRAAL_COUNTERS_SIZE > 0 -jlong JavaThread::_graal_old_thread_counters[GRAAL_COUNTERS_SIZE]; +jlong* JavaThread::_graal_old_thread_counters; bool graal_counters_include(oop threadObj) { - return !GRAAL_COUNTERS_EXCLUDE_COMPILER_THREADS || threadObj == NULL || threadObj->klass() != SystemDictionary::CompilerThread_klass(); + return !GraalCountersExcludeCompiler || threadObj == NULL || threadObj->klass() != SystemDictionary::CompilerThread_klass(); } void JavaThread::collect_counters(typeArrayOop array) { - MutexLocker tl(Threads_lock); - for (int i = 0; i < array->length(); i++) { - array->long_at_put(i, _graal_old_thread_counters[i]); - } - for (JavaThread* tp = Threads::first(); tp != NULL; tp = tp->next()) { - if (graal_counters_include(tp->threadObj())) { - for (int i = 0; i < array->length(); i++) { - array->long_at_put(i, array->long_at(i) + tp->_graal_counters[i]); + if (GraalCounterSize > 0) { + MutexLocker tl(Threads_lock); + for (int i = 0; i < array->length(); i++) { + array->long_at_put(i, _graal_old_thread_counters[i]); + } + for (JavaThread* tp = Threads::first(); tp != NULL; tp = tp->next()) { + if (graal_counters_include(tp->threadObj())) { + for (int i = 0; i < array->length(); i++) { + array->long_at_put(i, array->long_at(i) + tp->_graal_counters[i]); + } } } } } -#else -void JavaThread::collect_counters(typeArrayOop array) { - // empty -} -#endif // GRAAL_COUNTERS_SIZE > 0 #endif // GRAAL @@ -1486,11 +1482,12 @@ _graal_alternate_call_target = NULL; _graal_implicit_exception_pc = NULL; _graal_compiling = false; -#if GRAAL_COUNTERS_SIZE > 0 - for (int i = 0; i < GRAAL_COUNTERS_SIZE; i++) { - _graal_counters[i] = 0; + if (GraalCounterSize > 0) { + _graal_counters = NEW_C_HEAP_ARRAY(jlong, GraalCounterSize, mtInternal); + memset(_graal_counters, 0, sizeof(jlong) * GraalCounterSize); + } else { + _graal_counters = NULL; } -#endif // GRAAL_COUNTER_SIZE > 0 #endif // GRAAL (void)const_cast(_exception_oop = NULL); _exception_pc = 0; @@ -1680,13 +1677,14 @@ if (_thread_profiler != NULL) delete _thread_profiler; if (_thread_stat != NULL) delete _thread_stat; -#if defined(GRAAL) && (GRAAL_COUNTERS_SIZE > 0) - if (graal_counters_include(threadObj())) { - for (int i = 0; i < GRAAL_COUNTERS_SIZE; i++) { +#ifdef GRAAL + if (GraalCounterSize > 0 && graal_counters_include(threadObj())) { + for (int i = 0; i < GraalCounterSize; i++) { _graal_old_thread_counters[i] += _graal_counters[i]; } + FREE_C_HEAP_ARRAY(jlong, _graal_counters, mtInternal); } -#endif +#endif // GRAAL } @@ -3458,6 +3456,15 @@ // Initialize global data structures and create system classes in heap vm_init_globals(); +#ifdef GRAAL + if (GraalCounterSize > 0) { + JavaThread::_graal_old_thread_counters = NEW_C_HEAP_ARRAY(jlong, GraalCounterSize, mtInternal); + memset(JavaThread::_graal_old_thread_counters, 0, sizeof(jlong) * GraalCounterSize); + } else { + JavaThread::_graal_old_thread_counters = NULL; + } +#endif // GRAAL + // Attach the main thread to this os thread JavaThread* main_thread = new JavaThread(); main_thread->set_thread_state(_thread_in_vm); @@ -4109,6 +4116,12 @@ delete thread; +#ifdef GRAAL + if (GraalCounterSize > 0) { + FREE_C_HEAP_ARRAY(jlong, JavaThread::_graal_old_thread_counters, mtInternal); + } +#endif // GRAAL + // exit_globals() will delete tty exit_globals(); diff -r 030e75d4d7dc -r 44bcfc983adb src/share/vm/runtime/thread.hpp --- a/src/share/vm/runtime/thread.hpp Tue Jan 28 19:37:26 2014 +0100 +++ b/src/share/vm/runtime/thread.hpp Wed Jan 29 12:19:03 2014 +0100 @@ -922,16 +922,10 @@ address _graal_implicit_exception_pc; // pc at which the most recent implicit exception occurred bool _graal_compiling; - // number of counters, increase as needed. 0 == disabled -#define GRAAL_COUNTERS_SIZE (0) -#define GRAAL_COUNTERS_EXCLUDE_COMPILER_THREADS (true) - -#if GRAAL_COUNTERS_SIZE > 0 - jlong _graal_counters[GRAAL_COUNTERS_SIZE]; - static jlong _graal_old_thread_counters[GRAAL_COUNTERS_SIZE]; -#endif // GRAAL_COUNTERS_SIZE > 0 + jlong* _graal_counters; public: + static jlong* _graal_old_thread_counters; static void collect_counters(typeArrayOop array); private: #endif // GRAAL @@ -1394,11 +1388,7 @@ #ifdef GRAAL static ByteSize graal_alternate_call_target_offset() { return byte_offset_of(JavaThread, _graal_alternate_call_target); } static ByteSize graal_implicit_exception_pc_offset() { return byte_offset_of(JavaThread, _graal_implicit_exception_pc); } -#if GRAAL_COUNTERS_SIZE > 0 static ByteSize graal_counters_offset() { return byte_offset_of(JavaThread, _graal_counters ); } -#else - static ByteSize graal_counters_offset() { return in_ByteSize(0); } -#endif // GRAAL_COUNTERS_SIZE > 0 #endif // GRAAL static ByteSize exception_oop_offset() { return byte_offset_of(JavaThread, _exception_oop ); } static ByteSize exception_pc_offset() { return byte_offset_of(JavaThread, _exception_pc ); }