Tcl_Interp(3tcl)
π NAME π
ok so bestie, gather round: Tcl_Interp β it's giving client-visible fields of interpreter structures. That's the whole vibe. No cap.
β¨ SYNOPSIS β¨
Like, literally this is what you type:
#include <tcl.h>
typedef struct {
char *result;
Tcl_FreeProc *freeProc;
int errorLine;
} Tcl_Interp;
typedef void Tcl_FreeProc(
char *blockPtr);
Copy it exactly, don't freestyle, okay? π
π¦ DESCRIPTION π¦
So Tcl_CreateInterp hands you back a pointer to a Tcl_Interp structure. And here's the tea: if you're calling Tcl_CreateInterp, you should treat that pointer as an opaque token β like, it's good for exactly one thing and one thing only, which is passing it back to other routines in the Tcl interface. That's it. That's the job.
Reaching into the fields directly through the pointer, the way described below? Not supported anymore. No ma'am. Instead you use the supported public routines β Tcl_SetResult, Tcl_GetResult, Tcl_SetErrorLine, Tcl_GetErrorLine. Those are the ones. Use them.
πΈ legacy mode, iykyk πΈ
For legacy programs and extensions that are no longer being maintained (we don't judge, we just observe π ), compiling against the Tcl 8.6 header files is only possible with these compiler directives:
#define USE_INTERP_RESULT
and/or
#define USE_INTERP_ERRORLINE
which one you need depends on which fields of the Tcl_Interp struct you're touching. These directives can be embedded right in your code or supplied via compiler options β dealer's choice. β
π§ the result and freeProc fields π§
The result and freeProc fields are the ones that return results or error messages from commands. This info gets sent by command procedures back to Tcl_Eval, and by Tcl_Eval back to its callers. Here's the breakdown:
- The
resultfield points to the string that represents the result or error message. - The
freeProcfield tells you how to dispose of the storage for that string once nobody needs it anymore.
Now, the easiest way for command procedures to mess with these fields is to just call procedures like Tcl_SetResult or Tcl_AppendResult β they hide all the gory details of managing the fields. The description below? That's for the ones raw-dogging the fields directly. π
Whenever a command procedure returns, it must make sure that the result field of its interpreter points to the string being returned by the command. The result field must always point to a valid string β no exceptions, bestie. If a command wants to return no result at all, then interp->result should point to an empty string.
Normally, results are assumed to be statically allocated, which means the contents won't change before the next time Tcl_Eval is called or some other command procedure gets invoked. In this case, the freeProc field must be zero.
Alternatively β and this is the spicy option π₯ β a command procedure may dynamically allocate its return value (e.g. using Tcl_Alloc) and store a pointer to it in interp->result. In that case, the command procedure must also set interp->freeProc to the address of a procedure that can free the value, or to TCL_DYNAMIC if the storage was allocated directly by Tcl or by a call to Tcl_Alloc.
If interp->freeProc is non-zero, then Tcl will call freeProc to free the space pointed to by interp->result before it invokes the next command. And heads up: if a client procedure overwrites interp->result while interp->freeProc is non-zero, then it is responsible for calling freeProc to free the old interp->result β and for that purpose, the Tcl_FreeResult macro should be used. Don't skip that part, it's giving memory leak otherwise. π
FreeProc should have arguments and a result that match the Tcl_FreeProc declaration above: it receives a single argument, which is a pointer to the result value to free.
In most applications, TCL_DYNAMIC is the only non-zero value ever used for freeProc. But an application may store a different procedure address in freeProc in order to use an alternate memory allocator, or in order to do other cleanup when the result memory is freed. Main character energy, honestly. π
π what Tcl_Eval does for you π
As part of processing each command, Tcl_Eval initializes interp->result and interp->freeProc just before calling the command procedure for the command. Specifically:
- The
freeProcfield will be initialized to zero. interp->resultwill point to an empty string.
Commands that don't return any value can simply leave the fields alone. Slay, no work required.
Furthermore, the empty string pointed to by result is actually part of an array of TCL_RESULT_SIZE characters (approximately 200). So if a command wishes to return a short string, it can simply copy it to the area pointed to by interp->result. Or β cute alternative β it can use the sprintf procedure to generate a short result string at the location pointed to by interp->result.
π the initialized-state convention π
It's a general convention in Tcl-based applications that the result of an interpreter is normally in the initialized state described in the previous paragraph. Procedures that manipulate an interpreter's result (e.g. by returning an error) will generally assume that the result has been initialized when the procedure is called.
So if such a procedure is going to be called after the result has been changed, then Tcl_ResetResult should be called first to reset the result to its initialized state. Reset first, ask questions never. β¨
β οΈ Real talk: the direct use ofinterp->resultis strongly deprecated (seeTcl_SetResult). Like, we're telling you this for your own good.
π the errorLine field π
The errorLine field is valid only after Tcl_Eval returns a TCL_ERROR return code. In this situation, the errorLine field identifies the line number of the command being executed when the error occurred.
The line numbers are relative to the command being executed:
1means the first line of the command passed toTcl_Eval2means the second line- and so on, you get the pattern π«
The errorLine field is typically used in conjunction with Tcl_AddErrorInfo to report information about where an error occurred. And ErrorLine should not normally be modified except by Tcl_Eval β hands off, bestie. π
ββοΈ
π KEYWORDS π
free, initialized, interpreter, malloc, result
and that's the whole page, bestie!! this one's from the Tcl Library Procedures, dated way back in Tcl 7.5 β yes, 7.5, she's vintage, she's iconic, she's still serving. Tcl_Interp(3tcl) forever πβ¨π«Ά
π¦ where this page comes from
- debian bookworm: tcl8.6-doc 8.6.13+dfsg-2
- debian trixie: tcl8.6-doc 8.6.16+dfsg-1
- ubuntu jammy: tcl8.6-doc 8.6.12+dfsg-1build1
- ubuntu noble: tcl8.6-doc 8.6.14+dfsg-1build1
- ubuntu questing: tcl8.6-doc 8.6.17+dfsg-1
- ubuntu resolute: tcl8.6-doc 8.6.17+dfsg-1build1
- ubuntu stonking: tcl8.6-doc 8.6.18+dfsg-1
- Copyright (c) 1989-1993 The Regents of the University of California
- Copyright (c) 1994-1996 Sun Microsystems, Inc
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms