diff options
Diffstat (limited to 'generic/tclExecute.c')
| -rw-r--r-- | generic/tclExecute.c | 19 | 
1 files changed, 13 insertions, 6 deletions
| diff --git a/generic/tclExecute.c b/generic/tclExecute.c index 59412b8..4fd6dcc 100644 --- a/generic/tclExecute.c +++ b/generic/tclExecute.c @@ -11,7 +11,7 @@   * See the file "license.terms" for information on usage and redistribution   * of this file, and for a DISCLAIMER OF ALL WARRANTIES.   * - * RCS: @(#) $Id: tclExecute.c,v 1.94.2.20 2006/11/28 22:20:00 andreas_kupries Exp $ + * RCS: @(#) $Id: tclExecute.c,v 1.94.2.21 2007/03/13 16:26:32 dgp Exp $   */  #include "tclInt.h" @@ -4052,7 +4052,6 @@ TclExecuteByteCode(interp, codePtr)  	    int numLists = infoPtr->numLists;  	    Var *compiledLocals = iPtr->varFramePtr->compiledLocals;  	    Tcl_Obj *listPtr; -	    List *listRepPtr;  	    Var *iterVarPtr, *listVarPtr;  	    int iterNum, listTmpIndex, listLen, numVars;  	    int varIndex, valIndex, continueLoop, j; @@ -4106,15 +4105,23 @@ TclExecuteByteCode(interp, codePtr)  		    listVarPtr = &(compiledLocals[listTmpIndex]);  		    listPtr = listVarPtr->value.objPtr; -		    listRepPtr = (List *) listPtr->internalRep.twoPtrValue.ptr1; -		    listLen = listRepPtr->elemCount; -			 +  		    valIndex = (iterNum * numVars);  		    for (j = 0;  j < numVars;  j++) { +			Tcl_Obj **elements; + +			/* +			 * The call to TclPtrSetVar might shimmer listPtr, +			 * so re-fetch pointers every iteration for safety. +			 * See test foreach-10.1. +			 */ + +			Tcl_ListObjGetElements(NULL, listPtr, +				&listLen, &elements);  			if (valIndex >= listLen) {  			    TclNewObj(valuePtr);  			} else { -			    valuePtr = listRepPtr->elements[valIndex]; +			    valuePtr = elements[valIndex];  			}  			varIndex = varListPtr->varIndexes[j]; | 
