public static void Init(IScriptable scope, bool zealed) { Continuation obj = new Continuation(); obj.ExportAsJSClass(MAX_PROTOTYPE_ID, scope, zealed); }
static void captureContinuation (Context cx, CallFrame frame, int stackTop) { Continuation c = new Continuation (); ScriptRuntime.setObjectProtoAndParent (c, ScriptRuntime.getTopCallScope (cx)); // Make sure that all frames upstack frames are frozen CallFrame x = frame.parentFrame; while (x != null && !x.frozen) { x.frozen = true; // Allow to GC unused stack space for (int i = x.savedStackTop + 1; i != x.stack.Length; ++i) { // Allow to GC unused stack space x.stack [i] = null; } if (x.savedCallOp == Token.CALL) { // the call will always overwrite the stack top with the result x.stack [x.savedStackTop] = null; } else { if (x.savedCallOp != Token.NEW) Context.CodeBug (); // the new operator uses stack top to store the constructed // object so it shall not be cleared: see comments in // setCallResult } x = x.parentFrame; } c.initImplementation (frame.parentFrame); frame.stack [stackTop] = c; }
internal ContinuationJump (Continuation c, CallFrame current) { this.capturedFrame = (CallFrame)c.Implementation; if (this.capturedFrame == null || current == null) { // Continuation and current execution does not share // any frames if there is nothing to capture or // if there is no currently executed frames this.branchFrame = null; } else { // Search for branch frame where parent frame chains starting // from captured and current meet. CallFrame chain1 = this.capturedFrame; CallFrame chain2 = current; // First work parents of chain1 or chain2 until the same // frame depth. int diff = chain1.frameIndex - chain2.frameIndex; if (diff != 0) { if (diff < 0) { // swap to make sure that // chain1.frameIndex > chain2.frameIndex and diff > 0 chain1 = current; chain2 = this.capturedFrame; diff = -diff; } do { chain1 = chain1.parentFrame; } while (--diff != 0); if (chain1.frameIndex != chain2.frameIndex) Context.CodeBug (); } // Now walk parents in parallel until a shared frame is found // or until the root is reached. while (chain1 != chain2 && chain1 != null) { chain1 = chain1.parentFrame; chain2 = chain2.parentFrame; } this.branchFrame = chain1; if (this.branchFrame != null && !this.branchFrame.frozen) Context.CodeBug (); } }
public static object restartContinuation (Continuation c, Context cx, IScriptable scope, object [] args) { if (!ScriptRuntime.hasTopCall (cx)) { return ScriptRuntime.DoTopCall (c, cx, scope, null, args); } object arg; if (args.Length == 0) { arg = Undefined.Value; } else { arg = args [0]; } CallFrame capturedFrame = (CallFrame)c.Implementation; if (capturedFrame == null) { // No frames to restart return arg; } ContinuationJump cjump = new ContinuationJump (c, null); cjump.result = arg; return InterpretLoop (cx, null, cjump); }
public static void Init (IScriptable scope, bool zealed) { Continuation obj = new Continuation (); obj.ExportAsJSClass (MAX_PROTOTYPE_ID, scope, zealed); }