summaryrefslogtreecommitdiffstats
path: root/generic/tclExecute.c
diff options
context:
space:
mode:
authormig <mig>2013-01-10 21:18:52 (GMT)
committermig <mig>2013-01-10 21:18:52 (GMT)
commite89dea9b9b819e7b5ddc8d171127b749e237af35 (patch)
treeba9d20a99fce98d2f9273df62edbb14bab9f55d8 /generic/tclExecute.c
parent41c09d7b4d37c2b2fc7cec61aaaa3ca59a56a7c5 (diff)
downloadtcl-e89dea9b9b819e7b5ddc8d171127b749e237af35.zip
tcl-e89dea9b9b819e7b5ddc8d171127b749e237af35.tar.gz
tcl-e89dea9b9b819e7b5ddc8d171127b749e237af35.tar.bz2
tailcall now running in a simpler model, with no eval-flags and no nre-stack rewriting; yieldto also requires one fewer bounce. Mostly from mig-nre-mods
Diffstat (limited to 'generic/tclExecute.c')
-rw-r--r--generic/tclExecute.c20
1 files changed, 7 insertions, 13 deletions
diff --git a/generic/tclExecute.c b/generic/tclExecute.c
index ade71f6..af60a95 100644
--- a/generic/tclExecute.c
+++ b/generic/tclExecute.c
@@ -2399,7 +2399,6 @@ TEBCresume(
case INST_TAILCALL: {
Tcl_Obj *listPtr, *nsObjPtr;
- NRE_callback *tailcallPtr;
opnd = TclGetUInt1AtPtr(pc+1);
@@ -2433,18 +2432,12 @@ TEBCresume(
listPtr = Tcl_NewListObj(opnd, &OBJ_AT_DEPTH(opnd-1));
nsObjPtr = Tcl_NewStringObj(iPtr->varFramePtr->nsPtr->fullName, -1);
- Tcl_IncrRefCount(listPtr);
- Tcl_IncrRefCount(nsObjPtr);
- TclNRAddCallback(interp, TclNRTailcallEval, listPtr, nsObjPtr,
- NULL, NULL);
-
- /*
- * Unstitch ourselves and do a [return].
- */
+ TclListObjSetElement(interp, listPtr, 0, nsObjPtr);
+ if (iPtr->varFramePtr->tailcallPtr) {
+ Tcl_DecrRefCount(iPtr->varFramePtr->tailcallPtr);
+ }
+ iPtr->varFramePtr->tailcallPtr = listPtr;
- tailcallPtr = TOP_CB(interp);
- TOP_CB(interp) = tailcallPtr->nextPtr;
- iPtr->varFramePtr->tailcallPtr = tailcallPtr;
result = TCL_RETURN;
cleanup = opnd;
goto processExceptionReturn;
@@ -3054,8 +3047,9 @@ TEBCresume(
DECACHE_STACK_INFO();
pc += 6;
TEBC_YIELD();
+
TclNRAddCallback(interp, TclClearRootEnsemble, NULL,NULL,NULL,NULL);
- iPtr->evalFlags |= TCL_EVAL_REDIRECT;
+ TclDeferCallbacks(interp, /*skip tailcalls */ 1);
return TclNREvalObjEx(interp, objPtr, TCL_EVAL_INVOKE, NULL, INT_MIN);
/*