@@ -172,6 +172,23 @@ static int utf8_tounicode_case(const char *s, int *uc, int upper)
172172 return l;
173173}
174174
175+ /* A common pattern is to save an object from interp and set a new
176+ * value, and then restore the original. Use this pattern:
177+ *
178+ * Jim_Obj *saveObj = JimPushInterpObj(interp->obj, newobj);
179+ * JimPopInterpObj(interp, interp->obj, saveObj);
180+ */
181+ static Jim_Obj *JimPushInterpObjImpl(Jim_Obj **iop, Jim_Obj *no)
182+ {
183+ Jim_Obj *io = *iop;
184+ Jim_IncrRefCount(no);
185+ *iop = no;
186+ return io;
187+ }
188+
189+ #define JimPushInterpObj(IO, NO) JimPushInterpObjImpl(&(IO), NO)
190+ #define JimPopInterpObj(I, IO, SO) do { Jim_DecrRefCount(I, IO); IO = SO; } while (0)
191+
175192/* These can be used in addition to JIM_CASESENS/JIM_NOCASE */
176193#define JIM_CHARSET_SCAN 2
177194#define JIM_CHARSET_GLOB 0
@@ -5741,6 +5758,7 @@ Jim_Interp *Jim_CreateInterp(void)
57415758 i->errorProc = i->emptyObj;
57425759 i->nullScriptObj = Jim_NewEmptyStringObj(i);
57435760 i->evalFrame = &i->topEvalFrame;
5761+ i->currentFilenameObj = Jim_NewEmptyStringObj(i);
57445762 Jim_IncrRefCount(i->emptyObj);
57455763 Jim_IncrRefCount(i->result);
57465764 Jim_IncrRefCount(i->stackTrace);
@@ -5750,6 +5768,7 @@ Jim_Interp *Jim_CreateInterp(void)
57505768 Jim_IncrRefCount(i->errorProc);
57515769 Jim_IncrRefCount(i->trueObj);
57525770 Jim_IncrRefCount(i->falseObj);
5771+ Jim_IncrRefCount(i->currentFilenameObj);
57535772
57545773 /* Initialize key variables every interpreter should contain */
57555774 Jim_SetVariableStrWithStr(i, JIM_LIBPATH, TCL_LIBRARY);
@@ -5794,6 +5813,7 @@ void Jim_FreeInterp(Jim_Interp *i)
57945813 Jim_DecrRefCount(i, i->unknown);
57955814 Jim_DecrRefCount(i, i->defer);
57965815 Jim_DecrRefCount(i, i->nullScriptObj);
5816+ Jim_DecrRefCount(i, i->currentFilenameObj);
57975817
57985818 /* This will disard any cached commands */
57995819 Jim_InterpIncrProcEpoch(i);
@@ -11641,17 +11661,25 @@ static Jim_Obj *JimReadTextFile(Jim_Interp *interp, const char *filename)
1164111661
1164211662int Jim_EvalFile(Jim_Interp *interp, const char *filename)
1164311663{
11664+ Jim_Obj *filenameObj;
11665+ Jim_Obj *oldFilenameObj;
1164411666 Jim_Obj *scriptObjPtr;
1164511667 int retcode;
1164611668
1164711669 scriptObjPtr = JimReadTextFile(interp, filename);
1164811670 if (!scriptObjPtr) {
1164911671 return JIM_ERR;
1165011672 }
11651- JimSetSourceInfo(interp, scriptObjPtr, Jim_NewStringObj(interp, filename, -1), 1);
11673+
11674+ filenameObj = Jim_NewStringObj(interp, filename, -1);
11675+ JimSetSourceInfo(interp, scriptObjPtr, filenameObj, 1);
11676+
11677+ oldFilenameObj = JimPushInterpObj(interp->currentFilenameObj, filenameObj);
1165211678
1165311679 retcode = Jim_EvalObj(interp, scriptObjPtr);
1165411680
11681+ JimPopInterpObj(interp, interp->currentFilenameObj, oldFilenameObj);
11682+
1165511683 /* Handle the JIM_RETURN return code */
1165611684 if (retcode == JIM_RETURN) {
1165711685 if (--interp->returnLevel <= 0) {
@@ -15565,7 +15593,7 @@ static int Jim_InfoCoreCommand(Jim_Interp *interp, int argc, Jim_Obj *const *arg
1556515593 JIM_DEF_SUBCMD("procs", "?pattern?", 0, 1),
1556615594 JIM_DEF_SUBCMD("references", NULL, 0, 0),
1556715595 JIM_DEF_SUBCMD("returncodes", "?code?", 0, 1),
15568- JIM_DEF_SUBCMD("script", NULL , 0, 0 ),
15596+ JIM_DEF_SUBCMD("script", "?filename?" , 0, 1 ),
1556915597 JIM_DEF_SUBCMD("source", "source ?filename line?", 1, 3),
1557015598 JIM_DEF_SUBCMD("stacktrace", NULL, 0, 0),
1557115599 JIM_DEF_SUBCMD("statics", "procname", 1, 1),
@@ -15655,7 +15683,12 @@ static int Jim_InfoCoreCommand(Jim_Interp *interp, int argc, Jim_Obj *const *arg
1565515683 return JIM_OK;
1565615684
1565715685 case INFO_SCRIPT:
15658- Jim_SetResult(interp, JimGetScript(interp, interp->evalFrame->scriptObj)->fileNameObj);
15686+ if (argc == 3) {
15687+ Jim_IncrRefCount(argv[2]);
15688+ Jim_DecrRefCount(interp, interp->currentFilenameObj);
15689+ interp->currentFilenameObj = argv[2];
15690+ }
15691+ Jim_SetResult(interp, interp->currentFilenameObj);
1565915692 return JIM_OK;
1566015693
1566115694 case INFO_SOURCE:{
0 commit comments