org.chromium.sdk/src/org/chromium/sdk/internal/ContextBuilder.java
changeset 355 8726e95bcbba
parent 276 f2f4a1259de8
--- a/org.chromium.sdk/src/org/chromium/sdk/internal/ContextBuilder.java	Mon Jun 07 16:33:07 2010 -0700
+++ b/org.chromium.sdk/src/org/chromium/sdk/internal/ContextBuilder.java	Mon Jun 07 16:51:19 2010 -0700
@@ -237,6 +237,17 @@
       }
     }
 
+    private boolean sendNoMessageAndInvalidate() {
+      synchronized (sendContextCommandsMonitor) {
+        if (!isValid) {
+          return false;
+        }
+        isValid = false;
+        return true;
+      }
+    }
+
+
     private class UserContext implements DebugContext {
       private final DebugContextData data;
 
@@ -266,6 +277,14 @@
         return data.exceptionData;
       }
 
+      Collection<Breakpoint> getBreakpointsHitSafe() {
+        return data.breakpointsHit;
+      }
+
+      ExceptionData getExceptionDataSafe() {
+        return data.exceptionData;
+      }
+
       public JsEvaluateContext getGlobalEvaluateContext() {
         return evaluateContext;
       }
@@ -306,6 +325,19 @@
         sendMessageAsyncAndIvalidate(message, commandCallback, true, null);
       }
 
+      /**
+       * Behaves as continue but does not send any messages to remote VM.
+       * This brings ContextBuilder to state when we are about to build a new context.
+       */
+      boolean continueLocally() {
+        if (!sendNoMessageAndInvalidate()) {
+          return false;
+        }
+        contextDismissed(UserContext.this);
+        getDebugSession().getDebugEventListener().resumed();
+        return true;
+      }
+
       InternalContext getInternalContextForTests() {
         return PreContext.this;
       }
@@ -385,6 +417,24 @@
     }
   }
 
+  /**
+   * Drops the current context and initiates reading data and building a new one.
+   * Must be called from Dispatch thread.
+   * @return ExpectingBacktraceStep or null if there is no active context currently
+   */
+  ExpectingBacktraceStep startRebuildCurrentContext() {
+    // We can use currentStep as long as we are being operated from Dispatch thread.
+    if (currentStep instanceof PreContext.UserContext == false) {
+      return null;
+    }
+    PreContext.UserContext userContext = (PreContext.UserContext) currentStep;
+    if (!userContext.continueLocally()) {
+      return null;
+    }
+    return buildNewContext().setContextState(userContext.getBreakpointsHitSafe(),
+        userContext.getExceptionDataSafe());
+  }
+
   static InternalContext getInternalContextForTests(DebugContext debugContext) {
     PreContext.UserContext userContext = (PreContext.UserContext) debugContext;
     return userContext.getInternalContextForTests();