# HG changeset patch # User Doug Simon # Date 1336731636 -7200 # Node ID c862951e769dd4cb43bf32376a2341d2c0b9cbec # Parent 333b0089a909aa8691b303ab1e890e23fd7d1d7a moved checkcast lowering into LoweringPhase and added -G:HIRLowerCheckcast option to enable it (disabled by default) as it is not yet stable diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java Fri May 11 12:20:36 2012 +0200 @@ -169,7 +169,7 @@ } graph.mark(); - new LoweringPhase(runtime).apply(graph); + new LoweringPhase(runtime, assumptions).apply(graph); new CanonicalizerPhase(target, runtime, assumptions, true, null).apply(graph); if (GraalOptions.Lower) { diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalOptions.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalOptions.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalOptions.java Fri May 11 12:20:36 2012 +0200 @@ -256,6 +256,13 @@ public static int InstanceOfMaxHints = 1; /** + * Use HIR lowering instead of LIR lowering for checkcast instructions. + * Only checkcasts in methods in a class whose name contains this option will be HIR lowered. + * TDOD (dnsimon) remove once HIR checkcast lowering works reliably + */ + public static String HIRLowerCheckcast; + + /** * The profiling info cache directory. */ public static String PICache = null; diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/LoweringPhase.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/LoweringPhase.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/LoweringPhase.java Fri May 11 12:20:36 2012 +0200 @@ -27,7 +27,9 @@ import com.oracle.graal.graph.*; import com.oracle.graal.lir.cfg.*; import com.oracle.graal.nodes.*; +import com.oracle.graal.nodes.java.*; import com.oracle.graal.nodes.spi.*; +import com.oracle.max.cri.ci.*; import com.oracle.max.cri.ri.*; /** @@ -36,9 +38,11 @@ public class LoweringPhase extends Phase { private final GraalRuntime runtime; + private final CiAssumptions assumptions; - public LoweringPhase(GraalRuntime runtime) { + public LoweringPhase(GraalRuntime runtime, CiAssumptions assumptions) { this.runtime = runtime; + this.assumptions = assumptions; } @Override @@ -67,10 +71,19 @@ // TODO (thomaswue): Document why this must not be called on floating nodes. throw new UnsupportedOperationException(); } + + @Override + public CiAssumptions assumptions() { + return assumptions; + } }; for (Node node : processed) { - if (node instanceof Lowerable) { - assert !(node instanceof FixedNode) || node.predecessor() == null; + if (node instanceof CheckCastNode) { + // This is a checkcast that was created while lowering some other node (e.g. StoreIndexed). + // This checkcast must now be LIR lowered. + // TODO (dnsimon) this is temp workaround that will be removed + } else if (node instanceof Lowerable) { + assert !(node instanceof FixedNode) || node.predecessor() == null : node; ((Lowerable) node).lower(loweringTool); } } @@ -135,6 +148,11 @@ activeGuards.mark(newGuard); return newGuard; } + + @Override + public CiAssumptions assumptions() { + return assumptions; + } }; // Lower the instructions of this block. diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/util/InliningUtil.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/util/InliningUtil.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/util/InliningUtil.java Fri May 11 12:20:36 2012 +0200 @@ -40,6 +40,7 @@ import com.oracle.graal.nodes.extended.*; import com.oracle.graal.nodes.java.*; import com.oracle.graal.nodes.java.MethodCallTargetNode.InvokeKind; +import com.oracle.graal.nodes.spi.*; import com.oracle.graal.nodes.type.*; import com.oracle.graal.nodes.util.*; import com.oracle.max.cri.ci.*; @@ -921,11 +922,12 @@ final StructuredGraph snippetGraph, final boolean explodeLoops, final IsImmutablePredicate immutabilityPredicate, + final CiLoweringTool tool, final Object... args) { Debug.scope("InliningSnippet", snippetGraph.method(), new Runnable() { @Override public void run() { - inlineSnippet0(runtime, replacee, anchor, snippetGraph, explodeLoops, immutabilityPredicate, args); + inlineSnippet0(runtime, replacee, anchor, snippetGraph, explodeLoops, immutabilityPredicate, tool, args); } }); } @@ -935,7 +937,10 @@ StructuredGraph snippetGraph, boolean explodeLoops, IsImmutablePredicate immutabilityPredicate, - Object... args) { + CiLoweringTool tool, Object... args) { + + Debug.dump(replacee.graph(), "Before lowering %s", replacee); + // Copy snippet graph, replacing parameters with given args in the process StructuredGraph snippetCopy = new StructuredGraph(snippetGraph.name, snippetGraph.method()); IdentityHashMap replacements = new IdentityHashMap<>(); @@ -967,16 +972,20 @@ LoopBeginNode loopBegin = loop.loopBegin(); SuperBlock wholeLoop = LoopTransformUtil.wholeLoop(loop); Debug.dump(snippetCopy, "Before exploding loop %s", loopBegin); + int peel = 0; while (!loopBegin.isDeleted()) { snippetCopy.mark(); LoopTransformUtil.peel(loop, wholeLoop); + Debug.dump(snippetCopy, "After peel %d", peel); new CanonicalizerPhase(null, runtime, null, true, immutabilityPredicate).apply(snippetCopy); + peel++; } Debug.dump(snippetCopy, "After exploding loop %s", loopBegin); } + new DeadCodeEliminationPhase().apply(snippetCopy); } - // Gather the nodes in the snippets that are to be inlined + // Gather the nodes in the snippet that are to be inlined ArrayList nodes = new ArrayList<>(); ReturnNode returnNode = null; StartNode entryPointNode = snippetCopy.start(); @@ -1003,21 +1012,39 @@ // Inline the gathered snippet nodes StructuredGraph graph = (StructuredGraph) replacee.graph(); + graph.mark(); Map duplicates = graph.addDuplicates(nodes, replacements); + Debug.dump(graph, "After inlining snippet %s", snippetCopy.method()); // Remove all frame states from the inlined snippet graph. Snippets must be atomic (i.e. free // of side-effects that prevent deoptimizing to a point before the snippet). - for (Node node : duplicates.values()) { + if (tool != null) { + boolean innerLowering = false; + for (Node node : duplicates.values()) { + if (node instanceof Lowerable) { + innerLowering = true; + ((Lowerable) node).lower(tool); + + } + } + if (innerLowering) { + Debug.dump(graph, "After inner lowering"); + } + } + + for (Node node : graph.getNewNodes()) { if (node instanceof StateSplit) { StateSplit stateSplit = (StateSplit) node; FrameState frameState = stateSplit.stateAfter(); - assert !stateSplit.hasSideEffect() : "snippets cannot contain side-effecting node " + node; + assert !stateSplit.hasSideEffect() : "snippets cannot contain side-effecting node " + node + "\n " + replacee.graph(); if (frameState != null) { stateSplit.setStateAfter(null); } } } + Debug.dump(graph, "After removing frame states"); + // Rewire the control flow graph around the replacee FixedNode firstCFGNodeDuplicate = (FixedNode) duplicates.get(firstCFGNode); anchor.replaceAtPredecessors(firstCFGNodeDuplicate); diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotDebugConfig.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotDebugConfig.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotDebugConfig.java Fri May 11 12:20:36 2012 +0200 @@ -148,8 +148,7 @@ return null; } Debug.setConfig(Debug.fixedConfig(true, true, false, false, dumpHandlers, output)); - // sync "Exception occured in scope: " with mx/sanitycheck.py::Test.__init__ - Debug.log(String.format("Exception occured in scope: %s", Debug.currentScope())); + Debug.log(String.format("Exception occurred in scope: %s", Debug.currentScope())); for (Object o : Debug.context()) { Debug.log("Context obj %s", o); if (o instanceof Graph) { diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/VMToCompilerImpl.java Fri May 11 12:20:36 2012 +0200 @@ -53,7 +53,6 @@ private final Compiler compiler; private IntrinsifyArrayCopyPhase intrinsifyArrayCopy; - private LowerCheckCastPhase lowerCheckCastPhase; public final HotSpotTypePrimitive typeBoolean; public final HotSpotTypePrimitive typeChar; @@ -116,12 +115,8 @@ @Override public void run() { VMToCompilerImpl.this.intrinsifyArrayCopy = new IntrinsifyArrayCopyPhase(runtime); - VMToCompilerImpl.this.lowerCheckCastPhase = new LowerCheckCastPhase(runtime); GraalIntrinsics.installIntrinsics(runtime, runtime.getCompiler().getTarget()); - Snippets.install(runtime, runtime.getCompiler().getTarget(), new SystemSnippets()); - Snippets.install(runtime, runtime.getCompiler().getTarget(), new UnsafeSnippets()); - Snippets.install(runtime, runtime.getCompiler().getTarget(), new ArrayCopySnippets()); - Snippets.install(runtime, runtime.getCompiler().getTarget(), new CheckCastSnippets()); + runtime.installSnippets(); } }); @@ -495,7 +490,6 @@ if (GraalOptions.Intrinsify) { phasePlan.addPhase(PhasePosition.HIGH_LEVEL, intrinsifyArrayCopy); } - phasePlan.addPhase(PhasePosition.HIGH_LEVEL, lowerCheckCastPhase); return phasePlan; } diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/ri/HotSpotRuntime.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/ri/HotSpotRuntime.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/ri/HotSpotRuntime.java Fri May 11 12:20:36 2012 +0200 @@ -28,18 +28,24 @@ import java.util.*; import com.oracle.graal.compiler.*; +import com.oracle.graal.compiler.phases.*; +import com.oracle.graal.compiler.phases.CanonicalizerPhase.IsImmutablePredicate; import com.oracle.graal.compiler.target.*; +import com.oracle.graal.compiler.util.*; import com.oracle.graal.cri.*; +import com.oracle.graal.debug.*; import com.oracle.graal.graph.*; import com.oracle.graal.hotspot.*; import com.oracle.graal.hotspot.Compiler; import com.oracle.graal.hotspot.nodes.*; +import com.oracle.graal.hotspot.snippets.*; import com.oracle.graal.hotspot.target.amd64.*; import com.oracle.graal.nodes.*; import com.oracle.graal.nodes.calc.*; import com.oracle.graal.nodes.extended.*; import com.oracle.graal.nodes.java.*; import com.oracle.graal.nodes.type.*; +import com.oracle.graal.snippets.*; import com.oracle.max.cri.ci.*; import com.oracle.max.cri.ci.CiTargetMethod.Call; import com.oracle.max.cri.ci.CiTargetMethod.DataPatch; @@ -58,6 +64,7 @@ final HotSpotRegisterConfig regConfig; private final HotSpotRegisterConfig globalStubRegConfig; private final Compiler compiler; + private RiResolvedMethod checkcastSnippet; public HotSpotRuntime(HotSpotVMConfig config, Compiler compiler) { this.config = config; @@ -68,6 +75,19 @@ System.setProperty(Backend.BACKEND_CLASS_PROPERTY, HotSpotAMD64Backend.class.getName()); } + public void installSnippets() { + Snippets.install(this, compiler.getTarget(), new SystemSnippets()); + Snippets.install(this, compiler.getTarget(), new UnsafeSnippets()); + Snippets.install(this, compiler.getTarget(), new ArrayCopySnippets()); + Snippets.install(this, compiler.getTarget(), new CheckCastSnippets()); + try { + checkcastSnippet = getRiMethod(CheckCastSnippets.class.getDeclaredMethod("checkcast", Object.class, Object.class, Object[].class, boolean.class)); + } catch (NoSuchMethodException e) { + throw new GraalInternalError(e); + } + } + + @Override public int codeOffset() { return 0; @@ -330,6 +350,7 @@ CiKind elementKind = storeIndexed.elementKind(); LocationNode arrayLocation = createArrayLocation(graph, elementKind, storeIndexed.index()); ValueNode value = storeIndexed.value(); + CheckCastNode checkcast = null; ValueNode array = storeIndexed.array(); if (elementKind == CiKind.Object && !value.isNullConstant()) { // Store check! @@ -337,7 +358,7 @@ RiResolvedType elementType = array.exactType().componentType(); if (elementType.superType() != null) { ConstantNode type = ConstantNode.forCiConstant(elementType.getEncoding(Representation.ObjectHub), this, graph); - CheckCastNode checkcast = graph.add(new CheckCastNode(type, elementType, value)); + checkcast = graph.add(new CheckCastNode(type, elementType, value)); graph.addBeforeFixed(storeIndexed, checkcast); value = checkcast; } else { @@ -348,7 +369,7 @@ FloatingReadNode arrayClass = graph.unique(new FloatingReadNode(array, null, LocationNode.create(LocationNode.FINAL_LOCATION, CiKind.Object, config.hubOffset, graph), StampFactory.objectNonNull())); arrayClass.setGuard(guard); FloatingReadNode arrayElementKlass = graph.unique(new FloatingReadNode(arrayClass, null, LocationNode.create(LocationNode.FINAL_LOCATION, CiKind.Object, config.arrayClassElementOffset, graph), StampFactory.objectNonNull())); - CheckCastNode checkcast = graph.add(new CheckCastNode(arrayElementKlass, null, value)); + checkcast = graph.add(new CheckCastNode(arrayElementKlass, null, value)); graph.addBeforeFixed(storeIndexed, checkcast); value = checkcast; } @@ -362,6 +383,9 @@ if (elementKind == CiKind.Object && !value.isNullConstant()) { graph.addAfterFixed(memoryWrite, graph.add(new ArrayWriteBarrier(array, arrayLocation))); } + if (checkcast != null) { + checkcast.lower(tool); + } } else if (n instanceof UnsafeLoadNode) { UnsafeLoadNode load = (UnsafeLoadNode) n; assert load.kind() != CiKind.Illegal; @@ -387,6 +411,31 @@ ReadNode memoryRead = graph.add(new ReadNode(objectClassNode.object(), location, StampFactory.objectNonNull())); memoryRead.setGuard((GuardNode) tool.createGuard(graph.unique(new NullCheckNode(objectClassNode.object(), false)), RiDeoptReason.NullCheckException, RiDeoptAction.InvalidateReprofile, StructuredGraph.INVALID_GRAPH_ID)); graph.replaceFixed(objectClassNode, memoryRead); + } else if (n instanceof CheckCastNode) { + if (GraalOptions.HIRLowerCheckcast != null && graph.method() != null && graph.method().holder().name().contains(GraalOptions.HIRLowerCheckcast)) { + final Map hintHubsSet = new IdentityHashMap<>(); + IsImmutablePredicate immutabilityPredicate = new IsImmutablePredicate() { + public boolean apply(CiConstant constant) { + return hintHubsSet.containsKey(constant); + } + }; + CheckCastNode checkcast = (CheckCastNode) n; + ValueNode hub = checkcast.targetClassInstruction(); + ValueNode object = checkcast.object(); + TypeCheckHints hints = new TypeCheckHints(checkcast.targetClass(), checkcast.profile(), tool.assumptions(), GraalOptions.CheckcastMinHintHitProbability, GraalOptions.CheckcastMaxHints); + StructuredGraph snippetGraph = (StructuredGraph) checkcastSnippet.compilerStorage().get(Graph.class); + assert snippetGraph != null : CheckCastSnippets.class.getSimpleName() + " should be installed"; + HotSpotKlassOop[] hintHubs = new HotSpotKlassOop[hints.types.length]; + for (int i = 0; i < hintHubs.length; i++) { + hintHubs[i] = ((HotSpotType) hints.types[i]).klassOop(); + } + final CiConstant hintHubsConst = CiConstant.forObject(hintHubs); + hintHubsSet.put(hintHubsConst, hintHubsConst); + Debug.log("Lowering checkcast in %s: node=%s, hintsHubs=%s, exact=%b", graph, checkcast, Arrays.toString(hints.types), hints.exact); + + InliningUtil.inlineSnippet(this, checkcast, checkcast, snippetGraph, true, immutabilityPredicate, tool, hub, object, hintHubsConst, CiConstant.forBoolean(hints.exact)); + new DeadCodeEliminationPhase().apply(graph); + } } else { assert false : "Node implementing Lowerable not handled: " + n; } diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/snippets/LowerCheckCastPhase.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/snippets/LowerCheckCastPhase.java Fri May 11 11:57:29 2012 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,88 +0,0 @@ -/* - * 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.hotspot.snippets; - -import java.util.*; - -import com.oracle.graal.compiler.*; -import com.oracle.graal.compiler.phases.*; -import com.oracle.graal.compiler.phases.CanonicalizerPhase.IsImmutablePredicate; -import com.oracle.graal.compiler.util.*; -import com.oracle.graal.cri.*; -import com.oracle.graal.debug.*; -import com.oracle.graal.graph.*; -import com.oracle.graal.hotspot.ri.*; -import com.oracle.graal.nodes.*; -import com.oracle.graal.nodes.java.*; -import com.oracle.max.cri.ci.*; -import com.oracle.max.cri.ri.*; -import com.oracle.max.criutils.*; - -/** - * Lowers a {@link CheckCastNode} by replacing it with the graph of a {@linkplain CheckCastSnippets checkcast snippet}. - */ -public class LowerCheckCastPhase extends Phase { - private final GraalRuntime runtime; - private final RiResolvedMethod checkcast; - - public LowerCheckCastPhase(GraalRuntime runtime) { - this.runtime = runtime; - try { - checkcast = runtime.getRiMethod(CheckCastSnippets.class.getDeclaredMethod("checkcast", Object.class, Object.class, Object[].class, boolean.class)); - } catch (NoSuchMethodException e) { - throw new GraalInternalError(e); - } - } - - @Override - protected void run(StructuredGraph graph) { - final Map hintHubsSet = new IdentityHashMap<>(); - IsImmutablePredicate immutabilityPredicate = new IsImmutablePredicate() { - public boolean apply(CiConstant constant) { - return hintHubsSet.containsKey(constant); - } - }; - for (CheckCastNode node : graph.getNodes(CheckCastNode.class)) { - ValueNode hub = node.targetClassInstruction(); - ValueNode object = node.object(); - CiAssumptions assumptions = null; - TypeCheckHints hints = new TypeCheckHints(node.targetClass(), node.profile(), assumptions, GraalOptions.CheckcastMinHintHitProbability, GraalOptions.CheckcastMaxHints); - StructuredGraph snippetGraph = (StructuredGraph) checkcast.compilerStorage().get(Graph.class); - assert snippetGraph != null : CheckCastSnippets.class.getSimpleName() + " should be installed"; - HotSpotKlassOop[] hintHubs = new HotSpotKlassOop[hints.types.length]; - for (int i = 0; i < hintHubs.length; i++) { - hintHubs[i] = ((HotSpotType) hints.types[i]).klassOop(); - } - final CiConstant hintHubsConst = CiConstant.forObject(hintHubs); - hintHubsSet.put(hintHubsConst, hintHubsConst); - Debug.log("Lowering checkcast in %s: node=%s, hintsHubs=%s, exact=%b", graph, node, Arrays.toString(hints.types), hints.exact); - - InliningUtil.inlineSnippet(runtime, node, node, snippetGraph, true, immutabilityPredicate, hub, object, hintHubsConst, CiConstant.forBoolean(hints.exact)); - } - if (!hintHubsSet.isEmpty()) { - Debug.log("Lowered %d checkcasts in %s ", hintHubsSet.size(), graph); - new DeadCodeEliminationPhase().apply(graph); - new CanonicalizerPhase(null, runtime, null, false, immutabilityPredicate).apply(graph); - } - } -} diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.nodes/src/com/oracle/graal/cri/CiLoweringTool.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/cri/CiLoweringTool.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/cri/CiLoweringTool.java Fri May 11 12:20:36 2012 +0200 @@ -23,11 +23,13 @@ package com.oracle.graal.cri; import com.oracle.graal.graph.*; +import com.oracle.max.cri.ci.*; import com.oracle.max.cri.ri.*; public interface CiLoweringTool { GraalRuntime getRuntime(); Node getGuardAnchor(); Node createGuard(Node condition, RiDeoptReason deoptReason, RiDeoptAction action, long leafGraphId); + CiAssumptions assumptions(); } diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/CheckCastNode.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/CheckCastNode.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/CheckCastNode.java Fri May 11 12:20:36 2012 +0200 @@ -22,6 +22,7 @@ */ package com.oracle.graal.nodes.java; +import com.oracle.graal.cri.*; import com.oracle.graal.graph.*; import com.oracle.graal.nodes.*; import com.oracle.graal.nodes.calc.*; @@ -34,7 +35,7 @@ /** * Implements a type check that results in a {@link ClassCastException} if it fails. */ -public final class CheckCastNode extends FixedWithNextNode implements Canonicalizable, LIRLowerable, Node.IterableNodeType, TypeFeedbackProvider, TypeCanonicalizable { +public final class CheckCastNode extends FixedWithNextNode implements Canonicalizable, LIRLowerable, Lowerable, Node.IterableNodeType, TypeFeedbackProvider, TypeCanonicalizable { @Input private ValueNode object; @Input private ValueNode targetClassInstruction; @@ -60,6 +61,11 @@ } @Override + public void lower(CiLoweringTool tool) { + tool.getRuntime().lower(this, tool); + } + + @Override public void generate(LIRGeneratorTool gen) { gen.visitCheckCast(this); } diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippets.java --- a/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippets.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippets.java Fri May 11 12:20:36 2012 +0200 @@ -108,7 +108,7 @@ MethodCallTargetNode callTarget = invoke.callTarget(); RiResolvedMethod targetMethod = callTarget.targetMethod(); RiResolvedType holder = targetMethod.holder(); - if (holder.isSubtypeOf(runtime.getType(SnippetsInterface.class))) { + if (enclosedInSnippetsClass(holder)) { StructuredGraph targetGraph = (StructuredGraph) targetMethod.compilerStorage().get(Graph.class); if (targetGraph == null) { targetGraph = buildSnippetGraph(targetMethod, runtime, target, pool); @@ -140,6 +140,17 @@ return graph; } + + private boolean enclosedInSnippetsClass(RiResolvedType holder) { + Class enclosingClass = holder.toJava(); + while (enclosingClass != null) { + if (SnippetsInterface.class.isAssignableFrom(enclosingClass)) { + return true; + } + enclosingClass = enclosingClass.getEnclosingClass(); + } + return false; + } }); } diff -r 333b0089a909 -r c862951e769d graal/com.oracle.graal.tests/src/com/oracle/graal/compiler/tests/FloatingReadTest.java --- a/graal/com.oracle.graal.tests/src/com/oracle/graal/compiler/tests/FloatingReadTest.java Fri May 11 11:57:29 2012 +0200 +++ b/graal/com.oracle.graal.tests/src/com/oracle/graal/compiler/tests/FloatingReadTest.java Fri May 11 12:20:36 2012 +0200 @@ -52,7 +52,7 @@ private void test(String snippet) { StructuredGraph graph = parse(snippet); - new LoweringPhase(runtime()).apply(graph); + new LoweringPhase(runtime(), null).apply(graph); new FloatingReadPhase().apply(graph); ReturnNode returnNode = null;