4 * Contains support for namespaces, which provide a separate context of
5 * commands and global variables. The global :: namespace is the
6 * traditional Tcl "global" scope. Other namespaces are created as
7 * children of the global namespace. These other namespaces contain
8 * special-purpose commands and variables for packages.
10 * Copyright (c) 1993-1997 Lucent Technologies.
11 * Copyright (c) 1997 Sun Microsystems, Inc.
12 * Copyright (c) 1998-1999 by Scriptics Corporation.
13 * Copyright (c) 2002-2005 Donal K. Fellows.
14 * Copyright (c) 2006 Neil Madden.
15 * Contributions from Don Porter, NIST, 2007. (not subject to US copyright)
17 * Originally implemented by
19 * Bell Labs Innovations for Lucent Technologies
20 * mmclennan@lucent.com
22 * See the file "license.terms" for information on usage and redistribution of
23 * this file, and for a DISCLAIMER OF ALL WARRANTIES.
27 #include "tclCompile.h" /* for TclLogCommandInfo visibility */
30 * Thread-local storage used to avoid having a global lock on data that is not
31 * limited to a single interpreter.
34 typedef struct ThreadSpecificData {
35 long numNsCreated; /* Count of the number of namespaces created
36 * within the thread. This value is used as a
37 * unique id for each namespace. Cannot be
38 * per-interp because the nsId is used to
39 * distinguish objects which can be passed
40 * around between interps in the same thread,
41 * but does not need to be global because
42 * object internal reps are always per-thread
46 static Tcl_ThreadDataKey dataKey;
49 * This structure contains a cached pointer to a namespace that is the result
50 * of resolving the namespace's name in some other namespace. It is the
51 * internal representation for a nsName object. It contains the pointer along
52 * with some information that is used to check the cached pointer's validity.
55 typedef struct ResolvedNsName {
56 Namespace *nsPtr; /* A cached pointer to the Namespace that the
57 * name resolved to. */
58 Namespace *refNsPtr; /* Points to the namespace context in which
59 * the name was resolved. NULL if the name is
60 * fully qualified and thus the resolution
61 * does not depend on the context. */
62 int refCount; /* Reference count: 1 for each nsName object
63 * that has a pointer to this ResolvedNsName
64 * structure as its internal rep. This
65 * structure can be freed when refCount
70 * Declarations for functions local to this file:
73 static void DeleteImportedCmd(ClientData clientData);
74 static int DoImport(Tcl_Interp *interp,
75 Namespace *nsPtr, Tcl_HashEntry *hPtr,
76 const char *cmdName, const char *pattern,
77 Namespace *importNsPtr, int allowOverwrite);
78 static void DupNsNameInternalRep(Tcl_Obj *objPtr,Tcl_Obj *copyPtr);
79 static char * ErrorCodeRead(ClientData clientData,Tcl_Interp *interp,
80 const char *name1, const char *name2, int flags);
81 static char * ErrorInfoRead(ClientData clientData,Tcl_Interp *interp,
82 const char *name1, const char *name2, int flags);
83 static char * EstablishErrorCodeTraces(ClientData clientData,
84 Tcl_Interp *interp, const char *name1,
85 const char *name2, int flags);
86 static char * EstablishErrorInfoTraces(ClientData clientData,
87 Tcl_Interp *interp, const char *name1,
88 const char *name2, int flags);
89 static void FreeNsNameInternalRep(Tcl_Obj *objPtr);
90 static int GetNamespaceFromObj(Tcl_Interp *interp,
91 Tcl_Obj *objPtr, Tcl_Namespace **nsPtrPtr);
92 static int InvokeImportedCmd(ClientData clientData,
93 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
94 static int InvokeImportedNRCmd(ClientData clientData,
95 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
96 static int NamespaceChildrenCmd(ClientData dummy,
97 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
98 static int NamespaceCodeCmd(ClientData dummy, Tcl_Interp *interp,
99 int objc, Tcl_Obj *const objv[]);
100 static int NamespaceCurrentCmd(ClientData dummy,
101 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
102 static int NamespaceDeleteCmd(ClientData dummy,Tcl_Interp *interp,
103 int objc, Tcl_Obj *const objv[]);
104 static int NamespaceEvalCmd(ClientData dummy, Tcl_Interp *interp,
105 int objc, Tcl_Obj *const objv[]);
106 static int NRNamespaceEvalCmd(ClientData dummy,
107 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
108 static int NamespaceExistsCmd(ClientData dummy,Tcl_Interp *interp,
109 int objc, Tcl_Obj *const objv[]);
110 static int NamespaceExportCmd(ClientData dummy,Tcl_Interp *interp,
111 int objc, Tcl_Obj *const objv[]);
112 static int NamespaceForgetCmd(ClientData dummy,Tcl_Interp *interp,
113 int objc, Tcl_Obj *const objv[]);
114 static void NamespaceFree(Namespace *nsPtr);
115 static int NamespaceImportCmd(ClientData dummy,Tcl_Interp *interp,
116 int objc, Tcl_Obj *const objv[]);
117 static int NamespaceInscopeCmd(ClientData dummy,
118 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
119 static int NRNamespaceInscopeCmd(ClientData dummy,
120 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
121 static int NamespaceOriginCmd(ClientData dummy,Tcl_Interp *interp,
122 int objc, Tcl_Obj *const objv[]);
123 static int NamespaceParentCmd(ClientData dummy,Tcl_Interp *interp,
124 int objc, Tcl_Obj *const objv[]);
125 static int NamespacePathCmd(ClientData dummy, Tcl_Interp *interp,
126 int objc, Tcl_Obj *const objv[]);
127 static int NamespaceQualifiersCmd(ClientData dummy,
128 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
129 static int NamespaceTailCmd(ClientData dummy, Tcl_Interp *interp,
130 int objc, Tcl_Obj *const objv[]);
131 static int NamespaceUpvarCmd(ClientData dummy, Tcl_Interp *interp,
132 int objc, Tcl_Obj *const objv[]);
133 static int NamespaceUnknownCmd(ClientData dummy,
134 Tcl_Interp *interp,int objc,Tcl_Obj *const objv[]);
135 static int NamespaceWhichCmd(ClientData dummy, Tcl_Interp *interp,
136 int objc, Tcl_Obj *const objv[]);
137 static int SetNsNameFromAny(Tcl_Interp *interp, Tcl_Obj *objPtr);
138 static void UnlinkNsPath(Namespace *nsPtr);
140 static Tcl_NRPostProc NsEval_Callback;
143 * This structure defines a Tcl object type that contains a namespace
144 * reference. It is used in commands that take the name of a namespace as an
145 * argument. The namespace reference is resolved, and the result in cached in
149 static const Tcl_ObjType nsNameType = {
150 "nsName", /* the type's name */
151 FreeNsNameInternalRep, /* freeIntRepProc */
152 DupNsNameInternalRep, /* dupIntRepProc */
153 NULL, /* updateStringProc */
154 SetNsNameFromAny /* setFromAnyProc */
158 * Array of values describing how to implement each standard subcommand of the
159 * "namespace" command.
162 static const EnsembleImplMap defaultNamespaceMap[] = {
163 {"children", NamespaceChildrenCmd, TclCompileBasic0To2ArgCmd, NULL, NULL, 0},
164 {"code", NamespaceCodeCmd, TclCompileNamespaceCodeCmd, NULL, NULL, 0},
165 {"current", NamespaceCurrentCmd, TclCompileNamespaceCurrentCmd, NULL, NULL, 0},
166 {"delete", NamespaceDeleteCmd, TclCompileBasicMin0ArgCmd, NULL, NULL, 0},
167 {"ensemble", TclNamespaceEnsembleCmd, NULL, NULL, NULL, 0},
168 {"eval", NamespaceEvalCmd, NULL, NRNamespaceEvalCmd, NULL, 0},
169 {"exists", NamespaceExistsCmd, TclCompileBasic1ArgCmd, NULL, NULL, 0},
170 {"export", NamespaceExportCmd, TclCompileBasicMin0ArgCmd, NULL, NULL, 0},
171 {"forget", NamespaceForgetCmd, TclCompileBasicMin0ArgCmd, NULL, NULL, 0},
172 {"import", NamespaceImportCmd, TclCompileBasicMin0ArgCmd, NULL, NULL, 0},
173 {"inscope", NamespaceInscopeCmd, NULL, NRNamespaceInscopeCmd, NULL, 0},
174 {"origin", NamespaceOriginCmd, TclCompileNamespaceOriginCmd, NULL, NULL, 0},
175 {"parent", NamespaceParentCmd, TclCompileBasic0Or1ArgCmd, NULL, NULL, 0},
176 {"path", NamespacePathCmd, TclCompileBasic0Or1ArgCmd, NULL, NULL, 0},
177 {"qualifiers", NamespaceQualifiersCmd, TclCompileNamespaceQualifiersCmd, NULL, NULL, 0},
178 {"tail", NamespaceTailCmd, TclCompileNamespaceTailCmd, NULL, NULL, 0},
179 {"unknown", NamespaceUnknownCmd, TclCompileBasic0Or1ArgCmd, NULL, NULL, 0},
180 {"upvar", NamespaceUpvarCmd, TclCompileNamespaceUpvarCmd, NULL, NULL, 0},
181 {"which", NamespaceWhichCmd, TclCompileNamespaceWhichCmd, NULL, NULL, 0},
182 {NULL, NULL, NULL, NULL, NULL, 0}
186 *----------------------------------------------------------------------
188 * TclInitNamespaceSubsystem --
190 * This function is called to initialize all the structures that are used
191 * by namespaces on a per-process basis.
199 *----------------------------------------------------------------------
203 TclInitNamespaceSubsystem(void)
206 * Does nothing for now.
211 *----------------------------------------------------------------------
213 * Tcl_GetCurrentNamespace --
215 * Returns a pointer to an interpreter's currently active namespace.
218 * Returns a pointer to the interpreter's current namespace.
223 *----------------------------------------------------------------------
227 Tcl_GetCurrentNamespace(
228 Tcl_Interp *interp)/* Interpreter whose current namespace is
231 return TclGetCurrentNamespace(interp);
235 *----------------------------------------------------------------------
237 * Tcl_GetGlobalNamespace --
239 * Returns a pointer to an interpreter's global :: namespace.
242 * Returns a pointer to the specified interpreter's global namespace.
247 *----------------------------------------------------------------------
251 Tcl_GetGlobalNamespace(
252 Tcl_Interp *interp)/* Interpreter whose global namespace should
255 return TclGetGlobalNamespace(interp);
259 *----------------------------------------------------------------------
261 * Tcl_PushCallFrame --
263 * Pushes a new call frame onto the interpreter's Tcl call stack. Called
264 * when executing a Tcl procedure or a "namespace eval" or "namespace
268 * Returns TCL_OK if successful, or TCL_ERROR (along with an error
269 * message in the interpreter's result object) if something goes wrong.
272 * Modifies the interpreter's Tcl call stack.
274 *----------------------------------------------------------------------
279 Tcl_Interp *interp, /* Interpreter in which the new call frame is
281 Tcl_CallFrame *callFramePtr,/* Points to a call frame structure to push.
282 * Storage for this has already been allocated
283 * by the caller; typically this is the
284 * address of a CallFrame structure allocated
285 * on the caller's C stack. The call frame
286 * will be initialized by this function. The
287 * caller can pop the frame later with
288 * Tcl_PopCallFrame, and it is responsible for
289 * freeing the frame's storage. */
290 Tcl_Namespace *namespacePtr,/* Points to the namespace in which the frame
291 * will execute. If NULL, the interpreter's
292 * current namespace will be used. */
293 int isProcCallFrame) /* If nonzero, the frame represents a called
294 * Tcl procedure and may have local vars. Vars
295 * will ordinarily be looked up in the frame.
296 * If new variables are created, they will be
297 * created in the frame. If 0, the frame is
298 * for a "namespace eval" or "namespace
299 * inscope" command and var references are
300 * treated as references to namespace
303 Interp *iPtr = (Interp *) interp;
304 CallFrame *framePtr = (CallFrame *) callFramePtr;
307 if (namespacePtr == NULL) {
308 nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
310 nsPtr = (Namespace *) namespacePtr;
313 * TODO: Examine whether it would be better to guard based on NS_DYING
314 * or NS_KILLED. It appears that these are not tested because they can
315 * be set in a global interp that has been [namespace delete]d, but
316 * which never really completely goes away because of lingering global
317 * things like ::errorInfo and [::unknown] and hidden commands.
318 * Review of those designs might permit stricter checking here.
321 if (nsPtr->flags & NS_DEAD) {
322 Tcl_Panic("Trying to push call frame for dead namespace");
327 nsPtr->activationCount++;
328 framePtr->nsPtr = nsPtr;
329 framePtr->isProcCallFrame = isProcCallFrame;
331 framePtr->objv = NULL;
332 framePtr->callerPtr = iPtr->framePtr;
333 framePtr->callerVarPtr = iPtr->varFramePtr;
334 if (iPtr->varFramePtr != NULL) {
335 framePtr->level = (iPtr->varFramePtr->level + 1);
339 framePtr->procPtr = NULL; /* no called procedure */
340 framePtr->varTablePtr = NULL; /* and no local variables */
341 framePtr->numCompiledLocals = 0;
342 framePtr->compiledLocals = NULL;
343 framePtr->clientData = NULL;
344 framePtr->localCachePtr = NULL;
345 framePtr->tailcallPtr = NULL;
348 * Push the new call frame onto the interpreter's stack of procedure call
349 * frames making it the current frame.
352 iPtr->framePtr = framePtr;
353 iPtr->varFramePtr = framePtr;
359 *----------------------------------------------------------------------
361 * Tcl_PopCallFrame --
363 * Removes a call frame from the Tcl call stack for the interpreter.
364 * Called to remove a frame previously pushed by Tcl_PushCallFrame.
370 * Modifies the call stack of the interpreter. Resets various fields of
371 * the popped call frame. If a namespace has been deleted and has no more
372 * activations on the call stack, the namespace is destroyed.
374 *----------------------------------------------------------------------
379 Tcl_Interp *interp) /* Interpreter with call frame to pop. */
381 Interp *iPtr = (Interp *) interp;
382 CallFrame *framePtr = iPtr->framePtr;
386 * It's important to remove the call frame from the interpreter's stack of
387 * call frames before deleting local variables, so that traces invoked by
388 * the variable deletion don't see the partially-deleted frame.
391 if (framePtr->callerPtr) {
392 iPtr->framePtr = framePtr->callerPtr;
393 iPtr->varFramePtr = framePtr->callerVarPtr;
395 /* Tcl_PopCallFrame: trying to pop rootCallFrame! */
398 if (framePtr->varTablePtr != NULL) {
399 TclDeleteVars(iPtr, framePtr->varTablePtr);
400 ckfree(framePtr->varTablePtr);
401 framePtr->varTablePtr = NULL;
403 if (framePtr->numCompiledLocals > 0) {
404 TclDeleteCompiledLocalVars(iPtr, framePtr);
405 if (--framePtr->localCachePtr->refCount == 0) {
406 TclFreeLocalCache(interp, framePtr->localCachePtr);
408 framePtr->localCachePtr = NULL;
412 * Decrement the namespace's count of active call frames. If the namespace
413 * is "dying" and there are no more active call frames, call
414 * Tcl_DeleteNamespace to destroy it.
417 nsPtr = framePtr->nsPtr;
418 nsPtr->activationCount--;
419 if ((nsPtr->flags & NS_DYING)
420 && (nsPtr->activationCount - (nsPtr == iPtr->globalNsPtr) == 0)) {
421 Tcl_DeleteNamespace((Tcl_Namespace *) nsPtr);
423 framePtr->nsPtr = NULL;
425 if (framePtr->tailcallPtr) {
426 TclSetTailcall(interp, framePtr->tailcallPtr);
431 *----------------------------------------------------------------------
433 * TclPushStackFrame --
435 * Allocates a new call frame in the interpreter's execution stack, then
436 * pushes it onto the interpreter's Tcl call stack. Called when executing
437 * a Tcl procedure or a "namespace eval" or "namespace inscope" command.
440 * Returns TCL_OK if successful, or TCL_ERROR (along with an error
441 * message in the interpreter's result object) if something goes wrong.
444 * Modifies the interpreter's Tcl call stack.
446 *----------------------------------------------------------------------
451 Tcl_Interp *interp, /* Interpreter in which the new call frame is
453 Tcl_CallFrame **framePtrPtr,/* Place to store a pointer to the stack
454 * allocated call frame. */
455 Tcl_Namespace *namespacePtr,/* Points to the namespace in which the frame
456 * will execute. If NULL, the interpreter's
457 * current namespace will be used. */
458 int isProcCallFrame) /* If nonzero, the frame represents a called
459 * Tcl procedure and may have local vars. Vars
460 * will ordinarily be looked up in the frame.
461 * If new variables are created, they will be
462 * created in the frame. If 0, the frame is
463 * for a "namespace eval" or "namespace
464 * inscope" command and var references are
465 * treated as references to namespace
468 *framePtrPtr = TclStackAlloc(interp, sizeof(CallFrame));
469 return Tcl_PushCallFrame(interp, *framePtrPtr, namespacePtr,
475 Tcl_Interp *interp) /* Interpreter with call frame to pop. */
477 CallFrame *freePtr = ((Interp *) interp)->framePtr;
479 Tcl_PopCallFrame(interp);
480 TclStackFree(interp, freePtr);
484 *----------------------------------------------------------------------
486 * EstablishErrorCodeTraces --
488 * Creates traces on the ::errorCode variable to keep its value
489 * consistent with the expectations of legacy code.
495 * Read and unset traces are established on ::errorCode.
497 *----------------------------------------------------------------------
501 EstablishErrorCodeTraces(
502 ClientData clientData,
508 Tcl_TraceVar2(interp, "errorCode", NULL, TCL_GLOBAL_ONLY|TCL_TRACE_READS,
509 ErrorCodeRead, NULL);
510 Tcl_TraceVar2(interp, "errorCode", NULL, TCL_GLOBAL_ONLY|TCL_TRACE_UNSETS,
511 EstablishErrorCodeTraces, NULL);
516 *----------------------------------------------------------------------
520 * Called when the ::errorCode variable is read. Copies the current value
521 * of the interp's errorCode field into ::errorCode.
529 *----------------------------------------------------------------------
534 ClientData clientData,
540 Interp *iPtr = (Interp *) interp;
542 if (Tcl_InterpDeleted(interp) || !(iPtr->flags & ERR_LEGACY_COPY)) {
545 if (iPtr->errorCode) {
546 Tcl_ObjSetVar2(interp, iPtr->ecVar, NULL,
547 iPtr->errorCode, TCL_GLOBAL_ONLY);
550 if (NULL == Tcl_ObjGetVar2(interp, iPtr->ecVar, NULL, TCL_GLOBAL_ONLY)) {
551 Tcl_ObjSetVar2(interp, iPtr->ecVar, NULL,
552 Tcl_NewObj(), TCL_GLOBAL_ONLY);
558 *----------------------------------------------------------------------
560 * EstablishErrorInfoTraces --
562 * Creates traces on the ::errorInfo variable to keep its value
563 * consistent with the expectations of legacy code.
569 * Read and unset traces are established on ::errorInfo.
571 *----------------------------------------------------------------------
575 EstablishErrorInfoTraces(
576 ClientData clientData,
582 Tcl_TraceVar2(interp, "errorInfo", NULL, TCL_GLOBAL_ONLY|TCL_TRACE_READS,
583 ErrorInfoRead, NULL);
584 Tcl_TraceVar2(interp, "errorInfo", NULL, TCL_GLOBAL_ONLY|TCL_TRACE_UNSETS,
585 EstablishErrorInfoTraces, NULL);
590 *----------------------------------------------------------------------
594 * Called when the ::errorInfo variable is read. Copies the current value
595 * of the interp's errorInfo field into ::errorInfo.
603 *----------------------------------------------------------------------
608 ClientData clientData,
614 Interp *iPtr = (Interp *) interp;
616 if (Tcl_InterpDeleted(interp) || !(iPtr->flags & ERR_LEGACY_COPY)) {
619 if (iPtr->errorInfo) {
620 Tcl_ObjSetVar2(interp, iPtr->eiVar, NULL,
621 iPtr->errorInfo, TCL_GLOBAL_ONLY);
624 if (NULL == Tcl_ObjGetVar2(interp, iPtr->eiVar, NULL, TCL_GLOBAL_ONLY)) {
625 Tcl_ObjSetVar2(interp, iPtr->eiVar, NULL,
626 Tcl_NewObj(), TCL_GLOBAL_ONLY);
632 *----------------------------------------------------------------------
634 * Tcl_CreateNamespace --
636 * Creates a new namespace with the given name. If there is no active
637 * namespace (i.e., the interpreter is being initialized), the global ::
638 * namespace is created and returned.
641 * Returns a pointer to the new namespace if successful. If the namespace
642 * already exists or if another error occurs, this routine returns NULL,
643 * along with an error message in the interpreter's result object.
646 * If the name contains "::" qualifiers and a parent namespace does not
647 * already exist, it is automatically created.
649 *----------------------------------------------------------------------
654 Tcl_Interp *interp, /* Interpreter in which a new namespace is
655 * being created. Also used for error
657 const char *name, /* Name for the new namespace. May be a
658 * qualified name with names of ancestor
659 * namespaces separated by "::"s. */
660 ClientData clientData, /* One-word value to store with namespace. */
661 Tcl_NamespaceDeleteProc *deleteProc)
662 /* Function called to delete client data when
663 * the namespace is deleted. NULL if no
664 * function should be called. */
666 Interp *iPtr = (Interp *) interp;
667 Namespace *nsPtr, *ancestorPtr;
668 Namespace *parentPtr, *dummy1Ptr, *dummy2Ptr;
669 Namespace *globalNsPtr = iPtr->globalNsPtr;
670 const char *simpleName;
671 Tcl_HashEntry *entryPtr;
672 Tcl_DString buffer1, buffer2;
673 Tcl_DString *namePtr, *buffPtr;
674 int newEntry, nameLen;
675 ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
677 Tcl_DString tmpBuffer;
679 Tcl_DStringInit(&tmpBuffer);
682 * If there is no active namespace, the interpreter is being initialized.
685 if ((globalNsPtr == NULL) && (iPtr->varFramePtr == NULL)) {
687 * Treat this namespace as the global namespace, and avoid looking for
697 * Ensure that there are no trailing colons as that causes chaos when a
698 * deleteProc is specified. [Bug d614d63989]
701 if (deleteProc != NULL) {
702 nameStr = name + strlen(name) - 2;
703 if (nameStr >= name && nameStr[1] == ':' && nameStr[0] == ':') {
704 Tcl_DStringAppend(&tmpBuffer, name, -1);
705 while ((nameLen = Tcl_DStringLength(&tmpBuffer)) > 0
706 && Tcl_DStringValue(&tmpBuffer)[nameLen-1] == ':') {
707 Tcl_DStringSetLength(&tmpBuffer, nameLen-1);
709 name = Tcl_DStringValue(&tmpBuffer);
714 * If we've ended up with an empty string now, we're attempting to create
715 * the global namespace despite the global namespace existing. That's
720 Tcl_SetObjResult(interp, Tcl_NewStringObj("can't create namespace"
721 " \"\": only global namespace can have empty name", -1));
722 Tcl_SetErrorCode(interp, "TCL", "OPERATION", "NAMESPACE",
723 "CREATEGLOBAL", NULL);
724 Tcl_DStringFree(&tmpBuffer);
729 * Find the parent for the new namespace.
732 TclGetNamespaceForQualName(interp, name, NULL, TCL_CREATE_NS_IF_UNKNOWN,
733 &parentPtr, &dummy1Ptr, &dummy2Ptr, &simpleName);
736 * If the unqualified name at the end is empty, there were trailing "::"s
737 * after the namespace's name which we ignore. The new namespace was
738 * already (recursively) created and is pointed to by parentPtr.
741 if (*simpleName == '\0') {
742 Tcl_DStringFree(&tmpBuffer);
743 return (Tcl_Namespace *) parentPtr;
747 * Check for a bad namespace name and make sure that the name does not
748 * already exist in the parent namespace.
752 #ifndef BREAK_NAMESPACE_COMPAT
753 Tcl_FindHashEntry(&parentPtr->childTable, simpleName) != NULL
755 parentPtr->childTablePtr != NULL &&
756 Tcl_FindHashEntry(parentPtr->childTablePtr, simpleName) != NULL
759 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
760 "can't create namespace \"%s\": already exists", name));
761 Tcl_SetErrorCode(interp, "TCL", "OPERATION", "NAMESPACE",
762 "CREATEEXISTING", NULL);
763 Tcl_DStringFree(&tmpBuffer);
768 * Create the new namespace and root it in its parent. Increment the count
769 * of namespaces created.
773 nsPtr = ckalloc(sizeof(Namespace));
774 nameLen = strlen(simpleName) + 1;
775 nsPtr->name = ckalloc(nameLen);
776 memcpy(nsPtr->name, simpleName, nameLen);
777 nsPtr->fullName = NULL; /* Set below. */
778 nsPtr->clientData = clientData;
779 nsPtr->deleteProc = deleteProc;
780 nsPtr->parentPtr = parentPtr;
781 #ifndef BREAK_NAMESPACE_COMPAT
782 Tcl_InitHashTable(&nsPtr->childTable, TCL_STRING_KEYS);
784 nsPtr->childTablePtr = NULL;
786 nsPtr->nsId = ++(tsdPtr->numNsCreated);
787 nsPtr->interp = interp;
789 nsPtr->activationCount = 0;
791 Tcl_InitHashTable(&nsPtr->cmdTable, TCL_STRING_KEYS);
792 TclInitVarHashTable(&nsPtr->varTable, nsPtr);
793 nsPtr->exportArrayPtr = NULL;
794 nsPtr->numExportPatterns = 0;
795 nsPtr->maxExportPatterns = 0;
796 nsPtr->cmdRefEpoch = 0;
797 nsPtr->resolverEpoch = 0;
798 nsPtr->cmdResProc = NULL;
799 nsPtr->varResProc = NULL;
800 nsPtr->compiledVarResProc = NULL;
801 nsPtr->exportLookupEpoch = 0;
802 nsPtr->ensembles = NULL;
803 nsPtr->unknownHandlerPtr = NULL;
804 nsPtr->commandPathLength = 0;
805 nsPtr->commandPathArray = NULL;
806 nsPtr->commandPathSourceList = NULL;
807 nsPtr->earlyDeleteProc = NULL;
809 if (parentPtr != NULL) {
810 entryPtr = Tcl_CreateHashEntry(
811 TclGetNamespaceChildTable((Tcl_Namespace *) parentPtr),
812 simpleName, &newEntry);
813 Tcl_SetHashValue(entryPtr, nsPtr);
816 * In the global namespace create traces to maintain the ::errorInfo
817 * and ::errorCode variables.
820 iPtr->globalNsPtr = nsPtr;
821 EstablishErrorInfoTraces(NULL, interp, NULL, NULL, 0);
822 EstablishErrorCodeTraces(NULL, interp, NULL, NULL, 0);
826 * Build the fully qualified name for this namespace.
829 Tcl_DStringInit(&buffer1);
830 Tcl_DStringInit(&buffer2);
833 for (ancestorPtr = nsPtr; ancestorPtr != NULL;
834 ancestorPtr = ancestorPtr->parentPtr) {
835 if (ancestorPtr != globalNsPtr) {
836 Tcl_DString *tempPtr = namePtr;
838 TclDStringAppendLiteral(buffPtr, "::");
839 Tcl_DStringAppend(buffPtr, ancestorPtr->name, -1);
840 TclDStringAppendDString(buffPtr, namePtr);
843 * Clear the unwanted buffer or we end up appending to previous
844 * results, making the namespace fullNames of nested namespaces
845 * very wrong (and strange).
848 TclDStringClear(namePtr);
851 * Now swap the buffer pointers so that we build in the other
852 * buffer. This is faster than repeated copying back and forth
861 name = Tcl_DStringValue(namePtr);
862 nameLen = Tcl_DStringLength(namePtr);
863 nsPtr->fullName = ckalloc(nameLen + 1);
864 memcpy(nsPtr->fullName, name, nameLen + 1);
866 Tcl_DStringFree(&buffer1);
867 Tcl_DStringFree(&buffer2);
868 Tcl_DStringFree(&tmpBuffer);
871 * If compilation of commands originating from the parent NS is
872 * suppressed, suppress it for commands originating in this one too.
875 if (nsPtr->parentPtr != NULL &&
876 nsPtr->parentPtr->flags & NS_SUPPRESS_COMPILATION) {
877 nsPtr->flags |= NS_SUPPRESS_COMPILATION;
881 * Return a pointer to the new namespace.
884 return (Tcl_Namespace *) nsPtr;
888 *----------------------------------------------------------------------
890 * Tcl_DeleteNamespace --
892 * Deletes a namespace and all of the commands, variables, and other
893 * namespaces within it.
899 * When a namespace is deleted, it is automatically removed as a child of
900 * its parent namespace. Also, all its commands, variables and child
901 * namespaces are deleted.
903 *----------------------------------------------------------------------
908 Tcl_Namespace *namespacePtr)/* Points to the namespace to delete. */
910 Namespace *nsPtr = (Namespace *) namespacePtr;
911 Interp *iPtr = (Interp *) nsPtr->interp;
912 Namespace *globalNsPtr = (Namespace *)
913 TclGetGlobalNamespace((Tcl_Interp *) iPtr);
914 Tcl_HashEntry *entryPtr;
915 Tcl_HashSearch search;
919 * Ensure that this namespace doesn't get deallocated in the meantime.
924 * Give anyone interested - notably TclOO - a chance to use this namespace
925 * normally despite the fact that the namespace is going to go. Allows the
926 * calling of destructors. Will only be called once (unless re-established
927 * by the called function). [Bug 2950259]
929 * Note that setting this field requires access to the internal definition
930 * of namespaces, so it should only be accessed by code that knows about
931 * being careful with reentrancy.
934 if (nsPtr->earlyDeleteProc != NULL) {
935 Tcl_NamespaceDeleteProc *earlyDeleteProc = nsPtr->earlyDeleteProc;
937 nsPtr->earlyDeleteProc = NULL;
938 nsPtr->activationCount++;
939 earlyDeleteProc(nsPtr->clientData);
940 nsPtr->activationCount--;
944 * Delete all coroutine commands now: break the circular ref cycle between
945 * the namespace and the coroutine command [Bug 2724403]. This code is
946 * essentially duplicated in TclTeardownNamespace() for all other
947 * commands. Don't optimize to Tcl_NextHashEntry() because of traces.
949 * NOTE: we could avoid traversing the ns's command list by keeping a
950 * separate list of coros.
953 for (entryPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search);
955 cmdPtr = Tcl_GetHashValue(entryPtr);
956 if (cmdPtr->nreProc == TclNRInterpCoroutine) {
957 Tcl_DeleteCommandFromToken((Tcl_Interp *) iPtr,
958 (Tcl_Command) cmdPtr);
959 entryPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search);
961 entryPtr = Tcl_NextHashEntry(&search);
966 * If the namespace has associated ensemble commands, delete them first.
967 * This leaves the actual contents of the namespace alone (unless they are
968 * linked ensemble commands, of course). Note that this code is actually
969 * reentrant so command delete traces won't purturb things badly.
972 while (nsPtr->ensembles != NULL) {
973 EnsembleConfig *ensemblePtr = (EnsembleConfig *) nsPtr->ensembles;
976 * Splice out and link to indicate that we've already been killed.
979 nsPtr->ensembles = (Tcl_Ensemble *) ensemblePtr->next;
980 ensemblePtr->next = ensemblePtr;
981 Tcl_DeleteCommandFromToken(nsPtr->interp, ensemblePtr->token);
985 * If the namespace has a registered unknown handler (TIP 181), then free
989 if (nsPtr->unknownHandlerPtr != NULL) {
990 Tcl_DecrRefCount(nsPtr->unknownHandlerPtr);
991 nsPtr->unknownHandlerPtr = NULL;
995 * If the namespace is on the call frame stack, it is marked as "dying"
996 * (NS_DYING is OR'd into its flags): the namespace can't be looked up by
997 * name but its commands and variables are still usable by those active
998 * call frames. When all active call frames referring to the namespace
999 * have been popped from the Tcl stack, Tcl_PopCallFrame will call this
1000 * function again to delete everything in the namespace. If no nsName
1001 * objects refer to the namespace (i.e., if its refCount is zero), its
1002 * commands and variables are deleted and the storage for its namespace
1003 * structure is freed. Otherwise, if its refCount is nonzero, the
1004 * namespace's commands and variables are deleted but the structure isn't
1005 * freed. Instead, NS_DEAD is OR'd into the structure's flags to allow the
1006 * namespace resolution code to recognize that the namespace is "deleted".
1007 * The structure's storage is freed by FreeNsNameInternalRep when its
1008 * refCount reaches 0.
1011 if (nsPtr->activationCount - (nsPtr == globalNsPtr) > 0) {
1012 nsPtr->flags |= NS_DYING;
1013 if (nsPtr->parentPtr != NULL) {
1014 entryPtr = Tcl_FindHashEntry(
1015 TclGetNamespaceChildTable((Tcl_Namespace *)
1016 nsPtr->parentPtr), nsPtr->name);
1017 if (entryPtr != NULL) {
1018 Tcl_DeleteHashEntry(entryPtr);
1021 nsPtr->parentPtr = NULL;
1022 } else if (!(nsPtr->flags & NS_KILLED)) {
1024 * Delete the namespace and everything in it. If this is the global
1025 * namespace, then clear it but don't free its storage unless the
1026 * interpreter is being torn down. Set the NS_KILLED flag to avoid
1027 * recursive calls here - if the namespace is really in the process of
1028 * being deleted, ignore any second call.
1031 nsPtr->flags |= (NS_DYING|NS_KILLED);
1033 TclTeardownNamespace(nsPtr);
1035 if ((nsPtr != globalNsPtr) || (iPtr->flags & DELETED)) {
1037 * If this is the global namespace, then it may have residual
1038 * "errorInfo" and "errorCode" variables for errors that occurred
1039 * while it was being torn down. Try to clear the variable list
1043 TclDeleteNamespaceVars(nsPtr);
1045 #ifndef BREAK_NAMESPACE_COMPAT
1046 Tcl_DeleteHashTable(&nsPtr->childTable);
1048 if (nsPtr->childTablePtr != NULL) {
1049 Tcl_DeleteHashTable(nsPtr->childTablePtr);
1050 ckfree(nsPtr->childTablePtr);
1053 Tcl_DeleteHashTable(&nsPtr->cmdTable);
1055 nsPtr ->flags |= NS_DEAD;
1058 * Restore the ::errorInfo and ::errorCode traces.
1061 EstablishErrorInfoTraces(NULL, nsPtr->interp, NULL, NULL, 0);
1062 EstablishErrorCodeTraces(NULL, nsPtr->interp, NULL, NULL, 0);
1065 * We didn't really kill it, so remove the KILLED marks, so it can
1066 * get killed later, avoiding mem leaks.
1069 nsPtr->flags &= ~(NS_DYING|NS_KILLED);
1072 TclNsDecrRefCount(nsPtr);
1076 TclNamespaceDeleted(
1079 return (nsPtr->flags & NS_DYING) ? 1 : 0;
1083 *----------------------------------------------------------------------
1085 * TclTeardownNamespace --
1087 * Used internally to dismantle and unlink a namespace when it is
1088 * deleted. Divorces the namespace from its parent, and deletes all
1089 * commands, variables, and child namespaces.
1091 * This is kept separate from Tcl_DeleteNamespace so that the global
1092 * namespace can be handled specially.
1098 * Removes this namespace from its parent's child namespace hashtable.
1099 * Deletes all commands, variables and namespaces in this namespace.
1101 *----------------------------------------------------------------------
1105 TclTeardownNamespace(
1106 Namespace *nsPtr) /* Points to the namespace to be dismantled
1107 * and unlinked from its parent. */
1109 Interp *iPtr = (Interp *) nsPtr->interp;
1110 Tcl_HashEntry *entryPtr;
1111 Tcl_HashSearch search;
1115 * Start by destroying the namespace's variable table, since variables
1116 * might trigger traces. Variable table should be cleared but not freed!
1117 * TclDeleteNamespaceVars frees it, so we reinitialize it afterwards.
1120 TclDeleteNamespaceVars(nsPtr);
1121 TclInitVarHashTable(&nsPtr->varTable, nsPtr);
1124 * Delete all commands in this namespace. Be careful when traversing the
1125 * hash table: when each command is deleted, it removes itself from the
1126 * command table. Because of traces (and the desire to avoid the quadratic
1127 * problems of just using Tcl_FirstHashEntry over and over, [Bug
1128 * f97d4ee020]) we copy to a temporary array and then delete all those
1132 while (nsPtr->cmdTable.numEntries > 0) {
1133 int length = nsPtr->cmdTable.numEntries;
1134 Command **cmds = TclStackAlloc((Tcl_Interp *) iPtr,
1135 sizeof(Command *) * length);
1138 for (entryPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search);
1140 entryPtr = Tcl_NextHashEntry(&search)) {
1141 cmds[i] = Tcl_GetHashValue(entryPtr);
1142 cmds[i]->refCount++;
1145 for (i = 0 ; i < length ; i++) {
1146 Tcl_DeleteCommandFromToken((Tcl_Interp *) iPtr,
1147 (Tcl_Command) cmds[i]);
1148 TclCleanupCommandMacro(cmds[i]);
1150 TclStackFree((Tcl_Interp *) iPtr, cmds);
1152 Tcl_DeleteHashTable(&nsPtr->cmdTable);
1153 Tcl_InitHashTable(&nsPtr->cmdTable, TCL_STRING_KEYS);
1156 * Remove the namespace from its parent's child hashtable.
1159 if (nsPtr->parentPtr != NULL) {
1160 entryPtr = Tcl_FindHashEntry(
1161 TclGetNamespaceChildTable((Tcl_Namespace *)
1162 nsPtr->parentPtr), nsPtr->name);
1163 if (entryPtr != NULL) {
1164 Tcl_DeleteHashEntry(entryPtr);
1167 nsPtr->parentPtr = NULL;
1170 * Delete the namespace path if one is installed.
1173 if (nsPtr->commandPathLength != 0) {
1174 UnlinkNsPath(nsPtr);
1175 nsPtr->commandPathLength = 0;
1177 if (nsPtr->commandPathSourceList != NULL) {
1178 NamespacePathEntry *nsPathPtr = nsPtr->commandPathSourceList;
1181 if (nsPathPtr->nsPtr != NULL && nsPathPtr->creatorNsPtr != NULL) {
1182 nsPathPtr->creatorNsPtr->cmdRefEpoch++;
1184 nsPathPtr->nsPtr = NULL;
1185 nsPathPtr = nsPathPtr->nextPtr;
1186 } while (nsPathPtr != NULL);
1187 nsPtr->commandPathSourceList = NULL;
1191 * Delete all the child namespaces.
1193 * BE CAREFUL: When each child is deleted, it will divorce itself from its
1194 * parent. You can't traverse a hash table properly if its elements are
1195 * being deleted. Because of traces (and the desire to avoid the
1196 * quadratic problems of just using Tcl_FirstHashEntry over and over, [Bug
1197 * f97d4ee020]) we copy to a temporary array and then delete all those
1200 * Important: leave the hash table itself still live.
1203 #ifndef BREAK_NAMESPACE_COMPAT
1204 while (nsPtr->childTable.numEntries > 0) {
1205 int length = nsPtr->childTable.numEntries;
1206 Namespace **children = TclStackAlloc((Tcl_Interp *) iPtr,
1207 sizeof(Namespace *) * length);
1210 for (entryPtr = Tcl_FirstHashEntry(&nsPtr->childTable, &search);
1212 entryPtr = Tcl_NextHashEntry(&search)) {
1213 children[i] = Tcl_GetHashValue(entryPtr);
1214 children[i]->refCount++;
1217 for (i = 0 ; i < length ; i++) {
1218 Tcl_DeleteNamespace((Tcl_Namespace *) children[i]);
1219 TclNsDecrRefCount(children[i]);
1221 TclStackFree((Tcl_Interp *) iPtr, children);
1224 if (nsPtr->childTablePtr != NULL) {
1225 while (nsPtr->childTablePtr->numEntries > 0) {
1226 int length = nsPtr->childTablePtr->numEntries;
1227 Namespace **children = TclStackAlloc((Tcl_Interp *) iPtr,
1228 sizeof(Namespace *) * length);
1231 for (entryPtr = Tcl_FirstHashEntry(nsPtr->childTablePtr, &search);
1233 entryPtr = Tcl_NextHashEntry(&search)) {
1234 children[i] = Tcl_GetHashValue(entryPtr);
1235 children[i]->refCount++;
1238 for (i = 0 ; i < length ; i++) {
1239 Tcl_DeleteNamespace((Tcl_Namespace *) children[i]);
1240 TclNsDecrRefCount(children[i]);
1242 TclStackFree((Tcl_Interp *) iPtr, children);
1248 * Free the namespace's export pattern array.
1251 if (nsPtr->exportArrayPtr != NULL) {
1252 for (i = 0; i < nsPtr->numExportPatterns; i++) {
1253 ckfree(nsPtr->exportArrayPtr[i]);
1255 ckfree(nsPtr->exportArrayPtr);
1256 nsPtr->exportArrayPtr = NULL;
1257 nsPtr->numExportPatterns = 0;
1258 nsPtr->maxExportPatterns = 0;
1262 * Free any client data associated with the namespace.
1265 if (nsPtr->deleteProc != NULL) {
1266 nsPtr->deleteProc(nsPtr->clientData);
1268 nsPtr->deleteProc = NULL;
1269 nsPtr->clientData = NULL;
1272 * Reset the namespace's id field to ensure that this namespace won't be
1273 * interpreted as valid by, e.g., the cache validation code for cached
1274 * command references in Tcl_GetCommandFromObj.
1281 *----------------------------------------------------------------------
1285 * Called after a namespace has been deleted, when its reference count
1286 * reaches 0. Frees the data structure representing the namespace.
1294 *----------------------------------------------------------------------
1299 Namespace *nsPtr) /* Points to the namespace to free. */
1302 * Most of the namespace's contents are freed when the namespace is
1303 * deleted by Tcl_DeleteNamespace. All that remains is to free its names
1304 * (for error messages), and the structure itself.
1307 ckfree(nsPtr->name);
1308 ckfree(nsPtr->fullName);
1313 *----------------------------------------------------------------------
1315 * TclNsDecrRefCount --
1317 * Drops a reference to a namespace and frees it if the namespace has
1318 * been deleted and the last reference has just been dropped.
1326 *----------------------------------------------------------------------
1334 if ((nsPtr->refCount == 0) && (nsPtr->flags & NS_DEAD)) {
1335 NamespaceFree(nsPtr);
1340 *----------------------------------------------------------------------
1344 * Makes all the commands matching a pattern available to later be
1345 * imported from the namespace specified by namespacePtr (or the current
1346 * namespace if namespacePtr is NULL). The specified pattern is appended
1347 * onto the namespace's export pattern list, which is optionally cleared
1351 * Returns TCL_OK if successful, or TCL_ERROR (along with an error
1352 * message in the interpreter's result) if something goes wrong.
1355 * Appends the export pattern onto the namespace's export list.
1356 * Optionally reset the namespace's export pattern list.
1358 *----------------------------------------------------------------------
1363 Tcl_Interp *interp, /* Current interpreter. */
1364 Tcl_Namespace *namespacePtr,/* Points to the namespace from which commands
1365 * are to be exported. NULL for the current
1367 const char *pattern, /* String pattern indicating which commands to
1368 * export. This pattern may not include any
1369 * namespace qualifiers; only commands in the
1370 * specified namespace may be exported. */
1371 int resetListFirst) /* If nonzero, resets the namespace's export
1372 * list before appending. */
1374 #define INIT_EXPORT_PATTERNS 5
1375 Namespace *nsPtr, *exportNsPtr, *dummyPtr;
1376 Namespace *currNsPtr = (Namespace *) TclGetCurrentNamespace(interp);
1377 const char *simplePattern;
1379 int neededElems, len, i;
1382 * If the specified namespace is NULL, use the current namespace.
1385 if (namespacePtr == NULL) {
1386 nsPtr = (Namespace *) currNsPtr;
1388 nsPtr = (Namespace *) namespacePtr;
1392 * If resetListFirst is true (nonzero), clear the namespace's export
1396 if (resetListFirst) {
1397 if (nsPtr->exportArrayPtr != NULL) {
1398 for (i = 0; i < nsPtr->numExportPatterns; i++) {
1399 ckfree(nsPtr->exportArrayPtr[i]);
1401 ckfree(nsPtr->exportArrayPtr);
1402 nsPtr->exportArrayPtr = NULL;
1403 TclInvalidateNsCmdLookup(nsPtr);
1404 nsPtr->numExportPatterns = 0;
1405 nsPtr->maxExportPatterns = 0;
1410 * Check that the pattern doesn't have namespace qualifiers.
1413 TclGetNamespaceForQualName(interp, pattern, nsPtr, TCL_NAMESPACE_ONLY,
1414 &exportNsPtr, &dummyPtr, &dummyPtr, &simplePattern);
1416 if ((exportNsPtr != nsPtr) || (strcmp(pattern, simplePattern) != 0)) {
1417 Tcl_SetObjResult(interp, Tcl_ObjPrintf("invalid export pattern"
1418 " \"%s\": pattern can't specify a namespace", pattern));
1419 Tcl_SetErrorCode(interp, "TCL", "EXPORT", "INVALID", NULL);
1424 * Make sure that we don't already have the pattern in the array
1427 if (nsPtr->exportArrayPtr != NULL) {
1428 for (i = 0; i < nsPtr->numExportPatterns; i++) {
1429 if (strcmp(pattern, nsPtr->exportArrayPtr[i]) == 0) {
1431 * The pattern already exists in the list.
1440 * Make sure there is room in the namespace's pattern array for the new
1444 neededElems = nsPtr->numExportPatterns + 1;
1445 if (neededElems > nsPtr->maxExportPatterns) {
1446 nsPtr->maxExportPatterns = nsPtr->maxExportPatterns ?
1447 2 * nsPtr->maxExportPatterns : INIT_EXPORT_PATTERNS;
1448 nsPtr->exportArrayPtr = ckrealloc(nsPtr->exportArrayPtr,
1449 sizeof(char *) * nsPtr->maxExportPatterns);
1453 * Add the pattern to the namespace's array of export patterns.
1456 len = strlen(pattern);
1457 patternCpy = ckalloc(len + 1);
1458 memcpy(patternCpy, pattern, len + 1);
1460 nsPtr->exportArrayPtr[nsPtr->numExportPatterns] = patternCpy;
1461 nsPtr->numExportPatterns++;
1464 * The list of commands actually exported from the namespace might have
1465 * changed (probably will have!) However, we do not need to recompute this
1466 * just yet; next time we need the info will be soon enough.
1469 TclInvalidateNsCmdLookup(nsPtr);
1472 #undef INIT_EXPORT_PATTERNS
1476 *----------------------------------------------------------------------
1478 * Tcl_AppendExportList --
1480 * Appends onto the argument object the list of export patterns for the
1481 * specified namespace.
1484 * The return value is normally TCL_OK; in this case the object
1485 * referenced by objPtr has each export pattern appended to it. If an
1486 * error occurs, TCL_ERROR is returned and the interpreter's result holds
1490 * If necessary, the object referenced by objPtr is converted into a list
1493 *----------------------------------------------------------------------
1497 Tcl_AppendExportList(
1498 Tcl_Interp *interp, /* Interpreter used for error reporting. */
1499 Tcl_Namespace *namespacePtr,/* Points to the namespace whose export
1500 * pattern list is appended onto objPtr. NULL
1501 * for the current namespace. */
1502 Tcl_Obj *objPtr) /* Points to the Tcl object onto which the
1503 * export pattern list is appended. */
1509 * If the specified namespace is NULL, use the current namespace.
1512 if (namespacePtr == NULL) {
1513 nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
1515 nsPtr = (Namespace *) namespacePtr;
1519 * Append the export pattern list onto objPtr.
1522 for (i = 0; i < nsPtr->numExportPatterns; i++) {
1523 result = Tcl_ListObjAppendElement(interp, objPtr,
1524 Tcl_NewStringObj(nsPtr->exportArrayPtr[i], -1));
1525 if (result != TCL_OK) {
1533 *----------------------------------------------------------------------
1537 * Imports all of the commands matching a pattern into the namespace
1538 * specified by namespacePtr (or the current namespace if contextNsPtr is
1539 * NULL). This is done by creating a new command (the "imported command")
1540 * that points to the real command in its original namespace.
1542 * If matching commands are on the autoload path but haven't been loaded
1543 * yet, this command forces them to be loaded, then creates the links to
1547 * Returns TCL_OK if successful, or TCL_ERROR (along with an error
1548 * message in the interpreter's result) if something goes wrong.
1551 * Creates new commands in the importing namespace. These indirect calls
1552 * back to the real command and are deleted if the real commands are
1555 *----------------------------------------------------------------------
1560 Tcl_Interp *interp, /* Current interpreter. */
1561 Tcl_Namespace *namespacePtr,/* Points to the namespace into which the
1562 * commands are to be imported. NULL for the
1563 * current namespace. */
1564 const char *pattern, /* String pattern indicating which commands to
1565 * import. This pattern should be qualified by
1566 * the name of the namespace from which to
1567 * import the command(s). */
1568 int allowOverwrite) /* If nonzero, allow existing commands to be
1569 * overwritten by imported commands. If 0,
1570 * return an error if an imported cmd
1571 * conflicts with an existing one. */
1573 Namespace *nsPtr, *importNsPtr, *dummyPtr;
1574 const char *simplePattern;
1575 Tcl_HashEntry *hPtr;
1576 Tcl_HashSearch search;
1579 * If the specified namespace is NULL, use the current namespace.
1582 if (namespacePtr == NULL) {
1583 nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
1585 nsPtr = (Namespace *) namespacePtr;
1589 * First, invoke the "auto_import" command with the pattern being
1590 * imported. This command is part of the Tcl library. It looks for
1591 * imported commands in autoloaded libraries and loads them in. That way,
1592 * they will be found when we try to create links below.
1594 * Note that we don't just call Tcl_EvalObjv() directly because we do not
1595 * want absence of the command to be a failure case.
1598 if (Tcl_FindCommand(interp,"auto_import",NULL,TCL_GLOBAL_ONLY) != NULL) {
1602 TclNewLiteralStringObj(objv[0], "auto_import");
1603 objv[1] = Tcl_NewStringObj(pattern, -1);
1605 Tcl_IncrRefCount(objv[0]);
1606 Tcl_IncrRefCount(objv[1]);
1607 result = Tcl_EvalObjv(interp, 2, objv, TCL_GLOBAL_ONLY);
1608 Tcl_DecrRefCount(objv[0]);
1609 Tcl_DecrRefCount(objv[1]);
1611 if (result != TCL_OK) {
1614 Tcl_ResetResult(interp);
1618 * From the pattern, find the namespace from which we are importing and
1619 * get the simple pattern (no namespace qualifiers or ::'s) at the end.
1622 if (strlen(pattern) == 0) {
1623 Tcl_SetObjResult(interp, Tcl_NewStringObj("empty import pattern",-1));
1624 Tcl_SetErrorCode(interp, "TCL", "IMPORT", "EMPTY", NULL);
1627 TclGetNamespaceForQualName(interp, pattern, nsPtr, TCL_NAMESPACE_ONLY,
1628 &importNsPtr, &dummyPtr, &dummyPtr, &simplePattern);
1630 if (importNsPtr == NULL) {
1631 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1632 "unknown namespace in import pattern \"%s\"", pattern));
1633 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "NAMESPACE", pattern, NULL);
1636 if (importNsPtr == nsPtr) {
1637 if (pattern == simplePattern) {
1638 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1639 "no namespace specified in import pattern \"%s\"",
1641 Tcl_SetErrorCode(interp, "TCL", "IMPORT", "ORIGIN", NULL);
1643 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1644 "import pattern \"%s\" tries to import from namespace"
1645 " \"%s\" into itself", pattern, importNsPtr->name));
1646 Tcl_SetErrorCode(interp, "TCL", "IMPORT", "SELF", NULL);
1652 * Scan through the command table in the source namespace and look for
1653 * exported commands that match the string pattern. Create an "imported
1654 * command" in the current namespace for each imported command; these
1655 * commands redirect their invocations to the "real" command.
1658 if ((simplePattern != NULL) && TclMatchIsTrivial(simplePattern)) {
1659 hPtr = Tcl_FindHashEntry(&importNsPtr->cmdTable, simplePattern);
1663 return DoImport(interp, nsPtr, hPtr, simplePattern, pattern,
1664 importNsPtr, allowOverwrite);
1666 for (hPtr = Tcl_FirstHashEntry(&importNsPtr->cmdTable, &search);
1667 (hPtr != NULL); hPtr = Tcl_NextHashEntry(&search)) {
1668 char *cmdName = Tcl_GetHashKey(&importNsPtr->cmdTable, hPtr);
1670 if (Tcl_StringMatch(cmdName, simplePattern) &&
1671 DoImport(interp, nsPtr, hPtr, cmdName, pattern, importNsPtr,
1672 allowOverwrite) == TCL_ERROR) {
1680 *----------------------------------------------------------------------
1684 * Import a particular command from one namespace into another. Helper
1688 * Standard Tcl result code. If TCL_ERROR, appends an error message to
1689 * the interpreter result.
1692 * A new command is created in the target namespace unless this is a
1693 * reimport of exactly the same command as before.
1695 *----------------------------------------------------------------------
1702 Tcl_HashEntry *hPtr,
1703 const char *cmdName,
1704 const char *pattern,
1705 Namespace *importNsPtr,
1708 int i = 0, exported = 0;
1709 Tcl_HashEntry *found;
1712 * The command cmdName in the source namespace matches the pattern. Check
1713 * whether it was exported. If it wasn't, we ignore it.
1716 while (!exported && (i < importNsPtr->numExportPatterns)) {
1717 exported |= Tcl_StringMatch(cmdName,
1718 importNsPtr->exportArrayPtr[i++]);
1725 * Unless there is a name clash, create an imported command in the current
1726 * namespace that refers to cmdPtr.
1729 found = Tcl_FindHashEntry(&nsPtr->cmdTable, cmdName);
1730 if ((found == NULL) || allowOverwrite) {
1732 * Create the imported command and its client data. To create the new
1733 * command in the current namespace, generate a fully qualified name
1738 Tcl_Command importedCmd;
1739 ImportedCmdData *dataPtr;
1743 Tcl_DStringInit(&ds);
1744 Tcl_DStringAppend(&ds, nsPtr->fullName, -1);
1745 if (nsPtr != ((Interp *) interp)->globalNsPtr) {
1746 TclDStringAppendLiteral(&ds, "::");
1748 Tcl_DStringAppend(&ds, cmdName, -1);
1751 * Check whether creating the new imported command in the current
1752 * namespace would create a cycle of imported command references.
1755 cmdPtr = Tcl_GetHashValue(hPtr);
1756 if (found != NULL && cmdPtr->deleteProc == DeleteImportedCmd) {
1757 Command *overwrite = Tcl_GetHashValue(found);
1758 Command *linkCmd = cmdPtr;
1760 while (linkCmd->deleteProc == DeleteImportedCmd) {
1761 dataPtr = linkCmd->objClientData;
1762 linkCmd = dataPtr->realCmdPtr;
1763 if (overwrite == linkCmd) {
1764 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1765 "import pattern \"%s\" would create a loop"
1766 " containing command \"%s\"",
1767 pattern, Tcl_DStringValue(&ds)));
1768 Tcl_DStringFree(&ds);
1769 Tcl_SetErrorCode(interp, "TCL", "IMPORT", "LOOP", NULL);
1775 dataPtr = ckalloc(sizeof(ImportedCmdData));
1776 importedCmd = Tcl_NRCreateCommand(interp, Tcl_DStringValue(&ds),
1777 InvokeImportedCmd, InvokeImportedNRCmd, dataPtr,
1779 dataPtr->realCmdPtr = cmdPtr;
1780 dataPtr->selfPtr = (Command *) importedCmd;
1781 dataPtr->selfPtr->compileProc = cmdPtr->compileProc;
1782 Tcl_DStringFree(&ds);
1785 * Create an ImportRef structure describing this new import command
1786 * and add it to the import ref list in the "real" command.
1789 refPtr = ckalloc(sizeof(ImportRef));
1790 refPtr->importedCmdPtr = (Command *) importedCmd;
1791 refPtr->nextPtr = cmdPtr->importRefPtr;
1792 cmdPtr->importRefPtr = refPtr;
1794 Command *overwrite = Tcl_GetHashValue(found);
1796 if (overwrite->deleteProc == DeleteImportedCmd) {
1797 ImportedCmdData *dataPtr = overwrite->objClientData;
1799 if (dataPtr->realCmdPtr == Tcl_GetHashValue(hPtr)) {
1801 * Repeated import of same command is acceptable.
1807 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1808 "can't import command \"%s\": already exists", cmdName));
1809 Tcl_SetErrorCode(interp, "TCL", "IMPORT", "OVERWRITE", NULL);
1816 *----------------------------------------------------------------------
1818 * Tcl_ForgetImport --
1820 * Deletes commands previously imported into the namespace indicated.
1821 * The by namespacePtr, or the current namespace of interp, when
1822 * namespacePtr is NULL. The pattern controls which imported commands are
1823 * deleted. A simple pattern, one without namespace separators, matches
1824 * the current command names of imported commands in the namespace.
1825 * Matching imported commands are deleted. A qualified pattern is
1826 * interpreted as deletion selection on the basis of where the command is
1827 * imported from. The original command and "first link" command for each
1828 * imported command are determined, and they are matched against the
1829 * pattern. A match leads to deletion of the imported command.
1832 * Returns TCL_ERROR and records an error message in the interp result if
1833 * a namespace qualified pattern refers to a namespace that does not
1834 * exist. Otherwise, returns TCL_OK.
1837 * May delete commands.
1839 *----------------------------------------------------------------------
1844 Tcl_Interp *interp, /* Current interpreter. */
1845 Tcl_Namespace *namespacePtr,/* Points to the namespace from which
1846 * previously imported commands should be
1847 * removed. NULL for current namespace. */
1848 const char *pattern) /* String pattern indicating which imported
1849 * commands to remove. */
1851 Namespace *nsPtr, *sourceNsPtr, *dummyPtr;
1852 const char *simplePattern;
1854 Tcl_HashEntry *hPtr;
1855 Tcl_HashSearch search;
1858 * If the specified namespace is NULL, use the current namespace.
1861 if (namespacePtr == NULL) {
1862 nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
1864 nsPtr = (Namespace *) namespacePtr;
1868 * Parse the pattern into its namespace-qualification (if any) and the
1872 TclGetNamespaceForQualName(interp, pattern, nsPtr, TCL_NAMESPACE_ONLY,
1873 &sourceNsPtr, &dummyPtr, &dummyPtr, &simplePattern);
1875 if (sourceNsPtr == NULL) {
1876 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
1877 "unknown namespace in namespace forget pattern \"%s\"",
1879 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "NAMESPACE", pattern, NULL);
1883 if (strcmp(pattern, simplePattern) == 0) {
1885 * The pattern is simple. Delete any imported commands that match it.
1888 if (TclMatchIsTrivial(simplePattern)) {
1889 hPtr = Tcl_FindHashEntry(&nsPtr->cmdTable, simplePattern);
1891 Command *cmdPtr = Tcl_GetHashValue(hPtr);
1893 if (cmdPtr && (cmdPtr->deleteProc == DeleteImportedCmd)) {
1894 Tcl_DeleteCommandFromToken(interp, (Tcl_Command) cmdPtr);
1899 for (hPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search);
1900 (hPtr != NULL); hPtr = Tcl_NextHashEntry(&search)) {
1901 Command *cmdPtr = Tcl_GetHashValue(hPtr);
1903 if (cmdPtr->deleteProc != DeleteImportedCmd) {
1906 cmdName = Tcl_GetHashKey(&nsPtr->cmdTable, hPtr);
1907 if (Tcl_StringMatch(cmdName, simplePattern)) {
1908 Tcl_DeleteCommandFromToken(interp, (Tcl_Command) cmdPtr);
1915 * The pattern was namespace-qualified.
1918 for (hPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search); (hPtr != NULL);
1919 hPtr = Tcl_NextHashEntry(&search)) {
1921 Tcl_Command token = Tcl_GetHashValue(hPtr);
1922 Tcl_Command origin = TclGetOriginalCommand(token);
1924 if (Tcl_GetCommandInfoFromToken(origin, &info) == 0) {
1925 continue; /* Not an imported command. */
1927 if (info.namespacePtr != (Tcl_Namespace *) sourceNsPtr) {
1929 * Original not in namespace we're matching. Check the first link
1930 * in the import chain.
1933 Command *cmdPtr = (Command *) token;
1934 ImportedCmdData *dataPtr = cmdPtr->objClientData;
1935 Tcl_Command firstToken = (Tcl_Command) dataPtr->realCmdPtr;
1937 if (firstToken == origin) {
1940 Tcl_GetCommandInfoFromToken(firstToken, &info);
1941 if (info.namespacePtr != (Tcl_Namespace *) sourceNsPtr) {
1944 origin = firstToken;
1946 if (Tcl_StringMatch(Tcl_GetCommandName(NULL, origin), simplePattern)){
1947 Tcl_DeleteCommandFromToken(interp, token);
1954 *----------------------------------------------------------------------
1956 * TclGetOriginalCommand --
1958 * An imported command is created in an namespace when a "real" command
1959 * is imported from another namespace. If the specified command is an
1960 * imported command, this function returns the original command it refers
1964 * If the command was imported into a sequence of namespaces a, b,...,n
1965 * where each successive namespace just imports the command from the
1966 * previous namespace, this function returns the Tcl_Command token in the
1967 * first namespace, a. Otherwise, if the specified command is not an
1968 * imported command, the function returns NULL.
1973 *----------------------------------------------------------------------
1977 TclGetOriginalCommand(
1978 Tcl_Command command) /* The imported command for which the original
1979 * command should be returned. */
1981 Command *cmdPtr = (Command *) command;
1982 ImportedCmdData *dataPtr;
1984 if (cmdPtr->deleteProc != DeleteImportedCmd) {
1988 while (cmdPtr->deleteProc == DeleteImportedCmd) {
1989 dataPtr = cmdPtr->objClientData;
1990 cmdPtr = dataPtr->realCmdPtr;
1992 return (Tcl_Command) cmdPtr;
1996 *----------------------------------------------------------------------
1998 * InvokeImportedCmd --
2000 * Invoked by Tcl whenever the user calls an imported command that was
2001 * created by Tcl_Import. Finds the "real" command (in another
2002 * namespace), and passes control to it.
2005 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
2008 * Returns a result in the interpreter's result object. If anything goes
2009 * wrong, the result object is set to an error message.
2011 *----------------------------------------------------------------------
2015 InvokeImportedNRCmd(
2016 ClientData clientData, /* Points to the imported command's
2017 * ImportedCmdData structure. */
2018 Tcl_Interp *interp, /* Current interpreter. */
2019 int objc, /* Number of arguments. */
2020 Tcl_Obj *const objv[]) /* The argument objects. */
2022 ImportedCmdData *dataPtr = clientData;
2023 Command *realCmdPtr = dataPtr->realCmdPtr;
2025 TclSkipTailcall(interp);
2026 return TclNREvalObjv(interp, objc, objv, TCL_EVAL_NOERR, realCmdPtr);
2031 ClientData clientData, /* Points to the imported command's
2032 * ImportedCmdData structure. */
2033 Tcl_Interp *interp, /* Current interpreter. */
2034 int objc, /* Number of arguments. */
2035 Tcl_Obj *const objv[]) /* The argument objects. */
2037 return Tcl_NRCallObjProc(interp, InvokeImportedNRCmd, clientData,
2042 *----------------------------------------------------------------------
2044 * DeleteImportedCmd --
2046 * Invoked by Tcl whenever an imported command is deleted. The "real"
2047 * command keeps a list of all the imported commands that refer to it, so
2048 * those imported commands can be deleted when the real command is
2049 * deleted. This function removes the imported command reference from the
2050 * real command's list, and frees up the memory associated with the
2057 * Removes the imported command from the real command's import list.
2059 *----------------------------------------------------------------------
2064 ClientData clientData) /* Points to the imported command's
2065 * ImportedCmdData structure. */
2067 ImportedCmdData *dataPtr = clientData;
2068 Command *realCmdPtr = dataPtr->realCmdPtr;
2069 Command *selfPtr = dataPtr->selfPtr;
2070 ImportRef *refPtr, *prevPtr;
2073 for (refPtr = realCmdPtr->importRefPtr; refPtr != NULL;
2074 refPtr = refPtr->nextPtr) {
2075 if (refPtr->importedCmdPtr == selfPtr) {
2077 * Remove *refPtr from real command's list of imported commands
2081 if (prevPtr == NULL) { /* refPtr is first in list. */
2082 realCmdPtr->importRefPtr = refPtr->nextPtr;
2084 prevPtr->nextPtr = refPtr->nextPtr;
2093 Tcl_Panic("DeleteImportedCmd: did not find cmd in real cmd's list of import references");
2097 *----------------------------------------------------------------------
2099 * TclGetNamespaceForQualName --
2101 * Given a qualified name specifying a command, variable, or namespace,
2102 * and a namespace in which to resolve the name, this function returns a
2103 * pointer to the namespace that contains the item. A qualified name
2104 * consists of the "simple" name of an item qualified by the names of an
2105 * arbitrary number of containing namespace separated by "::"s. If the
2106 * qualified name starts with "::", it is interpreted absolutely from the
2107 * global namespace. Otherwise, it is interpreted relative to the
2108 * namespace specified by cxtNsPtr if it is non-NULL. If cxtNsPtr is
2109 * NULL, the name is interpreted relative to the current namespace.
2111 * A relative name like "foo::bar::x" can be found starting in either the
2112 * current namespace or in the global namespace. So each search usually
2113 * follows two tracks, and two possible namespaces are returned. If the
2114 * function sets either *nsPtrPtr or *altNsPtrPtr to NULL, then that path
2117 * If "flags" contains TCL_GLOBAL_ONLY, the relative qualified name is
2118 * sought only in the global :: namespace. The alternate search (also)
2119 * starting from the global namespace is ignored and *altNsPtrPtr is set
2122 * If "flags" contains TCL_NAMESPACE_ONLY, the relative qualified name is
2123 * sought only in the namespace specified by cxtNsPtr. The alternate
2124 * search starting from the global namespace is ignored and *altNsPtrPtr
2125 * is set NULL. If both TCL_GLOBAL_ONLY and TCL_NAMESPACE_ONLY are
2126 * specified, TCL_GLOBAL_ONLY is ignored and the search starts from the
2127 * namespace specified by cxtNsPtr.
2129 * If "flags" contains TCL_CREATE_NS_IF_UNKNOWN, all namespace components
2130 * of the qualified name that cannot be found are automatically created
2131 * within their specified parent. This makes sure that functions like
2132 * Tcl_CreateCommand always succeed. There is no alternate search path,
2133 * so *altNsPtrPtr is set NULL.
2135 * If "flags" contains TCL_FIND_ONLY_NS, the qualified name is treated as
2136 * a reference to a namespace, and the entire qualified name is followed.
2137 * If the name is relative, the namespace is looked up only in the
2138 * current namespace. A pointer to the namespace is stored in *nsPtrPtr
2139 * and NULL is stored in *simpleNamePtr. Otherwise, if TCL_FIND_ONLY_NS
2140 * is not specified, only the leading components are treated as namespace
2141 * names, and a pointer to the simple name of the final component is
2142 * stored in *simpleNamePtr.
2145 * It sets *nsPtrPtr and *altNsPtrPtr to point to the two possible
2146 * namespaces which represent the last (containing) namespace in the
2147 * qualified name. If the function sets either *nsPtrPtr or *altNsPtrPtr
2148 * to NULL, then the search along that path failed. The function also
2149 * stores a pointer to the simple name of the final component in
2150 * *simpleNamePtr. If the qualified name is "::" or was treated as a
2151 * namespace reference (TCL_FIND_ONLY_NS), the function stores a pointer
2152 * to the namespace in *nsPtrPtr, NULL in *altNsPtrPtr, and sets
2153 * *simpleNamePtr to point to an empty string.
2155 * If there is an error, this function returns TCL_ERROR. If "flags"
2156 * contains TCL_LEAVE_ERR_MSG, an error message is returned in the
2157 * interpreter's result object. Otherwise, the interpreter's result
2158 * object is left unchanged.
2160 * *actualCxtPtrPtr is set to the actual context namespace. It is set to
2161 * the input context namespace pointer in cxtNsPtr. If cxtNsPtr is NULL,
2162 * it is set to the current namespace context.
2164 * For backwards compatibility with the TclPro byte code loader, this
2165 * function always returns TCL_OK.
2168 * If "flags" contains TCL_CREATE_NS_IF_UNKNOWN, new namespaces may be
2171 *----------------------------------------------------------------------
2175 TclGetNamespaceForQualName(
2176 Tcl_Interp *interp, /* Interpreter in which to find the namespace
2177 * containing qualName. */
2178 const char *qualName, /* A namespace-qualified name of an command,
2179 * variable, or namespace. */
2180 Namespace *cxtNsPtr, /* The namespace in which to start the search
2181 * for qualName's namespace. If NULL start
2182 * from the current namespace. Ignored if
2183 * TCL_GLOBAL_ONLY is set. */
2184 int flags, /* Flags controlling the search: an OR'd
2185 * combination of TCL_GLOBAL_ONLY,
2186 * TCL_NAMESPACE_ONLY, TCL_FIND_ONLY_NS, and
2187 * TCL_CREATE_NS_IF_UNKNOWN. */
2188 Namespace **nsPtrPtr, /* Address where function stores a pointer to
2189 * containing namespace if qualName is found
2190 * starting from *cxtNsPtr or, if
2191 * TCL_GLOBAL_ONLY is set, if qualName is
2192 * found in the global :: namespace. NULL is
2193 * stored otherwise. */
2194 Namespace **altNsPtrPtr, /* Address where function stores a pointer to
2195 * containing namespace if qualName is found
2196 * starting from the global :: namespace.
2197 * NULL is stored if qualName isn't found
2198 * starting from :: or if the TCL_GLOBAL_ONLY,
2199 * TCL_NAMESPACE_ONLY, TCL_FIND_ONLY_NS,
2200 * TCL_CREATE_NS_IF_UNKNOWN flag is set. */
2201 Namespace **actualCxtPtrPtr,/* Address where function stores a pointer to
2202 * the actual namespace from which the search
2203 * started. This is either cxtNsPtr, the ::
2204 * namespace if TCL_GLOBAL_ONLY was specified,
2205 * or the current namespace if cxtNsPtr was
2207 const char **simpleNamePtr) /* Address where function stores the simple
2208 * name at end of the qualName, or NULL if
2209 * qualName is "::" or the flag
2210 * TCL_FIND_ONLY_NS was specified. */
2212 Interp *iPtr = (Interp *) interp;
2213 Namespace *nsPtr = cxtNsPtr;
2214 Namespace *altNsPtr;
2215 Namespace *globalNsPtr = iPtr->globalNsPtr;
2216 const char *start, *end;
2218 Tcl_HashEntry *entryPtr;
2223 * Determine the context namespace nsPtr in which to start the primary
2224 * search. If the qualName name starts with a "::" or TCL_GLOBAL_ONLY was
2225 * specified, search from the global namespace. Otherwise, use the
2226 * namespace given in cxtNsPtr, or if that is NULL, use the current
2227 * namespace context. Note that we always treat two or more adjacent ":"s
2228 * as a namespace separator.
2231 if (flags & TCL_GLOBAL_ONLY) {
2232 nsPtr = globalNsPtr;
2233 } else if (nsPtr == NULL) {
2234 nsPtr = iPtr->varFramePtr->nsPtr;
2237 start = qualName; /* Points to start of qualifying
2239 if ((*qualName == ':') && (*(qualName+1) == ':')) {
2240 start = qualName+2; /* Skip over the initial :: */
2241 while (*start == ':') {
2242 start++; /* Skip over a subsequent : */
2244 nsPtr = globalNsPtr;
2245 if (*start == '\0') { /* qualName is just two or more
2247 *nsPtrPtr = globalNsPtr;
2248 *altNsPtrPtr = NULL;
2249 *actualCxtPtrPtr = globalNsPtr;
2250 *simpleNamePtr = start; /* Points to empty string. */
2254 *actualCxtPtrPtr = nsPtr;
2257 * Start an alternate search path starting with the global namespace.
2258 * However, if the starting context is the global namespace, or if the
2259 * flag is set to search only the namespace *cxtNsPtr, ignore the
2260 * alternate search path.
2263 altNsPtr = globalNsPtr;
2264 if ((nsPtr == globalNsPtr)
2265 || (flags & (TCL_NAMESPACE_ONLY | TCL_FIND_ONLY_NS))) {
2270 * Loop to resolve each namespace qualifier in qualName.
2273 Tcl_DStringInit(&buffer);
2275 while (*start != '\0') {
2277 * Find the next namespace qualifier (i.e., a name ending in "::") or
2278 * the end of the qualified name (i.e., a name ending in "\0"). Set
2279 * len to the number of characters, starting from start, in the name;
2280 * set end to point after the "::"s or at the "\0".
2284 for (end = start; *end != '\0'; end++) {
2285 if ((*end == ':') && (*(end+1) == ':')) {
2286 end += 2; /* Skip over the initial :: */
2287 while (*end == ':') {
2288 end++; /* Skip over the subsequent : */
2290 break; /* Exit for loop; end is after ::'s */
2295 if (*end=='\0' && !(end-start>=2 && *(end-1)==':' && *(end-2)==':')) {
2297 * qualName ended with a simple name at start. If TCL_FIND_ONLY_NS
2298 * was specified, look this up as a namespace. Otherwise, start is
2299 * the name of a cmd or var and we are done.
2302 if (flags & TCL_FIND_ONLY_NS) {
2306 *altNsPtrPtr = altNsPtr;
2307 *simpleNamePtr = start;
2308 Tcl_DStringFree(&buffer);
2313 * start points to the beginning of a namespace qualifier ending
2314 * in "::". end points to the start of a name in that namespace
2315 * that might be empty. Copy the namespace qualifier to a buffer
2316 * so it can be null terminated. We can't modify the incoming
2317 * qualName since it may be a string constant.
2320 TclDStringClear(&buffer);
2321 Tcl_DStringAppend(&buffer, start, len);
2322 nsName = Tcl_DStringValue(&buffer);
2326 * Look up the namespace qualifier nsName in the current namespace
2327 * context. If it isn't found but TCL_CREATE_NS_IF_UNKNOWN is set,
2328 * create that qualifying namespace. This is needed for functions like
2329 * Tcl_CreateCommand that cannot fail.
2332 if (nsPtr != NULL) {
2333 #ifndef BREAK_NAMESPACE_COMPAT
2334 entryPtr = Tcl_FindHashEntry(&nsPtr->childTable, nsName);
2336 if (nsPtr->childTablePtr == NULL) {
2339 entryPtr = Tcl_FindHashEntry(nsPtr->childTablePtr, nsName);
2342 if (entryPtr != NULL) {
2343 nsPtr = Tcl_GetHashValue(entryPtr);
2344 } else if (flags & TCL_CREATE_NS_IF_UNKNOWN) {
2345 Tcl_CallFrame *framePtr;
2347 (void) TclPushStackFrame(interp, &framePtr,
2348 (Tcl_Namespace *) nsPtr, /*isProcCallFrame*/ 0);
2350 nsPtr = (Namespace *)
2351 Tcl_CreateNamespace(interp, nsName, NULL, NULL);
2352 TclPopStackFrame(interp);
2354 if (nsPtr == NULL) {
2355 Tcl_Panic("Could not create namespace '%s'", nsName);
2357 } else { /* Namespace not found and was not
2364 * Look up the namespace qualifier in the alternate search path too.
2367 if (altNsPtr != NULL) {
2368 #ifndef BREAK_NAMESPACE_COMPAT
2369 entryPtr = Tcl_FindHashEntry(&altNsPtr->childTable, nsName);
2371 if (altNsPtr->childTablePtr != NULL) {
2372 entryPtr = Tcl_FindHashEntry(altNsPtr->childTablePtr, nsName);
2377 if (entryPtr != NULL) {
2378 altNsPtr = Tcl_GetHashValue(entryPtr);
2385 * If both search paths have failed, return NULL results.
2388 if ((nsPtr == NULL) && (altNsPtr == NULL)) {
2390 *altNsPtrPtr = NULL;
2391 *simpleNamePtr = NULL;
2392 Tcl_DStringFree(&buffer);
2400 * We ignore trailing "::"s in a namespace name, but in a command or
2401 * variable name, trailing "::"s refer to the cmd or var named {}.
2404 if ((flags & TCL_FIND_ONLY_NS) || (end>start && *(end-1)!=':')) {
2405 *simpleNamePtr = NULL; /* Found namespace name. */
2407 *simpleNamePtr = end; /* Found cmd/var: points to empty
2412 * As a special case, if we are looking for a namespace and qualName is ""
2413 * and the current active namespace (nsPtr) is not the global namespace,
2414 * return NULL (no namespace was found). This is because namespaces can
2415 * not have empty names except for the global namespace.
2418 if ((flags & TCL_FIND_ONLY_NS) && (*qualName == '\0')
2419 && (nsPtr != globalNsPtr)) {
2424 *altNsPtrPtr = altNsPtr;
2425 Tcl_DStringFree(&buffer);
2430 *----------------------------------------------------------------------
2432 * TclEnsureNamespace --
2434 * Provide a namespace that is not deleted.
2438 * namespacePtr, if it is not scheduled for deletion, or a pointer to a
2439 * new namespace with the same name otherwise.
2444 *----------------------------------------------------------------------
2449 Tcl_Namespace *namespacePtr)
2451 Namespace *nsPtr = (Namespace *) namespacePtr;
2452 if (!(nsPtr->flags & NS_DYING)) {
2453 return namespacePtr;
2455 return Tcl_CreateNamespace(interp, nsPtr->fullName, NULL, NULL);
2459 *----------------------------------------------------------------------
2461 * Tcl_FindNamespace --
2463 * Searches for a namespace.
2466 * Returns a pointer to the namespace if it is found. Otherwise, returns
2467 * NULL and leaves an error message in the interpreter's result object if
2468 * "flags" contains TCL_LEAVE_ERR_MSG.
2473 *----------------------------------------------------------------------
2478 Tcl_Interp *interp, /* The interpreter in which to find the
2480 const char *name, /* Namespace name. If it starts with "::",
2481 * will be looked up in global namespace.
2482 * Else, looked up first in contextNsPtr
2483 * (current namespace if contextNsPtr is
2484 * NULL), then in global namespace. */
2485 Tcl_Namespace *contextNsPtr,/* Ignored if TCL_GLOBAL_ONLY flag is set or
2486 * if the name starts with "::". Otherwise,
2487 * points to namespace in which to resolve
2488 * name; if NULL, look up name in the current
2490 int flags) /* Flags controlling namespace lookup: an OR'd
2491 * combination of TCL_GLOBAL_ONLY and
2492 * TCL_LEAVE_ERR_MSG flags. */
2494 Namespace *nsPtr, *dummy1Ptr, *dummy2Ptr;
2498 * Find the namespace(s) that contain the specified namespace name. Add
2499 * the TCL_FIND_ONLY_NS flag to resolve the name all the way down to its
2500 * last component, a namespace.
2503 TclGetNamespaceForQualName(interp, name, (Namespace *) contextNsPtr,
2504 flags|TCL_FIND_ONLY_NS, &nsPtr, &dummy1Ptr, &dummy2Ptr, &dummy);
2506 if (nsPtr != NULL) {
2507 return (Tcl_Namespace *) nsPtr;
2510 if (flags & TCL_LEAVE_ERR_MSG) {
2511 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
2512 "unknown namespace \"%s\"", name));
2513 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "NAMESPACE", name, NULL);
2519 *----------------------------------------------------------------------
2521 * Tcl_FindCommand --
2523 * Searches for a command.
2526 * Returns a token for the command if it is found. Otherwise, if it can't
2527 * be found or there is an error, returns NULL and leaves an error
2528 * message in the interpreter's result object if "flags" contains
2529 * TCL_LEAVE_ERR_MSG.
2534 *----------------------------------------------------------------------
2539 Tcl_Interp *interp, /* The interpreter in which to find the
2540 * command and to report errors. */
2541 const char *name, /* Command's name. If it starts with "::",
2542 * will be looked up in global namespace.
2543 * Else, looked up first in contextNsPtr
2544 * (current namespace if contextNsPtr is
2545 * NULL), then in global namespace. */
2546 Tcl_Namespace *contextNsPtr,/* Ignored if TCL_GLOBAL_ONLY flag set.
2547 * Otherwise, points to namespace in which to
2548 * resolve name. If NULL, look up name in the
2549 * current namespace. */
2550 int flags) /* An OR'd combination of flags:
2551 * TCL_GLOBAL_ONLY (look up name only in
2552 * global namespace), TCL_NAMESPACE_ONLY (look
2553 * up only in contextNsPtr, or the current
2554 * namespace if contextNsPtr is NULL), and
2555 * TCL_LEAVE_ERR_MSG. If both TCL_GLOBAL_ONLY
2556 * and TCL_NAMESPACE_ONLY are given,
2557 * TCL_GLOBAL_ONLY is ignored. */
2559 Interp *iPtr = (Interp *) interp;
2560 Namespace *cxtNsPtr;
2561 Tcl_HashEntry *entryPtr;
2563 const char *simpleName;
2567 * If this namespace has a command resolver, then give it first crack at
2568 * the command resolution. If the interpreter has any command resolvers,
2569 * consult them next. The command resolver functions may return a
2570 * Tcl_Command value, they may signal to continue onward, or they may
2574 if ((flags & TCL_GLOBAL_ONLY) || !strncmp(name, "::", 2)) {
2575 cxtNsPtr = (Namespace *) TclGetGlobalNamespace(interp);
2576 } else if (contextNsPtr != NULL) {
2577 cxtNsPtr = (Namespace *) contextNsPtr;
2579 cxtNsPtr = (Namespace *) TclGetCurrentNamespace(interp);
2582 if (cxtNsPtr->cmdResProc != NULL || iPtr->resolverPtr != NULL) {
2583 ResolverScheme *resPtr = iPtr->resolverPtr;
2586 if (cxtNsPtr->cmdResProc) {
2587 result = cxtNsPtr->cmdResProc(interp, name,
2588 (Tcl_Namespace *) cxtNsPtr, flags, &cmd);
2590 result = TCL_CONTINUE;
2593 while (result == TCL_CONTINUE && resPtr) {
2594 if (resPtr->cmdResProc) {
2595 result = resPtr->cmdResProc(interp, name,
2596 (Tcl_Namespace *) cxtNsPtr, flags, &cmd);
2598 resPtr = resPtr->nextPtr;
2601 if (result == TCL_OK) {
2602 ((Command *)cmd)->flags |= CMD_VIA_RESOLVER;
2605 } else if (result != TCL_CONTINUE) {
2611 * Find the namespace(s) that contain the command.
2615 if (cxtNsPtr->commandPathLength!=0 && strncmp(name, "::", 2)
2616 && !(flags & TCL_NAMESPACE_ONLY)) {
2618 Namespace *pathNsPtr, *realNsPtr, *dummyNsPtr;
2620 (void) TclGetNamespaceForQualName(interp, name, cxtNsPtr,
2621 TCL_NAMESPACE_ONLY, &realNsPtr, &dummyNsPtr, &dummyNsPtr,
2623 if ((realNsPtr != NULL) && (simpleName != NULL)) {
2624 if ((cxtNsPtr == realNsPtr)
2625 || !(realNsPtr->flags & NS_DYING)) {
2626 entryPtr = Tcl_FindHashEntry(&realNsPtr->cmdTable, simpleName);
2627 if (entryPtr != NULL) {
2628 cmdPtr = Tcl_GetHashValue(entryPtr);
2634 * Next, check along the path.
2637 for (i=0 ; i<cxtNsPtr->commandPathLength && cmdPtr==NULL ; i++) {
2638 pathNsPtr = cxtNsPtr->commandPathArray[i].nsPtr;
2639 if (pathNsPtr == NULL) {
2642 (void) TclGetNamespaceForQualName(interp, name, pathNsPtr,
2643 TCL_NAMESPACE_ONLY, &realNsPtr, &dummyNsPtr, &dummyNsPtr,
2645 if ((realNsPtr != NULL) && (simpleName != NULL)
2646 && !(realNsPtr->flags & NS_DYING)) {
2647 entryPtr = Tcl_FindHashEntry(&realNsPtr->cmdTable, simpleName);
2648 if (entryPtr != NULL) {
2649 cmdPtr = Tcl_GetHashValue(entryPtr);
2655 * If we've still not found the command, look in the global namespace
2659 if (cmdPtr == NULL) {
2660 (void) TclGetNamespaceForQualName(interp, name, NULL,
2661 TCL_GLOBAL_ONLY, &realNsPtr, &dummyNsPtr, &dummyNsPtr,
2663 if ((realNsPtr != NULL) && (simpleName != NULL)
2664 && !(realNsPtr->flags & NS_DYING)) {
2665 entryPtr = Tcl_FindHashEntry(&realNsPtr->cmdTable, simpleName);
2666 if (entryPtr != NULL) {
2667 cmdPtr = Tcl_GetHashValue(entryPtr);
2672 Namespace *nsPtr[2];
2675 TclGetNamespaceForQualName(interp, name, cxtNsPtr,
2676 flags, &nsPtr[0], &nsPtr[1], &cxtNsPtr, &simpleName);
2679 * Look for the command in the command table of its namespace. Be sure
2680 * to check both possible search paths: from the specified namespace
2681 * context and from the global namespace.
2684 for (search = 0; (search < 2) && (cmdPtr == NULL); search++) {
2685 if ((nsPtr[search] != NULL) && (simpleName != NULL)) {
2686 entryPtr = Tcl_FindHashEntry(&nsPtr[search]->cmdTable,
2688 if (entryPtr != NULL) {
2689 cmdPtr = Tcl_GetHashValue(entryPtr);
2695 if (cmdPtr != NULL) {
2696 cmdPtr->flags &= ~CMD_VIA_RESOLVER;
2697 return (Tcl_Command) cmdPtr;
2700 if (flags & TCL_LEAVE_ERR_MSG) {
2701 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
2702 "unknown command \"%s\"", name));
2703 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "COMMAND", name, NULL);
2709 *----------------------------------------------------------------------
2711 * TclResetShadowedCmdRefs --
2713 * Called when a command is added to a namespace to check for existing
2714 * command references that the new command may invalidate. Consider the
2715 * following cases that could happen when you add a command "foo" to a
2717 * 1. It could shadow a command named "foo" at the global scope. If
2718 * it does, all command references in the namespace "b" are
2720 * 2. Suppose the namespace "b" resides in a namespace "a". Then to
2721 * "a" the new command "b::foo" could shadow another command
2722 * "b::foo" in the global namespace. If so, then all command
2723 * references in "a" * are suspect.
2724 * The same checks are applied to all parent namespaces, until we reach
2725 * the global :: namespace.
2731 * If the new command shadows an existing command, the cmdRefEpoch
2732 * counter is incremented in each namespace that sees the shadow. This
2733 * invalidates all command references that were previously cached in that
2734 * namespace. The next time the commands are used, they are resolved from
2737 *----------------------------------------------------------------------
2741 TclResetShadowedCmdRefs(
2742 Tcl_Interp *interp, /* Interpreter containing the new command. */
2743 Command *newCmdPtr) /* Points to the new command. */
2746 Tcl_HashEntry *hPtr;
2748 Namespace *trailNsPtr, *shadowNsPtr;
2749 Namespace *globalNsPtr = (Namespace *) TclGetGlobalNamespace(interp);
2751 int trailFront = -1;
2752 int trailSize = 5; /* Formerly NUM_TRAIL_ELEMS. */
2753 Namespace **trailPtr = TclStackAlloc(interp,
2754 trailSize * sizeof(Namespace *));
2757 * Start at the namespace containing the new command, and work up through
2758 * the list of parents. Stop just before the global namespace, since the
2759 * global namespace can't "shadow" its own entries.
2761 * The namespace "trail" list we build consists of the names of each
2762 * namespace that encloses the new command, in order from outermost to
2763 * innermost: for example, "a" then "b". Each iteration of this loop
2764 * eventually extends the trail upwards by one namespace, nsPtr. We use
2765 * this trail list to see if nsPtr (e.g. "a" in 2. above) could have
2766 * now-invalid cached command references. This will happen if nsPtr
2767 * (e.g. "a") contains a sequence of child namespaces (e.g. "b") such that
2768 * there is a identically-named sequence of child namespaces starting from
2769 * :: (e.g. "::b") whose tail namespace contains a command also named
2773 cmdName = Tcl_GetHashKey(newCmdPtr->hPtr->tablePtr, newCmdPtr->hPtr);
2774 for (nsPtr=newCmdPtr->nsPtr ; (nsPtr!=NULL) && (nsPtr!=globalNsPtr) ;
2775 nsPtr=nsPtr->parentPtr) {
2777 * Find the maximal sequence of child namespaces contained in nsPtr
2778 * such that there is a identically-named sequence of child namespaces
2779 * starting from ::. shadowNsPtr will be the tail of this sequence, or
2780 * the deepest namespace under :: that might contain a command now
2781 * shadowed by cmdName. We check below if shadowNsPtr actually
2782 * contains a command cmdName.
2786 shadowNsPtr = globalNsPtr;
2788 for (i = trailFront; i >= 0; i--) {
2789 trailNsPtr = trailPtr[i];
2790 #ifndef BREAK_NAMESPACE_COMPAT
2791 hPtr = Tcl_FindHashEntry(&shadowNsPtr->childTable,
2794 if (shadowNsPtr->childTablePtr != NULL) {
2795 hPtr = Tcl_FindHashEntry(shadowNsPtr->childTablePtr,
2802 shadowNsPtr = Tcl_GetHashValue(hPtr);
2810 * If shadowNsPtr contains a command named cmdName, we invalidate all
2811 * of the command refs cached in nsPtr. As a boundary case,
2812 * shadowNsPtr is initially :: and we check for case 1. above.
2816 hPtr = Tcl_FindHashEntry(&shadowNsPtr->cmdTable, cmdName);
2818 nsPtr->cmdRefEpoch++;
2819 TclInvalidateNsPath(nsPtr);
2822 * If the shadowed command was compiled to bytecodes, we
2823 * invalidate all the bytecodes in nsPtr, to force a new
2824 * compilation. We use the resolverEpoch to signal the need
2825 * for a fresh compilation of every bytecode.
2828 if (((Command *)Tcl_GetHashValue(hPtr))->compileProc != NULL){
2829 nsPtr->resolverEpoch++;
2835 * Insert nsPtr at the front of the trail list: i.e., at the end of
2836 * the trailPtr array.
2840 if (trailFront == trailSize) {
2841 int newSize = 2 * trailSize;
2843 trailPtr = TclStackRealloc(interp, trailPtr,
2844 newSize * sizeof(Namespace *));
2845 trailSize = newSize;
2847 trailPtr[trailFront] = nsPtr;
2849 TclStackFree(interp, trailPtr);
2853 *----------------------------------------------------------------------
2855 * TclGetNamespaceFromObj, GetNamespaceFromObj --
2857 * Gets the namespace specified by the name in a Tcl_Obj.
2860 * Returns TCL_OK if the namespace was resolved successfully, and stores
2861 * a pointer to the namespace in the location specified by nsPtrPtr. If
2862 * the namespace can't be found, or anything else goes wrong, this
2863 * function returns TCL_ERROR and writes an error message to interp,
2867 * May update the internal representation for the object, caching the
2868 * namespace reference. The next time this function is called, the
2869 * namespace value can be found quickly.
2871 *----------------------------------------------------------------------
2875 TclGetNamespaceFromObj(
2876 Tcl_Interp *interp, /* The current interpreter. */
2877 Tcl_Obj *objPtr, /* The object to be resolved as the name of a
2879 Tcl_Namespace **nsPtrPtr) /* Result namespace pointer goes here. */
2881 if (GetNamespaceFromObj(interp, objPtr, nsPtrPtr) == TCL_ERROR) {
2882 const char *name = TclGetString(objPtr);
2884 if ((name[0] == ':') && (name[1] == ':')) {
2885 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
2886 "namespace \"%s\" not found", name));
2889 * Get the current namespace name.
2892 NamespaceCurrentCmd(NULL, interp, 1, NULL);
2893 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
2894 "namespace \"%s\" not found in \"%s\"", name,
2895 Tcl_GetStringResult(interp)));
2897 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "NAMESPACE", name, NULL);
2904 GetNamespaceFromObj(
2905 Tcl_Interp *interp, /* The current interpreter. */
2906 Tcl_Obj *objPtr, /* The object to be resolved as the name of a
2908 Tcl_Namespace **nsPtrPtr) /* Result namespace pointer goes here. */
2910 ResolvedNsName *resNamePtr;
2911 Namespace *nsPtr, *refNsPtr;
2913 if (objPtr->typePtr == &nsNameType) {
2915 * Check that the ResolvedNsName is still valid; avoid letting the ref
2919 resNamePtr = objPtr->internalRep.twoPtrValue.ptr1;
2920 nsPtr = resNamePtr->nsPtr;
2921 refNsPtr = resNamePtr->refNsPtr;
2922 if (!(nsPtr->flags & NS_DYING) && (interp == nsPtr->interp) &&
2923 (!refNsPtr || ((interp == refNsPtr->interp) &&
2924 (refNsPtr== (Namespace *) Tcl_GetCurrentNamespace(interp))))){
2925 *nsPtrPtr = (Tcl_Namespace *) nsPtr;
2929 if (SetNsNameFromAny(interp, objPtr) == TCL_OK) {
2930 resNamePtr = objPtr->internalRep.twoPtrValue.ptr1;
2931 *nsPtrPtr = (Tcl_Namespace *) resNamePtr->nsPtr;
2938 *----------------------------------------------------------------------
2940 * TclInitNamespaceCmd --
2942 * This function is called to create the "namespace" Tcl command. See the
2943 * user documentation for details on what it does.
2946 * Handle for the namespace command, or NULL on failure.
2951 *----------------------------------------------------------------------
2955 TclInitNamespaceCmd(
2956 Tcl_Interp *interp) /* Current interpreter. */
2958 return TclMakeEnsemble(interp, "namespace", defaultNamespaceMap);
2962 *----------------------------------------------------------------------
2964 * NamespaceChildrenCmd --
2966 * Invoked to implement the "namespace children" command that returns a
2967 * list containing the fully-qualified names of the child namespaces of a
2968 * given namespace. Handles the following syntax:
2970 * namespace children ?name? ?pattern?
2973 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
2976 * Returns a result in the interpreter's result object. If anything goes
2977 * wrong, the result is an error message.
2979 *----------------------------------------------------------------------
2983 NamespaceChildrenCmd(
2984 ClientData dummy, /* Not used. */
2985 Tcl_Interp *interp, /* Current interpreter. */
2986 int objc, /* Number of arguments. */
2987 Tcl_Obj *const objv[]) /* Argument objects. */
2989 Tcl_Namespace *namespacePtr;
2990 Namespace *nsPtr, *childNsPtr;
2991 Namespace *globalNsPtr = (Namespace *) TclGetGlobalNamespace(interp);
2992 const char *pattern = NULL;
2994 Tcl_HashEntry *entryPtr;
2995 Tcl_HashSearch search;
2996 Tcl_Obj *listPtr, *elemPtr;
2999 * Get a pointer to the specified namespace, or the current namespace.
3003 nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
3004 } else if ((objc == 2) || (objc == 3)) {
3005 if (TclGetNamespaceFromObj(interp, objv[1], &namespacePtr) != TCL_OK){
3008 nsPtr = (Namespace *) namespacePtr;
3010 Tcl_WrongNumArgs(interp, 1, objv, "?name? ?pattern?");
3015 * Get the glob-style pattern, if any, used to narrow the search.
3018 Tcl_DStringInit(&buffer);
3020 const char *name = TclGetString(objv[2]);
3022 if ((*name == ':') && (*(name+1) == ':')) {
3025 Tcl_DStringAppend(&buffer, nsPtr->fullName, -1);
3026 if (nsPtr != globalNsPtr) {
3027 TclDStringAppendLiteral(&buffer, "::");
3029 Tcl_DStringAppend(&buffer, name, -1);
3030 pattern = Tcl_DStringValue(&buffer);
3035 * Create a list containing the full names of all child namespaces whose
3036 * names match the specified pattern, if any.
3039 listPtr = Tcl_NewListObj(0, NULL);
3040 if ((pattern != NULL) && TclMatchIsTrivial(pattern)) {
3041 unsigned int length = strlen(nsPtr->fullName);
3043 if (strncmp(pattern, nsPtr->fullName, length) != 0) {
3047 #ifndef BREAK_NAMESPACE_COMPAT
3048 Tcl_FindHashEntry(&nsPtr->childTable, pattern+length) != NULL
3050 nsPtr->childTablePtr != NULL &&
3051 Tcl_FindHashEntry(nsPtr->childTablePtr, pattern+length) != NULL
3054 Tcl_ListObjAppendElement(interp, listPtr,
3055 Tcl_NewStringObj(pattern, -1));
3059 #ifndef BREAK_NAMESPACE_COMPAT
3060 entryPtr = Tcl_FirstHashEntry(&nsPtr->childTable, &search);
3062 if (nsPtr->childTablePtr == NULL) {
3065 entryPtr = Tcl_FirstHashEntry(nsPtr->childTablePtr, &search);
3067 while (entryPtr != NULL) {
3068 childNsPtr = Tcl_GetHashValue(entryPtr);
3069 if ((pattern == NULL)
3070 || Tcl_StringMatch(childNsPtr->fullName, pattern)) {
3071 elemPtr = Tcl_NewStringObj(childNsPtr->fullName, -1);
3072 Tcl_ListObjAppendElement(interp, listPtr, elemPtr);
3074 entryPtr = Tcl_NextHashEntry(&search);
3078 Tcl_SetObjResult(interp, listPtr);
3079 Tcl_DStringFree(&buffer);
3084 *----------------------------------------------------------------------
3086 * NamespaceCodeCmd --
3088 * Invoked to implement the "namespace code" command to capture the
3089 * namespace context of a command. Handles the following syntax:
3091 * namespace code arg
3093 * Here "arg" can be a list. "namespace code arg" produces a result
3094 * equivalent to that produced by the command
3096 * list ::namespace inscope [namespace current] $arg
3098 * However, if "arg" is itself a scoped value starting with "::namespace
3099 * inscope", then the result is just "arg".
3102 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3105 * If anything goes wrong, this function returns an error message as the
3106 * result in the interpreter's result object.
3108 *----------------------------------------------------------------------
3113 ClientData dummy, /* Not used. */
3114 Tcl_Interp *interp, /* Current interpreter. */
3115 int objc, /* Number of arguments. */
3116 Tcl_Obj *const objv[]) /* Argument objects. */
3118 Namespace *currNsPtr;
3119 Tcl_Obj *listPtr, *objPtr;
3124 Tcl_WrongNumArgs(interp, 1, objv, "arg");
3129 * If "arg" is already a scoped value, then return it directly.
3130 * Take care to only check for scoping in precisely the style that
3131 * [::namespace code] generates it. Anything more forgiving can have
3132 * the effect of failing in namespaces that contain their own custom
3133 " "namespace" command. [Bug 3202171].
3136 arg = TclGetStringFromObj(objv[1], &length);
3137 if (*arg==':' && length > 20
3138 && strncmp(arg, "::namespace inscope ", 20) == 0) {
3139 Tcl_SetObjResult(interp, objv[1]);
3144 * Otherwise, construct a scoped command by building a list with
3145 * "namespace inscope", the full name of the current namespace, and the
3146 * argument "arg". By constructing a list, we ensure that scoped commands
3147 * are interpreted properly when they are executed later, by the
3148 * "namespace inscope" command.
3152 TclNewLiteralStringObj(objPtr, "::namespace");
3153 Tcl_ListObjAppendElement(interp, listPtr, objPtr);
3154 TclNewLiteralStringObj(objPtr, "inscope");
3155 Tcl_ListObjAppendElement(interp, listPtr, objPtr);
3157 currNsPtr = (Namespace *) TclGetCurrentNamespace(interp);
3158 if (currNsPtr == (Namespace *) TclGetGlobalNamespace(interp)) {
3159 TclNewLiteralStringObj(objPtr, "::");
3161 objPtr = Tcl_NewStringObj(currNsPtr->fullName, -1);
3163 Tcl_ListObjAppendElement(interp, listPtr, objPtr);
3165 Tcl_ListObjAppendElement(interp, listPtr, objv[1]);
3167 Tcl_SetObjResult(interp, listPtr);
3172 *----------------------------------------------------------------------
3174 * NamespaceCurrentCmd --
3176 * Invoked to implement the "namespace current" command which returns the
3177 * fully-qualified name of the current namespace. Handles the following
3183 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3186 * Returns a result in the interpreter's result object. If anything goes
3187 * wrong, the result is an error message.
3189 *----------------------------------------------------------------------
3193 NamespaceCurrentCmd(
3194 ClientData dummy, /* Not used. */
3195 Tcl_Interp *interp, /* Current interpreter. */
3196 int objc, /* Number of arguments. */
3197 Tcl_Obj *const objv[]) /* Argument objects. */
3199 Namespace *currNsPtr;
3202 Tcl_WrongNumArgs(interp, 1, objv, NULL);
3207 * The "real" name of the global namespace ("::") is the null string, but
3208 * we return "::" for it as a convenience to programmers. Note that "" and
3209 * "::" are treated as synonyms by the namespace code so that it is still
3210 * easy to do things like:
3212 * namespace [namespace current]::bar { ... }
3215 currNsPtr = (Namespace *) TclGetCurrentNamespace(interp);
3216 if (currNsPtr == (Namespace *) TclGetGlobalNamespace(interp)) {
3217 Tcl_SetObjResult(interp, Tcl_NewStringObj("::", 2));
3219 Tcl_SetObjResult(interp, Tcl_NewStringObj(currNsPtr->fullName, -1));
3225 *----------------------------------------------------------------------
3227 * NamespaceDeleteCmd --
3229 * Invoked to implement the "namespace delete" command to delete
3230 * namespace(s). Handles the following syntax:
3232 * namespace delete ?name name...?
3234 * Each name identifies a namespace. It may include a sequence of
3235 * namespace qualifiers separated by "::"s. If a namespace is found, it
3236 * is deleted: all variables and procedures contained in that namespace
3237 * are deleted. If that namespace is being used on the call stack, it is
3238 * kept alive (but logically deleted) until it is removed from the call
3239 * stack: that is, it can no longer be referenced by name but any
3240 * currently executing procedure that refers to it is allowed to do so
3241 * until the procedure returns. If the namespace can't be found, this
3242 * function returns an error. If no namespaces are specified, this
3243 * command does nothing.
3246 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3249 * Deletes the specified namespaces. If anything goes wrong, this
3250 * function returns an error message in the interpreter's result object.
3252 *----------------------------------------------------------------------
3257 ClientData dummy, /* Not used. */
3258 Tcl_Interp *interp, /* Current interpreter. */
3259 int objc, /* Number of arguments. */
3260 Tcl_Obj *const objv[]) /* Argument objects. */
3262 Tcl_Namespace *namespacePtr;
3267 Tcl_WrongNumArgs(interp, 1, objv, "?name name...?");
3272 * Destroying one namespace may cause another to be destroyed. Break this
3273 * into two passes: first check to make sure that all namespaces on the
3274 * command line are valid, and report any errors.
3277 for (i = 1; i < objc; i++) {
3278 name = TclGetString(objv[i]);
3279 namespacePtr = Tcl_FindNamespace(interp, name, NULL, /*flags*/ 0);
3280 if ((namespacePtr == NULL)
3281 || (((Namespace *) namespacePtr)->flags & NS_KILLED)) {
3282 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
3283 "unknown namespace \"%s\" in namespace delete command",
3284 TclGetString(objv[i])));
3285 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "NAMESPACE",
3286 TclGetString(objv[i]), NULL);
3292 * Okay, now delete each namespace.
3295 for (i = 1; i < objc; i++) {
3296 name = TclGetString(objv[i]);
3297 namespacePtr = Tcl_FindNamespace(interp, name, NULL, /* flags */ 0);
3299 Tcl_DeleteNamespace(namespacePtr);
3306 *----------------------------------------------------------------------
3308 * NamespaceEvalCmd --
3310 * Invoked to implement the "namespace eval" command. Executes commands
3311 * in a namespace. If the namespace does not already exist, it is
3312 * created. Handles the following syntax:
3314 * namespace eval name arg ?arg...?
3316 * If more than one arg argument is specified, the command that is
3317 * executed is the result of concatenating the arguments together with a
3318 * space between each argument.
3321 * Returns TCL_OK if the namespace is found and the commands are executed
3322 * successfully. Returns TCL_ERROR if anything goes wrong.
3325 * Returns the result of the command in the interpreter's result object.
3326 * If anything goes wrong, this function returns an error message as the
3329 *----------------------------------------------------------------------
3334 ClientData clientData, /* Arbitrary value passed to cmd. */
3335 Tcl_Interp *interp, /* Current interpreter. */
3336 int objc, /* Number of arguments. */
3337 Tcl_Obj *const objv[]) /* Argument objects. */
3339 return Tcl_NRCallObjProc(interp, NRNamespaceEvalCmd, clientData, objc,
3345 ClientData dummy, /* Not used. */
3346 Tcl_Interp *interp, /* Current interpreter. */
3347 int objc, /* Number of arguments. */
3348 Tcl_Obj *const objv[]) /* Argument objects. */
3350 Interp *iPtr = (Interp *) interp;
3353 Tcl_Namespace *namespacePtr;
3354 CallFrame *framePtr, **framePtrPtr;
3359 Tcl_WrongNumArgs(interp, 1, objv, "name arg ?arg...?");
3364 * Try to resolve the namespace reference, caching the result in the
3365 * namespace object along the way.
3368 result = GetNamespaceFromObj(interp, objv[1], &namespacePtr);
3371 * If the namespace wasn't found, try to create it.
3374 if (result == TCL_ERROR) {
3375 const char *name = TclGetString(objv[1]);
3377 namespacePtr = Tcl_CreateNamespace(interp, name, NULL, NULL);
3378 if (namespacePtr == NULL) {
3384 * Make the specified namespace the current namespace and evaluate the
3388 /* This is needed to satisfy GCC 3.3's strict aliasing rules */
3389 framePtrPtr = &framePtr;
3390 (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr,
3391 namespacePtr, /*isProcCallFrame*/ 0);
3393 framePtr->objv = TclFetchEnsembleRoot(interp, objv, objc, &framePtr->objc);
3397 * TIP #280: Make actual argument location available to eval'd script.
3401 invoker = iPtr->cmdFramePtr;
3403 TclArgumentGet(interp, objPtr, &invoker, &word);
3406 * More than one argument: concatenate them together with spaces
3407 * between, then evaluate the result. Tcl_EvalObjEx will delete the
3408 * object when it decrements its refcount after eval'ing it.
3411 objPtr = Tcl_ConcatObj(objc-2, objv+2);
3417 * TIP #280: Make invoking context available to eval'd script.
3420 TclNRAddCallback(interp, NsEval_Callback, namespacePtr, "eval",
3422 return TclNREvalObjEx(interp, objPtr, 0, invoker, word);
3431 Tcl_Namespace *namespacePtr = data[0];
3433 if (result == TCL_ERROR) {
3434 int length = strlen(namespacePtr->fullName);
3436 int overflow = (length > limit);
3437 char *cmd = data[1];
3439 Tcl_AppendObjToErrorInfo(interp, Tcl_ObjPrintf(
3440 "\n (in namespace %s \"%.*s%s\" script line %d)",
3442 (overflow ? limit : length), namespacePtr->fullName,
3443 (overflow ? "..." : ""), Tcl_GetErrorLine(interp)));
3447 * Restore the previous "current" namespace.
3450 TclPopStackFrame(interp);
3455 *----------------------------------------------------------------------
3457 * NamespaceExistsCmd --
3459 * Invoked to implement the "namespace exists" command that returns true
3460 * if the given namespace currently exists, and false otherwise. Handles
3461 * the following syntax:
3463 * namespace exists name
3466 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3469 * Returns a result in the interpreter's result object. If anything goes
3470 * wrong, the result is an error message.
3472 *----------------------------------------------------------------------
3477 ClientData dummy, /* Not used. */
3478 Tcl_Interp *interp, /* Current interpreter. */
3479 int objc, /* Number of arguments. */
3480 Tcl_Obj *const objv[]) /* Argument objects. */
3482 Tcl_Namespace *namespacePtr;
3485 Tcl_WrongNumArgs(interp, 1, objv, "name");
3489 Tcl_SetObjResult(interp, Tcl_NewBooleanObj(
3490 GetNamespaceFromObj(interp, objv[1], &namespacePtr) == TCL_OK));
3495 *----------------------------------------------------------------------
3497 * NamespaceExportCmd --
3499 * Invoked to implement the "namespace export" command that specifies
3500 * which commands are exported from a namespace. The exported commands
3501 * are those that can be imported into another namespace using "namespace
3502 * import". Both commands defined in a namespace and commands the
3503 * namespace has imported can be exported by a namespace. This command
3504 * has the following syntax:
3506 * namespace export ?-clear? ?pattern pattern...?
3508 * Each pattern may contain "string match"-style pattern matching special
3509 * characters, but the pattern may not include any namespace qualifiers:
3510 * that is, the pattern must specify commands in the current (exporting)
3511 * namespace. The specified patterns are appended onto the namespace's
3512 * list of export patterns.
3514 * To reset the namespace's export pattern list, specify the "-clear"
3517 * If there are no export patterns and the "-clear" flag isn't given,
3518 * this command returns the namespace's current export list.
3521 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3524 * Returns a result in the interpreter's result object. If anything goes
3525 * wrong, the result is an error message.
3527 *----------------------------------------------------------------------
3532 ClientData dummy, /* Not used. */
3533 Tcl_Interp *interp, /* Current interpreter. */
3534 int objc, /* Number of arguments. */
3535 Tcl_Obj *const objv[]) /* Argument objects. */
3540 Tcl_WrongNumArgs(interp, 1, objv, "?-clear? ?pattern pattern...?");
3545 * If no pattern arguments are given, and "-clear" isn't specified, return
3546 * the namespace's current export pattern list.
3553 (void) Tcl_AppendExportList(interp, NULL, listPtr);
3554 Tcl_SetObjResult(interp, listPtr);
3559 * Process the optional "-clear" argument.
3563 if (strcmp("-clear", Tcl_GetString(objv[firstArg])) == 0) {
3564 Tcl_Export(interp, NULL, "::", 1);
3565 Tcl_ResetResult(interp);
3570 * Add each pattern to the namespace's export pattern list.
3573 for (i = firstArg; i < objc; i++) {
3574 int result = Tcl_Export(interp, NULL, Tcl_GetString(objv[i]), 0);
3575 if (result != TCL_OK) {
3583 *----------------------------------------------------------------------
3585 * NamespaceForgetCmd --
3587 * Invoked to implement the "namespace forget" command to remove imported
3588 * commands from a namespace. Handles the following syntax:
3590 * namespace forget ?pattern pattern...?
3592 * Each pattern is a name like "foo::*" or "a::b::x*". That is, the
3593 * pattern may include the special pattern matching characters recognized
3594 * by the "string match" command, but only in the command name at the end
3595 * of the qualified name; the special pattern characters may not appear
3596 * in a namespace name. All of the commands that match that pattern are
3597 * checked to see if they have an imported command in the current
3598 * namespace that refers to the matched command. If there is an alias, it
3602 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3605 * Imported commands are removed from the current namespace. If anything
3606 * goes wrong, this function returns an error message in the
3607 * interpreter's result object.
3609 *----------------------------------------------------------------------
3614 ClientData dummy, /* Not used. */
3615 Tcl_Interp *interp, /* Current interpreter. */
3616 int objc, /* Number of arguments. */
3617 Tcl_Obj *const objv[]) /* Argument objects. */
3619 const char *pattern;
3623 Tcl_WrongNumArgs(interp, 1, objv, "?pattern pattern...?");
3627 for (i = 1; i < objc; i++) {
3628 pattern = TclGetString(objv[i]);
3629 result = Tcl_ForgetImport(interp, NULL, pattern);
3630 if (result != TCL_OK) {
3638 *----------------------------------------------------------------------
3640 * NamespaceImportCmd --
3642 * Invoked to implement the "namespace import" command that imports
3643 * commands into a namespace. Handles the following syntax:
3645 * namespace import ?-force? ?pattern pattern...?
3647 * Each pattern is a namespace-qualified name like "foo::*", "a::b::x*",
3648 * or "bar::p". That is, the pattern may include the special pattern
3649 * matching characters recognized by the "string match" command, but only
3650 * in the command name at the end of the qualified name; the special
3651 * pattern characters may not appear in a namespace name. All of the
3652 * commands that match the pattern and which are exported from their
3653 * namespace are made accessible from the current namespace context. This
3654 * is done by creating a new "imported command" in the current namespace
3655 * that points to the real command in its original namespace; when the
3656 * imported command is called, it invokes the real command.
3658 * If an imported command conflicts with an existing command, it is
3659 * treated as an error. But if the "-force" option is included, then
3660 * existing commands are overwritten by the imported commands.
3662 * If there are no pattern arguments and the "-force" flag isn't given,
3663 * this command returns the list of commands currently imported in
3664 * the current namespace.
3667 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3670 * Adds imported commands to the current namespace. If anything goes
3671 * wrong, this function returns an error message in the interpreter's
3674 *----------------------------------------------------------------------
3679 ClientData dummy, /* Not used. */
3680 Tcl_Interp *interp, /* Current interpreter. */
3681 int objc, /* Number of arguments. */
3682 Tcl_Obj *const objv[]) /* Argument objects. */
3684 int allowOverwrite = 0;
3685 const char *string, *pattern;
3690 Tcl_WrongNumArgs(interp, 1, objv, "?-force? ?pattern pattern...?");
3695 * Skip over the optional "-force" as the first argument.
3699 if (firstArg < objc) {
3700 string = TclGetString(objv[firstArg]);
3701 if ((*string == '-') && (strcmp(string, "-force") == 0)) {
3707 * When objc == 1, command is just [namespace import]. Introspection
3708 * form to return list of imported commands.
3711 Tcl_HashEntry *hPtr;
3712 Tcl_HashSearch search;
3713 Namespace *nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
3717 for (hPtr = Tcl_FirstHashEntry(&nsPtr->cmdTable, &search);
3718 hPtr != NULL; hPtr = Tcl_NextHashEntry(&search)) {
3719 Command *cmdPtr = Tcl_GetHashValue(hPtr);
3721 if (cmdPtr->deleteProc == DeleteImportedCmd) {
3722 Tcl_ListObjAppendElement(NULL, listPtr, Tcl_NewStringObj(
3723 Tcl_GetHashKey(&nsPtr->cmdTable, hPtr) ,-1));
3726 Tcl_SetObjResult(interp, listPtr);
3731 * Handle the imports for each of the patterns.
3734 for (i = firstArg; i < objc; i++) {
3735 pattern = TclGetString(objv[i]);
3736 result = Tcl_Import(interp, NULL, pattern, allowOverwrite);
3737 if (result != TCL_OK) {
3745 *----------------------------------------------------------------------
3747 * NamespaceInscopeCmd --
3749 * Invoked to implement the "namespace inscope" command that executes a
3750 * script in the context of a particular namespace. This command is not
3751 * expected to be used directly by programmers; calls to it are generated
3752 * implicitly when programs use "namespace code" commands to register
3753 * callback scripts. Handles the following syntax:
3755 * namespace inscope name arg ?arg...?
3757 * The "namespace inscope" command is much like the "namespace eval"
3758 * command except that it has lappend semantics and the namespace must
3759 * already exist. It treats the first argument as a list, and appends any
3760 * arguments after the first onto the end as proper list elements. For
3763 * namespace inscope ::foo {a b} c d e
3767 * namespace eval ::foo [concat {a b} [list c d e]]
3769 * This lappend semantics is important because many callback scripts are
3770 * actually prefixes.
3773 * Returns TCL_OK to indicate success, or TCL_ERROR to indicate failure.
3776 * Returns a result in the Tcl interpreter's result object.
3778 *----------------------------------------------------------------------
3782 NamespaceInscopeCmd(
3783 ClientData clientData, /* Arbitrary value passed to cmd. */
3784 Tcl_Interp *interp, /* Current interpreter. */
3785 int objc, /* Number of arguments. */
3786 Tcl_Obj *const objv[]) /* Argument objects. */
3788 return Tcl_NRCallObjProc(interp, NRNamespaceInscopeCmd, clientData, objc,
3793 NRNamespaceInscopeCmd(
3794 ClientData dummy, /* Not used. */
3795 Tcl_Interp *interp, /* Current interpreter. */
3796 int objc, /* Number of arguments. */
3797 Tcl_Obj *const objv[]) /* Argument objects. */
3799 Tcl_Namespace *namespacePtr;
3800 CallFrame *framePtr, **framePtrPtr;
3805 Tcl_WrongNumArgs(interp, 1, objv, "name arg ?arg...?");
3810 * Resolve the namespace reference.
3813 if (TclGetNamespaceFromObj(interp, objv[1], &namespacePtr) != TCL_OK) {
3818 * Make the specified namespace the current namespace.
3821 framePtrPtr = &framePtr; /* This is needed to satisfy GCC's
3822 * strict aliasing rules. */
3823 (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr,
3824 namespacePtr, /*isProcCallFrame*/ 0);
3826 framePtr->objv = TclFetchEnsembleRoot(interp, objv, objc, &framePtr->objc);
3829 * Execute the command. If there is just one argument, just treat it as a
3830 * script and evaluate it. Otherwise, create a list from the arguments
3831 * after the first one, then concatenate the first argument and the list
3832 * of extra arguments to form the command to evaluate.
3836 cmdObjPtr = objv[2];
3838 Tcl_Obj *concatObjv[2];
3841 listPtr = Tcl_NewListObj(0, NULL);
3842 for (i = 3; i < objc; i++) {
3843 if (Tcl_ListObjAppendElement(interp, listPtr, objv[i]) != TCL_OK){
3844 Tcl_DecrRefCount(listPtr); /* Free unneeded obj. */
3849 concatObjv[0] = objv[2];
3850 concatObjv[1] = listPtr;
3851 cmdObjPtr = Tcl_ConcatObj(2, concatObjv);
3852 Tcl_DecrRefCount(listPtr); /* We're done with the list object. */
3855 TclNRAddCallback(interp, NsEval_Callback, namespacePtr, "inscope",
3857 return TclNREvalObjEx(interp, cmdObjPtr, 0, NULL, 0);
3861 *----------------------------------------------------------------------
3863 * NamespaceOriginCmd --
3865 * Invoked to implement the "namespace origin" command to return the
3866 * fully-qualified name of the "real" command to which the specified
3867 * "imported command" refers. Handles the following syntax:
3869 * namespace origin name
3872 * An imported command is created in an namespace when that namespace
3873 * imports a command from another namespace. If a command is imported
3874 * into a sequence of namespaces a, b,...,n where each successive
3875 * namespace just imports the command from the previous namespace, this
3876 * command returns the fully-qualified name of the original command in
3877 * the first namespace, a. If "name" does not refer to an alias, its
3878 * fully-qualified name is returned. The returned name is stored in the
3879 * interpreter's result object. This function returns TCL_OK if
3880 * successful, and TCL_ERROR if anything goes wrong.
3883 * If anything goes wrong, this function returns an error message in the
3884 * interpreter's result object.
3886 *----------------------------------------------------------------------
3891 ClientData dummy, /* Not used. */
3892 Tcl_Interp *interp, /* Current interpreter. */
3893 int objc, /* Number of arguments. */
3894 Tcl_Obj *const objv[]) /* Argument objects. */
3896 Tcl_Command command, origCommand;
3900 Tcl_WrongNumArgs(interp, 1, objv, "name");
3904 command = Tcl_GetCommandFromObj(interp, objv[1]);
3905 if (command == NULL) {
3906 Tcl_SetObjResult(interp, Tcl_ObjPrintf(
3907 "invalid command name \"%s\"", TclGetString(objv[1])));
3908 Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "COMMAND",
3909 TclGetString(objv[1]), NULL);
3912 origCommand = TclGetOriginalCommand(command);
3913 TclNewObj(resultPtr);
3914 if (origCommand == NULL) {
3916 * The specified command isn't an imported command. Return the
3917 * command's name qualified by the full name of the namespace it was
3921 Tcl_GetCommandFullName(interp, command, resultPtr);
3923 Tcl_GetCommandFullName(interp, origCommand, resultPtr);
3925 Tcl_SetObjResult(interp, resultPtr);
3930 *----------------------------------------------------------------------
3932 * NamespaceParentCmd --
3934 * Invoked to implement the "namespace parent" command that returns the
3935 * fully-qualified name of the parent namespace for a specified
3936 * namespace. Handles the following syntax:
3938 * namespace parent ?name?
3941 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
3944 * Returns a result in the interpreter's result object. If anything goes
3945 * wrong, the result is an error message.
3947 *----------------------------------------------------------------------
3952 ClientData dummy, /* Not used. */
3953 Tcl_Interp *interp, /* Current interpreter. */
3954 int objc, /* Number of arguments. */
3955 Tcl_Obj *const objv[]) /* Argument objects. */
3957 Tcl_Namespace *nsPtr;
3960 nsPtr = TclGetCurrentNamespace(interp);
3961 } else if (objc == 2) {
3962 if (TclGetNamespaceFromObj(interp, objv[1], &nsPtr) != TCL_OK) {
3966 Tcl_WrongNumArgs(interp, 1, objv, "?name?");
3971 * Report the parent of the specified namespace.
3974 if (nsPtr->parentPtr != NULL) {
3975 Tcl_SetObjResult(interp, Tcl_NewStringObj(
3976 nsPtr->parentPtr->fullName, -1));
3982 *----------------------------------------------------------------------
3984 * NamespacePathCmd --
3986 * Invoked to implement the "namespace path" command that reads and
3987 * writes the current namespace's command resolution path. Has one
3988 * optional argument: if present, it is a list of named namespaces to set
3989 * the path to, and if absent, the current path should be returned.
3990 * Handles the following syntax:
3992 * namespace path ?nsList?
3995 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong
3996 * (most notably if the namespace list contains the name of something
3997 * other than a namespace). In the successful-exit case, may set the
3998 * interpreter result to the list of names of the namespaces on the
3999 * current namespace's path.
4002 * May update the namespace path (triggering a recomputing of all command
4003 * names that depend on the namespace for resolution).
4005 *----------------------------------------------------------------------
4010 ClientData dummy, /* Not used. */
4011 Tcl_Interp *interp, /* Current interpreter. */
4012 int objc, /* Number of arguments. */
4013 Tcl_Obj *const objv[]) /* Argument objects. */
4015 Namespace *nsPtr = (Namespace *) TclGetCurrentNamespace(interp);
4016 int i, nsObjc, result = TCL_ERROR;
4018 Tcl_Namespace **namespaceList = NULL;
4021 Tcl_WrongNumArgs(interp, 1, objv, "?pathList?");
4026 * If no path is given, return the current path.
4032 TclNewObj(resultObj);
4033 for (i=0 ; i<nsPtr->commandPathLength ; i++) {
4034 if (nsPtr->commandPathArray[i].nsPtr != NULL) {
4035 Tcl_ListObjAppendElement(NULL, resultObj, Tcl_NewStringObj(
4036 nsPtr->commandPathArray[i].nsPtr->fullName, -1));
4039 Tcl_SetObjResult(interp, resultObj);
4044 * There is a path given, so parse it into an array of namespace pointers.
4047 if (TclListObjGetElements(interp, objv[1], &nsObjc, &nsObjv) != TCL_OK) {
4051 namespaceList = TclStackAlloc(interp,
4052 sizeof(Tcl_Namespace *) * nsObjc);
4054 for (i=0 ; i<nsObjc ; i++) {
4055 if (TclGetNamespaceFromObj(interp, nsObjv[i],
4056 &namespaceList[i]) != TCL_OK) {
4063 * Now we have the list of valid namespaces, install it as the path.
4066 TclSetNsPath(nsPtr, nsObjc, namespaceList);
4070 if (namespaceList != NULL) {
4071 TclStackFree(interp, namespaceList);
4077 *----------------------------------------------------------------------
4081 * Sets the namespace command name resolution path to the given list of
4082 * namespaces. If the list is empty (of zero length) the path is set to
4083 * empty and the default old-style behaviour of command name resolution
4090 * Invalidates the command name resolution caches for any command
4091 * resolved in the given namespace.
4093 *----------------------------------------------------------------------
4098 Namespace *nsPtr, /* Namespace whose path is to be set. */
4099 int pathLength, /* Length of pathAry. */
4100 Tcl_Namespace *pathAry[]) /* Array of namespaces that are the path. */
4102 if (pathLength != 0) {
4103 NamespacePathEntry *tmpPathArray =
4104 ckalloc(sizeof(NamespacePathEntry) * pathLength);
4107 for (i=0 ; i<pathLength ; i++) {
4108 tmpPathArray[i].nsPtr = (Namespace *) pathAry[i];
4109 tmpPathArray[i].creatorNsPtr = nsPtr;
4110 tmpPathArray[i].prevPtr = NULL;
4111 tmpPathArray[i].nextPtr =
4112 tmpPathArray[i].nsPtr->commandPathSourceList;
4113 if (tmpPathArray[i].nextPtr != NULL) {
4114 tmpPathArray[i].nextPtr->prevPtr = &tmpPathArray[i];
4116 tmpPathArray[i].nsPtr->commandPathSourceList = &tmpPathArray[i];
4118 if (nsPtr->commandPathLength != 0) {
4119 UnlinkNsPath(nsPtr);
4121 nsPtr->commandPathArray = tmpPathArray;
4123 if (nsPtr->commandPathLength != 0) {
4124 UnlinkNsPath(nsPtr);
4128 nsPtr->commandPathLength = pathLength;
4129 nsPtr->cmdRefEpoch++;
4130 nsPtr->resolverEpoch++;
4134 *----------------------------------------------------------------------
4138 * Delete the given namespace's command name resolution path. Only call
4139 * if the path is non-empty. Caller must reset the counter containing the
4146 * Deletes the array of path entries and unlinks those path entries from
4147 * the target namespace's list of interested namespaces.
4149 *----------------------------------------------------------------------
4157 for (i=0 ; i<nsPtr->commandPathLength ; i++) {
4158 NamespacePathEntry *nsPathPtr = &nsPtr->commandPathArray[i];
4160 if (nsPathPtr->prevPtr != NULL) {
4161 nsPathPtr->prevPtr->nextPtr = nsPathPtr->nextPtr;
4163 if (nsPathPtr->nextPtr != NULL) {
4164 nsPathPtr->nextPtr->prevPtr = nsPathPtr->prevPtr;
4166 if (nsPathPtr->nsPtr != NULL) {
4167 if (nsPathPtr->nsPtr->commandPathSourceList == nsPathPtr) {
4168 nsPathPtr->nsPtr->commandPathSourceList = nsPathPtr->nextPtr;
4172 ckfree(nsPtr->commandPathArray);
4176 *----------------------------------------------------------------------
4178 * TclInvalidateNsPath --
4180 * Invalidate the name resolution caches for all names looked up in
4181 * namespaces whose name path includes the given namespace.
4187 * Increments the command reference epoch in each namespace whose path
4188 * includes the given namespace. This causes any cached resolved names
4189 * whose root cacheing context starts at that namespace to be recomputed
4190 * the next time they are used.
4192 *----------------------------------------------------------------------
4196 TclInvalidateNsPath(
4199 NamespacePathEntry *nsPathPtr = nsPtr->commandPathSourceList;
4201 while (nsPathPtr != NULL) {
4202 if (nsPathPtr->nsPtr != NULL) {
4203 nsPathPtr->creatorNsPtr->cmdRefEpoch++;
4205 nsPathPtr = nsPathPtr->nextPtr;
4210 *----------------------------------------------------------------------
4212 * NamespaceQualifiersCmd --
4214 * Invoked to implement the "namespace qualifiers" command that returns
4215 * any leading namespace qualifiers in a string. These qualifiers are
4216 * namespace names separated by "::"s. For example, for "::foo::p" this
4217 * command returns "::foo", and for "::" it returns "". This command is
4218 * the complement of the "namespace tail" command. Note that this command
4219 * does not check whether the "namespace" names are, in fact, the names
4220 * of currently defined namespaces. Handles the following syntax:
4222 * namespace qualifiers string
4225 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4228 * Returns a result in the interpreter's result object. If anything goes
4229 * wrong, the result is an error message.
4231 *----------------------------------------------------------------------
4235 NamespaceQualifiersCmd(
4236 ClientData dummy, /* Not used. */
4237 Tcl_Interp *interp, /* Current interpreter. */
4238 int objc, /* Number of arguments. */
4239 Tcl_Obj *const objv[]) /* Argument objects. */
4241 const char *name, *p;
4245 Tcl_WrongNumArgs(interp, 1, objv, "string");
4250 * Find the end of the string, then work backward and find the start of
4251 * the last "::" qualifier.
4254 name = TclGetString(objv[1]);
4255 for (p = name; *p != '\0'; p++) {
4258 while (--p >= name) {
4259 if ((*p == ':') && (p > name) && (*(p-1) == ':')) {
4260 p -= 2; /* Back up over the :: */
4261 while ((p >= name) && (*p == ':')) {
4262 p--; /* Back up over the preceeding : */
4270 Tcl_SetObjResult(interp, Tcl_NewStringObj(name, length));
4276 *----------------------------------------------------------------------
4278 * NamespaceUnknownCmd --
4280 * Invoked to implement the "namespace unknown" command (TIP 181) that
4281 * sets or queries a per-namespace unknown command handler. This handler
4282 * is called when command lookup fails (current and global ns). The
4283 * default handler for the global namespace is ::unknown. The default
4284 * handler for other namespaces is to call the global namespace unknown
4285 * handler. Passing an empty list results in resetting the handler to its
4288 * namespace unknown ?handler?
4291 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4294 * If no handler is specified, returns a result in the interpreter's
4295 * result object, otherwise it sets the unknown handler pointer in the
4296 * current namespace to the script fragment provided. If anything goes
4297 * wrong, the result is an error message.
4299 *----------------------------------------------------------------------
4303 NamespaceUnknownCmd(
4304 ClientData dummy, /* Not used. */
4305 Tcl_Interp *interp, /* Current interpreter. */
4306 int objc, /* Number of arguments. */
4307 Tcl_Obj *const objv[]) /* Argument objects. */
4309 Tcl_Namespace *currNsPtr;
4314 Tcl_WrongNumArgs(interp, 1, objv, "?script?");
4318 currNsPtr = TclGetCurrentNamespace(interp);
4322 * Introspection - return the current namespace handler.
4325 resultPtr = Tcl_GetNamespaceUnknownHandler(interp, currNsPtr);
4326 if (resultPtr == NULL) {
4327 TclNewObj(resultPtr);
4329 Tcl_SetObjResult(interp, resultPtr);
4331 rc = Tcl_SetNamespaceUnknownHandler(interp, currNsPtr, objv[1]);
4333 Tcl_SetObjResult(interp, objv[1]);
4341 *----------------------------------------------------------------------
4343 * Tcl_GetNamespaceUnknownHandler --
4345 * Returns the unknown command handler registered for the given
4349 * Returns the current unknown command handler, or NULL if none exists
4350 * for the namespace.
4355 *----------------------------------------------------------------------
4359 Tcl_GetNamespaceUnknownHandler(
4360 Tcl_Interp *interp, /* The interpreter in which the namespace
4362 Tcl_Namespace *nsPtr) /* The namespace. */
4364 Namespace *currNsPtr = (Namespace *) nsPtr;
4366 if (currNsPtr->unknownHandlerPtr == NULL &&
4367 currNsPtr == ((Interp *) interp)->globalNsPtr) {
4369 * Default handler for global namespace is "::unknown". For all other
4370 * namespaces, it is NULL (which falls back on the global unknown
4374 TclNewLiteralStringObj(currNsPtr->unknownHandlerPtr, "::unknown");
4375 Tcl_IncrRefCount(currNsPtr->unknownHandlerPtr);
4377 return currNsPtr->unknownHandlerPtr;
4381 *----------------------------------------------------------------------
4383 * Tcl_SetNamespaceUnknownHandler --
4385 * Sets the unknown command handler for the given namespace to the
4386 * command prefix passed.
4389 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4392 * Sets the namespace unknown command handler. If the passed in handler
4393 * is NULL or an empty list, then the handler is reset to its default. If
4394 * an error occurs, then an error message is left in the interpreter
4397 *----------------------------------------------------------------------
4401 Tcl_SetNamespaceUnknownHandler(
4402 Tcl_Interp *interp, /* Interpreter in which the namespace
4404 Tcl_Namespace *nsPtr, /* Namespace which is being updated. */
4405 Tcl_Obj *handlerPtr) /* The new handler, or NULL to reset. */
4408 Namespace *currNsPtr = (Namespace *) nsPtr;
4411 * Ensure that we check for errors *first* before we change anything.
4414 if (handlerPtr != NULL) {
4415 if (TclListObjLength(interp, handlerPtr, &lstlen) != TCL_OK) {
4424 * We are going to be saving this handler. Increment the reference
4425 * count before decrementing the refcount on the previous handler,
4426 * so that nothing strange can happen if we are told to set the
4427 * handler to the previous value.
4430 Tcl_IncrRefCount(handlerPtr);
4435 * Remove old handler next.
4438 if (currNsPtr->unknownHandlerPtr != NULL) {
4439 Tcl_DecrRefCount(currNsPtr->unknownHandlerPtr);
4443 * Install the new handler.
4448 * Just store the handler. It already has the correct reference count.
4451 currNsPtr->unknownHandlerPtr = handlerPtr;
4454 * If NULL or an empty list is passed, this resets to the default
4458 currNsPtr->unknownHandlerPtr = NULL;
4464 *----------------------------------------------------------------------
4466 * NamespaceTailCmd --
4468 * Invoked to implement the "namespace tail" command that returns the
4469 * trailing name at the end of a string with "::" namespace qualifiers.
4470 * These qualifiers are namespace names separated by "::"s. For example,
4471 * for "::foo::p" this command returns "p", and for "::" it returns "".
4472 * This command is the complement of the "namespace qualifiers" command.
4473 * Note that this command does not check whether the "namespace" names
4474 * are, in fact, the names of currently defined namespaces. Handles the
4477 * namespace tail string
4480 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4483 * Returns a result in the interpreter's result object. If anything goes
4484 * wrong, the result is an error message.
4486 *----------------------------------------------------------------------
4491 ClientData dummy, /* Not used. */
4492 Tcl_Interp *interp, /* Current interpreter. */
4493 int objc, /* Number of arguments. */
4494 Tcl_Obj *const objv[]) /* Argument objects. */
4496 const char *name, *p;
4499 Tcl_WrongNumArgs(interp, 1, objv, "string");
4504 * Find the end of the string, then work backward and find the last "::"
4508 name = TclGetString(objv[1]);
4509 for (p = name; *p != '\0'; p++) {
4512 while (--p > name) {
4513 if ((*p == ':') && (*(p-1) == ':')) {
4514 p++; /* Just after the last "::" */
4520 Tcl_SetObjResult(interp, Tcl_NewStringObj(p, -1));
4526 *----------------------------------------------------------------------
4528 * NamespaceUpvarCmd --
4530 * Invoked to implement the "namespace upvar" command, that creates
4531 * variables in the current scope linked to variables in another
4532 * namespace. Handles the following syntax:
4534 * namespace upvar ns otherVar myVar ?otherVar myVar ...?
4537 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4540 * Creates new variables in the current scope, linked to the
4541 * corresponding variables in the stipulated nmamespace. If anything goes
4542 * wrong, the result is an error message.
4544 *----------------------------------------------------------------------
4549 ClientData dummy, /* Not used. */
4550 Tcl_Interp *interp, /* Current interpreter. */
4551 int objc, /* Number of arguments. */
4552 Tcl_Obj *const objv[]) /* Argument objects. */
4554 Interp *iPtr = (Interp *) interp;
4555 Tcl_Namespace *nsPtr, *savedNsPtr;
4556 Var *otherPtr, *arrayPtr;
4559 if (objc < 2 || (objc & 1)) {
4560 Tcl_WrongNumArgs(interp, 1, objv, "ns ?otherVar myVar ...?");
4564 if (TclGetNamespaceFromObj(interp, objv[1], &nsPtr) != TCL_OK) {
4571 for (; objc>0 ; objc-=2, objv+=2) {
4573 * Locate the other variable.
4576 savedNsPtr = (Tcl_Namespace *) iPtr->varFramePtr->nsPtr;
4577 iPtr->varFramePtr->nsPtr = (Namespace *) nsPtr;
4578 otherPtr = TclObjLookupVarEx(interp, objv[0], NULL,
4579 (TCL_NAMESPACE_ONLY|TCL_LEAVE_ERR_MSG|TCL_AVOID_RESOLVERS),
4580 "access", /*createPart1*/ 1, /*createPart2*/ 1, &arrayPtr);
4581 iPtr->varFramePtr->nsPtr = (Namespace *) savedNsPtr;
4582 if (otherPtr == NULL) {
4587 * Create the new variable and link it to otherPtr.
4590 myName = TclGetString(objv[1]);
4591 if (TclPtrMakeUpvar(interp, otherPtr, myName, 0, -1) != TCL_OK) {
4600 *----------------------------------------------------------------------
4602 * NamespaceWhichCmd --
4604 * Invoked to implement the "namespace which" command that returns the
4605 * fully-qualified name of a command or variable. If the specified
4606 * command or variable does not exist, it returns "". Handles the
4609 * namespace which ?-command? ?-variable? name
4612 * Returns TCL_OK if successful, and TCL_ERROR if anything goes wrong.
4615 * Returns a result in the interpreter's result object. If anything goes
4616 * wrong, the result is an error message.
4618 *----------------------------------------------------------------------
4623 ClientData dummy, /* Not used. */
4624 Tcl_Interp *interp, /* Current interpreter. */
4625 int objc, /* Number of arguments. */
4626 Tcl_Obj *const objv[]) /* Argument objects. */
4628 static const char *const opts[] = {
4629 "-command", "-variable", NULL
4634 if (objc < 2 || objc > 3) {
4636 Tcl_WrongNumArgs(interp, 1, objv, "?-command? ?-variable? name");
4638 } else if (objc == 3) {
4640 * Look for a flag controlling the lookup.
4643 if (Tcl_GetIndexFromObj(interp, objv[1], opts, "option", 0,
4644 &lookupType) != TCL_OK) {
4646 * Preserve old style of error message!
4649 Tcl_ResetResult(interp);
4654 TclNewObj(resultPtr);
4655 switch (lookupType) {
4656 case 0: { /* -command */
4657 Tcl_Command cmd = Tcl_GetCommandFromObj(interp, objv[objc-1]);
4660 Tcl_GetCommandFullName(interp, cmd, resultPtr);
4664 case 1: { /* -variable */
4665 Tcl_Var var = Tcl_FindNamespaceVar(interp,
4666 TclGetString(objv[objc-1]), NULL, /*flags*/ 0);
4669 Tcl_GetVariableFullName(interp, var, resultPtr);
4674 Tcl_SetObjResult(interp, resultPtr);
4679 *----------------------------------------------------------------------
4681 * FreeNsNameInternalRep --
4683 * Frees the resources associated with a nsName object's internal
4690 * Decrements the ref count of any Namespace structure pointed to by the
4691 * nsName's internal representation. If there are no more references to
4692 * the namespace, it's structure will be freed.
4694 *----------------------------------------------------------------------
4698 FreeNsNameInternalRep(
4699 Tcl_Obj *objPtr) /* nsName object with internal representation
4702 ResolvedNsName *resNamePtr = objPtr->internalRep.twoPtrValue.ptr1;
4705 * Decrement the reference count of the namespace. If there are no more
4706 * references, free it up.
4709 resNamePtr->refCount--;
4710 if (resNamePtr->refCount == 0) {
4712 * Decrement the reference count for the cached namespace. If the
4713 * namespace is dead, and there are no more references to it, free
4717 TclNsDecrRefCount(resNamePtr->nsPtr);
4720 objPtr->typePtr = NULL;
4724 *----------------------------------------------------------------------
4726 * DupNsNameInternalRep --
4728 * Initializes the internal representation of a nsName object to a copy
4729 * of the internal representation of another nsName object.
4735 * copyPtr's internal rep is set to refer to the same namespace
4736 * referenced by srcPtr's internal rep. Increments the ref count of the
4737 * ResolvedNsName structure used to hold the namespace reference.
4739 *----------------------------------------------------------------------
4743 DupNsNameInternalRep(
4744 Tcl_Obj *srcPtr, /* Object with internal rep to copy. */
4745 Tcl_Obj *copyPtr) /* Object with internal rep to set. */
4747 ResolvedNsName *resNamePtr = srcPtr->internalRep.twoPtrValue.ptr1;
4749 copyPtr->internalRep.twoPtrValue.ptr1 = resNamePtr;
4750 resNamePtr->refCount++;
4751 copyPtr->typePtr = &nsNameType;
4755 *----------------------------------------------------------------------
4757 * SetNsNameFromAny --
4759 * Attempt to generate a nsName internal representation for a Tcl object.
4762 * Returns TCL_OK if the value could be converted to a proper namespace
4763 * reference. Otherwise, it returns TCL_ERROR, along with an error
4764 * message in the interpreter's result object.
4767 * If successful, the object is made a nsName object. Its internal rep is
4768 * set to point to a ResolvedNsName, which contains a cached pointer to
4769 * the Namespace. Reference counts are kept on both the ResolvedNsName
4770 * and the Namespace, so we can keep track of their usage and free them
4773 *----------------------------------------------------------------------
4778 Tcl_Interp *interp, /* Points to the namespace in which to resolve
4779 * name. Also used for error reporting if not
4781 Tcl_Obj *objPtr) /* The object to convert. */
4784 Namespace *nsPtr, *dummy1Ptr, *dummy2Ptr;
4785 ResolvedNsName *resNamePtr;
4788 if (interp == NULL) {
4792 name = TclGetString(objPtr);
4793 TclGetNamespaceForQualName(interp, name, NULL, TCL_FIND_ONLY_NS,
4794 &nsPtr, &dummy1Ptr, &dummy2Ptr, &dummy);
4797 * If we found a namespace, then create a new ResolvedNsName structure
4798 * that holds a reference to it.
4801 if ((nsPtr == NULL) || (nsPtr->flags & NS_DYING)) {
4803 * Our failed lookup proves any previously cached nsName internalrep is no
4804 * longer valid. Get rid of it so we no longer waste memory storing
4805 * it, nor time determining its invalidity again and again.
4808 if (objPtr->typePtr == &nsNameType) {
4809 TclFreeIntRep(objPtr);
4815 resNamePtr = ckalloc(sizeof(ResolvedNsName));
4816 resNamePtr->nsPtr = nsPtr;
4817 if ((name[0] == ':') && (name[1] == ':')) {
4818 resNamePtr->refNsPtr = NULL;
4820 resNamePtr->refNsPtr = (Namespace *) Tcl_GetCurrentNamespace(interp);
4822 resNamePtr->refCount = 1;
4823 TclFreeIntRep(objPtr);
4824 objPtr->internalRep.twoPtrValue.ptr1 = resNamePtr;
4825 objPtr->typePtr = &nsNameType;
4830 *----------------------------------------------------------------------
4832 * TclGetNamespaceCommandTable --
4834 * Returns the hash table of commands.
4837 * Pointer to the hash table.
4842 *----------------------------------------------------------------------
4846 TclGetNamespaceCommandTable(
4847 Tcl_Namespace *nsPtr)
4849 return &((Namespace *) nsPtr)->cmdTable;
4853 *----------------------------------------------------------------------
4855 * TclGetNamespaceChildTable --
4857 * Returns the hash table of child namespaces.
4860 * Pointer to the hash table.
4863 * Might allocate memory.
4865 *----------------------------------------------------------------------
4869 TclGetNamespaceChildTable(
4870 Tcl_Namespace *nsPtr)
4872 Namespace *nPtr = (Namespace *) nsPtr;
4873 #ifndef BREAK_NAMESPACE_COMPAT
4874 return &nPtr->childTable;
4876 if (nPtr->childTablePtr == NULL) {
4877 nPtr->childTablePtr = ckalloc(sizeof(Tcl_HashTable));
4878 Tcl_InitHashTable(nPtr->childTablePtr, TCL_STRING_KEYS);
4880 return nPtr->childTablePtr;
4885 *----------------------------------------------------------------------
4887 * TclLogCommandInfo --
4889 * This function is invoked after an error occurs in an interpreter. It
4890 * adds information to iPtr->errorInfo/errorStack fields to describe the
4891 * command that was being executed when the error occurred. When pc and
4892 * tosPtr are non-NULL, conveying a bytecode execution "inner context",
4893 * and the offending instruction is suitable, that inner context is
4894 * recorded in errorStack.
4900 * Information about the command is added to errorInfo/errorStack and the
4901 * line number stored internally in the interpreter is set.
4903 *----------------------------------------------------------------------
4908 Tcl_Interp *interp, /* Interpreter in which to log information. */
4909 const char *script, /* First character in script containing
4910 * command (must be <= command). */
4911 const char *command, /* First character in command that generated
4913 int length, /* Number of bytes in command (-1 means use
4914 * all bytes up to first null byte). */
4915 const unsigned char *pc, /* Current pc of bytecode execution context */
4916 Tcl_Obj **tosPtr) /* Current stack of bytecode execution
4920 Interp *iPtr = (Interp *) interp;
4921 int overflow, limit = 150;
4922 Var *varPtr, *arrayPtr;
4924 if (iPtr->flags & ERR_ALREADY_LOGGED) {
4926 * Someone else has already logged error information for this command;
4927 * we shouldn't add anything more.
4933 if (command != NULL) {
4935 * Compute the line number where the error occurred.
4938 iPtr->errorLine = 1;
4939 for (p = script; p != command; p++) {
4946 length = strlen(command);
4948 overflow = (length > limit);
4949 Tcl_AppendObjToErrorInfo(interp, Tcl_ObjPrintf(
4950 "\n %s\n\"%.*s%s\"", ((iPtr->errorInfo == NULL)
4951 ? "while executing" : "invoked from within"),
4952 (overflow ? limit : length), command,
4953 (overflow ? "..." : "")));
4955 varPtr = TclObjLookupVarEx(interp, iPtr->eiVar, NULL, TCL_GLOBAL_ONLY,
4956 NULL, 0, 0, &arrayPtr);
4957 if ((varPtr == NULL) || !TclIsVarTraced(varPtr)) {
4959 * Should not happen.
4965 = Tcl_FindHashEntry(&iPtr->varTraces, (char *) varPtr);
4966 VarTrace *tracePtr = Tcl_GetHashValue(hPtr);
4968 if (tracePtr->traceProc != EstablishErrorInfoTraces) {
4970 * The most recent trace set on ::errorInfo is not the one the
4971 * core itself puts on last. This means some other code is
4972 * tracing the variable, and the additional trace(s) might be
4973 * write traces that expect the timing of writes to
4974 * ::errorInfo that existed Tcl releases before 8.5. To
4975 * satisfy that compatibility need, we write the current
4976 * -errorinfo value to the ::errorInfo variable.
4979 Tcl_ObjSetVar2(interp, iPtr->eiVar, NULL, iPtr->errorInfo,
4989 if (Tcl_IsShared(iPtr->errorStack)) {
4992 newObj = Tcl_DuplicateObj(iPtr->errorStack);
4993 Tcl_DecrRefCount(iPtr->errorStack);
4994 Tcl_IncrRefCount(newObj);
4995 iPtr->errorStack = newObj;
4997 if (iPtr->resetErrorStack) {
5000 iPtr->resetErrorStack = 0;
5001 Tcl_ListObjLength(interp, iPtr->errorStack, &len);
5004 * Reset while keeping the list internalrep as much as possible.
5007 Tcl_ListObjReplace(interp, iPtr->errorStack, 0, len, 0, NULL);
5009 Tcl_Obj *innerContext;
5011 innerContext = TclGetInnerContext(interp, pc, tosPtr);
5012 if (innerContext != NULL) {
5013 Tcl_ListObjAppendElement(NULL, iPtr->errorStack,
5014 iPtr->innerLiteral);
5015 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, innerContext);
5017 } else if (command != NULL) {
5018 Tcl_ListObjAppendElement(NULL, iPtr->errorStack,
5019 iPtr->innerLiteral);
5020 Tcl_ListObjAppendElement(NULL, iPtr->errorStack,
5021 Tcl_NewStringObj(command, length));
5025 if (!iPtr->framePtr->objc) {
5027 * Special frame, nothing to report.
5029 } else if (iPtr->varFramePtr != iPtr->framePtr) {
5031 * uplevel case, [lappend errorstack UP $relativelevel]
5034 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, iPtr->upLiteral);
5035 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, Tcl_NewIntObj(
5036 iPtr->framePtr->level - iPtr->varFramePtr->level));
5037 } else if (iPtr->framePtr != iPtr->rootFramePtr) {
5039 * normal case, [lappend errorstack CALL [info level 0]]
5042 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, iPtr->callLiteral);
5043 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, Tcl_NewListObj(
5044 iPtr->framePtr->objc, iPtr->framePtr->objv));
5049 *----------------------------------------------------------------------
5051 * TclErrorStackResetIf --
5053 * The TIP 348 reset/no-bc part of TLCI, for specific use by
5054 * TclCompileSyntaxError.
5060 * Reset errorstack if it needs be, and in that case remember the
5061 * passed-in error message as inner context.
5063 *----------------------------------------------------------------------
5067 TclErrorStackResetIf(
5072 Interp *iPtr = (Interp *) interp;
5074 if (Tcl_IsShared(iPtr->errorStack)) {
5077 newObj = Tcl_DuplicateObj(iPtr->errorStack);
5078 Tcl_DecrRefCount(iPtr->errorStack);
5079 Tcl_IncrRefCount(newObj);
5080 iPtr->errorStack = newObj;
5082 if (iPtr->resetErrorStack) {
5085 iPtr->resetErrorStack = 0;
5086 Tcl_ListObjLength(interp, iPtr->errorStack, &len);
5089 * Reset while keeping the list internalrep as much as possible.
5092 Tcl_ListObjReplace(interp, iPtr->errorStack, 0, len, 0, NULL);
5093 Tcl_ListObjAppendElement(NULL, iPtr->errorStack, iPtr->innerLiteral);
5094 Tcl_ListObjAppendElement(NULL, iPtr->errorStack,
5095 Tcl_NewStringObj(msg, length));
5100 *----------------------------------------------------------------------
5102 * Tcl_LogCommandInfo --
5104 * This function is invoked after an error occurs in an interpreter. It
5105 * adds information to iPtr->errorInfo/errorStack fields to describe the
5106 * command that was being executed when the error occurred.
5112 * Information about the command is added to errorInfo/errorStack and the
5113 * line number stored internally in the interpreter is set.
5115 *----------------------------------------------------------------------
5120 Tcl_Interp *interp, /* Interpreter in which to log information. */
5121 const char *script, /* First character in script containing
5122 * command (must be <= command). */
5123 const char *command, /* First character in command that generated
5125 int length) /* Number of bytes in command (-1 means use
5126 * all bytes up to first null byte). */
5128 TclLogCommandInfo(interp, script, command, length, NULL, NULL);