source: HiSusy/trunk/Delphes-3.0.0/external/tcl/tclBasic.c @ 1

Last change on this file since 1 was 1, checked in by zerwas, 11 years ago

first import of structure, PYTHIA8 and DELPHES

File size: 112.2 KB
Line 
1/*
2 * tclBasic.c --
3 *
4 *      Contains the basic facilities for TCL command interpretation,
5 *      including interpreter creation and deletion, command creation
6 *      and deletion, and command parsing and execution.
7 *
8 * Copyright (c) 1987-1994 The Regents of the University of California.
9 * Copyright (c) 1994-1997 Sun Microsystems, Inc.
10 * Copyright (c) 1998-1999 by Scriptics Corporation.
11 *
12 * See the file "license.terms" for information on usage and redistribution
13 * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
14 *
15 * RCS: @(#) $Id: tclBasic.c,v 1.1 2008-06-04 13:58:03 demin Exp $
16 */
17
18#include "tclInt.h"
19#include "tclCompile.h"
20#ifndef TCL_GENERIC_ONLY
21#   include "tclPort.h"
22#endif
23
24/*
25 * Static procedures in this file:
26 */
27
28static void             DeleteInterpProc _ANSI_ARGS_((Tcl_Interp *interp));
29static void             HiddenCmdsDeleteProc _ANSI_ARGS_((
30                            ClientData clientData, Tcl_Interp *interp));
31
32/*
33 * The following structure defines the commands in the Tcl core.
34 */
35
36typedef struct {
37    char *name;                 /* Name of object-based command. */
38    Tcl_CmdProc *proc;          /* String-based procedure for command. */
39    Tcl_ObjCmdProc *objProc;    /* Object-based procedure for command. */
40    CompileProc *compileProc;   /* Procedure called to compile command. */
41    int isSafe;                 /* If non-zero, command will be present
42                                 * in safe interpreter. Otherwise it will
43                                 * be hidden. */
44} CmdInfo;
45
46/*
47 * The built-in commands, and the procedures that implement them:
48 */
49
50static CmdInfo builtInCmds[] = {
51    /*
52     * Commands in the generic core. Note that at least one of the proc or
53     * objProc members should be non-NULL. This avoids infinitely recursive
54     * calls between TclInvokeObjectCommand and TclInvokeStringCommand if a
55     * command name is computed at runtime and results in the name of a
56     * compiled command.
57     */
58
59    {"append",          (Tcl_CmdProc *) NULL,   Tcl_AppendObjCmd,
60        (CompileProc *) NULL,           1},
61    {"array",           (Tcl_CmdProc *) NULL,   Tcl_ArrayObjCmd,
62        (CompileProc *) NULL,           1},
63    {"break",           Tcl_BreakCmd,           (Tcl_ObjCmdProc *) NULL,
64        TclCompileBreakCmd,             1},
65    {"case",            (Tcl_CmdProc *) NULL,   Tcl_CaseObjCmd,
66        (CompileProc *) NULL,           1},
67    {"catch",           (Tcl_CmdProc *) NULL,   Tcl_CatchObjCmd,       
68        TclCompileCatchCmd,             1},
69    {"concat",          (Tcl_CmdProc *) NULL,   Tcl_ConcatObjCmd,
70        (CompileProc *) NULL,           1},
71    {"continue",        Tcl_ContinueCmd,        (Tcl_ObjCmdProc *) NULL,
72        TclCompileContinueCmd,          1},
73    {"error",           (Tcl_CmdProc *) NULL,   Tcl_ErrorObjCmd,
74        (CompileProc *) NULL,           1},
75    {"eval",            (Tcl_CmdProc *) NULL,   Tcl_EvalObjCmd,
76        (CompileProc *) NULL,           1},
77    {"expr",            (Tcl_CmdProc *) NULL,   Tcl_ExprObjCmd,
78        TclCompileExprCmd,              1},
79    {"for",             Tcl_ForCmd,             (Tcl_ObjCmdProc *) NULL,
80        TclCompileForCmd,               1},
81    {"foreach",         (Tcl_CmdProc *) NULL,   Tcl_ForeachObjCmd,
82        TclCompileForeachCmd,           1},
83    {"format",          (Tcl_CmdProc *) NULL,   Tcl_FormatObjCmd,
84        (CompileProc *) NULL,           1},
85    {"global",          (Tcl_CmdProc *) NULL,   Tcl_GlobalObjCmd,
86        (CompileProc *) NULL,           1},
87    {"if",              Tcl_IfCmd,              (Tcl_ObjCmdProc *) NULL,
88        TclCompileIfCmd,                1},
89    {"incr",            Tcl_IncrCmd,            (Tcl_ObjCmdProc *) NULL,
90        TclCompileIncrCmd,              1},
91    {"info",            (Tcl_CmdProc *) NULL,   Tcl_InfoObjCmd,
92        (CompileProc *) NULL,           1},
93    {"join",            (Tcl_CmdProc *) NULL,   Tcl_JoinObjCmd,
94        (CompileProc *) NULL,           1},
95    {"lappend",         (Tcl_CmdProc *) NULL,   Tcl_LappendObjCmd,
96        (CompileProc *) NULL,           1},
97    {"add",             (Tcl_CmdProc *) NULL,   Tcl_LappendObjCmd,
98        (CompileProc *) NULL,           1},
99    {"lindex",          (Tcl_CmdProc *) NULL,   Tcl_LindexObjCmd,
100        (CompileProc *) NULL,           1},
101    {"linsert",         (Tcl_CmdProc *) NULL,   Tcl_LinsertObjCmd,
102        (CompileProc *) NULL,           1},
103    {"list",            (Tcl_CmdProc *) NULL,   Tcl_ListObjCmd,
104        (CompileProc *) NULL,           1},
105    {"llength",         (Tcl_CmdProc *) NULL,   Tcl_LlengthObjCmd,
106        (CompileProc *) NULL,           1},
107    {"lrange",          (Tcl_CmdProc *) NULL,   Tcl_LrangeObjCmd,
108        (CompileProc *) NULL,           1},
109    {"lreplace",        (Tcl_CmdProc *) NULL,   Tcl_LreplaceObjCmd,
110        (CompileProc *) NULL,           1},
111    {"lsort",           (Tcl_CmdProc *) NULL,   Tcl_LsortObjCmd,
112        (CompileProc *) NULL,           1},
113    {"namespace",       (Tcl_CmdProc *) NULL,   Tcl_NamespaceObjCmd,
114        (CompileProc *) NULL,           1},
115    {"proc",            (Tcl_CmdProc *) NULL,   Tcl_ProcObjCmd, 
116        (CompileProc *) NULL,           1},
117    {"return",          (Tcl_CmdProc *) NULL,   Tcl_ReturnObjCmd,       
118        (CompileProc *) NULL,           1},
119    {"scan",            Tcl_ScanCmd,            (Tcl_ObjCmdProc *) NULL,
120        (CompileProc *) NULL,           1},
121    {"set",             Tcl_SetCmd,             (Tcl_ObjCmdProc *) NULL,   
122        TclCompileSetCmd,               1},
123    {"split",           (Tcl_CmdProc *) NULL,   Tcl_SplitObjCmd,
124        (CompileProc *) NULL,           1},
125    {"string",          (Tcl_CmdProc *) NULL,   Tcl_StringObjCmd,
126        (CompileProc *) NULL,           1},
127    {"subst",           Tcl_SubstCmd,           (Tcl_ObjCmdProc *) NULL,
128        (CompileProc *) NULL,           1},
129    {"trace",           Tcl_TraceCmd,           (Tcl_ObjCmdProc *) NULL,
130        (CompileProc *) NULL,           1},
131    {"unset",           (Tcl_CmdProc *) NULL,   Tcl_UnsetObjCmd,       
132        (CompileProc *) NULL,           1},
133    {"uplevel",         (Tcl_CmdProc *) NULL,   Tcl_UplevelObjCmd,     
134        (CompileProc *) NULL,           1},
135    {"upvar",           (Tcl_CmdProc *) NULL,   Tcl_UpvarObjCmd,       
136        (CompileProc *) NULL,           1},
137    {"variable",        (Tcl_CmdProc *) NULL,   Tcl_VariableObjCmd,
138        (CompileProc *) NULL,           1},
139    {"while",           Tcl_WhileCmd,           (Tcl_ObjCmdProc *) NULL,   
140        TclCompileWhileCmd,             1},
141
142    {NULL,              (Tcl_CmdProc *) NULL,   (Tcl_ObjCmdProc *) NULL,
143        (CompileProc *) NULL,           0}
144};
145
146/*
147 *----------------------------------------------------------------------
148 *
149 * Tcl_CreateInterp --
150 *
151 *      Create a new TCL command interpreter.
152 *
153 * Results:
154 *      The return value is a token for the interpreter, which may be
155 *      used in calls to procedures like Tcl_CreateCmd, Tcl_Eval, or
156 *      Tcl_DeleteInterp.
157 *
158 * Side effects:
159 *      The command interpreter is initialized with an empty variable
160 *      table and the built-in commands.
161 *
162 *----------------------------------------------------------------------
163 */
164
165Tcl_Interp *
166Tcl_CreateInterp()
167{
168    register Interp *iPtr;
169    register Command *cmdPtr;
170    register CmdInfo *cmdInfoPtr;
171    union {
172        char c[sizeof(short)];
173        short s;
174    } order;
175
176    /*
177     * Panic if someone updated the CallFrame structure without
178     * also updating the Tcl_CallFrame structure (or vice versa).
179     */ 
180
181    if (sizeof(Tcl_CallFrame) != sizeof(CallFrame)) {
182        /*NOTREACHED*/
183        panic("Tcl_CallFrame and CallFrame are not the same size");
184    }
185
186    /*
187     * Initialize support for namespaces and create the global namespace
188     * (whose name is ""; an alias is "::"). This also initializes the
189     * Tcl object type table and other object management code.
190     */
191
192    TclInitNamespaces();
193   
194    iPtr = (Interp *) ckalloc(sizeof(Interp));
195    iPtr->result = iPtr->resultSpace;
196    iPtr->freeProc = 0;
197    iPtr->objResultPtr = Tcl_NewObj(); /* an empty object */
198    Tcl_IncrRefCount(iPtr->objResultPtr);
199    iPtr->errorLine = 0;
200    Tcl_InitHashTable(&iPtr->mathFuncTable, TCL_STRING_KEYS);
201    iPtr->numLevels = 0;
202    iPtr->maxNestingDepth = 1000;
203    iPtr->framePtr = NULL;
204    iPtr->varFramePtr = NULL;
205    iPtr->activeTracePtr = NULL;
206    iPtr->returnCode = TCL_OK;
207    iPtr->errorInfo = NULL;
208    iPtr->errorCode = NULL;
209    iPtr->appendResult = NULL;
210    iPtr->appendAvl = 0;
211    iPtr->appendUsed = 0;
212    iPtr->cmdCount = 0;
213    iPtr->termOffset = 0;
214    iPtr->compileEpoch = 0;
215    iPtr->compiledProcPtr = NULL;
216    iPtr->resolverPtr = NULL;
217    iPtr->evalFlags = 0;
218    iPtr->scriptFile = NULL;
219    iPtr->flags = 0;
220    iPtr->tracePtr = NULL;
221    iPtr->assocData = (Tcl_HashTable *) NULL;
222    iPtr->execEnvPtr = NULL;          /* set after namespaces initialized */
223    iPtr->emptyObjPtr = Tcl_NewObj(); /* another empty object */
224    Tcl_IncrRefCount(iPtr->emptyObjPtr);
225    iPtr->resultSpace[0] = 0;
226
227    iPtr->globalNsPtr = NULL;   /* force creation of global ns below */
228    iPtr->globalNsPtr = (Namespace *) Tcl_CreateNamespace(
229            (Tcl_Interp *) iPtr, "", (ClientData) NULL,
230            (Tcl_NamespaceDeleteProc *) NULL);
231    if (iPtr->globalNsPtr == NULL) {
232        panic("Tcl_CreateInterp: can't create global namespace");
233    }
234
235    /*
236     * Initialize support for code compilation. Do this after initializing
237     * namespaces since TclCreateExecEnv will try to reference a Tcl
238     * variable (it links to the Tcl "tcl_traceExec" variable).
239     */
240   
241    iPtr->execEnvPtr = TclCreateExecEnv((Tcl_Interp *) iPtr);
242
243    /*
244     * Create the core commands. Do it here, rather than calling
245     * Tcl_CreateCommand, because it's faster (there's no need to check for
246     * a pre-existing command by the same name). If a command has a
247     * Tcl_CmdProc but no Tcl_ObjCmdProc, set the Tcl_ObjCmdProc to
248     * TclInvokeStringCommand. This is an object-based wrapper procedure
249     * that extracts strings, calls the string procedure, and creates an
250     * object for the result. Similarly, if a command has a Tcl_ObjCmdProc
251     * but no Tcl_CmdProc, set the Tcl_CmdProc to TclInvokeObjectCommand.
252     */
253
254    for (cmdInfoPtr = builtInCmds;  cmdInfoPtr->name != NULL;
255            cmdInfoPtr++) {
256        int new;
257        Tcl_HashEntry *hPtr;
258
259        if ((cmdInfoPtr->proc == (Tcl_CmdProc *) NULL)
260                && (cmdInfoPtr->objProc == (Tcl_ObjCmdProc *) NULL)
261                && (cmdInfoPtr->compileProc == (CompileProc *) NULL)) {
262            panic("Tcl_CreateInterp: builtin command with NULL string and object command procs and a NULL compile proc\n");
263        }
264       
265        hPtr = Tcl_CreateHashEntry(&iPtr->globalNsPtr->cmdTable,
266                cmdInfoPtr->name, &new);
267        if (new) {
268            cmdPtr = (Command *) ckalloc(sizeof(Command));
269            cmdPtr->hPtr = hPtr;
270            cmdPtr->nsPtr = iPtr->globalNsPtr;
271            cmdPtr->refCount = 1;
272            cmdPtr->cmdEpoch = 0;
273            cmdPtr->compileProc = cmdInfoPtr->compileProc;
274            if (cmdInfoPtr->proc == (Tcl_CmdProc *) NULL) {
275                cmdPtr->proc = TclInvokeObjectCommand;
276                cmdPtr->clientData = (ClientData) cmdPtr;
277            } else {
278                cmdPtr->proc = cmdInfoPtr->proc;
279                cmdPtr->clientData = (ClientData) NULL;
280            }
281            if (cmdInfoPtr->objProc == (Tcl_ObjCmdProc *) NULL) {
282                cmdPtr->objProc = TclInvokeStringCommand;
283                cmdPtr->objClientData = (ClientData) cmdPtr;
284            } else {
285                cmdPtr->objProc = cmdInfoPtr->objProc;
286                cmdPtr->objClientData = (ClientData) NULL;
287            }
288            cmdPtr->deleteProc = NULL;
289            cmdPtr->deleteData = (ClientData) NULL;
290            cmdPtr->deleted = 0;
291            cmdPtr->importRefPtr = NULL;
292            Tcl_SetHashValue(hPtr, cmdPtr);
293        }
294    }
295
296    /*
297     *  Initialize/Create "errorInfo" and "errorCode" global vars
298     *  (because some part of the C code assume they exists
299     *   and we can get a seg fault otherwise (in multiple
300     *   interps loading of extensions for instance) --dl)
301     */
302     /*
303      *  We can't assume that because we initialize
304      *  the variables here, they won't be unset later.
305      *  so we had 2 choices:
306      *    + Check every place where a GetVar of those is used
307      *      and the NULL result is not checked (like in tclLoad.c)
308      *    + Make SetVar,... NULL friendly
309      *  We choosed the second option because :
310      *    + It is easy and low cost to check for NULL pointer before
311      *      calling strlen()
312      *    + It can be helpfull to other people using those API
313      *    + Passing a NULL value to those closest 'meaning' is empty string
314      *      (specially with the new objects where 0 bytes strings are ok)
315      * So the following init is commented out:              -- dl
316      */
317    /*
318      (void)Tcl_SetVar2((Tcl_Interp *)iPtr, "errorInfo", (char *) NULL, "",
319         TCL_GLOBAL_ONLY);
320      (void)Tcl_SetVar2((Tcl_Interp *)iPtr, "errorCode", (char *) NULL, "NONE",
321            TCL_GLOBAL_ONLY);
322     */
323
324    /*
325     * Set up variables such as tcl_version.
326     */
327
328    Tcl_SetVar((Tcl_Interp *) iPtr, "tcl_patchLevel", TCL_PATCH_LEVEL,
329            TCL_GLOBAL_ONLY);
330    Tcl_SetVar((Tcl_Interp *) iPtr, "tcl_version", TCL_VERSION,
331            TCL_GLOBAL_ONLY);
332    Tcl_TraceVar2((Tcl_Interp *) iPtr, "tcl_precision", (char *) NULL,
333            TCL_GLOBAL_ONLY|TCL_TRACE_READS|TCL_TRACE_WRITES|TCL_TRACE_UNSETS,
334            TclPrecTraceProc, (ClientData) NULL);
335
336    /*
337     * Compute the byte order of this machine.
338     */
339
340    order.s = 1;
341    Tcl_SetVar2((Tcl_Interp *) iPtr, "tcl_platform", "byteOrder",
342            (order.c[0] == 1) ? "littleEndian" : "bigEndian",
343            TCL_GLOBAL_ONLY);
344   
345    return (Tcl_Interp *) iPtr;
346}
347
348/*
349 *--------------------------------------------------------------
350 *
351 * Tcl_CallWhenDeleted --
352 *
353 *      Arrange for a procedure to be called before a given
354 *      interpreter is deleted. The procedure is called as soon
355 *      as Tcl_DeleteInterp is called; if Tcl_CallWhenDeleted is
356 *      called on an interpreter that has already been deleted,
357 *      the procedure will be called when the last Tcl_Release is
358 *      done on the interpreter.
359 *
360 * Results:
361 *      None.
362 *
363 * Side effects:
364 *      When Tcl_DeleteInterp is invoked to delete interp,
365 *      proc will be invoked.  See the manual entry for
366 *      details.
367 *
368 *--------------------------------------------------------------
369 */
370
371void
372Tcl_CallWhenDeleted(interp, proc, clientData)
373    Tcl_Interp *interp;         /* Interpreter to watch. */
374    Tcl_InterpDeleteProc *proc; /* Procedure to call when interpreter
375                                 * is about to be deleted. */
376    ClientData clientData;      /* One-word value to pass to proc. */
377{
378    Interp *iPtr = (Interp *) interp;
379    static int assocDataCounter = 0;
380    int new;
381    char buffer[128];
382    AssocData *dPtr = (AssocData *) ckalloc(sizeof(AssocData));
383    Tcl_HashEntry *hPtr;
384
385    sprintf(buffer, "Assoc Data Key #%d", assocDataCounter);
386    assocDataCounter++;
387
388    if (iPtr->assocData == (Tcl_HashTable *) NULL) {
389        iPtr->assocData = (Tcl_HashTable *) ckalloc(sizeof(Tcl_HashTable));
390        Tcl_InitHashTable(iPtr->assocData, TCL_STRING_KEYS);
391    }
392    hPtr = Tcl_CreateHashEntry(iPtr->assocData, buffer, &new);
393    dPtr->proc = proc;
394    dPtr->clientData = clientData;
395    Tcl_SetHashValue(hPtr, dPtr);
396}
397
398/*
399 *--------------------------------------------------------------
400 *
401 * Tcl_DontCallWhenDeleted --
402 *
403 *      Cancel the arrangement for a procedure to be called when
404 *      a given interpreter is deleted.
405 *
406 * Results:
407 *      None.
408 *
409 * Side effects:
410 *      If proc and clientData were previously registered as a
411 *      callback via Tcl_CallWhenDeleted, they are unregistered.
412 *      If they weren't previously registered then nothing
413 *      happens.
414 *
415 *--------------------------------------------------------------
416 */
417
418void
419Tcl_DontCallWhenDeleted(interp, proc, clientData)
420    Tcl_Interp *interp;         /* Interpreter to watch. */
421    Tcl_InterpDeleteProc *proc; /* Procedure to call when interpreter
422                                 * is about to be deleted. */
423    ClientData clientData;      /* One-word value to pass to proc. */
424{
425    Interp *iPtr = (Interp *) interp;
426    Tcl_HashTable *hTablePtr;
427    Tcl_HashSearch hSearch;
428    Tcl_HashEntry *hPtr;
429    AssocData *dPtr;
430
431    hTablePtr = iPtr->assocData;
432    if (hTablePtr == (Tcl_HashTable *) NULL) {
433        return;
434    }
435    for (hPtr = Tcl_FirstHashEntry(hTablePtr, &hSearch); hPtr != NULL;
436            hPtr = Tcl_NextHashEntry(&hSearch)) {
437        dPtr = (AssocData *) Tcl_GetHashValue(hPtr);
438        if ((dPtr->proc == proc) && (dPtr->clientData == clientData)) {
439            ckfree((char *) dPtr);
440            Tcl_DeleteHashEntry(hPtr);
441            return;
442        }
443    }
444}
445
446/*
447 *----------------------------------------------------------------------
448 *
449 * Tcl_SetAssocData --
450 *
451 *      Creates a named association between user-specified data, a delete
452 *      function and this interpreter. If the association already exists
453 *      the data is overwritten with the new data. The delete function will
454 *      be invoked when the interpreter is deleted.
455 *
456 * Results:
457 *      None.
458 *
459 * Side effects:
460 *      Sets the associated data, creates the association if needed.
461 *
462 *----------------------------------------------------------------------
463 */
464
465void
466Tcl_SetAssocData(interp, name, proc, clientData)
467    Tcl_Interp *interp;         /* Interpreter to associate with. */
468    char *name;                 /* Name for association. */
469    Tcl_InterpDeleteProc *proc; /* Proc to call when interpreter is
470                                 * about to be deleted. */
471    ClientData clientData;      /* One-word value to pass to proc. */
472{
473    Interp *iPtr = (Interp *) interp;
474    AssocData *dPtr;
475    Tcl_HashEntry *hPtr;
476    int new;
477
478    if (iPtr->assocData == (Tcl_HashTable *) NULL) {
479        iPtr->assocData = (Tcl_HashTable *) ckalloc(sizeof(Tcl_HashTable));
480        Tcl_InitHashTable(iPtr->assocData, TCL_STRING_KEYS);
481    }
482    hPtr = Tcl_CreateHashEntry(iPtr->assocData, name, &new);
483    if (new == 0) {
484        dPtr = (AssocData *) Tcl_GetHashValue(hPtr);
485    } else {
486        dPtr = (AssocData *) ckalloc(sizeof(AssocData));
487    }
488    dPtr->proc = proc;
489    dPtr->clientData = clientData;
490
491    Tcl_SetHashValue(hPtr, dPtr);
492}
493
494/*
495 *----------------------------------------------------------------------
496 *
497 * Tcl_DeleteAssocData --
498 *
499 *      Deletes a named association of user-specified data with
500 *      the specified interpreter.
501 *
502 * Results:
503 *      None.
504 *
505 * Side effects:
506 *      Deletes the association.
507 *
508 *----------------------------------------------------------------------
509 */
510
511void
512Tcl_DeleteAssocData(interp, name)
513    Tcl_Interp *interp;                 /* Interpreter to associate with. */
514    char *name;                         /* Name of association. */
515{
516    Interp *iPtr = (Interp *) interp;
517    AssocData *dPtr;
518    Tcl_HashEntry *hPtr;
519
520    if (iPtr->assocData == (Tcl_HashTable *) NULL) {
521        return;
522    }
523    hPtr = Tcl_FindHashEntry(iPtr->assocData, name);
524    if (hPtr == (Tcl_HashEntry *) NULL) {
525        return;
526    }
527    dPtr = (AssocData *) Tcl_GetHashValue(hPtr);
528    if (dPtr->proc != NULL) {
529        (dPtr->proc) (dPtr->clientData, interp);
530    }
531    ckfree((char *) dPtr);
532    Tcl_DeleteHashEntry(hPtr);
533}
534
535/*
536 *----------------------------------------------------------------------
537 *
538 * Tcl_GetAssocData --
539 *
540 *      Returns the client data associated with this name in the
541 *      specified interpreter.
542 *
543 * Results:
544 *      The client data in the AssocData record denoted by the named
545 *      association, or NULL.
546 *
547 * Side effects:
548 *      None.
549 *
550 *----------------------------------------------------------------------
551 */
552
553ClientData
554Tcl_GetAssocData(interp, name, procPtr)
555    Tcl_Interp *interp;                 /* Interpreter associated with. */
556    char *name;                         /* Name of association. */
557    Tcl_InterpDeleteProc **procPtr;     /* Pointer to place to store address
558                                         * of current deletion callback. */
559{
560    Interp *iPtr = (Interp *) interp;
561    AssocData *dPtr;
562    Tcl_HashEntry *hPtr;
563
564    if (iPtr->assocData == (Tcl_HashTable *) NULL) {
565        return (ClientData) NULL;
566    }
567    hPtr = Tcl_FindHashEntry(iPtr->assocData, name);
568    if (hPtr == (Tcl_HashEntry *) NULL) {
569        return (ClientData) NULL;
570    }
571    dPtr = (AssocData *) Tcl_GetHashValue(hPtr);
572    if (procPtr != (Tcl_InterpDeleteProc **) NULL) {
573        *procPtr = dPtr->proc;
574    }
575    return dPtr->clientData;
576}
577
578/*
579 *----------------------------------------------------------------------
580 *
581 * DeleteInterpProc --
582 *
583 *      Helper procedure to delete an interpreter. This procedure is
584 *      called when the last call to Tcl_Preserve on this interpreter
585 *      is matched by a call to Tcl_Release. The procedure cleans up
586 *      all resources used in the interpreter and calls all currently
587 *      registered interpreter deletion callbacks.
588 *
589 * Results:
590 *      None.
591 *
592 * Side effects:
593 *      Whatever the interpreter deletion callbacks do. Frees resources
594 *      used by the interpreter.
595 *
596 *----------------------------------------------------------------------
597 */
598
599static void
600DeleteInterpProc(interp)
601    Tcl_Interp *interp;                 /* Interpreter to delete. */
602{
603    Interp *iPtr = (Interp *) interp;
604    Tcl_HashEntry *hPtr;
605    Tcl_HashSearch search;
606    Tcl_HashTable *hTablePtr;
607    AssocData *dPtr;
608    ResolverScheme *resPtr, *nextResPtr;
609
610    /*
611     * Punt if there is an error in the Tcl_Release/Tcl_Preserve matchup.
612     */
613   
614    if (iPtr->numLevels > 0) {
615        panic("DeleteInterpProc called with active evals");
616    }
617
618    /*
619     * The interpreter should already be marked deleted; otherwise how
620     * did we get here?
621     */
622
623    if (!(iPtr->flags & DELETED)) {
624        panic("DeleteInterpProc called on interpreter not marked deleted");
625    }
626
627    /*
628     * Dismantle everything in the global namespace except for the
629     * "errorInfo" and "errorCode" variables. These remain until the
630     * namespace is actually destroyed, in case any errors occur.
631     *   
632     * Dismantle the namespace here, before we clear the assocData. If any
633     * background errors occur here, they will be deleted below.
634     */
635   
636    TclTeardownNamespace(iPtr->globalNsPtr);
637
638    /*
639     * Tear down the math function table.
640     */
641
642    for (hPtr = Tcl_FirstHashEntry(&iPtr->mathFuncTable, &search);
643             hPtr != NULL;
644             hPtr = Tcl_NextHashEntry(&search)) {
645        ckfree((char *) Tcl_GetHashValue(hPtr));
646    }
647    Tcl_DeleteHashTable(&iPtr->mathFuncTable);
648
649    /*
650     * Invoke deletion callbacks; note that a callback can create new
651     * callbacks, so we iterate.
652     */
653
654    while (iPtr->assocData != (Tcl_HashTable *) NULL) {
655        hTablePtr = iPtr->assocData;
656        iPtr->assocData = (Tcl_HashTable *) NULL;
657        for (hPtr = Tcl_FirstHashEntry(hTablePtr, &search);
658                 hPtr != NULL;
659                 hPtr = Tcl_FirstHashEntry(hTablePtr, &search)) {
660            dPtr = (AssocData *) Tcl_GetHashValue(hPtr);
661            Tcl_DeleteHashEntry(hPtr);
662            if (dPtr->proc != NULL) {
663                (*dPtr->proc)(dPtr->clientData, interp);
664            }
665            ckfree((char *) dPtr);
666        }
667        Tcl_DeleteHashTable(hTablePtr);
668        ckfree((char *) hTablePtr);
669    }
670
671    /*
672     * Finish deleting the global namespace.
673     */
674   
675    Tcl_DeleteNamespace((Tcl_Namespace *) iPtr->globalNsPtr);
676
677    /*
678     * Free up the result *after* deleting variables, since variable
679     * deletion could have transferred ownership of the result string
680     * to Tcl.
681     */
682
683    Tcl_FreeResult(interp);
684    interp->result = NULL;
685    Tcl_DecrRefCount(iPtr->objResultPtr);
686    iPtr->objResultPtr = NULL;
687    if (iPtr->errorInfo != NULL) {
688        ckfree(iPtr->errorInfo);
689        iPtr->errorInfo = NULL;
690    }
691    if (iPtr->errorCode != NULL) {
692        ckfree(iPtr->errorCode);
693        iPtr->errorCode = NULL;
694    }
695    if (iPtr->appendResult != NULL) {
696        ckfree(iPtr->appendResult);
697        iPtr->appendResult = NULL;
698    }
699    while (iPtr->tracePtr != NULL) {
700        Trace *nextPtr = iPtr->tracePtr->nextPtr;
701
702        ckfree((char *) iPtr->tracePtr);
703        iPtr->tracePtr = nextPtr;
704    }
705    if (iPtr->execEnvPtr != NULL) {
706        TclDeleteExecEnv(iPtr->execEnvPtr);
707    }
708    Tcl_DecrRefCount(iPtr->emptyObjPtr);
709    iPtr->emptyObjPtr = NULL;
710
711    resPtr = iPtr->resolverPtr;
712    while (resPtr) {
713        nextResPtr = resPtr->nextPtr;
714        ckfree(resPtr->name);
715        ckfree((char *) resPtr);
716        resPtr = nextResPtr;
717    }
718   
719    ckfree((char *) iPtr);
720}
721
722/*
723 *----------------------------------------------------------------------
724 *
725 * Tcl_InterpDeleted --
726 *
727 *      Returns nonzero if the interpreter has been deleted with a call
728 *      to Tcl_DeleteInterp.
729 *
730 * Results:
731 *      Nonzero if the interpreter is deleted, zero otherwise.
732 *
733 * Side effects:
734 *      None.
735 *
736 *----------------------------------------------------------------------
737 */
738
739int
740Tcl_InterpDeleted(interp)
741    Tcl_Interp *interp;
742{
743    return (((Interp *) interp)->flags & DELETED) ? 1 : 0;
744}
745
746/*
747 *----------------------------------------------------------------------
748 *
749 * Tcl_DeleteInterp --
750 *
751 *      Ensures that the interpreter will be deleted eventually. If there
752 *      are no Tcl_Preserve calls in effect for this interpreter, it is
753 *      deleted immediately, otherwise the interpreter is deleted when
754 *      the last Tcl_Preserve is matched by a call to Tcl_Release. In either
755 *      case, the procedure runs the currently registered deletion callbacks.
756 *
757 * Results:
758 *      None.
759 *
760 * Side effects:
761 *      The interpreter is marked as deleted. The caller may still use it
762 *      safely if there are calls to Tcl_Preserve in effect for the
763 *      interpreter, but further calls to Tcl_Eval etc in this interpreter
764 *      will fail.
765 *
766 *----------------------------------------------------------------------
767 */
768
769void
770Tcl_DeleteInterp(interp)
771    Tcl_Interp *interp;         /* Token for command interpreter (returned
772                                 * by a previous call to Tcl_CreateInterp). */
773{
774    Interp *iPtr = (Interp *) interp;
775
776    /*
777     * If the interpreter has already been marked deleted, just punt.
778     */
779
780    if (iPtr->flags & DELETED) {
781        return;
782    }
783   
784    /*
785     * Mark the interpreter as deleted. No further evals will be allowed.
786     */
787
788    iPtr->flags |= DELETED;
789
790    /*
791     * Ensure that the interpreter is eventually deleted.
792     */
793
794    Tcl_EventuallyFree((ClientData) interp,
795            (Tcl_FreeProc *) DeleteInterpProc);
796}
797
798/*
799 *----------------------------------------------------------------------
800 *
801 * HiddenCmdsDeleteProc --
802 *
803 *      Called on interpreter deletion to delete all the hidden
804 *      commands in an interpreter.
805 *
806 * Results:
807 *      None.
808 *
809 * Side effects:
810 *      Frees up memory.
811 *
812 *----------------------------------------------------------------------
813 */
814
815static void
816HiddenCmdsDeleteProc(clientData, interp)
817    ClientData clientData;              /* The hidden commands hash table. */
818    Tcl_Interp *interp;                 /* The interpreter being deleted. */
819{
820    Tcl_HashTable *hiddenCmdTblPtr;
821    Tcl_HashEntry *hPtr;
822    Tcl_HashSearch hSearch;
823    Command *cmdPtr;
824
825    hiddenCmdTblPtr = (Tcl_HashTable *) clientData;
826    for (hPtr = Tcl_FirstHashEntry(hiddenCmdTblPtr, &hSearch);
827             hPtr != NULL;
828             hPtr = Tcl_FirstHashEntry(hiddenCmdTblPtr, &hSearch)) {
829
830        /*
831         * Cannot use Tcl_DeleteCommand because (a) the command is not
832         * in the command hash table, and (b) that table has already been
833         * deleted above. Hence we emulate what it does, below.
834         */
835       
836        cmdPtr = (Command *) Tcl_GetHashValue(hPtr);
837
838        /*
839         * The code here is tricky.  We can't delete the hash table entry
840         * before invoking the deletion callback because there are cases
841         * where the deletion callback needs to invoke the command (e.g.
842         * object systems such as OTcl).  However, this means that the
843         * callback could try to delete or rename the command.  The deleted
844         * flag allows us to detect these cases and skip nested deletes.
845         */
846
847        if (cmdPtr->deleted) {
848
849            /*
850             * Another deletion is already in progress.  Remove the hash
851             * table entry now, but don't invoke a callback or free the
852             * command structure.
853             */
854
855            Tcl_DeleteHashEntry(cmdPtr->hPtr);
856            cmdPtr->hPtr = NULL;
857            continue;
858        }
859        cmdPtr->deleted = 1;
860        if (cmdPtr->deleteProc != NULL) {
861            (*cmdPtr->deleteProc)(cmdPtr->deleteData);
862        }
863
864        /*
865         * Bump the command epoch counter. This will invalidate all cached
866         * references that refer to this command.
867         */
868       
869        cmdPtr->cmdEpoch++;
870
871        /*
872         * Don't use hPtr to delete the hash entry here, because it's
873         * possible that the deletion callback renamed the command.
874         * Instead, use cmdPtr->hptr, and make sure that no-one else
875         * has already deleted the hash entry.
876         */
877
878        if (cmdPtr->hPtr != NULL) {
879            Tcl_DeleteHashEntry(cmdPtr->hPtr);
880        }
881       
882        /*
883         * Now free the Command structure, unless there is another reference
884         * to it from a CmdName Tcl object in some ByteCode code
885         * sequence. In that case, delay the cleanup until all references
886         * are either discarded (when a ByteCode is freed) or replaced by a
887         * new reference (when a cached CmdName Command reference is found
888         * to be invalid and TclExecuteByteCode looks up the command in the
889         * command hashtable).
890         */
891       
892        TclCleanupCommand(cmdPtr);
893    }
894    Tcl_DeleteHashTable(hiddenCmdTblPtr);
895    ckfree((char *) hiddenCmdTblPtr);
896}
897
898/*
899 *----------------------------------------------------------------------
900 *
901 * Tcl_HideCommand --
902 *
903 *      Makes a command hidden so that it cannot be invoked from within
904 *      an interpreter, only from within an ancestor.
905 *
906 * Results:
907 *      A standard Tcl result; also leaves a message in interp->result
908 *      if an error occurs.
909 *
910 * Side effects:
911 *      Removes a command from the command table and create an entry
912 *      into the hidden command table under the specified token name.
913 *
914 *----------------------------------------------------------------------
915 */
916
917int
918Tcl_HideCommand(interp, cmdName, hiddenCmdToken)
919    Tcl_Interp *interp;         /* Interpreter in which to hide command. */
920    char *cmdName;              /* Name of command to hide. */
921    char *hiddenCmdToken;       /* Token name of the to-be-hidden command. */
922{
923    Interp *iPtr = (Interp *) interp;
924    Tcl_Command cmd;
925    Command *cmdPtr;
926    Tcl_HashTable *hTblPtr;
927    Tcl_HashEntry *hPtr;
928    int new;
929
930    if (iPtr->flags & DELETED) {
931
932        /*
933         * The interpreter is being deleted. Do not create any new
934         * structures, because it is not safe to modify the interpreter.
935         */
936       
937        return TCL_ERROR;
938    }
939
940    /*
941     * Disallow hiding of commands that are currently in a namespace or
942     * renaming (as part of hiding) into a namespace.
943     *
944     * (because the current implementation with a single global table
945     *  and the needed uniqueness of names cause problems with namespaces)
946     *
947     * we don't need to check for "::" in cmdName because the real check is
948     * on the nsPtr below.
949     *
950     * hiddenCmdToken is just a string which is not interpreted in any way.
951     * It may contain :: but the string is not interpreted as a namespace
952     * qualifier command name. Thus, hiding foo::bar to foo::bar and then
953     * trying to expose or invoke ::foo::bar will NOT work; but if the
954     * application always uses the same strings it will get consistent
955     * behaviour.
956     *
957     * But as we currently limit ourselves to the global namespace only
958     * for the source, in order to avoid potential confusion,
959     * lets prevent "::" in the token too.  --dl
960     */
961
962    if (strstr(hiddenCmdToken, "::") != NULL) {
963        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
964                "cannot use namespace qualifiers as hidden command",
965                "token (rename)", (char *) NULL);
966        return TCL_ERROR;
967    }
968
969    /*
970     * Find the command to hide. An error is returned if cmdName can't
971     * be found. Look up the command only from the global namespace.
972     * Full path of the command must be given if using namespaces.
973     */
974
975    cmd = Tcl_FindCommand(interp, cmdName, (Tcl_Namespace *) NULL,
976            /*flags*/ TCL_LEAVE_ERR_MSG | TCL_GLOBAL_ONLY);
977    if (cmd == (Tcl_Command) NULL) {
978        return TCL_ERROR;
979    }
980    cmdPtr = (Command *) cmd;
981
982    /*
983     * Check that the command is really in global namespace
984     */
985
986    if ( cmdPtr->nsPtr != iPtr->globalNsPtr ) {
987        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
988                "can only hide global namespace commands",
989                " (use rename then hide)", (char *) NULL);
990        return TCL_ERROR;
991    }
992   
993    /*
994     * Initialize the hidden command table if necessary.
995     */
996
997    hTblPtr = (Tcl_HashTable *) Tcl_GetAssocData(interp, "tclHiddenCmds",
998            NULL);
999    if (hTblPtr == (Tcl_HashTable *) NULL) {
1000        hTblPtr = (Tcl_HashTable *)
1001                ckalloc((unsigned) sizeof(Tcl_HashTable));
1002        Tcl_InitHashTable(hTblPtr, TCL_STRING_KEYS);
1003        Tcl_SetAssocData(interp, "tclHiddenCmds", HiddenCmdsDeleteProc,
1004                (ClientData) hTblPtr);
1005    }
1006
1007    /*
1008     * It is an error to move an exposed command to a hidden command with
1009     * hiddenCmdToken if a hidden command with the name hiddenCmdToken already
1010     * exists.
1011     */
1012   
1013    hPtr = Tcl_CreateHashEntry(hTblPtr, hiddenCmdToken, &new);
1014    if (!new) {
1015        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1016                "hidden command named \"", hiddenCmdToken, "\" already exists",
1017                (char *) NULL);
1018        return TCL_ERROR;
1019    }
1020
1021    /*
1022     * Nb : This code is currently 'like' a rename to a specialy set apart
1023     * name table. Changes here and in TclRenameCommand must
1024     * be kept in synch untill the common parts are actually
1025     * factorized out.
1026     */
1027
1028    /*
1029     * Remove the hash entry for the command from the interpreter command
1030     * table. This is like deleting the command, so bump its command epoch;
1031     * this invalidates any cached references that point to the command.
1032     */
1033
1034    if (cmdPtr->hPtr != NULL) {
1035        Tcl_DeleteHashEntry(cmdPtr->hPtr);
1036        cmdPtr->hPtr = (Tcl_HashEntry *) NULL;
1037        cmdPtr->cmdEpoch++;
1038    }
1039
1040    /*
1041     * Now link the hash table entry with the command structure.
1042     * We ensured above that the nsPtr was right.
1043     */
1044   
1045    cmdPtr->hPtr = hPtr;
1046    Tcl_SetHashValue(hPtr, (ClientData) cmdPtr);
1047
1048    /*
1049     * If the command being hidden has a compile procedure, increment the
1050     * interpreter's compileEpoch to invalidate its compiled code. This
1051     * makes sure that we don't later try to execute old code compiled with
1052     * command-specific (i.e., inline) bytecodes for the now-hidden
1053     * command. This field is checked in Tcl_EvalObj and ObjInterpProc,
1054     * and code whose compilation epoch doesn't match is recompiled.
1055     */
1056
1057    if (cmdPtr->compileProc != NULL) {
1058        iPtr->compileEpoch++;
1059    }
1060    return TCL_OK;
1061}
1062
1063/*
1064 *----------------------------------------------------------------------
1065 *
1066 * Tcl_ExposeCommand --
1067 *
1068 *      Makes a previously hidden command callable from inside the
1069 *      interpreter instead of only by its ancestors.
1070 *
1071 * Results:
1072 *      A standard Tcl result. If an error occurs, a message is left
1073 *      in interp->result.
1074 *
1075 * Side effects:
1076 *      Moves commands from one hash table to another.
1077 *
1078 *----------------------------------------------------------------------
1079 */
1080
1081int
1082Tcl_ExposeCommand(interp, hiddenCmdToken, cmdName)
1083    Tcl_Interp *interp;         /* Interpreter in which to make command
1084                                 * callable. */
1085    char *hiddenCmdToken;       /* Name of hidden command. */
1086    char *cmdName;              /* Name of to-be-exposed command. */
1087{
1088    Interp *iPtr = (Interp *) interp;
1089    Command *cmdPtr;
1090    Namespace *nsPtr;
1091    Tcl_HashEntry *hPtr;
1092    Tcl_HashTable *hTblPtr;
1093    int new;
1094
1095    if (iPtr->flags & DELETED) {
1096        /*
1097         * The interpreter is being deleted. Do not create any new
1098         * structures, because it is not safe to modify the interpreter.
1099         */
1100       
1101        return TCL_ERROR;
1102    }
1103
1104    /*
1105     * Check that we have a regular name for the command
1106     * (that the user is not trying to do an expose and a rename
1107     *  (to another namespace) at the same time)
1108     */
1109
1110    if (strstr(cmdName, "::") != NULL) {
1111        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1112                "can not expose to a namespace ",
1113                "(use expose to toplevel, then rename)",
1114                 (char *) NULL);
1115        return TCL_ERROR;
1116    }
1117
1118    /*
1119     * Find the hash table for the hidden commands; error out if there
1120     * is none.
1121     */
1122
1123    hTblPtr = (Tcl_HashTable *) Tcl_GetAssocData(interp, "tclHiddenCmds",
1124            NULL);
1125    if (hTblPtr == NULL) {
1126        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1127                "unknown hidden command \"", hiddenCmdToken,
1128                "\"", (char *) NULL);
1129        return TCL_ERROR;
1130    }
1131       
1132    /*
1133     * Get the command from the hidden command table:
1134     */
1135
1136    hPtr = Tcl_FindHashEntry(hTblPtr, hiddenCmdToken);
1137    if (hPtr == (Tcl_HashEntry *) NULL) {
1138        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1139                "unknown hidden command \"", hiddenCmdToken,
1140                "\"", (char *) NULL);
1141        return TCL_ERROR;
1142    }
1143    cmdPtr = (Command *) Tcl_GetHashValue(hPtr);
1144   
1145
1146    /*
1147     * Check that we have a true global namespace
1148     * command (enforced by Tcl_HideCommand() but let's double
1149     * check. (If it was not, we would not really know how to
1150     * handle it).
1151     */
1152    if ( cmdPtr->nsPtr != iPtr->globalNsPtr ) {
1153        /*
1154         * This case is theoritically impossible,
1155         * we might rather panic() than 'nicely' erroring out ?
1156         */
1157        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1158                "trying to expose a non global command name space command",
1159                (char *) NULL);
1160        return TCL_ERROR;
1161    }
1162   
1163    /* This is the global table */
1164    nsPtr = cmdPtr->nsPtr;
1165
1166    /*
1167     * It is an error to overwrite an existing exposed command as a result
1168     * of exposing a previously hidden command.
1169     */
1170
1171    hPtr = Tcl_CreateHashEntry(&nsPtr->cmdTable, cmdName, &new);
1172    if (!new) {
1173        Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
1174                "exposed command \"", cmdName,
1175                "\" already exists", (char *) NULL);
1176        return TCL_ERROR;
1177    }
1178
1179    /*
1180     * Remove the hash entry for the command from the interpreter hidden
1181     * command table.
1182     */
1183
1184    if (cmdPtr->hPtr != NULL) {
1185        Tcl_DeleteHashEntry(cmdPtr->hPtr);
1186        cmdPtr->hPtr = NULL;
1187    }
1188
1189    /*
1190     * Now link the hash table entry with the command structure.
1191     * This is like creating a new command, so deal with any shadowing
1192     * of commands in the global namespace.
1193     */
1194   
1195    cmdPtr->hPtr = hPtr;
1196
1197    Tcl_SetHashValue(hPtr, (ClientData) cmdPtr);
1198
1199    /*
1200     * Not needed as we are only in the global namespace
1201     * (but would be needed again if we supported namespace command hiding)
1202     *
1203     * TclResetShadowedCmdRefs(interp, cmdPtr);
1204     */
1205
1206
1207    /*
1208     * If the command being exposed has a compile procedure, increment
1209     * interpreter's compileEpoch to invalidate its compiled code. This
1210     * makes sure that we don't later try to execute old code compiled
1211     * assuming the command is hidden. This field is checked in Tcl_EvalObj
1212     * and ObjInterpProc, and code whose compilation epoch doesn't match is
1213     * recompiled.
1214     */
1215
1216    if (cmdPtr->compileProc != NULL) {
1217        iPtr->compileEpoch++;
1218    }
1219    return TCL_OK;
1220}
1221
1222/*
1223 *----------------------------------------------------------------------
1224 *
1225 * Tcl_CreateCommand --
1226 *
1227 *      Define a new command in a command table.
1228 *
1229 * Results:
1230 *      The return value is a token for the command, which can
1231 *      be used in future calls to Tcl_GetCommandName.
1232 *
1233 * Side effects:
1234 *      If a command named cmdName already exists for interp, it is deleted.
1235 *      In the future, when cmdName is seen as the name of a command by
1236 *      Tcl_Eval, proc will be called. To support the bytecode interpreter,
1237 *      the command is created with a wrapper Tcl_ObjCmdProc
1238 *      (TclInvokeStringCommand) that eventially calls proc. When the
1239 *      command is deleted from the table, deleteProc will be called.
1240 *      See the manual entry for details on the calling sequence.
1241 *
1242 *----------------------------------------------------------------------
1243 */
1244
1245Tcl_Command
1246Tcl_CreateCommand(interp, cmdName, proc, clientData, deleteProc)
1247    Tcl_Interp *interp;         /* Token for command interpreter returned by
1248                                 * a previous call to Tcl_CreateInterp. */
1249    char *cmdName;              /* Name of command. If it contains namespace
1250                                 * qualifiers, the new command is put in the
1251                                 * specified namespace; otherwise it is put
1252                                 * in the global namespace. */
1253    Tcl_CmdProc *proc;          /* Procedure to associate with cmdName. */
1254    ClientData clientData;      /* Arbitrary value passed to string proc. */
1255    Tcl_CmdDeleteProc *deleteProc;
1256                                /* If not NULL, gives a procedure to call
1257                                 * when this command is deleted. */
1258{
1259    Interp *iPtr = (Interp *) interp;
1260    ImportRef *oldRefPtr = NULL;
1261    Namespace *nsPtr, *dummy1, *dummy2;
1262    Command *cmdPtr, *refCmdPtr;
1263    Tcl_HashEntry *hPtr;
1264    char *tail;
1265    int new;
1266    ImportedCmdData *dataPtr;
1267
1268    if (iPtr->flags & DELETED) {
1269        /*
1270         * The interpreter is being deleted.  Don't create any new
1271         * commands; it's not safe to muck with the interpreter anymore.
1272         */
1273
1274        return (Tcl_Command) NULL;
1275    }
1276
1277    /*
1278     * Determine where the command should reside. If its name contains
1279     * namespace qualifiers, we put it in the specified namespace;
1280     * otherwise, we always put it in the global namespace.
1281     */
1282
1283    if (strstr(cmdName, "::") != NULL) {
1284       TclGetNamespaceForQualName(interp, cmdName, (Namespace *) NULL,
1285           CREATE_NS_IF_UNKNOWN, &nsPtr, &dummy1, &dummy2, &tail);
1286       if ((nsPtr == NULL) || (tail == NULL)) {
1287            return (Tcl_Command) NULL;
1288        }
1289    } else {
1290        nsPtr = iPtr->globalNsPtr;
1291        tail = cmdName;
1292    }
1293   
1294    hPtr = Tcl_CreateHashEntry(&nsPtr->cmdTable, tail, &new);
1295    if (!new) {
1296        /*
1297         * Command already exists. Delete the old one.
1298         * Be careful to preserve any existing import links so we can
1299         * restore them down below.  That way, you can redefine a
1300         * command and its import status will remain intact.
1301         */
1302
1303        cmdPtr = (Command *) Tcl_GetHashValue(hPtr);
1304        oldRefPtr = cmdPtr->importRefPtr;
1305        cmdPtr->importRefPtr = NULL;
1306
1307        Tcl_DeleteCommandFromToken(interp, (Tcl_Command) cmdPtr);
1308        hPtr = Tcl_CreateHashEntry(&nsPtr->cmdTable, tail, &new);
1309        if (!new) {
1310            /*
1311             * If the deletion callback recreated the command, just throw
1312             * away the new command (if we try to delete it again, we
1313             * could get stuck in an infinite loop).
1314             */
1315
1316             ckfree((char*) cmdPtr);
1317        }
1318    }
1319    cmdPtr = (Command *) ckalloc(sizeof(Command));
1320    Tcl_SetHashValue(hPtr, cmdPtr);
1321    cmdPtr->hPtr = hPtr;
1322    cmdPtr->nsPtr = nsPtr;
1323    cmdPtr->refCount = 1;
1324    cmdPtr->cmdEpoch = 0;
1325    cmdPtr->compileProc = (CompileProc *) NULL;
1326    cmdPtr->objProc = TclInvokeStringCommand;
1327    cmdPtr->objClientData = (ClientData) cmdPtr;
1328    cmdPtr->proc = proc;
1329    cmdPtr->clientData = clientData;
1330    cmdPtr->deleteProc = deleteProc;
1331    cmdPtr->deleteData = clientData;
1332    cmdPtr->deleted = 0;
1333    cmdPtr->importRefPtr = NULL;
1334
1335    /*
1336     * Plug in any existing import references found above.  Be sure
1337     * to update all of these references to point to the new command.
1338     */
1339
1340    if (oldRefPtr != NULL) {
1341        cmdPtr->importRefPtr = oldRefPtr;
1342        while (oldRefPtr != NULL) {
1343            refCmdPtr = oldRefPtr->importedCmdPtr;
1344            dataPtr = (ImportedCmdData*)refCmdPtr->objClientData;
1345            dataPtr->realCmdPtr = cmdPtr;
1346            oldRefPtr = oldRefPtr->nextPtr;
1347        }
1348    }
1349
1350    /*
1351     * We just created a command, so in its namespace and all of its parent
1352     * namespaces, it may shadow global commands with the same name. If any
1353     * shadowed commands are found, invalidate all cached command references
1354     * in the affected namespaces.
1355     */
1356   
1357    TclResetShadowedCmdRefs(interp, cmdPtr);
1358    return (Tcl_Command) cmdPtr;
1359}
1360
1361/*
1362 *----------------------------------------------------------------------
1363 *
1364 * Tcl_CreateObjCommand --
1365 *
1366 *      Define a new object-based command in a command table.
1367 *
1368 * Results:
1369 *      The return value is a token for the command, which can
1370 *      be used in future calls to Tcl_NameOfCommand.
1371 *
1372 * Side effects:
1373 *      If no command named "cmdName" already exists for interp, one is
1374 *      created. Otherwise, if a command does exist, then if the
1375 *      object-based Tcl_ObjCmdProc is TclInvokeStringCommand, we assume
1376 *      Tcl_CreateCommand was called previously for the same command and
1377 *      just set its Tcl_ObjCmdProc to the argument "proc"; otherwise, we
1378 *      delete the old command.
1379 *
1380 *      In the future, during bytecode evaluation when "cmdName" is seen as
1381 *      the name of a command by Tcl_EvalObj or Tcl_Eval, the object-based
1382 *      Tcl_ObjCmdProc proc will be called. When the command is deleted from
1383 *      the table, deleteProc will be called. See the manual entry for
1384 *      details on the calling sequence.
1385 *
1386 *----------------------------------------------------------------------
1387 */
1388
1389Tcl_Command
1390Tcl_CreateObjCommand(interp, cmdName, proc, clientData, deleteProc)
1391    Tcl_Interp *interp;         /* Token for command interpreter (returned
1392                                 * by previous call to Tcl_CreateInterp). */
1393    char *cmdName;              /* Name of command. If it contains namespace
1394                                 * qualifiers, the new command is put in the
1395                                 * specified namespace; otherwise it is put
1396                                 * in the global namespace. */
1397    Tcl_ObjCmdProc *proc;       /* Object-based procedure to associate with
1398                                 * name. */
1399    ClientData clientData;      /* Arbitrary value to pass to object
1400                                 * procedure. */
1401    Tcl_CmdDeleteProc *deleteProc;
1402                                /* If not NULL, gives a procedure to call
1403                                 * when this command is deleted. */
1404{
1405    Interp *iPtr = (Interp *) interp;
1406    ImportRef *oldRefPtr = NULL;
1407    Namespace *nsPtr, *dummy1, *dummy2;
1408    Command *cmdPtr, *refCmdPtr;
1409    Tcl_HashEntry *hPtr;
1410    char *tail;
1411    int new;
1412    ImportedCmdData *dataPtr;
1413
1414    if (iPtr->flags & DELETED) {
1415        /*
1416         * The interpreter is being deleted.  Don't create any new
1417         * commands;  it's not safe to muck with the interpreter anymore.
1418         */
1419
1420        return (Tcl_Command) NULL;
1421    }
1422
1423    /*
1424     * Determine where the command should reside. If its name contains
1425     * namespace qualifiers, we put it in the specified namespace;
1426     * otherwise, we always put it in the global namespace.
1427     */
1428
1429    if (strstr(cmdName, "::") != NULL) {
1430       TclGetNamespaceForQualName(interp, cmdName, (Namespace *) NULL,
1431           CREATE_NS_IF_UNKNOWN, &nsPtr, &dummy1, &dummy2, &tail);
1432       if ((nsPtr == NULL) || (tail == NULL)) {
1433            return (Tcl_Command) NULL;
1434        }
1435    } else {
1436        nsPtr = iPtr->globalNsPtr;
1437        tail = cmdName;
1438    }
1439
1440    hPtr = Tcl_CreateHashEntry(&nsPtr->cmdTable, tail, &new);
1441    if (!new) {
1442        cmdPtr = (Command *) Tcl_GetHashValue(hPtr);
1443
1444        /*
1445         * Command already exists. If its object-based Tcl_ObjCmdProc is
1446         * TclInvokeStringCommand, we just set its Tcl_ObjCmdProc to the
1447         * argument "proc". Otherwise, we delete the old command.
1448         */
1449
1450        if (cmdPtr->objProc == TclInvokeStringCommand) {
1451            cmdPtr->objProc = proc;
1452            cmdPtr->objClientData = clientData;
1453            cmdPtr->deleteProc = deleteProc;
1454            cmdPtr->deleteData = clientData;
1455            return (Tcl_Command) cmdPtr;
1456        }
1457
1458        /*
1459         * Otherwise, we delete the old command.  Be careful to preserve
1460         * any existing import links so we can restore them down below.
1461         * That way, you can redefine a command and its import status
1462         * will remain intact.
1463         */
1464
1465        oldRefPtr = cmdPtr->importRefPtr;
1466        cmdPtr->importRefPtr = NULL;
1467
1468        Tcl_DeleteCommandFromToken(interp, (Tcl_Command) cmdPtr);
1469        hPtr = Tcl_CreateHashEntry(&nsPtr->cmdTable, tail, &new);
1470        if (!new) {
1471            /*
1472             * If the deletion callback recreated the command, just throw
1473             * away the new command (if we try to delete it again, we
1474             * could get stuck in an infinite loop).
1475             */
1476
1477             ckfree((char *) Tcl_GetHashValue(hPtr));
1478        }
1479    }
1480    cmdPtr = (Command *) ckalloc(sizeof(Command));
1481    Tcl_SetHashValue(hPtr, cmdPtr);
1482    cmdPtr->hPtr = hPtr;
1483    cmdPtr->nsPtr = nsPtr;
1484    cmdPtr->refCount = 1;
1485    cmdPtr->cmdEpoch = 0;
1486    cmdPtr->compileProc = (CompileProc *) NULL;
1487    cmdPtr->objProc = proc;
1488    cmdPtr->objClientData = clientData;
1489    cmdPtr->proc = TclInvokeObjectCommand;
1490    cmdPtr->clientData = (ClientData) cmdPtr;
1491    cmdPtr->deleteProc = deleteProc;
1492    cmdPtr->deleteData = clientData;
1493    cmdPtr->deleted = 0;
1494    cmdPtr->importRefPtr = NULL;
1495
1496    /*
1497     * Plug in any existing import references found above.  Be sure
1498     * to update all of these references to point to the new command.
1499     */
1500
1501    if (oldRefPtr != NULL) {
1502        cmdPtr->importRefPtr = oldRefPtr;
1503        while (oldRefPtr != NULL) {
1504            refCmdPtr = oldRefPtr->importedCmdPtr;
1505            dataPtr = (ImportedCmdData*)refCmdPtr->objClientData;
1506            dataPtr->realCmdPtr = cmdPtr;
1507            oldRefPtr = oldRefPtr->nextPtr;
1508        }
1509    }
1510   
1511    /*
1512     * We just created a command, so in its namespace and all of its parent
1513     * namespaces, it may shadow global commands with the same name. If any
1514     * shadowed commands are found, invalidate all cached command references
1515     * in the affected namespaces.
1516     */
1517   
1518    TclResetShadowedCmdRefs(interp, cmdPtr);
1519    return (Tcl_Command) cmdPtr;
1520}
1521
1522/*
1523 *----------------------------------------------------------------------
1524 *
1525 * TclInvokeStringCommand --
1526 *
1527 *      "Wrapper" Tcl_ObjCmdProc used to call an existing string-based
1528 *      Tcl_CmdProc if no object-based procedure exists for a command. A
1529 *      pointer to this procedure is stored as the Tcl_ObjCmdProc in a
1530 *      Command structure. It simply turns around and calls the string
1531 *      Tcl_CmdProc in the Command structure.
1532 *
1533 * Results:
1534 *      A standard Tcl object result value.
1535 *
1536 * Side effects:
1537 *      Besides those side effects of the called Tcl_CmdProc,
1538 *      TclInvokeStringCommand allocates and frees storage.
1539 *
1540 *----------------------------------------------------------------------
1541 */
1542
1543int
1544TclInvokeStringCommand(clientData, interp, objc, objv)
1545    ClientData clientData;      /* Points to command's Command structure. */
1546    Tcl_Interp *interp;         /* Current interpreter. */
1547    register int objc;          /* Number of arguments. */
1548    Tcl_Obj *CONST objv[];      /* Argument objects. */
1549{
1550    register Command *cmdPtr = (Command *) clientData;
1551    register int i;
1552    int result;
1553
1554    /*
1555     * This procedure generates an argv array for the string arguments. It
1556     * starts out with stack-allocated space but uses dynamically-allocated
1557     * storage if needed.
1558     */
1559
1560#define NUM_ARGS 20
1561    char *(argStorage[NUM_ARGS]);
1562    char **argv = argStorage;
1563
1564    /*
1565     * Create the string argument array "argv". Make sure argv is large
1566     * enough to hold the objc arguments plus 1 extra for the zero
1567     * end-of-argv word.
1568     * THIS FAILS IF ANY ARGUMENT OBJECT CONTAINS AN EMBEDDED NULL.
1569     */
1570
1571    if ((objc + 1) > NUM_ARGS) {
1572        argv = (char **) ckalloc((unsigned)(objc + 1) * sizeof(char *));
1573    }
1574
1575    for (i = 0;  i < objc;  i++) {
1576        argv[i] = Tcl_GetStringFromObj(objv[i], (int *) NULL);
1577    }
1578    argv[objc] = 0;
1579
1580    /*
1581     * Invoke the command's string-based Tcl_CmdProc.
1582     */
1583
1584    result = (*cmdPtr->proc)(cmdPtr->clientData, interp, objc, argv);
1585
1586    /*
1587     * Free the argv array if malloc'ed storage was used.
1588     */
1589
1590    if (argv != argStorage) {
1591        ckfree((char *) argv);
1592    }
1593    return result;
1594#undef NUM_ARGS
1595}
1596
1597/*
1598 *----------------------------------------------------------------------
1599 *
1600 * TclInvokeObjectCommand --
1601 *
1602 *      "Wrapper" Tcl_CmdProc used to call an existing object-based
1603 *      Tcl_ObjCmdProc if no string-based procedure exists for a command.
1604 *      A pointer to this procedure is stored as the Tcl_CmdProc in a
1605 *      Command structure. It simply turns around and calls the object
1606 *      Tcl_ObjCmdProc in the Command structure.
1607 *
1608 * Results:
1609 *      A standard Tcl string result value.
1610 *
1611 * Side effects:
1612 *      Besides those side effects of the called Tcl_CmdProc,
1613 *      TclInvokeStringCommand allocates and frees storage.
1614 *
1615 *----------------------------------------------------------------------
1616 */
1617
1618int
1619TclInvokeObjectCommand(clientData, interp, argc, argv)
1620    ClientData clientData;      /* Points to command's Command structure. */
1621    Tcl_Interp *interp;         /* Current interpreter. */
1622    int argc;                   /* Number of arguments. */
1623    register char **argv;       /* Argument strings. */
1624{
1625    Command *cmdPtr = (Command *) clientData;
1626    register Tcl_Obj *objPtr;
1627    register int i;
1628    int length, result;
1629
1630    /*
1631     * This procedure generates an objv array for object arguments that hold
1632     * the argv strings. It starts out with stack-allocated space but uses
1633     * dynamically-allocated storage if needed.
1634     */
1635
1636#define NUM_ARGS 20
1637    Tcl_Obj *(argStorage[NUM_ARGS]);
1638    register Tcl_Obj **objv = argStorage;
1639
1640    /*
1641     * Create the object argument array "objv". Make sure objv is large
1642     * enough to hold the objc arguments plus 1 extra for the zero
1643     * end-of-objv word.
1644     */
1645
1646    if ((argc + 1) > NUM_ARGS) {
1647        objv = (Tcl_Obj **)
1648            ckalloc((unsigned)(argc + 1) * sizeof(Tcl_Obj *));
1649    }
1650
1651    for (i = 0;  i < argc;  i++) {
1652        length = strlen(argv[i]);
1653        TclNewObj(objPtr);
1654        TclInitStringRep(objPtr, argv[i], length);
1655        Tcl_IncrRefCount(objPtr);
1656        objv[i] = objPtr;
1657    }
1658    objv[argc] = 0;
1659
1660    /*
1661     * Invoke the command's object-based Tcl_ObjCmdProc.
1662     */
1663
1664    result = (*cmdPtr->objProc)(cmdPtr->objClientData, interp, argc, objv);
1665
1666    /*
1667     * Move the interpreter's object result to the string result,
1668     * then reset the object result.
1669     * FAILS IF OBJECT RESULT'S STRING REPRESENTATION CONTAINS NULL BYTES.
1670     */
1671
1672    Tcl_SetResult(interp,
1673            TclGetStringFromObj(Tcl_GetObjResult(interp), (int *) NULL),
1674            TCL_VOLATILE);
1675   
1676    /*
1677     * Decrement the ref counts for the argument objects created above,
1678     * then free the objv array if malloc'ed storage was used.
1679     */
1680
1681    for (i = 0;  i < argc;  i++) {
1682        objPtr = objv[i];
1683        Tcl_DecrRefCount(objPtr);
1684    }
1685    if (objv != argStorage) {
1686        ckfree((char *) objv);
1687    }
1688    return result;
1689#undef NUM_ARGS
1690}
1691/*
1692 *----------------------------------------------------------------------
1693 *
1694 * Tcl_SetCommandInfo --
1695 *
1696 *      Modifies various information about a Tcl command. Note that
1697 *      this procedure will not change a command's namespace; use
1698 *      Tcl_RenameCommand to do that. Also, the isNativeObjectProc
1699 *      member of *infoPtr is ignored.
1700 *
1701 * Results:
1702 *      If cmdName exists in interp, then the information at *infoPtr
1703 *      is stored with the command in place of the current information
1704 *      and 1 is returned. If the command doesn't exist then 0 is
1705 *      returned.
1706 *
1707 * Side effects:
1708 *      None.
1709 *
1710 *----------------------------------------------------------------------
1711 */
1712
1713int
1714Tcl_SetCommandInfo(interp, cmdName, infoPtr)
1715    Tcl_Interp *interp;                 /* Interpreter in which to look
1716                                         * for command. */
1717    char *cmdName;                      /* Name of desired command. */
1718    Tcl_CmdInfo *infoPtr;               /* Where to store information about
1719                                         * command. */
1720{
1721    Tcl_Command cmd;
1722    Command *cmdPtr;
1723
1724    cmd = Tcl_FindCommand(interp, cmdName, (Tcl_Namespace *) NULL,
1725            /*flags*/ 0);
1726    if (cmd == (Tcl_Command) NULL) {
1727        return 0;
1728    }
1729
1730    /*
1731     * The isNativeObjectProc and nsPtr members of *infoPtr are ignored.
1732     */
1733   
1734    cmdPtr = (Command *) cmd;
1735    cmdPtr->proc = infoPtr->proc;
1736    cmdPtr->clientData = infoPtr->clientData;
1737    if (infoPtr->objProc == (Tcl_ObjCmdProc *) NULL) {
1738        cmdPtr->objProc = TclInvokeStringCommand;
1739        cmdPtr->objClientData = (ClientData) cmdPtr;
1740    } else {
1741        cmdPtr->objProc = infoPtr->objProc;
1742        cmdPtr->objClientData = infoPtr->objClientData;
1743    }
1744    cmdPtr->deleteProc = infoPtr->deleteProc;
1745    cmdPtr->deleteData = infoPtr->deleteData;
1746    return 1;
1747}
1748
1749/*
1750 *----------------------------------------------------------------------
1751 *
1752 * Tcl_GetCommandInfo --
1753 *
1754 *      Returns various information about a Tcl command.
1755 *
1756 * Results:
1757 *      If cmdName exists in interp, then *infoPtr is modified to
1758 *      hold information about cmdName and 1 is returned.  If the
1759 *      command doesn't exist then 0 is returned and *infoPtr isn't
1760 *      modified.
1761 *
1762 * Side effects:
1763 *      None.
1764 *
1765 *----------------------------------------------------------------------
1766 */
1767
1768int
1769Tcl_GetCommandInfo(interp, cmdName, infoPtr)
1770    Tcl_Interp *interp;                 /* Interpreter in which to look
1771                                         * for command. */
1772    char *cmdName;                      /* Name of desired command. */
1773    Tcl_CmdInfo *infoPtr;               /* Where to store information about
1774                                         * command. */
1775{
1776    Tcl_Command cmd;
1777    Command *cmdPtr;
1778
1779    cmd = Tcl_FindCommand(interp, cmdName, (Tcl_Namespace *) NULL,
1780            /*flags*/ 0);
1781    if (cmd == (Tcl_Command) NULL) {
1782        return 0;
1783    }
1784
1785    /*
1786     * Set isNativeObjectProc 1 if objProc was registered by a call to
1787     * Tcl_CreateObjCommand. Otherwise set it to 0.
1788     */
1789
1790    cmdPtr = (Command *) cmd;
1791    infoPtr->isNativeObjectProc =
1792            (cmdPtr->objProc != TclInvokeStringCommand);
1793    infoPtr->objProc = cmdPtr->objProc;
1794    infoPtr->objClientData = cmdPtr->objClientData;
1795    infoPtr->proc = cmdPtr->proc;
1796    infoPtr->clientData = cmdPtr->clientData;
1797    infoPtr->deleteProc = cmdPtr->deleteProc;
1798    infoPtr->deleteData = cmdPtr->deleteData;
1799    infoPtr->namespacePtr = (Tcl_Namespace *) cmdPtr->nsPtr;
1800    return 1;
1801}
1802
1803/*
1804 *----------------------------------------------------------------------
1805 *
1806 * Tcl_GetCommandName --
1807 *
1808 *      Given a token returned by Tcl_CreateCommand, this procedure
1809 *      returns the current name of the command (which may have changed
1810 *      due to renaming).
1811 *
1812 * Results:
1813 *      The return value is the name of the given command.
1814 *
1815 * Side effects:
1816 *      None.
1817 *
1818 *----------------------------------------------------------------------
1819 */
1820
1821char *
1822Tcl_GetCommandName(interp, command)
1823    Tcl_Interp *interp;         /* Interpreter containing the command. */
1824    Tcl_Command command;        /* Token for command returned by a previous
1825                                 * call to Tcl_CreateCommand. The command
1826                                 * must not have been deleted. */
1827{
1828    Command *cmdPtr = (Command *) command;
1829
1830    if ((cmdPtr == NULL) || (cmdPtr->hPtr == NULL)) {
1831
1832        /*
1833         * This should only happen if command was "created" after the
1834         * interpreter began to be deleted, so there isn't really any
1835         * command. Just return an empty string.
1836         */
1837
1838        return "";
1839    }
1840    return Tcl_GetHashKey(cmdPtr->hPtr->tablePtr, cmdPtr->hPtr);
1841}
1842
1843/*
1844 *----------------------------------------------------------------------
1845 *
1846 * Tcl_GetCommandFullName --
1847 *
1848 *      Given a token returned by, e.g., Tcl_CreateCommand or
1849 *      Tcl_FindCommand, this procedure appends to an object the command's
1850 *      full name, qualified by a sequence of parent namespace names. The
1851 *      command's fully-qualified name may have changed due to renaming.
1852 *
1853 * Results:
1854 *      None.
1855 *
1856 * Side effects:
1857 *      The command's fully-qualified name is appended to the string
1858 *      representation of objPtr.
1859 *
1860 *----------------------------------------------------------------------
1861 */
1862
1863void
1864Tcl_GetCommandFullName(interp, command, objPtr)
1865    Tcl_Interp *interp;         /* Interpreter containing the command. */
1866    Tcl_Command command;        /* Token for command returned by a previous
1867                                 * call to Tcl_CreateCommand. The command
1868                                 * must not have been deleted. */
1869    Tcl_Obj *objPtr;            /* Points to the object onto which the
1870                                 * command's full name is appended. */
1871
1872{
1873    Interp *iPtr = (Interp *) interp;
1874    register Command *cmdPtr = (Command *) command;
1875    char *name;
1876
1877    /*
1878     * Add the full name of the containing namespace, followed by the "::"
1879     * separator, and the command name.
1880     */
1881
1882    if (cmdPtr != NULL) {
1883        if (cmdPtr->nsPtr != NULL) {
1884            Tcl_AppendToObj(objPtr, cmdPtr->nsPtr->fullName, -1);
1885            if (cmdPtr->nsPtr != iPtr->globalNsPtr) {
1886                Tcl_AppendToObj(objPtr, "::", 2);
1887            }
1888        }
1889        if (cmdPtr->hPtr != NULL) {
1890            name = Tcl_GetHashKey(cmdPtr->hPtr->tablePtr, cmdPtr->hPtr);
1891            Tcl_AppendToObj(objPtr, name, -1);
1892        }
1893    }
1894}
1895
1896/*
1897 *----------------------------------------------------------------------
1898 *
1899 * Tcl_DeleteCommand --
1900 *
1901 *      Remove the given command from the given interpreter.
1902 *
1903 * Results:
1904 *      0 is returned if the command was deleted successfully.
1905 *      -1 is returned if there didn't exist a command by that name.
1906 *
1907 * Side effects:
1908 *      cmdName will no longer be recognized as a valid command for
1909 *      interp.
1910 *
1911 *----------------------------------------------------------------------
1912 */
1913
1914int
1915Tcl_DeleteCommand(interp, cmdName)
1916    Tcl_Interp *interp;         /* Token for command interpreter (returned
1917                                 * by a previous Tcl_CreateInterp call). */
1918    char *cmdName;              /* Name of command to remove. */
1919{
1920    Tcl_Command cmd;
1921
1922    /*
1923     *  Find the desired command and delete it.
1924     */
1925
1926    cmd = Tcl_FindCommand(interp, cmdName, (Tcl_Namespace *) NULL,
1927            /*flags*/ 0);
1928    if (cmd == (Tcl_Command) NULL) {
1929        return -1;
1930    }
1931    return Tcl_DeleteCommandFromToken(interp, cmd);
1932}
1933
1934/*
1935 *----------------------------------------------------------------------
1936 *
1937 * Tcl_DeleteCommandFromToken --
1938 *
1939 *      Removes the given command from the given interpreter. This procedure
1940 *      resembles Tcl_DeleteCommand, but takes a Tcl_Command token instead
1941 *      of a command name for efficiency.
1942 *
1943 * Results:
1944 *      0 is returned if the command was deleted successfully.
1945 *      -1 is returned if there didn't exist a command by that name.
1946 *
1947 * Side effects:
1948 *      The command specified by "cmd" will no longer be recognized as a
1949 *      valid command for "interp".
1950 *
1951 *----------------------------------------------------------------------
1952 */
1953
1954int
1955Tcl_DeleteCommandFromToken(interp, cmd)
1956    Tcl_Interp *interp;         /* Token for command interpreter returned by
1957                                 * a previous call to Tcl_CreateInterp. */
1958    Tcl_Command cmd;            /* Token for command to delete. */
1959{
1960    Interp *iPtr = (Interp *) interp;
1961    Command *cmdPtr = (Command *) cmd;
1962    ImportRef *refPtr, *nextRefPtr;
1963    Tcl_Command importCmd;
1964
1965    /*
1966     * The code here is tricky.  We can't delete the hash table entry
1967     * before invoking the deletion callback because there are cases
1968     * where the deletion callback needs to invoke the command (e.g.
1969     * object systems such as OTcl). However, this means that the
1970     * callback could try to delete or rename the command. The deleted
1971     * flag allows us to detect these cases and skip nested deletes.
1972     */
1973
1974    if (cmdPtr->deleted) {
1975        /*
1976         * Another deletion is already in progress.  Remove the hash
1977         * table entry now, but don't invoke a callback or free the
1978         * command structure.
1979         */
1980
1981        Tcl_DeleteHashEntry(cmdPtr->hPtr);
1982        cmdPtr->hPtr = NULL;
1983        return 0;
1984    }
1985
1986    /*
1987     * If the command being deleted has a compile procedure, increment the
1988     * interpreter's compileEpoch to invalidate its compiled code. This
1989     * makes sure that we don't later try to execute old code compiled with
1990     * command-specific (i.e., inline) bytecodes for the now-deleted
1991     * command. This field is checked in Tcl_EvalObj and ObjInterpProc, and
1992     * code whose compilation epoch doesn't match is recompiled.
1993     */
1994
1995    if (cmdPtr->compileProc != NULL) {
1996        iPtr->compileEpoch++;
1997    }
1998
1999    cmdPtr->deleted = 1;
2000    if (cmdPtr->deleteProc != NULL) {
2001        /*
2002         * Delete the command's client data. If this was an imported command
2003         * created when a command was imported into a namespace, this client
2004         * data will be a pointer to a ImportedCmdData structure describing
2005         * the "real" command that this imported command refers to.
2006         */
2007       
2008        (*cmdPtr->deleteProc)(cmdPtr->deleteData);
2009    }
2010
2011    /*
2012     * Bump the command epoch counter. This will invalidate all cached
2013     * references that point to this command.
2014     */
2015   
2016    cmdPtr->cmdEpoch++;
2017
2018    /*
2019     * If this command was imported into other namespaces, then imported
2020     * commands were created that refer back to this command. Delete these
2021     * imported commands now.
2022     */
2023
2024    for (refPtr = cmdPtr->importRefPtr;  refPtr != NULL;
2025            refPtr = nextRefPtr) {
2026        nextRefPtr = refPtr->nextPtr;
2027        importCmd = (Tcl_Command) refPtr->importedCmdPtr;
2028        Tcl_DeleteCommandFromToken(interp, importCmd);
2029    }
2030
2031    /*
2032     * Don't use hPtr to delete the hash entry here, because it's
2033     * possible that the deletion callback renamed the command.
2034     * Instead, use cmdPtr->hptr, and make sure that no-one else
2035     * has already deleted the hash entry.
2036     */
2037
2038    if (cmdPtr->hPtr != NULL) {
2039        Tcl_DeleteHashEntry(cmdPtr->hPtr);
2040    }
2041
2042    /*
2043     * Mark the Command structure as no longer valid. This allows
2044     * TclExecuteByteCode to recognize when a Command has logically been
2045     * deleted and a pointer to this Command structure cached in a CmdName
2046     * object is invalid. TclExecuteByteCode will look up the command again
2047     * in the interpreter's command hashtable.
2048     */
2049
2050    cmdPtr->objProc = NULL;
2051
2052    /*
2053     * Now free the Command structure, unless there is another reference to
2054     * it from a CmdName Tcl object in some ByteCode code sequence. In that
2055     * case, delay the cleanup until all references are either discarded
2056     * (when a ByteCode is freed) or replaced by a new reference (when a
2057     * cached CmdName Command reference is found to be invalid and
2058     * TclExecuteByteCode looks up the command in the command hashtable).
2059     */
2060   
2061    TclCleanupCommand(cmdPtr);
2062    return 0;
2063}
2064
2065/*
2066 *----------------------------------------------------------------------
2067 *
2068 * TclCleanupCommand --
2069 *
2070 *      This procedure frees up a Command structure unless it is still
2071 *      referenced from an interpreter's command hashtable or from a CmdName
2072 *      Tcl object representing the name of a command in a ByteCode
2073 *      instruction sequence.
2074 *
2075 * Results:
2076 *      None.
2077 *
2078 * Side effects:
2079 *      Memory gets freed unless a reference to the Command structure still
2080 *      exists. In that case the cleanup is delayed until the command is
2081 *      deleted or when the last ByteCode referring to it is freed.
2082 *
2083 *----------------------------------------------------------------------
2084 */
2085
2086void
2087TclCleanupCommand(cmdPtr)
2088    register Command *cmdPtr;   /* Points to the Command structure to
2089                                 * be freed. */
2090{
2091    cmdPtr->refCount--;
2092    if (cmdPtr->refCount <= 0) {
2093        ckfree((char *) cmdPtr);
2094    }
2095}
2096
2097/*
2098 *----------------------------------------------------------------------
2099 *
2100 * Tcl_Eval --
2101 *
2102 *      Execute a Tcl command in a string.
2103 *
2104 * Results:
2105 *      The return value is one of the return codes defined in tcl.h
2106 *      (such as TCL_OK), and interp->result contains a string value
2107 *      to supplement the return code. The value of interp->result
2108 *      will persist only until the next call to Tcl_Eval or Tcl_EvalObj:
2109 *      you must copy it or lose it!
2110 *
2111 * Side effects:
2112 *      The string is compiled to produce a ByteCode object that holds the
2113 *      command's bytecode instructions. However, this ByteCode object is
2114 *      lost after executing the command. The command's execution will
2115 *      almost certainly have side effects. interp->termOffset is set to the
2116 *      offset of the character in "string" just after the last one
2117 *      successfully compiled or executed.
2118 *
2119 *----------------------------------------------------------------------
2120 */
2121
2122int
2123Tcl_Eval(interp, string)
2124    Tcl_Interp *interp;         /* Token for command interpreter (returned
2125                                 * by previous call to Tcl_CreateInterp). */
2126    char *string;               /* Pointer to TCL command to execute. */
2127{
2128    register Tcl_Obj *cmdPtr;
2129    int length = strlen(string);
2130    int result;
2131
2132    if (length > 0) {
2133        /*
2134         * Initialize a Tcl object from the command string.
2135         */
2136
2137        TclNewObj(cmdPtr);
2138        TclInitStringRep(cmdPtr, string, length);
2139        Tcl_IncrRefCount(cmdPtr);
2140
2141        /*
2142         * Compile and execute the bytecodes.
2143         */
2144   
2145        result = Tcl_EvalObj(interp, cmdPtr);
2146
2147        /*
2148         * Move the interpreter's object result to the string result,
2149         * then reset the object result.
2150         * FAILS IF OBJECT RESULT'S STRING REPRESENTATION CONTAINS NULLS.
2151         */
2152
2153        Tcl_SetResult(interp,
2154                TclGetStringFromObj(Tcl_GetObjResult(interp), (int *) NULL),
2155                TCL_VOLATILE);
2156
2157        /*
2158         * Discard the Tcl object created to hold the command and its code.
2159         */
2160       
2161        Tcl_DecrRefCount(cmdPtr);       
2162    } else {
2163        /*
2164         * An empty string. Just reset the interpreter's result.
2165         */
2166
2167        Tcl_ResetResult(interp);
2168        result = TCL_OK;
2169    }
2170    return result;
2171}
2172
2173/*
2174 *----------------------------------------------------------------------
2175 *
2176 * Tcl_EvalObj --
2177 *
2178 *      Execute Tcl commands stored in a Tcl object. These commands are
2179 *      compiled into bytecodes if necessary.
2180 *
2181 * Results:
2182 *      The return value is one of the return codes defined in tcl.h
2183 *      (such as TCL_OK), and the interpreter's result contains a value
2184 *      to supplement the return code.
2185 *
2186 * Side effects:
2187 *      The object is converted, if necessary, to a ByteCode object that
2188 *      holds the bytecode instructions for the commands. Executing the
2189 *      commands will almost certainly have side effects that depend
2190 *      on those commands.
2191 *
2192 *      Just as in Tcl_Eval, interp->termOffset is set to the offset of the
2193 *      last character executed in the objPtr's string.
2194 *
2195 *----------------------------------------------------------------------
2196 */
2197
2198#undef Tcl_EvalObj
2199
2200int
2201Tcl_EvalObj(interp, objPtr)
2202    Tcl_Interp *interp;                 /* Token for command interpreter
2203                                         * (returned by a previous call to
2204                                         * Tcl_CreateInterp). */
2205    Tcl_Obj *objPtr;                    /* Pointer to object containing
2206                                         * commands to execute. */
2207{
2208    register Interp *iPtr = (Interp *) interp;
2209    int flags;                          /* Interp->evalFlags value when the
2210                                         * procedure was called. */
2211    register ByteCode* codePtr;         /* Tcl Internal type of bytecode. */
2212    int oldCount = iPtr->cmdCount;      /* Used to tell whether any commands
2213                                         * at all were executed. */
2214    int numSrcChars;
2215    register int result;
2216    Namespace *namespacePtr;
2217
2218    /*
2219     * Reset both the interpreter's string and object results and clear out
2220     * any error information. This makes sure that we return an empty
2221     * result if there are no commands in the command string.
2222     */
2223
2224    Tcl_ResetResult(interp);
2225
2226    /*
2227     * Check depth of nested calls to Tcl_Eval:  if this gets too large,
2228     * it's probably because of an infinite loop somewhere.
2229     */
2230
2231    iPtr->numLevels++;
2232    if (iPtr->numLevels > iPtr->maxNestingDepth) {
2233        iPtr->numLevels--;
2234        Tcl_AppendToObj(Tcl_GetObjResult(interp),
2235                "too many nested calls to Tcl_EvalObj (infinite loop?)", -1);
2236        return TCL_ERROR;
2237    }   
2238
2239    /*
2240     * If the interpreter has been deleted, return an error.
2241     */
2242   
2243    if (iPtr->flags & DELETED) {
2244        Tcl_ResetResult(interp);
2245        Tcl_AppendToObj(Tcl_GetObjResult(interp),
2246                "attempt to call eval in deleted interpreter", -1);
2247        Tcl_SetErrorCode(interp, "CORE", "IDELETE",
2248                "attempt to call eval in deleted interpreter", (char *) NULL);
2249        iPtr->numLevels--;
2250        return TCL_ERROR;
2251    }
2252
2253    /*
2254     * Get the ByteCode from the object. If it exists, make sure it hasn't
2255     * been invalidated by, e.g., someone redefining a command with a
2256     * compile procedure (this might make the compiled code wrong). If
2257     * necessary, convert the object to be a ByteCode object and compile it.
2258     * Also, if the code was compiled in/for a different interpreter,
2259     * or for a different namespace, or for the same namespace but
2260     * with different name resolution rules, we recompile it.
2261     *
2262     * Precompiled objects, however, are immutable and therefore
2263     * they are not recompiled, even if the epoch has changed.
2264     */
2265
2266    if (iPtr->varFramePtr != NULL) {
2267        namespacePtr = iPtr->varFramePtr->nsPtr;
2268    } else {
2269        namespacePtr = iPtr->globalNsPtr;
2270    }
2271
2272    if (objPtr->typePtr == &tclByteCodeType) {
2273        codePtr = (ByteCode *) objPtr->internalRep.otherValuePtr;
2274       
2275        if ((codePtr->iPtr != iPtr)
2276                || (codePtr->compileEpoch != iPtr->compileEpoch)
2277                || (codePtr->nsPtr != namespacePtr)
2278                || (codePtr->nsEpoch != namespacePtr->resolverEpoch)) {
2279            if (codePtr->flags & TCL_BYTECODE_PRECOMPILED) {
2280                if (codePtr->iPtr != iPtr) {
2281                    panic("Tcl_EvalObj: compiled script jumped interps");
2282                }
2283                codePtr->compileEpoch = iPtr->compileEpoch;
2284            } else {
2285                tclByteCodeType.freeIntRepProc(objPtr);
2286            }
2287        }
2288    }
2289    if (objPtr->typePtr != &tclByteCodeType) {
2290        /*
2291         * First reset any error line number information.
2292         */
2293       
2294        iPtr->errorLine = 1;   /* no correct line # information yet */
2295        result = tclByteCodeType.setFromAnyProc(interp, objPtr);
2296        if (result != TCL_OK) {
2297            iPtr->numLevels--;
2298            return result;
2299        }
2300    }
2301    codePtr = (ByteCode *) objPtr->internalRep.otherValuePtr;
2302
2303    /*
2304     * Extract then reset the compilation flags in the interpreter.
2305     * Resetting the flags must be done after any compilation.
2306     */
2307
2308    flags = iPtr->evalFlags;
2309    iPtr->evalFlags = 0;
2310
2311    /*
2312     * Execute the commands. If the code was compiled from an empty string,
2313     * don't bother executing the code.
2314     */
2315
2316    numSrcChars = codePtr->numSrcChars;
2317    if ((numSrcChars > 0) || (codePtr->flags & TCL_BYTECODE_PRECOMPILED)) {
2318        /*
2319         * Increment the code's ref count while it is being executed. If
2320         * afterwards no references to it remain, free the code.
2321         */
2322       
2323        codePtr->refCount++;
2324        result = TclExecuteByteCode(interp, codePtr);
2325        codePtr->refCount--;
2326        if (codePtr->refCount <= 0) {
2327            TclCleanupByteCode(codePtr);
2328        }
2329    } else {
2330        Tcl_ResetResult(interp);
2331        result = TCL_OK;
2332    }
2333
2334    /*
2335     * If no commands at all were executed, check for asynchronous
2336     * handlers so that they at least get one change to execute.
2337     * This is needed to handle event loops written in Tcl with
2338     * empty bodies.
2339     */
2340
2341    if ((oldCount == iPtr->cmdCount) && (Tcl_AsyncReady())) {
2342        result = Tcl_AsyncInvoke(interp, result);
2343    }
2344
2345    /*
2346     * Free up any extra resources that were allocated.
2347     */
2348
2349    iPtr->numLevels--;
2350    if (iPtr->numLevels == 0) {
2351        if (result == TCL_RETURN) {
2352            result = TclUpdateReturnInfo(iPtr);
2353        }
2354        if ((result != TCL_OK) && (result != TCL_ERROR)
2355                && !(flags & TCL_ALLOW_EXCEPTIONS)) {
2356            Tcl_ResetResult(interp);
2357            if (result == TCL_BREAK) {
2358                Tcl_AppendToObj(Tcl_GetObjResult(interp),
2359                        "invoked \"break\" outside of a loop", -1);
2360            } else if (result == TCL_CONTINUE) {
2361                Tcl_AppendToObj(Tcl_GetObjResult(interp),
2362                        "invoked \"continue\" outside of a loop", -1);
2363            } else {
2364                char buf[50];
2365                sprintf(buf, "command returned bad code: %d", result);
2366                Tcl_AppendToObj(Tcl_GetObjResult(interp), buf, -1);
2367            }
2368            result = TCL_ERROR;
2369        }
2370    }
2371
2372    /*
2373     * If an error occurred, record information about what was being
2374     * executed when the error occurred.
2375     */
2376
2377    if ((result == TCL_ERROR) && !(iPtr->flags & ERR_ALREADY_LOGGED)) {
2378        char buf[200];
2379        char *ellipsis = "";
2380        char *bytes;
2381        int length;
2382
2383        /*
2384         * Figure out how much of the command to print in the error
2385         * message (up to a certain number of characters, or up to
2386         * the first new-line).
2387         * THIS FAILS IF THE OBJECT'S STRING REP CONTAINS A NULL.
2388         */
2389
2390        bytes = Tcl_GetStringFromObj(objPtr, &length);
2391        length = TclMin(numSrcChars, length);
2392        if (length > 150) {
2393            length = 150;
2394            ellipsis = " ...";
2395        }
2396
2397        if (!(iPtr->flags & ERR_IN_PROGRESS)) {
2398            sprintf(buf, "\n    while executing\n\"%.*s%s\"",
2399                    length, bytes, ellipsis);
2400        } else {
2401            sprintf(buf, "\n    invoked from within\n\"%.*s%s\"",
2402                    length, bytes, ellipsis);
2403        }
2404        Tcl_AddObjErrorInfo(interp, buf, -1);
2405    }
2406
2407    /*
2408     * Set the interpreter's termOffset member to the offset of the
2409     * character just after the last one executed. We approximate the offset
2410     * of the last character executed by using the number of characters
2411     * compiled.
2412     */
2413
2414    iPtr->termOffset = numSrcChars;
2415    iPtr->flags &= ~ERR_ALREADY_LOGGED;
2416    return result;
2417}
2418
2419/*
2420 *--------------------------------------------------------------
2421 *
2422 * Tcl_ExprLong, Tcl_ExprDouble, Tcl_ExprBoolean --
2423 *
2424 *      Procedures to evaluate an expression and return its value in a
2425 *      particular form.
2426 *
2427 * Results:
2428 *      Each of the procedures below returns a standard Tcl result. If an
2429 *      error occurs then an error message is left in interp->result.
2430 *      Otherwise the value of the expression, in the appropriate form, is
2431 *      stored at *ptr. If the expression had a result that was
2432 *      incompatible with the desired form then an error is returned.
2433 *
2434 * Side effects:
2435 *      None.
2436 *
2437 *--------------------------------------------------------------
2438 */
2439
2440int
2441Tcl_ExprLong(interp, string, ptr)
2442    Tcl_Interp *interp;         /* Context in which to evaluate the
2443                                 * expression. */
2444    char *string;               /* Expression to evaluate. */
2445    long *ptr;                  /* Where to store result. */
2446{
2447    register Tcl_Obj *exprPtr;
2448    Tcl_Obj *resultPtr;
2449    int length = strlen(string);
2450    int result = TCL_OK;
2451
2452    if (length > 0) {
2453        exprPtr = Tcl_NewStringObj(string, length);
2454        Tcl_IncrRefCount(exprPtr);
2455        result = Tcl_ExprObj(interp, exprPtr, &resultPtr);
2456        if (result == TCL_OK) {
2457            /*
2458             * Store an integer based on the expression result.
2459             */
2460           
2461            if (resultPtr->typePtr == &tclIntType) {
2462                *ptr = resultPtr->internalRep.longValue;
2463            } else if (resultPtr->typePtr == &tclDoubleType) {
2464                *ptr = (long) resultPtr->internalRep.doubleValue;
2465            } else {
2466                Tcl_SetResult(interp,
2467                        "expression didn't have numeric value", TCL_STATIC);
2468                result = TCL_ERROR;
2469            }
2470            Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2471        } else {
2472            /*
2473             * Move the interpreter's object result to the string result,
2474             * then reset the object result.
2475             * FAILS IF OBJECT RESULT'S STRING REPRESENTATION HAS NULLS.
2476             */
2477
2478            Tcl_SetResult(interp,
2479                    TclGetStringFromObj(Tcl_GetObjResult(interp),
2480                            (int *) NULL),
2481                    TCL_VOLATILE);
2482        }
2483        Tcl_DecrRefCount(exprPtr);  /* discard the expression object */ 
2484    } else {
2485        /*
2486         * An empty string. Just set the result integer to 0.
2487         */
2488       
2489        *ptr = 0;
2490    }
2491    return result;
2492}
2493
2494int
2495Tcl_ExprDouble(interp, string, ptr)
2496    Tcl_Interp *interp;         /* Context in which to evaluate the
2497                                 * expression. */
2498    char *string;               /* Expression to evaluate. */
2499    double *ptr;                /* Where to store result. */
2500{
2501    register Tcl_Obj *exprPtr;
2502    Tcl_Obj *resultPtr;
2503    int length = strlen(string);
2504    int result = TCL_OK;
2505
2506    if (length > 0) {
2507        exprPtr = Tcl_NewStringObj(string, length);
2508        Tcl_IncrRefCount(exprPtr);
2509        result = Tcl_ExprObj(interp, exprPtr, &resultPtr);
2510        if (result == TCL_OK) {
2511            /*
2512             * Store a double  based on the expression result.
2513             */
2514           
2515            if (resultPtr->typePtr == &tclIntType) {
2516                *ptr = (double) resultPtr->internalRep.longValue;
2517            } else if (resultPtr->typePtr == &tclDoubleType) {
2518                *ptr = resultPtr->internalRep.doubleValue;
2519            } else {
2520                Tcl_SetResult(interp,
2521                        "expression didn't have numeric value", TCL_STATIC);
2522                result = TCL_ERROR;
2523            }
2524            Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2525        } else {
2526            /*
2527             * Move the interpreter's object result to the string result,
2528             * then reset the object result.
2529             * FAILS IF OBJECT RESULT'S STRING REPRESENTATION HAS NULLS.
2530             */
2531
2532            Tcl_SetResult(interp,
2533                    TclGetStringFromObj(Tcl_GetObjResult(interp),
2534                            (int *) NULL),
2535                    TCL_VOLATILE);
2536        }
2537        Tcl_DecrRefCount(exprPtr);  /* discard the expression object */
2538    } else {
2539        /*
2540         * An empty string. Just set the result double to 0.0.
2541         */
2542       
2543        *ptr = 0.0;
2544    }
2545    return result;
2546}
2547
2548int
2549Tcl_ExprBoolean(interp, string, ptr)
2550    Tcl_Interp *interp;         /* Context in which to evaluate the
2551                                 * expression. */
2552    char *string;               /* Expression to evaluate. */
2553    int *ptr;                   /* Where to store 0/1 result. */
2554{
2555    register Tcl_Obj *exprPtr;
2556    Tcl_Obj *resultPtr;
2557    int length = strlen(string);
2558    int result = TCL_OK;
2559
2560    if (length > 0) {
2561        exprPtr = Tcl_NewStringObj(string, length);
2562        Tcl_IncrRefCount(exprPtr);
2563        result = Tcl_ExprObj(interp, exprPtr, &resultPtr);
2564        if (result == TCL_OK) {
2565            /*
2566             * Store a boolean based on the expression result.
2567             */
2568           
2569            if (resultPtr->typePtr == &tclIntType) {
2570                *ptr = (resultPtr->internalRep.longValue != 0);
2571            } else if (resultPtr->typePtr == &tclDoubleType) {
2572                *ptr = (resultPtr->internalRep.doubleValue != 0.0);
2573            } else {
2574                result = Tcl_GetBooleanFromObj(interp, resultPtr, ptr);
2575            }
2576            Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2577        }
2578        if (result != TCL_OK) {
2579            /*
2580             * Move the interpreter's object result to the string result,
2581             * then reset the object result.
2582             * FAILS IF OBJECT RESULT'S STRING REPRESENTATION HAS NULLS.
2583             */
2584
2585            Tcl_SetResult(interp,
2586                    TclGetStringFromObj(Tcl_GetObjResult(interp),
2587                            (int *) NULL),
2588                    TCL_VOLATILE);
2589        }
2590        Tcl_DecrRefCount(exprPtr); /* discard the expression object */
2591    } else {
2592        /*
2593         * An empty string. Just set the result boolean to 0 (false).
2594         */
2595       
2596        *ptr = 0;
2597    }
2598    return result;
2599}
2600
2601/*
2602 *--------------------------------------------------------------
2603 *
2604 * Tcl_ExprLongObj, Tcl_ExprDoubleObj, Tcl_ExprBooleanObj --
2605 *
2606 *      Procedures to evaluate an expression in an object and return its
2607 *      value in a particular form.
2608 *
2609 * Results:
2610 *      Each of the procedures below returns a standard Tcl result
2611 *      object. If an error occurs then an error message is left in the
2612 *      interpreter's result. Otherwise the value of the expression, in the
2613 *      appropriate form, is stored at *ptr. If the expression had a result
2614 *      that was incompatible with the desired form then an error is
2615 *      returned.
2616 *
2617 * Side effects:
2618 *      None.
2619 *
2620 *--------------------------------------------------------------
2621 */
2622
2623int
2624Tcl_ExprLongObj(interp, objPtr, ptr)
2625    Tcl_Interp *interp;                 /* Context in which to evaluate the
2626                                         * expression. */
2627    register Tcl_Obj *objPtr;           /* Expression to evaluate. */
2628    long *ptr;                          /* Where to store long result. */
2629{
2630    Tcl_Obj *resultPtr;
2631    int result;
2632
2633    result = Tcl_ExprObj(interp, objPtr, &resultPtr);
2634    if (result == TCL_OK) {
2635        if (resultPtr->typePtr == &tclIntType) {
2636            *ptr = resultPtr->internalRep.longValue;
2637        } else if (resultPtr->typePtr == &tclDoubleType) {
2638            *ptr = (long) resultPtr->internalRep.doubleValue;
2639        } else {
2640            result = Tcl_GetLongFromObj(interp, resultPtr, ptr);
2641            if (result != TCL_OK) {
2642                return result;
2643            }
2644        }
2645        Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2646    }
2647    return result;
2648}
2649
2650int
2651Tcl_ExprDoubleObj(interp, objPtr, ptr)
2652    Tcl_Interp *interp;                 /* Context in which to evaluate the
2653                                         * expression. */
2654    register Tcl_Obj *objPtr;           /* Expression to evaluate. */
2655    double *ptr;                        /* Where to store double result. */
2656{
2657    Tcl_Obj *resultPtr;
2658    int result;
2659
2660    result = Tcl_ExprObj(interp, objPtr, &resultPtr);
2661    if (result == TCL_OK) {
2662        if (resultPtr->typePtr == &tclIntType) {
2663            *ptr = (double) resultPtr->internalRep.longValue;
2664        } else if (resultPtr->typePtr == &tclDoubleType) {
2665            *ptr = resultPtr->internalRep.doubleValue;
2666        } else {
2667            result = Tcl_GetDoubleFromObj(interp, resultPtr, ptr);
2668            if (result != TCL_OK) {
2669                return result;
2670            }
2671        }
2672        Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2673    }
2674    return result;
2675}
2676
2677int
2678Tcl_ExprBooleanObj(interp, objPtr, ptr)
2679    Tcl_Interp *interp;                 /* Context in which to evaluate the
2680                                         * expression. */
2681    register Tcl_Obj *objPtr;           /* Expression to evaluate. */
2682    int *ptr;                           /* Where to store 0/1 result. */
2683{
2684    Tcl_Obj *resultPtr;
2685    int result;
2686
2687    result = Tcl_ExprObj(interp, objPtr, &resultPtr);
2688    if (result == TCL_OK) {
2689        if (resultPtr->typePtr == &tclIntType) {
2690            *ptr = (resultPtr->internalRep.longValue != 0);
2691        } else if (resultPtr->typePtr == &tclDoubleType) {
2692            *ptr = (resultPtr->internalRep.doubleValue != 0.0);
2693        } else {
2694            result = Tcl_GetBooleanFromObj(interp, resultPtr, ptr);
2695            if (result != TCL_OK) {
2696                return result;
2697            }
2698        }
2699        Tcl_DecrRefCount(resultPtr);  /* discard the result object */
2700    }
2701    return result;
2702}
2703
2704/*
2705 *----------------------------------------------------------------------
2706 *
2707 * TclInvoke --
2708 *
2709 *      Invokes a Tcl command, given an argv/argc, from either the
2710 *      exposed or the hidden sets of commands in the given interpreter.
2711 *      NOTE: The command is invoked in the current stack frame of
2712 *      the interpreter, thus it can modify local variables.
2713 *
2714 * Results:
2715 *      A standard Tcl result.
2716 *
2717 * Side effects:
2718 *      Whatever the command does.
2719 *
2720 *----------------------------------------------------------------------
2721 */
2722
2723int
2724TclInvoke(interp, argc, argv, flags)
2725    Tcl_Interp *interp;         /* Where to invoke the command. */
2726    int argc;                   /* Count of args. */
2727    register char **argv;       /* The arg strings; argv[0] is the name of
2728                                 * the command to invoke. */
2729    int flags;                  /* Combination of flags controlling the
2730                                 * call: TCL_INVOKE_HIDDEN and
2731                                 * TCL_INVOKE_NO_UNKNOWN. */
2732{
2733    register Tcl_Obj *objPtr;
2734    register int i;
2735    int length, result;
2736
2737    /*
2738     * This procedure generates an objv array for object arguments that hold
2739     * the argv strings. It starts out with stack-allocated space but uses
2740     * dynamically-allocated storage if needed.
2741     */
2742
2743#define NUM_ARGS 20
2744    Tcl_Obj *(objStorage[NUM_ARGS]);
2745    register Tcl_Obj **objv = objStorage;
2746
2747    /*
2748     * Create the object argument array "objv". Make sure objv is large
2749     * enough to hold the objc arguments plus 1 extra for the zero
2750     * end-of-objv word.
2751     */
2752
2753    if ((argc + 1) > NUM_ARGS) {
2754        objv = (Tcl_Obj **)
2755            ckalloc((unsigned)(argc + 1) * sizeof(Tcl_Obj *));
2756    }
2757
2758    for (i = 0;  i < argc;  i++) {
2759        length = strlen(argv[i]);
2760        objv[i] = Tcl_NewStringObj(argv[i], length);
2761        Tcl_IncrRefCount(objv[i]);
2762    }
2763    objv[argc] = 0;
2764
2765    /*
2766     * Use TclObjInterpProc to actually invoke the command.
2767     */
2768
2769    result = TclObjInvoke(interp, argc, objv, flags);
2770
2771    /*
2772     * Move the interpreter's object result to the string result,
2773     * then reset the object result.
2774     * FAILS IF OBJECT RESULT'S STRING REPRESENTATION CONTAINS NULLS.
2775     */
2776   
2777    Tcl_SetResult(interp,
2778            TclGetStringFromObj(Tcl_GetObjResult(interp), (int *) NULL),
2779            TCL_VOLATILE);
2780
2781    /*
2782     * Decrement the ref counts on the objv elements since we are done
2783     * with them.
2784     */
2785
2786    for (i = 0;  i < argc;  i++) {
2787        objPtr = objv[i];
2788        Tcl_DecrRefCount(objPtr);
2789    }
2790   
2791    /*
2792     * Free the objv array if malloc'ed storage was used.
2793     */
2794
2795    if (objv != objStorage) {
2796        ckfree((char *) objv);
2797    }
2798    return result;
2799#undef NUM_ARGS
2800}
2801
2802/*
2803 *----------------------------------------------------------------------
2804 *
2805 * TclGlobalInvoke --
2806 *
2807 *      Invokes a Tcl command, given an argv/argc, from either the
2808 *      exposed or hidden sets of commands in the given interpreter.
2809 *      NOTE: The command is invoked in the global stack frame of
2810 *      the interpreter, thus it cannot see any current state on
2811 *      the stack for that interpreter.
2812 *
2813 * Results:
2814 *      A standard Tcl result.
2815 *
2816 * Side effects:
2817 *      Whatever the command does.
2818 *
2819 *----------------------------------------------------------------------
2820 */
2821
2822int
2823TclGlobalInvoke(interp, argc, argv, flags)
2824    Tcl_Interp *interp;         /* Where to invoke the command. */
2825    int argc;                   /* Count of args. */
2826    register char **argv;       /* The arg strings; argv[0] is the name of
2827                                 * the command to invoke. */
2828    int flags;                  /* Combination of flags controlling the
2829                                 * call: TCL_INVOKE_HIDDEN and
2830                                 * TCL_INVOKE_NO_UNKNOWN. */
2831{
2832    register Interp *iPtr = (Interp *) interp;
2833    int result;
2834    CallFrame *savedVarFramePtr;
2835
2836    savedVarFramePtr = iPtr->varFramePtr;
2837    iPtr->varFramePtr = NULL;
2838    result = TclInvoke(interp, argc, argv, flags);
2839    iPtr->varFramePtr = savedVarFramePtr;
2840    return result;
2841}
2842
2843/*
2844 *----------------------------------------------------------------------
2845 *
2846 * TclObjInvokeGlobal --
2847 *
2848 *      Object version: Invokes a Tcl command, given an objv/objc, from
2849 *      either the exposed or hidden set of commands in the given
2850 *      interpreter.
2851 *      NOTE: The command is invoked in the global stack frame of the
2852 *      interpreter, thus it cannot see any current state on the
2853 *      stack of that interpreter.
2854 *
2855 * Results:
2856 *      A standard Tcl result.
2857 *
2858 * Side effects:
2859 *      Whatever the command does.
2860 *
2861 *----------------------------------------------------------------------
2862 */
2863
2864int
2865TclObjInvokeGlobal(interp, objc, objv, flags)
2866    Tcl_Interp *interp;         /* Interpreter in which command is
2867                                 * to be invoked. */
2868    int objc;                   /* Count of arguments. */
2869    Tcl_Obj *CONST objv[];      /* Argument value objects; objv[0]
2870                                 * points to the name of the
2871                                 * command to invoke. */
2872    int flags;                  /* Combination of flags controlling
2873                                 * the call: TCL_INVOKE_HIDDEN and
2874                                 * TCL_INVOKE_NO_UNKNOWN. */
2875{
2876    register Interp *iPtr = (Interp *) interp;
2877    int result;
2878    CallFrame *savedVarFramePtr;
2879
2880    savedVarFramePtr = iPtr->varFramePtr;
2881    iPtr->varFramePtr = NULL;
2882    result = TclObjInvoke(interp, objc, objv, flags);
2883    iPtr->varFramePtr = savedVarFramePtr;
2884    return result;
2885}
2886
2887/*
2888 *----------------------------------------------------------------------
2889 *
2890 * TclObjInvoke --
2891 *
2892 *      Invokes a Tcl command, given an objv/objc, from either the
2893 *      exposed or the hidden sets of commands in the given interpreter.
2894 *
2895 * Results:
2896 *      A standard Tcl object result.
2897 *
2898 * Side effects:
2899 *      Whatever the command does.
2900 *
2901 *----------------------------------------------------------------------
2902 */
2903
2904int
2905TclObjInvoke(interp, objc, objv, flags)
2906    Tcl_Interp *interp;         /* Interpreter in which command is
2907                                 * to be invoked. */
2908    int objc;                   /* Count of arguments. */
2909    Tcl_Obj *CONST objv[];      /* Argument value objects; objv[0]
2910                                 * points to the name of the
2911                                 * command to invoke. */
2912    int flags;                  /* Combination of flags controlling
2913                                 * the call: TCL_INVOKE_HIDDEN and
2914                                 * TCL_INVOKE_NO_UNKNOWN. */
2915{
2916    register Interp *iPtr = (Interp *) interp;
2917    Tcl_HashTable *hTblPtr;     /* Table of hidden commands. */
2918    char *cmdName;              /* Name of the command from objv[0]. */
2919    register Tcl_HashEntry *hPtr;
2920    Tcl_Command cmd;
2921    Command *cmdPtr;
2922    int localObjc;              /* Used to invoke "unknown" if the */
2923    Tcl_Obj **localObjv = NULL; /* command is not found. */
2924    register int i;
2925    int length, result;
2926    char *bytes;
2927
2928    if (interp == (Tcl_Interp *) NULL) {
2929        return TCL_ERROR;
2930    }
2931
2932    if ((objc < 1) || (objv == (Tcl_Obj **) NULL)) {
2933        Tcl_AppendToObj(Tcl_GetObjResult(interp),
2934                "illegal argument vector", -1);
2935        return TCL_ERROR;
2936    }
2937
2938    /*
2939     * THE FOLLOWING CODE FAILS IF THE STRING REP CONTAINS NULLS.
2940     */
2941   
2942    cmdName = Tcl_GetStringFromObj(objv[0], (int *) NULL);
2943    if (flags & TCL_INVOKE_HIDDEN) {
2944        /*
2945         * Find the table of hidden commands; error out if none.
2946         */
2947
2948        hTblPtr = (Tcl_HashTable *)
2949                Tcl_GetAssocData(interp, "tclHiddenCmds", NULL);
2950        if (hTblPtr == (Tcl_HashTable *) NULL) {
2951            badhiddenCmdToken:
2952            Tcl_ResetResult(interp);
2953            Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
2954                     "invalid hidden command name \"", cmdName, "\"",
2955                     (char *) NULL);
2956            return TCL_ERROR;
2957        }
2958        hPtr = Tcl_FindHashEntry(hTblPtr, cmdName);
2959
2960        /*
2961         * We never invoke "unknown" for hidden commands.
2962         */
2963       
2964        if (hPtr == NULL) {
2965            goto badhiddenCmdToken;
2966        }
2967        cmdPtr = (Command *) Tcl_GetHashValue(hPtr);
2968    } else {
2969        cmdPtr = NULL;
2970        cmd = Tcl_FindCommand(interp, cmdName,
2971                (Tcl_Namespace *) NULL, /*flags*/ TCL_GLOBAL_ONLY);
2972        if (cmd != (Tcl_Command) NULL) {
2973            cmdPtr = (Command *) cmd;
2974        }
2975        if (cmdPtr == NULL) {
2976            if (!(flags & TCL_INVOKE_NO_UNKNOWN)) {
2977                cmd = Tcl_FindCommand(interp, "unknown",
2978                        (Tcl_Namespace *) NULL, /*flags*/ TCL_GLOBAL_ONLY);
2979                if (cmd != (Tcl_Command) NULL) {
2980                    cmdPtr = (Command *) cmd;
2981                }
2982                if (cmdPtr != NULL) {
2983                    localObjc = (objc + 1);
2984                    localObjv = (Tcl_Obj **)
2985                        ckalloc((unsigned) (sizeof(Tcl_Obj *) * localObjc));
2986                    localObjv[0] = Tcl_NewStringObj("unknown", -1);
2987                    Tcl_IncrRefCount(localObjv[0]);
2988                    for (i = 0;  i < objc;  i++) {
2989                        localObjv[i+1] = objv[i];
2990                    }
2991                    objc = localObjc;
2992                    objv = localObjv;
2993                }
2994            }
2995
2996            /*
2997             * Check again if we found the command. If not, "unknown" is
2998             * not present and we cannot help, or the caller said not to
2999             * call "unknown" (they specified TCL_INVOKE_NO_UNKNOWN).
3000             */
3001
3002            if (cmdPtr == NULL) {
3003                Tcl_ResetResult(interp);
3004                Tcl_AppendStringsToObj(Tcl_GetObjResult(interp),
3005                        "invalid command name \"",  cmdName, "\"", 
3006                         (char *) NULL);
3007                return TCL_ERROR;
3008            }
3009        }
3010    }
3011
3012    /*
3013     * Invoke the command procedure. First reset the interpreter's string
3014     * and object results to their default empty values since they could
3015     * have gotten changed by earlier invocations.
3016     */
3017
3018    Tcl_ResetResult(interp);
3019    iPtr->cmdCount++;
3020    result = (*cmdPtr->objProc)(cmdPtr->objClientData, interp, objc, objv);
3021
3022    /*
3023     * If an error occurred, record information about what was being
3024     * executed when the error occurred.
3025     */
3026
3027    if ((result == TCL_ERROR) && !(iPtr->flags & ERR_ALREADY_LOGGED)) {
3028        Tcl_DString ds;
3029       
3030        Tcl_DStringInit(&ds);
3031        if (!(iPtr->flags & ERR_IN_PROGRESS)) {
3032            Tcl_DStringAppend(&ds, "\n    while invoking\n\"", -1);
3033        } else {
3034            Tcl_DStringAppend(&ds, "\n    invoked from within\n\"", -1);
3035        }
3036        for (i = 0;  i < objc;  i++) {
3037            bytes = Tcl_GetStringFromObj(objv[i], &length);
3038            Tcl_DStringAppend(&ds, bytes, length);
3039            if (i < (objc - 1)) {
3040                Tcl_DStringAppend(&ds, " ", -1);
3041            } else if (Tcl_DStringLength(&ds) > 100) {
3042                Tcl_DStringSetLength(&ds, 100);
3043                Tcl_DStringAppend(&ds, "...", -1);
3044                break;
3045            }
3046        }
3047       
3048        Tcl_DStringAppend(&ds, "\"", -1);
3049        Tcl_AddObjErrorInfo(interp, Tcl_DStringValue(&ds), -1);
3050        Tcl_DStringFree(&ds);
3051        iPtr->flags &= ~ERR_ALREADY_LOGGED;
3052    }
3053
3054    /*
3055     * Free any locally allocated storage used to call "unknown".
3056     */
3057
3058    if (localObjv != (Tcl_Obj **) NULL) {
3059        ckfree((char *) localObjv);
3060    }
3061    return result;
3062}
3063
3064/*
3065 *--------------------------------------------------------------
3066 *
3067 * Tcl_ExprString --
3068 *
3069 *      Evaluate an expression in a string and return its value in string
3070 *      form.
3071 *
3072 * Results:
3073 *      A standard Tcl result. If the result is TCL_OK, then the
3074 *      interpreter's result is set to the string value of the
3075 *      expression. If the result is TCL_OK, then interp->result
3076 *      contains an error message.
3077 *
3078 * Side effects:
3079 *      A Tcl object is allocated to hold a copy of the expression string.
3080 *      This expression object is passed to Tcl_ExprObj and then
3081 *      deallocated.
3082 *
3083 *--------------------------------------------------------------
3084 */
3085
3086int
3087Tcl_ExprString(interp, string)
3088    Tcl_Interp *interp;         /* Context in which to evaluate the
3089                                 * expression. */
3090    char *string;               /* Expression to evaluate. */
3091{
3092    register Tcl_Obj *exprPtr;
3093    Tcl_Obj *resultPtr;
3094    int length = strlen(string);
3095    char buf[100];
3096    int result = TCL_OK;
3097
3098    if (length > 0) {
3099        TclNewObj(exprPtr);
3100        TclInitStringRep(exprPtr, string, length);
3101        Tcl_IncrRefCount(exprPtr);
3102
3103        result = Tcl_ExprObj(interp, exprPtr, &resultPtr);
3104        if (result == TCL_OK) {
3105            /*
3106             * Set the interpreter's string result from the result object.
3107             */
3108           
3109            if (resultPtr->typePtr == &tclIntType) {
3110                sprintf(buf, "%ld", resultPtr->internalRep.longValue);
3111                Tcl_SetResult(interp, buf, TCL_VOLATILE);
3112            } else if (resultPtr->typePtr == &tclDoubleType) {
3113                Tcl_PrintDouble((Tcl_Interp *) NULL,
3114                        resultPtr->internalRep.doubleValue, buf);
3115                Tcl_SetResult(interp, buf, TCL_VOLATILE);
3116            } else {
3117                /*
3118                 * Set interpreter's string result from the result object.
3119                 * FAILS IF OBJECT RESULT'S STRING REPRESENTATION HAS NULLS.
3120                 */
3121           
3122                Tcl_SetResult(interp,
3123                        TclGetStringFromObj(resultPtr, (int *) NULL),
3124                        TCL_VOLATILE);
3125            }
3126            Tcl_DecrRefCount(resultPtr);  /* discard the result object */
3127        } else {
3128            /*
3129             * Move the interpreter's object result to the string result,
3130             * then reset the object result.
3131             * FAILS IF OBJECT RESULT'S STRING REPRESENTATION HAS NULLS.
3132             */
3133           
3134            Tcl_SetResult(interp,
3135                    TclGetStringFromObj(Tcl_GetObjResult(interp),
3136                            (int *) NULL),
3137                    TCL_VOLATILE);
3138        }
3139        Tcl_DecrRefCount(exprPtr); /* discard the expression object */
3140    } else {
3141        /*
3142         * An empty string. Just set the interpreter's result to 0.
3143         */
3144       
3145        Tcl_SetResult(interp, "0", TCL_VOLATILE);
3146    }
3147    return result;
3148}
3149
3150/*
3151 *--------------------------------------------------------------
3152 *
3153 * Tcl_ExprObj --
3154 *
3155 *      Evaluate an expression in a Tcl_Obj.
3156 *
3157 * Results:
3158 *      A standard Tcl object result. If the result is other than TCL_OK,
3159 *      then the interpreter's result contains an error message. If the
3160 *      result is TCL_OK, then a pointer to the expression's result value
3161 *      object is stored in resultPtrPtr. In that case, the object's ref
3162 *      count is incremented to reflect the reference returned to the
3163 *      caller; the caller is then responsible for the resulting object
3164 *      and must, for example, decrement the ref count when it is finished
3165 *      with the object.
3166 *
3167 * Side effects:
3168 *      Any side effects caused by subcommands in the expression, if any.
3169 *      The interpreter result is not modified unless there is an error.
3170 *
3171 *--------------------------------------------------------------
3172 */
3173
3174int
3175Tcl_ExprObj(interp, objPtr, resultPtrPtr)
3176    Tcl_Interp *interp;         /* Context in which to evaluate the
3177                                 * expression. */
3178    register Tcl_Obj *objPtr;   /* Points to Tcl object containing
3179                                 * expression to evaluate. */
3180    Tcl_Obj **resultPtrPtr;     /* Where the Tcl_Obj* that is the expression
3181                                 * result is stored if no errors occur. */
3182{
3183    Interp *iPtr = (Interp *) interp;
3184    CompileEnv compEnv;         /* Compilation environment structure
3185                                 * allocated in frame. */
3186    register ByteCode *codePtr = NULL;
3187                                /* Tcl Internal type of bytecode.
3188                                 * Initialized to avoid compiler warning. */
3189    AuxData *auxDataPtr;
3190    Interp dummy;
3191    Tcl_Obj *saveObjPtr;
3192    char *string;
3193    int result;
3194    int i;
3195
3196    /*
3197     * Get the ByteCode from the object. If it exists, make sure it hasn't
3198     * been invalidated by, e.g., someone redefining a command with a
3199     * compile procedure (this might make the compiled code wrong). If
3200     * necessary, convert the object to be a ByteCode object and compile it.
3201     * Also, if the code was compiled in/for a different interpreter, we
3202     * recompile it.
3203     *
3204     * Precompiled expressions, however, are immutable and therefore
3205     * they are not recompiled, even if the epoch has changed.
3206     *
3207     * THIS FAILS IF THE OBJECT'S STRING REP HAS A NULL BYTE.
3208     */
3209
3210    if (objPtr->typePtr == &tclByteCodeType) {
3211        codePtr = (ByteCode *) objPtr->internalRep.otherValuePtr;
3212        if ((codePtr->iPtr != iPtr)
3213                || (codePtr->compileEpoch != iPtr->compileEpoch)) {
3214            if (codePtr->flags & TCL_BYTECODE_PRECOMPILED) {
3215                if (codePtr->iPtr != iPtr) {
3216                    panic("Tcl_ExprObj: compiled expression jumped interps");
3217                }
3218                codePtr->compileEpoch = iPtr->compileEpoch;
3219            } else {
3220                tclByteCodeType.freeIntRepProc(objPtr);
3221                objPtr->typePtr = (Tcl_ObjType *) NULL;
3222            }
3223        }
3224    }
3225    if (objPtr->typePtr != &tclByteCodeType) {
3226        int length;
3227        string = Tcl_GetStringFromObj(objPtr, &length);
3228        TclInitCompileEnv(interp, &compEnv, string);
3229        result = TclCompileExpr(interp, string, string + length,
3230                /*flags*/ 0, &compEnv);
3231        if (result == TCL_OK) {
3232            /*
3233             * If the expression yielded no instructions (e.g., was empty),
3234             * push an integer zero object as the expressions's result.
3235             */
3236           
3237            if (compEnv.codeNext == NULL) {
3238                int objIndex = TclObjIndexForString("0", 0,
3239                        /*allocStrRep*/ 0, /*inHeap*/ 0, &compEnv);
3240                Tcl_Obj *objPtr = compEnv.objArrayPtr[objIndex];
3241
3242                Tcl_InvalidateStringRep(objPtr);
3243                objPtr->internalRep.longValue = 0;
3244                objPtr->typePtr = &tclIntType;
3245               
3246                TclEmitPush(objIndex, &compEnv);
3247            }
3248           
3249            /*
3250             * Add done instruction at the end of the instruction sequence.
3251             */
3252           
3253            TclEmitOpcode(INST_DONE, &compEnv);
3254           
3255            TclInitByteCodeObj(objPtr, &compEnv);
3256            codePtr = (ByteCode *) objPtr->internalRep.otherValuePtr;
3257            if (tclTraceCompile == 2) {
3258                TclPrintByteCodeObj(interp, objPtr);
3259            }
3260            TclFreeCompileEnv(&compEnv);
3261        } else {
3262            /*
3263             * Compilation errors. Decrement the ref counts on any objects
3264             * in the object array before freeing the compilation
3265             * environment.
3266             */
3267           
3268            for (i = 0;  i < compEnv.objArrayNext;  i++) {
3269                Tcl_Obj *elemPtr = compEnv.objArrayPtr[i];
3270                Tcl_DecrRefCount(elemPtr);
3271            }
3272
3273            auxDataPtr = compEnv.auxDataArrayPtr;
3274            for (i = 0;  i < compEnv.auxDataArrayNext;  i++) {
3275                if (auxDataPtr->type->freeProc != NULL) {
3276                    auxDataPtr->type->freeProc(auxDataPtr->clientData);
3277                }
3278                auxDataPtr++;
3279            }
3280            TclFreeCompileEnv(&compEnv);
3281            return result;
3282        }
3283    }
3284
3285    /*
3286     * Execute the expression after first saving the interpreter's result.
3287     */
3288   
3289    dummy.objResultPtr = Tcl_NewObj();
3290    Tcl_IncrRefCount(dummy.objResultPtr);
3291    if (interp->freeProc == 0) {
3292        dummy.freeProc = (Tcl_FreeProc *) 0;
3293        dummy.result = "";
3294        Tcl_SetResult((Tcl_Interp *) &dummy, interp->result,
3295                TCL_VOLATILE);
3296    } else {
3297        dummy.freeProc = interp->freeProc;
3298        dummy.result = interp->result;
3299        interp->freeProc = (Tcl_FreeProc *) 0;
3300    }
3301   
3302    saveObjPtr = Tcl_GetObjResult(interp);
3303    Tcl_IncrRefCount(saveObjPtr);
3304   
3305    /*
3306     * Increment the code's ref count while it is being executed. If
3307     * afterwards no references to it remain, free the code.
3308     */
3309   
3310    codePtr->refCount++;
3311    result = TclExecuteByteCode(interp, codePtr);
3312    codePtr->refCount--;
3313    if (codePtr->refCount <= 0) {
3314        TclCleanupByteCode(codePtr);
3315    }
3316   
3317    /*
3318     * If the expression evaluated successfully, store a pointer to its
3319     * value object in resultPtrPtr then restore the old interpreter result.
3320     * We increment the object's ref count to reflect the reference that we
3321     * are returning to the caller. We also decrement the ref count of the
3322     * interpreter's result object after calling Tcl_SetResult since we
3323     * next store into that field directly.
3324     */
3325   
3326    if (result == TCL_OK) {
3327        *resultPtrPtr = iPtr->objResultPtr;
3328        Tcl_IncrRefCount(iPtr->objResultPtr);
3329       
3330        Tcl_SetResult(interp, dummy.result,
3331                ((dummy.freeProc == 0) ? TCL_VOLATILE : dummy.freeProc));
3332        Tcl_DecrRefCount(iPtr->objResultPtr);
3333        iPtr->objResultPtr = saveObjPtr;
3334    } else {
3335        Tcl_DecrRefCount(saveObjPtr);
3336        Tcl_FreeResult((Tcl_Interp *) &dummy);
3337    }
3338
3339    Tcl_DecrRefCount(dummy.objResultPtr);
3340    dummy.objResultPtr = NULL;
3341    return result;
3342}
3343
3344/*
3345 *----------------------------------------------------------------------
3346 *
3347 * Tcl_CreateTrace --
3348 *
3349 *      Arrange for a procedure to be called to trace command execution.
3350 *
3351 * Results:
3352 *      The return value is a token for the trace, which may be passed
3353 *      to Tcl_DeleteTrace to eliminate the trace.
3354 *
3355 * Side effects:
3356 *      From now on, proc will be called just before a command procedure
3357 *      is called to execute a Tcl command.  Calls to proc will have the
3358 *      following form:
3359 *
3360 *      void
3361 *      proc(clientData, interp, level, command, cmdProc, cmdClientData,
3362 *              argc, argv)
3363 *          ClientData clientData;
3364 *          Tcl_Interp *interp;
3365 *          int level;
3366 *          char *command;
3367 *          int (*cmdProc)();
3368 *          ClientData cmdClientData;
3369 *          int argc;
3370 *          char **argv;
3371 *      {
3372 *      }
3373 *
3374 *      The clientData and interp arguments to proc will be the same
3375 *      as the corresponding arguments to this procedure.  Level gives
3376 *      the nesting level of command interpretation for this interpreter
3377 *      (0 corresponds to top level).  Command gives the ASCII text of
3378 *      the raw command, cmdProc and cmdClientData give the procedure that
3379 *      will be called to process the command and the ClientData value it
3380 *      will receive, and argc and argv give the arguments to the
3381 *      command, after any argument parsing and substitution.  Proc
3382 *      does not return a value.
3383 *
3384 *----------------------------------------------------------------------
3385 */
3386
3387Tcl_Trace
3388Tcl_CreateTrace(interp, level, proc, clientData)
3389    Tcl_Interp *interp;         /* Interpreter in which to create trace. */
3390    int level;                  /* Only call proc for commands at nesting
3391                                 * level<=argument level (1=>top level). */
3392    Tcl_CmdTraceProc *proc;     /* Procedure to call before executing each
3393                                 * command. */
3394    ClientData clientData;      /* Arbitrary value word to pass to proc. */
3395{
3396    register Trace *tracePtr;
3397    register Interp *iPtr = (Interp *) interp;
3398
3399    /*
3400     * Invalidate existing compiled code for this interpreter and arrange
3401     * (by setting the DONT_COMPILE_CMDS_INLINE flag) that when compiling
3402     * new code, no commands will be compiled inline (i.e., into an inline
3403     * sequence of instructions). We do this because commands that were
3404     * compiled inline will never result in a command trace being called.
3405     */
3406
3407    iPtr->compileEpoch++;
3408    iPtr->flags |= DONT_COMPILE_CMDS_INLINE;
3409
3410    tracePtr = (Trace *) ckalloc(sizeof(Trace));
3411    tracePtr->level = level;
3412    tracePtr->proc = proc;
3413    tracePtr->clientData = clientData;
3414    tracePtr->nextPtr = iPtr->tracePtr;
3415    iPtr->tracePtr = tracePtr;
3416
3417    return (Tcl_Trace) tracePtr;
3418}
3419
3420/*
3421 *----------------------------------------------------------------------
3422 *
3423 * Tcl_DeleteTrace --
3424 *
3425 *      Remove a trace.
3426 *
3427 * Results:
3428 *      None.
3429 *
3430 * Side effects:
3431 *      From now on there will be no more calls to the procedure given
3432 *      in trace.
3433 *
3434 *----------------------------------------------------------------------
3435 */
3436
3437void
3438Tcl_DeleteTrace(interp, trace)
3439    Tcl_Interp *interp;         /* Interpreter that contains trace. */
3440    Tcl_Trace trace;            /* Token for trace (returned previously by
3441                                 * Tcl_CreateTrace). */
3442{
3443    register Interp *iPtr = (Interp *) interp;
3444    register Trace *tracePtr = (Trace *) trace;
3445    register Trace *tracePtr2;
3446
3447    if (iPtr->tracePtr == tracePtr) {
3448        iPtr->tracePtr = tracePtr->nextPtr;
3449        ckfree((char *) tracePtr);
3450    } else {
3451        for (tracePtr2 = iPtr->tracePtr; tracePtr2 != NULL;
3452                tracePtr2 = tracePtr2->nextPtr) {
3453            if (tracePtr2->nextPtr == tracePtr) {
3454                tracePtr2->nextPtr = tracePtr->nextPtr;
3455                ckfree((char *) tracePtr);
3456                break;
3457            }
3458        }
3459    }
3460
3461    if (iPtr->tracePtr == NULL) {
3462        /*
3463         * When compiling new code, allow commands to be compiled inline.
3464         */
3465
3466        iPtr->flags &= ~DONT_COMPILE_CMDS_INLINE;
3467    }
3468}
3469
3470/*
3471 *----------------------------------------------------------------------
3472 *
3473 * Tcl_AddErrorInfo --
3474 *
3475 *      Add information to the "errorInfo" variable that describes the
3476 *      current error.
3477 *
3478 * Results:
3479 *      None.
3480 *
3481 * Side effects:
3482 *      The contents of message are added to the "errorInfo" variable.
3483 *      If Tcl_Eval has been called since the current value of errorInfo
3484 *      was set, errorInfo is cleared before adding the new message.
3485 *      If we are just starting to log an error, errorInfo is initialized
3486 *      from the error message in the interpreter's result.
3487 *
3488 *----------------------------------------------------------------------
3489 */
3490
3491void
3492Tcl_AddErrorInfo(interp, message)
3493    Tcl_Interp *interp;         /* Interpreter to which error information
3494                                 * pertains. */
3495    char *message;              /* Message to record. */
3496{
3497    Tcl_AddObjErrorInfo(interp, message, -1);
3498}
3499
3500/*
3501 *----------------------------------------------------------------------
3502 *
3503 * Tcl_AddObjErrorInfo --
3504 *
3505 *      Add information to the "errorInfo" variable that describes the
3506 *      current error. This routine differs from Tcl_AddErrorInfo by
3507 *      taking a byte pointer and length.
3508 *
3509 * Results:
3510 *      None.
3511 *
3512 * Side effects:
3513 *      "length" bytes from "message" are added to the "errorInfo" variable.
3514 *      If "length" is negative, use bytes up to the first NULL byte.
3515 *      If Tcl_EvalObj has been called since the current value of errorInfo
3516 *      was set, errorInfo is cleared before adding the new message.
3517 *      If we are just starting to log an error, errorInfo is initialized
3518 *      from the error message in the interpreter's result.
3519 *
3520 *----------------------------------------------------------------------
3521 */
3522
3523void
3524Tcl_AddObjErrorInfo(interp, message, length)
3525    Tcl_Interp *interp;         /* Interpreter to which error information
3526                                 * pertains. */
3527    char *message;              /* Points to the first byte of an array of
3528                                 * bytes of the message. */
3529    register int length;        /* The number of bytes in the message.
3530                                 * If < 0, then append all bytes up to a
3531                                 * NULL byte. */
3532{
3533    register Interp *iPtr = (Interp *) interp;
3534    Tcl_Obj *namePtr, *messagePtr;
3535   
3536    /*
3537     * If we are just starting to log an error, errorInfo is initialized
3538     * from the error message in the interpreter's result.
3539     */
3540
3541    namePtr = Tcl_NewStringObj("errorInfo", -1);
3542    Tcl_IncrRefCount(namePtr);
3543   
3544    if (!(iPtr->flags & ERR_IN_PROGRESS)) { /* just starting to log error */
3545        iPtr->flags |= ERR_IN_PROGRESS;
3546
3547        if (iPtr->result[0] == 0) {
3548            (void) Tcl_ObjSetVar2(interp, namePtr, (Tcl_Obj *) NULL,
3549                    iPtr->objResultPtr, TCL_GLOBAL_ONLY);
3550        } else {                /* use the string result */
3551            Tcl_SetVar2(interp, "errorInfo", (char *) NULL, interp->result,
3552                    TCL_GLOBAL_ONLY);
3553        }
3554
3555        /*
3556         * If the errorCode variable wasn't set by the code that generated
3557         * the error, set it to "NONE".
3558         */
3559
3560        if (!(iPtr->flags & ERROR_CODE_SET)) {
3561            (void) Tcl_SetVar2(interp, "errorCode", (char *) NULL, "NONE",
3562                    TCL_GLOBAL_ONLY);
3563        }
3564    }
3565
3566    /*
3567     * Now append "message" to the end of errorInfo.
3568     */
3569
3570    if (length != 0) {
3571        messagePtr = Tcl_NewStringObj(message, length);
3572        Tcl_IncrRefCount(messagePtr);
3573        Tcl_ObjSetVar2(interp, namePtr, (Tcl_Obj *) NULL, messagePtr,
3574                (TCL_GLOBAL_ONLY | TCL_APPEND_VALUE));
3575        Tcl_DecrRefCount(messagePtr); /* free msg object appended above */
3576    }
3577
3578    Tcl_DecrRefCount(namePtr);    /* free the name object */
3579}
3580
3581/*
3582 *----------------------------------------------------------------------
3583 *
3584 * Tcl_VarEval --
3585 *
3586 *      Given a variable number of string arguments, concatenate them
3587 *      all together and execute the result as a Tcl command.
3588 *
3589 * Results:
3590 *      A standard Tcl return result.  An error message or other
3591 *      result may be left in interp->result.
3592 *
3593 * Side effects:
3594 *      Depends on what was done by the command.
3595 *
3596 *----------------------------------------------------------------------
3597 */
3598        /* VARARGS2 */ /* ARGSUSED */
3599int
3600Tcl_VarEval TCL_VARARGS_DEF(Tcl_Interp *,arg1)
3601{
3602    va_list argList;
3603    Tcl_DString buf;
3604    char *string;
3605    Tcl_Interp *interp;
3606    int result;
3607
3608    /*
3609     * Copy the strings one after the other into a single larger
3610     * string.  Use stack-allocated space for small commands, but if
3611     * the command gets too large than call ckalloc to create the
3612     * space.
3613     */
3614
3615    interp = TCL_VARARGS_START(Tcl_Interp *,arg1,argList);
3616    Tcl_DStringInit(&buf);
3617    while (1) {
3618        string = va_arg(argList, char *);
3619        if (string == NULL) {
3620            break;
3621        }
3622        Tcl_DStringAppend(&buf, string, -1);
3623    }
3624    va_end(argList);
3625
3626    result = Tcl_Eval(interp, Tcl_DStringValue(&buf));
3627    Tcl_DStringFree(&buf);
3628    return result;
3629}
3630
3631/*
3632 *----------------------------------------------------------------------
3633 *
3634 * Tcl_GlobalEval --
3635 *
3636 *      Evaluate a command at global level in an interpreter.
3637 *
3638 * Results:
3639 *      A standard Tcl result is returned, and interp->result is
3640 *      modified accordingly.
3641 *
3642 * Side effects:
3643 *      The command string is executed in interp, and the execution
3644 *      is carried out in the variable context of global level (no
3645 *      procedures active), just as if an "uplevel #0" command were
3646 *      being executed.
3647 *
3648 *----------------------------------------------------------------------
3649 */
3650
3651int
3652Tcl_GlobalEval(interp, command)
3653    Tcl_Interp *interp;         /* Interpreter in which to evaluate command. */
3654    char *command;              /* Command to evaluate. */
3655{
3656    register Interp *iPtr = (Interp *) interp;
3657    int result;
3658    CallFrame *savedVarFramePtr;
3659
3660    savedVarFramePtr = iPtr->varFramePtr;
3661    iPtr->varFramePtr = NULL;
3662    result = Tcl_Eval(interp, command);
3663    iPtr->varFramePtr = savedVarFramePtr;
3664    return result;
3665}
3666
3667/*
3668 *----------------------------------------------------------------------
3669 *
3670 * Tcl_GlobalEvalObj --
3671 *
3672 *      Execute Tcl commands stored in a Tcl object at global level in
3673 *      an interpreter. These commands are compiled into bytecodes if
3674 *      necessary.
3675 *
3676 * Results:
3677 *      A standard Tcl result is returned, and the interpreter's result
3678 *      contains a Tcl object value to supplement the return code.
3679 *
3680 * Side effects:
3681 *      The object is converted, if necessary, to a ByteCode object that
3682 *      holds the bytecode instructions for the commands. Executing the
3683 *      commands will almost certainly have side effects that depend on
3684 *      those commands.
3685 *
3686 *      The commands are executed in interp, and the execution
3687 *      is carried out in the variable context of global level (no
3688 *      procedures active), just as if an "uplevel #0" command were
3689 *      being executed.
3690 *
3691 *----------------------------------------------------------------------
3692 */
3693
3694int
3695Tcl_GlobalEvalObj(interp, objPtr)
3696    Tcl_Interp *interp;         /* Interpreter in which to evaluate
3697                                 * commands. */
3698    Tcl_Obj *objPtr;            /* Pointer to object containing commands
3699                                 * to execute. */
3700{
3701    register Interp *iPtr = (Interp *) interp;
3702    int result;
3703    CallFrame *savedVarFramePtr;
3704
3705    savedVarFramePtr = iPtr->varFramePtr;
3706    iPtr->varFramePtr = NULL;
3707    result = Tcl_EvalObj(interp, objPtr);
3708    iPtr->varFramePtr = savedVarFramePtr;
3709    return result;
3710}
3711
3712/*
3713 *----------------------------------------------------------------------
3714 *
3715 * Tcl_SetRecursionLimit --
3716 *
3717 *      Set the maximum number of recursive calls that may be active
3718 *      for an interpreter at once.
3719 *
3720 * Results:
3721 *      The return value is the old limit on nesting for interp.
3722 *
3723 * Side effects:
3724 *      None.
3725 *
3726 *----------------------------------------------------------------------
3727 */
3728
3729int
3730Tcl_SetRecursionLimit(interp, depth)
3731    Tcl_Interp *interp;                 /* Interpreter whose nesting limit
3732                                         * is to be set. */
3733    int depth;                          /* New value for maximimum depth. */
3734{
3735    Interp *iPtr = (Interp *) interp;
3736    int old;
3737
3738    old = iPtr->maxNestingDepth;
3739    if (depth > 0) {
3740        iPtr->maxNestingDepth = depth;
3741    }
3742    return old;
3743}
3744
3745/*
3746 *----------------------------------------------------------------------
3747 *
3748 * Tcl_AllowExceptions --
3749 *
3750 *      Sets a flag in an interpreter so that exceptions can occur
3751 *      in the next call to Tcl_Eval without them being turned into
3752 *      errors.
3753 *
3754 * Results:
3755 *      None.
3756 *
3757 * Side effects:
3758 *      The TCL_ALLOW_EXCEPTIONS flag gets set in the interpreter's
3759 *      evalFlags structure.  See the reference documentation for
3760 *      more details.
3761 *
3762 *----------------------------------------------------------------------
3763 */
3764
3765void
3766Tcl_AllowExceptions(interp)
3767    Tcl_Interp *interp;         /* Interpreter in which to set flag. */
3768{
3769    Interp *iPtr = (Interp *) interp;
3770
3771    iPtr->evalFlags |= TCL_ALLOW_EXCEPTIONS;
3772}
3773
Note: See TracBrowser for help on using the repository browser.