summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authordgp <dgp@users.sourceforge.net>2016-05-10 16:03:13 (GMT)
committerdgp <dgp@users.sourceforge.net>2016-05-10 16:03:13 (GMT)
commit08df07894566ad1a3cf2dc750ab9322761ee400f (patch)
tree620e18d988e661349d957eb09da1777d21f4b2f9
parent20baf86d1e03655bb6d7fae562091e95fe52db15 (diff)
parent313d238fb894ff0775f40ec5aee77627742a3b1b (diff)
downloadtcl-08df07894566ad1a3cf2dc750ab9322761ee400f.zip
tcl-08df07894566ad1a3cf2dc750ab9322761ee400f.tar.gz
tcl-08df07894566ad1a3cf2dc750ab9322761ee400f.tar.bz2
-rw-r--r--doc/clock.n13
-rw-r--r--generic/regc_lex.c19
-rw-r--r--generic/tclAssembly.c12
-rw-r--r--generic/tclCmdIL.c2
-rw-r--r--generic/tclCompCmdsGR.c47
-rw-r--r--generic/tclCompExpr.c7
-rw-r--r--generic/tclCompile.c147
-rw-r--r--generic/tclCompile.h8
-rw-r--r--generic/tclEvent.c3
-rw-r--r--generic/tclExecute.c48
-rw-r--r--generic/tclInt.h2
-rw-r--r--generic/tclObj.c5
-rw-r--r--generic/tclProc.c127
-rw-r--r--generic/tclStringObj.c4
-rw-r--r--generic/tclUtf.c22
-rw-r--r--generic/tclVar.c100
-rw-r--r--generic/tclZlib.c9
-rwxr-xr-xlibrary/clock.tcl60
-rw-r--r--library/tzdata/America/Caracas1
-rw-r--r--library/tzdata/Asia/Almaty103
-rw-r--r--library/tzdata/Asia/Anadyr4
-rw-r--r--library/tzdata/Asia/Aqtau107
-rw-r--r--library/tzdata/Asia/Aqtobe105
-rw-r--r--library/tzdata/Asia/Baku2
-rw-r--r--library/tzdata/Asia/Barnaul4
-rw-r--r--library/tzdata/Asia/Chita4
-rw-r--r--library/tzdata/Asia/Irkutsk4
-rw-r--r--library/tzdata/Asia/Kamchatka4
-rw-r--r--library/tzdata/Asia/Khandyga4
-rw-r--r--library/tzdata/Asia/Krasnoyarsk4
-rw-r--r--library/tzdata/Asia/Magadan5
-rw-r--r--library/tzdata/Asia/Novokuznetsk4
-rw-r--r--library/tzdata/Asia/Novosibirsk4
-rw-r--r--library/tzdata/Asia/Omsk4
-rw-r--r--library/tzdata/Asia/Oral106
-rw-r--r--library/tzdata/Asia/Qyzylorda105
-rw-r--r--library/tzdata/Asia/Sakhalin4
-rw-r--r--library/tzdata/Asia/Srednekolymsk4
-rw-r--r--library/tzdata/Asia/Tomsk73
-rw-r--r--library/tzdata/Asia/Ust-Nera4
-rw-r--r--library/tzdata/Asia/Vladivostok4
-rw-r--r--library/tzdata/Asia/Yakutsk4
-rw-r--r--library/tzdata/Asia/Yekaterinburg4
-rw-r--r--library/tzdata/Asia/Yerevan6
-rw-r--r--library/tzdata/Europe/Astrakhan5
-rw-r--r--library/tzdata/Europe/Kaliningrad4
-rw-r--r--library/tzdata/Europe/Kirov70
-rw-r--r--library/tzdata/Europe/Minsk3
-rw-r--r--library/tzdata/Europe/Moscow4
-rw-r--r--library/tzdata/Europe/Samara4
-rw-r--r--library/tzdata/Europe/Ulyanovsk4
-rw-r--r--library/tzdata/Europe/Volgograd5
-rw-r--r--tests/clock.test55
-rw-r--r--tests/lreplace.test43
-rw-r--r--tests/uplevel.test99
-rw-r--r--tests/utf.test2
-rw-r--r--tests/zlib.test18
-rw-r--r--unix/tclUnixNotfy.c70
-rw-r--r--unix/tclUnixThrd.c25
-rw-r--r--win/coffbase.txt1
-rw-r--r--win/tclWinNotify.c32
-rw-r--r--win/tclWinSock.c19
-rw-r--r--win/tclWinThrd.c33
63 files changed, 1061 insertions, 747 deletions
diff --git a/doc/clock.n b/doc/clock.n
index 889a5da..ac50e36 100644
--- a/doc/clock.n
+++ b/doc/clock.n
@@ -89,10 +89,9 @@ have 59 or 61 seconds.
.TP
\fIunit\fR
One of the words, \fBseconds\fR, \fBminutes\fR, \fBhours\fR,
-\fBdays\fR, \fBweeks\fR, \fBmonths\fR, or \fByears\fR, or
-any unique prefix of such a word. Used in conjunction with \fIcount\fR
-to identify an interval of time, for example, \fI3 seconds\fR or
-\fI1 year\fR.
+\fBdays\fR, \fBweekdays\fR, \fBweeks\fR, \fBmonths\fR, or \fByears\fR.
+Used in conjunction with \fIcount\fR to identify an interval of time,
+for example, \fI3 seconds\fR or \fI1 year\fR.
.SS "OPTIONS"
.TP
\fB\-base\fR time
@@ -175,8 +174,7 @@ given as its first argument. The remaining arguments (other than the
possible \fB\-timezone\fR, \fB\-locale\fR and \fB\-gmt\fR options)
are integers and keywords in alternation, where the keywords are chosen
from \fBseconds\fR, \fBminutes\fR, \fBhours\fR,
-\fBdays\fR, \fBweeks\fR, \fBmonths\fR, or \fByears\fR, or
-any unique prefix of such a word.
+\fBdays\fR, \fBweekdays\fR, \fBweeks\fR, \fBmonths\fR, or \fByears\fR.
.PP
Addition of seconds, minutes and hours is fairly straightforward;
the given time increment (times sixty for minutes, or 3600 for hours)
@@ -213,7 +211,8 @@ the given time to a calendar day and time of day in the appropriate
time zone and locale. The requisite number of days (weeks are converted
to days by multiplying by seven) is added to the calendar day, and
the date and time are then converted back to a count of seconds from
-the epoch time.
+the epoch time. The \fBweekdays\fR keyword is similar to \fBdays\fR,
+with the only difference that weekends - Saturdays and Sundays - are skipped.
.PP
Adding and subtracting a given number of days across the point that
the time changes at the start or end of summer time (Daylight Saving Time)
diff --git a/generic/regc_lex.c b/generic/regc_lex.c
index 16e3ae9..affcb48 100644
--- a/generic/regc_lex.c
+++ b/generic/regc_lex.c
@@ -256,20 +256,33 @@ static const chr brbacks[] = { /* \s within brackets */
CHR('s'), CHR('p'), CHR('a'), CHR('c'), CHR('e'),
CHR(':'), CHR(']')
};
+
+#define PUNCT_CONN \
+ CHR('_'), \
+ 0x203f /* UNDERTIE */, \
+ 0x2040 /* CHARACTER TIE */,\
+ 0x2054 /* INVERTED UNDERTIE */,\
+ 0xfe33 /* PRESENTATION FORM FOR VERTICAL LOW LINE */, \
+ 0xfe34 /* PRESENTATION FORM FOR VERTICAL WAVY LOW LINE */, \
+ 0xfe4d /* DASHED LOW LINE */, \
+ 0xfe4e /* CENTRELINE LOW LINE */, \
+ 0xfe4f /* WAVY LOW LINE */, \
+ 0xff3f /* FULLWIDTH LOW LINE */
+
static const chr backw[] = { /* \w */
CHR('['), CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_'), CHR(']')
+ CHR(':'), CHR(']'), PUNCT_CONN, CHR(']')
};
static const chr backW[] = { /* \W */
CHR('['), CHR('^'), CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_'), CHR(']')
+ CHR(':'), CHR(']'), PUNCT_CONN, CHR(']')
};
static const chr brbackw[] = { /* \w within brackets */
CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_')
+ CHR(':'), CHR(']'), PUNCT_CONN
};
/*
diff --git a/generic/tclAssembly.c b/generic/tclAssembly.c
index 6d5676b..4ad31d2 100644
--- a/generic/tclAssembly.c
+++ b/generic/tclAssembly.c
@@ -866,7 +866,7 @@ CompileAssembleObj(
* Not valid, so free it and regenerate.
*/
- FreeAssembleCodeInternalRep(objPtr);
+ TclFreeIntRep(objPtr);
}
/*
@@ -891,15 +891,13 @@ CompileAssembleObj(
*/
TclEmitOpcode(INST_DONE, &compEnv);
- TclInitByteCodeObj(objPtr, &compEnv);
- objPtr->typePtr = &assembleCodeType;
+ codePtr = TclInitByteCodeObj(objPtr, &assembleCodeType, &compEnv);
TclFreeCompileEnv(&compEnv);
/*
* Record the local variable context to which the bytecode pertains
*/
- codePtr = objPtr->internalRep.twoPtrValue.ptr1;
if (iPtr->varFramePtr->localCachePtr) {
codePtr->localCachePtr = iPtr->varFramePtr->localCachePtr;
codePtr->localCachePtr->refCount++;
@@ -4313,11 +4311,7 @@ FreeAssembleCodeInternalRep(
{
ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1;
- codePtr->refCount--;
- if (codePtr->refCount <= 0) {
- TclCleanupByteCode(codePtr);
- }
- objPtr->typePtr = NULL;
+ TclReleaseByteCode(codePtr);
}
/*
diff --git a/generic/tclCmdIL.c b/generic/tclCmdIL.c
index 739dca9..0d35397 100644
--- a/generic/tclCmdIL.c
+++ b/generic/tclCmdIL.c
@@ -2755,7 +2755,7 @@ Tcl_LreplaceObjCmd(
* (to allow for replacing the last elem).
*/
- if ((first >= listLen) && (listLen > 0)) {
+ if ((first > listLen) && (listLen > 0)) {
Tcl_SetObjResult(interp, Tcl_ObjPrintf(
"list doesn't contain element %s", TclGetString(objv[2])));
Tcl_SetErrorCode(interp, "TCL", "OPERATION", "LREPLACE", "BADIDX",
diff --git a/generic/tclCompCmdsGR.c b/generic/tclCompCmdsGR.c
index 9f430ea..ffe39ba 100644
--- a/generic/tclCompCmdsGR.c
+++ b/generic/tclCompCmdsGR.c
@@ -1489,6 +1489,15 @@ TclCompileLreplaceCmd(
}
/*
+ * idx1, idx2 are now in canonical form:
+ *
+ * - integer: [0,len+1]
+ * - end index: INDEX_END
+ * - -ive offset: INDEX_END-[len-1,0]
+ * - +ive offset: INDEX_END+1
+ */
+
+ /*
* Compilation fails when one index is end-based but the other isn't.
* Fixing this will require more bytecodes, but this is a workaround for
* now. [Bug 47ac84309b]
@@ -1521,6 +1530,9 @@ TclCompileLreplaceCmd(
idx1 = 0;
goto dropEnd;
} else {
+ if (idx2 < idx1) {
+ idx2 = idx1 - 1;
+ }
if (idx1 > 0) {
tmpObj = Tcl_NewIntObj(idx1);
Tcl_IncrRefCount(tmpObj);
@@ -1548,9 +1560,7 @@ TclCompileLreplaceCmd(
idx1 = 0;
goto replaceTail;
} else {
- if (idx1 > 0 && idx2 > 0 && idx2 < idx1) {
- idx2 = idx1 - 1;
- } else if (idx1 < 0 && idx2 < 0 && idx2 < idx1) {
+ if (idx2 < idx1) {
idx2 = idx1 - 1;
}
if (idx1 > 0) {
@@ -1566,7 +1576,7 @@ TclCompileLreplaceCmd(
* operate on.
*/
- dropAll:
+ dropAll: /* This just ensures the arg is a list. */
TclEmitOpcode( INST_LIST_LENGTH, envPtr);
TclEmitOpcode( INST_POP, envPtr);
PushStringLiteral(envPtr, "");
@@ -1579,12 +1589,21 @@ TclCompileLreplaceCmd(
dropRange:
if (tmpObj != NULL) {
+ /*
+ * Emit bytecode to check the list length.
+ */
+
TclEmitOpcode( INST_DUP, envPtr);
TclEmitOpcode( INST_LIST_LENGTH, envPtr);
TclEmitPush(TclAddLiteralObj(envPtr, tmpObj, NULL), envPtr);
- TclEmitOpcode( INST_GT, envPtr);
+ TclEmitOpcode( INST_GE, envPtr);
offset = CurrentOffset(envPtr);
TclEmitInstInt1( INST_JUMP_TRUE1, 0, envPtr);
+
+ /*
+ * Emit an error if we've been given an empty list.
+ */
+
TclEmitOpcode( INST_DUP, envPtr);
TclEmitOpcode( INST_LIST_LENGTH, envPtr);
offset2 = CurrentOffset(envPtr);
@@ -1635,16 +1654,30 @@ TclCompileLreplaceCmd(
replaceRange:
if (tmpObj != NULL) {
+ /*
+ * Emit bytecode to check the list length.
+ */
+
TclEmitOpcode( INST_DUP, envPtr);
TclEmitOpcode( INST_LIST_LENGTH, envPtr);
+
+ /*
+ * Check the list length vs idx1.
+ */
+
TclEmitPush(TclAddLiteralObj(envPtr, tmpObj, NULL), envPtr);
- TclEmitOpcode( INST_GT, envPtr);
+ TclEmitOpcode( INST_GE, envPtr);
offset = CurrentOffset(envPtr);
TclEmitInstInt1( INST_JUMP_TRUE1, 0, envPtr);
+
+ /*
+ * Emit an error if we've been given an empty list.
+ */
+
TclEmitOpcode( INST_DUP, envPtr);
TclEmitOpcode( INST_LIST_LENGTH, envPtr);
offset2 = CurrentOffset(envPtr);
- TclEmitInstInt1( INST_JUMP_TRUE1, 0, envPtr);
+ TclEmitInstInt1( INST_JUMP_FALSE1, 0, envPtr);
TclEmitPush(TclAddLiteralObj(envPtr, Tcl_ObjPrintf(
"list doesn't contain element %d", idx1), NULL), envPtr);
CompileReturnInternal(envPtr, INST_RETURN_IMM, TCL_ERROR, 0,
diff --git a/generic/tclCompExpr.c b/generic/tclCompExpr.c
index 4390282..654666a 100644
--- a/generic/tclCompExpr.c
+++ b/generic/tclCompExpr.c
@@ -2181,7 +2181,6 @@ ExecConstantExprTree(
CompileEnv *envPtr;
ByteCode *byteCodePtr;
int code;
- Tcl_Obj *byteCodeObj = Tcl_NewObj();
NRE_callback *rootPtr = TOP_CB(interp);
/*
@@ -2195,14 +2194,12 @@ ExecConstantExprTree(
CompileExprTree(interp, nodes, index, litObjvPtr, NULL, NULL, envPtr,
0 /* optimize */);
TclEmitOpcode(INST_DONE, envPtr);
- Tcl_IncrRefCount(byteCodeObj);
- TclInitByteCodeObj(byteCodeObj, envPtr);
+ byteCodePtr = TclInitByteCode(envPtr);
TclFreeCompileEnv(envPtr);
TclStackFree(interp, envPtr);
- byteCodePtr = byteCodeObj->internalRep.twoPtrValue.ptr1;
TclNRExecuteByteCode(interp, byteCodePtr);
code = TclNRRunCallbacks(interp, TCL_OK, rootPtr);
- Tcl_DecrRefCount(byteCodeObj);
+ TclReleaseByteCode(byteCodePtr);
return code;
}
diff --git a/generic/tclCompile.c b/generic/tclCompile.c
index c0b5dcc..96b418c 100644
--- a/generic/tclCompile.c
+++ b/generic/tclCompile.c
@@ -661,6 +661,7 @@ InstructionDesc const tclInstructionTable[] = {
* Prototypes for procedures defined later in this file:
*/
+static void CleanupByteCode(ByteCode *codePtr);
static ByteCode * CompileSubstObj(Tcl_Interp *interp, Tcl_Obj *objPtr,
int flags);
static void DupByteCodeInternalRep(Tcl_Obj *srcPtr,
@@ -676,6 +677,7 @@ static void FreeSubstCodeInternalRep(Tcl_Obj *objPtr);
static int GetCmdLocEncodingSize(CompileEnv *envPtr);
static int IsCompactibleCompileEnv(Tcl_Interp *interp,
CompileEnv *envPtr);
+static void PreventCycle(Tcl_Obj *objPtr, CompileEnv *envPtr);
#ifdef TCL_COMPILE_STATS
static void RecordByteCodeStats(ByteCode *codePtr);
#endif /* TCL_COMPILE_STATS */
@@ -866,7 +868,7 @@ TclSetByteCodeFromAny(
#endif /*TCL_COMPILE_DEBUG*/
if (result == TCL_OK) {
- TclInitByteCodeObj(objPtr, &compEnv);
+ (void) TclInitByteCodeObj(objPtr, &tclByteCodeType, &compEnv);
#ifdef TCL_COMPILE_DEBUG
if (tclTraceCompile >= 2) {
TclPrintByteCodeObj(interp, objPtr);
@@ -967,16 +969,13 @@ FreeByteCodeInternalRep(
{
register ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1;
- objPtr->typePtr = NULL;
- if (codePtr->refCount-- <= 1) {
- TclCleanupByteCode(codePtr);
- }
+ TclReleaseByteCode(codePtr);
}
/*
*----------------------------------------------------------------------
*
- * TclCleanupByteCode --
+ * TclReleaseByteCode --
*
* This procedure does all the real work of freeing up a bytecode
* object's ByteCode structure. It's called only when the structure's
@@ -993,7 +992,26 @@ FreeByteCodeInternalRep(
*/
void
-TclCleanupByteCode(
+TclPreserveByteCode(
+ register ByteCode *codePtr)
+{
+ codePtr->refCount++;
+}
+
+void
+TclReleaseByteCode(
+ register ByteCode *codePtr)
+{
+ if (--codePtr->refCount) {
+ return;
+ }
+
+ /* Just dropped to refcount==0. Clean up. */
+ CleanupByteCode(codePtr);
+}
+
+static void
+CleanupByteCode(
register ByteCode *codePtr) /* Points to the ByteCode to free. */
{
Tcl_Interp *interp = (Tcl_Interp *) *codePtr->interpHandle;
@@ -1260,8 +1278,6 @@ Tcl_NRSubstObj(
*
* Results:
* A (ByteCode *) is returned pointing to the resulting ByteCode.
- * The caller must manage its refCount and arrange for a call to
- * TclCleanupByteCode() when the last reference disappears.
*
* Side effects:
* The Tcl_ObjType of objPtr is changed to the "substcode" type, and the
@@ -1292,7 +1308,7 @@ CompileSubstObj(
|| (codePtr->nsEpoch != nsPtr->resolverEpoch)
|| (codePtr->localCachePtr !=
iPtr->varFramePtr->localCachePtr)) {
- FreeSubstCodeInternalRep(objPtr);
+ TclFreeIntRep(objPtr);
}
}
if (objPtr->typePtr != &substCodeType) {
@@ -1306,11 +1322,9 @@ CompileSubstObj(
TclSubstCompile(interp, bytes, numBytes, flags, 1, &compEnv);
TclEmitOpcode(INST_DONE, &compEnv);
- TclInitByteCodeObj(objPtr, &compEnv);
- objPtr->typePtr = &substCodeType;
+ codePtr = TclInitByteCodeObj(objPtr, &substCodeType, &compEnv);
TclFreeCompileEnv(&compEnv);
- codePtr = objPtr->internalRep.twoPtrValue.ptr1;
objPtr->internalRep.twoPtrValue.ptr1 = codePtr;
objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(flags);
if (iPtr->varFramePtr->localCachePtr) {
@@ -1353,10 +1367,7 @@ FreeSubstCodeInternalRep(
{
register ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1;
- objPtr->typePtr = NULL;
- if (codePtr->refCount-- <= 1) {
- TclCleanupByteCode(codePtr);
- }
+ TclReleaseByteCode(codePtr);
}
static void
@@ -2697,11 +2708,40 @@ TclCompileNoOp(
*----------------------------------------------------------------------
*/
-void
-TclInitByteCodeObj(
- Tcl_Obj *objPtr, /* Points object that should be initialized,
- * and whose string rep contains the source
- * code. */
+static void
+PreventCycle(
+ Tcl_Obj *objPtr,
+ CompileEnv *envPtr)
+{
+ int i;
+
+ for (i = 0; i < envPtr->literalArrayNext; i++) {
+ if (objPtr == TclFetchLiteral(envPtr, i)) {
+ /*
+ * Prevent circular reference where the bytecode intrep of
+ * a value contains a literal which is that same value.
+ * If this is allowed to happen, refcount decrements may not
+ * reach zero, and memory may leak. Bugs 467523, 3357771
+ *
+ * NOTE: [Bugs 3392070, 3389764] We make a copy based completely
+ * on the string value, and do not call Tcl_DuplicateObj() so we
+ * can be sure we do not have any lingering cycles hiding in
+ * the intrep.
+ */
+ int numBytes;
+ const char *bytes = Tcl_GetStringFromObj(objPtr, &numBytes);
+ Tcl_Obj *copyPtr = Tcl_NewStringObj(bytes, numBytes);
+
+ Tcl_IncrRefCount(copyPtr);
+ TclReleaseLiteral((Tcl_Interp *)envPtr->iPtr, objPtr);
+
+ envPtr->literalArrayPtr[i].objPtr = copyPtr;
+ }
+ }
+}
+
+ByteCode *
+TclInitByteCode(
register CompileEnv *envPtr)/* Points to the CompileEnv structure from
* which to create a ByteCode structure. */
{
@@ -2752,7 +2792,8 @@ TclInitByteCodeObj(
codePtr->compileEpoch = iPtr->compileEpoch;
codePtr->nsPtr = namespacePtr;
codePtr->nsEpoch = namespacePtr->resolverEpoch;
- codePtr->refCount = 1;
+ codePtr->refCount = 0;
+ TclPreserveByteCode(codePtr);
if (namespacePtr->compiledVarResProc || iPtr->resolverPtr) {
codePtr->flags = TCL_BYTECODE_RESOLVE_VARS;
} else {
@@ -2778,29 +2819,7 @@ TclInitByteCodeObj(
p += TCL_ALIGN(codeBytes); /* align object array */
codePtr->objArrayPtr = (Tcl_Obj **) p;
for (i = 0; i < numLitObjects; i++) {
- Tcl_Obj *fetched = TclFetchLiteral(envPtr, i);
-
- if (objPtr == fetched) {
- /*
- * Prevent circular reference where the bytecode intrep of
- * a value contains a literal which is that same value.
- * If this is allowed to happen, refcount decrements may not
- * reach zero, and memory may leak. Bugs 467523, 3357771
- *
- * NOTE: [Bugs 3392070, 3389764] We make a copy based completely
- * on the string value, and do not call Tcl_DuplicateObj() so we
- * can be sure we do not have any lingering cycles hiding in
- * the intrep.
- */
- int numBytes;
- const char *bytes = Tcl_GetStringFromObj(objPtr, &numBytes);
-
- codePtr->objArrayPtr[i] = Tcl_NewStringObj(bytes, numBytes);
- Tcl_IncrRefCount(codePtr->objArrayPtr[i]);
- TclReleaseLiteral((Tcl_Interp *)iPtr, objPtr);
- } else {
- codePtr->objArrayPtr[i] = fetched;
- }
+ codePtr->objArrayPtr[i] = TclFetchLiteral(envPtr, i);
}
p += TCL_ALIGN(objArrayBytes); /* align exception range array */
@@ -2843,15 +2862,6 @@ TclInitByteCodeObj(
#endif /* TCL_COMPILE_STATS */
/*
- * Free the old internal rep then convert the object to a bytecode object
- * by making its internal rep point to the just compiled ByteCode.
- */
-
- TclFreeIntRep(objPtr);
- objPtr->internalRep.twoPtrValue.ptr1 = codePtr;
- objPtr->typePtr = &tclByteCodeType;
-
- /*
* TIP #280. Associate the extended per-word line information with the
* byte code object (internal rep), for use with the bc compiler.
*/
@@ -2864,6 +2874,33 @@ TclInitByteCodeObj(
envPtr->iPtr = NULL;
codePtr->localCachePtr = NULL;
+ return codePtr;
+}
+
+ByteCode *
+TclInitByteCodeObj(
+ Tcl_Obj *objPtr, /* Points object that should be initialized,
+ * and whose string rep contains the source
+ * code. */
+ const Tcl_ObjType *typePtr,
+ register CompileEnv *envPtr)/* Points to the CompileEnv structure from
+ * which to create a ByteCode structure. */
+{
+ ByteCode *codePtr;
+
+ PreventCycle(objPtr, envPtr);
+
+ codePtr = TclInitByteCode(envPtr);
+
+ /*
+ * Free the old internal rep then convert the object to a bytecode object
+ * by making its internal rep point to the just compiled ByteCode.
+ */
+
+ TclFreeIntRep(objPtr);
+ objPtr->internalRep.twoPtrValue.ptr1 = codePtr;
+ objPtr->typePtr = typePtr;
+ return codePtr;
}
/*
diff --git a/generic/tclCompile.h b/generic/tclCompile.h
index d5bc86b..f99c07c 100644
--- a/generic/tclCompile.h
+++ b/generic/tclCompile.h
@@ -1067,7 +1067,6 @@ MODULE_SCOPE ByteCode * TclCompileObj(Tcl_Interp *interp, Tcl_Obj *objPtr,
MODULE_SCOPE int TclAttemptCompileProc(Tcl_Interp *interp,
Tcl_Parse *parsePtr, int depth, Command *cmdPtr,
CompileEnv *envPtr);
-MODULE_SCOPE void TclCleanupByteCode(ByteCode *codePtr);
MODULE_SCOPE void TclCleanupStackForBreakContinue(CompileEnv *envPtr,
ExceptionAux *auxPtr);
MODULE_SCOPE void TclCompileCmdWord(Tcl_Interp *interp,
@@ -1119,8 +1118,9 @@ MODULE_SCOPE int TclFixupForwardJump(CompileEnv *envPtr,
int distThreshold);
MODULE_SCOPE void TclFreeCompileEnv(CompileEnv *envPtr);
MODULE_SCOPE void TclFreeJumpFixupArray(JumpFixupArray *fixupArrayPtr);
-MODULE_SCOPE void TclInitByteCodeObj(Tcl_Obj *objPtr,
- CompileEnv *envPtr);
+MODULE_SCOPE ByteCode * TclInitByteCode(CompileEnv *envPtr);
+MODULE_SCOPE ByteCode * TclInitByteCodeObj(Tcl_Obj *objPtr,
+ const Tcl_ObjType *typePtr, CompileEnv *envPtr);
MODULE_SCOPE void TclInitCompileEnv(Tcl_Interp *interp,
CompileEnv *envPtr, const char *string,
int numBytes, const CmdFrame *invoker, int word);
@@ -1157,6 +1157,8 @@ MODULE_SCOPE void TclPushVarName(Tcl_Interp *interp,
Tcl_Token *varTokenPtr, CompileEnv *envPtr,
int flags, int *localIndexPtr,
int *isScalarPtr);
+MODULE_SCOPE void TclPreserveByteCode(ByteCode *codePtr);
+MODULE_SCOPE void TclReleaseByteCode(ByteCode *codePtr);
MODULE_SCOPE void TclReleaseLiteral(Tcl_Interp *interp, Tcl_Obj *objPtr);
MODULE_SCOPE void TclInvalidateCmdLiteral(Tcl_Interp *interp,
const char *name, Namespace *nsPtr);
diff --git a/generic/tclEvent.c b/generic/tclEvent.c
index 8305410..a16a3b1 100644
--- a/generic/tclEvent.c
+++ b/generic/tclEvent.c
@@ -1043,6 +1043,9 @@ TclInitSubsystems(void)
#if USE_TCLALLOC
TclInitAlloc(); /* Process wide mutex init */
#endif
+#if defined(TCL_THREADS) && defined(USE_THREAD_ALLOC)
+ TclpInitAllocCache();
+#endif
#ifdef TCL_MEM_DEBUG
TclInitDbCkalloc(); /* Process wide mutex init */
#endif
diff --git a/generic/tclExecute.c b/generic/tclExecute.c
index d4077f5..cd28a92 100644
--- a/generic/tclExecute.c
+++ b/generic/tclExecute.c
@@ -35,14 +35,14 @@
#endif
/*
- * A mask (should be 2**n-1) that is used to work out when the bytecode engine
- * should call Tcl_AsyncReady() to see whether there is a signal that needs
- * handling.
+ * A counter that is used to work out when the bytecode engine should call
+ * Tcl_AsyncReady() to see whether there is a signal that needs handling, and
+ * other expensive periodic operations.
*/
-#ifndef ASYNC_CHECK_COUNT_MASK
-# define ASYNC_CHECK_COUNT_MASK 63
-#endif /* !ASYNC_CHECK_COUNT_MASK */
+#ifndef ASYNC_CHECK_COUNT
+# define ASYNC_CHECK_COUNT 64
+#endif /* !ASYNC_CHECK_COUNT */
/*
* Boolean flag indicating whether the Tcl bytecode interpreter has been
@@ -1499,11 +1499,9 @@ ExprObjCallback(
*
* Results:
* A (ByteCode *) is returned pointing to the resulting ByteCode.
- * The caller must manage its refCount and arrange for a call to
- * TclCleanupByteCode() when the last reference disappears.
*
* Side effects:
- * The Tcl_ObjType of objPtr is changed to the "bytecode" type,
+ * The Tcl_ObjType of objPtr is changed to the "exprcode" type,
* and the ByteCode is kept in the internal rep (along with context
* data for checking validity) for faster operations the next time
* CompileExprObj is called on the same value.
@@ -1536,7 +1534,7 @@ CompileExprObj(
|| (codePtr->nsPtr != namespacePtr)
|| (codePtr->nsEpoch != namespacePtr->resolverEpoch)
|| (codePtr->localCachePtr != iPtr->varFramePtr->localCachePtr)) {
- FreeExprCodeInternalRep(objPtr);
+ TclFreeIntRep(objPtr);
}
}
if (objPtr->typePtr != &exprCodeType) {
@@ -1567,10 +1565,8 @@ CompileExprObj(
*/
TclEmitOpcode(INST_DONE, &compEnv);
- TclInitByteCodeObj(objPtr, &compEnv);
- objPtr->typePtr = &exprCodeType;
+ codePtr = TclInitByteCodeObj(objPtr, &exprCodeType, &compEnv);
TclFreeCompileEnv(&compEnv);
- codePtr = objPtr->internalRep.twoPtrValue.ptr1;
if (iPtr->varFramePtr->localCachePtr) {
codePtr->localCachePtr = iPtr->varFramePtr->localCachePtr;
codePtr->localCachePtr->refCount++;
@@ -1644,10 +1640,7 @@ FreeExprCodeInternalRep(
{
ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1;
- objPtr->typePtr = NULL;
- if (codePtr->refCount-- <= 1) {
- TclCleanupByteCode(codePtr);
- }
+ TclReleaseByteCode(codePtr);
}
/*
@@ -2033,7 +2026,7 @@ TclNRExecuteByteCode(
* sizeof(void *);
int numWords = (size + sizeof(Tcl_Obj *) - 1) / sizeof(Tcl_Obj *);
- codePtr->refCount++;
+ TclPreserveByteCode(codePtr);
/*
* Reserve the stack, setup the TEBCdataPtr (TD) and CallFrame
@@ -2115,8 +2108,14 @@ TEBCresume(
* sporadically: no special need for speed.
*/
- int instructionCount = 0; /* Counter that is used to work out when to
- * call Tcl_AsyncReady() */
+ unsigned interruptCounter = 1;
+ /* Counter that is used to work out when to
+ * call Tcl_AsyncReady(). This must be 1
+ * initially so that we call the async-check
+ * stanza early, otherwise there are command
+ * sequences that can make the interpreter
+ * busy-loop without an opportunity to
+ * recognise an interrupt. */
const char *curInstName;
#ifdef TCL_COMPILE_DEBUG
int traceInstructions; /* Whether we are doing instruction-level
@@ -2314,10 +2313,11 @@ TEBCresume(
/*
* Check for asynchronous handlers [Bug 746722]; we do the check every
- * ASYNC_CHECK_COUNT_MASK instruction, of the form (2**n-1).
+ * ASYNC_CHECK_COUNT instructions.
*/
- if ((instructionCount++ & ASYNC_CHECK_COUNT_MASK) == 0) {
+ if ((--interruptCounter) == 0) {
+ interruptCounter = ASYNC_CHECK_COUNT;
DECACHE_STACK_INFO();
if (TclAsyncReady(iPtr)) {
result = Tcl_AsyncInvoke(interp, result);
@@ -8182,9 +8182,7 @@ TEBCresume(
}
iPtr->cmdFramePtr = bcFramePtr->nextPtr;
- if (codePtr->refCount-- <= 1) {
- TclCleanupByteCode(codePtr);
- }
+ TclReleaseByteCode(codePtr);
TclStackFree(interp, TD); /* free my stack */
return result;
diff --git a/generic/tclInt.h b/generic/tclInt.h
index 42c13dd..1dab0cb 100644
--- a/generic/tclInt.h
+++ b/generic/tclInt.h
@@ -3133,6 +3133,7 @@ MODULE_SCOPE int TclTrimLeft(const char *bytes, int numBytes,
MODULE_SCOPE int TclTrimRight(const char *bytes, int numBytes,
const char *trim, int numTrim);
MODULE_SCOPE int TclUtfCasecmp(const char *cs, const char *ct);
+MODULE_SCOPE int TclUtfCount(int ch);
MODULE_SCOPE Tcl_Obj * TclpNativeToNormalized(ClientData clientData);
MODULE_SCOPE Tcl_Obj * TclpFilesystemPathType(Tcl_Obj *pathPtr);
MODULE_SCOPE int TclpDlopen(Tcl_Interp *interp, Tcl_Obj *pathPtr,
@@ -4084,6 +4085,7 @@ MODULE_SCOPE void TclFreeAllocCache(void *);
MODULE_SCOPE void * TclpGetAllocCache(void);
MODULE_SCOPE void TclpSetAllocCache(void *);
MODULE_SCOPE void TclpFreeAllocMutex(Tcl_Mutex *mutex);
+MODULE_SCOPE void TclpInitAllocCache(void);
MODULE_SCOPE void TclpFreeAllocCache(void *);
/*
diff --git a/generic/tclObj.c b/generic/tclObj.c
index c641152..a45a392 100644
--- a/generic/tclObj.c
+++ b/generic/tclObj.c
@@ -320,7 +320,7 @@ const Tcl_HashKeyType tclObjHashKeyType = {
* does allow them to delete a command when references to it are gone, which
* is fragile but useful given their somewhat-OO style. Because of this, this
* structure MUST NOT be const so that the C compiler puts the data in
- * writable memory. [Bug 2558422]
+ * writable memory. [Bug 2558422] [Bug 07d13d99b0a9]
* TODO: Provide a better API for those extensions so that they can coexist...
*/
@@ -4176,7 +4176,8 @@ Tcl_GetCommandFromObj(
* had is invalid one way or another.
*/
- if (SetCmdNameFromAny(interp, objPtr) != TCL_OK) {
+ /* See [07d13d99b0a9] why we cannot call SetCmdNameFromAny() directly here. */
+ if (tclCmdNameType.setFromAnyProc(interp, objPtr) != TCL_OK) {
return NULL;
}
resPtr = objPtr->internalRep.twoPtrValue.ptr1;
diff --git a/generic/tclProc.c b/generic/tclProc.c
index ac65bde..172b860 100644
--- a/generic/tclProc.c
+++ b/generic/tclProc.c
@@ -69,9 +69,8 @@ const Tcl_ObjType tclProcBodyType = {
};
/*
- * The [upvar]/[uplevel] level reference type. Uses the twoPtrValue field,
- * encoding the type of level reference in ptr and the actual parsed out
- * offset in ptr2.
+ * The [upvar]/[uplevel] level reference type. Uses the longValue field
+ * to remember the integer value of a parsed #<integer> format.
*
* Uses the default behaviour throughout, and never disposes of the string
* rep; it's just a cache type.
@@ -785,7 +784,7 @@ TclGetFrame(
* Results:
* The return value is -1 if an error occurred in finding the frame (in
* this case an error message is left in the interp's result). 1 is
- * returned if objPtr was either a number or a number preceded by "#" and
+ * returned if objPtr was either an int or an int preceded by "#" and
* it specified a valid frame. 0 is returned if objPtr isn't one of the
* two things above (in this case, the lookup acts as if objPtr were
* "1"). The variable pointed to by framePtrPtr is filled in with the
@@ -807,95 +806,69 @@ TclObjGetFrame(
{
register Interp *iPtr = (Interp *) interp;
int curLevel, level, result;
- CallFrame *framePtr;
- const char *name;
+ const char *name = NULL;
/*
* Parse object to figure out which level number to go to.
*/
- result = 1;
+ result = 0;
curLevel = iPtr->varFramePtr->level;
- if (objPtr == NULL) {
- name = "1";
- goto haveLevel1;
- }
-
- name = TclGetString(objPtr);
- if (objPtr->typePtr == &levelReferenceType) {
- if (objPtr->internalRep.twoPtrValue.ptr1) {
- level = curLevel - PTR2INT(objPtr->internalRep.twoPtrValue.ptr2);
- } else {
- level = PTR2INT(objPtr->internalRep.twoPtrValue.ptr2);
- }
- if (level < 0) {
- goto levelError;
- }
- /* TODO: Consider skipping the typePtr checks */
- } else if (objPtr->typePtr == &tclIntType
-#ifndef TCL_WIDE_INT_IS_LONG
- || objPtr->typePtr == &tclWideIntType
-#endif
- ) {
- if (TclGetIntFromObj(NULL, objPtr, &level) != TCL_OK || level < 0) {
- goto levelError;
- }
- level = curLevel - level;
- } else if (*name == '#') {
- if (Tcl_GetInt(interp, name+1, &level) != TCL_OK || level < 0) {
- goto levelError;
- }
- /*
- * Cache for future reference.
- */
-
- TclFreeIntRep(objPtr);
- objPtr->typePtr = &levelReferenceType;
- objPtr->internalRep.twoPtrValue.ptr1 = (void *) 0;
- objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(level);
- } else if (isdigit(UCHAR(*name))) { /* INTL: digit */
- if (Tcl_GetInt(interp, name, &level) != TCL_OK) {
- return -1;
- }
-
- /*
- * Cache for future reference.
- */
+ /*
+ * Check for integer first, since that has potential to spare us
+ * a generation of a stringrep.
+ */
- TclFreeIntRep(objPtr);
- objPtr->typePtr = &levelReferenceType;
- objPtr->internalRep.twoPtrValue.ptr1 = (void *) 1;
- objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(level);
+ if (objPtr == NULL) {
+ /* Do nothing */
+ } else if (TCL_OK == Tcl_GetIntFromObj(NULL, objPtr, &level)
+ && (level >= 0)) {
level = curLevel - level;
+ result = 1;
+ } else if (objPtr->typePtr == &levelReferenceType) {
+ level = (int) objPtr->internalRep.longValue;
+ result = 1;
} else {
- /*
- * Don't cache as the object *isn't* a level reference (might even be
- * NULL...)
- */
+ name = TclGetString(objPtr);
+ if (name[0] == '#') {
+ if (TCL_OK == Tcl_GetInt(NULL, name+1, &level) && level >= 0) {
+ TclFreeIntRep(objPtr);
+ objPtr->typePtr = &levelReferenceType;
+ objPtr->internalRep.longValue = level;
+ result = 1;
+ } else {
+ result = -1;
+ }
+ } else if (isdigit(UCHAR(name[0]))) { /* INTL: digit */
+ /*
+ * If this were an integer, we'd have succeeded already.
+ * Docs say we have to treat this as a 'bad level' error.
+ */
+ result = -1;
+ }
+ }
- haveLevel1:
+ if (result == 0) {
level = curLevel - 1;
- result = 0;
+ name = "1";
}
-
- /*
- * Figure out which frame to use, and return it to the caller.
- */
-
- for (framePtr = iPtr->varFramePtr; framePtr != NULL;
- framePtr = framePtr->callerVarPtr) {
- if (framePtr->level == level) {
- break;
+ if (result != -1) {
+ if (level >= 0) {
+ CallFrame *framePtr;
+ for (framePtr = iPtr->varFramePtr; framePtr != NULL;
+ framePtr = framePtr->callerVarPtr) {
+ if (framePtr->level == level) {
+ *framePtrPtr = framePtr;
+ return result;
+ }
+ }
+ }
+ if (name == NULL) {
+ name = TclGetString(objPtr);
}
}
- if (framePtr == NULL) {
- goto levelError;
- }
- *framePtrPtr = framePtr;
- return result;
- levelError:
Tcl_SetObjResult(interp, Tcl_ObjPrintf("bad level \"%s\"", name));
Tcl_SetErrorCode(interp, "TCL", "VALUE", "STACKLEVEL", NULL);
return -1;
diff --git a/generic/tclStringObj.c b/generic/tclStringObj.c
index e718749..b480735 100644
--- a/generic/tclStringObj.c
+++ b/generic/tclStringObj.c
@@ -2967,7 +2967,7 @@ ExtendStringRepWithUnicode(
*/
int i, origLength, size = 0;
- char *dst, buf[TCL_UTF_MAX];
+ char *dst;
String *stringPtr = GET_STRING(objPtr);
if (numChars < 0) {
@@ -2993,7 +2993,7 @@ ExtendStringRepWithUnicode(
}
for (i = 0; i < numChars && size >= 0; i++) {
- size += Tcl_UniCharToUtf((int) unicode[i], buf);
+ size += TclUtfCount(unicode[i]);
}
if (size < 0) {
Tcl_Panic("max size for a Tcl value (%d bytes) exceeded", INT_MAX);
diff --git a/generic/tclUtf.c b/generic/tclUtf.c
index b878149..6c4cb7f 100644
--- a/generic/tclUtf.c
+++ b/generic/tclUtf.c
@@ -84,17 +84,11 @@ static const unsigned char totalBytes[256] = {
1,1,1,1
#endif
};
-
-/*
- * Functions used only in this module.
- */
-
-static int UtfCount(int ch);
/*
*---------------------------------------------------------------------------
*
- * UtfCount --
+ * TclUtfCount --
*
* Find the number of bytes in the Utf character "ch".
*
@@ -107,8 +101,8 @@ static int UtfCount(int ch);
*---------------------------------------------------------------------------
*/
-INLINE static int
-UtfCount(
+int
+TclUtfCount(
int ch) /* The Tcl_UniChar whose size is returned. */
{
if ((ch > 0) && (ch < UNICODE_SELF)) {
@@ -143,7 +137,7 @@ UtfCount(
*---------------------------------------------------------------------------
*/
-INLINE int
+int
Tcl_UniCharToUtf(
int ch, /* The Tcl_UniChar to be stored in the
* buffer. */
@@ -829,7 +823,7 @@ Tcl_UtfToUpper(
* char to dst if its size is <= the original char.
*/
- if (bytes < UtfCount(upChar)) {
+ if (bytes < TclUtfCount(upChar)) {
memcpy(dst, src, (size_t) bytes);
dst += bytes;
} else {
@@ -882,7 +876,7 @@ Tcl_UtfToLower(
* char to dst if its size is <= the original char.
*/
- if (bytes < UtfCount(lowChar)) {
+ if (bytes < TclUtfCount(lowChar)) {
memcpy(dst, src, (size_t) bytes);
dst += bytes;
} else {
@@ -932,7 +926,7 @@ Tcl_UtfToTitle(
bytes = TclUtfToUniChar(src, &ch);
titleChar = Tcl_UniCharToTitle(ch);
- if (bytes < UtfCount(titleChar)) {
+ if (bytes < TclUtfCount(titleChar)) {
memcpy(dst, src, (size_t) bytes);
dst += bytes;
} else {
@@ -944,7 +938,7 @@ Tcl_UtfToTitle(
bytes = TclUtfToUniChar(src, &ch);
lowChar = Tcl_UniCharToLower(ch);
- if (bytes < UtfCount(lowChar)) {
+ if (bytes < TclUtfCount(lowChar)) {
memcpy(dst, src, (size_t) bytes);
dst += bytes;
} else {
diff --git a/generic/tclVar.c b/generic/tclVar.c
index 5574f30..b5b5b10 100644
--- a/generic/tclVar.c
+++ b/generic/tclVar.c
@@ -202,14 +202,9 @@ MODULE_SCOPE Var * TclLookupSimpleVar(Tcl_Interp *interp,
static Tcl_DupInternalRepProc DupLocalVarName;
static Tcl_FreeInternalRepProc FreeLocalVarName;
-static Tcl_UpdateStringProc PanicOnUpdateVarName;
static Tcl_FreeInternalRepProc FreeParsedVarName;
static Tcl_DupInternalRepProc DupParsedVarName;
-static Tcl_UpdateStringProc UpdateParsedVarName;
-
-static Tcl_UpdateStringProc PanicOnUpdateVarName;
-static Tcl_SetFromAnyProc PanicOnSetVarName;
/*
* Types of Tcl_Objs used to cache variable lookups.
@@ -232,12 +227,12 @@ static Tcl_SetFromAnyProc PanicOnSetVarName;
static const Tcl_ObjType localVarNameType = {
"localVarName",
- FreeLocalVarName, DupLocalVarName, PanicOnUpdateVarName, PanicOnSetVarName
+ FreeLocalVarName, DupLocalVarName, NULL, NULL
};
static const Tcl_ObjType tclParsedVarNameType = {
"parsedVarName",
- FreeParsedVarName, DupParsedVarName, UpdateParsedVarName, PanicOnSetVarName
+ FreeParsedVarName, DupParsedVarName, NULL, NULL
};
/*
@@ -536,7 +531,6 @@ TclObjLookupVarEx(
const char *errMsg = NULL;
CallFrame *varFramePtr = iPtr->varFramePtr;
const char *part2 = part2Ptr? TclGetString(part2Ptr):NULL;
- char *newPart2 = NULL;
*arrayPtrPtr = NULL;
if (typePtr == &localVarNameType) {
@@ -583,9 +577,7 @@ TclObjLookupVarEx(
}
return NULL;
}
- part2 = newPart2 = part1Ptr->internalRep.twoPtrValue.ptr2;
- if (newPart2) {
- part2Ptr = Tcl_NewStringObj(newPart2, -1);
+ if ((part2Ptr = part1Ptr->internalRep.twoPtrValue.ptr2)) {
if (createPart2) {
Tcl_IncrRefCount(part2Ptr);
}
@@ -629,11 +621,7 @@ TclObjLookupVarEx(
len2 = len1 - i - 2;
len1 = i;
- newPart2 = ckalloc(len2 + 1);
- memcpy(newPart2, part2, (unsigned) len2);
- *(newPart2+len2) = '\0';
- part2 = newPart2;
- part2Ptr = Tcl_NewStringObj(newPart2, -1);
+ part2Ptr = Tcl_NewStringObj(part2, len2);
if (createPart2) {
Tcl_IncrRefCount(part2Ptr);
}
@@ -658,7 +646,8 @@ TclObjLookupVarEx(
Tcl_IncrRefCount(part1Ptr);
objPtr->internalRep.twoPtrValue.ptr1 = part1Ptr;
- objPtr->internalRep.twoPtrValue.ptr2 = (void *) part2;
+ Tcl_IncrRefCount(part2Ptr);
+ objPtr->internalRep.twoPtrValue.ptr2 = part2Ptr;
typePtr = part1Ptr->typePtr;
part1 = TclGetString(part1Ptr);
@@ -683,9 +672,6 @@ TclObjLookupVarEx(
Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "VARNAME",
TclGetString(part1Ptr), NULL);
}
- if (newPart2) {
- Tcl_DecrRefCount(part2Ptr);
- }
return NULL;
}
@@ -734,9 +720,6 @@ TclObjLookupVarEx(
*arrayPtrPtr = varPtr;
varPtr = TclLookupArrayElement(interp, part1Ptr, part2Ptr, flags, msg,
createPart1, createPart2, varPtr, -1);
- if (newPart2) {
- Tcl_DecrRefCount(part2Ptr);
- }
}
return varPtr;
}
@@ -5518,28 +5501,6 @@ TclObjVarErrMsg(
*/
/*
- * Panic functions that should never be called in normal operation.
- */
-
-static void
-PanicOnUpdateVarName(
- Tcl_Obj *objPtr)
-{
- Tcl_Panic("%s of type %s should not be called", "updateStringProc",
- objPtr->typePtr->name);
-}
-
-static int
-PanicOnSetVarName(
- Tcl_Interp *interp,
- Tcl_Obj *objPtr)
-{
- Tcl_Panic("%s of type %s should not be called", "setFromAnyProc",
- objPtr->typePtr->name);
- return TCL_ERROR;
-}
-
-/*
* localVarName -
*
* INTERNALREP DEFINITION:
@@ -5592,11 +5553,11 @@ FreeParsedVarName(
Tcl_Obj *objPtr)
{
register Tcl_Obj *arrayPtr = objPtr->internalRep.twoPtrValue.ptr1;
- register char *elem = objPtr->internalRep.twoPtrValue.ptr2;
+ register Tcl_Obj *elem = objPtr->internalRep.twoPtrValue.ptr2;
if (arrayPtr != NULL) {
TclDecrRefCount(arrayPtr);
- ckfree(elem);
+ TclDecrRefCount(elem);
}
objPtr->typePtr = NULL;
}
@@ -5607,58 +5568,17 @@ DupParsedVarName(
Tcl_Obj *dupPtr)
{
register Tcl_Obj *arrayPtr = srcPtr->internalRep.twoPtrValue.ptr1;
- register char *elem = srcPtr->internalRep.twoPtrValue.ptr2;
- char *elemCopy;
- unsigned elemLen;
+ register Tcl_Obj *elem = srcPtr->internalRep.twoPtrValue.ptr2;
if (arrayPtr != NULL) {
Tcl_IncrRefCount(arrayPtr);
- elemLen = strlen(elem);
- elemCopy = ckalloc(elemLen + 1);
- memcpy(elemCopy, elem, elemLen);
- *(elemCopy + elemLen) = '\0';
- elem = elemCopy;
+ Tcl_IncrRefCount(elem);
}
dupPtr->internalRep.twoPtrValue.ptr1 = arrayPtr;
dupPtr->internalRep.twoPtrValue.ptr2 = elem;
dupPtr->typePtr = &tclParsedVarNameType;
}
-
-static void
-UpdateParsedVarName(
- Tcl_Obj *objPtr)
-{
- Tcl_Obj *arrayPtr = objPtr->internalRep.twoPtrValue.ptr1;
- char *part2 = objPtr->internalRep.twoPtrValue.ptr2;
- const char *part1;
- char *p;
- int len1, len2, totalLen;
-
- if (arrayPtr == NULL) {
- /*
- * This is a parsed scalar name: what is it doing here?
- */
-
- Tcl_Panic("scalar parsedVarName without a string rep");
- }
-
- part1 = TclGetStringFromObj(arrayPtr, &len1);
- len2 = strlen(part2);
-
- totalLen = len1 + len2 + 2;
- p = ckalloc(totalLen + 1);
- objPtr->bytes = p;
- objPtr->length = totalLen;
-
- memcpy(p, part1, (unsigned) len1);
- p += len1;
- *p++ = '(';
- memcpy(p, part2, (unsigned) len2);
- p += len2;
- *p++ = ')';
- *p = '\0';
-}
/*
*----------------------------------------------------------------------
diff --git a/generic/tclZlib.c b/generic/tclZlib.c
index 50d9a30..691d57a 100644
--- a/generic/tclZlib.c
+++ b/generic/tclZlib.c
@@ -1194,11 +1194,12 @@ Tcl_ZlibStreamPut(
zshPtr->stream.next_out = (Bytef *) dataTmp;
e = deflate(&zshPtr->stream, flush);
- while (e == Z_BUF_ERROR) {
+ while (e == Z_BUF_ERROR || (flush == Z_FINISH && e == Z_OK)) {
/*
- * Output buffer too small to hold the data being generated; so
- * put a new buffer into place after saving the old generated
- * data to the outData list.
+ * Output buffer too small to hold the data being generated or we
+ * are doing the end-of-stream flush (which can spit out masses of
+ * data). This means we need to put a new buffer into place after
+ * saving the old generated data to the outData list.
*/
obj = Tcl_NewByteArrayObj((unsigned char *) dataTmp, outSize);
diff --git a/library/clock.tcl b/library/clock.tcl
index 8e4b657..535a67d 100755
--- a/library/clock.tcl
+++ b/library/clock.tcl
@@ -4248,7 +4248,7 @@ proc ::tcl::clock::add { clockval args } {
?-gmt boolean? ?-locale LOCALE? ?-timezone ZONE?\""
}
if { [catch { expr {wide($clockval)} } result] } {
- return -code error $result
+ return -code error "expected integer but got \"$clockval\""
}
set offsets {}
@@ -4287,9 +4287,6 @@ proc ::tcl::clock::add { clockval args } {
-errorcode [list CLOCK gmtWithTimezone] \
"cannot use -gmt and -timezone in same call"
}
- if { [catch { expr { wide($clockval) } } result] } {
- return -code error "expected integer but got \"$clockval\""
- }
if { ![string is boolean -strict $gmt] } {
return -code error "expected boolean value but got \"$gmt\""
} elseif { $gmt } {
@@ -4326,6 +4323,11 @@ proc ::tcl::clock::add { clockval args } {
$changeover]
}
+ weekdays - weekday {
+ set clockval [AddWeekDays $quantity $clockval $timezone \
+ $changeover]
+ }
+
hours - hour {
set clockval [expr { 3600 * $quantity + $clockval }]
}
@@ -4425,6 +4427,56 @@ proc ::tcl::clock::AddMonths { months clockval timezone changeover } {
#----------------------------------------------------------------------
#
+# AddWeekDays --
+#
+# Add a given number of week days (skipping Saturdays and Sundays)
+# to a given clock value in a given time zone.
+#
+# Parameters:
+# days - Number of days to add (may be negative)
+# clockval - Seconds since the epoch before the operation
+# timezone - Time zone in which the operation is to be performed
+# changeover - Julian Day on which the Gregorian calendar was adopted
+# in the target locale.
+#
+# Results:
+# Returns the new clock value as a number of seconds since the epoch.
+#
+# Side effects:
+# None.
+#
+#----------------------------------------------------------------------
+
+proc ::tcl::clock::AddWeekDays { days clockval timezone changeover } {
+
+ if {$days == 0} {
+ return $clockval
+ }
+
+ set day [format $clockval -format %u]
+
+ set weeks [expr {$days / 5}]
+ set rdays [expr {$days % 5}]
+ set toAdd [expr {7 * $weeks + $rdays}]
+ set resDay [expr {$day + ($toAdd % 7)}]
+
+ # Adjust if we start from a weekend
+ if {$day > 5} {
+ set adj [expr {5 - $day}]
+ incr toAdd $adj
+ incr resDay $adj
+ }
+
+ # Adjust if we end up on a weekend
+ if {$resDay > 5} {
+ incr toAdd 2
+ }
+
+ AddDays $toAdd $clockval $timezone $changeover
+}
+
+#----------------------------------------------------------------------
+#
# AddDays --
#
# Add a given number of days to a given clock value in a given time
diff --git a/library/tzdata/America/Caracas b/library/tzdata/America/Caracas
index 2ba87ae..253c4ce 100644
--- a/library/tzdata/America/Caracas
+++ b/library/tzdata/America/Caracas
@@ -6,4 +6,5 @@ set TZData(:America/Caracas) {
{-1826739140 -16200 0 VET}
{-157750200 -14400 0 VET}
{1197183600 -16200 0 VET}
+ {1462086000 -14400 0 VET}
}
diff --git a/library/tzdata/Asia/Almaty b/library/tzdata/Asia/Almaty
index 68dee29..2b83197 100644
--- a/library/tzdata/Asia/Almaty
+++ b/library/tzdata/Asia/Almaty
@@ -2,55 +2,56 @@
set TZData(:Asia/Almaty) {
{-9223372036854775808 18468 0 LMT}
- {-1441170468 18000 0 ALMT}
- {-1247547600 21600 0 ALMT}
- {354909600 25200 1 ALMST}
- {370717200 21600 0 ALMT}
- {386445600 25200 1 ALMST}
- {402253200 21600 0 ALMT}
- {417981600 25200 1 ALMST}
- {433789200 21600 0 ALMT}
- {449604000 25200 1 ALMST}
- {465336000 21600 0 ALMT}
- {481060800 25200 1 ALMST}
- {496785600 21600 0 ALMT}
- {512510400 25200 1 ALMST}
- {528235200 21600 0 ALMT}
- {543960000 25200 1 ALMST}
- {559684800 21600 0 ALMT}
- {575409600 25200 1 ALMST}
- {591134400 21600 0 ALMT}
- {606859200 25200 1 ALMST}
- {622584000 21600 0 ALMT}
- {638308800 25200 1 ALMST}
- {654638400 21600 0 ALMT}
- {662666400 21600 0 ALMT}
- {694202400 21600 0 ALMT}
- {701802000 25200 1 ALMST}
- {717523200 21600 0 ALMT}
- {733262400 25200 1 ALMST}
- {748987200 21600 0 ALMT}
- {764712000 25200 1 ALMST}
- {780436800 21600 0 ALMT}
- {796161600 25200 1 ALMST}
- {811886400 21600 0 ALMT}
- {828216000 25200 1 ALMST}
- {846360000 21600 0 ALMT}
- {859665600 25200 1 ALMST}
- {877809600 21600 0 ALMT}
- {891115200 25200 1 ALMST}
- {909259200 21600 0 ALMT}
- {922564800 25200 1 ALMST}
- {941313600 21600 0 ALMT}
- {954014400 25200 1 ALMST}
- {972763200 21600 0 ALMT}
- {985464000 25200 1 ALMST}
- {1004212800 21600 0 ALMT}
- {1017518400 25200 1 ALMST}
- {1035662400 21600 0 ALMT}
- {1048968000 25200 1 ALMST}
- {1067112000 21600 0 ALMT}
- {1080417600 25200 1 ALMST}
- {1099166400 21600 0 ALMT}
- {1110823200 21600 0 ALMT}
+ {-1441170468 18000 0 +05}
+ {-1247547600 21600 0 +06}
+ {354909600 25200 1 +07}
+ {370717200 21600 0 +06}
+ {386445600 25200 1 +07}
+ {402253200 21600 0 +06}
+ {417981600 25200 1 +07}
+ {433789200 21600 0 +06}
+ {449604000 25200 1 +07}
+ {465336000 21600 0 +06}
+ {481060800 25200 1 +07}
+ {496785600 21600 0 +06}
+ {512510400 25200 1 +07}
+ {528235200 21600 0 +06}
+ {543960000 25200 1 +07}
+ {559684800 21600 0 +06}
+ {575409600 25200 1 +07}
+ {591134400 21600 0 +06}
+ {606859200 25200 1 +07}
+ {622584000 21600 0 +06}
+ {638308800 25200 1 +07}
+ {654638400 21600 0 +06}
+ {670363200 18000 0 +05}
+ {670366800 21600 1 +06}
+ {686091600 18000 0 +05}
+ {695768400 21600 0 +06}
+ {701812800 25200 1 +07}
+ {717537600 21600 0 +06}
+ {733262400 25200 1 +07}
+ {748987200 21600 0 +06}
+ {764712000 25200 1 +07}
+ {780436800 21600 0 +06}
+ {796161600 25200 1 +07}
+ {811886400 21600 0 +06}
+ {828216000 25200 1 +07}
+ {846360000 21600 0 +06}
+ {859665600 25200 1 +07}
+ {877809600 21600 0 +06}
+ {891115200 25200 1 +07}
+ {909259200 21600 0 +06}
+ {922564800 25200 1 +07}
+ {941313600 21600 0 +06}
+ {954014400 25200 1 +07}
+ {972763200 21600 0 +06}
+ {985464000 25200 1 +07}
+ {1004212800 21600 0 +06}
+ {1017518400 25200 1 +07}
+ {1035662400 21600 0 +06}
+ {1048968000 25200 1 +07}
+ {1067112000 21600 0 +06}
+ {1080417600 25200 1 +07}
+ {1099166400 21600 0 +06}
}
diff --git a/library/tzdata/Asia/Anadyr b/library/tzdata/Asia/Anadyr
index 50ace50..2e8ffc7 100644
--- a/library/tzdata/Asia/Anadyr
+++ b/library/tzdata/Asia/Anadyr
@@ -29,8 +29,8 @@ set TZData(:Asia/Anadyr) {
{670345200 43200 1 ANAST}
{686070000 39600 0 ANAT}
{695746800 43200 0 ANAMMTT}
- {701780400 46800 1 ANAST}
- {717501600 43200 0 ANAT}
+ {701791200 46800 1 ANAST}
+ {717516000 43200 0 ANAT}
{733240800 46800 1 ANAST}
{748965600 43200 0 ANAT}
{764690400 46800 1 ANAST}
diff --git a/library/tzdata/Asia/Aqtau b/library/tzdata/Asia/Aqtau
index 11e89a2..90cc94d 100644
--- a/library/tzdata/Asia/Aqtau
+++ b/library/tzdata/Asia/Aqtau
@@ -2,57 +2,58 @@
set TZData(:Asia/Aqtau) {
{-9223372036854775808 12064 0 LMT}
- {-1441164064 14400 0 FORT}
- {-1247544000 18000 0 FORT}
- {-220942800 18000 0 SHET}
- {370724400 21600 0 SHET}
- {386445600 18000 0 SHET}
- {386449200 21600 1 SHEST}
- {402256800 18000 0 SHET}
- {417985200 21600 1 SHEST}
- {433792800 18000 0 SHET}
- {449607600 21600 1 SHEST}
- {465339600 18000 0 SHET}
- {481064400 21600 1 SHEST}
- {496789200 18000 0 SHET}
- {512514000 21600 1 SHEST}
- {528238800 18000 0 SHET}
- {543963600 21600 1 SHEST}
- {559688400 18000 0 SHET}
- {575413200 21600 1 SHEST}
- {591138000 18000 0 SHET}
- {606862800 21600 1 SHEST}
- {622587600 18000 0 SHET}
- {638312400 21600 1 SHEST}
- {654642000 18000 0 SHET}
- {662670000 18000 0 SHET}
- {692823600 18000 0 AQTT}
- {701805600 21600 1 AQTST}
- {717526800 18000 0 AQTT}
- {733266000 21600 1 AQTST}
- {748990800 18000 0 AQTT}
- {764715600 21600 1 AQTST}
- {780440400 18000 0 AQTT}
- {796165200 14400 0 AQTT}
- {796168800 18000 1 AQTST}
- {811893600 14400 0 AQTT}
- {828223200 18000 1 AQTST}
- {846367200 14400 0 AQTT}
- {859672800 18000 1 AQTST}
- {877816800 14400 0 AQTT}
- {891122400 18000 1 AQTST}
- {909266400 14400 0 AQTT}
- {922572000 18000 1 AQTST}
- {941320800 14400 0 AQTT}
- {954021600 18000 1 AQTST}
- {972770400 14400 0 AQTT}
- {985471200 18000 1 AQTST}
- {1004220000 14400 0 AQTT}
- {1017525600 18000 1 AQTST}
- {1035669600 14400 0 AQTT}
- {1048975200 18000 1 AQTST}
- {1067119200 14400 0 AQTT}
- {1080424800 18000 1 AQTST}
- {1099173600 14400 0 AQTT}
- {1110830400 18000 0 AQTT}
+ {-1441164064 14400 0 +04}
+ {-1247544000 18000 0 +05}
+ {-220942800 18000 0 +05}
+ {370724400 21600 0 +06}
+ {386445600 18000 0 +05}
+ {386449200 21600 1 +06}
+ {402256800 18000 0 +05}
+ {417985200 21600 1 +06}
+ {433792800 18000 0 +05}
+ {449607600 21600 1 +06}
+ {465339600 18000 0 +05}
+ {481064400 21600 1 +06}
+ {496789200 18000 0 +05}
+ {512514000 21600 1 +06}
+ {528238800 18000 0 +05}
+ {543963600 21600 1 +06}
+ {559688400 18000 0 +05}
+ {575413200 21600 1 +06}
+ {591138000 18000 0 +05}
+ {606862800 21600 1 +06}
+ {622587600 18000 0 +05}
+ {638312400 21600 1 +06}
+ {654642000 18000 0 +05}
+ {670366800 14400 0 +04}
+ {670370400 18000 1 +05}
+ {686095200 14400 0 +04}
+ {695772000 18000 0 +05}
+ {701816400 21600 1 +06}
+ {717541200 18000 0 +05}
+ {733266000 21600 1 +06}
+ {748990800 18000 0 +05}
+ {764715600 21600 1 +06}
+ {780440400 18000 0 +05}
+ {780444000 14400 0 +04}
+ {796168800 18000 1 +05}
+ {811893600 14400 0 +04}
+ {828223200 18000 1 +05}
+ {846367200 14400 0 +04}
+ {859672800 18000 1 +05}
+ {877816800 14400 0 +04}
+ {891122400 18000 1 +05}
+ {909266400 14400 0 +04}
+ {922572000 18000 1 +05}
+ {941320800 14400 0 +04}
+ {954021600 18000 1 +05}
+ {972770400 14400 0 +04}
+ {985471200 18000 1 +05}
+ {1004220000 14400 0 +04}
+ {1017525600 18000 1 +05}
+ {1035669600 14400 0 +04}
+ {1048975200 18000 1 +05}
+ {1067119200 14400 0 +04}
+ {1080424800 18000 1 +05}
+ {1099173600 18000 0 +05}
}
diff --git a/library/tzdata/Asia/Aqtobe b/library/tzdata/Asia/Aqtobe
index c857491..55ef556 100644
--- a/library/tzdata/Asia/Aqtobe
+++ b/library/tzdata/Asia/Aqtobe
@@ -2,56 +2,57 @@
set TZData(:Asia/Aqtobe) {
{-9223372036854775808 13720 0 LMT}
- {-1441165720 14400 0 AKTT}
- {-1247544000 18000 0 AKTT}
- {354913200 21600 1 AKTST}
- {370720800 21600 0 AKTT}
- {386445600 18000 0 AKTT}
- {386449200 21600 1 AKTST}
- {402256800 18000 0 AKTT}
- {417985200 21600 1 AKTST}
- {433792800 18000 0 AKTT}
- {449607600 21600 1 AKTST}
- {465339600 18000 0 AKTT}
- {481064400 21600 1 AKTST}
- {496789200 18000 0 AKTT}
- {512514000 21600 1 AKTST}
- {528238800 18000 0 AKTT}
- {543963600 21600 1 AKTST}
- {559688400 18000 0 AKTT}
- {575413200 21600 1 AKTST}
- {591138000 18000 0 AKTT}
- {606862800 21600 1 AKTST}
- {622587600 18000 0 AKTT}
- {638312400 21600 1 AKTST}
- {654642000 18000 0 AKTT}
- {662670000 18000 0 AKTT}
- {692823600 18000 0 AQTT}
- {701805600 21600 1 AQTST}
- {717526800 18000 0 AQTT}
- {733266000 21600 1 AQTST}
- {748990800 18000 0 AQTT}
- {764715600 21600 1 AQTST}
- {780440400 18000 0 AQTT}
- {796165200 21600 1 AQTST}
- {811890000 18000 0 AQTT}
- {828219600 21600 1 AQTST}
- {846363600 18000 0 AQTT}
- {859669200 21600 1 AQTST}
- {877813200 18000 0 AQTT}
- {891118800 21600 1 AQTST}
- {909262800 18000 0 AQTT}
- {922568400 21600 1 AQTST}
- {941317200 18000 0 AQTT}
- {954018000 21600 1 AQTST}
- {972766800 18000 0 AQTT}
- {985467600 21600 1 AQTST}
- {1004216400 18000 0 AQTT}
- {1017522000 21600 1 AQTST}
- {1035666000 18000 0 AQTT}
- {1048971600 21600 1 AQTST}
- {1067115600 18000 0 AQTT}
- {1080421200 21600 1 AQTST}
- {1099170000 18000 0 AQTT}
- {1110826800 18000 0 AQTT}
+ {-1441165720 14400 0 +04}
+ {-1247544000 18000 0 +05}
+ {354913200 21600 1 +06}
+ {370720800 21600 0 +06}
+ {386445600 18000 0 +05}
+ {386449200 21600 1 +06}
+ {402256800 18000 0 +05}
+ {417985200 21600 1 +06}
+ {433792800 18000 0 +05}
+ {449607600 21600 1 +06}
+ {465339600 18000 0 +05}
+ {481064400 21600 1 +06}
+ {496789200 18000 0 +05}
+ {512514000 21600 1 +06}
+ {528238800 18000 0 +05}
+ {543963600 21600 1 +06}
+ {559688400 18000 0 +05}
+ {575413200 21600 1 +06}
+ {591138000 18000 0 +05}
+ {606862800 21600 1 +06}
+ {622587600 18000 0 +05}
+ {638312400 21600 1 +06}
+ {654642000 18000 0 +05}
+ {670366800 14400 0 +04}
+ {670370400 18000 1 +05}
+ {686095200 14400 0 +04}
+ {695772000 18000 0 +05}
+ {701816400 21600 1 +06}
+ {717541200 18000 0 +05}
+ {733266000 21600 1 +06}
+ {748990800 18000 0 +05}
+ {764715600 21600 1 +06}
+ {780440400 18000 0 +05}
+ {796165200 21600 1 +06}
+ {811890000 18000 0 +05}
+ {828219600 21600 1 +06}
+ {846363600 18000 0 +05}
+ {859669200 21600 1 +06}
+ {877813200 18000 0 +05}
+ {891118800 21600 1 +06}
+ {909262800 18000 0 +05}
+ {922568400 21600 1 +06}
+ {941317200 18000 0 +05}
+ {954018000 21600 1 +06}
+ {972766800 18000 0 +05}
+ {985467600 21600 1 +06}
+ {1004216400 18000 0 +05}
+ {1017522000 21600 1 +06}
+ {1035666000 18000 0 +05}
+ {1048971600 21600 1 +06}
+ {1067115600 18000 0 +05}
+ {1080421200 21600 1 +06}
+ {1099170000 18000 0 +05}
}
diff --git a/library/tzdata/Asia/Baku b/library/tzdata/Asia/Baku
index c26a2f5..bc0701a 100644
--- a/library/tzdata/Asia/Baku
+++ b/library/tzdata/Asia/Baku
@@ -27,7 +27,7 @@ set TZData(:Asia/Baku) {
{670370400 14400 1 BAKST}
{683496000 14400 0 AZST}
{686098800 10800 0 AZT}
- {701812800 14400 1 AZST}
+ {701823600 14400 1 AZST}
{717537600 14400 0 AZT}
{820440000 14400 0 AZT}
{828234000 18000 1 AZST}
diff --git a/library/tzdata/Asia/Barnaul b/library/tzdata/Asia/Barnaul
index f6a45da..bf6abbf 100644
--- a/library/tzdata/Asia/Barnaul
+++ b/library/tzdata/Asia/Barnaul
@@ -28,8 +28,8 @@ set TZData(:Asia/Barnaul) {
{670363200 25200 1 +07}
{686088000 21600 0 +06}
{695764800 25200 0 +08}
- {701798400 28800 1 +08}
- {717519600 25200 0 +07}
+ {701809200 28800 1 +08}
+ {717534000 25200 0 +07}
{733258800 28800 1 +08}
{748983600 25200 0 +07}
{764708400 28800 1 +08}
diff --git a/library/tzdata/Asia/Chita b/library/tzdata/Asia/Chita
index 6aef523..2517beb 100644
--- a/library/tzdata/Asia/Chita
+++ b/library/tzdata/Asia/Chita
@@ -28,8 +28,8 @@ set TZData(:Asia/Chita) {
{670356000 32400 1 YAKST}
{686080800 28800 0 YAKT}
{695757600 32400 0 YAKMMTT}
- {701791200 36000 1 YAKST}
- {717512400 32400 0 YAKT}
+ {701802000 36000 1 YAKST}
+ {717526800 32400 0 YAKT}
{733251600 36000 1 YAKST}
{748976400 32400 0 YAKT}
{764701200 36000 1 YAKST}
diff --git a/library/tzdata/Asia/Irkutsk b/library/tzdata/Asia/Irkutsk
index 08e5798..ebe00c3 100644
--- a/library/tzdata/Asia/Irkutsk
+++ b/library/tzdata/Asia/Irkutsk
@@ -29,8 +29,8 @@ set TZData(:Asia/Irkutsk) {
{670359600 28800 1 IRKST}
{686084400 25200 0 IRKT}
{695761200 28800 0 IRKMMTT}
- {701794800 32400 1 IRKST}
- {717516000 28800 0 IRKT}
+ {701805600 32400 1 IRKST}
+ {717530400 28800 0 IRKT}
{733255200 32400 1 IRKST}
{748980000 28800 0 IRKT}
{764704800 32400 1 IRKST}
diff --git a/library/tzdata/Asia/Kamchatka b/library/tzdata/Asia/Kamchatka
index 82abcfa..2b77154 100644
--- a/library/tzdata/Asia/Kamchatka
+++ b/library/tzdata/Asia/Kamchatka
@@ -28,8 +28,8 @@ set TZData(:Asia/Kamchatka) {
{670345200 43200 1 PETST}
{686070000 39600 0 PETT}
{695746800 43200 0 PETMMTT}
- {701780400 46800 1 PETST}
- {717501600 43200 0 PETT}
+ {701791200 46800 1 PETST}
+ {717516000 43200 0 PETT}
{733240800 46800 1 PETST}
{748965600 43200 0 PETT}
{764690400 46800 1 PETST}
diff --git a/library/tzdata/Asia/Khandyga b/library/tzdata/Asia/Khandyga
index b2dc97a..b898e0d 100644
--- a/library/tzdata/Asia/Khandyga
+++ b/library/tzdata/Asia/Khandyga
@@ -28,8 +28,8 @@ set TZData(:Asia/Khandyga) {
{670356000 32400 1 YAKST}
{686080800 28800 0 YAKT}
{695757600 32400 0 YAKMMTT}
- {701791200 36000 1 YAKST}
- {717512400 32400 0 YAKT}
+ {701802000 36000 1 YAKST}
+ {717526800 32400 0 YAKT}
{733251600 36000 1 YAKST}
{748976400 32400 0 YAKT}
{764701200 36000 1 YAKST}
diff --git a/library/tzdata/Asia/Krasnoyarsk b/library/tzdata/Asia/Krasnoyarsk
index 17ea6c0..3c6285e 100644
--- a/library/tzdata/Asia/Krasnoyarsk
+++ b/library/tzdata/Asia/Krasnoyarsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Krasnoyarsk) {
{670363200 25200 1 KRAST}
{686088000 21600 0 KRAT}
{695764800 25200 0 KRAMMTT}
- {701798400 28800 1 KRAST}
- {717519600 25200 0 KRAT}
+ {701809200 28800 1 KRAST}
+ {717534000 25200 0 KRAT}
{733258800 28800 1 KRAST}
{748983600 25200 0 KRAT}
{764708400 28800 1 KRAST}
diff --git a/library/tzdata/Asia/Magadan b/library/tzdata/Asia/Magadan
index bf796a7..afe78da 100644
--- a/library/tzdata/Asia/Magadan
+++ b/library/tzdata/Asia/Magadan
@@ -28,8 +28,8 @@ set TZData(:Asia/Magadan) {
{670348800 39600 1 MAGST}
{686073600 36000 0 MAGT}
{695750400 39600 0 MAGMMTT}
- {701784000 43200 1 MAGST}
- {717505200 39600 0 MAGT}
+ {701794800 43200 1 MAGST}
+ {717519600 39600 0 MAGT}
{733244400 43200 1 MAGST}
{748969200 39600 0 MAGT}
{764694000 43200 1 MAGST}
@@ -68,4 +68,5 @@ set TZData(:Asia/Magadan) {
{1288450800 39600 0 MAGT}
{1301151600 43200 0 MAGT}
{1414245600 36000 0 MAGT}
+ {1461427200 39600 0 MAGT}
}
diff --git a/library/tzdata/Asia/Novokuznetsk b/library/tzdata/Asia/Novokuznetsk
index ab3c2d5..f079faa 100644
--- a/library/tzdata/Asia/Novokuznetsk
+++ b/library/tzdata/Asia/Novokuznetsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Novokuznetsk) {
{670363200 25200 1 KRAST}
{686088000 21600 0 KRAT}
{695764800 25200 0 KRAMMTT}
- {701798400 28800 1 KRAST}
- {717519600 25200 0 KRAT}
+ {701809200 28800 1 KRAST}
+ {717534000 25200 0 KRAT}
{733258800 28800 1 KRAST}
{748983600 25200 0 KRAT}
{764708400 28800 1 KRAST}
diff --git a/library/tzdata/Asia/Novosibirsk b/library/tzdata/Asia/Novosibirsk
index 7227780..54c83fa 100644
--- a/library/tzdata/Asia/Novosibirsk
+++ b/library/tzdata/Asia/Novosibirsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Novosibirsk) {
{670363200 25200 1 NOVST}
{686088000 21600 0 NOVT}
{695764800 25200 0 NOVMMTT}
- {701798400 28800 1 NOVST}
- {717519600 25200 0 NOVT}
+ {701809200 28800 1 NOVST}
+ {717534000 25200 0 NOVT}
{733258800 28800 1 NOVST}
{738090000 25200 0 NOVST}
{748987200 21600 0 NOVT}
diff --git a/library/tzdata/Asia/Omsk b/library/tzdata/Asia/Omsk
index f25b8d4..a6fa180 100644
--- a/library/tzdata/Asia/Omsk
+++ b/library/tzdata/Asia/Omsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Omsk) {
{670366800 21600 1 OMSST}
{686091600 18000 0 OMST}
{695768400 21600 0 OMSMMTT}
- {701802000 25200 1 OMSST}
- {717523200 21600 0 OMST}
+ {701812800 25200 1 OMSST}
+ {717537600 21600 0 OMST}
{733262400 25200 1 OMSST}
{748987200 21600 0 OMST}
{764712000 25200 1 OMSST}
diff --git a/library/tzdata/Asia/Oral b/library/tzdata/Asia/Oral
index 88b9a29..962111b 100644
--- a/library/tzdata/Asia/Oral
+++ b/library/tzdata/Asia/Oral
@@ -2,57 +2,57 @@
set TZData(:Asia/Oral) {
{-9223372036854775808 12324 0 LMT}
- {-1441164324 14400 0 URAT}
- {-1247544000 18000 0 URAT}
- {354913200 21600 1 URAST}
- {370720800 21600 0 URAT}
- {386445600 18000 0 URAT}
- {386449200 21600 1 URAST}
- {402256800 18000 0 URAT}
- {417985200 21600 1 URAST}
- {433792800 18000 0 URAT}
- {449607600 21600 1 URAST}
- {465339600 18000 0 URAT}
- {481064400 21600 1 URAST}
- {496789200 18000 0 URAT}
- {512514000 21600 1 URAST}
- {528238800 18000 0 URAT}
- {543963600 21600 1 URAST}
- {559688400 18000 0 URAT}
- {575413200 21600 1 URAST}
- {591138000 18000 0 URAT}
- {606862800 14400 0 URAT}
- {606866400 18000 1 URAST}
- {622591200 14400 0 URAT}
- {638316000 18000 1 URAST}
- {654645600 14400 0 URAT}
- {662673600 14400 0 URAT}
- {692827200 14400 0 ORAT}
- {701809200 18000 1 ORAST}
- {717530400 14400 0 ORAT}
- {733269600 18000 1 ORAST}
- {748994400 14400 0 ORAT}
- {764719200 18000 1 ORAST}
- {780444000 14400 0 ORAT}
- {796168800 18000 1 ORAST}
- {811893600 14400 0 ORAT}
- {828223200 18000 1 ORAST}
- {846367200 14400 0 ORAT}
- {859672800 18000 1 ORAST}
- {877816800 14400 0 ORAT}
- {891122400 18000 1 ORAST}
- {909266400 14400 0 ORAT}
- {922572000 18000 1 ORAST}
- {941320800 14400 0 ORAT}
- {954021600 18000 1 ORAST}
- {972770400 14400 0 ORAT}
- {985471200 18000 1 ORAST}
- {1004220000 14400 0 ORAT}
- {1017525600 18000 1 ORAST}
- {1035669600 14400 0 ORAT}
- {1048975200 18000 1 ORAST}
- {1067119200 14400 0 ORAT}
- {1080424800 18000 1 ORAST}
- {1099173600 14400 0 ORAT}
- {1110830400 18000 0 ORAT}
+ {-1441164324 14400 0 +04}
+ {-1247544000 18000 0 +05}
+ {354913200 21600 1 +06}
+ {370720800 21600 0 +06}
+ {386445600 18000 0 +05}
+ {386449200 21600 1 +06}
+ {402256800 18000 0 +05}
+ {417985200 21600 1 +06}
+ {433792800 18000 0 +05}
+ {449607600 21600 1 +06}
+ {465339600 18000 0 +05}
+ {481064400 21600 1 +06}
+ {496789200 18000 0 +05}
+ {512514000 21600 1 +06}
+ {528238800 18000 0 +05}
+ {543963600 21600 1 +06}
+ {559688400 18000 0 +05}
+ {575413200 21600 1 +06}
+ {591138000 18000 0 +05}
+ {606862800 14400 0 +04}
+ {606866400 18000 1 +05}
+ {622591200 14400 0 +04}
+ {638316000 18000 1 +05}
+ {654645600 14400 0 +04}
+ {670370400 18000 1 +05}
+ {686095200 14400 0 +04}
+ {701816400 14400 0 +04}
+ {701820000 18000 1 +05}
+ {717544800 14400 0 +04}
+ {733269600 18000 1 +05}
+ {748994400 14400 0 +04}
+ {764719200 18000 1 +05}
+ {780444000 14400 0 +04}
+ {796168800 18000 1 +05}
+ {811893600 14400 0 +04}
+ {828223200 18000 1 +05}
+ {846367200 14400 0 +04}
+ {859672800 18000 1 +05}
+ {877816800 14400 0 +04}
+ {891122400 18000 1 +05}
+ {909266400 14400 0 +04}
+ {922572000 18000 1 +05}
+ {941320800 14400 0 +04}
+ {954021600 18000 1 +05}
+ {972770400 14400 0 +04}
+ {985471200 18000 1 +05}
+ {1004220000 14400 0 +04}
+ {1017525600 18000 1 +05}
+ {1035669600 14400 0 +04}
+ {1048975200 18000 1 +05}
+ {1067119200 14400 0 +04}
+ {1080424800 18000 1 +05}
+ {1099173600 18000 0 +05}
}
diff --git a/library/tzdata/Asia/Qyzylorda b/library/tzdata/Asia/Qyzylorda
index 16da574..b2e9472 100644
--- a/library/tzdata/Asia/Qyzylorda
+++ b/library/tzdata/Asia/Qyzylorda
@@ -2,57 +2,56 @@
set TZData(:Asia/Qyzylorda) {
{-9223372036854775808 15712 0 LMT}
- {-1441167712 14400 0 KIZT}
- {-1247544000 18000 0 KIZT}
- {354913200 21600 1 KIZST}
- {370720800 21600 0 KIZT}
- {386445600 18000 0 KIZT}
- {386449200 21600 1 KIZST}
- {402256800 18000 0 KIZT}
- {417985200 21600 1 KIZST}
- {433792800 18000 0 KIZT}
- {449607600 21600 1 KIZST}
- {465339600 18000 0 KIZT}
- {481064400 21600 1 KIZST}
- {496789200 18000 0 KIZT}
- {512514000 21600 1 KIZST}
- {528238800 18000 0 KIZT}
- {543963600 21600 1 KIZST}
- {559688400 18000 0 KIZT}
- {575413200 21600 1 KIZST}
- {591138000 18000 0 KIZT}
- {606862800 21600 1 KIZST}
- {622587600 18000 0 KIZT}
- {638312400 21600 1 KIZST}
- {654642000 18000 0 KIZT}
- {662670000 18000 0 KIZT}
- {692823600 18000 0 QYZT}
- {695768400 21600 0 QYZT}
- {701802000 25200 1 QYZST}
- {717523200 21600 0 QYZT}
- {733262400 25200 1 QYZST}
- {748987200 21600 0 QYZT}
- {764712000 25200 1 QYZST}
- {780436800 21600 0 QYZT}
- {796161600 25200 1 QYZST}
- {811886400 21600 0 QYZT}
- {828216000 25200 1 QYZST}
- {846360000 21600 0 QYZT}
- {859665600 25200 1 QYZST}
- {877809600 21600 0 QYZT}
- {891115200 25200 1 QYZST}
- {909259200 21600 0 QYZT}
- {922564800 25200 1 QYZST}
- {941313600 21600 0 QYZT}
- {954014400 25200 1 QYZST}
- {972763200 21600 0 QYZT}
- {985464000 25200 1 QYZST}
- {1004212800 21600 0 QYZT}
- {1017518400 25200 1 QYZST}
- {1035662400 21600 0 QYZT}
- {1048968000 25200 1 QYZST}
- {1067112000 21600 0 QYZT}
- {1080417600 25200 1 QYZST}
- {1099166400 21600 0 QYZT}
- {1110823200 21600 0 QYZT}
+ {-1441167712 14400 0 +04}
+ {-1247544000 18000 0 +05}
+ {354913200 21600 1 +06}
+ {370720800 21600 0 +06}
+ {386445600 18000 0 +05}
+ {386449200 21600 1 +06}
+ {402256800 18000 0 +05}
+ {417985200 21600 1 +06}
+ {433792800 18000 0 +05}
+ {449607600 21600 1 +06}
+ {465339600 18000 0 +05}
+ {481064400 21600 1 +06}
+ {496789200 18000 0 +05}
+ {512514000 21600 1 +06}
+ {528238800 18000 0 +05}
+ {543963600 21600 1 +06}
+ {559688400 18000 0 +05}
+ {575413200 21600 1 +06}
+ {591138000 18000 0 +05}
+ {606862800 21600 1 +06}
+ {622587600 18000 0 +05}
+ {638312400 21600 1 +06}
+ {654642000 18000 0 +05}
+ {670366800 14400 0 +04}
+ {670370400 18000 1 +05}
+ {701812800 18000 0 +05}
+ {701816400 21600 1 +06}
+ {717541200 18000 0 +05}
+ {733266000 21600 1 +06}
+ {748990800 18000 0 +05}
+ {764715600 21600 1 +06}
+ {780440400 18000 0 +05}
+ {796165200 21600 1 +06}
+ {811890000 18000 0 +05}
+ {828219600 21600 1 +06}
+ {846363600 18000 0 +05}
+ {859669200 21600 1 +06}
+ {877813200 18000 0 +05}
+ {891118800 21600 1 +06}
+ {909262800 18000 0 +05}
+ {922568400 21600 1 +06}
+ {941317200 18000 0 +05}
+ {954018000 21600 1 +06}
+ {972766800 18000 0 +05}
+ {985467600 21600 1 +06}
+ {1004216400 18000 0 +05}
+ {1017522000 21600 1 +06}
+ {1035666000 18000 0 +05}
+ {1048971600 21600 1 +06}
+ {1067115600 18000 0 +05}
+ {1080421200 21600 1 +06}
+ {1099170000 21600 0 +06}
}
diff --git a/library/tzdata/Asia/Sakhalin b/library/tzdata/Asia/Sakhalin
index 9247046..1de22f4 100644
--- a/library/tzdata/Asia/Sakhalin
+++ b/library/tzdata/Asia/Sakhalin
@@ -29,8 +29,8 @@ set TZData(:Asia/Sakhalin) {
{670348800 39600 1 SAKST}
{686073600 36000 0 SAKT}
{695750400 39600 0 SAKMMTT}
- {701784000 43200 1 SAKST}
- {717505200 39600 0 SAKT}
+ {701794800 43200 1 SAKST}
+ {717519600 39600 0 SAKT}
{733244400 43200 1 SAKST}
{748969200 39600 0 SAKT}
{764694000 43200 1 SAKST}
diff --git a/library/tzdata/Asia/Srednekolymsk b/library/tzdata/Asia/Srednekolymsk
index d1dd879..a0586aa 100644
--- a/library/tzdata/Asia/Srednekolymsk
+++ b/library/tzdata/Asia/Srednekolymsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Srednekolymsk) {
{670348800 39600 1 MAGST}
{686073600 36000 0 MAGT}
{695750400 39600 0 MAGMMTT}
- {701784000 43200 1 MAGST}
- {717505200 39600 0 MAGT}
+ {701794800 43200 1 MAGST}
+ {717519600 39600 0 MAGT}
{733244400 43200 1 MAGST}
{748969200 39600 0 MAGT}
{764694000 43200 1 MAGST}
diff --git a/library/tzdata/Asia/Tomsk b/library/tzdata/Asia/Tomsk
new file mode 100644
index 0000000..0694d01
--- /dev/null
+++ b/library/tzdata/Asia/Tomsk
@@ -0,0 +1,73 @@
+# created by tools/tclZIC.tcl - do not edit
+
+set TZData(:Asia/Tomsk) {
+ {-9223372036854775808 20391 0 LMT}
+ {-1578807591 21600 0 +06}
+ {-1247551200 25200 0 +08}
+ {354906000 28800 1 +08}
+ {370713600 25200 0 +07}
+ {386442000 28800 1 +08}
+ {402249600 25200 0 +07}
+ {417978000 28800 1 +08}
+ {433785600 25200 0 +07}
+ {449600400 28800 1 +08}
+ {465332400 25200 0 +07}
+ {481057200 28800 1 +08}
+ {496782000 25200 0 +07}
+ {512506800 28800 1 +08}
+ {528231600 25200 0 +07}
+ {543956400 28800 1 +08}
+ {559681200 25200 0 +07}
+ {575406000 28800 1 +08}
+ {591130800 25200 0 +07}
+ {606855600 28800 1 +08}
+ {622580400 25200 0 +07}
+ {638305200 28800 1 +08}
+ {654634800 25200 0 +07}
+ {670359600 21600 0 +07}
+ {670363200 25200 1 +07}
+ {686088000 21600 0 +06}
+ {695764800 25200 0 +08}
+ {701809200 28800 1 +08}
+ {717534000 25200 0 +07}
+ {733258800 28800 1 +08}
+ {748983600 25200 0 +07}
+ {764708400 28800 1 +08}
+ {780433200 25200 0 +07}
+ {796158000 28800 1 +08}
+ {811882800 25200 0 +07}
+ {828212400 28800 1 +08}
+ {846356400 25200 0 +07}
+ {859662000 28800 1 +08}
+ {877806000 25200 0 +07}
+ {891111600 28800 1 +08}
+ {909255600 25200 0 +07}
+ {922561200 28800 1 +08}
+ {941310000 25200 0 +07}
+ {954010800 28800 1 +08}
+ {972759600 25200 0 +07}
+ {985460400 28800 1 +08}
+ {1004209200 25200 0 +07}
+ {1017514800 28800 1 +08}
+ {1020196800 25200 0 +07}
+ {1035662400 21600 0 +06}
+ {1048968000 25200 1 +07}
+ {1067112000 21600 0 +06}
+ {1080417600 25200 1 +07}
+ {1099166400 21600 0 +06}
+ {1111867200 25200 1 +07}
+ {1130616000 21600 0 +06}
+ {1143316800 25200 1 +07}
+ {1162065600 21600 0 +06}
+ {1174766400 25200 1 +07}
+ {1193515200 21600 0 +06}
+ {1206820800 25200 1 +07}
+ {1224964800 21600 0 +06}
+ {1238270400 25200 1 +07}
+ {1256414400 21600 0 +06}
+ {1269720000 25200 1 +07}
+ {1288468800 21600 0 +06}
+ {1301169600 25200 0 +07}
+ {1414263600 21600 0 +06}
+ {1464465600 25200 0 +07}
+}
diff --git a/library/tzdata/Asia/Ust-Nera b/library/tzdata/Asia/Ust-Nera
index 90fa7d5..3380b7b 100644
--- a/library/tzdata/Asia/Ust-Nera
+++ b/library/tzdata/Asia/Ust-Nera
@@ -27,8 +27,8 @@ set TZData(:Asia/Ust-Nera) {
{670348800 39600 1 MAGST}
{686073600 36000 0 MAGT}
{695750400 39600 0 MAGMMTT}
- {701784000 43200 1 MAGST}
- {717505200 39600 0 MAGT}
+ {701794800 43200 1 MAGST}
+ {717519600 39600 0 MAGT}
{733244400 43200 1 MAGST}
{748969200 39600 0 MAGT}
{764694000 43200 1 MAGST}
diff --git a/library/tzdata/Asia/Vladivostok b/library/tzdata/Asia/Vladivostok
index 119ff57..b279d1c 100644
--- a/library/tzdata/Asia/Vladivostok
+++ b/library/tzdata/Asia/Vladivostok
@@ -28,8 +28,8 @@ set TZData(:Asia/Vladivostok) {
{670352400 36000 1 VLAST}
{686077200 32400 0 VLAT}
{695754000 36000 0 VLAMMTT}
- {701787600 39600 1 VLAST}
- {717508800 36000 0 VLAT}
+ {701798400 39600 1 VLAST}
+ {717523200 36000 0 VLAT}
{733248000 39600 1 VLAST}
{748972800 36000 0 VLAT}
{764697600 39600 1 VLAST}
diff --git a/library/tzdata/Asia/Yakutsk b/library/tzdata/Asia/Yakutsk
index 17493a6..0074379 100644
--- a/library/tzdata/Asia/Yakutsk
+++ b/library/tzdata/Asia/Yakutsk
@@ -28,8 +28,8 @@ set TZData(:Asia/Yakutsk) {
{670356000 32400 1 YAKST}
{686080800 28800 0 YAKT}
{695757600 32400 0 YAKMMTT}
- {701791200 36000 1 YAKST}
- {717512400 32400 0 YAKT}
+ {701802000 36000 1 YAKST}
+ {717526800 32400 0 YAKT}
{733251600 36000 1 YAKST}
{748976400 32400 0 YAKT}
{764701200 36000 1 YAKST}
diff --git a/library/tzdata/Asia/Yekaterinburg b/library/tzdata/Asia/Yekaterinburg
index 2678958..fdd89b0 100644
--- a/library/tzdata/Asia/Yekaterinburg
+++ b/library/tzdata/Asia/Yekaterinburg
@@ -29,8 +29,8 @@ set TZData(:Asia/Yekaterinburg) {
{670370400 18000 1 SVEST}
{686095200 14400 0 SVET}
{695772000 18000 0 YEKMMTT}
- {701805600 21600 1 YEKST}
- {717526800 18000 0 YEKT}
+ {701816400 21600 1 YEKST}
+ {717541200 18000 0 YEKT}
{733266000 21600 1 YEKST}
{748990800 18000 0 YEKT}
{764715600 21600 1 YEKST}
diff --git a/library/tzdata/Asia/Yerevan b/library/tzdata/Asia/Yerevan
index 22008ef..c552403 100644
--- a/library/tzdata/Asia/Yerevan
+++ b/library/tzdata/Asia/Yerevan
@@ -27,8 +27,8 @@ set TZData(:Asia/Yerevan) {
{670370400 14400 1 YERST}
{685569600 14400 0 AMST}
{686098800 10800 0 AMT}
- {701812800 14400 1 AMST}
- {717534000 10800 0 AMT}
+ {701823600 14400 1 AMST}
+ {717548400 10800 0 AMT}
{733273200 14400 1 AMST}
{748998000 10800 0 AMT}
{764722800 14400 1 AMST}
@@ -66,5 +66,5 @@ set TZData(:Asia/Yerevan) {
{1288476000 14400 0 AMT}
{1301176800 18000 1 AMST}
{1319925600 14400 0 AMT}
- {1332626400 14400 0 AMT}
+ {1328731200 14400 0 AMT}
}
diff --git a/library/tzdata/Europe/Astrakhan b/library/tzdata/Europe/Astrakhan
index e5e9c26..9881bb8 100644
--- a/library/tzdata/Europe/Astrakhan
+++ b/library/tzdata/Europe/Astrakhan
@@ -26,8 +26,9 @@ set TZData(:Europe/Astrakhan) {
{638319600 14400 1 +04}
{654649200 10800 0 +03}
{670374000 14400 0 +04}
- {701820000 14400 0 +04}
- {717534000 10800 0 +03}
+ {701820000 10800 0 +04}
+ {701823600 14400 1 +04}
+ {717548400 10800 0 +03}
{733273200 14400 1 +04}
{748998000 10800 0 +03}
{764722800 14400 1 +04}
diff --git a/library/tzdata/Europe/Kaliningrad b/library/tzdata/Europe/Kaliningrad
index 32d7aaa..85add82 100644
--- a/library/tzdata/Europe/Kaliningrad
+++ b/library/tzdata/Europe/Kaliningrad
@@ -42,8 +42,8 @@ set TZData(:Europe/Kaliningrad) {
{654652800 7200 0 EET}
{670377600 10800 1 EEST}
{686102400 7200 0 EET}
- {701816400 10800 1 EEST}
- {717537600 7200 0 EET}
+ {701827200 10800 1 EEST}
+ {717552000 7200 0 EET}
{733276800 10800 1 EEST}
{749001600 7200 0 EET}
{764726400 10800 1 EEST}
diff --git a/library/tzdata/Europe/Kirov b/library/tzdata/Europe/Kirov
new file mode 100644
index 0000000..82ffc9e
--- /dev/null
+++ b/library/tzdata/Europe/Kirov
@@ -0,0 +1,70 @@
+# created by tools/tclZIC.tcl - do not edit
+
+set TZData(:Europe/Kirov) {
+ {-9223372036854775808 11928 0 LMT}
+ {-1593825528 10800 0 +03}
+ {-1247540400 14400 0 +05}
+ {354916800 18000 1 +05}
+ {370724400 14400 0 +04}
+ {386452800 18000 1 +05}
+ {402260400 14400 0 +04}
+ {417988800 18000 1 +05}
+ {433796400 14400 0 +04}
+ {449611200 18000 1 +05}
+ {465343200 14400 0 +04}
+ {481068000 18000 1 +05}
+ {496792800 14400 0 +04}
+ {512517600 18000 1 +05}
+ {528242400 14400 0 +04}
+ {543967200 18000 1 +05}
+ {559692000 14400 0 +04}
+ {575416800 18000 1 +05}
+ {591141600 14400 0 +04}
+ {606866400 10800 0 +04}
+ {606870000 14400 1 +04}
+ {622594800 10800 0 +03}
+ {638319600 14400 1 +04}
+ {654649200 10800 0 +03}
+ {670374000 14400 0 +04}
+ {701820000 10800 0 +04}
+ {701823600 14400 1 +04}
+ {717548400 10800 0 +03}
+ {733273200 14400 1 +04}
+ {748998000 10800 0 +03}
+ {764722800 14400 1 +04}
+ {780447600 10800 0 +03}
+ {796172400 14400 1 +04}
+ {811897200 10800 0 +03}
+ {828226800 14400 1 +04}
+ {846370800 10800 0 +03}
+ {859676400 14400 1 +04}
+ {877820400 10800 0 +03}
+ {891126000 14400 1 +04}
+ {909270000 10800 0 +03}
+ {922575600 14400 1 +04}
+ {941324400 10800 0 +03}
+ {954025200 14400 1 +04}
+ {972774000 10800 0 +03}
+ {985474800 14400 1 +04}
+ {1004223600 10800 0 +03}
+ {1017529200 14400 1 +04}
+ {1035673200 10800 0 +03}
+ {1048978800 14400 1 +04}
+ {1067122800 10800 0 +03}
+ {1080428400 14400 1 +04}
+ {1099177200 10800 0 +03}
+ {1111878000 14400 1 +04}
+ {1130626800 10800 0 +03}
+ {1143327600 14400 1 +04}
+ {1162076400 10800 0 +03}
+ {1174777200 14400 1 +04}
+ {1193526000 10800 0 +03}
+ {1206831600 14400 1 +04}
+ {1224975600 10800 0 +03}
+ {1238281200 14400 1 +04}
+ {1256425200 10800 0 +03}
+ {1269730800 14400 1 +04}
+ {1288479600 10800 0 +03}
+ {1301180400 14400 0 +04}
+ {1414274400 10800 0 +03}
+}
diff --git a/library/tzdata/Europe/Minsk b/library/tzdata/Europe/Minsk
index 0acb4aa..5e47063 100644
--- a/library/tzdata/Europe/Minsk
+++ b/library/tzdata/Europe/Minsk
@@ -33,7 +33,8 @@ set TZData(:Europe/Minsk) {
{670374000 10800 1 EEST}
{686102400 7200 0 EET}
{701820000 10800 1 EEST}
- {717544800 7200 0 EET}
+ {717544800 10800 0 EEST}
+ {717552000 7200 0 EET}
{733276800 10800 1 EEST}
{749001600 7200 0 EET}
{764726400 10800 1 EEST}
diff --git a/library/tzdata/Europe/Moscow b/library/tzdata/Europe/Moscow
index 686b3d0..1e2f45b 100644
--- a/library/tzdata/Europe/Moscow
+++ b/library/tzdata/Europe/Moscow
@@ -40,8 +40,8 @@ set TZData(:Europe/Moscow) {
{670377600 10800 1 EEST}
{686102400 7200 0 EET}
{695779200 10800 0 MSD}
- {701812800 14400 1 MSD}
- {717534000 10800 0 MSK}
+ {701823600 14400 1 MSD}
+ {717548400 10800 0 MSK}
{733273200 14400 1 MSD}
{748998000 10800 0 MSK}
{764722800 14400 1 MSD}
diff --git a/library/tzdata/Europe/Samara b/library/tzdata/Europe/Samara
index 47615de..08203c0 100644
--- a/library/tzdata/Europe/Samara
+++ b/library/tzdata/Europe/Samara
@@ -30,8 +30,8 @@ set TZData(:Europe/Samara) {
{670377600 10800 1 EEST}
{686102400 10800 0 SAMT}
{687916800 14400 0 SAMT}
- {701809200 18000 1 SAMST}
- {717530400 14400 0 SAMT}
+ {701820000 18000 1 SAMST}
+ {717544800 14400 0 SAMT}
{733269600 18000 1 SAMST}
{748994400 14400 0 SAMT}
{764719200 18000 1 SAMST}
diff --git a/library/tzdata/Europe/Ulyanovsk b/library/tzdata/Europe/Ulyanovsk
index b975622..d5c33b5 100644
--- a/library/tzdata/Europe/Ulyanovsk
+++ b/library/tzdata/Europe/Ulyanovsk
@@ -29,8 +29,8 @@ set TZData(:Europe/Ulyanovsk) {
{670377600 10800 1 +03}
{686102400 7200 0 +02}
{695779200 10800 0 +04}
- {701812800 14400 1 +04}
- {717534000 10800 0 +03}
+ {701823600 14400 1 +04}
+ {717548400 10800 0 +03}
{733273200 14400 1 +04}
{748998000 10800 0 +03}
{764722800 14400 1 +04}
diff --git a/library/tzdata/Europe/Volgograd b/library/tzdata/Europe/Volgograd
index ef33d4b..83996b0 100644
--- a/library/tzdata/Europe/Volgograd
+++ b/library/tzdata/Europe/Volgograd
@@ -28,8 +28,9 @@ set TZData(:Europe/Volgograd) {
{638319600 14400 1 VOLST}
{654649200 10800 0 VOLT}
{670374000 14400 0 VOLT}
- {701820000 14400 0 MSD}
- {717534000 10800 0 MSK}
+ {701820000 10800 0 MSD}
+ {701823600 14400 1 MSD}
+ {717548400 10800 0 MSK}
{733273200 14400 1 MSD}
{748998000 10800 0 MSK}
{764722800 14400 1 MSD}
diff --git a/tests/clock.test b/tests/clock.test
index b2ccdf2..08036ca 100644
--- a/tests/clock.test
+++ b/tests/clock.test
@@ -34992,6 +34992,10 @@ test clock-29.1800 {time parsing} {
} 86399
# END testcases29
+
+# BEGIN testcases30
+
+# Test [clock add]
test clock-30.1 {clock add years} {
set t [clock scan 2000-01-01 -format %Y-%m-%d -timezone :UTC]
set f [clock add $t 1 year -timezone :UTC]
@@ -35218,6 +35222,57 @@ test clock-30.25 {clock add seconds at DST conversion} {
set x1 [clock format $f1 -format {%Y-%m-%d %H:%M:%S %z} \
-timezone EST05:00EDT04:00,M4.1.0/02:00,M10.5.0/02:00]
} {2004-10-31 01:00:00 -0500}
+test clock-30.26 {clock add weekdays} {
+ set t [clock scan {2013-11-20}] ;# Wednesday
+ set f1 [clock add $t 3 weekdays]
+ set x1 [clock format $f1 -format {%Y-%m-%d}]
+} {2013-11-25}
+test clock-30.27 {clock add weekdays starting on Saturday} {
+ set t [clock scan {2013-11-23}] ;# Saturday
+ set f1 [clock add $t 1 weekday]
+ set x1 [clock format $f1 -format {%Y-%m-%d}]
+} {2013-11-25}
+test clock-30.28 {clock add weekdays starting on Sunday} {
+ set t [clock scan {2013-11-24}] ;# Sunday
+ set f1 [clock add $t 1 weekday]
+ set x1 [clock format $f1 -format {%Y-%m-%d}]
+} {2013-11-25}
+test clock-30.29 {clock add 0 weekdays starting on a weekend} {
+ set t [clock scan {2016-02-27}] ;# Saturday
+ set f1 [clock add $t 0 weekdays]
+ set x1 [clock format $f1 -format {%Y-%m-%d}]
+} {2016-02-27}
+test clock-30.30 {clock add weekdays and back} -body {
+ set n [clock seconds]
+ # we start on each day of the week
+ for {set i 0} {$i < 7} {incr i} {
+ set start [clock add $n $i days]
+ set startu [clock format $start -format %u]
+ # add 0 - 100 weekdays
+ for {set j 0} {$j < 100} {incr j} {
+ set forth [clock add $start $j weekdays]
+ set back [clock add $forth -$j weekdays]
+ # If $s was a weekday or $j was 0, $b must be the same day.
+ # Otherwise, $b must be the immediately preceeding Friday
+ set fail 0
+ if {$j == 0 || $startu < 6} {
+ if {$start != $back} { set fail 1}
+ } else {
+ set friday [clock add $start -[expr {$startu % 5}] days]
+ if {$friday != $back} { set fail 1 }
+ }
+ if {$fail} {
+ set sdate [clock format $start -format {%Y-%m-%d}]
+ set bdate [clock format $back -format {%Y-%m-%d}]
+ return "$sdate + $j - $j := $bdate"
+ }
+ }
+ }
+ return "OK"
+} -result {OK}
+
+# END testcases30
+
test clock-31.1 {system locale} \
-constraints win \
diff --git a/tests/lreplace.test b/tests/lreplace.test
index 55a36a8..d7f8226 100644
--- a/tests/lreplace.test
+++ b/tests/lreplace.test
@@ -98,7 +98,12 @@ test lreplace-1.26 {lreplace command} {
[set foo [lreplace $foo end end]] \
[set foo [lreplace $foo end end]]
} {a {} {}}
-
+test lreplace-1.27 {lreplace command} {
+ lreplace x 1 1
+} x
+test lreplace-1.28 {lreplace command} {
+ lreplace x 1 1 y
+} {x y}
test lreplace-2.1 {lreplace errors} {
list [catch lreplace msg] $msg
@@ -119,8 +124,8 @@ test lreplace-2.6 {lreplace errors} {
list [catch {lreplace x 3 2} msg] $msg
} {1 {list doesn't contain element 3}}
test lreplace-2.7 {lreplace errors} {
- list [catch {lreplace x 1 1} msg] $msg
-} {1 {list doesn't contain element 1}}
+ list [catch {lreplace x 2 2} msg] $msg
+} {1 {list doesn't contain element 2}}
test lreplace-3.1 {lreplace won't modify shared argument objects} {
proc p {} {
@@ -181,6 +186,12 @@ test lreplace-4.11 {lreplace end index first} {
test lreplace-4.12 {lreplace end index first} {
lreplace {0 1 2 3 4} end-2 2 a b c
} {0 1 a b c 3 4}
+test lreplace-4.13 {lreplace empty list} {
+ lreplace {} 1 1 1
+} 1
+test lreplace-4.14 {lreplace empty list} {
+ lreplace {} 2 2 2
+} 2
test lreplace-5.1 {compiled lreplace: Bug 47ac84309b} {
apply {x {
@@ -192,6 +203,32 @@ test lreplace-5.2 {compiled lreplace: Bug 47ac84309b} {
lreplace $x end 0 A
}} {a b c}
} {a b A c}
+
+# Testing for compiled behaviour. Far too many variations to check with
+# spelt-out tests. Note that this *just* checks whether the compiled version
+# and the interpreted version are the same, not whether the interpreted
+# version is correct.
+apply {{} {
+ set lss {{} {a} {a b c} {a b c d}}
+ set ins {{} A {A B}}
+ set idxs {-2 -1 0 1 2 3 end-3 end-2 end-1 end end+1 end+2}
+ set lreplace lreplace
+
+ foreach ls $lss {
+ foreach a $idxs {
+ foreach b $idxs {
+ foreach i $ins {
+ set expected [list [catch {$lreplace $ls $a $b {*}$i} m] $m]
+ set tester [list lreplace $ls $a $b {*}$i]
+ set script [list catch $tester m]
+ set script "list \[$script\] \$m"
+ test lreplace-6.[incr n] {lreplace battery} \
+ [list apply [list {} $script]] $expected
+ }
+ }
+ }
+ }
+}}
# cleanup
catch {unset foo}
diff --git a/tests/uplevel.test b/tests/uplevel.test
index 3f6b2a8..737c571 100644
--- a/tests/uplevel.test
+++ b/tests/uplevel.test
@@ -101,6 +101,105 @@ test uplevel-4.4 {error: not enough args} -returnCodes error -body {
uplevel 1
}}
} -result {wrong # args: should be "uplevel ?level? command ?arg ...?"}
+test uplevel-4.5 {level parsing} {
+ apply {{} {uplevel 0 {}}}
+} {}
+test uplevel-4.6 {level parsing} {
+ apply {{} {uplevel #0 {}}}
+} {}
+test uplevel-4.7 {level parsing} {
+ apply {{} {uplevel [expr 0] {}}}
+} {}
+test uplevel-4.8 {level parsing} {
+ apply {{} {uplevel #[expr 0] {}}}
+} {}
+test uplevel-4.9 {level parsing} {
+ apply {{} {uplevel -0 {}}}
+} {}
+test uplevel-4.10 {level parsing} {
+ apply {{} {uplevel #-0 {}}}
+} {}
+test uplevel-4.11 {level parsing} {
+ apply {{} {uplevel [expr -0] {}}}
+} {}
+test uplevel-4.12 {level parsing} {
+ apply {{} {uplevel #[expr -0] {}}}
+} {}
+test uplevel-4.13 {level parsing} {
+ apply {{} {uplevel 1 {}}}
+} {}
+test uplevel-4.14 {level parsing} {
+ apply {{} {uplevel #1 {}}}
+} {}
+test uplevel-4.15 {level parsing} {
+ apply {{} {uplevel [expr 1] {}}}
+} {}
+test uplevel-4.16 {level parsing} {
+ apply {{} {uplevel #[expr 1] {}}}
+} {}
+test uplevel-4.17 {level parsing} {
+ apply {{} {uplevel -0xffffffff {}}}
+} {}
+test uplevel-4.18 {level parsing} {
+ apply {{} {uplevel #-0xffffffff {}}}
+} {}
+test uplevel-4.19 {level parsing} {
+ apply {{} {uplevel [expr -0xffffffff] {}}}
+} {}
+test uplevel-4.20 {level parsing} {
+ apply {{} {uplevel #[expr -0xffffffff] {}}}
+} {}
+test uplevel-4.21 {level parsing} -body {
+ apply {{} {uplevel -1 {}}}
+} -returnCodes error -result {invalid command name "-1"}
+test uplevel-4.22 {level parsing} -body {
+ apply {{} {uplevel #-1 {}}}
+} -returnCodes error -result {bad level "#-1"}
+test uplevel-4.23 {level parsing} -body {
+ apply {{} {uplevel [expr -1] {}}}
+} -returnCodes error -result {invalid command name "-1"}
+test uplevel-4.24 {level parsing} -body {
+ apply {{} {uplevel #[expr -1] {}}}
+} -returnCodes error -result {bad level "#-1"}
+test uplevel-4.25 {level parsing} -body {
+ apply {{} {uplevel 0xffffffff {}}}
+} -returnCodes error -result {bad level "0xffffffff"}
+test uplevel-4.26 {level parsing} -body {
+ apply {{} {uplevel #0xffffffff {}}}
+} -returnCodes error -result {bad level "#0xffffffff"}
+test uplevel-4.27 {level parsing} -body {
+ apply {{} {uplevel [expr 0xffffffff] {}}}
+} -returnCodes error -result {bad level "4294967295"}
+test uplevel-4.28 {level parsing} -body {
+ apply {{} {uplevel #[expr 0xffffffff] {}}}
+} -returnCodes error -result {bad level "#4294967295"}
+test uplevel-4.29 {level parsing} -body {
+ apply {{} {uplevel 0.2 {}}}
+} -returnCodes error -result {bad level "0.2"}
+test uplevel-4.30 {level parsing} -body {
+ apply {{} {uplevel #0.2 {}}}
+} -returnCodes error -result {bad level "#0.2"}
+test uplevel-4.31 {level parsing} -body {
+ apply {{} {uplevel [expr 0.2] {}}}
+} -returnCodes error -result {bad level "0.2"}
+test uplevel-4.32 {level parsing} -body {
+ apply {{} {uplevel #[expr 0.2] {}}}
+} -returnCodes error -result {bad level "#0.2"}
+test uplevel-4.33 {level parsing} -body {
+ apply {{} {uplevel .2 {}}}
+} -returnCodes error -result {invalid command name ".2"}
+test uplevel-4.34 {level parsing} -body {
+ apply {{} {uplevel #.2 {}}}
+} -returnCodes error -result {bad level "#.2"}
+test uplevel-4.35 {level parsing} -body {
+ apply {{} {uplevel [expr .2] {}}}
+} -returnCodes error -result {bad level "0.2"}
+test uplevel-4.36 {level parsing} -body {
+ apply {{} {uplevel #[expr .2] {}}}
+} -returnCodes error -result {bad level "#0.2"}
+
+
+
proc a2 {} {
uplevel a3
diff --git a/tests/utf.test b/tests/utf.test
index ceb1af7..a03dd6c 100644
--- a/tests/utf.test
+++ b/tests/utf.test
@@ -302,7 +302,7 @@ test utf-21.1 {TclUniCharIsAlnum} {
} {1}
test utf-21.2 {unicode alnum char in regc_locale.c} {
# this returns 1 with Unicode 7 compliance
- list [regexp {^[[:alnum:]]+$} \u1040\u021f\u0220] [regexp {^\w+$} \u1040\u021f\u0220]
+ list [regexp {^[[:alnum:]]+$} \u1040\u021f\u0220] [regexp {^\w+$} \u1040\u021f\u0220_\u203f\u2040\u2054\ufe33\ufe34\ufe4d\ufe4e\ufe4f\uff3f]
} {1 1}
test utf-21.3 {unicode print char in regc_locale.c} {
# this returns 1 with Unicode 7 compliance
diff --git a/tests/zlib.test b/tests/zlib.test
index 7a486ba..968469d 100644
--- a/tests/zlib.test
+++ b/tests/zlib.test
@@ -875,6 +875,24 @@ test zlib-11.3 {Bug 3595576 variant} -setup {
} -cleanup {
removeFile $file
} -returnCodes error -result {can't set "noSuchNs::foo": parent namespace doesn't exist}
+
+test zlib-12.1 {Tk Bug 9eb55debc5} -constraints zlib -setup {
+ set stream [zlib stream compress]
+} -body {
+ for {set opts {};set y 0} {$y < 60} {incr y} {
+ for {set line {};set x 0} {$x < 100} {incr x} {
+ append line [binary format ccc $x $y 128]
+ }
+ if {$y == 59} {
+ set opts -finalize
+ }
+ $stream put {*}$opts $line
+ }
+ set data [$stream get]
+ list [string length $data] [string length [zlib decompress $data]]
+} -cleanup {
+ $stream close
+} -result {12026 18000}
::tcltest::cleanupTests
return
diff --git a/unix/tclUnixNotfy.c b/unix/tclUnixNotfy.c
index 1457890..3422089 100644
--- a/unix/tclUnixNotfy.c
+++ b/unix/tclUnixNotfy.c
@@ -1,7 +1,5 @@
-#define AT_FORK_INIT_VALUE 0
-#define RESET_ATFORK_MUTEX 1
/*
- * tclUnixNotify.c --
+ * tclUnixNotfy.c --
*
* This file contains the implementation of the select()-based
* Unix-specific notifier, which is the lowest-level part of the Tcl
@@ -197,9 +195,7 @@ static Tcl_ThreadId notifierThread;
#ifdef TCL_THREADS
static void NotifierThreadProc(ClientData clientData);
#if defined(HAVE_PTHREAD_ATFORK)
-static int atForkInit = AT_FORK_INIT_VALUE;
-static void AtForkPrepare(void);
-static void AtForkParent(void);
+static int atForkInit = 0;
static void AtForkChild(void);
#endif /* HAVE_PTHREAD_ATFORK */
#endif /* TCL_THREADS */
@@ -256,7 +252,7 @@ extern unsigned char __stdcall TranslateMessage(const MSG *);
* Threaded-cygwin specific constants and functions in this file:
*/
-static const WCHAR NotfyClassName[] = L"TclNotifier";
+static const WCHAR className[] = L"TclNotifier";
static DWORD __stdcall NotifierProc(void *hwnd, unsigned int message,
void *wParam, void *lParam);
#endif /* TCL_THREADS && __CYGWIN__ */
@@ -345,7 +341,7 @@ Tcl_InitNotifier(void)
class.hInstance = TclWinGetTclInstance();
class.hbrBackground = NULL;
class.lpszMenuName = NULL;
- class.lpszClassName = NotfyClassName;
+ class.lpszClassName = className;
class.lpfnWndProc = NotifierProc;
class.hIcon = NULL;
class.hCursor = NULL;
@@ -370,7 +366,7 @@ Tcl_InitNotifier(void)
*/
if (!atForkInit) {
- int result = pthread_atfork(AtForkPrepare, AtForkParent, AtForkChild);
+ int result = pthread_atfork(NULL, NULL, AtForkChild);
if (result) {
Tcl_Panic("Tcl_InitNotifier: pthread_atfork failed");
@@ -1351,54 +1347,6 @@ NotifierThreadProc(
/*
*----------------------------------------------------------------------
*
- * AtForkPrepare --
- *
- * Lock the notifier in preparation for a fork.
- *
- * Results:
- * None.
- *
- * Side effects:
- * None.
- *
- *----------------------------------------------------------------------
- */
-
-static void
-AtForkPrepare(void)
-{
-#if RESET_ATFORK_MUTEX == 0
- pthread_mutex_lock(&notifierInitMutex);
-#endif
-}
-
-/*
- *----------------------------------------------------------------------
- *
- * AtForkParent --
- *
- * Unlock the notifier in the parent after a fork.
- *
- * Results:
- * None.
- *
- * Side effects:
- * None.
- *
- *----------------------------------------------------------------------
- */
-
-static void
-AtForkParent(void)
-{
-#if RESET_ATFORK_MUTEX == 0
- pthread_mutex_unlock(&notifierInitMutex);
-#endif
-}
-
-/*
- *----------------------------------------------------------------------
- *
* AtForkChild --
*
* Unlock and reinstall the notifier in the child after a fork.
@@ -1418,12 +1366,8 @@ AtForkChild(void)
if (notifierThreadRunning == 1) {
pthread_cond_destroy(&notifierCV);
}
-#if RESET_ATFORK_MUTEX == 0
- pthread_mutex_unlock(&notifierInitMutex);
-#else
pthread_mutex_init(&notifierInitMutex, NULL);
pthread_mutex_init(&notifierMutex, NULL);
-#endif
pthread_cond_init(&notifierCV, NULL);
/*
@@ -1455,8 +1399,8 @@ AtForkChild(void)
*/
#ifdef __CYGWIN__
DestroyWindow(tsdPtr->hwnd);
- tsdPtr->hwnd = CreateWindowExW(NULL, NotfyClassName,
- NotfyClassName, 0, 0, 0, 0, 0, NULL, NULL,
+ tsdPtr->hwnd = CreateWindowExW(NULL, className,
+ className, 0, 0, 0, 0, 0, NULL, NULL,
TclWinGetTclInstance(), NULL);
ResetEvent(tsdPtr->event);
#else
diff --git a/unix/tclUnixThrd.c b/unix/tclUnixThrd.c
index 554a2dc..cf81850 100644
--- a/unix/tclUnixThrd.c
+++ b/unix/tclUnixThrd.c
@@ -673,7 +673,6 @@ TclpInetNtoa(
*/
#ifdef USE_THREAD_ALLOC
-static volatile int initialized = 0;
static pthread_key_t key;
typedef struct allocMutex {
@@ -710,6 +709,14 @@ TclpFreeAllocMutex(
}
void
+TclpInitAllocCache(void)
+{
+ pthread_mutex_lock(allocLockPtr);
+ pthread_key_create(&key, TclpFreeAllocCache);
+ pthread_mutex_unlock(allocLockPtr);
+}
+
+void
TclpFreeAllocCache(
void *ptr)
{
@@ -721,28 +728,14 @@ TclpFreeAllocCache(
TclFreeAllocCache(ptr);
pthread_setspecific(key, NULL);
- } else if (initialized) {
- /*
- * Called by us in TclFinalizeThreadAlloc() during the library
- * finalization initiated from Tcl_Finalize()
- */
-
+ } else {
pthread_key_delete(key);
- initialized = 0;
}
}
void *
TclpGetAllocCache(void)
{
- if (!initialized) {
- pthread_mutex_lock(allocLockPtr);
- if (!initialized) {
- pthread_key_create(&key, TclpFreeAllocCache);
- initialized = 1;
- }
- pthread_mutex_unlock(allocLockPtr);
- }
return pthread_getspecific(key);
}
diff --git a/win/coffbase.txt b/win/coffbase.txt
index 0ebe18a..3314f26 100644
--- a/win/coffbase.txt
+++ b/win/coffbase.txt
@@ -34,6 +34,7 @@ tclsdl 0x10B20000 0x00080000
vqtcl 0x10C00000 0x00010000
tdbc 0x10C40000 0x00010000
thread 0x10C80000 0x00020000
+nsf 0x10ca0000 0x00080000
;
; insert new packages here
;
diff --git a/win/tclWinNotify.c b/win/tclWinNotify.c
index 4543b02..1ad022d 100644
--- a/win/tclWinNotify.c
+++ b/win/tclWinNotify.c
@@ -50,8 +50,9 @@ static Tcl_ThreadDataKey dataKey;
*/
static int notifierCount = 0;
-static const TCHAR classname[] = TEXT("TclNotifier");
-TCL_DECLARE_MUTEX(notifierMutex)
+static const TCHAR className[] = TEXT("TclNotifier");
+static int initialized = 0;
+static CRITICAL_SECTION notifierMutex;
/*
* Static routines defined in this file.
@@ -85,12 +86,19 @@ Tcl_InitNotifier(void)
ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
WNDCLASS class;
+ TclpMasterLock();
+ if (!initialized) {
+ initialized = 1;
+ InitializeCriticalSection(&notifierMutex);
+ }
+ TclpMasterUnlock();
+
/*
* Register Notifier window class if this is the first thread to use
* this module.
*/
- Tcl_MutexLock(&notifierMutex);
+ EnterCriticalSection(&notifierMutex);
if (notifierCount == 0) {
class.style = 0;
class.cbClsExtra = 0;
@@ -98,7 +106,7 @@ Tcl_InitNotifier(void)
class.hInstance = TclWinGetTclInstance();
class.hbrBackground = NULL;
class.lpszMenuName = NULL;
- class.lpszClassName = classname;
+ class.lpszClassName = className;
class.lpfnWndProc = NotifierProc;
class.hIcon = NULL;
class.hCursor = NULL;
@@ -108,7 +116,7 @@ Tcl_InitNotifier(void)
}
}
notifierCount++;
- Tcl_MutexUnlock(&notifierMutex);
+ LeaveCriticalSection(&notifierMutex);
tsdPtr->pending = 0;
tsdPtr->timerActive = 0;
@@ -183,12 +191,14 @@ Tcl_FinalizeNotifier(
* notifier window class.
*/
- Tcl_MutexLock(&notifierMutex);
- notifierCount--;
- if (notifierCount == 0) {
- UnregisterClass(classname, TclWinGetTclInstance());
+ EnterCriticalSection(&notifierMutex);
+ if (notifierCount) {
+ notifierCount--;
+ if (notifierCount == 0) {
+ UnregisterClass(className, TclWinGetTclInstance());
+ }
}
- Tcl_MutexUnlock(&notifierMutex);
+ LeaveCriticalSection(&notifierMutex);
}
}
@@ -350,7 +360,7 @@ Tcl_ServiceModeHook(
*/
if (mode == TCL_SERVICE_ALL && !tsdPtr->hwnd) {
- tsdPtr->hwnd = CreateWindow(classname, classname,
+ tsdPtr->hwnd = CreateWindow(className, className,
WS_TILED, 0, 0, 0, 0, NULL, NULL, TclWinGetTclInstance(),
NULL);
diff --git a/win/tclWinSock.c b/win/tclWinSock.c
index a022ed5..cc77afe 100644
--- a/win/tclWinSock.c
+++ b/win/tclWinSock.c
@@ -62,15 +62,6 @@
#undef TCL_FEATURE_KEEPALIVE_NAGLE
/*
- * Make sure to remove the redirection defines set in tclWinPort.h that is in
- * use in other sections of the core, except for us.
- */
-
-#undef getservbyname
-#undef getsockopt
-#undef setsockopt
-
-/*
* Helper macros to make parts of this file clearer. The macros do exactly
* what they say on the tin. :-) They also only ever refer to their arguments
* once, and so can be used without regard to side effects.
@@ -90,7 +81,7 @@
*/
static int initialized = 0;
-static const TCHAR classname[] = TEXT("TclSocket");
+static const TCHAR className[] = TEXT("TclSocket");
TCL_DECLARE_MUTEX(socketMutex)
/*
@@ -2061,7 +2052,6 @@ Tcl_OpenTcpServer(
char channelName[SOCK_CHAN_LENGTH];
u_long flag = 1; /* Indicates nonblocking mode. */
const char *errorMsg = NULL;
- ThreadSpecificData *tsdPtr = TclThreadDataKeyGet(&dataKey);
if (TclpHasSockets(interp) != TCL_OK) {
return NULL;
@@ -2177,6 +2167,7 @@ error:
}
if (statePtr != NULL) {
+ ThreadSpecificData *tsdPtr = TclThreadDataKeyGet(&dataKey);
statePtr->acceptProc = acceptProc;
statePtr->acceptProcData = acceptProcData;
@@ -2336,7 +2327,7 @@ InitSockets(void)
windowClass.hInstance = TclWinGetTclInstance();
windowClass.hbrBackground = NULL;
windowClass.lpszMenuName = NULL;
- windowClass.lpszClassName = classname;
+ windowClass.lpszClassName = className;
windowClass.lpfnWndProc = SocketProc;
windowClass.hIcon = NULL;
windowClass.hCursor = NULL;
@@ -2466,7 +2457,7 @@ SocketExitHandler(
*/
TclpFinalizeSockets();
- UnregisterClass(classname, TclWinGetTclInstance());
+ UnregisterClass(className, TclWinGetTclInstance());
initialized = 0;
Tcl_MutexUnlock(&socketMutex);
}
@@ -2992,7 +2983,7 @@ SocketThread(
* Create a dummy window receiving socket events.
*/
- tsdPtr->hwnd = CreateWindow(classname, classname, WS_TILED, 0, 0, 0, 0,
+ tsdPtr->hwnd = CreateWindow(className, className, WS_TILED, 0, 0, 0, 0,
NULL, NULL, windowClass.hInstance, arg);
/*
diff --git a/win/tclWinThrd.c b/win/tclWinThrd.c
index e44363b..987734d 100644
--- a/win/tclWinThrd.c
+++ b/win/tclWinThrd.c
@@ -119,7 +119,6 @@ typedef struct WinCondition {
*/
#ifdef USE_THREAD_ALLOC
-static int once;
static DWORD tlsKey;
typedef struct allocMutex {
@@ -968,24 +967,24 @@ TclpFreeAllocMutex(
free(lockPtr);
}
-void *
-TclpGetAllocCache(void)
+void
+TclpInitAllocCache(void)
{
- void *result;
-
- if (!once) {
- /*
- * We need to make sure that TclpFreeAllocCache is called on each
- * thread that calls this, but only on threads that call this.
- */
+ /*
+ * We need to make sure that TclpFreeAllocCache is called on each
+ * thread that calls this, but only on threads that call this.
+ */
- tlsKey = TlsAlloc();
- once = 1;
- if (tlsKey == TLS_OUT_OF_INDEXES) {
- Tcl_Panic("could not allocate thread local storage");
- }
+ tlsKey = TlsAlloc();
+ if (tlsKey == TLS_OUT_OF_INDEXES) {
+ Tcl_Panic("could not allocate thread local storage");
}
+}
+void *
+TclpGetAllocCache(void)
+{
+ void *result;
result = TlsGetValue(tlsKey);
if ((result == NULL) && (GetLastError() != NO_ERROR)) {
Tcl_Panic("TlsGetValue failed from TclpGetAllocCache");
@@ -1021,7 +1020,7 @@ TclpFreeAllocCache(
if (!success) {
Tcl_Panic("TlsSetValue failed from TclpFreeAllocCache");
}
- } else if (once) {
+ } else {
/*
* Called by us in TclFinalizeThreadAlloc() during the library
* finalization initiated from Tcl_Finalize()
@@ -1031,9 +1030,7 @@ TclpFreeAllocCache(
if (!success) {
Tcl_Panic("TlsFree failed from TclpFreeAllocCache");
}
- once = 0; /* reset for next time. */
}
-
}
#endif /* USE_THREAD_ALLOC */