changeset 15374:669536c4949a

clean up ExceptionObjectNode lowering
author Lukas Stadler <lukas.stadler@oracle.com>
date Fri, 25 Apr 2014 10:13:54 +0200
parents 85e1bf62208c
children 1b82cd9e72e9
files graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/nodes/LoadExceptionObjectNode.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/replacements/LoadExceptionObjectSnippets.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/InvokeWithExceptionNode.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/cfg/Block.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/MemoryNode.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/ExceptionObjectNode.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadExceptionObjectNode.java
diffstat 8 files changed, 75 insertions(+), 109 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java	Fri Apr 25 10:13:54 2014 +0200
@@ -192,8 +192,10 @@
             if (graph.getGuardsStage() == StructuredGraph.GuardsStage.AFTER_FSA) {
                 newObjectSnippets.lower((NewMultiArrayNode) n, tool);
             }
-        } else if (n instanceof LoadExceptionObjectNode) {
-            exceptionObjectSnippets.lower((LoadExceptionObjectNode) n, registers, tool);
+        } else if (n instanceof ExceptionObjectNode) {
+            if (graph.getGuardsStage() == StructuredGraph.GuardsStage.FIXED_DEOPTS) {
+                lowerExceptionObjectNode((ExceptionObjectNode) n, tool);
+            }
         } else if (n instanceof IntegerDivNode || n instanceof IntegerRemNode || n instanceof UnsignedDivNode || n instanceof UnsignedRemNode) {
             // Nothing to do for division nodes. The HotSpot signal handler catches divisions by
             // zero and the MIN_VALUE / -1 cases.
@@ -732,6 +734,19 @@
         }
     }
 
