0

When using Tcl C++ API Tcl_Eval, if it returns TCL_ERROR, the error message can be retrieved from Tcl_GetStringResult(interp). However, when executing a bunch of tcl script, the error message doesn't indicate which line the script fails.

Eg:

can't find package foobar
    while executing
"package require foobar"
    (file "./test.tn" line 5)

Tcl_GetStringResult(interp) doesn't provide this information: (file "./test.tn" line 5). Is there a way to print out the call stack like in tcl interpreter so that I know which line the script fails?

Jackson
  • 5,627
  • 2
  • 29
  • 48
Stan
  • 37,207
  • 50
  • 124
  • 185

2 Answers2

1

I use the following code to pull back and report on the errorinfo that is available from the interpreter.

Tcl_Obj *top_interpInfoName ;
Tcl_Obj *top_interpInfo ;

top_interpInfoName = Tcl_NewStringObj("errorInfo", -1) ;
    Tcl_IncrRefCount(top_interpInfoName) ;
    top_interpInfo =  Tcl_ObjGetVar2(tcl_interp,
                                     top_interpInfoName,
                                     NULL,
                                     TCL_LEAVE_ERR_MSG) ;
    Tcl_IncrRefCount(top_interpInfo) ;
    ERR_REP2("ERROR: %s", Tcl_GetString(top_interpInfo)) ;
    Tcl_DecrRefCount(top_interpInfoName) ;
    Tcl_DecrRefCount(top_interpInfo) ;

ERR_REP2 is my error reporting macro you need to replace it with your own.

Jackson
  • 5,627
  • 2
  • 29
  • 48
1

The information you are looking for, the error info (i.e., stack trace), is in the global errorInfo variable. This information may be retrieved with Tcl_GetVar or one of its related functions. One of the best to choose is Tcl_GetVar2Ex (the name being a product of a slowly evolving API) which is highly efficient:

Tcl_Obj *infoObj = Tcl_GetVar2Ex(interp, "errorInfo", NULL, TCL_GLOBAL_ONLY);

Then you use Tcl_GetString to extract the human-readable part as a char * (treat as const).

Donal Fellows
  • 133,037
  • 18
  • 149
  • 215