diff options
-rw-r--r-- | generic/tclBasic.c | 16 | ||||
-rw-r--r-- | generic/tclExecute.c | 17 | ||||
-rw-r--r-- | generic/tclNRE.h | 17 | ||||
-rw-r--r-- | generic/tclTest.c | 22 | ||||
-rw-r--r-- | unix/Makefile.in | 2 |
5 files changed, 40 insertions, 34 deletions
diff --git a/generic/tclBasic.c b/generic/tclBasic.c index cb14afd..dfd27d2 100644 --- a/generic/tclBasic.c +++ b/generic/tclBasic.c @@ -4285,17 +4285,19 @@ EvalObjvCore( int TclNRRunCallbacks( Tcl_Interp *interp, - int result) /* Callbacks are run until the first NRRoot.*/ + int result) { NRE_callback *cbPtr; - Tcl_NRPostProc *procPtr; - while (TOP_CB(interp) && (TOP_CB(interp)->procPtr != NRRoot)) { - POP_CB(interp, cbPtr); - procPtr = cbPtr->procPtr; - result = procPtr(cbPtr->data, interp, result); - } + /* Callbacks are run until the first NRRoot.*/ + + do { + POP_CB(interp, cbPtr); + result = (cbPtr->procPtr)(cbPtr->data, interp, result); + } while (TOP_CB(interp) && (TOP_CB(interp)->procPtr != NRRoot)); + if (TOP_CB(interp)) { + /* pop the remaining NRRoot */ POP_CB(interp, cbPtr); } return result; diff --git a/generic/tclExecute.c b/generic/tclExecute.c index cbeaba3..05896f1 100644 --- a/generic/tclExecute.c +++ b/generic/tclExecute.c @@ -2817,23 +2817,6 @@ TEBCresume( TEBC_YIELD(); iPtr->numLevels++; - if (TCL_OK == TclInterpReady(interp)) { - /* - * If everything is OK, avoid going to TclNREvalObjv and do the - * job directly here. - */ - - Command *cmdPtr = (Command *) Tcl_GetCommandFromObj(interp, objv[0]); - if (cmdPtr && !(cmdPtr->flags & CMD_HAS_EXEC_TRACES) && !iPtr->tracePtr ) { - iPtr->ensembleRewrite.sourceObjs = NULL; - TclNRAddCallback(interp, NRCommand, NULL, NULL, NULL, NULL); - if (cmdPtr->nreProc) { - return cmdPtr->nreProc(cmdPtr->objClientData, interp, objc, objv); - } else { - return cmdPtr->objProc(cmdPtr->objClientData, interp, objc, objv); - } - } - } iPtr->numLevels--; return TclNREvalObjv(interp, objc, objv, TCL_EVAL_NOERR | TCL_EVAL_SOURCE_IN_FRAME, NULL); diff --git a/generic/tclNRE.h b/generic/tclNRE.h index ca8dd7f..c1df6d2 100644 --- a/generic/tclNRE.h +++ b/generic/tclNRE.h @@ -63,12 +63,25 @@ typedef struct NRE_stack { #define NEXT_CB(ptr) TclNextCallback(ptr) +#define NRE_TRAMPOLINE 0 +#if NRE_TRAMPOLINE +#define NRE_JUMP(interp,postProcPtr,data0,data1,data2,data3) \ + TclNRAddCallback((interp),(postProcPtr),(data0),(data1),(data2),(data3)); \ + NRE_NEXT(TCL_OK) #define NRE_NEXT(result) \ return (result) - +#else +/* no trampoline, optimized sibcalls */ #define NRE_JUMP(interp,postProcPtr,data0,data1,data2,data3) \ TclNRAddCallback((interp),(postProcPtr),(data0),(data1),(data2),(data3)); \ - NRE_NEXT(TCL_OK) + return TCL_OK +#define NRE_NEXT(result) \ + do { /* optimized indirect sibling calls?! */ \ + NRE_callback *cbPtr; \ + POP_CB(interp, cbPtr); \ + return (cbPtr->procPtr)(cbPtr->data, interp, result); \ + } while (0) +#endif MODULE_SCOPE TCL_NOINLINE NRE_callback *TclNewCallback(Tcl_Interp *interp); MODULE_SCOPE TCL_NOINLINE NRE_callback *TclPopCallback(Tcl_Interp *interp); diff --git a/generic/tclTest.c b/generic/tclTest.c index aa75738..baf54ec 100644 --- a/generic/tclTest.c +++ b/generic/tclTest.c @@ -394,6 +394,7 @@ static int TestHashSystemHashCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]); +static TCL_NOINLINE void *NRE_depth(void); static int NREUnwind_callback(ClientData data[], Tcl_Interp *interp, int result); static int TestNREUnwind(ClientData clientData, @@ -6557,31 +6558,38 @@ TestgetintCmd( } } + +static TCL_NOINLINE void * +NRE_depth( + void) +{ + int none; + return &none; +} + static int NREUnwind_callback( ClientData data[], Tcl_Interp *interp, int result) { - int none; - if (data[0] == INT2PTR(-1)) { - TclNRAddCallback(interp, NREUnwind_callback, &none, INT2PTR(-1), + TclNRAddCallback(interp, NREUnwind_callback, NRE_depth(), INT2PTR(-1), INT2PTR(-1), NULL); } else if (data[1] == INT2PTR(-1)) { - TclNRAddCallback(interp, NREUnwind_callback, data[0], &none, + TclNRAddCallback(interp, NREUnwind_callback, data[0], NRE_depth(), INT2PTR(-1), NULL); } else if (data[2] == INT2PTR(-1)) { TclNRAddCallback(interp, NREUnwind_callback, data[0], data[1], - &none, NULL); + NRE_depth(), NULL); } else { Tcl_Obj *idata[3]; idata[0] = Tcl_NewIntObj((int) (data[1] - data[0])); idata[1] = Tcl_NewIntObj((int) (data[2] - data[0])); - idata[2] = Tcl_NewIntObj((int) ((void *) &none - data[0])); + idata[2] = Tcl_NewIntObj((int) ((void *) NRE_depth() - data[0])); Tcl_SetObjResult(interp, Tcl_NewListObj(3, idata)); } - return TCL_OK; + NRE_NEXT(TCL_OK); } static int diff --git a/unix/Makefile.in b/unix/Makefile.in index ed9d9fb..de21f47 100644 --- a/unix/Makefile.in +++ b/unix/Makefile.in @@ -95,7 +95,7 @@ TCL_MODULE_PATH = @TCL_MODULE_PATH@ CFLAGS_WARNING = @CFLAGS_WARNING@ # The default switches for optimization or debugging -CFLAGS_DEBUG = @CFLAGS_DEBUG@ +CFLAGS_DEBUG = @CFLAGS_DEBUG@ @CFLAGS_OPTIMIZE@ CFLAGS_OPTIMIZE = @CFLAGS_OPTIMIZE@ # To change the compiler switches, for example to change from optimization to |