+    private void lowerExceptionObjectNode(ExceptionObjectNode n, LoweringTool tool) {
+        LocationIdentity locationsKilledByInvoke = ((InvokeWithExceptionNode) n.predecessor()).getLocationIdentity();
+        BeginNode entry = n.graph().add(new KillingBeginNode(locationsKilledByInvoke));
+        LoadExceptionObjectNode loadException = n.graph().add(new LoadExceptionObjectNode(StampFactory.declaredNonNull(metaAccess.lookupJavaType(Throwable.class))));
+
+        loadException.setStateAfter(n.stateAfter());
+        n.replaceAtUsages(InputType.Value, loadException);
+        n.graph().replaceFixedWithFixed(n, entry);
+        entry.graph().addAfterFixed(entry, loadException);
+
+        exceptionObjectSnippets.lower(loadException, registers, tool);
+    }
+
     protected static void finishAllocatedObjects(LoweringTool tool, CommitAllocationNode commit, ValueNode[] allocations) {
         StructuredGraph graph = commit.graph();
         for (int objIndex = 0; objIndex < commit.getVirtualObjects().size(); objIndex++) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/nodes/LoadExceptionObjectNode.java	Fri Apr 25 10:13:54 2014 +0200
@@ -0,0 +1,39 @@
+/*
+ * Copyright (c) 2009, 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.nodes;
+
+import com.oracle.graal.compiler.common.type.*;
+import com.oracle.graal.nodes.*;
+import com.oracle.graal.nodes.spi.*;
+
+public class LoadExceptionObjectNode extends AbstractStateSplit implements Lowerable {
+
+    public LoadExceptionObjectNode(Stamp stamp) {
+        super(stamp);
+    }
+
+    @Override
+    public void lower(LoweringTool tool) {
+        tool.getLowerer().lower(this, tool);
+    }
+}
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/replacements/LoadExceptionObjectSnippets.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/replacements/LoadExceptionObjectSnippets.java	Fri Apr 25 10:13:54 2014 +0200
@@ -30,9 +30,9 @@
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.compiler.common.type.*;
 import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.nodes.*;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.extended.*;
-import com.oracle.graal.nodes.java.*;
 import com.oracle.graal.nodes.spi.*;
 import com.oracle.graal.replacements.*;
 import com.oracle.graal.replacements.Snippet.ConstantParameter;
@@ -44,6 +44,12 @@
 
 /**
  * Snippet for loading the exception object at the start of an exception dispatcher.
+ * <p>
+ * The frame state upon entry to an exception handler is such that it is a
+ * {@link BytecodeFrame#rethrowException rethrow exception} state and the stack contains exactly the
+ * exception object (per the JVM spec) to rethrow. This means that the code generated for this node
+ * must not cause a deoptimization as the runtime/interpreter would not have a valid location to
+ * find the exception object to be rethrown.
  */
 public class LoadExceptionObjectSnippets implements Snippets {
 
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/InvokeWithExceptionNode.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/InvokeWithExceptionNode.java	Fri Apr 25 10:13:54 2014 +0200
@@ -37,7 +37,7 @@
     private static final double EXCEPTION_PROBA = 1e-5;
 
     @Successor private BeginNode next;
-    @Successor private DispatchBeginNode exceptionEdge;
+    @Successor private BeginNode exceptionEdge;
     @Input(InputType.Extension) private CallTargetNode callTarget;
     @Input(InputType.State) private FrameState stateDuring;
     @Input(InputType.State) private FrameState stateAfter;
@@ -47,7 +47,7 @@
     private boolean useForInlining;
     private double exceptionProbability;
 
-    public InvokeWithExceptionNode(CallTargetNode callTarget, DispatchBeginNode exceptionEdge, int bci) {
+    public InvokeWithExceptionNode(CallTargetNode callTarget, BeginNode exceptionEdge, int bci) {
         super(callTarget.returnStamp());
         this.exceptionEdge = exceptionEdge;
         this.bci = bci;
@@ -57,11 +57,11 @@
         this.exceptionProbability = EXCEPTION_PROBA;
     }
 
-    public DispatchBeginNode exceptionEdge() {
+    public BeginNode exceptionEdge() {
         return exceptionEdge;
     }
 
-    public void setExceptionEdge(DispatchBeginNode x) {
+    public void setExceptionEdge(BeginNode x) {
         updatePredecessor(exceptionEdge, x);
         exceptionEdge = x;
     }
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/cfg/Block.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/cfg/Block.java	Fri Apr 25 10:13:54 2014 +0200
@@ -25,8 +25,8 @@
 import java.util.*;
 
 import com.oracle.graal.compiler.common.cfg.*;
+import com.oracle.graal.graph.*;
 import com.oracle.graal.nodes.*;
-import com.oracle.graal.nodes.java.*;
 
 public final class Block extends AbstractBlockBase<Block> {
 
@@ -67,7 +67,8 @@
     }
 
     public boolean isExceptionEntry() {
-        return getBeginNode() instanceof ExceptionObjectNode;
+        Node predecessor = getBeginNode().predecessor();
+        return predecessor != null && predecessor instanceof InvokeWithExceptionNode && getBeginNode() != ((InvokeWithExceptionNode) predecessor).exceptionEdge();
     }
 
     public Block getFirstPredecessor() {
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/MemoryNode.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/MemoryNode.java	Fri Apr 25 10:13:54 2014 +0200
@@ -22,12 +22,13 @@
  */
 package com.oracle.graal.nodes.extended;
 
+import com.oracle.graal.graph.*;
 import com.oracle.graal.nodes.*;
 
 /**
  * This interface marks nodes that are part of the memory graph.
  */
-public interface MemoryNode {
+public interface MemoryNode extends NodeInterface {
 
     ValueNode asNode();
 
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/ExceptionObjectNode.java	Thu Apr 24 23:32:30 2014 +0100
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/ExceptionObjectNode.java	Fri Apr 25 10:13:54 2014 +0200
@@ -22,13 +22,9 @@
  */
 package com.oracle.graal.nodes.java;
 
-import java.util.*;
-
-import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.compiler.common.type.*;
 import com.oracle.graal.graph.*;
-import com.oracle.graal.graph.spi.*;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.extended.*;
 import com.oracle.graal.nodes.spi.*;
@@ -37,6 +33,7 @@
  * The entry to an exception handler with the exception coming from a call (as opposed to a local
  * throw instruction or implicit exception).
  */
+@NodeInfo(allowedUsageTypes = {InputType.Memory})
 public class ExceptionObjectNode extends DispatchBeginNode implements Lowerable, MemoryCheckpoint.Single {
 
     public ExceptionObjectNode(MetaAccessProvider metaAccess) {
@@ -49,56 +46,13 @@
     }
 
     @Override
-    public void simplify(SimplifierTool tool) {
-        //
-    }
-
-    private boolean isLowered() {
-        return (stamp() == StampFactory.forVoid());
-    }
-
-    /**
-     * The frame state upon entry to an exception handler is such that it is a
-     * {@link BytecodeFrame#rethrowException rethrow exception} state and the stack contains exactly
-     * the exception object (per the JVM spec) to rethrow. This means that the code creating this
-     * state (i.e. the {@link LoadExceptionObjectNode}) cannot cause a deoptimization as the
-     * runtime/interpreter would not have a valid location for the exception object to be rethrown.
-     */
-    @Override
     public void lower(LoweringTool tool) {
-        if (isLowered()) {
-            return;
-        }
-        LoadExceptionObjectNode loadException = graph().add(new LoadExceptionObjectNode(stamp()));
-        loadException.setStateAfter(stateAfter());
-        List<GuardedNode> guardedNodes = new ArrayList<>();
-        for (Node usage : usages().snapshot()) {
-            if (usage instanceof GuardedNode) {
-                // can't replace the guard with LoadExceptionObjectNode as it is not a GuardingNode
-                // so temporarily change it to remove the GuardedNode from usages
-                GuardedNode guardedNode = (GuardedNode) usage;
-                guardedNode.setGuard(graph().add(new BeginNode()));
-                guardedNodes.add(guardedNode);
-            }
-        }
-        replaceAtUsages(loadException);
-        for (GuardedNode guardedNode : guardedNodes) {
-            BeginNode dummyGuard = (BeginNode) guardedNode.getGuard();
-            guardedNode.setGuard(this);
-            graph().removeFixed(dummyGuard);
-        }
-        graph().addAfterFixed(this, loadException);
-        setStateAfter(null);
-        setStamp(StampFactory.forVoid());
-        loadException.lower(tool);
+        tool.getLowerer().lower(this, tool);
     }
 
     @Override
     public boolean verify() {
-        if (isLowered()) {
-            return true;
-        }
-        assertTrue(stateAfter() != null || stamp() == StampFactory.forVoid(), "an exception handler needs a frame state");
+        assertTrue(stateAfter() != null, "an exception handler needs a frame state");
         return super.verify();
     }
 
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadExceptionObjectNode.java	Thu Apr 24 23:32:30 2014 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,50 +0,0 @@
-/*
- * Copyright (c) 2009, 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.nodes.java;
-
-import com.oracle.graal.api.code.*;
-import com.oracle.graal.compiler.common.type.*;
-import com.oracle.graal.nodes.*;
-import com.oracle.graal.nodes.spi.*;
-
-/**
- * Loads an exception object passed by the runtime from a callee to an exception handler in a
- * caller. The node is only produced when lowering an {@link ExceptionObjectNode}.
- * <p>
- * The frame state upon entry to an exception handler is such that it is a
- * {@link BytecodeFrame#rethrowException rethrow exception} state and the stack contains exactly the
- * exception object (per the JVM spec) to rethrow. This means that the code generated for this node
- * must not cause a deoptimization as the runtime/interpreter would not have a valid location to
- * find the exception object to be rethrown.
- */
-public class LoadExceptionObjectNode extends AbstractStateSplit implements Lowerable {
-
-    public LoadExceptionObjectNode(Stamp stamp) {
-        super(stamp);
-    }
-
-    @Override
-    public void lower(LoweringTool tool) {
-        tool.getLowerer().lower(this, tool);
-    }
-}