changeset 16385:e0f77d30ad07

ensure the declared method holder is at least linked before emitting an invoke
author Tom Rodriguez <tom.rodriguez@oracle.com>
date Tue, 01 Jul 2014 19:36:36 -0700
parents 5d7b90ab9787
children 9ce3b1efc4e7
files graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java
diffstat 1 files changed, 20 insertions(+), 4 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java	Tue Jul 01 19:35:13 2014 -0700
+++ b/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java	Tue Jul 01 19:36:36 2014 -0700
@@ -680,9 +680,25 @@
                 return new StoreFieldNode(receiver, field, value);
             }
 
+            /**
+             * Ensure that concrete classes are at least linked before generating an invoke.
+             * Interfaces may never be linked so simply return true for them.
+             *
+             * @param target
+             * @return true if the declared holder is an interface or is linked
+             */
+            private boolean callTargetIsResolved(JavaMethod target) {
+                if (target instanceof ResolvedJavaMethod) {
+                    ResolvedJavaMethod resolvedTarget = (ResolvedJavaMethod) target;
+                    ResolvedJavaType resolvedType = resolvedTarget.getDeclaringClass();
+                    return resolvedType.isInterface() || resolvedType.isLinked();
+                }
+                return false;
+            }
+
             @Override
             protected void genInvokeStatic(JavaMethod target) {
-                if (target instanceof ResolvedJavaMethod) {
+                if (callTargetIsResolved(target)) {
                     ResolvedJavaMethod resolvedTarget = (ResolvedJavaMethod) target;
                     ResolvedJavaType holder = resolvedTarget.getDeclaringClass();
                     if (!holder.isInitialized() && ResolveClassBeforeStaticInvoke.getValue()) {
@@ -698,7 +714,7 @@
 
             @Override
             protected void genInvokeInterface(JavaMethod target) {
-                if (target instanceof ResolvedJavaMethod) {
+                if (callTargetIsResolved(target)) {
                     ValueNode[] args = frameState.popArguments(target.getSignature().getParameterSlots(true), target.getSignature().getParameterCount(true));
                     appendInvoke(InvokeKind.Interface, (ResolvedJavaMethod) target, args);
                 } else {
@@ -722,7 +738,7 @@
 
             @Override
             protected void genInvokeVirtual(JavaMethod target) {
-                if (target instanceof ResolvedJavaMethod) {
+                if (callTargetIsResolved(target)) {
                     /*
                      * Special handling for runtimes that rewrite an invocation of
                      * MethodHandle.invoke(...) or MethodHandle.invokeExact(...) to a static
@@ -749,7 +765,7 @@
 
             @Override
             protected void genInvokeSpecial(JavaMethod target) {
-                if (target instanceof ResolvedJavaMethod) {
+                if (callTargetIsResolved(target)) {
                     assert target != null;
                     assert target.getSignature() != null;
                     ValueNode[] args = frameState.popArguments(target.getSignature().getParameterSlots(true), target.getSignature().getParameterCount(true));