From f4fd0ce7331e763f7ee10e6717b1e6f26727be1a Mon Sep 17 00:00:00 2001
From: Lukas Stadler <lukas.stadler@oracle.com>
Date: Wed, 8 Jun 2016 11:54:28 +0200
Subject: [PATCH] unwrap promises for stable lookups in FrameSlotChangeMonitor

---
 .../env/frame/FrameSlotChangeMonitor.java       | 17 ++++++++++++++++-
 1 file changed, 16 insertions(+), 1 deletion(-)

diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/env/frame/FrameSlotChangeMonitor.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/env/frame/FrameSlotChangeMonitor.java
index 7d19a9c479..c616637b9d 100644
--- a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/env/frame/FrameSlotChangeMonitor.java
+++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/env/frame/FrameSlotChangeMonitor.java
@@ -46,6 +46,7 @@ import com.oracle.truffle.api.profiles.BranchProfile;
 import com.oracle.truffle.r.runtime.RArguments;
 import com.oracle.truffle.r.runtime.RInternalError;
 import com.oracle.truffle.r.runtime.StableValue;
+import com.oracle.truffle.r.runtime.data.RPromise;
 
 /**
  * This class maintains information about the current hierarchy of environments in the system. This
@@ -84,6 +85,7 @@ public final class FrameSlotChangeMonitor {
 
     private static final class StableValueLookupResult extends LookupResult {
         private final StableValue<Object> value;
+        @CompilationFinal private Object unwrappedValue;
 
         private StableValueLookupResult(String identifier, StableValue<Object> value) {
             super(identifier);
@@ -100,7 +102,20 @@ public final class FrameSlotChangeMonitor {
             assumption.check();
             StableValue<Object> result = value;
             result.getAssumption().check();
-            return result.getValue();
+            if (unwrappedValue == null) {
+                CompilerDirectives.transferToInterpreterAndInvalidate();
+                Object resultValue = result.getValue();
+                if (resultValue instanceof RPromise) {
+                    if (((RPromise) resultValue).isEvaluated()) {
+                        unwrappedValue = ((RPromise) resultValue).getValue();
+                    } else {
+                        return resultValue;
+                    }
+                } else {
+                    unwrappedValue = resultValue;
+                }
+            }
+            return unwrappedValue;
         }
     }
 
-- 
GitLab