This is not necessarily the current version of this TIP.
| TIP: | 32 |
| Title: | Add Tcl_Obj support to traces |
| Version: | $Revision: 1.3 $ |
| Authors: |
David Cuthbert <dacut at kanga dot org> Kevin Kenny <kennykb at acm dot org> |
| State: | Draft |
| Type: | Project |
| Tcl-Version: | 8.4a2 |
| Vote: | Pending |
| Created: | Friday, 23 March 2001 |
| Discussions To: | news:comp.lang.tcl |
| Keywords: | trace, Tcl_Obj |
This document proposes to add Tcl_Obj support for trace procedures written in C.
The Tcl_Obj system was introduced in version 8.0, making computations (potentially) much more efficient by eliminating many type conversions to and from strings. However, the trace API continues to require character strings in both command and variable traces.
Add the following functions to the Tcl core:
Tcl_Trace Tcl_CreateObjTrace(interp, level, objProc, clientData)
Tcl_CreateObjTrace behaves in the same manner as Tcl_CreateTrace, except the trace procedure (objProc) should have arguments and result that match type type Tcl_CmdObjTraceProc:
typedef void Tcl_CmdObjTraceProc(
ClientData clientData,
Tcl_Interp *interp,
int level,
char *command,
Tcl_ObjCmdProc *cmdProc,
ClientData cmdClientData,
int objc,
Tcl_Obj * CONST objv[] );
Trace tokens returned by Tcl_CreateObjTrace can be used in Tcl_DeleteTrace to remove the trace.
int Tcl_ObjTraceVar2(interp, part1Ptr, part2Ptr, flags, objProc, clientData)
Tcl_ObjTraceVar2 behaves in the same manner as Tcl_TraceVar2, except the variable name is passed as Tcl_Obj pointers (in the same manner as Tcl_ObjSetVar2, q.v.), and the trace procedure (objProc) should have arguments and result that match the type Tcl_VarObjTraceProc:
typedef Tcl_Obj *Tcl_VarObjTraceProc(
ClientData clientData,
Tcl_Interp *interp,
Tcl_Obj *part1Ptr,
Tcl_Obj *part2Ptr,
int flags );
Under normal conditions, the trace procedure should return NULL, indicating successful completion. If objProc returns a value other than NULL it signifies that an error occurred. Upon return, the reference count of the Tcl_Obj should be at least one; ownership of this reference is transferred to the Tcl interpreter.
void Tcl_ObjUntraceVar2(interp, part1Ptr, part2Ptr, flags, objProc, clientData)
Tcl_ObjUntraceVar2 behaves in the same manner as Tcl_UntraceVar2, except it is used to remove trace procedures registered with Tcl_ObjTraceVar2.
ClientData Tcl_ObjVarTraceInfo2(interp, part1Ptr, part2Ptr, flags, objProc, prevClientData)
Tcl_ObjVarTraceInfo2 behaves in the same manner as Tcl_VarTraceInfo2, except it is used to iterate through trace procedures registered with Tcl_ObjTraceVar2.
30 March 2001 - Changed return value of objProc to a Tcl_Obj * instead of int (and using the interpreter result to indicate an error). This is more consistent with the current behavior (but without the bug). -dac
Tcl manual pages Tcl_TraceVar and Tcl_CreateTrace.
Copyright © 2000 by David Cuthbert. Distribution in whole or part, with or without annotations, is unlimited.
Kevin Kenny (2 April 2001):
This proposal is detailing functionality that I've wanted for quite some time. Given, however, that it allows us to make a partial break with the past, I'd like to make some minor changes to Tcl_CmdObjTraceProc.
In place of the type signature,
typedef void Tcl_CmdObjTraceProc(
ClientData clientData,
Tcl_Interp *interp,
int level,
char *command,
Tcl_ObjCmdProc *cmdProc,
ClientData cmdClientData,
int objc,
Tcl_Obj * CONST objv[] );
may I suggest that since the interpreter has the Command structure in hand, it simply deliver a Tcl_Command with the command's information, in place of the command procedure and client data? Also, the command name is redundant, since the same information is present in objv[ 0 ].
The signature would then be:
typedef void Tcl_CmdObjTraceProc(
ClientData clientData, /* Client data from Tcl_CreateObjTrace */
Tcl_Interp* interp, /* Tcl interpreter */
int level, /* Execution level */
Tcl_Command cmdInfo, /* Command information */
int objc, /* Parameter count */
Tcl_Obj *CONST objv[] /* Parameter vector */
);
This would allow the trace procedure to do interesting things like replace the command's objCmdProc and client data temporarily, before the interpreter uses them. I have a profiler that works that way, using the existing API's. It's awkward at the moment, because it needs to use Tcl_FindCommand to get at the command object (Tcl_GetCommandInfo would also work in current releases, but I'm in the position of needing bugward compatibility with 8.0). It also is a horrible performance drain because of the shimmering that's needed to support tracing currently, and the fact that tracing defeats the bytecode compiler.
If this change gets approved, and I can get TclpGetTime exported, I'll definitely release the profiler. (I don't care to release code that depends on tclInt.h, because I don't want to track APIs that the maintainers don't consider 'stable'.)
By the way, this change should be easier from a political standpoint than it was a year ago, when any extension that used this mechanism was presumably a competitor of the TclPro tools.
This is not necessarily the current version of this TIP.