diff options
author | hypnotoad <yoda@etoyoc.com> | 2015-10-26 04:02:36 (GMT) |
---|---|---|
committer | hypnotoad <yoda@etoyoc.com> | 2015-10-26 04:02:36 (GMT) |
commit | 90b38da321e1b5d5885e4d4f57c8e8bc46a00793 (patch) | |
tree | 21fefd2f79c00cd95297dea6fce75902ffe07ba1 | |
parent | e448db56ee02e80b29e2fc3c2d07313e592ba554 (diff) | |
parent | 3fc99c04f6169eb97c2581310c254aefc9e14d6a (diff) | |
download | tcl-90b38da321e1b5d5885e4d4f57c8e8bc46a00793.zip tcl-90b38da321e1b5d5885e4d4f57c8e8bc46a00793.tar.gz tcl-90b38da321e1b5d5885e4d4f57c8e8bc46a00793.tar.bz2 |
Merged with trunk, fixes to allow builds outside of the tcl/unix|win directory
228 files changed, 13887 insertions, 10032 deletions
diff --git a/.fossil-settings/crnl-glob b/.fossil-settings/crnl-glob index e69de29..c014320 100644 --- a/.fossil-settings/crnl-glob +++ b/.fossil-settings/crnl-glob @@ -0,0 +1,10 @@ +tools/tcl.hpj.in +tools/tcl.wse.in +win/buildall.vc.bat +win/coffbase.txt +win/makefile.bc +win/makefile.vc +win/rules.vc +win/tcl.dsp +win/tcl.dsw +win/tcl.hpj.in diff --git a/.fossil-settings/encoding-glob b/.fossil-settings/encoding-glob new file mode 100644 index 0000000..c014320 --- /dev/null +++ b/.fossil-settings/encoding-glob @@ -0,0 +1,10 @@ +tools/tcl.hpj.in +tools/tcl.wse.in +win/buildall.vc.bat +win/coffbase.txt +win/makefile.bc +win/makefile.vc +win/rules.vc +win/tcl.dsp +win/tcl.dsw +win/tcl.hpj.in @@ -913,6 +913,14 @@ a better first place to look now. * win/nmakehlp.c: Let "nmakehlp -V" start searching digits after the found match (suggested by Harald Oehlmann). +2012-09-19 Harald Oehlmann <oehhar@users.sf.net> + + IMPLEMENTATION OF TIP#412. + + * library/msgcat/msgcat.tcl: dynamic locale change with mc file + * library/clock.tcl: load on locale change. + clock uses new msgcat features. + 2012-09-07 Harald Oehlmann <oehhar@users.sf.net> *** 8.6b3 TAGGED FOR RELEASE *** @@ -8455,6 +8455,7 @@ include ::oo::class (fellows) 2014-08-28 (bug)[b9e1a3] Correct Method Search Order (nadkarni,fellows) => TclOO 1.0.3 + *** POTENTIAL INCOMPATIBILITY *** 2014-09-05 (bug)[ccc2c2] Regression [lreplace {} 1 1] (bron,fellows) @@ -8527,3 +8528,7 @@ include ::oo::class (fellows) *** POTENTIAL INCOMPATIBILITY *** --- Released 8.6.4, March 12, 2015 --- http://core.tcl.tk/tcl/ for details + +2015-06-25 (TIP 412) msgcat dynamic locale change and package private locale (oehlmann) +=> msgcat 1.6.0 + diff --git a/compat/fake-rfc2553.c b/compat/fake-rfc2553.c index 3b91041..c8e69400 100644 --- a/compat/fake-rfc2553.c +++ b/compat/fake-rfc2553.c @@ -1,7 +1,7 @@ /* * Copyright (C) 2000-2003 Damien Miller. All rights reserved. * Copyright (C) 1999 WIDE Project. All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: @@ -13,7 +13,7 @@ * 3. Neither the name of the project nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. - * + * * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE @@ -67,7 +67,7 @@ strlcpy(char *dst, const char *src, size_t siz) } #endif -int fake_getnameinfo(const struct sockaddr *sa, size_t salen, char *host, +int fake_getnameinfo(const struct sockaddr *sa, size_t salen, char *host, size_t hostlen, char *serv, size_t servlen, int flags) { struct sockaddr_in *sin = (struct sockaddr_in *)sa; @@ -96,7 +96,7 @@ int fake_getnameinfo(const struct sockaddr *sa, size_t salen, char *host, } else { int ret; Tcl_MutexLock(&netdbMutex); - hp = gethostbyaddr((char *)&sin->sin_addr, + hp = gethostbyaddr((char *)&sin->sin_addr, sizeof(struct in_addr), AF_INET); if (hp == NULL) { ret = EAI_NODATA; @@ -130,7 +130,7 @@ fake_gai_strerror(int err) default: return ("unknown/invalid error."); } -} +} #endif /* !HAVE_GAI_STRERROR */ #ifndef HAVE_FREEADDRINFO @@ -156,9 +156,9 @@ addrinfo *malloc_ai(int port, u_long addr, const struct addrinfo *hints) ai = malloc(sizeof(*ai) + sizeof(struct sockaddr_in)); if (ai == NULL) return (NULL); - + memset(ai, '\0', sizeof(*ai) + sizeof(struct sockaddr_in)); - + ai->ai_addr = (struct sockaddr *)(ai + 1); /* XXX -- ssh doesn't use sa_len */ ai->ai_addrlen = sizeof(struct sockaddr_in); @@ -166,7 +166,7 @@ addrinfo *malloc_ai(int port, u_long addr, const struct addrinfo *hints) ((struct sockaddr_in *)(ai)->ai_addr)->sin_port = port; ((struct sockaddr_in *)(ai)->ai_addr)->sin_addr.s_addr = addr; - + /* XXX: the following is not generally correct, but does what we want */ if (hints->ai_socktype) ai->ai_socktype = hints->ai_socktype; @@ -180,7 +180,7 @@ addrinfo *malloc_ai(int port, u_long addr, const struct addrinfo *hints) } int -fake_getaddrinfo(const char *hostname, const char *servname, +fake_getaddrinfo(const char *hostname, const char *servname, const struct addrinfo *hints, struct addrinfo **res) { struct hostent *hp; @@ -211,29 +211,29 @@ fake_getaddrinfo(const char *hostname, const char *servname, if (hostname && inet_aton(hostname, &in) != 0) addr = in.s_addr; *res = malloc_ai(port, addr, hints); - if (*res == NULL) + if (*res == NULL) return (EAI_MEMORY); return (0); } - + if (!hostname) { *res = malloc_ai(port, htonl(0x7f000001), hints); - if (*res == NULL) + if (*res == NULL) return (EAI_MEMORY); return (0); } - + if (inet_aton(hostname, &in)) { *res = malloc_ai(port, in.s_addr, hints); - if (*res == NULL) + if (*res == NULL) return (EAI_MEMORY); return (0); } - + /* Don't try DNS if AI_NUMERICHOST is set */ if (hints && hints->ai_flags & AI_NUMERICHOST) return (EAI_NONAME); - + Tcl_MutexLock(&netdbMutex); hp = gethostbyname(hostname); if (hp && hp->h_name && hp->h_name[0] && hp->h_addr_list[0]) { diff --git a/compat/fake-rfc2553.h b/compat/fake-rfc2553.h index cc26f55..6413170 100644 --- a/compat/fake-rfc2553.h +++ b/compat/fake-rfc2553.h @@ -1,7 +1,7 @@ /* * Copyright (C) 2000-2003 Damien Miller. All rights reserved. * Copyright (C) 1999 WIDE Project. All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: @@ -13,7 +13,7 @@ * 3. Neither the name of the project nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. - * + * * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE @@ -39,7 +39,7 @@ #define _FAKE_RFC2553_H /* - * First, socket and INET6 related definitions + * First, socket and INET6 related definitions */ #ifndef HAVE_STRUCT_SOCKADDR_STORAGE # define _SS_MAXSIZE 128 /* Implementation specific max size */ @@ -146,7 +146,7 @@ struct addrinfo { # undef getaddrinfo #endif #define getaddrinfo(a,b,c,d) (fake_getaddrinfo(a,b,c,d)) -int getaddrinfo(const char *, const char *, +int getaddrinfo(const char *, const char *, const struct addrinfo *, struct addrinfo **); #endif /* !HAVE_GETADDRINFO */ @@ -162,7 +162,7 @@ void freeaddrinfo(struct addrinfo *); #ifndef HAVE_GETNAMEINFO #define getnameinfo(a,b,c,d,e,f,g) (fake_getnameinfo(a,b,c,d,e,f,g)) -int getnameinfo(const struct sockaddr *, size_t, char *, size_t, +int getnameinfo(const struct sockaddr *, size_t, char *, size_t, char *, size_t, int); #endif /* !HAVE_GETNAMEINFO */ diff --git a/compat/fixstrtod.c b/compat/fixstrtod.c index 91f309e..63fb8ef 100644 --- a/compat/fixstrtod.c +++ b/compat/fixstrtod.c @@ -1,4 +1,4 @@ -/* +/* * fixstrtod.c -- * * Source code for the "fixstrtod" procedure. This procedure is diff --git a/compat/gettod.c b/compat/gettod.c index 28e1432..ca20cf8 100644 --- a/compat/gettod.c +++ b/compat/gettod.c @@ -1,4 +1,4 @@ -/* +/* * gettod.c -- * * This file provides the gettimeofday function on systems diff --git a/compat/limits.h b/compat/limits.h deleted file mode 100644 index 2cb082b..0000000 --- a/compat/limits.h +++ /dev/null @@ -1,22 +0,0 @@ -/* - * limits.h -- - * - * This is a dummy header file to #include in Tcl when there - * is no limits.h in /usr/include. There are only a few - * definitions here; also see tclPort.h, which already - * #defines some of the things here if they're not arleady - * defined. - * - * Copyright (c) 1991 The Regents of the University of California. - * Copyright (c) 1994 Sun Microsystems, Inc. - * - * See the file "license.terms" for information on usage and redistribution - * of this file, and for a DISCLAIMER OF ALL WARRANTIES. - */ - -#define LONG_MIN 0x80000000 -#define LONG_MAX 0x7fffffff -#define INT_MIN 0x80000000 -#define INT_MAX 0x7fffffff -#define SHRT_MIN 0x8000 -#define SHRT_MAX 0x7fff diff --git a/compat/mkstemp.c b/compat/mkstemp.c index eaa0b66..1a44dfa 100644 --- a/compat/mkstemp.c +++ b/compat/mkstemp.c @@ -1,4 +1,4 @@ -/* +/* * mkstemp.c -- * * Source code for the "mkstemp" library routine. diff --git a/compat/opendir.c b/compat/opendir.c index a18f96b..22e8a3a 100644 --- a/compat/opendir.c +++ b/compat/opendir.c @@ -1,4 +1,4 @@ -/* +/* * opendir.c -- * * This file provides dirent-style directory-reading procedures for V7 diff --git a/compat/strncasecmp.c b/compat/strncasecmp.c index 299715d..0a69f35 100644 --- a/compat/strncasecmp.c +++ b/compat/strncasecmp.c @@ -1,4 +1,4 @@ -/* +/* * strncasecmp.c -- * * Source code for the "strncasecmp" library routine. diff --git a/compat/strstr.c b/compat/strstr.c index 6698c9f..e3b9b8d 100644 --- a/compat/strstr.c +++ b/compat/strstr.c @@ -1,4 +1,4 @@ -/* +/* * strstr.c -- * * Source code for the "strstr" library routine. diff --git a/compat/strtod.c b/compat/strtod.c index cb9f76d..9643c09 100644 --- a/compat/strtod.c +++ b/compat/strtod.c @@ -1,4 +1,4 @@ -/* +/* * strtod.c -- * * Source code for the "strtod" library procedure. @@ -137,7 +137,7 @@ strtod( * has more than 18 digits, ignore the extras, since they can't affect the * value anyway. */ - + pExp = p; p -= mantSize; if (decPt < 0) { @@ -217,7 +217,7 @@ strtod( * by processing the exponent one bit at a time to combine many powers of * 2 of 10. Then combine the exponent with the fraction. */ - + if (exp < 0) { expSign = TRUE; exp = -exp; diff --git a/compat/strtol.c b/compat/strtol.c index b111d97..811006a 100644 --- a/compat/strtol.c +++ b/compat/strtol.c @@ -1,4 +1,4 @@ -/* +/* * strtol.c -- * * Source code for the "strtol" library procedure. diff --git a/compat/strtoul.c b/compat/strtoul.c index d572c2b..15587f1 100644 --- a/compat/strtoul.c +++ b/compat/strtoul.c @@ -1,4 +1,4 @@ -/* +/* * strtoul.c -- * * Source code for the "strtoul" library procedure. @@ -90,7 +90,7 @@ strtoul( * If no base was provided, pick one from the leading characters of the * string. */ - + if (base == 0) { if (*p == '0') { p += 1; @@ -206,7 +206,7 @@ strtoul( if (overflow) { errno = ERANGE; return ULONG_MAX; - } + } if (negative) { return -result; } diff --git a/compat/unistd.h b/compat/unistd.h index 2de5bd0..a8f14f2 100644 --- a/compat/unistd.h +++ b/compat/unistd.h @@ -20,7 +20,7 @@ #define NULL 0 #endif -/* +/* * Strict POSIX stuff goes here. Extensions go down below, in the ifndef * _POSIX_SOURCE section. */ diff --git a/compat/waitpid.c b/compat/waitpid.c index 8f65799..e03275a 100644 --- a/compat/waitpid.c +++ b/compat/waitpid.c @@ -1,4 +1,4 @@ -/* +/* * waitpid.c -- * * This procedure emulates the POSIX waitpid kernel call on BSD systems diff --git a/doc/AddErrInfo.3 b/doc/AddErrInfo.3 index d4bf7d5..e6563a0 100644 --- a/doc/AddErrInfo.3 +++ b/doc/AddErrInfo.3 @@ -4,7 +4,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_AddErrorInfo 3 8.5 Tcl "Tcl Library Procedures" .so man.macros .BS diff --git a/doc/Class.3 b/doc/Class.3 index 7e421fe..1c3fe08 100644 --- a/doc/Class.3 +++ b/doc/Class.3 @@ -71,7 +71,8 @@ The name of the object to create, or NULL if a new unused name is to be automatically selected. .AP "const char" *nsName in The name of the namespace to create for the object's private use, or NULL if a -new unused name is to be automatically selected. +new unused name is to be automatically selected. The namespace must not +already exist. .AP int objc in The number of elements in the \fIobjv\fR array. .AP "Tcl_Obj *const" *objv in diff --git a/doc/DString.3 b/doc/DString.3 index 0e571d2..00f1b8a 100644 --- a/doc/DString.3 +++ b/doc/DString.3 @@ -4,7 +4,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_DString 3 7.4 Tcl "Tcl Library Procedures" .so man.macros .BS diff --git a/doc/Encoding.3 b/doc/Encoding.3 index 6664b3b..81ef508 100644 --- a/doc/Encoding.3 +++ b/doc/Encoding.3 @@ -3,7 +3,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_GetEncoding 3 "8.1" Tcl "Tcl Library Procedures" .so man.macros .BS @@ -76,7 +76,7 @@ desired. .AP "const char" *name in Name of encoding to load. .AP Tcl_Encoding encoding in -The encoding to query, free, or use for converting text. If \fIencoding\fR is +The encoding to query, free, or use for converting text. If \fIencoding\fR is NULL, the current system encoding is used. .AP Tcl_Obj *objPtr in Name of encoding to get token for. @@ -86,17 +86,17 @@ Points to storage where encoding token is to be written. For the \fBTcl_ExternalToUtf\fR functions, an array of bytes in the specified encoding that are to be converted to UTF-8. For the \fBTcl_UtfToExternal\fR and \fBTcl_WinUtfToTChar\fR functions, an array of -UTF-8 characters to be converted to the specified encoding. +UTF-8 characters to be converted to the specified encoding. .AP "const TCHAR" *tsrc in An array of Windows TCHAR characters to convert to UTF-8. -.AP int srcLen in -Length of \fIsrc\fR or \fItsrc\fR in bytes. If the length is negative, the +.AP int srcLen in +Length of \fIsrc\fR or \fItsrc\fR in bytes. If the length is negative, the encoding-specific length of the string is used. .AP Tcl_DString *dstPtr out Pointer to an uninitialized or free \fBTcl_DString\fR in which the converted result will be stored. .AP int flags in -Various flag bits OR-ed together. +Various flag bits OR-ed together. \fBTCL_ENCODING_START\fR signifies that the source buffer is the first block in a (potentially multi-block) input stream, telling the conversion routine to reset to an initial state and @@ -108,7 +108,7 @@ byte is converted and then to reset to an initial state. \fBTCL_ENCODING_STOPONERROR\fR signifies that the conversion routine should return immediately upon reading a source character that does not exist in the target encoding; otherwise a default fallback character will -automatically be substituted. +automatically be substituted. .AP Tcl_EncodingState *statePtr in/out Used when converting a (generally long or indefinite length) byte stream in a piece-by-piece fashion. The conversion routine stores its current @@ -116,7 +116,7 @@ state in \fI*statePtr\fR after \fIsrc\fR (the buffer containing the current piece) has been converted; that state information must be passed back when converting the next piece of the stream so the conversion routine knows what state it was in when it left off at the end of the -last piece. May be NULL, in which case the value specified for \fIflags\fR +last piece. May be NULL, in which case the value specified for \fIflags\fR is ignored and the source buffer is assumed to contain the complete string to convert. .AP char *dst out @@ -137,11 +137,11 @@ stored in the output buffer. May be NULL. .AP Tcl_DString *bufPtr out Storage for the prescribed system encoding name. .AP "const Tcl_EncodingType" *typePtr in -Structure that defines a new type of encoding. +Structure that defines a new type of encoding. .AP Tcl_Obj *searchPath in List of filesystem directories in which to search for encoding data files. .AP "const char" *path in -A path to the location of the encoding file. +A path to the location of the encoding file. .BE .SH INTRODUCTION .PP @@ -180,13 +180,13 @@ The first time \fIname\fR is seen, \fBTcl_GetEncoding\fR returns an encoding with a reference count of 1. If the same \fIname\fR is requested further times, then the reference count for that encoding is incremented without the overhead of allocating a new encoding and all its associated -data structures. +data structures. .PP When an \fIencoding\fR is no longer needed, \fBTcl_FreeEncoding\fR should be called to release it. When an \fIencoding\fR is no longer in use anywhere (i.e., it has been freed as many times as it has been gotten) \fBTcl_FreeEncoding\fR will release all storage the encoding was using -and delete it from the database. +and delete it from the database. .PP \fBTcl_GetEncodingFromObj\fR treats the string representation of \fIobjPtr\fR as an encoding name, and finds an encoding with that @@ -201,7 +201,7 @@ on the resulting encoding token when that token will no longer be used. .PP \fBTcl_ExternalToUtfDString\fR converts a source buffer \fIsrc\fR from the -specified \fIencoding\fR into UTF-8. The converted bytes are stored in +specified \fIencoding\fR into UTF-8. The converted bytes are stored in \fIdstPtr\fR, which is then null-terminated. The caller should eventually call \fBTcl_DStringFree\fR to free any information stored in \fIdstPtr\fR. When converting, if any of the characters in the source buffer cannot be @@ -227,17 +227,17 @@ sequence, but more bytes were needed to complete this sequence. A subsequent call to the conversion routine should pass a buffer containing the unconverted bytes that remained in \fIsrc\fR plus some further bytes from the source stream to properly convert the formerly split-up multibyte -sequence. +sequence. .IP \fBTCL_CONVERT_SYNTAX\fR 29 The source buffer contained an invalid character sequence. This may occur if the input stream has been damaged or if the input encoding method was misidentified. .IP \fBTCL_CONVERT_UNKNOWN\fR 29 The source buffer contained a character that could not be represented in -the target encoding and \fBTCL_ENCODING_STOPONERROR\fR was specified. +the target encoding and \fBTCL_ENCODING_STOPONERROR\fR was specified. .RE .LP -\fBTcl_UtfToExternalDString\fR converts a source buffer \fIsrc\fR from UTF-8 +\fBTcl_UtfToExternalDString\fR converts a source buffer \fIsrc\fR from UTF-8 into the specified \fIencoding\fR. The converted bytes are stored in \fIdstPtr\fR, which is then terminated with the appropriate encoding-specific null. The caller should eventually call \fBTcl_DStringFree\fR to free any @@ -267,7 +267,7 @@ Unicode encoding. .PP \fBTcl_GetEncodingName\fR is roughly the inverse of \fBTcl_GetEncoding\fR. Given an \fIencoding\fR, the return value is the \fIname\fR argument that -was used to create the encoding. The string returned by +was used to create the encoding. The string returned by \fBTcl_GetEncodingName\fR is only guaranteed to persist until the \fIencoding\fR is deleted. The caller must not modify this string. .PP @@ -306,9 +306,9 @@ reference count of 1. If an encoding with the specified \fIname\fR already exists, then its entry in the database is replaced with the new encoding; the token for the old encoding will remain valid and continue to behave as before, but users of the new token will now call the new -encoding procedures. +encoding procedures. .PP -The \fItypePtr\fR argument to \fBTcl_CreateEncoding\fR contains information +The \fItypePtr\fR argument to \fBTcl_CreateEncoding\fR contains information about the name of the encoding and the procedures that will be called to convert between this encoding and UTF-8. It is defined as follows: .PP @@ -320,7 +320,7 @@ typedef struct Tcl_EncodingType { Tcl_EncodingFreeProc *\fIfreeProc\fR; ClientData \fIclientData\fR; int \fInullSize\fR; -} \fBTcl_EncodingType\fR; +} \fBTcl_EncodingType\fR; .CE .PP The \fIencodingName\fR provides a string name for the encoding, by @@ -350,12 +350,12 @@ type \fBTcl_EncodingConvertProc\fR: .CS typedef int \fBTcl_EncodingConvertProc\fR( ClientData \fIclientData\fR, - const char *\fIsrc\fR, - int \fIsrcLen\fR, - int \fIflags\fR, + const char *\fIsrc\fR, + int \fIsrcLen\fR, + int \fIflags\fR, Tcl_EncodingState *\fIstatePtr\fR, - char *\fIdst\fR, - int \fIdstLen\fR, + char *\fIdst\fR, + int \fIdstLen\fR, int *\fIsrcReadPtr\fR, int *\fIdstWrotePtr\fR, int *\fIdstCharsPtr\fR); @@ -371,12 +371,12 @@ documented at the top, to \fBTcl_ExternalToUtf\fR or \fBTcl_UtfToExternal\fR, with the following exceptions. If the \fIsrcLen\fR argument to one of those high-level functions is negative, the value passed to the callback procedure will be the appropriate -encoding-specific string length of \fIsrc\fR. If any of the \fIsrcReadPtr\fR, +encoding-specific string length of \fIsrc\fR. If any of the \fIsrcReadPtr\fR, \fIdstWrotePtr\fR, or \fIdstCharsPtr\fR arguments to one of the high-level functions is NULL, the corresponding value passed to the callback procedure will be a non-NULL location. .PP -The callback procedure \fIfreeProc\fR, if non-NULL, should match the type +The callback procedure \fIfreeProc\fR, if non-NULL, should match the type \fBTcl_EncodingFreeProc\fR: .PP .CS @@ -386,11 +386,11 @@ typedef void \fBTcl_EncodingFreeProc\fR( .PP This \fIfreeProc\fR function is called when the encoding is deleted. The \fIclientData\fR parameter is the same as the \fIclientData\fR field -specified to \fBTcl_CreateEncoding\fR when the encoding was created. +specified to \fBTcl_CreateEncoding\fR when the encoding was created. .PP \fBTcl_GetEncodingSearchPath\fR and \fBTcl_SetEncodingSearchPath\fR are called to access and set the list of filesystem directories searched -for encoding data files. +for encoding data files. .PP The value returned by \fBTcl_GetEncodingSearchPath\fR is the value stored by the last successful call to @@ -423,7 +423,7 @@ encoding files that can be loaded using the same mechanism. These encoding files contain information about the tables and/or escape sequences used to map between an external encoding and Unicode. The external encoding may consist of single-byte, multi-byte, or double-byte -characters. +characters. .PP Each dynamically-loadable encoding is represented as a text file. The initial line of the file, beginning with a @@ -447,9 +447,9 @@ many Japanese computers. .IP "[4] \fBE\fR" An escape-sequence encoding, specifying that certain sequences of bytes do not represent characters, but commands that describe how following bytes -should be interpreted. +should be interpreted. .PP -The rest of the lines in the file depend on the type. +The rest of the lines in the file depend on the type. .PP Cases [1], [2], and [3] are collectively referred to as table-based encoding files. The lines in a table-based encoding file are in the same @@ -500,7 +500,7 @@ The third line of the file is three numbers. The first number is the fallback character (in base 16) to use when converting from UTF-8 to this encoding. The second number is a \fB1\fR if this file represents the encoding for a symbol font, or \fB0\fR otherwise. The last number (in base -10) is how many pages of data follow. +10) is how many pages of data follow. .PP Subsequent lines in the example above are pages that describe how to map from the encoding into 2-byte Unicode. The first line in a page identifies diff --git a/doc/Method.3 b/doc/Method.3 index 550b64a..225da00 100644 --- a/doc/Method.3 +++ b/doc/Method.3 @@ -67,7 +67,9 @@ The class to create the method in. The name of the method to create. Should not be NULL unless creating constructors or destructors. .AP int isPublic in -A boolean flag saying whether the method is to be exported. +A flag saying what the visibility of the method is. The only supported public +values of this flag are 0 for a non-exported method, and 1 for an exported +method. .AP Tcl_MethodType *methodTypePtr in A description of the type of the method to create, or the type of method to compare against. diff --git a/doc/Object.3 b/doc/Object.3 index 55451ab..bf80fe2 100644 --- a/doc/Object.3 +++ b/doc/Object.3 @@ -3,7 +3,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_Obj 3 8.5 Tcl "Tcl Library Procedures" .so man.macros .BS @@ -94,7 +94,7 @@ Also, most Tcl values are only read and never modified. This is especially true for procedure arguments, which can be shared between the caller and the called procedure. Assignment and argument binding is done by -simply assigning a pointer to the value. +simply assigning a pointer to the value. Reference counting is used to determine when it is safe to reclaim a value's storage. .PP diff --git a/doc/OpenFileChnl.3 b/doc/OpenFileChnl.3 index cca76c2..582ff4b 100644 --- a/doc/OpenFileChnl.3 +++ b/doc/OpenFileChnl.3 @@ -115,7 +115,7 @@ Used for error reporting and to look up a channel registered in it. The name of a local or network file. .AP "const char" *mode in Specifies how the file is to be accessed. May have any of the values -allowed for the \fImode\fR argument to the Tcl \fBopen\fR command. +allowed for the \fImode\fR argument to the Tcl \fBopen\fR command. .AP int permissions in POSIX-style permission flags such as 0644. If a new file is created, these permissions will be set on the created file. @@ -141,7 +141,7 @@ file descriptor, for Windows it is a HANDLE. OR-ed combination of \fBTCL_READABLE\fR and \fBTCL_WRITABLE\fR to indicate what operations are valid on \fIhandle\fR. .AP "const char" *channelName in -The name of the channel. +The name of the channel. .AP int *modePtr out Points at an integer variable that will receive an OR-ed combination of \fBTCL_READABLE\fR and \fBTCL_WRITABLE\fR denoting whether the channel is @@ -155,8 +155,8 @@ from a procedure such as \fBTcl_OpenFileChannel\fR. A pointer to a Tcl value in which to store the characters read from the channel. .AP int charsToRead in -The number of characters to read from the channel. If the channel's encoding -is \fBbinary\fR, this is equivalent to the number of bytes to read from the +The number of characters to read from the channel. If the channel's encoding +is \fBbinary\fR, this is equivalent to the number of bytes to read from the channel. .AP int appendFlag in If non-zero, data read from the channel will be appended to the value. @@ -169,7 +169,7 @@ be large enough to hold this many bytes. .AP Tcl_Obj *lineObjPtr in/out A pointer to a Tcl value in which to store the line read from the channel. The line read will be appended to the current value of the -value. +value. .AP Tcl_DString *lineRead in/out A pointer to a Tcl dynamic string in which to store the line read from the channel. Must have been initialized by the caller. The line read will be @@ -238,8 +238,8 @@ If an error occurs while opening the channel, \fBTcl_OpenFileChannel\fR returns NULL and records a POSIX error code that can be retrieved with \fBTcl_GetErrno\fR. In addition, if \fIinterp\fR is non-NULL, \fBTcl_OpenFileChannel\fR -leaves an error message in \fIinterp\fR's result after any error. -As of Tcl 8.4, the value-based API \fBTcl_FSOpenFileChannel\fR should +leaves an error message in \fIinterp\fR's result after any error. +As of Tcl 8.4, the value-based API \fBTcl_FSOpenFileChannel\fR should be used in preference to \fBTcl_OpenFileChannel\fR wherever possible. .PP The newly created channel is not registered in the supplied interpreter; to @@ -360,7 +360,7 @@ the standard channels (\fBstdout\fR, \fBstderr\fR, \fBstdin\fR), and will return Code not associated with a Tcl interpreter can call \fBTcl_DetachChannel\fR with \fIinterp\fR as NULL, to indicate to Tcl that it no longer holds a reference to that channel. If this is the last -reference to the channel, unlike \fBTcl_UnregisterChannel\fR, +reference to the channel, unlike \fBTcl_UnregisterChannel\fR, it will not be closed. .SH TCL_ISSTANDARDCHANNEL .PP @@ -368,7 +368,7 @@ it will not be closed. three standard channels, \fBstdin\fR, \fBstdout\fR or \fBstderr\fR. If so, it returns 1, otherwise 0. .PP -No attempt is made to check whether the given channel or the standard +No attempt is made to check whether the given channel or the standard channels are initialized or otherwise valid. .SH TCL_CLOSE .PP @@ -402,7 +402,7 @@ corresponding calls to \fBTcl_UnregisterChannel\fR. .SH "TCL_READCHARS AND TCL_READ" .PP \fBTcl_ReadChars\fR consumes bytes from \fIchannel\fR, converting the bytes -to UTF-8 based on the channel's encoding and storing the produced data in +to UTF-8 based on the channel's encoding and storing the produced data in \fIreadObjPtr\fR's string representation. The return value of \fBTcl_ReadChars\fR is the number of characters, up to \fIcharsToRead\fR, that were stored in \fIreadObjPtr\fR. If an error occurs while reading, the @@ -450,7 +450,7 @@ extensions. It consumes bytes from \fIchannel\fR and stores them in of \fBTcl_Read\fR is the number of bytes, up to \fIbytesToRead\fR, written in \fIreadBuf\fR. The buffer produced by \fBTcl_Read\fR is not null-terminated. Its contents are valid from the zeroth position up to and excluding the -position indicated by the return value. +position indicated by the return value. .PP \fBTcl_ReadRaw\fR is the same as \fBTcl_Read\fR but does not compensate for stacking. While \fBTcl_Read\fR (and the other functions @@ -507,7 +507,7 @@ to be null-terminated and it outputs everything up to the null. .PP Data queued for output may not appear on the output device immediately, due to internal buffering. If the data should appear immediately, call -\fBTcl_Flush\fR after the call to \fBTcl_WriteChars\fR, or set the +\fBTcl_Flush\fR after the call to \fBTcl_WriteChars\fR, or set the \fB\-buffering\fR option on the channel to \fBnone\fR. If you wish the data to appear as soon as a complete line is accepted for output, set the \fB\-buffering\fR option on the channel to \fBline\fR mode. @@ -525,7 +525,7 @@ channel. This is done even if the channel has no encoding. \fBTcl_WriteObj\fR is similar to \fBTcl_WriteChars\fR except it accepts a Tcl value whose contents will be output to the channel. The UTF-8 characters in \fIwriteObjPtr\fR's string representation are converted -to the channel's encoding and queued for output to \fIchannel\fR. +to the channel's encoding and queued for output to \fIchannel\fR. As a performance optimization, when writing to a channel with the encoding \fBbinary\fR, UTF-8 characters are not converted as they are written. Instead, the bytes in \fIwriteObjPtr\fR's internal representation as a diff --git a/doc/ParseCmd.3 b/doc/ParseCmd.3 index 7090dd3..667d697 100644 --- a/doc/ParseCmd.3 +++ b/doc/ParseCmd.3 @@ -3,7 +3,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_ParseCommand 3 8.3 Tcl "Tcl Library Procedures" .so man.macros .BS @@ -56,7 +56,7 @@ following \fIstart\fR up to the first null character. .AP int nested in Non-zero means that the script is part of a command substitution so an unquoted close bracket should be treated as a command terminator. If zero, -close brackets have no special meaning. +close brackets have no special meaning. .AP int append in Non-zero means that \fI*parsePtr\fR already contains valid tokens; the new tokens should be appended to those already present. Zero means that @@ -118,7 +118,7 @@ result, and no information is left at \fI*parsePtr\fR. enclosed in braces such as \fB{hello}\fR or \fB{string \et with \et tabs}\fR from the beginning of its argument \fIstart\fR. -The first character of \fIstart\fR must be \fB{\fR. +The first character of \fIstart\fR must be \fB{\fR. If the braced string was parsed successfully, \fBTcl_ParseBraces\fR returns \fBTCL_OK\fR, fills in the structure pointed to by \fIparsePtr\fR @@ -134,7 +134,7 @@ and no information is left at \fI*parsePtr\fR or \fI*termPtr\fR. \fBTcl_ParseQuotedString\fR parses a double-quoted string such as \fB"sum is [expr {$a+$b}]"\fR from the beginning of the argument \fIstart\fR. -The first character of \fIstart\fR must be \fB\N'34'\fR. +The first character of \fIstart\fR must be \fB\N'34'\fR. If the double-quoted string was parsed successfully, \fBTcl_ParseQuotedString\fR returns \fBTCL_OK\fR, fills in the structure pointed to by \fIparsePtr\fR @@ -150,7 +150,7 @@ and no information is left at \fI*parsePtr\fR or \fI*termPtr\fR. \fBTcl_ParseVarName\fR parses a Tcl variable reference such as \fB$abc\fR or \fB$x([expr {$index + 1}])\fR from the beginning of its \fIstart\fR argument. -The first character of \fIstart\fR must be \fB$\fR. +The first character of \fIstart\fR must be \fB$\fR. If a variable name was parsed successfully, \fBTcl_ParseVarName\fR returns \fBTCL_OK\fR and fills in the structure pointed to by \fIparsePtr\fR with information about the structure of the variable name @@ -184,7 +184,7 @@ a Tcl_Parse structure. The tokens typically consist of all the tokens in a word or all the tokens that make up the index for a reference to an array variable. \fBTcl_EvalTokensStandard\fR performs the substitutions requested by the tokens and concatenates the -resulting values. +resulting values. The return value from \fBTcl_EvalTokensStandard\fR is a Tcl completion code with one of the values \fBTCL_OK\fR, \fBTCL_ERROR\fR, \fBTCL_RETURN\fR, \fBTCL_BREAK\fR, or \fBTCL_CONTINUE\fR, or possibly @@ -242,7 +242,7 @@ character that terminates the last comment. If the command is not preceded by any comments, \fIcommentSize\fR is 0. \fBTcl_ParseCommand\fR also sets the \fIcommandStart\fR field to point to the first character of the first -word in the command (skipping any comments and leading space) and +word in the command (skipping any comments and leading space) and \fIcommandSize\fR gives the total number of bytes in the command, including the character pointed to by \fIcommandStart\fR up to and including the newline, close bracket, or semicolon character that @@ -350,7 +350,7 @@ just the \fBTCL_TOKEN_OPERATOR\fR token. Each operand is described by a \fBTCL_TOKEN_SUB_EXPR\fR token. Otherwise, the subexpression is a value described by one of the token types \fBTCL_TOKEN_WORD\fR, \fBTCL_TOKEN_TEXT\fR, -\fBTCL_TOKEN_BS\fR, \fBTCL_TOKEN_COMMAND\fR, +\fBTCL_TOKEN_BS\fR, \fBTCL_TOKEN_COMMAND\fR, \fBTCL_TOKEN_VARIABLE\fR, and \fBTCL_TOKEN_SUB_EXPR\fR. The \fInumComponents\fR field counts the total number of sub-tokens that make up the subexpression; @@ -389,7 +389,7 @@ is always 0. After \fBTcl_ParseCommand\fR returns, the first token pointed to by the \fItokenPtr\fR field of the Tcl_Parse structure always has type \fBTCL_TOKEN_WORD\fR or -\fBTCL_TOKEN_SIMPLE_WORD\fR or \fBTCL_TOKEN_EXPAND_WORD\fR. +\fBTCL_TOKEN_SIMPLE_WORD\fR or \fBTCL_TOKEN_EXPAND_WORD\fR. It is followed by the sub-tokens that must be concatenated to produce the value of that word. The next token is the \fBTCL_TOKEN_WORD\fR or \fBTCL_TOKEN_SIMPLE_WORD\fR diff --git a/doc/StringObj.3 b/doc/StringObj.3 index cf8f6d3..7042cc8 100644 --- a/doc/StringObj.3 +++ b/doc/StringObj.3 @@ -3,7 +3,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_StringObj 3 8.1 Tcl "Tcl Library Procedures" .so man.macros .BS @@ -308,7 +308,7 @@ sprintf(buf, format, ...); \fBTcl_NewStringObj\fR(buf, -1); .CE .PP -but with greater convenience and no need to +but with greater convenience and no need to determine \fBSOME_SUITABLE_LENGTH\fR. The formatting is done with the same core formatting engine used by \fBTcl_Format\fR. This means the set of supported conversion specifiers is that of the \fBformat\fR command and @@ -329,8 +329,8 @@ Tcl_Obj *objPtr = \fBTcl_ObjPrintf\fR("Value is %d", x); .PP If the value of \fIformat\fR contains internal inconsistencies or invalid specifier formats, the formatted string result produced by -\fBTcl_ObjPrintf\fR will be an error message describing the error. -It is impossible however to provide runtime protection against +\fBTcl_ObjPrintf\fR will be an error message describing the error. +It is impossible however to provide runtime protection against mismatches between the format and any subsequent arguments. Compile-time protection may be provided by some compilers. .PP diff --git a/doc/Thread.3 b/doc/Thread.3 index ac5f2ba..5966a71 100644 --- a/doc/Thread.3 +++ b/doc/Thread.3 @@ -4,7 +4,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Threads 3 "8.1" Tcl "Tcl Library Procedures" .so man.macros .BS @@ -79,9 +79,10 @@ waited upon into it. .SH INTRODUCTION Beginning with the 8.1 release, the Tcl core is thread safe, which allows you to incorporate Tcl into multithreaded applications without -customizing the Tcl core. To enable Tcl multithreading support, -you must include the \fB\-\|\-enable-threads\fR option to \fBconfigure\fR -when you configure and compile your Tcl core. +customizing the Tcl core. Starting with the 8.6 release, Tcl +multithreading support is on by default. To disable Tcl multithreading +support, you must include the \fB\-\|\-disable-threads\fR option to +\fBconfigure\fR when you configure and compile your Tcl core. .PP An important constraint of the Tcl threads implementation is that \fIonly the thread that created a Tcl interpreter can use that @@ -126,7 +127,7 @@ will cause a memory leak. .PP The \fBTcl_GetThreadData\fR call returns a pointer to a block of thread-private data. Its argument is a key that is shared by all threads -and a size for the block of storage. The storage is automatically +and a size for the block of storage. The storage is automatically allocated and initialized to all zeros the first time each thread asks for it. The storage is automatically deallocated by \fBTcl_FinalizeThread\fR. .SS "SYNCHRONIZATION AND COMMUNICATION" diff --git a/doc/ToUpper.3 b/doc/ToUpper.3 index 587e76b..b933e9c 100644 --- a/doc/ToUpper.3 +++ b/doc/ToUpper.3 @@ -3,7 +3,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Tcl_UtfToUpper 3 "8.1" Tcl "Tcl Library Procedures" .so man.macros .BS diff --git a/doc/TraceCmd.3 b/doc/TraceCmd.3 index db2f5d5..fccc0c6 100644 --- a/doc/TraceCmd.3 +++ b/doc/TraceCmd.3 @@ -78,7 +78,7 @@ created. \fIClientData\fR typically points to an application-specific data structure that describes what to do when \fIproc\fR is invoked. \fIOldName\fR gives the name of the command being renamed, and \fInewName\fR gives the name that the command is being renamed to (or -an empty string or NULL when the command is being deleted.) +NULL when the command is being deleted.) \fIFlags\fR is an OR'ed combination of bits potentially providing several pieces of information. One of the bits \fBTCL_TRACE_RENAME\fR and \fBTCL_TRACE_DELETE\fR will be set in \fIflags\fR to indicate which @@ -3,12 +3,12 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH Utf 3 "8.1" Tcl "Tcl Library Procedures" .so man.macros .BS .SH NAME -Tcl_UniChar, Tcl_UniCharCaseMatch, Tcl_UniCharNcasecmp, Tcl_UniCharToUtf, Tcl_UtfToUniChar, Tcl_UniCharToUtfDString, Tcl_UtfToUniCharDString, Tcl_UniCharLen, Tcl_UniCharNcmp, Tcl_UtfCharComplete, Tcl_NumUtfChars, Tcl_UtfFindFirst, Tcl_UtfFindLast, Tcl_UtfNext, Tcl_UtfPrev, Tcl_UniCharAtIndex, Tcl_UtfAtIndex, Tcl_UtfBackslash \- routines for manipulating UTF-8 strings +Tcl_UniChar, Tcl_UniCharToUtf, Tcl_UtfToUniChar, Tcl_UniCharToUtfDString, Tcl_UtfToUniCharDString, Tcl_UniCharLen, Tcl_UniCharNcmp, Tcl_UniCharNcasecmp, Tcl_UniCharCaseMatch, Tcl_UtfNcmp, Tcl_UtfNcasecmp, Tcl_UtfCharComplete, Tcl_NumUtfChars, Tcl_UtfFindFirst, Tcl_UtfFindLast, Tcl_UtfNext, Tcl_UtfPrev, Tcl_UniCharAtIndex, Tcl_UtfAtIndex, Tcl_UtfBackslash \- routines for manipulating UTF-8 strings .SH SYNOPSIS .nf \fB#include <tcl.h>\fR @@ -48,7 +48,7 @@ int int \fBTcl_UtfCharComplete\fR(\fIsrc, length\fR) .sp -int +int \fBTcl_NumUtfChars\fR(\fIsrc, length\fR) .sp const char * @@ -109,7 +109,7 @@ Pointer to the beginning of a UTF-8 string. .AP int index in The index of a character (not byte) in the UTF-8 string. .AP int *readPtr out -If non-NULL, filled with the number of bytes in the backslash sequence, +If non-NULL, filled with the number of bytes in the backslash sequence, including the backslash character. .AP char *dst out Buffer in which the bytes represented by the backslash sequence are stored. @@ -142,7 +142,7 @@ end and dereference non-existent or random memory; if the source buffer is known to be null-terminated, this will not happen. If the input is not in proper UTF-8 format, \fBTcl_UtfToUniChar\fR will store the first byte of \fIsrc\fR in \fI*chPtr\fR as a Tcl_UniChar between 0x0000 and -0x00ff and return 1. +0x00ff and return 1. .PP \fBTcl_UniCharToUtfDString\fR converts the given Unicode string to UTF-8, storing the result in a previously initialized \fBTcl_DString\fR. @@ -210,12 +210,12 @@ length is negative, all bytes up to the first null byte are used. \fBTcl_UtfFindFirst\fR corresponds to \fBstrchr\fR for UTF-8 strings. It returns a pointer to the first occurrence of the Tcl_UniChar \fIch\fR in the null-terminated UTF-8 string \fIsrc\fR. The null terminator is -considered part of the UTF-8 string. +considered part of the UTF-8 string. .PP \fBTcl_UtfFindLast\fR corresponds to \fBstrrchr\fR for UTF-8 strings. It returns a pointer to the last occurrence of the Tcl_UniChar \fIch\fR in the null-terminated UTF-8 string \fIsrc\fR. The null terminator is -considered part of the UTF-8 string. +considered part of the UTF-8 string. .PP Given \fIsrc\fR, a pointer to some location in a UTF-8 string, \fBTcl_UtfNext\fR returns a pointer to the next UTF-8 character in the @@ -239,7 +239,7 @@ characters. Behavior is undefined if a negative \fIindex\fR is given. .PP \fBTcl_UtfAtIndex\fR returns a pointer to the specified character (not byte) \fIindex\fR in the UTF-8 string \fIsrc\fR. The source string must -contain at least \fIindex\fR characters. This is equivalent to calling +contain at least \fIindex\fR characters. This is equivalent to calling \fBTcl_UtfNext\fR \fIindex\fR times. If a negative \fIindex\fR is given, the return pointer points to the first character in the source string. .PP diff --git a/doc/clock.n b/doc/clock.n index 910ebb8..889a5da 100644 --- a/doc/clock.n +++ b/doc/clock.n @@ -16,13 +16,13 @@ package require \fBTcl 8.5\fR .sp \fBclock format\fR \fItimeVal\fR ?\fI\-option value\fR...? .sp -\fBclock microseconds\fR +\fBclock microseconds\fR .sp -\fBclock milliseconds\fR +\fBclock milliseconds\fR .sp \fBclock scan\fR \fIinputString\fR ?\fI\-option value\fR...? .sp -\fBclock seconds\fR +\fBclock seconds\fR .sp .BE .SH "DESCRIPTION" @@ -58,10 +58,10 @@ Formats a time that is expressed as an integer number of seconds into a format intended for consumption by users or external programs. See \fBFORMATTING TIMES\fR for a full description. .TP -\fBclock microseconds\fR +\fBclock microseconds\fR Returns the current time as an integer number of microseconds. See \fBHIGH RESOLUTION TIMERS\fR for a full description. .TP -\fBclock milliseconds\fR +\fBclock milliseconds\fR Returns the current time as an integer number of milliseconds. See \fBHIGH RESOLUTION TIMERS\fR for a full description. .TP \fBclock scan\fR \fIinputString\fR ?\fI\-option value\fR...? @@ -69,7 +69,7 @@ Scans a time that is expressed as a character string and produces an integer number of seconds. See \fBSCANNING TIMES\fR for a full description. .TP -\fBclock seconds\fR +\fBclock seconds\fR Returns the current time as an integer number of seconds. .SS "PARAMETERS" .TP @@ -113,7 +113,7 @@ and their interpretation, are described under \fBFORMAT GROUPS\fR. On \fBclock format\fR, the default format is .PP .CS -%a %b %d %H:%M:%S %z %Y +%a %b %d %H:%M:%S %Z %Y .CE .PP On \fBclock scan\fR, the lack of a \fB\-format\fR option indicates that a @@ -525,7 +525,7 @@ string of the same meaning in the locale, to indicate whether \fB%Y\fR refers to years before or after Year 1 of the Common Era. On input, accepts the string \fBB.C.E.\fR, \fBB.C.\fR, \fBC.E.\fR, \fBA.D.\fR, or the abbreviation appropriate to the current locale, and uses it to fix -whether \fB%Y\fR refers to years before or after Year 1 of the +whether \fB%Y\fR refers to years before or after Year 1 of the Common Era. .TP \fB%Ex\fR @@ -684,8 +684,8 @@ ISO8601 week number. \fB%w\fR On output, produces the ordinal number of the day of the week (Sunday==0; Saturday==6). On input, accepts a single digit and -interprets it as the day of the week; Sunday may be represented as -either 0 or 7. Note that \fB%w\fR is not the ISO8601 weekday number, +interprets it as the day of the week; Sunday may be represented as +either 0 or 7. Note that \fB%w\fR is not the ISO8601 weekday number, which is produced and accepted by \fB%u\fR. .TP \fB%W\fR @@ -765,7 +765,7 @@ The local time zone from the Control Panel on Windows systems. The C library's idea of the local time zone, as defined by the \fBmktime\fR and \fBlocaltime\fR functions. .PP -In case [1] \fIonly,\fR the string is tested to see if it is one +In case [1] \fIonly,\fR the string is tested to see if it is one of the strings: .PP .CS @@ -783,7 +783,7 @@ of the strings: If it is a string in the above list, it designates a known time zone, and is interpreted as such. .PP -For time zones in case [1] that do not match any of the above strings, +For time zones in case [1] that do not match any of the above strings, and always for cases [2]-[6], the following rules apply. .PP If the time zone begins with a colon, it is one of a @@ -909,7 +909,7 @@ giving an explicit \fB\-format\fR option to the \fBclock scan\fR command. .TP \fIrelative time\fR A specification relative to the current time. The format is \fBnumber -unit\fR. Acceptable units are \fByear\fR, \fBfortnight\fR, +unit\fR. Acceptable units are \fByear\fR, \fBfortnight\fR, \fBmonth\fR, \fBweek\fR, \fBday\fR, \fBhour\fR, \fBminute\fR (or \fBmin\fR), and \fBsecond\fR (or \fBsec\fR). The unit can be specified as a singular or plural, as in \fB3 weeks\fR. @@ -35,7 +35,7 @@ proc main {} { if {[catch {main} msg options]} { puts stderr "unexpected script error: $msg" - if {[info exist env(DEBUG)]} { + if {[info exists env(DEBUG)]} { puts stderr "---- BEGIN TRACE ----" puts stderr [dict get $options -errorinfo] puts stderr "---- END TRACE ----" @@ -4,7 +4,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH for n "" Tcl "Tcl Built-In Commands" .so man.macros .BS @@ -49,7 +49,7 @@ each loop iteration), so changes in the variables will be visible. See below for an example: .SH EXAMPLES .PP -Print a line for each of the integers from 0 to 10: +Print a line for each of the integers from 0 to 9: .PP .CS \fBfor\fR {set x 0} {$x<10} {incr x} { diff --git a/doc/library.n b/doc/library.n index 775b7d9..6f8f265 100644 --- a/doc/library.n +++ b/doc/library.n @@ -4,7 +4,7 @@ '\" '\" See the file "license.terms" for information on usage and redistribution '\" of this file, and for a DISCLAIMER OF ALL WARRANTIES. -'\" +'\" .TH library n "8.0" Tcl "Tcl Built-In Commands" .so man.macros .BS @@ -19,7 +19,7 @@ auto_execok, auto_import, auto_load, auto_mkindex, auto_qualify, auto_reset, tcl \fBauto_qualify \fIcommand namespace\fR \fBauto_reset\fR \fBtcl_findLibrary \fIbasename version patch initScript enVarName varName\fR -\fBparray \fIarrayName\fR +\fBparray \fIarrayName\fR ?\fIpattern\fR? \fBtcl_endOfWord \fIstr start\fR \fBtcl_startOfNextWord \fIstr start\fR \fBtcl_startOfPreviousWord \fIstr start\fR @@ -139,7 +139,7 @@ as its first characters then it is assumed to be a procedure definition and the next word of the line is taken as the procedure's name. Procedure definitions that do not appear in this way (e.g.\ they -have spaces before the \fBproc\fR) will not be indexed. If your +have spaces before the \fBproc\fR) will not be indexed. If your script contains .QW dangerous code, such as global initialization @@ -178,7 +178,7 @@ performing the actual auto-loading of functions at runtime. This is a standard search procedure for use by extensions during their initialization. They call this procedure to look for their script library in several standard directories. -The last component of the name of the library directory is +The last component of the name of the library directory is normally \fIbasenameversion\fR (e.g., tk8.0), but it might be .QW library @@ -196,9 +196,11 @@ bin or bin/\fIarch\fR directory; relative to the executable file in the current build tree; relative to the executable file in a parallel build tree. .TP -\fBparray \fIarrayName\fR -Prints on standard output the names and values of all the elements -in the array \fIarrayName\fR. +\fBparray \fIarrayName\fR ?\fIpattern\fR? +Prints on standard output the names and values of all the elements in the +array \fIarrayName\fR, or just the names that match \fIpattern\fR (using the +matching rules of \fBstring match\fR) and their values if \fIpattern\fR is +given. \fIArrayName\fR must be an array accessible to the caller of \fBparray\fR. It may be either local or global. .TP @@ -283,7 +285,7 @@ a default value is used. .TP \fBenv(TCLLIBPATH)\fR If set, then it must contain a valid Tcl list giving directories to -search during auto-load operations. Directories must be specified in +search during auto-load operations. Directories must be specified in Tcl format, using .QW / as the path separator, regardless of platform. @@ -312,7 +314,7 @@ Unix, words are comprised of numbers, letters or underscores. .SH "SEE ALSO" env(n), info(n), re_syntax(n) .SH KEYWORDS -auto-exec, auto-load, library, unknown, word, whitespace +auto-exec, auto-load, library, unknown, word, whitespace '\"Local Variables: '\"mode: nroff '\"End: diff --git a/doc/lreplace.n b/doc/lreplace.n index 7bba543..d19f0cd 100644 --- a/doc/lreplace.n +++ b/doc/lreplace.n @@ -35,7 +35,7 @@ by \fIfirst\fR must exist or \fIfirst\fR must indicate before the start of the list. .PP If \fIlast\fR is less than \fIfirst\fR, then any specified elements -will be inserted into the list at the point specified by \fIfirst\fR +will be inserted into the list before the point specified by \fIfirst\fR with no elements being deleted. .PP The \fIelement\fR arguments specify zero or more new arguments to diff --git a/doc/msgcat.n b/doc/msgcat.n index bae6dbe..7e46528 100644 --- a/doc/msgcat.n +++ b/doc/msgcat.n @@ -13,29 +13,43 @@ msgcat \- Tcl message catalog .SH SYNOPSIS \fBpackage require Tcl 8.5\fR .sp -\fBpackage require msgcat 1.5\fR +\fBpackage require msgcat 1.6\fR .sp \fB::msgcat::mc \fIsrc-string\fR ?\fIarg arg ...\fR? .sp \fB::msgcat::mcmax ?\fIsrc-string src-string ...\fR? .sp +.VS "TIP 412" +\fB::msgcat::mcexists\fR ?\fB-exactnamespace\fR? ?\fB-exactlocale\fR? \fIsrc-string\fR +.VE "TIP 412" +.sp \fB::msgcat::mclocale \fR?\fInewLocale\fR? .sp \fB::msgcat::mcpreferences\fR .sp +.VS "TIP 412" +\fB::msgcat::mcloadedlocales subcommand\fR ?\fIlocale\fR? +.VE "TIP 412" +.sp \fB::msgcat::mcload \fIdirname\fR .sp \fB::msgcat::mcset \fIlocale src-string \fR?\fItranslate-string\fR? .sp \fB::msgcat::mcmset \fIlocale src-trans-list\fR .sp -.VS "TIP 404" \fB::msgcat::mcflset \fIsrc-string \fR?\fItranslate-string\fR? .sp \fB::msgcat::mcflmset \fIsrc-trans-list\fR -.VE "TIP 404" .sp \fB::msgcat::mcunknown \fIlocale src-string\fR ?\fIarg arg ...\fR? +.sp +.VS "TIP 412" +\fB::msgcat::mcpackagelocale subcommand\fR ?\fIlocale\fR? +.sp +\fB::msgcat::mcpackageconfig subcommand\fR \fIoption\fR ?\fIvalue\fR? +.sp +\fB::msgcat::mcforgetpackage\fR +.VE "TIP 412" .BE .SH DESCRIPTION .PP @@ -46,18 +60,23 @@ Text strings are defined in a which is independent from the application, and which can be edited or localized without modifying the application source code. New languages -or locales are provided by adding a new file to +or locales may be provided by adding a new file to the message catalog. .PP -Use of the message catalog is optional by any application -or package, but is encouraged if the application or package -wishes to be enabled for multi-lingual applications. +\fBmsgcat\fR distinguises packages by its namespace. +Each package has its own message catalog and configuration settings in \fBmsgcat\fR. +.PP +A \fIlocale\fR is a specification string describing a user language like \fBde_ch\fR for Swiss German. +In \fBmsgcat\fR, there is a global locale initialized by the system locale of the current system. +Each package may decide to use the global locale or to use a package specific locale. +.PP +The global locale may be changed on demand, for example by a user initiated language change or within a multi user application like a web server. .SH COMMANDS .TP \fB::msgcat::mc \fIsrc-string\fR ?\fIarg arg ...\fR? . Returns a translation of \fIsrc-string\fR according to the -user's current locale. If additional arguments past \fIsrc-string\fR +current locale. If additional arguments past \fIsrc-string\fR are given, the \fBformat\fR command is used to substitute the additional arguments in the translation of \fIsrc-string\fR. .RS @@ -84,6 +103,18 @@ of the longest translated string. This is useful when designing localized GUIs, which may require that all buttons, for example, be a fixed width (which will be the width of the widest button). .TP +\fB::msgcat::mcexists\fR ?\fB-exactnamespace\fR? ?\fB-exactlocale\fR? \fIsrc-string\fR +. +.VS "TIP 412" +Return true, if there is a translation for the given \fIsrc-string\fR. +.PP +.RS +The search may be limited by the option \fB\-exactnamespace\fR to only check the current namespace and not any parent namespaces. +.PP +It may also be limited by the option \fB\-exactlocale\fR to only check the first prefered locale (e.g. first element returned by \fB::msgcat::mcpreferences\fR if global locale is used). +.RE +.VE "TIP 412" +.TP \fB::msgcat::mclocale \fR?\fInewLocale\fR? . This function sets the locale to \fInewLocale\fR. If \fInewLocale\fR @@ -93,6 +124,13 @@ case-insensitive manner, and returns locales in lowercase. The initial locale is determined by the locale specified in the user's environment. See \fBLOCALE SPECIFICATION\fR below for a description of the locale string format. +.RS +.PP +.VS "TIP 412" +If the locale is set, the preference list of locales is evaluated. +Locales in this list are loaded now, if not jet loaded. +.VE "TIP 412" +.RE .TP \fB::msgcat::mcpreferences\fR . @@ -103,13 +141,26 @@ preference. The list is derived from the current locale set in msgcat by \fB::msgcat::mclocale\fR, and cannot be set independently. For example, if the current locale is en_US_funky, then \fB::msgcat::mcpreferences\fR -returns \fB{en_US_funky en_US en {}}\fR. +returns \fB{en_us_funky en_us en {}}\fR. +.TP +\fB::msgcat:mcloadedlocales subcommand\fR ?\fIlocale\fR? +. +This group of commands manage the list of loaded locales for packages not setting a package locale. +.PP +.RS +The subcommand \fBget\fR returns the list of currently loaded locales. +.PP +The subcommand \fBpresent\fR requires the argument \fIlocale\fR and returns true, if this locale is loaded. +.PP +The subcommand \fBclear\fR removes all locales and their data, which are not in the current preference list. +.RE .TP \fB::msgcat::mcload \fIdirname\fR . +.VS "TIP 412" Searches the specified directory for files that match -the language specifications returned by \fB::msgcat::mcpreferences\fR -(note that these are all lowercase), extended by the file extension +the language specifications returned by \fB::msgcat::mcloadedlocales get\fR +(or \fBmsgcat::mcpackagelocale preferences\fR if a package locale is set) (note that these are all lowercase), extended by the file extension .QW .msg . Each matching file is read in order, assuming a UTF-8 encoding. The file contents are @@ -118,6 +169,11 @@ may be present in the message file either directly in their UTF-8 encoded form, or by use of the backslash-u quoting recognized by Tcl evaluation. The number of message files which matched the specification and were loaded is returned. +.RS +.PP +In addition, the given folder is stored in the \fBmsgcat\fR package configuration option \fImcfolder\fR to eventually load message catalog files required by a locale change. +.VE "TIP 412" +.RE .TP \fB::msgcat::mcset \fIlocale src-string \fR?\fItranslate-string\fR? . @@ -138,16 +194,13 @@ faster than multiple invocations of \fB::msgcat::mcset\fR. The function returns the number of translations set. .TP \fB::msgcat::mcflset \fIsrc-string \fR?\fItranslate-string\fR? -.VS "TIP 404" Sets the translation for \fIsrc-string\fR to \fItranslate-string\fR in the current namespace for the locale implied by the name of the message catalog being loaded via \fB::msgcat::mcload\fR. If \fItranslate-string\fR is not specified, \fIsrc-string\fR is used for both. The function returns \fItranslate-string\fR. -.VE "TIP 404" .TP \fB::msgcat::mcflmset \fIsrc-trans-list\fR -.VS "TIP 404" Sets the translation for multiple source strings in \fIsrc-trans-list\fR in the current namespace for the locale implied by the name of the message catalog being loaded via \fB::msgcat::mcload\fR. \fIsrc-trans-list\fR must @@ -155,7 +208,6 @@ have an even number of elements and is in the form {\fIsrc-string translate-string\fR ?\fIsrc-string translate-string ...\fR?} \fB::msgcat::mcflmset\fR can be significantly faster than multiple invocations of \fB::msgcat::mcflset\fR. The function returns the number of translations set. -.VE "TIP 404" .TP \fB::msgcat::mcunknown \fIlocale src-string\fR ?\fIarg arg ...\fR? . @@ -168,7 +220,18 @@ application, for example to log error messages for each unknown string. The \fB::msgcat::mcunknown\fR procedure is invoked at the same stack context as the call to \fB::msgcat::mc\fR. The return value of \fB::msgcat::mcunknown\fR is used as the return value for the call -to \fB::msgcat::mc\fR. +to \fB::msgcat::mc\fR. +.VS "TIP 412" +.RS +.PP +Note that this routine is only called if the concerned package did not set a package locale unknown command name. +.RE +.TP +\fB::msgcat::mcforgetpackage\fR +. +The calling package clears all its state within the \fBmsgcat\fR package including all settings and translations. +.VE "TIP 412" +.PP .SH "LOCALE SPECIFICATION" .PP The locale is specified to \fBmsgcat\fR by a locale string @@ -217,15 +280,15 @@ When a locale is specified by the user, a search is performed during string translation. For example, if a user specifies en_GB_Funky, the locales -.QW en_GB_Funky , -.QW en_GB , +.QW en_gb_funky , +.QW en_gb , .QW en and .MT (the empty string) are searched in order until a matching translation string is found. If no translation string is available, then -\fB::msgcat::mcunknown\fR is called. +the unknown handler is called. .SH "NAMESPACES AND MESSAGE CATALOGS" .PP Strings stored in the message catalog are stored relative @@ -373,6 +436,209 @@ formatting substitution is done directly. # ... where that key is mapped to one of the # human-oriented versions by \fBmsgcat::mcset\fR .CE +.VS "TIP 412" +.SH Package private locale +.PP +A package using \fBmsgcat\fR may choose to use its own package private +locale and its own set of loaded locales, independent to the global +locale set by \fB::msgcat::mclocale\fR. +.PP +This allows a package to change its locale without causing any locales load or removal in other packages and not to invoke the global locale change callback (see below). +.PP +This action is controled by the following ensemble: +.TP +\fB::msgcat::mcpackagelocale set\fR ?\fIlocale\fR? +. +Set or change a package private locale. +The package private locale is set to the given \fIlocale\fR if the \fIlocale\fR is given. +If the option \fIlocale\fR is not given, the package is set to package private locale mode, but no locale is changed (e.g. if the global locale was valid for the package before, it is copied to the package private locale). +.PP +.RS +This command may cause the load of locales. +.RE +.TP +\fB::msgcat::mcpackagelocale get\fR +. +Return the package private locale or the global locale, if no package private locale is set. +.TP +\fB::msgcat::mcpackagelocale preferences\fR +. +Return the package private preferences or the global preferences, +if no package private locale is set. +.TP +\fB::msgcat::mcpackagelocale loaded\fR +. +Return the list of locales loaded for this package. +.TP +\fB::msgcat::mcpackagelocale isset\fR +. +Returns true, if a package private locale is set. +.TP +\fB::msgcat::mcpackagelocale unset\fR +. +Unset the package private locale and use the globale locale. +Load and remove locales to adjust the list of loaded locales for the +package to the global loaded locales list. +.TP +\fB::msgcat::mcpackagelocale present\fR \fIlocale\fR +. +Returns true, if the given locale is loaded for the package. +.TP +\fB::msgcat::mcpackagelocale clear\fR +. +Clear any loaded locales of the package not present in the package preferences. +.PP +.SH Changing package options +.PP +Each package using msgcat has a set of options within \fBmsgcat\fR. +The package options are described in the next sectionPackage options. +Each package option may be set or unset individually using the following ensemble: +.TP +\fB::msgcat::mcpackageconfig get\fR \fIoption\fR +. +Return the current value of the given \fIoption\fR. +This call returns an error if the option is not set for the package. +.TP +\fB::msgcat::mcpackageconfig isset\fR \fIoption\fR +. +Returns 1, if the given \fIoption\fR is set for the package, 0 otherwise. +.TP +\fB::msgcat::mcpackageconfig set\fR \fIoption\fR \fIvalue\fR +. +Set the given \fIoption\fR to the given \fIvalue\fR. +This may invoke additional actions in dependency of the \fIoption\fR. +The return value is 0 or the number of loaded packages for the option \fBmcfolder\fR. +.TP +\fB::msgcat::mcpackageconfig unset\fR \fIoption\fR +. +Unsets the given \fIoption\fR for the package. +No action is taken if the \fIoption\fR is not set for the package. +The empty string is returned. +.SS Package options +.PP +The following package options are available for each package: +.TP +\fBmcfolder\fR +. +This is the message folder of the package. This option is set by mcload and by the subcommand set. Both are identical and both return the number of loaded message catalog files. +.RS +.PP +Setting or changing this value will load all locales contained in the preferences valid for the package. This implies also to invoke any set loadcmd (see below). +.PP +Unsetting this value will disable message file load for the package. +.RE +.TP +\fBloadcmd\fR +. +This callback is invoked before a set of message catalog files are loaded for the package which has this property set. +.PP +.RS +This callback may be used to do any preparation work for message file load or to get the message data from another source like a data base. In this case, no message files are used (mcfolder is unset). +.PP +See section \fBcallback invocation\fR below. +The parameter list appended to this callback is the list of locales to load. +.PP +If this callback is changed, it is called with the preferences valid for the package. +.RE +.TP +\fBchangecmd\fR +. +This callback is invoked when a default local change was performed. Its purpose is to allow a package to update any dependency on the default locale like showing the GUI in another language. +.PP +.RS +See the callback invocation section below. +The parameter list appended to this callback is \fBmcpreferences\fR. +The registered callbacks are invoked in no particular order. +.RE +.TP +\fBunknowncmd\fR +. +Use a package locale mcunknown procedure instead of the standard version supplied by the msgcat package (msgcat::mcunknown). +.PP +.RS +The called procedure must return the formatted message which will finally be returned by msgcat::mc. +.PP +A generic unknown handler is used if set to the empty string. This consists in returning the key if no arguments are given. With given arguments, format is used to process the arguments. +.PP +See section \fBcallback invocation\fR below. +The appended arguments are identical to \fB::msgcat::mcunknown\fR. +.RE +.SS Callback invocation +A package may decide to register one or multiple callbacks, as described above. +.PP +Callbacks are invoked, if: +.PP +1. the callback command is set, +.PP +2. the command is not the empty string, +.PP +3. the registering namespace exists. +.PP +If a called routine fails with an error, the \fBbgerror\fR routine for the interpreter is invoked after command completion. +Only exception is the callback \fBunknowncmd\fR, where an error causes the invoking \fBmc\fR-command to fail with that error. +.PP +.SS Examples +Packages which display a GUI may update their widgets when the global locale changes. +To register to a callback, use: +.CS +namespace eval gui { + msgcat::mcpackageconfig changecmd updateGUI + + proc updateGui args { + puts "New locale is '[lindex $args 0]'." + } +} +% msgcat::mclocale fr +fr +% New locale is 'fr'. +.CE +.PP +If locales (or additional locales) are contained in another source like a data base, a package may use the load callback and not mcload: +.CS +namespace eval db { + msgcat::mcpackageconfig loadcmd loadMessages + + proc loadMessages args { + foreach locale $args { + if {[LocaleInDB $locale]} { + msgcat::mcmset $locale [GetLocaleList $locale] + } + } + } +} +.CE +.PP +The \fBclock\fR command implementation uses \fBmsgcat\fR with a package locale to implement the command line parameter \fB-locale\fR. +Here are some sketches of the implementation: +.PP +First, a package locale is initialized and the generic unknown function is desactivated: +.CS +msgcat::mcpackagelocale set +msgcat::mcpackageconfig unknowncmd "" +.CE +As an example, the user requires the week day in a certain locale as follows: +.CS +clock format clock seconds -format %A -locale fr +.CE +\fBclock\fR sets the package locale to \fBfr\fR and looks for the day name as follows: +.CS +msgcat::mcpackagelocale set $locale +return [lindex [msgcat::mc DAYS_OF_WEEK_FULL] $day] +### Returns "mercredi" +.CE +Within \fBclock\fR, some message-catalog items are heavy in computation and thus are dynamically cached using: +.CS +proc ::tcl::clock::LocalizeFormat { locale format } { + set key FORMAT_$format + if { [::msgcat::mcexists -exactlocale -exactnamespace $key] } { + return [mc $key] + } + #...expensive computation of format clipped... + mcset $locale $key $format + return $format +} +.CE +.VE "TIP 412" .SH CREDITS .PP The message catalog code was developed by Mark Harrison. @@ -37,7 +37,7 @@ the \fBoo::object\fR class, which is not publicly visible by default: oo::class create c { method count {} { \fBmy\fR variable counter - print [incr counter] + puts [incr counter] } } c create o @@ -96,9 +96,11 @@ forward to the proper implementation of the method (which it does by invoking the \fBnext\fR command as filters are inserted into the front of the method call chain) and is responsible for returning the result of \fBnext\fR. .PP -Filters are not invoked when processing an invocation of the \fBunknown\fR -method because of a failure to locate a method implementation, or when -invoking either constructors or destructors. +Filters are invoked when processing an invokation of the \fBunknown\fR +method because of a failure to locate a method implementation, but \fInot\fR +when invoking either constructors or destructors. (Note however that the +\fBdestroy\fR method is a conventional method, and filters are invoked as +normal when it is called.) .SH EXAMPLES .PP This example demonstrates how to use the \fBnext\fR command to call the @@ -120,7 +122,7 @@ oo::class create theSubclass { } } theSubclass create obj -oo::define obj method example args { +oo::objdefine obj method example args { puts "per-object method, args = $args" \fBnext\fR x {*}$args y \fBnext\fR @@ -174,7 +176,7 @@ oo::class create cache { } oo::object create demo -oo::define demo { +oo::objdefine demo { mixin cache method compute {a b c} { after 3000 \fI;# Simulate deep thought\fR diff --git a/doc/re_syntax.n b/doc/re_syntax.n index 46a180d..7988071 100644 --- a/doc/re_syntax.n +++ b/doc/re_syntax.n @@ -683,9 +683,33 @@ earlier in the RE taking priority over ones starting later. Note that outer subexpressions thus take priority over their component subexpressions. .PP -Note that the quantifiers \fB{1,1}\fR and \fB{1,1}?\fR can be used to +The quantifiers \fB{1,1}\fR and \fB{1,1}?\fR can be used to force longest and shortest preference, respectively, on a subexpression or a whole RE. +.RS +.PP +\fBNOTE:\fR This means that you can usually make a RE be non-greedy overall by +putting \fB{1,1}?\fR after one of the first non-constraint atoms or +parenthesized sub-expressions in it. \fIIt pays to experiment\fR with the +placing of this non-greediness override on a suitable range of input texts +when you are writing a RE if you are using this level of complexity. +.PP +For example, this regular expression is non-greedy, and will match the +shortest substring possible given that +.QW \fBabc\fR +will be matched as early as possible (the quantifier does not change that): +.PP +.CS +ab{1,1}?c.*x.*cba +.CE +.PP +The atom +.QW \fBa\fR +has no greediness preference, we explicitly give one for +.QW \fBb\fR , +and the remaining quantifiers are overridden to be non-greedy by the preceding +non-greedy quantifier. +.RE .PP Match lengths are measured in characters, not collating elements. An empty string is considered longer than no match at all. For example, diff --git a/doc/regexp.n b/doc/regexp.n index 17bf564..5fc2895 100644 --- a/doc/regexp.n +++ b/doc/regexp.n @@ -51,7 +51,7 @@ the \fB(?x)\fR embedded option (see the \fBre_syntax\fR manual page). .TP 15 \fB\-indices\fR . -Changes what is stored in the \fIsubMatchVar\fRs. +Changes what is stored in the \fImatchVar\fR and \fIsubMatchVar\fRs. Instead of storing the matching characters from \fIstring\fR, each variable will contain a list of two decimal strings giving the indices diff --git a/doc/source.n b/doc/source.n index 9f488c5..67d4b6b 100644 --- a/doc/source.n +++ b/doc/source.n @@ -43,6 +43,8 @@ or which will be safely substituted by the Tcl interpreter into .QW ^Z . .PP +A leading BOM (Byte order mark) contained in the file is ignored for unicode encodings (utf-8, unicode). +.PP The \fB\-encoding\fR option is used to specify the encoding of the data stored in \fIfileName\fR. When the \fB\-encoding\fR option is omitted, the system encoding is assumed. diff --git a/generic/regc_color.c b/generic/regc_color.c index f5d6dfd..92e0aad 100644 --- a/generic/regc_color.c +++ b/generic/regc_color.c @@ -259,7 +259,7 @@ newcolor( return COLORLESS; /* too many colors */ } n = cm->ncds * 2; - if (n < MAX_COLOR + 1) { + if (n > MAX_COLOR + 1) { n = MAX_COLOR + 1; } if (cm->cd == cm->cdspace) { @@ -777,18 +777,19 @@ dumpcolors( } /* - * It's hard to do this more efficiently. + * Unfortunately, it's hard to do this next bit more efficiently. + * + * Spencer's original coding has the loop iterating from CHR_MIN + * to CHR_MAX, but that's utterly unusable for 32-bit chr, or + * even 16-bit. For debugging purposes it seems fine to print + * only chr codes up to 1000 or so. */ - for (c=CHR_MIN ; c<CHR_MAX ; c++) { + for (c=CHR_MIN ; c<1000 ; c++) { if (GETCOLOR(cm, c) == co) { dumpchr(c, f); } } - assert(c == CHR_MAX); - if (GETCOLOR(cm, c) == co) { - dumpchr(c, f); - } fprintf(f, "\n"); } } diff --git a/generic/regc_cvec.c b/generic/regc_cvec.c index 0247521..d450d3e 100644 --- a/generic/regc_cvec.c +++ b/generic/regc_cvec.c @@ -81,6 +81,7 @@ addchr( struct cvec *cv, /* character vector */ pchr c) /* character to add */ { + assert(cv->nchrs < cv->chrspace); cv->chrs[cv->nchrs++] = (chr)c; } diff --git a/generic/regc_lex.c b/generic/regc_lex.c index 132e757..16e3ae9 100644 --- a/generic/regc_lex.c +++ b/generic/regc_lex.c @@ -1139,24 +1139,6 @@ newline(void) } /* - - ch - return the chr sequence for regc_locale.c's fake collating element ch - * This helps confine use of CHR to this source file. Beware that the caller - * knows how long the sequence is. - ^ #ifdef REG_DEBUG - ^ static const chr *ch(NOPARMS); - ^ #endif - */ -#ifdef REG_DEBUG -static const chr * -ch(void) -{ - static const chr chstr[] = { CHR('c'), CHR('h'), CHR('\0') }; - - return chstr; -} -#endif - -/* - chrnamed - return the chr known by a given (chr string) name * The code is a bit clumsy, but this routine gets only such specialized * use that it hardly matters. diff --git a/generic/regc_locale.c b/generic/regc_locale.c index d8664b5..3c10cb6 100644 --- a/generic/regc_locale.c +++ b/generic/regc_locale.c @@ -140,7 +140,7 @@ static const crange alphaRangeTable[] = { {0x3f7, 0x481}, {0x48a, 0x52f}, {0x531, 0x556}, {0x561, 0x587}, {0x5d0, 0x5ea}, {0x5f0, 0x5f2}, {0x620, 0x64a}, {0x671, 0x6d3}, {0x6fa, 0x6fc}, {0x712, 0x72f}, {0x74d, 0x7a5}, {0x7ca, 0x7ea}, - {0x800, 0x815}, {0x840, 0x858}, {0x8a0, 0x8b2}, {0x904, 0x939}, + {0x800, 0x815}, {0x840, 0x858}, {0x8a0, 0x8b4}, {0x904, 0x939}, {0x958, 0x961}, {0x971, 0x980}, {0x985, 0x98c}, {0x993, 0x9a8}, {0x9aa, 0x9b0}, {0x9b6, 0x9b9}, {0x9df, 0x9e1}, {0xa05, 0xa0a}, {0xa13, 0xa28}, {0xa2a, 0xa30}, {0xa59, 0xa5c}, {0xa72, 0xa74}, @@ -148,55 +148,58 @@ static const crange alphaRangeTable[] = { {0xab5, 0xab9}, {0xb05, 0xb0c}, {0xb13, 0xb28}, {0xb2a, 0xb30}, {0xb35, 0xb39}, {0xb5f, 0xb61}, {0xb85, 0xb8a}, {0xb8e, 0xb90}, {0xb92, 0xb95}, {0xba8, 0xbaa}, {0xbae, 0xbb9}, {0xc05, 0xc0c}, - {0xc0e, 0xc10}, {0xc12, 0xc28}, {0xc2a, 0xc39}, {0xc85, 0xc8c}, - {0xc8e, 0xc90}, {0xc92, 0xca8}, {0xcaa, 0xcb3}, {0xcb5, 0xcb9}, - {0xd05, 0xd0c}, {0xd0e, 0xd10}, {0xd12, 0xd3a}, {0xd7a, 0xd7f}, - {0xd85, 0xd96}, {0xd9a, 0xdb1}, {0xdb3, 0xdbb}, {0xdc0, 0xdc6}, - {0xe01, 0xe30}, {0xe40, 0xe46}, {0xe94, 0xe97}, {0xe99, 0xe9f}, - {0xea1, 0xea3}, {0xead, 0xeb0}, {0xec0, 0xec4}, {0xedc, 0xedf}, - {0xf40, 0xf47}, {0xf49, 0xf6c}, {0xf88, 0xf8c}, {0x1000, 0x102a}, - {0x1050, 0x1055}, {0x105a, 0x105d}, {0x106e, 0x1070}, {0x1075, 0x1081}, - {0x10a0, 0x10c5}, {0x10d0, 0x10fa}, {0x10fc, 0x1248}, {0x124a, 0x124d}, - {0x1250, 0x1256}, {0x125a, 0x125d}, {0x1260, 0x1288}, {0x128a, 0x128d}, - {0x1290, 0x12b0}, {0x12b2, 0x12b5}, {0x12b8, 0x12be}, {0x12c2, 0x12c5}, - {0x12c8, 0x12d6}, {0x12d8, 0x1310}, {0x1312, 0x1315}, {0x1318, 0x135a}, - {0x1380, 0x138f}, {0x13a0, 0x13f4}, {0x1401, 0x166c}, {0x166f, 0x167f}, - {0x1681, 0x169a}, {0x16a0, 0x16ea}, {0x16f1, 0x16f8}, {0x1700, 0x170c}, - {0x170e, 0x1711}, {0x1720, 0x1731}, {0x1740, 0x1751}, {0x1760, 0x176c}, - {0x176e, 0x1770}, {0x1780, 0x17b3}, {0x1820, 0x1877}, {0x1880, 0x18a8}, - {0x18b0, 0x18f5}, {0x1900, 0x191e}, {0x1950, 0x196d}, {0x1970, 0x1974}, - {0x1980, 0x19ab}, {0x19c1, 0x19c7}, {0x1a00, 0x1a16}, {0x1a20, 0x1a54}, - {0x1b05, 0x1b33}, {0x1b45, 0x1b4b}, {0x1b83, 0x1ba0}, {0x1bba, 0x1be5}, - {0x1c00, 0x1c23}, {0x1c4d, 0x1c4f}, {0x1c5a, 0x1c7d}, {0x1ce9, 0x1cec}, - {0x1cee, 0x1cf1}, {0x1d00, 0x1dbf}, {0x1e00, 0x1f15}, {0x1f18, 0x1f1d}, - {0x1f20, 0x1f45}, {0x1f48, 0x1f4d}, {0x1f50, 0x1f57}, {0x1f5f, 0x1f7d}, - {0x1f80, 0x1fb4}, {0x1fb6, 0x1fbc}, {0x1fc2, 0x1fc4}, {0x1fc6, 0x1fcc}, - {0x1fd0, 0x1fd3}, {0x1fd6, 0x1fdb}, {0x1fe0, 0x1fec}, {0x1ff2, 0x1ff4}, - {0x1ff6, 0x1ffc}, {0x2090, 0x209c}, {0x210a, 0x2113}, {0x2119, 0x211d}, - {0x212a, 0x212d}, {0x212f, 0x2139}, {0x213c, 0x213f}, {0x2145, 0x2149}, - {0x2c00, 0x2c2e}, {0x2c30, 0x2c5e}, {0x2c60, 0x2ce4}, {0x2ceb, 0x2cee}, - {0x2d00, 0x2d25}, {0x2d30, 0x2d67}, {0x2d80, 0x2d96}, {0x2da0, 0x2da6}, - {0x2da8, 0x2dae}, {0x2db0, 0x2db6}, {0x2db8, 0x2dbe}, {0x2dc0, 0x2dc6}, - {0x2dc8, 0x2dce}, {0x2dd0, 0x2dd6}, {0x2dd8, 0x2dde}, {0x3031, 0x3035}, - {0x3041, 0x3096}, {0x309d, 0x309f}, {0x30a1, 0x30fa}, {0x30fc, 0x30ff}, - {0x3105, 0x312d}, {0x3131, 0x318e}, {0x31a0, 0x31ba}, {0x31f0, 0x31ff}, - {0x3400, 0x4db5}, {0x4e00, 0x9fcc}, {0xa000, 0xa48c}, {0xa4d0, 0xa4fd}, - {0xa500, 0xa60c}, {0xa610, 0xa61f}, {0xa640, 0xa66e}, {0xa67f, 0xa69d}, - {0xa6a0, 0xa6e5}, {0xa717, 0xa71f}, {0xa722, 0xa788}, {0xa78b, 0xa78e}, - {0xa790, 0xa7ad}, {0xa7f7, 0xa801}, {0xa803, 0xa805}, {0xa807, 0xa80a}, - {0xa80c, 0xa822}, {0xa840, 0xa873}, {0xa882, 0xa8b3}, {0xa8f2, 0xa8f7}, - {0xa90a, 0xa925}, {0xa930, 0xa946}, {0xa960, 0xa97c}, {0xa984, 0xa9b2}, - {0xa9e0, 0xa9e4}, {0xa9e6, 0xa9ef}, {0xa9fa, 0xa9fe}, {0xaa00, 0xaa28}, - {0xaa40, 0xaa42}, {0xaa44, 0xaa4b}, {0xaa60, 0xaa76}, {0xaa7e, 0xaaaf}, - {0xaab9, 0xaabd}, {0xaadb, 0xaadd}, {0xaae0, 0xaaea}, {0xaaf2, 0xaaf4}, - {0xab01, 0xab06}, {0xab09, 0xab0e}, {0xab11, 0xab16}, {0xab20, 0xab26}, - {0xab28, 0xab2e}, {0xab30, 0xab5a}, {0xab5c, 0xab5f}, {0xabc0, 0xabe2}, - {0xac00, 0xd7a3}, {0xd7b0, 0xd7c6}, {0xd7cb, 0xd7fb}, {0xf900, 0xfa6d}, - {0xfa70, 0xfad9}, {0xfb00, 0xfb06}, {0xfb13, 0xfb17}, {0xfb1f, 0xfb28}, - {0xfb2a, 0xfb36}, {0xfb38, 0xfb3c}, {0xfb46, 0xfbb1}, {0xfbd3, 0xfd3d}, - {0xfd50, 0xfd8f}, {0xfd92, 0xfdc7}, {0xfdf0, 0xfdfb}, {0xfe70, 0xfe74}, - {0xfe76, 0xfefc}, {0xff21, 0xff3a}, {0xff41, 0xff5a}, {0xff66, 0xffbe}, - {0xffc2, 0xffc7}, {0xffca, 0xffcf}, {0xffd2, 0xffd7}, {0xffda, 0xffdc} + {0xc0e, 0xc10}, {0xc12, 0xc28}, {0xc2a, 0xc39}, {0xc58, 0xc5a}, + {0xc85, 0xc8c}, {0xc8e, 0xc90}, {0xc92, 0xca8}, {0xcaa, 0xcb3}, + {0xcb5, 0xcb9}, {0xd05, 0xd0c}, {0xd0e, 0xd10}, {0xd12, 0xd3a}, + {0xd5f, 0xd61}, {0xd7a, 0xd7f}, {0xd85, 0xd96}, {0xd9a, 0xdb1}, + {0xdb3, 0xdbb}, {0xdc0, 0xdc6}, {0xe01, 0xe30}, {0xe40, 0xe46}, + {0xe94, 0xe97}, {0xe99, 0xe9f}, {0xea1, 0xea3}, {0xead, 0xeb0}, + {0xec0, 0xec4}, {0xedc, 0xedf}, {0xf40, 0xf47}, {0xf49, 0xf6c}, + {0xf88, 0xf8c}, {0x1000, 0x102a}, {0x1050, 0x1055}, {0x105a, 0x105d}, + {0x106e, 0x1070}, {0x1075, 0x1081}, {0x10a0, 0x10c5}, {0x10d0, 0x10fa}, + {0x10fc, 0x1248}, {0x124a, 0x124d}, {0x1250, 0x1256}, {0x125a, 0x125d}, + {0x1260, 0x1288}, {0x128a, 0x128d}, {0x1290, 0x12b0}, {0x12b2, 0x12b5}, + {0x12b8, 0x12be}, {0x12c2, 0x12c5}, {0x12c8, 0x12d6}, {0x12d8, 0x1310}, + {0x1312, 0x1315}, {0x1318, 0x135a}, {0x1380, 0x138f}, {0x13a0, 0x13f5}, + {0x13f8, 0x13fd}, {0x1401, 0x166c}, {0x166f, 0x167f}, {0x1681, 0x169a}, + {0x16a0, 0x16ea}, {0x16f1, 0x16f8}, {0x1700, 0x170c}, {0x170e, 0x1711}, + {0x1720, 0x1731}, {0x1740, 0x1751}, {0x1760, 0x176c}, {0x176e, 0x1770}, + {0x1780, 0x17b3}, {0x1820, 0x1877}, {0x1880, 0x18a8}, {0x18b0, 0x18f5}, + {0x1900, 0x191e}, {0x1950, 0x196d}, {0x1970, 0x1974}, {0x1980, 0x19ab}, + {0x19b0, 0x19c9}, {0x1a00, 0x1a16}, {0x1a20, 0x1a54}, {0x1b05, 0x1b33}, + {0x1b45, 0x1b4b}, {0x1b83, 0x1ba0}, {0x1bba, 0x1be5}, {0x1c00, 0x1c23}, + {0x1c4d, 0x1c4f}, {0x1c5a, 0x1c7d}, {0x1ce9, 0x1cec}, {0x1cee, 0x1cf1}, + {0x1d00, 0x1dbf}, {0x1e00, 0x1f15}, {0x1f18, 0x1f1d}, {0x1f20, 0x1f45}, + {0x1f48, 0x1f4d}, {0x1f50, 0x1f57}, {0x1f5f, 0x1f7d}, {0x1f80, 0x1fb4}, + {0x1fb6, 0x1fbc}, {0x1fc2, 0x1fc4}, {0x1fc6, 0x1fcc}, {0x1fd0, 0x1fd3}, + {0x1fd6, 0x1fdb}, {0x1fe0, 0x1fec}, {0x1ff2, 0x1ff4}, {0x1ff6, 0x1ffc}, + {0x2090, 0x209c}, {0x210a, 0x2113}, {0x2119, 0x211d}, {0x212a, 0x212d}, + {0x212f, 0x2139}, {0x213c, 0x213f}, {0x2145, 0x2149}, {0x2c00, 0x2c2e}, + {0x2c30, 0x2c5e}, {0x2c60, 0x2ce4}, {0x2ceb, 0x2cee}, {0x2d00, 0x2d25}, + {0x2d30, 0x2d67}, {0x2d80, 0x2d96}, {0x2da0, 0x2da6}, {0x2da8, 0x2dae}, + {0x2db0, 0x2db6}, {0x2db8, 0x2dbe}, {0x2dc0, 0x2dc6}, {0x2dc8, 0x2dce}, + {0x2dd0, 0x2dd6}, {0x2dd8, 0x2dde}, {0x3031, 0x3035}, {0x3041, 0x3096}, + {0x309d, 0x309f}, {0x30a1, 0x30fa}, {0x30fc, 0x30ff}, {0x3105, 0x312d}, + {0x3131, 0x318e}, {0x31a0, 0x31ba}, {0x31f0, 0x31ff}, {0x3400, 0x4db5}, + {0x4e00, 0x9fd5}, {0xa000, 0xa48c}, {0xa4d0, 0xa4fd}, {0xa500, 0xa60c}, + {0xa610, 0xa61f}, {0xa640, 0xa66e}, {0xa67f, 0xa69d}, {0xa6a0, 0xa6e5}, + {0xa717, 0xa71f}, {0xa722, 0xa788}, {0xa78b, 0xa7ad}, {0xa7b0, 0xa7b7}, + {0xa7f7, 0xa801}, {0xa803, 0xa805}, {0xa807, 0xa80a}, {0xa80c, 0xa822}, + {0xa840, 0xa873}, {0xa882, 0xa8b3}, {0xa8f2, 0xa8f7}, {0xa90a, 0xa925}, + {0xa930, 0xa946}, {0xa960, 0xa97c}, {0xa984, 0xa9b2}, {0xa9e0, 0xa9e4}, + {0xa9e6, 0xa9ef}, {0xa9fa, 0xa9fe}, {0xaa00, 0xaa28}, {0xaa40, 0xaa42}, + {0xaa44, 0xaa4b}, {0xaa60, 0xaa76}, {0xaa7e, 0xaaaf}, {0xaab9, 0xaabd}, + {0xaadb, 0xaadd}, {0xaae0, 0xaaea}, {0xaaf2, 0xaaf4}, {0xab01, 0xab06}, + {0xab09, 0xab0e}, {0xab11, 0xab16}, {0xab20, 0xab26}, {0xab28, 0xab2e}, + {0xab30, 0xab5a}, {0xab5c, 0xab65}, {0xab70, 0xabe2}, {0xac00, 0xd7a3}, + {0xd7b0, 0xd7c6}, {0xd7cb, 0xd7fb}, {0xdc00, 0xdc3e}, {0xdc40, 0xdc7e}, + {0xde80, 0xdebe}, {0xdec0, 0xdefe}, {0xdf00, 0xdf3e}, {0xdf40, 0xdf7e}, + {0xdf80, 0xdfbe}, {0xdfc0, 0xdffe}, {0xf900, 0xfa6d}, {0xfa70, 0xfad9}, + {0xfb00, 0xfb06}, {0xfb13, 0xfb17}, {0xfb1f, 0xfb28}, {0xfb2a, 0xfb36}, + {0xfb38, 0xfb3c}, {0xfb46, 0xfbb1}, {0xfbd3, 0xfd3d}, {0xfd50, 0xfd8f}, + {0xfd92, 0xfdc7}, {0xfdf0, 0xfdfb}, {0xfe70, 0xfe74}, {0xfe76, 0xfefc}, + {0xff21, 0xff3a}, {0xff41, 0xff5a}, {0xff66, 0xffbe}, {0xffc2, 0xffc7}, + {0xffca, 0xffcf}, {0xffd2, 0xffd7}, {0xffda, 0xffdc} #if TCL_UTF_MAX > 4 ,{0x10000, 0x1000b}, {0x1000d, 0x10026}, {0x10028, 0x1003a}, {0x1003f, 0x1004d}, {0x10050, 0x1005d}, {0x10080, 0x100fa}, {0x10280, 0x1029c}, {0x102a0, 0x102d0}, @@ -204,30 +207,33 @@ static const crange alphaRangeTable[] = { {0x10380, 0x1039d}, {0x103a0, 0x103c3}, {0x103c8, 0x103cf}, {0x10400, 0x1049d}, {0x10500, 0x10527}, {0x10530, 0x10563}, {0x10600, 0x10736}, {0x10740, 0x10755}, {0x10760, 0x10767}, {0x10800, 0x10805}, {0x1080a, 0x10835}, {0x1083f, 0x10855}, - {0x10860, 0x10876}, {0x10880, 0x1089e}, {0x10900, 0x10915}, {0x10920, 0x10939}, - {0x10980, 0x109b7}, {0x10a10, 0x10a13}, {0x10a15, 0x10a17}, {0x10a19, 0x10a33}, - {0x10a60, 0x10a7c}, {0x10a80, 0x10a9c}, {0x10ac0, 0x10ac7}, {0x10ac9, 0x10ae4}, - {0x10b00, 0x10b35}, {0x10b40, 0x10b55}, {0x10b60, 0x10b72}, {0x10b80, 0x10b91}, - {0x10c00, 0x10c48}, {0x11003, 0x11037}, {0x11083, 0x110af}, {0x110d0, 0x110e8}, - {0x11103, 0x11126}, {0x11150, 0x11172}, {0x11183, 0x111b2}, {0x111c1, 0x111c4}, - {0x11200, 0x11211}, {0x11213, 0x1122b}, {0x112b0, 0x112de}, {0x11305, 0x1130c}, - {0x11313, 0x11328}, {0x1132a, 0x11330}, {0x11335, 0x11339}, {0x1135d, 0x11361}, - {0x11480, 0x114af}, {0x11580, 0x115ae}, {0x11600, 0x1162f}, {0x11680, 0x116aa}, - {0x118a0, 0x118df}, {0x11ac0, 0x11af8}, {0x12000, 0x12398}, {0x13000, 0x1342e}, - {0x16800, 0x16a38}, {0x16a40, 0x16a5e}, {0x16ad0, 0x16aed}, {0x16b00, 0x16b2f}, - {0x16b40, 0x16b43}, {0x16b63, 0x16b77}, {0x16b7d, 0x16b8f}, {0x16f00, 0x16f44}, - {0x16f93, 0x16f9f}, {0x1bc00, 0x1bc6a}, {0x1bc70, 0x1bc7c}, {0x1bc80, 0x1bc88}, - {0x1bc90, 0x1bc99}, {0x1d400, 0x1d454}, {0x1d456, 0x1d49c}, {0x1d4a9, 0x1d4ac}, - {0x1d4ae, 0x1d4b9}, {0x1d4bd, 0x1d4c3}, {0x1d4c5, 0x1d505}, {0x1d507, 0x1d50a}, - {0x1d50d, 0x1d514}, {0x1d516, 0x1d51c}, {0x1d51e, 0x1d539}, {0x1d53b, 0x1d53e}, - {0x1d540, 0x1d544}, {0x1d54a, 0x1d550}, {0x1d552, 0x1d6a5}, {0x1d6a8, 0x1d6c0}, - {0x1d6c2, 0x1d6da}, {0x1d6dc, 0x1d6fa}, {0x1d6fc, 0x1d714}, {0x1d716, 0x1d734}, - {0x1d736, 0x1d74e}, {0x1d750, 0x1d76e}, {0x1d770, 0x1d788}, {0x1d78a, 0x1d7a8}, - {0x1d7aa, 0x1d7c2}, {0x1d7c4, 0x1d7cb}, {0x1e800, 0x1e8c4}, {0x1ee00, 0x1ee03}, - {0x1ee05, 0x1ee1f}, {0x1ee29, 0x1ee32}, {0x1ee34, 0x1ee37}, {0x1ee4d, 0x1ee4f}, - {0x1ee67, 0x1ee6a}, {0x1ee6c, 0x1ee72}, {0x1ee74, 0x1ee77}, {0x1ee79, 0x1ee7c}, - {0x1ee80, 0x1ee89}, {0x1ee8b, 0x1ee9b}, {0x1eea1, 0x1eea3}, {0x1eea5, 0x1eea9}, - {0x1eeab, 0x1eebb}, {0x20000, 0x2a6d6}, {0x2a700, 0x2b734}, {0x2b740, 0x2b81d}, + {0x10860, 0x10876}, {0x10880, 0x1089e}, {0x108e0, 0x108f2}, {0x10900, 0x10915}, + {0x10920, 0x10939}, {0x10980, 0x109b7}, {0x10a10, 0x10a13}, {0x10a15, 0x10a17}, + {0x10a19, 0x10a33}, {0x10a60, 0x10a7c}, {0x10a80, 0x10a9c}, {0x10ac0, 0x10ac7}, + {0x10ac9, 0x10ae4}, {0x10b00, 0x10b35}, {0x10b40, 0x10b55}, {0x10b60, 0x10b72}, + {0x10b80, 0x10b91}, {0x10c00, 0x10c48}, {0x10c80, 0x10cb2}, {0x10cc0, 0x10cf2}, + {0x11003, 0x11037}, {0x11083, 0x110af}, {0x110d0, 0x110e8}, {0x11103, 0x11126}, + {0x11150, 0x11172}, {0x11183, 0x111b2}, {0x111c1, 0x111c4}, {0x11200, 0x11211}, + {0x11213, 0x1122b}, {0x11280, 0x11286}, {0x1128a, 0x1128d}, {0x1128f, 0x1129d}, + {0x1129f, 0x112a8}, {0x112b0, 0x112de}, {0x11305, 0x1130c}, {0x11313, 0x11328}, + {0x1132a, 0x11330}, {0x11335, 0x11339}, {0x1135d, 0x11361}, {0x11480, 0x114af}, + {0x11580, 0x115ae}, {0x115d8, 0x115db}, {0x11600, 0x1162f}, {0x11680, 0x116aa}, + {0x11700, 0x11719}, {0x118a0, 0x118df}, {0x11ac0, 0x11af8}, {0x12000, 0x12399}, + {0x12480, 0x12543}, {0x13000, 0x1342e}, {0x14400, 0x14646}, {0x16800, 0x16a38}, + {0x16a40, 0x16a5e}, {0x16ad0, 0x16aed}, {0x16b00, 0x16b2f}, {0x16b40, 0x16b43}, + {0x16b63, 0x16b77}, {0x16b7d, 0x16b8f}, {0x16f00, 0x16f44}, {0x16f93, 0x16f9f}, + {0x1bc00, 0x1bc6a}, {0x1bc70, 0x1bc7c}, {0x1bc80, 0x1bc88}, {0x1bc90, 0x1bc99}, + {0x1d400, 0x1d454}, {0x1d456, 0x1d49c}, {0x1d4a9, 0x1d4ac}, {0x1d4ae, 0x1d4b9}, + {0x1d4bd, 0x1d4c3}, {0x1d4c5, 0x1d505}, {0x1d507, 0x1d50a}, {0x1d50d, 0x1d514}, + {0x1d516, 0x1d51c}, {0x1d51e, 0x1d539}, {0x1d53b, 0x1d53e}, {0x1d540, 0x1d544}, + {0x1d54a, 0x1d550}, {0x1d552, 0x1d6a5}, {0x1d6a8, 0x1d6c0}, {0x1d6c2, 0x1d6da}, + {0x1d6dc, 0x1d6fa}, {0x1d6fc, 0x1d714}, {0x1d716, 0x1d734}, {0x1d736, 0x1d74e}, + {0x1d750, 0x1d76e}, {0x1d770, 0x1d788}, {0x1d78a, 0x1d7a8}, {0x1d7aa, 0x1d7c2}, + {0x1d7c4, 0x1d7cb}, {0x1e800, 0x1e8c4}, {0x1ee00, 0x1ee03}, {0x1ee05, 0x1ee1f}, + {0x1ee29, 0x1ee32}, {0x1ee34, 0x1ee37}, {0x1ee4d, 0x1ee4f}, {0x1ee67, 0x1ee6a}, + {0x1ee6c, 0x1ee72}, {0x1ee74, 0x1ee77}, {0x1ee79, 0x1ee7c}, {0x1ee80, 0x1ee89}, + {0x1ee8b, 0x1ee9b}, {0x1eea1, 0x1eea3}, {0x1eea5, 0x1eea9}, {0x1eeab, 0x1eebb}, + {0x20000, 0x2a6d6}, {0x2a700, 0x2b734}, {0x2b740, 0x2b81d}, {0x2b820, 0x2cea1}, {0x2f800, 0x2fa1d} #endif }; @@ -240,27 +246,27 @@ static const chr alphaCharTable[] = { 0x6ff, 0x710, 0x7b1, 0x7f4, 0x7f5, 0x7fa, 0x81a, 0x824, 0x828, 0x93d, 0x950, 0x98f, 0x990, 0x9b2, 0x9bd, 0x9ce, 0x9dc, 0x9dd, 0x9f0, 0x9f1, 0xa0f, 0xa10, 0xa32, 0xa33, 0xa35, 0xa36, 0xa38, - 0xa39, 0xa5e, 0xab2, 0xab3, 0xabd, 0xad0, 0xae0, 0xae1, 0xb0f, - 0xb10, 0xb32, 0xb33, 0xb3d, 0xb5c, 0xb5d, 0xb71, 0xb83, 0xb99, - 0xb9a, 0xb9c, 0xb9e, 0xb9f, 0xba3, 0xba4, 0xbd0, 0xc3d, 0xc58, - 0xc59, 0xc60, 0xc61, 0xcbd, 0xcde, 0xce0, 0xce1, 0xcf1, 0xcf2, - 0xd3d, 0xd4e, 0xd60, 0xd61, 0xdbd, 0xe32, 0xe33, 0xe81, 0xe82, - 0xe84, 0xe87, 0xe88, 0xe8a, 0xe8d, 0xea5, 0xea7, 0xeaa, 0xeab, - 0xeb2, 0xeb3, 0xebd, 0xec6, 0xf00, 0x103f, 0x1061, 0x1065, 0x1066, - 0x108e, 0x10c7, 0x10cd, 0x1258, 0x12c0, 0x17d7, 0x17dc, 0x18aa, 0x1aa7, - 0x1bae, 0x1baf, 0x1cf5, 0x1cf6, 0x1f59, 0x1f5b, 0x1f5d, 0x1fbe, 0x2071, - 0x207f, 0x2102, 0x2107, 0x2115, 0x2124, 0x2126, 0x2128, 0x214e, 0x2183, - 0x2184, 0x2cf2, 0x2cf3, 0x2d27, 0x2d2d, 0x2d6f, 0x2e2f, 0x3005, 0x3006, - 0x303b, 0x303c, 0xa62a, 0xa62b, 0xa7b0, 0xa7b1, 0xa8fb, 0xa9cf, 0xaa7a, - 0xaab1, 0xaab5, 0xaab6, 0xaac0, 0xaac2, 0xab64, 0xab65, 0xfb1d, 0xfb3e, - 0xfb40, 0xfb41, 0xfb43, 0xfb44 + 0xa39, 0xa5e, 0xab2, 0xab3, 0xabd, 0xad0, 0xae0, 0xae1, 0xaf9, + 0xb0f, 0xb10, 0xb32, 0xb33, 0xb3d, 0xb5c, 0xb5d, 0xb71, 0xb83, + 0xb99, 0xb9a, 0xb9c, 0xb9e, 0xb9f, 0xba3, 0xba4, 0xbd0, 0xc3d, + 0xc60, 0xc61, 0xcbd, 0xcde, 0xce0, 0xce1, 0xcf1, 0xcf2, 0xd3d, + 0xd4e, 0xdbd, 0xe32, 0xe33, 0xe81, 0xe82, 0xe84, 0xe87, 0xe88, + 0xe8a, 0xe8d, 0xea5, 0xea7, 0xeaa, 0xeab, 0xeb2, 0xeb3, 0xebd, + 0xec6, 0xf00, 0x103f, 0x1061, 0x1065, 0x1066, 0x108e, 0x10c7, 0x10cd, + 0x1258, 0x12c0, 0x17d7, 0x17dc, 0x18aa, 0x1aa7, 0x1bae, 0x1baf, 0x1cf5, + 0x1cf6, 0x1f59, 0x1f5b, 0x1f5d, 0x1fbe, 0x2071, 0x207f, 0x2102, 0x2107, + 0x2115, 0x2124, 0x2126, 0x2128, 0x214e, 0x2183, 0x2184, 0x2cf2, 0x2cf3, + 0x2d27, 0x2d2d, 0x2d6f, 0x2e2f, 0x3005, 0x3006, 0x303b, 0x303c, 0xa62a, + 0xa62b, 0xa8fb, 0xa8fd, 0xa9cf, 0xaa7a, 0xaab1, 0xaab5, 0xaab6, 0xaac0, + 0xaac2, 0xfb1d, 0xfb3e, 0xfb40, 0xfb41, 0xfb43, 0xfb44 #if TCL_UTF_MAX > 4 - ,0x1003c, 0x1003d, 0x10808, 0x10837, 0x10838, 0x1083c, 0x109be, 0x109bf, 0x10a00, - 0x11176, 0x111da, 0x1130f, 0x11310, 0x11332, 0x11333, 0x1133d, 0x114c4, 0x114c5, - 0x114c7, 0x11644, 0x118ff, 0x16f50, 0x1b000, 0x1b001, 0x1d49e, 0x1d49f, 0x1d4a2, - 0x1d4a5, 0x1d4a6, 0x1d4bb, 0x1d546, 0x1ee21, 0x1ee22, 0x1ee24, 0x1ee27, 0x1ee39, - 0x1ee3b, 0x1ee42, 0x1ee47, 0x1ee49, 0x1ee4b, 0x1ee51, 0x1ee52, 0x1ee54, 0x1ee57, - 0x1ee59, 0x1ee5b, 0x1ee5d, 0x1ee5f, 0x1ee61, 0x1ee62, 0x1ee64, 0x1ee7e + ,0x1003c, 0x1003d, 0x10808, 0x10837, 0x10838, 0x1083c, 0x108f4, 0x108f5, 0x109be, + 0x109bf, 0x10a00, 0x11176, 0x111da, 0x111dc, 0x11288, 0x1130f, 0x11310, 0x11332, + 0x11333, 0x1133d, 0x11350, 0x114c4, 0x114c5, 0x114c7, 0x11644, 0x118ff, 0x16f50, + 0x1b000, 0x1b001, 0x1d49e, 0x1d49f, 0x1d4a2, 0x1d4a5, 0x1d4a6, 0x1d4bb, 0x1d546, + 0x1ee21, 0x1ee22, 0x1ee24, 0x1ee27, 0x1ee39, 0x1ee3b, 0x1ee42, 0x1ee47, 0x1ee49, + 0x1ee4b, 0x1ee51, 0x1ee52, 0x1ee54, 0x1ee57, 0x1ee59, 0x1ee5b, 0x1ee5d, 0x1ee5f, + 0x1ee61, 0x1ee62, 0x1ee64, 0x1ee7e #endif }; @@ -309,8 +315,8 @@ static const crange digitRangeTable[] = { #if TCL_UTF_MAX > 4 ,{0x104a0, 0x104a9}, {0x11066, 0x1106f}, {0x110f0, 0x110f9}, {0x11136, 0x1113f}, {0x111d0, 0x111d9}, {0x112f0, 0x112f9}, {0x114d0, 0x114d9}, {0x11650, 0x11659}, - {0x116c0, 0x116c9}, {0x118e0, 0x118e9}, {0x16a60, 0x16a69}, {0x16b50, 0x16b59}, - {0x1d7ce, 0x1d7ff} + {0x116c0, 0x116c9}, {0x11730, 0x11739}, {0x118e0, 0x118e9}, {0x16a60, 0x16a69}, + {0x16b50, 0x16b59}, {0x1d7ce, 0x1d7ff} #endif }; @@ -342,8 +348,9 @@ static const crange punctRangeTable[] = { #if TCL_UTF_MAX > 4 ,{0x10100, 0x10102}, {0x10a50, 0x10a58}, {0x10af0, 0x10af6}, {0x10b39, 0x10b3f}, {0x10b99, 0x10b9c}, {0x11047, 0x1104d}, {0x110be, 0x110c1}, {0x11140, 0x11143}, - {0x111c5, 0x111c8}, {0x11238, 0x1123d}, {0x115c1, 0x115c9}, {0x11641, 0x11643}, - {0x12470, 0x12474}, {0x16b37, 0x16b3b} + {0x111c5, 0x111c9}, {0x111dd, 0x111df}, {0x11238, 0x1123d}, {0x115c1, 0x115d7}, + {0x11641, 0x11643}, {0x1173c, 0x1173e}, {0x12470, 0x12474}, {0x16b37, 0x16b3b}, + {0x1da87, 0x1da8b} #endif }; @@ -359,12 +366,13 @@ static const chr punctCharTable[] = { 0x1945, 0x1a1e, 0x1a1f, 0x1c7e, 0x1c7f, 0x1cd3, 0x207d, 0x207e, 0x208d, 0x208e, 0x2329, 0x232a, 0x27c5, 0x27c6, 0x29fc, 0x29fd, 0x2cfe, 0x2cff, 0x2d70, 0x3030, 0x303d, 0x30a0, 0x30fb, 0xa4fe, 0xa4ff, 0xa673, 0xa67e, - 0xa8ce, 0xa8cf, 0xa92e, 0xa92f, 0xa95f, 0xa9de, 0xa9df, 0xaade, 0xaadf, - 0xaaf0, 0xaaf1, 0xabeb, 0xfd3e, 0xfd3f, 0xfe63, 0xfe68, 0xfe6a, 0xfe6b, - 0xff1a, 0xff1b, 0xff1f, 0xff20, 0xff3f, 0xff5b, 0xff5d + 0xa8ce, 0xa8cf, 0xa8fc, 0xa92e, 0xa92f, 0xa95f, 0xa9de, 0xa9df, 0xaade, + 0xaadf, 0xaaf0, 0xaaf1, 0xabeb, 0xfd3e, 0xfd3f, 0xfe63, 0xfe68, 0xfe6a, + 0xfe6b, 0xff1a, 0xff1b, 0xff1f, 0xff20, 0xff3f, 0xff5b, 0xff5d #if TCL_UTF_MAX > 4 ,0x1039f, 0x103d0, 0x1056f, 0x10857, 0x1091f, 0x1093f, 0x10a7f, 0x110bb, 0x110bc, - 0x11174, 0x11175, 0x111cd, 0x114c6, 0x16a6e, 0x16a6f, 0x16af5, 0x16b44, 0x1bc9f + 0x11174, 0x11175, 0x111cd, 0x111db, 0x112a9, 0x114c6, 0x16a6e, 0x16a6f, 0x16af5, + 0x16b44, 0x1bc9f #endif }; @@ -395,23 +403,25 @@ static const crange lowerRangeTable[] = { {0x61, 0x7a}, {0xdf, 0xf6}, {0xf8, 0xff}, {0x17e, 0x180}, {0x199, 0x19b}, {0x1bd, 0x1bf}, {0x233, 0x239}, {0x24f, 0x293}, {0x295, 0x2af}, {0x37b, 0x37d}, {0x3ac, 0x3ce}, {0x3d5, 0x3d7}, - {0x3ef, 0x3f3}, {0x430, 0x45f}, {0x561, 0x587}, {0x1d00, 0x1d2b}, - {0x1d6b, 0x1d77}, {0x1d79, 0x1d9a}, {0x1e95, 0x1e9d}, {0x1eff, 0x1f07}, - {0x1f10, 0x1f15}, {0x1f20, 0x1f27}, {0x1f30, 0x1f37}, {0x1f40, 0x1f45}, - {0x1f50, 0x1f57}, {0x1f60, 0x1f67}, {0x1f70, 0x1f7d}, {0x1f80, 0x1f87}, - {0x1f90, 0x1f97}, {0x1fa0, 0x1fa7}, {0x1fb0, 0x1fb4}, {0x1fc2, 0x1fc4}, - {0x1fd0, 0x1fd3}, {0x1fe0, 0x1fe7}, {0x1ff2, 0x1ff4}, {0x2146, 0x2149}, - {0x2c30, 0x2c5e}, {0x2c76, 0x2c7b}, {0x2d00, 0x2d25}, {0xa72f, 0xa731}, - {0xa771, 0xa778}, {0xa793, 0xa795}, {0xab30, 0xab5a}, {0xfb00, 0xfb06}, - {0xfb13, 0xfb17}, {0xff41, 0xff5a} + {0x3ef, 0x3f3}, {0x430, 0x45f}, {0x561, 0x587}, {0x13f8, 0x13fd}, + {0x1d00, 0x1d2b}, {0x1d6b, 0x1d77}, {0x1d79, 0x1d9a}, {0x1e95, 0x1e9d}, + {0x1eff, 0x1f07}, {0x1f10, 0x1f15}, {0x1f20, 0x1f27}, {0x1f30, 0x1f37}, + {0x1f40, 0x1f45}, {0x1f50, 0x1f57}, {0x1f60, 0x1f67}, {0x1f70, 0x1f7d}, + {0x1f80, 0x1f87}, {0x1f90, 0x1f97}, {0x1fa0, 0x1fa7}, {0x1fb0, 0x1fb4}, + {0x1fc2, 0x1fc4}, {0x1fd0, 0x1fd3}, {0x1fe0, 0x1fe7}, {0x1ff2, 0x1ff4}, + {0x2146, 0x2149}, {0x2c30, 0x2c5e}, {0x2c76, 0x2c7b}, {0x2d00, 0x2d25}, + {0xa72f, 0xa731}, {0xa771, 0xa778}, {0xa793, 0xa795}, {0xab30, 0xab5a}, + {0xab60, 0xab65}, {0xab70, 0xabbf}, {0xfb00, 0xfb06}, {0xfb13, 0xfb17}, + {0xff41, 0xff5a} #if TCL_UTF_MAX > 4 - ,{0x10428, 0x1044f}, {0x118c0, 0x118df}, {0x1d41a, 0x1d433}, {0x1d44e, 0x1d454}, - {0x1d456, 0x1d467}, {0x1d482, 0x1d49b}, {0x1d4b6, 0x1d4b9}, {0x1d4bd, 0x1d4c3}, - {0x1d4c5, 0x1d4cf}, {0x1d4ea, 0x1d503}, {0x1d51e, 0x1d537}, {0x1d552, 0x1d56b}, - {0x1d586, 0x1d59f}, {0x1d5ba, 0x1d5d3}, {0x1d5ee, 0x1d607}, {0x1d622, 0x1d63b}, - {0x1d656, 0x1d66f}, {0x1d68a, 0x1d6a5}, {0x1d6c2, 0x1d6da}, {0x1d6dc, 0x1d6e1}, - {0x1d6fc, 0x1d714}, {0x1d716, 0x1d71b}, {0x1d736, 0x1d74e}, {0x1d750, 0x1d755}, - {0x1d770, 0x1d788}, {0x1d78a, 0x1d78f}, {0x1d7aa, 0x1d7c2}, {0x1d7c4, 0x1d7c9} + ,{0x10428, 0x1044f}, {0x10cc0, 0x10cf2}, {0x118c0, 0x118df}, {0x1d41a, 0x1d433}, + {0x1d44e, 0x1d454}, {0x1d456, 0x1d467}, {0x1d482, 0x1d49b}, {0x1d4b6, 0x1d4b9}, + {0x1d4bd, 0x1d4c3}, {0x1d4c5, 0x1d4cf}, {0x1d4ea, 0x1d503}, {0x1d51e, 0x1d537}, + {0x1d552, 0x1d56b}, {0x1d586, 0x1d59f}, {0x1d5ba, 0x1d5d3}, {0x1d5ee, 0x1d607}, + {0x1d622, 0x1d63b}, {0x1d656, 0x1d66f}, {0x1d68a, 0x1d6a5}, {0x1d6c2, 0x1d6da}, + {0x1d6dc, 0x1d6e1}, {0x1d6fc, 0x1d714}, {0x1d716, 0x1d71b}, {0x1d736, 0x1d74e}, + {0x1d750, 0x1d755}, {0x1d770, 0x1d788}, {0x1d78a, 0x1d78f}, {0x1d7aa, 0x1d7c2}, + {0x1d7c4, 0x1d7c9} #endif }; @@ -481,7 +491,7 @@ static const chr lowerCharTable[] = { 0xa763, 0xa765, 0xa767, 0xa769, 0xa76b, 0xa76d, 0xa76f, 0xa77a, 0xa77c, 0xa77f, 0xa781, 0xa783, 0xa785, 0xa787, 0xa78c, 0xa78e, 0xa791, 0xa797, 0xa799, 0xa79b, 0xa79d, 0xa79f, 0xa7a1, 0xa7a3, 0xa7a5, 0xa7a7, 0xa7a9, - 0xa7fa, 0xab64, 0xab65 + 0xa7b5, 0xa7b7, 0xa7fa #if TCL_UTF_MAX > 4 ,0x1d4bb, 0x1d7cb #endif @@ -498,20 +508,20 @@ static const crange upperRangeTable[] = { {0x18e, 0x191}, {0x196, 0x198}, {0x1b1, 0x1b3}, {0x1f6, 0x1f8}, {0x243, 0x246}, {0x388, 0x38a}, {0x391, 0x3a1}, {0x3a3, 0x3ab}, {0x3d2, 0x3d4}, {0x3fd, 0x42f}, {0x531, 0x556}, {0x10a0, 0x10c5}, - {0x1f08, 0x1f0f}, {0x1f18, 0x1f1d}, {0x1f28, 0x1f2f}, {0x1f38, 0x1f3f}, - {0x1f48, 0x1f4d}, {0x1f68, 0x1f6f}, {0x1fb8, 0x1fbb}, {0x1fc8, 0x1fcb}, - {0x1fd8, 0x1fdb}, {0x1fe8, 0x1fec}, {0x1ff8, 0x1ffb}, {0x210b, 0x210d}, - {0x2110, 0x2112}, {0x2119, 0x211d}, {0x212a, 0x212d}, {0x2130, 0x2133}, - {0x2c00, 0x2c2e}, {0x2c62, 0x2c64}, {0x2c6d, 0x2c70}, {0x2c7e, 0x2c80}, - {0xa7aa, 0xa7ad}, {0xff21, 0xff3a} + {0x13a0, 0x13f5}, {0x1f08, 0x1f0f}, {0x1f18, 0x1f1d}, {0x1f28, 0x1f2f}, + {0x1f38, 0x1f3f}, {0x1f48, 0x1f4d}, {0x1f68, 0x1f6f}, {0x1fb8, 0x1fbb}, + {0x1fc8, 0x1fcb}, {0x1fd8, 0x1fdb}, {0x1fe8, 0x1fec}, {0x1ff8, 0x1ffb}, + {0x210b, 0x210d}, {0x2110, 0x2112}, {0x2119, 0x211d}, {0x212a, 0x212d}, + {0x2130, 0x2133}, {0x2c00, 0x2c2e}, {0x2c62, 0x2c64}, {0x2c6d, 0x2c70}, + {0x2c7e, 0x2c80}, {0xa7aa, 0xa7ad}, {0xa7b0, 0xa7b4}, {0xff21, 0xff3a} #if TCL_UTF_MAX > 4 - ,{0x10400, 0x10427}, {0x118a0, 0x118bf}, {0x1d400, 0x1d419}, {0x1d434, 0x1d44d}, - {0x1d468, 0x1d481}, {0x1d4a9, 0x1d4ac}, {0x1d4ae, 0x1d4b5}, {0x1d4d0, 0x1d4e9}, - {0x1d507, 0x1d50a}, {0x1d50d, 0x1d514}, {0x1d516, 0x1d51c}, {0x1d53b, 0x1d53e}, - {0x1d540, 0x1d544}, {0x1d54a, 0x1d550}, {0x1d56c, 0x1d585}, {0x1d5a0, 0x1d5b9}, - {0x1d5d4, 0x1d5ed}, {0x1d608, 0x1d621}, {0x1d63c, 0x1d655}, {0x1d670, 0x1d689}, - {0x1d6a8, 0x1d6c0}, {0x1d6e2, 0x1d6fa}, {0x1d71c, 0x1d734}, {0x1d756, 0x1d76e}, - {0x1d790, 0x1d7a8} + ,{0x10400, 0x10427}, {0x10c80, 0x10cb2}, {0x118a0, 0x118bf}, {0x1d400, 0x1d419}, + {0x1d434, 0x1d44d}, {0x1d468, 0x1d481}, {0x1d4a9, 0x1d4ac}, {0x1d4ae, 0x1d4b5}, + {0x1d4d0, 0x1d4e9}, {0x1d507, 0x1d50a}, {0x1d50d, 0x1d514}, {0x1d516, 0x1d51c}, + {0x1d53b, 0x1d53e}, {0x1d540, 0x1d544}, {0x1d54a, 0x1d550}, {0x1d56c, 0x1d585}, + {0x1d5a0, 0x1d5b9}, {0x1d5d4, 0x1d5ed}, {0x1d608, 0x1d621}, {0x1d63c, 0x1d655}, + {0x1d670, 0x1d689}, {0x1d6a8, 0x1d6c0}, {0x1d6e2, 0x1d6fa}, {0x1d71c, 0x1d734}, + {0x1d756, 0x1d76e}, {0x1d790, 0x1d7a8} #endif }; @@ -580,8 +590,7 @@ static const chr upperCharTable[] = { 0xa756, 0xa758, 0xa75a, 0xa75c, 0xa75e, 0xa760, 0xa762, 0xa764, 0xa766, 0xa768, 0xa76a, 0xa76c, 0xa76e, 0xa779, 0xa77b, 0xa77d, 0xa77e, 0xa780, 0xa782, 0xa784, 0xa786, 0xa78b, 0xa78d, 0xa790, 0xa792, 0xa796, 0xa798, - 0xa79a, 0xa79c, 0xa79e, 0xa7a0, 0xa7a2, 0xa7a4, 0xa7a6, 0xa7a8, 0xa7b0, - 0xa7b1 + 0xa79a, 0xa79c, 0xa79e, 0xa7a0, 0xa7a2, 0xa7a4, 0xa7a6, 0xa7a8, 0xa7b6 #if TCL_UTF_MAX > 4 ,0x1d49c, 0x1d49e, 0x1d49f, 0x1d4a2, 0x1d4a5, 0x1d4a6, 0x1d504, 0x1d505, 0x1d538, 0x1d539, 0x1d546, 0x1d7ca @@ -600,8 +609,8 @@ static const crange graphRangeTable[] = { {0x559, 0x55f}, {0x561, 0x587}, {0x58d, 0x58f}, {0x591, 0x5c7}, {0x5d0, 0x5ea}, {0x5f0, 0x5f4}, {0x606, 0x61b}, {0x61e, 0x6dc}, {0x6de, 0x70d}, {0x710, 0x74a}, {0x74d, 0x7b1}, {0x7c0, 0x7fa}, - {0x800, 0x82d}, {0x830, 0x83e}, {0x840, 0x85b}, {0x8a0, 0x8b2}, - {0x8e4, 0x983}, {0x985, 0x98c}, {0x993, 0x9a8}, {0x9aa, 0x9b0}, + {0x800, 0x82d}, {0x830, 0x83e}, {0x840, 0x85b}, {0x8a0, 0x8b4}, + {0x8e3, 0x983}, {0x985, 0x98c}, {0x993, 0x9a8}, {0x9aa, 0x9b0}, {0x9b6, 0x9b9}, {0x9bc, 0x9c4}, {0x9cb, 0x9ce}, {0x9df, 0x9e3}, {0x9e6, 0x9fb}, {0xa01, 0xa03}, {0xa05, 0xa0a}, {0xa13, 0xa28}, {0xa2a, 0xa30}, {0xa3e, 0xa42}, {0xa4b, 0xa4d}, {0xa59, 0xa5c}, @@ -614,66 +623,67 @@ static const crange graphRangeTable[] = { {0xba8, 0xbaa}, {0xbae, 0xbb9}, {0xbbe, 0xbc2}, {0xbc6, 0xbc8}, {0xbca, 0xbcd}, {0xbe6, 0xbfa}, {0xc00, 0xc03}, {0xc05, 0xc0c}, {0xc0e, 0xc10}, {0xc12, 0xc28}, {0xc2a, 0xc39}, {0xc3d, 0xc44}, - {0xc46, 0xc48}, {0xc4a, 0xc4d}, {0xc60, 0xc63}, {0xc66, 0xc6f}, - {0xc78, 0xc7f}, {0xc81, 0xc83}, {0xc85, 0xc8c}, {0xc8e, 0xc90}, - {0xc92, 0xca8}, {0xcaa, 0xcb3}, {0xcb5, 0xcb9}, {0xcbc, 0xcc4}, - {0xcc6, 0xcc8}, {0xcca, 0xccd}, {0xce0, 0xce3}, {0xce6, 0xcef}, - {0xd01, 0xd03}, {0xd05, 0xd0c}, {0xd0e, 0xd10}, {0xd12, 0xd3a}, - {0xd3d, 0xd44}, {0xd46, 0xd48}, {0xd4a, 0xd4e}, {0xd60, 0xd63}, - {0xd66, 0xd75}, {0xd79, 0xd7f}, {0xd85, 0xd96}, {0xd9a, 0xdb1}, - {0xdb3, 0xdbb}, {0xdc0, 0xdc6}, {0xdcf, 0xdd4}, {0xdd8, 0xddf}, - {0xde6, 0xdef}, {0xdf2, 0xdf4}, {0xe01, 0xe3a}, {0xe3f, 0xe5b}, - {0xe94, 0xe97}, {0xe99, 0xe9f}, {0xea1, 0xea3}, {0xead, 0xeb9}, - {0xebb, 0xebd}, {0xec0, 0xec4}, {0xec8, 0xecd}, {0xed0, 0xed9}, - {0xedc, 0xedf}, {0xf00, 0xf47}, {0xf49, 0xf6c}, {0xf71, 0xf97}, - {0xf99, 0xfbc}, {0xfbe, 0xfcc}, {0xfce, 0xfda}, {0x1000, 0x10c5}, - {0x10d0, 0x1248}, {0x124a, 0x124d}, {0x1250, 0x1256}, {0x125a, 0x125d}, - {0x1260, 0x1288}, {0x128a, 0x128d}, {0x1290, 0x12b0}, {0x12b2, 0x12b5}, - {0x12b8, 0x12be}, {0x12c2, 0x12c5}, {0x12c8, 0x12d6}, {0x12d8, 0x1310}, - {0x1312, 0x1315}, {0x1318, 0x135a}, {0x135d, 0x137c}, {0x1380, 0x1399}, - {0x13a0, 0x13f4}, {0x1400, 0x167f}, {0x1681, 0x169c}, {0x16a0, 0x16f8}, - {0x1700, 0x170c}, {0x170e, 0x1714}, {0x1720, 0x1736}, {0x1740, 0x1753}, - {0x1760, 0x176c}, {0x176e, 0x1770}, {0x1780, 0x17dd}, {0x17e0, 0x17e9}, - {0x17f0, 0x17f9}, {0x1800, 0x180d}, {0x1810, 0x1819}, {0x1820, 0x1877}, - {0x1880, 0x18aa}, {0x18b0, 0x18f5}, {0x1900, 0x191e}, {0x1920, 0x192b}, - {0x1930, 0x193b}, {0x1944, 0x196d}, {0x1970, 0x1974}, {0x1980, 0x19ab}, - {0x19b0, 0x19c9}, {0x19d0, 0x19da}, {0x19de, 0x1a1b}, {0x1a1e, 0x1a5e}, - {0x1a60, 0x1a7c}, {0x1a7f, 0x1a89}, {0x1a90, 0x1a99}, {0x1aa0, 0x1aad}, - {0x1ab0, 0x1abe}, {0x1b00, 0x1b4b}, {0x1b50, 0x1b7c}, {0x1b80, 0x1bf3}, - {0x1bfc, 0x1c37}, {0x1c3b, 0x1c49}, {0x1c4d, 0x1c7f}, {0x1cc0, 0x1cc7}, - {0x1cd0, 0x1cf6}, {0x1d00, 0x1df5}, {0x1dfc, 0x1f15}, {0x1f18, 0x1f1d}, - {0x1f20, 0x1f45}, {0x1f48, 0x1f4d}, {0x1f50, 0x1f57}, {0x1f5f, 0x1f7d}, - {0x1f80, 0x1fb4}, {0x1fb6, 0x1fc4}, {0x1fc6, 0x1fd3}, {0x1fd6, 0x1fdb}, - {0x1fdd, 0x1fef}, {0x1ff2, 0x1ff4}, {0x1ff6, 0x1ffe}, {0x2010, 0x2027}, - {0x2030, 0x205e}, {0x2074, 0x208e}, {0x2090, 0x209c}, {0x20a0, 0x20bd}, - {0x20d0, 0x20f0}, {0x2100, 0x2189}, {0x2190, 0x23fa}, {0x2400, 0x2426}, - {0x2440, 0x244a}, {0x2460, 0x2b73}, {0x2b76, 0x2b95}, {0x2b98, 0x2bb9}, - {0x2bbd, 0x2bc8}, {0x2bca, 0x2bd1}, {0x2c00, 0x2c2e}, {0x2c30, 0x2c5e}, - {0x2c60, 0x2cf3}, {0x2cf9, 0x2d25}, {0x2d30, 0x2d67}, {0x2d7f, 0x2d96}, - {0x2da0, 0x2da6}, {0x2da8, 0x2dae}, {0x2db0, 0x2db6}, {0x2db8, 0x2dbe}, - {0x2dc0, 0x2dc6}, {0x2dc8, 0x2dce}, {0x2dd0, 0x2dd6}, {0x2dd8, 0x2dde}, - {0x2de0, 0x2e42}, {0x2e80, 0x2e99}, {0x2e9b, 0x2ef3}, {0x2f00, 0x2fd5}, - {0x2ff0, 0x2ffb}, {0x3001, 0x303f}, {0x3041, 0x3096}, {0x3099, 0x30ff}, - {0x3105, 0x312d}, {0x3131, 0x318e}, {0x3190, 0x31ba}, {0x31c0, 0x31e3}, - {0x31f0, 0x321e}, {0x3220, 0x32fe}, {0x3300, 0x4db5}, {0x4dc0, 0x9fcc}, - {0xa000, 0xa48c}, {0xa490, 0xa4c6}, {0xa4d0, 0xa62b}, {0xa640, 0xa69d}, - {0xa69f, 0xa6f7}, {0xa700, 0xa78e}, {0xa790, 0xa7ad}, {0xa7f7, 0xa82b}, - {0xa830, 0xa839}, {0xa840, 0xa877}, {0xa880, 0xa8c4}, {0xa8ce, 0xa8d9}, - {0xa8e0, 0xa8fb}, {0xa900, 0xa953}, {0xa95f, 0xa97c}, {0xa980, 0xa9cd}, - {0xa9cf, 0xa9d9}, {0xa9de, 0xa9fe}, {0xaa00, 0xaa36}, {0xaa40, 0xaa4d}, - {0xaa50, 0xaa59}, {0xaa5c, 0xaac2}, {0xaadb, 0xaaf6}, {0xab01, 0xab06}, - {0xab09, 0xab0e}, {0xab11, 0xab16}, {0xab20, 0xab26}, {0xab28, 0xab2e}, - {0xab30, 0xab5f}, {0xabc0, 0xabed}, {0xabf0, 0xabf9}, {0xac00, 0xd7a3}, - {0xd7b0, 0xd7c6}, {0xd7cb, 0xd7fb}, {0xdc00, 0xdc3e}, {0xdc40, 0xdc7e}, - {0xdc80, 0xdcbe}, {0xdcc0, 0xdcfe}, {0xdd80, 0xddbe}, {0xddc0, 0xddfe}, - {0xde80, 0xdebe}, {0xdec0, 0xdefe}, {0xdf00, 0xdf3e}, {0xdf40, 0xdf7e}, + {0xc46, 0xc48}, {0xc4a, 0xc4d}, {0xc58, 0xc5a}, {0xc60, 0xc63}, + {0xc66, 0xc6f}, {0xc78, 0xc7f}, {0xc81, 0xc83}, {0xc85, 0xc8c}, + {0xc8e, 0xc90}, {0xc92, 0xca8}, {0xcaa, 0xcb3}, {0xcb5, 0xcb9}, + {0xcbc, 0xcc4}, {0xcc6, 0xcc8}, {0xcca, 0xccd}, {0xce0, 0xce3}, + {0xce6, 0xcef}, {0xd01, 0xd03}, {0xd05, 0xd0c}, {0xd0e, 0xd10}, + {0xd12, 0xd3a}, {0xd3d, 0xd44}, {0xd46, 0xd48}, {0xd4a, 0xd4e}, + {0xd5f, 0xd63}, {0xd66, 0xd75}, {0xd79, 0xd7f}, {0xd85, 0xd96}, + {0xd9a, 0xdb1}, {0xdb3, 0xdbb}, {0xdc0, 0xdc6}, {0xdcf, 0xdd4}, + {0xdd8, 0xddf}, {0xde6, 0xdef}, {0xdf2, 0xdf4}, {0xe01, 0xe3a}, + {0xe3f, 0xe5b}, {0xe94, 0xe97}, {0xe99, 0xe9f}, {0xea1, 0xea3}, + {0xead, 0xeb9}, {0xebb, 0xebd}, {0xec0, 0xec4}, {0xec8, 0xecd}, + {0xed0, 0xed9}, {0xedc, 0xedf}, {0xf00, 0xf47}, {0xf49, 0xf6c}, + {0xf71, 0xf97}, {0xf99, 0xfbc}, {0xfbe, 0xfcc}, {0xfce, 0xfda}, + {0x1000, 0x10c5}, {0x10d0, 0x1248}, {0x124a, 0x124d}, {0x1250, 0x1256}, + {0x125a, 0x125d}, {0x1260, 0x1288}, {0x128a, 0x128d}, {0x1290, 0x12b0}, + {0x12b2, 0x12b5}, {0x12b8, 0x12be}, {0x12c2, 0x12c5}, {0x12c8, 0x12d6}, + {0x12d8, 0x1310}, {0x1312, 0x1315}, {0x1318, 0x135a}, {0x135d, 0x137c}, + {0x1380, 0x1399}, {0x13a0, 0x13f5}, {0x13f8, 0x13fd}, {0x1400, 0x167f}, + {0x1681, 0x169c}, {0x16a0, 0x16f8}, {0x1700, 0x170c}, {0x170e, 0x1714}, + {0x1720, 0x1736}, {0x1740, 0x1753}, {0x1760, 0x176c}, {0x176e, 0x1770}, + {0x1780, 0x17dd}, {0x17e0, 0x17e9}, {0x17f0, 0x17f9}, {0x1800, 0x180d}, + {0x1810, 0x1819}, {0x1820, 0x1877}, {0x1880, 0x18aa}, {0x18b0, 0x18f5}, + {0x1900, 0x191e}, {0x1920, 0x192b}, {0x1930, 0x193b}, {0x1944, 0x196d}, + {0x1970, 0x1974}, {0x1980, 0x19ab}, {0x19b0, 0x19c9}, {0x19d0, 0x19da}, + {0x19de, 0x1a1b}, {0x1a1e, 0x1a5e}, {0x1a60, 0x1a7c}, {0x1a7f, 0x1a89}, + {0x1a90, 0x1a99}, {0x1aa0, 0x1aad}, {0x1ab0, 0x1abe}, {0x1b00, 0x1b4b}, + {0x1b50, 0x1b7c}, {0x1b80, 0x1bf3}, {0x1bfc, 0x1c37}, {0x1c3b, 0x1c49}, + {0x1c4d, 0x1c7f}, {0x1cc0, 0x1cc7}, {0x1cd0, 0x1cf6}, {0x1d00, 0x1df5}, + {0x1dfc, 0x1f15}, {0x1f18, 0x1f1d}, {0x1f20, 0x1f45}, {0x1f48, 0x1f4d}, + {0x1f50, 0x1f57}, {0x1f5f, 0x1f7d}, {0x1f80, 0x1fb4}, {0x1fb6, 0x1fc4}, + {0x1fc6, 0x1fd3}, {0x1fd6, 0x1fdb}, {0x1fdd, 0x1fef}, {0x1ff2, 0x1ff4}, + {0x1ff6, 0x1ffe}, {0x2010, 0x2027}, {0x2030, 0x205e}, {0x2074, 0x208e}, + {0x2090, 0x209c}, {0x20a0, 0x20be}, {0x20d0, 0x20f0}, {0x2100, 0x218b}, + {0x2190, 0x23fa}, {0x2400, 0x2426}, {0x2440, 0x244a}, {0x2460, 0x2b73}, + {0x2b76, 0x2b95}, {0x2b98, 0x2bb9}, {0x2bbd, 0x2bc8}, {0x2bca, 0x2bd1}, + {0x2bec, 0x2bef}, {0x2c00, 0x2c2e}, {0x2c30, 0x2c5e}, {0x2c60, 0x2cf3}, + {0x2cf9, 0x2d25}, {0x2d30, 0x2d67}, {0x2d7f, 0x2d96}, {0x2da0, 0x2da6}, + {0x2da8, 0x2dae}, {0x2db0, 0x2db6}, {0x2db8, 0x2dbe}, {0x2dc0, 0x2dc6}, + {0x2dc8, 0x2dce}, {0x2dd0, 0x2dd6}, {0x2dd8, 0x2dde}, {0x2de0, 0x2e42}, + {0x2e80, 0x2e99}, {0x2e9b, 0x2ef3}, {0x2f00, 0x2fd5}, {0x2ff0, 0x2ffb}, + {0x3001, 0x303f}, {0x3041, 0x3096}, {0x3099, 0x30ff}, {0x3105, 0x312d}, + {0x3131, 0x318e}, {0x3190, 0x31ba}, {0x31c0, 0x31e3}, {0x31f0, 0x321e}, + {0x3220, 0x32fe}, {0x3300, 0x4db5}, {0x4dc0, 0x9fd5}, {0xa000, 0xa48c}, + {0xa490, 0xa4c6}, {0xa4d0, 0xa62b}, {0xa640, 0xa6f7}, {0xa700, 0xa7ad}, + {0xa7b0, 0xa7b7}, {0xa7f7, 0xa82b}, {0xa830, 0xa839}, {0xa840, 0xa877}, + {0xa880, 0xa8c4}, {0xa8ce, 0xa8d9}, {0xa8e0, 0xa8fd}, {0xa900, 0xa953}, + {0xa95f, 0xa97c}, {0xa980, 0xa9cd}, {0xa9cf, 0xa9d9}, {0xa9de, 0xa9fe}, + {0xaa00, 0xaa36}, {0xaa40, 0xaa4d}, {0xaa50, 0xaa59}, {0xaa5c, 0xaac2}, + {0xaadb, 0xaaf6}, {0xab01, 0xab06}, {0xab09, 0xab0e}, {0xab11, 0xab16}, + {0xab20, 0xab26}, {0xab28, 0xab2e}, {0xab30, 0xab65}, {0xab70, 0xabed}, + {0xabf0, 0xabf9}, {0xac00, 0xd7a3}, {0xd7b0, 0xd7c6}, {0xd7cb, 0xd7fb}, + {0xdc00, 0xdc3e}, {0xdc40, 0xdc7e}, {0xdc80, 0xdcbe}, {0xdcc0, 0xdcfe}, + {0xdd00, 0xdd3e}, {0xdd40, 0xdd7e}, {0xdd80, 0xddbe}, {0xddc0, 0xddfe}, + {0xde00, 0xde3e}, {0xde40, 0xde7e}, {0xde80, 0xdebe}, {0xdec0, 0xdefe}, + {0xdf00, 0xdf3e}, {0xdf40, 0xdf7e}, {0xdf80, 0xdfbe}, {0xdfc0, 0xdffe}, {0xf900, 0xfa6d}, {0xfa70, 0xfad9}, {0xfb00, 0xfb06}, {0xfb13, 0xfb17}, {0xfb1d, 0xfb36}, {0xfb38, 0xfb3c}, {0xfb46, 0xfbc1}, {0xfbd3, 0xfd3f}, {0xfd50, 0xfd8f}, {0xfd92, 0xfdc7}, {0xfdf0, 0xfdfd}, {0xfe00, 0xfe19}, - {0xfe20, 0xfe2d}, {0xfe30, 0xfe52}, {0xfe54, 0xfe66}, {0xfe68, 0xfe6b}, - {0xfe70, 0xfe74}, {0xfe76, 0xfefc}, {0xff01, 0xffbe}, {0xffc2, 0xffc7}, - {0xffca, 0xffcf}, {0xffd2, 0xffd7}, {0xffda, 0xffdc}, {0xffe0, 0xffe6}, - {0xffe8, 0xffee} + {0xfe20, 0xfe52}, {0xfe54, 0xfe66}, {0xfe68, 0xfe6b}, {0xfe70, 0xfe74}, + {0xfe76, 0xfefc}, {0xff01, 0xffbe}, {0xffc2, 0xffc7}, {0xffca, 0xffcf}, + {0xffd2, 0xffd7}, {0xffda, 0xffdc}, {0xffe0, 0xffe6}, {0xffe8, 0xffee} #if TCL_UTF_MAX > 4 ,{0x10000, 0x1000b}, {0x1000d, 0x10026}, {0x10028, 0x1003a}, {0x1003f, 0x1004d}, {0x10050, 0x1005d}, {0x10080, 0x100fa}, {0x10100, 0x10102}, {0x10107, 0x10133}, @@ -683,45 +693,48 @@ static const crange graphRangeTable[] = { {0x10400, 0x1049d}, {0x104a0, 0x104a9}, {0x10500, 0x10527}, {0x10530, 0x10563}, {0x10600, 0x10736}, {0x10740, 0x10755}, {0x10760, 0x10767}, {0x10800, 0x10805}, {0x1080a, 0x10835}, {0x1083f, 0x10855}, {0x10857, 0x1089e}, {0x108a7, 0x108af}, - {0x10900, 0x1091b}, {0x1091f, 0x10939}, {0x10980, 0x109b7}, {0x10a00, 0x10a03}, - {0x10a0c, 0x10a13}, {0x10a15, 0x10a17}, {0x10a19, 0x10a33}, {0x10a38, 0x10a3a}, - {0x10a3f, 0x10a47}, {0x10a50, 0x10a58}, {0x10a60, 0x10a9f}, {0x10ac0, 0x10ae6}, - {0x10aeb, 0x10af6}, {0x10b00, 0x10b35}, {0x10b39, 0x10b55}, {0x10b58, 0x10b72}, - {0x10b78, 0x10b91}, {0x10b99, 0x10b9c}, {0x10ba9, 0x10baf}, {0x10c00, 0x10c48}, - {0x10e60, 0x10e7e}, {0x11000, 0x1104d}, {0x11052, 0x1106f}, {0x1107f, 0x110bc}, - {0x110be, 0x110c1}, {0x110d0, 0x110e8}, {0x110f0, 0x110f9}, {0x11100, 0x11134}, - {0x11136, 0x11143}, {0x11150, 0x11176}, {0x11180, 0x111c8}, {0x111d0, 0x111da}, - {0x111e1, 0x111f4}, {0x11200, 0x11211}, {0x11213, 0x1123d}, {0x112b0, 0x112ea}, - {0x112f0, 0x112f9}, {0x11301, 0x11303}, {0x11305, 0x1130c}, {0x11313, 0x11328}, - {0x1132a, 0x11330}, {0x11335, 0x11339}, {0x1133c, 0x11344}, {0x1134b, 0x1134d}, - {0x1135d, 0x11363}, {0x11366, 0x1136c}, {0x11370, 0x11374}, {0x11480, 0x114c7}, - {0x114d0, 0x114d9}, {0x11580, 0x115b5}, {0x115b8, 0x115c9}, {0x11600, 0x11644}, - {0x11650, 0x11659}, {0x11680, 0x116b7}, {0x116c0, 0x116c9}, {0x118a0, 0x118f2}, - {0x11ac0, 0x11af8}, {0x12000, 0x12398}, {0x12400, 0x1246e}, {0x12470, 0x12474}, - {0x13000, 0x1342e}, {0x16800, 0x16a38}, {0x16a40, 0x16a5e}, {0x16a60, 0x16a69}, - {0x16ad0, 0x16aed}, {0x16af0, 0x16af5}, {0x16b00, 0x16b45}, {0x16b50, 0x16b59}, - {0x16b5b, 0x16b61}, {0x16b63, 0x16b77}, {0x16b7d, 0x16b8f}, {0x16f00, 0x16f44}, - {0x16f50, 0x16f7e}, {0x16f8f, 0x16f9f}, {0x1bc00, 0x1bc6a}, {0x1bc70, 0x1bc7c}, - {0x1bc80, 0x1bc88}, {0x1bc90, 0x1bc99}, {0x1bc9c, 0x1bc9f}, {0x1d000, 0x1d0f5}, - {0x1d100, 0x1d126}, {0x1d129, 0x1d172}, {0x1d17b, 0x1d1dd}, {0x1d200, 0x1d245}, - {0x1d300, 0x1d356}, {0x1d360, 0x1d371}, {0x1d400, 0x1d454}, {0x1d456, 0x1d49c}, - {0x1d4a9, 0x1d4ac}, {0x1d4ae, 0x1d4b9}, {0x1d4bd, 0x1d4c3}, {0x1d4c5, 0x1d505}, - {0x1d507, 0x1d50a}, {0x1d50d, 0x1d514}, {0x1d516, 0x1d51c}, {0x1d51e, 0x1d539}, - {0x1d53b, 0x1d53e}, {0x1d540, 0x1d544}, {0x1d54a, 0x1d550}, {0x1d552, 0x1d6a5}, - {0x1d6a8, 0x1d7cb}, {0x1d7ce, 0x1d7ff}, {0x1e800, 0x1e8c4}, {0x1e8c7, 0x1e8d6}, + {0x108e0, 0x108f2}, {0x108fb, 0x1091b}, {0x1091f, 0x10939}, {0x10980, 0x109b7}, + {0x109bc, 0x109cf}, {0x109d2, 0x10a03}, {0x10a0c, 0x10a13}, {0x10a15, 0x10a17}, + {0x10a19, 0x10a33}, {0x10a38, 0x10a3a}, {0x10a3f, 0x10a47}, {0x10a50, 0x10a58}, + {0x10a60, 0x10a9f}, {0x10ac0, 0x10ae6}, {0x10aeb, 0x10af6}, {0x10b00, 0x10b35}, + {0x10b39, 0x10b55}, {0x10b58, 0x10b72}, {0x10b78, 0x10b91}, {0x10b99, 0x10b9c}, + {0x10ba9, 0x10baf}, {0x10c00, 0x10c48}, {0x10c80, 0x10cb2}, {0x10cc0, 0x10cf2}, + {0x10cfa, 0x10cff}, {0x10e60, 0x10e7e}, {0x11000, 0x1104d}, {0x11052, 0x1106f}, + {0x1107f, 0x110bc}, {0x110be, 0x110c1}, {0x110d0, 0x110e8}, {0x110f0, 0x110f9}, + {0x11100, 0x11134}, {0x11136, 0x11143}, {0x11150, 0x11176}, {0x11180, 0x111cd}, + {0x111d0, 0x111df}, {0x111e1, 0x111f4}, {0x11200, 0x11211}, {0x11213, 0x1123d}, + {0x11280, 0x11286}, {0x1128a, 0x1128d}, {0x1128f, 0x1129d}, {0x1129f, 0x112a9}, + {0x112b0, 0x112ea}, {0x112f0, 0x112f9}, {0x11300, 0x11303}, {0x11305, 0x1130c}, + {0x11313, 0x11328}, {0x1132a, 0x11330}, {0x11335, 0x11339}, {0x1133c, 0x11344}, + {0x1134b, 0x1134d}, {0x1135d, 0x11363}, {0x11366, 0x1136c}, {0x11370, 0x11374}, + {0x11480, 0x114c7}, {0x114d0, 0x114d9}, {0x11580, 0x115b5}, {0x115b8, 0x115dd}, + {0x11600, 0x11644}, {0x11650, 0x11659}, {0x11680, 0x116b7}, {0x116c0, 0x116c9}, + {0x11700, 0x11719}, {0x1171d, 0x1172b}, {0x11730, 0x1173f}, {0x118a0, 0x118f2}, + {0x11ac0, 0x11af8}, {0x12000, 0x12399}, {0x12400, 0x1246e}, {0x12470, 0x12474}, + {0x12480, 0x12543}, {0x13000, 0x1342e}, {0x14400, 0x14646}, {0x16800, 0x16a38}, + {0x16a40, 0x16a5e}, {0x16a60, 0x16a69}, {0x16ad0, 0x16aed}, {0x16af0, 0x16af5}, + {0x16b00, 0x16b45}, {0x16b50, 0x16b59}, {0x16b5b, 0x16b61}, {0x16b63, 0x16b77}, + {0x16b7d, 0x16b8f}, {0x16f00, 0x16f44}, {0x16f50, 0x16f7e}, {0x16f8f, 0x16f9f}, + {0x1bc00, 0x1bc6a}, {0x1bc70, 0x1bc7c}, {0x1bc80, 0x1bc88}, {0x1bc90, 0x1bc99}, + {0x1bc9c, 0x1bc9f}, {0x1d000, 0x1d0f5}, {0x1d100, 0x1d126}, {0x1d129, 0x1d172}, + {0x1d17b, 0x1d1e8}, {0x1d200, 0x1d245}, {0x1d300, 0x1d356}, {0x1d360, 0x1d371}, + {0x1d400, 0x1d454}, {0x1d456, 0x1d49c}, {0x1d4a9, 0x1d4ac}, {0x1d4ae, 0x1d4b9}, + {0x1d4bd, 0x1d4c3}, {0x1d4c5, 0x1d505}, {0x1d507, 0x1d50a}, {0x1d50d, 0x1d514}, + {0x1d516, 0x1d51c}, {0x1d51e, 0x1d539}, {0x1d53b, 0x1d53e}, {0x1d540, 0x1d544}, + {0x1d54a, 0x1d550}, {0x1d552, 0x1d6a5}, {0x1d6a8, 0x1d7cb}, {0x1d7ce, 0x1da8b}, + {0x1da9b, 0x1da9f}, {0x1daa1, 0x1daaf}, {0x1e800, 0x1e8c4}, {0x1e8c7, 0x1e8d6}, {0x1ee00, 0x1ee03}, {0x1ee05, 0x1ee1f}, {0x1ee29, 0x1ee32}, {0x1ee34, 0x1ee37}, {0x1ee4d, 0x1ee4f}, {0x1ee67, 0x1ee6a}, {0x1ee6c, 0x1ee72}, {0x1ee74, 0x1ee77}, {0x1ee79, 0x1ee7c}, {0x1ee80, 0x1ee89}, {0x1ee8b, 0x1ee9b}, {0x1eea1, 0x1eea3}, {0x1eea5, 0x1eea9}, {0x1eeab, 0x1eebb}, {0x1f000, 0x1f02b}, {0x1f030, 0x1f093}, {0x1f0a0, 0x1f0ae}, {0x1f0b1, 0x1f0bf}, {0x1f0c1, 0x1f0cf}, {0x1f0d1, 0x1f0f5}, {0x1f100, 0x1f10c}, {0x1f110, 0x1f12e}, {0x1f130, 0x1f16b}, {0x1f170, 0x1f19a}, - {0x1f1e6, 0x1f202}, {0x1f210, 0x1f23a}, {0x1f240, 0x1f248}, {0x1f300, 0x1f32c}, - {0x1f330, 0x1f37d}, {0x1f380, 0x1f3ce}, {0x1f3d4, 0x1f3f7}, {0x1f400, 0x1f4fe}, - {0x1f500, 0x1f54a}, {0x1f550, 0x1f579}, {0x1f57b, 0x1f5a3}, {0x1f5a5, 0x1f642}, - {0x1f645, 0x1f6cf}, {0x1f6e0, 0x1f6ec}, {0x1f6f0, 0x1f6f3}, {0x1f700, 0x1f773}, - {0x1f780, 0x1f7d4}, {0x1f800, 0x1f80b}, {0x1f810, 0x1f847}, {0x1f850, 0x1f859}, - {0x1f860, 0x1f887}, {0x1f890, 0x1f8ad}, {0x20000, 0x2a6d6}, {0x2a700, 0x2b734}, - {0x2b740, 0x2b81d}, {0x2f800, 0x2fa1d}, {0xe0100, 0xe01ef} + {0x1f1e6, 0x1f202}, {0x1f210, 0x1f23a}, {0x1f240, 0x1f248}, {0x1f300, 0x1f579}, + {0x1f57b, 0x1f5a3}, {0x1f5a5, 0x1f6d0}, {0x1f6e0, 0x1f6ec}, {0x1f6f0, 0x1f6f3}, + {0x1f700, 0x1f773}, {0x1f780, 0x1f7d4}, {0x1f800, 0x1f80b}, {0x1f810, 0x1f847}, + {0x1f850, 0x1f859}, {0x1f860, 0x1f887}, {0x1f890, 0x1f8ad}, {0x1f910, 0x1f918}, + {0x1f980, 0x1f984}, {0x20000, 0x2a6d6}, {0x2a700, 0x2b734}, {0x2b740, 0x2b81d}, + {0x2b820, 0x2cea1}, {0x2f800, 0x2fa1d}, {0xe0100, 0xe01ef} #endif }; @@ -731,23 +744,23 @@ static const chr graphCharTable[] = { 0x38c, 0x589, 0x58a, 0x85e, 0x98f, 0x990, 0x9b2, 0x9c7, 0x9c8, 0x9d7, 0x9dc, 0x9dd, 0xa0f, 0xa10, 0xa32, 0xa33, 0xa35, 0xa36, 0xa38, 0xa39, 0xa3c, 0xa47, 0xa48, 0xa51, 0xa5e, 0xab2, 0xab3, - 0xad0, 0xb0f, 0xb10, 0xb32, 0xb33, 0xb47, 0xb48, 0xb56, 0xb57, - 0xb5c, 0xb5d, 0xb82, 0xb83, 0xb99, 0xb9a, 0xb9c, 0xb9e, 0xb9f, - 0xba3, 0xba4, 0xbd0, 0xbd7, 0xc55, 0xc56, 0xc58, 0xc59, 0xcd5, - 0xcd6, 0xcde, 0xcf1, 0xcf2, 0xd57, 0xd82, 0xd83, 0xdbd, 0xdca, - 0xdd6, 0xe81, 0xe82, 0xe84, 0xe87, 0xe88, 0xe8a, 0xe8d, 0xea5, - 0xea7, 0xeaa, 0xeab, 0xec6, 0x10c7, 0x10cd, 0x1258, 0x12c0, 0x1772, - 0x1773, 0x1940, 0x1cf8, 0x1cf9, 0x1f59, 0x1f5b, 0x1f5d, 0x2070, 0x2071, - 0x2d27, 0x2d2d, 0x2d6f, 0x2d70, 0xa7b0, 0xa7b1, 0xab64, 0xab65, 0xfb3e, - 0xfb40, 0xfb41, 0xfb43, 0xfb44, 0xfffc, 0xfffd + 0xad0, 0xaf9, 0xb0f, 0xb10, 0xb32, 0xb33, 0xb47, 0xb48, 0xb56, + 0xb57, 0xb5c, 0xb5d, 0xb82, 0xb83, 0xb99, 0xb9a, 0xb9c, 0xb9e, + 0xb9f, 0xba3, 0xba4, 0xbd0, 0xbd7, 0xc55, 0xc56, 0xcd5, 0xcd6, + 0xcde, 0xcf1, 0xcf2, 0xd57, 0xd82, 0xd83, 0xdbd, 0xdca, 0xdd6, + 0xe81, 0xe82, 0xe84, 0xe87, 0xe88, 0xe8a, 0xe8d, 0xea5, 0xea7, + 0xeaa, 0xeab, 0xec6, 0x10c7, 0x10cd, 0x1258, 0x12c0, 0x1772, 0x1773, + 0x1940, 0x1cf8, 0x1cf9, 0x1f59, 0x1f5b, 0x1f5d, 0x2070, 0x2071, 0x2d27, + 0x2d2d, 0x2d6f, 0x2d70, 0xfb3e, 0xfb40, 0xfb41, 0xfb43, 0xfb44, 0xfffc, + 0xfffd #if TCL_UTF_MAX > 4 - ,0x1003c, 0x1003d, 0x101a0, 0x1056f, 0x10808, 0x10837, 0x10838, 0x1083c, 0x1093f, - 0x109be, 0x109bf, 0x10a05, 0x10a06, 0x111cd, 0x1130f, 0x11310, 0x11332, 0x11333, - 0x11347, 0x11348, 0x11357, 0x118ff, 0x16a6e, 0x16a6f, 0x1b000, 0x1b001, 0x1d49e, - 0x1d49f, 0x1d4a2, 0x1d4a5, 0x1d4a6, 0x1d4bb, 0x1d546, 0x1ee21, 0x1ee22, 0x1ee24, - 0x1ee27, 0x1ee39, 0x1ee3b, 0x1ee42, 0x1ee47, 0x1ee49, 0x1ee4b, 0x1ee51, 0x1ee52, - 0x1ee54, 0x1ee57, 0x1ee59, 0x1ee5b, 0x1ee5d, 0x1ee5f, 0x1ee61, 0x1ee62, 0x1ee64, - 0x1ee7e, 0x1eef0, 0x1eef1, 0x1f250, 0x1f251 + ,0x1003c, 0x1003d, 0x101a0, 0x1056f, 0x10808, 0x10837, 0x10838, 0x1083c, 0x108f4, + 0x108f5, 0x1093f, 0x10a05, 0x10a06, 0x11288, 0x1130f, 0x11310, 0x11332, 0x11333, + 0x11347, 0x11348, 0x11350, 0x11357, 0x118ff, 0x16a6e, 0x16a6f, 0x1b000, 0x1b001, + 0x1d49e, 0x1d49f, 0x1d4a2, 0x1d4a5, 0x1d4a6, 0x1d4bb, 0x1d546, 0x1ee21, 0x1ee22, + 0x1ee24, 0x1ee27, 0x1ee39, 0x1ee3b, 0x1ee42, 0x1ee47, 0x1ee49, 0x1ee4b, 0x1ee51, + 0x1ee52, 0x1ee54, 0x1ee57, 0x1ee59, 0x1ee5b, 0x1ee5d, 0x1ee5f, 0x1ee61, 0x1ee62, + 0x1ee64, 0x1ee7e, 0x1eef0, 0x1eef1, 0x1f250, 0x1f251, 0x1f9c0 #endif }; diff --git a/generic/regc_nfa.c b/generic/regc_nfa.c index 1f0583e..0e0343e 100644 --- a/generic/regc_nfa.c +++ b/generic/regc_nfa.c @@ -34,6 +34,9 @@ #define NISERR() VISERR(nfa->v) #define NERR(e) VERR(nfa->v, (e)) +#define STACK_TOO_DEEP(x) (0) +#define CANCEL_REQUESTED(x) (0) +#define REG_CANCEL 777 /* - newnfa - set up an NFA @@ -49,6 +52,7 @@ newnfa( nfa = (struct nfa *) MALLOC(sizeof(struct nfa)); if (nfa == NULL) { + ERR(REG_ESPACE); return NULL; } @@ -58,7 +62,6 @@ newnfa( nfa->nstates = 0; nfa->cm = cm; nfa->v = v; - nfa->size = 0; nfa->bos[0] = nfa->bos[1] = COLORLESS; nfa->eos[0] = nfa->eos[1] = COLORLESS; nfa->parent = parent; /* Precedes newfstate so parent is valid. */ @@ -86,61 +89,6 @@ newnfa( } /* - - TooManyStates - checks if the max states exceeds the compile-time value - ^ static int TooManyStates(struct nfa *); - */ -static int -TooManyStates( - struct nfa *nfa) -{ - struct nfa *parent = nfa->parent; - size_t sz = nfa->size; - - while (parent != NULL) { - sz = parent->size; - parent = parent->parent; - } - if (sz > REG_MAX_STATES) { - return 1; - } - return 0; -} - -/* - - IncrementSize - increases the tracked size of the NFA and its parents. - ^ static void IncrementSize(struct nfa *); - */ -static void -IncrementSize( - struct nfa *nfa) -{ - struct nfa *parent = nfa->parent; - - nfa->size++; - while (parent != NULL) { - parent->size++; - parent = parent->parent; - } -} - -/* - - DecrementSize - increases the tracked size of the NFA and its parents. - ^ static void DecrementSize(struct nfa *); - */ -static void -DecrementSize( - struct nfa *nfa) -{ - struct nfa *parent = nfa->parent; - - nfa->size--; - while (parent != NULL) { - parent->size--; - parent = parent->parent; - } -} - -/* - freenfa - free an entire NFA ^ static void freenfa(struct nfa *); */ @@ -176,20 +124,20 @@ newstate( { struct state *s; - if (TooManyStates(nfa)) { - /* XXX: add specific error for this */ - NERR(REG_ETOOBIG); - return NULL; - } if (nfa->free != NULL) { s = nfa->free; nfa->free = s->next; } else { + if (nfa->v->spaceused >= REG_MAX_COMPILE_SPACE) { + NERR(REG_ETOOBIG); + return NULL; + } s = (struct state *) MALLOC(sizeof(struct state)); if (s == NULL) { NERR(REG_ESPACE); return NULL; } + nfa->v->spaceused += sizeof(struct state); s->oas.next = NULL; s->free = NULL; s->noas = 0; @@ -213,12 +161,6 @@ newstate( } s->prev = nfa->slast; nfa->slast = s; - - /* - * Track the current size and the parent size. - */ - - IncrementSize(nfa); return s; } @@ -289,7 +231,6 @@ freestate( s->prev = NULL; s->next = nfa->free; /* don't delete it, put it on the free list */ nfa->free = s; - DecrementSize(nfa); } /* @@ -308,11 +249,13 @@ destroystate( for (ab=s->oas.next ; ab!=NULL ; ab=abnext) { abnext = ab->next; FREE(ab); + nfa->v->spaceused -= sizeof(struct arcbatch); } s->ins = NULL; s->outs = NULL; s->next = NULL; FREE(s); + nfa->v->spaceused -= sizeof(struct state); } /* @@ -320,6 +263,10 @@ destroystate( ^ static void newarc(struct nfa *, int, pcolor, struct state *, ^ struct state *); */ +/* + * This function checks to make sure that no duplicate arcs are created. + * In general we never want duplicates. + */ static void newarc( struct nfa *nfa, @@ -332,16 +279,42 @@ newarc( assert(from != NULL && to != NULL); - /* - * Check for duplicates. - */ - - for (a=from->outs ; a!=NULL ; a=a->outchain) { - if (a->to == to && a->co == co && a->type == t) { - return; + /* check for duplicate arc, using whichever chain is shorter */ + if (from->nouts <= to->nins) { + for (a = from->outs; a != NULL; a = a->outchain) { + if (a->to == to && a->co == co && a->type == t) { + return; + } + } + } else { + for (a = to->ins; a != NULL; a = a->inchain) { + if (a->from == from && a->co == co && a->type == t) { + return; + } } } + + /* no dup, so create the arc */ + createarc(nfa, t, co, from, to); +} +/* + * createarc - create a new arc within an NFA + * + * This function must *only* be used after verifying that there is no existing + * identical arc (same type/color/from/to). + */ +static void +createarc( + struct nfa * nfa, + int t, + pcolor co, + struct state * from, + struct state * to) +{ + struct arc *a; + + /* the arc is physically allocated within its from-state */ a = allocarc(nfa, from); if (NISERR()) { return; @@ -354,15 +327,21 @@ newarc( a->from = from; /* - * Put the new arc on the beginning, not the end, of the chains. Not only - * is this easier, it has the very useful side effect that deleting the - * most-recently-added arc is the cheapest case rather than the most - * expensive one. + * Put the new arc on the beginning, not the end, of the chains; it's + * simpler here, and freearc() is the same cost either way. See also the + * logic in moveins() and its cohorts, as well as fixempties(). */ - a->inchain = to->ins; + a->inchainRev = NULL; + if (to->ins) { + to->ins->inchainRev = a; + } to->ins = a; a->outchain = from->outs; + a->outchainRev = NULL; + if (from->outs) { + from->outs->outchainRev = a; + } from->outs = a; from->nouts++; @@ -399,14 +378,19 @@ allocarc( */ if (s->free == NULL) { - struct arcbatch *newAb = (struct arcbatch *) - MALLOC(sizeof(struct arcbatch)); + struct arcbatch *newAb; int i; + if (nfa->v->spaceused >= REG_MAX_COMPILE_SPACE) { + NERR(REG_ETOOBIG); + return NULL; + } + newAb = (struct arcbatch *) MALLOC(sizeof(struct arcbatch)); if (newAb == NULL) { NERR(REG_ESPACE); return NULL; } + nfa->v->spaceused += sizeof(struct arcbatch); newAb->next = s->oas.next; s->oas.next = newAb; @@ -435,7 +419,7 @@ freearc( { struct state *from = victim->from; struct state *to = victim->to; - struct arc *a; + struct arc *predecessor; assert(victim->type != 0); @@ -452,16 +436,17 @@ freearc( */ assert(from != NULL); - assert(from->outs != NULL); - a = from->outs; - if (a == victim) { /* simple case: first in chain */ + predecessor = victim->outchainRev; + if (predecessor == NULL) { + assert(from->outs == victim); from->outs = victim->outchain; } else { - for (; a!=NULL && a->outchain!=victim ; a=a->outchain) { - continue; - } - assert(a != NULL); - a->outchain = victim->outchain; + assert(predecessor->outchain == victim); + predecessor->outchain = victim->outchain; + } + if (victim->outchain != NULL) { + assert(victim->outchain->outchainRev == victim); + victim->outchain->outchainRev = predecessor; } from->nouts--; @@ -470,86 +455,95 @@ freearc( */ assert(to != NULL); - assert(to->ins != NULL); - a = to->ins; - if (a == victim) { /* simple case: first in chain */ + predecessor = victim->inchainRev; + if (predecessor == NULL) { + assert(to->ins == victim); to->ins = victim->inchain; } else { - for (; a->inchain!=victim ; a=a->inchain) { - assert(a->inchain != NULL); - continue; - } - a->inchain = victim->inchain; + assert(predecessor->inchain == victim); + predecessor->inchain = victim->inchain; + } + if (victim->inchain != NULL) { + assert(victim->inchain->inchainRev == victim); + victim->inchain->inchainRev = predecessor; } to->nins--; /* - * Clean up and place on free list. + * Clean up and place on from-state's free list. */ victim->type = 0; victim->from = NULL; /* precautions... */ victim->to = NULL; victim->inchain = NULL; + victim->inchainRev = NULL; victim->outchain = NULL; + victim->outchainRev = NULL; victim->freechain = from->free; from->free = victim; } - + /* - - hasnonemptyout - Does state have a non-EMPTY out arc? - ^ static int hasnonemptyout(struct state *); + * changearctarget - flip an arc to have a different to state + * + * Caller must have verified that there is no pre-existing duplicate arc. + * + * Note that because we store arcs in their from state, we can't easily have + * a similar changearcsource function. */ -static int -hasnonemptyout( - struct state *s) +static void +changearctarget(struct arc * a, struct state * newto) { - struct arc *a; + struct state *oldto = a->to; + struct arc *predecessor; - for (a = s->outs; a != NULL; a = a->outchain) { - if (a->type != EMPTY) { - return 1; - } + assert(oldto != newto); + + /* take it off old target's in-chain */ + assert(oldto != NULL); + predecessor = a->inchainRev; + if (predecessor == NULL) { + assert(oldto->ins == a); + oldto->ins = a->inchain; + } else { + assert(predecessor->inchain == a); + predecessor->inchain = a->inchain; } - return 0; -} - -/* - - nonemptyouts - count non-EMPTY out arcs of a state - ^ static int nonemptyouts(struct state *); - */ -static int -nonemptyouts( - struct state *s) -{ - int n = 0; - struct arc *a; + if (a->inchain != NULL) { + assert(a->inchain->inchainRev == a); + a->inchain->inchainRev = predecessor; + } + oldto->nins--; - for (a = s->outs; a != NULL; a = a->outchain) { - if (a->type != EMPTY) { - n++; - } + a->to = newto; + + /* prepend it to new target's in-chain */ + a->inchain = newto->ins; + a->inchainRev = NULL; + if (newto->ins) { + newto->ins->inchainRev = a; } - return n; + newto->ins = a; + newto->nins++; } /* - - nonemptyins - count non-EMPTY in arcs of a state - ^ static int nonemptyins(struct state *); + - hasnonemptyout - Does state have a non-EMPTY out arc? + ^ static int hasnonemptyout(struct state *); */ static int -nonemptyins( +hasnonemptyout( struct state *s) { - int n = 0; struct arc *a; - for (a = s->ins; a != NULL; a = a->inchain) { + for (a = s->outs; a != NULL; a = a->outchain) { if (a->type != EMPTY) { - n++; + return 1; } } - return n; + return 0; } /* @@ -587,13 +581,181 @@ cparc( { newarc(nfa, oa->type, oa->co, from, to); } + +/* + * sortins - sort the in arcs of a state by from/color/type + */ +static void +sortins( + struct nfa * nfa, + struct state * s) +{ + struct arc **sortarray; + struct arc *a; + int n = s->nins; + int i; + + if (n <= 1) { + return; /* nothing to do */ + } + /* make an array of arc pointers ... */ + sortarray = (struct arc **) MALLOC(n * sizeof(struct arc *)); + if (sortarray == NULL) { + NERR(REG_ESPACE); + return; + } + i = 0; + for (a = s->ins; a != NULL; a = a->inchain) { + sortarray[i++] = a; + } + assert(i == n); + /* ... sort the array */ + qsort(sortarray, n, sizeof(struct arc *), sortins_cmp); + /* ... and rebuild arc list in order */ + /* it seems worth special-casing first and last items to simplify loop */ + a = sortarray[0]; + s->ins = a; + a->inchain = sortarray[1]; + a->inchainRev = NULL; + for (i = 1; i < n - 1; i++) { + a = sortarray[i]; + a->inchain = sortarray[i + 1]; + a->inchainRev = sortarray[i - 1]; + } + a = sortarray[i]; + a->inchain = NULL; + a->inchainRev = sortarray[i - 1]; + FREE(sortarray); +} + +static int +sortins_cmp( + const void *a, + const void *b) +{ + const struct arc *aa = *((const struct arc * const *) a); + const struct arc *bb = *((const struct arc * const *) b); + + /* we check the fields in the order they are most likely to be different */ + if (aa->from->no < bb->from->no) { + return -1; + } + if (aa->from->no > bb->from->no) { + return 1; + } + if (aa->co < bb->co) { + return -1; + } + if (aa->co > bb->co) { + return 1; + } + if (aa->type < bb->type) { + return -1; + } + if (aa->type > bb->type) { + return 1; + } + return 0; +} + +/* + * sortouts - sort the out arcs of a state by to/color/type + */ +static void +sortouts( + struct nfa * nfa, + struct state * s) +{ + struct arc **sortarray; + struct arc *a; + int n = s->nouts; + int i; + + if (n <= 1) { + return; /* nothing to do */ + } + /* make an array of arc pointers ... */ + sortarray = (struct arc **) MALLOC(n * sizeof(struct arc *)); + if (sortarray == NULL) { + NERR(REG_ESPACE); + return; + } + i = 0; + for (a = s->outs; a != NULL; a = a->outchain) { + sortarray[i++] = a; + } + assert(i == n); + /* ... sort the array */ + qsort(sortarray, n, sizeof(struct arc *), sortouts_cmp); + /* ... and rebuild arc list in order */ + /* it seems worth special-casing first and last items to simplify loop */ + a = sortarray[0]; + s->outs = a; + a->outchain = sortarray[1]; + a->outchainRev = NULL; + for (i = 1; i < n - 1; i++) { + a = sortarray[i]; + a->outchain = sortarray[i + 1]; + a->outchainRev = sortarray[i - 1]; + } + a = sortarray[i]; + a->outchain = NULL; + a->outchainRev = sortarray[i - 1]; + FREE(sortarray); +} + +static int +sortouts_cmp( + const void *a, + const void *b) +{ + const struct arc *aa = *((const struct arc * const *) a); + const struct arc *bb = *((const struct arc * const *) b); + + /* we check the fields in the order they are most likely to be different */ + if (aa->to->no < bb->to->no) { + return -1; + } + if (aa->to->no > bb->to->no) { + return 1; + } + if (aa->co < bb->co) { + return -1; + } + if (aa->co > bb->co) { + return 1; + } + if (aa->type < bb->type) { + return -1; + } + if (aa->type > bb->type) { + return 1; + } + return 0; +} + +/* + * Common decision logic about whether to use arc-by-arc operations or + * sort/merge. If there's just a few source arcs we cannot recoup the + * cost of sorting the destination arc list, no matter how large it is. + * Otherwise, limit the number of arc-by-arc comparisons to about 1000 + * (a somewhat arbitrary choice, but the breakeven point would probably + * be machine dependent anyway). + */ +#define BULK_ARC_OP_USE_SORT(nsrcarcs, ndestarcs) \ + ((nsrcarcs) < 4 ? 0 : ((nsrcarcs) > 32 || (ndestarcs) > 32)) /* - moveins - move all in arcs of a state to another state * You might think this could be done better by just updating the - * existing arcs, and you would be right if it weren't for the desire + * existing arcs, and you would be right if it weren't for the need * for duplicate suppression, which makes it easier to just make new * ones to exploit the suppression built into newarc. + * + * However, if we have a whole lot of arcs to deal with, retail duplicate + * checks become too slow. In that case we proceed by sorting and merging + * the arc lists, and then we can indeed just update the arcs in-place. + * ^ static void moveins(struct nfa *, struct state *, struct state *); */ static void @@ -602,38 +764,253 @@ moveins( struct state *oldState, struct state *newState) { - struct arc *a; - assert(oldState != newState); - while ((a = oldState->ins) != NULL) { - cparc(nfa, a, a->from, newState); - freearc(nfa, a); + if (!BULK_ARC_OP_USE_SORT(oldState->nins, newState->nins)) { + /* With not too many arcs, just do them one at a time */ + struct arc *a; + + while ((a = oldState->ins) != NULL) { + cparc(nfa, a, a->from, newState); + freearc(nfa, a); + } + } else { + /* + * With many arcs, use a sort-merge approach. Note changearctarget() + * will put the arc onto the front of newState's chain, so it does not + * break our walk through the sorted part of the chain. + */ + struct arc *oa; + struct arc *na; + + /* + * Because we bypass newarc() in this code path, we'd better include a + * cancel check. + */ + if (CANCEL_REQUESTED(nfa->v->re)) { + NERR(REG_CANCEL); + return; + } + + sortins(nfa, oldState); + sortins(nfa, newState); + if (NISERR()) { + return; /* might have failed to sort */ + } + oa = oldState->ins; + na = newState->ins; + while (oa != NULL && na != NULL) { + struct arc *a = oa; + + switch (sortins_cmp(&oa, &na)) { + case -1: + /* newState does not have anything matching oa */ + oa = oa->inchain; + + /* + * Rather than doing createarc+freearc, we can just unlink + * and relink the existing arc struct. + */ + changearctarget(a, newState); + break; + case 0: + /* match, advance in both lists */ + oa = oa->inchain; + na = na->inchain; + /* ... and drop duplicate arc from oldState */ + freearc(nfa, a); + break; + case +1: + /* advance only na; oa might have a match later */ + na = na->inchain; + break; + default: + assert(NOTREACHED); + } + } + while (oa != NULL) { + /* newState does not have anything matching oa */ + struct arc *a = oa; + + oa = oa->inchain; + changearctarget(a, newState); + } } + assert(oldState->nins == 0); assert(oldState->ins == NULL); } /* - copyins - copy in arcs of a state to another state - * Either all arcs, or only non-empty ones as determined by all value. ^ static VOID copyins(struct nfa *, struct state *, struct state *, int); */ static void copyins( struct nfa *nfa, struct state *oldState, - struct state *newState, - int all) + struct state *newState) { - struct arc *a; - assert(oldState != newState); - for (a=oldState->ins ; a!=NULL ; a=a->inchain) { - if (all || a->type != EMPTY) { + if (!BULK_ARC_OP_USE_SORT(oldState->nins, newState->nins)) { + /* With not too many arcs, just do them one at a time */ + struct arc *a; + + for (a = oldState->ins; a != NULL; a = a->inchain) { cparc(nfa, a, a->from, newState); } + } else { + /* + * With many arcs, use a sort-merge approach. Note that createarc() + * will put new arcs onto the front of newState's chain, so it does + * not break our walk through the sorted part of the chain. + */ + struct arc *oa; + struct arc *na; + + /* + * Because we bypass newarc() in this code path, we'd better include a + * cancel check. + */ + if (CANCEL_REQUESTED(nfa->v->re)) { + NERR(REG_CANCEL); + return; + } + + sortins(nfa, oldState); + sortins(nfa, newState); + if (NISERR()) { + return; /* might have failed to sort */ + } + oa = oldState->ins; + na = newState->ins; + while (oa != NULL && na != NULL) { + struct arc *a = oa; + + switch (sortins_cmp(&oa, &na)) { + case -1: + /* newState does not have anything matching oa */ + oa = oa->inchain; + createarc(nfa, a->type, a->co, a->from, newState); + break; + case 0: + /* match, advance in both lists */ + oa = oa->inchain; + na = na->inchain; + break; + case +1: + /* advance only na; oa might have a match later */ + na = na->inchain; + break; + default: + assert(NOTREACHED); + } + } + while (oa != NULL) { + /* newState does not have anything matching oa */ + struct arc *a = oa; + + oa = oa->inchain; + createarc(nfa, a->type, a->co, a->from, newState); + } + } +} + +/* + * mergeins - merge a list of inarcs into a state + * + * This is much like copyins, but the source arcs are listed in an array, + * and are not guaranteed unique. It's okay to clobber the array contents. + */ +static void +mergeins( + struct nfa * nfa, + struct state * s, + struct arc ** arcarray, + int arccount) +{ + struct arc *na; + int i; + int j; + + if (arccount <= 0) { + return; + } + + /* + * Because we bypass newarc() in this code path, we'd better include a + * cancel check. + */ + if (CANCEL_REQUESTED(nfa->v->re)) { + NERR(REG_CANCEL); + return; + } + + /* Sort existing inarcs as well as proposed new ones */ + sortins(nfa, s); + if (NISERR()) { + return; /* might have failed to sort */ + } + + qsort(arcarray, arccount, sizeof(struct arc *), sortins_cmp); + + /* + * arcarray very likely includes dups, so we must eliminate them. (This + * could be folded into the next loop, but it's not worth the trouble.) + */ + j = 0; + for (i = 1; i < arccount; i++) { + switch (sortins_cmp(&arcarray[j], &arcarray[i])) { + case -1: + /* non-dup */ + arcarray[++j] = arcarray[i]; + break; + case 0: + /* dup */ + break; + default: + /* trouble */ + assert(NOTREACHED); + } + } + arccount = j + 1; + + /* + * Now merge into s' inchain. Note that createarc() will put new arcs + * onto the front of s's chain, so it does not break our walk through the + * sorted part of the chain. + */ + i = 0; + na = s->ins; + while (i < arccount && na != NULL) { + struct arc *a = arcarray[i]; + + switch (sortins_cmp(&a, &na)) { + case -1: + /* s does not have anything matching a */ + createarc(nfa, a->type, a->co, a->from, s); + i++; + break; + case 0: + /* match, advance in both lists */ + i++; + na = na->inchain; + break; + case +1: + /* advance only na; array might have a match later */ + na = na->inchain; + break; + default: + assert(NOTREACHED); + } + } + while (i < arccount) { + /* s does not have anything matching a */ + struct arc *a = arcarray[i]; + + createarc(nfa, a->type, a->co, a->from, s); + i++; } } @@ -647,36 +1024,153 @@ moveouts( struct state *oldState, struct state *newState) { - struct arc *a; - assert(oldState != newState); - while ((a = oldState->outs) != NULL) { - cparc(nfa, a, newState, a->to); - freearc(nfa, a); + if (!BULK_ARC_OP_USE_SORT(oldState->nouts, newState->nouts)) { + /* With not too many arcs, just do them one at a time */ + struct arc *a; + + while ((a = oldState->outs) != NULL) { + cparc(nfa, a, newState, a->to); + freearc(nfa, a); + } + } else { + /* + * With many arcs, use a sort-merge approach. Note that createarc() + * will put new arcs onto the front of newState's chain, so it does + * not break our walk through the sorted part of the chain. + */ + struct arc *oa; + struct arc *na; + + /* + * Because we bypass newarc() in this code path, we'd better include a + * cancel check. + */ + if (CANCEL_REQUESTED(nfa->v->re)) { + NERR(REG_CANCEL); + return; + } + + sortouts(nfa, oldState); + sortouts(nfa, newState); + if (NISERR()) { + return; /* might have failed to sort */ + } + oa = oldState->outs; + na = newState->outs; + while (oa != NULL && na != NULL) { + struct arc *a = oa; + + switch (sortouts_cmp(&oa, &na)) { + case -1: + /* newState does not have anything matching oa */ + oa = oa->outchain; + createarc(nfa, a->type, a->co, newState, a->to); + freearc(nfa, a); + break; + case 0: + /* match, advance in both lists */ + oa = oa->outchain; + na = na->outchain; + /* ... and drop duplicate arc from oldState */ + freearc(nfa, a); + break; + case +1: + /* advance only na; oa might have a match later */ + na = na->outchain; + break; + default: + assert(NOTREACHED); + } + } + while (oa != NULL) { + /* newState does not have anything matching oa */ + struct arc *a = oa; + + oa = oa->outchain; + createarc(nfa, a->type, a->co, newState, a->to); + freearc(nfa, a); + } } + + assert(oldState->nouts == 0); + assert(oldState->outs == NULL); } /* - copyouts - copy out arcs of a state to another state - * Either all arcs, or only non-empty ones as determined by all value. ^ static VOID copyouts(struct nfa *, struct state *, struct state *, int); */ static void copyouts( struct nfa *nfa, struct state *oldState, - struct state *newState, - int all) + struct state *newState) { - struct arc *a; - assert(oldState != newState); - for (a=oldState->outs ; a!=NULL ; a=a->outchain) { - if (all || a->type != EMPTY) { + if (!BULK_ARC_OP_USE_SORT(oldState->nouts, newState->nouts)) { + /* With not too many arcs, just do them one at a time */ + struct arc *a; + + for (a = oldState->outs; a != NULL; a = a->outchain) { cparc(nfa, a, newState, a->to); } + } else { + /* + * With many arcs, use a sort-merge approach. Note that createarc() + * will put new arcs onto the front of newState's chain, so it does + * not break our walk through the sorted part of the chain. + */ + struct arc *oa; + struct arc *na; + + /* + * Because we bypass newarc() in this code path, we'd better include a + * cancel check. + */ + if (CANCEL_REQUESTED(nfa->v->re)) { + NERR(REG_CANCEL); + return; + } + + sortouts(nfa, oldState); + sortouts(nfa, newState); + if (NISERR()) { + return; /* might have failed to sort */ + } + oa = oldState->outs; + na = newState->outs; + while (oa != NULL && na != NULL) { + struct arc *a = oa; + + switch (sortouts_cmp(&oa, &na)) { + case -1: + /* newState does not have anything matching oa */ + oa = oa->outchain; + createarc(nfa, a->type, a->co, newState, a->to); + break; + case 0: + /* match, advance in both lists */ + oa = oa->outchain; + na = na->outchain; + break; + case +1: + /* advance only na; oa might have a match later */ + na = na->outchain; + break; + default: + assert(NOTREACHED); + } + } + while (oa != NULL) { + /* newState does not have anything matching oa */ + struct arc *a = oa; + + oa = oa->outchain; + createarc(nfa, a->type, a->co, newState, a->to); + } } } @@ -895,6 +1389,20 @@ specialcolors( - optimize - optimize an NFA ^ static long optimize(struct nfa *, FILE *); */ + + /* + * The main goal of this function is not so much "optimization" (though it + * does try to get rid of useless NFA states) as reducing the NFA to a form + * the regex executor can handle. The executor, and indeed the cNFA format + * that is its input, can only handle PLAIN and LACON arcs. The output of + * the regex parser also includes EMPTY (do-nothing) arcs, as well as + * ^, $, AHEAD, and BEHIND constraint arcs, which we must get rid of here. + * We first get rid of EMPTY arcs and then deal with the constraint arcs. + * The hardest part of either job is to get rid of circular loops of the + * target arc type. We would have to do that in any case, though, as such a + * loop would otherwise allow the executor to cycle through the loop endlessly + * without making any progress in the input string. + */ static long /* re_info bits */ optimize( struct nfa *nfa, @@ -916,17 +1424,23 @@ optimize( if (verbose) { fprintf(f, "\nconstraints:\n"); } + fixconstraintloops(nfa, f); /* get rid of constraint loops */ pullback(nfa, f); /* pull back constraints backward */ pushfwd(nfa, f); /* push fwd constraints forward */ if (verbose) { fprintf(f, "\nfinal cleanup:\n"); } cleanup(nfa); /* final tidying */ +#ifdef REG_DEBUG + if (verbose) { + dumpnfa(nfa, f); + } +#endif return analyze(nfa); /* and analysis */ } /* - - pullback - pull back constraints backward to (with luck) eliminate them + - pullback - pull back constraints backward to eliminate them ^ static void pullback(struct nfa *, FILE *); */ static void @@ -938,6 +1452,7 @@ pullback( struct state *nexts; struct arc *a; struct arc *nexta; + struct state *intermediates; int progress; /* @@ -948,15 +1463,27 @@ pullback( progress = 0; for (s=nfa->states ; s!=NULL && !NISERR() ; s=nexts) { nexts = s->next; + intermediates = NULL; for (a=s->outs ; a!=NULL && !NISERR() ; a=nexta) { nexta = a->outchain; if (a->type == '^' || a->type == BEHIND) { - if (pull(nfa, a)) { + if (pull(nfa, a, &intermediates)) { progress = 1; } } assert(nexta == NULL || s->no != FREESTATE); } + /* clear tmp fields of intermediate states created here */ + while (intermediates != NULL) { + struct state *ns = intermediates->tmp; + + intermediates->tmp = NULL; + intermediates = ns; + } + /* if s is now useless, get rid of it */ + if ((s->nins == 0 || s->nouts == 0) && !s->flag) { + dropstate(nfa, s); + } } if (progress && f != NULL) { dumpnfa(nfa, f); @@ -966,6 +1493,12 @@ pullback( return; } + /* + * Any ^ constraints we were able to pull to the start state can now be + * replaced by PLAIN arcs referencing the BOS or BOL colors. There should + * be no other ^ or BEHIND arcs left in the NFA, though we do not check + * that here (compact() will fail if so). + */ for (a=nfa->pre->outs ; a!=NULL ; a=nexta) { nexta = a->outchain; if (a->type == '^') { @@ -978,15 +1511,28 @@ pullback( /* - pull - pull a back constraint backward past its source state - * A significant property of this function is that it deletes at most - * one state -- the constraint's from state -- and only if the constraint - * was that state's last outarc. + * + * Returns 1 if successful (which it always is unless the source is the + * start state or we have an internal error), 0 if nothing happened. + * + * A significant property of this function is that it deletes no pre-existing + * states, and no outarcs of the constraint's from state other than the given + * constraint arc. This makes the loops in pullback() safe, at the cost that + * we may leave useless states behind. Therefore, we leave it to pullback() + * to delete such states. + * + * If the from state has multiple back-constraint outarcs, and/or multiple + * compatible constraint inarcs, we only need to create one new intermediate + * state per combination of predecessor and successor states. *intermediates + * points to a list of such intermediate states for this from state (chained + * through their tmp fields). ^ static int pull(struct nfa *, struct arc *); */ -static int /* 0 couldn't, 1 could */ +static int pull( struct nfa *nfa, - struct arc *con) + struct arc *con, + struct state **intermediates) { struct state *from = con->from; struct state *to = con->to; @@ -994,10 +1540,7 @@ pull( struct arc *nexta; struct state *s; - if (from == to) { /* circular constraint is pointless */ - freearc(nfa, con); - return 1; - } + assert(from != to); /* should have gotten rid of this earlier */ if (from->flag) { /* can't pull back beyond start */ return 0; } @@ -1007,26 +1550,9 @@ pull( } /* - * DGP 2007-11-15: Cloning a state with a circular constraint on its list - * of outs can lead to trouble [Bug 1810038], so get rid of them first. - */ - - for (a = from->outs; a != NULL; a = nexta) { - nexta = a->outchain; - switch (a->type) { - case '^': - case '$': - case BEHIND: - case AHEAD: - if (from == a->to) { - freearc(nfa, a); - } - break; - } - } - - /* - * First, clone from state if necessary to avoid other outarcs. + * First, clone from state if necessary to avoid other outarcs. This may + * seem wasteful, but it simplifies the logic, and we'll get rid of the + * clone state again at the bottom. */ if (from->nouts > 1) { @@ -1034,10 +1560,12 @@ pull( if (NISERR()) { return 0; } - assert(to != from); /* con is not an inarc */ - copyins(nfa, from, s, 1); /* duplicate inarcs */ + copyins(nfa, from, s); /* duplicate inarcs */ cparc(nfa, con, s, to); /* move constraint arc */ freearc(nfa, con); + if (NISERR()) { + return 0; + } from = s; con = from->outs; } @@ -1047,7 +1575,7 @@ pull( * Propagate the constraint into the from state's inarcs. */ - for (a=from->ins ; a!=NULL ; a=nexta) { + for (a=from->ins ; a!=NULL && !NISERR(); a=nexta) { nexta = a->inchain; switch (combine(con, a)) { case INCOMPATIBLE: /* destroy the arc */ @@ -1056,17 +1584,25 @@ pull( case SATISFIED: /* no action needed */ break; case COMPATIBLE: /* swap the two arcs, more or less */ - s = newstate(nfa); - if (NISERR()) { - return 0; + /* need an intermediate state, but might have one already */ + for (s = *intermediates; s != NULL; s = s->tmp) { + assert(s->nins > 0 && s->nouts > 0); + if (s->ins->from == a->from && s->outs->to == to) { + break; + } } - cparc(nfa, a, s, to); /* anticipate move */ - cparc(nfa, con, a->from, s); - if (NISERR()) { - return 0; + if (s == NULL) { + s = newstate(nfa); + if (NISERR()) { + return 0; + } + s->tmp = *intermediates; + *intermediates = s; } - freearc(nfa, a); - break; + cparc(nfa, con, a->from, s); + cparc(nfa, a, s, to); + freearc(nfa, a); + break; default: assert(NOTREACHED); break; @@ -1078,12 +1614,13 @@ pull( */ moveins(nfa, from, to); - dropstate(nfa, from); /* will free the constraint */ + freearc(nfa, con); + /* from state is now useless, but we leave it to pullback() to clean up */ return 1; } /* - - pushfwd - push forward constraints forward to (with luck) eliminate them + - pushfwd - push forward constraints forward to eliminate them ^ static void pushfwd(struct nfa *, FILE *); */ static void @@ -1095,6 +1632,7 @@ pushfwd( struct state *nexts; struct arc *a; struct arc *nexta; + struct state *intermediates; int progress; /* @@ -1105,14 +1643,25 @@ pushfwd( progress = 0; for (s=nfa->states ; s!=NULL && !NISERR() ; s=nexts) { nexts = s->next; + intermediates = NULL; for (a = s->ins; a != NULL && !NISERR(); a = nexta) { nexta = a->inchain; if (a->type == '$' || a->type == AHEAD) { - if (push(nfa, a)) { + if (push(nfa, a, &intermediates)) { progress = 1; } } - assert(nexta == NULL || s->no != FREESTATE); + } + /* clear tmp fields of intermediate states created here */ + while (intermediates != NULL) { + struct state *ns = intermediates->tmp; + + intermediates->tmp = NULL; + intermediates = ns; + } + /* if s is now useless, get rid of it */ + if ((s->nins == 0 || s->nouts == 0) && !s->flag) { + dropstate(nfa, s); } } if (progress && f != NULL) { @@ -1123,6 +1672,12 @@ pushfwd( return; } + /* + * Any $ constraints we were able to push to the post state can now be + * replaced by PLAIN arcs referencing the EOS or EOL colors. There should + * be no other $ or AHEAD arcs left in the NFA, though we do not check + * that here (compact() will fail if so). + */ for (a = nfa->post->ins; a != NULL; a = nexta) { nexta = a->inchain; if (a->type == '$') { @@ -1135,15 +1690,28 @@ pushfwd( /* - push - push a forward constraint forward past its destination state - * A significant property of this function is that it deletes at most - * one state -- the constraint's to state -- and only if the constraint - * was that state's last inarc. + * + * Returns 1 if successful (which it always is unless the destination is the + * post state or we have an internal error), 0 if nothing happened. + * + * A significant property of this function is that it deletes no pre-existing + * states, and no inarcs of the constraint's to state other than the given + * constraint arc. This makes the loops in pushfwd() safe, at the cost that + * we may leave useless states behind. Therefore, we leave it to pushfwd() + * to delete such states. + * + * If the to state has multiple forward-constraint inarcs, and/or multiple + * compatible constraint outarcs, we only need to create one new intermediate + * state per combination of predecessor and successor states. *intermediates + * points to a list of such intermediate states for this to state (chained + * through their tmp fields). ^ static int push(struct nfa *, struct arc *); */ -static int /* 0 couldn't, 1 could */ +static int push( struct nfa *nfa, - struct arc *con) + struct arc *con, + struct state **intermediates) { struct state *from = con->from; struct state *to = con->to; @@ -1151,10 +1719,7 @@ push( struct arc *nexta; struct state *s; - if (to == from) { /* circular constraint is pointless */ - freearc(nfa, con); - return 1; - } + assert(to != from); /* should have gotten rid of this earlier */ if (to->flag) { /* can't push forward beyond end */ return 0; } @@ -1164,29 +1729,9 @@ push( } /* - * DGP 2007-11-15: Here we duplicate the same protections as appear - * in pull() above to avoid troubles with cloning a state with a - * circular constraint on its list of ins. It is not clear whether - * this is necessary, or is protecting against a "can't happen". - * Any test case that actually leads to a freearc() call here would - * be a welcome addition to the test suite. - */ - - for (a = to->ins; a != NULL; a = nexta) { - nexta = a->inchain; - switch (a->type) { - case '^': - case '$': - case BEHIND: - case AHEAD: - if (a->from == to) { - freearc(nfa, a); - } - break; - } - } - /* - * First, clone to state if necessary to avoid other inarcs. + * First, clone to state if necessary to avoid other inarcs. This may + * seem wasteful, but it simplifies the logic, and we'll get rid of the + * clone state again at the bottom. */ if (to->nins > 1) { @@ -1194,9 +1739,12 @@ push( if (NISERR()) { return 0; } - copyouts(nfa, to, s, 1); /* duplicate outarcs */ - cparc(nfa, con, from, s); /* move constraint */ + copyouts(nfa, to, s); /* duplicate outarcs */ + cparc(nfa, con, from, s); /* move constraint arc */ freearc(nfa, con); + if (NISERR()) { + return 0; + } to = s; con = to->ins; } @@ -1206,7 +1754,7 @@ push( * Propagate the constraint into the to state's outarcs. */ - for (a = to->outs; a != NULL; a = nexta) { + for (a = to->outs; a != NULL && !NISERR(); a = nexta) { nexta = a->outchain; switch (combine(con, a)) { case INCOMPATIBLE: /* destroy the arc */ @@ -1215,17 +1763,25 @@ push( case SATISFIED: /* no action needed */ break; case COMPATIBLE: /* swap the two arcs, more or less */ - s = newstate(nfa); - if (NISERR()) { - return 0; + /* need an intermediate state, but might have one already */ + for (s = *intermediates; s != NULL; s = s->tmp) { + assert(s->nins > 0 && s->nouts > 0); + if (s->ins->from == from && s->outs->to == a->to) { + break; + } } - cparc(nfa, con, s, a->to); /* anticipate move */ - cparc(nfa, a, from, s); - if (NISERR()) { - return 0; + if (s == NULL) { + s = newstate(nfa); + if (NISERR()) { + return 0; + } + s->tmp = *intermediates; + *intermediates = s; } - freearc(nfa, a); - break; + cparc(nfa, con, s, a->to); + cparc(nfa, a, from, s); + freearc(nfa, a); + break; default: assert(NOTREACHED); break; @@ -1237,7 +1793,8 @@ push( */ moveouts(nfa, to, from); - dropstate(nfa, to); /* will free the constraint */ + freearc(nfa, con); + /* to state is now useless, but we leave it to pushfwd() to clean up */ return 1; } @@ -1315,6 +1872,12 @@ fixempties( struct state *nexts; struct arc *a; struct arc *nexta; + int totalinarcs; + struct arc **inarcsorig; + struct arc **arcarray; + int arccount; + int prevnins; + int nskip; /* * First, get rid of any states whose sole out-arc is an EMPTY, @@ -1360,42 +1923,129 @@ fixempties( dropstate(nfa, s); } + if (NISERR()) { + return; + } + /* - * For each remaining NFA state, find all other states that are - * reachable from it by a chain of one or more EMPTY arcs. Then - * generate new arcs that eliminate the need for each such chain. + * For each remaining NFA state, find all other states from which it is + * reachable by a chain of one or more EMPTY arcs. Then generate new arcs + * that eliminate the need for each such chain. + * + * We could replace a chain of EMPTY arcs that leads from a "from" state + * to a "to" state either by pushing non-EMPTY arcs forward (linking + * directly from "from"'s predecessors to "to") or by pulling them back + * (linking directly from "from" to "to"'s successors). We choose to + * always do the former; this choice is somewhat arbitrary, but the + * approach below requires that we uniformly do one or the other. * - * If we just do this straightforwardly, the algorithm gets slow in - * complex graphs, because the same arcs get copied to all - * intermediate states of an EMPTY chain, and then uselessly pushed - * repeatedly to the chain's final state; we waste a lot of time in - * newarc's duplicate checking. To improve matters, we decree that - * any state with only EMPTY out-arcs is "doomed" and will not be - * part of the final NFA. That can be ensured by not adding any new - * out-arcs to such a state. Having ensured that, we need not update - * the state's in-arcs list either; all arcs that might have gotten - * pushed forward to it will just get pushed directly to successor - * states. This eliminates most of the useless duplicate arcs. + * Suppose we have a chain of N successive EMPTY arcs (where N can easily + * approach the size of the NFA). All of the intermediate states must + * have additional inarcs and outarcs, else they'd have been removed by + * the steps above. Assuming their inarcs are mostly not empties, we will + * add O(N^2) arcs to the NFA, since a non-EMPTY inarc leading to any one + * state in the chain must be duplicated to lead to all its successor + * states as well. So there is no hope of doing less than O(N^2) work; + * however, we should endeavor to keep the big-O cost from being even + * worse than that, which it can easily become without care. In + * particular, suppose we were to copy all S1's inarcs forward to S2, and + * then also to S3, and then later we consider pushing S2's inarcs forward + * to S3. If we include the arcs already copied from S1 in that, we'd be + * doing O(N^3) work. (The duplicate-arc elimination built into newarc() + * and its cohorts would get rid of the extra arcs, but not without cost.) + * + * We can avoid this cost by treating only arcs that existed at the start + * of this phase as candidates to be pushed forward. To identify those, + * we remember the first inarc each state had to start with. We rely on + * the fact that newarc() and friends put new arcs on the front of their + * to-states' inchains, and that this phase never deletes arcs, so that + * the original arcs must be the last arcs in their to-states' inchains. + * + * So the process here is that, for each state in the NFA, we gather up + * all non-EMPTY inarcs of states that can reach the target state via + * EMPTY arcs. We then sort, de-duplicate, and merge these arcs into the + * target state's inchain. (We can safely use sort-merge for this as long + * as we update each state's original-arcs pointer after we add arcs to + * it; the sort step of mergeins probably changed the order of the old + * arcs.) + * + * Another refinement worth making is that, because we only add non-EMPTY + * arcs during this phase, and all added arcs have the same from-state as + * the non-EMPTY arc they were cloned from, we know ahead of time that any + * states having only EMPTY outarcs will be useless for lack of outarcs + * after we drop the EMPTY arcs. (They cannot gain non-EMPTY outarcs if + * they had none to start with.) So we need not bother to update the + * inchains of such states at all. + */ + + /* Remember the states' first original inarcs */ + /* ... and while at it, count how many old inarcs there are altogether */ + inarcsorig = (struct arc **) MALLOC(nfa->nstates * sizeof(struct arc *)); + if (inarcsorig == NULL) { + NERR(REG_ESPACE); + return; + } + totalinarcs = 0; + for (s = nfa->states; s != NULL; s = s->next) { + inarcsorig[s->no] = s->ins; + totalinarcs += s->nins; + } + + /* + * Create a workspace for accumulating the inarcs to be added to the + * current target state. totalinarcs is probably a considerable + * overestimate of the space needed, but the NFA is unlikely to be large + * enough at this point to make it worth being smarter. */ + arcarray = (struct arc **) MALLOC(totalinarcs * sizeof(struct arc *)); + if (arcarray == NULL) { + NERR(REG_ESPACE); + FREE(inarcsorig); + return; + } + + /* And iterate over the target states */ for (s = nfa->states; s != NULL && !NISERR(); s = s->next) { - for (s2 = emptyreachable(s, s); s2 != s && !NISERR(); - s2 = nexts) { - /* - * If s2 is doomed, we decide that (1) we will always push - * arcs forward to it, not pull them back to s; and (2) we - * can optimize away the push-forward, per comment above. - * So do nothing. - */ - if (s2->flag || hasnonemptyout(s2)) { - replaceempty(nfa, s, s2); - } + /* Ignore target states without non-EMPTY outarcs, per note above */ + if (!s->flag && !hasnonemptyout(s)) { + continue; + } - /* Reset the tmp fields as we walk back */ - nexts = s2->tmp; - s2->tmp = NULL; + /* Find predecessor states and accumulate their original inarcs */ + arccount = 0; + for (s2 = emptyreachable(nfa, s, s, inarcsorig); s2 != s; s2 = nexts) { + /* Add s2's original inarcs to arcarray[], but ignore empties */ + for (a = inarcsorig[s2->no]; a != NULL; a = a->inchain) { + if (a->type != EMPTY) { + arcarray[arccount++] = a; + } + } + + /* Reset the tmp fields as we walk back */ + nexts = s2->tmp; + s2->tmp = NULL; + } + s->tmp = NULL; + assert(arccount <= totalinarcs); + + /* Remember how many original inarcs this state has */ + prevnins = s->nins; + + /* Add non-duplicate inarcs to target state */ + mergeins(nfa, s, arcarray, arccount); + + /* Now we must update the state's inarcsorig pointer */ + nskip = s->nins - prevnins; + a = s->ins; + while (nskip-- > 0) { + a = a->inchain; } - s->tmp = NULL; + inarcsorig[s->no] = a; } + + FREE(arcarray); + FREE(inarcsorig); + if (NISERR()) { return; } @@ -1431,89 +2081,604 @@ fixempties( } /* - - emptyreachable - recursively find all states reachable from s by EMPTY arcs + - emptyreachable - recursively find all states that can reach s by EMPTY arcs * The return value is the last such state found. Its tmp field links back * to the next-to-last such state, and so on back to s, so that all these * states can be located without searching the whole NFA. + * + * Since this is only used in fixempties(), we pass in the inarcsorig[] array + * maintained by that function. This lets us skip over all new inarcs, which + * are certainly not EMPTY arcs. + * * The maximum recursion depth here is equal to the length of the longest * loop-free chain of EMPTY arcs, which is surely no more than the size of - * the NFA, and in practice will be a lot less than that. + * the NFA, and in practice will be less than that. ^ static struct state *emptyreachable(struct state *, struct state *); */ static struct state * emptyreachable( + struct nfa *nfa, struct state *s, - struct state *lastfound) + struct state *lastfound, + struct arc **inarcsorig) { struct arc *a; s->tmp = lastfound; lastfound = s; - for (a = s->outs; a != NULL; a = a->outchain) { - if (a->type == EMPTY && a->to->tmp == NULL) { - lastfound = emptyreachable(a->to, lastfound); + for (a = inarcsorig[s->no]; a != NULL; a = a->inchain) { + if (a->type == EMPTY && a->from->tmp == NULL) { + lastfound = emptyreachable(nfa, a->from, lastfound, inarcsorig); } } return lastfound; } - + /* - - replaceempty - replace an EMPTY arc chain with some non-empty arcs - * The EMPTY arc(s) should be deleted later, but we can't do it here because - * they may still be needed to identify other arc chains during fixempties(). - ^ static void replaceempty(struct nfa *, struct state *, struct state *); + * isconstraintarc - detect whether an arc is of a constraint type + */ +static inline int +isconstraintarc(struct arc * a) +{ + switch (a->type) + { + case '^': + case '$': + case BEHIND: + case AHEAD: + case LACON: + return 1; + } + return 0; +} + +/* + * hasconstraintout - does state have a constraint out arc? + */ +static int +hasconstraintout(struct state * s) +{ + struct arc *a; + + for (a = s->outs; a != NULL; a = a->outchain) { + if (isconstraintarc(a)) { + return 1; + } + } + return 0; +} + +/* + * fixconstraintloops - get rid of loops containing only constraint arcs + * + * A loop of states that contains only constraint arcs is useless, since + * passing around the loop represents no forward progress. Moreover, it + * would cause infinite looping in pullback/pushfwd, so we need to get rid + * of such loops before doing that. */ static void -replaceempty( - struct nfa *nfa, - struct state *from, - struct state *to) +fixconstraintloops( + struct nfa * nfa, + FILE *f) /* for debug output; NULL none */ { - int fromouts; - int toins; + struct state *s; + struct state *nexts; + struct arc *a; + struct arc *nexta; + int hasconstraints; + + /* + * In the trivial case of a state that loops to itself, we can just drop + * the constraint arc altogether. This is worth special-casing because + * such loops are far more common than loops containing multiple states. + * While we're at it, note whether any constraint arcs survive. + */ + hasconstraints = 0; + for (s = nfa->states; s != NULL && !NISERR(); s = nexts) { + nexts = s->next; + /* while we're at it, ensure tmp fields are clear for next step */ + assert(s->tmp == NULL); + for (a = s->outs; a != NULL && !NISERR(); a = nexta) { + nexta = a->outchain; + if (isconstraintarc(a)) { + if (a->to == s) { + freearc(nfa, a); + } else { + hasconstraints = 1; + } + } + } + /* If we removed all the outarcs, the state is useless. */ + if (s->nouts == 0 && !s->flag) { + dropstate(nfa, s); + } + } + + /* Nothing to do if no remaining constraint arcs */ + if (NISERR() || !hasconstraints) { + return; + } - assert(from != to); + /* + * Starting from each remaining NFA state, search outwards for a + * constraint loop. If we find a loop, break the loop, then start the + * search over. (We could possibly retain some state from the first scan, + * but it would complicate things greatly, and multi-state constraint + * loops are rare enough that it's not worth optimizing the case.) + */ + restart: + for (s = nfa->states; s != NULL && !NISERR(); s = s->next) { + if (findconstraintloop(nfa, s)) { + goto restart; + } + } + + if (NISERR()) { + return; + } /* - * Create replacement arcs that bypass the need for the EMPTY chain. We - * can do this either by pushing arcs forward (linking directly from - * "from"'s predecessors to "to") or by pulling them back (linking - * directly from "from" to "to"'s successors). In general, we choose - * whichever way creates greater fan-out or fan-in, so as to improve the - * odds of reducing the other state to zero in-arcs or out-arcs and - * thereby being able to delete it. However, if "from" is doomed (has no - * non-EMPTY out-arcs), we must keep it so, so always push forward in that - * case. + * Now remove any states that have become useless. (This cleanup is not + * very thorough, and would be even less so if we tried to combine it with + * the previous step; but cleanup() will take care of anything we miss.) * - * The fan-out/fan-in comparison should count only non-EMPTY arcs. If - * "from" is doomed, we can skip counting "to"'s arcs, since we want to - * force taking the copynonemptyins path in that case. + * Because findconstraintloop intentionally doesn't reset all tmp fields, + * we have to clear them after it's done. This is a convenient place to + * do that, too. + */ + for (s = nfa->states; s != NULL; s = nexts) { + nexts = s->next; + s->tmp = NULL; + if ((s->nins == 0 || s->nouts == 0) && !s->flag) { + dropstate(nfa, s); + } + } + + if (f != NULL) { + dumpnfa(nfa, f); + } +} + +/* + * findconstraintloop - recursively find a loop of constraint arcs + * + * If we find a loop, break it by calling breakconstraintloop(), then + * return 1; otherwise return 0. + * + * State tmp fields are guaranteed all NULL on a success return, because + * breakconstraintloop does that. After a failure return, any state that + * is known not to be part of a loop is marked with s->tmp == s; this allows + * us not to have to re-prove that fact on later calls. (This convention is + * workable because we already eliminated single-state loops.) + * + * Note that the found loop doesn't necessarily include the first state we + * are called on. Any loop reachable from that state will do. + * + * The maximum recursion depth here is one more than the length of the longest + * loop-free chain of constraint arcs, which is surely no more than the size + * of the NFA, and in practice will be a lot less than that. + */ +static int +findconstraintloop(struct nfa * nfa, struct state * s) +{ + struct arc *a; + + /* Since this is recursive, it could be driven to stack overflow */ + if (STACK_TOO_DEEP(nfa->v->re)) { + NERR(REG_ETOOBIG); + return 1; /* to exit as quickly as possible */ + } + + if (s->tmp != NULL) { + /* Already proven uninteresting? */ + if (s->tmp == s) { + return 0; + } + /* Found a loop involving s */ + breakconstraintloop(nfa, s); + /* The tmp fields have been cleaned up by breakconstraintloop */ + return 1; + } + for (a = s->outs; a != NULL; a = a->outchain) { + if (isconstraintarc(a)) { + struct state *sto = a->to; + + assert(sto != s); + s->tmp = sto; + if (findconstraintloop(nfa, sto)) { + return 1; + } + } + } + + /* + * If we get here, no constraint loop exists leading out from s. Mark it + * with s->tmp == s so we need not rediscover that fact again later. + */ + s->tmp = s; + return 0; +} + +/* + * breakconstraintloop - break a loop of constraint arcs + * + * sinitial is any one member state of the loop. Each loop member's tmp + * field links to its successor within the loop. (Note that this function + * will reset all the tmp fields to NULL.) + * + * We can break the loop by, for any one state S1 in the loop, cloning its + * loop successor state S2 (and possibly following states), and then moving + * all S1->S2 constraint arcs to point to the cloned S2. The cloned S2 should + * copy any non-constraint outarcs of S2. Constraint outarcs should be + * dropped if they point back to S1, else they need to be copied as arcs to + * similarly cloned states S3, S4, etc. In general, each cloned state copies + * non-constraint outarcs, drops constraint outarcs that would lead to itself + * or any earlier cloned state, and sends other constraint outarcs to newly + * cloned states. No cloned state will have any inarcs that aren't constraint + * arcs or do not lead from S1 or earlier-cloned states. It's okay to drop + * constraint back-arcs since they would not take us to any state we've not + * already been in; therefore, no new constraint loop is created. In this way + * we generate a modified NFA that can still represent every useful state + * sequence, but not sequences that represent state loops with no consumption + * of input data. Note that the set of cloned states will certainly include + * all of the loop member states other than S1, and it may also include + * non-loop states that are reachable from S2 via constraint arcs. This is + * important because there is no guarantee that findconstraintloop found a + * maximal loop (and searching for one would be NP-hard, so don't try). + * Frequently the "non-loop states" are actually part of a larger loop that + * we didn't notice, and indeed there may be several overlapping loops. + * This technique ensures convergence in such cases, while considering only + * the originally-found loop does not. + * + * If there is only one S1->S2 constraint arc, then that constraint is + * certainly satisfied when we enter any of the clone states. This means that + * in the common case where many of the constraint arcs are identically + * labeled, we can merge together clone states linked by a similarly-labeled + * constraint: if we can get to the first one we can certainly get to the + * second, so there's no need to distinguish. This greatly reduces the number + * of new states needed, so we preferentially break the given loop at a state + * pair where this is true. + * + * Furthermore, it's fairly common to find that a cloned successor state has + * no outarcs, especially if we're a bit aggressive about removing unnecessary + * outarcs. If that happens, then there is simply not any interesting state + * that can be reached through the predecessor's loop arcs, which means we can + * break the loop just by removing those loop arcs, with no new states added. + */ +static void +breakconstraintloop(struct nfa * nfa, struct state * sinitial) +{ + struct state *s; + struct state *shead; + struct state *stail; + struct state *sclone; + struct state *nexts; + struct arc *refarc; + struct arc *a; + struct arc *nexta; + + /* + * Start by identifying which loop step we want to break at. + * Preferentially this is one with only one constraint arc. (XXX are + * there any other secondary heuristics we want to use here?) Set refarc + * to point to the selected lone constraint arc, if there is one. + */ + refarc = NULL; + s = sinitial; + do { + nexts = s->tmp; + assert(nexts != s); /* should not see any one-element loops */ + if (refarc == NULL) { + int narcs = 0; + + for (a = s->outs; a != NULL; a = a->outchain) { + if (a->to == nexts && isconstraintarc(a)) { + refarc = a; + narcs++; + } + } + assert(narcs > 0); + if (narcs > 1) { + refarc = NULL; /* multiple constraint arcs here, no good */ + } + } + s = nexts; + } while (s != sinitial); + + if (refarc) { + /* break at the refarc */ + shead = refarc->from; + stail = refarc->to; + assert(stail == shead->tmp); + } else { + /* for lack of a better idea, break after sinitial */ + shead = sinitial; + stail = sinitial->tmp; + } + + /* + * Reset the tmp fields so that we can use them for local storage in + * clonesuccessorstates. (findconstraintloop won't mind, since it's just + * going to abandon its search anyway.) */ - fromouts = nonemptyouts(from); - toins = (fromouts == 0) ? 1 : nonemptyins(to); + for (s = nfa->states; s != NULL; s = s->next) { + s->tmp = NULL; + } - if (fromouts > toins) { - copyouts(nfa, to, from, 0); + /* + * Recursively build clone state(s) as needed. + */ + sclone = newstate(nfa); + if (sclone == NULL) { + assert(NISERR()); return; } - if (fromouts < toins) { - copyins(nfa, from, to, 0); + + clonesuccessorstates(nfa, stail, sclone, shead, refarc, + NULL, NULL, nfa->nstates); + + if (NISERR()) { return; } /* - * fromouts == toins. Decide on secondary issue: copy fewest arcs. - * - * Doesn't seem to be worth the trouble to exclude empties from these - * comparisons; that takes extra time and doesn't seem to improve the - * resulting graph much. + * It's possible that sclone has no outarcs at all, in which case it's + * useless. (We don't try extremely hard to get rid of useless states + * here, but this is an easy and fairly common case.) + */ + if (sclone->nouts == 0) { + freestate(nfa, sclone); + sclone = NULL; + } + + /* + * Move shead's constraint-loop arcs to point to sclone, or just drop them + * if we discovered we don't need sclone. */ - if (from->nins > to->nouts) { - copyouts(nfa, to, from, 0); + for (a = shead->outs; a != NULL; a = nexta) { + nexta = a->outchain; + if (a->to == stail && isconstraintarc(a)) { + if (sclone) { + cparc(nfa, a, shead, sclone); + } + freearc(nfa, a); + if (NISERR()) { + break; + } + } + } +} + +/* + * clonesuccessorstates - create a tree of constraint-arc successor states + * + * ssource is the state to be cloned, and sclone is the state to copy its + * outarcs into. sclone's inarcs, if any, should already be set up. + * + * spredecessor is the original predecessor state that we are trying to build + * successors for (it may not be the immediate predecessor of ssource). + * refarc, if not NULL, is the original constraint arc that is known to have + * been traversed out of spredecessor to reach the successor(s). + * + * For each cloned successor state, we transiently create a "donemap" that is + * a boolean array showing which source states we've already visited for this + * clone state. This prevents infinite recursion as well as useless repeat + * visits to the same state subtree (which can add up fast, since typical NFAs + * have multiple redundant arc pathways). Each donemap is a char array + * indexed by state number. The donemaps are all of the same size "nstates", + * which is nfa->nstates as of the start of the recursion. This is enough to + * have entries for all pre-existing states, but *not* entries for clone + * states created during the recursion. That's okay since we have no need to + * mark those. + * + * curdonemap is NULL when recursing to a new sclone state, or sclone's + * donemap when we are recursing without having created a new state (which we + * do when we decide we can merge a successor state into the current clone + * state). outerdonemap is NULL at the top level and otherwise the parent + * clone state's donemap. + * + * The successor states we create and fill here form a strict tree structure, + * with each state having exactly one predecessor, except that the toplevel + * state has no inarcs as yet (breakconstraintloop will add its inarcs from + * spredecessor after we're done). Thus, we can examine sclone's inarcs back + * to the root, plus refarc if any, to identify the set of constraints already + * known valid at the current point. This allows us to avoid generating extra + * successor states. + */ +static void +clonesuccessorstates( + struct nfa * nfa, + struct state * ssource, + struct state * sclone, + struct state * spredecessor, + struct arc * refarc, + char *curdonemap, + char *outerdonemap, + int nstates) +{ + char *donemap; + struct arc *a; + + /* Since this is recursive, it could be driven to stack overflow */ + if (STACK_TOO_DEEP(nfa->v->re)) { + NERR(REG_ETOOBIG); return; } - copyins(nfa, from, to, 0); + /* If this state hasn't already got a donemap, create one */ + donemap = curdonemap; + if (donemap == NULL) { + donemap = (char *) MALLOC(nstates * sizeof(char)); + if (donemap == NULL) { + NERR(REG_ESPACE); + return; + } + + if (outerdonemap != NULL) { + /* + * Not at outermost recursion level, so copy the outer level's + * donemap; this ensures that we see states in process of being + * visited at outer levels, or already merged into predecessor + * states, as ones we shouldn't traverse back to. + */ + memcpy(donemap, outerdonemap, nstates * sizeof(char)); + } else { + /* At outermost level, only spredecessor is off-limits */ + memset(donemap, 0, nstates * sizeof(char)); + assert(spredecessor->no < nstates); + donemap[spredecessor->no] = 1; + } + } + + /* Mark ssource as visited in the donemap */ + assert(ssource->no < nstates); + assert(donemap[ssource->no] == 0); + donemap[ssource->no] = 1; + + /* + * We proceed by first cloning all of ssource's outarcs, creating new + * clone states as needed but not doing more with them than that. Then in + * a second pass, recurse to process the child clone states. This allows + * us to have only one child clone state per reachable source state, even + * when there are multiple outarcs leading to the same state. Also, when + * we do visit a child state, its set of inarcs is known exactly, which + * makes it safe to apply the constraint-is-already-checked optimization. + * Also, this ensures that we've merged all the states we can into the + * current clone before we recurse to any children, thus possibly saving + * them from making extra images of those states. + * + * While this function runs, child clone states of the current state are + * marked by setting their tmp fields to point to the original state they + * were cloned from. This makes it possible to detect multiple outarcs + * leading to the same state, and also makes it easy to distinguish clone + * states from original states (which will have tmp == NULL). + */ + for (a = ssource->outs; a != NULL && !NISERR(); a = a->outchain) { + struct state *sto = a->to; + + /* + * We do not consider cloning successor states that have no constraint + * outarcs; just link to them as-is. They cannot be part of a + * constraint loop so there is no need to make copies. In particular, + * this rule keeps us from trying to clone the post state, which would + * be a bad idea. + */ + if (isconstraintarc(a) && hasconstraintout(sto)) { + struct state *prevclone; + int canmerge; + struct arc *a2; + + /* + * Back-link constraint arcs must not be followed. Nor is there a + * need to revisit states previously merged into this clone. + */ + assert(sto->no < nstates); + if (donemap[sto->no] != 0) { + continue; + } + + /* + * Check whether we already have a child clone state for this + * source state. + */ + prevclone = NULL; + for (a2 = sclone->outs; a2 != NULL; a2 = a2->outchain) { + if (a2->to->tmp == sto) { + prevclone = a2->to; + break; + } + } + + /* + * If this arc is labeled the same as refarc, or the same as any + * arc we must have traversed to get to sclone, then no additional + * constraints need to be met to get to sto, so we should just + * merge its outarcs into sclone. + */ + if (refarc && a->type == refarc->type && a->co == refarc->co) { + canmerge = 1; + } else { + struct state *s; + + canmerge = 0; + for (s = sclone; s->ins; s = s->ins->from) { + if (s->nins == 1 && + a->type == s->ins->type && a->co == s->ins->co) { + canmerge = 1; + break; + } + } + } + + if (canmerge) { + /* + * We can merge into sclone. If we previously made a child + * clone state, drop it; there's no need to visit it. (This + * can happen if ssource has multiple pathways to sto, and we + * only just now found one that is provably a no-op.) + */ + if (prevclone) { + dropstate(nfa, prevclone); /* kills our outarc, too */ + } + + /* Recurse to merge sto's outarcs into sclone */ + clonesuccessorstates(nfa, sto, sclone, spredecessor, refarc, + donemap, outerdonemap, nstates); + /* sto should now be marked as previously visited */ + assert(NISERR() || donemap[sto->no] == 1); + } else if (prevclone) { + /* + * We already have a clone state for this successor, so just + * make another arc to it. + */ + cparc(nfa, a, sclone, prevclone); + } else { + /* + * We need to create a new successor clone state. + */ + struct state *stoclone; + + stoclone = newstate(nfa); + if (stoclone == NULL) { + assert(NISERR()); + break; + } + /* Mark it as to what it's a clone of */ + stoclone->tmp = sto; + /* ... and add the outarc leading to it */ + cparc(nfa, a, sclone, stoclone); + } + } else { + /* + * Non-constraint outarcs just get copied to sclone, as do outarcs + * leading to states with no constraint outarc. + */ + cparc(nfa, a, sclone, sto); + } + } + + /* + * If we are at outer level for this clone state, recurse to all its child + * clone states, clearing their tmp fields as we go. (If we're not + * outermost for sclone, leave this to be done by the outer call level.) + * Note that if we have multiple outarcs leading to the same clone state, + * it will only be recursed-to once. + */ + if (curdonemap == NULL) { + for (a = sclone->outs; a != NULL && !NISERR(); a = a->outchain) { + struct state *stoclone = a->to; + struct state *sto = stoclone->tmp; + + if (sto != NULL) { + stoclone->tmp = NULL; + clonesuccessorstates(nfa, sto, stoclone, spredecessor, refarc, + NULL, donemap, nstates); + } + } + + /* Don't forget to free sclone's donemap when done with it */ + FREE(donemap); + } } /* @@ -1630,7 +2795,7 @@ analyze( } /* - - compact - compact an NFA + - compact - construct the compact representation of an NFA ^ static void compact(struct nfa *, struct cnfa *); */ static void @@ -1651,13 +2816,16 @@ compact( narcs = 0; for (s = nfa->states; s != NULL; s = s->next) { nstates++; - narcs += 1 + s->nouts + 1; - /* 1 as a fake for flags, nouts for arcs, 1 as endmarker */ + narcs += s->nouts + 1; /* need one extra for endmarker */ } + cnfa->stflags = (char *) MALLOC(nstates * sizeof(char)); cnfa->states = (struct carc **) MALLOC(nstates * sizeof(struct carc *)); cnfa->arcs = (struct carc *) MALLOC(narcs * sizeof(struct carc)); - if (cnfa->states == NULL || cnfa->arcs == NULL) { + if (cnfa->stflags == NULL || cnfa->states == NULL || cnfa->arcs == NULL) { + if (cnfa->stflags != NULL) { + FREE(cnfa->stflags); + } if (cnfa->states != NULL) { FREE(cnfa->states); } @@ -1680,9 +2848,8 @@ compact( ca = cnfa->arcs; for (s = nfa->states; s != NULL; s = s->next) { assert((size_t) s->no < nstates); + cnfa->stflags[s->no] = 0; cnfa->states[s->no] = ca; - ca->co = 0; /* clear and skip flags "arc" */ - ca++; first = ca; for (a = s->outs; a != NULL; a = a->outchain) { switch (a->type) { @@ -1699,11 +2866,11 @@ compact( cnfa->flags |= HASLACONS; break; default: - assert(NOTREACHED); + NERR(REG_ASSERT); break; } } - carcsort(first, ca-1); + carcsort(first, ca - first); ca->co = COLORLESS; ca->to = 0; ca++; @@ -1716,40 +2883,46 @@ compact( */ for (a = nfa->pre->outs; a != NULL; a = a->outchain) { - cnfa->states[a->to->no]->co = 1; + cnfa->stflags[a->to->no] = CNFA_NOPROGRESS; } - cnfa->states[nfa->pre->no]->co = 1; + cnfa->stflags[nfa->pre->no] = CNFA_NOPROGRESS; } /* - carcsort - sort compacted-NFA arcs by color - * Really dumb algorithm, but if the list is long enough for that to matter, - * you're in real trouble anyway. ^ static void carcsort(struct carc *, struct carc *); */ static void carcsort( struct carc *first, - struct carc *last) + size_t n) { - struct carc *p; - struct carc *q; - struct carc tmp; - - if (last - first <= 1) { - return; + if (n > 1) { + qsort(first, n, sizeof(struct carc), carc_cmp); } +} - for (p = first; p <= last; p++) { - for (q = p; q <= last; q++) { - if (p->co > q->co || (p->co == q->co && p->to > q->to)) { - assert(p != q); - tmp = *p; - *p = *q; - *q = tmp; - } - } +static int +carc_cmp( + const void *a, + const void *b) +{ + const struct carc *aa = (const struct carc *) a; + const struct carc *bb = (const struct carc *) b; + + if (aa->co < bb->co) { + return -1; } + if (aa->co > bb->co) { + return +1; + } + if (aa->to < bb->to) { + return -1; + } + if (aa->to > bb->to) { + return +1; + } + return 0; } /* @@ -1762,6 +2935,7 @@ freecnfa( { assert(cnfa->nstates != 0); /* not empty already */ cnfa->nstates = 0; + FREE(cnfa->stflags); FREE(cnfa->states); FREE(cnfa->arcs); } @@ -1777,6 +2951,8 @@ dumpnfa( { #ifdef REG_DEBUG struct state *s; + int nstates = 0; + int narcs = 0; fprintf(f, "pre %d, post %d", nfa->pre->no, nfa->post->no); if (nfa->bos[0] != COLORLESS) { @@ -1794,7 +2970,10 @@ dumpnfa( fprintf(f, "\n"); for (s = nfa->states; s != NULL; s = s->next) { dumpstate(s, f); + nstates++; + narcs += s->nouts; } + fprintf(f, "total of %d states, %d arcs\n", nstates, narcs); if (nfa->parent == NULL) { dumpcolors(nfa->cm, f); } @@ -1847,37 +3026,28 @@ dumparcs( FILE *f) { int pos; + struct arc *a; - assert(s->nouts > 0); - /* printing arcs in reverse order is usually clearer */ - pos = dumprarcs(s->outs, s, f, 1); - if (pos != 1) { - fprintf(f, "\n"); - } -} - -/* - - dumprarcs - dump remaining outarcs, recursively, in reverse order - ^ static int dumprarcs(struct arc *, struct state *, FILE *, int); - */ -static int /* resulting print position */ -dumprarcs( - struct arc *a, - struct state *s, - FILE *f, - int pos) /* initial print position */ -{ - if (a->outchain != NULL) { - pos = dumprarcs(a->outchain, s, f, pos); + /* printing oldest arcs first is usually clearer */ + a = s->outs; + assert(a != NULL); + while (a->outchain != NULL) { + a = a->outchain; } - dumparc(a, s, f); - if (pos == 5) { + pos = 1; + do { + dumparc(a, s, f); + if (pos == 5) { + fprintf(f, "\n"); + pos = 1; + } else { + pos++; + } + a = a->outchainRev; + } while (a != NULL); + if (pos != 1) { fprintf(f, "\n"); - pos = 1; - } else { - pos++; } - return pos; } /* @@ -1984,7 +3154,7 @@ dumpcnfa( } fprintf(f, "\n"); for (st = 0; st < cnfa->nstates; st++) { - dumpcstate(st, cnfa->states[st], cnfa, f); + dumpcstate(st, cnfa, f); } fflush(f); #endif @@ -1997,25 +3167,24 @@ dumpcnfa( /* - dumpcstate - dump a compacted-NFA state in human-readable form - ^ static void dumpcstate(int, struct carc *, struct cnfa *, FILE *); + ^ static void dumpcstate(int, struct cnfa *, FILE *); */ static void dumpcstate( int st, - struct carc *ca, struct cnfa *cnfa, FILE *f) { - int i; + struct carc *ca; int pos; - fprintf(f, "%d%s", st, (ca[0].co) ? ":" : "."); + fprintf(f, "%d%s", st, (cnfa->stflags[st] & CNFA_NOPROGRESS) ? ":" : "."); pos = 1; - for (i = 1; ca[i].co != COLORLESS; i++) { - if (ca[i].co < cnfa->ncolors) { - fprintf(f, "\t[%ld]->%d", (long) ca[i].co, ca[i].to); + for (ca = cnfa->states[st]; ca->co != COLORLESS; ca++) { + if (ca->co < cnfa->ncolors) { + fprintf(f, "\t[%ld]->%d", (long) ca->co, ca->to); } else { - fprintf(f, "\t:%ld:->%d", (long) ca[i].co-cnfa->ncolors,ca[i].to); + fprintf(f, "\t:%ld:->%d", (long) (ca->co - cnfa->ncolors), ca->to); } if (pos == 5) { fprintf(f, "\n"); @@ -2024,7 +3193,7 @@ dumpcstate( pos++; } } - if (i == 1 || pos != 1) { + if (ca == cnfa->states[st] || pos != 1) { fprintf(f, "\n"); } fflush(f); diff --git a/generic/regcomp.c b/generic/regcomp.c index 7ca4346..211cd70 100644 --- a/generic/regcomp.c +++ b/generic/regcomp.c @@ -83,9 +83,6 @@ static int lexdigits(struct vars *, int, int, int); static int brenext(struct vars *, pchr); static void skip(struct vars *); static chr newline(NOPARMS); -#ifdef REG_DEBUG -static const chr *ch(NOPARMS); -#endif static chr chrnamed(struct vars *, const chr *, const chr *, pchr); /* === regc_color.c === */ static void initcm(struct vars *, struct colormap *); @@ -119,17 +116,22 @@ static void dropstate(struct nfa *, struct state *); static void freestate(struct nfa *, struct state *); static void destroystate(struct nfa *, struct state *); static void newarc(struct nfa *, int, pcolor, struct state *, struct state *); +static void createarc(struct nfa *, int, pcolor, struct state *, struct state *); static struct arc *allocarc(struct nfa *, struct state *); static void freearc(struct nfa *, struct arc *); +static void changearctarget(struct arc *, struct state *); static int hasnonemptyout(struct state *); -static int nonemptyouts(struct state *); -static int nonemptyins(struct state *); static struct arc *findarc(struct state *, int, pcolor); static void cparc(struct nfa *, struct arc *, struct state *, struct state *); +static void sortins(struct nfa *, struct state *); +static int sortins_cmp(const void *, const void *); +static void sortouts(struct nfa *, struct state *); +static int sortouts_cmp(const void *, const void *); static void moveins(struct nfa *, struct state *, struct state *); -static void copyins(struct nfa *, struct state *, struct state *, int); +static void copyins(struct nfa *, struct state *, struct state *); +static void mergeins(struct nfa *, struct state *, struct arc **, int); static void moveouts(struct nfa *, struct state *, struct state *); -static void copyouts(struct nfa *, struct state *, struct state *, int); +static void copyouts(struct nfa *, struct state *, struct state *); static void cloneouts(struct nfa *, struct state *, struct state *, struct state *, int); static void delsub(struct nfa *, struct state *, struct state *); static void deltraverse(struct nfa *, struct state *, struct state *); @@ -139,33 +141,40 @@ static void cleartraverse(struct nfa *, struct state *); static void specialcolors(struct nfa *); static long optimize(struct nfa *, FILE *); static void pullback(struct nfa *, FILE *); -static int pull(struct nfa *, struct arc *); +static int pull(struct nfa *, struct arc *, struct state **); static void pushfwd(struct nfa *, FILE *); -static int push(struct nfa *, struct arc *); +static int push(struct nfa *, struct arc *, struct state **); #define INCOMPATIBLE 1 /* destroys arc */ #define SATISFIED 2 /* constraint satisfied */ #define COMPATIBLE 3 /* compatible but not satisfied yet */ static int combine(struct arc *, struct arc *); static void fixempties(struct nfa *, FILE *); -static struct state *emptyreachable(struct state *, struct state *); -static void replaceempty(struct nfa *, struct state *, struct state *); +static struct state *emptyreachable(struct nfa *, struct state *, + struct state *, struct arc **); +static int isconstraintarc(struct arc *); +static int hasconstraintout(struct state *); +static void fixconstraintloops(struct nfa *, FILE *); +static int findconstraintloop(struct nfa *, struct state *); +static void breakconstraintloop(struct nfa *, struct state *); +static void clonesuccessorstates(struct nfa *, struct state *, struct state *, + struct state *, struct arc *, char *, char *, int); static void cleanup(struct nfa *); static void markreachable(struct nfa *, struct state *, struct state *, struct state *); static void markcanreach(struct nfa *, struct state *, struct state *, struct state *); static long analyze(struct nfa *); static void compact(struct nfa *, struct cnfa *); -static void carcsort(struct carc *, struct carc *); +static void carcsort(struct carc *, size_t); +static int carc_cmp(const void *, const void *); static void freecnfa(struct cnfa *); static void dumpnfa(struct nfa *, FILE *); #ifdef REG_DEBUG static void dumpstate(struct state *, FILE *); static void dumparcs(struct state *, FILE *); -static int dumprarcs(struct arc *, struct state *, FILE *, int); static void dumparc(struct arc *, struct state *, FILE *); #endif static void dumpcnfa(struct cnfa *, FILE *); #ifdef REG_DEBUG -static void dumpcstate(int, struct carc *, struct cnfa *, FILE *); +static void dumpcstate(int, struct cnfa *, FILE *); #endif /* === regc_cvec.c === */ static struct cvec *clearcvec(struct cvec *); @@ -210,11 +219,12 @@ struct vars { struct subre *tree; /* subexpression tree */ struct subre *treechain; /* all tree nodes allocated */ struct subre *treefree; /* any free tree nodes */ - int ntree; /* number of tree nodes */ + int ntree; /* number of tree nodes, plus one */ struct cvec *cv; /* interface cvec */ struct cvec *cv2; /* utility cvec */ struct subre *lacons; /* lookahead-constraint vector */ int nlacons; /* size of lacons */ + size_t spaceused; /* approx. space used for compilation */ }; /* parsing macros; most know that `v' is the struct vars pointer */ @@ -223,13 +233,13 @@ struct vars { #define EAT(t) (SEE(t) && next(v)) /* if next is this, swallow it */ #define VISERR(vv) ((vv)->err != 0)/* have we seen an error yet? */ #define ISERR() VISERR(v) -#define VERR(vv,e) \ - ((vv)->nexttype = EOS, ((vv)->err) ? (vv)->err : ((vv)->err = (e))) +#define VERR(vv,e) ((vv)->nexttype = EOS, \ + (vv)->err = ((vv)->err ? (vv)->err : (e))) #define ERR(e) VERR(v, e) /* record an error */ #define NOERR() {if (ISERR()) return;} /* if error seen, return */ #define NOERRN() {if (ISERR()) return NULL;} /* NOERR with retval */ #define NOERRZ() {if (ISERR()) return 0;} /* NOERR with retval */ -#define INSIST(c, e) ((c) ? 0 : ERR(e)) /* if condition false, error */ +#define INSIST(c, e) do { if (!(c)) ERR(e); } while (0) /* error if c false */ #define NOTE(b) (v->re->re_info |= (b)) /* note visible condition */ #define EMPTYARC(x, y) newarc(v->nfa, EMPTY, 0, x, y) @@ -258,12 +268,14 @@ struct vars { ((a)->type == PLAIN || (a)->type == AHEAD || (a)->type == BEHIND) /* static function list */ -static struct fns functions = { +static const struct fns functions = { rfree, /* regfree insides */ }; /* - compile - compile regular expression + * Note: on failure, no resources remain allocated, so regfree() + * need not be applied to re. ^ int compile(regex_t *, const chr *, size_t, int); */ int @@ -324,6 +336,7 @@ compile( v->cv2 = NULL; v->lacons = NULL; v->nlacons = 0; + v->spaceused = 0; re->re_magic = REMAGIC; re->re_info = 0; /* bits get set during parse */ re->re_csize = sizeof(chr); @@ -593,13 +606,15 @@ makesearch( break; } } - if (b != NULL && s->tmp == NULL) { - /* - * Must be split if not already in the list (fixes bugs 505048, - * 230589, 840258, 504785). - */ - s->tmp = slist; + /* + * We want to mark states as being in the list already by having non + * NULL tmp fields, but we can't just store the old slist value in tmp + * because that doesn't work for the first such state. Instead, the + * first list entry gets its own address in tmp. + */ + if (b != NULL && s->tmp == NULL) { + s->tmp = (slist != NULL) ? slist : s; slist = s; } } @@ -610,8 +625,9 @@ makesearch( for (s=slist ; s!=NULL ; s=s2) { s2 = newstate(nfa); - - copyouts(nfa, s, s2, 1); + NOERR(); + copyouts(nfa, s, s2); + NOERR(); for (a=s->ins ; a!=NULL ; a=b) { b = a->inchain; @@ -620,7 +636,7 @@ makesearch( freearc(nfa, a); } } - s2 = s->tmp; + s2 = (s->tmp != s) ? s->tmp : NULL; s->tmp = NULL; /* clean up while we're at it */ } } @@ -982,6 +998,7 @@ parseqatom( NOERR(); assert(v->nextvalue > 0); atom = subre(v, 'b', BACKR, lp, rp); + NOERR(); subno = v->nextvalue; atom->subno = subno; EMPTYARC(lp, rp); /* temporarily, so there's something */ @@ -1102,11 +1119,17 @@ parseqatom( /* * Prepare a general-purpose state skeleton. * - * ---> [s] ---prefix---> [begin] ---atom---> [end] ----rest---> [rp] - * / / - * [lp] ----> [s2] ----bypass--------------------- + * In the no-backrefs case, we want this: + * + * [lp] ---> [s] ---prefix---> [begin] ---atom---> [end] ---rest---> [rp] * - * where bypass is an empty, and prefix is some repetitions of atom + * where prefix is some repetitions of atom. In the general case we need + * + * [lp] ---> [s] ---iterator---> [s2] ---rest---> [rp] + * + * where the iterator wraps around [begin] ---atom---> [end] + * + * We make the s state here for both cases; s2 is made below if needed */ s = newstate(v->nfa); /* first, new endpoints for the atom */ @@ -1117,11 +1140,9 @@ parseqatom( NOERR(); atom->begin = s; atom->end = s2; - s = newstate(v->nfa); /* and spots for prefix and bypass */ - s2 = newstate(v->nfa); + s = newstate(v->nfa); /* set up starting state */ NOERR(); EMPTYARC(lp, s); - EMPTYARC(lp, s2); NOERR(); /* @@ -1129,6 +1150,7 @@ parseqatom( */ t = subre(v, '.', COMBINE(qprefer, atom->flags), lp, rp); + NOERR(); t->left = atom; atomp = &t->left; @@ -1142,6 +1164,7 @@ parseqatom( assert(top->op == '=' && top->left == NULL && top->right == NULL); top->left = subre(v, '=', top->flags, top->begin, lp); + NOERR(); top->op = '.'; top->right = t; @@ -1166,27 +1189,8 @@ parseqatom( } /* - * It's quantifier time; first, turn x{0,...} into x{1,...}|empty - */ - - if (m == 0) { - EMPTYARC(s2, atom->end);/* the bypass */ - assert(PREF(qprefer) != 0); - f = COMBINE(qprefer, atom->flags); - t = subre(v, '|', f, lp, atom->end); - NOERR(); - t->left = atom; - t->right = subre(v, '|', PREF(f), s2, atom->end); - NOERR(); - t->right->left = subre(v, '=', 0, s2, atom->end); - NOERR(); - *atomp = t; - atomp = &t->left; - m = 1; - } - - /* - * Deal with the rest of the quantifier. + * It's quantifier time. If the atom is just a backref, we'll let it deal + * with quantifiers internally. */ if (atomtype == BACKREF) { @@ -1204,16 +1208,24 @@ parseqatom( atom->min = (short) m; atom->max = (short) n; atom->flags |= COMBINE(qprefer, atom->flags); + /* rest of branch can be strung starting from atom->end */ + s2 = atom->end; } else if (m == 1 && n == 1) { /* * No/vacuous quantifier: done. */ EMPTYARC(s, atom->begin); /* empty prefix */ - } else { + /* rest of branch can be strung starting from atom->end */ + s2 = atom->end; + } else if (m > 0 && !(atom->flags & BACKR)) { /* - * Turn x{m,n} into x{m-1,n-1}x, with capturing parens in only second - * x + * If there's no backrefs involved, we can turn x{m,n} into + * x{m-1,n-1}x, with capturing parens in only the second x. This + * is valid because we only care about capturing matches from the + * final iteration of the quantifier. It's a win because we can + * implement the backref-free left side as a plain DFA node, since + * we don't really care where its submatches are. */ dupnfa(v->nfa, atom->begin, atom->end, s, atom->begin); @@ -1226,6 +1238,24 @@ parseqatom( NOERR(); t->right = atom; *atomp = t; + /* rest of branch can be strung starting from atom->end */ + s2 = atom->end; + } else { + /* general case: need an iteration node */ + s2 = newstate(v->nfa); + NOERR(); + moveouts(v->nfa, atom->end, s2); + NOERR(); + dupnfa(v->nfa, atom->begin, atom->end, s, s2); + repeat(v, s, s2, m, n); + f = COMBINE(qprefer, atom->flags); + t = subre(v, '*', f, s, s2); + NOERR(); + t->min = (short) m; + t->max = (short) n; + t->left = atom; + *atomp = t; + /* rest of branch is to be strung from iteration's end state */ } /* @@ -1234,10 +1264,10 @@ parseqatom( t = top->right; if (!(SEE('|') || SEE(stopper) || SEE(EOS))) { - t->right = parsebranch(v, stopper, type, atom->end, rp, 1); + t->right = parsebranch(v, stopper, type, s2, rp, 1); } else { - EMPTYARC(atom->end, rp); - t->right = subre(v, '=', 0, atom->end, rp); + EMPTYARC(s2, rp); + t->right = subre(v, '=', 0, s2, rp); } NOERR(); assert(SEE('|') || SEE(stopper) || SEE(EOS)); @@ -1304,6 +1334,8 @@ scannum( /* - repeat - replicate subNFA for quantifiers + * The sub-NFA strung from lp to rp is modified to represent m to n + * repetitions of its initial contents. * The duplication sequences used here are chosen carefully so that any * pointers starting out pointing into the subexpression end up pointing into * the last occurrence. (Note that it may not be strung between the same left @@ -1713,11 +1745,11 @@ subre( v->treechain = ret; } - assert(strchr("|.b(=", op) != NULL); + assert(strchr("=b|.*(", op) != NULL); ret->op = op; ret->flags = flags; - ret->retry = 0; + ret->id = 0; /* will be assigned later */ ret->subno = 0; ret->min = ret->max = 1; ret->left = NULL; @@ -1770,7 +1802,8 @@ freesrnode( } sr->flags = 0; - if (v != NULL) { + if (v != NULL && v->treechain != NULL) { + /* we're still parsing, maybe we can reuse the subre */ sr->left = v->treefree; v->treefree = sr; } else { @@ -1798,7 +1831,7 @@ optst( } /* - - numst - number tree nodes (assigning retry indexes) + - numst - number tree nodes (assigning "id" indexes) ^ static int numst(struct subre *, int); */ static int /* next number */ @@ -1811,7 +1844,7 @@ numst( assert(t != NULL); i = start; - t->retry = (short) i++; + t->id = (short) i++; if (t->left != NULL) { i = numst(t->left, i); } @@ -1823,6 +1856,19 @@ numst( /* - markst - mark tree nodes as INUSE + * Note: this is a great deal more subtle than it looks. During initial + * parsing of a regex, all subres are linked into the treechain list; + * discarded ones are also linked into the treefree list for possible reuse. + * After we are done creating all subres required for a regex, we run markst() + * then cleanst(), which results in discarding all subres not reachable from + * v->tree. We then clear v->treechain, indicating that subres must be found + * by descending from v->tree. This changes the behavior of freesubre(): it + * will henceforth FREE() unwanted subres rather than sticking them into the + * treefree list. (Doing that any earlier would result in dangling links in + * the treechain list.) This all means that freev() will clean up correctly + * if invoked before or after markst()+cleanst(); but it would not work if + * called partway through this state conversion, so we mustn't error out + * in or between these two functions. ^ static void markst(struct subre *); */ static void @@ -1929,24 +1975,26 @@ newlacon( struct state *end, int pos) { - struct subre *sub; int n; + struct subre *newlacons; + struct subre *sub; if (v->nlacons == 0) { - v->lacons = (struct subre *) MALLOC(2 * sizeof(struct subre)); n = 1; /* skip 0th */ - v->nlacons = 2; + newlacons = (struct subre *) MALLOC(2 * sizeof(struct subre)); } else { - v->lacons = (struct subre *) REALLOC(v->lacons, - (v->nlacons+1)*sizeof(struct subre)); - n = v->nlacons++; + n = v->nlacons; + newlacons = (struct subre *) REALLOC(v->lacons, + (n + 1) * sizeof(struct subre)); } - if (v->lacons == NULL) { + if (newlacons == NULL) { ERR(REG_ESPACE); return 0; } + v->lacons = newlacons; + v->nlacons = n + 1; sub = &v->lacons[n]; sub->begin = begin; sub->end = end; @@ -1994,18 +2042,20 @@ rfree( g = (struct guts *) re->re_guts; re->re_guts = NULL; re->re_fns = NULL; - g->magic = 0; - freecm(&g->cmap); - if (g->tree != NULL) { - freesubre(NULL, g->tree); - } - if (g->lacons != NULL) { - freelacons(g->lacons, g->nlacons); - } - if (!NULLCNFA(g->search)) { - freecnfa(&g->search); + if (g != NULL) { + g->magic = 0; + freecm(&g->cmap); + if (g->tree != NULL) { + freesubre(NULL, g->tree); + } + if (g->lacons != NULL) { + freelacons(g->lacons, g->nlacons); + } + if (!NULLCNFA(g->search)) { + freecnfa(&g->search); + } + FREE(g); } - FREE(g); } /* @@ -2037,11 +2087,11 @@ dump( fprintf(f, "\n\n\n========= DUMP ==========\n"); fprintf(f, "nsub %d, info 0%lo, csize %d, ntree %d\n", - re->re_nsub, re->re_info, re->re_csize, g->ntree); + (int) re->re_nsub, re->re_info, re->re_csize, g->ntree); dumpcolors(&g->cmap, f); if (!NULLCNFA(g->search)) { - printf("\nsearch:\n"); + fprintf(f, "\nsearch:\n"); dumpcnfa(&g->search, f); } for (i = 1; i < g->nlacons; i++) { @@ -2146,14 +2196,14 @@ stid( size_t bufsize) { /* - * Big enough for hex int or decimal t->retry? + * Big enough for hex int or decimal t->id? */ - if (bufsize < sizeof(void*)*2 + 3 || bufsize < sizeof(t->retry)*3 + 1) { + if (bufsize < sizeof(void*)*2 + 3 || bufsize < sizeof(t->id)*3 + 1) { return "unable"; } - if (t->retry != 0) { - sprintf(buf, "%d", t->retry); + if (t->id != 0) { + sprintf(buf, "%d", t->id); } else { sprintf(buf, "%p", t); } diff --git a/generic/rege_dfa.c b/generic/rege_dfa.c index 920ea6c..e5f22c4 100644 --- a/generic/rege_dfa.c +++ b/generic/rege_dfa.c @@ -84,7 +84,7 @@ longest( if (v->eflags®_FTRACE) { while (cp < realstop) { - FDEBUG(("+++ at c%d +++\n", css - d->ssets)); + FDEBUG(("+++ at c%d +++\n", (int) (css - d->ssets))); co = GETCOLOR(cm, *cp); FDEBUG(("char %c, color %ld\n", (char)*cp, (long)co)); ss = css->outs[co]; @@ -118,7 +118,7 @@ longest( * Shutdown. */ - FDEBUG(("+++ shutdown at c%d +++\n", css - d->ssets)); + FDEBUG(("+++ shutdown at c%d +++\n", (int) (css - d->ssets))); if (cp == v->stop && stop == v->stop) { if (hitstopp != NULL) { *hitstopp = 1; @@ -213,7 +213,7 @@ shortest( if (v->eflags®_FTRACE) { while (cp < realmax) { - FDEBUG(("--- at c%d ---\n", css - d->ssets)); + FDEBUG(("--- at c%d ---\n", (int) (css - d->ssets))); co = GETCOLOR(cm, *cp); FDEBUG(("char %c, color %ld\n", (char)*cp, (long)co)); ss = css->outs[co]; @@ -516,14 +516,14 @@ miss( gotState = 0; for (i = 0; i < d->nstates; i++) { if (ISBSET(css->states, i)) { - for (ca = cnfa->states[i]+1; ca->co != COLORLESS; ca++) { + for (ca = cnfa->states[i]; ca->co != COLORLESS; ca++) { if (ca->co == co) { BSET(d->work, ca->to); gotState = 1; if (ca->to == cnfa->post) { isPost = 1; } - if (!cnfa->states[ca->to]->co) { + if (!(cnfa->stflags[ca->to] & CNFA_NOPROGRESS)) { noProgress = 0; } FDEBUG(("%d -> %d\n", i, ca->to)); @@ -537,8 +537,8 @@ miss( doLAConstraints = 0; for (i = 0; i < d->nstates; i++) { if (ISBSET(d->work, i)) { - for (ca = cnfa->states[i]+1; ca->co != COLORLESS; ca++) { - if (ca->co <= cnfa->ncolors) { + for (ca = cnfa->states[i]; ca->co != COLORLESS; ca++) { + if (ca->co < cnfa->ncolors) { continue; /* NOTE CONTINUE */ } sawLAConstraints = 1; @@ -553,7 +553,7 @@ miss( if (ca->to == cnfa->post) { isPost = 1; } - if (!cnfa->states[ca->to]->co) { + if (!(cnfa->stflags[ca->to] & CNFA_NOPROGRESS)) { noProgress = 0; } FDEBUG(("%d :> %d\n", i, ca->to)); @@ -572,7 +572,7 @@ miss( for (p = d->ssets, i = d->nssused; i > 0; p++, i--) { if (HIT(h, d->work, p, d->wordsper)) { - FDEBUG(("cached c%d\n", p - d->ssets)); + FDEBUG(("cached c%d\n", (int) (p - d->ssets))); break; /* NOTE BREAK OUT */ } } @@ -594,7 +594,8 @@ miss( } if (!sawLAConstraints) { /* lookahead conds. always cache miss */ - FDEBUG(("c%d[%d]->c%d\n", css - d->ssets, co, p - d->ssets)); + FDEBUG(("c%d[%d]->c%d\n", + (int) (css - d->ssets), co, (int) (p - d->ssets))); css->outs[co] = p; css->inchain[co] = p->ins; p->ins.ss = css; @@ -663,7 +664,7 @@ getVacantSS( ap = ss->ins; while ((p = ap.ss) != NULL) { co = ap.co; - FDEBUG(("zapping c%d's %ld outarc\n", p - d->ssets, (long)co)); + FDEBUG(("zapping c%d's %ld outarc\n", (int) (p - d->ssets), (long)co)); p->outs[co] = NULL; ap = p->inchain[co]; p->inchain[co].ss = NULL; /* paranoia */ @@ -680,7 +681,7 @@ getVacantSS( if (p == NULL) { continue; /* NOTE CONTINUE */ } - FDEBUG(("del outarc %d from c%d's in chn\n", i, p - d->ssets)); + FDEBUG(("del outarc %d from c%d's in chn\n", i, (int) (p - d->ssets))); if (p->ins.ss == ss && p->ins.co == i) { p->ins = ss->inchain[i]; } else { @@ -772,7 +773,7 @@ pickNextSS( if ((ss->lastseen == NULL || ss->lastseen < ancient) && !(ss->flags&LOCKED)) { d->search = ss + 1; - FDEBUG(("replacing c%d\n", ss - d->ssets)); + FDEBUG(("replacing c%d\n", (int) (ss - d->ssets))); return ss; } } @@ -780,7 +781,7 @@ pickNextSS( if ((ss->lastseen == NULL || ss->lastseen < ancient) && !(ss->flags&LOCKED)) { d->search = ss + 1; - FDEBUG(("replacing c%d\n", ss - d->ssets)); + FDEBUG(("replacing c%d\n", (int) (ss - d->ssets))); return ss; } } diff --git a/generic/regerror.c b/generic/regerror.c index a1a0163..49d93ed 100644 --- a/generic/regerror.c +++ b/generic/regerror.c @@ -41,7 +41,7 @@ static const char unk[] = "*** unknown regex error code 0x%x ***"; * Struct to map among codes, code names, and explanations. */ -static struct rerr { +static const struct rerr { int code; const char *name; const char *explain; @@ -62,7 +62,7 @@ regerror( char *errbuf, /* Result buffer (unless errbuf_size==0) */ size_t errbuf_size) /* Available space in errbuf, can be 0 */ { - struct rerr *r; + const struct rerr *r; const char *msg; char convbuf[sizeof(unk)+50]; /* 50 = plenty for int */ size_t len; diff --git a/generic/regerrs.h b/generic/regerrs.h index 72548ff..ee203d5 100644 --- a/generic/regerrs.h +++ b/generic/regerrs.h @@ -16,5 +16,5 @@ { REG_INVARG, "REG_INVARG", "invalid argument to regex function" }, { REG_MIXED, "REG_MIXED", "character widths of regex and string differ" }, { REG_BADOPT, "REG_BADOPT", "invalid embedded option" }, -{ REG_ETOOBIG, "REG_ETOOBIG", "nfa has too many states" }, +{ REG_ETOOBIG, "REG_ETOOBIG", "regular expression is too complex" }, { REG_ECOLORS, "REG_ECOLORS", "too many colors" }, diff --git a/generic/regex.h b/generic/regex.h index 9466fbb..53450e5 100644 --- a/generic/regex.h +++ b/generic/regex.h @@ -280,7 +280,7 @@ typedef struct { #define REG_INVARG 16 /* invalid argument to regex function */ #define REG_MIXED 17 /* character widths of regex and string differ */ #define REG_BADOPT 18 /* invalid embedded option */ -#define REG_ETOOBIG 19 /* nfa has too many states */ +#define REG_ETOOBIG 19 /* regular expression is too complex */ #define REG_ECOLORS 20 /* too many colors */ /* two specials for debugging and testing */ #define REG_ATOI 101 /* convert error-code name to number */ diff --git a/generic/regexec.c b/generic/regexec.c index 3b9af3e..6d12827 100644 --- a/generic/regexec.c +++ b/generic/regexec.c @@ -107,13 +107,13 @@ struct vars { chr *start; /* start of string */ chr *stop; /* just past end of string */ int err; /* error code if any (0 none) */ - regoff_t *mem; /* memory vector for backtracking */ + struct dfa **subdfas; /* per-subre DFAs */ struct smalldfa dfa1; struct smalldfa dfa2; }; #define VISERR(vv) ((vv)->err != 0) /* have we seen an error yet? */ #define ISERR() VISERR(v) -#define VERR(vv,e) (((vv)->err) ? (vv)->err : ((vv)->err = (e))) +#define VERR(vv,e) ((vv)->err = ((vv)->err ? (vv)->err : (e))) #define ERR(e) VERR(v, e) /* record an error */ #define NOERR() {if (ISERR()) return v->err;} /* if error seen, return it */ #define OFF(p) ((p) - v->start) @@ -126,21 +126,20 @@ struct vars { /* automatically gathered by fwd; do not hand-edit */ /* === regexec.c === */ int exec(regex_t *, const chr *, size_t, rm_detail_t *, size_t, regmatch_t [], int); +static struct dfa *getsubdfa(struct vars *, struct subre *); static int simpleFind(struct vars *const, struct cnfa *const, struct colormap *const); static int complicatedFind(struct vars *const, struct cnfa *const, struct colormap *const); static int complicatedFindLoop(struct vars *const, struct cnfa *const, struct colormap *const, struct dfa *const, struct dfa *const, chr **const); -static void zapSubexpressions(regmatch_t *const, const size_t); -static void zapSubtree(struct vars *const, struct subre *const); +static void zapallsubs(regmatch_t *const, const size_t); +static void zaptreesubs(struct vars *const, struct subre *const); static void subset(struct vars *const, struct subre *const, chr *const, chr *const); -static int dissect(struct vars *const, struct subre *, chr *const, chr *const); -static int concatenationDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int alternationDissect(struct vars *const, struct subre *, chr *const, chr *const); -static inline int complicatedDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int complicatedCapturingDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int complicatedConcatenationDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int complicatedReversedDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int complicatedBackrefDissect(struct vars *const, struct subre *const, chr *const, chr *const); -static int complicatedAlternationDissect(struct vars *const, struct subre *, chr *const, chr *const); +static int cdissect(struct vars *, struct subre *, chr *, chr *); +static int ccondissect(struct vars *, struct subre *, chr *, chr *); +static int crevcondissect(struct vars *, struct subre *, chr *, chr *); +static int cbrdissect(struct vars *, struct subre *, chr *, chr *); +static int caltdissect(struct vars *, struct subre *, chr *, chr *); +static int citerdissect(struct vars *, struct subre *, chr *, chr *); +static int creviterdissect(struct vars *, struct subre *, chr *, chr *); /* === rege_dfa.c === */ static chr *longest(struct vars *const, struct dfa *const, chr *const, chr *const, int *const); static chr *shortest(struct vars *const, struct dfa *const, chr *const, chr *const, chr *const, chr **const, int *const); @@ -174,10 +173,11 @@ exec( AllocVars(v); int st, backref; size_t n; + size_t i; #define LOCALMAT 20 regmatch_t mat[LOCALMAT]; -#define LOCALMEM 40 - regoff_t mem[LOCALMEM]; +#define LOCALDFAS 40 + struct dfa *subdfas[LOCALDFAS]; /* * Sanity checks. @@ -235,28 +235,20 @@ exec( v->start = (chr *)string; v->stop = (chr *)string + len; v->err = 0; - if (backref) { - /* - * Need retry memory. - */ - - assert(v->g->ntree >= 0); - n = (size_t)v->g->ntree; - if (n <= LOCALMEM) { - v->mem = mem; - } else { - v->mem = (regoff_t *) MALLOC(n*sizeof(regoff_t)); - } - if (v->mem == NULL) { - if (v->pmatch != pmatch && v->pmatch != mat) { - FREE(v->pmatch); - } - FreeVars(v); - return REG_ESPACE; - } - } else { - v->mem = NULL; + assert(v->g->ntree >= 0); + n = (size_t) v->g->ntree; + if (n <= LOCALDFAS) + v->subdfas = subdfas; + else + v->subdfas = (struct dfa **) MALLOC(n * sizeof(struct dfa *)); + if (v->subdfas == NULL) { + if (v->pmatch != pmatch && v->pmatch != mat) + FREE(v->pmatch); + FreeVars(v); + return REG_ESPACE; } + for (i = 0; i < n; i++) + v->subdfas[i] = NULL; /* * Do it. @@ -274,7 +266,7 @@ exec( */ if (st == REG_OKAY && v->pmatch != pmatch && nmatch > 0) { - zapSubexpressions(pmatch, nmatch); + zapallsubs(pmatch, nmatch); n = (nmatch < v->nmatch) ? nmatch : v->nmatch; memcpy(VS(pmatch), VS(v->pmatch), n*sizeof(regmatch_t)); } @@ -286,14 +278,35 @@ exec( if (v->pmatch != pmatch && v->pmatch != mat) { FREE(v->pmatch); } - if (v->mem != NULL && v->mem != mem) { - FREE(v->mem); + n = (size_t) v->g->ntree; + for (i = 0; i < n; i++) { + if (v->subdfas[i] != NULL) + freeDFA(v->subdfas[i]); } + if (v->subdfas != subdfas) + FREE(v->subdfas); FreeVars(v); return st; } /* + - getsubdfa - create or re-fetch the DFA for a subre node + * We only need to create the DFA once per overall regex execution. + * The DFA will be freed by the cleanup step in exec(). + */ +static struct dfa * +getsubdfa(struct vars * v, + struct subre * t) +{ + if (v->subdfas[t->id] == NULL) { + v->subdfas[t->id] = newDFA(v, &t->cnfa, &v->g->cmap, DOMALLOC); + if (ISERR()) + return NULL; + } + return v->subdfas[t->id]; +} + +/* - simpleFind - find a match for the main NFA (no-complications case) ^ static int simpleFind(struct vars *, struct cnfa *, struct colormap *); */ @@ -357,7 +370,10 @@ simpleFind( } else { end = longest(v, d, begin, v->stop, &hitend); } - NOERR(); + if (ISERR()) { + freeDFA(d); + return v->err; + } if (hitend && cold == NULL) { cold = begin; } @@ -388,11 +404,11 @@ simpleFind( } /* - * Submatches. + * Find submatches. */ - zapSubexpressions(v->pmatch, v->nmatch); - return dissect(v, v->g->tree, begin, end); + zapallsubs(v->pmatch, v->nmatch); + return cdissect(v, v->g->tree, begin, end); } /* @@ -488,9 +504,8 @@ complicatedFindLoop( } MDEBUG(("tentative end %ld\n", LOFF(end))); - zapSubexpressions(v->pmatch, v->nmatch); - zapSubtree(v, v->g->tree); - er = complicatedDissect(v, v->g->tree, begin, end); + zapallsubs(v->pmatch, v->nmatch); + er = cdissect(v, v->g->tree, begin, end); if (er == REG_OKAY) { if (v->nmatch > 0) { v->pmatch[0].rm_so = OFF(begin); @@ -501,6 +516,7 @@ complicatedFindLoop( } if (er != REG_NOMATCH) { ERR(er); + *coldp = cold; return er; } if ((shorter) ? end == estop : end == begin) { @@ -525,11 +541,11 @@ complicatedFindLoop( } /* - - zapSubexpressions - initialize the subexpression matches to "no match" - ^ static void zapSubexpressions(regmatch_t *, size_t); + - zapallsubs - initialize all subexpression matches to "no match" + ^ static void zapallsubs(regmatch_t *, size_t); */ static void -zapSubexpressions( +zapallsubs( regmatch_t *const p, const size_t n) { @@ -542,36 +558,33 @@ zapSubexpressions( } /* - - zapSubtree - initialize the retry memory of a subtree to zeros - ^ static void zapSubtree(struct vars *, struct subre *); + - zaptreesubs - initialize subexpressions within subtree to "no match" + ^ static void zaptreesubs(struct vars *, struct subre *); */ static void -zapSubtree( +zaptreesubs( struct vars *const v, struct subre *const t) { - if (t == NULL) { - return; - } - - assert(v->mem != NULL); - v->mem[t->retry] = 0; if (t->op == '(') { - assert(t->subno > 0); - v->pmatch[t->subno].rm_so = -1; - v->pmatch[t->subno].rm_eo = -1; + int n = t->subno; + assert(n > 0); + if ((size_t) n < v->nmatch) { + v->pmatch[n].rm_so = -1; + v->pmatch[n].rm_eo = -1; + } } if (t->left != NULL) { - zapSubtree(v, t->left); + zaptreesubs(v, t->left); } if (t->right != NULL) { - zapSubtree(v, t->right); + zaptreesubs(v, t->right); } } /* - - subset - set any subexpression relevant to a successful subre + - subset - set subexpression match data for a successful subre ^ static void subset(struct vars *, struct subre *, chr *, chr *); */ static void @@ -594,247 +607,91 @@ subset( } /* - - dissect - determine subexpression matches (uncomplicated case) - ^ static int dissect(struct vars *, struct subre *, chr *, chr *); + - cdissect - check backrefs and determine subexpression matches + * cdissect recursively processes a subre tree to check matching of backrefs + * and/or identify submatch boundaries for capture nodes. The proposed match + * runs from "begin" to "end" (not including "end"), and we are basically + * "dissecting" it to see where the submatches are. + * Before calling any level of cdissect, the caller must have run the node's + * DFA and found that the proposed substring satisfies the DFA. (We make + * the caller do that because in concatenation and iteration nodes, it's + * much faster to check all the substrings against the child DFAs before we + * recurse.) Also, caller must have cleared subexpression match data via + * zaptreesubs (or zapallsubs at the top level). + ^ static int cdissect(struct vars *, struct subre *, chr *, chr *); */ static int /* regexec return code */ -dissect( - struct vars *const v, +cdissect( + struct vars *v, struct subre *t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ { -#ifndef COMPILER_DOES_TAILCALL_OPTIMIZATION - restart: -#endif - assert(t != NULL); - MDEBUG(("dissect %ld-%ld\n", LOFF(begin), LOFF(end))); - - switch (t->op) { - case '=': /* terminal node */ - assert(t->left == NULL && t->right == NULL); - return REG_OKAY; /* no action, parent did the work */ - case '|': /* alternation */ - assert(t->left != NULL); - return alternationDissect(v, t, begin, end); - case 'b': /* back ref -- shouldn't be calling us! */ - return REG_ASSERT; - case '.': /* concatenation */ - assert(t->left != NULL && t->right != NULL); - return concatenationDissect(v, t, begin, end); - case '(': /* capturing */ - assert(t->left != NULL && t->right == NULL); - assert(t->subno > 0); - subset(v, t, begin, end); -#ifndef COMPILER_DOES_TAILCALL_OPTIMIZATION - t = t->left; - goto restart; -#else - return dissect(v, t->left, begin, end); -#endif - default: - return REG_ASSERT; - } -} - -/* - - concatenationDissect - determine concatenation subexpression matches - - (uncomplicated) - ^ static int concatenationDissect(struct vars *, struct subre *, chr *, chr *); - */ -static int /* regexec return code */ -concatenationDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ -{ - struct dfa *d, *d2; - chr *mid; - int i; - int shorter = (t->left->flags&SHORTER) ? 1 : 0; - chr *stop = (shorter) ? end : begin; - - assert(t->op == '.'); - assert(t->left != NULL && t->left->cnfa.nstates > 0); - assert(t->right != NULL && t->right->cnfa.nstates > 0); - - d = newDFA(v, &t->left->cnfa, &v->g->cmap, &v->dfa1); - NOERR(); - d2 = newDFA(v, &t->right->cnfa, &v->g->cmap, &v->dfa2); - if (ISERR()) { - assert(d2 == NULL); - freeDFA(d); - return v->err; - } - - /* - * Pick a tentative midpoint. - */ - - if (shorter) { - mid = shortest(v, d, begin, begin, end, NULL, NULL); - } else { - mid = longest(v, d, begin, end, NULL); - } - if (mid == NULL) { - freeDFA(d); - freeDFA(d2); - return REG_ASSERT; - } - MDEBUG(("tentative midpoint %ld\n", LOFF(mid))); - - /* - * Iterate until satisfaction or failure. - */ - - while (longest(v, d2, mid, end, NULL) != end) { - /* - * That midpoint didn't work, find a new one. - */ - - if (mid == stop) { - /* - * All possibilities exhausted! - */ - - MDEBUG(("no midpoint!\n")); - freeDFA(d); - freeDFA(d2); - return REG_ASSERT; - } - if (shorter) { - mid = shortest(v, d, begin, mid+1, end, NULL, NULL); - } else { - mid = longest(v, d, begin, mid-1, NULL); - } - if (mid == NULL) { - /* - * Failed to find a new one! - */ - - MDEBUG(("failed midpoint!\n")); - freeDFA(d); - freeDFA(d2); - return REG_ASSERT; - } - MDEBUG(("new midpoint %ld\n", LOFF(mid))); - } - - /* - * Satisfaction. - */ - - MDEBUG(("successful\n")); - freeDFA(d); - freeDFA(d2); - i = dissect(v, t->left, begin, mid); - if (i != REG_OKAY) { - return i; - } - return dissect(v, t->right, mid, end); -} - -/* - - alternationDissect - determine alternative subexpression matches (uncomplicated) - ^ static int alternationDissect(struct vars *, struct subre *, chr *, chr *); - */ -static int /* regexec return code */ -alternationDissect( - struct vars *const v, - struct subre *t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ -{ - int i; - - assert(t != NULL); - assert(t->op == '|'); - - for (i = 0; t != NULL; t = t->right, i++) { - struct dfa *d; + int er; - MDEBUG(("trying %dth\n", i)); - assert(t->left != NULL && t->left->cnfa.nstates > 0); - d = newDFA(v, &t->left->cnfa, &v->g->cmap, &v->dfa1); - if (ISERR()) { - return v->err; - } - if (longest(v, d, begin, end, NULL) == end) { - MDEBUG(("success\n")); - freeDFA(d); - return dissect(v, t->left, begin, end); - } - freeDFA(d); - } - return REG_ASSERT; /* none of them matched?!? */ -} - -/* - - complicatedDissect - determine subexpression matches (with complications) - * The retry memory stores the offset of the trial midpoint from begin, plus 1 - * so that 0 uniquely means "clean slate". - ^ static int complicatedDissect(struct vars *, struct subre *, chr *, chr *); - */ -static inline int /* regexec return code */ -complicatedDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ -{ assert(t != NULL); - MDEBUG(("complicatedDissect %ld-%ld %c\n", LOFF(begin), LOFF(end), t->op)); + MDEBUG(("cdissect %ld-%ld %c\n", LOFF(begin), LOFF(end), t->op)); switch (t->op) { case '=': /* terminal node */ assert(t->left == NULL && t->right == NULL); - return REG_OKAY; /* no action, parent did the work */ - case '|': /* alternation */ - assert(t->left != NULL); - return complicatedAlternationDissect(v, t, begin, end); - case 'b': /* back ref -- shouldn't be calling us! */ + er = REG_OKAY; /* no action, parent did the work */ + break; + case 'b': /* back reference */ assert(t->left == NULL && t->right == NULL); - return complicatedBackrefDissect(v, t, begin, end); + er = cbrdissect(v, t, begin, end); + break; case '.': /* concatenation */ assert(t->left != NULL && t->right != NULL); - return complicatedConcatenationDissect(v, t, begin, end); + if (t->left->flags & SHORTER) /* reverse scan */ + er = crevcondissect(v, t, begin, end); + else + er = ccondissect(v, t, begin, end); + break; + case '|': /* alternation */ + assert(t->left != NULL); + er = caltdissect(v, t, begin, end); + break; + case '*': /* iteration */ + assert(t->left != NULL); + if (t->left->flags & SHORTER) /* reverse scan */ + er = creviterdissect(v, t, begin, end); + else + er = citerdissect(v, t, begin, end); + break; case '(': /* capturing */ assert(t->left != NULL && t->right == NULL); assert(t->subno > 0); - return complicatedCapturingDissect(v, t, begin, end); + er = cdissect(v, t->left, begin, end); + if (er == REG_OKAY) { + subset(v, t, begin, end); + } + break; default: - return REG_ASSERT; + er = REG_ASSERT; + break; } -} -static int /* regexec return code */ -complicatedCapturingDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ -{ - int er = complicatedDissect(v, t->left, begin, end); + /* + * We should never have a match failure unless backrefs lurk below; + * otherwise, either caller failed to check the DFA, or there's some + * inconsistency between the DFA and the node's innards. + */ + assert(er != REG_NOMATCH || (t->flags & BACKR)); - if (er == REG_OKAY) { - subset(v, t, begin, end); - } return er; } /* - - complicatedConcatenationDissect - concatenation subexpression matches (with complications) - * The retry memory stores the offset of the trial midpoint from begin, plus 1 - * so that 0 uniquely means "clean slate". - ^ static int complicatedConcatenationDissect(struct vars *, struct subre *, chr *, chr *); + - ccondissect - dissect match for concatenation node + ^ static int ccondissect(struct vars *, struct subre *, chr *, chr *); */ static int /* regexec return code */ -complicatedConcatenationDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ +ccondissect( + struct vars *v, + struct subre *t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ { struct dfa *d, *d2; chr *mid; @@ -842,39 +699,23 @@ complicatedConcatenationDissect( assert(t->op == '.'); assert(t->left != NULL && t->left->cnfa.nstates > 0); assert(t->right != NULL && t->right->cnfa.nstates > 0); + assert(!(t->left->flags & SHORTER)); - if (t->left->flags&SHORTER) { /* reverse scan */ - return complicatedReversedDissect(v, t, begin, end); - } + d = getsubdfa(v, t->left); + NOERR(); + d2 = getsubdfa(v, t->right); + NOERR(); - d = newDFA(v, &t->left->cnfa, &v->g->cmap, DOMALLOC); - if (ISERR()) { - return v->err; - } - d2 = newDFA(v, &t->right->cnfa, &v->g->cmap, DOMALLOC); - if (ISERR()) { - freeDFA(d); - return v->err; - } - MDEBUG(("cConcat %d\n", t->retry)); + MDEBUG(("cConcat %d\n", t->id)); /* * Pick a tentative midpoint. */ - - if (v->mem[t->retry] == 0) { - mid = longest(v, d, begin, end, NULL); - if (mid == NULL) { - freeDFA(d); - freeDFA(d2); - return REG_NOMATCH; - } - MDEBUG(("tentative midpoint %ld\n", LOFF(mid))); - v->mem[t->retry] = (mid - begin) + 1; - } else { - mid = begin + (v->mem[t->retry] - 1); - MDEBUG(("working midpoint %ld\n", LOFF(mid))); + mid = longest(v, d, begin, end, (int *) NULL); + if (mid == NULL) { + return REG_NOMATCH; } + MDEBUG(("tentative midpoint %ld\n", LOFF(mid))); /* * Iterate until satisfaction or failure. @@ -886,24 +727,20 @@ complicatedConcatenationDissect( */ if (longest(v, d2, mid, end, NULL) == end) { - int er = complicatedDissect(v, t->left, begin, mid); + int er = cdissect(v, t->left, begin, mid); if (er == REG_OKAY) { - er = complicatedDissect(v, t->right, mid, end); + er = cdissect(v, t->right, mid, end); if (er == REG_OKAY) { /* * Satisfaction. */ MDEBUG(("successful\n")); - freeDFA(d); - freeDFA(d2); return REG_OKAY; } } - if ((er != REG_OKAY) && (er != REG_NOMATCH)) { - freeDFA(d); - freeDFA(d2); + if (er != REG_NOMATCH) { return er; } } @@ -917,9 +754,7 @@ complicatedConcatenationDissect( * All possibilities exhausted. */ - MDEBUG(("%d no midpoint\n", t->retry)); - freeDFA(d); - freeDFA(d2); + MDEBUG(("%d no midpoint\n", t->id)); return REG_NOMATCH; } mid = longest(v, d, begin, mid-1, NULL); @@ -928,31 +763,25 @@ complicatedConcatenationDissect( * Failed to find a new one. */ - MDEBUG(("%d failed midpoint\n", t->retry)); - freeDFA(d); - freeDFA(d2); + MDEBUG(("%d failed midpoint\n", t->id)); return REG_NOMATCH; } - MDEBUG(("%d: new midpoint %ld\n", t->retry, LOFF(mid))); - v->mem[t->retry] = (mid - begin) + 1; - zapSubtree(v, t->left); - zapSubtree(v, t->right); + MDEBUG(("%d: new midpoint %ld\n", t->id, LOFF(mid))); + zaptreesubs(v, t->left); + zaptreesubs(v, t->right); } } /* - - complicatedReversedDissect - determine backref shortest-first subexpression - - matches - * The retry memory stores the offset of the trial midpoint from begin, plus 1 - * so that 0 uniquely means "clean slate". - ^ static int complicatedReversedDissect(struct vars *, struct subre *, chr *, chr *); + - crevcondissect - dissect match for concatenation node, shortest-first + ^ static int crevcondissect(struct vars *, struct subre *, chr *, chr *); */ static int /* regexec return code */ -complicatedReversedDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ +crevcondissect( + struct vars *v, + struct subre *t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ { struct dfa *d, *d2; chr *mid; @@ -962,38 +791,22 @@ complicatedReversedDissect( assert(t->right != NULL && t->right->cnfa.nstates > 0); assert(t->left->flags&SHORTER); - /* - * Concatenation -- need to split the substring between parts. - */ + d = getsubdfa(v, t->left); + NOERR(); + d2 = getsubdfa(v, t->right); + NOERR(); - d = newDFA(v, &t->left->cnfa, &v->g->cmap, DOMALLOC); - if (ISERR()) { - return v->err; - } - d2 = newDFA(v, &t->right->cnfa, &v->g->cmap, DOMALLOC); - if (ISERR()) { - freeDFA(d); - return v->err; - } - MDEBUG(("cRev %d\n", t->retry)); + MDEBUG(("crevcon %d\n", t->id)); /* * Pick a tentative midpoint. */ - if (v->mem[t->retry] == 0) { - mid = shortest(v, d, begin, begin, end, NULL, NULL); - if (mid == NULL) { - freeDFA(d); - freeDFA(d2); - return REG_NOMATCH; - } - MDEBUG(("tentative midpoint %ld\n", LOFF(mid))); - v->mem[t->retry] = (mid - begin) + 1; - } else { - mid = begin + (v->mem[t->retry] - 1); - MDEBUG(("working midpoint %ld\n", LOFF(mid))); + mid = shortest(v, d, begin, begin, end, (chr **) NULL, (int *) NULL); + if (mid == NULL) { + return REG_NOMATCH; } + MDEBUG(("tentative midpoint %ld\n", LOFF(mid))); /* * Iterate until satisfaction or failure. @@ -1005,24 +818,20 @@ complicatedReversedDissect( */ if (longest(v, d2, mid, end, NULL) == end) { - int er = complicatedDissect(v, t->left, begin, mid); + int er = cdissect(v, t->left, begin, mid); if (er == REG_OKAY) { - er = complicatedDissect(v, t->right, mid, end); + er = cdissect(v, t->right, mid, end); if (er == REG_OKAY) { /* * Satisfaction. */ MDEBUG(("successful\n")); - freeDFA(d); - freeDFA(d2); return REG_OKAY; } } - if (er != REG_OKAY && er != REG_NOMATCH) { - freeDFA(d); - freeDFA(d2); + if (er != REG_NOMATCH) { return er; } } @@ -1036,9 +845,7 @@ complicatedReversedDissect( * All possibilities exhausted. */ - MDEBUG(("%d no midpoint\n", t->retry)); - freeDFA(d); - freeDFA(d2); + MDEBUG(("%d no midpoint\n", t->id)); return REG_NOMATCH; } mid = shortest(v, d, begin, mid+1, end, NULL, NULL); @@ -1047,164 +854,474 @@ complicatedReversedDissect( * Failed to find a new one. */ - MDEBUG(("%d failed midpoint\n", t->retry)); - freeDFA(d); - freeDFA(d2); + MDEBUG(("%d failed midpoint\n", t->id)); return REG_NOMATCH; } - MDEBUG(("%d: new midpoint %ld\n", t->retry, LOFF(mid))); - v->mem[t->retry] = (mid - begin) + 1; - zapSubtree(v, t->left); - zapSubtree(v, t->right); + MDEBUG(("%d: new midpoint %ld\n", t->id, LOFF(mid))); + zaptreesubs(v, t->left); + zaptreesubs(v, t->right); } } /* - - complicatedBackrefDissect - determine backref subexpression matches - ^ static int complicatedBackrefDissect(struct vars *, struct subre *, chr *, chr *); + - cbrdissect - dissect match for backref node + ^ static int cbrdissect(struct vars *, struct subre *, chr *, chr *); */ static int /* regexec return code */ -complicatedBackrefDissect( - struct vars *const v, - struct subre *const t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ +cbrdissect( + struct vars *v, + struct subre *t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ { - int i, n = t->subno, min = t->min, max = t->max; - chr *paren, *p, *stop; - size_t len; + int n = t->subno, min = t->min, max = t->max; + size_t numreps; + size_t tlen; + size_t brlen; + chr *brstring; + chr *p; assert(t != NULL); assert(t->op == 'b'); assert(n >= 0); assert((size_t)n < v->nmatch); - MDEBUG(("cbackref n%d %d{%d-%d}\n", t->retry, n, min, max)); + MDEBUG(("cbackref n%d %d{%d-%d}\n", t->id, n, min, max)); + /* get the backreferenced string */ if (v->pmatch[n].rm_so == -1) { return REG_NOMATCH; } - paren = v->start + v->pmatch[n].rm_so; - len = v->pmatch[n].rm_eo - v->pmatch[n].rm_so; + brstring = v->start + v->pmatch[n].rm_so; + brlen = v->pmatch[n].rm_eo - v->pmatch[n].rm_so; - /* - * No room to maneuver -- retries are pointless. - */ - - if (v->mem[t->retry]) { + /* special cases for zero-length strings */ + if (brlen == 0) { + /* + * matches only if target is zero length, but any number of + * repetitions can be considered to be present + */ + if (begin == end && min <= max) { + MDEBUG(("cbackref matched trivially\n")); + return REG_OKAY; + } return REG_NOMATCH; } - v->mem[t->retry] = 1; - - /* - * Special-case zero-length string. - */ - - if (len == 0) { - if (begin == end) { + if (begin == end) { + /* matches only if zero repetitions are okay */ + if (min == 0) { + MDEBUG(("cbackref matched trivially\n")); return REG_OKAY; } return REG_NOMATCH; } /* - * And too-short string. + * check target length to see if it could possibly be an allowed number of + * repetitions of brstring */ - assert(end >= begin); - if ((size_t)(end - begin) < len) { + assert(end > begin); + tlen = end - begin; + if (tlen % brlen != 0) + return REG_NOMATCH; + numreps = tlen / brlen; + if (numreps < (size_t)min || (numreps > (size_t)max && max != DUPINF)) return REG_NOMATCH; + + /* okay, compare the actual string contents */ + p = begin; + while (numreps-- > 0) { + if ((*v->g->compare) (brstring, p, brlen) != 0) + return REG_NOMATCH; + p += brlen; } - stop = end - len; - /* - * Count occurrences. - */ + MDEBUG(("cbackref matched\n")); + return REG_OKAY; +} + +/* + - caltdissect - dissect match for alternation node + ^ static int caltdissect(struct vars *, struct subre *, chr *, chr *); + */ +static int /* regexec return code */ +caltdissect( + struct vars *v, + struct subre *t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ +{ + struct dfa *d; + int er; + + /* We loop, rather than tail-recurse, to handle a chain of alternatives */ + while (t != NULL) { + assert(t->op == '|'); + assert(t->left != NULL && t->left->cnfa.nstates > 0); - i = 0; - for (p = begin; p <= stop && (i < max || max == DUPINF); p += len) { - if (v->g->compare(paren, p, len) != 0) { - break; + MDEBUG(("calt n%d\n", t->id)); + + d = getsubdfa(v, t->left); + NOERR(); + if (longest(v, d, begin, end, (int *) NULL) == end) { + MDEBUG(("calt matched\n")); + er = cdissect(v, t->left, begin, end); + if (er != REG_NOMATCH) { + return er; + } } - i++; + + t = t->right; } - MDEBUG(("cbackref found %d\n", i)); + + return REG_NOMATCH; +} + +/* + - citerdissect - dissect match for iteration node + ^ static int citerdissect(struct vars *, struct subre *, chr *, chr *); + */ +static int /* regexec return code */ +citerdissect(struct vars * v, + struct subre * t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ +{ + struct dfa *d; + chr **endpts; + chr *limit; + int min_matches; + size_t max_matches; + int nverified; + int k; + int i; + int er; + + assert(t->op == '*'); + assert(t->left != NULL && t->left->cnfa.nstates > 0); + assert(!(t->left->flags & SHORTER)); + assert(begin <= end); /* - * And sort it out. + * If zero matches are allowed, and target string is empty, just declare + * victory. OTOH, if target string isn't empty, zero matches can't work + * so we pretend the min is 1. */ + min_matches = t->min; + if (min_matches <= 0) { + if (begin == end) + return REG_OKAY; + min_matches = 1; + } - if (p != end) { /* didn't consume all of it */ - return REG_NOMATCH; + /* + * We need workspace to track the endpoints of each sub-match. Normally + * we consider only nonzero-length sub-matches, so there can be at most + * end-begin of them. However, if min is larger than that, we will also + * consider zero-length sub-matches in order to find enough matches. + * + * For convenience, endpts[0] contains the "begin" pointer and we store + * sub-match endpoints in endpts[1..max_matches]. + */ + max_matches = end - begin; + if (max_matches > (size_t)t->max && t->max != DUPINF) + max_matches = t->max; + if (max_matches < (size_t)min_matches) + max_matches = min_matches; + endpts = (chr **) MALLOC((max_matches + 1) * sizeof(chr *)); + if (endpts == NULL) + return REG_ESPACE; + endpts[0] = begin; + + d = getsubdfa(v, t->left); + if (ISERR()) { + FREE(endpts); + return v->err; } - if (min <= i && (i <= max || max == DUPINF)) { - return REG_OKAY; + MDEBUG(("citer %d\n", t->id)); + + /* + * Our strategy is to first find a set of sub-match endpoints that are + * valid according to the child node's DFA, and then recursively dissect + * each sub-match to confirm validity. If any validity check fails, + * backtrack the last sub-match and try again. And, when we next try for + * a validity check, we need not recheck any successfully verified + * sub-matches that we didn't move the endpoints of. nverified remembers + * how many sub-matches are currently known okay. + */ + + /* initialize to consider first sub-match */ + nverified = 0; + k = 1; + limit = end; + + /* iterate until satisfaction or failure */ + while (k > 0) { + /* try to find an endpoint for the k'th sub-match */ + endpts[k] = longest(v, d, endpts[k - 1], limit, (int *) NULL); + if (endpts[k] == NULL) { + /* no match possible, so see if we can shorten previous one */ + k--; + goto backtrack; + } + MDEBUG(("%d: working endpoint %d: %ld\n", + t->id, k, LOFF(endpts[k]))); + + /* k'th sub-match can no longer be considered verified */ + if (nverified >= k) + nverified = k - 1; + + if (endpts[k] != end) { + /* haven't reached end yet, try another iteration if allowed */ + if ((size_t)k >= max_matches) { + /* must try to shorten some previous match */ + k--; + goto backtrack; + } + + /* reject zero-length match unless necessary to achieve min */ + if (endpts[k] == endpts[k - 1] && + (k >= min_matches || min_matches - k < end - endpts[k])) + goto backtrack; + + k++; + limit = end; + continue; + } + + /* + * We've identified a way to divide the string into k sub-matches + * that works so far as the child DFA can tell. If k is an allowed + * number of matches, start the slow part: recurse to verify each + * sub-match. We always have k <= max_matches, needn't check that. + */ + if (k < min_matches) + goto backtrack; + + MDEBUG(("%d: verifying %d..%d\n", t->id, nverified + 1, k)); + + for (i = nverified + 1; i <= k; i++) { + zaptreesubs(v, t->left); + er = cdissect(v, t->left, endpts[i - 1], endpts[i]); + if (er == REG_OKAY) { + nverified = i; + continue; + } + if (er == REG_NOMATCH) + break; + /* oops, something failed */ + FREE(endpts); + return er; + } + + if (i > k) { + /* satisfaction */ + MDEBUG(("%d successful\n", t->id)); + FREE(endpts); + return REG_OKAY; + } + + /* match failed to verify, so backtrack */ + + backtrack: + /* + * Must consider shorter versions of the current sub-match. However, + * we'll only ask for a zero-length match if necessary. + */ + while (k > 0) { + chr *prev_end = endpts[k - 1]; + + if (endpts[k] > prev_end) { + limit = endpts[k] - 1; + if (limit > prev_end || + (k < min_matches && min_matches - k >= end - prev_end)) { + /* break out of backtrack loop, continue the outer one */ + break; + } + } + /* can't shorten k'th sub-match any more, consider previous one */ + k--; + } } - return REG_NOMATCH; /* out of range */ + + /* all possibilities exhausted */ + MDEBUG(("%d failed\n", t->id)); + FREE(endpts); + return REG_NOMATCH; } /* - - complicatedAlternationDissect - determine alternative subexpression matches (w. - - complications) - ^ static int complicatedAlternationDissect(struct vars *, struct subre *, chr *, chr *); + - creviterdissect - dissect match for iteration node, shortest-first + ^ static int creviterdissect(struct vars *, struct subre *, chr *, chr *); */ static int /* regexec return code */ -complicatedAlternationDissect( - struct vars *const v, - struct subre *t, - chr *const begin, /* beginning of relevant substring */ - chr *const end) /* end of same */ +creviterdissect(struct vars * v, + struct subre * t, + chr *begin, /* beginning of relevant substring */ + chr *end) /* end of same */ { - int er; -#define UNTRIED 0 /* not yet tried at all */ -#define TRYING 1 /* top matched, trying submatches */ -#define TRIED 2 /* top didn't match or submatches exhausted */ + struct dfa *d; + chr **endpts; + chr *limit; + int min_matches; + size_t max_matches; + int nverified; + int k; + int i; + int er; + + assert(t->op == '*'); + assert(t->left != NULL && t->left->cnfa.nstates > 0); + assert(t->left->flags & SHORTER); + assert(begin <= end); -#ifndef COMPILER_DOES_TAILCALL_OPTIMIZATION - if (0) { - doRight: - t = t->right; - } -#endif - if (t == NULL) { - return REG_NOMATCH; + /* + * If zero matches are allowed, and target string is empty, just declare + * victory. OTOH, if target string isn't empty, zero matches can't work + * so we pretend the min is 1. + */ + min_matches = t->min; + if (min_matches <= 0) { + if (begin == end) + return REG_OKAY; + min_matches = 1; } - assert(t->op == '|'); - if (v->mem[t->retry] == TRIED) { - goto doRight; + + /* + * We need workspace to track the endpoints of each sub-match. Normally + * we consider only nonzero-length sub-matches, so there can be at most + * end-begin of them. However, if min is larger than that, we will also + * consider zero-length sub-matches in order to find enough matches. + * + * For convenience, endpts[0] contains the "begin" pointer and we store + * sub-match endpoints in endpts[1..max_matches]. + */ + max_matches = end - begin; + if (max_matches > (size_t)t->max && t->max != DUPINF) + max_matches = t->max; + if (max_matches < (size_t)min_matches) + max_matches = min_matches; + endpts = (chr **) MALLOC((max_matches + 1) * sizeof(chr *)); + if (endpts == NULL) + return REG_ESPACE; + endpts[0] = begin; + + d = getsubdfa(v, t->left); + if (ISERR()) { + FREE(endpts); + return v->err; } + MDEBUG(("creviter %d\n", t->id)); - MDEBUG(("cAlt n%d\n", t->retry)); - assert(t->left != NULL); + /* + * Our strategy is to first find a set of sub-match endpoints that are + * valid according to the child node's DFA, and then recursively dissect + * each sub-match to confirm validity. If any validity check fails, + * backtrack the last sub-match and try again. And, when we next try for + * a validity check, we need not recheck any successfully verified + * sub-matches that we didn't move the endpoints of. nverified remembers + * how many sub-matches are currently known okay. + */ - if (v->mem[t->retry] == UNTRIED) { - struct dfa *d = newDFA(v, &t->left->cnfa, &v->g->cmap, DOMALLOC); + /* initialize to consider first sub-match */ + nverified = 0; + k = 1; + limit = begin; + + /* iterate until satisfaction or failure */ + while (k > 0) { + /* disallow zero-length match unless necessary to achieve min */ + if (limit == endpts[k - 1] && + limit != end && + (k >= min_matches || min_matches - k < end - limit)) + limit++; + + /* if this is the last allowed sub-match, it must reach to the end */ + if ((size_t)k >= max_matches) + limit = end; + + /* try to find an endpoint for the k'th sub-match */ + endpts[k] = shortest(v, d, endpts[k - 1], limit, end, + (chr **) NULL, (int *) NULL); + if (endpts[k] == NULL) { + /* no match possible, so see if we can lengthen previous one */ + k--; + goto backtrack; + } + MDEBUG(("%d: working endpoint %d: %ld\n", + t->id, k, LOFF(endpts[k]))); + + /* k'th sub-match can no longer be considered verified */ + if (nverified >= k) + nverified = k - 1; + + if (endpts[k] != end) { + /* haven't reached end yet, try another iteration if allowed */ + if ((size_t)k >= max_matches) { + /* must try to lengthen some previous match */ + k--; + goto backtrack; + } - if (ISERR()) { - return v->err; + k++; + limit = endpts[k - 1]; + continue; } - if (longest(v, d, begin, end, NULL) != end) { - freeDFA(d); - v->mem[t->retry] = TRIED; - goto doRight; + + /* + * We've identified a way to divide the string into k sub-matches + * that works so far as the child DFA can tell. If k is an allowed + * number of matches, start the slow part: recurse to verify each + * sub-match. We always have k <= max_matches, needn't check that. + */ + if (k < min_matches) + goto backtrack; + + MDEBUG(("%d: verifying %d..%d\n", t->id, nverified + 1, k)); + + for (i = nverified + 1; i <= k; i++) { + zaptreesubs(v, t->left); + er = cdissect(v, t->left, endpts[i - 1], endpts[i]); + if (er == REG_OKAY) { + nverified = i; + continue; + } + if (er == REG_NOMATCH) + break; + /* oops, something failed */ + FREE(endpts); + return er; } - freeDFA(d); - MDEBUG(("cAlt matched\n")); - v->mem[t->retry] = TRYING; - } - er = complicatedDissect(v, t->left, begin, end); - if (er != REG_NOMATCH) { - return er; + if (i > k) { + /* satisfaction */ + MDEBUG(("%d successful\n", t->id)); + FREE(endpts); + return REG_OKAY; + } + + /* match failed to verify, so backtrack */ + + backtrack: + /* + * Must consider longer versions of the current sub-match. + */ + while (k > 0) { + if (endpts[k] < end) { + limit = endpts[k] + 1; + /* break out of backtrack loop, continue the outer one */ + break; + } + /* can't lengthen k'th sub-match any more, consider previous one */ + k--; + } } - v->mem[t->retry] = TRIED; -#ifndef COMPILER_DOES_TAILCALL_OPTIMIZATION - goto doRight; -#else - doRight: - return complicatedAlternationDissect(v, t->right, begin, end); -#endif + /* all possibilities exhausted */ + MDEBUG(("%d failed\n", t->id)); + FREE(endpts); + return REG_NOMATCH; } #include "rege_dfa.c" diff --git a/generic/regguts.h b/generic/regguts.h index 1b6abe6..1ac2465 100644 --- a/generic/regguts.h +++ b/generic/regguts.h @@ -186,7 +186,14 @@ struct colordesc { union tree *block; /* block of solid color, if any */ }; -/* the color map itself */ +/* + * The color map itself + * + * Much of the data in the colormap struct is only used at compile time. + * However, the bulk of the space usage is in the "tree" structure, so it's + * not clear that there's much point in converting the rest to a more compact + * form when compilation is finished. + */ struct colormap { int magic; #define CMMAGIC 0x876 @@ -242,14 +249,15 @@ struct cvec { struct state; struct arc { - int type; -#define ARCFREE '\0' + int type; /* 0 if free, else an NFA arc type code */ color co; struct state *from; /* where it's from (and contained within) */ struct state *to; /* where it's to */ - struct arc *outchain; /* *from's outs chain or free chain */ -#define freechain outchain + struct arc *outchain; /* link in *from's outs chain or free chain */ + struct arc *outchainRev; /* back-link in *from's outs chain */ +#define freechain outchain /* we do not maintain "freechainRev" */ struct arc *inchain; /* *to's ins chain */ + struct arc *inchainRev; /* back-link in *to's ins chain */ struct arc *colorchain; /* color's arc chain */ struct arc *colorchainRev; /* back-link in color's arc chain */ }; @@ -288,20 +296,28 @@ struct nfa { struct colormap *cm; /* the color map */ color bos[2]; /* colors, if any, assigned to BOS and BOL */ color eos[2]; /* colors, if any, assigned to EOS and EOL */ - size_t size; /* Current NFA size; differs from nstates as - * it also counts the number of states created - * by children of this state. */ struct vars *v; /* simplifies compile error reporting */ struct nfa *parent; /* parent NFA, if any */ }; /* * definitions for compacted NFA + * + * The main space savings in a compacted NFA is from making the arcs as small + * as possible. We store only the transition color and next-state number for + * each arc. The list of out arcs for each state is an array beginning at + * cnfa.states[statenumber], and terminated by a dummy carc struct with + * co == COLORLESS. + * + * The non-dummy carc structs are of two types: plain arcs and LACON arcs. + * Plain arcs just store the transition color number as "co". LACON arcs + * store the lookahead constraint number plus cnfa.ncolors as "co". LACON + * arcs can be distinguished from plain by testing for co >= cnfa.ncolors. */ struct carc { color co; /* COLORLESS is list terminator */ - int to; /* state number */ + int to; /* next-state number */ }; struct cnfa { @@ -313,27 +329,52 @@ struct cnfa { int post; /* teardown state number */ color bos[2]; /* colors, if any, assigned to BOS and BOL */ color eos[2]; /* colors, if any, assigned to EOS and EOL */ + char *stflags; /* vector of per-state flags bytes */ +#define CNFA_NOPROGRESS 01 /* flag bit for a no-progress state */ struct carc **states; /* vector of pointers to outarc lists */ + /* states[n] are pointers into a single malloc'd array of arcs */ struct carc *arcs; /* the area for the lists */ }; #define ZAPCNFA(cnfa) ((cnfa).nstates = 0) #define NULLCNFA(cnfa) ((cnfa).nstates == 0) /* - * Used to limit the maximum NFA size to something sane. [Bug 1810264] + * This symbol limits the transient heap space used by the regex compiler, + * and thereby also the maximum complexity of NFAs that we'll deal with. + * Currently we only count NFA states and arcs against this; the other + * transient data is generally not large enough to notice compared to those. + * Note that we do not charge anything for the final output data structures + * (the compacted NFA and the colormap). */ - -#ifndef REG_MAX_STATES -# define REG_MAX_STATES 100000 +#ifndef REG_MAX_COMPILE_SPACE +#define REG_MAX_COMPILE_SPACE \ + (100000 * sizeof(struct state) + 100000 * sizeof(struct arcbatch)) #endif /* * subexpression tree + * + * "op" is one of: + * '=' plain regex without interesting substructure (implemented as DFA) + * 'b' back-reference (has no substructure either) + * '(' capture node: captures the match of its single child + * '.' concatenation: matches a match for left, then a match for right + * '|' alternation: matches a match for left or a match for right + * '*' iteration: matches some number of matches of its single child + * + * Note: the right child of an alternation must be another alternation or + * NULL; hence, an N-way branch requires N alternation nodes, not N-1 as you + * might expect. This could stand to be changed. Actually I'd rather see + * a single alternation node with N children, but that will take revising + * the representation of struct subre. + * + * Note: when a backref is directly quantified, we stick the min/max counts + * into the backref rather than plastering an iteration node on top. This is + * for efficiency: there is no need to search for possible division points. */ struct subre { - char op; /* '|', '.' (concat), 'b' (backref), '(', - * '=' */ + char op; /* see type codes above */ char flags; #define LONGER 01 /* prefers longer match */ #define SHORTER 02 /* prefers shorter match */ @@ -349,10 +390,10 @@ struct subre { #define PREF(f) ((f)&NOPROP) #define PREF2(f1, f2) ((PREF(f1) != 0) ? PREF(f1) : PREF(f2)) #define COMBINE(f1, f2) (UP((f1)|(f2)) | PREF2(f1, f2)) - short retry; /* index into retry memory */ + short id; /* ID of subre (1..ntree-1) */ int subno; /* subexpression number (for 'b' and '(') */ - short min; /* min repetitions, for backref only */ - short max; /* max repetitions, for backref only */ + short min; /* min repetitions for iteration or backref */ + short max; /* max repetitions for iteration or backref */ struct subre *left; /* left child, if any (also freelist chain) */ struct subre *right; /* right child, if any */ struct state *begin; /* outarcs from here... */ @@ -382,7 +423,7 @@ struct guts { size_t nsub; /* copy of re_nsub */ struct subre *tree; struct cnfa search; /* for fast preliminary search */ - int ntree; + int ntree; /* number of subre's, plus one */ struct colormap cmap; int FUNCPTR(compare, (const chr *, const chr *, size_t)); struct subre *lacons; /* lookahead-constraint vector */ diff --git a/generic/tcl.decls b/generic/tcl.decls index 1829249..797a5a7 100644 --- a/generic/tcl.decls +++ b/generic/tcl.decls @@ -37,7 +37,7 @@ declare 1 { void *clientDataPtr) } declare 2 { - void Tcl_Panic(const char *format, ...) + TCL_NORETURN void Tcl_Panic(const char *format, ...) } declare 3 { char *Tcl_Alloc(unsigned int size) @@ -480,7 +480,7 @@ declare 132 { void Tcl_EventuallyFree(ClientData clientData, Tcl_FreeProc *freeProc) } declare 133 { - void Tcl_Exit(int status) + TCL_NORETURN void Tcl_Exit(int status) } declare 134 { int Tcl_ExposeCommand(Tcl_Interp *interp, const char *hiddenCmdToken, @@ -815,7 +815,7 @@ declare 229 { void Tcl_SetMaxBlockTime(const Tcl_Time *timePtr) } declare 230 { - void Tcl_SetPanicProc(Tcl_PanicProc *panicProc) + void Tcl_SetPanicProc(TCL_NORETURN1 Tcl_PanicProc *panicProc) } declare 231 { int Tcl_SetRecursionLimit(Tcl_Interp *interp, int depth) @@ -986,7 +986,7 @@ declare 277 { Tcl_Pid Tcl_WaitPid(Tcl_Pid pid, int *statPtr, int options) } declare 278 { - void Tcl_PanicVA(const char *format, va_list argList) + TCL_NORETURN void Tcl_PanicVA(const char *format, va_list argList) } declare 279 { void Tcl_GetVersion(int *major, int *minor, int *patchLevel, int *type) @@ -1872,7 +1872,7 @@ declare 518 { # TIP#121 (exit handler) dkf for Joe Mistachkin declare 519 { - Tcl_ExitProc *Tcl_SetExitProc(Tcl_ExitProc *proc) + Tcl_ExitProc *Tcl_SetExitProc(TCL_NORETURN1 Tcl_ExitProc *proc) } # TIP#143 (resource limits) dkf diff --git a/generic/tcl.h b/generic/tcl.h index ae425bb..a08edde 100644 --- a/generic/tcl.h +++ b/generic/tcl.h @@ -77,16 +77,6 @@ extern "C" { #endif /* - * STRICT: See MSDN Article Q83456 - */ - -#ifdef _WIN32 -# ifndef STRICT -# define STRICT -# endif -#endif /* _WIN32 */ - -/* * Utility macros: STRINGIFY takes an argument and wraps it in "" (double * quotation marks), JOIN joins two arguments. */ @@ -153,8 +143,20 @@ extern "C" { #endif #if defined(__GNUC__) && (__GNUC__ > 2) # define TCL_FORMAT_PRINTF(a,b) __attribute__ ((__format__ (__printf__, a, b))) +# define TCL_NORETURN __attribute__ ((noreturn)) +# if defined(BUILD_tcl) || defined(BUILD_tk) +# define TCL_NORETURN1 __attribute__ ((noreturn)) +# else +# define TCL_NORETURN1 /* nothing */ +# endif #else # define TCL_FORMAT_PRINTF(a,b) +# if defined(_MSC_VER) && (_MSC_VER >= 1310) +# define TCL_NORETURN _declspec(noreturn) +# else +# define TCL_NORETURN /* nothing */ +# endif +# define TCL_NORETURN1 /* nothing */ #endif /* @@ -402,16 +404,12 @@ typedef long LONG; * Don't know what platform it is and configure hasn't discovered what is * going on for us. Try to guess... */ -# ifdef NO_LIMITS_H -# error please define either TCL_WIDE_INT_TYPE or TCL_WIDE_INT_IS_LONG -# else /* !NO_LIMITS_H */ -# include <limits.h> -# if (INT_MAX < LONG_MAX) -# define TCL_WIDE_INT_IS_LONG 1 -# else -# define TCL_WIDE_INT_TYPE long long -# endif -# endif /* NO_LIMITS_H */ +# include <limits.h> +# if (INT_MAX < LONG_MAX) +# define TCL_WIDE_INT_IS_LONG 1 +# else +# define TCL_WIDE_INT_TYPE long long +# endif # endif /* _WIN32 */ #endif /* !TCL_WIDE_INT_TYPE & !TCL_WIDE_INT_IS_LONG */ #ifdef TCL_WIDE_INT_IS_LONG @@ -830,18 +828,19 @@ typedef struct Tcl_Obj { union { /* The internal representation: */ long longValue; /* - an long integer value. */ double doubleValue; /* - a double-precision floating value. */ - void *otherValuePtr; /* - another, type-specific value. */ + void *otherValuePtr; /* - another, type-specific value, + not used internally any more. */ Tcl_WideInt wideValue; /* - a long long value. */ - struct { /* - internal rep as two pointers. */ + struct { /* - internal rep as two pointers. + * the main use of which is a bignum's + * tightly packed fields, where the alloc, + * used and signum flags are packed into + * ptr2 with everything else hung off ptr1. */ void *ptr1; void *ptr2; } twoPtrValue; struct { /* - internal rep as a pointer and a long, - * the main use of which is a bignum's - * tightly packed fields, where the alloc, - * used and signum flags are packed into a - * single word with everything else hung - * off the pointer. */ + not used internally any more. */ void *ptr; unsigned long value; } ptrAndLongRep; @@ -2156,7 +2155,7 @@ typedef struct Tcl_EncodingType { * Tcl_ExternalToUtf takes the initial value * of *dstCharsPtr is taken as a limit of the * maximum number of chars to produce in the - * encoded UTF-8 content. Otherwise, the + * encoded UTF-8 content. Otherwise, the * number of chars produced is controlled only * by other limiting factors. */ @@ -2436,9 +2435,7 @@ EXTERN void Tcl_MainEx(int argc, char **argv, Tcl_AppInitProc *appInitProc, Tcl_Interp *interp); EXTERN const char * Tcl_PkgInitStubsCheck(Tcl_Interp *interp, const char *version, int exact); -#if defined(TCL_THREADS) && defined(USE_THREAD_ALLOC) EXTERN void Tcl_GetMemoryInfo(Tcl_DString *dsPtr); -#endif /* *---------------------------------------------------------------------------- @@ -2525,7 +2522,7 @@ EXTERN void Tcl_GetMemoryInfo(Tcl_DString *dsPtr); # define Tcl_DecrRefCount(objPtr) \ do { \ Tcl_Obj *_objPtr = (objPtr); \ - if (--(_objPtr)->refCount <= 0) { \ + if ((_objPtr)->refCount-- <= 1) { \ TclFreeObj(_objPtr); \ } \ } while(0) diff --git a/generic/tclBasic.c b/generic/tclBasic.c index 361ed49..a09bf10 100644 --- a/generic/tclBasic.c +++ b/generic/tclBasic.c @@ -472,7 +472,6 @@ Tcl_CreateInterp(void) #endif /* TCL_COMPILE_STATS */ char mathFuncName[32]; CallFrame *framePtr; - int result; TclInitSubsystems(); @@ -642,11 +641,8 @@ Tcl_CreateInterp(void) /* This is needed to satisfy GCC 3.3's strict aliasing rules */ framePtr = ckalloc(sizeof(CallFrame)); - result = Tcl_PushCallFrame(interp, (Tcl_CallFrame *) framePtr, + (void) Tcl_PushCallFrame(interp, (Tcl_CallFrame *) framePtr, (Tcl_Namespace *) iPtr->globalNsPtr, /*isProcCallFrame*/ 0); - if (result != TCL_OK) { - Tcl_Panic("Tcl_CreateInterp: failed to push the root stack frame"); - } framePtr->objc = 0; iPtr->framePtr = framePtr; @@ -2260,7 +2256,7 @@ Tcl_CreateObjCommand( /* Command already exists. */ /* - * [***] This is wrong. See Tcl Bug a16752c252. + * [***] This is wrong. See Tcl Bug a16752c252. * However, this buggy behavior is kept under particular * circumstances to accommodate deployed binaries of the * "tclcompiler" program. http://sourceforge.net/projects/tclpro/ @@ -3084,7 +3080,7 @@ Tcl_DeleteCommandFromToken( while (tracePtr != NULL) { CommandTrace *nextPtr = tracePtr->nextPtr; - if ((--tracePtr->refCount) <= 0) { + if (tracePtr->refCount-- <= 1) { ckfree(tracePtr); } tracePtr = nextPtr; @@ -3270,7 +3266,7 @@ CallCommandTraces( tracePtr->traceProc(tracePtr->clientData, (Tcl_Interp *) iPtr, oldName, newName, flags); cmdPtr->flags &= ~tracePtr->flags; - if ((--tracePtr->refCount) <= 0) { + if (tracePtr->refCount-- <= 1) { ckfree(tracePtr); } } @@ -4142,8 +4138,9 @@ TclNREvalObjv( /* * data[1] stores a marker for use by tailcalls; it will be set to 1 by - * command redirectors (imports, alias, ensembles) so that tailcalls - * finishes the source command and not just the target. + * command redirectors (imports, alias, ensembles) so that tailcall skips + * this callback (that marks the end of the target command) and goes back + * to the end of the source command. */ if (iPtr->deferredCallbacks) { @@ -4171,7 +4168,7 @@ EvalObjvCore( Interp *iPtr = (Interp *) interp; Namespace *lookupNsPtr = NULL; int enterTracesDone = 0; - + /* * Push records for task to be done on return, in INVERSE order. First, if * needed, the exception handlers (as they should happen last). @@ -4297,7 +4294,7 @@ EvalObjvCore( } } - /* + /* * Schedule leave traces. Raise the refCount on the resolved * cmdPtr, so that when it passes to the leave traces we know * it's still valid. @@ -4406,9 +4403,9 @@ NRCommand( iPtr->numLevels--; /* - * If there is a tailcall, schedule it + * If there is a tailcall, schedule it next */ - + if (data[1] && (data[1] != INT2PTR(1))) { TclNRAddCallback(interp, TclNRTailcallEval, data[1], NULL, NULL, NULL); } @@ -5642,10 +5639,10 @@ TclArgumentBCEnter( * ensemble dispatch. Ensemble subcommands that lead to script * evaluation are not supposed to get compiled, because a command * such as [info level] in the script can expose some of the dispatch - * shenanigans. This means that we don't have to tend to the + * shenanigans. This means that we don't have to tend to the * housekeeping, and can escape now. */ - + if (ePtr->nline != objc) { return; } @@ -5909,7 +5906,7 @@ Tcl_GlobalEvalObj( * * If the flag TCL_EVAL_DIRECT is passed in, the value of invoker * must be NULL. Support for non-NULL invokers in that mode has - * been removed since it was unused and untested. Failure to + * been removed since it was unused and untested. Failure to * follow this limitation will lead to an assertion panic. * * Results: @@ -6517,11 +6514,7 @@ TclObjInvokeNamespace( * command. */ - result = TclPushStackFrame(interp, &framePtr, nsPtr, /*isProcFrame*/0); - if (result != TCL_OK) { - return TCL_ERROR; - } - + (void) TclPushStackFrame(interp, &framePtr, nsPtr, /*isProcFrame*/0); result = TclObjInvoke(interp, objc, objv, flags); TclPopStackFrame(interp); @@ -8170,27 +8163,31 @@ Tcl_NRCmdSwap( } /***************************************************************************** - * Stuff for tailcalls + * Tailcall related code ***************************************************************************** * - * Just to show that IT CAN BE DONE! The precise semantics are not simple, - * require more thought. Possibly need a new Tcl return code to do it right? - * Questions include: - * (1) How is the objc/objv tailcall to be run? My current thinking is that - * it should essentially be - * [tailcall a b c] <=> [uplevel 1 [list a b c]] - * with two caveats - * (a) the current frame is dropped first, after running all pending - * cleanup tasks and saving its namespace - * (b) 'a' is looked up in the returning frame's namespace, but the - * command is run in the context to which we are returning - * Current implementation does this if [tailcall] is called from within - * a proc, errors otherwise. - * (2) Should a tailcall bypass [catch] in the returning frame? Current - * implementation does not (or does it? Changed, test!) - it causes an - * error. - * - * FIXME NRE! + * The steps of the tailcall dance are as follows: + * + * 1. when [tailcall] is invoked, it stores the corresponding callback in + * the current CallFrame and returns TCL_RETURN + * 2. when the CallFrame is popped, it calls TclSetTailcall to store the + * callback in the proper NRCommand callback - the spot where the command + * that pushed the CallFrame is completely cleaned up + * 3. when the NRCommand callback runs, it schedules the tailcall callback + * to run immediately after it returns + * + * One delicate point is to properly define the NRCommand where the tailcall + * will execute. There are functions whose purpose is to help define the + * precise spot: + * TclMarkTailcall: if the NEXT command to be pushed tailcalls, execution + * should continue right here + * TclSkipTailcall: if the NEXT command to be pushed tailcalls, execution + * should continue after the CURRENT command is fully returned ("skip + * the next command: we are redirecting to it, tailcalls should run + * after WE return") + * TclPushTailcallPoint: the search for a tailcalling spot cannot traverse + * this point. This is special for OO, as some of the oo constructs + * that behave like commands may not push an NRCommand callback. */ void @@ -8224,6 +8221,18 @@ TclPushTailcallPoint( ((Interp *) interp)->numLevels++; } + +/* + *---------------------------------------------------------------------- + * + * TclSetTailcall -- + * + * Splice a tailcall command in the proper spot of the NRE callback + * stack, so that it runs at the right time. + * + *---------------------------------------------------------------------- + */ + void TclSetTailcall( Tcl_Interp *interp, @@ -8248,6 +8257,23 @@ TclSetTailcall( runPtr->data[1] = listPtr; } + +/* + *---------------------------------------------------------------------- + * + * TclNRTailcallObjCmd -- + * + * Prepare the tailcall as a list and store it in the current + * varFrame. When the frame is later popped the tailcall will be spliced + * at the proper place. + * + * Results: + * The first NRCommand callback that is not marked to be skipped is + * updated so that its data[1] field contains the tailcall list. + * + *---------------------------------------------------------------------- + */ + int TclNRTailcallObjCmd( ClientData clientData, @@ -8262,9 +8288,9 @@ TclNRTailcallObjCmd( return TCL_ERROR; } - if (!(iPtr->varFramePtr->isProcCallFrame & 1)) { /* or is upleveled */ + if (!(iPtr->varFramePtr->isProcCallFrame & 1)) { Tcl_SetObjResult(interp, Tcl_NewStringObj( - "tailcall can only be called from a proc or lambda", -1)); + "tailcall can only be called from a proc, lambda or method", -1)); Tcl_SetErrorCode(interp, "TCL", "TAILCALL", "ILLEGAL", NULL); return TCL_ERROR; } @@ -8282,8 +8308,7 @@ TclNRTailcallObjCmd( /* * Create the callback to actually evaluate the tailcalled * command, then set it in the varFrame so that PopCallFrame can use it - * at the proper time. Being lazy: exploit the TclNRAddCallBack macro to - * build the callback. + * at the proper time. */ if (objc > 1) { @@ -8293,7 +8318,7 @@ TclNRTailcallObjCmd( /* The tailcall data is in a Tcl list: the first element is the * namespace, the rest the command to be tailcalled. */ - + listPtr = Tcl_NewListObj(objc, objv); nsObjPtr = Tcl_NewStringObj(nsPtr->fullName, -1); @@ -8302,12 +8327,23 @@ TclNRTailcallObjCmd( Tcl_Panic("Tailcall failed to find the proper namespace"); } TclListObjSetElement(interp, listPtr, 0, nsObjPtr); - + iPtr->varFramePtr->tailcallPtr = listPtr; } return TCL_RETURN; } + +/* + *---------------------------------------------------------------------- + * + * TclNRTailcallEval -- + * + * This NREcallback actually causes the tailcall to be evaluated. + * + *---------------------------------------------------------------------- + */ + int TclNRTailcallEval( ClientData data[], @@ -8320,9 +8356,9 @@ TclNRTailcallEval( int objc; Tcl_Obj **objv; - Tcl_ListObjGetElements(interp, listPtr, &objc, &objv); + Tcl_ListObjGetElements(interp, listPtr, &objc, &objv); nsObjPtr = objv[0]; - + if (result == TCL_OK) { result = TclGetNamespaceFromObj(interp, nsObjPtr, &nsPtr); } diff --git a/generic/tclCmdAH.c b/generic/tclCmdAH.c index d90a747..54e0227 100644 --- a/generic/tclCmdAH.c +++ b/generic/tclCmdAH.c @@ -748,7 +748,7 @@ Tcl_EvalObjCmd( int objc, /* Number of arguments. */ Tcl_Obj *const objv[]) /* Argument objects. */ { - return Tcl_NRCallObjProc(interp, TclNREvalObjCmd, dummy, objc, objv); + return Tcl_NRCallObjProc(interp, TclNREvalObjCmd, dummy, objc, objv); } int diff --git a/generic/tclCmdMZ.c b/generic/tclCmdMZ.c index 841002f..13f9e7d 100644 --- a/generic/tclCmdMZ.c +++ b/generic/tclCmdMZ.c @@ -38,7 +38,7 @@ static int UniCharIsHexDigit(int character); * UTF-8 literal string containing all Unicode space characters [TIP #413] */ -const char tclDefaultTrimSet[] = +const char tclDefaultTrimSet[] = "\x09\x0a\x0b\x0c\x0d " /* ASCII */ "\xc0\x80" /* nul (U+0000) */ "\xc2\x85" /* next line (U+0085) */ @@ -2884,7 +2884,7 @@ StringCatCmd( Tcl_AppendObjToObj(objResultPtr, objv[i]); } Tcl_SetObjResult(interp, objResultPtr); - + return TCL_OK; } diff --git a/generic/tclCompCmds.c b/generic/tclCompCmds.c index 6a22a30..18da741 100644 --- a/generic/tclCompCmds.c +++ b/generic/tclCompCmds.c @@ -351,7 +351,7 @@ TclCompileArraySetCmd( TclEmitInstInt4(INST_UPVAR, localIndex, envPtr); TclEmitOpcode(INST_POP, envPtr); } - + /* * Prepare for the internal foreach. */ @@ -547,7 +547,7 @@ TclCompileCatchCmd( int resultIndex, optsIndex, range, dropScript = 0; DefineLineInformation; /* TIP #280 */ int depth = TclGetStackDepth(envPtr); - + /* * If syntax does not match what we expect for [catch], do not compile. * Let runtime checks determine if syntax has changed. @@ -626,7 +626,7 @@ TclCompileCatchCmd( } ExceptionRangeEnds(envPtr, range); - + /* * Emit the "no errors" epilogue: push "0" (TCL_OK) as the catch result, * and jump around the "error case" code. @@ -636,14 +636,14 @@ TclCompileCatchCmd( PushStringLiteral(envPtr, "0"); TclEmitForwardJump(envPtr, TCL_UNCONDITIONAL_JUMP, &jumpFixup); - /* + /* * Emit the "error case" epilogue. Push the interpreter result and the * return code. */ ExceptionRangeTarget(envPtr, range, catchOffset); TclSetStackDepth(depth + dropScript, envPtr); - + if (dropScript) { TclEmitOpcode( INST_POP, envPtr); } @@ -2530,7 +2530,7 @@ CompileEachloopCmd( ForeachInfo *infoPtr=NULL; /* Points to the structure describing this * foreach command. Stored in a AuxData * record in the ByteCode. */ - + Tcl_Token *tokenPtr, *bodyTokenPtr; int jumpBackOffset, infoIndex, range; int numWords, numLists, i, j, code = TCL_OK; @@ -2637,11 +2637,11 @@ CompileEachloopCmd( /* * Create the collecting object, unshared. */ - + if (collect == TCL_EACH_COLLECT) { TclEmitInstInt4(INST_LIST, 0, envPtr); } - + /* * Evaluate each value list and leave it on stack. */ @@ -2655,7 +2655,7 @@ CompileEachloopCmd( } TclEmitInstInt4(INST_FOREACH_START, infoIndex, envPtr); - + /* * Inline compile the loop body. */ @@ -2665,7 +2665,7 @@ CompileEachloopCmd( ExceptionRangeStarts(envPtr, range); BODY(bodyTokenPtr, numWords - 1); ExceptionRangeEnds(envPtr, range); - + if (collect == TCL_EACH_COLLECT) { TclEmitOpcode(INST_LMAP_COLLECT, envPtr); } else { @@ -2674,7 +2674,7 @@ CompileEachloopCmd( /* * Bottom of loop code: assign each loop variable and check whether - * to terminate the loop. Set the loop's break target. + * to terminate the loop. Set the loop's break target. */ ExceptionRangeTarget(envPtr, range, continueOffset); @@ -2688,7 +2688,7 @@ CompileEachloopCmd( * Set the jumpback distance from INST_FOREACH_STEP to the start of the * body's code. Misuse loopCtTemp for storing the jump size. */ - + jumpBackOffset = envPtr->exceptArrayPtr[range].continueOffset - envPtr->exceptArrayPtr[range].codeOffset; infoPtr->loopCtTemp = -jumpBackOffset; @@ -2701,16 +2701,12 @@ CompileEachloopCmd( if (collect != TCL_EACH_COLLECT) { PushStringLiteral(envPtr, ""); } - + done: if (code == TCL_ERROR) { - if (infoPtr) { - FreeForeachInfo(infoPtr); - } - } - if (varListObj) { - Tcl_DecrRefCount(varListObj); + FreeForeachInfo(infoPtr); } + Tcl_DecrRefCount(varListObj); return code; } diff --git a/generic/tclCompCmdsGR.c b/generic/tclCompCmdsGR.c index b77c43c..e674fb0 100644 --- a/generic/tclCompCmdsGR.c +++ b/generic/tclCompCmdsGR.c @@ -144,7 +144,7 @@ TclCompileGlobalCmd( return TCL_ERROR; } - /* TODO: Consider what value can pass throug the + /* TODO: Consider what value can pass throug the * IndexTailVarIfKnown() screen. Full CompileWord() * likely does not apply here. Push known value instead. */ CompileWord(envPtr, varTokenPtr, interp, i); @@ -1210,20 +1210,7 @@ TclCompileListCmd( valueTokenPtr = TokenAfter(valueTokenPtr); } if (listObj != NULL) { - int len; - const char *bytes = Tcl_GetStringFromObj(listObj, &len); - - PushLiteral(envPtr, bytes, len); - Tcl_DecrRefCount(listObj); - if (len > 0) { - /* - * Force list interpretation! - */ - - TclEmitOpcode( INST_DUP, envPtr); - TclEmitOpcode( INST_LIST_LENGTH, envPtr); - TclEmitOpcode( INST_POP, envPtr); - } + TclEmitPush(TclAddLiteralObj(envPtr, listObj, NULL), envPtr); return TCL_OK; } @@ -1501,7 +1488,7 @@ TclCompileLreplaceCmd( return TCL_ERROR; } - if(idx2 != INDEX_END && idx2 < idx1) { + if(idx2 != INDEX_END && idx2 >= 0 && idx2 < idx1) { idx2 = idx1-1; } @@ -2903,7 +2890,7 @@ TclCompileVariableCmd( return TCL_ERROR; } - /* TODO: Consider what value can pass throug the + /* TODO: Consider what value can pass throug the * IndexTailVarIfKnown() screen. Full CompileWord() * likely does not apply here. Push known value instead. */ CompileWord(envPtr, varTokenPtr, interp, i); diff --git a/generic/tclCompCmdsSZ.c b/generic/tclCompCmdsSZ.c index 382d2d1..ef9340e 100644 --- a/generic/tclCompCmdsSZ.c +++ b/generic/tclCompCmdsSZ.c @@ -292,7 +292,7 @@ TclCompileStringCatCmd( PushStringLiteral(envPtr, ""); return TCL_OK; } - + /* General case: issue CONCAT1's (by chunks of 254 if needed), folding contiguous constants along the way */ @@ -313,7 +313,7 @@ TclCompileStringCatCmd( if (folded) { int len; const char *bytes = Tcl_GetStringFromObj(folded, &len); - + PushLiteral(envPtr, bytes, len); Tcl_DecrRefCount(folded); folded = NULL; @@ -331,7 +331,7 @@ TclCompileStringCatCmd( if (folded) { int len; const char *bytes = Tcl_GetStringFromObj(folded, &len); - + PushLiteral(envPtr, bytes, len); Tcl_DecrRefCount(folded); folded = NULL; @@ -1003,7 +1003,7 @@ TclCompileStringRangeCmd( /* * Push the operands onto the stack and then the substring operation. - */ + */ nonConstantIndices: CompileWord(envPtr, stringTokenPtr, interp, 1); @@ -2182,7 +2182,7 @@ IssueSwitchChainedTests( } /* - * Now do the actual compilation. Note that we do not use BODY() + * Now do the actual compilation. Note that we do not use BODY() * because we may have synthesized the tokens in a non-standard * pattern. */ @@ -2640,7 +2640,7 @@ TclCompileThrowCmd( } CompileWord(envPtr, msgToken, interp, 2); - codeIsList = codeKnown && (TCL_OK == + codeIsList = codeKnown && (TCL_OK == Tcl_ListObjLength(interp, objPtr, &len)); codeIsValid = codeIsList && (len != 0); @@ -3575,16 +3575,16 @@ TclCompileUnsetCmd( } return TCL_ERROR; } - if (i == 1) { + if (varCount == 0) { const char *bytes; int len; bytes = Tcl_GetStringFromObj(leadingWord, &len); - if (len == 11 && !strncmp("-nocomplain", bytes, 11)) { + if (i == 1 && len == 11 && !strncmp("-nocomplain", bytes, 11)) { flags = 0; - haveFlags = 1; - } else if (len == 2 && !strncmp("--", bytes, 2)) { - haveFlags = 1; + haveFlags++; + } else if (i == (2 - flags) && len == 2 && !strncmp("--", bytes, 2)) { + haveFlags++; } else { varCount++; } @@ -3599,7 +3599,7 @@ TclCompileUnsetCmd( */ varTokenPtr = TokenAfter(parsePtr->tokenPtr); - if (haveFlags) { + for (i=0; i<haveFlags;i++) { varTokenPtr = TokenAfter(varTokenPtr); } for (i=1+haveFlags ; i<parsePtr->numWords ; i++) { diff --git a/generic/tclCompExpr.c b/generic/tclCompExpr.c index 38c1ceb..50edbec 100644 --- a/generic/tclCompExpr.c +++ b/generic/tclCompExpr.c @@ -663,10 +663,12 @@ ParseExpr( if (nodesUsed >= nodesAvailable) { int size = nodesUsed * 2; - OpNode *newPtr; + OpNode *newPtr = NULL; do { + if (size <= UINT_MAX/sizeof(OpNode)) { newPtr = attemptckrealloc(nodes, size * sizeof(OpNode)); + } } while ((newPtr == NULL) && ((size -= (size - nodesUsed) / 2) > nodesUsed)); if (newPtr == NULL) { diff --git a/generic/tclCompile.c b/generic/tclCompile.c index 0f4dfaf..f62ec14 100644 --- a/generic/tclCompile.c +++ b/generic/tclCompile.c @@ -356,7 +356,7 @@ InstructionDesc const tclInstructionTable[] = { /* Create the variables (described in the aux data referred to by the * second immediate argument) to mirror the state of the dictionary in * the variable referred to by the first immediate argument. The list - * of keys (top of the stack, not poppsed) must be the same length as + * of keys (top of the stack, not popped) must be the same length as * the list of variables. * Stack: ... keyList => ... keyList */ {"dictUpdateEnd", 9, -1, 2, {OPERAND_LVT4, OPERAND_AUX4}}, @@ -518,7 +518,7 @@ InstructionDesc const tclInstructionTable[] = { * case. Also runs the whole-array trace on the named variable, so can * throw anything. * Stack: ... varName => ... boolean */ - {"arrayExistsImm", 5, +1, 1, {OPERAND_UINT4}}, + {"arrayExistsImm", 5, +1, 1, {OPERAND_LVT4}}, /* Looks up the variable indexed by opnd and tests whether it is an * array. Pushes a boolean describing whether this is the case. Also * runs the whole-array trace on the named variable, so can throw @@ -528,7 +528,7 @@ InstructionDesc const tclInstructionTable[] = { /* Forces the element on the top of the stack to be the name of an * array. * Stack: ... varName => ... */ - {"arrayMakeImm", 5, 0, 1, {OPERAND_UINT4}}, + {"arrayMakeImm", 5, 0, 1, {OPERAND_LVT4}}, /* Forces the variable indexed by opnd to be an array. Does not touch * the stack. */ @@ -978,8 +978,7 @@ FreeByteCodeInternalRep( register ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1; objPtr->typePtr = NULL; - codePtr->refCount--; - if (codePtr->refCount <= 0) { + if (codePtr->refCount-- <= 1) { TclCleanupByteCode(codePtr); } } @@ -1295,8 +1294,8 @@ CompileSubstObj( if (objPtr->typePtr == &substCodeType) { Namespace *nsPtr = iPtr->varFramePtr->nsPtr; - codePtr = objPtr->internalRep.ptrAndLongRep.ptr; - if ((unsigned long)flags != objPtr->internalRep.ptrAndLongRep.value + codePtr = objPtr->internalRep.twoPtrValue.ptr1; + if (flags != PTR2INT(objPtr->internalRep.twoPtrValue.ptr2) || ((Interp *) *codePtr->interpHandle != iPtr) || (codePtr->compileEpoch != iPtr->compileEpoch) || (codePtr->nsPtr != nsPtr) @@ -1322,8 +1321,8 @@ CompileSubstObj( TclFreeCompileEnv(&compEnv); codePtr = objPtr->internalRep.twoPtrValue.ptr1; - objPtr->internalRep.ptrAndLongRep.ptr = codePtr; - objPtr->internalRep.ptrAndLongRep.value = flags; + objPtr->internalRep.twoPtrValue.ptr1 = codePtr; + objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(flags); if (iPtr->varFramePtr->localCachePtr) { codePtr->localCachePtr = iPtr->varFramePtr->localCachePtr; codePtr->localCachePtr->refCount++; @@ -1362,11 +1361,10 @@ static void FreeSubstCodeInternalRep( register Tcl_Obj *objPtr) /* Object whose internal rep to free. */ { - register ByteCode *codePtr = objPtr->internalRep.ptrAndLongRep.ptr; + register ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1; objPtr->typePtr = NULL; - codePtr->refCount--; - if (codePtr->refCount <= 0) { + if (codePtr->refCount-- <= 1) { TclCleanupByteCode(codePtr); } } @@ -1626,7 +1624,7 @@ TclFreeCompileEnv( envPtr->localLitTable.buckets = envPtr->localLitTable.staticBuckets; } if (envPtr->iPtr) { - /* + /* * We never converted to Bytecode, so free the things we would * have transferred to it. */ @@ -1858,7 +1856,7 @@ CompileExpanded( int wordIdx = 0; DefineLineInformation; int depth = TclGetStackDepth(envPtr); - + StartExpanding(envPtr); if (cmdObj) { CompileCmdLiteral(interp, cmdObj, envPtr); @@ -1907,7 +1905,7 @@ CompileExpanded( TclCheckStackDepth(depth+1, envPtr); } -static int +static int CompileCmdCompileProc( Tcl_Interp *interp, Tcl_Parse *parsePtr, @@ -2008,7 +2006,7 @@ CompileCommandTokens( int cmdIdx = envPtr->numCommands; int startCodeOffset = envPtr->codeNext - envPtr->codeStart; int depth = TclGetStackDepth(envPtr); - + assert (parsePtr->numWords > 0); /* Pre-Compile */ @@ -4037,7 +4035,7 @@ TclEmitInvoke( int arg1, arg2, wordCount = 0, expandCount = 0; int loopRange = 0, breakRange = 0, continueRange = 0; int cleanup, depth = TclGetStackDepth(envPtr); - + /* * Parse the arguments. */ @@ -4085,16 +4083,6 @@ TclEmitInvoke( * calls from inside a [for] increment clause). */ - rangePtr = TclGetInnermostExceptionRange(envPtr, TCL_BREAK, &auxBreakPtr); - if (rangePtr == NULL || rangePtr->type != LOOP_EXCEPTION_RANGE) { - auxBreakPtr = NULL; - } else if (auxBreakPtr->stackDepth == envPtr->currStackDepth-wordCount - && auxBreakPtr->expandTarget == envPtr->expandCount-expandCount) { - auxBreakPtr = NULL; - } else { - breakRange = auxBreakPtr - envPtr->exceptAuxArrayPtr; - } - rangePtr = TclGetInnermostExceptionRange(envPtr, TCL_CONTINUE, &auxContinuePtr); if (rangePtr == NULL || rangePtr->type != LOOP_EXCEPTION_RANGE) { @@ -4103,7 +4091,18 @@ TclEmitInvoke( && auxContinuePtr->expandTarget == envPtr->expandCount-expandCount) { auxContinuePtr = NULL; } else { - continueRange = auxBreakPtr - envPtr->exceptAuxArrayPtr; + continueRange = auxContinuePtr - envPtr->exceptAuxArrayPtr; + } + + rangePtr = TclGetInnermostExceptionRange(envPtr, TCL_BREAK, &auxBreakPtr); + if (rangePtr == NULL || rangePtr->type != LOOP_EXCEPTION_RANGE) { + auxBreakPtr = NULL; + } else if (auxContinuePtr == NULL + && auxBreakPtr->stackDepth == envPtr->currStackDepth-wordCount + && auxBreakPtr->expandTarget == envPtr->expandCount-expandCount) { + auxBreakPtr = NULL; + } else { + breakRange = auxBreakPtr - envPtr->exceptAuxArrayPtr; } if (auxBreakPtr != NULL || auxContinuePtr != NULL) { diff --git a/generic/tclCompile.h b/generic/tclCompile.h index c6c7a7c..b89346d 100644 --- a/generic/tclCompile.h +++ b/generic/tclCompile.h @@ -1171,7 +1171,7 @@ MODULE_SCOPE void TclPushVarName(Tcl_Interp *interp, int flags, int *localIndexPtr, int *isScalarPtr); MODULE_SCOPE void TclReleaseLiteral(Tcl_Interp *interp, Tcl_Obj *objPtr); -MODULE_SCOPE void TclInvalidateCmdLiteral(Tcl_Interp *interp, +MODULE_SCOPE void TclInvalidateCmdLiteral(Tcl_Interp *interp, const char *name, Namespace *nsPtr); MODULE_SCOPE int TclSingleOpCmd(ClientData clientData, Tcl_Interp *interp, int objc, @@ -1194,7 +1194,7 @@ MODULE_SCOPE int TclWordKnownAtCompileTime(Tcl_Token *tokenPtr, MODULE_SCOPE void TclLogCommandInfo(Tcl_Interp *interp, const char *script, const char *command, int length, const unsigned char *pc, - Tcl_Obj **tosPtr); + Tcl_Obj **tosPtr); MODULE_SCOPE Tcl_Obj *TclGetInnerContext(Tcl_Interp *interp, const unsigned char *pc, Tcl_Obj **tosPtr); MODULE_SCOPE Tcl_Obj *TclNewInstNameObj(unsigned char inst); @@ -1660,7 +1660,7 @@ MODULE_SCOPE int TclPushProcCallFrame(ClientData clientData, #define PushVarNameWord(i,v,e,f,l,sc,word) \ SetLineInformation(word); \ - TclPushVarName(i,v,e,f,l,sc) + TclPushVarName(i,v,e,f,l,sc) /* * Often want to issue one of two versions of an instruction based on whether diff --git a/generic/tclDecls.h b/generic/tclDecls.h index 91c0add..b022d3c 100644 --- a/generic/tclDecls.h +++ b/generic/tclDecls.h @@ -48,7 +48,7 @@ EXTERN CONST84_RETURN char * Tcl_PkgRequireEx(Tcl_Interp *interp, const char *name, const char *version, int exact, void *clientDataPtr); /* 2 */ -EXTERN void Tcl_Panic(const char *format, ...) TCL_FORMAT_PRINTF(1, 2); +EXTERN TCL_NORETURN void Tcl_Panic(const char *format, ...) TCL_FORMAT_PRINTF(1, 2); /* 3 */ EXTERN char * Tcl_Alloc(unsigned int size); /* 4 */ @@ -417,7 +417,7 @@ EXTERN int Tcl_EvalObj(Tcl_Interp *interp, Tcl_Obj *objPtr); EXTERN void Tcl_EventuallyFree(ClientData clientData, Tcl_FreeProc *freeProc); /* 133 */ -EXTERN void Tcl_Exit(int status); +EXTERN TCL_NORETURN void Tcl_Exit(int status); /* 134 */ EXTERN int Tcl_ExposeCommand(Tcl_Interp *interp, const char *hiddenCmdToken, @@ -686,7 +686,8 @@ EXTERN void Tcl_SetErrorCode(Tcl_Interp *interp, ...); /* 229 */ EXTERN void Tcl_SetMaxBlockTime(const Tcl_Time *timePtr); /* 230 */ -EXTERN void Tcl_SetPanicProc(Tcl_PanicProc *panicProc); +EXTERN void Tcl_SetPanicProc( + TCL_NORETURN1 Tcl_PanicProc *panicProc); /* 231 */ EXTERN int Tcl_SetRecursionLimit(Tcl_Interp *interp, int depth); /* 232 */ @@ -835,7 +836,7 @@ EXTERN int Tcl_VarEvalVA(Tcl_Interp *interp, va_list argList); /* 277 */ EXTERN Tcl_Pid Tcl_WaitPid(Tcl_Pid pid, int *statPtr, int options); /* 278 */ -EXTERN void Tcl_PanicVA(const char *format, va_list argList); +EXTERN TCL_NORETURN void Tcl_PanicVA(const char *format, va_list argList); /* 279 */ EXTERN void Tcl_GetVersion(int *major, int *minor, int *patchLevel, int *type); @@ -1499,7 +1500,7 @@ EXTERN void Tcl_GetCommandFullName(Tcl_Interp *interp, EXTERN int Tcl_FSEvalFileEx(Tcl_Interp *interp, Tcl_Obj *fileName, const char *encodingName); /* 519 */ -EXTERN Tcl_ExitProc * Tcl_SetExitProc(Tcl_ExitProc *proc); +EXTERN Tcl_ExitProc * Tcl_SetExitProc(TCL_NORETURN1 Tcl_ExitProc *proc); /* 520 */ EXTERN void Tcl_LimitAddHandler(Tcl_Interp *interp, int type, Tcl_LimitHandlerProc *handlerProc, @@ -1828,7 +1829,7 @@ typedef struct TclStubs { int (*tcl_PkgProvideEx) (Tcl_Interp *interp, const char *name, const char *version, const void *clientData); /* 0 */ CONST84_RETURN char * (*tcl_PkgRequireEx) (Tcl_Interp *interp, const char *name, const char *version, int exact, void *clientDataPtr); /* 1 */ - void (*tcl_Panic) (const char *format, ...) TCL_FORMAT_PRINTF(1, 2); /* 2 */ + TCL_NORETURN1 void (*tcl_Panic) (const char *format, ...) TCL_FORMAT_PRINTF(1, 2); /* 2 */ char * (*tcl_Alloc) (unsigned int size); /* 3 */ void (*tcl_Free) (char *ptr); /* 4 */ char * (*tcl_Realloc) (char *ptr, unsigned int size); /* 5 */ @@ -1975,7 +1976,7 @@ typedef struct TclStubs { int (*tcl_EvalFile) (Tcl_Interp *interp, const char *fileName); /* 130 */ int (*tcl_EvalObj) (Tcl_Interp *interp, Tcl_Obj *objPtr); /* 131 */ void (*tcl_EventuallyFree) (ClientData clientData, Tcl_FreeProc *freeProc); /* 132 */ - void (*tcl_Exit) (int status); /* 133 */ + TCL_NORETURN1 void (*tcl_Exit) (int status); /* 133 */ int (*tcl_ExposeCommand) (Tcl_Interp *interp, const char *hiddenCmdToken, const char *cmdName); /* 134 */ int (*tcl_ExprBoolean) (Tcl_Interp *interp, const char *expr, int *ptr); /* 135 */ int (*tcl_ExprBooleanObj) (Tcl_Interp *interp, Tcl_Obj *objPtr, int *ptr); /* 136 */ @@ -2080,7 +2081,7 @@ typedef struct TclStubs { void (*tcl_SetErrno) (int err); /* 227 */ void (*tcl_SetErrorCode) (Tcl_Interp *interp, ...); /* 228 */ void (*tcl_SetMaxBlockTime) (const Tcl_Time *timePtr); /* 229 */ - void (*tcl_SetPanicProc) (Tcl_PanicProc *panicProc); /* 230 */ + void (*tcl_SetPanicProc) (TCL_NORETURN1 Tcl_PanicProc *panicProc); /* 230 */ int (*tcl_SetRecursionLimit) (Tcl_Interp *interp, int depth); /* 231 */ void (*tcl_SetResult) (Tcl_Interp *interp, char *result, Tcl_FreeProc *freeProc); /* 232 */ int (*tcl_SetServiceMode) (int mode); /* 233 */ @@ -2128,7 +2129,7 @@ typedef struct TclStubs { void (*tcl_SetErrorCodeVA) (Tcl_Interp *interp, va_list argList); /* 275 */ int (*tcl_VarEvalVA) (Tcl_Interp *interp, va_list argList); /* 276 */ Tcl_Pid (*tcl_WaitPid) (Tcl_Pid pid, int *statPtr, int options); /* 277 */ - void (*tcl_PanicVA) (const char *format, va_list argList); /* 278 */ + TCL_NORETURN1 void (*tcl_PanicVA) (const char *format, va_list argList); /* 278 */ void (*tcl_GetVersion) (int *major, int *minor, int *patchLevel, int *type); /* 279 */ void (*tcl_InitMemory) (Tcl_Interp *interp); /* 280 */ Tcl_Channel (*tcl_StackChannel) (Tcl_Interp *interp, const Tcl_ChannelType *typePtr, ClientData instanceData, int mask, Tcl_Channel prevChan); /* 281 */ @@ -2369,7 +2370,7 @@ typedef struct TclStubs { Tcl_Command (*tcl_GetCommandFromObj) (Tcl_Interp *interp, Tcl_Obj *objPtr); /* 516 */ void (*tcl_GetCommandFullName) (Tcl_Interp *interp, Tcl_Command command, Tcl_Obj *objPtr); /* 517 */ int (*tcl_FSEvalFileEx) (Tcl_Interp *interp, Tcl_Obj *fileName, const char *encodingName); /* 518 */ - Tcl_ExitProc * (*tcl_SetExitProc) (Tcl_ExitProc *proc); /* 519 */ + Tcl_ExitProc * (*tcl_SetExitProc) (TCL_NORETURN1 Tcl_ExitProc *proc); /* 519 */ void (*tcl_LimitAddHandler) (Tcl_Interp *interp, int type, Tcl_LimitHandlerProc *handlerProc, ClientData clientData, Tcl_LimitHandlerDeleteProc *deleteProc); /* 520 */ void (*tcl_LimitRemoveHandler) (Tcl_Interp *interp, int type, Tcl_LimitHandlerProc *handlerProc, ClientData clientData); /* 521 */ int (*tcl_LimitReady) (Tcl_Interp *interp); /* 522 */ diff --git a/generic/tclDictObj.c b/generic/tclDictObj.c index 15fbe1e..c8474e6 100644 --- a/generic/tclDictObj.c +++ b/generic/tclDictObj.c @@ -631,7 +631,7 @@ SetDictFromAny( } for (i=0 ; i<objc ; i+=2) { - + /* Store key and value in the hash table we're building. */ hPtr = CreateChainEntry(dict, objv[i], &isNew); if (!isNew) { @@ -3051,14 +3051,14 @@ DictFilterCmd( Tcl_IncrRefCount(valueObj); if (Tcl_ObjSetVar2(interp, keyVarObj, NULL, keyObj, TCL_LEAVE_ERR_MSG) == NULL) { - Tcl_AddErrorInfo(interp, + Tcl_AddErrorInfo(interp, "\n (\"dict filter\" filter script key variable)"); result = TCL_ERROR; goto abnormalResult; } if (Tcl_ObjSetVar2(interp, valueVarObj, NULL, valueObj, TCL_LEAVE_ERR_MSG) == NULL) { - Tcl_AddErrorInfo(interp, + Tcl_AddErrorInfo(interp, "\n (\"dict filter\" filter script value variable)"); result = TCL_ERROR; goto abnormalResult; diff --git a/generic/tclDisassemble.c b/generic/tclDisassemble.c index b3753c31..86f0e1d 100644 --- a/generic/tclDisassemble.c +++ b/generic/tclDisassemble.c @@ -794,6 +794,7 @@ PrintSourceToObj( { register const char *p; register int i = 0, len; + Tcl_UniChar ch = 0; if (stringPtr == NULL) { Tcl_AppendToObj(appendObj, "\"\"", -1); @@ -803,7 +804,6 @@ PrintSourceToObj( Tcl_AppendToObj(appendObj, "\"", -1); p = stringPtr; for (; (*p != '\0') && (i < maxChars); p+=len) { - Tcl_UniChar ch; len = TclUtfToUniChar(p, &ch); switch (ch) { @@ -832,6 +832,23 @@ PrintSourceToObj( i += 2; continue; default: +#if TCL_UTF_MAX > 4 + if (ch > 0xffff) { + Tcl_AppendPrintfToObj(appendObj, "\\U%08x", ch); + i += 10; + } else +#elif TCL_UTF_MAX > 3 + /* If len == 0, this means we have a char > 0xffff, resulting in + * TclUtfToUniChar producing a surrogate pair. We want to output + * this pair as a single Unicode character. + */ + if (len == 0) { + int upper = ((ch & 0x3ff) + 1) << 10; + len = TclUtfToUniChar(p, &ch); + Tcl_AppendPrintfToObj(appendObj, "\\U%08x", upper + (ch & 0x3ff)); + i += 10; + } else +#endif if (ch < 0x20 || ch >= 0x7f) { Tcl_AppendPrintfToObj(appendObj, "\\u%04x", ch); i += 6; @@ -842,10 +859,10 @@ PrintSourceToObj( continue; } } - Tcl_AppendToObj(appendObj, "\"", -1); if (*p != '\0') { Tcl_AppendToObj(appendObj, "...", -1); } + Tcl_AppendToObj(appendObj, "\"", -1); } /* diff --git a/generic/tclEncoding.c b/generic/tclEncoding.c index 179ca17..4edebcf 100644 --- a/generic/tclEncoding.c +++ b/generic/tclEncoding.c @@ -1450,7 +1450,7 @@ Tcl_UtfToExternal( * * Side effects: * The absolute pathname for the application is computed and stored to be - * returned later be [info nameofexecutable]. + * returned later by [info nameofexecutable]. * *--------------------------------------------------------------------------- */ @@ -2334,7 +2334,7 @@ UtfToUtfProc( *dst++ = *src++; } else if (pureNullMode == 1 && UCHAR(*src) == 0xc0 && - UCHAR(*(src+1)) == 0x80) { + (src + 1 < srcEnd) && UCHAR(*(src+1)) == 0x80) { /* * Convert 0xc080 to real nulls when we are in output mode. */ @@ -2525,22 +2525,35 @@ UtfToUnicodeProc( if (dst > dstEnd) { result = TCL_CONVERT_NOSPACE; break; - } + } src += TclUtfToUniChar(src, &ch); /* * Need to handle this in a way that won't cause misalignment by * casting dst to a Tcl_UniChar. [Bug 1122671] - * XXX: This hard-codes the assumed size of Tcl_UniChar as 2. */ #ifdef WORDS_BIGENDIAN +#if TCL_UTF_MAX > 4 + *dst++ = (ch >> 24); + *dst++ = ((ch >> 16) & 0xFF); + *dst++ = ((ch >> 8) & 0xFF); + *dst++ = (ch & 0xFF); +#else *dst++ = (ch >> 8); *dst++ = (ch & 0xFF); +#endif +#else +#if TCL_UTF_MAX > 4 + *dst++ = (ch & 0xFF); + *dst++ = ((ch >> 8) & 0xFF); + *dst++ = ((ch >> 16) & 0xFF); + *dst++ = (ch >> 24); #else *dst++ = (ch & 0xFF); *dst++ = (ch >> 8); #endif +#endif } *srcReadPtr = src - srcStart; *dstWrotePtr = dst - dstStart; diff --git a/generic/tclEnsemble.c b/generic/tclEnsemble.c index 473c4bb..8f7d1a2 100644 --- a/generic/tclEnsemble.c +++ b/generic/tclEnsemble.c @@ -3115,7 +3115,7 @@ TclAttemptCompileProc( result = cmdPtr->compileProc(interp, parsePtr, cmdPtr, envPtr); /* - * Undo the shift. + * Undo the shift. */ mapPtr->loc[eclIndex].line -= (depth - 1); diff --git a/generic/tclEnv.c b/generic/tclEnv.c index cd1a954..2cb240d 100644 --- a/generic/tclEnv.c +++ b/generic/tclEnv.c @@ -43,11 +43,6 @@ static char * EnvTraceProc(ClientData clientData, Tcl_Interp *interp, static void ReplaceString(const char *oldStr, char *newStr); MODULE_SCOPE void TclSetEnv(const char *name, const char *value); MODULE_SCOPE void TclUnsetEnv(const char *name); - -#if defined(__CYGWIN__) - static void TclCygwinPutenv(char *string); -# define putenv TclCygwinPutenv -#endif /* *---------------------------------------------------------------------- @@ -444,7 +439,7 @@ TclUnsetEnv( * that no = should be included, and Windows requires it. */ -#if defined(_WIN32) || defined(__CYGWIN__) +#if defined(_WIN32) string = ckalloc(length + 2); memcpy(string, name, (size_t) length); string[length] = '='; @@ -740,98 +735,6 @@ TclFinalizeEnvironment(void) } } -#if defined(__CYGWIN__) - -/* - * When using cygwin, when an environment variable changes, we need to synch - * with both the cygwin environment (in case the application C code calls - * fork) and the Windows environment (in case the application TCL code calls - * exec, which calls the Windows CreateProcess function). - */ -DLLIMPORT extern void __stdcall SetEnvironmentVariableA(const char*, const char *); - -static void -TclCygwinPutenv( - char *str) -{ - char *name, *value; - - /* - * Get the name and value, so that we can change the environment variable - * for Windows. - */ - - name = alloca(strlen(str) + 1); - strcpy(name, str); - for (value=name ; *value!='=' && *value!='\0' ; ++value) { - /* Empty body */ - } - if (*value == '\0') { - /* Can't happen. */ - return; - } - *(value++) = '\0'; - if (*value == '\0') { - value = NULL; - } - - /* - * Set the cygwin environment variable. - */ - -#undef putenv - if (value == NULL) { - unsetenv(name); - } else { - putenv(str); - } - - /* - * Before changing the environment variable in Windows, if this is PATH, - * we need to convert the value back to a Windows style path. - * - * FIXME: The calling program may know it is running under windows, and - * may have set the path to a Windows path, or, worse, appended or - * prepended a Windows path to PATH. - */ - - if (strcmp(name, "PATH") != 0) { - /* - * If this is Path, eliminate any PATH variable, to prevent any - * confusion. - */ - - if (strcmp(name, "Path") == 0) { - SetEnvironmentVariableA("PATH", NULL); - unsetenv("PATH"); - } - - SetEnvironmentVariableA(name, value); - } else { - char *buf; - - /* - * Eliminate any Path variable, to prevent any confusion. - */ - - SetEnvironmentVariableA("Path", NULL); - unsetenv("Path"); - - if (value == NULL) { - buf = NULL; - } else { - int size; - - size = cygwin_conv_path_list(0, value, NULL, 0); - buf = alloca(size + 1); - cygwin_conv_path_list(0, value, buf, size); - } - - SetEnvironmentVariableA(name, buf); - } -} -#endif /* __CYGWIN__ */ - /* * Local Variables: * mode: c diff --git a/generic/tclEvent.c b/generic/tclEvent.c index 6ca22a6..8305410 100644 --- a/generic/tclEvent.c +++ b/generic/tclEvent.c @@ -89,7 +89,7 @@ static int subsystemsInitialized = 0; * non-NULL value. */ -static Tcl_ExitProc *appExitPtr = NULL; +static TCL_NORETURN1 Tcl_ExitProc *appExitPtr = NULL; typedef struct ThreadSpecificData { ExitHandler *firstExitPtr; /* First in list of all exit handlers for this @@ -263,7 +263,7 @@ HandleBgErrors( if (errChannel != NULL) { Tcl_Obj *options = Tcl_GetReturnOptions(interp, code); - Tcl_Obj *keyPtr, *valuePtr; + Tcl_Obj *keyPtr, *valuePtr = NULL; TclNewLiteralStringObj(keyPtr, "-errorinfo"); Tcl_IncrRefCount(keyPtr); @@ -315,7 +315,7 @@ TclDefaultBgErrorHandlerObjCmd( { Tcl_Obj *keyPtr, *valuePtr; Tcl_Obj *tempObjv[2]; - int code, level; + int result, code, level; Tcl_InterpState saved; if (objc != 3) { @@ -329,9 +329,9 @@ TclDefaultBgErrorHandlerObjCmd( TclNewLiteralStringObj(keyPtr, "-level"); Tcl_IncrRefCount(keyPtr); - Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); + result = Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); Tcl_DecrRefCount(keyPtr); - if (valuePtr == NULL) { + if (result != TCL_OK || valuePtr == NULL) { Tcl_SetObjResult(interp, Tcl_NewStringObj( "missing return option \"-level\"", -1)); Tcl_SetErrorCode(interp, "TCL", "ARGUMENT", "MISSING", NULL); @@ -342,9 +342,9 @@ TclDefaultBgErrorHandlerObjCmd( } TclNewLiteralStringObj(keyPtr, "-code"); Tcl_IncrRefCount(keyPtr); - Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); + result = Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); Tcl_DecrRefCount(keyPtr); - if (valuePtr == NULL) { + if (result != TCL_OK || valuePtr == NULL) { Tcl_SetObjResult(interp, Tcl_NewStringObj( "missing return option \"-code\"", -1)); Tcl_SetErrorCode(interp, "TCL", "ARGUMENT", "MISSING", NULL); @@ -407,17 +407,17 @@ TclDefaultBgErrorHandlerObjCmd( TclNewLiteralStringObj(keyPtr, "-errorcode"); Tcl_IncrRefCount(keyPtr); - Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); + result = Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); Tcl_DecrRefCount(keyPtr); - if (valuePtr) { + if (result == TCL_OK && valuePtr != NULL) { Tcl_SetObjErrorCode(interp, valuePtr); } TclNewLiteralStringObj(keyPtr, "-errorinfo"); Tcl_IncrRefCount(keyPtr); - Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); + result = Tcl_DictObjGet(NULL, objv[2], keyPtr, &valuePtr); Tcl_DecrRefCount(keyPtr); - if (valuePtr) { + if (result == TCL_OK && valuePtr != NULL) { Tcl_AppendObjToErrorInfo(interp, valuePtr); } @@ -857,7 +857,7 @@ Tcl_DeleteThreadExitHandler( Tcl_ExitProc * Tcl_SetExitProc( - Tcl_ExitProc *proc) /* New exit handler for app or NULL */ + TCL_NORETURN1 Tcl_ExitProc *proc) /* New exit handler for app or NULL */ { Tcl_ExitProc *prevExitProc; @@ -892,7 +892,7 @@ Tcl_SetExitProc( *---------------------------------------------------------------------- */ static void -InvokeExitHandlers(void) +InvokeExitHandlers(void) { ExitHandler *exitPtr; @@ -933,12 +933,12 @@ InvokeExitHandlers(void) *---------------------------------------------------------------------- */ -void +TCL_NORETURN void Tcl_Exit( int status) /* Exit status for application; typically 0 * for normal return, 1 for error return. */ { - Tcl_ExitProc *currentAppExitPtr; + TCL_NORETURN1 Tcl_ExitProc *currentAppExitPtr; Tcl_MutexLock(&exitMutex); currentAppExitPtr = appExitPtr; @@ -968,22 +968,22 @@ Tcl_Exit( /* * Fast and deterministic exit (default behavior) */ - + InvokeExitHandlers(); - + /* * Ensure the thread-specific data is initialised as it is used in * Tcl_FinalizeThread() */ - + (void) TCL_TSD_INIT(&dataKey); - + /* * Now finalize the calling thread only (others are not safely * reachable). Among other things, this triggers a flush of the * Tcl_Channels that may have data enqueued. */ - + FinalizeThread(/* quick */ 1); } TclpExit(status); @@ -1090,7 +1090,7 @@ Tcl_Finalize(void) * Invoke exit handlers first. */ - InvokeExitHandlers(); + InvokeExitHandlers(); TclpInitLock(); if (subsystemsInitialized == 0) { diff --git a/generic/tclExecute.c b/generic/tclExecute.c index b9da8fc..7f65262 100644 --- a/generic/tclExecute.c +++ b/generic/tclExecute.c @@ -198,14 +198,14 @@ typedef struct TEBCdata { if (auxObjList) { \ objPtr->length += auxObjList->length; \ } \ - objPtr->internalRep.ptrAndLongRep.ptr = auxObjList; \ + objPtr->internalRep.twoPtrValue.ptr1 = auxObjList; \ auxObjList = objPtr; \ } while (0) #define POP_TAUX_OBJ() \ do { \ tmpPtr = auxObjList; \ - auxObjList = tmpPtr->internalRep.ptrAndLongRep.ptr; \ + auxObjList = tmpPtr->internalRep.twoPtrValue.ptr1; \ Tcl_DecrRefCount(tmpPtr); \ } while (0) @@ -758,7 +758,7 @@ static Tcl_Obj * ExecuteExtendedUnaryMathOp(int opcode, Tcl_Obj *valuePtr); static void FreeExprCodeInternalRep(Tcl_Obj *objPtr); static ExceptionRange * GetExceptRangeForPc(const unsigned char *pc, - int catchOnly, ByteCode *codePtr); + int searchMode, ByteCode *codePtr); static const char * GetSrcInfoForPc(const unsigned char *pc, ByteCode *codePtr, int *lengthPtr, const unsigned char **pcBeg, int *cmdIdxPtr); @@ -1138,7 +1138,7 @@ GrowEvaluationStack( } needed = growth + moveWords + WALLOCALIGN; - + /* * Check if there is enough room in the next stack (if there is one, it * should be both empty and the last one!) @@ -1176,7 +1176,7 @@ GrowEvaluationStack( #else newElems = needed; #endif - + newBytes = sizeof(ExecStack) + (newElems-1) * sizeof(Tcl_Obj *); oldPtr = esPtr; @@ -1649,8 +1649,7 @@ FreeExprCodeInternalRep( ByteCode *codePtr = objPtr->internalRep.twoPtrValue.ptr1; objPtr->typePtr = NULL; - codePtr->refCount--; - if (codePtr->refCount <= 0) { + if (codePtr->refCount-- <= 1) { TclCleanupByteCode(codePtr); } } @@ -2153,7 +2152,7 @@ TEBCresume( const unsigned char *pc = data[1]; /* The current program counter. */ unsigned char inst; /* The currently running instruction */ - + /* * Transfer variables - needed only between opcodes, but not while * executing an instruction. @@ -2358,7 +2357,7 @@ TEBCresume( */ inst = *pc; - + peepholeStart: #ifdef TCL_COMPILE_STATS iPtr->stats.instructionCount[*pc]++; @@ -2378,7 +2377,7 @@ TEBCresume( #endif /* TCL_COMPILE_DEBUG */ TCL_DTRACE_INST_NEXT(); - + if (inst == INST_LOAD_SCALAR1) { goto instLoadScalar1; } else if (inst == INST_PUSH1) { @@ -2390,7 +2389,7 @@ TEBCresume( /* * Peephole: do not run INST_START_CMD, just skip it */ - + iPtr->cmdCount += TclGetUInt4AtPtr(pc+5); if (checkInterp) { checkInterp = 0; @@ -2411,7 +2410,7 @@ TEBCresume( } goto peepholeStart; } - + switch (inst) { case INST_SYNTAX: case INST_RETURN_IMM: { @@ -2558,7 +2557,7 @@ TEBCresume( /* TIP #280: Record the last piece of info needed by * 'TclGetSrcInfoForPc', and push the frame. */ - + bcFramePtr->data.tebc.pc = (char *) pc; iPtr->cmdFramePtr = bcFramePtr; @@ -2858,7 +2857,7 @@ TEBCresume( */ TclNewObj(objPtr); - objPtr->internalRep.ptrAndLongRep.value = CURR_DEPTH; + objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(CURR_DEPTH); objPtr->length = 0; PUSH_TAUX_OBJ(objPtr); TRACE(("=> mark depth as %d\n", (int) CURR_DEPTH)); @@ -2872,7 +2871,7 @@ TEBCresume( */ CLANG_ASSERT(auxObjList); - objc = CURR_DEPTH - auxObjList->internalRep.ptrAndLongRep.value; + objc = CURR_DEPTH - PTR2INT(auxObjList->internalRep.twoPtrValue.ptr2); POP_TAUX_OBJ(); #ifdef TCL_COMPILE_DEBUG /* Ugly abuse! */ @@ -2921,7 +2920,6 @@ TEBCresume( * stack-allocated parameter, update the stack pointers. */ - esPtr = iPtr->execEnvPtr->execStackPtr; TD = (TEBCdata *) (((Tcl_Obj **)TD) + moved); catchTop += moved; @@ -2973,7 +2971,7 @@ TEBCresume( case INST_INVOKE_EXPANDED: CLANG_ASSERT(auxObjList); - objc = CURR_DEPTH - auxObjList->internalRep.ptrAndLongRep.value; + objc = CURR_DEPTH - PTR2INT(auxObjList->internalRep.twoPtrValue.ptr2); POP_TAUX_OBJ(); if (objc) { pcAdjustment = 1; @@ -3185,8 +3183,8 @@ TEBCresume( pc += 6; TEBC_YIELD(); + TclMarkTailcall(interp); TclNRAddCallback(interp, TclClearRootEnsemble, NULL,NULL,NULL,NULL); - TclSkipTailcall(interp); return TclNREvalObjEx(interp, objPtr, TCL_EVAL_INVOKE, NULL, INT_MIN); /* @@ -4182,10 +4180,12 @@ TEBCresume( if (!TclIsVarUndefined(varPtr)) { TclDecrRefCount(varPtr->value.objPtr); + TclSetVarUndefined(varPtr); + TclClearVarNamespaceVar(varPtr); + TclCleanupVar(varPtr, arrayPtr); } else if (flags & TCL_LEAVE_ERR_MSG) { goto slowUnsetArray; } - varPtr->value.objPtr = NULL; TRACE_APPEND(("OK\n")); NEXT_INST_F(6, 1, 0); } else if (!varPtr && !(flags & TCL_LEAVE_ERR_MSG)) { @@ -4946,6 +4946,7 @@ TEBCresume( pc += pcAdjustment; TEBC_YIELD(); + TclPushTailcallPoint(interp); oPtr = contextPtr->oPtr; if (oPtr->flags & FILTER_HANDLING) { TclNRAddCallback(interp, FinalizeOONextFilter, @@ -5591,7 +5592,7 @@ TEBCresume( TclNewObj(objResultPtr); } else if (TclIsPureByteArray(valuePtr)) { objResultPtr = Tcl_NewByteArrayObj( - Tcl_GetByteArrayFromObj(valuePtr, &length)+index, 1); + Tcl_GetByteArrayFromObj(valuePtr, NULL)+index, 1); } else if (valuePtr->bytes && length == valuePtr->length) { objResultPtr = Tcl_NewStringObj((const char *) valuePtr->bytes+index, 1); @@ -5763,7 +5764,7 @@ TEBCresume( * at this point (post Tcl_GetUnicodeFromObj). */ - ((int *) objResultPtr->internalRep.otherValuePtr)[1] = 0; + ((int *) objResultPtr->internalRep.twoPtrValue.ptr1)[1] = 0; } Tcl_InvalidateStringRep(objResultPtr); TclDecrRefCount(value3Ptr); @@ -5790,7 +5791,7 @@ TEBCresume( * at this point (post Tcl_GetUnicodeFromObj). */ - ((int *) objResultPtr->internalRep.otherValuePtr)[1] = 0; + ((int *) objResultPtr->internalRep.twoPtrValue.ptr1)[1] = 0; } Tcl_InvalidateStringRep(valuePtr); TclDecrRefCount(value3Ptr); @@ -7111,7 +7112,7 @@ TEBCresume( */ TclNewObj(tmpPtr); - tmpPtr->internalRep.otherValuePtr = infoPtr; + tmpPtr->internalRep.twoPtrValue.ptr1 = infoPtr; PUSH_OBJECT(tmpPtr); /* infoPtr object */ TRACE_APPEND(("jump to loop step\n")); @@ -7129,7 +7130,7 @@ TEBCresume( */ tmpPtr = OBJ_AT_TOS; - infoPtr = tmpPtr->internalRep.otherValuePtr; + infoPtr = tmpPtr->internalRep.twoPtrValue.ptr1; numLists = infoPtr->numLists; TRACE(("=> ")); @@ -7213,7 +7214,7 @@ TEBCresume( case INST_FOREACH_END: /* THIS INSTRUCTION IS ONLY CALLED AS A BREAK TARGET */ tmpPtr = OBJ_AT_TOS; - infoPtr = tmpPtr->internalRep.otherValuePtr; + infoPtr = tmpPtr->internalRep.twoPtrValue.ptr1; numLists = infoPtr->numLists; TRACE(("=> loop terminated\n")); NEXT_INST_V(1, numLists+2, 0); @@ -7230,10 +7231,10 @@ TEBCresume( */ tmpPtr = OBJ_AT_DEPTH(1); - infoPtr = tmpPtr->internalRep.otherValuePtr; + infoPtr = tmpPtr->internalRep.twoPtrValue.ptr1; numLists = infoPtr->numLists; TRACE_APPEND(("=> appending to list at depth %d\n", 3 + numLists)); - + objPtr = OBJ_AT_DEPTH(3 + numLists); Tcl_ListObjAppendElement(NULL, objPtr, OBJ_AT_TOS); NEXT_INST_F(1, 1, 0); @@ -7953,7 +7954,7 @@ TEBCresume( } #endif if ((result == TCL_CONTINUE) || (result == TCL_BREAK)) { - rangePtr = GetExceptRangeForPc(pc, /*catchOnly*/ 0, codePtr); + rangePtr = GetExceptRangeForPc(pc, result, codePtr); if (rangePtr == NULL) { TRACE_APPEND(("no encl. loop or catch, returning %s\n", StringForResultCode(result))); @@ -8065,7 +8066,7 @@ TEBCresume( while (auxObjList) { if ((catchTop != initCatchTop) && (*catchTop > (ptrdiff_t) - auxObjList->internalRep.ptrAndLongRep.value)) { + auxObjList->internalRep.twoPtrValue.ptr2)) { break; } POP_TAUX_OBJ(); @@ -8114,7 +8115,7 @@ TEBCresume( #endif goto abnormalReturn; } - rangePtr = GetExceptRangeForPc(pc, /*catchOnly*/ 1, codePtr); + rangePtr = GetExceptRangeForPc(pc, TCL_ERROR, codePtr); if (rangePtr == NULL) { /* * This is only possible when compiling a [catch] that sends its @@ -8195,7 +8196,7 @@ TEBCresume( } iPtr->cmdFramePtr = bcFramePtr->nextPtr; - if (--codePtr->refCount <= 0) { + if (codePtr->refCount-- <= 1) { TclCleanupByteCode(codePtr); } TclStackFree(interp, TD); /* free my stack */ @@ -8234,6 +8235,7 @@ TEBCresume( bytes = GetSrcInfoForPc(pc, codePtr, &length, NULL, NULL); opnd = TclGetUInt4AtPtr(pc+1); pc += (opnd-1); + assert(bytes); PUSH_OBJECT(Tcl_NewStringObj(bytes, length)); goto instEvalStk; } @@ -8247,6 +8249,7 @@ TEBCresume( #undef auxObjList #undef catchTop #undef TCONST +#undef esPtr static int FinalizeOONext( @@ -9773,7 +9776,7 @@ ValidatePcAndStackTop( (unsigned) opCode, relativePc); Tcl_Panic("TclNRExecuteByteCode execution failure: bad opcode"); } - if (checkStack && + if (checkStack && ((stackTop < 0) || (stackTop > stackUpperBound))) { int numChars; const char *cmd = GetSrcInfoForPc(pc, codePtr, &numChars, NULL, NULL); @@ -9899,7 +9902,11 @@ TclGetSourceFromFrame( cfPtr->cmd = GetSrcInfoForPc((unsigned char *) cfPtr->data.tebc.pc, codePtr, &cfPtr->len, NULL, NULL); } - cfPtr->cmdObj = Tcl_NewStringObj(cfPtr->cmd, cfPtr->len); + if (cfPtr->cmd) { + cfPtr->cmdObj = Tcl_NewStringObj(cfPtr->cmd, cfPtr->len); + } else { + cfPtr->cmdObj = Tcl_NewListObj(objc, objv); + } Tcl_IncrRefCount(cfPtr->cmdObj); } return cfPtr->cmdObj; @@ -9981,7 +9988,7 @@ GetSrcInfoForPc( * where the current instruction starts. * If NULL; no pointer is stored. */ int *cmdIdxPtr) /* If non-NULL, the location where the index - * of the command containing the pc should + * of the command containing the pc should * be stored. */ { register int pcOffset = (pc - codePtr->codeStart); @@ -9994,10 +10001,8 @@ GetSrcInfoForPc( int bestSrcLength = -1; /* Initialized to avoid compiler warning. */ int bestCmdIdx = -1; - if ((pcOffset < 0) || (pcOffset >= codePtr->numCodeBytes)) { - if (pcBeg != NULL) *pcBeg = NULL; - return NULL; - } + /* The pc must point within the bytecode */ + assert ((pcOffset >= 0) && (pcOffset < codePtr->numCodeBytes)); /* * Decode the code and source offset and length for each command. The @@ -10106,13 +10111,14 @@ GetSrcInfoForPc( * ExceptionRange. * * Results: - * In the normal case, catchOnly is 0 (false) and this procedure returns - * a pointer to the most closely enclosing ExceptionRange structure - * regardless of whether it is a loop or catch exception range. This is - * appropriate when processing a TCL_BREAK or TCL_CONTINUE, which will be - * "handled" either by a loop exception range or a closer catch range. If - * catchOnly is nonzero, this procedure ignores loop exception ranges and - * returns a pointer to the closest catch range. If no matching + * If the searchMode is TCL_ERROR, this procedure ignores loop exception + * ranges and returns a pointer to the closest catch range. If the + * searchMode is TCL_BREAK, this procedure returns a pointer to the most + * closely enclosing ExceptionRange regardless of whether it is a loop or + * catch exception range. If the searchMode is TCL_CONTINUE, this + * procedure returns a pointer to the most closely enclosing + * ExceptionRange (of any type) skipping only loop exception ranges if + * they don't have a sensible continueOffset defined. If no matching * ExceptionRange is found that encloses pc, a NULL is returned. * * Side effects: @@ -10123,14 +10129,16 @@ GetSrcInfoForPc( static ExceptionRange * GetExceptRangeForPc( - const unsigned char *pc, /* The program counter value for which to + const unsigned char *pc, /* The program counter value for which to * search for a closest enclosing exception * range. This points to a bytecode * instruction in codePtr's code. */ - int catchOnly, /* If 0, consider either loop or catch - * ExceptionRanges in search. If nonzero + int searchMode, /* If TCL_BREAK, consider either loop or catch + * ExceptionRanges in search. If TCL_ERROR * consider only catch ranges (and ignore any - * closer loop ranges). */ + * closer loop ranges). If TCL_CONTINUE, look + * for loop ranges that define a continue + * point or a catch range. */ ByteCode *codePtr) /* Points to the ByteCode in which to search * for the enclosing ExceptionRange. */ { @@ -10156,8 +10164,13 @@ GetExceptRangeForPc( start = rangePtr->codeOffset; if ((start <= pcOffset) && (pcOffset < (start + rangePtr->numCodeBytes))) { - if ((!catchOnly) - || (rangePtr->type == CATCH_EXCEPTION_RANGE)) { + if (rangePtr->type == CATCH_EXCEPTION_RANGE) { + return rangePtr; + } + if (searchMode == TCL_BREAK) { + return rangePtr; + } + if (searchMode == TCL_CONTINUE && rangePtr->continueOffset != -1){ return rangePtr; } } diff --git a/generic/tclFCmd.c b/generic/tclFCmd.c index 8bf0a5a..bb814ea 100644 --- a/generic/tclFCmd.c +++ b/generic/tclFCmd.c @@ -120,7 +120,7 @@ FileCopyRename( } i++; if ((objc - i) < 2) { - Tcl_WrongNumArgs(interp, 1, objv, + Tcl_WrongNumArgs(interp, 1, objv, "?-option value ...? source ?source ...? target"); return TCL_ERROR; } @@ -735,7 +735,7 @@ CopyRenameOneFile( errfile = target; } - /* + /* * We now need to reset the result, because the above call, * may have left set it. (Ideally we would prefer not to pass * an interpreter in above, but the channel IO code used by diff --git a/generic/tclFileName.c b/generic/tclFileName.c index a7251bb..39bac99 100644 --- a/generic/tclFileName.c +++ b/generic/tclFileName.c @@ -821,10 +821,10 @@ Tcl_FSJoinToPath( return TclJoinPath(2, pair); } else { int elemc = objc + 1; - Tcl_Obj *ret, **elemv = ckalloc(elemc*sizeof(Tcl_Obj **)); + Tcl_Obj *ret, **elemv = ckalloc(elemc*sizeof(Tcl_Obj *)); elemv[0] = pathPtr; - memcpy(elemv+1, objv, objc*sizeof(Tcl_Obj **)); + memcpy(elemv+1, objv, objc*sizeof(Tcl_Obj *)); ret = TclJoinPath(elemc, elemv); ckfree(elemv); return ret; diff --git a/generic/tclFileSystem.h b/generic/tclFileSystem.h index 6be3e03..1eec7ff 100644 --- a/generic/tclFileSystem.h +++ b/generic/tclFileSystem.h @@ -33,7 +33,7 @@ MODULE_SCOPE void TclFSSetPathDetails(Tcl_Obj *pathPtr, const Tcl_Filesystem *fsPtr, ClientData clientData); MODULE_SCOPE Tcl_Obj * TclFSNormalizeAbsolutePath(Tcl_Interp *interp, Tcl_Obj *pathPtr); -MODULE_SCOPE int TclFSEpoch(void); +MODULE_SCOPE size_t TclFSEpoch(void); /* * Private shared variables for use by tclIOUtil.c and tclPathObj.c @@ -55,7 +55,7 @@ MODULE_SCOPE Tcl_PathType TclFSNonnativePathType(const char *pathPtr, MODULE_SCOPE Tcl_PathType TclGetPathType(Tcl_Obj *pathPtr, const Tcl_Filesystem **filesystemPtrPtr, int *driveNameLengthPtr, Tcl_Obj **driveNameRef); -MODULE_SCOPE int TclFSEpochOk(int filesystemEpoch); +MODULE_SCOPE int TclFSEpochOk(size_t filesystemEpoch); MODULE_SCOPE int TclFSCwdIsNative(void); MODULE_SCOPE Tcl_Obj * TclWinVolumeRelativeNormalize(Tcl_Interp *interp, const char *path, Tcl_Obj **useThisCwdPtr); diff --git a/generic/tclHash.c b/generic/tclHash.c index 90be511..1991aea 100644 --- a/generic/tclHash.c +++ b/generic/tclHash.c @@ -326,7 +326,7 @@ CreateHashEntry( continue; } #endif - if (compareKeysProc((void *) key, hPtr)) { + if (((void *) key == hPtr) || compareKeysProc((void *) key, hPtr)) { if (newPtr) { *newPtr = 0; } diff --git a/generic/tclHistory.c b/generic/tclHistory.c index b10d423..b08e352 100644 --- a/generic/tclHistory.c +++ b/generic/tclHistory.c @@ -161,7 +161,7 @@ Tcl_RecordAndEvalObj( Tcl_Obj *list[3]; /* - * Do recording by eval'ing a tcl history command: history add $cmd. + * Do recording by eval'ing a tcl history command: history add $cmd. */ list[0] = histObjsPtr->historyObj; @@ -175,7 +175,7 @@ Tcl_RecordAndEvalObj( /* * One possible failure mode above: exceeding a resource limit. */ - + if (Tcl_LimitExceeded(interp)) { return TCL_ERROR; } diff --git a/generic/tclIO.c b/generic/tclIO.c index c4757ea..8e9e346 100644 --- a/generic/tclIO.c +++ b/generic/tclIO.c @@ -421,7 +421,11 @@ ChanRead( * Each read op must set the blocked and eof states anew, not let * the effect of prior reads leak through. */ + if (GotFlag(chanPtr->state, CHANNEL_EOF)) { + chanPtr->state->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(chanPtr->state, CHANNEL_BLOCKED | CHANNEL_EOF); + chanPtr->state->inputEncodingFlags &= ~TCL_ENCODING_END; if (WillRead(chanPtr) < 0) { return -1; } @@ -430,7 +434,11 @@ ChanRead( dst, dstSize, &result); /* Stop any flag leakage through stacked channel levels */ + if (GotFlag(chanPtr->state, CHANNEL_EOF)) { + chanPtr->state->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(chanPtr->state, CHANNEL_BLOCKED | CHANNEL_EOF); + chanPtr->state->inputEncodingFlags &= ~TCL_ENCODING_END; if (bytesRead > 0) { /* * If we get a short read, signal up that we may be BLOCKED. @@ -570,11 +578,11 @@ TclFinalizeIOSubsystem(void) int active = 1; /* Flag == 1 while there's still work to do */ int doflushnb; - /* Fetch the pre-TIP#398 compatibility flag */ + /* Fetch the pre-TIP#398 compatibility flag */ { const char *s; Tcl_DString ds; - + s = TclGetEnv("TCL_FLUSH_NONBLOCKING_ON_EXIT", &ds); doflushnb = ((s != NULL) && strcmp(s, "0")); if (s != NULL) { @@ -627,9 +635,9 @@ TclFinalizeIOSubsystem(void) /* Set the channel back into blocking mode to ensure that we wait * for all data to flush out. */ - + (void) Tcl_SetChannelOption(NULL, (Tcl_Channel) chanPtr, - "-blocking", "on"); + "-blocking", "on"); } if ((chanPtr == (Channel *) tsdPtr->stdinChannel) || @@ -1014,8 +1022,7 @@ DeleteChannelTable( Tcl_DeleteHashEntry(hPtr); SetFlag(statePtr, CHANNEL_TAINTED); - statePtr->refCount--; - if (statePtr->refCount <= 0) { + if (statePtr->refCount-- <= 1) { if (!GotFlag(statePtr, BG_FLUSH_SCHEDULED)) { (void) Tcl_Close(interp, (Tcl_Channel) chanPtr); } @@ -2649,6 +2656,8 @@ FlushChannel( * the post-condition that on a successful return to caller we've * left space in the current output buffer for more writing (the flush * call was to make new room). + * If the channel is blocking, then yes, so we guarantee that + * blocking flushes actually flush all pending data. * Otherwise, no. Keep the current output buffer where it is so more * can be written to it, possibly filling it, to promote more efficient * buffer usage. @@ -2656,7 +2665,8 @@ FlushChannel( bufPtr = statePtr->curOutPtr; if (bufPtr && BytesLeft(bufPtr) && /* Keep empties off queue */ - (statePtr->outQueueHead == NULL || IsBufferFull(bufPtr))) { + (statePtr->outQueueHead == NULL || IsBufferFull(bufPtr) + || !GotFlag(statePtr, CHANNEL_NONBLOCKING))) { if (statePtr->outQueueHead == NULL) { statePtr->outQueueHead = bufPtr; } else { @@ -2833,7 +2843,7 @@ FlushChannel( /* * When we are calledFromAsyncFlush, that means a writable * state on the channel triggered the call, so we should be - * able to write something. Either we did write something + * able to write something. Either we did write something * and wroteSome should be set, or there was nothing left to * write in this call, and we've completed the BG flush. * These are the two cases above. If we get here, that means @@ -4213,7 +4223,7 @@ Write( if (nextNewLine) { srcLimit = nextNewLine - src; } - + /* Get space to write into */ bufPtr = statePtr->curOutPtr; if (bufPtr == NULL) { @@ -4241,7 +4251,7 @@ Write( /* See chan-io-1.[89]. Tcl Bug 506297. */ statePtr->outputEncodingFlags &= ~TCL_ENCODING_START; - + if ((result != TCL_OK) && (srcRead + dstWrote == 0)) { /* We're reading from invalid/incomplete UTF-8 */ ReleaseChannelBuffer(bufPtr); @@ -4281,7 +4291,7 @@ Write( Tcl_Panic("unknown output translation requested"); break; } - + result |= Tcl_UtfToExternal(NULL, encoding, nl, nlLen, statePtr->outputEncodingFlags, &statePtr->outputEncodingState, dst, @@ -4323,7 +4333,18 @@ Write( return -1; } flushed += statePtr->bufSize; - if (saved == 0 || src[-1] != '\n') { + + /* + * We just flushed. So if we have needNlFlush set to record + * that we need to flush because theres a (translated) newline + * in the buffer, that's likely not true any more. But there + * is a tricky exception. If we have saved bytes that did not + * really get flushed and those bytes came from a translation + * of a newline as the last thing taken from the src array, + * then needNlFlush needs to remain set to flag that the + * next buffer still needs a newline flush. + */ + if (needNlFlush && (saved == 0 || src[-1] != '\n')) { needNlFlush = 0; } } @@ -5700,7 +5721,7 @@ DoReadChars( int factor = UTF_EXPANSION_FACTOR; binaryMode = (encoding == NULL) - && (statePtr->inputTranslation == TCL_TRANSLATE_LF) + && (statePtr->inputTranslation == TCL_TRANSLATE_LF) && (statePtr->inEofChar == '\0'); if (appendFlag == 0) { @@ -5733,13 +5754,19 @@ DoReadChars( assert( statePtr->inputEncodingFlags & TCL_ENCODING_END ); assert( !GotFlag(statePtr, CHANNEL_BLOCKED|INPUT_SAW_CR) ); + /* TODO: We don't need this call? */ UpdateInterest(chanPtr); return 0; } /* Special handling for zero-char read request. */ if (toRead == 0) { + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_BLOCKED|CHANNEL_EOF); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; + /* TODO: We don't need this call? */ UpdateInterest(chanPtr); return 0; } @@ -5752,7 +5779,11 @@ DoReadChars( TclChannelPreserve((Tcl_Channel)chanPtr); /* Must clear the BLOCKED|EOF flags here since we check before reading */ + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_BLOCKED|CHANNEL_EOF); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; for (copied = 0; (unsigned) toRead > 0; ) { copiedNow = -1; if (statePtr->inQueueHead != NULL) { @@ -5962,7 +5993,7 @@ ReadChars( * expand when converted to UTF-8 chars. This guess comes from analyzing * how many characters were produced by the previous pass. */ - + int factor = *factorPtr; int dstLimit = TCL_UTF_MAX - 1 + toRead * factor / UTF_EXPANSION_FACTOR; @@ -5995,7 +6026,7 @@ ReadChars( while (1) { int dstDecoded, dstRead, dstWrote, srcRead, numChars, code; int flags = statePtr->inputEncodingFlags | TCL_ENCODING_NO_TERMINATE; - + if (charsToRead > 0) { flags |= TCL_ENCODING_CHAR_LIMIT; numChars = charsToRead; @@ -6004,12 +6035,24 @@ ReadChars( /* * Perform the encoding transformation. Read no more than * srcLen bytes, write no more than dstLimit bytes. + * + * Some trickiness with encoding flags here. We do not want + * the end of a buffer to be treated as the end of all input + * when the presence of bytes in a next buffer are already + * known to exist. This is checked with an assert() because + * so far no test case causing the assertion to be false has + * been created. The normal operations of channel reading + * appear to cause EOF and TCL_ENCODING_END setting to appear + * only in situations where there are no further bytes in + * any buffers. */ + assert(bufPtr->nextPtr == NULL || BytesLeft(bufPtr->nextPtr) == 0 + || (statePtr->inputEncodingFlags & TCL_ENCODING_END) == 0); + code = Tcl_ExternalToUtf(NULL, encoding, src, srcLen, - flags & (bufPtr->nextPtr ? ~0 : ~TCL_ENCODING_END), - &statePtr->inputEncodingState, dst, dstLimit, &srcRead, - &dstDecoded, &numChars); + flags, &statePtr->inputEncodingState, + dst, dstLimit, &srcRead, &dstDecoded, &numChars); /* * Perform the translation transformation in place. Read no more @@ -6118,7 +6161,7 @@ ReadChars( char buffer[TCL_UTF_MAX + 1]; int read, decoded, count; - /* + /* * Didn't get everything the buffer could offer */ @@ -6126,9 +6169,12 @@ ReadChars( statePtr->inputEncodingFlags = savedIEFlags; statePtr->inputEncodingState = savedState; + assert(bufPtr->nextPtr == NULL + || BytesLeft(bufPtr->nextPtr) == 0 || 0 == + (statePtr->inputEncodingFlags & TCL_ENCODING_END)); + Tcl_ExternalToUtf(NULL, encoding, src, srcLen, - (statePtr->inputEncodingFlags | TCL_ENCODING_NO_TERMINATE) - & (bufPtr->nextPtr ? ~0 : ~TCL_ENCODING_END), + (statePtr->inputEncodingFlags | TCL_ENCODING_NO_TERMINATE), &statePtr->inputEncodingState, buffer, TCL_UTF_MAX + 1, &read, &decoded, &count); @@ -6171,7 +6217,7 @@ ReadChars( /* FALL THROUGH - get more data (dstWrote == 0) */ } - /* + /* * The translation transformation can only reduce the number * of chars when it converts \r\n into \n. The reduction in * the number of chars is the difference in bytes read and written. @@ -6181,7 +6227,7 @@ ReadChars( if (charsToRead > 0 && numChars > charsToRead) { - /* + /* * TODO: This cannot happen anymore. * * We read more chars than allowed. Reset limits to @@ -6204,7 +6250,7 @@ ReadChars( assert (numChars == 0); - /* + /* * There is one situation where this is the correct final * result. If the src buffer contains only a single \n * byte, and we are in TCL_TRANSLATE_AUTO mode, and @@ -6297,7 +6343,7 @@ ReadChars( *--------------------------------------------------------------------------- */ -static void +static void TranslateInputEOL( ChannelState *statePtr, /* Channel being read, for EOL translation and * EOF character. */ @@ -6504,8 +6550,12 @@ Tcl_Ungets( * Clear the EOF flags, and clear the BLOCKED bit. */ + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_BLOCKED | CHANNEL_STICKY_EOF | CHANNEL_EOF | INPUT_SAW_CR); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; bufPtr = AllocChannelBuffer(len); memcpy(InsertPoint(bufPtr), str, (size_t) len); @@ -6656,7 +6706,7 @@ GetInput( ChannelState *statePtr = chanPtr->state; /* State info for channel */ - /* + /* * Verify that all callers know better than to call us when * it's recorded that the next char waiting to be read is the * eofchar. @@ -6875,8 +6925,12 @@ Tcl_Seek( * point. Also clear CR related flags. */ + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_EOF | CHANNEL_STICKY_EOF | CHANNEL_BLOCKED | INPUT_SAW_CR); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; /* * If the channel is in asynchronous output mode, switch it back to @@ -7970,7 +8024,11 @@ Tcl_SetChannelOption( * ahead'. Ditto for blocked. */ + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_EOF|CHANNEL_STICKY_EOF|CHANNEL_BLOCKED); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; return TCL_OK; } else if (HaveOpt(1, "-translation")) { const char *readMode, *writeMode; @@ -8270,6 +8328,11 @@ Tcl_NotifyChannel( */ if (chanPtr->typePtr != NULL) { + /* + * TODO: This call may not be needed. If a handler induced a + * change in interest, that handler should have made its own + * UpdateInterest() call, one would think. + */ UpdateInterest(chanPtr); } @@ -9160,7 +9223,7 @@ MBEvent( } } -static int +static int MBRead( CopyState *csPtr) { @@ -9181,7 +9244,7 @@ MBRead( } } -static int +static int MBWrite( CopyState *csPtr) { @@ -9608,7 +9671,7 @@ CopyData( * DoRead -- * * Stores up to "bytesToRead" bytes in memory pointed to by "dst". - * These bytes come from reading the channel "chanPtr" and + * These bytes come from reading the channel "chanPtr" and * performing the configured translations. No encoding conversions * are applied to the bytes being read. * @@ -9660,13 +9723,19 @@ DoRead( assert( statePtr->inputEncodingFlags & TCL_ENCODING_END ); assert( !GotFlag(statePtr, CHANNEL_BLOCKED|INPUT_SAW_CR) ); + /* TODO: Don't need this call */ UpdateInterest(chanPtr); return 0; } /* Special handling for zero-char read request. */ if (bytesToRead == 0) { + if (GotFlag(statePtr, CHANNEL_EOF)) { + statePtr->inputEncodingFlags |= TCL_ENCODING_START; + } ResetFlag(statePtr, CHANNEL_BLOCKED|CHANNEL_EOF); + statePtr->inputEncodingFlags &= ~TCL_ENCODING_END; + /* TODO: Don't need this call */ UpdateInterest(chanPtr); return 0; } @@ -9674,7 +9743,7 @@ DoRead( TclChannelPreserve((Tcl_Channel)chanPtr); while (bytesToRead) { /* - * Each pass through the loop is intended to process up to + * Each pass through the loop is intended to process up to * one channel buffer. */ @@ -9682,13 +9751,13 @@ DoRead( ChannelBuffer *bufPtr = statePtr->inQueueHead; /* - * Don't read more data if we have what we need. + * Don't read more data if we have what we need. */ while (!bufPtr || /* We got no buffer! OR */ (!IsBufferFull(bufPtr) && /* Our buffer has room AND */ (BytesLeft(bufPtr) < bytesToRead) ) ) { - /* Not enough bytes in it + /* Not enough bytes in it * yet to fill the dst */ int code; @@ -9733,7 +9802,6 @@ DoRead( */ if (bytesToRead == 0) { - UpdateInterest(chanPtr); break; } @@ -9742,7 +9810,6 @@ DoRead( */ if (GotFlag(statePtr, CHANNEL_STICKY_EOF)) { - UpdateInterest(chanPtr); break; } @@ -9767,7 +9834,6 @@ DoRead( } else if (statePtr->flags & CHANNEL_BLOCKED) { /* ...and we cannot get more now. */ SetFlag(statePtr, CHANNEL_NEED_MORE_DATA); - UpdateInterest(chanPtr); break; } else { /* ... so we need to get some. */ @@ -9819,6 +9885,7 @@ DoRead( || Tcl_InputBuffered((Tcl_Channel)chanPtr) == 0); assert( !(GotFlag(statePtr, CHANNEL_EOF|CHANNEL_BLOCKED) == (CHANNEL_EOF|CHANNEL_BLOCKED)) ); + UpdateInterest(chanPtr); TclChannelRelease((Tcl_Channel)chanPtr); return (int)(p - dst); } diff --git a/generic/tclIO.h b/generic/tclIO.h index ca74c3e..b799375 100644 --- a/generic/tclIO.h +++ b/generic/tclIO.h @@ -126,7 +126,7 @@ typedef struct Channel { */ typedef struct ChannelState { - const char *channelName; /* The name of the channel instance in Tcl + char *channelName; /* The name of the channel instance in Tcl * commands. Storage is owned by the generic * IO code, is dynamically allocated. */ int flags; /* ORed combination of the flags defined diff --git a/generic/tclIOGT.c b/generic/tclIOGT.c index 58d1a22..7f61def 100644 --- a/generic/tclIOGT.c +++ b/generic/tclIOGT.c @@ -683,7 +683,7 @@ TransformInputProc( * Already saw EOF from downChan; don't ask again. * NOTE: Could move this up to avoid the last maxRead * execution. Believe this would still be correct behavior, - * but the test suite tests the whole command callback + * but the test suite tests the whole command callback * sequence, so leave it unchanged for now. */ diff --git a/generic/tclIORTrans.c b/generic/tclIORTrans.c index 8baa9ad..af86ba5 100644 --- a/generic/tclIORTrans.c +++ b/generic/tclIORTrans.c @@ -943,7 +943,7 @@ ReflectClose( Tcl_EventuallyFree(rtPtr, (Tcl_FreeProc *) FreeReflectedTransform); return errorCode; - } + } #endif /* TCL_THREADS */ errorCodeSet = 1; goto cleanup; @@ -957,7 +957,7 @@ ReflectClose( Tcl_EventuallyFree(rtPtr, (Tcl_FreeProc *) FreeReflectedTransform); return errorCode; - } + } #endif /* TCL_THREADS */ errorCodeSet = 1; goto cleanup; @@ -1177,7 +1177,7 @@ ReflectInput( */ rtPtr->eofPending = 1; - + /* * Now this is a bit different. The partial data waiting is * converted and returned. diff --git a/generic/tclIOSock.c b/generic/tclIOSock.c index f69d30f..d578d19 100644 --- a/generic/tclIOSock.c +++ b/generic/tclIOSock.c @@ -23,7 +23,7 @@ static Tcl_ThreadDataKey dataKey; #undef gai_strerror static const char *gai_strerror(int code) { ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey); - + if (tsdPtr->initialized) { Tcl_DStringFree(&tsdPtr->errorMsg); } else { @@ -187,11 +187,11 @@ TclCreateSocketAddress( TclFormatInt(portbuf, port); portstring = portbuf; } - + (void) memset(&hints, 0, sizeof(hints)); hints.ai_family = AF_UNSPEC; - /* + /* * Magic variable to enforce a certain address family - to be superseded * by a TIP that adds explicit switches to [socket] */ @@ -228,7 +228,7 @@ TclCreateSocketAddress( if (willBind) { hints.ai_flags |= AI_PASSIVE; - } + } result = getaddrinfo(native, portstring, &hints, addrlist); @@ -283,7 +283,7 @@ TclCreateSocketAddress( for (p = *addrlist; p != NULL; p = p->ai_next) { i++; } - + return 1; } diff --git a/generic/tclIOUtil.c b/generic/tclIOUtil.c index d2919fc..1330c02 100644 --- a/generic/tclIOUtil.c +++ b/generic/tclIOUtil.c @@ -59,12 +59,12 @@ typedef struct FilesystemRecord { typedef struct ThreadSpecificData { int initialized; - int cwdPathEpoch; - int filesystemEpoch; + size_t cwdPathEpoch; + size_t filesystemEpoch; Tcl_Obj *cwdPathPtr; ClientData cwdClientData; FilesystemRecord *filesystemList; - int claims; + size_t claims; } ThreadSpecificData; /* @@ -215,7 +215,7 @@ static FilesystemRecord nativeFilesystemRecord = { * trigger cache cleanup in all threads. */ -static int theFilesystemEpoch = 1; +static size_t theFilesystemEpoch = 1; /* * Stores the linked list of filesystems. A 1:1 copy of this list is also @@ -231,7 +231,7 @@ TCL_DECLARE_MUTEX(filesystemMutex) */ static Tcl_Obj *cwdPathPtr = NULL; -static int cwdPathEpoch = 0; +static size_t cwdPathEpoch = 0; static ClientData cwdClientData = NULL; TCL_DECLARE_MUTEX(cwdMutex) @@ -645,7 +645,7 @@ FsGetFirstFilesystem(void) int TclFSEpochOk( - int filesystemEpoch) + size_t filesystemEpoch) { return (filesystemEpoch == 0 || filesystemEpoch == theFilesystemEpoch); } @@ -666,7 +666,7 @@ Disclaim(void) tsdPtr->claims--; } -int +size_t TclFSEpoch(void) { ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&fsDataKey); @@ -713,7 +713,9 @@ FsUpdateCwd( cwdClientData = TclNativeDupInternalRep(clientData); } - cwdPathEpoch++; + if (++cwdPathEpoch == 0) { + ++cwdPathEpoch; + } tsdPtr->cwdPathEpoch = cwdPathEpoch; Tcl_MutexUnlock(&cwdMutex); @@ -790,7 +792,9 @@ TclFinalizeFilesystem(void) } fsRecPtr = tmpFsRecPtr; } - theFilesystemEpoch++; + if (++theFilesystemEpoch == 0) { + ++theFilesystemEpoch; + } filesystemList = NULL; /* @@ -823,7 +827,9 @@ void TclResetFilesystem(void) { filesystemList = &nativeFilesystemRecord; - theFilesystemEpoch++; + if (++theFilesystemEpoch == 0) { + ++theFilesystemEpoch; + } #ifdef _WIN32 /* @@ -908,7 +914,9 @@ Tcl_FSRegister( * conceivably now belong to different filesystems. */ - theFilesystemEpoch++; + if (++theFilesystemEpoch == 0) { + ++theFilesystemEpoch; + } Tcl_MutexUnlock(&filesystemMutex); return TCL_OK; @@ -973,7 +981,9 @@ Tcl_FSUnregister( * (which would of course lead to memory exceptions). */ - theFilesystemEpoch++; + if (++theFilesystemEpoch == 0) { + ++theFilesystemEpoch; + } ckfree(fsRecPtr); @@ -1304,7 +1314,9 @@ Tcl_FSMountsChanged( */ Tcl_MutexLock(&filesystemMutex); - theFilesystemEpoch++; + if (++theFilesystemEpoch == 0) { + ++theFilesystemEpoch; + } Tcl_MutexUnlock(&filesystemMutex); } @@ -2890,9 +2902,13 @@ int Tcl_FSChdir( Tcl_Obj *pathPtr) { - const Tcl_Filesystem *fsPtr; + const Tcl_Filesystem *fsPtr, *oldFsPtr = NULL; + ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&fsDataKey); int retVal = -1; + if (tsdPtr->cwdPathPtr != NULL) { + oldFsPtr = Tcl_FSGetFileSystemForPath(tsdPtr->cwdPathPtr); + } if (Tcl_FSGetNormalizedPath(NULL, pathPtr) == NULL) { Tcl_SetErrno(ENOENT); return retVal; @@ -2992,7 +3008,6 @@ Tcl_FSChdir( * instead. This should be examined by someone on Unix. */ - ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&fsDataKey); ClientData cd; ClientData oldcd = tsdPtr->cwdClientData; @@ -3009,6 +3024,14 @@ Tcl_FSChdir( } else { FsUpdateCwd(normDirName, NULL); } + + /* + * If the filesystem changed between old and new cwd + * force filesystem refresh on path objects. + */ + if (oldFsPtr != NULL && fsPtr != oldFsPtr) { + Tcl_FSMountsChanged(NULL); + } } return retVal; @@ -3150,7 +3173,7 @@ TclSkipUnlink (Tcl_Obj* shlibFile) * * Ad 2: This variable can disable/override the AUFS detection, i.e. for * testing if a newer AUFS does not have the bug any more. - * + * * Ad 3: This is conditionally compiled in. Condition currently must be set manually. * This part needs proper tests in the configure(.in). */ @@ -3231,7 +3254,9 @@ Tcl_LoadFile( if (*handlePtr == NULL) { return TCL_ERROR; } - Tcl_ResetResult(interp); + if (interp) { + Tcl_ResetResult(interp); + } goto resolveSymbols; } if (Tcl_GetErrno() != EXDEV) { @@ -3247,9 +3272,11 @@ Tcl_LoadFile( */ if (Tcl_FSAccess(pathPtr, R_OK) != 0) { - Tcl_SetObjResult(interp, Tcl_ObjPrintf( - "couldn't load library \"%s\": %s", - Tcl_GetString(pathPtr), Tcl_PosixError(interp))); + if (interp) { + Tcl_SetObjResult(interp, Tcl_ObjPrintf( + "couldn't load library \"%s\": %s", + Tcl_GetString(pathPtr), Tcl_PosixError(interp))); + } return TCL_ERROR; } @@ -3298,7 +3325,9 @@ Tcl_LoadFile( } mustCopyToTempAnyway: - Tcl_ResetResult(interp); + if (interp) { + Tcl_ResetResult(interp); + } #endif /* TCL_LOAD_FROM_MEMORY */ /* @@ -3322,8 +3351,10 @@ Tcl_LoadFile( Tcl_FSDeleteFile(copyToPtr); Tcl_DecrRefCount(copyToPtr); - Tcl_SetObjResult(interp, Tcl_NewStringObj( - "couldn't load from current filesystem", -1)); + if (interp) { + Tcl_SetObjResult(interp, Tcl_NewStringObj( + "couldn't load from current filesystem", -1)); + } return TCL_ERROR; } @@ -3363,7 +3394,9 @@ Tcl_LoadFile( * have stored the number of bytes in the result. */ - Tcl_ResetResult(interp); + if (interp) { + Tcl_ResetResult(interp); + } retVal = Tcl_LoadFile(interp, copyToPtr, symbols, flags, procPtrs, &newLoadHandle); @@ -3395,7 +3428,9 @@ Tcl_LoadFile( */ *handlePtr = newLoadHandle; - Tcl_ResetResult(interp); + if (interp) { + Tcl_ResetResult(interp); + } return TCL_OK; } @@ -3456,11 +3491,13 @@ Tcl_LoadFile( divertedLoadHandle->unloadFileProcPtr = DivertUnloadFile; *handlePtr = divertedLoadHandle; - Tcl_ResetResult(interp); + if (interp) { + Tcl_ResetResult(interp); + } return retVal; resolveSymbols: - /* + /* * At this point, *handlePtr is already set up to the handle for the * loaded library. We now try to resolve the symbols. */ @@ -3469,7 +3506,7 @@ Tcl_LoadFile( for (i=0 ; symbols[i] != NULL; i++) { procPtrs[i] = Tcl_FindSymbol(interp, *handlePtr, symbols[i]); if (procPtrs[i] == NULL) { - /* + /* * At least one symbol in the list was not found. Unload the * file, and report the problem back to the caller. * (Tcl_FindSymbol should already have left an appropriate @@ -3489,7 +3526,7 @@ Tcl_LoadFile( *---------------------------------------------------------------------- * * DivertFindSymbol -- - * + * * Find a symbol in a shared library loaded by copy-from-VFS. * *---------------------------------------------------------------------- diff --git a/generic/tclInt.h b/generic/tclInt.h index 3f84717..356d250 100644 --- a/generic/tclInt.h +++ b/generic/tclInt.h @@ -1177,25 +1177,25 @@ typedef struct CmdFrame { * * Field TEBC EvalEx * ======= ==== ====== - * level yes yes + * level yes yes * type BC/PREBC SRC/EVAL - * line0 yes yes - * framePtr yes yes + * line0 yes yes + * framePtr yes yes * ======= ==== ====== * * ======= ==== ========= union data - * line1 - yes - * line3 - yes - * path - yes + * line1 - yes + * line3 - yes + * path - yes * ------- ---- ------ - * codePtr yes - - * pc yes - + * codePtr yes - + * pc yes - * ======= ==== ====== * * ======= ==== ========= union cmd - * str.cmd yes yes - * str.len yes yes - * ------- ---- ------ + * str.cmd yes yes + * str.len yes yes + * ------- ---- ------ */ union { @@ -3230,15 +3230,15 @@ MODULE_SCOPE Tcl_Obj * TclDictWithInit(Tcl_Interp *interp, Tcl_Obj *dictPtr, MODULE_SCOPE int Tcl_DisassembleObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]); - -/* Assemble command function */ + +/* Assemble command function */ MODULE_SCOPE int Tcl_AssembleObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, - Tcl_Obj *const objv[]); + Tcl_Obj *const objv[]); MODULE_SCOPE int TclNRAssembleObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, - Tcl_Obj *const objv[]); - + Tcl_Obj *const objv[]); + MODULE_SCOPE int Tcl_EncodingObjCmd(ClientData clientData, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]); @@ -3909,7 +3909,7 @@ MODULE_SCOPE int TclStreqOpCmd(ClientData clientData, MODULE_SCOPE int TclCompileStreqOpCmd(Tcl_Interp *interp, Tcl_Parse *parsePtr, Command *cmdPtr, struct CompileEnv *envPtr); - + MODULE_SCOPE int TclCompileAssembleCmd(Tcl_Interp *interp, Tcl_Parse *parsePtr, Command *cmdPtr, struct CompileEnv *envPtr); @@ -4039,7 +4039,7 @@ typedef const char *TclDTraceStr; */ # define TclDecrRefCount(objPtr) \ - if (--(objPtr)->refCount > 0) ; else { \ + if ((objPtr)->refCount-- > 1) ; else { \ if (!(objPtr)->typePtr || !(objPtr)->typePtr->freeIntRepProc) { \ TCL_DTRACE_OBJ_FREE(objPtr); \ if ((objPtr)->bytes \ @@ -4116,7 +4116,8 @@ MODULE_SCOPE void TclpFreeAllocCache(void *); AllocCache *cachePtr; \ if (((interp) == NULL) || \ ((cachePtr = ((Interp *)(interp))->allocCache), \ - (cachePtr->numObjects >= ALLOC_NOBJHIGH))) { \ + ((cachePtr->numObjects == 0) || \ + (cachePtr->numObjects >= ALLOC_NOBJHIGH)))) { \ TclThreadFreeObj(objPtr); \ } else { \ (objPtr)->internalRep.twoPtrValue.ptr1 = cachePtr->firstObjPtr; \ @@ -4678,7 +4679,7 @@ MODULE_SCOPE Tcl_PackageInitProc Procbodytest_SafeInit; */ #define TclCleanupCommandMacro(cmdPtr) \ - if (--(cmdPtr)->refCount <= 0) { \ + if ((cmdPtr)->refCount-- <= 1) { \ ckfree((char *) (cmdPtr));\ } diff --git a/generic/tclListObj.c b/generic/tclListObj.c index bd2dbc4..fa67ee6 100644 --- a/generic/tclListObj.c +++ b/generic/tclListObj.c @@ -137,7 +137,7 @@ NewListIntRep( * Creates a list internal rep with space for objc elements. objc * must be > 0. If objv!=NULL, initializes with the first objc values * in that array. If objv==NULL, initalize list internal rep to have - * 0 elements, with space to add objc more. + * 0 elements, with space to add objc more. * * Results: * A new List struct with refCount 0 is returned. If some failure @@ -1726,7 +1726,7 @@ FreeListInternalRep( { List *listRepPtr = ListRepPtr(listPtr); - if (--listRepPtr->refCount <= 0) { + if (listRepPtr->refCount-- <= 1) { Tcl_Obj **elemPtrs = &listRepPtr->elements; int i, numElems = listRepPtr->elemCount; diff --git a/generic/tclLiteral.c b/generic/tclLiteral.c index 2b0cc7e..03200ca 100644 --- a/generic/tclLiteral.c +++ b/generic/tclLiteral.c @@ -426,7 +426,7 @@ TclRegisterLiteral( } else { nsPtr = NULL; } - + /* * Is it in the interpreter's global literal table? If not, create it. */ @@ -717,16 +717,22 @@ ExpandLocalLiteralArray( LiteralEntry *currArrayPtr = envPtr->literalArrayPtr; LiteralEntry *newArrayPtr; int i; + unsigned int newSize = (currBytes <= UINT_MAX / 2) ? 2*currBytes : UINT_MAX; + + if (currBytes == newSize) { + Tcl_Panic("max size of Tcl literal array (%d literals) exceeded", + currElems); + } if (envPtr->mallocedLiteralArray) { - newArrayPtr = ckrealloc(currArrayPtr, 2 * currBytes); + newArrayPtr = ckrealloc(currArrayPtr, newSize); } else { /* * envPtr->literalArrayPtr isn't a ckalloc'd pointer, so we must * code a ckrealloc equivalent for ourselves. */ - newArrayPtr = ckalloc(2 * currBytes); + newArrayPtr = ckalloc(newSize); memcpy(newArrayPtr, currArrayPtr, currBytes); envPtr->mallocedLiteralArray = 1; } @@ -751,7 +757,7 @@ ExpandLocalLiteralArray( } envPtr->literalArrayPtr = newArrayPtr; - envPtr->literalArrayEnd = (2 * currElems); + envPtr->literalArrayEnd = newSize / sizeof(LiteralEntry); } /* @@ -932,7 +938,8 @@ RebuildLiteralTable( register LiteralEntry *entryPtr; LiteralEntry **bucketPtr; const char *bytes; - int oldSize, count, index, length; + unsigned int oldSize; + int count, index, length; oldSize = tablePtr->numBuckets; oldBuckets = tablePtr->buckets; @@ -942,6 +949,16 @@ RebuildLiteralTable( * constants for new array size. */ + if (oldSize > UINT_MAX/(4 * sizeof(LiteralEntry *))) { + /* + * Memory allocator limitations will not let us create the + * next larger table size. Best option is to limp along + * with what we have. + */ + + return; + } + tablePtr->numBuckets *= 4; tablePtr->buckets = ckalloc(tablePtr->numBuckets * sizeof(LiteralEntry*)); for (count=tablePtr->numBuckets, newChainPtr=tablePtr->buckets; @@ -991,7 +1008,7 @@ RebuildLiteralTable( * Results: * None. * - * Side effects: + * Side effects: * Resets the internal representation of the CmdName Tcl_Obj * using TclFreeIntRep(). * diff --git a/generic/tclLoadNone.c b/generic/tclLoadNone.c index 6cb4378..6af5c4f 100644 --- a/generic/tclLoadNone.c +++ b/generic/tclLoadNone.c @@ -45,9 +45,11 @@ TclpDlopen( * file. */ int flags) { - Tcl_SetObjResult(interp, Tcl_NewStringObj( - "dynamic loading is not currently available on this system", - -1)); + if (interp) { + Tcl_SetObjResult(interp, Tcl_NewStringObj( + "dynamic loading is not currently available on this system", + -1)); + } return TCL_ERROR; } @@ -109,8 +111,10 @@ TclpLoadMemory( int flags) /* Dummy: unused by this implementation */ { - Tcl_SetObjResult(interp, Tcl_NewStringObj("dynamic loading from memory " - "is not available on this system", -1)); + if (interp) { + Tcl_SetObjResult(interp, Tcl_NewStringObj("dynamic loading from memory " + "is not available on this system", -1)); + } return TCL_ERROR; } diff --git a/generic/tclMain.c b/generic/tclMain.c index 360f5e9..927de7e 100644 --- a/generic/tclMain.c +++ b/generic/tclMain.c @@ -80,7 +80,10 @@ NewNativeObj( * source directory to make their own modified versions). */ +#if defined _MSC_VER && _MSC_VER < 1900 +/* isatty is always defined on MSVC 14.0, but not necessarily as CRTIMPORT. */ extern CRTIMPORT int isatty(int fd); +#endif /* * The thread-local variables for this file's functions. @@ -616,7 +619,7 @@ Tcl_MainEx( if (!Tcl_InterpDeleted(interp) && !Tcl_LimitExceeded(interp)) { Tcl_Obj *cmd = Tcl_ObjPrintf("exit %d", exitCode); - + Tcl_IncrRefCount(cmd); Tcl_EvalObjEx(interp, cmd, TCL_EVAL_GLOBAL); Tcl_DecrRefCount(cmd); @@ -729,7 +732,7 @@ TclFullFinalizationRequested(void) const char *fin; Tcl_DString ds; int finalize = 0; - + fin = TclGetEnv("TCL_FINALIZE_ON_EXIT", &ds); finalize = ((fin != NULL) && strcmp(fin, "0")); if (fin != NULL) { diff --git a/generic/tclNamesp.c b/generic/tclNamesp.c index 8f2f10e..dfab185 100644 --- a/generic/tclNamesp.c +++ b/generic/tclNamesp.c @@ -343,7 +343,7 @@ Tcl_PushCallFrame( framePtr->clientData = NULL; framePtr->localCachePtr = NULL; framePtr->tailcallPtr = NULL; - + /* * Push the new call frame onto the interpreter's stack of procedure call * frames making it the current frame. @@ -3056,7 +3056,7 @@ NamespaceCodeCmd( */ arg = TclGetStringFromObj(objv[1], &length); - if (*arg==':' && length > 20 + if (*arg==':' && length > 20 && strncmp(arg, "::namespace inscope ", 20) == 0) { Tcl_SetObjResult(interp, objv[1]); return TCL_OK; @@ -3309,11 +3309,8 @@ NRNamespaceEvalCmd( /* This is needed to satisfy GCC 3.3's strict aliasing rules */ framePtrPtr = &framePtr; - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, namespacePtr, /*isProcCallFrame*/ 0); - if (result != TCL_OK) { - return TCL_ERROR; - } if (iPtr->ensembleRewrite.sourceObjs == NULL) { framePtr->objc = objc; @@ -3730,7 +3727,7 @@ NRNamespaceInscopeCmd( Tcl_Namespace *namespacePtr; CallFrame *framePtr, **framePtrPtr; register Interp *iPtr = (Interp *) interp; - int i, result; + int i; Tcl_Obj *cmdObjPtr; if (objc < 3) { @@ -3752,11 +3749,8 @@ NRNamespaceInscopeCmd( framePtrPtr = &framePtr; /* This is needed to satisfy GCC's * strict aliasing rules. */ - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, namespacePtr, /*isProcCallFrame*/ 0); - if (result != TCL_OK) { - return result; - } if (iPtr->ensembleRewrite.sourceObjs == NULL) { framePtr->objc = objc; @@ -4929,7 +4923,7 @@ TclLogCommandInfo( if (Tcl_IsShared(iPtr->errorStack)) { Tcl_Obj *newObj; - + newObj = Tcl_DuplicateObj(iPtr->errorStack); Tcl_DecrRefCount(iPtr->errorStack); Tcl_IncrRefCount(newObj); @@ -4961,7 +4955,7 @@ TclLogCommandInfo( Tcl_ListObjAppendElement(NULL, iPtr->errorStack, Tcl_NewStringObj(command, length)); } - } + } if (!iPtr->framePtr->objc) { /* @@ -5014,7 +5008,7 @@ TclErrorStackResetIf( if (Tcl_IsShared(iPtr->errorStack)) { Tcl_Obj *newObj; - + newObj = Tcl_DuplicateObj(iPtr->errorStack); Tcl_DecrRefCount(iPtr->errorStack); Tcl_IncrRefCount(newObj); @@ -5034,7 +5028,7 @@ TclErrorStackResetIf( Tcl_ListObjAppendElement(NULL, iPtr->errorStack, iPtr->innerLiteral); Tcl_ListObjAppendElement(NULL, iPtr->errorStack, Tcl_NewStringObj(msg, length)); - } + } } /* diff --git a/generic/tclOO.c b/generic/tclOO.c index 77e668b..84bb85a 100644 --- a/generic/tclOO.c +++ b/generic/tclOO.c @@ -793,7 +793,7 @@ ObjectRenamedTrace( ClientData clientData, /* The object being deleted. */ Tcl_Interp *interp, /* The interpreter containing the object. */ const char *oldName, /* What the object was (last) called. */ - const char *newName, /* Always NULL. */ + const char *newName, /* What it's getting renamed to. (unused) */ int flags) /* Why was the object deleted? */ { Object *oPtr = clientData; @@ -1675,10 +1675,13 @@ Tcl_NewObjectInstance( /* * Take care to not delete a deleted object; that would be - * bad. [Bug 2903011] + * bad. [Bug 2903011] Also take care to make sure that we have + * the name of the command before we delete it. [Bug + * 9dd1bd7a74] */ if (!Deleted(oPtr)) { + (void) TclOOObjectName(interp, oPtr); Tcl_DeleteCommandFromToken(interp, oPtr->command); } return NULL; @@ -1821,10 +1824,12 @@ FinalizeAlloc( /* * Take care to not delete a deleted object; that would be bad. [Bug - * 2903011] + * 2903011] Also take care to make sure that we have the name of the + * command before we delete it. [Bug 9dd1bd7a74] */ if (!Deleted(oPtr)) { + (void) TclOOObjectName(interp, oPtr); Tcl_DeleteCommandFromToken(interp, oPtr->command); } DelRef(oPtr); diff --git a/generic/tclOOBasic.c b/generic/tclOOBasic.c index 0b0516b..8cb80e5 100644 --- a/generic/tclOOBasic.c +++ b/generic/tclOOBasic.c @@ -402,7 +402,6 @@ TclOO_Object_Eval( register const int skip = Tcl_ObjectContextSkippedArgs(context); CallFrame *framePtr, **framePtrPtr = &framePtr; Tcl_Obj *scriptPtr; - int result; CmdFrame *invoker; if (objc-1 < skip) { @@ -415,11 +414,8 @@ TclOO_Object_Eval( * command(s). */ - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, Tcl_GetObjectNamespace(object), 0); - if (result != TCL_OK) { - return TCL_ERROR; - } framePtr->objc = objc; framePtr->objv = objv; /* Reference counts do not need to be * incremented here. */ diff --git a/generic/tclOOCall.c b/generic/tclOOCall.c index 2a81091..facf90d 100644 --- a/generic/tclOOCall.c +++ b/generic/tclOOCall.c @@ -156,7 +156,7 @@ void TclOODeleteChain( CallChain *callPtr) { - if (callPtr == NULL || --callPtr->refCount >= 1) { + if (callPtr == NULL || callPtr->refCount-- > 1) { return; } if (callPtr->chain != callPtr->staticChain) { diff --git a/generic/tclOODefineCmds.c b/generic/tclOODefineCmds.c index 5a6c0ad..c3184be 100644 --- a/generic/tclOODefineCmds.c +++ b/generic/tclOODefineCmds.c @@ -646,7 +646,6 @@ InitDefineContext( Tcl_Obj *const objv[]) { CallFrame *framePtr, **framePtrPtr = &framePtr; - int result; if (namespacePtr == NULL) { Tcl_SetObjResult(interp, Tcl_NewStringObj( @@ -658,11 +657,8 @@ InitDefineContext( /* framePtrPtr is needed to satisfy GCC 3.3's strict aliasing rules */ - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, namespacePtr, FRAME_IS_OO_DEFINE); - if (result != TCL_OK) { - return TCL_ERROR; - } framePtr->clientData = oPtr; framePtr->objc = objc; framePtr->objv = objv; /* Reference counts do not need to be diff --git a/generic/tclOOInfo.c b/generic/tclOOInfo.c index 3217f98..0c22bcf 100644 --- a/generic/tclOOInfo.c +++ b/generic/tclOOInfo.c @@ -401,7 +401,7 @@ InfoObjectIsACmd( IsClass, IsMetaclass, IsMixin, IsObject, IsType }; Object *oPtr, *o2Ptr; - int idx, i; + int idx, i, result = 0; if (objc < 3) { Tcl_WrongNumArgs(interp, 1, objv, "category objName ?arg ...?"); @@ -412,93 +412,85 @@ InfoObjectIsACmd( return TCL_ERROR; } - if (idx == IsObject) { - int ok = (Tcl_GetObjectFromObj(interp, objv[2]) != NULL); - - if (!ok) { - Tcl_ResetResult(interp); - } - Tcl_SetObjResult(interp, Tcl_NewIntObj(ok ? 1 : 0)); - return TCL_OK; - } - oPtr = (Object *) Tcl_GetObjectFromObj(interp, objv[2]); - if (oPtr == NULL) { - return TCL_ERROR; - } + /* + * Now we know what test we are doing, we can check we've got the right + * number of arguments. + */ switch ((enum IsACats) idx) { + case IsObject: case IsClass: - if (objc != 3) { - Tcl_WrongNumArgs(interp, 2, objv, "objName"); - return TCL_ERROR; - } - Tcl_SetObjResult(interp, Tcl_NewIntObj(oPtr->classPtr ? 1 : 0)); - return TCL_OK; case IsMetaclass: if (objc != 3) { Tcl_WrongNumArgs(interp, 2, objv, "objName"); return TCL_ERROR; } - if (oPtr->classPtr == NULL) { - Tcl_SetObjResult(interp, Tcl_NewIntObj(0)); - } else { - Class *classCls = TclOOGetFoundation(interp)->classCls; - - Tcl_SetObjResult(interp, Tcl_NewIntObj( - TclOOIsReachable(classCls, oPtr->classPtr) ? 1 : 0)); - } - return TCL_OK; + break; case IsMixin: + case IsType: if (objc != 4) { Tcl_WrongNumArgs(interp, 2, objv, "objName className"); return TCL_ERROR; } + break; + } + + /* + * Perform the check. Note that we can guarantee that we will not fail + * from here on; "failures" result in a false-TCL_OK result. + */ + + oPtr = (Object *) Tcl_GetObjectFromObj(interp, objv[2]); + if (oPtr == NULL) { + goto failPrecondition; + } + + switch ((enum IsACats) idx) { + case IsObject: + result = 1; + break; + case IsClass: + result = (oPtr->classPtr != NULL); + break; + case IsMetaclass: + if (oPtr->classPtr != NULL) { + result = TclOOIsReachable(TclOOGetFoundation(interp)->classCls, + oPtr->classPtr); + } + break; + case IsMixin: o2Ptr = (Object *) Tcl_GetObjectFromObj(interp, objv[3]); if (o2Ptr == NULL) { - return TCL_ERROR; + goto failPrecondition; } - if (o2Ptr->classPtr == NULL) { - Tcl_SetObjResult(interp, Tcl_NewStringObj( - "non-classes cannot be mixins", -1)); - Tcl_SetErrorCode(interp, "TCL", "OO", "NONCLASS", NULL); - return TCL_ERROR; - } else { + if (o2Ptr->classPtr != NULL) { Class *mixinPtr; FOREACH(mixinPtr, oPtr->mixins) { - if (mixinPtr == o2Ptr->classPtr) { - Tcl_SetObjResult(interp, Tcl_NewIntObj(1)); - return TCL_OK; + if (TclOOIsReachable(o2Ptr->classPtr, mixinPtr)) { + result = 1; + break; } } } - Tcl_SetObjResult(interp, Tcl_NewIntObj(0)); - return TCL_OK; + break; case IsType: - if (objc != 4) { - Tcl_WrongNumArgs(interp, 2, objv, "objName className"); - return TCL_ERROR; - } o2Ptr = (Object *) Tcl_GetObjectFromObj(interp, objv[3]); if (o2Ptr == NULL) { - return TCL_ERROR; - } - if (o2Ptr->classPtr == NULL) { - Tcl_SetObjResult(interp, Tcl_NewStringObj( - "non-classes cannot be types", -1)); - Tcl_SetErrorCode(interp, "TCL", "OO", "NONCLASS", NULL); - return TCL_ERROR; + goto failPrecondition; } - if (TclOOIsReachable(o2Ptr->classPtr, oPtr->selfCls)) { - Tcl_SetObjResult(interp, Tcl_NewIntObj(1)); - } else { - Tcl_SetObjResult(interp, Tcl_NewIntObj(0)); + if (o2Ptr->classPtr != NULL) { + result = TclOOIsReachable(o2Ptr->classPtr, oPtr->selfCls); } - return TCL_OK; - case IsObject: - Tcl_Panic("unexpected fallthrough"); + break; } - return TCL_ERROR; + Tcl_SetObjResult(interp, Tcl_NewBooleanObj(result)); + return TCL_OK; + + failPrecondition: + Tcl_ResetResult(interp); + Tcl_SetObjResult(interp, Tcl_NewBooleanObj(0)); + return TCL_OK; } /* diff --git a/generic/tclOOInt.h b/generic/tclOOInt.h index c0e4022..208e32c 100644 --- a/generic/tclOOInt.h +++ b/generic/tclOOInt.h @@ -588,7 +588,7 @@ MODULE_SCOPE void TclOOSetupVariableResolver(Tcl_Namespace *nsPtr); #define AddRef(ptr) ((ptr)->refCount++) #define DelRef(ptr) do { \ - if (--(ptr)->refCount < 1) { \ + if ((ptr)->refCount-- <= 1) { \ ckfree((char *) (ptr)); \ } \ } while(0) diff --git a/generic/tclOOMethod.c b/generic/tclOOMethod.c index 61215de..34fa108 100644 --- a/generic/tclOOMethod.c +++ b/generic/tclOOMethod.c @@ -272,7 +272,7 @@ void TclOODelMethodRef( Method *mPtr) { - if ((mPtr != NULL) && (--mPtr->refCount <= 0)) { + if ((mPtr != NULL) && (mPtr->refCount-- <= 1)) { if (mPtr->typePtr != NULL && mPtr->typePtr->deleteProc != NULL) { mPtr->typePtr->deleteProc(mPtr->clientData); } @@ -720,7 +720,7 @@ InvokeProcedureMethod( Tcl_PopCallFrame(interp); TclStackFree(interp, fdPtr->framePtr); - if (--pmPtr->refCount < 1) { + if (pmPtr->refCount-- <= 1) { DeleteProcedureMethodRecord(pmPtr); } TclStackFree(interp, fdPtr); @@ -771,7 +771,7 @@ FinalizePMCall( * sensitive when it comes to performance! */ - if (--pmPtr->refCount < 1) { + if (pmPtr->refCount-- <= 1) { DeleteProcedureMethodRecord(pmPtr); } TclStackFree(interp, fdPtr); @@ -875,11 +875,8 @@ PushMethodCallFrame( * This operation may fail. */ - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, (Tcl_Namespace *) nsPtr, FRAME_IS_PROC|FRAME_IS_METHOD); - if (result != TCL_OK) { - goto failureReturn; - } fdPtr->framePtr->clientData = contextPtr; fdPtr->framePtr->objc = objc; @@ -961,7 +958,7 @@ ProcedureMethodVarResolver( { int result; Tcl_ResolvedVarInfo *rPtr = NULL; - + result = ProcedureMethodCompiledVarResolver(interp, varName, strlen(varName), contextNs, &rPtr); @@ -1278,7 +1275,7 @@ DeleteProcedureMethod( { register ProcedureMethod *pmPtr = clientData; - if (--pmPtr->refCount < 1) { + if (pmPtr->refCount-- <= 1) { DeleteProcedureMethodRecord(pmPtr); } } @@ -1351,7 +1348,7 @@ CloneProcedureMethod( /* * ---------------------------------------------------------------------- * - * TclOONewForwardMethod -- + * TclOONewForwardInstanceMethod -- * * Create a forwarded method for an object. * @@ -1369,7 +1366,6 @@ TclOONewForwardInstanceMethod( { int prefixLen; register ForwardMethod *fmPtr; - Tcl_Obj *cmdObj; if (Tcl_ListObjLength(interp, prefixObj, &prefixLen) != TCL_OK) { return NULL; @@ -1383,7 +1379,6 @@ TclOONewForwardInstanceMethod( fmPtr = ckalloc(sizeof(ForwardMethod)); fmPtr->prefixObj = prefixObj; - Tcl_ListObjIndex(interp, prefixObj, 0, &cmdObj); Tcl_IncrRefCount(prefixObj); return (Method *) Tcl_NewInstanceMethod(interp, (Tcl_Object) oPtr, nameObj, flags, &fwdMethodType, fmPtr); @@ -1410,7 +1405,6 @@ TclOONewForwardMethod( { int prefixLen; register ForwardMethod *fmPtr; - Tcl_Obj *cmdObj; if (Tcl_ListObjLength(interp, prefixObj, &prefixLen) != TCL_OK) { return NULL; @@ -1424,7 +1418,6 @@ TclOONewForwardMethod( fmPtr = ckalloc(sizeof(ForwardMethod)); fmPtr->prefixObj = prefixObj; - Tcl_ListObjIndex(interp, prefixObj, 0, &cmdObj); Tcl_IncrRefCount(prefixObj); return (Method *) Tcl_NewMethod(interp, (Tcl_Class) clsPtr, nameObj, flags, &fwdMethodType, fmPtr); @@ -1477,7 +1470,7 @@ FinalizeForwardCall( int result) { Tcl_Obj **argObjs = data[0]; - + TclStackFree(interp, argObjs); return result; } diff --git a/generic/tclObj.c b/generic/tclObj.c index 930e1fd..c641152 100644 --- a/generic/tclObj.c +++ b/generic/tclObj.c @@ -180,26 +180,26 @@ static Tcl_ThreadDataKey pendingObjDataKey; if ((bignum).used > 0x7fff) { \ mp_int *temp = (void *) ckalloc((unsigned) sizeof(mp_int)); \ *temp = bignum; \ - (objPtr)->internalRep.ptrAndLongRep.ptr = temp; \ - (objPtr)->internalRep.ptrAndLongRep.value = (unsigned long)(-1); \ + (objPtr)->internalRep.twoPtrValue.ptr1 = temp; \ + (objPtr)->internalRep.twoPtrValue.ptr2 = INT2PTR(-1); \ } else { \ if ((bignum).alloc > 0x7fff) { \ mp_shrink(&(bignum)); \ } \ - (objPtr)->internalRep.ptrAndLongRep.ptr = (void *) (bignum).dp; \ - (objPtr)->internalRep.ptrAndLongRep.value = ( ((bignum).sign << 30) \ + (objPtr)->internalRep.twoPtrValue.ptr1 = (void *) (bignum).dp; \ + (objPtr)->internalRep.twoPtrValue.ptr2 = INT2PTR( ((bignum).sign << 30) \ | ((bignum).alloc << 15) | ((bignum).used)); \ } #define UNPACK_BIGNUM(objPtr, bignum) \ - if ((objPtr)->internalRep.ptrAndLongRep.value == (unsigned long)(-1)) { \ - (bignum) = *((mp_int *) ((objPtr)->internalRep.ptrAndLongRep.ptr)); \ + if ((objPtr)->internalRep.twoPtrValue.ptr2 == INT2PTR(-1)) { \ + (bignum) = *((mp_int *) ((objPtr)->internalRep.twoPtrValue.ptr1)); \ } else { \ - (bignum).dp = (objPtr)->internalRep.ptrAndLongRep.ptr; \ - (bignum).sign = (objPtr)->internalRep.ptrAndLongRep.value >> 30; \ + (bignum).dp = (objPtr)->internalRep.twoPtrValue.ptr1; \ + (bignum).sign = PTR2INT((objPtr)->internalRep.twoPtrValue.ptr2) >> 30; \ (bignum).alloc = \ - ((objPtr)->internalRep.ptrAndLongRep.value >> 15) & 0x7fff; \ - (bignum).used = (objPtr)->internalRep.ptrAndLongRep.value & 0x7fff; \ + (PTR2INT((objPtr)->internalRep.twoPtrValue.ptr2) >> 15) & 0x7fff; \ + (bignum).used = PTR2INT((objPtr)->internalRep.twoPtrValue.ptr2) & 0x7fff; \ } /* @@ -1301,6 +1301,39 @@ TclFreeObj( ObjInitDeletionContext(context); +# ifdef TCL_THREADS + /* + * Check to make sure that the Tcl_Obj was allocated by the current + * thread. Don't do this check when shutting down since thread local + * storage can be finalized before the last Tcl_Obj is freed. + */ + + if (!TclInExit()) { + Tcl_HashTable *tablePtr; + Tcl_HashEntry *hPtr; + ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey); + + tablePtr = tsdPtr->objThreadMap; + if (!tablePtr) { + Tcl_Panic("TclFreeObj: object table not initialized"); + } + hPtr = Tcl_FindHashEntry(tablePtr, (char *) objPtr); + if (hPtr) { + /* + * As the Tcl_Obj is going to be deleted we remove the entry. + */ + + ObjData *objData = Tcl_GetHashValue(hPtr); + + if (objData != NULL) { + ckfree(objData); + } + + Tcl_DeleteHashEntry(hPtr); + } + } +# endif + /* * Check for a double free of the same value. This is slightly tricky * because it is customary to free a Tcl_Obj when its refcount falls @@ -3148,8 +3181,8 @@ FreeBignum( UNPACK_BIGNUM(objPtr, toFree); mp_clear(&toFree); - if ((long) objPtr->internalRep.ptrAndLongRep.value < 0) { - ckfree(objPtr->internalRep.ptrAndLongRep.ptr); + if (PTR2INT(objPtr->internalRep.twoPtrValue.ptr2) < 0) { + ckfree(objPtr->internalRep.twoPtrValue.ptr1); } objPtr->typePtr = NULL; } @@ -3360,8 +3393,8 @@ GetBignumFromObj( mp_init_copy(bignumValue, &temp); } else { UNPACK_BIGNUM(objPtr, *bignumValue); - objPtr->internalRep.ptrAndLongRep.ptr = NULL; - objPtr->internalRep.ptrAndLongRep.value = 0; + objPtr->internalRep.twoPtrValue.ptr1 = NULL; + objPtr->internalRep.twoPtrValue.ptr2 = NULL; objPtr->typePtr = NULL; if (objPtr->bytes == NULL) { TclInitStringRep(objPtr, tclEmptyStringRep, 0); @@ -3766,25 +3799,11 @@ Tcl_DbDecrRefCount( Tcl_Panic("Trying to %s of Tcl_Obj allocated in another thread", "decr ref count"); } - - /* - * If the Tcl_Obj is going to be deleted, remove the entry. - */ - - if ((objPtr->refCount - 1) <= 0) { - ObjData *objData = Tcl_GetHashValue(hPtr); - - if (objData != NULL) { - ckfree(objData); - } - - Tcl_DeleteHashEntry(hPtr); - } } # endif /* TCL_THREADS */ #endif /* TCL_MEM_DEBUG */ - if (--(objPtr)->refCount <= 0) { + if (objPtr->refCount-- <= 1) { TclFreeObj(objPtr); } } @@ -3952,11 +3971,10 @@ TclCompareObjKeys( /* * If the object pointers are the same then they match. - */ + * OPT: this comparison was moved to the caller - if (objPtr1 == objPtr2) { - return 1; - } + if (objPtr1 == objPtr2) return 1; + */ /* * Don't use Tcl_GetStringFromObj as it would prevent l1 and l2 being @@ -4269,8 +4287,7 @@ FreeCmdNameInternalRep( * there are no more uses, free the ResolvedCmdName structure. */ - resPtr->refCount--; - if (resPtr->refCount == 0) { + if (resPtr->refCount-- == 1) { /* * Now free the cached command, unless it is still in its hash * table or if there are other references to it from other cmdName diff --git a/generic/tclPanic.c b/generic/tclPanic.c index 2a453b9..b032449 100644 --- a/generic/tclPanic.c +++ b/generic/tclPanic.c @@ -15,7 +15,7 @@ #include "tclInt.h" #if defined(_WIN32) || defined(__CYGWIN__) - MODULE_SCOPE void tclWinDebugPanic(const char *format, ...); + MODULE_SCOPE TCL_NORETURN void tclWinDebugPanic(const char *format, ...); #endif /* @@ -24,9 +24,9 @@ */ #if defined(__CYGWIN__) -static Tcl_PanicProc *panicProc = tclWinDebugPanic; +static TCL_NORETURN Tcl_PanicProc *panicProc = tclWinDebugPanic; #else -static Tcl_PanicProc *panicProc = NULL; +static TCL_NORETURN1 Tcl_PanicProc *panicProc = NULL; #endif /* @@ -47,7 +47,7 @@ static Tcl_PanicProc *panicProc = NULL; void Tcl_SetPanicProc( - Tcl_PanicProc *proc) + TCL_NORETURN1 Tcl_PanicProc *proc) { #if defined(_WIN32) /* tclWinDebugPanic only installs if there is no panicProc yet. */ @@ -141,7 +141,14 @@ Tcl_PanicVA( *---------------------------------------------------------------------- */ - /* ARGSUSED */ +/* ARGSUSED */ + +/* + * The following comment is here so that Coverity's static analizer knows that + * a Tcl_Panic() call can never return and avoids lots of false positives. + */ + +/* coverity[+kill] */ void Tcl_Panic( const char *format, diff --git a/generic/tclParse.c b/generic/tclParse.c index 5524979..95abc45 100644 --- a/generic/tclParse.c +++ b/generic/tclParse.c @@ -12,7 +12,7 @@ * See the file "license.terms" for information on usage and redistribution of * this file, and for a DISCLAIMER OF ALL WARRANTIES. */ - + #include "tclInt.h" #include "tclParse.h" #include <assert.h> @@ -511,7 +511,7 @@ Tcl_ParseCommand( listStart = nextElem = tokenPtr[1].start; while (nextElem < listEnd) { int quoted; - + tokenPtr->type = TCL_TOKEN_SIMPLE_WORD; tokenPtr->numComponents = 1; @@ -1915,7 +1915,7 @@ Tcl_ParseQuotedString( * flags argument to provide support for the -nobackslashes, -nocommands, * and -novariables options, as represented by the flag values * TCL_SUBST_BACKSLASHES, TCL_SUBST_COMMANDS, TCL_SUBST_VARIABLES. - * + * * Results: * None. * diff --git a/generic/tclPkg.c b/generic/tclPkg.c index df90cea..f6e8b20 100644 --- a/generic/tclPkg.c +++ b/generic/tclPkg.c @@ -383,7 +383,7 @@ PkgRequireCore( if (pkgPtr->clientData != NULL) { Tcl_SetObjResult(interp, Tcl_ObjPrintf( "circular package dependency:" - " attempt to provide %s %s requires %s", + " attempt to provide %s %s requires %s", name, (char *) pkgPtr->clientData, name)); AddRequirementsToResult(interp, reqc, reqv); Tcl_SetErrorCode(interp, "TCL", "PACKAGE", "CIRCULARITY", NULL); diff --git a/generic/tclPreserve.c b/generic/tclPreserve.c index 0bd8f93..cca13e8 100644 --- a/generic/tclPreserve.c +++ b/generic/tclPreserve.c @@ -459,8 +459,7 @@ TclHandleRelease( handlePtr, handlePtr->ptr2, handlePtr->ptr); } #endif - handlePtr->refCount--; - if ((handlePtr->refCount == 0) && (handlePtr->ptr == NULL)) { + if ((--handlePtr->refCount == 0) && (handlePtr->ptr == NULL)) { ckfree(handlePtr); } } diff --git a/generic/tclProc.c b/generic/tclProc.c index e0d6ec7..ac65bde 100644 --- a/generic/tclProc.c +++ b/generic/tclProc.c @@ -69,9 +69,9 @@ const Tcl_ObjType tclProcBodyType = { }; /* - * The [upvar]/[uplevel] level reference type. Uses the ptrAndLongRep field, + * 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 value. + * offset in ptr2. * * Uses the default behaviour throughout, and never disposes of the string * rep; it's just a cache type. @@ -823,10 +823,10 @@ TclObjGetFrame( name = TclGetString(objPtr); if (objPtr->typePtr == &levelReferenceType) { - if (objPtr->internalRep.ptrAndLongRep.ptr != NULL) { - level = curLevel - objPtr->internalRep.ptrAndLongRep.value; + if (objPtr->internalRep.twoPtrValue.ptr1) { + level = curLevel - PTR2INT(objPtr->internalRep.twoPtrValue.ptr2); } else { - level = objPtr->internalRep.ptrAndLongRep.value; + level = PTR2INT(objPtr->internalRep.twoPtrValue.ptr2); } if (level < 0) { goto levelError; @@ -848,14 +848,12 @@ TclObjGetFrame( /* * Cache for future reference. - * - * TODO: Use the new ptrAndLongRep intrep */ TclFreeIntRep(objPtr); objPtr->typePtr = &levelReferenceType; - objPtr->internalRep.ptrAndLongRep.ptr = NULL; - objPtr->internalRep.ptrAndLongRep.value = level; + 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; @@ -863,14 +861,12 @@ TclObjGetFrame( /* * Cache for future reference. - * - * TODO: Use the new ptrAndLongRep intrep */ TclFreeIntRep(objPtr); objPtr->typePtr = &levelReferenceType; - objPtr->internalRep.ptrAndLongRep.ptr = (void *) 1; /* non-NULL */ - objPtr->internalRep.ptrAndLongRep.value = level; + objPtr->internalRep.twoPtrValue.ptr1 = (void *) 1; + objPtr->internalRep.twoPtrValue.ptr2 = INT2PTR(level); level = curLevel - level; } else { /* @@ -1646,12 +1642,9 @@ TclPushProcCallFrame( */ framePtrPtr = &framePtr; - result = TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, + (void) TclPushStackFrame(interp, (Tcl_CallFrame **) framePtrPtr, (Tcl_Namespace *) nsPtr, (isLambda? (FRAME_IS_PROC|FRAME_IS_LAMBDA) : FRAME_IS_PROC)); - if (result != TCL_OK) { - return result; - } framePtr->objc = objc; framePtr->objv = objv; @@ -1846,7 +1839,7 @@ InterpProcNR2( TCL_DTRACE_PROC_RETURN(l < iPtr->varFramePtr->objc ? TclGetString(iPtr->varFramePtr->objv[l]) : NULL, result); } - if (--procPtr->refCount <= 0) { + if (procPtr->refCount-- <= 1) { TclProcCleanupProc(procPtr); } @@ -1861,8 +1854,8 @@ InterpProcNR2( if (result != TCL_OK) { goto process; } - - done: + + done: if (TCL_DTRACE_PROC_RESULT_ENABLED()) { int l = iPtr->varFramePtr->isProcCallFrame & FRAME_IS_LAMBDA ? 1 : 0; Tcl_Obj *r = Tcl_GetObjResult(interp); @@ -2059,7 +2052,7 @@ TclProcCompileProc( procPtr->numCompiledLocals = procPtr->numArgs; } - TclPushStackFrame(interp, &framePtr, (Tcl_Namespace *) nsPtr, + (void) TclPushStackFrame(interp, &framePtr, (Tcl_Namespace *) nsPtr, /* isProcCallFrame */ 0); /* @@ -2151,8 +2144,7 @@ TclProcDeleteProc( { Proc *procPtr = clientData; - procPtr->refCount--; - if (procPtr->refCount <= 0) { + if (procPtr->refCount-- <= 1) { TclProcCleanupProc(procPtr); } } @@ -2407,7 +2399,7 @@ ProcBodyFree( { Proc *procPtr = objPtr->internalRep.twoPtrValue.ptr1; - if (procPtr->refCount-- < 2) { + if (procPtr->refCount-- <= 1) { TclProcCleanupProc(procPtr); } } @@ -2450,8 +2442,7 @@ FreeLambdaInternalRep( Proc *procPtr = objPtr->internalRep.twoPtrValue.ptr1; Tcl_Obj *nsObjPtr = objPtr->internalRep.twoPtrValue.ptr2; - procPtr->refCount--; - if (procPtr->refCount == 0) { + if (procPtr->refCount-- == 1) { TclProcCleanupProc(procPtr); } TclDecrRefCount(nsObjPtr); diff --git a/generic/tclRegexp.c b/generic/tclRegexp.c index 5bc3aa2..ea25d4b 100644 --- a/generic/tclRegexp.c +++ b/generic/tclRegexp.c @@ -755,7 +755,7 @@ FreeRegexpInternalRep( * If this is the last reference to the regexp, free it. */ - if (--(regexpRepPtr->refCount) <= 0) { + if (regexpRepPtr->refCount-- <= 1) { FreeRegexp(regexpRepPtr); } objPtr->typePtr = NULL; @@ -976,7 +976,7 @@ CompileRegexp( if (tsdPtr->patterns[NUM_REGEXPS-1] != NULL) { TclRegexp *oldRegexpPtr = tsdPtr->regexps[NUM_REGEXPS-1]; - if (--(oldRegexpPtr->refCount) <= 0) { + if (oldRegexpPtr->refCount-- <= 1) { FreeRegexp(oldRegexpPtr); } ckfree(tsdPtr->patterns[NUM_REGEXPS-1]); @@ -1050,7 +1050,7 @@ FinalizeRegexp( for (i = 0; (i < NUM_REGEXPS) && (tsdPtr->patterns[i] != NULL); i++) { regexpPtr = tsdPtr->regexps[i]; - if (--(regexpPtr->refCount) <= 0) { + if (regexpPtr->refCount-- <= 1) { FreeRegexp(regexpPtr); } ckfree(tsdPtr->patterns[i]); diff --git a/generic/tclResult.c b/generic/tclResult.c index 2f2563a..9d0714c 100644 --- a/generic/tclResult.c +++ b/generic/tclResult.c @@ -1293,7 +1293,7 @@ TclProcessReturn( if (Tcl_IsShared(iPtr->errorStack)) { Tcl_Obj *newObj; - + newObj = Tcl_DuplicateObj(iPtr->errorStack); Tcl_DecrRefCount(iPtr->errorStack); Tcl_IncrRefCount(newObj); @@ -1626,7 +1626,7 @@ TclNoErrorStack( Tcl_Obj *options) { Tcl_Obj **keys = GetKeys(); - + Tcl_DictObjRemove(interp, options, keys[KEY_ERRORSTACK]); return options; } diff --git a/generic/tclScan.c b/generic/tclScan.c index 4dfc2d6..3edb8be 100644 --- a/generic/tclScan.c +++ b/generic/tclScan.c @@ -595,7 +595,7 @@ Tcl_ScanObjCmd( return TCL_ERROR; } - format = Tcl_GetStringFromObj(objv[2], NULL); + format = Tcl_GetString(objv[2]); numVars = objc-3; /* @@ -617,7 +617,7 @@ Tcl_ScanObjCmd( } } - string = Tcl_GetStringFromObj(objv[1], NULL); + string = Tcl_GetString(objv[1]); baseString = string; /* diff --git a/generic/tclStrToD.c b/generic/tclStrToD.c index 883e2ea..f69f6b9 100644 --- a/generic/tclStrToD.c +++ b/generic/tclStrToD.c @@ -1548,7 +1548,7 @@ MakeLowPrecisionDouble( * Test for the easy cases. */ - if (numSigDigs <= DBL_DIG) { + if (numSigDigs <= QUICK_MAX) { if (exponent >= 0) { if (exponent <= mmaxpow) { /* @@ -1561,7 +1561,7 @@ MakeLowPrecisionDouble( ((Tcl_WideInt)significand * pow10vals[exponent]); goto returnValue; } else { - int diff = DBL_DIG - numSigDigs; + int diff = QUICK_MAX - numSigDigs; if (exponent-diff <= mmaxpow) { /* @@ -1798,6 +1798,12 @@ RefineApproximation( double quot; /* Correction term. */ double minincr; /* Lower bound on the absolute value of the * correction term. */ + int roundToEven = 0; /* Flag == TRUE if we need to invoke + * "round to even" functionality */ + double rteSignificand; /* Significand of the round-to-even result */ + int rteExponent; /* Exponent of the round-to-even result */ + Tcl_WideInt rteSigWide; /* Wide integer version of the significand + * for testing evenness */ int i; /* @@ -1893,15 +1899,33 @@ RefineApproximation( mp_div_2d(&twoMv, -multiplier, &twoMv, NULL); } - /* - * If the result is less than unity, the error is less than 1/2 unit in - * the last place, so there's no correction to make. - */ - - if (mp_cmp_mag(&twoMd, &twoMv) == MP_LT) { + switch (mp_cmp_mag(&twoMd, &twoMv)) { + case MP_LT: + /* + * If the result is less than unity, the error is less than 1/2 unit in + * the last place, so there's no correction to make. + */ mp_clear(&twoMd); mp_clear(&twoMv); return approxResult; + case MP_EQ: + /* + * If the result is exactly unity, we need to round to even. + */ + roundToEven = 1; + break; + case MP_GT: + break; + } + + if (roundToEven) { + rteSignificand = frexp(approxResult, &rteExponent); + rteSigWide = (Tcl_WideInt) ldexp(rteSignificand, FP_PRECISION); + if ((rteSigWide & 1) == 0) { + mp_clear(&twoMd); + mp_clear(&twoMv); + return approxResult; + } } /* @@ -4025,7 +4049,7 @@ StrictBignumConversion( * choosing the one that is closest to the given number (and * resolving ties with 'round to even'). It is allowed to return * fewer than 'ndigits' if the number converts exactly; if the - * TCL_DD_E_FORMAT|TCL_DD_SHORTEN_FLAG is supplied instead, it + * TCL_DD_E_FORMAT|TCL_DD_SHORTEN_FLAG is supplied instead, it * also returns fewer digits if the shorter string will still * reconvert without loss to the given input number. In any case, * strings of trailing zeroes are suppressed. @@ -4559,7 +4583,7 @@ TclBignumToDouble( /* - * We need a 'mantBits'-bit significand. Determine what shift will + * We need a 'mantBits'-bit significand. Determine what shift will * give us that. */ @@ -4574,7 +4598,7 @@ TclBignumToDouble( } shift = mantBits - bits; - /* + /* * If shift > 0, shift the significand left by the requisite number of * bits. If shift == 0, the significand is already exactly 'mantBits' * in length. If shift < 0, we will need to shift the significand right diff --git a/generic/tclStringObj.c b/generic/tclStringObj.c index c04944d..8d70d20 100644 --- a/generic/tclStringObj.c +++ b/generic/tclStringObj.c @@ -188,7 +188,7 @@ GrowStringBuffer( int flag) { /* - * Pre-conditions: + * Pre-conditions: * objPtr->typePtr == &tclStringType * needed > stringPtr->allocated * flag || objPtr->bytes != NULL @@ -238,7 +238,7 @@ GrowUnicodeBuffer( int needed) { /* - * Pre-conditions: + * Pre-conditions: * objPtr->typePtr == &tclStringType * needed > stringPtr->maxChars * needed < STRING_MAXCHARS @@ -1334,7 +1334,7 @@ Tcl_AppendObjToObj( * appendObjPtr and append it. */ - if (stringPtr->hasUnicode + if (stringPtr->hasUnicode #if COMPAT && stringPtr->numChars > 0 #endif @@ -2314,7 +2314,7 @@ Tcl_AppendFormatToObj( p += sprintf(p, "%d", width); if (width > length) { length = width; - } + } } if (gotPrecision) { *p++ = '.'; @@ -2878,7 +2878,7 @@ ExtendUnicodeRepWithString( } needed = numOrigChars + numAppendChars; stringCheckLimits(needed); - + if (needed > stringPtr->maxChars) { GrowUnicodeBuffer(objPtr, needed); stringPtr = GET_STRING(objPtr); @@ -3096,7 +3096,7 @@ ExtendStringRepWithUnicode( * Pre-condition: this is the "string" Tcl_ObjType. */ - int i, origLength, size = 0; + int i, origLength, size = 0; char *dst, buf[TCL_UTF_MAX]; String *stringPtr = GET_STRING(objPtr); @@ -3112,12 +3112,12 @@ ExtendStringRepWithUnicode( objPtr->length = 0; } size = origLength = objPtr->length; - + /* * Quick cheap check in case we have more than enough room. */ - if (numChars <= (INT_MAX - size)/TCL_UTF_MAX + if (numChars <= (INT_MAX - size)/TCL_UTF_MAX && stringPtr->allocated >= size + numChars * TCL_UTF_MAX) { goto copyBytes; } diff --git a/generic/tclStubInit.c b/generic/tclStubInit.c index 7a84cba..7d44163 100644 --- a/generic/tclStubInit.c +++ b/generic/tclStubInit.c @@ -82,7 +82,7 @@ static const char *TclGetStartupScriptFileName(void) if (path == NULL) { return NULL; } - return Tcl_GetStringFromObj(path, NULL); + return Tcl_GetString(path); } #if defined(_WIN32) || defined(__CYGWIN__) diff --git a/generic/tclTest.c b/generic/tclTest.c index 0f4b6d4..600f5ec 100644 --- a/generic/tclTest.c +++ b/generic/tclTest.c @@ -928,7 +928,7 @@ TestasyncCmd( static int AsyncHandlerProc( - ClientData clientData, /* If of TestAsyncHandler structure. + ClientData clientData, /* If of TestAsyncHandler structure. * in global list. */ Tcl_Interp *interp, /* Interpreter in which command was * executed, or NULL. */ @@ -2306,9 +2306,9 @@ TesteventDeleteProc( return 0; } targetName = (Tcl_Obj *) clientData; - targetNameStr = (char *) Tcl_GetStringFromObj(targetName, NULL); + targetNameStr = (char *) Tcl_GetString(targetName); ev = (TestEvent *) event; - evNameStr = Tcl_GetStringFromObj(ev->tag, NULL); + evNameStr = Tcl_GetString(ev->tag); if (strcmp(evNameStr, targetNameStr) == 0) { Tcl_DecrRefCount(ev->tag); Tcl_DecrRefCount(ev->command); @@ -4671,7 +4671,6 @@ TestgetvarfullnameCmd( Tcl_Namespace *namespacePtr; Tcl_CallFrame *framePtr; Tcl_Var variable; - int result; if (objc != 3) { Tcl_WrongNumArgs(interp, 1, objv, "name scope"); @@ -4699,11 +4698,8 @@ TestgetvarfullnameCmd( if (namespacePtr == NULL) { return TCL_ERROR; } - result = TclPushStackFrame(interp, &framePtr, namespacePtr, + (void) TclPushStackFrame(interp, &framePtr, namespacePtr, /*isProcCallFrame*/ 0); - if (result != TCL_OK) { - return result; - } } variable = Tcl_FindNamespaceVar(interp, name, NULL, diff --git a/generic/tclTestProcBodyObj.c b/generic/tclTestProcBodyObj.c index a3f89f6..0d3617e 100644 --- a/generic/tclTestProcBodyObj.c +++ b/generic/tclTestProcBodyObj.c @@ -245,7 +245,7 @@ ProcBodyTestProcObjCmd( * Find the Command pointer to this procedure */ - fullName = Tcl_GetStringFromObj(objv[3], NULL); + fullName = Tcl_GetString(objv[3]); procCmd = Tcl_FindCommand(interp, fullName, NULL, TCL_LEAVE_ERR_MSG); if (procCmd == NULL) { return TCL_ERROR; diff --git a/generic/tclThreadAlloc.c b/generic/tclThreadAlloc.c index 560556d..018f006 100644 --- a/generic/tclThreadAlloc.c +++ b/generic/tclThreadAlloc.c @@ -84,6 +84,7 @@ typedef union Block { typedef struct Bucket { Block *firstPtr; /* First block available */ + Block *lastPtr; /* End of block list */ long numFree; /* Number of blocks available */ /* All fields below for accounting only */ @@ -107,6 +108,7 @@ typedef struct Cache { Tcl_ThreadId owner; /* Which thread's cache is this? */ Tcl_Obj *firstObjPtr; /* List of free objects for thread */ int numObjects; /* Number of objects for thread */ + Tcl_Obj *lastPtr; /* Last object in this cache */ int totalAssigned; /* Total space assigned to thread */ Bucket buckets[NBUCKETS]; /* The buckets for this thread */ } Cache; @@ -135,6 +137,7 @@ static int GetBlocks(Cache *cachePtr, int bucket); static Block * Ptr2Block(char *ptr); static char * Block2Ptr(Block *blockPtr, int bucket, unsigned int reqSize); static void MoveObjs(Cache *fromPtr, Cache *toPtr, int numMove); +static void PutObjs(Cache *fromPtr, int numMove); /* * Local variables defined in this file and initialized at startup. @@ -271,9 +274,7 @@ TclFreeAllocCache( */ if (cachePtr->numObjects > 0) { - Tcl_MutexLock(objLockPtr); - MoveObjs(cachePtr, sharedPtr, cachePtr->numObjects); - Tcl_MutexUnlock(objLockPtr); + PutObjs(cachePtr, cachePtr->numObjects); } /* @@ -415,6 +416,9 @@ TclpFree( cachePtr->buckets[bucket].totalAssigned -= blockPtr->blockReqSize; blockPtr->nextBlock = cachePtr->buckets[bucket].firstPtr; cachePtr->buckets[bucket].firstPtr = blockPtr; + if (cachePtr->buckets[bucket].numFree == 0) { + cachePtr->buckets[bucket].lastPtr = blockPtr; + } cachePtr->buckets[bucket].numFree++; cachePtr->buckets[bucket].numInserts++; @@ -572,11 +576,13 @@ TclThreadAllocObj(void) if (newObjsPtr == NULL) { Tcl_Panic("alloc: could not allocate %d new objects", numMove); } + cachePtr->lastPtr = newObjsPtr + numMove - 1; + objPtr = cachePtr->firstObjPtr; /* NULL */ while (--numMove >= 0) { - objPtr = &newObjsPtr[numMove]; - objPtr->internalRep.twoPtrValue.ptr1 = cachePtr->firstObjPtr; - cachePtr->firstObjPtr = objPtr; + newObjsPtr[numMove].internalRep.twoPtrValue.ptr1 = objPtr; + objPtr = newObjsPtr + numMove; } + cachePtr->firstObjPtr = newObjsPtr; } } @@ -624,6 +630,9 @@ TclThreadFreeObj( objPtr->internalRep.twoPtrValue.ptr1 = cachePtr->firstObjPtr; cachePtr->firstObjPtr = objPtr; + if (cachePtr->numObjects == 0) { + cachePtr->lastPtr = objPtr; + } cachePtr->numObjects++; /* @@ -632,9 +641,7 @@ TclThreadFreeObj( */ if (cachePtr->numObjects > NOBJHIGH) { - Tcl_MutexLock(objLockPtr); - MoveObjs(cachePtr, sharedPtr, NOBJALLOC); - Tcl_MutexUnlock(objLockPtr); + PutObjs(cachePtr, NOBJALLOC); } } @@ -732,13 +739,67 @@ MoveObjs( * just have to update the first and last. */ - objPtr->internalRep.twoPtrValue.ptr1 = toPtr->firstObjPtr; + toPtr->lastPtr = objPtr; + objPtr->internalRep.twoPtrValue.ptr1 = toPtr->firstObjPtr; /* NULL */ toPtr->firstObjPtr = fromFirstObjPtr; } /* *---------------------------------------------------------------------- * + * PutObjs -- + * + * Move Tcl_Obj's from thread cache to shared cache. + * + * Results: + * None. + * + * Side effects: + * None. + * + *---------------------------------------------------------------------- + */ + +static void +PutObjs( + Cache *fromPtr, + int numMove) +{ + int keep = fromPtr->numObjects - numMove; + Tcl_Obj *firstPtr, *lastPtr = NULL; + + fromPtr->numObjects = keep; + firstPtr = fromPtr->firstObjPtr; + if (keep == 0) { + fromPtr->firstObjPtr = NULL; + } else { + do { + lastPtr = firstPtr; + firstPtr = firstPtr->internalRep.twoPtrValue.ptr1; + } while (--keep > 0); + lastPtr->internalRep.twoPtrValue.ptr1 = NULL; + } + + /* + * Move all objects as a block - they are already linked to each other, we + * just have to update the first and last. + */ + + Tcl_MutexLock(objLockPtr); + fromPtr->lastPtr->internalRep.twoPtrValue.ptr1 = sharedPtr->firstObjPtr; + sharedPtr->firstObjPtr = firstPtr; + if (sharedPtr->numObjects == 0) { + sharedPtr->lastPtr = fromPtr->lastPtr; + } + sharedPtr->numObjects += numMove; + Tcl_MutexUnlock(objLockPtr); + + fromPtr->lastPtr = lastPtr; +} + +/* + *---------------------------------------------------------------------- + * * Block2Ptr, Ptr2Block -- * * Convert between internal blocks and user pointers. @@ -848,20 +909,25 @@ PutBlocks( int bucket, int numMove) { - register Block *lastPtr, *firstPtr; - register int n = numMove; - /* - * Before acquiring the lock, walk the block list to find the last block - * to be moved. + * We have numFree. Want to shed numMove. So compute how many + * Blocks to keep. */ - firstPtr = lastPtr = cachePtr->buckets[bucket].firstPtr; - while (--n > 0) { - lastPtr = lastPtr->nextBlock; + int keep = cachePtr->buckets[bucket].numFree - numMove; + Block *lastPtr = NULL, *firstPtr; + + cachePtr->buckets[bucket].numFree = keep; + firstPtr = cachePtr->buckets[bucket].firstPtr; + if (keep == 0) { + cachePtr->buckets[bucket].firstPtr = NULL; + } else { + do { + lastPtr = firstPtr; + firstPtr = firstPtr->nextBlock; + } while (--keep > 0); + lastPtr->nextBlock = NULL; } - cachePtr->buckets[bucket].firstPtr = lastPtr->nextBlock; - cachePtr->buckets[bucket].numFree -= numMove; /* * Aquire the lock and place the list of blocks at the front of the shared @@ -869,10 +935,17 @@ PutBlocks( */ LockBucket(cachePtr, bucket); - lastPtr->nextBlock = sharedPtr->buckets[bucket].firstPtr; + cachePtr->buckets[bucket].lastPtr->nextBlock + = sharedPtr->buckets[bucket].firstPtr; sharedPtr->buckets[bucket].firstPtr = firstPtr; + if (sharedPtr->buckets[bucket].numFree == 0) { + sharedPtr->buckets[bucket].lastPtr + = cachePtr->buckets[bucket].lastPtr; + } sharedPtr->buckets[bucket].numFree += numMove; UnlockBucket(cachePtr, bucket); + + cachePtr->buckets[bucket].lastPtr = lastPtr; } /* @@ -919,6 +992,8 @@ GetBlocks( if (n >= sharedPtr->buckets[bucket].numFree) { cachePtr->buckets[bucket].firstPtr = sharedPtr->buckets[bucket].firstPtr; + cachePtr->buckets[bucket].lastPtr = + sharedPtr->buckets[bucket].lastPtr; cachePtr->buckets[bucket].numFree = sharedPtr->buckets[bucket].numFree; sharedPtr->buckets[bucket].firstPtr = NULL; @@ -932,6 +1007,7 @@ GetBlocks( blockPtr = blockPtr->nextBlock; } sharedPtr->buckets[bucket].firstPtr = blockPtr->nextBlock; + cachePtr->buckets[bucket].lastPtr = blockPtr; blockPtr->nextBlock = NULL; } } @@ -983,6 +1059,7 @@ GetBlocks( ((char *) blockPtr + bucketInfo[bucket].blockSize); blockPtr = blockPtr->nextBlock; } + cachePtr->buckets[bucket].lastPtr = blockPtr; blockPtr->nextBlock = NULL; } return 1; @@ -1030,7 +1107,7 @@ TclFinalizeThreadAlloc(void) * TclFinalizeThreadAllocThread -- * * This procedure is used to destroy single thread private resources used - * in this file. + * in this file. * Called in TclpFinalizeThreadData when a thread exits (Tcl_FinalizeThread). * * Results: diff --git a/generic/tclThreadStorage.c b/generic/tclThreadStorage.c index f24e334..755a461 100644 --- a/generic/tclThreadStorage.c +++ b/generic/tclThreadStorage.c @@ -208,12 +208,12 @@ TclThreadStorageKeyGet( * * This procedure set an association of value with the key passed. The * associated value may be retrieved with TclThreadDataKeyGet(). - * + * * Results: * None. * * Side effects: - * The thread-specific table may be created or reallocated. + * The thread-specific table may be created or reallocated. * *---------------------------------------------------------------------- */ @@ -285,7 +285,7 @@ TclThreadStorageKeySet( *---------------------------------------------------------------------- */ -void +void TclFinalizeThreadDataThread(void) { TSDTable *tsdTablePtr = TclpThreadGetMasterTSD(tsdMaster.key); diff --git a/generic/tclTrace.c b/generic/tclTrace.c index 6184a89..fe52d59 100644 --- a/generic/tclTrace.c +++ b/generic/tclTrace.c @@ -544,7 +544,7 @@ TraceExecutionObjCmd( tcmdPtr->flags = 0; } - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } break; @@ -748,7 +748,7 @@ TraceCommandObjCmd( Tcl_UntraceCommand(interp, name, flags | TCL_TRACE_DELETE, TraceCommandProc, clientData); tcmdPtr->flags |= TCL_TRACE_DESTROYED; - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } break; @@ -1130,7 +1130,7 @@ Tcl_TraceCommand( /* * Bug 3484621: up the interp's epoch if this is a BC'ed command */ - + if ((cmdPtr->compileProc != NULL) && !(cmdPtr->flags & CMD_HAS_EXEC_TRACES)){ Interp *iPtr = (Interp *) interp; iPtr->compileEpoch++; @@ -1138,7 +1138,7 @@ Tcl_TraceCommand( cmdPtr->flags |= CMD_HAS_EXEC_TRACES; } - + return TCL_OK; } @@ -1223,7 +1223,7 @@ Tcl_UntraceCommand( } tracePtr->flags = 0; - if ((--tracePtr->refCount) <= 0) { + if (tracePtr->refCount-- <= 1) { ckfree(tracePtr); } @@ -1245,7 +1245,7 @@ Tcl_UntraceCommand( /* * Bug 3484621: up the interp's epoch if this is a BC'ed command */ - + if (cmdPtr->compileProc != NULL) { Interp *iPtr = (Interp *) interp; iPtr->compileEpoch++; @@ -1382,7 +1382,7 @@ TraceCommandProc( Tcl_RestoreInterpState(interp, state); tcmdPtr->refCount--; } - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } } @@ -1474,7 +1474,7 @@ TclCheckExecutionTraces( } traceCode = TraceExecutionProc(tcmdPtr, interp, curLevel, command, (Tcl_Command) cmdPtr, objc, objv); - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } } @@ -1721,7 +1721,7 @@ CommandObjTraceDeleted( { TraceCommandInfo *tcmdPtr = clientData; - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } } @@ -1936,7 +1936,7 @@ TraceExecutionProc( } } if (call) { - if ((--tcmdPtr->refCount) <= 0) { + if (tcmdPtr->refCount-- <= 1) { ckfree(tcmdPtr); } } diff --git a/generic/tclUniData.c b/generic/tclUniData.c index 78e7d17..1ca119d 100644 --- a/generic/tclUniData.c +++ b/generic/tclUniData.c @@ -36,29 +36,29 @@ static const unsigned short pageMap[] = { 3200, 1792, 3232, 3264, 3296, 1792, 3328, 3360, 3392, 3424, 3456, 3488, 3520, 1792, 1344, 3552, 3584, 3616, 3648, 3680, 3712, 3744, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 3776, 1344, 3808, 3840, - 3872, 1344, 3904, 1344, 3936, 3968, 4000, 1344, 1344, 4032, 4064, 1344, + 3872, 1344, 3904, 1344, 3936, 3968, 4000, 4032, 4032, 4064, 4096, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 4096, 4128, 1344, 1344, 4160, 4192, 4224, - 4256, 4288, 1344, 4320, 4352, 4384, 4416, 1344, 4448, 4480, 1344, 4512, - 1344, 4544, 4576, 4608, 4640, 4672, 1344, 4704, 4736, 4768, 4800, 1344, - 4832, 4864, 4896, 4928, 1792, 1792, 4960, 4992, 5024, 5056, 5088, 5120, - 1344, 5152, 1344, 5184, 5216, 5248, 1792, 1792, 5280, 5312, 5344, 5376, - 5408, 5440, 5472, 5408, 704, 5504, 224, 224, 224, 224, 5536, 224, 224, - 224, 5568, 5600, 5632, 5664, 5696, 5728, 5760, 5792, 5824, 5856, 5888, - 5920, 5952, 5984, 6016, 6048, 6080, 6112, 6144, 6176, 6208, 6240, 6272, - 6304, 6336, 6336, 6336, 6336, 6336, 6336, 6336, 6336, 6368, 6400, 4768, - 6432, 6464, 6496, 6528, 6560, 4768, 6592, 6624, 6656, 6688, 6720, 6752, - 6784, 4768, 4768, 4768, 4768, 4768, 6816, 6848, 6880, 4768, 4768, 4768, - 6912, 4768, 4768, 4768, 4768, 4768, 4768, 4768, 6944, 6976, 4768, 7008, - 7040, 4768, 4768, 4768, 4768, 4768, 4768, 4768, 4768, 6336, 6336, 6336, - 6336, 7072, 6336, 7104, 7136, 6336, 6336, 6336, 6336, 6336, 6336, 6336, - 6336, 4768, 7168, 7200, 7232, 7264, 7296, 7328, 1792, 7360, 7392, 7424, - 7456, 224, 224, 224, 7488, 7520, 7552, 1344, 7584, 7616, 7648, 7648, - 704, 7680, 7712, 7744, 1792, 7776, 4768, 4768, 7808, 4768, 4768, 4768, - 4768, 4768, 4768, 7840, 7872, 7904, 7936, 3136, 1344, 7968, 4064, 1344, - 8000, 8032, 8064, 1344, 1344, 8096, 8128, 4768, 8160, 8192, 8224, 8256, - 4768, 8224, 8288, 4768, 8192, 4768, 4768, 4768, 4768, 4768, 4768, 4768, - 4768, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 4128, 4160, 1344, 1344, 4192, 4224, 4256, + 4288, 4320, 1344, 4352, 4384, 4416, 4448, 1344, 4480, 4512, 1344, 4544, + 1344, 4576, 4608, 4640, 4672, 4704, 1344, 4736, 4768, 4800, 4832, 1344, + 4864, 4896, 4928, 4960, 1792, 1792, 4992, 5024, 5056, 5088, 5120, 5152, + 1344, 5184, 1344, 5216, 5248, 5280, 1792, 1792, 5312, 5344, 5376, 5408, + 5440, 5472, 5504, 5440, 704, 5536, 224, 224, 224, 224, 5568, 224, 224, + 224, 5600, 5632, 5664, 5696, 5728, 5760, 5792, 5824, 5856, 5888, 5920, + 5952, 5984, 6016, 6048, 6080, 6112, 6144, 6176, 6208, 6240, 6272, 6304, + 6336, 6368, 6368, 6368, 6368, 6368, 6368, 6368, 6368, 6400, 6432, 4800, + 6464, 6496, 6528, 6560, 6592, 4800, 6624, 6656, 6688, 6720, 6752, 6784, + 6816, 4800, 4800, 4800, 4800, 4800, 6848, 6880, 6912, 4800, 4800, 4800, + 6944, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 6976, 7008, 4800, 7040, + 7072, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 6368, 6368, 6368, + 6368, 7104, 6368, 7136, 7168, 6368, 6368, 6368, 6368, 6368, 6368, 6368, + 6368, 4800, 7200, 7232, 7264, 7296, 7328, 7360, 7392, 7424, 7456, 7488, + 7520, 224, 224, 224, 7552, 7584, 7616, 1344, 7648, 7680, 7712, 7712, + 704, 7744, 7776, 7808, 1792, 7840, 4800, 4800, 7872, 4800, 4800, 4800, + 4800, 4800, 4800, 7904, 7936, 7968, 8000, 3136, 1344, 8032, 4096, 1344, + 8064, 8096, 8128, 1344, 1344, 8160, 8192, 4800, 8224, 8256, 8288, 8320, + 4800, 8288, 8352, 4800, 8256, 4800, 4800, 4800, 4800, 4800, 4800, 4800, + 4800, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, @@ -75,7 +75,7 @@ static const unsigned short pageMap[] = { 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 4544, 4768, 4768, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 4576, 4800, 4800, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, @@ -129,16 +129,16 @@ static const unsigned short pageMap[] = { 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 8320, - 1792, 8352, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 4576, + 1792, 8384, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 8384, 4768, 8416, 5248, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 8448, 8480, 224, 8512, 8544, 1344, 1344, 8576, 8608, 8640, 224, - 8672, 8704, 8736, 1792, 8768, 8800, 8832, 1344, 8864, 8896, 8928, 8960, - 8992, 1632, 9024, 9056, 9088, 1888, 9120, 9152, 9184, 1344, 9216, 9248, - 9280, 1344, 9312, 9344, 9376, 9408, 9440, 9472, 9504, 1792, 1792, 1344, - 9536, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 8416, 4800, 8448, 5280, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 8480, 8512, 224, 8544, 8576, 1344, 1344, 8608, 8640, 8672, 224, + 8704, 8736, 8768, 1792, 8800, 8832, 8864, 1344, 8896, 8928, 8960, 8992, + 9024, 1632, 9056, 9088, 9120, 1888, 9152, 9184, 9216, 1344, 9248, 9280, + 9312, 1344, 9344, 9376, 9408, 9440, 9472, 9504, 9536, 9568, 9568, 1344, + 9600, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, @@ -167,77 +167,72 @@ static const unsigned short pageMap[] = { 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 9568, 9600, 9632, 9664, 9664, 9664, 9664, 9664, 9664, 9664, - 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, - 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, - 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, - 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, - 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9664, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, 9696, - 9696, 9696, 9696, 9696, 9696, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 9728, 1344, 1344, 9760, 1792, 9792, 9824, 9856, - 1344, 1344, 9888, 9920, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 9952, 9984, 1344, 10016, 1344, 10048, 10080, 10112, 10144, - 10176, 10208, 1344, 1344, 1344, 10240, 10272, 64, 10304, 10336, 10368, - 4576, 10400, 10432 + 1344, 1344, 9632, 9664, 9696, 9728, 9728, 9728, 9728, 9728, 9728, 9728, + 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, + 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, + 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, + 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, + 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9728, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, 9760, + 9760, 9760, 9760, 9760, 9760, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 9792, 1344, 1344, 9824, 1792, 9856, 9888, 9920, + 1344, 1344, 9952, 9984, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 10016, 10048, 1344, 10080, 1344, 10112, 10144, 10176, 10208, + 10240, 10272, 1344, 1344, 1344, 10304, 10336, 64, 10368, 10400, 10432, + 4608, 10464, 10496 #if TCL_UTF_MAX > 3 - ,10464, 10496, 10528, 1792, 1344, 1344, 1344, 8128, 10560, 10592, 10624, - 10656, 10688, 10720, 10752, 10784, 1792, 1792, 1792, 1792, 9088, 1344, - 10816, 10848, 1344, 10880, 10912, 10944, 10976, 1344, 11008, 1792, - 11040, 11072, 11104, 1344, 11136, 11168, 1792, 1792, 1344, 11200, 1344, - 11232, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 7616, 4544, 10048, 1792, 1792, 1792, 1792, 11264, - 11296, 11328, 11360, 4576, 11392, 1792, 1792, 11424, 11456, 1792, 1792, - 1344, 11488, 1792, 1792, 11520, 11552, 11584, 11616, 11648, 1792, 11680, - 11712, 1344, 11744, 11776, 11808, 11840, 11872, 1792, 1792, 1344, 1344, - 11904, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 11936, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 11968, 12000, 12032, - 12064, 5088, 12096, 12128, 12160, 12192, 12224, 12256, 12288, 5088, - 12320, 12352, 12384, 12416, 12448, 1792, 1792, 1792, 9984, 12480, 12512, - 2400, 2304, 12544, 12576, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1344, 12608, 12640, 1792, 1792, 1792, 1792, 1792, 1344, 12672, - 12704, 1792, 1344, 12736, 12768, 1792, 1344, 12800, 11168, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 12832, 12864, 12896, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1344, 12928, 1792, 1792, 1792, + ,10528, 10560, 10592, 1792, 1344, 1344, 1344, 8192, 10624, 10656, 10688, + 10720, 10752, 10784, 10816, 10848, 1792, 1792, 1792, 1792, 9120, 1344, + 10880, 10912, 1344, 10944, 10976, 11008, 11040, 1344, 11072, 1792, + 11104, 11136, 11168, 1344, 11200, 11232, 1792, 1792, 1344, 11264, 1344, + 11296, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 7680, 4576, 10112, 1792, 1792, 1792, 1792, 11328, + 11360, 11392, 11424, 4608, 11456, 1792, 11488, 11520, 11552, 1792, + 1792, 1344, 11584, 11616, 6688, 11648, 11680, 11712, 11744, 11776, + 1792, 11808, 11840, 1344, 11872, 11904, 11936, 11968, 12000, 1792, + 1792, 1344, 1344, 12032, 1792, 12064, 12096, 12128, 12160, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 12192, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 12224, + 12256, 12288, 12320, 5120, 12352, 12384, 12416, 12448, 12480, 12512, + 12544, 5120, 12576, 12608, 12640, 12672, 12704, 1792, 1792, 12736, + 12768, 12800, 12832, 12864, 2304, 12896, 12928, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1344, 12960, 12992, 1792, 1792, 1792, 1792, + 1792, 1344, 13024, 13056, 1792, 1344, 13088, 13120, 1792, 1344, 13152, + 11232, 1792, 13184, 13216, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 13248, 13280, 13312, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, 13344, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 12928, 1792, 1792, 1792, 10624, 10624, - 10624, 12960, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 9824, 1792, 1792, 1792, + 10688, 10688, 10688, 13376, 1344, 1344, 1344, 1344, 1344, 1344, 13408, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 12992, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 13440, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -248,6 +243,9 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 13472, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -267,13 +265,14 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 12928, 4576, - 13024, 1792, 1792, 9984, 13056, 1344, 13088, 13120, 13152, 13184, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1344, 1344, 13216, 13248, 13280, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 13344, 4608, 13504, 1792, 1792, 10048, 13536, 1344, 13568, 13600, 13632, + 13664, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1344, 1344, 13696, 13728, 13760, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -315,17 +314,17 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 13312, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 13792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 13344, - 13376, 13408, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, + 1344, 1344, 13824, 13856, 13888, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -337,14 +336,16 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 4768, 4768, 4768, 4768, 4768, 4768, 4768, 7840, 4768, 13440, - 4768, 13472, 13504, 13536, 13568, 1792, 4768, 4768, 13600, 1792, 1792, - 1792, 1792, 1792, 4768, 4768, 13632, 13664, 1792, 1792, 1792, 1792, - 13696, 13728, 13760, 13792, 13824, 13856, 13888, 13920, 13952, 13984, - 14016, 14048, 14080, 13696, 13728, 14112, 13792, 14144, 14176, 14208, - 13920, 14240, 14272, 14304, 14336, 14368, 14400, 14432, 14464, 14496, - 14528, 14560, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1792, 1792, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 7904, + 4800, 13920, 4800, 13952, 13984, 14016, 4800, 14048, 4800, 4800, 14080, + 1792, 1792, 1792, 1792, 1792, 4800, 4800, 14112, 14144, 1792, 1792, + 1792, 1792, 14176, 14208, 14240, 14272, 14304, 14336, 14368, 14400, + 14432, 14464, 14496, 14528, 14560, 14176, 14208, 14592, 14272, 14624, + 14656, 14688, 14400, 14720, 14752, 14784, 14816, 14848, 14880, 14912, + 14944, 14976, 15008, 15040, 4800, 4800, 4800, 4800, 4800, 4800, 4800, + 4800, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 4800, 704, 15072, 704, + 15104, 15136, 15168, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -353,24 +354,23 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, - 1344, 1344, 1344, 1344, 1344, 14592, 1792, 1792, 1792, 1792, 1792, + 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 15200, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 14624, 14656, 14688, 14720, 14752, 14784, 1792, 14816, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 4768, 14848, 4768, 4768, 7808, - 14880, 14912, 7840, 14944, 14976, 4768, 14848, 15008, 1792, 1792, 15040, - 15072, 15008, 15104, 1792, 1792, 1792, 1792, 1792, 4768, 15136, 4768, - 13568, 4768, 4768, 15168, 15200, 4768, 4768, 4768, 4768, 4768, 4768, - 4768, 8192, 4768, 4768, 15232, 7776, 4768, 15264, 4768, 4768, 4768, - 4768, 15296, 4768, 4768, 4768, 15328, 15360, 4768, 4768, 4768, 7808, - 4768, 4768, 15392, 1792, 14848, 4768, 15424, 4768, 15456, 15488, 1792, + 1792, 1792, 1792, 15232, 15264, 15296, 15328, 15360, 15392, 1792, 15424, + 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 4800, 15456, 4800, + 4800, 7872, 15488, 15520, 7904, 15552, 15584, 4800, 15456, 15616, 1792, + 1792, 15648, 15680, 15616, 15712, 1792, 1792, 1792, 1792, 1792, 4800, + 4800, 4800, 4800, 4800, 4800, 4800, 15744, 4800, 4800, 4800, 4800, + 4800, 4800, 4800, 4800, 4800, 4800, 4800, 7840, 4800, 15776, 4800, + 4800, 4800, 4800, 4800, 4800, 4800, 4800, 15808, 15840, 4800, 4800, + 4800, 7872, 4800, 4800, 15872, 1792, 15456, 4800, 15904, 4800, 15936, + 15968, 1792, 1792, 16000, 1792, 1792, 1792, 16032, 1792, 10784, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, @@ -481,9 +481,8 @@ static const unsigned short pageMap[] = { 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 7616, - 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 7680, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, @@ -492,23 +491,24 @@ static const unsigned short pageMap[] = { 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 4032, 1344, - 1344, 1344, 1344, 1344, 1344, 11136, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1824, 1344, 1344, 1344, 1344, 1344, 1344, 11200, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 13792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, @@ -536,8 +536,8 @@ static const unsigned short pageMap[] = { 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, 1792, - 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, - 1344, 1344, 1344, 1344, 1344, 1344, 11136 + 1792, 1792, 1792, 1792, 1792, 1792, 1344, 1344, 1344, 1344, 1344, 1344, + 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 1344, 11200 #endif /* TCL_UTF_MAX > 3 */ }; @@ -582,328 +582,331 @@ static const unsigned char groupMap[] = { 73, 74, 21, 75, 76, 21, 77, 78, 21, 21, 76, 21, 79, 80, 21, 21, 81, 21, 21, 21, 21, 21, 21, 21, 82, 21, 21, 83, 21, 21, 83, 21, 21, 21, 84, 83, 85, 86, 86, 87, 21, 21, 21, 21, 21, 88, 21, 15, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 89, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 90, 11, 11, 11, 11, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 90, 90, 90, 90, 90, 11, 11, 11, 11, 11, 11, 11, 90, - 11, 90, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 92, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 23, 24, 23, - 24, 90, 11, 23, 24, 0, 0, 90, 42, 42, 42, 3, 93, 0, 0, 0, 0, 11, 11, - 94, 3, 95, 95, 95, 0, 96, 0, 97, 97, 21, 10, 10, 10, 10, 10, 10, 10, + 21, 21, 21, 21, 21, 89, 90, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 11, 11, 11, 11, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, + 11, 11, 11, 11, 91, 91, 91, 91, 91, 11, 11, 11, 11, 11, 11, 11, 91, + 11, 91, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, + 11, 11, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 93, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 23, 24, 23, + 24, 91, 11, 23, 24, 0, 0, 91, 42, 42, 42, 3, 94, 0, 0, 0, 0, 11, 11, + 95, 3, 96, 96, 96, 0, 97, 0, 98, 98, 21, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 0, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 98, 99, 99, 99, 21, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 100, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 101, 102, 102, 103, 104, 105, 106, 106, 106, 107, 108, 109, 23, - 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 23, 24, 110, 111, 112, 113, 114, 115, 7, 23, 24, 116, - 23, 24, 21, 54, 54, 54, 117, 117, 117, 117, 117, 117, 117, 117, 117, - 117, 117, 117, 117, 117, 117, 117, 10, 10, 10, 10, 10, 10, 10, 10, + 10, 10, 10, 99, 100, 100, 100, 21, 13, 13, 13, 13, 13, 13, 13, 13, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 101, 13, 13, 13, 13, 13, 13, 13, + 13, 13, 102, 103, 103, 104, 105, 106, 107, 107, 107, 108, 109, 110, + 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 23, 24, 23, 24, 23, 24, 111, 112, 113, 114, 115, 116, 7, 23, 24, + 117, 23, 24, 21, 54, 54, 54, 118, 118, 118, 118, 118, 118, 118, 118, + 118, 118, 118, 118, 118, 118, 118, 118, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 10, 10, 10, 10, 10, 10, 10, 10, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, - 111, 111, 111, 111, 111, 111, 23, 24, 14, 91, 91, 91, 91, 91, 118, - 118, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 23, 24, 119, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 120, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, - 24, 23, 24, 0, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, - 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, - 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 0, - 0, 90, 3, 3, 3, 3, 3, 3, 0, 122, 122, 122, 122, 122, 122, 122, 122, + 13, 13, 13, 13, 13, 13, 112, 112, 112, 112, 112, 112, 112, 112, 112, + 112, 112, 112, 112, 112, 112, 112, 23, 24, 14, 92, 92, 92, 92, 92, + 119, 119, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 23, 24, 23, 24, 23, 24, 120, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 23, 24, 23, 24, 121, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, + 23, 24, 23, 24, 0, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, - 122, 122, 21, 0, 3, 8, 0, 0, 14, 14, 4, 0, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 8, 91, 3, 91, 91, 3, 91, 91, 3, 91, 0, 0, 0, 0, + 0, 0, 91, 3, 3, 3, 3, 3, 3, 0, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 21, 0, 3, 8, 0, 0, 14, 14, 4, 0, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 8, 92, 3, 92, 92, 3, 92, 92, 3, 92, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 15, 15, 15, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 17, 17, 17, - 17, 17, 7, 7, 7, 3, 3, 4, 3, 3, 14, 14, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 3, 17, 0, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 17, 17, 7, 7, 7, 3, 3, 4, 3, 3, 14, 14, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 3, 17, 0, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 90, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 15, 15, 91, + 15, 15, 15, 15, 15, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 15, 15, 92, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 3, 15, 91, 91, 91, 91, 91, 91, 91, 17, 14, 91, 91, 91, 91, 91, - 91, 90, 90, 91, 91, 14, 91, 91, 91, 91, 15, 15, 9, 9, 9, 9, 9, 9, 9, + 15, 3, 15, 92, 92, 92, 92, 92, 92, 92, 17, 14, 92, 92, 92, 92, 92, + 92, 91, 91, 92, 92, 14, 92, 92, 92, 92, 15, 15, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 14, 14, 15, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 0, 17, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 3, 3, 0, 17, 15, 92, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 0, 15, 15, 15, 15, 15, + 15, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 15, 0, 0, 0, + 15, 15, 15, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 90, 90, 14, 3, 3, 3, 90, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 91, 91, 14, 3, 3, 3, 91, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 91, 91, 91, 91, 90, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 90, 91, 91, 91, 90, 91, 91, 91, 91, 91, 0, 0, 3, 3, 3, 3, 3, + 15, 15, 15, 15, 15, 92, 92, 92, 92, 91, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 91, 92, 92, 92, 91, 92, 92, 92, 92, 92, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, - 91, 91, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, + 92, 92, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 123, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 91, 15, 123, 123, - 123, 91, 91, 91, 91, 91, 91, 91, 91, 123, 123, 123, 123, 91, 123, 123, - 15, 91, 91, 91, 91, 91, 91, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 91, 91, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 90, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 123, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 0, 0, 15, 15, 15, 15, 0, 0, - 91, 15, 123, 123, 123, 91, 91, 91, 91, 0, 0, 123, 123, 0, 0, 123, 123, - 91, 15, 0, 0, 0, 0, 0, 0, 0, 0, 123, 0, 0, 0, 0, 15, 15, 0, 15, 15, - 15, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 4, 4, 18, 18, - 18, 18, 18, 18, 14, 4, 0, 0, 0, 0, 0, 91, 91, 123, 0, 15, 15, 15, 15, - 15, 15, 0, 0, 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 124, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 92, 15, 124, + 124, 124, 92, 92, 92, 92, 92, 92, 92, 92, 124, 124, 124, 124, 92, 124, + 124, 15, 92, 92, 92, 92, 92, 92, 92, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 92, 92, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 91, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 124, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 0, 0, 15, 15, 15, 15, + 0, 0, 92, 15, 124, 124, 124, 92, 92, 92, 92, 0, 0, 124, 124, 0, 0, + 124, 124, 92, 15, 0, 0, 0, 0, 0, 0, 0, 0, 124, 0, 0, 0, 0, 15, 15, + 0, 15, 15, 15, 92, 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, + 4, 4, 18, 18, 18, 18, 18, 18, 14, 4, 0, 0, 0, 0, 0, 92, 92, 124, 0, + 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 0, 15, 15, 0, 15, 15, 0, + 0, 92, 0, 124, 124, 124, 92, 92, 0, 0, 0, 0, 92, 92, 0, 0, 92, 92, + 92, 0, 0, 0, 92, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 15, 0, 0, + 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 92, 92, 15, 15, 15, 92, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 92, 124, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, - 15, 15, 15, 15, 0, 15, 15, 0, 15, 15, 0, 15, 15, 0, 0, 91, 0, 123, - 123, 123, 91, 91, 0, 0, 0, 0, 91, 91, 0, 0, 91, 91, 91, 0, 0, 0, 91, - 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 15, 0, 0, 0, 0, 0, 0, 0, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 91, 91, 15, 15, 15, 91, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 91, 91, 123, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 0, 15, 15, 15, 15, 15, 0, 0, 91, 15, 123, 123, 123, 91, - 91, 91, 91, 91, 0, 91, 91, 123, 0, 123, 123, 91, 0, 0, 15, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 91, 91, 0, 0, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 3, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 91, 123, 123, 0, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 0, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 0, - 15, 15, 15, 15, 15, 0, 0, 91, 15, 123, 91, 123, 91, 91, 91, 91, 0, - 0, 123, 123, 0, 0, 123, 123, 91, 0, 0, 0, 0, 0, 0, 0, 0, 91, 123, 0, - 0, 0, 0, 15, 15, 0, 15, 15, 15, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 14, 15, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 91, 15, 0, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 0, 15, 15, - 15, 15, 0, 0, 0, 15, 15, 0, 15, 0, 15, 15, 0, 0, 0, 15, 15, 0, 0, 0, - 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 0, 0, 0, 123, 123, 91, 123, 123, 0, 0, 0, 123, 123, 123, 0, 123, - 123, 123, 91, 0, 0, 15, 0, 0, 0, 0, 0, 0, 123, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 18, 18, 14, - 14, 14, 14, 14, 14, 4, 14, 0, 0, 0, 0, 0, 91, 123, 123, 123, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 15, 15, 0, 15, 15, 15, 15, 15, 0, 0, 92, 15, 124, + 124, 124, 92, 92, 92, 92, 92, 0, 92, 92, 124, 0, 124, 124, 92, 0, 0, + 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 92, 92, 0, + 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 4, 0, 0, 0, 0, 0, 0, 0, 15, 0, + 0, 0, 0, 0, 0, 0, 92, 124, 124, 0, 15, 15, 15, 15, 15, 15, 15, 15, + 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, + 15, 0, 15, 15, 0, 15, 15, 15, 15, 15, 0, 0, 92, 15, 124, 92, 124, 92, + 92, 92, 92, 0, 0, 124, 124, 0, 0, 124, 124, 92, 0, 0, 0, 0, 0, 0, 0, + 0, 92, 124, 0, 0, 0, 0, 15, 15, 0, 15, 15, 15, 92, 92, 0, 0, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 14, 15, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 92, 15, 0, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, + 15, 0, 15, 15, 15, 15, 0, 0, 0, 15, 15, 0, 15, 0, 15, 15, 0, 0, 0, + 15, 15, 0, 0, 0, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 0, 0, 0, 124, 124, 92, 124, 124, 0, 0, 0, 124, 124, + 124, 0, 124, 124, 124, 92, 0, 0, 15, 0, 0, 0, 0, 0, 0, 124, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, + 18, 18, 14, 14, 14, 14, 14, 14, 4, 14, 0, 0, 0, 0, 0, 92, 124, 124, + 124, 0, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 0, 15, 92, 92, 92, 124, 124, 124, 124, 0, 92, 92, + 92, 0, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 92, 92, 0, 15, 15, 15, + 0, 0, 0, 0, 0, 15, 15, 92, 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 0, 0, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 14, 0, 92, 124, + 124, 0, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, + 15, 15, 0, 0, 92, 15, 124, 92, 124, 124, 124, 124, 124, 0, 92, 124, + 124, 0, 124, 124, 92, 92, 0, 0, 0, 0, 0, 0, 0, 124, 124, 0, 0, 0, 0, + 0, 0, 0, 15, 0, 15, 15, 92, 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 0, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 0, 0, 15, 124, 124, 124, 92, 92, 92, 92, 0, 124, + 124, 124, 0, 124, 124, 124, 92, 15, 0, 0, 0, 0, 0, 0, 0, 0, 124, 0, + 0, 0, 0, 0, 0, 0, 15, 15, 15, 92, 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 18, 18, 18, 18, 18, 18, 0, 0, 0, 14, 15, 15, 15, 15, 15, 15, + 0, 0, 124, 124, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 0, 15, 15, 15, 15, 15, 15, + 15, 0, 0, 0, 92, 0, 0, 0, 0, 124, 124, 124, 92, 92, 92, 0, 92, 0, 124, + 124, 124, 124, 124, 124, 124, 124, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 0, 0, 124, 124, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 0, 0, 15, 91, 91, 91, 123, 123, 123, 123, 0, 91, 91, 91, 0, 91, - 91, 91, 91, 0, 0, 0, 0, 0, 0, 0, 91, 91, 0, 15, 15, 0, 0, 0, 0, 0, - 0, 15, 15, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, - 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 14, 0, 91, 123, 123, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 0, - 0, 91, 15, 123, 91, 123, 123, 123, 123, 123, 0, 91, 123, 123, 0, 123, - 123, 91, 91, 0, 0, 0, 0, 0, 0, 0, 123, 123, 0, 0, 0, 0, 0, 0, 0, 15, - 0, 15, 15, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 15, 15, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 0, 0, 15, 123, 123, 123, 91, 91, 91, 91, 0, 123, 123, 123, - 0, 123, 123, 123, 91, 15, 0, 0, 0, 0, 0, 0, 0, 0, 123, 0, 0, 0, 0, - 0, 0, 0, 0, 15, 15, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, - 18, 18, 18, 18, 18, 0, 0, 0, 14, 15, 15, 15, 15, 15, 15, 0, 0, 123, - 123, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 0, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 0, - 0, 91, 0, 0, 0, 0, 123, 123, 123, 91, 91, 91, 0, 91, 0, 123, 123, 123, - 123, 123, 123, 123, 123, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 0, 0, 123, 123, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 15, 15, 91, 91, - 91, 91, 91, 91, 91, 0, 0, 0, 0, 4, 15, 15, 15, 15, 15, 15, 90, 91, - 91, 91, 91, 91, 91, 91, 91, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, - 0, 0, 0, 0, 0, 15, 15, 0, 15, 0, 0, 15, 15, 0, 15, 0, 0, 15, 0, 0, - 0, 0, 0, 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, - 15, 0, 15, 0, 15, 0, 0, 15, 15, 0, 15, 15, 15, 15, 91, 15, 15, 91, - 91, 91, 91, 91, 91, 0, 91, 91, 15, 0, 0, 15, 15, 15, 15, 15, 0, 90, - 0, 91, 91, 91, 91, 91, 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, - 15, 15, 15, 15, 15, 14, 14, 14, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 14, 3, 14, 14, 14, 91, 91, 14, 14, 14, 14, 14, 14, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 14, 91, - 14, 91, 14, 91, 5, 6, 5, 6, 123, 123, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 0, 0, 0, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 123, 91, 91, 91, 91, 91, 3, 91, 91, 15, 15, 15, 15, 15, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 14, 14, - 14, 14, 14, 14, 14, 14, 91, 14, 14, 14, 14, 14, 14, 0, 14, 14, 3, 3, - 3, 3, 3, 14, 14, 14, 14, 3, 3, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 123, 123, 91, 91, 91, 91, 123, 91, 91, 91, 91, - 91, 91, 123, 91, 91, 123, 123, 91, 91, 15, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 3, 3, 3, 3, 3, 3, 15, 15, 15, 15, 15, 15, 123, 123, 91, 91, 15, - 15, 15, 15, 91, 91, 91, 15, 123, 123, 123, 15, 15, 123, 123, 123, 123, - 123, 123, 123, 15, 15, 15, 91, 91, 91, 91, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 91, 123, 123, 91, 91, 123, 123, 123, 123, - 123, 123, 91, 15, 123, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 123, 123, 123, - 91, 14, 14, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, - 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, - 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 0, - 124, 0, 0, 0, 0, 0, 124, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 15, + 15, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 4, 15, 15, 15, 15, 15, + 15, 91, 92, 92, 92, 92, 92, 92, 92, 92, 3, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 3, 3, 0, 0, 0, 0, 0, 15, 15, 0, 15, 0, 0, 15, 15, 0, 15, 0, 0, + 15, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, + 0, 15, 15, 15, 0, 15, 0, 15, 0, 0, 15, 15, 0, 15, 15, 15, 15, 92, 15, + 15, 92, 92, 92, 92, 92, 92, 0, 92, 92, 15, 0, 0, 15, 15, 15, 15, 15, + 0, 91, 0, 92, 92, 92, 92, 92, 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 0, 0, 15, 15, 15, 15, 15, 14, 14, 14, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 3, 3, 14, 3, 14, 14, 14, 92, 92, 14, 14, 14, 14, 14, 14, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 14, 92, 14, 92, 14, 92, 5, 6, 5, 6, 124, 124, 15, 15, 15, 15, 15, 15, + 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 0, 0, 0, 0, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 124, 92, 92, 92, 92, 92, 3, 92, 92, 15, 15, 15, + 15, 15, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0, + 14, 14, 14, 14, 14, 14, 14, 14, 92, 14, 14, 14, 14, 14, 14, 0, 14, + 14, 3, 3, 3, 3, 3, 14, 14, 14, 14, 3, 3, 0, 0, 0, 0, 0, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 92, 92, 92, 92, 124, 92, + 92, 92, 92, 92, 92, 124, 92, 92, 124, 124, 92, 92, 15, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 3, 3, 15, 15, 15, 15, 15, 15, 124, 124, + 92, 92, 15, 15, 15, 15, 92, 92, 92, 15, 124, 124, 124, 15, 15, 124, + 124, 124, 124, 124, 124, 124, 15, 15, 15, 92, 92, 92, 92, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 124, 92, 92, 124, + 124, 124, 124, 124, 124, 92, 15, 124, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 124, 124, 124, 92, 14, 14, 125, 125, 125, 125, 125, 125, 125, 125, + 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, + 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, + 125, 125, 0, 125, 0, 0, 0, 0, 0, 125, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 3, 90, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, - 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 15, 15, 15, 15, 0, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, - 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 15, 15, 15, + 15, 15, 15, 3, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 0, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, 15, + 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, - 0, 91, 91, 91, 3, 3, 3, 3, 3, 3, 3, 3, 3, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 8, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 0, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 0, + 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, + 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 0, 0, 92, 92, 92, 3, 3, 3, 3, 3, 3, 3, 3, 3, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, + 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 126, 126, + 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, + 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, + 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, + 126, 126, 126, 126, 104, 104, 104, 104, 104, 104, 0, 0, 110, 110, 110, + 110, 110, 110, 0, 0, 8, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, + 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 2, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 5, 6, 0, 0, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, 3, 3, 125, 125, 125, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, 3, 3, 127, 127, 127, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 91, 91, 91, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 3, 3, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 92, 92, 92, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 91, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 91, 91, 0, 0, + 15, 15, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 0, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, 123, 91, 91, 91, 91, - 91, 91, 91, 123, 123, 123, 123, 123, 123, 123, 123, 91, 123, 123, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 3, 3, 3, 90, 3, 3, 3, 4, 15, - 91, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 18, 18, 18, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 92, 124, 92, 92, 92, 92, + 92, 92, 92, 124, 124, 124, 124, 124, 124, 124, 124, 92, 124, 124, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 3, 3, 3, 91, 3, 3, 3, 4, 15, + 92, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 8, - 3, 3, 3, 3, 91, 91, 91, 17, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, - 0, 0, 0, 0, 15, 15, 15, 90, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 3, 3, 3, 3, 92, 92, 92, 17, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, + 0, 0, 0, 0, 15, 15, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 91, 15, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 92, 15, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 0, 91, 91, 91, 123, 123, 123, 123, 91, 91, 123, 123, - 123, 0, 0, 0, 0, 123, 123, 91, 123, 123, 123, 123, 123, 123, 91, 91, - 91, 0, 0, 0, 0, 14, 0, 0, 0, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, + 15, 15, 15, 15, 0, 92, 92, 92, 124, 124, 124, 124, 92, 92, 124, 124, + 124, 0, 0, 0, 0, 124, 124, 92, 124, 124, 124, 124, 124, 124, 92, 92, + 92, 0, 0, 0, 0, 14, 0, 0, 0, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 0, 0, 0, 0, 123, 123, 123, 123, 123, 123, 123, 123, - 123, 123, 123, 123, 123, 123, 123, 123, 123, 15, 15, 15, 15, 15, 15, - 15, 123, 123, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 0, - 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 15, 15, 15, 15, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, + 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 91, 91, 123, 123, 91, 0, 0, 3, 3, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 123, 91, 123, 91, 91, 91, 91, 91, 91, 91, 0, 91, 123, 91, 123, - 123, 91, 91, 91, 91, 91, 91, 91, 91, 123, 123, 123, 123, 123, 123, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 0, 91, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, - 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 90, 3, 3, 3, 3, 3, 3, 0, 0, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 118, 0, 91, 91, 91, 91, - 123, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 91, - 91, 91, 91, 91, 123, 91, 123, 123, 123, 123, 123, 91, 123, 123, 15, - 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, - 3, 3, 3, 3, 3, 3, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, - 91, 91, 123, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 123, - 91, 91, 91, 91, 123, 123, 91, 91, 123, 91, 91, 91, 15, 15, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 91, 123, 91, 91, 123, 123, 123, 91, 123, 91, 91, 91, 123, 123, 0, 0, - 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 15, 15, 15, 15, 123, 123, 123, 123, 123, - 123, 123, 123, 91, 91, 91, 91, 91, 91, 91, 91, 123, 123, 91, 91, 0, - 0, 0, 3, 3, 3, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 15, 15, - 15, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 90, 90, 90, 90, 90, 90, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 0, 0, 0, 0, 0, 0, 0, 0, 91, 91, 91, 3, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 123, 91, 91, 91, 91, 91, 91, 91, 15, 15, 15, - 15, 91, 15, 15, 15, 15, 123, 123, 91, 15, 15, 0, 91, 91, 0, 0, 0, 0, - 0, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 92, 92, 124, 124, 92, 0, 0, 3, 3, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 92, + 124, 92, 92, 92, 92, 92, 92, 92, 0, 92, 124, 92, 124, 124, 92, 92, + 92, 92, 92, 92, 92, 92, 124, 124, 124, 124, 124, 124, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 0, 0, 92, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, + 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 3, 3, + 3, 3, 3, 3, 3, 91, 3, 3, 3, 3, 3, 3, 0, 0, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 119, 0, 92, 92, 92, 92, 124, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 92, 92, 92, 92, + 92, 124, 92, 124, 124, 124, 124, 124, 92, 124, 124, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 3, + 3, 3, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 92, 92, 124, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 92, 92, 92, + 92, 124, 124, 92, 92, 124, 92, 92, 92, 15, 15, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 92, + 92, 124, 124, 124, 92, 124, 92, 92, 92, 124, 124, 0, 0, 0, 0, 0, 0, + 0, 0, 3, 3, 3, 3, 15, 15, 15, 15, 124, 124, 124, 124, 124, 124, 124, + 124, 92, 92, 92, 92, 92, 92, 92, 92, 124, 124, 92, 92, 0, 0, 0, 3, + 3, 3, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 15, 15, 15, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 91, 91, 91, 91, 91, 91, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 0, + 0, 0, 0, 0, 0, 0, 92, 92, 92, 3, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 124, 92, 92, 92, 92, 92, 92, 92, 15, 15, 15, 15, 92, + 15, 15, 15, 15, 124, 124, 92, 15, 15, 0, 92, 92, 0, 0, 0, 0, 0, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 90, 90, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 90, 126, 21, 21, 21, 127, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 90, 90, 90, 90, 90, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 0, 0, 0, 0, - 0, 91, 91, 91, 91, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 21, 21, 21, 21, 21, 128, 21, - 21, 129, 21, 130, 130, 130, 130, 130, 130, 130, 130, 131, 131, 131, - 131, 131, 131, 131, 131, 130, 130, 130, 130, 130, 130, 0, 0, 131, 131, - 131, 131, 131, 131, 0, 0, 130, 130, 130, 130, 130, 130, 130, 130, 131, - 131, 131, 131, 131, 131, 131, 131, 130, 130, 130, 130, 130, 130, 130, - 130, 131, 131, 131, 131, 131, 131, 131, 131, 130, 130, 130, 130, 130, - 130, 0, 0, 131, 131, 131, 131, 131, 131, 0, 0, 21, 130, 21, 130, 21, - 130, 21, 130, 0, 131, 0, 131, 0, 131, 0, 131, 130, 130, 130, 130, 130, - 130, 130, 130, 131, 131, 131, 131, 131, 131, 131, 131, 132, 132, 133, - 133, 133, 133, 134, 134, 135, 135, 136, 136, 137, 137, 0, 0, 130, 130, - 130, 130, 130, 130, 130, 130, 138, 138, 138, 138, 138, 138, 138, 138, - 130, 130, 130, 130, 130, 130, 130, 130, 138, 138, 138, 138, 138, 138, - 138, 138, 130, 130, 130, 130, 130, 130, 130, 130, 138, 138, 138, 138, - 138, 138, 138, 138, 130, 130, 21, 139, 21, 0, 21, 21, 131, 131, 140, - 140, 141, 11, 142, 11, 11, 11, 21, 139, 21, 0, 21, 21, 143, 143, 143, - 143, 141, 11, 11, 11, 130, 130, 21, 21, 0, 0, 21, 21, 131, 131, 144, - 144, 0, 11, 11, 11, 130, 130, 21, 21, 21, 112, 21, 21, 131, 131, 145, - 145, 116, 11, 11, 11, 0, 0, 21, 139, 21, 0, 21, 21, 146, 146, 147, - 147, 141, 11, 11, 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 17, 17, 17, 17, - 17, 8, 8, 8, 8, 8, 8, 3, 3, 16, 20, 5, 16, 16, 20, 5, 16, 3, 3, 3, - 3, 3, 3, 3, 3, 148, 149, 17, 17, 17, 17, 17, 2, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 16, 20, 3, 3, 3, 3, 12, 12, 3, 3, 3, 7, 5, 6, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 7, 3, 12, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 17, 17, - 17, 17, 17, 0, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 18, 90, 0, 0, - 18, 18, 18, 18, 18, 18, 7, 7, 7, 5, 6, 90, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 7, 7, 7, 5, 6, 0, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 0, 0, 0, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 118, 118, 118, 118, 91, 118, 118, 118, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 14, 14, 106, 14, 14, 14, 14, 106, 14, 14, 21, 106, 106, - 106, 21, 21, 106, 106, 106, 21, 14, 106, 14, 14, 7, 106, 106, 106, - 106, 106, 14, 14, 14, 14, 14, 14, 106, 14, 150, 14, 106, 14, 151, 152, - 106, 106, 14, 21, 106, 106, 153, 106, 21, 15, 15, 15, 15, 21, 14, 14, - 21, 21, 106, 106, 7, 7, 7, 7, 7, 106, 21, 21, 21, 21, 14, 7, 14, 14, - 154, 14, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 155, 155, 155, 155, 155, 155, 155, 155, 155, 155, 155, 155, 155, - 155, 155, 155, 156, 156, 156, 156, 156, 156, 156, 156, 156, 156, 156, - 156, 156, 156, 156, 156, 125, 125, 125, 23, 24, 125, 125, 125, 125, - 18, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, 7, 14, 14, 14, 14, 14, 7, 7, 14, - 14, 14, 14, 7, 14, 14, 7, 14, 14, 7, 14, 14, 14, 14, 14, 14, 14, 7, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 91, 91, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 91, 128, 21, 21, 21, 129, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 91, 91, 91, 91, 91, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 92, + 92, 92, 92, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, + 23, 24, 23, 24, 23, 24, 23, 24, 21, 21, 21, 21, 21, 130, 21, 21, 131, + 21, 132, 132, 132, 132, 132, 132, 132, 132, 133, 133, 133, 133, 133, + 133, 133, 133, 132, 132, 132, 132, 132, 132, 0, 0, 133, 133, 133, 133, + 133, 133, 0, 0, 132, 132, 132, 132, 132, 132, 132, 132, 133, 133, 133, + 133, 133, 133, 133, 133, 132, 132, 132, 132, 132, 132, 132, 132, 133, + 133, 133, 133, 133, 133, 133, 133, 132, 132, 132, 132, 132, 132, 0, + 0, 133, 133, 133, 133, 133, 133, 0, 0, 21, 132, 21, 132, 21, 132, 21, + 132, 0, 133, 0, 133, 0, 133, 0, 133, 132, 132, 132, 132, 132, 132, + 132, 132, 133, 133, 133, 133, 133, 133, 133, 133, 134, 134, 135, 135, + 135, 135, 136, 136, 137, 137, 138, 138, 139, 139, 0, 0, 132, 132, 132, + 132, 132, 132, 132, 132, 140, 140, 140, 140, 140, 140, 140, 140, 132, + 132, 132, 132, 132, 132, 132, 132, 140, 140, 140, 140, 140, 140, 140, + 140, 132, 132, 132, 132, 132, 132, 132, 132, 140, 140, 140, 140, 140, + 140, 140, 140, 132, 132, 21, 141, 21, 0, 21, 21, 133, 133, 142, 142, + 143, 11, 144, 11, 11, 11, 21, 141, 21, 0, 21, 21, 145, 145, 145, 145, + 143, 11, 11, 11, 132, 132, 21, 21, 0, 0, 21, 21, 133, 133, 146, 146, + 0, 11, 11, 11, 132, 132, 21, 21, 21, 113, 21, 21, 133, 133, 147, 147, + 117, 11, 11, 11, 0, 0, 21, 141, 21, 0, 21, 21, 148, 148, 149, 149, + 143, 11, 11, 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 17, 17, 17, 17, 17, + 8, 8, 8, 8, 8, 8, 3, 3, 16, 20, 5, 16, 16, 20, 5, 16, 3, 3, 3, 3, 3, + 3, 3, 3, 150, 151, 17, 17, 17, 17, 17, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 16, 20, 3, 3, 3, 3, 12, 12, 3, 3, 3, 7, 5, 6, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 7, 3, 12, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 17, 17, 17, + 17, 17, 0, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 18, 91, 0, 0, 18, + 18, 18, 18, 18, 18, 7, 7, 7, 5, 6, 91, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 7, 7, 7, 5, 6, 0, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, + 91, 91, 91, 0, 0, 0, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, + 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 119, 119, 119, 119, 92, 119, 119, 119, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 14, 14, 107, 14, 14, 14, 14, 107, 14, 14, 21, 107, 107, 107, + 21, 21, 107, 107, 107, 21, 14, 107, 14, 14, 7, 107, 107, 107, 107, + 107, 14, 14, 14, 14, 14, 14, 107, 14, 152, 14, 107, 14, 153, 154, 107, + 107, 14, 21, 107, 107, 155, 107, 21, 15, 15, 15, 15, 21, 14, 14, 21, + 21, 107, 107, 7, 7, 7, 7, 7, 107, 21, 21, 21, 21, 14, 7, 14, 14, 156, + 14, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, + 157, 157, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, + 158, 158, 158, 158, 127, 127, 127, 23, 24, 127, 127, 127, 127, 18, + 14, 14, 0, 0, 0, 0, 7, 7, 7, 7, 7, 14, 14, 14, 14, 14, 7, 7, 14, 14, + 14, 14, 7, 14, 14, 7, 14, 14, 7, 14, 14, 14, 14, 14, 14, 14, 7, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 7, 7, 14, 14, - 7, 14, 7, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 7, 7, 14, 14, 7, + 14, 7, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 14, 14, @@ -927,11 +930,11 @@ static const unsigned char groupMap[] = { 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 157, 157, 157, 157, 157, 157, 157, - 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, 157, - 157, 157, 157, 157, 157, 158, 158, 158, 158, 158, 158, 158, 158, 158, - 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, 158, - 158, 158, 158, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 14, 14, 14, 14, 14, 14, 14, 14, 159, 159, 159, 159, 159, 159, 159, + 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, + 159, 159, 159, 159, 159, 160, 160, 160, 160, 160, 160, 160, 160, 160, + 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, + 160, 160, 160, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 7, 14, 14, 14, 14, 14, 14, 14, 14, 14, 7, 14, 14, 14, 14, 14, 14, 14, 14, @@ -961,179 +964,182 @@ static const unsigned char groupMap[] = { 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, - 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, - 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, 121, - 121, 121, 121, 121, 121, 121, 0, 122, 122, 122, 122, 122, 122, 122, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, - 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 0, 23, - 24, 159, 160, 161, 162, 163, 23, 24, 23, 24, 23, 24, 164, 165, 166, - 167, 21, 23, 24, 21, 23, 24, 21, 21, 21, 21, 21, 90, 90, 168, 168, - 23, 24, 23, 24, 21, 14, 14, 14, 14, 14, 14, 23, 24, 23, 24, 91, 91, - 91, 23, 24, 0, 0, 0, 0, 0, 3, 3, 3, 3, 18, 3, 3, 169, 169, 169, 169, - 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, - 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, 169, - 169, 169, 169, 169, 169, 169, 0, 169, 0, 0, 0, 0, 0, 169, 0, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 90, 3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, - 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, - 3, 3, 16, 20, 16, 20, 3, 3, 3, 16, 20, 3, 16, 20, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 8, 3, 3, 8, 3, 16, 20, 3, 3, 16, 20, 5, 6, 5, 6, 5, 6, 5, - 6, 3, 3, 3, 3, 3, 90, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 8, 8, 3, 3, 3, - 3, 8, 3, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 0, 123, + 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, + 123, 123, 123, 123, 0, 23, 24, 161, 162, 163, 164, 165, 23, 24, 23, + 24, 23, 24, 166, 167, 168, 169, 21, 23, 24, 21, 23, 24, 21, 21, 21, + 21, 21, 91, 91, 170, 170, 23, 24, 23, 24, 21, 14, 14, 14, 14, 14, 14, + 23, 24, 23, 24, 92, 92, 92, 23, 24, 0, 0, 0, 0, 0, 3, 3, 3, 3, 18, + 3, 3, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, + 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, + 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 0, 171, 0, 0, + 0, 0, 0, 171, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, + 91, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, + 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, + 15, 15, 15, 15, 0, 3, 3, 16, 20, 16, 20, 3, 3, 3, 16, 20, 3, 16, 20, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 8, 3, 3, 8, 3, 16, 20, 3, 3, 16, 20, 5, + 6, 5, 6, 5, 6, 5, 6, 3, 3, 3, 3, 3, 91, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 8, 8, 3, 3, 3, 3, 8, 3, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 0, 0, 0, 0, 2, 3, 3, 3, 14, 90, 15, 125, 5, 6, 5, 6, 5, 6, - 5, 6, 5, 6, 14, 14, 5, 6, 5, 6, 5, 6, 5, 6, 8, 5, 6, 6, 14, 125, 125, - 125, 125, 125, 125, 125, 125, 125, 91, 91, 91, 91, 123, 123, 8, 90, - 90, 90, 90, 90, 14, 14, 125, 125, 125, 90, 15, 3, 14, 14, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 0, 91, 91, 11, 11, 90, 90, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 3, 90, 90, 90, 15, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 2, 3, 3, 3, 14, 91, 15, + 127, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 14, 14, 5, 6, 5, 6, 5, 6, 5, 6, + 8, 5, 6, 6, 14, 127, 127, 127, 127, 127, 127, 127, 127, 127, 92, 92, + 92, 92, 124, 124, 8, 91, 91, 91, 91, 91, 14, 14, 127, 127, 127, 91, + 15, 3, 14, 14, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 92, 92, 11, 11, 91, 91, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, 91, 91, 91, 15, 0, 0, + 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 14, 14, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 15, 15, 15, 15, 15, 15, 15, 0, 14, 14, 18, 18, 18, 18, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 14, 14, 14, - 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 14, 14, 14, 14, 14, 14, 14, 14, + 0, 0, 0, 0, 0, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 18, 18, 18, 18, - 18, 18, 18, 18, 14, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 90, 15, + 14, 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, 14, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 90, 3, 3, 3, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 15, 91, 118, 118, 118, 3, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 3, 90, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, - 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 90, - 90, 0, 91, 15, 15, 15, 15, 15, 15, 125, 125, 125, 125, 125, 125, 125, - 125, 125, 125, 91, 91, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 11, + 15, 15, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 3, 3, 3, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 15, 92, 119, 119, 119, 3, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 3, 91, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, + 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 91, 91, 92, 92, + 15, 15, 15, 15, 15, 15, 127, 127, 127, 127, 127, 127, 127, 127, 127, + 127, 92, 92, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 90, 90, 90, 90, 90, 90, 90, 90, 90, 11, 11, 23, - 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 21, 21, 23, 24, - 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, - 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 90, 21, 21, 21, 21, 21, - 21, 21, 21, 23, 24, 23, 24, 170, 23, 24, 23, 24, 23, 24, 23, 24, 23, - 24, 90, 11, 11, 23, 24, 171, 21, 0, 23, 24, 23, 24, 21, 21, 23, 24, + 11, 11, 11, 91, 91, 91, 91, 91, 91, 91, 91, 91, 11, 11, 23, 24, 23, + 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 21, 21, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, - 24, 172, 173, 174, 175, 0, 0, 176, 177, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 24, 23, 24, 23, 24, 23, 24, 23, 24, 91, 21, 21, 21, 21, 21, 21, 21, + 21, 23, 24, 23, 24, 172, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 91, + 11, 11, 23, 24, 173, 21, 15, 23, 24, 23, 24, 21, 21, 23, 24, 23, 24, + 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 23, 24, 174, + 175, 176, 177, 0, 0, 178, 179, 180, 181, 23, 24, 23, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 15, 90, 90, 21, 15, 15, 15, 15, 15, 15, 15, 91, 15, - 15, 15, 91, 15, 15, 15, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 123, 123, 91, - 91, 123, 14, 14, 14, 14, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 14, 14, - 4, 14, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, - 0, 123, 123, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, - 123, 123, 123, 123, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 15, 15, 15, 15, 15, 15, 3, - 3, 3, 15, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 91, - 91, 91, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 123, 123, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 123, 91, - 91, 91, 91, 123, 123, 91, 123, 123, 123, 123, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 0, 90, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, - 3, 3, 15, 15, 15, 15, 15, 91, 90, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 91, 123, 123, 91, 91, 123, - 123, 91, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 91, 15, 15, 15, - 15, 15, 15, 15, 15, 91, 123, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, - 0, 3, 3, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 90, 15, 15, 15, 15, 15, 15, 14, 14, 14, 15, 123, 91, 123, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 91, 15, 91, 91, 91, 15, 15, 91, 91, 15, 15, 15, 15, 15, 91, 91, - 15, 91, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 15, 15, 90, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 123, 91, 91, 123, 123, 3, 3, 15, 90, 90, 123, 91, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, - 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, - 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 21, 21, 21, + 0, 0, 0, 0, 15, 91, 91, 21, 15, 15, 15, 15, 15, 15, 15, 92, 15, 15, + 15, 92, 15, 15, 15, 15, 92, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 92, 92, + 124, 14, 14, 14, 14, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 14, 14, 4, + 14, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, + 124, 124, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, + 124, 124, 124, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 15, 15, 15, 15, 15, 15, 3, 3, 3, + 15, 3, 15, 0, 0, 15, 15, 15, 15, 15, 15, 92, 92, 92, 92, 92, 92, 92, + 92, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 124, 124, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 124, 92, 92, + 92, 92, 124, 124, 92, 124, 124, 124, 124, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 0, 91, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 3, 3, + 15, 15, 15, 15, 15, 92, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 92, 92, 92, 92, 92, 92, 124, 124, 92, 92, 124, 124, + 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 92, 15, 15, 15, 15, + 15, 15, 15, 15, 92, 124, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, + 3, 3, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 91, 15, 15, 15, 15, 15, 15, 14, 14, 14, 15, 124, 92, 124, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 92, 15, 92, 92, 92, 15, 15, 92, 92, 15, 15, 15, 15, 15, 92, 92, 15, + 92, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 15, 15, 91, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 124, 92, 92, 124, 124, 3, 3, 15, 91, 91, 124, 92, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, + 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, + 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 11, 90, 90, 90, 90, 0, 0, 0, 0, 21, 21, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 15, 15, 15, 123, 123, 91, 123, 123, 91, 123, 123, 3, 123, 91, - 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, - 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, - 0, 0, 0, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, - 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, - 178, 178, 178, 178, 178, 178, 179, 179, 179, 179, 179, 179, 179, 179, - 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, - 179, 179, 179, 179, 179, 179, 179, 179, 179, 179, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 182, 21, 21, 21, + 21, 21, 21, 21, 11, 91, 91, 91, 91, 21, 21, 21, 21, 21, 21, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, + 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, + 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, + 183, 183, 183, 183, 183, 183, 183, 183, 183, 183, 15, 15, 15, 124, + 124, 92, 124, 124, 92, 124, 124, 3, 124, 92, 0, 0, 9, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 184, 184, 184, + 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, + 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, 184, + 184, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, + 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, 185, + 185, 185, 185, 185, 185, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 21, + 21, 21, 21, 21, 21, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 21, + 21, 21, 21, 0, 0, 0, 0, 0, 15, 92, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 7, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, + 15, 15, 15, 15, 0, 15, 0, 15, 15, 0, 15, 15, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, + 11, 11, 11, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 6, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 0, 0, 0, 0, 0, 0, 21, 21, 21, 21, 21, 21, 21, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 21, 21, 21, 21, 21, 0, 0, 0, 0, 0, 15, 91, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 7, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 0, 15, 0, 15, 15, 0, 15, - 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 4, + 14, 0, 0, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 3, 3, 3, 3, 3, 3, 3, 5, 6, 3, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 3, 8, 8, 12, 12, 5, + 6, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 3, 3, 5, 6, 3, 3, 3, 3, + 12, 12, 12, 3, 3, 3, 0, 3, 3, 3, 3, 8, 5, 6, 5, 6, 5, 6, 3, 3, 3, 7, + 8, 7, 7, 7, 0, 3, 4, 3, 3, 0, 0, 0, 0, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 6, - 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 17, 0, 3, 3, 3, 4, 3, 3, 3, 5, 6, 3, 7, 3, 8, 3, + 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, 7, 7, 7, 3, 11, 13, 13, 13, + 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, + 13, 13, 13, 13, 13, 13, 5, 7, 6, 7, 5, 6, 3, 5, 6, 3, 3, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 4, 14, 0, 0, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 3, 3, 3, 3, 3, 3, 3, 5, 6, - 3, 0, 0, 0, 0, 0, 0, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 0, 0, 3, 8, 8, 12, 12, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6, - 5, 6, 5, 6, 3, 3, 5, 6, 3, 3, 3, 3, 12, 12, 12, 3, 3, 3, 0, 3, 3, 3, - 3, 8, 5, 6, 5, 6, 5, 6, 3, 3, 3, 7, 8, 7, 7, 7, 0, 3, 4, 3, 3, 0, 0, - 0, 0, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 17, 0, 3, 3, - 3, 4, 3, 3, 3, 5, 6, 3, 7, 3, 8, 3, 3, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 3, 3, 7, 7, 7, 3, 11, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 5, 7, 6, 7, - 5, 6, 3, 5, 6, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 90, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 90, 90, 0, 0, 15, 15, 15, 15, - 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, - 0, 0, 15, 15, 15, 0, 0, 0, 4, 4, 7, 11, 14, 4, 4, 0, 14, 7, 7, 7, 7, - 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 17, 17, 14, 14, 0, 0 + 15, 15, 91, 91, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 15, + 15, 15, 0, 0, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 15, 0, 0, 0, 4, + 4, 7, 11, 14, 4, 4, 0, 14, 7, 7, 7, 7, 14, 14, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 17, 17, 17, 14, 14, 0, 0 #if TCL_UTF_MAX > 3 ,15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, @@ -1144,10 +1150,10 @@ static const unsigned char groupMap[] = { 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, - 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, - 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, - 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 18, + 14, 14, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, + 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, + 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, + 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 18, 18, 18, 18, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 18, 18, 14, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -1155,25 +1161,25 @@ static const unsigned char groupMap[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 91, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 91, 18, + 14, 14, 92, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 125, 15, 15, 15, 15, 15, 15, 15, 15, - 125, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 127, 15, 15, 15, 15, 15, 15, 15, 15, + 127, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 3, 15, 15, - 15, 15, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 3, 125, 125, 125, - 125, 125, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 180, 180, 180, 180, 180, 180, - 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, - 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, 180, - 180, 180, 180, 180, 180, 180, 181, 181, 181, 181, 181, 181, 181, 181, - 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, - 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, - 181, 181, 181, 181, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 3, 127, 127, 127, + 127, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 186, 186, 186, 186, 186, 186, + 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, + 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, 186, + 186, 186, 186, 186, 186, 186, 187, 187, 187, 187, 187, 187, 187, 187, + 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, + 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, 187, + 187, 187, 187, 187, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -1190,236 +1196,262 @@ static const unsigned char groupMap[] = { 15, 15, 15, 15, 15, 15, 15, 15, 15, 14, 14, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 18, 18, - 18, 18, 18, 18, 0, 0, 0, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, - 0, 0, 0, 0, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 15, 15, - 15, 91, 91, 91, 0, 91, 91, 0, 0, 0, 0, 0, 91, 91, 91, 91, 15, 15, 15, - 15, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, - 0, 91, 91, 91, 0, 0, 0, 0, 91, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, - 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 18, 18, 3, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 18, 18, 18, 15, 15, 15, 15, 15, - 15, 15, 15, 14, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, - 0, 0, 0, 0, 18, 18, 18, 18, 18, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 0, 0, 0, + 0, 0, 18, 18, 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 18, 18, 18, 18, 18, 18, + 0, 0, 0, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, - 0, 18, 18, 18, 18, 18, 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 3, 3, - 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 18, 18, 15, 15, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 15, 92, 92, 92, 0, 92, 92, + 0, 0, 0, 0, 0, 92, 92, 92, 92, 15, 15, 15, 15, 0, 15, 15, 15, 0, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 92, 92, 92, 0, 0, 0, + 0, 92, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, + 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 18, 18, 3, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, 14, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 92, 0, 0, 0, 0, 18, 18, 18, + 18, 18, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 18, 18, + 18, 18, 18, 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, + 18, 18, 18, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 97, + 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, + 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, + 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 102, 102, 102, 102, 102, 102, 102, + 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, + 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, + 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, + 102, 102, 0, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 0, 123, 91, 123, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 124, 92, 124, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 91, 91, 91, 91, 91, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 123, 123, 123, 91, 91, 91, 91, 123, 123, 91, 91, 3, 3, 17, 3, 3, - 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, - 0, 0, 0, 0, 91, 91, 91, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 3, 3, 3, + 3, 3, 3, 3, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 18, 18, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 124, 92, 92, 92, + 92, 124, 124, 92, 92, 3, 3, 17, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 92, 92, 92, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 123, 91, 91, 91, - 91, 91, 91, 91, 91, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 3, 3, 15, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 123, 123, 123, 91, 91, 91, 91, 91, 91, 91, 91, 91, - 123, 123, 15, 15, 15, 15, 3, 3, 3, 3, 0, 0, 0, 0, 3, 0, 0, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 15, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 123, 123, - 123, 91, 91, 91, 123, 123, 91, 123, 91, 91, 3, 3, 3, 3, 3, 3, 0, 0, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 123, - 123, 91, 91, 91, 91, 91, 91, 91, 91, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 91, 123, 123, 123, 123, 0, 0, 123, - 123, 0, 0, 123, 123, 123, 0, 0, 0, 0, 0, 0, 0, 0, 0, 123, 0, 0, 0, - 0, 0, 15, 15, 15, 15, 15, 123, 123, 0, 0, 91, 91, 91, 91, 91, 91, 91, - 0, 0, 0, 91, 91, 91, 91, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 123, 123, 123, - 91, 91, 91, 91, 91, 91, 123, 91, 123, 123, 123, 123, 91, 91, 123, 91, - 91, 15, 15, 3, 15, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 92, 92, 92, 92, 92, 124, 92, 92, 92, 92, 92, 92, 92, 92, 0, 9, 9, 9, + 9, 9, 9, 9, 9, 9, 9, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 92, 3, 3, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 124, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 124, 124, 15, 15, 15, 15, 3, 3, + 3, 3, 3, 92, 92, 92, 3, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, 3, + 15, 3, 3, 3, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 124, 92, 92, 92, 124, 124, + 92, 124, 92, 92, 3, 3, 3, 3, 3, 3, 0, 0, 15, 15, 15, 15, 15, 15, 15, + 0, 15, 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 3, 0, + 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 92, 124, 124, 124, 92, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 9, + 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 92, 92, 124, 124, 0, 15, + 15, 15, 15, 15, 15, 15, 15, 0, 0, 15, 15, 0, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, 124, 124, 124, 0, 0, 124, + 124, 0, 0, 124, 124, 124, 0, 0, 15, 0, 0, 0, 0, 0, 0, 124, 0, 0, 0, + 0, 0, 15, 15, 15, 15, 15, 124, 124, 0, 0, 92, 92, 92, 92, 92, 92, 92, + 0, 0, 0, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 124, + 92, 92, 92, 92, 92, 92, 124, 92, 124, 124, 124, 124, 92, 92, 124, 92, + 92, 15, 15, 3, 15, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 123, 123, 123, 91, 91, 91, 91, 0, 0, 123, 123, 123, - 123, 91, 91, 123, 91, 91, 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 123, 123, 123, 91, - 91, 91, 91, 91, 91, 91, 91, 123, 123, 91, 123, 91, 91, 3, 3, 3, 15, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, - 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 123, 91, - 123, 123, 91, 91, 91, 91, 91, 91, 123, 91, 0, 0, 0, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 124, 124, 124, 92, 92, 92, 92, 0, 0, 124, 124, 124, + 124, 92, 92, 124, 92, 92, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 15, 15, 15, 15, 92, 92, 0, 0, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 124, 124, 124, + 92, 92, 92, 92, 92, 92, 92, 92, 124, 124, 92, 124, 92, 92, 3, 3, 3, + 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, + 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 92, 124, + 92, 124, 124, 92, 92, 92, 92, 92, 92, 124, 92, 0, 0, 0, 0, 0, 0, 0, + 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 92, 92, 92, 124, 124, + 92, 92, 92, 92, 124, 92, 92, 92, 92, 92, 0, 0, 0, 0, 9, 9, 9, 9, 9, + 9, 9, 9, 9, 9, 18, 18, 3, 3, 3, 14, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 13, 13, + 10, 10, 10, 10, 10, 10, 10, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, - 0, 0, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, 125, - 125, 125, 0, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, + 13, 13, 13, 13, 13, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 127, 127, 127, 127, 127, 127, + 127, 127, 127, 127, 127, 127, 127, 127, 127, 0, 3, 3, 3, 3, 3, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, - 0, 0, 0, 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 91, 91, 91, - 91, 91, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 91, 91, 91, 91, 91, 91, 91, 3, - 3, 3, 3, 3, 14, 14, 14, 14, 90, 90, 90, 90, 3, 14, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 18, 18, 18, 18, 18, 18, - 18, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 15, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, - 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, - 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, - 123, 123, 123, 123, 123, 123, 123, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 91, 91, 91, 91, 90, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 90, 90, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, - 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 14, - 91, 91, 3, 17, 17, 17, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, - 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 123, 123, 91, 91, 91, - 14, 14, 14, 123, 123, 123, 123, 123, 123, 17, 17, 17, 17, 17, 17, 17, - 17, 91, 91, 91, 91, 91, 91, 91, 91, 14, 14, 91, 91, 91, 91, 91, 91, - 91, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 91, 91, 91, - 91, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 0, 0, 0, 0, 3, 3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 0, 0, 92, 92, 92, 92, 92, 3, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 92, 92, 92, 92, 92, 92, 92, 3, 3, 3, 3, 3, 14, 14, 14, 14, 91, 91, + 91, 91, 3, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, + 9, 9, 0, 18, 18, 18, 18, 18, 18, 18, 0, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, + 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, + 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 124, 124, 124, 124, + 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, + 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, + 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, 91, + 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 91, 15, 15, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 0, 0, 14, 92, 92, 3, 17, 17, 17, 17, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 14, 14, 14, 14, 14, 14, 14, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 14, - 14, 91, 91, 91, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 21, 21, 21, 21, 21, + 14, 14, 14, 124, 124, 92, 92, 92, 14, 14, 14, 124, 124, 124, 124, 124, + 124, 17, 17, 17, 17, 17, 17, 17, 17, 92, 92, 92, 92, 92, 92, 92, 92, + 14, 14, 92, 92, 92, 92, 92, 92, 92, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 92, 92, 92, 92, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 14, 14, 92, 92, 92, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 21, 21, 21, 21, 21, 21, 21, 0, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 106, - 0, 106, 106, 0, 0, 106, 0, 0, 106, 106, 0, 0, 106, 106, 106, 106, 0, - 106, 106, 106, 106, 106, 106, 106, 106, 21, 21, 21, 21, 0, 21, 0, 21, - 21, 21, 21, 21, 21, 21, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 21, 21, 21, 21, 21, 21, 21, 0, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 106, 106, 0, 106, 106, 106, 106, 0, - 0, 106, 106, 106, 106, 106, 106, 106, 106, 0, 106, 106, 106, 106, 106, - 106, 106, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 106, 106, 0, 106, 106, - 106, 106, 0, 106, 106, 106, 106, 106, 0, 106, 0, 0, 0, 106, 106, 106, - 106, 106, 106, 106, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 107, 0, 107, 107, 0, 0, 107, 0, 0, 107, 107, 0, 0, + 107, 107, 107, 107, 0, 107, 107, 107, 107, 107, 107, 107, 107, 21, + 21, 21, 21, 0, 21, 0, 21, 21, 21, 21, 21, 21, 21, 0, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, 0, + 107, 107, 107, 107, 0, 0, 107, 107, 107, 107, 107, 107, 107, 107, 0, + 107, 107, 107, 107, 107, 107, 107, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 106, 106, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 21, 21, 21, + 21, 107, 107, 0, 107, 107, 107, 107, 0, 107, 107, 107, 107, 107, 0, + 107, 0, 0, 0, 107, 107, 107, 107, 107, 107, 107, 0, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 21, 21, 21, 21, 21, 21, 0, 0, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 7, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 7, 21, 21, 21, 21, 21, 21, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 7, - 21, 21, 21, 21, 21, 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 21, + 21, 21, 21, 21, 21, 0, 0, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 7, 21, 21, 21, 21, 21, - 21, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 7, 21, + 21, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 21, 21, 21, 21, 21, 7, 21, 21, 21, 21, 21, 21, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, - 106, 106, 106, 106, 106, 106, 106, 106, 7, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 7, 21, 21, 21, 21, 21, 21, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, - 21, 21, 7, 21, 21, 21, 21, 21, 21, 106, 21, 0, 0, 9, 9, 9, 9, 9, 9, + 21, 21, 7, 21, 21, 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 7, 21, 21, + 21, 21, 21, 21, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, + 7, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, + 21, 21, 21, 21, 21, 21, 21, 21, 21, 7, 21, 21, 21, 21, 21, 21, 107, + 21, 0, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 15, - 15, 15, 15, 15, 0, 0, 18, 18, 18, 18, 18, 18, 18, 18, 18, 91, 91, 91, - 91, 91, 91, 91, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 0, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 0, 15, 0, 0, 15, 0, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 15, 0, 15, - 0, 0, 0, 0, 0, 0, 15, 0, 0, 0, 0, 15, 0, 15, 0, 15, 0, 15, 15, 15, - 0, 15, 15, 0, 15, 0, 0, 15, 0, 15, 0, 15, 0, 15, 0, 15, 0, 15, 15, - 0, 15, 0, 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 0, 15, - 15, 15, 15, 0, 15, 15, 15, 15, 0, 15, 0, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 0, 0, 0, 0, 0, 15, 15, 15, 0, 15, 15, 15, 15, 15, 0, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 7, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 0, 0, 0, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 14, - 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, + 9, 9, 9, 9, 9, 9, 9, 9, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 14, 14, 14, 14, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, + 14, 14, 14, 14, 14, 14, 14, 14, 92, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 92, 14, 14, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 92, 92, 92, 92, 92, 0, 92, 92, 92, 92, 92, + 92, 92, 92, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 15, 15, 15, 15, 15, 0, 0, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 92, 92, 92, 92, 92, 92, 92, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, + 15, 0, 15, 0, 0, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, + 15, 15, 15, 15, 0, 15, 0, 15, 0, 0, 0, 0, 0, 0, 15, 0, 0, 0, 0, 15, + 0, 15, 0, 15, 0, 15, 15, 15, 0, 15, 15, 0, 15, 0, 0, 15, 0, 15, 0, + 15, 0, 15, 0, 15, 0, 15, 15, 0, 15, 0, 0, 15, 15, 15, 15, 0, 15, 15, + 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 15, 15, 15, 15, 0, 15, 0, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 15, 15, + 15, 0, 15, 15, 15, 15, 15, 0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, + 15, 15, 15, 15, 15, 15, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 7, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 18, 18, 18, 18, 18, 18, 18, 18, + 18, 18, 18, 18, 18, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, - 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 14, 14, + 14, 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, - 0, 0, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, + 14, 0, 0, 0, 0, 0, 0, 0, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 11, 11, 11, 11, 11, 14, + 14, 14, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, - 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, - 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, - 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 0, 0, 0, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, + 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 0, + 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, + 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 14, 14, + 14, 14, 0, 0, 0, 0, 0, 0, 0, 14, 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 #endif /* TCL_UTF_MAX > 3 */ }; @@ -1450,18 +1482,19 @@ static const int groups[] = { -2759550, -2760062, 53890, 52866, 52610, 51842, 52098, -10833534, -10832510, 53122, -10823550, -10830718, 53634, 54146, -2750078, -10829950, -2751614, 54658, 54914, -2745982, 55938, -10824062, - 17794, 55682, 18306, 56194, -10817918, 4, 6, -21370, 29761, 9793, - 9537, 16449, 16193, 9858, 9602, 8066, 16514, 16258, 2113, 16002, - 14722, 1, 12162, 13954, 2178, 22146, 20610, -1662, 29826, -15295, - 24706, -1727, 20545, 7, 3905, 3970, 12353, 12418, 8, 1859649, - 10, -9044862, -976254, 15234, -1949375, -1918, -1983, -18814, - -21886, -25470, -32638, -28542, -32126, -1981, -2174, -18879, - -2237, 1844610, -21951, -25535, -28607, -32703, -32191, 13, 14, - -1924287, -2145983, -2115007, 7233, 7298, 4170, 4234, 6749, 6813, - -2750143, -976319, -2746047, 2763650, 2762882, -2759615, -2751679, - -2760383, -2760127, -2768575, 1859714, -9044927, -10823615, -10830783, - -10833599, -10832575, -10830015, -10817983, -10824127, 18, 17, - 10305, 10370 + 17794, 55682, 18306, 56194, -10818686, -10817918, 4, 6, -21370, + 29761, 9793, 9537, 16449, 16193, 9858, 9602, 8066, 16514, 16258, + 2113, 16002, 14722, 1, 12162, 13954, 2178, 22146, 20610, -1662, + 29826, -15295, 24706, -1727, 20545, 7, 3905, 3970, 12353, 12418, + 8, 1859649, 9949249, 10, -9044862, -976254, 15234, -1949375, -1918, + -1983, -18814, -21886, -25470, -32638, -28542, -32126, -1981, + -2174, -18879, -2237, 1844610, -21951, -25535, -28607, -32703, + -32191, 13, 14, -1924287, -2145983, -2115007, 7233, 7298, 4170, + 4234, 6749, 6813, -2750143, -976319, -2746047, 2763650, 2762882, + -2759615, -2751679, -2760383, -2760127, -2768575, 1859714, -9044927, + -10823615, -10830783, -10833599, -10832575, -10830015, -10817983, + -10824127, -10818751, 237633, 237698, 9949314, 18, 17, 10305, + 10370 }; #if TCL_UTF_MAX > 3 @@ -1523,4 +1556,8 @@ enum { * Unicode character tables. */ -#define GetUniCharInfo(ch) (groups[groupMap[pageMap[((ch) & 0xffff) >> OFFSET_BITS] | ((ch) & ((1 << OFFSET_BITS)-1))]]) +#if TCL_UTF_MAX > 3 +# define GetUniCharInfo(ch) (groups[groupMap[pageMap[((ch) & 0x1fffff) >> OFFSET_BITS] | ((ch) & ((1 << OFFSET_BITS)-1))]]) +#else +# define GetUniCharInfo(ch) (groups[groupMap[pageMap[((ch) & 0xffff) >> OFFSET_BITS] | ((ch) & ((1 << OFFSET_BITS)-1))]]) +#endif diff --git a/generic/tclUtf.c b/generic/tclUtf.c index 15529c7..b878149 100644 --- a/generic/tclUtf.c +++ b/generic/tclUtf.c @@ -117,19 +117,10 @@ UtfCount( if (ch <= 0x7FF) { return 2; } - if (ch <= 0xFFFF) { - return 3; - } #if TCL_UTF_MAX > 3 - if (ch <= 0x1FFFFF) { + if ((ch > 0xFFFF) && (ch <= 0x10FFFF)) { return 4; } - if (ch <= 0x3FFFFFF) { - return 5; - } - if (ch <= 0x7FFFFFFF) { - return 6; - } #endif return 3; } @@ -172,6 +163,23 @@ Tcl_UniCharToUtf( return 2; } if (ch <= 0xFFFF) { +#if TCL_UTF_MAX == 4 + if ((ch & 0xF800) == 0xD800) { + if (ch & 0x0400) { + /* Low surrogate */ + buf[3] = (char) ((ch | 0x80) & 0xBF); + buf[2] |= (char) (((ch >> 6) | 0x80) & 0x8F); + return 4; + } else { + /* High surrogate */ + ch += 0x40; + buf[2] = (char) (((ch << 4) | 0x80) & 0xB0); + buf[1] = (char) (((ch >> 2) | 0x80) & 0xBF); + buf[0] = (char) (((ch >> 8) | 0xF0) & 0xF7); + return 0; + } + } +#endif three: buf[2] = (char) ((ch | 0x80) & 0xBF); buf[1] = (char) (((ch >> 6) | 0x80) & 0xBF); @@ -180,30 +188,13 @@ Tcl_UniCharToUtf( } #if TCL_UTF_MAX > 3 - if (ch <= 0x1FFFFF) { + if (ch <= 0x10FFFF) { buf[3] = (char) ((ch | 0x80) & 0xBF); buf[2] = (char) (((ch >> 6) | 0x80) & 0xBF); buf[1] = (char) (((ch >> 12) | 0x80) & 0xBF); buf[0] = (char) ((ch >> 18) | 0xF0); return 4; } - if (ch <= 0x3FFFFFF) { - buf[4] = (char) ((ch | 0x80) & 0xBF); - buf[3] = (char) (((ch >> 6) | 0x80) & 0xBF); - buf[2] = (char) (((ch >> 12) | 0x80) & 0xBF); - buf[1] = (char) (((ch >> 18) | 0x80) & 0xBF); - buf[0] = (char) ((ch >> 24) | 0xF8); - return 5; - } - if (ch <= 0x7FFFFFFF) { - buf[5] = (char) ((ch | 0x80) & 0xBF); - buf[4] = (char) (((ch >> 6) | 0x80) & 0xBF); - buf[3] = (char) (((ch >> 12) | 0x80) & 0xBF); - buf[2] = (char) (((ch >> 18) | 0x80) & 0xBF); - buf[1] = (char) (((ch >> 24) | 0x80) & 0xBF); - buf[0] = (char) ((ch >> 30) | 0xFC); - return 6; - } #endif } @@ -1365,6 +1356,11 @@ int Tcl_UniCharIsAlnum( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return (((ALPHA_BITS | DIGIT_BITS) >> GetCategory(ch)) & 1); } @@ -1388,6 +1384,11 @@ int Tcl_UniCharIsAlpha( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return ((ALPHA_BITS >> GetCategory(ch)) & 1); } @@ -1411,6 +1412,18 @@ int Tcl_UniCharIsControl( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + ch &= 0x1fffff; + if ((ch == 0xe0001) || ((ch >= 0xe0020) && (ch <= 0xe007f))) { + return 1; + } + if ((ch >= 0xf0000) && ((ch & 0xffff) <= 0xfffd)) { + return 1; + } + return 0; + } +#endif return ((CONTROL_BITS >> GetCategory(ch)) & 1); } @@ -1434,6 +1447,11 @@ int Tcl_UniCharIsDigit( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return (GetCategory(ch) == DECIMAL_DIGIT_NUMBER); } @@ -1457,6 +1475,12 @@ int Tcl_UniCharIsGraph( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + ch &= 0x1fffff; + return (ch >= 0xe0100) && (ch <= 0xe01ef); + } +#endif return ((GRAPH_BITS >> GetCategory(ch)) & 1); } @@ -1480,6 +1504,11 @@ int Tcl_UniCharIsLower( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return (GetCategory(ch) == LOWERCASE_LETTER); } @@ -1503,6 +1532,12 @@ int Tcl_UniCharIsPrint( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + ch &= 0x1fffff; + return (ch >= 0xe0100) && (ch <= 0xe01ef); + } +#endif return (((GRAPH_BITS|SPACE_BITS) >> GetCategory(ch)) & 1); } @@ -1526,6 +1561,11 @@ int Tcl_UniCharIsPunct( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return ((PUNCT_BITS >> GetCategory(ch)) & 1); } @@ -1549,16 +1589,27 @@ int Tcl_UniCharIsSpace( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + /* Ignore upper 11 bits. */ + ch &= 0x1fffff; +#else + /* Ignore upper 16 bits. */ + ch &= 0xffff; +#endif + /* * If the character is within the first 127 characters, just use the * standard C function, otherwise consult the Unicode table. */ - if (((Tcl_UniChar) ch) < ((Tcl_UniChar) 0x80)) { + if (ch < 0x80) { return TclIsSpaceProc((char) ch); - } else if ((Tcl_UniChar) ch == 0x0085 || (Tcl_UniChar) ch == 0x180e - || (Tcl_UniChar) ch == 0x200b || (Tcl_UniChar) ch == 0x2060 - || (Tcl_UniChar) ch == 0x202f || (Tcl_UniChar) ch == 0xfeff) { +#if TCL_UTF_MAX > 3 + } else if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; +#endif + } else if (ch == 0x0085 || ch == 0x180e || ch == 0x200b + || ch == 0x202f || ch == 0x2060 || ch == 0xfeff) { return 1; } else { return ((SPACE_BITS >> GetCategory(ch)) & 1); @@ -1585,6 +1636,11 @@ int Tcl_UniCharIsUpper( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return (GetCategory(ch) == UPPERCASE_LETTER); } @@ -1608,6 +1664,11 @@ int Tcl_UniCharIsWordChar( int ch) /* Unicode character to test. */ { +#if TCL_UTF_MAX > 3 + if (UNICODE_OUT_OF_RANGE(ch)) { + return 0; + } +#endif return ((WORD_BITS >> GetCategory(ch)) & 1); } diff --git a/generic/tclUtil.c b/generic/tclUtil.c index 64589a2..8de0267 100644 --- a/generic/tclUtil.c +++ b/generic/tclUtil.c @@ -82,7 +82,7 @@ static ProcessGlobalValue executableName = { * in other cases this means an overestimate of the * required size. * - * For more details, see the comments on the Tcl*Scan*Element and + * For more details, see the comments on the Tcl*Scan*Element and * Tcl*Convert*Element routines. */ @@ -180,7 +180,7 @@ const Tcl_ObjType tclEndOffsetType = { * * NOTE: This means that if and when backslash substitution rules ever change * for command parsing, the interpretation of strings as lists also changes. - * + * * Backslash substitution replaces an "escape sequence" of one or more * characters starting with * \u005c \ BACKSLASH @@ -193,7 +193,7 @@ const Tcl_ObjType tclEndOffsetType = { * * * If the first character of a formatted substring is * \u007b { OPEN BRACE - * then the end of the substring is the matching + * then the end of the substring is the matching * \u007d } CLOSE BRACE * character, where matching is determined by counting nesting levels, and * not including any brace characters that are contained within a backslash @@ -215,7 +215,7 @@ const Tcl_ObjType tclEndOffsetType = { * includes an unbalanced brace not in a backslash escape sequence, and any * value that ends with a backslash not itself in a backslash escape * sequence. - * + * * * If the first character of a formatted substring is * \u0022 " QUOTE * then the end of the substring is the next QUOTE character, not counting @@ -342,7 +342,7 @@ const Tcl_ObjType tclEndOffsetType = { * directives. This makes it easy to experiment with eliminating this * formatting mode simply with "#define COMPAT 0" above. I believe this is * worth considering. - * + * * Another consideration is the treatment of QUOTE characters in list * elements. TclConvertElement() must have the ability to produce the escape * sequence \" so that when a list element begins with a QUOTE we do not @@ -402,7 +402,7 @@ TclMaxListLength( * No list element before leading white space. */ - count += 1 - TclIsSpaceProc(*bytes); + count += 1 - TclIsSpaceProc(*bytes); /* * Count white space runs as potential element separators. @@ -438,7 +438,7 @@ TclMaxListLength( * No list element following trailing white space. */ - count -= TclIsSpaceProc(bytes[-1]); + count -= TclIsSpaceProc(bytes[-1]); done: if (endPtr) { @@ -506,7 +506,7 @@ TclFindElement( * indicate that the substring of *sizePtr * bytes starting at **elementPtr is/is not * the literal list element and therefore - * does not/does require a call to + * does not/does require a call to * TclCopyAndCollapse() by the caller. */ { return FindElement(interp, list, listLength, "list", "LIST", elementPtr, @@ -535,7 +535,7 @@ TclFindDictElement( * indicate that the substring of *sizePtr * bytes starting at **elementPtr is/is not * the literal key or value and therefore - * does not/does require a call to + * does not/does require a call to * TclCopyAndCollapse() by the caller. */ { return FindElement(interp, dict, dictLength, "dict", "DICTIONARY", @@ -567,7 +567,7 @@ FindElement( * indicate that the substring of *sizePtr * bytes starting at **elementPtr is/is not * the literal list/dict element and therefore - * does not/does require a call to + * does not/does require a call to * TclCopyAndCollapse() by the caller. */ { const char *p = string; @@ -582,7 +582,7 @@ FindElement( /* * Skim off leading white space and check for an opening brace or quote. - * We treat embedded NULLs in the list/dict as bytes belonging to a list + * We treat embedded NULLs in the list/dict as bytes belonging to a list * element (or dictionary key or value). */ @@ -1034,7 +1034,7 @@ TclScanElement( int preferBrace = 0; /* CONVERT_MASK mode. */ int braceCount = 0; /* Count of all braces '{' '}' seen. */ #endif /* COMPAT */ - + if ((p == NULL) || (length == 0) || ((*p == '\0') && (length == -1))) { /* * Empty string element must be brace quoted. @@ -1112,7 +1112,7 @@ TclScanElement( * Final backslash. Cannot format with brace quoting. */ - requireEscape = 1; + requireEscape = 1; break; } if (p[1] == '\n') { @@ -1506,7 +1506,7 @@ TclConvertElement( return p - dst; } - /* + /* * If we reach this point, there's an embedded NULL in the string * range being processed, which should not happen when the * encoding rules for Tcl strings are properly followed. If the @@ -1882,7 +1882,7 @@ Tcl_Concat( for (p = result, i = 0; i < argc; i++) { int trim, elemLength; const char *element; - + element = argv[i]; elemLength = strlen(argv[i]); @@ -2014,12 +2014,12 @@ Tcl_ConcatObj( */ TclNewObj(resPtr); - Tcl_AttemptSetObjLength(resPtr, bytesNeeded + objc - 1); + (void) Tcl_AttemptSetObjLength(resPtr, bytesNeeded + objc - 1); Tcl_SetObjLength(resPtr, 0); for (i = 0; i < objc; i++) { int trim; - + element = TclGetStringFromObj(objv[i], &elemLength); /* @@ -3003,7 +3003,7 @@ TclDStringToObj( /* * Static buffer, so must copy. */ - + TclNewStringObj(result, dsPtr->string, dsPtr->length); } } else { @@ -3121,7 +3121,7 @@ Tcl_PrintDouble( /* * Handle NaN. */ - + if (TclIsNaN(value)) { TclFormatNaN(value, dst); return; @@ -3130,12 +3130,12 @@ Tcl_PrintDouble( /* * Handle infinities. */ - + if (TclIsInfinite(value)) { /* * Remember to copy the terminating NUL too. */ - + if (value < 0) { memcpy(dst, "-Inf", 5); } else { @@ -3147,7 +3147,7 @@ Tcl_PrintDouble( /* * Ordinary (normal and denormal) values. */ - + if (*precisionPtr == 0) { digits = TclDoubleDigits(value, -1, TCL_DD_SHORTEST, &exponent, &signum, &end); @@ -3192,7 +3192,7 @@ Tcl_PrintDouble( */ digits = TclDoubleDigits(value, *precisionPtr, - TCL_DD_E_FORMAT /* | TCL_DD_SHORTEN_FLAG */, + TCL_DD_E_FORMAT /* | TCL_DD_SHORTEN_FLAG */, &exponent, &signum, &end); } if (signum) { @@ -3203,7 +3203,7 @@ Tcl_PrintDouble( /* * E format for numbers < 1e-3 or >= 1e17. */ - + *dst++ = *p++; c = *p; if (c != '\0') { @@ -3228,7 +3228,7 @@ Tcl_PrintDouble( /* * F format for others. */ - + if (exponent < 0) { *dst++ = '0'; } diff --git a/generic/tclVar.c b/generic/tclVar.c index 0228a2c..451ef7b 100644 --- a/generic/tclVar.c +++ b/generic/tclVar.c @@ -215,9 +215,9 @@ static Tcl_SetFromAnyProc PanicOnSetVarName; * Types of Tcl_Objs used to cache variable lookups. * * localVarName - INTERNALREP DEFINITION: - * ptrAndLongRep.ptr: pointer to name obj in varFramePtr->localCache + * twoPtrValue.ptr1: pointer to name obj in varFramePtr->localCache * or NULL if it is this same obj - * ptrAndLongRep.value: index into locals table + * twoPtrValue.ptr2: index into locals table * * nsVarName - INTERNALREP DEFINITION: * twoPtrValue.ptr1: pointer to the namespace containing the reference @@ -235,25 +235,6 @@ static const Tcl_ObjType localVarNameType = { FreeLocalVarName, DupLocalVarName, PanicOnUpdateVarName, PanicOnSetVarName }; -/* - * Caching of namespace variables disabled: no simple way was found to avoid - * interfering with the resolver's idea of variable existence. A cached - * varName may keep a variable's name in the namespace's hash table, which is - * the resolver's criterion for existence (see test namespace-17.10). - */ - -#define ENABLE_NS_VARNAME_CACHING 0 - -#if ENABLE_NS_VARNAME_CACHING -static Tcl_FreeInternalRepProc FreeNsVarName; -static Tcl_DupInternalRepProc DupNsVarName; - -static const Tcl_ObjType tclNsVarNameType = { - "namespaceVarName", - FreeNsVarName, DupNsVarName, PanicOnUpdateVarName, PanicOnSetVarName -}; -#endif - static const Tcl_ObjType tclParsedVarNameType = { "parsedVarName", FreeParsedVarName, DupParsedVarName, UpdateParsedVarName, PanicOnSetVarName @@ -554,32 +535,15 @@ TclObjLookupVarEx( const Tcl_ObjType *typePtr = part1Ptr->typePtr; const char *errMsg = NULL; CallFrame *varFramePtr = iPtr->varFramePtr; -#if ENABLE_NS_VARNAME_CACHING - Namespace *nsPtr; -#endif const char *part2 = part2Ptr? TclGetString(part2Ptr):NULL; char *newPart2 = NULL; - *arrayPtrPtr = NULL; -#if ENABLE_NS_VARNAME_CACHING - if (varFramePtr) { - nsPtr = varFramePtr->nsPtr; - } else { - /* - * Some variables in the global ns have to be initialized before the - * root call frame is in place. - */ - - nsPtr = NULL; - } -#endif - if (typePtr == &localVarNameType) { int localIndex; localVarNameTypeHandling: - localIndex = (int) part1Ptr->internalRep.ptrAndLongRep.value; + localIndex = PTR2INT(part1Ptr->internalRep.twoPtrValue.ptr2); if (HasLocalVars(varFramePtr) && !(flags & (TCL_GLOBAL_ONLY | TCL_NAMESPACE_ONLY)) && (localIndex < varFramePtr->numCompiledLocals)) { @@ -587,7 +551,7 @@ TclObjLookupVarEx( * Use the cached index if the names coincide. */ - Tcl_Obj *namePtr = part1Ptr->internalRep.ptrAndLongRep.ptr; + Tcl_Obj *namePtr = part1Ptr->internalRep.twoPtrValue.ptr1; Tcl_Obj *checkNamePtr = localName(iPtr->varFramePtr, localIndex); if ((!namePtr && (checkNamePtr == part1Ptr)) || @@ -597,44 +561,6 @@ TclObjLookupVarEx( } } goto doneParsing; -#if ENABLE_NS_VARNAME_CACHING - } else if (typePtr == &tclNsVarNameType) { - int useGlobal, useReference; - Namespace *cachedNsPtr = part1Ptr->internalRep.twoPtrValue.ptr1; - varPtr = part1Ptr->internalRep.twoPtrValue.ptr2; - - useGlobal = (cachedNsPtr == iPtr->globalNsPtr) && ( - (flags & TCL_GLOBAL_ONLY) || - (part1[0]==':' && part1[1]==':') || - (!HasLocalVars(varFramePtr) && (nsPtr==iPtr->globalNsPtr))); - - useReference = useGlobal || ((cachedNsPtr == nsPtr) && ( - (flags & TCL_NAMESPACE_ONLY) || - (!HasLocalVars(varFramePtr) && !(flags & TCL_GLOBAL_ONLY) && - /* - * Careful: an undefined ns variable could be hiding a valid - * global reference. - */ - !TclIsVarUndefined(varPtr)))); - - if (useReference && !TclIsVarDeadHash(varPtr)) { - /* - * A straight global or namespace reference, use it. It isn't so - * simple to deal with 'implicit' namespace references, i.e., - * those where the reference could be to either a namespace or a - * global variable. Those we lookup again. - * - * If TclIsVarDeadHash(varPtr), this might be a reference to a - * variable in a deleted namespace, kept alive by e.g. part1Ptr. - * We could conceivably be so unlucky that a new namespace was - * created at the same address as the deleted one, so to be safe - * we test for a valid hPtr. - */ - - goto donePart1; - } - goto doneParsing; -#endif } /* @@ -674,7 +600,7 @@ TclObjLookupVarEx( } part1 = TclGetStringFromObj(part1Ptr, &len1); - if (!parsed && (*(part1 + len1 - 1) == ')')) { + if (!parsed && len1 && (*(part1 + len1 - 1) == ')')) { /* * part1Ptr is possibly an unparsed array element. */ @@ -774,28 +700,14 @@ TclObjLookupVarEx( part1Ptr->typePtr = &localVarNameType; if (part1Ptr != localName(iPtr->varFramePtr, index)) { - part1Ptr->internalRep.ptrAndLongRep.ptr = + part1Ptr->internalRep.twoPtrValue.ptr1 = localName(iPtr->varFramePtr, index); Tcl_IncrRefCount((Tcl_Obj *) - part1Ptr->internalRep.ptrAndLongRep.ptr); + part1Ptr->internalRep.twoPtrValue.ptr1); } else { - part1Ptr->internalRep.ptrAndLongRep.ptr = NULL; + part1Ptr->internalRep.twoPtrValue.ptr1 = NULL; } - part1Ptr->internalRep.ptrAndLongRep.value = (long) index; -#if ENABLE_NS_VARNAME_CACHING - } else if (index > -3) { - /* - * A cacheable namespace or global variable. - */ - - Namespace *nsPtr; - - nsPtr = ((index == -1) ? iPtr->globalNsPtr : varFramePtr->nsPtr); - varPtr->refCount++; - part1Ptr->typePtr = &tclNsVarNameType; - part1Ptr->internalRep.twoPtrValue.ptr1 = nsPtr; - part1Ptr->internalRep.twoPtrValue.ptr2 = varPtr; -#endif + part1Ptr->internalRep.twoPtrValue.ptr2 = INT2PTR(index); } else { /* * At least mark part1Ptr as already parsed. @@ -807,18 +719,6 @@ TclObjLookupVarEx( } donePart1: -#if 0 /* ENABLE_NS_VARNAME_CACHING perhaps? */ - if (varPtr == NULL) { - if (flags & TCL_LEAVE_ERR_MSG) { - part1 = TclGetString(part1Ptr); - TclObjVarErrMsg(interp, part1Ptr, part2Ptr, msg, - "cached variable reference is NULL.", -1); - Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "VARNAME", - TclGetString(part1Ptr), NULL); - } - return NULL; - } -#endif while (TclIsVarLink(varPtr)) { varPtr = varPtr->value.linkPtr; } @@ -1605,7 +1505,7 @@ Tcl_SetVar( Tcl_Obj *varValuePtr, *varNamePtr = Tcl_NewStringObj(varName, -1); Tcl_IncrRefCount(varNamePtr); - varValuePtr = Tcl_ObjSetVar2(interp, varNamePtr, NULL, + varValuePtr = Tcl_ObjSetVar2(interp, varNamePtr, NULL, Tcl_NewStringObj(newValue, -1), flags); Tcl_DecrRefCount(varNamePtr); @@ -1912,17 +1812,6 @@ TclPtrSetVar( varPtr->value.objPtr = NULL; } if (flags & (TCL_APPEND_VALUE|TCL_LIST_ELEMENT)) { -#if 0 /* ENABLE_NS_VARNAME_CACHING perhaps? */ - /* - * Can't happen now! - */ - - if (TclIsVarUndefined(varPtr) && (oldValuePtr != NULL)) { - TclDecrRefCount(oldValuePtr); /* Discard old value. */ - varPtr->value.objPtr = NULL; - oldValuePtr = NULL; - } -#endif if (flags & TCL_LIST_ELEMENT) { /* Append list element. */ if (oldValuePtr == NULL) { TclNewObj(oldValuePtr); @@ -2149,7 +2038,7 @@ TclPtrIncrObjVar( if (Tcl_IsShared(varValuePtr)) { /* Copy on write */ varValuePtr = Tcl_DuplicateObj(varValuePtr); - + if (TCL_OK == TclIncrObj(interp, varValuePtr, incrPtr)) { return TclPtrSetVar(interp, varPtr, arrayPtr, part1Ptr, part2Ptr, varValuePtr, flags, index); @@ -2388,18 +2277,6 @@ TclPtrUnsetVar( } } -#if ENABLE_NS_VARNAME_CACHING - /* - * Try to avoid keeping the Var struct allocated due to a tclNsVarNameType - * keeping a reference. This removes some additional exteriorisations of - * [Bug 736729], but may be a good thing independently of the bug. - */ - - if (part1Ptr->typePtr == &tclNsVarNameType) { - TclFreeIntRep(part1Ptr); - } -#endif - /* * Finally, if the variable is truly not in use then free up its Var * structure and remove it from its hash table, if any. The ref count of @@ -2517,8 +2394,8 @@ UnsetVarStruct( tracePtr = NULL; if (TclIsVarTraced(&dummyVar)) { tPtr = Tcl_FindHashEntry(&iPtr->varTraces, &dummyVar); - tracePtr = Tcl_GetHashValue(tPtr); if (tPtr) { + tracePtr = Tcl_GetHashValue(tPtr); Tcl_DeleteHashEntry(tPtr); } } @@ -4463,7 +4340,7 @@ TclPtrMakeUpvar( } /* Callers must Incr myNamePtr if they plan to Decr it. */ - + int TclPtrObjMakeUpvar( Tcl_Interp *interp, /* Interpreter containing variables. Used for @@ -5663,16 +5540,16 @@ PanicOnSetVarName( * localVarName - * * INTERNALREP DEFINITION: - * ptrAndLongRep.ptr: pointer to name obj in varFramePtr->localCache + * twoPtrValue.ptr1: pointer to name obj in varFramePtr->localCache * or NULL if it is this same obj - * ptrAndLongRep.value: index into locals table + * twoPtrValue.ptr2: index into locals table */ static void FreeLocalVarName( Tcl_Obj *objPtr) { - Tcl_Obj *namePtr = objPtr->internalRep.ptrAndLongRep.ptr; + Tcl_Obj *namePtr = objPtr->internalRep.twoPtrValue.ptr1; if (namePtr) { Tcl_DecrRefCount(namePtr); @@ -5685,60 +5562,19 @@ DupLocalVarName( Tcl_Obj *srcPtr, Tcl_Obj *dupPtr) { - Tcl_Obj *namePtr = srcPtr->internalRep.ptrAndLongRep.ptr; + Tcl_Obj *namePtr = srcPtr->internalRep.twoPtrValue.ptr1; if (!namePtr) { namePtr = srcPtr; } - dupPtr->internalRep.ptrAndLongRep.ptr = namePtr; + dupPtr->internalRep.twoPtrValue.ptr1 = namePtr; Tcl_IncrRefCount(namePtr); - dupPtr->internalRep.ptrAndLongRep.value = - srcPtr->internalRep.ptrAndLongRep.value; + dupPtr->internalRep.twoPtrValue.ptr2 = + srcPtr->internalRep.twoPtrValue.ptr2; dupPtr->typePtr = &localVarNameType; } -#if ENABLE_NS_VARNAME_CACHING -/* - * nsVarName - - * - * INTERNALREP DEFINITION: - * twoPtrValue.ptr1: pointer to the namespace containing the reference. - * twoPtrValue.ptr2: pointer to the corresponding Var - */ - -static void -FreeNsVarName( - Tcl_Obj *objPtr) -{ - register Var *varPtr = objPtr->internalRep.twoPtrValue.ptr2; - - if (TclIsVarInHash(varPtr)) { - varPtr->refCount--; - if (TclIsVarUndefined(varPtr) && (varPtr->refCount == 0)) { - CleanupVar(varPtr, NULL); - } - } - objPtr->typePtr = NULL; -} - -static void -DupNsVarName( - Tcl_Obj *srcPtr, - Tcl_Obj *dupPtr) -{ - Namespace *nsPtr = srcPtr->internalRep.twoPtrValue.ptr1; - register Var *varPtr = srcPtr->internalRep.twoPtrValue.ptr2; - - dupPtr->internalRep.twoPtrValue.ptr1 = nsPtr; - dupPtr->internalRep.twoPtrValue.ptr2 = varPtr; - if (TclIsVarInHash(varPtr)) { - varPtr->refCount++; - } - dupPtr->typePtr = &tclNsVarNameType; -} -#endif - /* * parsedVarName - * @@ -6528,11 +6364,10 @@ CompareVarKeys( /* * If the object pointers are the same then they match. - */ + * OPT: this comparison was moved to the caller - if (objPtr1 == objPtr2) { - return 1; - } + if (objPtr1 == objPtr2) return 1; + */ /* * Don't use Tcl_GetStringFromObj as it would prevent l1 and l2 being in a diff --git a/generic/tclZlib.c b/generic/tclZlib.c index 956e3f9..44dd9e0 100644 --- a/generic/tclZlib.c +++ b/generic/tclZlib.c @@ -1534,7 +1534,7 @@ Tcl_ZlibDeflate( if (!interp) { return TCL_ERROR; } - + /* * Compressed format is specified by the wbits parameter. See zlib.h for * details. @@ -1757,6 +1757,7 @@ Tcl_ZlibInflate( if (headerPtr) { e = inflateGetHeader(&stream, headerPtr); if (e != Z_OK) { + inflateEnd(&stream); goto error; } } @@ -1780,7 +1781,7 @@ Tcl_ZlibInflate( if ((stream.avail_in == 0) && (stream.avail_out > 0)) { e = Z_STREAM_ERROR; - goto error; + break; } newBufferSize = bufferSize + 5 * stream.avail_in; if (newBufferSize == bufferSize) { diff --git a/library/clock.tcl b/library/clock.tcl index 67d15b1..8e4b657 100644 --- a/library/clock.tcl +++ b/library/clock.tcl @@ -19,7 +19,7 @@ # access to the Registry on Windows systems. uplevel \#0 { - package require msgcat 1.4 + package require msgcat 1.6 if { $::tcl_platform(platform) eq {windows} } { if { [catch { package require registry 1.1 }] } { namespace eval ::tcl::clock [list variable NoRegistry {}] @@ -60,6 +60,8 @@ namespace eval ::tcl::clock { namespace import ::msgcat::mcload namespace import ::msgcat::mclocale + namespace import ::msgcat::mc + namespace import ::msgcat::mcpackagelocale } @@ -106,6 +108,11 @@ proc ::tcl::clock::Initialize {} { } InitTZData + mcpackagelocale set {} + ::msgcat::mcpackageconfig set mcfolder [file join $LibDir msgs] + ::msgcat::mcpackageconfig set unknowncmd "" + ::msgcat::mcpackageconfig set changecmd ChangeCurrentLocale + # Define the message catalog for the root locale. ::msgcat::mcmset {} { @@ -249,7 +256,6 @@ proc ::tcl::clock::Initialize {} { # Define the directories for time zone data and message catalogs. variable DataDir [file join $LibDir tzdata] - variable MsgDir [file join $LibDir msgs] # Number of days in the months, in common years and leap years. @@ -623,11 +629,6 @@ proc ::tcl::clock::Initialize {} { # in the given locales and dictionaries # mapping the numerals to their numeric # values. - variable McLoaded {}; # Dictionary whose keys are locales - # in which [mcload] has been executed - # and whose values are second-level - # dictionaries indexed by message - # name and giving message text. # variable CachedSystemTimeZone; # If 'CachedSystemTimeZone' exists, # it contains the value of the # system time zone, as determined from @@ -659,6 +660,7 @@ proc ::tcl::clock::Initialize {} { #---------------------------------------------------------------------- proc ::tcl::clock::format { args } { + variable FormatProc variable TZData @@ -692,6 +694,7 @@ proc ::tcl::clock::format { args } { } return [$procName $clockval $timezone] + } #---------------------------------------------------------------------- @@ -710,13 +713,14 @@ proc ::tcl::clock::format { args } { #---------------------------------------------------------------------- proc ::tcl::clock::ParseClockFormatFormat {procName format locale} { + if {[namespace which $procName] ne {}} { return $procName } # Map away the locale-dependent composite format groups - EnterLocale $locale oldLocale + EnterLocale $locale # Change locale if a fresh locale has been given on the command line. @@ -725,12 +729,6 @@ proc ::tcl::clock::ParseClockFormatFormat {procName format locale} { } trap CLOCK {result opts} { dict unset opts -errorinfo return -options $opts $result - } finally { - # Restore the locale - - if { [info exists oldLocale] } { - mclocale $oldLocale - } } } @@ -1181,6 +1179,7 @@ proc ::tcl::clock::ParseClockFormatFormat2 {format locale procName} { #---------------------------------------------------------------------- proc ::tcl::clock::scan { args } { + set format {} # Check the count of args @@ -1264,7 +1263,7 @@ proc ::tcl::clock::scan { args } { # Change locale if a fresh locale has been given on the command line. - EnterLocale $locale oldLocale + EnterLocale $locale try { # Map away the locale-dependent composite format groups @@ -1273,15 +1272,8 @@ proc ::tcl::clock::scan { args } { return [$scanner $string $base $timezone] } trap CLOCK {result opts} { # Conceal location of generation of expected errors - dict unset opts -errorinfo return -options $opts $result - } finally { - # Restore the locale - - if { [info exists oldLocale] } { - mclocale $oldLocale - } } } @@ -1304,6 +1296,7 @@ proc ::tcl::clock::scan { args } { #---------------------------------------------------------------------- proc ::tcl::clock::FreeScan { string base timezone locale } { + variable TZData # Get the data for time changes in the given zone @@ -1431,6 +1424,7 @@ proc ::tcl::clock::FreeScan { string base timezone locale } { set date2 [ConvertLocalToUTC $date2[set date2 {}] $TZData($timezone) \ 2361222] set seconds [dict get $date2 seconds] + } # Do relative month @@ -2155,6 +2149,7 @@ proc ::tcl::clock::UniquePrefixRegexp { data } { proc ::tcl::clock::MakeUniquePrefixRegexp { successors uniquePrefixMapping prefixString } { + # Get the characters that may follow the current prefix string set schars [lsort -ascii [dict keys [dict get $successors $prefixString]]] @@ -2224,6 +2219,7 @@ proc ::tcl::clock::MakeUniquePrefixRegexp { successors #---------------------------------------------------------------------- proc ::tcl::clock::MakeParseCodeFromFields { dateFields parseActions } { + set currPrio 999 set currFieldPos [list] set currCodeBurst { @@ -2297,26 +2293,16 @@ proc ::tcl::clock::MakeParseCodeFromFields { dateFields parseActions } { # # Parameters: # locale -- Desired locale -# oldLocaleVar -- Name of a variable in caller's scope that -# tracks the previous locale name. # # Results: # Returns the locale that was previously current. # # Side effects: -# Does [mclocale]. If necessary, uses [mcload] to load the designated -# locale's files, and tracks that it has done so in the 'McLoaded' -# variable. +# Does [mclocale]. If necessary, loades the designated locale's files. # #---------------------------------------------------------------------- -proc ::tcl::clock::EnterLocale { locale oldLocaleVar } { - upvar 1 $oldLocaleVar oldLocale - - variable MsgDir - variable McLoaded - - set oldLocale [mclocale] +proc ::tcl::clock::EnterLocale { locale } { if { $locale eq {system} } { if { $::tcl_platform(platform) ne {windows} } { # On a non-windows platform, the 'system' locale is the same as @@ -2329,33 +2315,22 @@ proc ::tcl::clock::EnterLocale { locale oldLocaleVar } { # Control Panel. First, load the 'current' locale if it's not yet # loaded - if {![dict exists $McLoaded $oldLocale] } { - mcload $MsgDir - dict set McLoaded $oldLocale {} - } + mcpackagelocale set [mclocale] # Make a new locale string for the system locale, and get the # Control Panel information - set locale ${oldLocale}_windows - if { ![dict exists $McLoaded $locale] } { + set locale [mclocale]_windows + if { ! [mcpackagelocale present $locale] } { LoadWindowsDateTimeFormats $locale - dict set McLoaded $locale {} } } } if { $locale eq {current}} { - set locale $oldLocale - unset oldLocale - } elseif { $locale eq $oldLocale } { - unset oldLocale - } else { - mclocale $locale - } - if { ![dict exists $McLoaded $locale] } { - mcload $MsgDir - dict set McLoaded $locale {} + set locale [mclocale] } + # Eventually load the locale + mcpackagelocale set $locale } #---------------------------------------------------------------------- @@ -2482,6 +2457,7 @@ proc ::tcl::clock::LoadWindowsDateTimeFormats { locale } { } return + } #---------------------------------------------------------------------- @@ -2505,13 +2481,13 @@ proc ::tcl::clock::LoadWindowsDateTimeFormats { locale } { #---------------------------------------------------------------------- proc ::tcl::clock::LocalizeFormat { locale format } { - variable McLoaded - if { [dict exists $McLoaded $locale FORMAT $format] } { - return [dict get $McLoaded $locale FORMAT $format] - } - set inFormat $format + # message catalog key to cache this format + set key FORMAT_$format + if { [::msgcat::mcexists -exactlocale -exactnamespace $key] } { + return [mc $key] + } # Handle locale-dependent format groups by mapping them out of the format # string. Note that the order of the [string map] operations is # significant because later formats can refer to later ones; for example @@ -2534,7 +2510,7 @@ proc ::tcl::clock::LocalizeFormat { locale format } { lappend list %Ec [string map $list [mc LOCALE_DATE_TIME_FORMAT]] set format [string map $list $format] - dict set McLoaded $locale FORMAT $inFormat $format + ::msgcat::mcset $locale $key $format return $format } @@ -3133,7 +3109,6 @@ proc ::tcl::clock::SetupTimeZone { timezone } { -errorcode [list CLOCK badTimeZone $timezone] \ "time zone \"$timezone\" not found" } - } elseif { ![catch {ParsePosixTimeZone $timezone} tzfields] } { # This looks like a POSIX time zone - try to process it @@ -3901,6 +3876,7 @@ proc ::tcl::clock::ProcessPosixTimeZone { z } { #---------------------------------------------------------------------- proc ::tcl::clock::DeterminePosixDSTTime { z bound y } { + variable FEB_28 # Determine the start or end day of DST @@ -3908,6 +3884,7 @@ proc ::tcl::clock::DeterminePosixDSTTime { z bound y } { set date [dict create era CE year $y] set doy [dict get $z ${bound}DayOfYear] if { $doy ne {} } { + # Time was specified as a day of the year if { [dict get $z ${bound}J] ne {} @@ -4319,7 +4296,7 @@ proc ::tcl::clock::add { clockval args } { set timezone :GMT } - EnterLocale $locale oldLocale + EnterLocale $locale set changeover [mc GREGORIAN_CHANGE_DATE] @@ -4371,12 +4348,6 @@ proc ::tcl::clock::add { clockval args } { # Conceal the innards of [clock] when it's an expected error dict unset opts -errorinfo return -options $opts $result - } finally { - # Restore the locale - - if { [info exists oldLocale] } { - mclocale $oldLocale - } } } @@ -4449,6 +4420,7 @@ proc ::tcl::clock::AddMonths { months clockval timezone changeover } { $changeover] return [dict get $date seconds] + } #---------------------------------------------------------------------- @@ -4499,38 +4471,42 @@ proc ::tcl::clock::AddDays { days clockval timezone changeover } { $changeover] return [dict get $date seconds] + } #---------------------------------------------------------------------- # -# mc -- +# ChangeCurrentLocale -- # -# Wrapper around ::msgcat::mc that caches the result according to the -# locale. +# The global locale was changed within msgcat. +# Clears the buffered parse functions of the current locale. # # Parameters: -# Accepts the name of the message to retrieve. +# loclist (ignored) # # Results: -# Returns the message text. +# None. # # Side effects: -# Caches the message text. -# -# Notes: -# Only the single-argument version of [mc] is supported. +# Buffered parse functions are cleared. # #---------------------------------------------------------------------- -proc ::tcl::clock::mc { name } { - variable McLoaded - set Locale [mclocale] - if { [dict exists $McLoaded $Locale $name] } { - return [dict get $McLoaded $Locale $name] +proc ::tcl::clock::ChangeCurrentLocale {args} { + variable FormatProc + variable LocaleNumeralCache + variable CachedSystemTimeZone + variable TimeZoneBad + + foreach p [info procs [namespace current]::scanproc'*'current] { + rename $p {} + } + foreach p [info procs [namespace current]::formatproc'*'current] { + rename $p {} } - set val [::msgcat::mc $name] - dict set McLoaded $Locale $name $val - return $val + + catch {array unset FormatProc *'current} + set LocaleNumeralCache {} } #---------------------------------------------------------------------- @@ -4553,7 +4529,6 @@ proc ::tcl::clock::mc { name } { proc ::tcl::clock::ClearCaches {} { variable FormatProc variable LocaleNumeralCache - variable McLoaded variable CachedSystemTimeZone variable TimeZoneBad @@ -4566,7 +4541,6 @@ proc ::tcl::clock::ClearCaches {} { catch {unset FormatProc} set LocaleNumeralCache {} - set McLoaded {} catch {unset CachedSystemTimeZone} set TimeZoneBad {} InitTZData diff --git a/library/encoding/jis0208.enc b/library/encoding/jis0208.enc index 8460b69..11c49a4 100644 --- a/library/encoding/jis0208.enc +++ b/library/encoding/jis0208.enc @@ -1311,9 +1311,9 @@ FF50FF51FF52FF53FF54FF55FF56FF57FF58FF59FF5A00000000000000000000 0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000 R -2141 301C FF5E -2142 2016 2225 -215D 2212 FF0D -2171 00A2 FFE0 -2172 00A3 FFE1 -224C 00AC FFE2 +2141 301C FF5E +2142 2016 2225 +215D 2212 FF0D +2171 00A2 FFE0 +2172 00A3 FFE1 +224C 00AC FFE2 diff --git a/library/http/http.tcl b/library/http/http.tcl index a6b2bfd..5a05fa0 100644 --- a/library/http/http.tcl +++ b/library/http/http.tcl @@ -11,7 +11,7 @@ package require Tcl 8.6 # Keep this in sync with pkgIndex.tcl and with the install directories in # Makefiles -package provide http 2.8.8 +package provide http 2.8.9 namespace eval http { # Allow resourcing to not clobber existing data @@ -566,6 +566,10 @@ proc http::geturl {url args} { # Proxy connections aren't shared among different hosts. set state(socketinfo) $host:$port + # Save the accept types at this point to prevent a race condition. [Bug + # c11a51c482] + set state(accept-types) $http(-accept) + # See if we are supposed to use a previously opened channel. if {$state(-keepalive)} { variable socketmap @@ -637,8 +641,20 @@ proc http::geturl {url args} { return $token } +# http::Connected -- +# +# Callback used when the connection to the HTTP server is actually +# established. +# +# Arguments: +# token State token. +# proto What protocol (http, https, etc.) was used to connect. +# phost Are we using keep-alive? Non-empty if yes. +# srvurl Service-local URL that we're requesting +# Results: +# None. -proc http::Connected { token proto phost srvurl} { +proc http::Connected {token proto phost srvurl} { variable http variable urlTypes @@ -691,13 +707,12 @@ proc http::Connected { token proto phost srvurl} { if {[info exists state(-handler)]} { set state(-protocol) 1.0 } + set accept_types_seen 0 if {[catch { puts $sock "$how $srvurl HTTP/$state(-protocol)" - puts $sock "Accept: $http(-accept)" - array set hdrs $state(-headers) - if {[info exists hdrs(Host)]} { + if {[dict exists $state(-headers) Host]} { # Allow Host spoofing. [Bug 928154] - puts $sock "Host: $hdrs(Host)" + puts $sock "Host: [dict get $state(-headers) Host]" } elseif {$port == $defport} { # Don't add port in this case, to handle broken servers. [Bug # #504508] @@ -705,7 +720,6 @@ proc http::Connected { token proto phost srvurl} { } else { puts $sock "Host: $host:$port" } - unset hdrs puts $sock "User-Agent: $http(-useragent)" if {$state(-protocol) == 1.0 && $state(-keepalive)} { puts $sock "Connection: keep-alive" @@ -718,18 +732,21 @@ proc http::Connected { token proto phost srvurl} { } set accept_encoding_seen 0 set content_type_seen 0 - foreach {key value} $state(-headers) { + dict for {key value} $state(-headers) { + set value [string map [list \n "" \r ""] $value] + set key [string map {" " -} [string trim $key]] if {[string equal -nocase $key "host"]} { continue } if {[string equal -nocase $key "accept-encoding"]} { set accept_encoding_seen 1 } + if {[string equal -nocase $key "accept"]} { + set accept_types_seen 1 + } if {[string equal -nocase $key "content-type"]} { set content_type_seen 1 } - set value [string map [list \n "" \r ""] $value] - set key [string trim $key] if {[string equal -nocase $key "content-length"]} { set contDone 1 set state(querylength) $value @@ -738,8 +755,13 @@ proc http::Connected { token proto phost srvurl} { puts $sock "$key: $value" } } + # Allow overriding the Accept header on a per-connection basis. Useful + # for working with REST services. [Bug c11a51c482] + if {!$accept_types_seen} { + puts $sock "Accept: $state(accept-types)" + } if {!$accept_encoding_seen && ![info exists state(-handler)]} { - puts $sock "Accept-Encoding: deflate,gzip,compress" + puts $sock "Accept-Encoding: gzip,deflate,compress" } if {$isQueryChannel && $state(querylength) == 0} { # Try to determine size of data in channel. If we cannot seek, the @@ -795,7 +817,6 @@ proc http::Connected { token proto phost srvurl} { Finish $token $err } } - } # Data access functions: @@ -1299,7 +1320,7 @@ proc http::Eof {token {force 0}} { set state(body) [zlib $coding $state(body)] } } err]} { - Log "error doing $coding '$state(body)'" + Log "error doing decompression: $err" return [Finish $token $err] } diff --git a/library/http/pkgIndex.tcl b/library/http/pkgIndex.tcl index 27ba795..6e0301a 100644 --- a/library/http/pkgIndex.tcl +++ b/library/http/pkgIndex.tcl @@ -1,2 +1,2 @@ if {![package vsatisfies [package provide Tcl] 8.6]} {return} -package ifneeded http 2.8.8 [list tclPkgSetup $dir http 2.8.8 {{http.tcl source {::http::config ::http::formatQuery ::http::geturl ::http::reset ::http::wait ::http::register ::http::unregister ::http::mapReply}}}] +package ifneeded http 2.8.9 [list tclPkgSetup $dir http 2.8.9 {{http.tcl source {::http::config ::http::formatQuery ::http::geturl ::http::reset ::http::wait ::http::register ::http::unregister ::http::mapReply}}}] diff --git a/library/init.tcl b/library/init.tcl index 05ac4a3..85900d2 100644 --- a/library/init.tcl +++ b/library/init.tcl @@ -12,7 +12,7 @@ # of this file, and for a DISCLAIMER OF ALL WARRANTIES. # -# This test intentionally written in pre-7.5 Tcl +# This test intentionally written in pre-7.5 Tcl if {[info commands package] == ""} { error "version mismatch: library\nscripts expect Tcl version 7.5b1 or later but the loaded version is\nonly [info patchlevel]" } @@ -332,7 +332,7 @@ proc unknown args { } } - if {([info level] == 1) && ([info script] eq "") + if {([info level] == 1) && ([info script] eq "") && [info exists tcl_interactive] && $tcl_interactive} { if {![info exists auto_noexec]} { set new [auto_execok $name] @@ -636,12 +636,8 @@ proc auto_execok name { } set auto_execs($name) "" - set shellBuiltins [list cls copy date del erase dir echo mkdir \ - md rename ren rmdir rd time type ver vol] - if {$tcl_platform(os) eq "Windows NT"} { - # NT includes the 'start' built-in - lappend shellBuiltins "start" - } + set shellBuiltins [list cls copy date del dir echo erase md mkdir \ + mklink rd ren rename rmdir start time type ver vol] if {[info exists env(PATHEXT)]} { # Add an initial ; to have the {} extension check first. set execExtensions [split ";$env(PATHEXT)" ";"] diff --git a/library/msgcat/msgcat.tcl b/library/msgcat/msgcat.tcl index cf3b9d7..a43f13e 100644 --- a/library/msgcat/msgcat.tcl +++ b/library/msgcat/msgcat.tcl @@ -4,6 +4,7 @@ # message catalog facility for Tcl programs. It should be # loaded with the command "package require msgcat". # +# Copyright (c) 2010-2015 by Harald Oehlmann. # Copyright (c) 1998-2000 by Ajuba Solutions. # Copyright (c) 1998 by Mark Harrison. # @@ -13,23 +14,30 @@ package require Tcl 8.5 # When the version number changes, be sure to update the pkgIndex.tcl file, # and the installation directory in the Makefiles. -package provide msgcat 1.5.2 +package provide msgcat 1.6.0 namespace eval msgcat { - namespace export mc mcload mclocale mcmax mcmset mcpreferences mcset \ - mcunknown mcflset mcflmset - - # Records the current locale as passed to mclocale - variable Locale "" + namespace export mc mcexists mcload mclocale mcmax mcmset mcpreferences mcset\ + mcunknown mcflset mcflmset mcloadedlocales mcforgetpackage\ + mcpackageconfig mcpackagelocale # Records the list of locales to search variable Loclist {} + # List of currently loaded locales + variable LoadedLocales {} + # Records the locale of the currently sourced message catalogue file variable FileLocale + # Configuration values per Package (e.g. client namespace). + # The dict key is of the form "<option> <namespace>" and the value is the + # configuration option. A nonexisting key is an unset option. + variable PackageConfig [dict create mcfolder {} loadcmd {} changecmd {}\ + unknowncmd {} loadedlocales {} loclist {}] + # Records the mapping between source strings and translated strings. The - # dict key is of the form "<locale> <namespace> <src>", where locale and + # dict key is of the form "<namespace> <locale> <src>", where locale and # namespace should be themselves dict values and the value is # the translated string. variable Msgs [dict create] @@ -173,6 +181,8 @@ namespace eval msgcat { # parent namespace until the source is found. If additional args are # specified, use the format command to work them into the traslated # string. +# If no catalog item is found, mcunknown is called in the caller frame +# and its result is returned. # # Arguments: # src The string to translate. @@ -183,30 +193,86 @@ namespace eval msgcat { # format command. proc msgcat::mc {src args} { + # this may be replaced by: + # return [mcget -namespace [uplevel 1 [list ::namespace current]] --\ + # $src {*}$args] + # Check for the src in each namespace starting from the local and # ending in the global. variable Msgs variable Loclist - variable Locale set ns [uplevel 1 [list ::namespace current]] + set loclist [PackagePreferences $ns] - while {$ns != ""} { - foreach loc $Loclist { - if {[dict exists $Msgs $loc $ns $src]} { - if {[llength $args] == 0} { - return [dict get $Msgs $loc $ns $src] - } else { - return [format [dict get $Msgs $loc $ns $src] {*}$args] - } + set nscur $ns + while {$nscur != ""} { + foreach loc $loclist { + if {[dict exists $Msgs $nscur $loc $src]} { + return [DefaultUnknown "" [dict get $Msgs $nscur $loc $src]\ + {*}$args] + } + } + set nscur [namespace parent $nscur] + } + # call package local or default unknown command + set args [linsert $args 0 [lindex $loclist 0] $src] + switch -exact -- [Invoke unknowncmd $args $ns result 1] { + 0 { return [uplevel 1 [linsert $args 0 [namespace origin mcunknown]]] } + 1 { return [DefaultUnknown {*}$args] } + default { return $result } + } +} + +# msgcat::mcexists -- +# +# Check if a catalog item is set or if mc would invoke mcunknown. +# +# Arguments: +# -exactnamespace Only check the exact namespace and no +# parent namespaces +# -exactlocale Only check the exact locale and not all members +# of the preferences list +# src Message catalog key +# +# Results: +# true if an adequate catalog key was found + +proc msgcat::mcexists {args} { + + variable Msgs + variable Loclist + variable PackageConfig + + set ns [uplevel 1 [list ::namespace current]] + set loclist [PackagePreferences $ns] + + while {[llength $args] != 1} { + set args [lassign $args option] + switch -glob -- $option { + -exactnamespace { set exactnamespace 1 } + -exactlocale { set loclist [lrange $loclist 0 0] } + -* { return -code error "unknown option \"$option\"" } + default { + return -code error "wrong # args: should be\ + \"[lindex [info level 0] 0] ?-exactnamespace?\ + ?-exactlocale? src\"" } } + } + set src [lindex $args 0] + + while {$ns ne ""} { + foreach loc $loclist { + if {[dict exists $Msgs $ns $loc $src]} { + return 1 + } + } + if {[info exists exactnamespace]} {return 0} set ns [namespace parent $ns] } - # we have not found the translation - return [uplevel 1 [list [namespace origin mcunknown] \ - $Locale $src {*}$args]] + return 0 } # msgcat::mclocale -- @@ -219,11 +285,11 @@ proc msgcat::mc {src args} { # separated by underscores (e.g. en_US). # # Results: -# Returns the current locale. +# Returns the normalized set locale. proc msgcat::mclocale {args} { variable Loclist - variable Locale + variable LoadedLocales set len [llength $args] if {$len > 1} { @@ -232,24 +298,49 @@ proc msgcat::mclocale {args} { } if {$len == 1} { - set newLocale [lindex $args 0] + set newLocale [string tolower [lindex $args 0]] if {$newLocale ne [file tail $newLocale]} { return -code error "invalid newLocale value \"$newLocale\":\ could be path to unsafe code." } - set Locale [string tolower $newLocale] - set Loclist {} - set word "" - foreach part [split $Locale _] { - set word [string trim "${word}_${part}" _] - if {$word ne [lindex $Loclist 0]} { - set Loclist [linsert $Loclist 0 $word] - } + if {[lindex $Loclist 0] ne $newLocale} { + set Loclist [GetPreferences $newLocale] + + # locale not loaded jet + LoadAll $Loclist + # Invoke callback + Invoke changecmd $Loclist + } + } + return [lindex $Loclist 0] +} + +# msgcat::GetPreferences -- +# +# Get list of locales from a locale. +# The first element is always the lowercase locale. +# Other elements have one component separated by "_" less. +# Multiple "_" are seen as one separator: de__ch_spec de__ch de {} +# +# Arguments: +# Locale. +# +# Results: +# Locale list + +proc msgcat::GetPreferences {locale} { + set locale [string tolower $locale] + set loclist [list $locale] + while {-1 !=[set pos [string last "_" $locale]]} { + set locale [string range $locale 0 $pos-1] + if { "_" ne [string index $locale end] } { + lappend loclist $locale } - lappend Loclist {} - set Locale [lindex $Loclist 0] } - return $Locale + if {"" ne [lindex $loclist end]} { + lappend loclist {} + } + return $loclist } # msgcat::mcpreferences -- @@ -268,6 +359,391 @@ proc msgcat::mcpreferences {} { return $Loclist } +# msgcat::mcloadedlocales -- +# +# Get or change the list of currently loaded default locales +# +# The following subcommands are available: +# loaded +# Get the current list of loaded locales +# clear +# Remove all loaded locales not present in mcpreferences. +# +# Arguments: +# subcommand One of loaded or clear +# +# Results: +# Empty string, if not stated differently for the subcommand + +proc msgcat::mcloadedlocales {subcommand} { + variable Loclist + variable LoadedLocales + variable Msgs + variable PackageConfig + switch -exact -- $subcommand { + clear { + # Remove all locales not contained in Loclist + # skip any packages with package locale + set LoadedLocales $Loclist + foreach ns [dict keys $Msgs] { + if {![dict exists $PackageConfig loclist $ns]} { + foreach locale [dict keys [dict get $Msgs $ns]] { + if {$locale ni $Loclist} { + dict unset Msgs $ns $locale + } + } + } + } + } + loaded { return $LoadedLocales } + default { + return -code error "unknown subcommand \"$subcommand\": must be\ + clear, or loaded" + } + } + return +} + +# msgcat::mcpackagelocale -- +# +# Get or change the package locale of the calling package. +# +# The following subcommands are available: +# set +# Set a package locale. +# This may load message catalog files and may clear message catalog +# items, if the former locale was the default locale. +# Returns the normalized set locale. +# The default locale is taken, if locale is not given. +# get +# Get the locale valid for this package. +# isset +# Returns true, if a package locale is set +# unset +# Unset the package locale and activate the default locale. +# This loads message catalog file which where missing in the package +# locale. +# preferences +# Return locale preference list valid for the package. +# loaded +# Return loaded locale list valid for the current package. +# clear +# If the current package has a package locale, remove all package +# locales not containes in package mcpreferences. +# It is an error to call this without a package locale set. +# +# The subcommands get, preferences and loaded return the corresponding +# default data, if no package locale is set. +# +# Arguments: +# subcommand see list above +# locale package locale (only set subcommand) +# +# Results: +# Empty string, if not stated differently for the subcommand + +proc msgcat::mcpackagelocale {subcommand {locale ""}} { + # todo: implement using an ensemble + variable Loclist + variable LoadedLocales + variable Msgs + variable PackageConfig + # Check option + # check if required item is exactly provided + if {[llength [info level 0]] == 2} { + # locale not given + unset locale + } else { + # locale given + if {$subcommand in + {"get" "isset" "unset" "preferences" "loaded" "clear"} } { + return -code error "wrong # args: should be\ + \"[lrange [info level 0] 0 1]\"" + } + set locale [string tolower $locale] + } + set ns [uplevel 1 {::namespace current}] + + switch -exact -- $subcommand { + get { return [lindex [PackagePreferences $ns] 0] } + preferences { return [PackagePreferences $ns] } + loaded { return [PackageLocales $ns] } + present { return [expr {$locale in [PackageLocales $ns]} ]} + isset { return [dict exists $PackageConfig loclist $ns] } + set { # set a package locale or add a package locale + + # Copy the default locale if no package locale set so far + if {![dict exists $PackageConfig loclist $ns]} { + dict set PackageConfig loclist $ns $Loclist + dict set PackageConfig loadedlocales $ns $LoadedLocales + } + + # Check if changed + set loclist [dict get $PackageConfig loclist $ns] + if {! [info exists locale] || $locale eq [lindex $loclist 0] } { + return [lindex $loclist 0] + } + + # Change loclist + set loclist [GetPreferences $locale] + set locale [lindex $loclist 0] + dict set PackageConfig loclist $ns $loclist + + # load eventual missing locales + set loadedLocales [dict get $PackageConfig loadedlocales $ns] + if {$locale in $loadedLocales} { return $locale } + set loadLocales [ListComplement $loadedLocales $loclist] + dict set PackageConfig loadedlocales $ns\ + [concat $loadedLocales $loadLocales] + Load $ns $loadLocales + return $locale + } + clear { # Remove all locales not contained in Loclist + if {![dict exists $PackageConfig loclist $ns]} { + return -code error "clear only when package locale set" + } + set loclist [dict get $PackageConfig loclist $ns] + dict set PackageConfig loadedlocales $ns $loclist + if {[dict exists $Msgs $ns]} { + foreach locale [dict keys [dict get $Msgs $ns]] { + if {$locale ni $loclist} { + dict unset Msgs $ns $locale + } + } + } + } + unset { # unset package locale and restore default locales + + if { ![dict exists $PackageConfig loclist $ns] } { return } + + # unset package locale + set loadLocales [ListComplement\ + [dict get $PackageConfig loadedlocales $ns] $LoadedLocales] + dict unset PackageConfig loadedlocales $ns + dict unset PackageConfig loclist $ns + + # unset keys not in global loaded locales + if {[dict exists $Msgs $ns]} { + foreach locale [dict keys [dict get $Msgs $ns]] { + if {$locale ni $LoadedLocales} { + dict unset Msgs $ns $locale + } + } + } + + # Add missing locales + Load $ns $loadLocales + } + default { + return -code error "unknown subcommand \"$subcommand\": must be\ + clear, get, isset, loaded, present, set, or unset" + } + } + return +} + +# msgcat::mcforgetpackage -- +# +# Remove any data of the calling package from msgcat +# + +proc msgcat::mcforgetpackage {} { + # todo: this may be implemented using an ensemble + variable PackageConfig + variable Msgs + set ns [uplevel 1 {::namespace current}] + # Remove MC items + dict unset Msgs $ns + # Remove config items + foreach key [dict keys $PackageConfig] { + dict unset PackageConfig $key $ns + } + return +} + +# msgcat::mcpackageconfig -- +# +# Get or modify the per caller namespace (e.g. packages) config options. +# +# Available subcommands are: +# +# get get the current value or an error if not set. +# isset return true, if the option is set +# set set the value (see also distinct option). +# Returns the number of loaded message files. +# unset Clear option. return "". +# +# Available options are: +# +# mcfolder +# The message catalog folder of the package. +# This is automatically set by mcload. +# If the value is changed using the set subcommand, an evntual +# loadcmd is invoked and all message files of the package locale are +# loaded. +# +# loadcmd +# The command gets executed before a message file would be +# sourced for this module. +# The command is invoked with the expanded locale list to load. +# The command is not invoked if the registering package namespace +# is not present. +# This callback might also be used as an alternative to message +# files. +# If the value is changed using the set subcommand, the callback is +# directly invoked with the current file locale list. No file load is +# executed. +# +# changecmd +# The command is invoked, after an executed locale change. +# Appended argument is expanded mcpreferences. +# +# unknowncmd +# Use a package locale mcunknown procedure instead the global one. +# The appended arguments are identical to mcunknown. +# A default unknown handler is used if set to the empty string. +# This consists in returning the key if no arguments are given. +# With given arguments, format is used to process the arguments. +# +# Arguments: +# subcommand Operation on the package +# option The package option to get or set. +# ?value? Eventual value for the subcommand +# +# Results: +# Depends on the subcommand and option and is described there + +proc msgcat::mcpackageconfig {subcommand option {value ""}} { + variable PackageConfig + # get namespace + set ns [uplevel 1 {::namespace current}] + + if {$option ni {"mcfolder" "loadcmd" "changecmd" "unknowncmd"}} { + return -code error "bad option \"$option\": must be mcfolder, loadcmd,\ + changecmd, or unknowncmd" + } + + # check if value argument is exactly provided + if {[llength [info level 0]] == 4 } { + # value provided + if {$subcommand in {"get" "isset" "unset"}} { + return -code error "wrong # args: should be\ + \"[lrange [info level 0] 0 2] value\"" + } + } elseif {$subcommand eq "set"} { + return -code error\ + "wrong # args: should be \"[lrange [info level 0] 0 2]\"" + } + + # Execute subcommands + switch -exact -- $subcommand { + get { # Operation get return current value + if {![dict exists $PackageConfig $option $ns]} { + return -code error "package option \"$option\" not set" + } + return [dict get $PackageConfig $option $ns] + } + isset { return [dict exists $PackageConfig $option $ns] } + unset { dict unset PackageConfig $option $ns } + set { # Set option + + if {$option eq "mcfolder"} { + set value [file normalize $value] + } + # Check if changed + if { [dict exists $PackageConfig $option $ns] + && $value eq [dict get $PackageConfig $option $ns] } { + return 0 + } + + # set new value + dict set PackageConfig $option $ns $value + + # Reload pending message catalogs + switch -exact -- $option { + mcfolder { return [Load $ns [PackageLocales $ns]] } + loadcmd { return [Load $ns [PackageLocales $ns] 1] } + } + return 0 + } + default { + return -code error "unknown subcommand \"$subcommand\":\ + must be get, isset, set, or unset" + } + } + return +} + +# msgcat::PackagePreferences -- +# +# Return eventual present package preferences or the default list if not +# present. +# +# Arguments: +# ns Package namespace +# +# Results: +# locale list + +proc msgcat::PackagePreferences {ns} { + variable PackageConfig + if {[dict exists $PackageConfig loclist $ns]} { + return [dict get $PackageConfig loclist $ns] + } + variable Loclist + return $Loclist +} + +# msgcat::PackageLocales -- +# +# Return eventual present package locales or the default list if not +# present. +# +# Arguments: +# ns Package namespace +# +# Results: +# locale list + +proc msgcat::PackageLocales {ns} { + variable PackageConfig + if {[dict exists $PackageConfig loadedlocales $ns]} { + return [dict get $PackageConfig loadedlocales $ns] + } + variable LoadedLocales + return $LoadedLocales +} + +# msgcat::ListComplement -- +# +# Build the complement of two lists. +# Return a list with all elements in list2 but not in list1. +# Optionally return the intersection. +# +# Arguments: +# list1 excluded list +# list2 included list +# inlistname If not "", write in this variable the intersection list +# +# Results: +# list with all elements in list2 but not in list1 + +proc msgcat::ListComplement {list1 list2 {inlistname ""}} { + if {"" ne $inlistname} { + upvar 1 $inlistname inlist + } + set inlist {} + set outlist {} + foreach item $list2 { + if {$item in $list1} { + lappend inlist $item + } else { + lappend outlist $item + } + } + return $outlist +} + # msgcat::mcload -- # # Attempt to load message catalogs for each locale in the @@ -280,24 +756,88 @@ proc msgcat::mcpreferences {} { # Returns the number of message catalogs that were loaded. proc msgcat::mcload {langdir} { + return [uplevel 1 [list\ + [namespace origin mcpackageconfig] set mcfolder $langdir]] +} + +# msgcat::LoadAll -- +# +# Load a list of locales for all packages not having a package locale +# list. +# +# Arguments: +# langdir The directory to search. +# +# Results: +# Returns the number of message catalogs that were loaded. + +proc msgcat::LoadAll {locales} { + variable PackageConfig + variable LoadedLocales + if {0 == [llength $locales]} { return {} } + # filter jet unloaded locales + set locales [ListComplement $LoadedLocales $locales] + if {0 == [llength $locales]} { return {} } + lappend LoadedLocales {*}$locales + + set packages [lsort -unique [concat\ + [dict keys [dict get $PackageConfig loadcmd]]\ + [dict keys [dict get $PackageConfig mcfolder]]]] + foreach ns $packages { + if {! [dict exists $PackageConfig loclist $ns] } { + Load $ns $locales + } + } + return $locales +} + +# msgcat::Load -- +# +# Invoke message load callback and load message catalog files. +# +# Arguments: +# ns Namespace (equal package) to load the message catalog. +# locales List of locales to load. +# callbackonly true if only callback should be invoked +# +# Results: +# Returns the number of message catalogs that were loaded. + +proc msgcat::Load {ns locales {callbackonly 0}} { variable FileLocale + variable PackageConfig + variable LoadedLocals + + if {0 == [llength $locales]} { return 0 } + + # Invoke callback + Invoke loadcmd $locales $ns + + if {$callbackonly || ![dict exists $PackageConfig mcfolder $ns]} { + return 0 + } + + # Invoke file load + set langdir [dict get $PackageConfig mcfolder $ns] + # Save the file locale if we are recursively called if {[info exists FileLocale]} { set nestedFileLocale $FileLocale } set x 0 - foreach p [mcpreferences] { + foreach p $locales { if {$p eq {}} { set p ROOT } set langfile [file join $langdir $p.msg] if {[file exists $langfile]} { incr x - set FileLocale [string tolower [file tail [file rootname $langfile]]] + set FileLocale [string tolower\ + [file tail [file rootname $langfile]]] if {"root" eq $FileLocale} { set FileLocale "" } - uplevel 1 [list ::source -encoding utf-8 $langfile] + namespace inscope $ns [list ::source -encoding utf-8 $langfile] unset FileLocale } } @@ -307,6 +847,63 @@ proc msgcat::mcload {langdir} { return $x } +# msgcat::Invoke -- +# +# Invoke a set of registered callbacks. +# The callback is only invoked, if its registered namespace exists. +# +# Arguments: +# index Index into PackageConfig to get callback command +# arglist parameters to the callback invocation +# ns (Optional) package to call. +# If not given or empty, check all registered packages. +# resultname Variable to save the callback result of the last called +# callback to. May be set to "" to discard the result. +# failerror (0) Fail on error if true. Otherwise call bgerror. +# +# Results: +# Possible values: +# - 0: no valid command registered +# - 1: registered command was the empty string +# - 2: registered command called, resultname is set +# - 3: registered command failed +# If multiple commands are called, the maximum of all results is returned. + +proc msgcat::Invoke {index arglist {ns ""} {resultname ""} {failerror 0}} { + variable PackageConfig + variable Config + if {"" ne $resultname} { + upvar 1 $resultname result + } + if {"" eq $ns} { + set packageList [dict keys [dict get $PackageConfig $index]] + } else { + set packageList [list $ns] + } + set ret 0 + foreach ns $packageList { + if {[dict exists $PackageConfig $index $ns] && [namespace exists $ns]} { + set cmd [dict get $PackageConfig $index $ns] + if {"" eq $cmd} { + if {$ret == 0} {set ret 1} + } else { + if {$failerror} { + set result [namespace inscope $ns $cmd {*}$arglist] + set ret 2 + } elseif {1 == [catch { + set result [namespace inscope $ns $cmd {*}$arglist] + if {$ret < 2} {set ret 2} + } err derr]} { + after idle [concat [::interp bgerror ""]\ + [list $err $derr]] + set ret 3 + } + } + } + } + return $ret +} + # msgcat::mcset -- # # Set the translation for a given string in a specified locale. @@ -330,7 +927,7 @@ proc msgcat::mcset {locale src {dest ""}} { set locale [string tolower $locale] - dict set Msgs $locale $ns $src $dest + dict set Msgs $ns $locale $src $dest return $dest } @@ -351,16 +948,10 @@ proc msgcat::mcflset {src {dest ""}} { variable Msgs if {![info exists FileLocale]} { - return -code error \ - "must only be used inside a message catalog loaded with ::msgcat::mcload" + return -code error "must only be used inside a message catalog loaded\ + with ::msgcat::mcload" } - if {[llength [info level 0]] == 2} { ;# dest not specified - set dest $src - } - - set ns [uplevel 1 [list ::namespace current]] - dict set Msgs $FileLocale $ns $src $dest - return $dest + return [uplevel 1 [list [namespace origin mcset] $FileLocale $src $dest]] } # msgcat::mcmset -- @@ -380,14 +971,14 @@ proc msgcat::mcmset {locale pairs} { set length [llength $pairs] if {$length % 2} { return -code error "bad translation list:\ - should be \"[lindex [info level 0] 0] locale {src dest ...}\"" + should be \"[lindex [info level 0] 0] locale {src dest ...}\"" } set locale [string tolower $locale] set ns [uplevel 1 [list ::namespace current]] foreach {src dest} $pairs { - dict set Msgs $locale $ns $src $dest + dict set Msgs $ns $locale $src $dest } return [expr {$length / 2}] @@ -408,26 +999,17 @@ proc msgcat::mcflmset {pairs} { variable Msgs if {![info exists FileLocale]} { - return -code error \ - "must only be used inside a message catalog loaded with ::msgcat::mcload" + return -code error "must only be used inside a message catalog loaded\ + with ::msgcat::mcload" } - set length [llength $pairs] - if {$length % 2} { - return -code error "bad translation list:\ - should be \"[lindex [info level 0] 0] locale {src dest ...}\"" - } - - set ns [uplevel 1 [list ::namespace current]] - foreach {src dest} $pairs { - dict set Msgs $FileLocale $ns $src $dest - } - return [expr {$length / 2}] + return [uplevel 1 [list [namespace origin mcmset] $FileLocale $pairs]] } # msgcat::mcunknown -- # # This routine is called by msgcat::mc if a translation cannot -# be found for a string. This routine is intended to be replaced +# be found for a string and no unknowncmd is set for the current +# package. This routine is intended to be replaced # by an application specific routine for error reporting # purposes. The default behavior is to return the source string. # If additional args are specified, the format command will be used @@ -441,7 +1023,30 @@ proc msgcat::mcflmset {pairs} { # Results: # Returns the translated value. -proc msgcat::mcunknown {locale src args} { +proc msgcat::mcunknown {args} { + return [uplevel 1 [list [namespace origin DefaultUnknown] {*}$args]] +} + +# msgcat::DefaultUnknown -- +# +# This routine is called by msgcat::mc if a translation cannot +# be found for a string in the following circumstances: +# - Default global handler, if mcunknown is not redefined. +# - Per package handler, if the package sets unknowncmd to the empty +# string. +# It returna the source string if the argument list is empty. +# If additional args are specified, the format command will be used +# to work them into the traslated string. +# +# Arguments: +# locale (unused) The current locale. +# src The string to be translated. +# args Args to pass to the format command +# +# Results: +# Returns the translated value. + +proc msgcat::DefaultUnknown {locale src args} { if {[llength $args]} { return [format $src {*}$args] } else { diff --git a/library/msgcat/pkgIndex.tcl b/library/msgcat/pkgIndex.tcl index 5fabfe3..7399c92 100644 --- a/library/msgcat/pkgIndex.tcl +++ b/library/msgcat/pkgIndex.tcl @@ -1,2 +1,2 @@ if {![package vsatisfies [package provide Tcl] 8.5]} {return} -package ifneeded msgcat 1.5.2 [list source [file join $dir msgcat.tcl]] +package ifneeded msgcat 1.6.0 [list source [file join $dir msgcat.tcl]] diff --git a/library/opt/optparse.tcl b/library/opt/optparse.tcl index fc77fa1..869a2b6 100644 --- a/library/opt/optparse.tcl +++ b/library/opt/optparse.tcl @@ -435,7 +435,7 @@ proc ::tcl::OptProcArgGiven {argname} { } elseif {$state == "optValue"} { set state next; # not used, for debug only # go to next state - return + return } else { return -code error [OptMissingValue $descriptions] } @@ -538,7 +538,7 @@ proc ::tcl::OptKeyParse {descKey arglist} { # Analyse the result # Walk through the tree: - OptTreeVars $desc "#[expr {[info level]-1}]" + OptTreeVars $desc "#[expr {[info level]-1}]" } # determine string length for nice tabulated output diff --git a/library/package.tcl b/library/package.tcl index 52daa0e..44e3b28 100644 --- a/library/package.tcl +++ b/library/package.tcl @@ -726,7 +726,7 @@ proc ::tcl::Pkg::Create {args} { foreach key {load source} { foreach filespec $opts(-$key) { lassign $filespec filename proclist - + if { [llength $proclist] == 0 } { set cmd "\[list $key \[file join \$dir [list $filename]\]\]" lappend cmdList $cmd diff --git a/library/platform/pkgIndex.tcl b/library/platform/pkgIndex.tcl index 5250163..5970a3f 100644 --- a/library/platform/pkgIndex.tcl +++ b/library/platform/pkgIndex.tcl @@ -1,3 +1,3 @@ -package ifneeded platform 1.0.13 [list source [file join $dir platform.tcl]] +package ifneeded platform 1.0.14 [list source [file join $dir platform.tcl]] package ifneeded platform::shell 1.1.4 [list source [file join $dir shell.tcl]] diff --git a/library/platform/platform.tcl b/library/platform/platform.tcl index 1bce7b5..35a22a3 100644 --- a/library/platform/platform.tcl +++ b/library/platform/platform.tcl @@ -93,9 +93,16 @@ proc ::platform::generic {} { } } - switch -- $plat { + switch -glob -- $plat { + cygwin* { + set plat cygwin + } windows { - set plat win32 + if {$tcl_platform(platform) == "unix"} { + set plat cygwin + } else { + set plat win32 + } if {$cpu eq "amd64"} { # Do not check wordSize, win32-x64 is an IL32P64 platform. set cpu x86_64 @@ -323,7 +330,7 @@ proc ::platform::patterns {id} { lappend res macosx-universal macosx-i386-x86_64 } macosx*-* { - # 10.5+ + # 10.5+ if {[regexp {macosx([^-]*)-(.*)} $id -> v cpu]} { switch -exact -- $cpu { @@ -371,7 +378,7 @@ proc ::platform::patterns {id} { # ### ### ### ######### ######### ######### ## Ready -package provide platform 1.0.13 +package provide platform 1.0.14 # ### ### ### ######### ######### ######### ## Demo application diff --git a/library/reg/pkgIndex.tcl b/library/reg/pkgIndex.tcl index 55af4b3..49fd1ac 100755 --- a/library/reg/pkgIndex.tcl +++ b/library/reg/pkgIndex.tcl @@ -1,9 +1,9 @@ if {([info commands ::tcl::pkgconfig] eq "") || ([info sharedlibextension] ne ".dll")} return if {[::tcl::pkgconfig get debug]} { - package ifneeded registry 1.3.0 \ + package ifneeded registry 1.3.1 \ [list load [file join $dir tclreg13g.dll] registry] } else { - package ifneeded registry 1.3.0 \ + package ifneeded registry 1.3.1 \ [list load [file join $dir tclreg13.dll] registry] } diff --git a/library/safe.tcl b/library/safe.tcl index 394aa97..ea6391d 100644 --- a/library/safe.tcl +++ b/library/safe.tcl @@ -853,7 +853,7 @@ proc ::safe::AliasSource {slave args} { return -code error $msg } set file [lindex $args $at] - + # get the real path from the virtual one. if {[catch { set realfile [TranslatePath $slave $file] @@ -861,7 +861,7 @@ proc ::safe::AliasSource {slave args} { Log $slave $msg return -code error "permission denied" } - + # check that the path is in the access path of that slave if {[catch { FileInAccessPath $slave $realfile diff --git a/library/tcltest/tcltest.tcl b/library/tcltest/tcltest.tcl index 8e43859..29ef778 100644 --- a/library/tcltest/tcltest.tcl +++ b/library/tcltest/tcltest.tcl @@ -347,7 +347,7 @@ namespace eval tcltest { # This is very subtle and tricky, so let me try to explain. # (Hopefully this longer comment will be clear when I come # back in a few months, unlike its predecessor :) ) - # + # # The [outputChannel] command (and underlying variable) have to # be kept in sync with the [configure -outfile] configuration # option ( and underlying variable Option(-outfile) ). This is @@ -362,12 +362,12 @@ namespace eval tcltest { # configuration options to parse the command line option the first # time they are read. These traces are cancelled whenever the # program itself calls [configure]. - # + # # OK, then so to support tcltest 1 compatibility, it seems we want # to get the return from [outputFile] to trigger the read traces, # just in case. # - # BUT! A little known feature of Tcl variable traces is that + # BUT! A little known feature of Tcl variable traces is that # traces are disabled during the handling of other traces. So, # if we trigger read traces on Option(-outfile) and that triggers # command line parsing which turns around and sets an initial @@ -608,7 +608,7 @@ namespace eval tcltest { set code [catch {Configure {*}$args} msg] return -code $code $msg } - + proc AcceptVerbose { level } { set level [AcceptList $level] if {[llength $level] == 1} { @@ -639,7 +639,7 @@ namespace eval tcltest { skipped tests if 's' is specified, the bodies of failed tests if 'b' is specified, and when tests start if 't' is specified. ErrorInfo is displayed if 'e' is specified. Source file line - information of failed tests is displayed if 'l' is specified. + information of failed tests is displayed if 'l' is specified. } AcceptVerbose verbose # Match and skip patterns default to the empty list, except for @@ -687,7 +687,7 @@ namespace eval tcltest { # some additional output regarding operations of the test harness. # The tcltest package currently implements only up to debug level 3. Option -debug 0 { - Internal debug level + Internal debug level } AcceptInteger debug proc SetSelectedConstraints args { @@ -715,7 +715,7 @@ namespace eval tcltest { } Option -limitconstraints 0 { whether to run only tests with the constraints - } AcceptBoolean limitConstraints + } AcceptBoolean limitConstraints trace add variable Option(-limitconstraints) write \ [namespace code {ClearUnselectedConstraints ;#}] @@ -728,7 +728,7 @@ namespace eval tcltest { # Default is to run each test file in a separate process Option -singleproc 0 { whether to run all tests in one process - } AcceptBoolean singleProcess + } AcceptBoolean singleProcess proc AcceptTemporaryDirectory { directory } { set directory [AcceptAbsolutePath $directory] @@ -1257,7 +1257,7 @@ proc tcltest::DefineConstraintInitializers {} { # setting files into nonblocking mode. ConstraintInitializer nonBlockFiles { - set code [expr {[catch {set f [open defs r]}] + set code [expr {[catch {set f [open defs r]}] || [catch {chan configure $f -blocking off}]}] catch {close $f} set code @@ -1271,7 +1271,7 @@ proc tcltest::DefineConstraintInitializers {} { # (Mark Diekhans). ConstraintInitializer asyncPipeClose {expr { - !([string equal unix $::tcl_platform(platform)] + !([string equal unix $::tcl_platform(platform)] && ([catch {exec uname -X | fgrep {Release = 3.2v}}] == 0))}} # Test to see if we have a broken version of sprintf with respect @@ -1954,7 +1954,7 @@ proc tcltest::test {name description args} { return } - # Save information about the core file. + # Save information about the core file. if {[preserveCore]} { if {[file exists [file join [workingDirectory] core]]} { set coreModTime [file mtime [file join [workingDirectory] core]] @@ -2060,7 +2060,7 @@ proc tcltest::test {name description args} { } else { set coreFailure 1 } - + if {([preserveCore] > 1) && ($coreFailure)} { append coreMsg "\nMoving file to:\ [file join [temporaryDirectory] core-$name]" @@ -2100,7 +2100,7 @@ proc tcltest::test {name description args} { variable currentFailure true if {![IsVerbose body]} { set body "" - } + } puts [outputChannel] "\n" if {[IsVerbose line]} { if {![catch {set testFrame [info frame -1]}] && @@ -2121,7 +2121,7 @@ proc tcltest::test {name description args} { puts [outputChannel] "$testFile:$testLine: error: test failed:\ $name [string trim $description]" } - } + } puts [outputChannel] "==== $name\ [string trim $description] FAILED" if {[string length $body]} { @@ -2277,7 +2277,7 @@ proc tcltest::Skipped {name constraints} { } } } - + if {!$doTest} { if {[IsVerbose skip]} { puts [outputChannel] "++++ $name SKIPPED: $constraints" @@ -2834,9 +2834,9 @@ proc tcltest::runAllTests { {shell ""} } { set dir [file tail $directory] puts [outputChannel] [string repeat ~ 44] puts [outputChannel] "$dir test began at [eval $timeCmd]\n" - + uplevel 1 [list ::source [file join $directory all.tcl]] - + set endTime [eval $timeCmd] puts [outputChannel] "\n$dir test ended at $endTime" puts [outputChannel] "" @@ -3019,7 +3019,7 @@ proc tcltest::removeFile {name {directory ""}} { DebugDo 1 { Warn "removeFile removing \"$fullName\":\n not created by makeFile" } - } + } if {![file isfile $fullName]} { DebugDo 1 { Warn "removeFile removing \"$fullName\":\n not a file" @@ -3090,7 +3090,7 @@ proc tcltest::removeDirectory {name {directory ""}} { Warn "removeDirectory removing \"$fullName\":\n not created\ by makeDirectory" } - } + } if {![file isdirectory $fullName]} { DebugDo 1 { Warn "removeDirectory removing \"$fullName\":\n not a directory" @@ -3285,7 +3285,7 @@ proc tcltest::threadReap {} { testthread errorproc ThreadError return [llength [testthread names]] } elseif {[info commands thread::id] ne {}} { - + # Thread extension thread::errorproc ThreadNullError diff --git a/library/tzdata/Africa/Cairo b/library/tzdata/Africa/Cairo index f453da2..aaeec54 100644 --- a/library/tzdata/Africa/Cairo +++ b/library/tzdata/Africa/Cairo @@ -129,184 +129,4 @@ set TZData(:Africa/Cairo) { {1403816400 7200 0 EET} {1406844000 10800 1 EEST} {1411678800 7200 0 EET} - {1429826400 10800 1 EEST} - {1434056400 7200 0 EET} - {1437688800 10800 1 EEST} - {1443128400 7200 0 EET} - {1461880800 10800 1 EEST} - {1464901200 7200 0 EET} - {1467928800 10800 1 EEST} - {1475182800 7200 0 EET} - {1493330400 10800 1 EEST} - {1495746000 7200 0 EET} - {1498773600 10800 1 EEST} - {1506632400 7200 0 EET} - {1524780000 10800 1 EEST} - {1525986000 7200 0 EET} - {1529013600 10800 1 EEST} - {1538082000 7200 0 EET} - {1556229600 10800 1 EEST} - {1556830800 7200 0 EET} - {1559858400 10800 1 EEST} - {1569531600 7200 0 EET} - {1590703200 10800 1 EEST} - {1600981200 7200 0 EET} - {1620943200 10800 1 EEST} - {1633035600 7200 0 EET} - {1651788000 10800 1 EEST} - {1664485200 7200 0 EET} - {1682632800 10800 1 EEST} - {1695934800 7200 0 EET} - {1714082400 10800 1 EEST} - {1727384400 7200 0 EET} - {1745532000 10800 1 EEST} - {1758834000 7200 0 EET} - {1776981600 10800 1 EEST} - {1790283600 7200 0 EET} - {1809036000 10800 1 EEST} - {1822338000 7200 0 EET} - {1840485600 10800 1 EEST} - {1853787600 7200 0 EET} - {1871935200 10800 1 EEST} - {1885237200 7200 0 EET} - {1903384800 10800 1 EEST} - {1916686800 7200 0 EET} - {1934834400 10800 1 EEST} - {1948136400 7200 0 EET} - {1966888800 10800 1 EEST} - {1980190800 7200 0 EET} - {1998338400 10800 1 EEST} - {2011640400 7200 0 EET} - {2029788000 10800 1 EEST} - {2043090000 7200 0 EET} - {2061237600 10800 1 EEST} - {2074539600 7200 0 EET} - {2092687200 10800 1 EEST} - {2105989200 7200 0 EET} - {2124136800 10800 1 EEST} - {2137438800 7200 0 EET} - {2156191200 10800 1 EEST} - {2169493200 7200 0 EET} - {2187640800 10800 1 EEST} - {2200942800 7200 0 EET} - {2219090400 10800 1 EEST} - {2232392400 7200 0 EET} - {2250540000 10800 1 EEST} - {2263842000 7200 0 EET} - {2281989600 10800 1 EEST} - {2295291600 7200 0 EET} - {2313439200 10800 1 EEST} - {2326741200 7200 0 EET} - {2345493600 10800 1 EEST} - {2358795600 7200 0 EET} - {2376943200 10800 1 EEST} - {2390245200 7200 0 EET} - {2408392800 10800 1 EEST} - {2421694800 7200 0 EET} - {2439842400 10800 1 EEST} - {2453144400 7200 0 EET} - {2471292000 10800 1 EEST} - {2484594000 7200 0 EET} - {2503346400 10800 1 EEST} - {2516648400 7200 0 EET} - {2534796000 10800 1 EEST} - {2548098000 7200 0 EET} - {2566245600 10800 1 EEST} - {2579547600 7200 0 EET} - {2597695200 10800 1 EEST} - {2610997200 7200 0 EET} - {2629144800 10800 1 EEST} - {2642446800 7200 0 EET} - {2660594400 10800 1 EEST} - {2673896400 7200 0 EET} - {2692648800 10800 1 EEST} - {2705950800 7200 0 EET} - {2724098400 10800 1 EEST} - {2737400400 7200 0 EET} - {2755548000 10800 1 EEST} - {2768850000 7200 0 EET} - {2786997600 10800 1 EEST} - {2800299600 7200 0 EET} - {2818447200 10800 1 EEST} - {2831749200 7200 0 EET} - {2850501600 10800 1 EEST} - {2863803600 7200 0 EET} - {2881951200 10800 1 EEST} - {2895253200 7200 0 EET} - {2913400800 10800 1 EEST} - {2926702800 7200 0 EET} - {2944850400 10800 1 EEST} - {2958152400 7200 0 EET} - {2976300000 10800 1 EEST} - {2989602000 7200 0 EET} - {3007749600 10800 1 EEST} - {3021051600 7200 0 EET} - {3039804000 10800 1 EEST} - {3053106000 7200 0 EET} - {3071253600 10800 1 EEST} - {3084555600 7200 0 EET} - {3102703200 10800 1 EEST} - {3116005200 7200 0 EET} - {3134152800 10800 1 EEST} - {3147454800 7200 0 EET} - {3165602400 10800 1 EEST} - {3178904400 7200 0 EET} - {3197052000 10800 1 EEST} - {3210354000 7200 0 EET} - {3229106400 10800 1 EEST} - {3242408400 7200 0 EET} - {3260556000 10800 1 EEST} - {3273858000 7200 0 EET} - {3292005600 10800 1 EEST} - {3305307600 7200 0 EET} - {3323455200 10800 1 EEST} - {3336757200 7200 0 EET} - {3354904800 10800 1 EEST} - {3368206800 7200 0 EET} - {3386959200 10800 1 EEST} - {3400261200 7200 0 EET} - {3418408800 10800 1 EEST} - {3431710800 7200 0 EET} - {3449858400 10800 1 EEST} - {3463160400 7200 0 EET} - {3481308000 10800 1 EEST} - {3494610000 7200 0 EET} - {3512757600 10800 1 EEST} - {3526059600 7200 0 EET} - {3544207200 10800 1 EEST} - {3557509200 7200 0 EET} - {3576261600 10800 1 EEST} - {3589563600 7200 0 EET} - {3607711200 10800 1 EEST} - {3621013200 7200 0 EET} - {3639160800 10800 1 EEST} - {3652462800 7200 0 EET} - {3670610400 10800 1 EEST} - {3683912400 7200 0 EET} - {3702060000 10800 1 EEST} - {3715362000 7200 0 EET} - {3734114400 10800 1 EEST} - {3747416400 7200 0 EET} - {3765564000 10800 1 EEST} - {3778866000 7200 0 EET} - {3797013600 10800 1 EEST} - {3810315600 7200 0 EET} - {3828463200 10800 1 EEST} - {3841765200 7200 0 EET} - {3859912800 10800 1 EEST} - {3873214800 7200 0 EET} - {3891362400 10800 1 EEST} - {3904664400 7200 0 EET} - {3923416800 10800 1 EEST} - {3936718800 7200 0 EET} - {3954866400 10800 1 EEST} - {3968168400 7200 0 EET} - {3986316000 10800 1 EEST} - {3999618000 7200 0 EET} - {4017765600 10800 1 EEST} - {4031067600 7200 0 EET} - {4049215200 10800 1 EEST} - {4062517200 7200 0 EET} - {4080664800 10800 1 EEST} - {4093966800 7200 0 EET} } diff --git a/library/tzdata/Africa/Casablanca b/library/tzdata/Africa/Casablanca index 224e5c2..33ad99b 100644 --- a/library/tzdata/Africa/Casablanca +++ b/library/tzdata/Africa/Casablanca @@ -42,42 +42,40 @@ set TZData(:Africa/Casablanca) { {1406944800 3600 1 WEST} {1414288800 0 0 WET} {1427594400 3600 1 WEST} - {1434160800 0 0 WET} - {1437184800 3600 1 WEST} + {1434247200 0 0 WET} + {1437271200 3600 1 WEST} {1445738400 0 0 WET} {1459044000 3600 1 WEST} - {1465005600 0 0 WET} - {1468029600 3600 1 WEST} + {1465092000 0 0 WET} + {1468116000 3600 1 WEST} {1477792800 0 0 WET} {1490493600 3600 1 WEST} - {1495245600 0 0 WET} - {1498874400 3600 1 WEST} + {1495332000 0 0 WET} + {1498960800 3600 1 WEST} {1509242400 0 0 WET} {1521943200 3600 1 WEST} - {1526090400 0 0 WET} - {1529114400 3600 1 WEST} + {1526176800 0 0 WET} + {1529200800 3600 1 WEST} {1540692000 0 0 WET} {1553997600 3600 1 WEST} - {1556935200 0 0 WET} - {1559959200 3600 1 WEST} + {1557021600 0 0 WET} + {1560045600 3600 1 WEST} {1572141600 0 0 WET} {1585447200 3600 1 WEST} - {1587175200 0 0 WET} - {1590804000 3600 1 WEST} + {1587261600 0 0 WET} + {1590285600 3600 1 WEST} {1603591200 0 0 WET} {1616896800 3600 1 WEST} - {1618020000 0 0 WET} - {1621044000 3600 1 WEST} + {1618106400 0 0 WET} + {1621130400 3600 1 WEST} {1635645600 0 0 WET} - {1648346400 3600 1 WEST} - {1648864800 0 0 WET} - {1651888800 3600 1 WEST} + {1651975200 3600 1 WEST} {1667095200 0 0 WET} - {1682128800 3600 1 WEST} + {1682215200 3600 1 WEST} {1698544800 0 0 WET} - {1712973600 3600 1 WEST} + {1713060000 3600 1 WEST} {1729994400 0 0 WET} - {1743818400 3600 1 WEST} + {1743904800 3600 1 WEST} {1761444000 0 0 WET} {1774749600 3600 1 WEST} {1792893600 0 0 WET} @@ -98,13 +96,12 @@ set TZData(:Africa/Casablanca) { {2026951200 3600 1 WEST} {2045700000 0 0 WET} {2058400800 3600 1 WEST} - {2077063200 0 0 WET} - {2077153200 0 0 WET} + {2077149600 0 0 WET} {2090455200 3600 1 WEST} - {2107908000 0 0 WET} + {2107994400 0 0 WET} {2108602800 0 0 WET} {2121904800 3600 1 WEST} - {2138752800 0 0 WET} + {2138234400 0 0 WET} {2140052400 0 0 WET} {2153354400 3600 1 WEST} {2172103200 0 0 WET} diff --git a/library/tzdata/Africa/El_Aaiun b/library/tzdata/Africa/El_Aaiun index 3a5c934..77e149e 100644 --- a/library/tzdata/Africa/El_Aaiun +++ b/library/tzdata/Africa/El_Aaiun @@ -31,42 +31,40 @@ set TZData(:Africa/El_Aaiun) { {1406944800 3600 1 WEST} {1414288800 0 0 WET} {1427594400 3600 1 WEST} - {1434160800 0 0 WET} - {1437184800 3600 1 WEST} + {1434247200 0 0 WET} + {1437271200 3600 1 WEST} {1445738400 0 0 WET} {1459044000 3600 1 WEST} - {1465005600 0 0 WET} - {1468029600 3600 1 WEST} + {1465092000 0 0 WET} + {1468116000 3600 1 WEST} {1477792800 0 0 WET} {1490493600 3600 1 WEST} - {1495245600 0 0 WET} - {1498874400 3600 1 WEST} + {1495332000 0 0 WET} + {1498960800 3600 1 WEST} {1509242400 0 0 WET} {1521943200 3600 1 WEST} - {1526090400 0 0 WET} - {1529114400 3600 1 WEST} + {1526176800 0 0 WET} + {1529200800 3600 1 WEST} {1540692000 0 0 WET} {1553997600 3600 1 WEST} - {1556935200 0 0 WET} - {1559959200 3600 1 WEST} + {1557021600 0 0 WET} + {1560045600 3600 1 WEST} {1572141600 0 0 WET} {1585447200 3600 1 WEST} - {1587175200 0 0 WET} - {1590804000 3600 1 WEST} + {1587261600 0 0 WET} + {1590285600 3600 1 WEST} {1603591200 0 0 WET} {1616896800 3600 1 WEST} - {1618020000 0 0 WET} - {1621044000 3600 1 WEST} + {1618106400 0 0 WET} + {1621130400 3600 1 WEST} {1635645600 0 0 WET} - {1648346400 3600 1 WEST} - {1648864800 0 0 WET} - {1651888800 3600 1 WEST} + {1651975200 3600 1 WEST} {1667095200 0 0 WET} - {1682128800 3600 1 WEST} + {1682215200 3600 1 WEST} {1698544800 0 0 WET} - {1712973600 3600 1 WEST} + {1713060000 3600 1 WEST} {1729994400 0 0 WET} - {1743818400 3600 1 WEST} + {1743904800 3600 1 WEST} {1761444000 0 0 WET} {1774749600 3600 1 WEST} {1792893600 0 0 WET} @@ -87,13 +85,12 @@ set TZData(:Africa/El_Aaiun) { {2026951200 3600 1 WEST} {2045700000 0 0 WET} {2058400800 3600 1 WEST} - {2077063200 0 0 WET} - {2077153200 0 0 WET} + {2077149600 0 0 WET} {2090455200 3600 1 WEST} - {2107908000 0 0 WET} + {2107994400 0 0 WET} {2108602800 0 0 WET} {2121904800 3600 1 WEST} - {2138752800 0 0 WET} + {2138234400 0 0 WET} {2140052400 0 0 WET} {2153354400 3600 1 WEST} {2172103200 0 0 WET} diff --git a/library/tzdata/America/Adak b/library/tzdata/America/Adak index f3c5e5c..bd5d5ab 100644 --- a/library/tzdata/America/Adak +++ b/library/tzdata/America/Adak @@ -40,237 +40,237 @@ set TZData(:America/Adak) { {388587600 -36000 1 BDT} {404913600 -39600 0 BST} {420037200 -36000 1 BDT} - {439034400 -36000 0 HAST} - {452088000 -32400 1 HADT} - {467809200 -36000 0 HAST} - {483537600 -32400 1 HADT} - {499258800 -36000 0 HAST} - {514987200 -32400 1 HADT} - {530708400 -36000 0 HAST} - {544622400 -32400 1 HADT} - {562158000 -36000 0 HAST} - {576072000 -32400 1 HADT} - {594212400 -36000 0 HAST} - {607521600 -32400 1 HADT} - {625662000 -36000 0 HAST} - {638971200 -32400 1 HADT} - {657111600 -36000 0 HAST} - {671025600 -32400 1 HADT} - {688561200 -36000 0 HAST} - {702475200 -32400 1 HADT} - {720010800 -36000 0 HAST} - {733924800 -32400 1 HADT} - {752065200 -36000 0 HAST} - {765374400 -32400 1 HADT} - {783514800 -36000 0 HAST} - {796824000 -32400 1 HADT} - {814964400 -36000 0 HAST} - {828878400 -32400 1 HADT} - {846414000 -36000 0 HAST} - {860328000 -32400 1 HADT} - {877863600 -36000 0 HAST} - {891777600 -32400 1 HADT} - {909313200 -36000 0 HAST} - {923227200 -32400 1 HADT} - {941367600 -36000 0 HAST} - {954676800 -32400 1 HADT} - {972817200 -36000 0 HAST} - {986126400 -32400 1 HADT} - {1004266800 -36000 0 HAST} - {1018180800 -32400 1 HADT} - {1035716400 -36000 0 HAST} - {1049630400 -32400 1 HADT} - {1067166000 -36000 0 HAST} - {1081080000 -32400 1 HADT} - {1099220400 -36000 0 HAST} - {1112529600 -32400 1 HADT} - {1130670000 -36000 0 HAST} - {1143979200 -32400 1 HADT} - {1162119600 -36000 0 HAST} - {1173614400 -32400 1 HADT} - {1194174000 -36000 0 HAST} - {1205064000 -32400 1 HADT} - {1225623600 -36000 0 HAST} - {1236513600 -32400 1 HADT} - {1257073200 -36000 0 HAST} - {1268568000 -32400 1 HADT} - {1289127600 -36000 0 HAST} - {1300017600 -32400 1 HADT} - {1320577200 -36000 0 HAST} - {1331467200 -32400 1 HADT} - {1352026800 -36000 0 HAST} - {1362916800 -32400 1 HADT} - {1383476400 -36000 0 HAST} - {1394366400 -32400 1 HADT} - {1414926000 -36000 0 HAST} - {1425816000 -32400 1 HADT} - {1446375600 -36000 0 HAST} - {1457870400 -32400 1 HADT} - {1478430000 -36000 0 HAST} - {1489320000 -32400 1 HADT} - {1509879600 -36000 0 HAST} - {1520769600 -32400 1 HADT} - {1541329200 -36000 0 HAST} - {1552219200 -32400 1 HADT} - {1572778800 -36000 0 HAST} - {1583668800 -32400 1 HADT} - {1604228400 -36000 0 HAST} - {1615723200 -32400 1 HADT} - {1636282800 -36000 0 HAST} - {1647172800 -32400 1 HADT} - {1667732400 -36000 0 HAST} - {1678622400 -32400 1 HADT} - {1699182000 -36000 0 HAST} - {1710072000 -32400 1 HADT} - {1730631600 -36000 0 HAST} - {1741521600 -32400 1 HADT} - {1762081200 -36000 0 HAST} - {1772971200 -32400 1 HADT} - {1793530800 -36000 0 HAST} - {1805025600 -32400 1 HADT} - {1825585200 -36000 0 HAST} - {1836475200 -32400 1 HADT} - {1857034800 -36000 0 HAST} - {1867924800 -32400 1 HADT} - {1888484400 -36000 0 HAST} - {1899374400 -32400 1 HADT} - {1919934000 -36000 0 HAST} - {1930824000 -32400 1 HADT} - {1951383600 -36000 0 HAST} - {1962878400 -32400 1 HADT} - {1983438000 -36000 0 HAST} - {1994328000 -32400 1 HADT} - {2014887600 -36000 0 HAST} - {2025777600 -32400 1 HADT} - {2046337200 -36000 0 HAST} - {2057227200 -32400 1 HADT} - {2077786800 -36000 0 HAST} - {2088676800 -32400 1 HADT} - {2109236400 -36000 0 HAST} - {2120126400 -32400 1 HADT} - {2140686000 -36000 0 HAST} - {2152180800 -32400 1 HADT} - {2172740400 -36000 0 HAST} - {2183630400 -32400 1 HADT} - {2204190000 -36000 0 HAST} - {2215080000 -32400 1 HADT} - {2235639600 -36000 0 HAST} - {2246529600 -32400 1 HADT} - {2267089200 -36000 0 HAST} - {2277979200 -32400 1 HADT} - {2298538800 -36000 0 HAST} - {2309428800 -32400 1 HADT} - {2329988400 -36000 0 HAST} - {2341483200 -32400 1 HADT} - {2362042800 -36000 0 HAST} - {2372932800 -32400 1 HADT} - {2393492400 -36000 0 HAST} - {2404382400 -32400 1 HADT} - {2424942000 -36000 0 HAST} - {2435832000 -32400 1 HADT} - {2456391600 -36000 0 HAST} - {2467281600 -32400 1 HADT} - {2487841200 -36000 0 HAST} - {2499336000 -32400 1 HADT} - {2519895600 -36000 0 HAST} - {2530785600 -32400 1 HADT} - {2551345200 -36000 0 HAST} - {2562235200 -32400 1 HADT} - {2582794800 -36000 0 HAST} - {2593684800 -32400 1 HADT} - {2614244400 -36000 0 HAST} - {2625134400 -32400 1 HADT} - {2645694000 -36000 0 HAST} - {2656584000 -32400 1 HADT} - {2677143600 -36000 0 HAST} - {2688638400 -32400 1 HADT} - {2709198000 -36000 0 HAST} - {2720088000 -32400 1 HADT} - {2740647600 -36000 0 HAST} - {2751537600 -32400 1 HADT} - {2772097200 -36000 0 HAST} - {2782987200 -32400 1 HADT} - {2803546800 -36000 0 HAST} - {2814436800 -32400 1 HADT} - {2834996400 -36000 0 HAST} - {2846491200 -32400 1 HADT} - {2867050800 -36000 0 HAST} - {2877940800 -32400 1 HADT} - {2898500400 -36000 0 HAST} - {2909390400 -32400 1 HADT} - {2929950000 -36000 0 HAST} - {2940840000 -32400 1 HADT} - {2961399600 -36000 0 HAST} - {2972289600 -32400 1 HADT} - {2992849200 -36000 0 HAST} - {3003739200 -32400 1 HADT} - {3024298800 -36000 0 HAST} - {3035793600 -32400 1 HADT} - {3056353200 -36000 0 HAST} - {3067243200 -32400 1 HADT} - {3087802800 -36000 0 HAST} - {3098692800 -32400 1 HADT} - {3119252400 -36000 0 HAST} - {3130142400 -32400 1 HADT} - {3150702000 -36000 0 HAST} - {3161592000 -32400 1 HADT} - {3182151600 -36000 0 HAST} - {3193041600 -32400 1 HADT} - {3213601200 -36000 0 HAST} - {3225096000 -32400 1 HADT} - {3245655600 -36000 0 HAST} - {3256545600 -32400 1 HADT} - {3277105200 -36000 0 HAST} - {3287995200 -32400 1 HADT} - {3308554800 -36000 0 HAST} - {3319444800 -32400 1 HADT} - {3340004400 -36000 0 HAST} - {3350894400 -32400 1 HADT} - {3371454000 -36000 0 HAST} - {3382948800 -32400 1 HADT} - {3403508400 -36000 0 HAST} - {3414398400 -32400 1 HADT} - {3434958000 -36000 0 HAST} - {3445848000 -32400 1 HADT} - {3466407600 -36000 0 HAST} - {3477297600 -32400 1 HADT} - {3497857200 -36000 0 HAST} - {3508747200 -32400 1 HADT} - {3529306800 -36000 0 HAST} - {3540196800 -32400 1 HADT} - {3560756400 -36000 0 HAST} - {3572251200 -32400 1 HADT} - {3592810800 -36000 0 HAST} - {3603700800 -32400 1 HADT} - {3624260400 -36000 0 HAST} - {3635150400 -32400 1 HADT} - {3655710000 -36000 0 HAST} - {3666600000 -32400 1 HADT} - {3687159600 -36000 0 HAST} - {3698049600 -32400 1 HADT} - {3718609200 -36000 0 HAST} - {3730104000 -32400 1 HADT} - {3750663600 -36000 0 HAST} - {3761553600 -32400 1 HADT} - {3782113200 -36000 0 HAST} - {3793003200 -32400 1 HADT} - {3813562800 -36000 0 HAST} - {3824452800 -32400 1 HADT} - {3845012400 -36000 0 HAST} - {3855902400 -32400 1 HADT} - {3876462000 -36000 0 HAST} - {3887352000 -32400 1 HADT} - {3907911600 -36000 0 HAST} - {3919406400 -32400 1 HADT} - {3939966000 -36000 0 HAST} - {3950856000 -32400 1 HADT} - {3971415600 -36000 0 HAST} - {3982305600 -32400 1 HADT} - {4002865200 -36000 0 HAST} - {4013755200 -32400 1 HADT} - {4034314800 -36000 0 HAST} - {4045204800 -32400 1 HADT} - {4065764400 -36000 0 HAST} - {4076654400 -32400 1 HADT} - {4097214000 -36000 0 HAST} + {439034400 -36000 0 HST} + {452088000 -32400 1 HDT} + {467809200 -36000 0 HST} + {483537600 -32400 1 HDT} + {499258800 -36000 0 HST} + {514987200 -32400 1 HDT} + {530708400 -36000 0 HST} + {544622400 -32400 1 HDT} + {562158000 -36000 0 HST} + {576072000 -32400 1 HDT} + {594212400 -36000 0 HST} + {607521600 -32400 1 HDT} + {625662000 -36000 0 HST} + {638971200 -32400 1 HDT} + {657111600 -36000 0 HST} + {671025600 -32400 1 HDT} + {688561200 -36000 0 HST} + {702475200 -32400 1 HDT} + {720010800 -36000 0 HST} + {733924800 -32400 1 HDT} + {752065200 -36000 0 HST} + {765374400 -32400 1 HDT} + {783514800 -36000 0 HST} + {796824000 -32400 1 HDT} + {814964400 -36000 0 HST} + {828878400 -32400 1 HDT} + {846414000 -36000 0 HST} + {860328000 -32400 1 HDT} + {877863600 -36000 0 HST} + {891777600 -32400 1 HDT} + {909313200 -36000 0 HST} + {923227200 -32400 1 HDT} + {941367600 -36000 0 HST} + {954676800 -32400 1 HDT} + {972817200 -36000 0 HST} + {986126400 -32400 1 HDT} + {1004266800 -36000 0 HST} + {1018180800 -32400 1 HDT} + {1035716400 -36000 0 HST} + {1049630400 -32400 1 HDT} + {1067166000 -36000 0 HST} + {1081080000 -32400 1 HDT} + {1099220400 -36000 0 HST} + {1112529600 -32400 1 HDT} + {1130670000 -36000 0 HST} + {1143979200 -32400 1 HDT} + {1162119600 -36000 0 HST} + {1173614400 -32400 1 HDT} + {1194174000 -36000 0 HST} + {1205064000 -32400 1 HDT} + {1225623600 -36000 0 HST} + {1236513600 -32400 1 HDT} + {1257073200 -36000 0 HST} + {1268568000 -32400 1 HDT} + {1289127600 -36000 0 HST} + {1300017600 -32400 1 HDT} + {1320577200 -36000 0 HST} + {1331467200 -32400 1 HDT} + {1352026800 -36000 0 HST} + {1362916800 -32400 1 HDT} + {1383476400 -36000 0 HST} + {1394366400 -32400 1 HDT} + {1414926000 -36000 0 HST} + {1425816000 -32400 1 HDT} + {1446375600 -36000 0 HST} + {1457870400 -32400 1 HDT} + {1478430000 -36000 0 HST} + {1489320000 -32400 1 HDT} + {1509879600 -36000 0 HST} + {1520769600 -32400 1 HDT} + {1541329200 -36000 0 HST} + {1552219200 -32400 1 HDT} + {1572778800 -36000 0 HST} + {1583668800 -32400 1 HDT} + {1604228400 -36000 0 HST} + {1615723200 -32400 1 HDT} + {1636282800 -36000 0 HST} + {1647172800 -32400 1 HDT} + {1667732400 -36000 0 HST} + {1678622400 -32400 1 HDT} + {1699182000 -36000 0 HST} + {1710072000 -32400 1 HDT} + {1730631600 -36000 0 HST} + {1741521600 -32400 1 HDT} + {1762081200 -36000 0 HST} + {1772971200 -32400 1 HDT} + {1793530800 -36000 0 HST} + {1805025600 -32400 1 HDT} + {1825585200 -36000 0 HST} + {1836475200 -32400 1 HDT} + {1857034800 -36000 0 HST} + {1867924800 -32400 1 HDT} + {1888484400 -36000 0 HST} + {1899374400 -32400 1 HDT} + {1919934000 -36000 0 HST} + {1930824000 -32400 1 HDT} + {1951383600 -36000 0 HST} + {1962878400 -32400 1 HDT} + {1983438000 -36000 0 HST} + {1994328000 -32400 1 HDT} + {2014887600 -36000 0 HST} + {2025777600 -32400 1 HDT} + {2046337200 -36000 0 HST} + {2057227200 -32400 1 HDT} + {2077786800 -36000 0 HST} + {2088676800 -32400 1 HDT} + {2109236400 -36000 0 HST} + {2120126400 -32400 1 HDT} + {2140686000 -36000 0 HST} + {2152180800 -32400 1 HDT} + {2172740400 -36000 0 HST} + {2183630400 -32400 1 HDT} + {2204190000 -36000 0 HST} + {2215080000 -32400 1 HDT} + {2235639600 -36000 0 HST} + {2246529600 -32400 1 HDT} + {2267089200 -36000 0 HST} + {2277979200 -32400 1 HDT} + {2298538800 -36000 0 HST} + {2309428800 -32400 1 HDT} + {2329988400 -36000 0 HST} + {2341483200 -32400 1 HDT} + {2362042800 -36000 0 HST} + {2372932800 -32400 1 HDT} + {2393492400 -36000 0 HST} + {2404382400 -32400 1 HDT} + {2424942000 -36000 0 HST} + {2435832000 -32400 1 HDT} + {2456391600 -36000 0 HST} + {2467281600 -32400 1 HDT} + {2487841200 -36000 0 HST} + {2499336000 -32400 1 HDT} + {2519895600 -36000 0 HST} + {2530785600 -32400 1 HDT} + {2551345200 -36000 0 HST} + {2562235200 -32400 1 HDT} + {2582794800 -36000 0 HST} + {2593684800 -32400 1 HDT} + {2614244400 -36000 0 HST} + {2625134400 -32400 1 HDT} + {2645694000 -36000 0 HST} + {2656584000 -32400 1 HDT} + {2677143600 -36000 0 HST} + {2688638400 -32400 1 HDT} + {2709198000 -36000 0 HST} + {2720088000 -32400 1 HDT} + {2740647600 -36000 0 HST} + {2751537600 -32400 1 HDT} + {2772097200 -36000 0 HST} + {2782987200 -32400 1 HDT} + {2803546800 -36000 0 HST} + {2814436800 -32400 1 HDT} + {2834996400 -36000 0 HST} + {2846491200 -32400 1 HDT} + {2867050800 -36000 0 HST} + {2877940800 -32400 1 HDT} + {2898500400 -36000 0 HST} + {2909390400 -32400 1 HDT} + {2929950000 -36000 0 HST} + {2940840000 -32400 1 HDT} + {2961399600 -36000 0 HST} + {2972289600 -32400 1 HDT} + {2992849200 -36000 0 HST} + {3003739200 -32400 1 HDT} + {3024298800 -36000 0 HST} + {3035793600 -32400 1 HDT} + {3056353200 -36000 0 HST} + {3067243200 -32400 1 HDT} + {3087802800 -36000 0 HST} + {3098692800 -32400 1 HDT} + {3119252400 -36000 0 HST} + {3130142400 -32400 1 HDT} + {3150702000 -36000 0 HST} + {3161592000 -32400 1 HDT} + {3182151600 -36000 0 HST} + {3193041600 -32400 1 HDT} + {3213601200 -36000 0 HST} + {3225096000 -32400 1 HDT} + {3245655600 -36000 0 HST} + {3256545600 -32400 1 HDT} + {3277105200 -36000 0 HST} + {3287995200 -32400 1 HDT} + {3308554800 -36000 0 HST} + {3319444800 -32400 1 HDT} + {3340004400 -36000 0 HST} + {3350894400 -32400 1 HDT} + {3371454000 -36000 0 HST} + {3382948800 -32400 1 HDT} + {3403508400 -36000 0 HST} + {3414398400 -32400 1 HDT} + {3434958000 -36000 0 HST} + {3445848000 -32400 1 HDT} + {3466407600 -36000 0 HST} + {3477297600 -32400 1 HDT} + {3497857200 -36000 0 HST} + {3508747200 -32400 1 HDT} + {3529306800 -36000 0 HST} + {3540196800 -32400 1 HDT} + {3560756400 -36000 0 HST} + {3572251200 -32400 1 HDT} + {3592810800 -36000 0 HST} + {3603700800 -32400 1 HDT} + {3624260400 -36000 0 HST} + {3635150400 -32400 1 HDT} + {3655710000 -36000 0 HST} + {3666600000 -32400 1 HDT} + {3687159600 -36000 0 HST} + {3698049600 -32400 1 HDT} + {3718609200 -36000 0 HST} + {3730104000 -32400 1 HDT} + {3750663600 -36000 0 HST} + {3761553600 -32400 1 HDT} + {3782113200 -36000 0 HST} + {3793003200 -32400 1 HDT} + {3813562800 -36000 0 HST} + {3824452800 -32400 1 HDT} + {3845012400 -36000 0 HST} + {3855902400 -32400 1 HDT} + {3876462000 -36000 0 HST} + {3887352000 -32400 1 HDT} + {3907911600 -36000 0 HST} + {3919406400 -32400 1 HDT} + {3939966000 -36000 0 HST} + {3950856000 -32400 1 HDT} + {3971415600 -36000 0 HST} + {3982305600 -32400 1 HDT} + {4002865200 -36000 0 HST} + {4013755200 -32400 1 HDT} + {4034314800 -36000 0 HST} + {4045204800 -32400 1 HDT} + {4065764400 -36000 0 HST} + {4076654400 -32400 1 HDT} + {4097214000 -36000 0 HST} } diff --git a/library/tzdata/America/Antigua b/library/tzdata/America/Antigua index 5433e9b..be0c88e 100644 --- a/library/tzdata/America/Antigua +++ b/library/tzdata/America/Antigua @@ -1,7 +1,5 @@ # created by tools/tclZIC.tcl - do not edit - -set TZData(:America/Antigua) { - {-9223372036854775808 -14832 0 LMT} - {-1825098768 -18000 0 EST} - {-599598000 -14400 0 AST} +if {![info exists TZData(America/Port_of_Spain)]} { + LoadTimeZoneFile America/Port_of_Spain } +set TZData(:America/Antigua) $TZData(:America/Port_of_Spain) diff --git a/library/tzdata/America/Cayman b/library/tzdata/America/Cayman index 3e2e3cc..5231ca9 100644 --- a/library/tzdata/America/Cayman +++ b/library/tzdata/America/Cayman @@ -4,4 +4,173 @@ set TZData(:America/Cayman) { {-9223372036854775808 -19532 0 LMT} {-2524502068 -18431 0 KMT} {-1827687169 -18000 0 EST} + {1451624400 -18000 0 EST} + {1457852400 -14400 1 EDT} + {1478412000 -18000 0 EST} + {1489302000 -14400 1 EDT} + {1509861600 -18000 0 EST} + {1520751600 -14400 1 EDT} + {1541311200 -18000 0 EST} + {1552201200 -14400 1 EDT} + {1572760800 -18000 0 EST} + {1583650800 -14400 1 EDT} + {1604210400 -18000 0 EST} + {1615705200 -14400 1 EDT} + {1636264800 -18000 0 EST} + {1647154800 -14400 1 EDT} + {1667714400 -18000 0 EST} + {1678604400 -14400 1 EDT} + {1699164000 -18000 0 EST} + {1710054000 -14400 1 EDT} + {1730613600 -18000 0 EST} + {1741503600 -14400 1 EDT} + {1762063200 -18000 0 EST} + {1772953200 -14400 1 EDT} + {1793512800 -18000 0 EST} + {1805007600 -14400 1 EDT} + {1825567200 -18000 0 EST} + {1836457200 -14400 1 EDT} + {1857016800 -18000 0 EST} + {1867906800 -14400 1 EDT} + {1888466400 -18000 0 EST} + {1899356400 -14400 1 EDT} + {1919916000 -18000 0 EST} + {1930806000 -14400 1 EDT} + {1951365600 -18000 0 EST} + {1962860400 -14400 1 EDT} + {1983420000 -18000 0 EST} + {1994310000 -14400 1 EDT} + {2014869600 -18000 0 EST} + {2025759600 -14400 1 EDT} + {2046319200 -18000 0 EST} + {2057209200 -14400 1 EDT} + {2077768800 -18000 0 EST} + {2088658800 -14400 1 EDT} + {2109218400 -18000 0 EST} + {2120108400 -14400 1 EDT} + {2140668000 -18000 0 EST} + {2152162800 -14400 1 EDT} + {2172722400 -18000 0 EST} + {2183612400 -14400 1 EDT} + {2204172000 -18000 0 EST} + {2215062000 -14400 1 EDT} + {2235621600 -18000 0 EST} + {2246511600 -14400 1 EDT} + {2267071200 -18000 0 EST} + {2277961200 -14400 1 EDT} + {2298520800 -18000 0 EST} + {2309410800 -14400 1 EDT} + {2329970400 -18000 0 EST} + {2341465200 -14400 1 EDT} + {2362024800 -18000 0 EST} + {2372914800 -14400 1 EDT} + {2393474400 -18000 0 EST} + {2404364400 -14400 1 EDT} + {2424924000 -18000 0 EST} + {2435814000 -14400 1 EDT} + {2456373600 -18000 0 EST} + {2467263600 -14400 1 EDT} + {2487823200 -18000 0 EST} + {2499318000 -14400 1 EDT} + {2519877600 -18000 0 EST} + {2530767600 -14400 1 EDT} + {2551327200 -18000 0 EST} + {2562217200 -14400 1 EDT} + {2582776800 -18000 0 EST} + {2593666800 -14400 1 EDT} + {2614226400 -18000 0 EST} + {2625116400 -14400 1 EDT} + {2645676000 -18000 0 EST} + {2656566000 -14400 1 EDT} + {2677125600 -18000 0 EST} + {2688620400 -14400 1 EDT} + {2709180000 -18000 0 EST} + {2720070000 -14400 1 EDT} + {2740629600 -18000 0 EST} + {2751519600 -14400 1 EDT} + {2772079200 -18000 0 EST} + {2782969200 -14400 1 EDT} + {2803528800 -18000 0 EST} + {2814418800 -14400 1 EDT} + {2834978400 -18000 0 EST} + {2846473200 -14400 1 EDT} + {2867032800 -18000 0 EST} + {2877922800 -14400 1 EDT} + {2898482400 -18000 0 EST} + {2909372400 -14400 1 EDT} + {2929932000 -18000 0 EST} + {2940822000 -14400 1 EDT} + {2961381600 -18000 0 EST} + {2972271600 -14400 1 EDT} + {2992831200 -18000 0 EST} + {3003721200 -14400 1 EDT} + {3024280800 -18000 0 EST} + {3035775600 -14400 1 EDT} + {3056335200 -18000 0 EST} + {3067225200 -14400 1 EDT} + {3087784800 -18000 0 EST} + {3098674800 -14400 1 EDT} + {3119234400 -18000 0 EST} + {3130124400 -14400 1 EDT} + {3150684000 -18000 0 EST} + {3161574000 -14400 1 EDT} + {3182133600 -18000 0 EST} + {3193023600 -14400 1 EDT} + {3213583200 -18000 0 EST} + {3225078000 -14400 1 EDT} + {3245637600 -18000 0 EST} + {3256527600 -14400 1 EDT} + {3277087200 -18000 0 EST} + {3287977200 -14400 1 EDT} + {3308536800 -18000 0 EST} + {3319426800 -14400 1 EDT} + {3339986400 -18000 0 EST} + {3350876400 -14400 1 EDT} + {3371436000 -18000 0 EST} + {3382930800 -14400 1 EDT} + {3403490400 -18000 0 EST} + {3414380400 -14400 1 EDT} + {3434940000 -18000 0 EST} + {3445830000 -14400 1 EDT} + {3466389600 -18000 0 EST} + {3477279600 -14400 1 EDT} + {3497839200 -18000 0 EST} + {3508729200 -14400 1 EDT} + {3529288800 -18000 0 EST} + {3540178800 -14400 1 EDT} + {3560738400 -18000 0 EST} + {3572233200 -14400 1 EDT} + {3592792800 -18000 0 EST} + {3603682800 -14400 1 EDT} + {3624242400 -18000 0 EST} + {3635132400 -14400 1 EDT} + {3655692000 -18000 0 EST} + {3666582000 -14400 1 EDT} + {3687141600 -18000 0 EST} + {3698031600 -14400 1 EDT} + {3718591200 -18000 0 EST} + {3730086000 -14400 1 EDT} + {3750645600 -18000 0 EST} + {3761535600 -14400 1 EDT} + {3782095200 -18000 0 EST} + {3792985200 -14400 1 EDT} + {3813544800 -18000 0 EST} + {3824434800 -14400 1 EDT} + {3844994400 -18000 0 EST} + {3855884400 -14400 1 EDT} + {3876444000 -18000 0 EST} + {3887334000 -14400 1 EDT} + {3907893600 -18000 0 EST} + {3919388400 -14400 1 EDT} + {3939948000 -18000 0 EST} + {3950838000 -14400 1 EDT} + {3971397600 -18000 0 EST} + {3982287600 -14400 1 EDT} + {4002847200 -18000 0 EST} + {4013737200 -14400 1 EDT} + {4034296800 -18000 0 EST} + {4045186800 -14400 1 EDT} + {4065746400 -18000 0 EST} + {4076636400 -14400 1 EDT} + {4097196000 -18000 0 EST} } diff --git a/library/tzdata/America/Montevideo b/library/tzdata/America/Montevideo index aa469b9..91a5117 100644 --- a/library/tzdata/America/Montevideo +++ b/library/tzdata/America/Montevideo @@ -89,173 +89,4 @@ set TZData(:America/Montevideo) { {1394337600 -10800 0 UYT} {1412485200 -7200 1 UYST} {1425787200 -10800 0 UYT} - {1443934800 -7200 1 UYST} - {1457841600 -10800 0 UYT} - {1475384400 -7200 1 UYST} - {1489291200 -10800 0 UYT} - {1506834000 -7200 1 UYST} - {1520740800 -10800 0 UYT} - {1538888400 -7200 1 UYST} - {1552190400 -10800 0 UYT} - {1570338000 -7200 1 UYST} - {1583640000 -10800 0 UYT} - {1601787600 -7200 1 UYST} - {1615694400 -10800 0 UYT} - {1633237200 -7200 1 UYST} - {1647144000 -10800 0 UYT} - {1664686800 -7200 1 UYST} - {1678593600 -10800 0 UYT} - {1696136400 -7200 1 UYST} - {1710043200 -10800 0 UYT} - {1728190800 -7200 1 UYST} - {1741492800 -10800 0 UYT} - {1759640400 -7200 1 UYST} - {1772942400 -10800 0 UYT} - {1791090000 -7200 1 UYST} - {1804996800 -10800 0 UYT} - {1822539600 -7200 1 UYST} - {1836446400 -10800 0 UYT} - {1853989200 -7200 1 UYST} - {1867896000 -10800 0 UYT} - {1886043600 -7200 1 UYST} - {1899345600 -10800 0 UYT} - {1917493200 -7200 1 UYST} - {1930795200 -10800 0 UYT} - {1948942800 -7200 1 UYST} - {1962849600 -10800 0 UYT} - {1980392400 -7200 1 UYST} - {1994299200 -10800 0 UYT} - {2011842000 -7200 1 UYST} - {2025748800 -10800 0 UYT} - {2043291600 -7200 1 UYST} - {2057198400 -10800 0 UYT} - {2075346000 -7200 1 UYST} - {2088648000 -10800 0 UYT} - {2106795600 -7200 1 UYST} - {2120097600 -10800 0 UYT} - {2138245200 -7200 1 UYST} - {2152152000 -10800 0 UYT} - {2169694800 -7200 1 UYST} - {2183601600 -10800 0 UYT} - {2201144400 -7200 1 UYST} - {2215051200 -10800 0 UYT} - {2233198800 -7200 1 UYST} - {2246500800 -10800 0 UYT} - {2264648400 -7200 1 UYST} - {2277950400 -10800 0 UYT} - {2296098000 -7200 1 UYST} - {2309400000 -10800 0 UYT} - {2327547600 -7200 1 UYST} - {2341454400 -10800 0 UYT} - {2358997200 -7200 1 UYST} - {2372904000 -10800 0 UYT} - {2390446800 -7200 1 UYST} - {2404353600 -10800 0 UYT} - {2422501200 -7200 1 UYST} - {2435803200 -10800 0 UYT} - {2453950800 -7200 1 UYST} - {2467252800 -10800 0 UYT} - {2485400400 -7200 1 UYST} - {2499307200 -10800 0 UYT} - {2516850000 -7200 1 UYST} - {2530756800 -10800 0 UYT} - {2548299600 -7200 1 UYST} - {2562206400 -10800 0 UYT} - {2579749200 -7200 1 UYST} - {2593656000 -10800 0 UYT} - {2611803600 -7200 1 UYST} - {2625105600 -10800 0 UYT} - {2643253200 -7200 1 UYST} - {2656555200 -10800 0 UYT} - {2674702800 -7200 1 UYST} - {2688609600 -10800 0 UYT} - {2706152400 -7200 1 UYST} - {2720059200 -10800 0 UYT} - {2737602000 -7200 1 UYST} - {2751508800 -10800 0 UYT} - {2769656400 -7200 1 UYST} - {2782958400 -10800 0 UYT} - {2801106000 -7200 1 UYST} - {2814408000 -10800 0 UYT} - {2832555600 -7200 1 UYST} - {2846462400 -10800 0 UYT} - {2864005200 -7200 1 UYST} - {2877912000 -10800 0 UYT} - {2895454800 -7200 1 UYST} - {2909361600 -10800 0 UYT} - {2926904400 -7200 1 UYST} - {2940811200 -10800 0 UYT} - {2958958800 -7200 1 UYST} - {2972260800 -10800 0 UYT} - {2990408400 -7200 1 UYST} - {3003710400 -10800 0 UYT} - {3021858000 -7200 1 UYST} - {3035764800 -10800 0 UYT} - {3053307600 -7200 1 UYST} - {3067214400 -10800 0 UYT} - {3084757200 -7200 1 UYST} - {3098664000 -10800 0 UYT} - {3116811600 -7200 1 UYST} - {3130113600 -10800 0 UYT} - {3148261200 -7200 1 UYST} - {3161563200 -10800 0 UYT} - {3179710800 -7200 1 UYST} - {3193012800 -10800 0 UYT} - {3211160400 -7200 1 UYST} - {3225067200 -10800 0 UYT} - {3242610000 -7200 1 UYST} - {3256516800 -10800 0 UYT} - {3274059600 -7200 1 UYST} - {3287966400 -10800 0 UYT} - {3306114000 -7200 1 UYST} - {3319416000 -10800 0 UYT} - {3337563600 -7200 1 UYST} - {3350865600 -10800 0 UYT} - {3369013200 -7200 1 UYST} - {3382920000 -10800 0 UYT} - {3400462800 -7200 1 UYST} - {3414369600 -10800 0 UYT} - {3431912400 -7200 1 UYST} - {3445819200 -10800 0 UYT} - {3463362000 -7200 1 UYST} - {3477268800 -10800 0 UYT} - {3495416400 -7200 1 UYST} - {3508718400 -10800 0 UYT} - {3526866000 -7200 1 UYST} - {3540168000 -10800 0 UYT} - {3558315600 -7200 1 UYST} - {3572222400 -10800 0 UYT} - {3589765200 -7200 1 UYST} - {3603672000 -10800 0 UYT} - {3621214800 -7200 1 UYST} - {3635121600 -10800 0 UYT} - {3653269200 -7200 1 UYST} - {3666571200 -10800 0 UYT} - {3684718800 -7200 1 UYST} - {3698020800 -10800 0 UYT} - {3716168400 -7200 1 UYST} - {3730075200 -10800 0 UYT} - {3747618000 -7200 1 UYST} - {3761524800 -10800 0 UYT} - {3779067600 -7200 1 UYST} - {3792974400 -10800 0 UYT} - {3810517200 -7200 1 UYST} - {3824424000 -10800 0 UYT} - {3842571600 -7200 1 UYST} - {3855873600 -10800 0 UYT} - {3874021200 -7200 1 UYST} - {3887323200 -10800 0 UYT} - {3905470800 -7200 1 UYST} - {3919377600 -10800 0 UYT} - {3936920400 -7200 1 UYST} - {3950827200 -10800 0 UYT} - {3968370000 -7200 1 UYST} - {3982276800 -10800 0 UYT} - {4000424400 -7200 1 UYST} - {4013726400 -10800 0 UYT} - {4031874000 -7200 1 UYST} - {4045176000 -10800 0 UYT} - {4063323600 -7200 1 UYST} - {4076625600 -10800 0 UYT} - {4094773200 -7200 1 UYST} } diff --git a/library/tzdata/America/Montreal b/library/tzdata/America/Montreal index bebe7dc..0ead8ee 100644 --- a/library/tzdata/America/Montreal +++ b/library/tzdata/America/Montreal @@ -1,366 +1,5 @@ # created by tools/tclZIC.tcl - do not edit - -set TZData(:America/Montreal) { - {-9223372036854775808 -17656 0 LMT} - {-2713892744 -18000 0 EST} - {-1665334800 -14400 1 EDT} - {-1662753600 -18000 0 EST} - {-1640977200 -18000 0 EST} - {-1632070800 -14400 1 EDT} - {-1615140000 -18000 0 EST} - {-1609441200 -18000 0 EST} - {-1601742600 -14400 1 EDT} - {-1583775000 -18000 0 EST} - {-1567355400 -14400 1 EDT} - {-1554053400 -18000 0 EST} - {-1535907600 -14400 1 EDT} - {-1522603800 -18000 0 EST} - {-1504458000 -14400 1 EDT} - {-1491154200 -18000 0 EST} - {-1439830800 -14400 1 EDT} - {-1428255000 -18000 0 EST} - {-1409504400 -14400 1 EDT} - {-1396805400 -18000 0 EST} - {-1378054800 -14400 1 EDT} - {-1365355800 -18000 0 EST} - {-1346612400 -14400 1 EDT} - {-1333915200 -18000 0 EST} - {-1315162800 -14400 1 EDT} - {-1301860800 -18000 0 EST} - {-1283713200 -14400 1 EDT} - {-1270411200 -18000 0 EST} - {-1252263600 -14400 1 EDT} - {-1238961600 -18000 0 EST} - {-1220814000 -14400 1 EDT} - {-1207512000 -18000 0 EST} - {-1188759600 -14400 1 EDT} - {-1176062400 -18000 0 EST} - {-1157310000 -14400 1 EDT} - {-1144008000 -18000 0 EST} - {-1125860400 -14400 1 EDT} - {-1112558400 -18000 0 EST} - {-1094410800 -14400 1 EDT} - {-1081108800 -18000 0 EST} - {-1062961200 -14400 1 EDT} - {-1049659200 -18000 0 EST} - {-1031511600 -14400 1 EDT} - {-1018209600 -18000 0 EST} - {-1000062000 -14400 1 EDT} - {-986760000 -18000 0 EST} - {-968007600 -14400 1 EDT} - {-955310400 -18000 0 EST} - {-936558000 -14400 1 EDT} - {-880218000 -14400 0 EWT} - {-769395600 -14400 1 EPT} - {-765396000 -18000 0 EST} - {-757364400 -18000 0 EST} - {-747248400 -14400 1 EDT} - {-733946400 -18000 0 EST} - {-715798800 -14400 1 EDT} - {-702496800 -18000 0 EST} - {-684349200 -14400 1 EDT} - {-671047200 -18000 0 EST} - {-652899600 -14400 1 EDT} - {-636573600 -18000 0 EST} - {-620845200 -14400 1 EDT} - {-605124000 -18000 0 EST} - {-589395600 -14400 1 EDT} - {-576093600 -18000 0 EST} - {-557946000 -14400 1 EDT} - {-544644000 -18000 0 EST} - {-526496400 -14400 1 EDT} - {-513194400 -18000 0 EST} - {-495046800 -14400 1 EDT} - {-481744800 -18000 0 EST} - {-463597200 -14400 1 EDT} - {-450295200 -18000 0 EST} - {-431542800 -14400 1 EDT} - {-418240800 -18000 0 EST} - {-400093200 -14400 1 EDT} - {-384372000 -18000 0 EST} - {-368643600 -14400 1 EDT} - {-352922400 -18000 0 EST} - {-337194000 -14400 1 EDT} - {-321472800 -18000 0 EST} - {-305744400 -14400 1 EDT} - {-289418400 -18000 0 EST} - {-273690000 -14400 1 EDT} - {-257968800 -18000 0 EST} - {-242240400 -14400 1 EDT} - {-226519200 -18000 0 EST} - {-210790800 -14400 1 EDT} - {-195069600 -18000 0 EST} - {-179341200 -14400 1 EDT} - {-163620000 -18000 0 EST} - {-147891600 -14400 1 EDT} - {-131565600 -18000 0 EST} - {-116442000 -14400 1 EDT} - {-100116000 -18000 0 EST} - {-84387600 -14400 1 EDT} - {-68666400 -18000 0 EST} - {-52938000 -14400 1 EDT} - {-37216800 -18000 0 EST} - {-21488400 -14400 1 EDT} - {-5767200 -18000 0 EST} - {9961200 -14400 1 EDT} - {25682400 -18000 0 EST} - {41410800 -14400 1 EDT} - {57736800 -18000 0 EST} - {73465200 -14400 1 EDT} - {89186400 -18000 0 EST} - {104914800 -14400 1 EDT} - {120636000 -18000 0 EST} - {126248400 -18000 0 EST} - {136364400 -14400 1 EDT} - {152085600 -18000 0 EST} - {167814000 -14400 1 EDT} - {183535200 -18000 0 EST} - {199263600 -14400 1 EDT} - {215589600 -18000 0 EST} - {230713200 -14400 1 EDT} - {247039200 -18000 0 EST} - {262767600 -14400 1 EDT} - {278488800 -18000 0 EST} - {294217200 -14400 1 EDT} - {309938400 -18000 0 EST} - {325666800 -14400 1 EDT} - {341388000 -18000 0 EST} - {357116400 -14400 1 EDT} - {372837600 -18000 0 EST} - {388566000 -14400 1 EDT} - {404892000 -18000 0 EST} - {420015600 -14400 1 EDT} - {436341600 -18000 0 EST} - {452070000 -14400 1 EDT} - {467791200 -18000 0 EST} - {483519600 -14400 1 EDT} - {499240800 -18000 0 EST} - {514969200 -14400 1 EDT} - {530690400 -18000 0 EST} - {544604400 -14400 1 EDT} - {562140000 -18000 0 EST} - {576054000 -14400 1 EDT} - {594194400 -18000 0 EST} - {607503600 -14400 1 EDT} - {625644000 -18000 0 EST} - {638953200 -14400 1 EDT} - {657093600 -18000 0 EST} - {671007600 -14400 1 EDT} - {688543200 -18000 0 EST} - {702457200 -14400 1 EDT} - {719992800 -18000 0 EST} - {733906800 -14400 1 EDT} - {752047200 -18000 0 EST} - {765356400 -14400 1 EDT} - {783496800 -18000 0 EST} - {796806000 -14400 1 EDT} - {814946400 -18000 0 EST} - {828860400 -14400 1 EDT} - {846396000 -18000 0 EST} - {860310000 -14400 1 EDT} - {877845600 -18000 0 EST} - {891759600 -14400 1 EDT} - {909295200 -18000 0 EST} - {923209200 -14400 1 EDT} - {941349600 -18000 0 EST} - {954658800 -14400 1 EDT} - {972799200 -18000 0 EST} - {986108400 -14400 1 EDT} - {1004248800 -18000 0 EST} - {1018162800 -14400 1 EDT} - {1035698400 -18000 0 EST} - {1049612400 -14400 1 EDT} - {1067148000 -18000 0 EST} - {1081062000 -14400 1 EDT} - {1099202400 -18000 0 EST} - {1112511600 -14400 1 EDT} - {1130652000 -18000 0 EST} - {1143961200 -14400 1 EDT} - {1162101600 -18000 0 EST} - {1173596400 -14400 1 EDT} - {1194156000 -18000 0 EST} - {1205046000 -14400 1 EDT} - {1225605600 -18000 0 EST} - {1236495600 -14400 1 EDT} - {1257055200 -18000 0 EST} - {1268550000 -14400 1 EDT} - {1289109600 -18000 0 EST} - {1299999600 -14400 1 EDT} - {1320559200 -18000 0 EST} - {1331449200 -14400 1 EDT} - {1352008800 -18000 0 EST} - {1362898800 -14400 1 EDT} - {1383458400 -18000 0 EST} - {1394348400 -14400 1 EDT} - {1414908000 -18000 0 EST} - {1425798000 -14400 1 EDT} - {1446357600 -18000 0 EST} - {1457852400 -14400 1 EDT} - {1478412000 -18000 0 EST} - {1489302000 -14400 1 EDT} - {1509861600 -18000 0 EST} - {1520751600 -14400 1 EDT} - {1541311200 -18000 0 EST} - {1552201200 -14400 1 EDT} - {1572760800 -18000 0 EST} - {1583650800 -14400 1 EDT} - {1604210400 -18000 0 EST} - {1615705200 -14400 1 EDT} - {1636264800 -18000 0 EST} - {1647154800 -14400 1 EDT} - {1667714400 -18000 0 EST} - {1678604400 -14400 1 EDT} - {1699164000 -18000 0 EST} - {1710054000 -14400 1 EDT} - {1730613600 -18000 0 EST} - {1741503600 -14400 1 EDT} - {1762063200 -18000 0 EST} - {1772953200 -14400 1 EDT} - {1793512800 -18000 0 EST} - {1805007600 -14400 1 EDT} - {1825567200 -18000 0 EST} - {1836457200 -14400 1 EDT} - {1857016800 -18000 0 EST} - {1867906800 -14400 1 EDT} - {1888466400 -18000 0 EST} - {1899356400 -14400 1 EDT} - {1919916000 -18000 0 EST} - {1930806000 -14400 1 EDT} - {1951365600 -18000 0 EST} - {1962860400 -14400 1 EDT} - {1983420000 -18000 0 EST} - {1994310000 -14400 1 EDT} - {2014869600 -18000 0 EST} - {2025759600 -14400 1 EDT} - {2046319200 -18000 0 EST} - {2057209200 -14400 1 EDT} - {2077768800 -18000 0 EST} - {2088658800 -14400 1 EDT} - {2109218400 -18000 0 EST} - {2120108400 -14400 1 EDT} - {2140668000 -18000 0 EST} - {2152162800 -14400 1 EDT} - {2172722400 -18000 0 EST} - {2183612400 -14400 1 EDT} - {2204172000 -18000 0 EST} - {2215062000 -14400 1 EDT} - {2235621600 -18000 0 EST} - {2246511600 -14400 1 EDT} - {2267071200 -18000 0 EST} - {2277961200 -14400 1 EDT} - {2298520800 -18000 0 EST} - {2309410800 -14400 1 EDT} - {2329970400 -18000 0 EST} - {2341465200 -14400 1 EDT} - {2362024800 -18000 0 EST} - {2372914800 -14400 1 EDT} - {2393474400 -18000 0 EST} - {2404364400 -14400 1 EDT} - {2424924000 -18000 0 EST} - {2435814000 -14400 1 EDT} - {2456373600 -18000 0 EST} - {2467263600 -14400 1 EDT} - {2487823200 -18000 0 EST} - {2499318000 -14400 1 EDT} - {2519877600 -18000 0 EST} - {2530767600 -14400 1 EDT} - {2551327200 -18000 0 EST} - {2562217200 -14400 1 EDT} - {2582776800 -18000 0 EST} - {2593666800 -14400 1 EDT} - {2614226400 -18000 0 EST} - {2625116400 -14400 1 EDT} - {2645676000 -18000 0 EST} - {2656566000 -14400 1 EDT} - {2677125600 -18000 0 EST} - {2688620400 -14400 1 EDT} - {2709180000 -18000 0 EST} - {2720070000 -14400 1 EDT} - {2740629600 -18000 0 EST} - {2751519600 -14400 1 EDT} - {2772079200 -18000 0 EST} - {2782969200 -14400 1 EDT} - {2803528800 -18000 0 EST} - {2814418800 -14400 1 EDT} - {2834978400 -18000 0 EST} - {2846473200 -14400 1 EDT} - {2867032800 -18000 0 EST} - {2877922800 -14400 1 EDT} - {2898482400 -18000 0 EST} - {2909372400 -14400 1 EDT} - {2929932000 -18000 0 EST} - {2940822000 -14400 1 EDT} - {2961381600 -18000 0 EST} - {2972271600 -14400 1 EDT} - {2992831200 -18000 0 EST} - {3003721200 -14400 1 EDT} - {3024280800 -18000 0 EST} - {3035775600 -14400 1 EDT} - {3056335200 -18000 0 EST} - {3067225200 -14400 1 EDT} - {3087784800 -18000 0 EST} - {3098674800 -14400 1 EDT} - {3119234400 -18000 0 EST} - {3130124400 -14400 1 EDT} - {3150684000 -18000 0 EST} - {3161574000 -14400 1 EDT} - {3182133600 -18000 0 EST} - {3193023600 -14400 1 EDT} - {3213583200 -18000 0 EST} - {3225078000 -14400 1 EDT} - {3245637600 -18000 0 EST} - {3256527600 -14400 1 EDT} - {3277087200 -18000 0 EST} - {3287977200 -14400 1 EDT} - {3308536800 -18000 0 EST} - {3319426800 -14400 1 EDT} - {3339986400 -18000 0 EST} - {3350876400 -14400 1 EDT} - {3371436000 -18000 0 EST} - {3382930800 -14400 1 EDT} - {3403490400 -18000 0 EST} - {3414380400 -14400 1 EDT} - {3434940000 -18000 0 EST} - {3445830000 -14400 1 EDT} - {3466389600 -18000 0 EST} - {3477279600 -14400 1 EDT} - {3497839200 -18000 0 EST} - {3508729200 -14400 1 EDT} - {3529288800 -18000 0 EST} - {3540178800 -14400 1 EDT} - {3560738400 -18000 0 EST} - {3572233200 -14400 1 EDT} - {3592792800 -18000 0 EST} - {3603682800 -14400 1 EDT} - {3624242400 -18000 0 EST} - {3635132400 -14400 1 EDT} - {3655692000 -18000 0 EST} - {3666582000 -14400 1 EDT} - {3687141600 -18000 0 EST} - {3698031600 -14400 1 EDT} - {3718591200 -18000 0 EST} - {3730086000 -14400 1 EDT} - {3750645600 -18000 0 EST} - {3761535600 -14400 1 EDT} - {3782095200 -18000 0 EST} - {3792985200 -14400 1 EDT} - {3813544800 -18000 0 EST} - {3824434800 -14400 1 EDT} - {3844994400 -18000 0 EST} - {3855884400 -14400 1 EDT} - {3876444000 -18000 0 EST} - {3887334000 -14400 1 EDT} - {3907893600 -18000 0 EST} - {3919388400 -14400 1 EDT} - {3939948000 -18000 0 EST} - {3950838000 -14400 1 EDT} - {3971397600 -18000 0 EST} - {3982287600 -14400 1 EDT} - {4002847200 -18000 0 EST} - {4013737200 -14400 1 EDT} - {4034296800 -18000 0 EST} - {4045186800 -14400 1 EDT} - {4065746400 -18000 0 EST} - {4076636400 -14400 1 EDT} - {4097196000 -18000 0 EST} +if {![info exists TZData(America/Toronto)]} { + LoadTimeZoneFile America/Toronto } +set TZData(:America/Montreal) $TZData(:America/Toronto) diff --git a/library/tzdata/America/Santiago b/library/tzdata/America/Santiago index 29c2a93..b6d9b38 100644 --- a/library/tzdata/America/Santiago +++ b/library/tzdata/America/Santiago @@ -3,9 +3,9 @@ set TZData(:America/Santiago) { {-9223372036854775808 -16966 0 LMT} {-2524504634 -16966 0 SMT} - {-1893439034 -18000 0 CLT} + {-1892661434 -18000 0 CLT} {-1688410800 -16966 0 SMT} - {-1619983034 -14400 0 CLT} + {-1619205434 -14400 0 CLT} {-1593806400 -16966 0 SMT} {-1335986234 -18000 0 CLT} {-1335985200 -14400 1 CLST} @@ -18,13 +18,13 @@ set TZData(:America/Santiago) { {-1222977600 -18000 0 CLT} {-1209754800 -14400 1 CLST} {-1191355200 -18000 0 CLT} - {-1178132400 -14400 1 CLST} + {-1178132400 -14400 0 CLT} {-870552000 -18000 0 CLT} - {-865278000 -14400 1 CLST} - {-740520000 -14400 1 CLST} - {-736376400 -18000 0 CLT} + {-865278000 -14400 0 CLT} + {-740520000 -10800 1 CLST} + {-736376400 -14400 0 CLT} {-718056000 -18000 0 CLT} - {-713646000 -14400 0 CLT} + {-713649600 -14400 0 CLT} {-36619200 -10800 1 CLST} {-23922000 -14400 0 CLT} {-3355200 -10800 1 CLST} @@ -65,10 +65,10 @@ set TZData(:America/Santiago) { {545194800 -14400 0 CLT} {560923200 -10800 1 CLST} {574225200 -14400 0 CLT} - {591768000 -10800 1 CLST} + {592372800 -10800 1 CLST} {605674800 -14400 0 CLT} {624427200 -10800 1 CLST} - {637729200 -14400 0 CLT} + {637124400 -14400 0 CLT} {653457600 -10800 1 CLST} {668574000 -14400 0 CLT} {687326400 -10800 1 CLST} diff --git a/library/tzdata/Antarctica/Palmer b/library/tzdata/Antarctica/Palmer index f12528b..2c43861 100644 --- a/library/tzdata/Antarctica/Palmer +++ b/library/tzdata/Antarctica/Palmer @@ -28,10 +28,10 @@ set TZData(:Antarctica/Palmer) { {545194800 -14400 0 CLT} {560923200 -10800 1 CLST} {574225200 -14400 0 CLT} - {591768000 -10800 1 CLST} + {592372800 -10800 1 CLST} {605674800 -14400 0 CLT} {624427200 -10800 1 CLST} - {637729200 -14400 0 CLT} + {637124400 -14400 0 CLT} {653457600 -10800 1 CLST} {668574000 -14400 0 CLT} {687326400 -10800 1 CLST} diff --git a/library/tzdata/Asia/Choibalsan b/library/tzdata/Asia/Choibalsan index 3d42617..2bcf7f7 100644 --- a/library/tzdata/Asia/Choibalsan +++ b/library/tzdata/Asia/Choibalsan @@ -48,4 +48,175 @@ set TZData(:Asia/Choibalsan) { {1127491200 32400 0 CHOT} {1143219600 36000 1 CHOST} {1159545600 32400 0 CHOT} + {1206889200 28800 0 CHOT} + {1427479200 32400 1 CHOST} + {1443193200 28800 0 CHOT} + {1458928800 32400 1 CHOST} + {1474642800 28800 0 CHOT} + {1490378400 32400 1 CHOST} + {1506697200 28800 0 CHOT} + {1522432800 32400 1 CHOST} + {1538146800 28800 0 CHOT} + {1553882400 32400 1 CHOST} + {1569596400 28800 0 CHOT} + {1585332000 32400 1 CHOST} + {1601046000 28800 0 CHOT} + {1616781600 32400 1 CHOST} + {1632495600 28800 0 CHOT} + {1648231200 32400 1 CHOST} + {1663945200 28800 0 CHOT} + {1679680800 32400 1 CHOST} + {1695999600 28800 0 CHOT} + {1711735200 32400 1 CHOST} + {1727449200 28800 0 CHOT} + {1743184800 32400 1 CHOST} + {1758898800 28800 0 CHOT} + {1774634400 32400 1 CHOST} + {1790348400 28800 0 CHOT} + {1806084000 32400 1 CHOST} + {1821798000 28800 0 CHOT} + {1837533600 32400 1 CHOST} + {1853852400 28800 0 CHOT} + {1869588000 32400 1 CHOST} + {1885302000 28800 0 CHOT} + {1901037600 32400 1 CHOST} + {1916751600 28800 0 CHOT} + {1932487200 32400 1 CHOST} + {1948201200 28800 0 CHOT} + {1963936800 32400 1 CHOST} + {1979650800 28800 0 CHOT} + {1995386400 32400 1 CHOST} + {2011100400 28800 0 CHOT} + {2026836000 32400 1 CHOST} + {2043154800 28800 0 CHOT} + {2058890400 32400 1 CHOST} + {2074604400 28800 0 CHOT} + {2090340000 32400 1 CHOST} + {2106054000 28800 0 CHOT} + {2121789600 32400 1 CHOST} + {2137503600 28800 0 CHOT} + {2153239200 32400 1 CHOST} + {2168953200 28800 0 CHOT} + {2184688800 32400 1 CHOST} + {2200402800 28800 0 CHOT} + {2216743200 32400 1 CHOST} + {2232457200 28800 0 CHOT} + {2248192800 32400 1 CHOST} + {2263906800 28800 0 CHOT} + {2279642400 32400 1 CHOST} + {2295356400 28800 0 CHOT} + {2311092000 32400 1 CHOST} + {2326806000 28800 0 CHOT} + {2342541600 32400 1 CHOST} + {2358255600 28800 0 CHOT} + {2373991200 32400 1 CHOST} + {2390310000 28800 0 CHOT} + {2406045600 32400 1 CHOST} + {2421759600 28800 0 CHOT} + {2437495200 32400 1 CHOST} + {2453209200 28800 0 CHOT} + {2468944800 32400 1 CHOST} + {2484658800 28800 0 CHOT} + {2500394400 32400 1 CHOST} + {2516108400 28800 0 CHOT} + {2531844000 32400 1 CHOST} + {2547558000 28800 0 CHOT} + {2563293600 32400 1 CHOST} + {2579612400 28800 0 CHOT} + {2595348000 32400 1 CHOST} + {2611062000 28800 0 CHOT} + {2626797600 32400 1 CHOST} + {2642511600 28800 0 CHOT} + {2658247200 32400 1 CHOST} + {2673961200 28800 0 CHOT} + {2689696800 32400 1 CHOST} + {2705410800 28800 0 CHOT} + {2721146400 32400 1 CHOST} + {2737465200 28800 0 CHOT} + {2753200800 32400 1 CHOST} + {2768914800 28800 0 CHOT} + {2784650400 32400 1 CHOST} + {2800364400 28800 0 CHOT} + {2816100000 32400 1 CHOST} + {2831814000 28800 0 CHOT} + {2847549600 32400 1 CHOST} + {2863263600 28800 0 CHOT} + {2878999200 32400 1 CHOST} + {2894713200 28800 0 CHOT} + {2910448800 32400 1 CHOST} + {2926767600 28800 0 CHOT} + {2942503200 32400 1 CHOST} + {2958217200 28800 0 CHOT} + {2973952800 32400 1 CHOST} + {2989666800 28800 0 CHOT} + {3005402400 32400 1 CHOST} + {3021116400 28800 0 CHOT} + {3036852000 32400 1 CHOST} + {3052566000 28800 0 CHOT} + {3068301600 32400 1 CHOST} + {3084015600 28800 0 CHOT} + {3100356000 32400 1 CHOST} + {3116070000 28800 0 CHOT} + {3131805600 32400 1 CHOST} + {3147519600 28800 0 CHOT} + {3163255200 32400 1 CHOST} + {3178969200 28800 0 CHOT} + {3194704800 32400 1 CHOST} + {3210418800 28800 0 CHOT} + {3226154400 32400 1 CHOST} + {3241868400 28800 0 CHOT} + {3257604000 32400 1 CHOST} + {3273922800 28800 0 CHOT} + {3289658400 32400 1 CHOST} + {3305372400 28800 0 CHOT} + {3321108000 32400 1 CHOST} + {3336822000 28800 0 CHOT} + {3352557600 32400 1 CHOST} + {3368271600 28800 0 CHOT} + {3384007200 32400 1 CHOST} + {3399721200 28800 0 CHOT} + {3415456800 32400 1 CHOST} + {3431170800 28800 0 CHOT} + {3446906400 32400 1 CHOST} + {3463225200 28800 0 CHOT} + {3478960800 32400 1 CHOST} + {3494674800 28800 0 CHOT} + {3510410400 32400 1 CHOST} + {3526124400 28800 0 CHOT} + {3541860000 32400 1 CHOST} + {3557574000 28800 0 CHOT} + {3573309600 32400 1 CHOST} + {3589023600 28800 0 CHOT} + {3604759200 32400 1 CHOST} + {3621078000 28800 0 CHOT} + {3636813600 32400 1 CHOST} + {3652527600 28800 0 CHOT} + {3668263200 32400 1 CHOST} + {3683977200 28800 0 CHOT} + {3699712800 32400 1 CHOST} + {3715426800 28800 0 CHOT} + {3731162400 32400 1 CHOST} + {3746876400 28800 0 CHOT} + {3762612000 32400 1 CHOST} + {3778326000 28800 0 CHOT} + {3794061600 32400 1 CHOST} + {3810380400 28800 0 CHOT} + {3826116000 32400 1 CHOST} + {3841830000 28800 0 CHOT} + {3857565600 32400 1 CHOST} + {3873279600 28800 0 CHOT} + {3889015200 32400 1 CHOST} + {3904729200 28800 0 CHOT} + {3920464800 32400 1 CHOST} + {3936178800 28800 0 CHOT} + {3951914400 32400 1 CHOST} + {3967628400 28800 0 CHOT} + {3983968800 32400 1 CHOST} + {3999682800 28800 0 CHOT} + {4015418400 32400 1 CHOST} + {4031132400 28800 0 CHOT} + {4046868000 32400 1 CHOST} + {4062582000 28800 0 CHOT} + {4078317600 32400 1 CHOST} + {4094031600 28800 0 CHOT} } diff --git a/library/tzdata/Asia/Gaza b/library/tzdata/Asia/Gaza index 8ec9c5b..805b6b7 100644 --- a/library/tzdata/Asia/Gaza +++ b/library/tzdata/Asia/Gaza @@ -104,175 +104,175 @@ set TZData(:Asia/Gaza) { {1364508000 10800 1 EEST} {1380229200 7200 0 EET} {1395957600 10800 1 EEST} - {1411678800 7200 0 EET} - {1427407200 10800 1 EEST} - {1443128400 7200 0 EET} - {1459461600 10800 1 EEST} - {1474578000 7200 0 EET} - {1490911200 10800 1 EEST} - {1506027600 7200 0 EET} - {1522360800 10800 1 EEST} - {1537477200 7200 0 EET} - {1553810400 10800 1 EEST} - {1569531600 7200 0 EET} - {1585260000 10800 1 EEST} - {1600981200 7200 0 EET} - {1616709600 10800 1 EEST} - {1632430800 7200 0 EET} - {1648764000 10800 1 EEST} - {1663880400 7200 0 EET} - {1680213600 10800 1 EEST} - {1695330000 7200 0 EET} - {1711663200 10800 1 EEST} - {1727384400 7200 0 EET} - {1743112800 10800 1 EEST} - {1758834000 7200 0 EET} - {1774562400 10800 1 EEST} - {1790283600 7200 0 EET} - {1806012000 10800 1 EEST} - {1821733200 7200 0 EET} - {1838066400 10800 1 EEST} - {1853182800 7200 0 EET} - {1869516000 10800 1 EEST} - {1884632400 7200 0 EET} - {1900965600 10800 1 EEST} - {1916686800 7200 0 EET} - {1932415200 10800 1 EEST} - {1948136400 7200 0 EET} - {1963864800 10800 1 EEST} - {1979586000 7200 0 EET} - {1995919200 10800 1 EEST} - {2011035600 7200 0 EET} - {2027368800 10800 1 EEST} - {2042485200 7200 0 EET} - {2058818400 10800 1 EEST} - {2073934800 7200 0 EET} - {2090268000 10800 1 EEST} - {2105989200 7200 0 EET} - {2121717600 10800 1 EEST} - {2137438800 7200 0 EET} - {2153167200 10800 1 EEST} - {2168888400 7200 0 EET} - {2185221600 10800 1 EEST} - {2200338000 7200 0 EET} - {2216671200 10800 1 EEST} - {2231787600 7200 0 EET} - {2248120800 10800 1 EEST} - {2263842000 7200 0 EET} - {2279570400 10800 1 EEST} - {2295291600 7200 0 EET} - {2311020000 10800 1 EEST} - {2326741200 7200 0 EET} - {2343074400 10800 1 EEST} - {2358190800 7200 0 EET} - {2374524000 10800 1 EEST} - {2389640400 7200 0 EET} - {2405973600 10800 1 EEST} - {2421090000 7200 0 EET} - {2437423200 10800 1 EEST} - {2453144400 7200 0 EET} - {2468872800 10800 1 EEST} - {2484594000 7200 0 EET} - {2500322400 10800 1 EEST} - {2516043600 7200 0 EET} - {2532376800 10800 1 EEST} - {2547493200 7200 0 EET} - {2563826400 10800 1 EEST} - {2578942800 7200 0 EET} - {2595276000 10800 1 EEST} - {2610997200 7200 0 EET} - {2626725600 10800 1 EEST} - {2642446800 7200 0 EET} - {2658175200 10800 1 EEST} - {2673896400 7200 0 EET} - {2689624800 10800 1 EEST} - {2705346000 7200 0 EET} - {2721679200 10800 1 EEST} - {2736795600 7200 0 EET} - {2753128800 10800 1 EEST} - {2768245200 7200 0 EET} - {2784578400 10800 1 EEST} - {2800299600 7200 0 EET} - {2816028000 10800 1 EEST} - {2831749200 7200 0 EET} - {2847477600 10800 1 EEST} - {2863198800 7200 0 EET} - {2879532000 10800 1 EEST} - {2894648400 7200 0 EET} - {2910981600 10800 1 EEST} - {2926098000 7200 0 EET} - {2942431200 10800 1 EEST} - {2957547600 7200 0 EET} - {2973880800 10800 1 EEST} - {2989602000 7200 0 EET} - {3005330400 10800 1 EEST} - {3021051600 7200 0 EET} - {3036780000 10800 1 EEST} - {3052501200 7200 0 EET} - {3068834400 10800 1 EEST} - {3083950800 7200 0 EET} - {3100284000 10800 1 EEST} - {3115400400 7200 0 EET} - {3131733600 10800 1 EEST} - {3147454800 7200 0 EET} - {3163183200 10800 1 EEST} - {3178904400 7200 0 EET} - {3194632800 10800 1 EEST} - {3210354000 7200 0 EET} - {3226687200 10800 1 EEST} - {3241803600 7200 0 EET} - {3258136800 10800 1 EEST} - {3273253200 7200 0 EET} - {3289586400 10800 1 EEST} - {3304702800 7200 0 EET} - {3321036000 10800 1 EEST} - {3336757200 7200 0 EET} - {3352485600 10800 1 EEST} - {3368206800 7200 0 EET} - {3383935200 10800 1 EEST} - {3399656400 7200 0 EET} - {3415989600 10800 1 EEST} - {3431106000 7200 0 EET} - {3447439200 10800 1 EEST} - {3462555600 7200 0 EET} - {3478888800 10800 1 EEST} - {3494610000 7200 0 EET} - {3510338400 10800 1 EEST} - {3526059600 7200 0 EET} - {3541788000 10800 1 EEST} - {3557509200 7200 0 EET} - {3573237600 10800 1 EEST} - {3588958800 7200 0 EET} - {3605292000 10800 1 EEST} - {3620408400 7200 0 EET} - {3636741600 10800 1 EEST} - {3651858000 7200 0 EET} - {3668191200 10800 1 EEST} - {3683912400 7200 0 EET} - {3699640800 10800 1 EEST} - {3715362000 7200 0 EET} - {3731090400 10800 1 EEST} - {3746811600 7200 0 EET} - {3763144800 10800 1 EEST} - {3778261200 7200 0 EET} - {3794594400 10800 1 EEST} - {3809710800 7200 0 EET} - {3826044000 10800 1 EEST} - {3841160400 7200 0 EET} - {3857493600 10800 1 EEST} - {3873214800 7200 0 EET} - {3888943200 10800 1 EEST} - {3904664400 7200 0 EET} - {3920392800 10800 1 EEST} - {3936114000 7200 0 EET} - {3952447200 10800 1 EEST} - {3967563600 7200 0 EET} - {3983896800 10800 1 EEST} - {3999013200 7200 0 EET} - {4015346400 10800 1 EEST} - {4031067600 7200 0 EET} - {4046796000 10800 1 EEST} - {4062517200 7200 0 EET} - {4078245600 10800 1 EEST} - {4093966800 7200 0 EET} + {1414098000 7200 0 EET} + {1427493600 10800 1 EEST} + {1445547600 7200 0 EET} + {1458943200 10800 1 EEST} + {1476997200 7200 0 EET} + {1490997600 10800 1 EEST} + {1509051600 7200 0 EET} + {1522447200 10800 1 EEST} + {1540501200 7200 0 EET} + {1553896800 10800 1 EEST} + {1571950800 7200 0 EET} + {1585346400 10800 1 EEST} + {1603400400 7200 0 EET} + {1616796000 10800 1 EEST} + {1634850000 7200 0 EET} + {1648245600 10800 1 EEST} + {1666299600 7200 0 EET} + {1680300000 10800 1 EEST} + {1698354000 7200 0 EET} + {1711749600 10800 1 EEST} + {1729803600 7200 0 EET} + {1743199200 10800 1 EEST} + {1761253200 7200 0 EET} + {1774648800 10800 1 EEST} + {1792702800 7200 0 EET} + {1806098400 10800 1 EEST} + {1824152400 7200 0 EET} + {1838152800 10800 1 EEST} + {1856206800 7200 0 EET} + {1869602400 10800 1 EEST} + {1887656400 7200 0 EET} + {1901052000 10800 1 EEST} + {1919106000 7200 0 EET} + {1932501600 10800 1 EEST} + {1950555600 7200 0 EET} + {1963951200 10800 1 EEST} + {1982005200 7200 0 EET} + {1995400800 10800 1 EEST} + {2013454800 7200 0 EET} + {2027455200 10800 1 EEST} + {2045509200 7200 0 EET} + {2058904800 10800 1 EEST} + {2076958800 7200 0 EET} + {2090354400 10800 1 EEST} + {2108408400 7200 0 EET} + {2121804000 10800 1 EEST} + {2139858000 7200 0 EET} + {2153253600 10800 1 EEST} + {2171307600 7200 0 EET} + {2184703200 10800 1 EEST} + {2202757200 7200 0 EET} + {2216757600 10800 1 EEST} + {2234811600 7200 0 EET} + {2248207200 10800 1 EEST} + {2266261200 7200 0 EET} + {2279656800 10800 1 EEST} + {2297710800 7200 0 EET} + {2311106400 10800 1 EEST} + {2329160400 7200 0 EET} + {2342556000 10800 1 EEST} + {2360610000 7200 0 EET} + {2374610400 10800 1 EEST} + {2392664400 7200 0 EET} + {2406060000 10800 1 EEST} + {2424114000 7200 0 EET} + {2437509600 10800 1 EEST} + {2455563600 7200 0 EET} + {2468959200 10800 1 EEST} + {2487013200 7200 0 EET} + {2500408800 10800 1 EEST} + {2518462800 7200 0 EET} + {2531858400 10800 1 EEST} + {2549912400 7200 0 EET} + {2563912800 10800 1 EEST} + {2581966800 7200 0 EET} + {2595362400 10800 1 EEST} + {2613416400 7200 0 EET} + {2626812000 10800 1 EEST} + {2644866000 7200 0 EET} + {2658261600 10800 1 EEST} + {2676315600 7200 0 EET} + {2689711200 10800 1 EEST} + {2707765200 7200 0 EET} + {2721765600 10800 1 EEST} + {2739819600 7200 0 EET} + {2753215200 10800 1 EEST} + {2771269200 7200 0 EET} + {2784664800 10800 1 EEST} + {2802718800 7200 0 EET} + {2816114400 10800 1 EEST} + {2834168400 7200 0 EET} + {2847564000 10800 1 EEST} + {2865618000 7200 0 EET} + {2879013600 10800 1 EEST} + {2897067600 7200 0 EET} + {2911068000 10800 1 EEST} + {2929122000 7200 0 EET} + {2942517600 10800 1 EEST} + {2960571600 7200 0 EET} + {2973967200 10800 1 EEST} + {2992021200 7200 0 EET} + {3005416800 10800 1 EEST} + {3023470800 7200 0 EET} + {3036866400 10800 1 EEST} + {3054920400 7200 0 EET} + {3068316000 10800 1 EEST} + {3086370000 7200 0 EET} + {3100370400 10800 1 EEST} + {3118424400 7200 0 EET} + {3131820000 10800 1 EEST} + {3149874000 7200 0 EET} + {3163269600 10800 1 EEST} + {3181323600 7200 0 EET} + {3194719200 10800 1 EEST} + {3212773200 7200 0 EET} + {3226168800 10800 1 EEST} + {3244222800 7200 0 EET} + {3258223200 10800 1 EEST} + {3276277200 7200 0 EET} + {3289672800 10800 1 EEST} + {3307726800 7200 0 EET} + {3321122400 10800 1 EEST} + {3339176400 7200 0 EET} + {3352572000 10800 1 EEST} + {3370626000 7200 0 EET} + {3384021600 10800 1 EEST} + {3402075600 7200 0 EET} + {3415471200 10800 1 EEST} + {3433525200 7200 0 EET} + {3447525600 10800 1 EEST} + {3465579600 7200 0 EET} + {3478975200 10800 1 EEST} + {3497029200 7200 0 EET} + {3510424800 10800 1 EEST} + {3528478800 7200 0 EET} + {3541874400 10800 1 EEST} + {3559928400 7200 0 EET} + {3573324000 10800 1 EEST} + {3591378000 7200 0 EET} + {3605378400 10800 1 EEST} + {3623432400 7200 0 EET} + {3636828000 10800 1 EEST} + {3654882000 7200 0 EET} + {3668277600 10800 1 EEST} + {3686331600 7200 0 EET} + {3699727200 10800 1 EEST} + {3717781200 7200 0 EET} + {3731176800 10800 1 EEST} + {3749230800 7200 0 EET} + {3762626400 10800 1 EEST} + {3780680400 7200 0 EET} + {3794680800 10800 1 EEST} + {3812734800 7200 0 EET} + {3826130400 10800 1 EEST} + {3844184400 7200 0 EET} + {3857580000 10800 1 EEST} + {3875634000 7200 0 EET} + {3889029600 10800 1 EEST} + {3907083600 7200 0 EET} + {3920479200 10800 1 EEST} + {3938533200 7200 0 EET} + {3951928800 10800 1 EEST} + {3969982800 7200 0 EET} + {3983983200 10800 1 EEST} + {4002037200 7200 0 EET} + {4015432800 10800 1 EEST} + {4033486800 7200 0 EET} + {4046882400 10800 1 EEST} + {4064936400 7200 0 EET} + {4078332000 10800 1 EEST} + {4096386000 7200 0 EET} } diff --git a/library/tzdata/Asia/Hebron b/library/tzdata/Asia/Hebron index 900ffad..9049d93 100644 --- a/library/tzdata/Asia/Hebron +++ b/library/tzdata/Asia/Hebron @@ -103,175 +103,175 @@ set TZData(:Asia/Hebron) { {1364508000 10800 1 EEST} {1380229200 7200 0 EET} {1395957600 10800 1 EEST} - {1411678800 7200 0 EET} - {1427407200 10800 1 EEST} - {1443128400 7200 0 EET} - {1459461600 10800 1 EEST} - {1474578000 7200 0 EET} - {1490911200 10800 1 EEST} - {1506027600 7200 0 EET} - {1522360800 10800 1 EEST} - {1537477200 7200 0 EET} - {1553810400 10800 1 EEST} - {1569531600 7200 0 EET} - {1585260000 10800 1 EEST} - {1600981200 7200 0 EET} - {1616709600 10800 1 EEST} - {1632430800 7200 0 EET} - {1648764000 10800 1 EEST} - {1663880400 7200 0 EET} - {1680213600 10800 1 EEST} - {1695330000 7200 0 EET} - {1711663200 10800 1 EEST} - {1727384400 7200 0 EET} - {1743112800 10800 1 EEST} - {1758834000 7200 0 EET} - {1774562400 10800 1 EEST} - {1790283600 7200 0 EET} - {1806012000 10800 1 EEST} - {1821733200 7200 0 EET} - {1838066400 10800 1 EEST} - {1853182800 7200 0 EET} - {1869516000 10800 1 EEST} - {1884632400 7200 0 EET} - {1900965600 10800 1 EEST} - {1916686800 7200 0 EET} - {1932415200 10800 1 EEST} - {1948136400 7200 0 EET} - {1963864800 10800 1 EEST} - {1979586000 7200 0 EET} - {1995919200 10800 1 EEST} - {2011035600 7200 0 EET} - {2027368800 10800 1 EEST} - {2042485200 7200 0 EET} - {2058818400 10800 1 EEST} - {2073934800 7200 0 EET} - {2090268000 10800 1 EEST} - {2105989200 7200 0 EET} - {2121717600 10800 1 EEST} - {2137438800 7200 0 EET} - {2153167200 10800 1 EEST} - {2168888400 7200 0 EET} - {2185221600 10800 1 EEST} - {2200338000 7200 0 EET} - {2216671200 10800 1 EEST} - {2231787600 7200 0 EET} - {2248120800 10800 1 EEST} - {2263842000 7200 0 EET} - {2279570400 10800 1 EEST} - {2295291600 7200 0 EET} - {2311020000 10800 1 EEST} - {2326741200 7200 0 EET} - {2343074400 10800 1 EEST} - {2358190800 7200 0 EET} - {2374524000 10800 1 EEST} - {2389640400 7200 0 EET} - {2405973600 10800 1 EEST} - {2421090000 7200 0 EET} - {2437423200 10800 1 EEST} - {2453144400 7200 0 EET} - {2468872800 10800 1 EEST} - {2484594000 7200 0 EET} - {2500322400 10800 1 EEST} - {2516043600 7200 0 EET} - {2532376800 10800 1 EEST} - {2547493200 7200 0 EET} - {2563826400 10800 1 EEST} - {2578942800 7200 0 EET} - {2595276000 10800 1 EEST} - {2610997200 7200 0 EET} - {2626725600 10800 1 EEST} - {2642446800 7200 0 EET} - {2658175200 10800 1 EEST} - {2673896400 7200 0 EET} - {2689624800 10800 1 EEST} - {2705346000 7200 0 EET} - {2721679200 10800 1 EEST} - {2736795600 7200 0 EET} - {2753128800 10800 1 EEST} - {2768245200 7200 0 EET} - {2784578400 10800 1 EEST} - {2800299600 7200 0 EET} - {2816028000 10800 1 EEST} - {2831749200 7200 0 EET} - {2847477600 10800 1 EEST} - {2863198800 7200 0 EET} - {2879532000 10800 1 EEST} - {2894648400 7200 0 EET} - {2910981600 10800 1 EEST} - {2926098000 7200 0 EET} - {2942431200 10800 1 EEST} - {2957547600 7200 0 EET} - {2973880800 10800 1 EEST} - {2989602000 7200 0 EET} - {3005330400 10800 1 EEST} - {3021051600 7200 0 EET} - {3036780000 10800 1 EEST} - {3052501200 7200 0 EET} - {3068834400 10800 1 EEST} - {3083950800 7200 0 EET} - {3100284000 10800 1 EEST} - {3115400400 7200 0 EET} - {3131733600 10800 1 EEST} - {3147454800 7200 0 EET} - {3163183200 10800 1 EEST} - {3178904400 7200 0 EET} - {3194632800 10800 1 EEST} - {3210354000 7200 0 EET} - {3226687200 10800 1 EEST} - {3241803600 7200 0 EET} - {3258136800 10800 1 EEST} - {3273253200 7200 0 EET} - {3289586400 10800 1 EEST} - {3304702800 7200 0 EET} - {3321036000 10800 1 EEST} - {3336757200 7200 0 EET} - {3352485600 10800 1 EEST} - {3368206800 7200 0 EET} - {3383935200 10800 1 EEST} - {3399656400 7200 0 EET} - {3415989600 10800 1 EEST} - {3431106000 7200 0 EET} - {3447439200 10800 1 EEST} - {3462555600 7200 0 EET} - {3478888800 10800 1 EEST} - {3494610000 7200 0 EET} - {3510338400 10800 1 EEST} - {3526059600 7200 0 EET} - {3541788000 10800 1 EEST} - {3557509200 7200 0 EET} - {3573237600 10800 1 EEST} - {3588958800 7200 0 EET} - {3605292000 10800 1 EEST} - {3620408400 7200 0 EET} - {3636741600 10800 1 EEST} - {3651858000 7200 0 EET} - {3668191200 10800 1 EEST} - {3683912400 7200 0 EET} - {3699640800 10800 1 EEST} - {3715362000 7200 0 EET} - {3731090400 10800 1 EEST} - {3746811600 7200 0 EET} - {3763144800 10800 1 EEST} - {3778261200 7200 0 EET} - {3794594400 10800 1 EEST} - {3809710800 7200 0 EET} - {3826044000 10800 1 EEST} - {3841160400 7200 0 EET} - {3857493600 10800 1 EEST} - {3873214800 7200 0 EET} - {3888943200 10800 1 EEST} - {3904664400 7200 0 EET} - {3920392800 10800 1 EEST} - {3936114000 7200 0 EET} - {3952447200 10800 1 EEST} - {3967563600 7200 0 EET} - {3983896800 10800 1 EEST} - {3999013200 7200 0 EET} - {4015346400 10800 1 EEST} - {4031067600 7200 0 EET} - {4046796000 10800 1 EEST} - {4062517200 7200 0 EET} - {4078245600 10800 1 EEST} - {4093966800 7200 0 EET} + {1414098000 7200 0 EET} + {1427493600 10800 1 EEST} + {1445547600 7200 0 EET} + {1458943200 10800 1 EEST} + {1476997200 7200 0 EET} + {1490997600 10800 1 EEST} + {1509051600 7200 0 EET} + {1522447200 10800 1 EEST} + {1540501200 7200 0 EET} + {1553896800 10800 1 EEST} + {1571950800 7200 0 EET} + {1585346400 10800 1 EEST} + {1603400400 7200 0 EET} + {1616796000 10800 1 EEST} + {1634850000 7200 0 EET} + {1648245600 10800 1 EEST} + {1666299600 7200 0 EET} + {1680300000 10800 1 EEST} + {1698354000 7200 0 EET} + {1711749600 10800 1 EEST} + {1729803600 7200 0 EET} + {1743199200 10800 1 EEST} + {1761253200 7200 0 EET} + {1774648800 10800 1 EEST} + {1792702800 7200 0 EET} + {1806098400 10800 1 EEST} + {1824152400 7200 0 EET} + {1838152800 10800 1 EEST} + {1856206800 7200 0 EET} + {1869602400 10800 1 EEST} + {1887656400 7200 0 EET} + {1901052000 10800 1 EEST} + {1919106000 7200 0 EET} + {1932501600 10800 1 EEST} + {1950555600 7200 0 EET} + {1963951200 10800 1 EEST} + {1982005200 7200 0 EET} + {1995400800 10800 1 EEST} + {2013454800 7200 0 EET} + {2027455200 10800 1 EEST} + {2045509200 7200 0 EET} + {2058904800 10800 1 EEST} + {2076958800 7200 0 EET} + {2090354400 10800 1 EEST} + {2108408400 7200 0 EET} + {2121804000 10800 1 EEST} + {2139858000 7200 0 EET} + {2153253600 10800 1 EEST} + {2171307600 7200 0 EET} + {2184703200 10800 1 EEST} + {2202757200 7200 0 EET} + {2216757600 10800 1 EEST} + {2234811600 7200 0 EET} + {2248207200 10800 1 EEST} + {2266261200 7200 0 EET} + {2279656800 10800 1 EEST} + {2297710800 7200 0 EET} + {2311106400 10800 1 EEST} + {2329160400 7200 0 EET} + {2342556000 10800 1 EEST} + {2360610000 7200 0 EET} + {2374610400 10800 1 EEST} + {2392664400 7200 0 EET} + {2406060000 10800 1 EEST} + {2424114000 7200 0 EET} + {2437509600 10800 1 EEST} + {2455563600 7200 0 EET} + {2468959200 10800 1 EEST} + {2487013200 7200 0 EET} + {2500408800 10800 1 EEST} + {2518462800 7200 0 EET} + {2531858400 10800 1 EEST} + {2549912400 7200 0 EET} + {2563912800 10800 1 EEST} + {2581966800 7200 0 EET} + {2595362400 10800 1 EEST} + {2613416400 7200 0 EET} + {2626812000 10800 1 EEST} + {2644866000 7200 0 EET} + {2658261600 10800 1 EEST} + {2676315600 7200 0 EET} + {2689711200 10800 1 EEST} + {2707765200 7200 0 EET} + {2721765600 10800 1 EEST} + {2739819600 7200 0 EET} + {2753215200 10800 1 EEST} + {2771269200 7200 0 EET} + {2784664800 10800 1 EEST} + {2802718800 7200 0 EET} + {2816114400 10800 1 EEST} + {2834168400 7200 0 EET} + {2847564000 10800 1 EEST} + {2865618000 7200 0 EET} + {2879013600 10800 1 EEST} + {2897067600 7200 0 EET} + {2911068000 10800 1 EEST} + {2929122000 7200 0 EET} + {2942517600 10800 1 EEST} + {2960571600 7200 0 EET} + {2973967200 10800 1 EEST} + {2992021200 7200 0 EET} + {3005416800 10800 1 EEST} + {3023470800 7200 0 EET} + {3036866400 10800 1 EEST} + {3054920400 7200 0 EET} + {3068316000 10800 1 EEST} + {3086370000 7200 0 EET} + {3100370400 10800 1 EEST} + {3118424400 7200 0 EET} + {3131820000 10800 1 EEST} + {3149874000 7200 0 EET} + {3163269600 10800 1 EEST} + {3181323600 7200 0 EET} + {3194719200 10800 1 EEST} + {3212773200 7200 0 EET} + {3226168800 10800 1 EEST} + {3244222800 7200 0 EET} + {3258223200 10800 1 EEST} + {3276277200 7200 0 EET} + {3289672800 10800 1 EEST} + {3307726800 7200 0 EET} + {3321122400 10800 1 EEST} + {3339176400 7200 0 EET} + {3352572000 10800 1 EEST} + {3370626000 7200 0 EET} + {3384021600 10800 1 EEST} + {3402075600 7200 0 EET} + {3415471200 10800 1 EEST} + {3433525200 7200 0 EET} + {3447525600 10800 1 EEST} + {3465579600 7200 0 EET} + {3478975200 10800 1 EEST} + {3497029200 7200 0 EET} + {3510424800 10800 1 EEST} + {3528478800 7200 0 EET} + {3541874400 10800 1 EEST} + {3559928400 7200 0 EET} + {3573324000 10800 1 EEST} + {3591378000 7200 0 EET} + {3605378400 10800 1 EEST} + {3623432400 7200 0 EET} + {3636828000 10800 1 EEST} + {3654882000 7200 0 EET} + {3668277600 10800 1 EEST} + {3686331600 7200 0 EET} + {3699727200 10800 1 EEST} + {3717781200 7200 0 EET} + {3731176800 10800 1 EEST} + {3749230800 7200 0 EET} + {3762626400 10800 1 EEST} + {3780680400 7200 0 EET} + {3794680800 10800 1 EEST} + {3812734800 7200 0 EET} + {3826130400 10800 1 EEST} + {3844184400 7200 0 EET} + {3857580000 10800 1 EEST} + {3875634000 7200 0 EET} + {3889029600 10800 1 EEST} + {3907083600 7200 0 EET} + {3920479200 10800 1 EEST} + {3938533200 7200 0 EET} + {3951928800 10800 1 EEST} + {3969982800 7200 0 EET} + {3983983200 10800 1 EEST} + {4002037200 7200 0 EET} + {4015432800 10800 1 EEST} + {4033486800 7200 0 EET} + {4046882400 10800 1 EEST} + {4064936400 7200 0 EET} + {4078332000 10800 1 EEST} + {4096386000 7200 0 EET} } diff --git a/library/tzdata/Asia/Hovd b/library/tzdata/Asia/Hovd index 2a87dab..3d200a6 100644 --- a/library/tzdata/Asia/Hovd +++ b/library/tzdata/Asia/Hovd @@ -48,4 +48,174 @@ set TZData(:Asia/Hovd) { {1127498400 25200 0 HOVT} {1143226800 28800 1 HOVST} {1159552800 25200 0 HOVT} + {1427482800 28800 1 HOVST} + {1443196800 25200 0 HOVT} + {1458932400 28800 1 HOVST} + {1474646400 25200 0 HOVT} + {1490382000 28800 1 HOVST} + {1506700800 25200 0 HOVT} + {1522436400 28800 1 HOVST} + {1538150400 25200 0 HOVT} + {1553886000 28800 1 HOVST} + {1569600000 25200 0 HOVT} + {1585335600 28800 1 HOVST} + {1601049600 25200 0 HOVT} + {1616785200 28800 1 HOVST} + {1632499200 25200 0 HOVT} + {1648234800 28800 1 HOVST} + {1663948800 25200 0 HOVT} + {1679684400 28800 1 HOVST} + {1696003200 25200 0 HOVT} + {1711738800 28800 1 HOVST} + {1727452800 25200 0 HOVT} + {1743188400 28800 1 HOVST} + {1758902400 25200 0 HOVT} + {1774638000 28800 1 HOVST} + {1790352000 25200 0 HOVT} + {1806087600 28800 1 HOVST} + {1821801600 25200 0 HOVT} + {1837537200 28800 1 HOVST} + {1853856000 25200 0 HOVT} + {1869591600 28800 1 HOVST} + {1885305600 25200 0 HOVT} + {1901041200 28800 1 HOVST} + {1916755200 25200 0 HOVT} + {1932490800 28800 1 HOVST} + {1948204800 25200 0 HOVT} + {1963940400 28800 1 HOVST} + {1979654400 25200 0 HOVT} + {1995390000 28800 1 HOVST} + {2011104000 25200 0 HOVT} + {2026839600 28800 1 HOVST} + {2043158400 25200 0 HOVT} + {2058894000 28800 1 HOVST} + {2074608000 25200 0 HOVT} + {2090343600 28800 1 HOVST} + {2106057600 25200 0 HOVT} + {2121793200 28800 1 HOVST} + {2137507200 25200 0 HOVT} + {2153242800 28800 1 HOVST} + {2168956800 25200 0 HOVT} + {2184692400 28800 1 HOVST} + {2200406400 25200 0 HOVT} + {2216746800 28800 1 HOVST} + {2232460800 25200 0 HOVT} + {2248196400 28800 1 HOVST} + {2263910400 25200 0 HOVT} + {2279646000 28800 1 HOVST} + {2295360000 25200 0 HOVT} + {2311095600 28800 1 HOVST} + {2326809600 25200 0 HOVT} + {2342545200 28800 1 HOVST} + {2358259200 25200 0 HOVT} + {2373994800 28800 1 HOVST} + {2390313600 25200 0 HOVT} + {2406049200 28800 1 HOVST} + {2421763200 25200 0 HOVT} + {2437498800 28800 1 HOVST} + {2453212800 25200 0 HOVT} + {2468948400 28800 1 HOVST} + {2484662400 25200 0 HOVT} + {2500398000 28800 1 HOVST} + {2516112000 25200 0 HOVT} + {2531847600 28800 1 HOVST} + {2547561600 25200 0 HOVT} + {2563297200 28800 1 HOVST} + {2579616000 25200 0 HOVT} + {2595351600 28800 1 HOVST} + {2611065600 25200 0 HOVT} + {2626801200 28800 1 HOVST} + {2642515200 25200 0 HOVT} + {2658250800 28800 1 HOVST} + {2673964800 25200 0 HOVT} + {2689700400 28800 1 HOVST} + {2705414400 25200 0 HOVT} + {2721150000 28800 1 HOVST} + {2737468800 25200 0 HOVT} + {2753204400 28800 1 HOVST} + {2768918400 25200 0 HOVT} + {2784654000 28800 1 HOVST} + {2800368000 25200 0 HOVT} + {2816103600 28800 1 HOVST} + {2831817600 25200 0 HOVT} + {2847553200 28800 1 HOVST} + {2863267200 25200 0 HOVT} + {2879002800 28800 1 HOVST} + {2894716800 25200 0 HOVT} + {2910452400 28800 1 HOVST} + {2926771200 25200 0 HOVT} + {2942506800 28800 1 HOVST} + {2958220800 25200 0 HOVT} + {2973956400 28800 1 HOVST} + {2989670400 25200 0 HOVT} + {3005406000 28800 1 HOVST} + {3021120000 25200 0 HOVT} + {3036855600 28800 1 HOVST} + {3052569600 25200 0 HOVT} + {3068305200 28800 1 HOVST} + {3084019200 25200 0 HOVT} + {3100359600 28800 1 HOVST} + {3116073600 25200 0 HOVT} + {3131809200 28800 1 HOVST} + {3147523200 25200 0 HOVT} + {3163258800 28800 1 HOVST} + {3178972800 25200 0 HOVT} + {3194708400 28800 1 HOVST} + {3210422400 25200 0 HOVT} + {3226158000 28800 1 HOVST} + {3241872000 25200 0 HOVT} + {3257607600 28800 1 HOVST} + {3273926400 25200 0 HOVT} + {3289662000 28800 1 HOVST} + {3305376000 25200 0 HOVT} + {3321111600 28800 1 HOVST} + {3336825600 25200 0 HOVT} + {3352561200 28800 1 HOVST} + {3368275200 25200 0 HOVT} + {3384010800 28800 1 HOVST} + {3399724800 25200 0 HOVT} + {3415460400 28800 1 HOVST} + {3431174400 25200 0 HOVT} + {3446910000 28800 1 HOVST} + {3463228800 25200 0 HOVT} + {3478964400 28800 1 HOVST} + {3494678400 25200 0 HOVT} + {3510414000 28800 1 HOVST} + {3526128000 25200 0 HOVT} + {3541863600 28800 1 HOVST} + {3557577600 25200 0 HOVT} + {3573313200 28800 1 HOVST} + {3589027200 25200 0 HOVT} + {3604762800 28800 1 HOVST} + {3621081600 25200 0 HOVT} + {3636817200 28800 1 HOVST} + {3652531200 25200 0 HOVT} + {3668266800 28800 1 HOVST} + {3683980800 25200 0 HOVT} + {3699716400 28800 1 HOVST} + {3715430400 25200 0 HOVT} + {3731166000 28800 1 HOVST} + {3746880000 25200 0 HOVT} + {3762615600 28800 1 HOVST} + {3778329600 25200 0 HOVT} + {3794065200 28800 1 HOVST} + {3810384000 25200 0 HOVT} + {3826119600 28800 1 HOVST} + {3841833600 25200 0 HOVT} + {3857569200 28800 1 HOVST} + {3873283200 25200 0 HOVT} + {3889018800 28800 1 HOVST} + {3904732800 25200 0 HOVT} + {3920468400 28800 1 HOVST} + {3936182400 25200 0 HOVT} + {3951918000 28800 1 HOVST} + {3967632000 25200 0 HOVT} + {3983972400 28800 1 HOVST} + {3999686400 25200 0 HOVT} + {4015422000 28800 1 HOVST} + {4031136000 25200 0 HOVT} + {4046871600 28800 1 HOVST} + {4062585600 25200 0 HOVT} + {4078321200 28800 1 HOVST} + {4094035200 25200 0 HOVT} } diff --git a/library/tzdata/Asia/Pyongyang b/library/tzdata/Asia/Pyongyang index fafed54..4ade8e6 100644 --- a/library/tzdata/Asia/Pyongyang +++ b/library/tzdata/Asia/Pyongyang @@ -6,4 +6,5 @@ set TZData(:Asia/Pyongyang) { {-1830414600 32400 0 JCST} {-1017824400 32400 0 JST} {-768646800 32400 0 KST} + {1439564400 30600 0 KST} } diff --git a/library/tzdata/Asia/Ulaanbaatar b/library/tzdata/Asia/Ulaanbaatar index fef76ec..93e066c 100644 --- a/library/tzdata/Asia/Ulaanbaatar +++ b/library/tzdata/Asia/Ulaanbaatar @@ -48,4 +48,174 @@ set TZData(:Asia/Ulaanbaatar) { {1127494800 28800 0 ULAT} {1143223200 32400 1 ULAST} {1159549200 28800 0 ULAT} + {1427479200 32400 1 ULAST} + {1443193200 28800 0 ULAT} + {1458928800 32400 1 ULAST} + {1474642800 28800 0 ULAT} + {1490378400 32400 1 ULAST} + {1506697200 28800 0 ULAT} + {1522432800 32400 1 ULAST} + {1538146800 28800 0 ULAT} + {1553882400 32400 1 ULAST} + {1569596400 28800 0 ULAT} + {1585332000 32400 1 ULAST} + {1601046000 28800 0 ULAT} + {1616781600 32400 1 ULAST} + {1632495600 28800 0 ULAT} + {1648231200 32400 1 ULAST} + {1663945200 28800 0 ULAT} + {1679680800 32400 1 ULAST} + {1695999600 28800 0 ULAT} + {1711735200 32400 1 ULAST} + {1727449200 28800 0 ULAT} + {1743184800 32400 1 ULAST} + {1758898800 28800 0 ULAT} + {1774634400 32400 1 ULAST} + {1790348400 28800 0 ULAT} + {1806084000 32400 1 ULAST} + {1821798000 28800 0 ULAT} + {1837533600 32400 1 ULAST} + {1853852400 28800 0 ULAT} + {1869588000 32400 1 ULAST} + {1885302000 28800 0 ULAT} + {1901037600 32400 1 ULAST} + {1916751600 28800 0 ULAT} + {1932487200 32400 1 ULAST} + {1948201200 28800 0 ULAT} + {1963936800 32400 1 ULAST} + {1979650800 28800 0 ULAT} + {1995386400 32400 1 ULAST} + {2011100400 28800 0 ULAT} + {2026836000 32400 1 ULAST} + {2043154800 28800 0 ULAT} + {2058890400 32400 1 ULAST} + {2074604400 28800 0 ULAT} + {2090340000 32400 1 ULAST} + {2106054000 28800 0 ULAT} + {2121789600 32400 1 ULAST} + {2137503600 28800 0 ULAT} + {2153239200 32400 1 ULAST} + {2168953200 28800 0 ULAT} + {2184688800 32400 1 ULAST} + {2200402800 28800 0 ULAT} + {2216743200 32400 1 ULAST} + {2232457200 28800 0 ULAT} + {2248192800 32400 1 ULAST} + {2263906800 28800 0 ULAT} + {2279642400 32400 1 ULAST} + {2295356400 28800 0 ULAT} + {2311092000 32400 1 ULAST} + {2326806000 28800 0 ULAT} + {2342541600 32400 1 ULAST} + {2358255600 28800 0 ULAT} + {2373991200 32400 1 ULAST} + {2390310000 28800 0 ULAT} + {2406045600 32400 1 ULAST} + {2421759600 28800 0 ULAT} + {2437495200 32400 1 ULAST} + {2453209200 28800 0 ULAT} + {2468944800 32400 1 ULAST} + {2484658800 28800 0 ULAT} + {2500394400 32400 1 ULAST} + {2516108400 28800 0 ULAT} + {2531844000 32400 1 ULAST} + {2547558000 28800 0 ULAT} + {2563293600 32400 1 ULAST} + {2579612400 28800 0 ULAT} + {2595348000 32400 1 ULAST} + {2611062000 28800 0 ULAT} + {2626797600 32400 1 ULAST} + {2642511600 28800 0 ULAT} + {2658247200 32400 1 ULAST} + {2673961200 28800 0 ULAT} + {2689696800 32400 1 ULAST} + {2705410800 28800 0 ULAT} + {2721146400 32400 1 ULAST} + {2737465200 28800 0 ULAT} + {2753200800 32400 1 ULAST} + {2768914800 28800 0 ULAT} + {2784650400 32400 1 ULAST} + {2800364400 28800 0 ULAT} + {2816100000 32400 1 ULAST} + {2831814000 28800 0 ULAT} + {2847549600 32400 1 ULAST} + {2863263600 28800 0 ULAT} + {2878999200 32400 1 ULAST} + {2894713200 28800 0 ULAT} + {2910448800 32400 1 ULAST} + {2926767600 28800 0 ULAT} + {2942503200 32400 1 ULAST} + {2958217200 28800 0 ULAT} + {2973952800 32400 1 ULAST} + {2989666800 28800 0 ULAT} + {3005402400 32400 1 ULAST} + {3021116400 28800 0 ULAT} + {3036852000 32400 1 ULAST} + {3052566000 28800 0 ULAT} + {3068301600 32400 1 ULAST} + {3084015600 28800 0 ULAT} + {3100356000 32400 1 ULAST} + {3116070000 28800 0 ULAT} + {3131805600 32400 1 ULAST} + {3147519600 28800 0 ULAT} + {3163255200 32400 1 ULAST} + {3178969200 28800 0 ULAT} + {3194704800 32400 1 ULAST} + {3210418800 28800 0 ULAT} + {3226154400 32400 1 ULAST} + {3241868400 28800 0 ULAT} + {3257604000 32400 1 ULAST} + {3273922800 28800 0 ULAT} + {3289658400 32400 1 ULAST} + {3305372400 28800 0 ULAT} + {3321108000 32400 1 ULAST} + {3336822000 28800 0 ULAT} + {3352557600 32400 1 ULAST} + {3368271600 28800 0 ULAT} + {3384007200 32400 1 ULAST} + {3399721200 28800 0 ULAT} + {3415456800 32400 1 ULAST} + {3431170800 28800 0 ULAT} + {3446906400 32400 1 ULAST} + {3463225200 28800 0 ULAT} + {3478960800 32400 1 ULAST} + {3494674800 28800 0 ULAT} + {3510410400 32400 1 ULAST} + {3526124400 28800 0 ULAT} + {3541860000 32400 1 ULAST} + {3557574000 28800 0 ULAT} + {3573309600 32400 1 ULAST} + {3589023600 28800 0 ULAT} + {3604759200 32400 1 ULAST} + {3621078000 28800 0 ULAT} + {3636813600 32400 1 ULAST} + {3652527600 28800 0 ULAT} + {3668263200 32400 1 ULAST} + {3683977200 28800 0 ULAT} + {3699712800 32400 1 ULAST} + {3715426800 28800 0 ULAT} + {3731162400 32400 1 ULAST} + {3746876400 28800 0 ULAT} + {3762612000 32400 1 ULAST} + {3778326000 28800 0 ULAT} + {3794061600 32400 1 ULAST} + {3810380400 28800 0 ULAT} + {3826116000 32400 1 ULAST} + {3841830000 28800 0 ULAT} + {3857565600 32400 1 ULAST} + {3873279600 28800 0 ULAT} + {3889015200 32400 1 ULAST} + {3904729200 28800 0 ULAT} + {3920464800 32400 1 ULAST} + {3936178800 28800 0 ULAT} + {3951914400 32400 1 ULAST} + {3967628400 28800 0 ULAT} + {3983968800 32400 1 ULAST} + {3999682800 28800 0 ULAT} + {4015418400 32400 1 ULAST} + {4031132400 28800 0 ULAT} + {4046868000 32400 1 ULAST} + {4062582000 28800 0 ULAT} + {4078317600 32400 1 ULAST} + {4094031600 28800 0 ULAT} } diff --git a/library/tzdata/Atlantic/Canary b/library/tzdata/Atlantic/Canary index 4b802c7..dcfba83 100644 --- a/library/tzdata/Atlantic/Canary +++ b/library/tzdata/Atlantic/Canary @@ -5,7 +5,6 @@ set TZData(:Atlantic/Canary) { {-1509663504 -3600 0 CANT} {-733874400 0 0 WET} {323827200 3600 1 WEST} - {338947200 3600 0 WEST} {338950800 0 0 WET} {354675600 3600 1 WEST} {370400400 0 0 WET} diff --git a/library/tzdata/Europe/Chisinau b/library/tzdata/Europe/Chisinau index 4ef466b..5c240e7 100644 --- a/library/tzdata/Europe/Chisinau +++ b/library/tzdata/Europe/Chisinau @@ -63,210 +63,210 @@ set TZData(:Europe/Chisinau) { {828223200 10800 1 EEST} {846363600 7200 0 EET} {852069600 7200 0 EET} - {859683600 10800 1 EEST} - {877827600 7200 0 EET} - {891133200 10800 1 EEST} - {909277200 7200 0 EET} - {922582800 10800 1 EEST} - {941331600 7200 0 EET} - {954032400 10800 1 EEST} - {972781200 7200 0 EET} - {985482000 10800 1 EEST} - {1004230800 7200 0 EET} - {1017536400 10800 1 EEST} - {1035680400 7200 0 EET} - {1048986000 10800 1 EEST} - {1067130000 7200 0 EET} - {1080435600 10800 1 EEST} - {1099184400 7200 0 EET} - {1111885200 10800 1 EEST} - {1130634000 7200 0 EET} - {1143334800 10800 1 EEST} - {1162083600 7200 0 EET} - {1174784400 10800 1 EEST} - {1193533200 7200 0 EET} - {1206838800 10800 1 EEST} - {1224982800 7200 0 EET} - {1238288400 10800 1 EEST} - {1256432400 7200 0 EET} - {1269738000 10800 1 EEST} - {1288486800 7200 0 EET} - {1301187600 10800 1 EEST} - {1319936400 7200 0 EET} - {1332637200 10800 1 EEST} - {1351386000 7200 0 EET} - {1364691600 10800 1 EEST} - {1382835600 7200 0 EET} - {1396141200 10800 1 EEST} - {1414285200 7200 0 EET} - {1427590800 10800 1 EEST} - {1445734800 7200 0 EET} - {1459040400 10800 1 EEST} - {1477789200 7200 0 EET} - {1490490000 10800 1 EEST} - {1509238800 7200 0 EET} - {1521939600 10800 1 EEST} - {1540688400 7200 0 EET} - {1553994000 10800 1 EEST} - {1572138000 7200 0 EET} - {1585443600 10800 1 EEST} - {1603587600 7200 0 EET} - {1616893200 10800 1 EEST} - {1635642000 7200 0 EET} - {1648342800 10800 1 EEST} - {1667091600 7200 0 EET} - {1679792400 10800 1 EEST} - {1698541200 7200 0 EET} - {1711846800 10800 1 EEST} - {1729990800 7200 0 EET} - {1743296400 10800 1 EEST} - {1761440400 7200 0 EET} - {1774746000 10800 1 EEST} - {1792890000 7200 0 EET} - {1806195600 10800 1 EEST} - {1824944400 7200 0 EET} - {1837645200 10800 1 EEST} - {1856394000 7200 0 EET} - {1869094800 10800 1 EEST} - {1887843600 7200 0 EET} - {1901149200 10800 1 EEST} - {1919293200 7200 0 EET} - {1932598800 10800 1 EEST} - {1950742800 7200 0 EET} - {1964048400 10800 1 EEST} - {1982797200 7200 0 EET} - {1995498000 10800 1 EEST} - {2014246800 7200 0 EET} - {2026947600 10800 1 EEST} - {2045696400 7200 0 EET} - {2058397200 10800 1 EEST} - {2077146000 7200 0 EET} - {2090451600 10800 1 EEST} - {2108595600 7200 0 EET} - {2121901200 10800 1 EEST} - {2140045200 7200 0 EET} - {2153350800 10800 1 EEST} - {2172099600 7200 0 EET} - {2184800400 10800 1 EEST} - {2203549200 7200 0 EET} - {2216250000 10800 1 EEST} - {2234998800 7200 0 EET} - {2248304400 10800 1 EEST} - {2266448400 7200 0 EET} - {2279754000 10800 1 EEST} - {2297898000 7200 0 EET} - {2311203600 10800 1 EEST} - {2329347600 7200 0 EET} - {2342653200 10800 1 EEST} - {2361402000 7200 0 EET} - {2374102800 10800 1 EEST} - {2392851600 7200 0 EET} - {2405552400 10800 1 EEST} - {2424301200 7200 0 EET} - {2437606800 10800 1 EEST} - {2455750800 7200 0 EET} - {2469056400 10800 1 EEST} - {2487200400 7200 0 EET} - {2500506000 10800 1 EEST} - {2519254800 7200 0 EET} - {2531955600 10800 1 EEST} - {2550704400 7200 0 EET} - {2563405200 10800 1 EEST} - {2582154000 7200 0 EET} - {2595459600 10800 1 EEST} - {2613603600 7200 0 EET} - {2626909200 10800 1 EEST} - {2645053200 7200 0 EET} - {2658358800 10800 1 EEST} - {2676502800 7200 0 EET} - {2689808400 10800 1 EEST} - {2708557200 7200 0 EET} - {2721258000 10800 1 EEST} - {2740006800 7200 0 EET} - {2752707600 10800 1 EEST} - {2771456400 7200 0 EET} - {2784762000 10800 1 EEST} - {2802906000 7200 0 EET} - {2816211600 10800 1 EEST} - {2834355600 7200 0 EET} - {2847661200 10800 1 EEST} - {2866410000 7200 0 EET} - {2879110800 10800 1 EEST} - {2897859600 7200 0 EET} - {2910560400 10800 1 EEST} - {2929309200 7200 0 EET} - {2942010000 10800 1 EEST} - {2960758800 7200 0 EET} - {2974064400 10800 1 EEST} - {2992208400 7200 0 EET} - {3005514000 10800 1 EEST} - {3023658000 7200 0 EET} - {3036963600 10800 1 EEST} - {3055712400 7200 0 EET} - {3068413200 10800 1 EEST} - {3087162000 7200 0 EET} - {3099862800 10800 1 EEST} - {3118611600 7200 0 EET} - {3131917200 10800 1 EEST} - {3150061200 7200 0 EET} - {3163366800 10800 1 EEST} - {3181510800 7200 0 EET} - {3194816400 10800 1 EEST} - {3212960400 7200 0 EET} - {3226266000 10800 1 EEST} - {3245014800 7200 0 EET} - {3257715600 10800 1 EEST} - {3276464400 7200 0 EET} - {3289165200 10800 1 EEST} - {3307914000 7200 0 EET} - {3321219600 10800 1 EEST} - {3339363600 7200 0 EET} - {3352669200 10800 1 EEST} - {3370813200 7200 0 EET} - {3384118800 10800 1 EEST} - {3402867600 7200 0 EET} - {3415568400 10800 1 EEST} - {3434317200 7200 0 EET} - {3447018000 10800 1 EEST} - {3465766800 7200 0 EET} - {3479072400 10800 1 EEST} - {3497216400 7200 0 EET} - {3510522000 10800 1 EEST} - {3528666000 7200 0 EET} - {3541971600 10800 1 EEST} - {3560115600 7200 0 EET} - {3573421200 10800 1 EEST} - {3592170000 7200 0 EET} - {3604870800 10800 1 EEST} - {3623619600 7200 0 EET} - {3636320400 10800 1 EEST} - {3655069200 7200 0 EET} - {3668374800 10800 1 EEST} - {3686518800 7200 0 EET} - {3699824400 10800 1 EEST} - {3717968400 7200 0 EET} - {3731274000 10800 1 EEST} - {3750022800 7200 0 EET} - {3762723600 10800 1 EEST} - {3781472400 7200 0 EET} - {3794173200 10800 1 EEST} - {3812922000 7200 0 EET} - {3825622800 10800 1 EEST} - {3844371600 7200 0 EET} - {3857677200 10800 1 EEST} - {3875821200 7200 0 EET} - {3889126800 10800 1 EEST} - {3907270800 7200 0 EET} - {3920576400 10800 1 EEST} - {3939325200 7200 0 EET} - {3952026000 10800 1 EEST} - {3970774800 7200 0 EET} - {3983475600 10800 1 EEST} - {4002224400 7200 0 EET} - {4015530000 10800 1 EEST} - {4033674000 7200 0 EET} - {4046979600 10800 1 EEST} - {4065123600 7200 0 EET} - {4078429200 10800 1 EEST} - {4096573200 7200 0 EET} + {859680000 10800 1 EEST} + {877824000 7200 0 EET} + {891129600 10800 1 EEST} + {909273600 7200 0 EET} + {922579200 10800 1 EEST} + {941328000 7200 0 EET} + {954028800 10800 1 EEST} + {972777600 7200 0 EET} + {985478400 10800 1 EEST} + {1004227200 7200 0 EET} + {1017532800 10800 1 EEST} + {1035676800 7200 0 EET} + {1048982400 10800 1 EEST} + {1067126400 7200 0 EET} + {1080432000 10800 1 EEST} + {1099180800 7200 0 EET} + {1111881600 10800 1 EEST} + {1130630400 7200 0 EET} + {1143331200 10800 1 EEST} + {1162080000 7200 0 EET} + {1174780800 10800 1 EEST} + {1193529600 7200 0 EET} + {1206835200 10800 1 EEST} + {1224979200 7200 0 EET} + {1238284800 10800 1 EEST} + {1256428800 7200 0 EET} + {1269734400 10800 1 EEST} + {1288483200 7200 0 EET} + {1301184000 10800 1 EEST} + {1319932800 7200 0 EET} + {1332633600 10800 1 EEST} + {1351382400 7200 0 EET} + {1364688000 10800 1 EEST} + {1382832000 7200 0 EET} + {1396137600 10800 1 EEST} + {1414281600 7200 0 EET} + {1427587200 10800 1 EEST} + {1445731200 7200 0 EET} + {1459036800 10800 1 EEST} + {1477785600 7200 0 EET} + {1490486400 10800 1 EEST} + {1509235200 7200 0 EET} + {1521936000 10800 1 EEST} + {1540684800 7200 0 EET} + {1553990400 10800 1 EEST} + {1572134400 7200 0 EET} + {1585440000 10800 1 EEST} + {1603584000 7200 0 EET} + {1616889600 10800 1 EEST} + {1635638400 7200 0 EET} + {1648339200 10800 1 EEST} + {1667088000 7200 0 EET} + {1679788800 10800 1 EEST} + {1698537600 7200 0 EET} + {1711843200 10800 1 EEST} + {1729987200 7200 0 EET} + {1743292800 10800 1 EEST} + {1761436800 7200 0 EET} + {1774742400 10800 1 EEST} + {1792886400 7200 0 EET} + {1806192000 10800 1 EEST} + {1824940800 7200 0 EET} + {1837641600 10800 1 EEST} + {1856390400 7200 0 EET} + {1869091200 10800 1 EEST} + {1887840000 7200 0 EET} + {1901145600 10800 1 EEST} + {1919289600 7200 0 EET} + {1932595200 10800 1 EEST} + {1950739200 7200 0 EET} + {1964044800 10800 1 EEST} + {1982793600 7200 0 EET} + {1995494400 10800 1 EEST} + {2014243200 7200 0 EET} + {2026944000 10800 1 EEST} + {2045692800 7200 0 EET} + {2058393600 10800 1 EEST} + {2077142400 7200 0 EET} + {2090448000 10800 1 EEST} + {2108592000 7200 0 EET} + {2121897600 10800 1 EEST} + {2140041600 7200 0 EET} + {2153347200 10800 1 EEST} + {2172096000 7200 0 EET} + {2184796800 10800 1 EEST} + {2203545600 7200 0 EET} + {2216246400 10800 1 EEST} + {2234995200 7200 0 EET} + {2248300800 10800 1 EEST} + {2266444800 7200 0 EET} + {2279750400 10800 1 EEST} + {2297894400 7200 0 EET} + {2311200000 10800 1 EEST} + {2329344000 7200 0 EET} + {2342649600 10800 1 EEST} + {2361398400 7200 0 EET} + {2374099200 10800 1 EEST} + {2392848000 7200 0 EET} + {2405548800 10800 1 EEST} + {2424297600 7200 0 EET} + {2437603200 10800 1 EEST} + {2455747200 7200 0 EET} + {2469052800 10800 1 EEST} + {2487196800 7200 0 EET} + {2500502400 10800 1 EEST} + {2519251200 7200 0 EET} + {2531952000 10800 1 EEST} + {2550700800 7200 0 EET} + {2563401600 10800 1 EEST} + {2582150400 7200 0 EET} + {2595456000 10800 1 EEST} + {2613600000 7200 0 EET} + {2626905600 10800 1 EEST} + {2645049600 7200 0 EET} + {2658355200 10800 1 EEST} + {2676499200 7200 0 EET} + {2689804800 10800 1 EEST} + {2708553600 7200 0 EET} + {2721254400 10800 1 EEST} + {2740003200 7200 0 EET} + {2752704000 10800 1 EEST} + {2771452800 7200 0 EET} + {2784758400 10800 1 EEST} + {2802902400 7200 0 EET} + {2816208000 10800 1 EEST} + {2834352000 7200 0 EET} + {2847657600 10800 1 EEST} + {2866406400 7200 0 EET} + {2879107200 10800 1 EEST} + {2897856000 7200 0 EET} + {2910556800 10800 1 EEST} + {2929305600 7200 0 EET} + {2942006400 10800 1 EEST} + {2960755200 7200 0 EET} + {2974060800 10800 1 EEST} + {2992204800 7200 0 EET} + {3005510400 10800 1 EEST} + {3023654400 7200 0 EET} + {3036960000 10800 1 EEST} + {3055708800 7200 0 EET} + {3068409600 10800 1 EEST} + {3087158400 7200 0 EET} + {3099859200 10800 1 EEST} + {3118608000 7200 0 EET} + {3131913600 10800 1 EEST} + {3150057600 7200 0 EET} + {3163363200 10800 1 EEST} + {3181507200 7200 0 EET} + {3194812800 10800 1 EEST} + {3212956800 7200 0 EET} + {3226262400 10800 1 EEST} + {3245011200 7200 0 EET} + {3257712000 10800 1 EEST} + {3276460800 7200 0 EET} + {3289161600 10800 1 EEST} + {3307910400 7200 0 EET} + {3321216000 10800 1 EEST} + {3339360000 7200 0 EET} + {3352665600 10800 1 EEST} + {3370809600 7200 0 EET} + {3384115200 10800 1 EEST} + {3402864000 7200 0 EET} + {3415564800 10800 1 EEST} + {3434313600 7200 0 EET} + {3447014400 10800 1 EEST} + {3465763200 7200 0 EET} + {3479068800 10800 1 EEST} + {3497212800 7200 0 EET} + {3510518400 10800 1 EEST} + {3528662400 7200 0 EET} + {3541968000 10800 1 EEST} + {3560112000 7200 0 EET} + {3573417600 10800 1 EEST} + {3592166400 7200 0 EET} + {3604867200 10800 1 EEST} + {3623616000 7200 0 EET} + {3636316800 10800 1 EEST} + {3655065600 7200 0 EET} + {3668371200 10800 1 EEST} + {3686515200 7200 0 EET} + {3699820800 10800 1 EEST} + {3717964800 7200 0 EET} + {3731270400 10800 1 EEST} + {3750019200 7200 0 EET} + {3762720000 10800 1 EEST} + {3781468800 7200 0 EET} + {3794169600 10800 1 EEST} + {3812918400 7200 0 EET} + {3825619200 10800 1 EEST} + {3844368000 7200 0 EET} + {3857673600 10800 1 EEST} + {3875817600 7200 0 EET} + {3889123200 10800 1 EEST} + {3907267200 7200 0 EET} + {3920572800 10800 1 EEST} + {3939321600 7200 0 EET} + {3952022400 10800 1 EEST} + {3970771200 7200 0 EET} + {3983472000 10800 1 EEST} + {4002220800 7200 0 EET} + {4015526400 10800 1 EEST} + {4033670400 7200 0 EET} + {4046976000 10800 1 EEST} + {4065120000 7200 0 EET} + {4078425600 10800 1 EEST} + {4096569600 7200 0 EET} } diff --git a/library/tzdata/Europe/Simferopol b/library/tzdata/Europe/Simferopol index f6431fa..3e4b60a 100644 --- a/library/tzdata/Europe/Simferopol +++ b/library/tzdata/Europe/Simferopol @@ -42,7 +42,6 @@ set TZData(:Europe/Simferopol) { {796165200 14400 1 MSD} {811886400 10800 0 MSK} {828219600 14400 1 MSD} - {828230400 14400 1 MSD} {852066000 10800 0 MSK} {859683600 10800 0 EEST} {877827600 7200 0 EET} diff --git a/library/tzdata/Europe/Sofia b/library/tzdata/Europe/Sofia index 8fd55f6..a07f3bc 100644 --- a/library/tzdata/Europe/Sofia +++ b/library/tzdata/Europe/Sofia @@ -18,7 +18,6 @@ set TZData(:Europe/Sofia) { {355266000 10800 1 EEST} {370393200 7200 0 EET} {386715600 10800 1 EEST} - {401842800 10800 0 EEST} {401846400 7200 0 EET} {417571200 10800 1 EEST} {433296000 7200 0 EET} diff --git a/library/tzdata/Europe/Tallinn b/library/tzdata/Europe/Tallinn index 17f14e6..e0f22a5 100644 --- a/library/tzdata/Europe/Tallinn +++ b/library/tzdata/Europe/Tallinn @@ -53,8 +53,7 @@ set TZData(:Europe/Tallinn) { {906415200 10800 0 EEST} {909277200 7200 0 EET} {922582800 10800 1 EEST} - {941331600 7200 0 EET} - {941407200 7200 0 EET} + {941335200 7200 0 EET} {1014242400 7200 0 EET} {1017536400 10800 1 EEST} {1035680400 7200 0 EET} diff --git a/library/tzdata/Europe/Volgograd b/library/tzdata/Europe/Volgograd index 8c29c58..d71fb0b 100644 --- a/library/tzdata/Europe/Volgograd +++ b/library/tzdata/Europe/Volgograd @@ -28,43 +28,43 @@ set TZData(:Europe/Volgograd) { {638319600 14400 1 VOLST} {654649200 10800 0 VOLT} {670374000 14400 0 VOLT} - {701820000 14400 0 MSK} + {701820000 14400 0 MSD} {717534000 10800 0 MSK} - {733273200 14400 1 MSK} + {733273200 14400 1 MSD} {748998000 10800 0 MSK} - {764722800 14400 1 MSK} + {764722800 14400 1 MSD} {780447600 10800 0 MSK} - {796172400 14400 1 MSK} + {796172400 14400 1 MSD} {811897200 10800 0 MSK} - {828226800 14400 1 MSK} + {828226800 14400 1 MSD} {846370800 10800 0 MSK} - {859676400 14400 1 MSK} + {859676400 14400 1 MSD} {877820400 10800 0 MSK} - {891126000 14400 1 MSK} + {891126000 14400 1 MSD} {909270000 10800 0 MSK} - {922575600 14400 1 MSK} + {922575600 14400 1 MSD} {941324400 10800 0 MSK} - {954025200 14400 1 MSK} + {954025200 14400 1 MSD} {972774000 10800 0 MSK} - {985474800 14400 1 MSK} + {985474800 14400 1 MSD} {1004223600 10800 0 MSK} - {1017529200 14400 1 MSK} + {1017529200 14400 1 MSD} {1035673200 10800 0 MSK} - {1048978800 14400 1 MSK} + {1048978800 14400 1 MSD} {1067122800 10800 0 MSK} - {1080428400 14400 1 MSK} + {1080428400 14400 1 MSD} {1099177200 10800 0 MSK} - {1111878000 14400 1 MSK} + {1111878000 14400 1 MSD} {1130626800 10800 0 MSK} - {1143327600 14400 1 MSK} + {1143327600 14400 1 MSD} {1162076400 10800 0 MSK} - {1174777200 14400 1 MSK} + {1174777200 14400 1 MSD} {1193526000 10800 0 MSK} - {1206831600 14400 1 MSK} + {1206831600 14400 1 MSD} {1224975600 10800 0 MSK} - {1238281200 14400 1 MSK} + {1238281200 14400 1 MSD} {1256425200 10800 0 MSK} - {1269730800 14400 1 MSK} + {1269730800 14400 1 MSD} {1288479600 10800 0 MSK} {1301180400 14400 0 MSK} {1414274400 10800 0 MSK} diff --git a/library/tzdata/Pacific/Easter b/library/tzdata/Pacific/Easter index f76594a..4b45ba2 100644 --- a/library/tzdata/Pacific/Easter +++ b/library/tzdata/Pacific/Easter @@ -1,14 +1,9 @@ # created by tools/tclZIC.tcl - do not edit set TZData(:Pacific/Easter) { - {-9223372036854775808 -26264 0 LMT} - {-2524495336 -26248 0 EMT} - {-1178124152 -21600 0 EASST} - {-870552000 -25200 0 EAST} - {-865278000 -21600 1 EASST} - {-740520000 -21600 1 EASST} - {-736376400 -25200 0 EAST} - {-718056000 -25200 0 EAST} + {-9223372036854775808 -26248 0 LMT} + {-2524495352 -26248 0 EMT} + {-1178124152 -25200 0 EAST} {-36619200 -21600 1 EASST} {-23922000 -25200 0 EAST} {-3355200 -21600 1 EASST} @@ -36,7 +31,6 @@ set TZData(:Pacific/Easter) { {340171200 -21600 1 EASST} {353473200 -25200 0 EAST} {371620800 -21600 1 EASST} - {384836400 -18000 0 EAST} {384922800 -21600 0 EAST} {403070400 -18000 1 EASST} {416372400 -21600 0 EAST} @@ -50,10 +44,10 @@ set TZData(:Pacific/Easter) { {545194800 -21600 0 EAST} {560923200 -18000 1 EASST} {574225200 -21600 0 EAST} - {591768000 -18000 1 EASST} + {592372800 -18000 1 EASST} {605674800 -21600 0 EAST} {624427200 -18000 1 EASST} - {637729200 -21600 0 EAST} + {637124400 -21600 0 EAST} {653457600 -18000 1 EASST} {668574000 -21600 0 EAST} {687326400 -18000 1 EASST} diff --git a/library/tzdata/Pacific/Midway b/library/tzdata/Pacific/Midway index c07b030..d044569 100644 --- a/library/tzdata/Pacific/Midway +++ b/library/tzdata/Pacific/Midway @@ -1,10 +1,5 @@ # created by tools/tclZIC.tcl - do not edit - -set TZData(:Pacific/Midway) { - {-9223372036854775808 -42568 0 LMT} - {-2177410232 -39600 0 NST} - {-428504400 -36000 1 NDT} - {-420645600 -39600 0 NST} - {-86878800 -39600 0 BST} - {439038000 -39600 0 SST} +if {![info exists TZData(Pacific/Pago_Pago)]} { + LoadTimeZoneFile Pacific/Pago_Pago } +set TZData(:Pacific/Midway) $TZData(:Pacific/Pago_Pago) diff --git a/library/tzdata/Pacific/Saipan b/library/tzdata/Pacific/Saipan index b799298..4e769cd 100644 --- a/library/tzdata/Pacific/Saipan +++ b/library/tzdata/Pacific/Saipan @@ -1,9 +1,5 @@ # created by tools/tclZIC.tcl - do not edit - -set TZData(:Pacific/Saipan) { - {-9223372036854775808 -51420 0 LMT} - {-3944626980 34980 0 LMT} - {-2177487780 32400 0 MPT} - {-7981200 36000 0 MPT} - {977493600 36000 0 ChST} +if {![info exists TZData(Pacific/Guam)]} { + LoadTimeZoneFile Pacific/Guam } +set TZData(:Pacific/Saipan) $TZData(:Pacific/Guam) diff --git a/macosx/Tcl.xcode/project.pbxproj b/macosx/Tcl.xcode/project.pbxproj index a2a703b..a28b8db 100644 --- a/macosx/Tcl.xcode/project.pbxproj +++ b/macosx/Tcl.xcode/project.pbxproj @@ -770,7 +770,6 @@ F96D43D108F272B8004A47F5 /* checkLibraryDoc.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = checkLibraryDoc.tcl; sourceTree = "<group>"; }; F96D43D208F272B8004A47F5 /* configure */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.script.sh; path = configure; sourceTree = "<group>"; }; F96D43D308F272B8004A47F5 /* configure.in */ = {isa = PBXFileReference; explicitFileType = text.script.sh; fileEncoding = 4; path = configure.in; sourceTree = "<group>"; }; - F96D442208F272B8004A47F5 /* eolFix.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = eolFix.tcl; sourceTree = "<group>"; }; F96D442408F272B8004A47F5 /* fix_tommath_h.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = fix_tommath_h.tcl; sourceTree = "<group>"; }; F96D442508F272B8004A47F5 /* genStubs.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = genStubs.tcl; sourceTree = "<group>"; }; F96D442708F272B8004A47F5 /* index.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = index.tcl; sourceTree = "<group>"; }; @@ -1668,7 +1667,6 @@ F96D43D108F272B8004A47F5 /* checkLibraryDoc.tcl */, F96D43D208F272B8004A47F5 /* configure */, F96D43D308F272B8004A47F5 /* configure.in */, - F96D442208F272B8004A47F5 /* eolFix.tcl */, F96D442408F272B8004A47F5 /* fix_tommath_h.tcl */, F96D442508F272B8004A47F5 /* genStubs.tcl */, F96D442708F272B8004A47F5 /* index.tcl */, diff --git a/macosx/Tcl.xcodeproj/project.pbxproj b/macosx/Tcl.xcodeproj/project.pbxproj index 9c18ac0..7c0d083 100644 --- a/macosx/Tcl.xcodeproj/project.pbxproj +++ b/macosx/Tcl.xcodeproj/project.pbxproj @@ -770,7 +770,6 @@ F96D43D108F272B8004A47F5 /* checkLibraryDoc.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = checkLibraryDoc.tcl; sourceTree = "<group>"; }; F96D43D208F272B8004A47F5 /* configure */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.script.sh; path = configure; sourceTree = "<group>"; }; F96D43D308F272B8004A47F5 /* configure.in */ = {isa = PBXFileReference; explicitFileType = text.script.sh; fileEncoding = 4; path = configure.in; sourceTree = "<group>"; }; - F96D442208F272B8004A47F5 /* eolFix.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = eolFix.tcl; sourceTree = "<group>"; }; F96D442408F272B8004A47F5 /* fix_tommath_h.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = fix_tommath_h.tcl; sourceTree = "<group>"; }; F96D442508F272B8004A47F5 /* genStubs.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = genStubs.tcl; sourceTree = "<group>"; }; F96D442708F272B8004A47F5 /* index.tcl */ = {isa = PBXFileReference; explicitFileType = text.script; fileEncoding = 4; path = index.tcl; sourceTree = "<group>"; }; @@ -1668,7 +1667,6 @@ F96D43D108F272B8004A47F5 /* checkLibraryDoc.tcl */, F96D43D208F272B8004A47F5 /* configure */, F96D43D308F272B8004A47F5 /* configure.in */, - F96D442208F272B8004A47F5 /* eolFix.tcl */, F96D442408F272B8004A47F5 /* fix_tommath_h.tcl */, F96D442508F272B8004A47F5 /* genStubs.tcl */, F96D442708F272B8004A47F5 /* index.tcl */, diff --git a/tests/clock.test b/tests/clock.test index 2abeab9..615f3a8 100644 --- a/tests/clock.test +++ b/tests/clock.test @@ -36931,11 +36931,37 @@ test clock-67.2 {Bug d19a30db57} -body { # error, not segfault tcl::clock::GetJulianDayFromEraYearMonthDay {} 2361222 } -returnCodes error -match glob -result * + test clock-67.3 {Bug d19a30db57} -body { # error, not segfault tcl::clock::GetJulianDayFromEraYearWeekDay {} 2361222 } -returnCodes error -match glob -result * +test clock-67.4 {Change format %x output on global locale change [Bug 4a0c163d24]} -setup { + package require msgcat + set current [msgcat::mclocale] +} -body { + msgcat::mclocale de_de + set res [regexp {^\d{2}\.\d{2}\.\d{4}$} [clock format 1 -locale current -format %x]] + msgcat::mclocale en_uk + lappend res [regexp {^\d{2}/\d{2}/\d{4}$} [clock format 1 -locale current -format %x]] +} -cleanup { + msgcat::mclocale $current +} -result {1 1} + +test clock-67.5 {Change scan %x output on global locale change [Bug 4a0c163d24]} -setup { + package require msgcat + set current [msgcat::mclocale] +} -body { + msgcat::mclocale de_de + set res [clock scan "01.01.1970" -locale current -format %x] + msgcat::mclocale en_uk + # This will fail without the bug fix, as still de_de is active + expr {$res == [clock scan "01/01/1970" -locale current -format %x]} +} -cleanup { + msgcat::mclocale $current +} -result {1} + # cleanup namespace delete ::testClock diff --git a/tests/execute.test b/tests/execute.test index 94af158..9a2ffbd 100644 --- a/tests/execute.test +++ b/tests/execute.test @@ -1043,6 +1043,29 @@ test execute-11.1 {Bug 3142026: GrowEvaluationStack off-by-one} -setup { } -cleanup { interp delete slave } -result ok + +test execute-11.2 {Bug 268b23df11} -setup { + proc zero {} {return 0} + proc crash {} {expr {abs([zero])}} + proc noop args {} + trace add execution crash enterstep noop +} -body { + crash +} -cleanup { + trace remove execution crash enterstep noop + rename noop {} + rename crash {} + rename zero {} +} -result 0 +test execute-11.3 {Bug a0ece9d6d4} -setup { + proc crash {} {expr {rand()}} + trace add execution crash enterstep {apply {args {info frame -2}}} +} -body { + string is double [crash] +} -cleanup { + trace remove execution crash enterstep {apply {args {info frame -2}}} + rename crash {} +} -result 1 # cleanup if {[info commands testobj] != {}} { diff --git a/tests/expr.test b/tests/expr.test index 6ad7208..4c03262 100644 --- a/tests/expr.test +++ b/tests/expr.test @@ -7174,6 +7174,10 @@ test expr-50.1 {test sqrt() of bignums with non-Inf answer} { expr {sqrt("1[string repeat 0 616]") == 1e308} } 1 +test expr-51.1 {test round-to-even on input} { + expr 6.9294956446009195e15 +} 6929495644600920.0 + # cleanup diff --git a/tests/for.test b/tests/for.test index 8abd270..1a65274 100644 --- a/tests/for.test +++ b/tests/for.test @@ -1184,6 +1184,172 @@ test for-7.24 {Bug 3614226: ensure that continue from expanded command only clea expr {$end - $tmp} }} {return -level 0 -code continue} } 0 + +test for-8.0 {Coverity CID 1251203: break vs continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i; list a [eval {}]} { + incr j + }] + incr i + } + list $i $j $k + }} +} {6 5 3} +test for-8.1 {Coverity CID 1251203: break vs continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i;list a [eval break]} { + incr j + }] + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.2 {Coverity CID 1251203: break vs continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i;list a [eval continue]} { + incr j + }] + incr i + } + list $i $j $k + }} +} {1 1 3} +test for-8.3 {break in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i; break} { + incr j + }] + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.4 {continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i; continue} { + incr j + }] + incr i + } + list $i $j $k + }} +} {1 1 3} +test for-8.5 {break in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i; list a [break]} { + incr j + }] + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.6 {continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i; list a [continue]} { + incr j + }] + incr i + } + list $i $j $k + }} +} {1 1 3} +test for-8.7 {break in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i;eval break} { + incr j + }] + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.8 {continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + list a [\ + for {set i 0} {$i < 5} {incr i;eval continue} { + incr j + }] + incr i + } + list $i $j $k + }} +} {1 1 3} +test for-8.9 {break in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + for {set i 0} {$i < 5} {incr i;eval break} { + incr j + } + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.10 {continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + for {set i 0} {$i < 5} {incr i;eval continue} { + incr j + } + incr i + } + list $i $j $k + }} +} {1 1 3} +test for-8.11 {break in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + for {set i 0} {$i < 5} {incr i;break} { + incr j + } + incr i + } + list $i $j $k + }} +} {2 1 3} +test for-8.12 {continue in for-step clause} { + apply {{} { + for {set k 0} {$k < 3} {incr k} { + set j 0 + for {set i 0} {$i < 5} {incr i;continue} { + incr j + } + incr i + } + list $i $j $k + }} +} {1 1 3} # cleanup ::tcltest::cleanupTests diff --git a/tests/http.test b/tests/http.test index a0a26de..41820cb 100644 --- a/tests/http.test +++ b/tests/http.test @@ -306,7 +306,6 @@ test http-3.13 {http::geturl socket leak test} { for {set i 0} {$i < 3} {incr i} { catch {http::geturl $badurl -timeout 5000} } - # No extra channels should be taken expr {[llength [file channels]] == $chanCount} } 1 @@ -372,11 +371,11 @@ test http-3.27 {http::geturl: -headers override -type} -body { http::data $token } -cleanup { http::cleanup $token -} -match regexp -result {(?n)Accept \*/\* -Host .* +} -match regexp -result {(?n)Host .* User-Agent .* Connection close Content-Type {text/plain;charset=utf-8} +Accept \*/\* Accept-Encoding .* Content-Length 5} test http-3.28 {http::geturl: -headers override -type default} -body { @@ -385,11 +384,11 @@ test http-3.28 {http::geturl: -headers override -type default} -body { http::data $token } -cleanup { http::cleanup $token -} -match regexp -result {(?n)Accept \*/\* -Host .* +} -match regexp -result {(?n)Host .* User-Agent .* Connection close Content-Type {text/plain;charset=utf-8} +Accept \*/\* Accept-Encoding .* Content-Length 5} test http-3.29 {http::geturl IPv6 address} -body { @@ -418,6 +417,21 @@ test http-3.31 {http::geturl fragment without path} -body { } -cleanup { catch { http::cleanup $token } } -result 200 +# Bug c11a51c482 +test http-3.32 {http::geturl: -headers override -accept default} -body { + set token [http::geturl $url/headers -query dummy \ + -headers [list "Accept" "text/plain,application/tcl-test-value"]] + http::data $token +} -cleanup { + http::cleanup $token +} -match regexp -result {(?n)Host .* +User-Agent .* +Connection close +Accept text/plain,application/tcl-test-value +Accept-Encoding .* +Content-Type application/x-www-form-urlencoded +Content-Length 5} + test http-4.1 {http::Event} -body { set token [http::geturl $url -keepalive 0] upvar #0 $token data diff --git a/tests/http11.test b/tests/http11.test index 230ce5a..c9ded0b 100644 --- a/tests/http11.test +++ b/tests/http11.test @@ -70,11 +70,8 @@ proc check_crc {tok args} { return "ok" } -makeFile "<html><head><title>test</title></head>\ -<body><p>this is a test</p>\n\ -[string repeat {<p>This is a tcl test file.</p>} 4192]\n\ -</body></html>" testdoc.html - +makeFile "<html><head><title>test</title></head><body><p>this is a test</p>\n[string repeat {<p>This is a tcl test file.</p>} 4192]\n</body></html>" testdoc.html + # ------------------------------------------------------------------------- test http11-1.0 "normal request for document " -setup { @@ -447,7 +444,8 @@ test http11-2.10 "-channel,deflate,keepalive" -setup { set chan [open [makeFile {} testfile.tmp] wb+] } -body { set tok [http::geturl http://localhost:$httpd_port/testdoc.html \ - -timeout 5000 -channel $chan -keepalive 1] + -timeout 5000 -channel $chan -keepalive 1 \ + -headers {accept-encoding deflate}] http::wait $tok seek $chan 0 set data [read $chan] @@ -482,6 +480,27 @@ test http11-2.11 "-channel,identity,keepalive" -setup { halt_httpd } -result {ok {HTTP/1.1 200 OK} ok {} {} chunked} +test http11-2.12 "-channel,negotiate,keepalive" -setup { + variable httpd [create_httpd] + set chan [open [makeFile {} testfile.tmp] wb+] +} -body { + set tok [http::geturl http://localhost:$httpd_port/testdoc.html \ + -timeout 5000 -channel $chan -keepalive 1] + http::wait $tok + seek $chan 0 + set data [read $chan] + list [http::status $tok] [http::code $tok] [check_crc $tok $data]\ + [meta $tok connection] [meta $tok content-encoding]\ + [meta $tok transfer-encoding] [meta $tok x-requested-encodings]\ + [expr {[file size testdoc.html]-[file size testfile.tmp]}] +} -cleanup { + http::cleanup $tok + close $chan + removeFile testfile.tmp + halt_httpd +} -result {ok {HTTP/1.1 200 OK} ok {} gzip chunked gzip,deflate,compress 0} + + # ------------------------------------------------------------------------- # # The following tests for the -handler option will require changes in @@ -644,7 +663,7 @@ test http11-4.3 "normal post request, check channel query length" -setup { removeFile testfile.tmp halt_httpd } -result {status ok code {HTTP/1.1 200 OK} crc ok connection close query-length 122880} - + # ------------------------------------------------------------------------- foreach p {create_httpd httpd_read halt_httpd meta check_crc} { diff --git a/tests/httpd11.tcl b/tests/httpd11.tcl index 9c543dc..6eae2b7 100644 --- a/tests/httpd11.tcl +++ b/tests/httpd11.tcl @@ -44,7 +44,7 @@ proc get-chunks {data {compression gzip}} { deflate { set data [zlib deflate $data] } compress { set data [zlib compress $data] } } - + set data "" set chunker [make-chunk-generator $data 512] while {[string length [set chunk [$chunker]]]} { @@ -59,7 +59,7 @@ proc blow-chunks {data {ochan stdout} {compression gzip}} { deflate { set data [zlib deflate $data] } compress { set data [zlib compress $data] } } - + set chunker [make-chunk-generator $data 512] while {[string length [set chunk [$chunker]]]} { puts -nonewline $ochan $chunk @@ -156,20 +156,20 @@ proc Service {chan addr port} { set code "200 OK" set close [expr {[dict get? $meta connection] eq "close"}] } - + if {$protocol eq "HTTP/1.1"} { - if {[string match "*deflate*" [dict get? $meta accept-encoding]]} { - set encoding deflate - } elseif {[string match "*gzip*" [dict get? $meta accept-encoding]]} { - set encoding gzip - } elseif {[string match "*compress*" [dict get? $meta accept-encoding]]} { - set encoding compress - } + foreach enc [split [dict get? $meta accept-encoding] ,] { + set enc [string trim $enc] + if {$enc in {deflate gzip compress}} { + set encoding $enc + break + } + } set transfer chunked } else { set close 1 } - + foreach pair [split $query &] { if {[scan $pair {%[^=]=%s} key val] != 2} {set val ""} switch -exact -- $key { @@ -189,6 +189,7 @@ proc Service {chan addr port} { if {$close} { Puts $chan "connection: close" } + Puts $chan "x-requested-encodings: [dict get? $meta accept-encoding]" if {$encoding eq "identity"} { Puts $chan "content-length: [string length $data]" } else { @@ -208,7 +209,7 @@ proc Service {chan addr port} { } else { puts -nonewline $chan $data } - + if {$close} { chan event $chan readable {} close $chan diff --git a/tests/io.test b/tests/io.test index 06ae81d..6b6ad6d 100644 --- a/tests/io.test +++ b/tests/io.test @@ -1517,6 +1517,39 @@ test io-12.7 {ReadChars: too many chars read [bc5b790099]} { } close $c } {} +test io-12.8 {ReadChars: multibyte chars split} { + set f [open $path(test1) w] + fconfigure $f -translation binary + puts -nonewline $f [string repeat a 9]\xc2\xa0 + close $f + set f [open $path(test1)] + fconfigure $f -encoding utf-8 -buffersize 10 + set in [read $f] + close $f + scan [string index $in end] %c +} 160 +test io-12.9 {ReadChars: multibyte chars split} { + set f [open $path(test1) w] + fconfigure $f -translation binary + puts -nonewline $f [string repeat a 9]\xc2 + close $f + set f [open $path(test1)] + fconfigure $f -encoding utf-8 -buffersize 10 + set in [read $f] + close $f + scan [string index $in end] %c +} 194 +test io-12.10 {ReadChars: multibyte chars split} { + set f [open $path(test1) w] + fconfigure $f -translation binary + puts -nonewline $f [string repeat a 9]\xc2 + close $f + set f [open $path(test1)] + fconfigure $f -encoding utf-8 -buffersize 11 + set in [read $f] + close $f + scan [string index $in end] %c +} 194 test io-13.1 {TranslateInputEOL: cr mode} {} { set f [open $path(test1) w] @@ -7355,7 +7388,7 @@ test io-53.4 {CopyData: background write overflow} {stdio unix openpipe fileeven set result "" fileevent $f1 read [namespace code { append result [read $f1 1024] - if {[string length $result] >= [string length $big]} { + if {[string length $result] >= [string length $big]+1} { set x done } }] @@ -7364,6 +7397,38 @@ test io-53.4 {CopyData: background write overflow} {stdio unix openpipe fileeven set big {} set x } done +test io-53.4.1 {Bug 894da183c8} {stdio fcopy} { + set big bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb\n + variable x + for {set x 0} {$x < 12} {incr x} { + append big $big + } + file delete $path(pipe) + set f1 [open $path(pipe) w] + puts $f1 [list file delete $path(test1)] + puts $f1 { + puts ready + set f [open io-53.4.1 w] + chan configure $f -translation lf + fcopy stdin $f -command { set x } + vwait x + close $f + } + puts $f1 "close \[[list open $path(test1) w]]" + close $f1 + set f1 [open "|[list [interpreter] $path(pipe)]" r+] + set result [gets $f1] + fconfigure $f1 -blocking 0 -buffersize 125000 -translation lf + puts $f1 $big + fconfigure $f1 -blocking 1 + close $f1 + set big {} + while {[catch {glob $path(test1)}]} {after 50} + file delete $path(test1) + set check [file size io-53.4.1] + file delete io-53.4.1 + set check +} 266241 set result {} proc FcopyTestAccept {sock args} { after 1000 "close $sock" @@ -8542,6 +8607,25 @@ test io-73.4 {[5adc350683] [read] after EOF} -setup { } -result {1 1 {more data } 1} +test io-73.5 {effect of eof on encoding end flags} -setup { + set fn [makeFile {} io-73.5] + set rfd [open $fn r] + set wfd [open $fn a] + chan configure $wfd -buffering none -translation binary + chan configure $rfd -buffersize 5 -encoding utf-8 + read $rfd +} -body { + set result [eof $rfd] + puts -nonewline $wfd "more\u00c2\u00a0data" + lappend result [eof $rfd] + lappend result [read $rfd] + lappend result [eof $rfd] +} -cleanup { + close $wfd + close $rfd + removeFile io-73.5 +} -result [list 1 1 more\u00a0data 1] + # ### ### ### ######### ######### ######### # cleanup diff --git a/tests/ioCmd.test b/tests/ioCmd.test index 4fbc380..cd89a02 100644 --- a/tests/ioCmd.test +++ b/tests/ioCmd.test @@ -349,7 +349,7 @@ test iocmd-8.19 {fconfigure command / win tty channel} -constraints {nonPortable close $tty } } -returnCodes error -result {bad option "-blah": should be one of -blocking, -buffering, -buffersize, -encoding, -eofchar, -translation, -mode, -handshake, -pollinterval, -sysbuffer, -timeout, -ttycontrol, or -xchar} -# TODO: Test parsing of serial channel options (nonportable, since requires an +# TODO: Test parsing of serial channel options (nonPortable, since requires an # open channel to work with). test iocmd-9.1 {eof command} { @@ -3770,7 +3770,7 @@ test iocmd.tf-32.0 {origin thread of moved channel gone} -match glob -body { # The test iocmd.tf-32.1 unavoidably exhibits a memory leak. We are testing # the ability of the reflected channel system to react to the situation where # the thread in which the driver routines runs exits during driver operations. -# In this case, thread exit handlers signal back to the owner thread so that the +# In this case, thread exit handlers signal back to the owner thread so that the # channel operation does not hang. There's no way to test this without actually # exiting a thread in mid-operation, and that action is unavoidably leaky (which # is why [thread::exit] is advised against). diff --git a/tests/lreplace.test b/tests/lreplace.test index d1319c6..e66a331 100644 --- a/tests/lreplace.test +++ b/tests/lreplace.test @@ -133,7 +133,6 @@ test lreplace-3.1 {lreplace won't modify shared argument objects} { test lreplace-4.1 {Bug ccc2c2cc98: lreplace edge case} { lreplace {} 1 1 } {} -# Note that this test will fail in 8.5 test lreplace-4.2 {Bug ccc2c2cc98: lreplace edge case} { lreplace { } 1 1 } {} @@ -146,6 +145,42 @@ test lreplace-4.4 {lreplace edge case} { test lreplace-4.5 {lreplace edge case} { lreplace {1 2 3 4 5} 3 0 _ } {1 2 3 _ 4 5} +test lreplace-4.6 {lreplace end-x: bug a4cb3f06c4} { + lreplace {0 1 2 3 4} 0 end-2 +} {3 4} +test lreplace-4.6.1 {lreplace end-x: bug a4cb3f06c4} { + lreplace {0 1 2 3 4} 0 end-2 a b c +} {a b c 3 4} +test lreplace-4.7 {lreplace with two end-indexes: increasing} { + lreplace {0 1 2 3 4} end-2 end-1 +} {0 1 4} +test lreplace-4.7.1 {lreplace with two end-indexes: increasing} { + lreplace {0 1 2 3 4} end-2 end-1 a b c +} {0 1 a b c 4} +test lreplace-4.8 {lreplace with two end-indexes: equal} { + lreplace {0 1 2 3 4} end-2 end-2 +} {0 1 3 4} +test lreplace-4.8.1 {lreplace with two end-indexes: equal} { + lreplace {0 1 2 3 4} end-2 end-2 a b c +} {0 1 a b c 3 4} +test lreplace-4.9 {lreplace with two end-indexes: decreasing} { + lreplace {0 1 2 3 4} end-2 end-3 +} {0 1 2 3 4} +test lreplace-4.9.1 {lreplace with two end-indexes: decreasing} { + lreplace {0 1 2 3 4} end-2 end-3 a b c +} {0 1 a b c 2 3 4} +test lreplace-4.10 {lreplace with two equal indexes} { + lreplace {0 1 2 3 4} 2 2 +} {0 1 3 4} +test lreplace-4.10.1 {lreplace with two equal indexes} { + lreplace {0 1 2 3 4} 2 2 a b c +} {0 1 a b c 3 4} +test lreplace-4.11 {lreplace end index first} { + lreplace {0 1 2 3 4} end-2 1 a b c +} {0 1 a b c 2 3 4} +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} # cleanup catch {unset foo} diff --git a/tests/msgcat.test b/tests/msgcat.test index 050b592..6b965d1 100644 --- a/tests/msgcat.test +++ b/tests/msgcat.test @@ -17,8 +17,8 @@ if {[catch {package require tcltest 2}]} { puts stderr "Skipping tests in [info script]. tcltest 2 required." return } -if {[catch {package require msgcat 1.5}]} { - puts stderr "Skipping tests in [info script]. No msgcat 1.5 found to test." +if {[catch {package require msgcat 1.6}]} { + puts stderr "Skipping tests in [info script]. No msgcat 1.6 found to test." return } @@ -32,6 +32,8 @@ namespace eval ::msgcat::test { # Tests msgcat-0.*: locale initialization + # Calculate set of all permutations of a list + # PowerSet {1 2 3} -> {1 2 3} {2 3} {1 3} 3 {1 2} 2 1 {} proc PowerSet {l} { if {[llength $l] == 0} {return [list [list]]} set element [lindex $l 0] @@ -412,9 +414,14 @@ namespace eval ::msgcat::test { foreach loc {foo foo_BAR foo_BAR_baz} { test msgcat-5.$count {mcload} -setup { variable locale [mclocale] + ::msgcat::mclocale "" + ::msgcat::mcloadedlocales clear + ::msgcat::mcpackageconfig unset mcfolder mclocale $loc } -cleanup { mclocale $locale + ::msgcat::mcloadedlocales clear + ::msgcat::mcpackageconfig unset mcfolder } -body { mcload $msgdir } -result [expr { $count+1 }] @@ -428,6 +435,8 @@ namespace eval ::msgcat::test { mclocale foo_BAR_notexist } -cleanup { mclocale $locale + mcloadedlocales clear + mcpackageconfig unset mcfolder } -body { mcload $msgdir } -result 3 @@ -437,6 +446,8 @@ namespace eval ::msgcat::test { mclocale no_FI_notexist } -cleanup { mclocale $locale + mcloadedlocales clear + mcpackageconfig unset mcfolder } -body { mcload $msgdir } -result 1 @@ -497,6 +508,20 @@ namespace eval ::msgcat::test { mc def } -result unknown:no_fi_notexist:def + test msgcat-5.11 {mcpackageconfig mcfolder} -setup { + variable locale [mclocale] + mclocale "" + mcloadedlocales clear + mcpackageconfig unset mcfolder + } -cleanup { + mclocale $locale + mcloadedlocales clear + mcpackageconfig unset mcfolder + } -body { + mclocale foo + mcpackageconfig set mcfolder $msgdir + } -result 2 + foreach loc $locales { if { $loc eq {} } { set msg ROOT @@ -657,6 +682,394 @@ namespace eval ::msgcat::test { removeDirectory msgdir2 removeDirectory msgdir3 + # Tests msgcat-9.*: [mcexists] + + test msgcat-9.1 {mcexists no parameter} -body { + mcexists + } -returnCodes 1\ + -result {wrong # args: should be "mcexists ?-exactnamespace? ?-exactlocale? src"} + + test msgcat-9.2 {mcexists unknown option} -body { + mcexists -unknown src + } -returnCodes 1\ + -result {unknown option "-unknown"} + + test msgcat-9.3 {mcexists} -setup { + mcforgetpackage + variable locale [mclocale] + mclocale foo + mcset foo k1 v1 + } -cleanup { + mclocale $locale + } -body { + list [mcexists k1] [mcexists k2] + } -result {1 0} + + test msgcat-9.4 {mcexists descendent preference} -setup { + mcforgetpackage + variable locale [mclocale] + mclocale foo_bar + mcset foo k1 v1 + } -cleanup { + mclocale $locale + } -body { + list [mcexists k1] [mcexists -exactlocale k1] + } -result {1 0} + + test msgcat-9.5 {mcexists parent namespace} -setup { + mcforgetpackage + variable locale [mclocale] + mclocale foo_bar + mcset foo k1 v1 + } -cleanup { + mclocale $locale + } -body { + namespace eval ::msgcat::test::sub { + list [::msgcat::mcexists k1]\ + [::msgcat::mcexists -exactnamespace k1] + } + } -result {1 0} + + # Tests msgcat-10.*: [mcloadedlocales] + + test msgcat-10.1 {mcloadedlocales no arg} -body { + mcloadedlocales + } -returnCodes 1\ + -result {wrong # args: should be "mcloadedlocales subcommand"} + + test msgcat-10.2 {mcloadedlocales wrong subcommand} -body { + mcloadedlocales junk + } -returnCodes 1\ + -result {unknown subcommand "junk": must be clear, or loaded} + + test msgcat-10.3 {mcloadedlocales loaded} -setup { + mcforgetpackage + variable locale [mclocale] + mclocale {} + mcloadedlocales clear + } -cleanup { + mclocale $locale + } -body { + mclocale foo_bar + # The result is position independent so sort + set resultlist [lsort [mcloadedlocales loaded]] + } -result {{} foo foo_bar} + + test msgcat-10.4 {mcloadedlocales clear} -setup { + mcforgetpackage + variable locale [mclocale] + mclocale {} + mcloadedlocales clear + } -cleanup { + mclocale $locale + } -body { + mclocale foo + mcset foo k1 v1 + set res [mcexists k1] + mclocale "" + mcloadedlocales clear + mclocale foo + lappend res [mcexists k1] + } -result {1 0} + + # Tests msgcat-11.*: [mcforgetpackage] + + test msgcat-11.1 {mcforgetpackage translation} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + } -body { + mclocale foo + mcset foo k1 v1 + set res [mcexists k1] + mcforgetpackage + lappend res [mcexists k1] + } -result {1 0} + + test msgcat-11.2 {mcforgetpackage locale} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + } -body { + mclocale foo + mcpackagelocale set bar + set res [mcpackagelocale get] + mcforgetpackage + lappend res [mcpackagelocale get] + } -result {bar foo} + + test msgcat-11.3 {mcforgetpackage options} -body { + mcpackageconfig set loadcmd "" + set res [mcpackageconfig isset loadcmd] + mcforgetpackage + lappend res [mcpackageconfig isset loadcmd] + } -result {1 0} + + # Tests msgcat-12.*: [mcpackagelocale] + + test msgcat-12.1 {mcpackagelocale no subcommand} -body { + mcpackagelocale + } -returnCodes 1\ + -result {wrong # args: should be "mcpackagelocale subcommand ?locale?"} + + test msgcat-12.2 {mclpackagelocale wrong subcommand} -body { + mcpackagelocale junk + } -returnCodes 1\ + -result {unknown subcommand "junk": must be clear, get, isset, loaded, present, set, or unset} + + test msgcat-12.3 {mcpackagelocale set} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale foo + mcpackagelocale set bar + list [mcpackagelocale get] [mclocale] + } -result {bar foo} + + test msgcat-12.4 {mcpackagelocale get} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale foo + set res [mcpackagelocale get] + mcpackagelocale set bar + lappend res [mcpackagelocale get] + } -result {foo bar} + + test msgcat-12.5 {mcpackagelocale preferences} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale foo + set res [list [mcpackagelocale preferences]] + mcpackagelocale set bar + lappend res [mcpackagelocale preferences] + } -result {{foo {}} {bar {}}} + + test msgcat-12.6 {mcpackagelocale loaded} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale "" + mcloadedlocales clear + mclocale foo + # The result is position independent so sort + set res [list [lsort [mcpackagelocale loaded]]] + mcpackagelocale set bar + lappend res [lsort [mcpackagelocale loaded]] + } -result {{{} foo} {{} bar foo}} + + test msgcat-12.7 {mcpackagelocale isset} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale foo + set res [mcpackagelocale isset] + mcpackagelocale set bar + lappend res [mcpackagelocale isset] + } -result {0 1} + + test msgcat-12.8 {mcpackagelocale unset} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mcpackagelocale set bar + set res [mcpackagelocale isset] + mcpackagelocale unset + lappend res [mcpackagelocale isset] + } -result {1 0} + + test msgcat-12.9 {mcpackagelocale present} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale "" + mcloadedlocales clear + mclocale foo + set res [mcpackagelocale present foo] + lappend res [mcpackagelocale present bar] + mcpackagelocale set bar + lappend res [mcpackagelocale present foo]\ + [mcpackagelocale present bar] + } -result {1 0 1 1} + + test msgcat-12.10 {mcpackagelocale clear} -setup { + variable locale [mclocale] + } -cleanup { + mclocale $locale + mcforgetpackage + } -body { + mclocale "" + mcloadedlocales clear + mclocale foo + mcpackagelocale set bar + mcpackagelocale clear + list [mcpackagelocale present foo] [mcpackagelocale present bar] + } -result {0 1} + + # Tests msgcat-13.*: [mcpackageconfig subcmds] + + test msgcat-13.1 {mcpackageconfig no subcommand} -body { + mcpackageconfig + } -returnCodes 1\ + -result {wrong # args: should be "mcpackageconfig subcommand option ?value?"} + + test msgcat-13.2 {mclpackageconfig wrong subcommand} -body { + mcpackageconfig junk mcfolder + } -returnCodes 1\ + -result {unknown subcommand "junk": must be get, isset, set, or unset} + + test msgcat-13.3 {mclpackageconfig wrong option} -body { + mcpackageconfig get junk + } -returnCodes 1\ + -result {bad option "junk": must be mcfolder, loadcmd, changecmd, or unknowncmd} + + test msgcat-13.4 {mcpackageconfig get} -setup { + mcforgetpackage + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set loadcmd "" + mcpackageconfig get loadcmd + } -result {} + + test msgcat-13.5 {mcpackageconfig (is/un)set} -setup { + mcforgetpackage + } -cleanup { + mcforgetpackage + } -body { + set res [mcpackageconfig isset loadcmd] + lappend res [mcpackageconfig set loadcmd ""] + lappend res [mcpackageconfig isset loadcmd] + mcpackageconfig unset loadcmd + lappend res [mcpackageconfig isset loadcmd] + } -result {0 0 1 0} + + # option mcfolder is already tested with 5.11 + + # Tests msgcat-14.*: callbacks: loadcmd, changecmd, unknowncmd + + # This routine is used as bgerror and by direct callback invocation + proc callbackproc args { + variable resultvariable + set resultvariable $args + } + proc callbackfailproc args { + return -code error fail + } + set bgerrorsaved [interp bgerror {}] + interp bgerror {} [namespace code callbackproc] + + test msgcat-14.1 {invokation loadcmd} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + mcloadedlocales clear + set resultvariable "" + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set loadcmd [namespace code callbackproc] + mclocale foo_bar + lsort $resultvariable + } -result {foo foo_bar} + + test msgcat-14.2 {invokation failed in loadcmd} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + mcloadedlocales clear + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set loadcmd [namespace code callbackfailproc] + mclocale foo_bar + # let the bgerror run + after 100 set [namespace current]::resultvariable timeout + vwait [namespace current]::resultvariable + lassign $resultvariable err errdict + list $err [dict get $errdict -code] + } -result {fail 1} + + test msgcat-14.3 {invokation changecmd} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + set resultvariable "" + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set changecmd [namespace code callbackproc] + mclocale foo_bar + set resultvariable + } -result {foo_bar foo {}} + + test msgcat-14.4 {invokation unknowncmd} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + mcloadedlocales clear + set resultvariable "" + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set unknowncmd [namespace code callbackproc] + mclocale foo_bar + mc k1 p1 + set resultvariable + } -result {foo_bar k1 p1} + + test msgcat-14.5 {disable global unknowncmd} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + mcloadedlocales clear + set resultvariable "" + rename ::msgcat::mcunknown SavedMcunknown + proc ::msgcat::mcunknown {dom s} { + return unknown:$dom:$s + } + } -cleanup { + mcforgetpackage + rename ::msgcat::mcunknown {} + rename SavedMcunknown ::msgcat::mcunknown + } -body { + mcpackageconfig set unknowncmd "" + mclocale foo_bar + mc k1%s p1 + } -result {k1p1} + + test msgcat-14.6 {unknowncmd failing} -setup { + mcforgetpackage + mclocale $locale + mclocale "" + mcloadedlocales clear + set resultvariable "" + } -cleanup { + mcforgetpackage + } -body { + mcpackageconfig set unknowncmd [namespace code callbackfailproc] + mclocale foo_bar + mc k1 + } -returnCodes 1\ + -result {fail} + + interp bgerror {} $bgerrorsaved + cleanupTests } namespace delete ::msgcat::test diff --git a/tests/nre.test b/tests/nre.test index b5eb032..e512eac 100644 --- a/tests/nre.test +++ b/tests/nre.test @@ -151,6 +151,27 @@ test nre-4.1 {ensembles are not recursive} -setup { testnrelevels } -result {{0 2 1 1} 0} +test nre-4.2 {(compiled) ensembles do not break tailcall} -setup { + # Fix Bug d87cb18205 + proc b {} { + tailcall append result first + } + set map [namespace ensemble configure ::dict -map] + dict set map a b + namespace ensemble configure ::dict -map $map + proc demo {} { + dict a + append result second + } +} -body { + demo +} -cleanup { + rename demo {} + namespace ensemble configure ::dict -map [dict remove $map a] + unset map + rename b {} +} -result firstsecond + test nre-5.1 {[namespace eval] is not recursive} -setup { namespace eval ::foo { setabs diff --git a/tests/oo.test b/tests/oo.test index 5fa760b..c83e015 100644 --- a/tests/oo.test +++ b/tests/oo.test @@ -416,6 +416,31 @@ test oo-2.8 {construction, method calls and ensembles - Bug 3514761} -setup { } -returnCodes error -cleanup { namespace delete k } -result {wrong # args: should be "k next j"} +test oo-2.9 {construction failures and self creation} -setup { + set ::result {} + oo::class create Root +} -body { + oo::class create A { + superclass Root + constructor {} { + lappend ::result "in A" + error "failure in A" + } + destructor {lappend ::result [self]} + } + oo::class create B { + superclass Root + constructor {} { + lappend ::result "in B [self]" + error "failure in B" + } + destructor {lappend ::result [self]} + } + lappend ::result [catch {A create a} msg] $msg + lappend ::result [catch {B create b} msg] $msg +} -cleanup { + Root destroy +} -result {{in A} ::a 1 {failure in A} {in B ::b} ::b 1 {failure in B}} test oo-3.1 {basic test of OO functionality: destructor} -setup { # This is a bit complex because it needs to run in a sub-interp as we're @@ -1544,6 +1569,34 @@ test oo-12.7 {OO: filters} -setup { } -cleanup { Aclass destroy } -result {foo {{::Aclass outerfoo} {::Aclass InnerFoo}}} +test oo-12.8 {OO: filters and destructors} -setup { + oo::class create Aclass + Aclass create Aobject + set ::log {} +} -body { + oo::define Aclass { + constructor {} { + lappend ::log "in constructor" + } + destructor { + lappend ::log "in destructor" + } + method bar {} { + lappend ::log "in method" + } + method Boo args { + lappend ::log [self target] + next {*}$args + } + filter Boo + } + set obj [Aclass new] + $obj bar + $obj destroy + return $::log +} -cleanup { + Aclass destroy +} -result {{in constructor} {::Aclass bar} {in method} {::oo::object destroy} {in destructor}} test oo-13.1 {OO: changing an object's class} { oo::class create Aclass @@ -2024,6 +2077,30 @@ test oo-16.13 {OO: object introspection} -setup { oo::objdefine foo method Bar {} {return "ok in foo"} [info object namespace foo]::my Bar } -result "ok in foo" +test oo-16.14 {OO: object introspection: TIP #436} -setup { + oo::class create meta { superclass oo::class } + [meta create instance1] create instance2 +} -body { + list class [list [info object isa class NOTANOBJECT] \ + [info object isa class list]] \ + meta [list [info object isa metaclass NOTANOBJECT] \ + [info object isa metaclass list] \ + [info object isa metaclass oo::object]] \ + type [list [info object isa typeof oo::object NOTANOBJECT] \ + [info object isa typeof NOTANOBJECT oo::object] \ + [info object isa typeof list NOTANOBJECT] \ + [info object isa typeof NOTANOBJECT list] \ + [info object isa typeof oo::object list] \ + [info object isa typeof list oo::object]] \ + mix [list [info object isa mixin oo::object NOTANOBJECT] \ + [info object isa mixin NOTANOBJECT oo::object] \ + [info object isa mixin list NOTANOBJECT] \ + [info object isa mixin NOTANOBJECT list] \ + [info object isa mixin oo::object list] \ + [info object isa mixin list oo::object]] +} -cleanup { + meta destroy +} -result {class {0 0} meta {0 0 0} type {0 0 0 0 0 0} mix {0 0 0 0 0 0}} test oo-17.1 {OO: class introspection} -body { info class diff --git a/tests/ooNext2.test b/tests/ooNext2.test index 5ecd209..6a48d28 100644 --- a/tests/ooNext2.test +++ b/tests/ooNext2.test @@ -866,6 +866,196 @@ test oo-call-3.4 {current call introspection: in destructors} -setup { } -cleanup { root destroy } -result {{{{method <destructor> ::B method} {method <destructor> ::A method}} 0} {{{method <destructor> ::B method} {method <destructor> ::A method}} 1}} + +# Contributed tests from aspect, related to [0f42ff7871] +# +# dkf's "Principles Leading to a Fix" +# +# A method ought to work "the same" whether or not it has been overridden by +# a subclass. A tailcalled command ought to have as parent stack the same +# thing you'd get with uplevel 1. A subclass will often expect the +# superclass's result to be the result that would be returned if the +# subclass was not there. + +# Common setup: +# any invocation of bar should emit "abc\nhi\n" then return to its +# caller +set testopts { + -setup { + oo::class create Master + oo::class create Foo { + superclass Master + method bar {} { + puts abc + tailcall puts hi + puts xyz + } + } + oo::class create Foo2 { + superclass Master + } + } + -cleanup { + Master destroy + } +} + +# these succeed, showing that without [next] the bug doesn't fire +test next-tailcall-simple-1 "trivial case with one method" {*}$testopts -body { + [Foo create foo] bar +} -output [join {abc hi} \n]\n +test next-tailcall-simple-2 "my bar" {*}$testopts -body { + oo::define Foo method baz {} { + puts a + my bar + puts b + } + [Foo create foo] baz +} -output [join {a abc hi b} \n]\n +test next-tailcall-simple-3 "\[self\] bar" {*}$testopts -body { + oo::define Foo method baz {} { + puts a + [self] bar + puts b + } + [Foo create foo] baz +} -output [join {a abc hi b} \n]\n +test next-tailcall-simple-4 "foo bar" {*}$testopts -body { + oo::define Foo method baz {} { + puts a + foo bar + puts b + } + [Foo create foo] baz +} -output [join {a abc hi b} \n]\n + +# everything from here on uses [next], and fails on 8.6.4 with compilation +test next-tailcall-superclass-1 "next superclass" {*}$testopts -body { + oo::define Foo2 { + superclass Foo + method bar {} { + puts a + next + puts b + } + } + [Foo2 create foo] bar +} -output [join {a abc hi b} \n]\n +test next-tailcall-superclass-2 "nextto superclass" {*}$testopts -body { + oo::define Foo2 { + superclass Foo + method bar {} { + puts a + nextto Foo + puts b + } + } + [Foo2 create foo] bar +} -output [join {a abc hi b} \n]\n + +test next-tailcall-mixin-1 "class mixin" {*}$testopts -body { + oo::define Foo2 { + method Bar {} { + puts a + next + puts b + } + filter Bar + } + oo::define Foo mixin Foo2 + Foo create foo + foo bar +} -output [join {a abc hi b} \n]\n + +test next-tailcall-objmixin-1 "object mixin" {*}$testopts -body { + oo::define Foo2 { + method Bar {} { + puts a + next + puts b + } + filter Bar + } + Foo create foo + oo::objdefine foo mixin Foo2 + foo bar +} -output [join {a abc hi b} \n]\n + +test next-tailcall-filter-1 "filter method" {*}$testopts -body { + oo::define Foo method Filter {} { + puts a + next + puts b + } + oo::define Foo filter Filter + [Foo new] bar +} -output [join {a abc hi b} \n]\n + +test next-tailcall-forward-1 "forward method" {*}$testopts -body { + proc foobar {} { + puts "abc" + tailcall puts "hi" + puts "xyz" + } + oo::define Foo forward foobar foobar + oo::define Foo2 { + superclass Foo + method foobar {} { + puts a + next + puts b + } + } + [Foo2 new] foobar +} -output [join {a abc hi b} \n]\n + +test next-tailcall-constructor-1 "next in constructor" -body { + oo::class create Foo { + constructor {} { + puts abc + tailcall puts hi + puts xyz + } + } + oo::class create Foo2 { + superclass Foo + constructor {} { + puts a + next + puts b + } + } + list [Foo new] [Foo2 new] + return "" +} -cleanup { + Foo destroy +} -output [join {abc hi a abc hi b} \n]\n + +test next-tailcall-destructor-1 "next in destructor" -body { + oo::class create Foo { + destructor { + puts abc + tailcall puts hi + puts xyz + } + } + oo::class create Foo2 { + superclass Foo + destructor { + puts a + next + puts b + } + } + Foo create foo + Foo2 create foo2 + foo destroy + foo2 destroy +} -output [join {abc hi a abc hi b} \n]\n -cleanup { + Foo destroy +} + +unset testopts cleanupTests return diff --git a/tests/platform.test b/tests/platform.test index 6596975..cc00d49 100644 --- a/tests/platform.test +++ b/tests/platform.test @@ -1,4 +1,4 @@ -# The file tests the tcl_platform variable +# The file tests the tcl_platform variable and platform package. # # This file contains a collection of tests for one or more of the Tcl # built-in commands. Sourcing this file into Tcl runs the tests and @@ -57,6 +57,17 @@ test platform-3.1 {CPU ID on Windows/UNIX} \ -match regexp \ -result {^(?:AuthenticAMD|CentaurHauls|CyrixInstead|GenuineIntel)$} +# The platform package makes very few promises, but does promise that the +# format of string it produces consists of two non-empty words separated by a +# hyphen. +package require platform +test platform-4.1 {format of platform::identify result} -match regexp -body { + platform::identify +} -result {^([^-]+-)+[^-]+$} +test platform-4.2 {format of platform::generic result} -match regexp -body { + platform::generic +} -result {^([^-]+-)+[^-]+$} + # cleanup cleanupTests diff --git a/tests/reg.test b/tests/reg.test index e6ce42c..d040632 100644 --- a/tests/reg.test +++ b/tests/reg.test @@ -669,7 +669,13 @@ expectError 14.19 - {a(b)c\2} ESUBREG expectMatch 14.20 bR {a\(b*\)c\1} abbcbb abbcbb bb expectMatch 14.21 RP {^([bc])\1*$} bbb bbb b expectMatch 14.22 RP {^([bc])\1*$} ccc ccc c -knownBug expectNomatch 14.23 R {^([bc])\1*$} bcb +expectNomatch 14.23 RP {^([bc])\1*$} bcb +expectMatch 14.24 LRP {^(\w+)( \1)+$} {abc abc abc} {abc abc abc} abc { abc} +expectNomatch 14.25 LRP {^(\w+)( \1)+$} {abc abd abc} +expectNomatch 14.26 LRP {^(\w+)( \1)+$} {abc abc abd} +expectMatch 14.27 RP {^(.+)( \1)+$} {abc abc abc} {abc abc abc} abc { abc} +expectNomatch 14.28 RP {^(.+)( \1)+$} {abc abd abc} +expectNomatch 14.29 RP {^(.+)( \1)+$} {abc abc abd} doing 15 "octal escapes vs back references" @@ -796,6 +802,7 @@ expectMatch 21.31 LP "\\y(\\w+)\\y" "-- abc-" "abc" "abc" expectMatch 21.32 - a((b|c)d+)+ abacdbd acdbd bd b expectMatch 21.33 N (.*).* abc abc abc expectMatch 21.34 N (a*)* bc "" "" +expectMatch 21.35 M { TO (([a-z0-9._]+|"([^"]+|"")+")+)} {asd TO foo} { TO foo} foo o {} doing 22 "multicharacter collating elements" @@ -848,6 +855,7 @@ expectMatch 24.9 - 3z* 123zzzz456 3zzzz expectMatch 24.10 PT 3z*? 123zzzz456 3 expectMatch 24.11 - z*4 123zzzz456 zzzz4 expectMatch 24.12 PT z*?4 123zzzz456 zzzz4 +expectMatch 24.13 PT {^([^/]+?)(?:/([^/]+?))(?:/([^/]+?))?$} {foo/bar/baz} {foo/bar/baz} {foo} {bar} {baz} doing 25 "mixed quantifiers" @@ -1080,7 +1088,8 @@ test reg-33.13 {Bug 1810264 - infinite loop} { test reg-33.14 {Bug 1810264 - super-expensive expression} nonPortable { regexp {(x{200}){200}$y} {x} } 0 -test reg-33.15 {Bug 3603557 - an "in the wild" RE} { + +test reg-33.15.1 {Bug 3603557 - an "in the wild" RE} { lindex [regexp -expanded -about { ^TETRA_MODE_CMD # Message Type ([[:blank:]]+) # Pad @@ -1155,10 +1164,62 @@ test reg-33.15 {Bug 3603557 - an "in the wild" RE} { (.*) # ConditionalFields }] 0 } 68 -test reg-33.16 {Bug [8d2c0da36d]- another "in the wild" RE} { +test reg-33.16.1 {Bug [8d2c0da36d]- another "in the wild" RE} { lindex [regexp -about "^MRK:client1: =1339 14HKelly Talisman 10011000 (\[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]*) \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 8 0 8 0 0 0 77 77 1 1 2 0 11 { 1 3 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 13HC6 My Creator 2 3 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 31HC7 Slightly offensive name, huh 3 8 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 23HE-mail:kelly@hotbox.com 4 9 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 17Hcompface must die 5 10 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 0 3HAir 6 12 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 14HPGP public key 7 13 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 16Hkelly@hotbox.com 8 30 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 0 12H2 text/plain 9 30 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 0 13H2 x-kom/basic 10 33 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 1H0 11 14 8 \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* \[0-9\]* 00000000 1 1H3 }\r?"] 0 } 1 - + +test reg-33.15 {constraint fixes} { + regexp {(^)+^} x +} 1 +test reg-33.16 {constraint fixes} { + regexp {($^)+} x +} 0 +test reg-33.17 {constraint fixes} { + regexp {(^$)*} x +} 1 +test reg-33.18 {constraint fixes} { + regexp {(^(?!aa))+} {aa bb cc} +} 0 +test reg-33.19 {constraint fixes} { + regexp {(^(?!aa)(?!bb)(?!cc))+} {aa x} +} 0 +test reg-33.20 {constraint fixes} { + regexp {(^(?!aa)(?!bb)(?!cc))+} {bb x} +} 0 +test reg-33.21 {constraint fixes} { + regexp {(^(?!aa)(?!bb)(?!cc))+} {cc x} +} 0 +test reg-33.22 {constraint fixes} { + regexp {(^(?!aa)(?!bb)(?!cc))+} {dd x} +} 1 + +test reg-33.23 {} { + regexp {abcd(\m)+xyz} x +} 0 +test reg-33.24 {} { + regexp {abcd(\m)+xyz} a +} 0 +test reg-33.25 {} { + regexp {^abcd*(((((^(a c(e?d)a+|)+|)+|)+|)+|a)+|)} x +} 0 +test reg-33.26 {} { + regexp {a^(^)bcd*xy(((((($a+|)+|)+|)+$|)+|)+|)^$} x +} 0 +test reg-33.27 {} { + regexp {xyz(\Y\Y)+} x +} 0 +test reg-33.28 {} { + regexp {x|(?:\M)+} x +} 1 +test reg-33.29 {} { + # This is near the limits of the RE engine + regexp [string repeat x*y*z* 480] x +} 1 + +test reg-33.30 {Bug 1080042} { + regexp {(\Y)+} foo +} 1 + # cleanup ::tcltest::cleanupTests return diff --git a/tests/regexp.test b/tests/regexp.test index a83c99b..9fff262 100644 --- a/tests/regexp.test +++ b/tests/regexp.test @@ -864,7 +864,7 @@ test regexp-22.4 {Bug 3606139} -setup { [a 668]([a 55])[a 668]([a 55])[a 668]([a 55])[a 511]] {}] a } -cleanup { rename a {} -} -returnCodes 1 -result {couldn't compile regular expression pattern: nfa has too many states} +} -returnCodes 1 -match glob -result {couldn't compile regular expression pattern: *} test regexp-22.5 {Bug 3610026} -setup { set e {} set cp 99 diff --git a/tests/registry.test b/tests/registry.test index 77588e3..0f78212 100644 --- a/tests/registry.test +++ b/tests/registry.test @@ -19,7 +19,7 @@ testConstraint reg 0 if {[testConstraint win]} { if {![catch { ::tcltest::loadTestedCommands - set ::regver [package require registry 1.3.0] + set ::regver [package require registry 1.3.1] }]} { testConstraint reg 1 } @@ -33,7 +33,7 @@ testConstraint english [expr { test registry-1.0 {check if we are testing the right dll} {win reg} { set ::regver -} {1.3.0} +} {1.3.1} test registry-1.1 {argument parsing for registry command} {win reg} { list [catch {registry} msg] $msg } {1 {wrong # args: should be "registry ?-32bit|-64bit? option ?arg ...?"}} diff --git a/tests/set-old.test b/tests/set-old.test index 4c25ec5..94b6901 100644 --- a/tests/set-old.test +++ b/tests/set-old.test @@ -305,6 +305,11 @@ test set-old-7.18 {unset command, -nocomplain (no abbreviation)} { catch {unset -nocomp} list [info exists -nocomp] [catch {unset -nocomp}] } {0 1} +test set-old-7.19 {unset command, both switches} { + set -- val + list [info exists --] [catch {unset -nocomplain --}] [info exists --]\ + [catch {unset -nocomplain -- --}] [info exists --] +} {1 0 1 0 0} # Array command. diff --git a/tests/socket.test b/tests/socket.test index 4f90e51..8473602 100644 --- a/tests/socket.test +++ b/tests/socket.test @@ -1794,7 +1794,7 @@ test socket_$af-13.1 {Testing use of shared socket between two threads} -body { close $s thread::release $serverthread append result " " [llength [thread::names]] -} -result {hello 1} -constraints [list socket supported_$af thread] +} -result {hello 1} -constraints [list socket supported_$af thread] # ---------------------------------------------------------------------- @@ -2249,7 +2249,7 @@ test socket-14.11.0 {pending [socket -async] and nonblocking [puts], no listener unset x } -result {socket is not connected} -returnCodes 1 test socket-14.11.1 {pending [socket -async] and nonblocking [puts], no listener, flush} \ - -constraints {socket nonportable} \ + -constraints {socket nonPortable} \ -body { set sock [socket -async localhost [randport]] fconfigure $sock -blocking 0 @@ -2281,10 +2281,10 @@ test socket-14.13 {testing writable event when quick failure} \ -constraints {socket win supported_inet} \ -body { # Test for bug 336441ed59 where a quick background fail was ignored - + # Test only for windows as socket -async 255.255.255.255 fails # directly on unix - + # The following connect should fail very quickly set a1 [after 2000 {set x timeout}] set s [socket -async 255.255.255.255 43434] @@ -2299,7 +2299,7 @@ test socket-14.13 {testing writable event when quick failure} \ test socket-14.14 {testing fileevent readable on failed async socket connect} \ -constraints {socket} -body { # Test for bug 581937ab1e - + set a1 [after 5000 {set x timeout}] # This connect should fail set s [socket -async localhost [randport]] diff --git a/tests/tailcall.test b/tests/tailcall.test index 2d04f82..26f3cbf 100644 --- a/tests/tailcall.test +++ b/tests/tailcall.test @@ -147,6 +147,36 @@ test tailcall-0.5 {tailcall is constant space} -constraints testnrelevels -setup rename b {} } -result {0 0 0 0 0 0} +test tailcall-0.5.1 {tailcall is constant space} -constraints testnrelevels -setup { + # + # This test is related to [bug d87cb182053fd79b3]: the fix to that bug was + # to remove a call to TclSkipTailcall, which caused a violation of the + # constant-space property of tailcall in that particular + # configuration. This test was added to detect that, and insure that the + # problem is fixed. + # + + proc b i { + if {$i == 1} { + depthDiff + } + if {[incr i] > 10} { + return [depthDiff] + } + tailcall dict b $i + } + set map0 [namespace ensemble configure dict -map] + set map $map0 + dict set map b b + namespace ensemble configure dict -map $map +} -body { + dict b 0 +} -cleanup { + rename b {} + namespace ensemble configure dict -map $map0 + unset map map0 +} -result {0 0 0 0 0 0} + test tailcall-0.6 {tailcall is constant space} -constraints {testnrelevels knownBug} -setup { # # This test fails because ns-unknown is not NR-enabled diff --git a/tests/thread.test b/tests/thread.test index f32ef61..cc4c871 100644 --- a/tests/thread.test +++ b/tests/thread.test @@ -564,7 +564,7 @@ test thread-7.14 {cancel: vwait} -constraints {thread drainEventQueue} -setup { unset -nocomplain ::threadSawError ::threadError ::threadId ::threadIdStarted } -body { set serverthread [thread::create -joinable \ - [string map [list %ID [thread::id]] { + [string map [list %ID% [thread::id]] { if {![info exists foo]} then { # signal the primary thread that we are ready # to be canceled now (we are running). @@ -616,7 +616,7 @@ test thread-7.16 {cancel: expr} -constraints {thread drainEventQueue} -setup { unset -nocomplain ::threadSawError ::threadError ::threadId ::threadIdStarted } -body { set serverthread [thread::create -joinable \ - [string map [list %ID [thread::id]] { + [string map [list %ID% [thread::id]] { set i [interp create] $i eval "package require -exact Thread [package present Thread]" $i eval { @@ -1372,7 +1372,7 @@ test thread-7.37 {cancel: send async thread cancel nested catch inside pure insi unset -nocomplain ::threadSawError ::threadError ::threadId ::threadIdStarted } -body { set serverthread [thread::create -joinable \ - [string map [list %ID [thread::id]] { + [string map [list %ID% [thread::id]] { proc foobar {} { set catch catch set while while @@ -1412,6 +1412,32 @@ test thread-7.37 {cancel: send async thread cancel nested catch inside pure insi unset -nocomplain ::threadSawError ::threadError ::threadId ::threadIdStarted } -result {{} 1 1 {eval unwound}} +test thread-8.1 {threaded fork stress} -constraints {thread} -setup { + unset -nocomplain ::threadCount ::execCount ::threads ::thread + set ::threadCount 10 + set ::execCount 10 +} -body { + set ::threads [list] + for {set i 0} {$i < $::threadCount} {incr i} { + lappend ::threads [thread::create -joinable [string map \ + [list %execCount% $::execCount] { + proc execLs {} { + if {$::tcl_platform(platform) eq "windows"} then { + return [exec $::env(COMSPEC) /c DIR] + } else { + return [exec /bin/ls] + } + } + set j {%execCount%}; while {[incr j -1]} {execLs} + }]] + } + foreach ::thread $::threads { + thread::join $::thread + } +} -cleanup { + unset -nocomplain ::threadCount ::execCount ::threads ::thread +} -result {} + # cleanup ::tcltest::cleanupTests return diff --git a/tests/unixFCmd.test b/tests/unixFCmd.test index 2d227fe..183c145 100644 --- a/tests/unixFCmd.test +++ b/tests/unixFCmd.test @@ -385,7 +385,7 @@ file delete -force -- foo.test test unixFCmd-18.1 {Unix pwd} -constraints {unix notRoot nonPortable} -setup { set cd [pwd] } -body { - # This test is nonportable because SunOS generates a weird error + # This test is nonPortable because SunOS generates a weird error # message when the current directory isn't readable. set nd $cd/tstdir file mkdir $nd diff --git a/tests/var.test b/tests/var.test index 7ff394e..0531746 100644 --- a/tests/var.test +++ b/tests/var.test @@ -25,6 +25,7 @@ catch [list package require -exact Tcltest [info patchlevel]] testConstraint testupvar [llength [info commands testupvar]] testConstraint testgetvarfullname [llength [info commands testgetvarfullname]] testConstraint testsetnoerr [llength [info commands testsetnoerr]] +testConstraint memory [llength [info commands memory]] catch {rename p ""} catch {namespace delete test_ns_var} @@ -894,6 +895,33 @@ test var-21.0 {PushVarNameWord OBOE in compiled unset} -setup { rename linenumber {} } -result 1 +test var-22.0 {leak in array element unset: Bug a3309d01db} -setup { + proc getbytes {} { + lindex [split [memory info] \n] 3 3 + } + proc doit k { + variable A + set A($k) {} + foreach n [array names A] { + if {$n <= $k-1} { + unset A($n) + } + } + } +} -constraints memory -body { + set end [getbytes] + for {set i 0} {$i < 5} {incr i} { + doit $i + set tmp $end + set end [getbytes] + } + set leakedBytes [expr {$end - $tmp}] +} -cleanup { + array unset A + rename getbytes {} + rename doit {} +} -result 0 + catch {namespace delete ns} catch {unset arr} diff --git a/tools/Makefile.in b/tools/Makefile.in index 6034fe9..5e9f88e 100644 --- a/tools/Makefile.in +++ b/tools/Makefile.in @@ -32,9 +32,9 @@ ITCL_DOCS = \ # $(ITCL_SOURCE)/iwidgets3.0.0/doc/*.[13n] -COREDOCS = $(TCL_DOCS) $(TK_DOCS) +COREDOCS = $(TCL_DOCS) $(TK_DOCS) #PRODOCS = $(COREDOCS) $(PRO_DOCS) $(ITCL_DOCS) -PRODOCS = $(COREDOCS) $(PRO_DOCS) +PRODOCS = $(COREDOCS) $(PRO_DOCS) TCLSH = $(TCL_BIN_DIR)/tclsh CC = @CC@ diff --git a/tools/findBadExternals.tcl b/tools/findBadExternals.tcl index 7592f17..2228357 100755 --- a/tools/findBadExternals.tcl +++ b/tools/findBadExternals.tcl @@ -1,5 +1,5 @@ # findBadExternals.tcl -- -# +# # This script scans the Tcl load library for exported symbols # that do not begin with 'Tcl' or 'tcl'. It reports them on the # standard output. It is used to make sure that the library does @@ -29,7 +29,7 @@ proc main {argc argv} { macosx { set status [catch { exec nm --extern-only --defined-only [lindex $argv 0] - } result] + } result] } windows { set status [catch { diff --git a/tools/genStubs.tcl b/tools/genStubs.tcl index 7a75dc6..beede9e 100644 --- a/tools/genStubs.tcl +++ b/tools/genStubs.tcl @@ -582,6 +582,8 @@ proc genStubs::makeSlot {name decl index} { } if {[string range $rtype end-8 end] eq "__stdcall"} { append text [string trim [string range $rtype 0 end-9]] " (__stdcall *" $lfname ") " + } elseif {[string range $rtype 0 11] eq "TCL_NORETURN"} { + append text "TCL_NORETURN1 " [string trim [string range $rtype 12 end]] " (*" $lfname ") " } else { append text $rtype " (*" $lfname ") " } diff --git a/tools/loadICU.tcl b/tools/loadICU.tcl index 5b09e2c..31f1e54 100755 --- a/tools/loadICU.tcl +++ b/tools/loadICU.tcl @@ -432,7 +432,7 @@ proc handleLocaleFile { localeName fileName msgFileName } { if { ![info exists format($localeName,TIME_FORMAT)] } { for { set i 3 } { $i >= 0 } { incr i -1 } { - if { [regexp H [lindex $items(DateTimePatterns) $i]] + if { [regexp H [lindex $items(DateTimePatterns) $i]] && [regexp s [lindex $items(DateTimePatterns) $i]] } { break } @@ -464,7 +464,7 @@ proc handleLocaleFile { localeName fileName msgFileName } { if { ![info exists format($localeName,TIME_FORMAT_12)] } { for { set i 3 } { $i >= 0 } { incr i -1 } { - if { [regexp h [lindex $items(DateTimePatterns) $i]] + if { [regexp h [lindex $items(DateTimePatterns) $i]] && [regexp s [lindex $items(DateTimePatterns) $i]] } { break } @@ -489,7 +489,7 @@ proc handleLocaleFile { localeName fileName msgFileName } { # Date and time... Prefer 24-hour format to 12-hour format. - if { ![info exists format($localeName,DATE_TIME_FORMAT)] + if { ![info exists format($localeName,DATE_TIME_FORMAT)] && [info exists format($localeName,DATE_FORMAT)] && [info exists format($localeName,TIME_FORMAT)]} { set format($localeName,DATE_TIME_FORMAT) \ @@ -497,7 +497,7 @@ proc handleLocaleFile { localeName fileName msgFileName } { append format($localeName,DATE_TIME_FORMAT) \ " " $format($localeName,TIME_FORMAT) " %z" } - if { ![info exists format($localeName,DATE_TIME_FORMAT)] + if { ![info exists format($localeName,DATE_TIME_FORMAT)] && [info exists format($localeName,DATE_FORMAT)] && [info exists format($localeName,TIME_FORMAT_12)]} { set format($localeName,DATE_TIME_FORMAT) \ @@ -517,7 +517,7 @@ proc handleLocaleFile { localeName fileName msgFileName } { # Write the string sets to the file. - foreach key { + foreach key { LOCALE_NUMERALS LOCALE_DATE_FORMAT LOCALE_TIME_FORMAT LOCALE_DATE_TIME_FORMAT LOCALE_ERAS LOCALE_YEAR_FORMAT } { @@ -588,7 +588,7 @@ proc backslashify { string } { set retval {} foreach char [split $string {}] { scan $char %c ccode - if { $ccode >= 0x0020 && $ccode < 0x007f && $char ne "\"" + if { $ccode >= 0x0020 && $ccode < 0x007f && $char ne "\"" && $char ne "\{" && $char ne "\}" && $char ne "\[" && $char ne "\]" && $char ne "\\" && $char ne "\$" } { append retval $char diff --git a/tools/makeTestCases.tcl b/tools/makeTestCases.tcl index d96a221..6cc033b 100755 --- a/tools/makeTestCases.tcl +++ b/tools/makeTestCases.tcl @@ -40,7 +40,7 @@ namespace eval ::tcl::clock { l li lii liii liv lv lvi lvii lviii lix lx lxi lxii lxiii lxiv lxv lxvi lxvii lxviii lxix lxx lxxi lxxii lxxiii lxxiv lxxv lxxvi lxxvii lxxviii lxxix - lxxx lxxxi lxxxii lxxxiii lxxxiv lxxxv lxxxvi lxxxvii lxxxviii + lxxx lxxxi lxxxii lxxxiii lxxxiv lxxxv lxxxvi lxxxvii lxxxviii lxxxix xc xci xcii xciii xciv xcv xcvi xcvii xcviii xcix c @@ -62,7 +62,7 @@ namespace eval ::tcl::clock { # # Parameters: # startOfYearArray - Name of an array in caller's scope that will -# be initialized as +# be initialized as # Results: # None # @@ -106,7 +106,7 @@ proc listYears { startOfYearArray } { set s $s2 incr y } - + # List years before 1970 set y 1970 @@ -138,7 +138,7 @@ proc listYears { startOfYearArray } { #---------------------------------------------------------------------- # -# processFile - +# processFile - # # Processes the 'clock.test' file, updating the test cases in it. # @@ -153,7 +153,7 @@ proc listYears { startOfYearArray } { proc processFile {d} { # Open two files - + set f1 [open [file join $d tests/clock.test] r] set f2 [open [file join $d tests/clock.new] w] @@ -164,7 +164,7 @@ proc processFile {d} { switch -exact -- $state { {} { puts $f2 $line - if { [regexp "^\# BEGIN (.*)" $line -> cases] + if { [regexp "^\# BEGIN (.*)" $line -> cases] && [string compare {} [info commands $cases]] } { set state inCaseSet $cases $f2 @@ -213,7 +213,7 @@ proc testcases2 { f2 } { listYears startOfYear # Define the roman numerals - + set roman { ? i ii iii iv v vi vii viii ix x xi xii xiii xiv xv xvi xvii xviii xix @@ -235,20 +235,20 @@ proc testcases2 { f2 } { } # Names of the months - + set short {{} Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec} set long { {} January February March April May June July August September October November December } - + # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test formatting of Gregorian year, month, day, all formats" puts $f2 "\# Formats tested: %b %B %c %Ec %C %EC %d %Od %e %Oe %h %j %J %m %Om %N %x %Ex %y %Oy %Y %EY" puts $f2 "" - + # Generate the test cases for the first and last day of every month # from 1896 to 2045 @@ -262,7 +262,7 @@ proc testcases2 { f2 } { if { $m == 2 && ( $y%4 == 0 && $y%100 != 0 || $y%400 == 0 ) } { incr hath } - + set b [lindex $short $m] set B [lindex $long $m] set C [format %02d [expr { $y / 100 }]] @@ -271,9 +271,9 @@ proc testcases2 { f2 } { set mm [format %02d $m] set N [format %2d $m] set yy [format %02d [expr { $y % 100 }]] - + set J [expr { ( $s / 86400 ) + 2440588 }] - + set dt $y-$mm-01 set result "" append result $b " " $B " " \ @@ -296,17 +296,17 @@ proc testcases2 { f2 } { puts $f2 "\t-format {%b %B %c %Ec %C %EC %d %Od %e %Oe %h %j %J %m %Om %N %x %Ex %y %Oy %Y} \\" puts $f2 "\t-gmt true -locale en_US_roman" puts $f2 "} {$result}" - + set hm1 [expr { $hath - 1 }] incr s [expr { 86400 * ( $hath - 1 ) }] incr yd $hm1 - + set dd [format %02d $hath] set ee [format %2d $hath] set j [format %03d $yd] - + set J [expr { ( $s / 86400 ) + 2440588 }] - + set dt $y-$mm-$dd set result "" append result $b " " $B " " \ @@ -332,7 +332,7 @@ proc testcases2 { f2 } { puts $f2 "\t-format {%b %B %c %Ec %C %EC %d %Od %e %Oe %h %j %J %m %Om %N %x %Ex %y %Oy %Y} \\" puts $f2 "\t-gmt true -locale en_US_roman" puts $f2 "} {$result}" - + incr s 86400 incr yd } @@ -451,7 +451,7 @@ proc testcases3 { f2 } { testISO $f2 $ym1 52 1 [expr { $secs - 5*86400 }] testISO $f2 $ym1 52 6 $secs testISO $f2 $ym1 52 7 [expr { $secs + 86400 }] - } + } testISO $f2 $y 1 1 [expr { $secs + 2*86400 }] testISO $f2 $y 1 6 [expr { $secs + 7*86400 }] testISO $f2 $y 1 7 [expr { $secs + 8*86400 }] @@ -466,10 +466,10 @@ proc testcases3 { f2 } { proc testISO { f2 G V u secs } { upvar 1 case case - + set longdays {Sunday Monday Tuesday Wednesday Thursday Friday Saturday Sunday} set shortdays {Sun Mon Tue Wed Thu Fri Sat Sun} - + puts $f2 "test clock-3.[incr case] {ISO week-based calendar [format %04d-W%02d-%d $G $V $u]} {" puts $f2 " clock format $secs -format {%a %A %g %G %u %U %V %w %W} -gmt true; \# $G-W[format %02d $V]-$u" puts $f2 "} {[lindex $shortdays $u] [lindex $longdays $u]\ @@ -478,7 +478,7 @@ proc testISO { f2 G V u secs } { [clock format $secs -format %U -gmt true]\ [format %02d $V] [expr { $u % 7 }]\ [clock format $secs -format %W -gmt true]}" - + } #---------------------------------------------------------------------- @@ -504,15 +504,15 @@ proc testcases4 { f2 } { puts $f2 "\# Test formatting of time of day" puts $f2 "\# Format groups tested: %H %OH %I %OI %k %Ok %l %Ol %M %OM %p %P %r %R %S %OS %T %X %EX %+" puts $f2 {} - + set i 0 set fmt "%H %OH %I %OI %k %Ok %l %Ol %M %OM %p %P %r %R %S %OS %T %X %EX %+" - foreach { h romanH I romanI am } { - 0 ? 12 xii AM - 1 i 1 i AM - 11 xi 11 xi AM - 12 xii 12 xii PM - 13 xiii 1 i PM + foreach { h romanH I romanI am } { + 0 ? 12 xii AM + 1 i 1 i AM + 11 xi 11 xi AM + 12 xii 12 xii PM + 13 xiii 1 i PM 23 xxiii 11 xi PM } { set hh [format %02d $h] @@ -547,7 +547,7 @@ proc testcases4 { f2 } { puts "testcases4: $i test cases." } - + #---------------------------------------------------------------------- # # testcases5 -- @@ -572,9 +572,9 @@ proc testcases5 { f2 } { puts $f2 {} puts $f2 "\# Test formatting of Daylight Saving Time" puts $f2 {} - + set fmt {%H:%M:%S %z %Z} - + set i 0 puts $f2 "test clock-5.[incr i] {does Detroit exist} {" puts $f2 " clock format 0 -format {} -timezone :America/Detroit" @@ -587,7 +587,7 @@ proc testcases5 { f2 } { puts $f2 " concat {ok}" puts $f2 " }" puts $f2 "} ok" - + foreach row $TZData(:America/Detroit) { foreach { t offset isdst tzname } $row break if { $t > -4000000000000 } { @@ -648,12 +648,12 @@ proc testcases5 { f2 } { proc testcases8 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of ccyymmdd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 1971 2000 2001} { foreach month {01 12} { foreach day {02 31} { @@ -670,7 +670,7 @@ proc testcases8 { f2 } { puts $f2 "} $scanned" } } - } + } foreach fmt {%x %D} { set string [clock format $scanned \ -format $fmt \ @@ -708,11 +708,11 @@ proc testcases8 { f2 } { proc testcases11 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test precedence among yyyymmdd and yyyyddd" puts $f2 "" - + array set v { Y 1970 m 01 @@ -771,12 +771,12 @@ proc testcases11 { f2 } { proc testcases12 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of ccyyWwwd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 1971 2000 2001} { foreach month {01 12} { foreach day {02 31} { @@ -817,12 +817,12 @@ proc testcases12 { f2 } { proc testcases14 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of yymmdd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1938 1970 2000 2037} { foreach month {01 12} { foreach day {02 31} { @@ -839,7 +839,7 @@ proc testcases14 { f2 } { puts $f2 "} $scanned" } } - } + } } } } @@ -868,12 +868,12 @@ proc testcases14 { f2 } { proc testcases17 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of yyWwwd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 1971 2000 2001} { foreach month {01 12} { foreach day {02 31} { @@ -914,12 +914,12 @@ proc testcases17 { f2 } { proc testcases19 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of mmdd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1938 1970 2000 2037} { set base [clock scan ${year}0101 -gmt true] foreach month {01 12} { @@ -935,7 +935,7 @@ proc testcases19 { f2 } { puts $f2 " [list clock scan $string -format [list $mm $dd] -locale en_US_roman -base $base -gmt 1]" puts $f2 "} $scanned" } - } + } } } } @@ -964,12 +964,12 @@ proc testcases19 { f2 } { proc testcases22 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of Wwwd" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 1971 2000 2001} { set base [clock scan ${year}0104 -gmt true] foreach month {03 10} { @@ -1011,12 +1011,12 @@ proc testcases22 { f2 } { proc testcases24 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of naked day-of-month" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 2000} { foreach month {01 12} { set base [clock scan ${year}${month}01 -gmt true] @@ -1030,7 +1030,7 @@ proc testcases24 { f2 } { puts $f2 "test clock-24.[incr n] {parse naked day of month} {" puts $f2 " [list clock scan $string -format $dd -locale en_US_roman -base $base -gmt 1]" puts $f2 "} $scanned" - } + } } } } @@ -1059,12 +1059,12 @@ proc testcases24 { f2 } { proc testcases26 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of naked day of week" puts $f2 "" - - set n 0 + + set n 0 foreach year {1970 2001} { foreach week {01 52} { set base [clock scan ${year}W${week}4 \ @@ -1108,7 +1108,7 @@ proc testcases26 { f2 } { proc testcases29 { f2 } { # Put out a header describing the tests - + puts $f2 "" puts $f2 "\# Test parsing of time of day" puts $f2 "" @@ -1172,7 +1172,7 @@ proc testcases29 { f2 } { } } } - + } puts "testcases29: $n test cases" } diff --git a/tools/man2help.tcl b/tools/man2help.tcl index 018fa84..ca29226 100644 --- a/tools/man2help.tcl +++ b/tools/man2help.tcl @@ -36,7 +36,7 @@ proc generateContents {basename version files} { set lastTopic {} foreach topic [getTopics $package $section] { if {[string compare $lastTopic $topic]} { - set id $topics($package,$section,$topic) + set id $topics($package,$section,$topic) puts $fd "2 $topic=$id" set lastTopic $topic } diff --git a/tools/man2html.tcl b/tools/man2html.tcl index fa57b03..6d4724f 100644 --- a/tools/man2html.tcl +++ b/tools/man2html.tcl @@ -27,8 +27,8 @@ proc sarray {file args} { if {![array exists array]} { puts "sarray: \"$a\" isn't an array" break - } - + } + foreach name [lsort [array names array]] { regsub -all " " $name "\\ " name1 puts $file "set ${a}($name1) \{$array($name)\}" @@ -141,12 +141,12 @@ proc main {argv} { foreach package $packages { file mkdir $html_dir/$package - + # build hyperlink database arrays: NAME_file and KEY_file # puts "\nScanning man pages in $tcl_dir/$package/doc..." uplevel \#0 [list source $homeDir/man2html1.tcl] - + doDir $tcl_dir/$package/doc # clean up the NAME_file and KEY_file database arrays diff --git a/tools/man2html1.tcl b/tools/man2html1.tcl index f2b2e43..e8d29e8 100644 --- a/tools/man2html1.tcl +++ b/tools/man2html1.tcl @@ -10,7 +10,7 @@ package require Tcl 8.4 # Global variables used by these scripts: # # state - state variable that controls action of text proc. -# +# # curFile - tail of current man page. # # file - file pointer; for both xref.tcl and contents.html @@ -23,7 +23,7 @@ package require Tcl 8.4 # # lib - contains package name. Used to label section in contents.html # -# inDT - in dictionary term. +# inDT - in dictionary term. # text -- @@ -32,7 +32,7 @@ package require Tcl 8.4 # and KEY_file. # # DT: might do this: if first word of $dt matches $name and [llength $name==1] -# and [llength $dt > 1], then add to NAME_file. +# and [llength $dt > 1], then add to NAME_file. # # Arguments: # string - Text to index. @@ -86,7 +86,7 @@ proc macro {name args} { KEYWORDS {set state KEY} default {set state OFF} } - + } TP { global inDT @@ -138,7 +138,7 @@ proc newline {} { # initGlobals, tab, font, char, macro2 -- # -# These procedures do nothing during the first pass. +# These procedures do nothing during the first pass. # # Arguments: # None. @@ -214,9 +214,9 @@ proc doListing {file pattern} { proc doContents {file packageName} { global footer - + set file [open $file w] - + puts $file "<HTML><HEAD><TITLE>$packageName Manual</TITLE></HEAD><BODY>" puts $file "<H3>$packageName</H3>" doListing $file "*.1" @@ -237,8 +237,8 @@ proc doContents {file packageName} { # # This is the toplevel procedure that searches a man page # for hypertext links. It builds a data base consisting of -# two arrays: NAME_file and KEY file. It runs the man2tcl -# program to turn the man page into a script, then it evals +# two arrays: NAME_file and KEY file. It runs the man2tcl +# program to turn the man page into a script, then it evals # that script. # # Arguments: diff --git a/tools/mkdepend.tcl b/tools/mkdepend.tcl index de5fdba..ecb2206 100644 --- a/tools/mkdepend.tcl +++ b/tools/mkdepend.tcl @@ -10,20 +10,20 @@ # above copyright notice and the following two paragraphs appear in # all copies of this software. # -# IN NO EVENT SHALL THE AUTHOR BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT, -# SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OF -# THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE AUTHOR HAS BEEN ADVISED +# IN NO EVENT SHALL THE AUTHOR BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT, +# SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OF +# THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE AUTHOR HAS BEEN ADVISED # OF THE POSSIBILITY OF SUCH DAMAGE. # -# THE AUTHOR SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT -# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A -# PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" +# THE AUTHOR SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A +# PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" # BASIS, AND THE AUTHOR HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, # UPDATES, ENHANCEMENTS, OR MODIFICATIONS. #============================================================================== # # Modified heavily by David Gravereaux <davygrvy@pobox.com> about 9/17/2006. -# Original can be found @ +# Original can be found @ # http://web.archive.org/web/20070616205924/http://www.doc.ic.ac.uk/~np2/software/mkdepend.html #============================================================================== diff --git a/tools/tcl.hpj.in b/tools/tcl.hpj.in index 3bdccbe..a94cea6 100644 --- a/tools/tcl.hpj.in +++ b/tools/tcl.hpj.in @@ -1,19 +1,19 @@ -; This file is maintained by HCW. Do not modify this file directly. - -[OPTIONS] -HCW=0 -LCID=0x409 0x0 0x0 ;English (United States) -REPORT=Yes -TITLE=Tcl/Tk Reference Manual -CNT=tcl86.cnt -COPYRIGHT=Copyright © 2000 Ajuba Solutions -HLP=tcl86.hlp - -[FILES] -tcl.rtf - -[WINDOWS] -main="Tcl/Tk Reference Manual",,0 - -[CONFIG] -BrowseButtons() +; This file is maintained by HCW. Do not modify this file directly.
+
+[OPTIONS]
+HCW=0
+LCID=0x409 0x0 0x0 ;English (United States)
+REPORT=Yes
+TITLE=Tcl/Tk Reference Manual
+CNT=tcl86.cnt
+COPYRIGHT=Copyright © 2000 Ajuba Solutions
+HLP=tcl86.hlp
+
+[FILES]
+tcl.rtf
+
+[WINDOWS]
+main="Tcl/Tk Reference Manual",,0
+
+[CONFIG]
+BrowseButtons()
diff --git a/tools/uniParse.tcl b/tools/uniParse.tcl index e33b3c7..8125790 100644 --- a/tools/uniParse.tcl +++ b/tools/uniParse.tcl @@ -396,7 +396,11 @@ enum { * Unicode character tables. */ -#define GetUniCharInfo(ch) (groups\[groupMap\[pageMap\[((ch) & 0xffff) >> OFFSET_BITS\] | ((ch) & ((1 << OFFSET_BITS)-1))\]\]) +#if TCL_UTF_MAX > 3 +# define GetUniCharInfo(ch) (groups\[groupMap\[pageMap\[((ch) & 0x1fffff) >> OFFSET_BITS\] | ((ch) & ((1 << OFFSET_BITS)-1))\]\]) +#else +# define GetUniCharInfo(ch) (groups\[groupMap\[pageMap\[((ch) & 0xffff) >> OFFSET_BITS\] | ((ch) & ((1 << OFFSET_BITS)-1))\]\]) +#endif " close $f diff --git a/unix/Makefile.in b/unix/Makefile.in index be769a4..e26d536 100644 --- a/unix/Makefile.in +++ b/unix/Makefile.in @@ -96,7 +96,7 @@ CFLAGS_WARNING = @CFLAGS_WARNING@ # The default switches for optimization or debugging CFLAGS_DEBUG = @CFLAGS_DEBUG@ -CFLAGS_OPTIMIZE = -DNDEBUG @CFLAGS_OPTIMIZE@ +CFLAGS_OPTIMIZE = @CFLAGS_OPTIMIZE@ # To change the compiler switches, for example to change from optimization to # debugging symbols, change the following line: @@ -662,18 +662,19 @@ basekit.vfs: "$(UNIX_DIR)/basekit.vfs/boot/tcl" "$(TOP_DIR)" unix basekit.zip: basekit.vfs - @$(TCL_EXE) ../tools/mkzip.tcl basekit.zip \ + @$(TCL_EXE) "$(TOP_DIR)/tools/mkzip.tcl" basekit.zip \ -directory basekit.vfs -# Builds an executable directly from the Tcl sources -${BASEKIT_EXE}: ${TCLSH_OBJS} ${OBJS} ${ZLIB_OBJS} basekit.vfs - +${BASEKIT_EXE}_bare: ${TCLSH_OBJS} ${OBJS} ${ZLIB_OBJS} basekit.vfs ${CC} ${CFLAGS} ${LDFLAGS} \ ${TCLSH_OBJS} ${OBJS} ${ZLIB_OBJS} \ ${LIBS} @EXTRA_TCLSH_LIBS@ \ ${CC_SEARCH_FLAGS} -o ${BASEKIT_EXE}_bare + +# Builds an executable directly from the Tcl sources +${BASEKIT_EXE}: ${BASEKIT_EXE}_bare @echo zipping... - @$(TCL_EXE) ../tools/mkzip.tcl ${BASEKIT_EXE} \ + @$(TCL_EXE) "$(TOP_DIR)/tools/mkzip.tcl" ${BASEKIT_EXE} \ -runtime ${BASEKIT_EXE}_bare \ -directory basekit.vfs chmod a+x ${BASEKIT_EXE} @@ -813,10 +814,6 @@ install-strip: INSTALL_PROGRAM="$(INSTALL_PROGRAM) ${INSTALL_STRIP_PROGRAM}" \ INSTALL_LIBRARY="$(INSTALL_LIBRARY) ${INSTALL_STRIP_LIBRARY}" -# Note: before running ranlib below, must cd to target directory because some -# ranlibs write to current directory, and this might not always be possible -# (e.g. if installing as root). - install-binaries: binaries @for i in "$(LIB_INSTALL_DIR)" "$(BIN_INSTALL_DIR)" \ "$(CONFIG_INSTALL_DIR)"; \ @@ -881,20 +878,20 @@ install-libraries: libraries do \ $(INSTALL_DATA) $$i "$(SCRIPT_INSTALL_DIR)"/http1.0; \ done; - @echo "Installing package http 2.8.8 as a Tcl Module"; - @$(INSTALL_DATA) $(TOP_DIR)/library/http/http.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.6/http-2.8.8.tm; + @echo "Installing package http 2.8.9 as a Tcl Module"; + @$(INSTALL_DATA) $(TOP_DIR)/library/http/http.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.6/http-2.8.9.tm; @echo "Installing package opt0.4 files to $(SCRIPT_INSTALL_DIR)/opt0.4/"; @for i in $(TOP_DIR)/library/opt/*.tcl ; \ do \ $(INSTALL_DATA) $$i "$(SCRIPT_INSTALL_DIR)"/opt0.4; \ done; - @echo "Installing package msgcat 1.5.2 as a Tcl Module"; - @$(INSTALL_DATA) $(TOP_DIR)/library/msgcat/msgcat.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.5/msgcat-1.5.2.tm; + @echo "Installing package msgcat 1.6.0 as a Tcl Module"; + @$(INSTALL_DATA) $(TOP_DIR)/library/msgcat/msgcat.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.5/msgcat-1.6.0.tm; @echo "Installing package tcltest 2.3.8 as a Tcl Module"; @$(INSTALL_DATA) $(TOP_DIR)/library/tcltest/tcltest.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.5/tcltest-2.3.8.tm; - @echo "Installing package platform 1.0.13 as a Tcl Module"; - @$(INSTALL_DATA) $(TOP_DIR)/library/platform/platform.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.4/platform-1.0.13.tm; + @echo "Installing package platform 1.0.14 as a Tcl Module"; + @$(INSTALL_DATA) $(TOP_DIR)/library/platform/platform.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.4/platform-1.0.14.tm; @echo "Installing package platform::shell 1.1.4 as a Tcl Module"; @$(INSTALL_DATA) $(TOP_DIR)/library/platform/shell.tcl "$(SCRIPT_INSTALL_DIR)"/../tcl8/8.4/platform/shell-1.1.4.tm; @@ -1244,7 +1241,6 @@ tclLoadDld.o: $(UNIX_DIR)/tclLoadDld.c $(CC) -c $(CC_SWITCHES) $(UNIX_DIR)/tclLoadDld.c tclLoadDyld.o: $(UNIX_DIR)/tclLoadDyld.c - @echo Warnings are expected from compiling tclLoadDyld.c: deprecated API use $(CC) -c $(CC_SWITCHES) $(UNIX_DIR)/tclLoadDyld.c tclLoadNone.o: $(GENERIC_DIR)/tclLoadNone.c @@ -2007,7 +2003,6 @@ $(MAC_OSX_DIR)/configure: $(MAC_OSX_DIR)/configure.ac $(UNIX_DIR)/configure $(UNIX_DIR)/tclConfig.h.in: $(MAC_OSX_DIR)/configure cd $(MAC_OSX_DIR); autoheader; touch $@ -EOLFIX=$(NATIVE_TCLSH) $(TOOL_DIR)/eolFix.tcl dist: $(UNIX_DIR)/configure $(UNIX_DIR)/tclConfig.h.in $(UNIX_DIR)/tcl.pc.in $(MAC_OSX_DIR)/configure genstubs dist-packages ${NATIVE_TCLSH} rm -rf $(DISTDIR) mkdir -p $(DISTDIR)/unix @@ -2074,17 +2069,11 @@ dist: $(UNIX_DIR)/configure $(UNIX_DIR)/tclConfig.h.in $(UNIX_DIR)/tcl.pc.in $(M cp -p $(TOP_DIR)/win/*.[ch] $(TOP_DIR)/win/*.ico $(TOP_DIR)/win/*.rc \ $(DISTDIR)/win cp -p $(TOP_DIR)/win/*.bat $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/*.bat cp -p $(TOP_DIR)/win/makefile.* $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/makefile.bc $(DISTDIR)/win/makefile.vc cp -p $(TOP_DIR)/win/rules.vc $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/rules.vc cp -p $(TOP_DIR)/win/coffbase.txt $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/coffbase.txt cp -p $(TOP_DIR)/win/tcl.hpj.in $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/tcl.hpj.in cp -p $(TOP_DIR)/win/tcl.ds* $(DISTDIR)/win - @$(EOLFIX) -crlf $(DISTDIR)/win/tcl.ds* cp -p $(TOP_DIR)/win/README $(DISTDIR)/win cp -p $(TOP_DIR)/license.terms $(DISTDIR)/win @mkdir $(DISTDIR)/macosx @@ -2110,7 +2099,6 @@ dist: $(UNIX_DIR)/configure $(UNIX_DIR)/tclConfig.h.in $(UNIX_DIR)/tcl.pc.in $(M $(TOOL_DIR)/*.tcl $(TOOL_DIR)/man2tcl.c \ $(TOOL_DIR)/*.bmp $(TOOL_DIR)/tcl.hpj.in \ $(DISTDIR)/tools - @$(EOLFIX) -crlf $(DISTDIR)/tools/tcl.hpj.in @mkdir $(DISTDIR)/libtommath cp -p $(TOMMATH_SRCS) $(TOMMATH_DIR)/*.h $(DISTDIR)/libtommath @mkdir $(DISTDIR)/pkgs diff --git a/unix/configure b/unix/configure index 6f5311c..27e147b 100755 --- a/unix/configure +++ b/unix/configure @@ -857,6 +857,8 @@ Optional Features: --enable-load allow dynamic loading and "load" command (default: on) --enable-symbols build with debugging symbols (default: off) + --enable-usleep use usleep if possible to sleep, otherwise use + Tcl_Sleep (default: on) --enable-langinfo use nl_langinfo if possible to determine encoding at startup, otherwise use old heuristic (default: on) --enable-dll-unloading enable the 'unload' command (default: on) @@ -3332,158 +3334,6 @@ _ACEOF fi - if test "${ac_cv_header_limits_h+set}" = set; then - echo "$as_me:$LINENO: checking for limits.h" >&5 -echo $ECHO_N "checking for limits.h... $ECHO_C" >&6 -if test "${ac_cv_header_limits_h+set}" = set; then - echo $ECHO_N "(cached) $ECHO_C" >&6 -fi -echo "$as_me:$LINENO: result: $ac_cv_header_limits_h" >&5 -echo "${ECHO_T}$ac_cv_header_limits_h" >&6 -else - # Is the header compilable? -echo "$as_me:$LINENO: checking limits.h usability" >&5 -echo $ECHO_N "checking limits.h usability... $ECHO_C" >&6 -cat >conftest.$ac_ext <<_ACEOF -/* confdefs.h. */ -_ACEOF -cat confdefs.h >>conftest.$ac_ext -cat >>conftest.$ac_ext <<_ACEOF -/* end confdefs.h. */ -$ac_includes_default -#include <limits.h> -_ACEOF -rm -f conftest.$ac_objext -if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 - (eval $ac_compile) 2>conftest.er1 - ac_status=$? - grep -v '^ *+' conftest.er1 >conftest.err - rm -f conftest.er1 - cat conftest.err >&5 - echo "$as_me:$LINENO: \$? = $ac_status" >&5 - (exit $ac_status); } && - { ac_try='test -z "$ac_c_werror_flag" - || test ! -s conftest.err' - { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 - (eval $ac_try) 2>&5 - ac_status=$? - echo "$as_me:$LINENO: \$? = $ac_status" >&5 - (exit $ac_status); }; } && - { ac_try='test -s conftest.$ac_objext' - { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 - (eval $ac_try) 2>&5 - ac_status=$? - echo "$as_me:$LINENO: \$? = $ac_status" >&5 - (exit $ac_status); }; }; then - ac_header_compiler=yes -else - echo "$as_me: failed program was:" >&5 -sed 's/^/| /' conftest.$ac_ext >&5 - -ac_header_compiler=no -fi -rm -f conftest.err conftest.$ac_objext conftest.$ac_ext -echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 -echo "${ECHO_T}$ac_header_compiler" >&6 - -# Is the header present? -echo "$as_me:$LINENO: checking limits.h presence" >&5 -echo $ECHO_N "checking limits.h presence... $ECHO_C" >&6 -cat >conftest.$ac_ext <<_ACEOF -/* confdefs.h. */ -_ACEOF -cat confdefs.h >>conftest.$ac_ext -cat >>conftest.$ac_ext <<_ACEOF -/* end confdefs.h. */ -#include <limits.h> -_ACEOF -if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 - (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 - ac_status=$? - grep -v '^ *+' conftest.er1 >conftest.err - rm -f conftest.er1 - cat conftest.err >&5 - echo "$as_me:$LINENO: \$? = $ac_status" >&5 - (exit $ac_status); } >/dev/null; then - if test -s conftest.err; then - ac_cpp_err=$ac_c_preproc_warn_flag - ac_cpp_err=$ac_cpp_err$ac_c_werror_flag - else - ac_cpp_err= - fi -else - ac_cpp_err=yes -fi -if test -z "$ac_cpp_err"; then - ac_header_preproc=yes -else - echo "$as_me: failed program was:" >&5 -sed 's/^/| /' conftest.$ac_ext >&5 - - ac_header_preproc=no -fi -rm -f conftest.err conftest.$ac_ext -echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 -echo "${ECHO_T}$ac_header_preproc" >&6 - -# So? What about this header? -case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in - yes:no: ) - { echo "$as_me:$LINENO: WARNING: limits.h: accepted by the compiler, rejected by the preprocessor!" >&5 -echo "$as_me: WARNING: limits.h: accepted by the compiler, rejected by the preprocessor!" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: proceeding with the compiler's result" >&5 -echo "$as_me: WARNING: limits.h: proceeding with the compiler's result" >&2;} - ac_header_preproc=yes - ;; - no:yes:* ) - { echo "$as_me:$LINENO: WARNING: limits.h: present but cannot be compiled" >&5 -echo "$as_me: WARNING: limits.h: present but cannot be compiled" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: check for missing prerequisite headers?" >&5 -echo "$as_me: WARNING: limits.h: check for missing prerequisite headers?" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: see the Autoconf documentation" >&5 -echo "$as_me: WARNING: limits.h: see the Autoconf documentation" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: section \"Present But Cannot Be Compiled\"" >&5 -echo "$as_me: WARNING: limits.h: section \"Present But Cannot Be Compiled\"" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: proceeding with the preprocessor's result" >&5 -echo "$as_me: WARNING: limits.h: proceeding with the preprocessor's result" >&2;} - { echo "$as_me:$LINENO: WARNING: limits.h: in the future, the compiler will take precedence" >&5 -echo "$as_me: WARNING: limits.h: in the future, the compiler will take precedence" >&2;} - ( - cat <<\_ASBOX -## ------------------------------ ## -## Report this to the tcl lists. ## -## ------------------------------ ## -_ASBOX - ) | - sed "s/^/$as_me: WARNING: /" >&2 - ;; -esac -echo "$as_me:$LINENO: checking for limits.h" >&5 -echo $ECHO_N "checking for limits.h... $ECHO_C" >&6 -if test "${ac_cv_header_limits_h+set}" = set; then - echo $ECHO_N "(cached) $ECHO_C" >&6 -else - ac_cv_header_limits_h=$ac_header_preproc -fi -echo "$as_me:$LINENO: result: $ac_cv_header_limits_h" >&5 -echo "${ECHO_T}$ac_cv_header_limits_h" >&6 - -fi -if test $ac_cv_header_limits_h = yes; then - -cat >>confdefs.h <<\_ACEOF -#define HAVE_LIMITS_H 1 -_ACEOF - -else - -cat >>confdefs.h <<\_ACEOF -#define NO_LIMITS_H 1 -_ACEOF - -fi - - if test "${ac_cv_header_stdlib_h+set}" = set; then echo "$as_me:$LINENO: checking for stdlib.h" >&5 echo $ECHO_N "checking for stdlib.h... $ECHO_C" >&6 @@ -7677,7 +7527,7 @@ fi ;; *) case "$arch" in - alpha|sparc64) + alpha|sparc|sparc64) SHLIB_CFLAGS="-fPIC" ;; *) @@ -9008,15 +8858,14 @@ else if test "$RANLIB" = ""; then MAKE_LIB='$(STLIB_LD) $@ ${OBJS}' - INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)"' else MAKE_LIB='${STLIB_LD} $@ ${OBJS} ; ${RANLIB} $@' - INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)" ; (cd "$(LIB_INSTALL_DIR)" ; $(RANLIB) $(LIB_FILE))' fi + INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)"' fi @@ -9025,15 +8874,14 @@ fi if test "$RANLIB" = ""; then MAKE_STUB_LIB='${STLIB_LD} $@ ${STUB_LIB_OBJS}' - INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)"' else MAKE_STUB_LIB='${STLIB_LD} $@ ${STUB_LIB_OBJS} ; ${RANLIB} $@' - INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)" ; (cd "$(LIB_INSTALL_DIR)" ; $(RANLIB) $(STUB_LIB_FILE))' fi + INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)"' # Define TCL_LIBS now that we know what DL_LIBS is. # The trick here is that we don't want to change the value of TCL_LIBS if @@ -16882,6 +16730,235 @@ _ACEOF fi #-------------------------------------------------------------------- +# Check for support of usleep function +#-------------------------------------------------------------------- + + + # Check whether --enable-usleep or --disable-usleep was given. +if test "${enable_usleep+set}" = set; then + enableval="$enable_usleep" + usleep_ok=$enableval +else + usleep_ok=yes +fi; + + HAVE_USLEEP=0 + if test "$usleep_ok" = "yes"; then + if test "${ac_cv_header_unistd_h+set}" = set; then + echo "$as_me:$LINENO: checking for unistd.h" >&5 +echo $ECHO_N "checking for unistd.h... $ECHO_C" >&6 +if test "${ac_cv_header_unistd_h+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: $ac_cv_header_unistd_h" >&5 +echo "${ECHO_T}$ac_cv_header_unistd_h" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking unistd.h usability" >&5 +echo $ECHO_N "checking unistd.h usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <unistd.h> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking unistd.h presence" >&5 +echo $ECHO_N "checking unistd.h presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <unistd.h> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: unistd.h: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: unistd.h: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: unistd.h: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: unistd.h: present but cannot be compiled" >&5 +echo "$as_me: WARNING: unistd.h: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: unistd.h: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: unistd.h: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: unistd.h: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: unistd.h: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: unistd.h: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: unistd.h: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## ------------------------------ ## +## Report this to the tcl lists. ## +## ------------------------------ ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for unistd.h" >&5 +echo $ECHO_N "checking for unistd.h... $ECHO_C" >&6 +if test "${ac_cv_header_unistd_h+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_header_unistd_h=$ac_header_preproc +fi +echo "$as_me:$LINENO: result: $ac_cv_header_unistd_h" >&5 +echo "${ECHO_T}$ac_cv_header_unistd_h" >&6 + +fi +if test $ac_cv_header_unistd_h = yes; then + usleep_ok=yes +else + usleep_ok=no +fi + + + fi + echo "$as_me:$LINENO: checking whether to use usleep" >&5 +echo $ECHO_N "checking whether to use usleep... $ECHO_C" >&6 + if test "$usleep_ok" = "yes"; then + if test "${tcl_cv_usleep_h+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <unistd.h> +int +main () +{ +usleep(0); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + tcl_cv_usleep_h=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +tcl_cv_usleep_h=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi + + echo "$as_me:$LINENO: result: $tcl_cv_usleep_h" >&5 +echo "${ECHO_T}$tcl_cv_usleep_h" >&6 + if test $tcl_cv_usleep_h = yes; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_USLEEP 1 +_ACEOF + + fi + else + echo "$as_me:$LINENO: result: $usleep_ok" >&5 +echo "${ECHO_T}$usleep_ok" >&6 + fi + + +#-------------------------------------------------------------------- # Check for support of nl_langinfo function #-------------------------------------------------------------------- diff --git a/unix/configure.in b/unix/configure.in index c7b0edc..ce68391 100644 --- a/unix/configure.in +++ b/unix/configure.in @@ -545,6 +545,12 @@ if test $tcl_cv_putenv_copy = yes; then fi #-------------------------------------------------------------------- +# Check for support of usleep function +#-------------------------------------------------------------------- + +SC_ENABLE_USLEEP + +#-------------------------------------------------------------------- # Check for support of nl_langinfo function #-------------------------------------------------------------------- diff --git a/unix/tcl.m4 b/unix/tcl.m4 index 277fe0b..83c3fb1 100644 --- a/unix/tcl.m4 +++ b/unix/tcl.m4 @@ -774,6 +774,48 @@ AC_DEFUN([SC_ENABLE_SYMBOLS], [ ]) #------------------------------------------------------------------------ +# SC_ENABLE_USLEEP -- +# +# Allows use of usleep function. +# This is only relevant for Unix. +# +# Arguments: +# none +# +# Results: +# +# Adds the following arguments to configure: +# --enable-usleep=yes|no (default is yes) +# +# Defines the following vars: +# HAVE_USLEEP Triggers use of usleep if defined. +#------------------------------------------------------------------------ + +AC_DEFUN([SC_ENABLE_USLEEP], [ + AC_ARG_ENABLE(usleep, + AC_HELP_STRING([--enable-usleep], + [use usleep if possible to sleep, otherwise use Tcl_Sleep (default: on)]), + [usleep_ok=$enableval], [usleep_ok=yes]) + + HAVE_USLEEP=0 + if test "$usleep_ok" = "yes"; then + AC_CHECK_HEADER(unistd.h,[usleep_ok=yes],[usleep_ok=no]) + fi + AC_MSG_CHECKING([whether to use usleep]) + if test "$usleep_ok" = "yes"; then + AC_CACHE_VAL(tcl_cv_usleep_h, [ + AC_TRY_COMPILE([#include <unistd.h>], [usleep(0);], + [tcl_cv_usleep_h=yes],[tcl_cv_usleep_h=no])]) + AC_MSG_RESULT([$tcl_cv_usleep_h]) + if test $tcl_cv_usleep_h = yes; then + AC_DEFINE(HAVE_USLEEP, 1, [Do we have usleep()?]) + fi + else + AC_MSG_RESULT([$usleep_ok]) + fi +]) + +#------------------------------------------------------------------------ # SC_ENABLE_LANGINFO -- # # Allows use of modern nl_langinfo check for better l10n. @@ -1476,7 +1518,7 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ ;; *) case "$arch" in - alpha|sparc64) + alpha|sparc|sparc64) SHLIB_CFLAGS="-fPIC" ;; *) @@ -2060,21 +2102,19 @@ dnl # preprocessing tests use only CPPFLAGS. AS_IF([test "$RANLIB" = ""], [ MAKE_LIB='$(STLIB_LD) [$]@ ${OBJS}' - INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)"' ], [ MAKE_LIB='${STLIB_LD} [$]@ ${OBJS} ; ${RANLIB} [$]@' - INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)" ; (cd "$(LIB_INSTALL_DIR)" ; $(RANLIB) $(LIB_FILE))' ]) + INSTALL_LIB='$(INSTALL_LIBRARY) $(LIB_FILE) "$(LIB_INSTALL_DIR)/$(LIB_FILE)"' ]) # Stub lib does not depend on shared/static configuration AS_IF([test "$RANLIB" = ""], [ MAKE_STUB_LIB='${STLIB_LD} [$]@ ${STUB_LIB_OBJS}' - INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)"' ], [ MAKE_STUB_LIB='${STLIB_LD} [$]@ ${STUB_LIB_OBJS} ; ${RANLIB} [$]@' - INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)" ; (cd "$(LIB_INSTALL_DIR)" ; $(RANLIB) $(STUB_LIB_FILE))' ]) + INSTALL_STUB_LIB='$(INSTALL_LIBRARY) $(STUB_LIB_FILE) "$(LIB_INSTALL_DIR)/$(STUB_LIB_FILE)"' # Define TCL_LIBS now that we know what DL_LIBS is. # The trick here is that we don't want to change the value of TCL_LIBS if @@ -2158,7 +2198,6 @@ dnl # preprocessing tests use only CPPFLAGS. # Defines some of the following vars: # NO_DIRENT_H # NO_VALUES_H -# HAVE_LIMITS_H or NO_LIMITS_H # NO_STDLIB_H # NO_STRING_H # NO_SYS_WAIT_H @@ -2198,9 +2237,6 @@ closedir(d); AC_CHECK_HEADER(float.h, , [AC_DEFINE(NO_FLOAT_H, 1, [Do we have <float.h>?])]) AC_CHECK_HEADER(values.h, , [AC_DEFINE(NO_VALUES_H, 1, [Do we have <values.h>?])]) - AC_CHECK_HEADER(limits.h, - [AC_DEFINE(HAVE_LIMITS_H, 1, [Do we have <limits.h>?])], - [AC_DEFINE(NO_LIMITS_H, 1, [Do we have <limits.h>?])]) AC_CHECK_HEADER(stdlib.h, tcl_ok=1, tcl_ok=0) AC_EGREP_HEADER(strtol, stdlib.h, , tcl_ok=0) AC_EGREP_HEADER(strtoul, stdlib.h, , tcl_ok=0) diff --git a/unix/tclConfig.h.in b/unix/tclConfig.h.in index 10ae12f..6972664 100644 --- a/unix/tclConfig.h.in +++ b/unix/tclConfig.h.in @@ -4,6 +4,9 @@ #ifndef _TCLCONFIG #define _TCLCONFIG +/* Define if building universal (internal helper macro) */ +#undef AC_APPLE_UNIVERSAL_BUILD + /* Is gettimeofday() actually declared in <sys/time.h>? */ #undef GETTOD_NOT_DECLARED @@ -127,9 +130,6 @@ /* Define to 1 if you have the <libkern/OSAtomic.h> header file. */ #undef HAVE_LIBKERN_OSATOMIC_H -/* Do we have <limits.h>? */ -#undef HAVE_LIMITS_H - /* Define to 1 if you have the `localtime_r' function. */ #undef HAVE_LOCALTIME_R @@ -211,10 +211,10 @@ /* Is 'struct stat64' in <sys/stat.h>? */ #undef HAVE_STRUCT_STAT64 -/* Define to 1 if `st_blksize' is member of `struct stat'. */ +/* Define to 1 if `st_blksize' is a member of `struct stat'. */ #undef HAVE_STRUCT_STAT_ST_BLKSIZE -/* Define to 1 if `st_blocks' is member of `struct stat'. */ +/* Define to 1 if `st_blocks' is a member of `struct stat'. */ #undef HAVE_STRUCT_STAT_ST_BLOCKS /* Define to 1 if you have the <sys/filio.h> header file. */ @@ -313,9 +313,6 @@ /* Do we have a usable 'isnan'? */ #undef NO_ISNAN -/* Do we have <limits.h>? */ -#undef NO_LIMITS_H - /* Do we have memmove()? */ #undef NO_MEMMOVE @@ -358,6 +355,9 @@ /* Define to the one symbol short name of this package. */ #undef PACKAGE_TARNAME +/* Define to the home page for this package. */ +#undef PACKAGE_URL + /* Define to the version of this package. */ #undef PACKAGE_VERSION @@ -436,9 +436,17 @@ /* Should we use vfork() instead of fork()? */ #undef USE_VFORK -/* Define to 1 if your processor stores words with the most significant byte - first (like Motorola and SPARC, unlike Intel and VAX). */ -#undef WORDS_BIGENDIAN +/* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most + significant byte first (like Motorola and SPARC, unlike Intel). */ +#if defined AC_APPLE_UNIVERSAL_BUILD +# if defined __BIG_ENDIAN__ +# define WORDS_BIGENDIAN 1 +# endif +#else +# ifndef WORDS_BIGENDIAN +# undef WORDS_BIGENDIAN +# endif +#endif /* Are Darwin SUSv3 extensions available? */ #undef _DARWIN_C_SOURCE @@ -493,7 +501,7 @@ /* Define to `int' if <sys/types.h> does not define. */ #undef pid_t -/* Define to `unsigned' if <sys/types.h> does not define. */ +/* Define to `unsigned int' if <sys/types.h> does not define. */ #undef size_t /* Define as int if socklen_t is not available */ diff --git a/unix/tclLoadDl.c b/unix/tclLoadDl.c index dc711f8..aec071c 100644 --- a/unix/tclLoadDl.c +++ b/unix/tclLoadDl.c @@ -124,9 +124,11 @@ TclpDlopen( const char *errorStr = dlerror(); - Tcl_SetObjResult(interp, Tcl_ObjPrintf( - "couldn't load file \"%s\": %s", - Tcl_GetString(pathPtr), errorStr)); + if (interp) { + Tcl_SetObjResult(interp, Tcl_ObjPrintf( + "couldn't load file \"%s\": %s", + Tcl_GetString(pathPtr), errorStr)); + } return TCL_ERROR; } newHandle = ckalloc(sizeof(*newHandle)); @@ -187,17 +189,18 @@ FindSymbol( Tcl_DStringFree(&newName); } Tcl_DStringFree(&ds); - if (proc == NULL && interp != NULL) { + if (proc == NULL) { const char *errorStr = dlerror(); - if (!errorStr) { - errorStr = "unknown"; + if (interp) { + if (!errorStr) { + errorStr = "unknown"; + } + Tcl_SetObjResult(interp, Tcl_ObjPrintf( + "cannot find symbol \"%s\": %s", symbol, errorStr)); + Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "LOAD_SYMBOL", symbol, + NULL); } - - Tcl_SetObjResult(interp, Tcl_ObjPrintf( - "cannot find symbol \"%s\": %s", symbol, errorStr)); - Tcl_SetErrorCode(interp, "TCL", "LOOKUP", "LOAD_SYMBOL", symbol, - NULL); } return proc; } diff --git a/unix/tclLoadDyld.c b/unix/tclLoadDyld.c index 50c283d..8b7dc58 100644 --- a/unix/tclLoadDyld.c +++ b/unix/tclLoadDyld.c @@ -48,6 +48,7 @@ #endif /* TCL_DYLD_USE_DLFCN */ #if TCL_DYLD_USE_NSMODULE || defined(TCL_LOAD_FROM_MEMORY) +#pragma GCC diagnostic ignored "-Wdeprecated-declarations" #include <mach-o/dyld.h> #include <mach-o/fat.h> #include <mach-o/swap.h> diff --git a/unix/tclUnixChan.c b/unix/tclUnixChan.c index a1fe090..b4b2739 100644 --- a/unix/tclUnixChan.c +++ b/unix/tclUnixChan.c @@ -988,6 +988,39 @@ static const struct {int baud; speed_t speed;} speeds[] = { #ifdef B460800 {460800, B460800}, #endif +#ifdef B500000 + {500000, B500000}, +#endif +#ifdef B576000 + {576000, B576000}, +#endif +#ifdef B921600 + {921600, B921600}, +#endif +#ifdef B1000000 + {1000000, B1000000}, +#endif +#ifdef B1152000 + {1152000, B1152000}, +#endif +#ifdef B1500000 + {1500000,B1500000}, +#endif +#ifdef B2000000 + {2000000, B2000000}, +#endif +#ifdef B2500000 + {2500000,B2500000}, +#endif +#ifdef B3000000 + {3000000,B3000000}, +#endif +#ifdef B3500000 + {3500000,B3500000}, +#endif +#ifdef B4000000 + {4000000,B4000000}, +#endif {-1, 0} }; diff --git a/unix/tclUnixFile.c b/unix/tclUnixFile.c index 2cb0027..7ffbf8d 100644 --- a/unix/tclUnixFile.c +++ b/unix/tclUnixFile.c @@ -155,6 +155,11 @@ TclpFindExecutable( goto done; } + if (TclpGetCwd(NULL, &cwd) == NULL) { + TclSetObjNameOfExecutable(Tcl_NewObj(), NULL); + goto done; + } + /* * The name is relative to the current working directory. First strip off * a leading "./", if any, then add the full path name of the current @@ -168,8 +173,6 @@ TclpFindExecutable( Tcl_DStringInit(&nameString); Tcl_DStringAppend(&nameString, name, -1); - TclpGetCwd(NULL, &cwd); - Tcl_DStringFree(&buffer); Tcl_UtfToExternalDString(NULL, Tcl_DStringValue(&cwd), Tcl_DStringLength(&cwd), &buffer); diff --git a/unix/tclUnixInit.c b/unix/tclUnixInit.c index 520c8e5..5fc0035 100644 --- a/unix/tclUnixInit.c +++ b/unix/tclUnixInit.c @@ -602,7 +602,7 @@ SearchKnownEncodings( int left = 0; int right = sizeof(localeTable)/sizeof(LocaleTable); - while (left <= right) { + while (left < right) { int test = (left + right)/2; int code = strcmp(localeTable[test].lang, encoding); diff --git a/unix/tclUnixNotfy.c b/unix/tclUnixNotfy.c index b2bea45..48ba0cc 100644 --- a/unix/tclUnixNotfy.c +++ b/unix/tclUnixNotfy.c @@ -1,3 +1,5 @@ +#define AT_FORK_INIT_VALUE 0 +#define RESET_ATFORK_MUTEX 1 /* * tclUnixNotify.c -- * @@ -97,10 +99,11 @@ typedef struct ThreadSpecificData { * by sending this event. */ void *hwnd; /* Messaging window. */ #else /* !__CYGWIN__ */ - Tcl_Condition waitCV; /* Any other thread alerts a notifier that an + pthread_cond_t waitCV; /* Any other thread alerts a notifier that an * event is ready to be processed by signaling * this condition variable. */ #endif /* __CYGWIN__ */ + int waitCVinitialized; /* Variable to flag initialization of the structure */ int eventReady; /* True if an event is ready to be processed. * Used as condition flag together with waitCV * above. */ @@ -120,15 +123,6 @@ static Tcl_ThreadDataKey dataKey; static int notifierCount = 0; /* - * The following static stores the process ID of the initialized notifier - * thread. If it changes, we have passed a fork and we should start a new - * notifier thread. - * - * You must hold the notifierMutex lock before accessing this variable. - */ -static pid_t processIDInitialized = 0; - -/* * The following variable points to the head of a doubly-linked list of * ThreadSpecificData structures for all threads that are currently waiting on * an event. @@ -158,7 +152,15 @@ static int triggerPipe = -1; * The notifierMutex locks access to all of the global notifier state. */ -TCL_DECLARE_MUTEX(notifierMutex) +pthread_mutex_t notifierInitMutex = PTHREAD_MUTEX_INITIALIZER; +pthread_mutex_t notifierMutex = PTHREAD_MUTEX_INITIALIZER; +/* + * The following static indicates if the notifier thread is running. + * + * You must hold the notifierInitMutex before accessing this variable. + */ + +static int notifierThreadRunning = 0; /* * The notifier thread signals the notifierCV when it has finished @@ -166,7 +168,7 @@ TCL_DECLARE_MUTEX(notifierMutex) * terminates. */ -static Tcl_Condition notifierCV; +static pthread_cond_t notifierCV = PTHREAD_COND_INITIALIZER; /* * The pollState bits @@ -194,15 +196,15 @@ static Tcl_ThreadId notifierThread; #ifdef TCL_THREADS static void NotifierThreadProc(ClientData clientData); -#if defined(HAVE_PTHREAD_ATFORK) && !defined(__APPLE__) && !defined(__hpux) -static int atForkInit = 0; +#if defined(HAVE_PTHREAD_ATFORK) +static int atForkInit = AT_FORK_INIT_VALUE; static void AtForkPrepare(void); static void AtForkParent(void); static void AtForkChild(void); #endif /* HAVE_PTHREAD_ATFORK */ #endif /* TCL_THREADS */ static int FileHandlerEventProc(Tcl_Event *evPtr, int flags); - + /* * Import of Windows API when building threaded with Cygwin. */ @@ -251,13 +253,58 @@ extern unsigned char __stdcall ResetEvent(void *); extern unsigned char __stdcall TranslateMessage(const MSG *); /* - * Threaded-cygwin specific functions in this file: + * Threaded-cygwin specific constants and functions in this file: */ +static const WCHAR NotfyClassName[] = L"TclNotifier"; static DWORD __stdcall NotifierProc(void *hwnd, unsigned int message, void *wParam, void *lParam); #endif /* TCL_THREADS && __CYGWIN__ */ +#if TCL_THREADS +/* + *---------------------------------------------------------------------- + * + * StartNotifierThread -- + * + * Start a notfier thread and wait for the notifier pipe to be created. + * + * Results: + * None. + * + * Side effects: + * Running Thread. + * + *---------------------------------------------------------------------- + */ +static void +StartNotifierThread(const char *proc) +{ + if (!notifierThreadRunning) { + pthread_mutex_lock(¬ifierInitMutex); + if (!notifierThreadRunning) { + if (TclpThreadCreate(¬ifierThread, NotifierThreadProc, NULL, + TCL_THREAD_STACK_DEFAULT, TCL_THREAD_JOINABLE) != TCL_OK) { + Tcl_Panic("%s: unable to start notifier thread", proc); + } + + pthread_mutex_lock(¬ifierMutex); + /* + * Wait for the notifier pipe to be created. + */ + + while (triggerPipe < 0) { + pthread_cond_wait(¬ifierCV, ¬ifierMutex); + } + pthread_mutex_unlock(¬ifierMutex); + + notifierThreadRunning = 1; + } + pthread_mutex_unlock(¬ifierInitMutex); + } +} +#endif /* TCL_THREADS */ + /* *---------------------------------------------------------------------- * @@ -286,13 +333,39 @@ Tcl_InitNotifier(void) tsdPtr->eventReady = 0; /* - * Start the Notifier thread if necessary. + * Initialize thread specific condition variable for this thread. */ + if (tsdPtr->waitCVinitialized == 0) { +#ifdef __CYGWIN__ + WNDCLASS class; + + class.style = 0; + class.cbClsExtra = 0; + class.cbWndExtra = 0; + class.hInstance = TclWinGetTclInstance(); + class.hbrBackground = NULL; + class.lpszMenuName = NULL; + class.lpszClassName = NotfyClassName; + class.lpfnWndProc = NotifierProc; + class.hIcon = NULL; + class.hCursor = NULL; + + RegisterClassW(&class); + tsdPtr->hwnd = CreateWindowExW(NULL, class.lpszClassName, + class.lpszClassName, 0, 0, 0, 0, 0, NULL, NULL, + TclWinGetTclInstance(), NULL); + tsdPtr->event = CreateEventW(NULL, 1 /* manual */, + 0 /* !signaled */, NULL); +#else + pthread_cond_init(&tsdPtr->waitCV, NULL); +#endif /* __CYGWIN__ */ + tsdPtr->waitCVinitialized = 1; + } - Tcl_MutexLock(¬ifierMutex); -#if defined(HAVE_PTHREAD_ATFORK) && !defined(__APPLE__) && !defined(__hpux) + pthread_mutex_lock(¬ifierInitMutex); +#if defined(HAVE_PTHREAD_ATFORK) /* - * Install pthread_atfork handlers to reinitialize the notifier in the + * Install pthread_atfork handlers to clean up the notifier in the * child of a fork. */ @@ -305,36 +378,11 @@ Tcl_InitNotifier(void) atForkInit = 1; } #endif /* HAVE_PTHREAD_ATFORK */ - /* - * Check if my process id changed, e.g. I was forked - * In this case, restart the notifier thread and close the - * pipe to the original notifier thread - */ - if (notifierCount > 0 && processIDInitialized != getpid()) { - Tcl_ConditionFinalize(¬ifierCV); - notifierCount = 0; - processIDInitialized = 0; - close(triggerPipe); - triggerPipe = -1; - } - if (notifierCount == 0) { - if (TclpThreadCreate(¬ifierThread, NotifierThreadProc, NULL, - TCL_THREAD_STACK_DEFAULT, TCL_THREAD_JOINABLE) != TCL_OK) { - Tcl_Panic("Tcl_InitNotifier: unable to start notifier thread"); - } - processIDInitialized = getpid(); - } - notifierCount++; - /* - * Wait for the notifier pipe to be created. - */ + notifierCount++; - while (triggerPipe < 0) { - Tcl_ConditionWait(¬ifierCV, ¬ifierMutex, NULL); - } + pthread_mutex_unlock(¬ifierInitMutex); - Tcl_MutexUnlock(¬ifierMutex); #endif /* TCL_THREADS */ return tsdPtr; } @@ -369,7 +417,7 @@ Tcl_FinalizeNotifier( #ifdef TCL_THREADS ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey); - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierInitMutex); notifierCount--; /* @@ -378,37 +426,25 @@ Tcl_FinalizeNotifier( */ if (notifierCount == 0) { - int result; - - if (triggerPipe < 0) { - Tcl_Panic("Tcl_FinalizeNotifier: %s", - "notifier pipe not initialized"); - } - /* - * Send "q" message to the notifier thread so that it will - * terminate. The notifier will return from its call to select() - * and notice that a "q" message has arrived, it will then close - * its side of the pipe and terminate its thread. Note the we can - * not just close the pipe and check for EOF in the notifier thread - * because if a background child process was created with exec, - * select() would not register the EOF on the pipe until the child - * processes had terminated. [Bug: 4139] [Bug: 1222872] - */ - - if (write(triggerPipe, "q", 1) != 1) { - Tcl_Panic("Tcl_FinalizeNotifier: %s", - "unable to write q to triggerPipe"); - } - close(triggerPipe); - while(triggerPipe >= 0) { - Tcl_ConditionWait(¬ifierCV, ¬ifierMutex, NULL); - } + if (triggerPipe != -1) { + if (write(triggerPipe, "q", 1) != 1) { + Tcl_Panic("Tcl_FinalizeNotifier: %s", + "unable to write q to triggerPipe"); + } + close(triggerPipe); + while(triggerPipe != -1) { + pthread_cond_wait(¬ifierCV, ¬ifierMutex); + } + if (notifierThreadRunning) { + int result = pthread_join((pthread_t) notifierThread, NULL); - result = Tcl_JoinThread(notifierThread, NULL); - if (result) { - Tcl_Panic("Tcl_FinalizeNotifier: %s", - "unable to join notifier thread"); + if (result) { + Tcl_Panic("Tcl_FinalizeNotifier: unable to join notifier " + "thread"); + } + notifierThreadRunning = 0; + } } } @@ -417,12 +453,14 @@ Tcl_FinalizeNotifier( */ #ifdef __CYGWIN__ + DestroyWindow(tsdPtr->hwnd); CloseHandle(tsdPtr->event); #else /* __CYGWIN__ */ - Tcl_ConditionFinalize(&(tsdPtr->waitCV)); + pthread_cond_destroy(&tsdPtr->waitCV); #endif /* __CYGWIN__ */ + tsdPtr->waitCVinitialized = 0; - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierInitMutex); #endif /* TCL_THREADS */ } } @@ -457,14 +495,15 @@ Tcl_AlertNotifier( #ifdef TCL_THREADS ThreadSpecificData *tsdPtr = clientData; - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); tsdPtr->eventReady = 1; + # ifdef __CYGWIN__ PostMessageW(tsdPtr->hwnd, 1024, 0, 0); # else - Tcl_ConditionNotify(&tsdPtr->waitCV); + pthread_cond_broadcast(&tsdPtr->waitCV); # endif /* __CYGWIN__ */ - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierMutex); #endif /* TCL_THREADS */ } } @@ -527,8 +566,10 @@ Tcl_ServiceModeHook( if (tclNotifierHooks.serviceModeHookProc) { tclNotifierHooks.serviceModeHookProc(mode); return; - } else { - /* Does nothing in this implementation. */ + } else if (mode == TCL_SERVICE_ALL) { +#if TCL_THREADS + StartNotifierThread("Tcl_ServiceModeHook"); +#endif } } @@ -741,6 +782,7 @@ FileHandlerEventProc( */ tsdPtr = TCL_TSD_INIT(&dataKey); + for (filePtr = tsdPtr->firstFileHandlerPtr; filePtr != NULL; filePtr = filePtr->nextPtr) { if (filePtr->fd != fileEvPtr->fd) { @@ -878,35 +920,13 @@ Tcl_WaitForEvent( #ifdef TCL_THREADS /* - * Place this thread on the list of interested threads, signal the - * notifier thread, and wait for a response or a timeout. + * Start notifier thread and place this thread on the list of + * interested threads, signal the notifier thread, and wait for a + * response or a timeout. */ + StartNotifierThread("Tcl_WaitForEvent"); -#ifdef __CYGWIN__ - if (!tsdPtr->hwnd) { - WNDCLASS class; - - class.style = 0; - class.cbClsExtra = 0; - class.cbWndExtra = 0; - class.hInstance = TclWinGetTclInstance(); - class.hbrBackground = NULL; - class.lpszMenuName = NULL; - class.lpszClassName = L"TclNotifier"; - class.lpfnWndProc = NotifierProc; - class.hIcon = NULL; - class.hCursor = NULL; - - RegisterClassW(&class); - tsdPtr->hwnd = CreateWindowExW(NULL, class.lpszClassName, - class.lpszClassName, 0, 0, 0, 0, 0, NULL, NULL, - TclWinGetTclInstance(), NULL); - tsdPtr->event = CreateEventW(NULL, 1 /* manual */, - 0 /* !signaled */, NULL); - } -#endif /* __CYGWIN */ - - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); if (timePtr != NULL && timePtr->sec == 0 && (timePtr->usec == 0 #if defined(__APPLE__) && defined(__LP64__) @@ -971,12 +991,23 @@ Tcl_WaitForEvent( } else { timeout = 0xFFFFFFFF; } - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierMutex); MsgWaitForMultipleObjects(1, &tsdPtr->event, 0, timeout, 1279); - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); } #else - Tcl_ConditionWait(&tsdPtr->waitCV, ¬ifierMutex, timePtr); + if (timePtr != NULL) { + Tcl_Time now; + struct timespec ptime; + + Tcl_GetTime(&now); + ptime.tv_sec = timePtr->sec + now.sec + (timePtr->usec + now.usec) / 1000000; + ptime.tv_nsec = 1000 * ((timePtr->usec + now.usec) % 1000000); + + pthread_cond_timedwait(&tsdPtr->waitCV, ¬ifierMutex, &ptime); + } else { + pthread_cond_wait(&tsdPtr->waitCV, ¬ifierMutex); + } #endif /* __CYGWIN__ */ } tsdPtr->eventReady = 0; @@ -1079,7 +1110,7 @@ Tcl_WaitForEvent( filePtr->readyMask = mask; } #ifdef TCL_THREADS - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierMutex); #endif /* TCL_THREADS */ return 0; } @@ -1151,15 +1182,15 @@ NotifierThreadProc( * Install the write end of the pipe into the global variable. */ - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); triggerPipe = fds[1]; /* * Signal any threads that are waiting. */ - Tcl_ConditionNotify(¬ifierCV); - Tcl_MutexUnlock(¬ifierMutex); + pthread_cond_broadcast(¬ifierCV); + pthread_mutex_unlock(¬ifierMutex); /* * Look for file events and report them to interested threads. @@ -1175,7 +1206,7 @@ NotifierThreadProc( * notifiers. */ - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); timePtr = NULL; for (tsdPtr = waitingListPtr; tsdPtr; tsdPtr = tsdPtr->nextPtr) { for (i = tsdPtr->numFdBits-1; i >= 0; --i) { @@ -1202,7 +1233,7 @@ NotifierThreadProc( timePtr = &poll; } } - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierMutex); /* * Set up the select mask to include the receive pipe. @@ -1226,7 +1257,7 @@ NotifierThreadProc( * Alert any threads that are waiting on a ready file descriptor. */ - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); for (tsdPtr = waitingListPtr; tsdPtr; tsdPtr = tsdPtr->nextPtr) { found = 0; @@ -1272,12 +1303,12 @@ NotifierThreadProc( } #ifdef __CYGWIN__ PostMessageW(tsdPtr->hwnd, 1024, 0, 0); -#else - Tcl_ConditionNotify(&tsdPtr->waitCV); +#else /* __CYGWIN__ */ + pthread_cond_broadcast(&tsdPtr->waitCV); #endif /* __CYGWIN__ */ } } - Tcl_MutexUnlock(¬ifierMutex); + pthread_mutex_unlock(¬ifierMutex); /* * Consume the next byte from the notifier pipe if the pipe was @@ -1306,15 +1337,15 @@ NotifierThreadProc( */ close(receivePipe); - Tcl_MutexLock(¬ifierMutex); + pthread_mutex_lock(¬ifierMutex); triggerPipe = -1; - Tcl_ConditionNotify(¬ifierCV); - Tcl_MutexUnlock(¬ifierMutex); + pthread_cond_broadcast(¬ifierCV); + pthread_mutex_unlock(¬ifierMutex); TclpThreadExit(0); } -#if defined(HAVE_PTHREAD_ATFORK) && !defined(__APPLE__) && !defined(__hpux) +#if defined(HAVE_PTHREAD_ATFORK) /* *---------------------------------------------------------------------- * @@ -1334,6 +1365,9 @@ NotifierThreadProc( static void AtForkPrepare(void) { +#if RESET_ATFORK_MUTEX == 0 + pthread_mutex_lock(¬ifierInitMutex); +#endif } /* @@ -1355,6 +1389,9 @@ AtForkPrepare(void) static void AtForkParent(void) { +#if RESET_ATFORK_MUTEX == 0 + pthread_mutex_unlock(¬ifierInitMutex); +#endif } /* @@ -1376,7 +1413,67 @@ AtForkParent(void) static void AtForkChild(void) { - Tcl_MutexFinalize(¬ifierMutex); + if (notifierThreadRunning == 1) { + pthread_cond_destroy(¬ifierCV); + } +#if RESET_ATFORK_MUTEX == 0 + pthread_mutex_unlock(¬ifierInitMutex); +#else + pthread_mutex_init(¬ifierInitMutex, NULL); + pthread_mutex_init(¬ifierMutex, NULL); +#endif + pthread_cond_init(¬ifierCV, NULL); + + /* + * notifierThreadRunning == 1: thread is running, (there might be data in notifier lists) + * atForkInit == 0: InitNotifier was never called + * notifierCount != 0: unbalanced InitNotifier() / FinalizeNotifier calls + * waitingListPtr != 0: there are threads currently waiting for events. + */ + + if (atForkInit == 1) { + + notifierCount = 0; + if (notifierThreadRunning == 1) { + ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey); + notifierThreadRunning = 0; + + close(triggerPipe); + triggerPipe = -1; + /* + * The waitingListPtr might contain event info from multiple + * threads, which are invalid here, so setting it to NULL is not + * unreasonable. + */ + waitingListPtr = NULL; + + /* + * The tsdPtr from before the fork is copied as well. But since + * we are paranoic, we don't trust its condvar and reset it. + */ +#ifdef __CYGWIN__ + DestroyWindow(tsdPtr->hwnd); + tsdPtr->hwnd = CreateWindowExW(NULL, NotfyClassName, + NotfyClassName, 0, 0, 0, 0, 0, NULL, NULL, + TclWinGetTclInstance(), NULL); + ResetEvent(tsdPtr->event); +#else + pthread_cond_destroy(&tsdPtr->waitCV); + pthread_cond_init(&tsdPtr->waitCV, NULL); +#endif + /* + * In case, we had multiple threads running before the fork, + * make sure, we don't try to reach out to their thread local data. + */ + tsdPtr->nextPtr = tsdPtr->prevPtr = NULL; + + /* + * The list of registered event handlers at fork time is in + * tsdPtr->firstFileHandlerPtr; + */ + } + } + Tcl_InitNotifier(); } #endif /* HAVE_PTHREAD_ATFORK */ diff --git a/unix/tclUnixPort.h b/unix/tclUnixPort.h index f64d453..2728957 100644 --- a/unix/tclUnixPort.h +++ b/unix/tclUnixPort.h @@ -98,9 +98,6 @@ typedef off_t Tcl_SeekOffset; __declspec(dllimport) extern __stdcall int SetFileAttributesW(const WCHAR *, int); __declspec(dllimport) extern int cygwin_conv_path(int, const void *, void *, int); - __declspec(dllimport) extern int cygwin_conv_path_list(int, const void *, void *, int); -# define USE_PUTENV 1 -# define USE_PUTENV_FOR_UNSET 1 /* On Cygwin, the environment is imported from the Cygwin DLL. */ #ifndef __x86_64__ # define environ __cygwin_environ @@ -144,11 +141,7 @@ typedef off_t Tcl_SeekOffset; #if HAVE_INTTYPES_H # include <inttypes.h> #endif -#ifdef NO_LIMITS_H -# include "../compat/limits.h" -#else -# include <limits.h> -#endif +#include <limits.h> #if HAVE_STDINT_H # include <stdint.h> #endif @@ -450,16 +443,6 @@ extern int gettimeofday(struct timeval *tp, /* *--------------------------------------------------------------------------- - * Make sure that L_tmpnam is defined. - *--------------------------------------------------------------------------- - */ - -#ifndef L_tmpnam -# define L_tmpnam 100 -#endif - -/* - *--------------------------------------------------------------------------- * The following macro defines the type of the mask arguments to select: *--------------------------------------------------------------------------- */ diff --git a/unix/tclUnixThrd.c b/unix/tclUnixThrd.c index d34bc88..ea03332 100644 --- a/unix/tclUnixThrd.c +++ b/unix/tclUnixThrd.c @@ -360,7 +360,6 @@ TclpMasterUnlock(void) pthread_mutex_unlock(&masterLock); #endif } - /* *---------------------------------------------------------------------- diff --git a/win/Makefile.in b/win/Makefile.in index 0b34570..1b75a72 100644 --- a/win/Makefile.in +++ b/win/Makefile.in @@ -22,6 +22,7 @@ exec_prefix = @exec_prefix@ bindir = @bindir@ libdir = @libdir@ includedir = @includedir@ +datarootdir = @datarootdir@ mandir = @mandir@ # The following definition can be set to non-null for special systems like AFS @@ -110,10 +111,16 @@ VFS_PKG_INSTALL_DIR = $(WIN_DIR)/tclvfs.zip/lib # Converts a POSIX path to a Windows native path. CYGPATH = @CYGPATH@ -GENERIC_DIR_NATIVE = $(shell $(CYGPATH) '$(GENERIC_DIR)' | sed 's!\\!/!g') -TOMMATH_DIR_NATIVE = $(shell $(CYGPATH) '$(TOMMATH_DIR)' | sed 's!\\!/!g') -WIN_DIR_NATIVE = $(shell $(CYGPATH) '$(WIN_DIR)' | sed 's!\\!/!g') -ROOT_DIR_NATIVE = $(shell $(CYGPATH) '$(ROOT_DIR)' | sed 's!\\!/!g') +libdir_native = $(shell $(CYGPATH) '$(libdir)') +bindir_native = $(shell $(CYGPATH) '$(bindir)') +includedir_native = $(shell $(CYGPATH) '$(includedir)') +mandir_native = $(shell $(CYGPATH) '$(mandir)') +TCL_LIBRARY_NATIVE = $(shell $(CYGPATH) '$(TCL_LIBRARY)') +GENERIC_DIR_NATIVE = $(shell $(CYGPATH) '$(GENERIC_DIR)') +TOMMATH_DIR_NATIVE = $(shell $(CYGPATH) '$(TOMMATH_DIR)') +WIN_DIR_NATIVE = $(shell $(CYGPATH) '$(WIN_DIR)') +ROOT_DIR_NATIVE = $(shell $(CYGPATH) '$(ROOT_DIR)') +ZLIB_DIR_NATIVE = $(shell $(CYGPATH) '$(ZLIB_DIR)') #GENERIC_DIR_NATIVE = $(GENERIC_DIR) #TOMMATH_DIR_NATIVE = $(TOMMATH_DIR) #WIN_DIR_NATIVE = $(WIN_DIR) @@ -122,7 +129,7 @@ ROOT_DIR_NATIVE = $(shell $(CYGPATH) '$(ROOT_DIR)' | sed 's!\\!/!g') # Fully qualify library path so that `make test` # does not depend on the current directory. LIBRARY_DIR1 = $(shell cd '$(ROOT_DIR_NATIVE)/library' ; pwd -P) -LIBRARY_DIR = $(shell $(CYGPATH) '$(LIBRARY_DIR1)' | sed 's!\\!/!g') +LIBRARY_DIR = $(shell $(CYGPATH) '$(LIBRARY_DIR1)') DLLSUFFIX = @DLLSUFFIX@ LIBSUFFIX = @LIBSUFFIX@ EXESUFFIX = @EXESUFFIX@ @@ -186,7 +193,7 @@ SHLIB_LD = @SHLIB_LD@ SHLIB_LD_LIBS = @SHLIB_LD_LIBS@ SHLIB_CFLAGS = @SHLIB_CFLAGS@ SHLIB_SUFFIX = @SHLIB_SUFFIX@ -LIBS = @LIBS@ @ZLIB_LIBS@ +LIBS = @LIBS@ $(shell $(CYGPATH) '@ZLIB_LIBS@') RMDIR = rm -rf MKDIR = mkdir -p @@ -194,10 +201,10 @@ SHELL = @SHELL@ RM = rm -f COPY = cp -CC_SWITCHES = ${CFLAGS} ${CFLAGS_WARNING} ${TCL_SHLIB_CFLAGS} -I"${ZLIB_DIR}" \ --I"${GENERIC_DIR_NATIVE}" -DTCL_TOMMATH -DMP_PREC=4 -I"${TOMMATH_DIR_NATIVE}" \ --I"${WIN_DIR_NATIVE}" ${AC_FLAGS} \ -${COMPILE_DEBUG_FLAGS} ${NO_DEPRECATED_FLAGS} +CC_SWITCHES = ${CFLAGS} ${CFLAGS_WARNING} ${TCL_SHLIB_CFLAGS} \ +-I"${ZLIB_DIR_NATIVE}" -I"${GENERIC_DIR_NATIVE}" -DTCL_TOMMATH \ +-DMP_PREC=4 -I"${TOMMATH_DIR_NATIVE}" -I"${WIN_DIR_NATIVE}" \ +${AC_FLAGS} ${COMPILE_DEBUG_FLAGS} ${NO_DEPRECATED_FLAGS} CC_OBJNAME = @CC_OBJNAME@ CC_EXENAME = @CC_EXENAME@ @@ -542,17 +549,17 @@ tclZipShInit.${OBJEXT}: tclAppInit.c tclPkgConfig.${OBJEXT}: tclPkgConfig.c $(CC) -c $(CC_SWITCHES) \ - -DCFG_INSTALL_LIBDIR=\"$(LIB_INSTALL_DIR)\" \ - -DCFG_INSTALL_BINDIR=\"$(BIN_INSTALL_DIR)\" \ - -DCFG_INSTALL_SCRDIR=\"$(SCRIPT_INSTALL_DIR)\" \ - -DCFG_INSTALL_INCDIR=\"$(INCLUDE_INSTALL_DIR)\" \ + -DCFG_INSTALL_LIBDIR=\"$(LIB_INSTALL_DIR_NATIVE)\" \ + -DCFG_INSTALL_BINDIR=\"$(BIN_INSTALL_DIR_NATIVE)\" \ + -DCFG_INSTALL_SCRDIR=\"$(SCRIPT_INSTALL_DIR_NATIVE)\" \ + -DCFG_INSTALL_INCDIR=\"$(INCLUDE_INSTALL_DIR_NATIVE)\" \ -DCFG_INSTALL_DOCDIR=\"$(MAN_INSTALL_DIR)\" \ \ - -DCFG_RUNTIME_LIBDIR=\"$(libdir)\" \ - -DCFG_RUNTIME_BINDIR=\"$(bindir)\" \ - -DCFG_RUNTIME_SCRDIR=\"$(TCL_LIBRARY)\" \ - -DCFG_RUNTIME_INCDIR=\"$(includedir)\" \ - -DCFG_RUNTIME_DOCDIR=\"$(mandir)\" \ + -DCFG_RUNTIME_LIBDIR=\"$(libdir_native)\" \ + -DCFG_RUNTIME_BINDIR=\"$(bindir_native)\" \ + -DCFG_RUNTIME_SCRDIR=\"$(TCL_LIBRARY_NATIVE)\" \ + -DCFG_RUNTIME_INCDIR=\"$(includedir_native)\" \ + -DCFG_RUNTIME_DOCDIR=\"$(mandir_native)\" \ -DBUILD_tcl \ @DEPARG@ $(CC_OBJNAME) @@ -652,7 +659,7 @@ install-binaries: binaries fi install-libraries: libraries install-tzdata install-msgs - @for i in $(prefix)/lib $(INCLUDE_INSTALL_DIR) \ + @for i in "$$($(CYGPATH) $(prefix)/lib)" "$(INCLUDE_INSTALL_DIR)" \ $(SCRIPT_INSTALL_DIR); \ do \ if [ ! -d $$i ] ; then \ @@ -688,19 +695,19 @@ install-libraries: libraries install-tzdata install-msgs do \ $(COPY) "$$j" "$(SCRIPT_INSTALL_DIR)/http1.0"; \ done; - @echo "Installing package http 2.8.8 as a Tcl Module"; - @$(COPY) $(ROOT_DIR)/library/http/http.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.6/http-2.8.8.tm; + @echo "Installing package http 2.8.9 as a Tcl Module"; + @$(COPY) $(ROOT_DIR)/library/http/http.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.6/http-2.8.9.tm; @echo "Installing library opt0.4 directory"; @for j in $(ROOT_DIR)/library/opt/*.tcl; \ do \ $(COPY) "$$j" "$(SCRIPT_INSTALL_DIR)/opt0.4"; \ done; - @echo "Installing package msgcat 1.5.2 as a Tcl Module"; - @$(COPY) $(ROOT_DIR)/library/msgcat/msgcat.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.5/msgcat-1.5.2.tm; + @echo "Installing package msgcat 1.6.0 as a Tcl Module"; + @$(COPY) $(ROOT_DIR)/library/msgcat/msgcat.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.5/msgcat-1.6.0.tm; @echo "Installing package tcltest 2.3.8 as a Tcl Module"; @$(COPY) $(ROOT_DIR)/library/tcltest/tcltest.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.5/tcltest-2.3.8.tm; - @echo "Installing package platform 1.0.13 as a Tcl Module"; - @$(COPY) $(ROOT_DIR)/library/platform/platform.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.4/platform-1.0.13.tm; + @echo "Installing package platform 1.0.14 as a Tcl Module"; + @$(COPY) $(ROOT_DIR)/library/platform/platform.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.4/platform-1.0.14.tm; @echo "Installing package platform::shell 1.1.4 as a Tcl Module"; @$(COPY) $(ROOT_DIR)/library/platform/shell.tcl $(SCRIPT_INSTALL_DIR)/../tcl8/8.4/platform/shell-1.1.4.tm; @echo "Installing encodings"; @@ -750,14 +757,14 @@ test-tcl: binaries $(TCLSH) $(CAT32) $(TEST_DLL_FILE) ./$(TCLSH) "$(ROOT_DIR_NATIVE)/tests/all.tcl" $(TESTFLAGS) \ -load "package ifneeded Tcltest ${VERSION}@TCL_PATCH_LEVEL@ [list load [file normalize ${TEST_DLL_FILE}] Tcltest]; \ package ifneeded dde 1.4.0 [list load [file normalize ${DDE_DLL_FILE}] dde]; \ - package ifneeded registry 1.3.0 [list load [file normalize ${REG_DLL_FILE}] registry]" | ./$(CAT32) + package ifneeded registry 1.3.1 [list load [file normalize ${REG_DLL_FILE}] registry]" | ./$(CAT32) # Useful target to launch a built tclsh with the proper path,... runtest: binaries $(TCLSH) $(TEST_DLL_FILE) @TCL_LIBRARY="$(LIBRARY_DIR)"; export TCL_LIBRARY; \ ./$(TCLSH) $(TESTFLAGS) -load "package ifneeded Tcltest ${VERSION}@TCL_PATCH_LEVEL@ [list load [file normalize ${TEST_DLL_FILE}] Tcltest]; \ package ifneeded dde 1.4.0 [list load [file normalize ${DDE_DLL_FILE}] dde]; \ - package ifneeded registry 1.3.0 [list load [file normalize ${REG_DLL_FILE}] registry]" $(SCRIPT) + package ifneeded registry 1.3.1 [list load [file normalize ${REG_DLL_FILE}] registry]" $(SCRIPT) # This target can be used to run tclsh from the build directory via # `make shell SCRIPT=foo.tcl` @@ -797,7 +804,7 @@ PKG_CFG_ARGS = @PKG_CFG_ARGS@ PKG_DIR = ./pkgs packages: - @builddir=`pwd -P`; \ + @builddir=`$(CYGPATH) $$(pwd -P)`; \ for i in $(PKGS_DIR)/*; do \ if [ -d $$i ] ; then \ if [ -x $$i/configure ] ; then \ @@ -805,8 +812,8 @@ packages: mkdir -p $(PKG_DIR)/$$pkg; \ if [ ! -f $(PKG_DIR)/$$pkg/Makefile ]; then \ ( cd $(PKG_DIR)/$$pkg; \ - echo "Configuring package '$$i' wd = `pwd -P`"; \ - $$i/configure --with-tcl=$$builddir --with-tclinclude=$(GENERIC_DIR) $(PKG_CFG_ARGS) --enable-shared --enable-threads; ) \ + echo "Configuring package '$$i' wd = `$(CYGPATH) $$(pwd -P)`"; \ + $$i/configure --with-tcl=$$builddir --with-tclinclude=$(GENERIC_DIR_NATIVE) $(PKG_CFG_ARGS) --enable-shared --enable-threads; ) \ fi ; \ echo "Building package '$$pkg'"; \ ( cd $(PKG_DIR)/$$pkg; $(MAKE); ) \ diff --git a/win/buildall.vc.bat b/win/buildall.vc.bat index e4f0a30..deb9e39 100644 --- a/win/buildall.vc.bat +++ b/win/buildall.vc.bat @@ -1,103 +1,103 @@ -@echo off - -:: This is an example batchfile for building everything. Please -:: edit this (or make your own) for your needs and wants using -:: the instructions for calling makefile.vc found in makefile.vc - -set SYMBOLS= - -:OPTIONS -if "%1" == "/?" goto help -if /i "%1" == "/help" goto help -if %1.==symbols. goto SYMBOLS -if %1.==debug. goto SYMBOLS -goto OPTIONS_DONE - -:SYMBOLS - set SYMBOLS=symbols - shift - goto OPTIONS - -:OPTIONS_DONE - -:: reset errorlevel -cd > nul - -:: You might have installed your developer studio to add itself to the -:: path or have already run vcvars32.bat. Testing these envars proves -:: cl.exe and friends are in your path. -:: -if defined VCINSTALLDIR (goto :startBuilding) -if defined MSDEVDIR (goto :startBuilding) -if defined MSVCDIR (goto :startBuilding) -if defined MSSDK (goto :startBuilding) -if defined WINDOWSSDKDIR (goto :startBuilding) - -:: We need to run the development environment batch script that comes -:: with developer studio (v4,5,6,7,etc...) All have it. This path -:: might not be correct. You should call it yourself prior to running -:: this batchfile. -:: -call "C:\Program Files\Microsoft Developer Studio\vc98\bin\vcvars32.bat" -if errorlevel 1 (goto no_vcvars) - -:startBuilding - -echo. -echo Sit back and have a cup of coffee while this grinds through ;) -echo You asked for *everything*, remember? -echo. -title Building Tcl, please wait... - - -:: makefile.vc uses this for its default anyways, but show its use here -:: just to be explicit and convey understanding to the user. Setting -:: the INSTALLDIR envar prior to running this batchfile affects all builds. -:: -if "%INSTALLDIR%" == "" set INSTALLDIR=C:\Program Files\Tcl - - -:: Build the normal stuff along with the help file. -:: -set OPTS=none -if not %SYMBOLS%.==. set OPTS=symbols -nmake -nologo -f makefile.vc release htmlhelp OPTS=%OPTS% %1 -if errorlevel 1 goto error - -:: Build the static core and shell. -:: -set OPTS=static,msvcrt -if not %SYMBOLS%.==. set OPTS=symbols,static,msvcrt -nmake -nologo -f makefile.vc shell OPTS=%OPTS% %1 -if errorlevel 1 goto error - -set OPTS= -set SYMBOLS= -goto end - -:error -echo *** BOOM! *** -goto end - -:no_vcvars -echo vcvars32.bat was not run prior to this batchfile, nor are the MS tools in your path. -goto out - -:help -title buildall.vc.bat help message -echo usage: -echo %0 : builds Tcl for all build types (do this first) -echo %0 install : installs all the release builds (do this second) -echo %0 symbols : builds Tcl for all debugging build types -echo %0 symbols install : install all the debug builds. -echo. -goto out - -:end -title Building Tcl, please wait... DONE! -echo DONE! -goto out - -:out -pause -title Command Prompt +@echo off
+
+:: This is an example batchfile for building everything. Please
+:: edit this (or make your own) for your needs and wants using
+:: the instructions for calling makefile.vc found in makefile.vc
+
+set SYMBOLS=
+
+:OPTIONS
+if "%1" == "/?" goto help
+if /i "%1" == "/help" goto help
+if %1.==symbols. goto SYMBOLS
+if %1.==debug. goto SYMBOLS
+goto OPTIONS_DONE
+
+:SYMBOLS
+ set SYMBOLS=symbols
+ shift
+ goto OPTIONS
+
+:OPTIONS_DONE
+
+:: reset errorlevel
+cd > nul
+
+:: You might have installed your developer studio to add itself to the
+:: path or have already run vcvars32.bat. Testing these envars proves
+:: cl.exe and friends are in your path.
+::
+if defined VCINSTALLDIR (goto :startBuilding)
+if defined MSDEVDIR (goto :startBuilding)
+if defined MSVCDIR (goto :startBuilding)
+if defined MSSDK (goto :startBuilding)
+if defined WINDOWSSDKDIR (goto :startBuilding)
+
+:: We need to run the development environment batch script that comes
+:: with developer studio (v4,5,6,7,etc...) All have it. This path
+:: might not be correct. You should call it yourself prior to running
+:: this batchfile.
+::
+call "C:\Program Files\Microsoft Developer Studio\vc98\bin\vcvars32.bat"
+if errorlevel 1 (goto no_vcvars)
+
+:startBuilding
+
+echo.
+echo Sit back and have a cup of coffee while this grinds through ;)
+echo You asked for *everything*, remember?
+echo.
+title Building Tcl, please wait...
+
+
+:: makefile.vc uses this for its default anyways, but show its use here
+:: just to be explicit and convey understanding to the user. Setting
+:: the INSTALLDIR envar prior to running this batchfile affects all builds.
+::
+if "%INSTALLDIR%" == "" set INSTALLDIR=C:\Program Files\Tcl
+
+
+:: Build the normal stuff along with the help file.
+::
+set OPTS=none
+if not %SYMBOLS%.==. set OPTS=symbols
+nmake -nologo -f makefile.vc release htmlhelp OPTS=%OPTS% %1
+if errorlevel 1 goto error
+
+:: Build the static core and shell.
+::
+set OPTS=static,msvcrt
+if not %SYMBOLS%.==. set OPTS=symbols,static,msvcrt
+nmake -nologo -f makefile.vc shell OPTS=%OPTS% %1
+if errorlevel 1 goto error
+
+set OPTS=
+set SYMBOLS=
+goto end
+
+:error
+echo *** BOOM! ***
+goto end
+
+:no_vcvars
+echo vcvars32.bat was not run prior to this batchfile, nor are the MS tools in your path.
+goto out
+
+:help
+title buildall.vc.bat help message
+echo usage:
+echo %0 : builds Tcl for all build types (do this first)
+echo %0 install : installs all the release builds (do this second)
+echo %0 symbols : builds Tcl for all debugging build types
+echo %0 symbols install : install all the debug builds.
+echo.
+goto out
+
+:end
+title Building Tcl, please wait... DONE!
+echo DONE!
+goto out
+
+:out
+pause
+title Command Prompt
diff --git a/win/coffbase.txt b/win/coffbase.txt index bdf5506..0ebe18a 100644 --- a/win/coffbase.txt +++ b/win/coffbase.txt @@ -1,42 +1,42 @@ -; -; This file defines the virtual base addresses for the Dynamic Link Libraries -; that are part of the Tcl system. The first token on a line is the key (or name -; of the DLL) and the second token is the virtual base address, in hexidecimal. -; The third token is the maximum size of the DLL image file, including symbols. -; -; Using a specified "prefered load address" should speed loading time by avoiding -; relocations (NT supported only). It is assumed extension authors will contribute -; their modules to this grand-master list. You can use the dumpbin utility with -; the /headers option to get the "size of image" data (already in hex). If the -; maximum size is too small a linker warning will occur. Modules can overlap when -; they're mutually exclusive. This info is placed in the DLL's PE header by the -; linker with the `-base:@$(TCLDIR)\win\coffbase.txt,<key>` option. - -tcl 0x10000000 0x00200000 -tcldde 0x10200000 0x00010000 -tclreg 0x10210000 0x00010000 -tk 0x10220000 0x00200000 -expect 0x10480000 0x00080000 -itcl 0x10500000 0x00080000 -itk 0x10580000 0x00080000 -bltlite 0x10600000 0x00080000 -blt 0x10680000 0x00080000 -iocpsock 0x10700000 0x00080000 -tls 0x10780000 0x00100000 -winico 0x10880000 0x00010000 -sample 0x108B0000 0x00010000 -tile 0x10900000 0x00080000 -memchan 0x109D0000 0x00010000 -tdom 0x109E0000 0x00080000 -tclvfs 0x10A70000 0x00010000 -tkvideo 0x10B00000 0x00010000 -tclsdl 0x10B20000 0x00080000 -vqtcl 0x10C00000 0x00010000 -tdbc 0x10C40000 0x00010000 -thread 0x10C80000 0x00020000 -; -; insert new packages here -; -snack 0x1E000000 0x00400000 -sound 0x1E400000 0x00400000 -snackogg 0x1E800000 0x00200000 +;
+; This file defines the virtual base addresses for the Dynamic Link Libraries
+; that are part of the Tcl system. The first token on a line is the key (or name
+; of the DLL) and the second token is the virtual base address, in hexidecimal.
+; The third token is the maximum size of the DLL image file, including symbols.
+;
+; Using a specified "prefered load address" should speed loading time by avoiding
+; relocations (NT supported only). It is assumed extension authors will contribute
+; their modules to this grand-master list. You can use the dumpbin utility with
+; the /headers option to get the "size of image" data (already in hex). If the
+; maximum size is too small a linker warning will occur. Modules can overlap when
+; they're mutually exclusive. This info is placed in the DLL's PE header by the
+; linker with the `-base:@$(TCLDIR)\win\coffbase.txt,<key>` option.
+
+tcl 0x10000000 0x00200000
+tcldde 0x10200000 0x00010000
+tclreg 0x10210000 0x00010000
+tk 0x10220000 0x00200000
+expect 0x10480000 0x00080000
+itcl 0x10500000 0x00080000
+itk 0x10580000 0x00080000
+bltlite 0x10600000 0x00080000
+blt 0x10680000 0x00080000
+iocpsock 0x10700000 0x00080000
+tls 0x10780000 0x00100000
+winico 0x10880000 0x00010000
+sample 0x108B0000 0x00010000
+tile 0x10900000 0x00080000
+memchan 0x109D0000 0x00010000
+tdom 0x109E0000 0x00080000
+tclvfs 0x10A70000 0x00010000
+tkvideo 0x10B00000 0x00010000
+tclsdl 0x10B20000 0x00080000
+vqtcl 0x10C00000 0x00010000
+tdbc 0x10C40000 0x00010000
+thread 0x10C80000 0x00020000
+;
+; insert new packages here
+;
+snack 0x1E000000 0x00400000
+sound 0x1E400000 0x00400000
+snackogg 0x1E800000 0x00200000
diff --git a/win/configure b/win/configure index bdfa908..4ce23f9 100755 --- a/win/configure +++ b/win/configure @@ -3300,7 +3300,7 @@ do test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_CYGPATH="cygpath -w" + ac_cv_prog_CYGPATH="cygpath -m" echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -3587,7 +3587,7 @@ echo $ECHO_N "checking compiler flags... $ECHO_C" >&6 if test "${GCC}" = "yes" ; then SHLIB_LD="" SHLIB_LD_LIBS='${LIBS}' - LIBS="-lnetapi32 -lkernel32 -luser32 -ladvapi32 -lws2_32" + LIBS="-lnetapi32 -lkernel32 -luser32 -ladvapi32 -luserenv -lws2_32" # mingw needs to link ole32 and oleaut32 for [send], but MSVC doesn't LIBS_GUI="-lgdi32 -lcomdlg32 -limm32 -lcomctl32 -lshell32 -luuid -lole32 -loleaut32" STLIB_LD='${AR} cr' @@ -3757,6 +3757,13 @@ echo "${ECHO_T}using shared flags" >&6 # Add SHLIB_LD_LIBS to the Make rule, not here. LIBRARIES="\${SHARED_LIBRARIES}" EXESUFFIX="\${DBGX}.exe" + case "x`echo \${VisualStudioVersion}`" in + x1[4-9]*) + lflags="${lflags} -nodefaultlib:libucrt.lib" + ;; + *) + ;; + esac fi MAKE_DLL="\${SHLIB_LD} \$(LDFLAGS) -out:\$@" # DLLSUFFIX is separate because it is the building block for @@ -3796,7 +3803,16 @@ echo "${ECHO_T} Using 64-bit $MACHINE mode" >&6 fi fi - LIBS="netapi32.lib kernel32.lib user32.lib advapi32.lib ws2_32.lib" + LIBS="netapi32.lib kernel32.lib user32.lib advapi32.lib userenv.lib ws2_32.lib" + + case "x`echo \${VisualStudioVersion}`" in + x1[4-9]*) + LIBS="$LIBS ucrt.lib" + ;; + *) + ;; + esac + if test "$do64bit" != "no" ; then # The space-based-path will work for the Makefile, but will # not work if AC_TRY_COMPILE is called. TEA has the @@ -3871,7 +3887,7 @@ fi CFLAGS_DEBUG="-nologo -Zi -Od ${runtime}d" # Do not use -O2 for Win64 - this has proved buggy in code gen. CFLAGS_OPTIMIZE="-nologo -O1 ${runtime}" - lflags="-nologo -MACHINE:${MACHINE} -LIBPATH:\"${MSSDK}/Lib/${MACHINE}\"" + lflags="${lflags} -nologo -MACHINE:${MACHINE} -LIBPATH:\"${MSSDK}/Lib/${MACHINE}\"" LINKBIN="\"${PATH64}/link.exe\"" # Avoid 'unresolved external symbol __security_cookie' errors. # c.f. http://support.microsoft.com/?id=894573 @@ -3883,7 +3899,7 @@ fi CFLAGS_DEBUG="-nologo -Z7 -Od -WX ${runtime}d" # -O2 - create fast code (/Og /Oi /Ot /Oy /Ob2 /Gs /GF /Gy) CFLAGS_OPTIMIZE="-nologo -O2 ${runtime}" - lflags="-nologo" + lflags="${lflags} -nologo" LINKBIN="link" fi @@ -4364,12 +4380,12 @@ if test "$tcl_ok" = "yes"; then if test "$GCC" == "yes"; then - ZLIB_LIBS=\${ZLIB_DIR}/win64/libz.dll.a + ZLIB_LIBS=\${ZLIB_DIR_NATIVE}/win64/libz.dll.a else - ZLIB_LIBS=\${ZLIB_DIR}/win64/zdll.lib + ZLIB_LIBS=\${ZLIB_DIR_NATIVE}/win64/zdll.lib fi @@ -4377,7 +4393,7 @@ fi else - ZLIB_LIBS=\${ZLIB_DIR}/win32/zdll.lib + ZLIB_LIBS=\${ZLIB_DIR_NATIVE}/win32/zdll.lib fi diff --git a/win/configure.in b/win/configure.in index 99d78f2..9e9df90 100644 --- a/win/configure.in +++ b/win/configure.in @@ -130,12 +130,12 @@ AS_IF([test "$tcl_ok" = "yes"], [ AC_SUBST(ZLIB_DLL_FILE,[\${ZLIB_DLL_FILE}]) AS_IF([test "$do64bit" = "yes"], [ AS_IF([test "$GCC" == "yes"],[ - AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR}/win64/libz.dll.a]) + AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR_NATIVE}/win64/libz.dll.a]) ], [ - AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR}/win64/zdll.lib]) + AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR_NATIVE}/win64/zdll.lib]) ]) ], [ - AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR}/win32/zdll.lib]) + AC_SUBST(ZLIB_LIBS,[\${ZLIB_DIR_NATIVE}/win32/zdll.lib]) ]) ], [ AC_SUBST(ZLIB_OBJS,[\${ZLIB_OBJS}]) @@ -290,19 +290,19 @@ TCL_SHARED_LIB_SUFFIX="\${NODOT_VERSION}${DLLSUFFIX}" TCL_UNSHARED_LIB_SUFFIX="\${NODOT_VERSION}${LIBSUFFIX}" TCL_EXPORT_FILE_SUFFIX="\${NODOT_VERSION}${LIBSUFFIX}" -eval "TCL_SRC_DIR=\"`cd $srcdir/..; pwd`\"" +eval "TCL_SRC_DIR=\"`cd $srcdir/..; $CYGPATH $(pwd)`\"" eval "TCL_DLL_FILE=tcl${VER}${DLLSUFFIX}" eval "TCL_STUB_LIB_FILE=\"${LIBPREFIX}tclstub${VER}${LIBSUFFIX}\"" eval "TCL_STUB_LIB_FLAG=\"-ltclstub${VER}${LIBFLAGSUFFIX}\"" -eval "TCL_BUILD_STUB_LIB_SPEC=\"-L`pwd` ${TCL_STUB_LIB_FLAG}\"" +eval "TCL_BUILD_STUB_LIB_SPEC=\"-L`$CYGPATH $(pwd)` ${TCL_STUB_LIB_FLAG}\"" eval "TCL_STUB_LIB_SPEC=\"-L${libdir} ${TCL_STUB_LIB_FLAG}\"" -eval "TCL_BUILD_STUB_LIB_PATH=\"`pwd`/${TCL_STUB_LIB_FILE}\"" +eval "TCL_BUILD_STUB_LIB_PATH=\"`$CYGPATH $(pwd)`/${TCL_STUB_LIB_FILE}\"" eval "TCL_STUB_LIB_PATH=\"${libdir}/${TCL_STUB_LIB_FILE}\"" eval "TCL_LIB_FILE=\"${LIBPREFIX}tcl${VER}${LIBSUFFIX}\"" -eval "TCL_BUILD_LIB_SPEC=\"-L`pwd` -ltcl${VER}${FLAGSUFFIX}\"" +eval "TCL_BUILD_LIB_SPEC=\"-L`$CYGPATH $(pwd)` -ltcl${VER}${FLAGSUFFIX}\"" eval "TCL_LIB_SPEC=\"-L${libdir} -ltcl${VER}${FLAGSUFFIX}\"" # Install time header dir can be set via --includedir diff --git a/win/makefile.bc b/win/makefile.bc index 3f4ae52..f5b5acc 100644 --- a/win/makefile.bc +++ b/win/makefile.bc @@ -1,608 +1,594 @@ -# -# Makefile for Borland C++ 5.5 (or C++ Builder 5), adapted from the makefile -# for Visual C++ that came with tcl 8.3.3 -# -# See the file "license.terms" for information on usage and redistribution -# of this file, and for a DISCLAIMER OF ALL WARRANTIES. -# -# Copyright (c) 1995-1996 Sun Microsystems, Inc. -# Copyright (c) 1998-1999 by Scriptics Corporation. - -# TIP #59 information. -# -# This makefile does not set the following configuration cpp -# defines. Behind the defines are the makefile variables listed to set -# to -D... when that feature is enabled. -# -# - TCL_CFG_PROFILED PROFDEFINES -# - TCL_CFG_OPTIMIZED OPTDEFINES -# - TCL_CFG_DO64BIT SIXFOURDEFINES - -# Have a look at the complete description on how to build and test Tcl with -# the current Borland compilers at www.ratiosoft.com/tcl/borland. -# -# Usage: -# - Adapt the paths below to match your compiler's location -# - Make sure the compiler's bin directory is on your path -# - Open a console -# - To make a debug version enter -# make -fmakefile.bc -DNODEBUG=0 xxx -# where 'xxx' is the target you want (e.g. 'all', 'test', ...) -# Please note: I omitted the 'd' suffix for debug versions because Tcl -# will always call tclpip83.dll and not tclpip83d.dll, causing an error. -# ^ -# Besides, the debug version goes into a separate directory, so there -# should be no problem having DLLs and EXEs with the same name. -# If you prefer your debug version having the 'd' suffix just uncomment -# the line -# #DBGX = d -# -# - To make a 'normal' version enter -# make -fmakefile.bc xxx -# where 'xxx' is the target you want (e.g. 'all', 'test', ...) -# -# DISCLAIMER: -# This makefile has an experimental status - that is those targets which -# have been modified do in fact compile and link with Borland's C++ -# Builder 5 and with the free Borland compiler (Borland C++ 5.5). -# However the author assumes no responsiblity for any effect which the use of -# this makefile or of the resulting programs might have on your system. -# -# Not yet modified: -# - The 'plug-in-DLL' and the associated shell. -# -# Suggestions and / or improvements are always welcome. -# -# May 2001, H. Giese (hgiese@ratiosoft.com) -# - -# Does not depend on the presence of any environment variables in -# order to compile tcl; all needed information is derived from -# location of the compiler directories. - -# -# Project directories -# -# ROOT = top of source tree -# -# TOOLS32 = location of Borland development tools. -# -# INSTALLDIR = where the install-targets should copy the binaries and -# support files -# - -ROOT = .. -INSTALLDIR = c:\program files\tcl - -# If you have C++ Builder 5 or the free Borland C++ 5.5 compiler -# adapt the following paths as appropriate for your system -TOOLS32 = c:\dev\bcc55 -TOOLS32_rc = c:\dev\bcc55 -#TOOLS32 = c:\bc55 -#TOOLS32_rc = c:\bc55 - -cc32 = "$(TOOLS32)\bin\bcc32.exe" -link32 = "$(TOOLS32)\bin\ilink32.exe" -lib32 = "$(TOOLS32)\bin\tlib.exe" -rc32 = "$(TOOLS32_rc)\bin\brcc32.exe" -include32 = -I"$(TOOLS32)\include" -libpath32 = -L"$(TOOLS32)\lib" - -# Uncomment the following line to compile with thread support -#THREADDEFINES = -DTCL_THREADS=1 - -# Allow definition of NDEBUG via command line -# Set NODEBUG to 0 to compile with symbols -!if !defined(NODEBUG) -NODEBUG = 1 -!endif - -# CFG_ENCODING=encoding -# name of encoding for configuration information. Defaults -# to cp1252 -!if !defined(CFG_ENCODING) -CFG_ENCODING = \"cp1252\" -!endif - -# The following defines can be used to control the amount of debugging -# code that is added to the compilation. -# -# -DTCL_MEM_DEBUG Enables the debugging memory allocator. -# -DTCL_COMPILE_DEBUG Enables byte compilation logging. -# -DTCL_COMPILE_STATS Enables byte compilation statistics gathering. -# -DUSE_TCLALLOC=0 Disables the Tcl memory allocator in favor -# of the native malloc implementation. This is -# needed when using Purify. -# -#DEBUGDEFINES = -DTCL_MEM_DEBUG -DTCL_COMPILE_DEBUG -DTCL_COMPILE_STATS -#DEBUGDEFINES = -DUSE_TCLALLOC=0 - -###################################################################### -# Do not modify below this line -###################################################################### - -NAMEPREFIX = tcl -STUBPREFIX = $(NAMEPREFIX)stub -DOTVERSION = 8.6 -VERSION = 86 - -DDEVERSION = 14 -DDEDOTVERSION = 1.4 - -REGVERSION = 13 -REGDOTVERSION = 1.3 - -BINROOT = .. -!IF "$(NODEBUG)" == "1" -TMPDIRNAME = Release -DBGX = -SYMDEFINES = -DNDEBUG -!ELSE -TMPDIRNAME = Debug -#DBGX = d -DBGX = -SYMDEFINES = -DTCL_CFG_DEBUG -!ENDIF -TMPDIR = $(BINROOT)\$(TMPDIRNAME) -OUTDIRNAME = $(TMPDIRNAME) -OUTDIR = $(TMPDIR) - -TCLLIB = $(OUTDIR)\$(NAMEPREFIX)$(VERSION)$(DBGX).lib -TCLDLLNAME = $(NAMEPREFIX)$(VERSION)$(DBGX).dll -TCLDLL = $(OUTDIR)\$(TCLDLLNAME) - -TCLSTUBLIBNAME = $(STUBPREFIX)$(VERSION)$(DBGX).lib -TCLSTUBLIB = $(OUTDIR)\$(TCLSTUBLIBNAME) - -TCLPLUGINLIB = $(OUTDIR)\$(NAMEPREFIX)$(VERSION)p$(DBGX).lib -TCLPLUGINDLLNAME = $(NAMEPREFIX)$(VERSION)p$(DBGX).dll -TCLPLUGINDLL = $(OUTDIR)\$(TCLPLUGINDLLNAME) -TCLSH = $(OUTDIR)\$(NAMEPREFIX)sh$(VERSION)$(DBGX).exe -TCLSHP = $(OUTDIR)\$(NAMEPREFIX)shp$(VERSION)$(DBGX).exe -TCLKIT = $(OUTDIR)\$(NAMEPREFIX)kit$(VERSION)$(DBGX).exe -TCLREGDLLNAME = $(NAMEPREFIX)reg$(REGVERSION)$(DBGX).dll -TCLREGDLL = $(OUTDIR)\$(TCLREGDLLNAME) -TCLDDEDLLNAME = $(NAMEPREFIX)dde$(DDEVERSION)$(DBGX).dll -TCLDDEDLL = $(OUTDIR)\$(TCLDDEDLLNAME) -TCLTEST = $(OUTDIR)\$(NAMEPREFIX)test.exe -CAT32 = $(TMPDIR)\cat32.exe -RMDIR = .\rmd.bat -MKDIR = .\mkd.bat -RM = del - -LIB_INSTALL_DIR = $(INSTALLDIR)\lib -BIN_INSTALL_DIR = $(INSTALLDIR)\bin -SCRIPT_INSTALL_DIR = $(INSTALLDIR)\lib\tcl$(DOTVERSION) -INCLUDE_INSTALL_DIR = $(INSTALLDIR)\include - -TCLSHOBJS = \ - $(TMPDIR)\tclAppInit.obj - -TCLKITOBJS = \ - $(TMP_DIR)\tclZipVfs.obj \ - $(TMPDIR)\tclKitInit.obj - -TCLTESTOBJS = \ - $(TMPDIR)\tclTest.obj \ - $(TMPDIR)\tclTestObj.obj \ - $(TMPDIR)\tclTestProcBodyObj.obj \ - $(TMPDIR)\tclThreadTest.obj \ - $(TMPDIR)\tclWinTest.obj \ - $(TMPDIR)\testMain.obj - -TCLOBJS = \ - $(TMPDIR)\regcomp.obj \ - $(TMPDIR)\regexec.obj \ - $(TMPDIR)\regfree.obj \ - $(TMPDIR)\regerror.obj \ - $(TMPDIR)\tclAlloc.obj \ - $(TMPDIR)\tclAsync.obj \ - $(TMPDIR)\tclBasic.obj \ - $(TMPDIR)\tclBinary.obj \ - $(TMPDIR)\tclCkalloc.obj \ - $(TMPDIR)\tclClock.obj \ - $(TMPDIR)\tclCmdAH.obj \ - $(TMPDIR)\tclCmdIL.obj \ - $(TMPDIR)\tclCmdMZ.obj \ - $(TMPDIR)\tclCompCmds.obj \ - $(TMPDIR)\tclCompCmdsGR.obj \ - $(TMPDIR)\tclCompCmdsSZ.obj \ - $(TMPDIR)\tclCompExpr.obj \ - $(TMPDIR)\tclCompile.obj \ - $(TMPDIR)\tclConfig.obj \ - $(TMPDIR)\tclDate.obj \ - $(TMPDIR)\tclDictObj.obj \ - $(TMPDIR)\tclDisassemble.obj \ - $(TMPDIR)\tclEncoding.obj \ - $(TMPDIR)\tclEnsemble.obj \ - $(TMPDIR)\tclEnv.obj \ - $(TMPDIR)\tclEvent.obj \ - $(TMPDIR)\tclExecute.obj \ - $(TMPDIR)\tclFCmd.obj \ - $(TMPDIR)\tclFileName.obj \ - $(TMPDIR)\tclGet.obj \ - $(TMPDIR)\tclHash.obj \ - $(TMPDIR)\tclHistory.obj \ - $(TMPDIR)\tclIndexObj.obj \ - $(TMPDIR)\tclInterp.obj \ - $(TMPDIR)\tclIO.obj \ - $(TMPDIR)\tclIOCmd.obj \ - $(TMPDIR)\tclIOGT.obj \ - $(TMPDIR)\tclIOSock.obj \ - $(TMPDIR)\tclIOUtil.obj \ - $(TMPDIR)\tclLink.obj \ - $(TMPDIR)\tclLiteral.obj \ - $(TMPDIR)\tclListObj.obj \ - $(TMPDIR)\tclLoad.obj \ - $(TMPDIR)\tclMain.obj \ - $(TMPDIR)\tclNamesp.obj \ - $(TMPDIR)\tclNotify.obj \ - $(TMPDIR)\tclOO.obj \ - $(TMPDIR)\tclOOBasic.obj \ - $(TMPDIR)\tclOOCall.obj \ - $(TMPDIR)\tclOODefineCmds.obj \ - $(TMPDIR)\tclOOInfo.obj \ - $(TMPDIR)\tclOOMethod.obj \ - $(TMPDIR)\tclOOStubInit.obj \ - $(TMPDIR)\tclObj.obj \ - $(TMPDIR)\tclOptimize.obj \ - $(TMPDIR)\tclPanic.obj \ - $(TMPDIR)\tclParse.obj \ - $(TMPDIR)\tclPipe.obj \ - $(TMPDIR)\tclPkg.obj \ - $(TMPDIR)\tclPkgConfig.obj \ - $(TMPDIR)\tclPosixStr.obj \ - $(TMPDIR)\tclPreserve.obj \ - $(TMPDIR)\tclProc.obj \ - $(TMPDIR)\tclRegexp.obj \ - $(TMPDIR)\tclResolve.obj \ - $(TMPDIR)\tclResult.obj \ - $(TMPDIR)\tclScan.obj \ - $(TMPDIR)\tclStringObj.obj \ - $(TMPDIR)\tclStubInit.obj \ - $(TMPDIR)\tclThread.obj \ - $(TMPDIR)\tclThreadJoin.obj \ - $(TMPDIR)\tclTimer.obj \ - $(TMPDIR)\tclTrace.obj \ - $(TMPDIR)\tclUtf.obj \ - $(TMPDIR)\tclUtil.obj \ - $(TMPDIR)\tclVar.obj \ - $(TMPDIR)\tclWin32Dll.obj \ - $(TMPDIR)\tclWinChan.obj \ - $(TMPDIR)\tclWinConsole.obj \ - $(TMPDIR)\tclWinSerial.obj \ - $(TMPDIR)\tclWinError.obj \ - $(TMPDIR)\tclWinFCmd.obj \ - $(TMPDIR)\tclWinFile.obj \ - $(TMPDIR)\tclWinInit.obj \ - $(TMPDIR)\tclWinLoad.obj \ - $(TMPDIR)\tclWinNotify.obj \ - $(TMPDIR)\tclWinPipe.obj \ - $(TMPDIR)\tclWinSock.obj \ - $(TMPDIR)\tclWinThrd.obj \ - $(TMPDIR)\tclWinTime.obj \ - $(TMPDIR)\tclZlib.obj - -TCLSTUBOBJS = \ - $(TMPDIR)\tclStubLib.obj \ - $(TMPDIR)\tclTomMathStubLib.obj \ - $(TMPDIR)\tclOOStubLib.obj - -WINDIR = $(ROOT)\win -GENERICDIR = $(ROOT)\generic - -TCL_INCLUDES = -I"$(WINDIR)" -I"$(GENERICDIR)" -TCL_DEFINES = $(DEBUGDEFINES) $(THREADDEFINES) $(SYMDEFINES) \ - $(PROFDEFINES) $(OPTDEFINES) $(SIXFOURDEFINES) \ - -DTCL_CFGVAL_ENCODING=${CFG_ENCODING} -### TODO: Add -DHAVE_ZLIB=1 - -###################################################################### -# Compiler flags -###################################################################### - -!IF "$(NODEBUG)" == "1" -# these macros cause maximum optimization and no symbols -cdebug = -v- -vi- -O2 -D_DEBUG -!ELSE -# these macros enable debugging -cdebug = -k -Od -r- -v -vi- -y -!ENDIF - -SYSDEFINES = _MT;NO_STRICT;_NO_VCL - -# declarations common to all compiler options -cbase = -c -q -3 -a4 -g0 -tWM -Ve -Vx -X- -WARNINGS = -w-rch -w-pch -w-par -w-dup -w-pro -w-dpu - -ccons = -tWC - -INCLUDEPATH = $(include32) $(TCL_INCLUDES) - -CFLAGS = $(cdebug) $(cbase) $(INCLUDEPATH) $(WARNINGS) -D$(SYSDEFINES) -TCL_CFLAGS = $(CFLAGS) $(TCL_DEFINES) -CONS_CFLAGS = $(CFLAGS) $(TCL_DEFINES) $(ccons) - -###################################################################### -# Linker flags -###################################################################### - -!IF "$(NODEBUG)" == "1" -ldebug = -!ELSE -ldebug = -v -!ENDIF - -# declarations common to all linker options -LNFLAGS = -D"" -Gn -I$(TMPDIR) -x $(ldebug) $(libpath32) -# -Gi: create lib file (is -Gl in doc) -# -aa: Windows app, -ap: Windows console app -LNFLAGS_DLL = -ap -Gi -Tpd -LNFLAGS_CONS = -ap -Tpe - -LNLIBS = import32 cw32mt - - -###################################################################### -# Project specific targets -###################################################################### - -release: setup $(TCLSH) dlls -dlls: setup $(TCLREGDLL) $(TCLDDEDLL) -all: setup $(TCLSH) dlls $(CAT32) -tcltest: setup $(TCLTEST) dlls $(CAT32) -plugin: setup $(TCLPLUGINDLL) $(TCLSHP) -install: install-binaries install-libraries - -test: setup $(TCLTEST) dlls $(CAT32) - set TCL_LIBRARY=$(ROOT)/library - $(TCLTEST) $(ROOT)/tests/all.tcl - -setup: - @if not exist $(OUT_DIR)\nul mkdir $(OUT_DIR) &\ - echo *** Created directory '$(OUT_DIR)' - @if not exist $(TMP_DIR)\nul mkdir $(TMP_DIR) &\ - echo *** Created directory '$(TMP_DIR)' - - -$(TCLLIB): $(TCLDLL) - -$(TCLDLL): $(TCLOBJS) $(TMPDIR)\$(NAMEPREFIX).res - $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 @&&! - $(TCLOBJS), $@, -x, $(LNLIBS),, $(TMPDIR)\$(NAMEPREFIX).res -! - -$(TCLSTUBLIB): $(TCLSTUBOBJS) - $(lib32) /u $@ $(TCLSTUBOBJS) - -$(TCLPLUGINLIB): $(TCLPLUGINDLL) - -$(TCLPLUGINDLL): $(TCLOBJS) $(TMPDIR)\tcl.res - $(link32) $(ldebug) $(dlllflags) \ - -out:$@ $(TMPDIR)\tcl.res $(guilibsdll) @&&! -$(TCLOBJS) -! - -$(TCLSH): $(TCLSHOBJS) $(TCLLIB) $(TMPDIR)\$(NAMEPREFIX)sh.res - $(link32) $(ldebug) -S:2400000 $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 @&&! - $(TCLSHOBJS), $@, -x, $(LNLIBS) $(TCLLIB),, $(TMPDIR)\$(NAMEPREFIX)sh.res -! - -$(TCLSHP): $(TCLSHOBJS) $(TCLPLUGINLIB) $(TMPDIR)\tclsh.res - $(link32) $(ldebug) $(conlflags) $(TMPDIR)\tclsh.res -stack:2300000 \ - -out:$@ $(conlibsdll) $(TCLPLUGINLIB) $(TCLSHOBJS) - -$(TCLTEST): $(TCLTESTOBJS) $(TCLLIB) $(TMPDIR)\$(NAMEPREFIX)sh.res - $(link32) $(ldebug) -S:2400000 $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 @&&! - $(TCLTESTOBJS), $@, -x, $(LNLIBS) $(TCLLIB),, $(TMPDIR)\$(NAMEPREFIX)sh.res -! - -$(TCLKIT): $(TCLKITOBJS) $(TCLLIB) $(TMPDIR)\$(NAMEPREFIX)sh.res - $(link32) $(ldebug) -S:2400000 $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 @&&! - $(TCLSHOBJS), $@, -x, $(LNLIBS) $(TCLLIB),, $(TMPDIR)\$(NAMEPREFIX)sh.res -! - -$(TCLDDEDLL): $(TMPDIR)\tclWinDde.obj $(TCLSTUBLIB) - $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 \ - $(TMPDIR)\tclWinDde.obj, $@, -x, $(LNLIBS) $(TCLSTUBLIB),, \ - $(TMPDIR)\$(NAMEPREFIX).res - -$(TCLREGDLL): $(TMPDIR)\tclWinReg.obj $(TCLSTUBLIB) - $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 \ - $(TMPDIR)\tclWinReg.obj, $@, -x, $(LNLIBS) $(TCLSTUBLIB),, \ - $(TMPDIR)\$(NAMEPREFIX).res - -$(CAT32): $(WINDIR)\cat.c - $(cc32) $(CONS_CFLAGS) -o$(TMPDIR)\cat.obj $? - $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 \ - $(TMPDIR)\cat.obj, $@, -x, $(LNLIBS),, - -install-binaries: $(TCLSH) - $(MKDIR) "$(BIN_INSTALL_DIR)" - $(MKDIR) "$(LIB_INSTALL_DIR)" - @echo Installing $(TCLDLLNAME) - @copy "$(TCLDLL)" "$(BIN_INSTALL_DIR)" - @copy "$(TCLLIB)" "$(LIB_INSTALL_DIR)" - @echo Installing "$(TCLSH)" - @copy "$(TCLSH)" "$(BIN_INSTALL_DIR)" - @echo Installing $(TCLSTUBLIBNAME) - @copy "$(TCLSTUBLIB)" "$(LIB_INSTALL_DIR)" - @echo Installing $(WINDIR)\tclooConfig.sh - @copy "$(WINDIR)\tclooConfig.sh" "$(LIB_INSTALL_DIR)" - -install-libraries: - -@$(MKDIR) "$(LIB_INSTALL_DIR)" - -@$(MKDIR) "$(INCLUDE_INSTALL_DIR)" - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)" - @echo Installing http1.0 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\http1.0" - -@copy "$(ROOT)\library\http1.0\http.tcl" "$(SCRIPT_INSTALL_DIR)\http1.0" - -@copy "$(ROOT)\library\http1.0\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\http1.0" - @echo Installing http2.8 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\http2.8" - -@copy "$(ROOT)\library\http\http.tcl" "$(SCRIPT_INSTALL_DIR)\http2.8" - -@copy "$(ROOT)\library\http\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\http2.8" - @echo Installing opt0.4 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\opt0.4" - -@copy "$(ROOT)\library\opt\optparse.tcl" "$(SCRIPT_INSTALL_DIR)\opt0.4" - -@copy "$(ROOT)\library\opt\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\opt0.4" - @echo Installing msgcat1.5 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\msgcat1.5" - -@copy "$(ROOT)\library\msgcat\msgcat.tcl" "$(SCRIPT_INSTALL_DIR)\msgcat1.5" - -@copy "$(ROOT)\library\msgcat\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\msgcat1.5" - @echo Installing tcltest2.3 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\tcltest2.3" - -@copy "$(ROOT)\library\tcltest\tcltest.tcl" "$(SCRIPT_INSTALL_DIR)\tcltest2.3" - -@copy "$(ROOT)\library\tcltest\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\tcltest2.3" - @echo Installing platform1.0 - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\platform1.0" - -@copy "$(ROOT)\library\platform\platform.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0" - -@copy "$(ROOT)\library\platform\shell.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0" - -@copy "$(ROOT)\library\platform\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0" - @echo Installing $(TCLDDEDLLNAME) - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\dde1.3" - -@copy "$(TCLDDEDLL)" "$(SCRIPT_INSTALL_DIR)\dde1.3" - -@copy "$(ROOT)\library\dde\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\dde1.3" - @echo Installing $(TCLREGDLLNAME) - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\reg1.2" - -@copy "$(TCLREGDLL)" "$(SCRIPT_INSTALL_DIR)\reg1.3" - -@copy "$(ROOT)\library\reg\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\reg1.2" - @echo Installing encoding files - -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\encoding" - -@copy "$(ROOT)\library\encoding\*.enc" "$(SCRIPT_INSTALL_DIR)\encoding" - @echo Installing library files - -@copy "$(GENERICDIR)\tcl.h" "$(INCLUDE_INSTALL_DIR)" - -@copy "$(GENERICDIR)\tclDecls.h" "$(INCLUDE_INSTALL_DIR)" - -@copy "$(GENERICDIR)\tclOO.h" "$(INCLUDE_INSTALL_DIR)" - -@copy "$(GENERICDIR)\tclOODecls.h" "$(INCLUDE_INSTALL_DIR)" - -@copy "$(GENERICDIR)\tclPlatDecls.h" "$(INCLUDE_INSTALL_DIR)" - -@copy "$(ROOT)\library\history.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\init.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\parray.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\safe.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\tclIndex" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\package.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\word.tcl" "$(SCRIPT_INSTALL_DIR)" - -@copy "$(ROOT)\library\auto.tcl" "$(SCRIPT_INSTALL_DIR)" - -# -# Regenerate the stubs files. -# - -genstubs: - tclsh$(VERSION) $(ROOT)\tools\genStubs.tcl $(GENERICDIR) \ - $(GENERICDIR)\tcl.decls $(GENERICDIR)\tclInt.decls - -# -# Special case object file targets -# -$(TMPDIR)\tclWinInit.obj: $(WINDIR)\tclWinInit.c - $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$(TMPDIR)\$@ $? - -$(TMPDIR)\testMain.obj: $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) -DTCL_TEST -o$(TMPDIR)\testMain.obj $? - -$(TMPDIR)\tclTest.obj: $(GENERICDIR)\tclTest.c - $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclTestObj.obj: $(GENERICDIR)\tclTestObj.c - $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclWinTest.obj: $(WINDIR)\tclWinTest.c - $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $? - -$(TMP_DIR)\tclPkgConfig.obj: $(GENERICDIR)\tclPkgConfig.c - $(cc32) $(TCL_CFLAGS) \ - -DCFG_INSTALL_EXEC_PREFIX=\"$(INSTALL_EXEC_PREFIX)\" \ - -DCFG_INSTALL_PREFIX=\"$(INSTALL_PREFIX)\" \ - -DCFG_RUNTIME_EXEC_PREFIX=\"$(RUNTIME_EXEC_PREFIX)\" \ - -DCFG_RUNTIME_PREFIX=\"$(RUNTIME_PREFIX)\" \ - -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclAppInit.obj : $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclKitInit.obj : $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) -DDTCL_ZIPVFS -o$(TMPDIR)\$@ $? - - -# The following objects should be built using the stub interfaces - -# tclWinReg: Produces errors in ANSI mode -$(TMPDIR)\tclWinReg.obj : $(WINDIR)\tclWinReg.c - $(cc32) $(TCL_CFLAGS) -DUSE_TCL_STUBS -o$(TMPDIR)\$@ $? - -# tclWinDde: Produces errors in ANSI mode -$(TMPDIR)\tclWinDde.obj : $(WINDIR)\tclWinDde.c - $(cc32) $(TCL_CFLAGS) -DUSE_TCL_STUBS -o$(TMPDIR)\$@ $? - - -# The following objects are part of the stub library and should not -# be built as DLL objects but none of the symbols should be exported - -$(TMPDIR)\tclStubLib.obj : $(GENERICDIR)\tclStubLib.c - $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclTomMathStubLib.obj : $(GENERICDIR)\tclTomMathStubLib.c - $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $? - -$(TMPDIR)\tclOOStubLib.obj : $(GENERICDIR)\tclOOStubLib.c - $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $? - - -# Dedependency rules - -$(GENERICDIR)\regcomp.c: \ - $(GENERICDIR)\regguts.h \ - $(GENERICDIR)\regc_lex.c \ - $(GENERICDIR)\regc_color.c \ - $(GENERICDIR)\regc_nfa.c \ - $(GENERICDIR)\regc_cvec.c \ - $(GENERICDIR)\regc_locale.c - -$(GENERICDIR)\regcustom.h: \ - $(GENERICDIR)\tclInt.h \ - $(GENERICDIR)\tclPort.h \ - $(GENERICDIR)\regex.h - -$(GENERICDIR)\regexec.c: \ - $(GENERICDIR)\rege_dfa.c \ - $(GENERICDIR)\regguts.h - -$(GENERICDIR)\regerror.c: $(GENERICDIR)\regguts.h -$(GENERICDIR)\regfree.c: $(GENERICDIR)\regguts.h -$(GENERICDIR)\regfronts.c: $(GENERICDIR)\regguts.h -$(GENERICDIR)\regguts.h: $(GENERICDIR)\regcustom.h - -# -# Implicit rules -# - -{$(WINDIR)}.c{$(TMPDIR)}.obj: - $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $< - -{$(GENERICDIR)}.c{$(TMPDIR)}.obj: - $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $< - -{$(ROOT)\compat}.c{$(TMPDIR)}.obj: - $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $< - -{$(WINDIR)}.rc{$(TMPDIR)}.res: - $(rc32) $(INCLUDEPATH) -D$(USERDEFINES);$(SYSDEFINES) -fo$@ $< - -clean: - -@$(RM) $(OUTDIR)\*.exp - -@$(RM) $(OUTDIR)\*.lib - -@$(RM) $(OUTDIR)\*.dll - -@$(RM) $(OUTDIR)\*.exe - -@$(RM) $(OUTDIR)\*.pdb - -@$(RM) $(TMPDIR)\*.pch - -@$(RM) $(TMPDIR)\*.obj - -@$(RM) $(TMPDIR)\*.res - -@$(RM) $(TMPDIR)\*.exe - -@$(RMDIR) $(OUTDIR) - -@$(RMDIR) $(TMPDIR) - -# Local Variables: -# mode: makefile -# End: +#
+# Makefile for Borland C++ 5.5 (or C++ Builder 5), adapted from the makefile
+# for Visual C++ that came with tcl 8.3.3
+#
+# See the file "license.terms" for information on usage and redistribution
+# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
+#
+# Copyright (c) 1995-1996 Sun Microsystems, Inc.
+# Copyright (c) 1998-1999 by Scriptics Corporation.
+
+# TIP #59 information.
+#
+# This makefile does not set the following configuration cpp
+# defines. Behind the defines are the makefile variables listed to set
+# to -D... when that feature is enabled.
+#
+# - TCL_CFG_PROFILED PROFDEFINES
+# - TCL_CFG_OPTIMIZED OPTDEFINES
+# - TCL_CFG_DO64BIT SIXFOURDEFINES
+
+# Have a look at the complete description on how to build and test Tcl with
+# the current Borland compilers at www.ratiosoft.com/tcl/borland.
+#
+# Usage:
+# - Adapt the paths below to match your compiler's location
+# - Make sure the compiler's bin directory is on your path
+# - Open a console
+# - To make a debug version enter
+# make -fmakefile.bc -DNODEBUG=0 xxx
+# where 'xxx' is the target you want (e.g. 'all', 'test', ...)
+# Please note: I omitted the 'd' suffix for debug versions because Tcl
+# will always call tclpip83.dll and not tclpip83d.dll, causing an error.
+# ^
+# Besides, the debug version goes into a separate directory, so there
+# should be no problem having DLLs and EXEs with the same name.
+# If you prefer your debug version having the 'd' suffix just uncomment
+# the line
+# #DBGX = d
+#
+# - To make a 'normal' version enter
+# make -fmakefile.bc xxx
+# where 'xxx' is the target you want (e.g. 'all', 'test', ...)
+#
+# DISCLAIMER:
+# This makefile has an experimental status - that is those targets which
+# have been modified do in fact compile and link with Borland's C++
+# Builder 5 and with the free Borland compiler (Borland C++ 5.5).
+# However the author assumes no responsiblity for any effect which the use of
+# this makefile or of the resulting programs might have on your system.
+#
+# Not yet modified:
+# - The 'plug-in-DLL' and the associated shell.
+#
+# Suggestions and / or improvements are always welcome.
+#
+# May 2001, H. Giese (hgiese@ratiosoft.com)
+#
+
+# Does not depend on the presence of any environment variables in
+# order to compile tcl; all needed information is derived from
+# location of the compiler directories.
+
+#
+# Project directories
+#
+# ROOT = top of source tree
+#
+# TOOLS32 = location of Borland development tools.
+#
+# INSTALLDIR = where the install-targets should copy the binaries and
+# support files
+#
+
+ROOT = ..
+INSTALLDIR = c:\program files\tcl
+
+# If you have C++ Builder 5 or the free Borland C++ 5.5 compiler
+# adapt the following paths as appropriate for your system
+TOOLS32 = c:\dev\bcc55
+TOOLS32_rc = c:\dev\bcc55
+#TOOLS32 = c:\bc55
+#TOOLS32_rc = c:\bc55
+
+cc32 = "$(TOOLS32)\bin\bcc32.exe"
+link32 = "$(TOOLS32)\bin\ilink32.exe"
+lib32 = "$(TOOLS32)\bin\tlib.exe"
+rc32 = "$(TOOLS32_rc)\bin\brcc32.exe"
+include32 = -I"$(TOOLS32)\include"
+libpath32 = -L"$(TOOLS32)\lib"
+
+# Uncomment the following line to compile with thread support
+#THREADDEFINES = -DTCL_THREADS=1
+
+# Allow definition of NDEBUG via command line
+# Set NODEBUG to 0 to compile with symbols
+!if !defined(NODEBUG)
+NODEBUG = 1
+!endif
+
+# CFG_ENCODING=encoding
+# name of encoding for configuration information. Defaults
+# to cp1252
+!if !defined(CFG_ENCODING)
+CFG_ENCODING = \"cp1252\"
+!endif
+
+# The following defines can be used to control the amount of debugging
+# code that is added to the compilation.
+#
+# -DTCL_MEM_DEBUG Enables the debugging memory allocator.
+# -DTCL_COMPILE_DEBUG Enables byte compilation logging.
+# -DTCL_COMPILE_STATS Enables byte compilation statistics gathering.
+# -DUSE_TCLALLOC=0 Disables the Tcl memory allocator in favor
+# of the native malloc implementation. This is
+# needed when using Purify.
+#
+#DEBUGDEFINES = -DTCL_MEM_DEBUG -DTCL_COMPILE_DEBUG -DTCL_COMPILE_STATS
+#DEBUGDEFINES = -DUSE_TCLALLOC=0
+
+######################################################################
+# Do not modify below this line
+######################################################################
+
+NAMEPREFIX = tcl
+STUBPREFIX = $(NAMEPREFIX)stub
+DOTVERSION = 8.6
+VERSION = 86
+
+DDEVERSION = 14
+DDEDOTVERSION = 1.4
+
+REGVERSION = 13
+REGDOTVERSION = 1.3
+
+BINROOT = ..
+!IF "$(NODEBUG)" == "1"
+TMPDIRNAME = Release
+DBGX =
+SYMDEFINES = -DNDEBUG
+!ELSE
+TMPDIRNAME = Debug
+#DBGX = d
+DBGX =
+SYMDEFINES = -DTCL_CFG_DEBUG
+!ENDIF
+TMPDIR = $(BINROOT)\$(TMPDIRNAME)
+OUTDIRNAME = $(TMPDIRNAME)
+OUTDIR = $(TMPDIR)
+
+TCLLIB = $(OUTDIR)\$(NAMEPREFIX)$(VERSION)$(DBGX).lib
+TCLDLLNAME = $(NAMEPREFIX)$(VERSION)$(DBGX).dll
+TCLDLL = $(OUTDIR)\$(TCLDLLNAME)
+
+TCLSTUBLIBNAME = $(STUBPREFIX)$(VERSION)$(DBGX).lib
+TCLSTUBLIB = $(OUTDIR)\$(TCLSTUBLIBNAME)
+
+TCLPLUGINLIB = $(OUTDIR)\$(NAMEPREFIX)$(VERSION)p$(DBGX).lib
+TCLPLUGINDLLNAME = $(NAMEPREFIX)$(VERSION)p$(DBGX).dll
+TCLPLUGINDLL = $(OUTDIR)\$(TCLPLUGINDLLNAME)
+TCLSH = $(OUTDIR)\$(NAMEPREFIX)sh$(VERSION)$(DBGX).exe
+TCLSHP = $(OUTDIR)\$(NAMEPREFIX)shp$(VERSION)$(DBGX).exe
+TCLREGDLLNAME = $(NAMEPREFIX)reg$(REGVERSION)$(DBGX).dll
+TCLREGDLL = $(OUTDIR)\$(TCLREGDLLNAME)
+TCLDDEDLLNAME = $(NAMEPREFIX)dde$(DDEVERSION)$(DBGX).dll
+TCLDDEDLL = $(OUTDIR)\$(TCLDDEDLLNAME)
+TCLTEST = $(OUTDIR)\$(NAMEPREFIX)test.exe
+CAT32 = $(TMPDIR)\cat32.exe
+RMDIR = .\rmd.bat
+MKDIR = .\mkd.bat
+RM = del
+
+LIB_INSTALL_DIR = $(INSTALLDIR)\lib
+BIN_INSTALL_DIR = $(INSTALLDIR)\bin
+SCRIPT_INSTALL_DIR = $(INSTALLDIR)\lib\tcl$(DOTVERSION)
+INCLUDE_INSTALL_DIR = $(INSTALLDIR)\include
+
+TCLSHOBJS = \
+ $(TMPDIR)\tclAppInit.obj
+
+TCLTESTOBJS = \
+ $(TMPDIR)\tclTest.obj \
+ $(TMPDIR)\tclTestObj.obj \
+ $(TMPDIR)\tclTestProcBodyObj.obj \
+ $(TMPDIR)\tclThreadTest.obj \
+ $(TMPDIR)\tclWinTest.obj \
+ $(TMPDIR)\testMain.obj
+
+TCLOBJS = \
+ $(TMPDIR)\regcomp.obj \
+ $(TMPDIR)\regexec.obj \
+ $(TMPDIR)\regfree.obj \
+ $(TMPDIR)\regerror.obj \
+ $(TMPDIR)\tclAlloc.obj \
+ $(TMPDIR)\tclAsync.obj \
+ $(TMPDIR)\tclBasic.obj \
+ $(TMPDIR)\tclBinary.obj \
+ $(TMPDIR)\tclCkalloc.obj \
+ $(TMPDIR)\tclClock.obj \
+ $(TMPDIR)\tclCmdAH.obj \
+ $(TMPDIR)\tclCmdIL.obj \
+ $(TMPDIR)\tclCmdMZ.obj \
+ $(TMPDIR)\tclCompCmds.obj \
+ $(TMPDIR)\tclCompCmdsGR.obj \
+ $(TMPDIR)\tclCompCmdsSZ.obj \
+ $(TMPDIR)\tclCompExpr.obj \
+ $(TMPDIR)\tclCompile.obj \
+ $(TMPDIR)\tclConfig.obj \
+ $(TMPDIR)\tclDate.obj \
+ $(TMPDIR)\tclDictObj.obj \
+ $(TMPDIR)\tclDisassemble.obj \
+ $(TMPDIR)\tclEncoding.obj \
+ $(TMPDIR)\tclEnsemble.obj \
+ $(TMPDIR)\tclEnv.obj \
+ $(TMPDIR)\tclEvent.obj \
+ $(TMPDIR)\tclExecute.obj \
+ $(TMPDIR)\tclFCmd.obj \
+ $(TMPDIR)\tclFileName.obj \
+ $(TMPDIR)\tclGet.obj \
+ $(TMPDIR)\tclHash.obj \
+ $(TMPDIR)\tclHistory.obj \
+ $(TMPDIR)\tclIndexObj.obj \
+ $(TMPDIR)\tclInterp.obj \
+ $(TMPDIR)\tclIO.obj \
+ $(TMPDIR)\tclIOCmd.obj \
+ $(TMPDIR)\tclIOGT.obj \
+ $(TMPDIR)\tclIOSock.obj \
+ $(TMPDIR)\tclIOUtil.obj \
+ $(TMPDIR)\tclLink.obj \
+ $(TMPDIR)\tclLiteral.obj \
+ $(TMPDIR)\tclListObj.obj \
+ $(TMPDIR)\tclLoad.obj \
+ $(TMPDIR)\tclMain.obj \
+ $(TMPDIR)\tclNamesp.obj \
+ $(TMPDIR)\tclNotify.obj \
+ $(TMPDIR)\tclOO.obj \
+ $(TMPDIR)\tclOOBasic.obj \
+ $(TMPDIR)\tclOOCall.obj \
+ $(TMPDIR)\tclOODefineCmds.obj \
+ $(TMPDIR)\tclOOInfo.obj \
+ $(TMPDIR)\tclOOMethod.obj \
+ $(TMPDIR)\tclOOStubInit.obj \
+ $(TMPDIR)\tclObj.obj \
+ $(TMPDIR)\tclOptimize.obj \
+ $(TMPDIR)\tclPanic.obj \
+ $(TMPDIR)\tclParse.obj \
+ $(TMPDIR)\tclPipe.obj \
+ $(TMPDIR)\tclPkg.obj \
+ $(TMPDIR)\tclPkgConfig.obj \
+ $(TMPDIR)\tclPosixStr.obj \
+ $(TMPDIR)\tclPreserve.obj \
+ $(TMPDIR)\tclProc.obj \
+ $(TMPDIR)\tclRegexp.obj \
+ $(TMPDIR)\tclResolve.obj \
+ $(TMPDIR)\tclResult.obj \
+ $(TMPDIR)\tclScan.obj \
+ $(TMPDIR)\tclStringObj.obj \
+ $(TMPDIR)\tclStubInit.obj \
+ $(TMPDIR)\tclThread.obj \
+ $(TMPDIR)\tclThreadJoin.obj \
+ $(TMPDIR)\tclTimer.obj \
+ $(TMPDIR)\tclTrace.obj \
+ $(TMPDIR)\tclUtf.obj \
+ $(TMPDIR)\tclUtil.obj \
+ $(TMPDIR)\tclVar.obj \
+ $(TMPDIR)\tclWin32Dll.obj \
+ $(TMPDIR)\tclWinChan.obj \
+ $(TMPDIR)\tclWinConsole.obj \
+ $(TMPDIR)\tclWinSerial.obj \
+ $(TMPDIR)\tclWinError.obj \
+ $(TMPDIR)\tclWinFCmd.obj \
+ $(TMPDIR)\tclWinFile.obj \
+ $(TMPDIR)\tclWinInit.obj \
+ $(TMPDIR)\tclWinLoad.obj \
+ $(TMPDIR)\tclWinNotify.obj \
+ $(TMPDIR)\tclWinPipe.obj \
+ $(TMPDIR)\tclWinSock.obj \
+ $(TMPDIR)\tclWinThrd.obj \
+ $(TMPDIR)\tclWinTime.obj \
+ $(TMPDIR)\tclZlib.obj
+
+TCLSTUBOBJS = \
+ $(TMPDIR)\tclStubLib.obj \
+ $(TMPDIR)\tclTomMathStubLib.obj \
+ $(TMPDIR)\tclOOStubLib.obj
+
+WINDIR = $(ROOT)\win
+GENERICDIR = $(ROOT)\generic
+
+TCL_INCLUDES = -I"$(WINDIR)" -I"$(GENERICDIR)"
+TCL_DEFINES = $(DEBUGDEFINES) $(THREADDEFINES) $(SYMDEFINES) \
+ $(PROFDEFINES) $(OPTDEFINES) $(SIXFOURDEFINES) \
+ -DTCL_CFGVAL_ENCODING=${CFG_ENCODING}
+### TODO: Add -DHAVE_ZLIB=1
+
+######################################################################
+# Compiler flags
+######################################################################
+
+!IF "$(NODEBUG)" == "1"
+# these macros cause maximum optimization and no symbols
+cdebug = -v- -vi- -O2 -D_DEBUG
+!ELSE
+# these macros enable debugging
+cdebug = -k -Od -r- -v -vi- -y
+!ENDIF
+
+SYSDEFINES = _MT;NO_STRICT;_NO_VCL
+
+# declarations common to all compiler options
+cbase = -c -q -3 -a4 -g0 -tWM -Ve -Vx -X-
+WARNINGS = -w-rch -w-pch -w-par -w-dup -w-pro -w-dpu
+
+ccons = -tWC
+
+INCLUDEPATH = $(include32) $(TCL_INCLUDES)
+
+CFLAGS = $(cdebug) $(cbase) $(INCLUDEPATH) $(WARNINGS) -D$(SYSDEFINES)
+TCL_CFLAGS = $(CFLAGS) $(TCL_DEFINES)
+CONS_CFLAGS = $(CFLAGS) $(TCL_DEFINES) $(ccons)
+
+######################################################################
+# Linker flags
+######################################################################
+
+!IF "$(NODEBUG)" == "1"
+ldebug =
+!ELSE
+ldebug = -v
+!ENDIF
+
+# declarations common to all linker options
+LNFLAGS = -D"" -Gn -I$(TMPDIR) -x $(ldebug) $(libpath32)
+# -Gi: create lib file (is -Gl in doc)
+# -aa: Windows app, -ap: Windows console app
+LNFLAGS_DLL = -ap -Gi -Tpd
+LNFLAGS_CONS = -ap -Tpe
+
+LNLIBS = import32 cw32mt
+
+
+######################################################################
+# Project specific targets
+######################################################################
+
+release: setup $(TCLSH) dlls
+dlls: setup $(TCLREGDLL) $(TCLDDEDLL)
+all: setup $(TCLSH) dlls $(CAT32)
+tcltest: setup $(TCLTEST) dlls $(CAT32)
+plugin: setup $(TCLPLUGINDLL) $(TCLSHP)
+install: install-binaries install-libraries
+
+test: setup $(TCLTEST) dlls $(CAT32)
+ set TCL_LIBRARY=$(ROOT)/library
+ $(TCLTEST) $(ROOT)/tests/all.tcl
+
+setup:
+ @if not exist $(OUT_DIR)\nul mkdir $(OUT_DIR) &\
+ echo *** Created directory '$(OUT_DIR)'
+ @if not exist $(TMP_DIR)\nul mkdir $(TMP_DIR) &\
+ echo *** Created directory '$(TMP_DIR)'
+
+
+$(TCLLIB): $(TCLDLL)
+
+$(TCLDLL): $(TCLOBJS) $(TMPDIR)\$(NAMEPREFIX).res
+ $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 @&&!
+ $(TCLOBJS), $@, -x, $(LNLIBS),, $(TMPDIR)\$(NAMEPREFIX).res
+!
+
+$(TCLSTUBLIB): $(TCLSTUBOBJS)
+ $(lib32) /u $@ $(TCLSTUBOBJS)
+
+$(TCLPLUGINLIB): $(TCLPLUGINDLL)
+
+$(TCLPLUGINDLL): $(TCLOBJS) $(TMPDIR)\tcl.res
+ $(link32) $(ldebug) $(dlllflags) \
+ -out:$@ $(TMPDIR)\tcl.res $(guilibsdll) @&&!
+$(TCLOBJS)
+!
+
+$(TCLSH): $(TCLSHOBJS) $(TCLLIB) $(TMPDIR)\$(NAMEPREFIX)sh.res
+ $(link32) $(ldebug) -S:2400000 $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 @&&!
+ $(TCLSHOBJS), $@, -x, $(LNLIBS) $(TCLLIB),, $(TMPDIR)\$(NAMEPREFIX)sh.res
+!
+
+$(TCLSHP): $(TCLSHOBJS) $(TCLPLUGINLIB) $(TMPDIR)\tclsh.res
+ $(link32) $(ldebug) $(conlflags) $(TMPDIR)\tclsh.res -stack:2300000 \
+ -out:$@ $(conlibsdll) $(TCLPLUGINLIB) $(TCLSHOBJS)
+
+$(TCLTEST): $(TCLTESTOBJS) $(TCLLIB) $(TMPDIR)\$(NAMEPREFIX)sh.res
+ $(link32) $(ldebug) -S:2400000 $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 @&&!
+ $(TCLTESTOBJS), $@, -x, $(LNLIBS) $(TCLLIB),, $(TMPDIR)\$(NAMEPREFIX)sh.res
+!
+
+$(TCLDDEDLL): $(TMPDIR)\tclWinDde.obj $(TCLSTUBLIB)
+ $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 \
+ $(TMPDIR)\tclWinDde.obj, $@, -x, $(LNLIBS) $(TCLSTUBLIB),, \
+ $(TMPDIR)\$(NAMEPREFIX).res
+
+$(TCLREGDLL): $(TMPDIR)\tclWinReg.obj $(TCLSTUBLIB)
+ $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_DLL) $(TOOLS32)\lib\c0d32 \
+ $(TMPDIR)\tclWinReg.obj, $@, -x, $(LNLIBS) $(TCLSTUBLIB),, \
+ $(TMPDIR)\$(NAMEPREFIX).res
+
+$(CAT32): $(WINDIR)\cat.c
+ $(cc32) $(CONS_CFLAGS) -o$(TMPDIR)\cat.obj $?
+ $(link32) $(ldebug) $(LNFLAGS) $(LNFLAGS_CONS) $(TOOLS32)\lib\c0x32 \
+ $(TMPDIR)\cat.obj, $@, -x, $(LNLIBS),,
+
+install-binaries: $(TCLSH)
+ $(MKDIR) "$(BIN_INSTALL_DIR)"
+ $(MKDIR) "$(LIB_INSTALL_DIR)"
+ @echo Installing $(TCLDLLNAME)
+ @copy "$(TCLDLL)" "$(BIN_INSTALL_DIR)"
+ @copy "$(TCLLIB)" "$(LIB_INSTALL_DIR)"
+ @echo Installing "$(TCLSH)"
+ @copy "$(TCLSH)" "$(BIN_INSTALL_DIR)"
+ @echo Installing $(TCLSTUBLIBNAME)
+ @copy "$(TCLSTUBLIB)" "$(LIB_INSTALL_DIR)"
+ @echo Installing $(WINDIR)\tclooConfig.sh
+ @copy "$(WINDIR)\tclooConfig.sh" "$(LIB_INSTALL_DIR)"
+
+install-libraries:
+ -@$(MKDIR) "$(LIB_INSTALL_DIR)"
+ -@$(MKDIR) "$(INCLUDE_INSTALL_DIR)"
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)"
+ @echo Installing http1.0
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\http1.0"
+ -@copy "$(ROOT)\library\http1.0\http.tcl" "$(SCRIPT_INSTALL_DIR)\http1.0"
+ -@copy "$(ROOT)\library\http1.0\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\http1.0"
+ @echo Installing http2.8
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\http2.8"
+ -@copy "$(ROOT)\library\http\http.tcl" "$(SCRIPT_INSTALL_DIR)\http2.8"
+ -@copy "$(ROOT)\library\http\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\http2.8"
+ @echo Installing opt0.4
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\opt0.4"
+ -@copy "$(ROOT)\library\opt\optparse.tcl" "$(SCRIPT_INSTALL_DIR)\opt0.4"
+ -@copy "$(ROOT)\library\opt\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\opt0.4"
+ @echo Installing msgcat1.5
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\msgcat1.5"
+ -@copy "$(ROOT)\library\msgcat\msgcat.tcl" "$(SCRIPT_INSTALL_DIR)\msgcat1.5"
+ -@copy "$(ROOT)\library\msgcat\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\msgcat1.5"
+ @echo Installing tcltest2.3
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\tcltest2.3"
+ -@copy "$(ROOT)\library\tcltest\tcltest.tcl" "$(SCRIPT_INSTALL_DIR)\tcltest2.3"
+ -@copy "$(ROOT)\library\tcltest\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\tcltest2.3"
+ @echo Installing platform1.0
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\platform1.0"
+ -@copy "$(ROOT)\library\platform\platform.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0"
+ -@copy "$(ROOT)\library\platform\shell.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0"
+ -@copy "$(ROOT)\library\platform\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\platform1.0"
+ @echo Installing $(TCLDDEDLLNAME)
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\dde1.3"
+ -@copy "$(TCLDDEDLL)" "$(SCRIPT_INSTALL_DIR)\dde1.3"
+ -@copy "$(ROOT)\library\dde\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\dde1.3"
+ @echo Installing $(TCLREGDLLNAME)
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\reg1.2"
+ -@copy "$(TCLREGDLL)" "$(SCRIPT_INSTALL_DIR)\reg1.3"
+ -@copy "$(ROOT)\library\reg\pkgIndex.tcl" "$(SCRIPT_INSTALL_DIR)\reg1.2"
+ @echo Installing encoding files
+ -@$(MKDIR) "$(SCRIPT_INSTALL_DIR)\encoding"
+ -@copy "$(ROOT)\library\encoding\*.enc" "$(SCRIPT_INSTALL_DIR)\encoding"
+ @echo Installing library files
+ -@copy "$(GENERICDIR)\tcl.h" "$(INCLUDE_INSTALL_DIR)"
+ -@copy "$(GENERICDIR)\tclDecls.h" "$(INCLUDE_INSTALL_DIR)"
+ -@copy "$(GENERICDIR)\tclOO.h" "$(INCLUDE_INSTALL_DIR)"
+ -@copy "$(GENERICDIR)\tclOODecls.h" "$(INCLUDE_INSTALL_DIR)"
+ -@copy "$(GENERICDIR)\tclPlatDecls.h" "$(INCLUDE_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\history.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\init.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\parray.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\safe.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\tclIndex" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\package.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\word.tcl" "$(SCRIPT_INSTALL_DIR)"
+ -@copy "$(ROOT)\library\auto.tcl" "$(SCRIPT_INSTALL_DIR)"
+
+#
+# Regenerate the stubs files.
+#
+
+genstubs:
+ tclsh$(VERSION) $(ROOT)\tools\genStubs.tcl $(GENERICDIR) \
+ $(GENERICDIR)\tcl.decls $(GENERICDIR)\tclInt.decls
+
+#
+# Special case object file targets
+#
+$(TMPDIR)\tclWinInit.obj: $(WINDIR)\tclWinInit.c
+ $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\testMain.obj: $(WINDIR)\tclAppInit.c
+ $(cc32) $(TCL_CFLAGS) -DTCL_TEST -o$(TMPDIR)\testMain.obj $?
+
+$(TMPDIR)\tclTest.obj: $(GENERICDIR)\tclTest.c
+ $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\tclTestObj.obj: $(GENERICDIR)\tclTestObj.c
+ $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\tclWinTest.obj: $(WINDIR)\tclWinTest.c
+ $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $?
+
+$(TMP_DIR)\tclPkgConfig.obj: $(GENERICDIR)\tclPkgConfig.c
+ $(cc32) $(TCL_CFLAGS) \
+ -DCFG_INSTALL_EXEC_PREFIX=\"$(INSTALL_EXEC_PREFIX)\" \
+ -DCFG_INSTALL_PREFIX=\"$(INSTALL_PREFIX)\" \
+ -DCFG_RUNTIME_EXEC_PREFIX=\"$(RUNTIME_EXEC_PREFIX)\" \
+ -DCFG_RUNTIME_PREFIX=\"$(RUNTIME_PREFIX)\" \
+ -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\tclAppInit.obj : $(WINDIR)\tclAppInit.c
+ $(cc32) $(TCL_CFLAGS) -o$(TMPDIR)\$@ $?
+
+# The following objects should be built using the stub interfaces
+
+# tclWinReg: Produces errors in ANSI mode
+$(TMPDIR)\tclWinReg.obj : $(WINDIR)\tclWinReg.c
+ $(cc32) $(TCL_CFLAGS) -DUSE_TCL_STUBS -o$(TMPDIR)\$@ $?
+
+# tclWinDde: Produces errors in ANSI mode
+$(TMPDIR)\tclWinDde.obj : $(WINDIR)\tclWinDde.c
+ $(cc32) $(TCL_CFLAGS) -DUSE_TCL_STUBS -o$(TMPDIR)\$@ $?
+
+
+# The following objects are part of the stub library and should not
+# be built as DLL objects but none of the symbols should be exported
+
+$(TMPDIR)\tclStubLib.obj : $(GENERICDIR)\tclStubLib.c
+ $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\tclTomMathStubLib.obj : $(GENERICDIR)\tclTomMathStubLib.c
+ $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $?
+
+$(TMPDIR)\tclOOStubLib.obj : $(GENERICDIR)\tclOOStubLib.c
+ $(cc32) $(TCL_CFLAGS) -DSTATIC_BUILD -o$(TMPDIR)\$@ $?
+
+
+# Dedependency rules
+
+$(GENERICDIR)\regcomp.c: \
+ $(GENERICDIR)\regguts.h \
+ $(GENERICDIR)\regc_lex.c \
+ $(GENERICDIR)\regc_color.c \
+ $(GENERICDIR)\regc_nfa.c \
+ $(GENERICDIR)\regc_cvec.c \
+ $(GENERICDIR)\regc_locale.c
+
+$(GENERICDIR)\regcustom.h: \
+ $(GENERICDIR)\tclInt.h \
+ $(GENERICDIR)\tclPort.h \
+ $(GENERICDIR)\regex.h
+
+$(GENERICDIR)\regexec.c: \
+ $(GENERICDIR)\rege_dfa.c \
+ $(GENERICDIR)\regguts.h
+
+$(GENERICDIR)\regerror.c: $(GENERICDIR)\regguts.h
+$(GENERICDIR)\regfree.c: $(GENERICDIR)\regguts.h
+$(GENERICDIR)\regfronts.c: $(GENERICDIR)\regguts.h
+$(GENERICDIR)\regguts.h: $(GENERICDIR)\regcustom.h
+
+#
+# Implicit rules
+#
+
+{$(WINDIR)}.c{$(TMPDIR)}.obj:
+ $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $<
+
+{$(GENERICDIR)}.c{$(TMPDIR)}.obj:
+ $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $<
+
+{$(ROOT)\compat}.c{$(TMPDIR)}.obj:
+ $(cc32) -DBUILD_tcl $(TCL_CFLAGS) -o$@ $<
+
+{$(WINDIR)}.rc{$(TMPDIR)}.res:
+ $(rc32) $(INCLUDEPATH) -D$(USERDEFINES);$(SYSDEFINES) -fo$@ $<
+
+clean:
+ -@$(RM) $(OUTDIR)\*.exp
+ -@$(RM) $(OUTDIR)\*.lib
+ -@$(RM) $(OUTDIR)\*.dll
+ -@$(RM) $(OUTDIR)\*.exe
+ -@$(RM) $(OUTDIR)\*.pdb
+ -@$(RM) $(TMPDIR)\*.pch
+ -@$(RM) $(TMPDIR)\*.obj
+ -@$(RM) $(TMPDIR)\*.res
+ -@$(RM) $(TMPDIR)\*.exe
+ -@$(RMDIR) $(OUTDIR)
+ -@$(RMDIR) $(TMPDIR)
+
+# Local Variables:
+# mode: makefile
+# End:
diff --git a/win/makefile.vc b/win/makefile.vc index 2e27275..70f3f6e 100644 --- a/win/makefile.vc +++ b/win/makefile.vc @@ -1,1260 +1,1243 @@ -#------------------------------------------------------------- -# makefile.vc -- -# -# Microsoft Visual C++ makefile for use with nmake.exe v1.62+ (VC++ 5.0+) -# -# See the file "license.terms" for information on usage and redistribution -# of this file, and for a DISCLAIMER OF ALL WARRANTIES. -# -# Copyright (c) 1995-1996 Sun Microsystems, Inc. -# Copyright (c) 1998-2000 Ajuba Solutions. -# Copyright (c) 2001-2005 ActiveState Corporation. -# Copyright (c) 2001-2004 David Gravereaux. -# Copyright (c) 2003-2008 Pat Thoyts. -#------------------------------------------------------------------------------ - -# Check to see we are configured to build with MSVC (MSDEVDIR, MSVCDIR or -# VCINSTALLDIR) or with the MS Platform SDK (MSSDK or WindowsSDKDir) -!if !defined(MSDEVDIR) && !defined(MSVCDIR) && !defined(VCINSTALLDIR) && !defined(MSSDK) && !defined(WINDOWSSDKDIR) -MSG = ^ -You need to run vcvars32.bat from Developer Studio or setenv.bat from the^ -Platform SDK first to setup the environment. Jump to this line to read^ -the build instructions. -!error $(MSG) -!endif - -#------------------------------------------------------------------------------ -# HOW TO USE this makefile: -# -# 1) It is now necessary to have MSVCDir, MSDevDir or MSSDK set in the -# environment. This is used as a check to see if vcvars32.bat had been -# run prior to running nmake or during the installation of Microsoft -# Visual C++, MSVCDir had been set globally and the PATH adjusted. -# Either way is valid. -# -# You'll need to run vcvars32.bat contained in the MsDev's vc(98)/bin -# directory to setup the proper environment, if needed, for your -# current setup. This is a needed bootstrap requirement and allows the -# swapping of different environments to be easier. -# -# 2) To use the Platform SDK (not expressly needed), run setenv.bat after -# vcvars32.bat according to the instructions for it. This can also -# turn on the 64-bit compiler, if your SDK has it. -# -# 3) Targets are: -# release -- Builds the core, the shell and the dlls. (default) -# dlls -- Just builds the windows extensions -# shell -- Just builds the shell and the core. -# core -- Only builds the core [tclXX.(dll|lib)]. -# all -- Builds everything. -# test -- Builds and runs the test suite. -# tcltest -- Just builds the test shell. -# install -- Installs the built binaries and libraries to $(INSTALLDIR) -# as the root of the install tree. -# tidy/clean/hose -- varying levels of cleaning. -# genstubs -- Rebuilds the Stubs table and support files (dev only). -# depend -- Generates an accurate set of source dependancies for this -# makefile. Helpful to avoid problems when the sources are -# refreshed and you rebuild, but can "overbuild" when common -# headers like tclInt.h just get small changes. -# htmlhelp -- Builds a Windows .chm help file for Tcl and Tk from the -# troff manual pages found in $(ROOT)\doc. You need to -# have installed the HTML Help Compiler package from Microsoft -# to produce the .chm file. -# winhelp -- (deprecated) Builds the windows .hlp file for Tcl from -# the troff man files found in $(ROOT)\doc. This type of -# help file is deprecated by Microsoft in favour of html -# help files (.chm) -# -# 4) Macros usable on the commandline: -# INSTALLDIR=<path> -# Sets where to install Tcl from the built binaries. -# C:\Progra~1\Tcl is assumed when not specified. -# -# OPTS=loimpact,msvcrt,nothreads,pdbs,profile,static,staticpkg,symbols,thrdalloc,tclalloc,unchecked,none -# Sets special options for the core. The default is for none. -# Any combination of the above may be used (comma separated). -# 'none' will over-ride everything to nothing. -# -# loimpact = Adds a flag for how NT treats the heap to keep memory -# in use, low. This is said to impact alloc performance. -# msvcrt = Affects the static option only to switch it from -# using libcmt(d) as the C runtime [by default] to -# msvcrt(d). This is useful for static embedding -# support. -# nothreads= Turns off full multithreading support. -# pdbs = Build detached symbols for release builds. -# profile = Adds profiling hooks. Map file is assumed. -# static = Builds a static library of the core instead of a -# dll. The static library will contain the dde and reg -# extensions. External applications who want to use -# this, need to link with the stub library as well as -# the static Tcl library.The shell will be static (and -# large), as well. -# staticpkg = Affects the static option only to switch -# tclshXX.exe to have the dde and reg extension linked -# inside it. -# symbols = Debug build. Links to the debug C runtime, disables -# optimizations and creates pdb symbols files. -# thrdalloc = Use the thread allocator (shared global free pool) -# This is the default on threaded builds. -# tclalloc = Use the old non-thread allocator -# unchecked= Allows a symbols build to not use the debug -# enabled runtime (msvcrt.dll not msvcrtd.dll -# or libcmt.lib not libcmtd.lib). -# -# STATS=compdbg,memdbg,none -# Sets optional memory and bytecode compiler debugging code added -# to the core. The default is for none. Any combination of the -# above may be used (comma separated). 'none' will over-ride -# everything to nothing. -# -# compdbg = Enables byte compilation logging. -# memdbg = Enables the debugging memory allocator. -# -# CHECKS=64bit,fullwarn,nodep,none -# Sets special macros for checking compatability. -# -# 64bit = Enable 64bit portability warnings (if available) -# fullwarn = Builds with full compiler and link warnings enabled. -# Very verbose. -# nodep = Turns off compatability macros to ensure the core -# isn't being built with deprecated functions. -# -# MACHINE=(ALPHA|AMD64|IA64|IX86) -# Set the machine type used for the compiler, linker, and -# resource compiler. This hook is needed to tell the tools -# when alternate platforms are requested. IX86 is the default -# when not specified. If the CPU environment variable has been -# set (ie: recent Platform SDK) then MACHINE is set from CPU. -# -# TMP_DIR=<path> -# OUT_DIR=<path> -# Hooks to allow the intermediate and output directories to be -# changed. $(OUT_DIR) is assumed to be -# $(BINROOT)\(Release|Debug) based on if symbols are requested. -# $(TMP_DIR) will de $(OUT_DIR)\<buildtype> by default. -# -# TESTPAT=<file> -# Reads the tests requested to be run from this file. -# -# CFG_ENCODING=encoding -# name of encoding for configuration information. Defaults -# to cp1252 -# -# 5) Examples: -# -# Basic syntax of calling nmake looks like this: -# nmake [-nologo] -f makefile.vc [target|macrodef [target|macrodef] [...]] -# -# Standard (no frills) -# c:\tcl_src\win\>c:\progra~1\micros~1\vc98\bin\vcvars32.bat -# Setting environment for using Microsoft Visual C++ tools. -# c:\tcl_src\win\>nmake -f makefile.vc release -# c:\tcl_src\win\>nmake -f makefile.vc install INSTALLDIR=c:\progra~1\tcl -# -# Building for Win64 -# c:\tcl_src\win\>c:\progra~1\micros~1\vc98\bin\vcvars32.bat -# Setting environment for using Microsoft Visual C++ tools. -# c:\tcl_src\win\>c:\progra~1\platfo~1\setenv.bat /pre64 /RETAIL -# Targeting Windows pre64 RETAIL -# c:\tcl_src\win\>nmake -f makefile.vc MACHINE=IA64 -# -#------------------------------------------------------------------------------ -#============================================================================== -############################################################################### - - -# //==================================================================\\ -# >>[ -> Do not modify below this line. <- ]<< -# >>[ Please, use the commandline macros to modify how Tcl is built. ]<< -# >>[ If you need more features, send us a patch for more macros. ]<< -# \\==================================================================// - - -############################################################################### -#============================================================================== -#------------------------------------------------------------------------------ - -!if !exist("makefile.vc") -MSG = ^ -You must run this makefile only from the directory it is in.^ -Please `cd` to its location first. -!error $(MSG) -!endif - -PROJECT = tcl -!include "rules.vc" - -STUBPREFIX = $(PROJECT)stub -DOTVERSION = $(TCL_MAJOR_VERSION).$(TCL_MINOR_VERSION) -VERSION = $(TCL_MAJOR_VERSION)$(TCL_MINOR_VERSION) - -DDEDOTVERSION = 1.4 -DDEVERSION = $(DDEDOTVERSION:.=) - -REGDOTVERSION = 1.3 -REGVERSION = $(REGDOTVERSION:.=) - -BINROOT = $(MAKEDIR) # originally . -ROOT = $(MAKEDIR)\.. # originally .. - -TCLIMPLIB = $(OUT_DIR)\$(PROJECT)$(VERSION)$(SUFX).lib -TCLLIBNAME = $(PROJECT)$(VERSION)$(SUFX).$(EXT) -TCLLIB = $(OUT_DIR)\$(TCLLIBNAME) - -TCLSTUBLIBNAME = $(STUBPREFIX)$(VERSION).lib -TCLSTUBLIB = $(OUT_DIR)\$(TCLSTUBLIBNAME) - -TCLSHNAME = $(PROJECT)sh$(VERSION)$(SUFX).exe -TCLSH = $(OUT_DIR)\$(TCLSHNAME) - -TCLKITNAME = $(PROJECT)kit$(VERSION)$(SUFX).exe -TCLKIT = $(OUT_DIR)\$(TCLSHNAME) - -TCLREGLIBNAME = $(PROJECT)reg$(REGVERSION)$(SUFX:t=).$(EXT) -TCLREGLIB = $(OUT_DIR)\$(TCLREGLIBNAME) - -TCLDDELIBNAME = $(PROJECT)dde$(DDEVERSION)$(SUFX:t=).$(EXT) -TCLDDELIB = $(OUT_DIR)\$(TCLDDELIBNAME) - -TCLTEST = $(OUT_DIR)\$(PROJECT)test.exe -CAT32 = $(OUT_DIR)\cat32.exe - -# Can we run what we build? IX86 runs on all architectures. -!ifndef TCLSH_NATIVE -!if "$(MACHINE)" == "IX86" || "$(MACHINE)" == "$(NATIVE_ARCH)" -TCLSH_NATIVE = $(TCLSH) -!else -!error You must explicitly set TCLSH_NATIVE for cross-compilation -!endif -!endif - -### Make sure we use backslash only. -LIB_INSTALL_DIR = $(_INSTALLDIR)\lib -BIN_INSTALL_DIR = $(_INSTALLDIR)\bin -DOC_INSTALL_DIR = $(_INSTALLDIR)\doc -SCRIPT_INSTALL_DIR = $(_INSTALLDIR)\lib\tcl$(DOTVERSION) -INCLUDE_INSTALL_DIR = $(_INSTALLDIR)\include - -TCLSHOBJS = \ - $(TMP_DIR)\tclAppInit.obj \ -!if !$(STATIC_BUILD) -!if $(TCL_USE_STATIC_PACKAGES) - $(TMP_DIR)\tclWinReg.obj \ - $(TMP_DIR)\tclWinDde.obj \ -!endif -!endif - $(TMP_DIR)\tclsh.res - -TCLKITOBJS = \ - $(TMP_DIR)\tclKitInit.obj \ - $(TMP_DIR)\tclZipVfs.obj \ -!if !$(STATIC_BUILD) -!if $(TCL_USE_STATIC_PACKAGES) - $(TMP_DIR)\tclWinReg.obj \ - $(TMP_DIR)\tclWinDde.obj \ -!endif -!endif - $(TMP_DIR)\tclsh.res - - -TCLTESTOBJS = \ - $(TMP_DIR)\tclTest.obj \ - $(TMP_DIR)\tclTestObj.obj \ - $(TMP_DIR)\tclTestProcBodyObj.obj \ - $(TMP_DIR)\tclThreadTest.obj \ - $(TMP_DIR)\tclWinTest.obj \ -!if !$(STATIC_BUILD) -!if $(TCL_USE_STATIC_PACKAGES) - $(TMP_DIR)\tclWinReg.obj \ - $(TMP_DIR)\tclWinDde.obj \ -!endif -!endif - $(TMP_DIR)\testMain.obj - -COREOBJS = \ - $(TMP_DIR)\regcomp.obj \ - $(TMP_DIR)\regerror.obj \ - $(TMP_DIR)\regexec.obj \ - $(TMP_DIR)\regfree.obj \ - $(TMP_DIR)\tclAlloc.obj \ - $(TMP_DIR)\tclAssembly.obj \ - $(TMP_DIR)\tclAsync.obj \ - $(TMP_DIR)\tclBasic.obj \ - $(TMP_DIR)\tclBinary.obj \ - $(TMP_DIR)\tclCkalloc.obj \ - $(TMP_DIR)\tclClock.obj \ - $(TMP_DIR)\tclCmdAH.obj \ - $(TMP_DIR)\tclCmdIL.obj \ - $(TMP_DIR)\tclCmdMZ.obj \ - $(TMP_DIR)\tclCompCmds.obj \ - $(TMP_DIR)\tclCompCmdsGR.obj \ - $(TMP_DIR)\tclCompCmdsSZ.obj \ - $(TMP_DIR)\tclCompExpr.obj \ - $(TMP_DIR)\tclCompile.obj \ - $(TMP_DIR)\tclConfig.obj \ - $(TMP_DIR)\tclDate.obj \ - $(TMP_DIR)\tclDictObj.obj \ - $(TMP_DIR)\tclDisassemble.obj \ - $(TMP_DIR)\tclEncoding.obj \ - $(TMP_DIR)\tclEnsemble.obj \ - $(TMP_DIR)\tclEnv.obj \ - $(TMP_DIR)\tclEvent.obj \ - $(TMP_DIR)\tclExecute.obj \ - $(TMP_DIR)\tclFCmd.obj \ - $(TMP_DIR)\tclFileName.obj \ - $(TMP_DIR)\tclGet.obj \ - $(TMP_DIR)\tclHash.obj \ - $(TMP_DIR)\tclHistory.obj \ - $(TMP_DIR)\tclIndexObj.obj \ - $(TMP_DIR)\tclInterp.obj \ - $(TMP_DIR)\tclIO.obj \ - $(TMP_DIR)\tclIOCmd.obj \ - $(TMP_DIR)\tclIOGT.obj \ - $(TMP_DIR)\tclIOSock.obj \ - $(TMP_DIR)\tclIOUtil.obj \ - $(TMP_DIR)\tclIORChan.obj \ - $(TMP_DIR)\tclIORTrans.obj \ - $(TMP_DIR)\tclLink.obj \ - $(TMP_DIR)\tclListObj.obj \ - $(TMP_DIR)\tclLiteral.obj \ - $(TMP_DIR)\tclLoad.obj \ - $(TMP_DIR)\tclMain.obj \ - $(TMP_DIR)\tclMain2.obj \ - $(TMP_DIR)\tclNamesp.obj \ - $(TMP_DIR)\tclNotify.obj \ - $(TMP_DIR)\tclOO.obj \ - $(TMP_DIR)\tclOOBasic.obj \ - $(TMP_DIR)\tclOOCall.obj \ - $(TMP_DIR)\tclOODefineCmds.obj \ - $(TMP_DIR)\tclOOInfo.obj \ - $(TMP_DIR)\tclOOMethod.obj \ - $(TMP_DIR)\tclOOStubInit.obj \ - $(TMP_DIR)\tclObj.obj \ - $(TMP_DIR)\tclOptimize.obj \ - $(TMP_DIR)\tclPanic.obj \ - $(TMP_DIR)\tclParse.obj \ - $(TMP_DIR)\tclPathObj.obj \ - $(TMP_DIR)\tclPipe.obj \ - $(TMP_DIR)\tclPkg.obj \ - $(TMP_DIR)\tclPkgConfig.obj \ - $(TMP_DIR)\tclPosixStr.obj \ - $(TMP_DIR)\tclPreserve.obj \ - $(TMP_DIR)\tclProc.obj \ - $(TMP_DIR)\tclRegexp.obj \ - $(TMP_DIR)\tclResolve.obj \ - $(TMP_DIR)\tclResult.obj \ - $(TMP_DIR)\tclScan.obj \ - $(TMP_DIR)\tclStringObj.obj \ - $(TMP_DIR)\tclStrToD.obj \ - $(TMP_DIR)\tclStubInit.obj \ - $(TMP_DIR)\tclThread.obj \ - $(TMP_DIR)\tclThreadAlloc.obj \ - $(TMP_DIR)\tclThreadJoin.obj \ - $(TMP_DIR)\tclThreadStorage.obj \ - $(TMP_DIR)\tclTimer.obj \ - $(TMP_DIR)\tclTomMathInterface.obj \ - $(TMP_DIR)\tclTrace.obj \ - $(TMP_DIR)\tclUtf.obj \ - $(TMP_DIR)\tclUtil.obj \ - $(TMP_DIR)\tclVar.obj \ - $(TMP_DIR)\tclZlib.obj - -ZLIBOBJS = \ - $(TMP_DIR)\adler32.obj \ - $(TMP_DIR)\compress.obj \ - $(TMP_DIR)\crc32.obj \ - $(TMP_DIR)\deflate.obj \ - $(TMP_DIR)\infback.obj \ - $(TMP_DIR)\inffast.obj \ - $(TMP_DIR)\inflate.obj \ - $(TMP_DIR)\inftrees.obj \ - $(TMP_DIR)\trees.obj \ - $(TMP_DIR)\uncompr.obj \ - $(TMP_DIR)\zutil.obj - -TOMMATHOBJS = \ - $(TMP_DIR)\bncore.obj \ - $(TMP_DIR)\bn_reverse.obj \ - $(TMP_DIR)\bn_fast_s_mp_mul_digs.obj \ - $(TMP_DIR)\bn_fast_s_mp_sqr.obj \ - $(TMP_DIR)\bn_mp_add.obj \ - $(TMP_DIR)\bn_mp_add_d.obj \ - $(TMP_DIR)\bn_mp_and.obj \ - $(TMP_DIR)\bn_mp_clamp.obj \ - $(TMP_DIR)\bn_mp_clear.obj \ - $(TMP_DIR)\bn_mp_clear_multi.obj \ - $(TMP_DIR)\bn_mp_cmp.obj \ - $(TMP_DIR)\bn_mp_cmp_d.obj \ - $(TMP_DIR)\bn_mp_cmp_mag.obj \ - $(TMP_DIR)\bn_mp_cnt_lsb.obj \ - $(TMP_DIR)\bn_mp_copy.obj \ - $(TMP_DIR)\bn_mp_count_bits.obj \ - $(TMP_DIR)\bn_mp_div.obj \ - $(TMP_DIR)\bn_mp_div_d.obj \ - $(TMP_DIR)\bn_mp_div_2.obj \ - $(TMP_DIR)\bn_mp_div_2d.obj \ - $(TMP_DIR)\bn_mp_div_3.obj \ - $(TMP_DIR)\bn_mp_exch.obj \ - $(TMP_DIR)\bn_mp_expt_d.obj \ - $(TMP_DIR)\bn_mp_grow.obj \ - $(TMP_DIR)\bn_mp_init.obj \ - $(TMP_DIR)\bn_mp_init_copy.obj \ - $(TMP_DIR)\bn_mp_init_multi.obj \ - $(TMP_DIR)\bn_mp_init_set.obj \ - $(TMP_DIR)\bn_mp_init_set_int.obj \ - $(TMP_DIR)\bn_mp_init_size.obj \ - $(TMP_DIR)\bn_mp_karatsuba_mul.obj \ - $(TMP_DIR)\bn_mp_karatsuba_sqr.obj \ - $(TMP_DIR)\bn_mp_lshd.obj \ - $(TMP_DIR)\bn_mp_mod.obj \ - $(TMP_DIR)\bn_mp_mod_2d.obj \ - $(TMP_DIR)\bn_mp_mul.obj \ - $(TMP_DIR)\bn_mp_mul_2.obj \ - $(TMP_DIR)\bn_mp_mul_2d.obj \ - $(TMP_DIR)\bn_mp_mul_d.obj \ - $(TMP_DIR)\bn_mp_neg.obj \ - $(TMP_DIR)\bn_mp_or.obj \ - $(TMP_DIR)\bn_mp_radix_size.obj \ - $(TMP_DIR)\bn_mp_radix_smap.obj \ - $(TMP_DIR)\bn_mp_read_radix.obj \ - $(TMP_DIR)\bn_mp_rshd.obj \ - $(TMP_DIR)\bn_mp_set.obj \ - $(TMP_DIR)\bn_mp_set_int.obj \ - $(TMP_DIR)\bn_mp_shrink.obj \ - $(TMP_DIR)\bn_mp_sqr.obj \ - $(TMP_DIR)\bn_mp_sqrt.obj \ - $(TMP_DIR)\bn_mp_sub.obj \ - $(TMP_DIR)\bn_mp_sub_d.obj \ - $(TMP_DIR)\bn_mp_to_unsigned_bin.obj \ - $(TMP_DIR)\bn_mp_to_unsigned_bin_n.obj \ - $(TMP_DIR)\bn_mp_toom_mul.obj \ - $(TMP_DIR)\bn_mp_toom_sqr.obj \ - $(TMP_DIR)\bn_mp_toradix_n.obj \ - $(TMP_DIR)\bn_mp_unsigned_bin_size.obj \ - $(TMP_DIR)\bn_mp_xor.obj \ - $(TMP_DIR)\bn_mp_zero.obj \ - $(TMP_DIR)\bn_s_mp_add.obj \ - $(TMP_DIR)\bn_s_mp_mul_digs.obj \ - $(TMP_DIR)\bn_s_mp_sqr.obj \ - $(TMP_DIR)\bn_s_mp_sub.obj - -PLATFORMOBJS = \ - $(TMP_DIR)\tclWin32Dll.obj \ - $(TMP_DIR)\tclWinChan.obj \ - $(TMP_DIR)\tclWinConsole.obj \ - $(TMP_DIR)\tclWinError.obj \ - $(TMP_DIR)\tclWinFCmd.obj \ - $(TMP_DIR)\tclWinFile.obj \ - $(TMP_DIR)\tclWinInit.obj \ - $(TMP_DIR)\tclWinLoad.obj \ - $(TMP_DIR)\tclWinNotify.obj \ - $(TMP_DIR)\tclWinPipe.obj \ - $(TMP_DIR)\tclWinSerial.obj \ - $(TMP_DIR)\tclWinSock.obj \ - $(TMP_DIR)\tclWinThrd.obj \ - $(TMP_DIR)\tclWinTime.obj \ -!if $(STATIC_BUILD) - $(TMP_DIR)\tclWinReg.obj \ - $(TMP_DIR)\tclWinDde.obj \ -!else - $(TMP_DIR)\tcl.res -!endif - -TCLOBJS = $(COREOBJS) $(ZLIBOBJS) $(TOMMATHOBJS) $(PLATFORMOBJS) - -TCLSTUBOBJS = \ - $(TMP_DIR)\tclStubLib.obj \ - $(TMP_DIR)\tclTomMathStubLib.obj \ - $(TMP_DIR)\tclOOStubLib.obj - -### The following paths CANNOT have spaces in them. -COMPATDIR = $(ROOT)\compat -DOCDIR = $(ROOT)\doc -GENERICDIR = $(ROOT)\generic -TOMMATHDIR = $(ROOT)\libtommath -TOOLSDIR = $(ROOT)\tools -WINDIR = $(ROOT)\win -PKGSDIR = $(ROOT)\pkgs - -#--------------------------------------------------------------------- -# Compile flags -#--------------------------------------------------------------------- - -!if !$(DEBUG) -!if $(OPTIMIZING) -### This cranks the optimization level to maximize speed -cdebug = -O2 $(OPTIMIZATIONS) -!else -cdebug = -!endif -!if $(SYMBOLS) -cdebug = $(cdebug) -Zi -!endif -!else if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64" -### Warnings are too many, can't support warnings into errors. -cdebug = -Zi -Od $(DEBUGFLAGS) -!else -cdebug = -Zi -WX $(DEBUGFLAGS) -!endif - -### Declarations common to all compiler options -cwarn = $(WARNINGS) -D _CRT_SECURE_NO_DEPRECATE -D _CRT_NONSTDC_NO_DEPRECATE -cflags = -nologo -c $(COMPILERFLAGS) $(cwarn) -Fp$(TMP_DIR)^\ - -!if $(MSVCRT) -!if $(DEBUG) && !$(UNCHECKED) -crt = -MDd -!else -crt = -MD -!endif -!else -!if $(DEBUG) && !$(UNCHECKED) -crt = -MTd -!else -crt = -MT -!endif -!endif - -TCL_INCLUDES = -I"$(WINDIR)" -I"$(GENERICDIR)" -I"$(TOMMATHDIR)" -TCL_DEFINES = -DTCL_TOMMATH -DMP_PREC=4 -Dinline=__inline -DHAVE_ZLIB=1 -BASE_CFLAGS = $(cflags) $(cdebug) $(crt) $(TCL_INCLUDES) $(TCL_DEFINES) -CON_CFLAGS = $(cflags) $(cdebug) $(crt) -DCONSOLE -TCL_CFLAGS = $(BASE_CFLAGS) $(OPTDEFINES) -STUB_CFLAGS = $(cflags) $(cdebug) $(OPTDEFINES) - - -#--------------------------------------------------------------------- -# Link flags -#--------------------------------------------------------------------- - -!if $(DEBUG) -ldebug = -debug -debugtype:cv -!else -ldebug = -release -opt:ref -opt:icf,3 -!if $(SYMBOLS) -ldebug = $(ldebug) -debug -debugtype:cv -!endif -!endif - -### Declarations common to all linker options -lflags = -nologo -machine:$(MACHINE) $(LINKERFLAGS) $(ldebug) - -!if $(PROFILE) -lflags = $(lflags) -profile -!endif - -!if $(ALIGN98_HACK) && !$(STATIC_BUILD) -### Align sections for PE size savings. -lflags = $(lflags) -opt:nowin98 -!else if !$(ALIGN98_HACK) && $(STATIC_BUILD) -### Align sections for speed in loading by choosing the virtual page size. -lflags = $(lflags) -align:4096 -!endif - -!if $(LOIMPACT) -lflags = $(lflags) -ws:aggressive -!endif - -dlllflags = $(lflags) -dll -conlflags = $(lflags) -subsystem:console -guilflags = $(lflags) -subsystem:windows - -baselibs = netapi32.lib kernel32.lib user32.lib advapi32.lib ws2_32.lib -# Avoid 'unresolved external symbol __security_cookie' errors. -# c.f. http://support.microsoft.com/?id=894573 -!if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64" -!if $(VCVERSION) > 1399 && $(VCVERSION) < 1500 -baselibs = $(baselibs) bufferoverflowU.lib -!endif -!endif - -#--------------------------------------------------------------------- -# TclTest flags -#--------------------------------------------------------------------- - -!if "$(TESTPAT)" != "" -TESTFLAGS = $(TESTFLAGS) -file $(TESTPAT) -!endif - - -#--------------------------------------------------------------------- -# Project specific targets -#--------------------------------------------------------------------- - -release: setup $(TCLSH) $(TCLSTUBLIB) dlls pkgs -core: setup $(TCLLIB) $(TCLSTUBLIB) -shell: setup $(TCLSH) -dlls: setup $(TCLREGLIB) $(TCLDDELIB) -all: setup $(TCLSH) $(TCLSTUBLIB) dlls $(CAT32) pkgs -tcltest: setup $(TCLTEST) dlls $(CAT32) -install: install-binaries install-libraries install-docs install-pkgs - -test: test-core test-pkgs -test-core: setup $(TCLTEST) dlls $(CAT32) - set TCL_LIBRARY=$(ROOT:\=/)/library -!if "$(OS)" == "Windows_NT" || "$(MSVCDIR)" == "IDE" - $(DEBUGGER) $(TCLTEST) "$(ROOT:\=/)/tests/all.tcl" $(TESTFLAGS) -loadfile << - package ifneeded dde 1.4.0 [list load "$(TCLDDELIB:\=/)" dde] - package ifneeded registry 1.3.0 [list load "$(TCLREGLIB:\=/)" registry] -<< -!else - @echo Please wait while the tests are collected... - $(TCLTEST) "$(ROOT:\=/)/tests/all.tcl" $(TESTFLAGS) -loadfile << > tests.log - package ifneeded dde 1.4.0 "$(TCLDDELIB:\=/)" dde] - package ifneeded registry 1.3.0 "$(TCLREGLIB:\=/)" registry] -<< - type tests.log | more -!endif - -runtest: setup $(TCLTEST) dlls $(CAT32) - set TCL_LIBRARY=$(ROOT:\=/)/library - $(DEBUGGER) $(TCLTEST) $(SCRIPT) - -runshell: setup $(TCLSH) dlls - set TCL_LIBRARY=$(ROOT:\=/)/library - $(DEBUGGER) $(TCLSH) $(SCRIPT) - -setup: - @if not exist $(OUT_DIR)\nul mkdir $(OUT_DIR) - @if not exist $(TMP_DIR)\nul mkdir $(TMP_DIR) - -!if !$(STATIC_BUILD) -$(TCLIMPLIB): $(TCLLIB) -!endif - -$(TCLLIB): $(TCLOBJS) -!if $(STATIC_BUILD) - $(lib32) -nologo $(LINKERFLAGS) -out:$@ @<< -$** -<< -!else - $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tcl -out:$@ \ - $(baselibs) @<< -$** -<< - $(_VC_MANIFEST_EMBED_DLL) -!endif - -$(TCLSTUBLIB): $(TCLSTUBOBJS) - $(lib32) -nologo $(LINKERFLAGS) -nodefaultlib -out:$@ $(TCLSTUBOBJS) - -$(TCLSH): $(TCLSHOBJS) $(TCLSTUBLIB) $(TCLIMPLIB) - $(link32) $(conlflags) -stack:2300000 -out:$@ $(baselibs) $** - $(_VC_MANIFEST_EMBED_EXE) - -$(TCLTEST): $(TCLTESTOBJS) $(TCLSTUBLIB) $(TCLIMPLIB) - $(link32) $(conlflags) -stack:2300000 -out:$@ $(baselibs) $** - $(_VC_MANIFEST_EMBED_EXE) - -!if $(STATIC_BUILD) -$(TCLDDELIB): $(TMP_DIR)\tclWinDde.obj - $(lib32) -nologo $(LINKERFLAGS) -out:$@ $** -!else -$(TCLDDELIB): $(TMP_DIR)\tclWinDde.obj $(TCLSTUBLIB) - $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tcldde -out:$@ \ - $** $(baselibs) - $(_VC_MANIFEST_EMBED_DLL) -!endif - -!if $(STATIC_BUILD) -$(TCLREGLIB): $(TMP_DIR)\tclWinReg.obj - $(lib32) -nologo $(LINKERFLAGS) -out:$@ $** -!else -$(TCLREGLIB): $(TMP_DIR)\tclWinReg.obj $(TCLSTUBLIB) - $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tclreg -out:$@ \ - $** $(baselibs) - $(_VC_MANIFEST_EMBED_DLL) -!endif - -pkgs: - @for /d %d in ($(PKGSDIR)\*) do \ - @if exist "%~fd\win\makefile.vc" ( \ - pushd "%~fd\win" & \ - $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) &\ - popd \ - ) - -test-pkgs: - @for /d %d in ($(PKGSDIR)\*) do \ - @if exist "%~fd\win\makefile.vc" ( \ - pushd "%~fd\win" & \ - $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) test &\ - popd \ - ) - -install-pkgs: - @for /d %d in ($(PKGSDIR)\*) do \ - @if exist "%~fd\win\makefile.vc" ( \ - pushd "%~fd\win" & \ - $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) install &\ - popd \ - ) - -clean-pkgs: - @for /d %d in ($(PKGSDIR)\*) do \ - @if exist "%~fd\win\makefile.vc" ( \ - pushd "%~fd\win" & \ - $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) clean &\ - popd \ - ) - -$(CAT32): $(WINDIR)\cat.c - $(cc32) $(CON_CFLAGS) -Fo$(TMP_DIR)\ $? - $(link32) $(conlflags) -out:$@ -stack:16384 $(TMP_DIR)\cat.obj \ - $(baselibs) - $(_VC_MANIFEST_EMBED_EXE) - -#--------------------------------------------------------------------- -# Regenerate the stubs files. [Development use only] -#--------------------------------------------------------------------- - -genstubs: -!if !exist($(TCLSH)) - @echo Build tclsh first! -!else - $(TCLSH) $(TOOLSDIR:\=/)/genStubs.tcl $(GENERICDIR:\=/) \ - $(GENERICDIR:\=/)/tcl.decls $(GENERICDIR:\=/)/tclInt.decls \ - $(GENERICDIR:\=/)/tclTomMath.decls - $(TCLSH) $(TOOLSDIR:\=/)/genStubs.tcl $(GENERICDIR:\=/) \ - $(GENERICDIR:\=/)/tclOO.decls -!endif - - -#---------------------------------------------------------------------- -# The following target generates the file generic/tclTomMath.h. -# It needs to be run (and the results checked) after updating -# to a new release of libtommath. -#---------------------------------------------------------------------- - -gentommath_h: -!if !exist($(TCLSH)) - @echo Build tclsh first! -!else - $(TCLSH) "$(TOOLSDIR:\=/)/fix_tommath_h.tcl" \ - "$(TOMMATHDIR:\=/)/tommath.h" \ - > "$(GENERICDIR)\tclTomMath.h" -!endif - -#--------------------------------------------------------------------- -# Build the Windows HTML help file. -#--------------------------------------------------------------------- - -# NOTE: you can define HHC on the command-line to override this -!ifndef HHC -HHC=""%ProgramFiles%\HTML Help Workshop\hhc.exe"" -!endif -HTMLDIR=$(ROOT)\html -HTMLBASE=TclTk$(VERSION) -HHPFILE=$(HTMLDIR)\$(HTMLBASE).hhp -CHMFILE=$(HTMLDIR)\$(HTMLBASE).chm - -htmlhelp: chmsetup $(CHMFILE) - -$(CHMFILE): $(DOCDIR)\* - @$(TCLSH) $(TOOLSDIR)\tcltk-man2html.tcl - @echo Compiling HTML help project - @$(HHC) <<$(HHPFILE) >NUL -[OPTIONS] -Compatibility=1.1 or later -Compiled file=$(HTMLBASE).chm -Display compile progress=no -Error log file=$(HTMLBASE).log -Language=0x409 English (United States) -Title=Tcl/Tk $(DOT_VERSION) Help -[FILES] -contents.htm -docs.css -Keywords -TclCmd -TclLib -TkCmd -TkLib -UserCmd -<< - -chmsetup: - @if not exist $(HTMLDIR)\nul mkdir $(HTMLDIR) - -#------------------------------------------------------------------------- -# Build the old-style Windows .hlp file -#------------------------------------------------------------------------- - -TCLHLPBASE = $(PROJECT)$(VERSION) -HELPFILE = $(OUT_DIR)\$(TCLHLPBASE).hlp -HELPCNT = $(OUT_DIR)\$(TCLHLPBASE).cnt -DOCTMP_DIR = $(OUT_DIR)\$(PROJECT)_docs -HELPRTF = $(DOCTMP_DIR)\$(PROJECT).rtf -MAN2HELP = $(DOCTMP_DIR)\man2help.tcl -MAN2HELP2 = $(DOCTMP_DIR)\man2help2.tcl -INDEX = $(DOCTMP_DIR)\index.tcl -BMP = $(DOCTMP_DIR)\feather.bmp -BMP_NOPATH = feather.bmp -MAN2TCL = $(DOCTMP_DIR)\man2tcl.exe - -winhelp: docsetup $(HELPFILE) - -docsetup: - @if not exist $(DOCTMP_DIR)\nul mkdir $(DOCTMP_DIR) - -$(MAN2HELP) $(MAN2HELP2) $(INDEX) $(BMP): $(TOOLSDIR)\$$(@F) - @$(CPY) $(TOOLSDIR)\$(@F) $(@D) - -$(HELPFILE): $(HELPRTF) $(BMP) - cd $(DOCTMP_DIR) - start /wait hcrtf.exe -x <<$(PROJECT).hpj -[OPTIONS] -COMPRESS=12 Hall Zeck -LCID=0x409 0x0 0x0 ; English (United States) -TITLE=Tcl/Tk Reference Manual -BMROOT=. -CNT=$(@B).cnt -HLP=$(@B).hlp - -[FILES] -$(PROJECT).rtf - -[WINDOWS] -main="Tcl/Tk Reference Manual",,27648,(r15263976),(r65535) - -[CONFIG] -BrowseButtons() -CreateButton(1, "Web", ExecFile("http://www.tcl.tk")) -CreateButton(2, "SF", ExecFile("http://sf.net/projects/tcl")) -CreateButton(3, "Wiki", ExecFile("http://wiki.tcl.tk")) -CreateButton(4, "FAQ", ExecFile("http://www.purl.org/NET/Tcl-FAQ/")) -<< - cd $(MAKEDIR) - @$(CPY) "$(DOCTMP_DIR)\$(@B).hlp" "$(OUT_DIR)" - @$(CPY) "$(DOCTMP_DIR)\$(@B).cnt" "$(OUT_DIR)" - -$(MAN2TCL): $(TOOLSDIR)\$$(@B).c - $(cc32) $(TCL_CFLAGS) -Fo$(@D)\ $(TOOLSDIR)\$(@B).c - $(link32) $(conlflags) -out:$@ -stack:16384 $(@D)\man2tcl.obj - $(_VC_MANIFEST_EMBED_EXE) - -$(HELPRTF): $(MAN2TCL) $(MAN2HELP) $(MAN2HELP2) $(INDEX) $(DOCDIR)\* - $(TCLSH) $(MAN2HELP) -bitmap $(BMP_NOPATH) $(PROJECT) $(VERSION) $(DOCDIR:\=/) - -install-docs: -!if exist("$(CHMFILE)") - @echo Installing compiled HTML help - @$(CPY) "$(CHMFILE)" "$(DOC_INSTALL_DIR)\" -!endif -!if exist("$(HELPFILE)") - @echo Installing Windows help - @$(CPY) "$(HELPFILE)" "$(DOC_INSTALL_DIR)\" - @$(CPY) "$(HELPCNT)" "$(DOC_INSTALL_DIR)\" -!endif - -#--------------------------------------------------------------------- -# Build tclConfig.sh for the TEA build system. -#--------------------------------------------------------------------- - -tclConfig: $(OUT_DIR)\tclConfig.sh - -$(OUT_DIR)\tclConfig.sh: $(WINDIR)\tclConfig.sh.in - @echo Creating tclConfig.sh - @nmakehlp -s << $** >$@ -@TCL_DLL_FILE@ $(TCLLIBNAME) -@TCL_VERSION@ $(DOTVERSION) -@TCL_MAJOR_VERSION@ $(TCL_MAJOR_VERSION) -@TCL_MINOR_VERSION@ $(TCL_MINOR_VERSION) -@TCL_PATCH_LEVEL@ $(TCL_PATCH_LEVEL) -@CC@ $(CC) -@DEFS@ $(TCL_CFLAGS) -@CFLAGS_DEBUG@ -nologo -c -W3 -YX -Fp$(TMP_DIR)\ -MDd -@CFLAGS_OPTIMIZE@ -nologo -c -W3 -YX -Fp$(TMP_DIR)\ -MD -@LDFLAGS_DEBUG@ -nologo -machine:$(MACHINE) -debug -debugtype:cv -@LDFLAGS_OPTIMIZE@ -nologo -machine:$(MACHINE) -release -opt:ref -opt:icf,3 -@TCL_DBGX@ $(SUFX) -@TCL_LIB_FILE@ $(PROJECT)$(VERSION)$(SUFX).lib -@TCL_NEEDS_EXP_FILE@ -@LIBS@ $(baselibs) -@prefix@ $(_INSTALLDIR) -@exec_prefix@ $(BIN_INSTALL_DIR) -@SHLIB_CFLAGS@ -@STLIB_CFLAGS@ -@CFLAGS_WARNING@ -W3 -@EXTRA_CFLAGS@ -YX -@SHLIB_LD@ $(link32) $(dlllflags) -@STLIB_LD@ $(lib32) -nologo -@SHLIB_LD_LIBS@ $(baselibs) -@SHLIB_SUFFIX@ .dll -@DL_LIBS@ -@LDFLAGS@ -@TCL_LD_SEARCH_FLAGS@ -@LIBOBJS@ -@RANLIB@ -@TCL_LIB_FLAG@ -@TCL_BUILD_LIB_SPEC@ -@TCL_LIB_SPEC@ $(LIB_INSTALL_DIR)\$(PROJECT)$(VERSION)$(SUFX).lib -@TCL_INCLUDE_SPEC@ -I$(INCLUDE_INSTALL_DIR) -@TCL_LIB_VERSIONS_OK@ -@TCL_SRC_DIR@ $(ROOT) -@TCL_PACKAGE_PATH@ -@TCL_STUB_LIB_FILE@ $(TCLSTUBLIBNAME) -@TCL_STUB_LIB_FLAG@ $(TCLSTUBLIBNAME) -@TCL_STUB_LIB_SPEC@ -L$(LIB_INSTALL_DIR) $(TCLSTUBLIBNAME) -@TCL_THREADS@ $(TCL_THREADS) -@TCL_BUILD_STUB_LIB_SPEC@ -L$(OUT_DIR) $(TCLSTUBLIBNAME) -@TCL_BUILD_STUB_LIB_PATH@ $(TCLSTUBLIB) -@TCL_STUB_LIB_PATH@ $(LIB_INSTALL_DIR)\$(TCLSTUBLIBNAME) -@CFG_TCL_EXPORT_FILE_SUFFIX@ $(VERSION)$(SUFX).lib -@CFG_TCL_SHARED_LIB_SUFFIX@ $(VERSION)$(SUFX).dll -@CFG_TCL_UNSHARED_LIB_SUFFIX@ $(VERSION)$(SUFX).lib -!if $(STATIC_BUILD) -@TCL_SHARED_BUILD@ 0 -!else -@TCL_SHARED_BUILD@ 1 -!endif -<< - - -#--------------------------------------------------------------------- -# The following target generates the file generic/tclDate.c -# from the yacc grammar found in generic/tclGetDate.y. This is -# only run by hand as yacc is not available in all environments. -# The name of the .c file is different than the name of the .y file -# so that make doesn't try to automatically regenerate the .c file. -#--------------------------------------------------------------------- - -gendate: - bison --output-file=$(GENERICDIR)/tclDate.c \ - --name-prefix=TclDate \ - $(GENERICDIR)/tclGetDate.y - -#--------------------------------------------------------------------- -# Special case object file targets -#--------------------------------------------------------------------- - -$(TMP_DIR)\testMain.obj: $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) -DTCL_TEST \ - -DTCL_USE_STATIC_PACKAGES=$(TCL_USE_STATIC_PACKAGES) \ - -Fo$@ $? - -$(TMP_DIR)\tclMain2.obj: $(GENERICDIR)\tclMain.c - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -DTCL_ASCII_MAIN \ - -Fo$@ $? - -$(TMP_DIR)\tclTest.obj: $(GENERICDIR)\tclTest.c - $(cc32) $(TCL_CFLAGS) -Fo$@ $? - -$(TMP_DIR)\tclTestObj.obj: $(GENERICDIR)\tclTestObj.c - $(cc32) $(TCL_CFLAGS) -Fo$@ $? - -$(TMP_DIR)\tclWinTest.obj: $(WINDIR)\tclWinTest.c - $(cc32) $(TCL_CFLAGS) -Fo$@ $? - -$(TMP_DIR)\tclZipVfs.obj: $(GENERICDIR)\tclZipVfs.c - $(cc32) $(TCL_CFLAGS) -I$(COMPATDIR)\zlib -DBUILD_tcl -Fo$@ $? - -$(TMP_DIR)\tclZlib.obj: $(GENERICDIR)\tclZlib.c - $(cc32) $(TCL_CFLAGS) -I$(COMPATDIR)\zlib -DBUILD_tcl -Fo$@ $? - -$(TMP_DIR)\tclPkgConfig.obj: $(GENERICDIR)\tclPkgConfig.c - $(cc32) -DBUILD_tcl $(TCL_CFLAGS) \ - -DCFG_INSTALL_LIBDIR="\"$(LIB_INSTALL_DIR:\=\\)\"" \ - -DCFG_INSTALL_BINDIR="\"$(BIN_INSTALL_DIR:\=\\)\"" \ - -DCFG_INSTALL_SCRDIR="\"$(SCRIPT_INSTALL_DIR:\=\\)\"" \ - -DCFG_INSTALL_INCDIR="\"$(INCLUDE_INSTALL_DIR:\=\\)\"" \ - -DCFG_INSTALL_DOCDIR="\"$(DOC_INSTALL_DIR:\=\\)\"" \ - -DCFG_RUNTIME_LIBDIR="\"$(LIB_INSTALL_DIR:\=\\)\"" \ - -DCFG_RUNTIME_BINDIR="\"$(BIN_INSTALL_DIR:\=\\)\"" \ - -DCFG_RUNTIME_SCRDIR="\"$(SCRIPT_INSTALL_DIR:\=\\)\"" \ - -DCFG_RUNTIME_INCDIR="\"$(INCLUDE_INSTALL_DIR:\=\\)\"" \ - -DCFG_RUNTIME_DOCDIR="\"$(DOC_INSTALL_DIR:\=\\)\"" \ - -Fo$@ $? - -$(TMP_DIR)\tclAppInit.obj: $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) \ - -DTCL_USE_STATIC_PACKAGES=$(TCL_USE_STATIC_PACKAGES) \ - -Fo$@ $? - -$(TMP_DIR)\tclKitInit.obj: $(WINDIR)\tclAppInit.c - $(cc32) $(TCL_CFLAGS) \ - -DTCL_USE_STATIC_PACKAGES=$(TCL_USE_STATIC_PACKAGES) \ - -DTCL_ZIPVFS \ - -Fo$@ $? - -### The following objects should be built using the stub interfaces -### *ALL* extensions need to built with -DTCL_THREADS=1 - -$(TMP_DIR)\tclWinReg.obj: $(WINDIR)\tclWinReg.c -!if $(STATIC_BUILD) - $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DSTATIC_BUILD -Fo$@ $? -!else - $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DUSE_TCL_STUBS -Fo$@ $? -!endif - - -$(TMP_DIR)\tclWinDde.obj: $(WINDIR)\tclWinDde.c -!if $(STATIC_BUILD) - $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DSTATIC_BUILD -Fo$@ $? -!else - $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DUSE_TCL_STUBS -Fo$@ $? -!endif - - -### The following objects are part of the stub library and should not -### be built as DLL objects. -Zl is used to avoid a dependency on any -### specific C run-time. - -$(TMP_DIR)\tclStubLib.obj: $(GENERICDIR)\tclStubLib.c - $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $? - -$(TMP_DIR)\tclTomMathStubLib.obj: $(GENERICDIR)\tclTomMathStubLib.c - $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $? - -$(TMP_DIR)\tclOOStubLib.obj: $(GENERICDIR)\tclOOStubLib.c - $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $? - -$(TMP_DIR)\tclsh.exe.manifest: $(WINDIR)\tclsh.exe.manifest.in - @nmakehlp -s << $** >$@ -@MACHINE@ $(MACHINE:IX86=X86) -@TCL_WIN_VERSION@ $(DOTVERSION).0.0 -<< - -#--------------------------------------------------------------------- -# Generate the source dependencies. Having dependency rules will -# improve incremental build accuracy without having to resort to a -# full rebuild just because some non-global header file like -# tclCompile.h was changed. These rules aren't needed when building -# from scratch. -#--------------------------------------------------------------------- - -depend: -!if !exist($(TCLSH)) - @echo Build tclsh first! -!else - $(TCLSH) $(TOOLSDIR:\=/)/mkdepend.tcl -vc32 -out:"$(OUT_DIR)\depend.mk" \ - -passthru:"-DBUILD_tcl $(TCL_INCLUDES)" $(GENERICDIR),$$(GENERICDIR) \ - $(COMPATDIR),$$(COMPATDIR) $(TOMMATHDIR),$$(TOMMATHDIR) $(WINDIR),$$(WINDIR) @<< -$(TCLOBJS) -<< -!endif - -#--------------------------------------------------------------------- -# Dependency rules -#--------------------------------------------------------------------- - -!if exist("$(OUT_DIR)\depend.mk") -!include "$(OUT_DIR)\depend.mk" -!message *** Dependency rules in use. -!else -!message *** Dependency rules are not being used. -!endif - -### add a spacer in the output -!message - - -#--------------------------------------------------------------------- -# Implicit rules. A limitation exists with nmake that requires that -# source directory can not contain spaces in the path. This an -# absolute. -#--------------------------------------------------------------------- - -{$(WINDIR)}.c{$(TMP_DIR)}.obj:: - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<< -$< -<< - -{$(TOMMATHDIR)}.c{$(TMP_DIR)}.obj:: - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<< -$< -<< - -{$(GENERICDIR)}.c{$(TMP_DIR)}.obj:: - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<< -$< -<< - -{$(COMPATDIR)}.c{$(TMP_DIR)}.obj:: - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<< -$< -<< - -{$(COMPATDIR)\zlib}.c{$(TMP_DIR)}.obj:: - $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<< -$< -<< - -{$(WINDIR)}.rc{$(TMP_DIR)}.res: - $(rc32) -fo $@ -r -i "$(GENERICDIR)" -i "$(TMP_DIR)" \ - -d DEBUG=$(DEBUG) -d UNCHECKED=$(UNCHECKED) \ - -d TCL_THREADS=$(TCL_THREADS) \ - -d STATIC_BUILD=$(STATIC_BUILD) \ - $< - -$(TMP_DIR)\tclsh.res: $(TMP_DIR)\tclsh.exe.manifest - -.SUFFIXES: -.SUFFIXES:.c .rc - - -#--------------------------------------------------------------------- -# Installation. -#--------------------------------------------------------------------- - -install-binaries: - @echo Installing to '$(_INSTALLDIR)' - @echo Installing $(TCLLIBNAME) -!if "$(TCLLIB)" != "$(TCLIMPLIB)" - @$(CPY) "$(TCLLIB)" "$(BIN_INSTALL_DIR)\" -!endif - @$(CPY) "$(TCLIMPLIB)" "$(LIB_INSTALL_DIR)\" -!if exist($(TCLSH)) - @echo Installing $(TCLSHNAME) - @$(CPY) "$(TCLSH)" "$(BIN_INSTALL_DIR)\" -!endif - @echo Installing $(TCLSTUBLIBNAME) - @$(CPY) "$(TCLSTUBLIB)" "$(LIB_INSTALL_DIR)\" - -#" emacs fix - -install-libraries: tclConfig install-msgs install-tzdata - @if not exist "$(SCRIPT_INSTALL_DIR)$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.2$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.2" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.3$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.3" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5" - @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6$(NULL)" \ - $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6" - @echo Installing header files - @$(CPY) "$(GENERICDIR)\tcl.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclDecls.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclOO.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclOODecls.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclPlatDecls.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclTomMath.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(GENERICDIR)\tclTomMathDecls.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(TOMMATHDIR)\tommath_class.h" "$(INCLUDE_INSTALL_DIR)\" - @$(CPY) "$(TOMMATHDIR)\tommath_superclass.h" "$(INCLUDE_INSTALL_DIR)\" - @echo Installing library files to $(SCRIPT_INSTALL_DIR) - @$(CPY) "$(ROOT)\library\history.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\init.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\clock.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\tm.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\parray.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\safe.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\tclIndex" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\package.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\word.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(ROOT)\library\auto.tcl" "$(SCRIPT_INSTALL_DIR)\" - @$(CPY) "$(OUT_DIR)\tclConfig.sh" "$(LIB_INSTALL_DIR)\" - @$(CPY) "$(WINDIR)\tclooConfig.sh" "$(LIB_INSTALL_DIR)\" - @echo Installing library http1.0 directory - @$(CPY) "$(ROOT)\library\http1.0\*.tcl" \ - "$(SCRIPT_INSTALL_DIR)\http1.0\" - @echo Installing library opt0.4 directory - @$(CPY) "$(ROOT)\library\opt\*.tcl" \ - "$(SCRIPT_INSTALL_DIR)\opt0.4\" - @echo Installing package http $(PKG_HTTP_VER) as a Tcl Module - @$(COPY) "$(ROOT)\library\http\http.tcl" \ - "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6\http-$(PKG_HTTP_VER).tm" - @echo Installing package msgcat $(PKG_MSGCAT_VER) as a Tcl Module - @$(COPY) "$(ROOT)\library\msgcat\msgcat.tcl" \ - "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5\msgcat-$(PKG_MSGCAT_VER).tm" - @echo Installing package tcltest $(PKG_TCLTEST_VER) as a Tcl Module - @$(COPY) "$(ROOT)\library\tcltest\tcltest.tcl" \ - "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5\tcltest-$(PKG_TCLTEST_VER).tm" - @echo Installing package platform $(PKG_PLATFORM_VER) as a Tcl Module - @$(COPY) "$(ROOT)\library\platform\platform.tcl" \ - "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform-$(PKG_PLATFORM_VER).tm" - @echo Installing package platform::shell $(PKG_SHELL_VER) as a Tcl Module - @$(COPY) "$(ROOT)\library\platform\shell.tcl" \ - "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform\shell-$(PKG_SHELL_VER).tm" - @echo Installing $(TCLDDELIBNAME) -!if $(STATIC_BUILD) -!if !$(TCL_USE_STATIC_PACKAGES) - @$(CPY) "$(TCLDDELIB)" "$(LIB_INSTALL_DIR)\" -!endif -!else - @$(CPY) "$(TCLDDELIB)" "$(LIB_INSTALL_DIR)\dde$(DDEDOTVERSION)\" - @$(CPY) "$(ROOT)\library\dde\pkgIndex.tcl" \ - "$(LIB_INSTALL_DIR)\dde$(DDEDOTVERSION)\" -!endif - @echo Installing $(TCLREGLIBNAME) -!if $(STATIC_BUILD) -!if !$(TCL_USE_STATIC_PACKAGES) - @$(CPY) "$(TCLREGLIB)" "$(LIB_INSTALL_DIR)\" -!endif -!else - @$(CPY) "$(TCLREGLIB)" "$(LIB_INSTALL_DIR)\reg$(REGDOTVERSION)\" - @$(CPY) "$(ROOT)\library\reg\pkgIndex.tcl" \ - "$(LIB_INSTALL_DIR)\reg$(REGDOTVERSION)\" -!endif - @echo Installing encodings - @$(CPY) "$(ROOT)\library\encoding\*.enc" \ - "$(SCRIPT_INSTALL_DIR)\encoding\" - -#" emacs fix - -install-tzdata: - @echo Installing time zone data - @set TCL_LIBRARY=$(ROOT:\=/)/library - @$(TCLSH_NATIVE) "$(ROOT:\=/)/tools/installData.tcl" \ - "$(ROOT:\=/)/library/tzdata" "$(SCRIPT_INSTALL_DIR)/tzdata" - -install-msgs: - @echo Installing message catalogs - @set TCL_LIBRARY=$(ROOT:\=/)/library - @$(TCLSH_NATIVE) "$(ROOT:\=/)/tools/installData.tcl" \ - "$(ROOT:\=/)/library/msgs" "$(SCRIPT_INSTALL_DIR)/msgs" - -#--------------------------------------------------------------------- -# Clean up -#--------------------------------------------------------------------- - -tidy: -!if "$(TCLLIB)" != "$(TCLIMPLIB)" - @echo Removing $(TCLLIB) ... - @if exist $(TCLLIB) del $(TCLLIB) -!endif - @echo Removing $(TCLIMPLIB) ... - @if exist $(TCLIMPLIB) del $(TCLIMPLIB) - @echo Removing $(TCLSH) ... - @if exist $(TCLSH) del $(TCLSH) - @echo Removing $(TCLTEST) ... - @if exist $(TCLTEST) del $(TCLTEST) - @echo Removing $(TCLDDELIB) ... - @if exist $(TCLDDELIB) del $(TCLDDELIB) - @echo Removing $(TCLREGLIB) ... - @if exist $(TCLREGLIB) del $(TCLREGLIB) - -clean: clean-pkgs - @echo Cleaning $(TMP_DIR)\* ... - @if exist $(TMP_DIR)\nul $(RMDIR) $(TMP_DIR) - @echo Cleaning $(WINDIR)\nmakehlp.obj ... - @if exist $(WINDIR)\nmakehlp.obj del $(WINDIR)\nmakehlp.obj - @echo Cleaning $(WINDIR)\nmakehlp.exe ... - @if exist $(WINDIR)\nmakehlp.exe del $(WINDIR)\nmakehlp.exe - @echo Cleaning $(WINDIR)\_junk.pch ... - @if exist $(WINDIR)\_junk.pch del $(WINDIR)\_junk.pch - @echo Cleaning $(WINDIR)\vercl.x ... - @if exist $(WINDIR)\vercl.x del $(WINDIR)\vercl.x - @echo Cleaning $(WINDIR)\vercl.i ... - @if exist $(WINDIR)\vercl.i del $(WINDIR)\vercl.i - @echo Cleaning $(WINDIR)\versions.vc ... - @if exist $(WINDIR)\versions.vc del $(WINDIR)\versions.vc - -realclean: hose - -hose: - @echo Hosing $(OUT_DIR)\* ... - @if exist $(OUT_DIR)\nul $(RMDIR) $(OUT_DIR) - -# Local Variables: -# mode: makefile -# End: +#-------------------------------------------------------------
+# makefile.vc --
+#
+# Microsoft Visual C++ makefile for use with nmake.exe v1.62+ (VC++ 5.0+)
+#
+# See the file "license.terms" for information on usage and redistribution
+# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
+#
+# Copyright (c) 1995-1996 Sun Microsystems, Inc.
+# Copyright (c) 1998-2000 Ajuba Solutions.
+# Copyright (c) 2001-2005 ActiveState Corporation.
+# Copyright (c) 2001-2004 David Gravereaux.
+# Copyright (c) 2003-2008 Pat Thoyts.
+#------------------------------------------------------------------------------
+
+# Check to see we are configured to build with MSVC (MSDEVDIR, MSVCDIR or
+# VCINSTALLDIR) or with the MS Platform SDK (MSSDK or WindowsSDKDir)
+!if !defined(MSDEVDIR) && !defined(MSVCDIR) && !defined(VCINSTALLDIR) && !defined(MSSDK) && !defined(WINDOWSSDKDIR)
+MSG = ^
+You need to run vcvars32.bat from Developer Studio or setenv.bat from the^
+Platform SDK first to setup the environment. Jump to this line to read^
+the build instructions.
+!error $(MSG)
+!endif
+
+#------------------------------------------------------------------------------
+# HOW TO USE this makefile:
+#
+# 1) It is now necessary to have MSVCDir, MSDevDir or MSSDK set in the
+# environment. This is used as a check to see if vcvars32.bat had been
+# run prior to running nmake or during the installation of Microsoft
+# Visual C++, MSVCDir had been set globally and the PATH adjusted.
+# Either way is valid.
+#
+# You'll need to run vcvars32.bat contained in the MsDev's vc(98)/bin
+# directory to setup the proper environment, if needed, for your
+# current setup. This is a needed bootstrap requirement and allows the
+# swapping of different environments to be easier.
+#
+# 2) To use the Platform SDK (not expressly needed), run setenv.bat after
+# vcvars32.bat according to the instructions for it. This can also
+# turn on the 64-bit compiler, if your SDK has it.
+#
+# 3) Targets are:
+# release -- Builds the core, the shell and the dlls. (default)
+# dlls -- Just builds the windows extensions
+# shell -- Just builds the shell and the core.
+# core -- Only builds the core [tclXX.(dll|lib)].
+# all -- Builds everything.
+# test -- Builds and runs the test suite.
+# tcltest -- Just builds the test shell.
+# install -- Installs the built binaries and libraries to $(INSTALLDIR)
+# as the root of the install tree.
+# tidy/clean/hose -- varying levels of cleaning.
+# genstubs -- Rebuilds the Stubs table and support files (dev only).
+# depend -- Generates an accurate set of source dependancies for this
+# makefile. Helpful to avoid problems when the sources are
+# refreshed and you rebuild, but can "overbuild" when common
+# headers like tclInt.h just get small changes.
+# htmlhelp -- Builds a Windows .chm help file for Tcl and Tk from the
+# troff manual pages found in $(ROOT)\doc. You need to
+# have installed the HTML Help Compiler package from Microsoft
+# to produce the .chm file.
+# winhelp -- (deprecated) Builds the windows .hlp file for Tcl from
+# the troff man files found in $(ROOT)\doc. This type of
+# help file is deprecated by Microsoft in favour of html
+# help files (.chm)
+#
+# 4) Macros usable on the commandline:
+# INSTALLDIR=<path>
+# Sets where to install Tcl from the built binaries.
+# C:\Progra~1\Tcl is assumed when not specified.
+#
+# OPTS=loimpact,msvcrt,nothreads,pdbs,profile,static,staticpkg,symbols,thrdalloc,tclalloc,unchecked,none
+# Sets special options for the core. The default is for none.
+# Any combination of the above may be used (comma separated).
+# 'none' will over-ride everything to nothing.
+#
+# loimpact = Adds a flag for how NT treats the heap to keep memory
+# in use, low. This is said to impact alloc performance.
+# msvcrt = Affects the static option only to switch it from
+# using libcmt(d) as the C runtime [by default] to
+# msvcrt(d). This is useful for static embedding
+# support.
+# nothreads= Turns off full multithreading support.
+# pdbs = Build detached symbols for release builds.
+# profile = Adds profiling hooks. Map file is assumed.
+# static = Builds a static library of the core instead of a
+# dll. The static library will contain the dde and reg
+# extensions. External applications who want to use
+# this, need to link with the stub library as well as
+# the static Tcl library.The shell will be static (and
+# large), as well.
+# staticpkg = Affects the static option only to switch
+# tclshXX.exe to have the dde and reg extension linked
+# inside it.
+# symbols = Debug build. Links to the debug C runtime, disables
+# optimizations and creates pdb symbols files.
+# thrdalloc = Use the thread allocator (shared global free pool)
+# This is the default on threaded builds.
+# tclalloc = Use the old non-thread allocator
+# unchecked= Allows a symbols build to not use the debug
+# enabled runtime (msvcrt.dll not msvcrtd.dll
+# or libcmt.lib not libcmtd.lib).
+#
+# STATS=compdbg,memdbg,none
+# Sets optional memory and bytecode compiler debugging code added
+# to the core. The default is for none. Any combination of the
+# above may be used (comma separated). 'none' will over-ride
+# everything to nothing.
+#
+# compdbg = Enables byte compilation logging.
+# memdbg = Enables the debugging memory allocator.
+#
+# CHECKS=64bit,fullwarn,nodep,none
+# Sets special macros for checking compatability.
+#
+# 64bit = Enable 64bit portability warnings (if available)
+# fullwarn = Builds with full compiler and link warnings enabled.
+# Very verbose.
+# nodep = Turns off compatability macros to ensure the core
+# isn't being built with deprecated functions.
+#
+# MACHINE=(ALPHA|AMD64|IA64|IX86)
+# Set the machine type used for the compiler, linker, and
+# resource compiler. This hook is needed to tell the tools
+# when alternate platforms are requested. IX86 is the default
+# when not specified. If the CPU environment variable has been
+# set (ie: recent Platform SDK) then MACHINE is set from CPU.
+#
+# TMP_DIR=<path>
+# OUT_DIR=<path>
+# Hooks to allow the intermediate and output directories to be
+# changed. $(OUT_DIR) is assumed to be
+# $(BINROOT)\(Release|Debug) based on if symbols are requested.
+# $(TMP_DIR) will de $(OUT_DIR)\<buildtype> by default.
+#
+# TESTPAT=<file>
+# Reads the tests requested to be run from this file.
+#
+# CFG_ENCODING=encoding
+# name of encoding for configuration information. Defaults
+# to cp1252
+#
+# 5) Examples:
+#
+# Basic syntax of calling nmake looks like this:
+# nmake [-nologo] -f makefile.vc [target|macrodef [target|macrodef] [...]]
+#
+# Standard (no frills)
+# c:\tcl_src\win\>c:\progra~1\micros~1\vc98\bin\vcvars32.bat
+# Setting environment for using Microsoft Visual C++ tools.
+# c:\tcl_src\win\>nmake -f makefile.vc release
+# c:\tcl_src\win\>nmake -f makefile.vc install INSTALLDIR=c:\progra~1\tcl
+#
+# Building for Win64
+# c:\tcl_src\win\>c:\progra~1\micros~1\vc98\bin\vcvars32.bat
+# Setting environment for using Microsoft Visual C++ tools.
+# c:\tcl_src\win\>c:\progra~1\platfo~1\setenv.bat /pre64 /RETAIL
+# Targeting Windows pre64 RETAIL
+# c:\tcl_src\win\>nmake -f makefile.vc MACHINE=IA64
+#
+#------------------------------------------------------------------------------
+#==============================================================================
+###############################################################################
+
+
+# //==================================================================\\
+# >>[ -> Do not modify below this line. <- ]<<
+# >>[ Please, use the commandline macros to modify how Tcl is built. ]<<
+# >>[ If you need more features, send us a patch for more macros. ]<<
+# \\==================================================================//
+
+
+###############################################################################
+#==============================================================================
+#------------------------------------------------------------------------------
+
+!if !exist("makefile.vc")
+MSG = ^
+You must run this makefile only from the directory it is in.^
+Please `cd` to its location first.
+!error $(MSG)
+!endif
+
+PROJECT = tcl
+!include "rules.vc"
+
+STUBPREFIX = $(PROJECT)stub
+DOTVERSION = $(TCL_MAJOR_VERSION).$(TCL_MINOR_VERSION)
+VERSION = $(TCL_MAJOR_VERSION)$(TCL_MINOR_VERSION)
+
+DDEDOTVERSION = 1.4
+DDEVERSION = $(DDEDOTVERSION:.=)
+
+REGDOTVERSION = 1.3
+REGVERSION = $(REGDOTVERSION:.=)
+
+BINROOT = $(MAKEDIR) # originally .
+ROOT = $(MAKEDIR)\.. # originally ..
+
+TCLIMPLIB = $(OUT_DIR)\$(PROJECT)$(VERSION)$(SUFX).lib
+TCLLIBNAME = $(PROJECT)$(VERSION)$(SUFX).$(EXT)
+TCLLIB = $(OUT_DIR)\$(TCLLIBNAME)
+
+TCLSTUBLIBNAME = $(STUBPREFIX)$(VERSION).lib
+TCLSTUBLIB = $(OUT_DIR)\$(TCLSTUBLIBNAME)
+
+TCLSHNAME = $(PROJECT)sh$(VERSION)$(SUFX).exe
+TCLSH = $(OUT_DIR)\$(TCLSHNAME)
+
+TCLREGLIBNAME = $(PROJECT)reg$(REGVERSION)$(SUFX:t=).$(EXT)
+TCLREGLIB = $(OUT_DIR)\$(TCLREGLIBNAME)
+
+TCLDDELIBNAME = $(PROJECT)dde$(DDEVERSION)$(SUFX:t=).$(EXT)
+TCLDDELIB = $(OUT_DIR)\$(TCLDDELIBNAME)
+
+TCLTEST = $(OUT_DIR)\$(PROJECT)test.exe
+CAT32 = $(OUT_DIR)\cat32.exe
+
+# Can we run what we build? IX86 runs on all architectures.
+!ifndef TCLSH_NATIVE
+!if "$(MACHINE)" == "IX86" || "$(MACHINE)" == "$(NATIVE_ARCH)"
+TCLSH_NATIVE = $(TCLSH)
+!else
+!error You must explicitly set TCLSH_NATIVE for cross-compilation
+!endif
+!endif
+
+### Make sure we use backslash only.
+LIB_INSTALL_DIR = $(_INSTALLDIR)\lib
+BIN_INSTALL_DIR = $(_INSTALLDIR)\bin
+DOC_INSTALL_DIR = $(_INSTALLDIR)\doc
+SCRIPT_INSTALL_DIR = $(_INSTALLDIR)\lib\tcl$(DOTVERSION)
+INCLUDE_INSTALL_DIR = $(_INSTALLDIR)\include
+
+TCLSHOBJS = \
+ $(TMP_DIR)\tclAppInit.obj \
+!if !$(STATIC_BUILD)
+!if $(TCL_USE_STATIC_PACKAGES)
+ $(TMP_DIR)\tclWinReg.obj \
+ $(TMP_DIR)\tclWinDde.obj \
+!endif
+!endif
+ $(TMP_DIR)\tclsh.res
+
+TCLTESTOBJS = \
+ $(TMP_DIR)\tclTest.obj \
+ $(TMP_DIR)\tclTestObj.obj \
+ $(TMP_DIR)\tclTestProcBodyObj.obj \
+ $(TMP_DIR)\tclThreadTest.obj \
+ $(TMP_DIR)\tclWinTest.obj \
+!if !$(STATIC_BUILD)
+!if $(TCL_USE_STATIC_PACKAGES)
+ $(TMP_DIR)\tclWinReg.obj \
+ $(TMP_DIR)\tclWinDde.obj \
+!endif
+!endif
+ $(TMP_DIR)\testMain.obj
+
+COREOBJS = \
+ $(TMP_DIR)\regcomp.obj \
+ $(TMP_DIR)\regerror.obj \
+ $(TMP_DIR)\regexec.obj \
+ $(TMP_DIR)\regfree.obj \
+ $(TMP_DIR)\tclAlloc.obj \
+ $(TMP_DIR)\tclAssembly.obj \
+ $(TMP_DIR)\tclAsync.obj \
+ $(TMP_DIR)\tclBasic.obj \
+ $(TMP_DIR)\tclBinary.obj \
+ $(TMP_DIR)\tclCkalloc.obj \
+ $(TMP_DIR)\tclClock.obj \
+ $(TMP_DIR)\tclCmdAH.obj \
+ $(TMP_DIR)\tclCmdIL.obj \
+ $(TMP_DIR)\tclCmdMZ.obj \
+ $(TMP_DIR)\tclCompCmds.obj \
+ $(TMP_DIR)\tclCompCmdsGR.obj \
+ $(TMP_DIR)\tclCompCmdsSZ.obj \
+ $(TMP_DIR)\tclCompExpr.obj \
+ $(TMP_DIR)\tclCompile.obj \
+ $(TMP_DIR)\tclConfig.obj \
+ $(TMP_DIR)\tclDate.obj \
+ $(TMP_DIR)\tclDictObj.obj \
+ $(TMP_DIR)\tclDisassemble.obj \
+ $(TMP_DIR)\tclEncoding.obj \
+ $(TMP_DIR)\tclEnsemble.obj \
+ $(TMP_DIR)\tclEnv.obj \
+ $(TMP_DIR)\tclEvent.obj \
+ $(TMP_DIR)\tclExecute.obj \
+ $(TMP_DIR)\tclFCmd.obj \
+ $(TMP_DIR)\tclFileName.obj \
+ $(TMP_DIR)\tclGet.obj \
+ $(TMP_DIR)\tclHash.obj \
+ $(TMP_DIR)\tclHistory.obj \
+ $(TMP_DIR)\tclIndexObj.obj \
+ $(TMP_DIR)\tclInterp.obj \
+ $(TMP_DIR)\tclIO.obj \
+ $(TMP_DIR)\tclIOCmd.obj \
+ $(TMP_DIR)\tclIOGT.obj \
+ $(TMP_DIR)\tclIOSock.obj \
+ $(TMP_DIR)\tclIOUtil.obj \
+ $(TMP_DIR)\tclIORChan.obj \
+ $(TMP_DIR)\tclIORTrans.obj \
+ $(TMP_DIR)\tclLink.obj \
+ $(TMP_DIR)\tclListObj.obj \
+ $(TMP_DIR)\tclLiteral.obj \
+ $(TMP_DIR)\tclLoad.obj \
+ $(TMP_DIR)\tclMain.obj \
+ $(TMP_DIR)\tclMain2.obj \
+ $(TMP_DIR)\tclNamesp.obj \
+ $(TMP_DIR)\tclNotify.obj \
+ $(TMP_DIR)\tclOO.obj \
+ $(TMP_DIR)\tclOOBasic.obj \
+ $(TMP_DIR)\tclOOCall.obj \
+ $(TMP_DIR)\tclOODefineCmds.obj \
+ $(TMP_DIR)\tclOOInfo.obj \
+ $(TMP_DIR)\tclOOMethod.obj \
+ $(TMP_DIR)\tclOOStubInit.obj \
+ $(TMP_DIR)\tclObj.obj \
+ $(TMP_DIR)\tclOptimize.obj \
+ $(TMP_DIR)\tclPanic.obj \
+ $(TMP_DIR)\tclParse.obj \
+ $(TMP_DIR)\tclPathObj.obj \
+ $(TMP_DIR)\tclPipe.obj \
+ $(TMP_DIR)\tclPkg.obj \
+ $(TMP_DIR)\tclPkgConfig.obj \
+ $(TMP_DIR)\tclPosixStr.obj \
+ $(TMP_DIR)\tclPreserve.obj \
+ $(TMP_DIR)\tclProc.obj \
+ $(TMP_DIR)\tclRegexp.obj \
+ $(TMP_DIR)\tclResolve.obj \
+ $(TMP_DIR)\tclResult.obj \
+ $(TMP_DIR)\tclScan.obj \
+ $(TMP_DIR)\tclStringObj.obj \
+ $(TMP_DIR)\tclStrToD.obj \
+ $(TMP_DIR)\tclStubInit.obj \
+ $(TMP_DIR)\tclThread.obj \
+ $(TMP_DIR)\tclThreadAlloc.obj \
+ $(TMP_DIR)\tclThreadJoin.obj \
+ $(TMP_DIR)\tclThreadStorage.obj \
+ $(TMP_DIR)\tclTimer.obj \
+ $(TMP_DIR)\tclTomMathInterface.obj \
+ $(TMP_DIR)\tclTrace.obj \
+ $(TMP_DIR)\tclUtf.obj \
+ $(TMP_DIR)\tclUtil.obj \
+ $(TMP_DIR)\tclVar.obj \
+ $(TMP_DIR)\tclZlib.obj
+
+ZLIBOBJS = \
+ $(TMP_DIR)\adler32.obj \
+ $(TMP_DIR)\compress.obj \
+ $(TMP_DIR)\crc32.obj \
+ $(TMP_DIR)\deflate.obj \
+ $(TMP_DIR)\infback.obj \
+ $(TMP_DIR)\inffast.obj \
+ $(TMP_DIR)\inflate.obj \
+ $(TMP_DIR)\inftrees.obj \
+ $(TMP_DIR)\trees.obj \
+ $(TMP_DIR)\uncompr.obj \
+ $(TMP_DIR)\zutil.obj
+
+TOMMATHOBJS = \
+ $(TMP_DIR)\bncore.obj \
+ $(TMP_DIR)\bn_reverse.obj \
+ $(TMP_DIR)\bn_fast_s_mp_mul_digs.obj \
+ $(TMP_DIR)\bn_fast_s_mp_sqr.obj \
+ $(TMP_DIR)\bn_mp_add.obj \
+ $(TMP_DIR)\bn_mp_add_d.obj \
+ $(TMP_DIR)\bn_mp_and.obj \
+ $(TMP_DIR)\bn_mp_clamp.obj \
+ $(TMP_DIR)\bn_mp_clear.obj \
+ $(TMP_DIR)\bn_mp_clear_multi.obj \
+ $(TMP_DIR)\bn_mp_cmp.obj \
+ $(TMP_DIR)\bn_mp_cmp_d.obj \
+ $(TMP_DIR)\bn_mp_cmp_mag.obj \
+ $(TMP_DIR)\bn_mp_cnt_lsb.obj \
+ $(TMP_DIR)\bn_mp_copy.obj \
+ $(TMP_DIR)\bn_mp_count_bits.obj \
+ $(TMP_DIR)\bn_mp_div.obj \
+ $(TMP_DIR)\bn_mp_div_d.obj \
+ $(TMP_DIR)\bn_mp_div_2.obj \
+ $(TMP_DIR)\bn_mp_div_2d.obj \
+ $(TMP_DIR)\bn_mp_div_3.obj \
+ $(TMP_DIR)\bn_mp_exch.obj \
+ $(TMP_DIR)\bn_mp_expt_d.obj \
+ $(TMP_DIR)\bn_mp_grow.obj \
+ $(TMP_DIR)\bn_mp_init.obj \
+ $(TMP_DIR)\bn_mp_init_copy.obj \
+ $(TMP_DIR)\bn_mp_init_multi.obj \
+ $(TMP_DIR)\bn_mp_init_set.obj \
+ $(TMP_DIR)\bn_mp_init_set_int.obj \
+ $(TMP_DIR)\bn_mp_init_size.obj \
+ $(TMP_DIR)\bn_mp_karatsuba_mul.obj \
+ $(TMP_DIR)\bn_mp_karatsuba_sqr.obj \
+ $(TMP_DIR)\bn_mp_lshd.obj \
+ $(TMP_DIR)\bn_mp_mod.obj \
+ $(TMP_DIR)\bn_mp_mod_2d.obj \
+ $(TMP_DIR)\bn_mp_mul.obj \
+ $(TMP_DIR)\bn_mp_mul_2.obj \
+ $(TMP_DIR)\bn_mp_mul_2d.obj \
+ $(TMP_DIR)\bn_mp_mul_d.obj \
+ $(TMP_DIR)\bn_mp_neg.obj \
+ $(TMP_DIR)\bn_mp_or.obj \
+ $(TMP_DIR)\bn_mp_radix_size.obj \
+ $(TMP_DIR)\bn_mp_radix_smap.obj \
+ $(TMP_DIR)\bn_mp_read_radix.obj \
+ $(TMP_DIR)\bn_mp_rshd.obj \
+ $(TMP_DIR)\bn_mp_set.obj \
+ $(TMP_DIR)\bn_mp_set_int.obj \
+ $(TMP_DIR)\bn_mp_shrink.obj \
+ $(TMP_DIR)\bn_mp_sqr.obj \
+ $(TMP_DIR)\bn_mp_sqrt.obj \
+ $(TMP_DIR)\bn_mp_sub.obj \
+ $(TMP_DIR)\bn_mp_sub_d.obj \
+ $(TMP_DIR)\bn_mp_to_unsigned_bin.obj \
+ $(TMP_DIR)\bn_mp_to_unsigned_bin_n.obj \
+ $(TMP_DIR)\bn_mp_toom_mul.obj \
+ $(TMP_DIR)\bn_mp_toom_sqr.obj \
+ $(TMP_DIR)\bn_mp_toradix_n.obj \
+ $(TMP_DIR)\bn_mp_unsigned_bin_size.obj \
+ $(TMP_DIR)\bn_mp_xor.obj \
+ $(TMP_DIR)\bn_mp_zero.obj \
+ $(TMP_DIR)\bn_s_mp_add.obj \
+ $(TMP_DIR)\bn_s_mp_mul_digs.obj \
+ $(TMP_DIR)\bn_s_mp_sqr.obj \
+ $(TMP_DIR)\bn_s_mp_sub.obj
+
+PLATFORMOBJS = \
+ $(TMP_DIR)\tclWin32Dll.obj \
+ $(TMP_DIR)\tclWinChan.obj \
+ $(TMP_DIR)\tclWinConsole.obj \
+ $(TMP_DIR)\tclWinError.obj \
+ $(TMP_DIR)\tclWinFCmd.obj \
+ $(TMP_DIR)\tclWinFile.obj \
+ $(TMP_DIR)\tclWinInit.obj \
+ $(TMP_DIR)\tclWinLoad.obj \
+ $(TMP_DIR)\tclWinNotify.obj \
+ $(TMP_DIR)\tclWinPipe.obj \
+ $(TMP_DIR)\tclWinSerial.obj \
+ $(TMP_DIR)\tclWinSock.obj \
+ $(TMP_DIR)\tclWinThrd.obj \
+ $(TMP_DIR)\tclWinTime.obj \
+!if $(STATIC_BUILD)
+ $(TMP_DIR)\tclWinReg.obj \
+ $(TMP_DIR)\tclWinDde.obj \
+!else
+ $(TMP_DIR)\tcl.res
+!endif
+
+TCLOBJS = $(COREOBJS) $(ZLIBOBJS) $(TOMMATHOBJS) $(PLATFORMOBJS)
+
+TCLSTUBOBJS = \
+ $(TMP_DIR)\tclStubLib.obj \
+ $(TMP_DIR)\tclTomMathStubLib.obj \
+ $(TMP_DIR)\tclOOStubLib.obj
+
+### The following paths CANNOT have spaces in them.
+COMPATDIR = $(ROOT)\compat
+DOCDIR = $(ROOT)\doc
+GENERICDIR = $(ROOT)\generic
+TOMMATHDIR = $(ROOT)\libtommath
+TOOLSDIR = $(ROOT)\tools
+WINDIR = $(ROOT)\win
+PKGSDIR = $(ROOT)\pkgs
+
+#---------------------------------------------------------------------
+# Compile flags
+#---------------------------------------------------------------------
+
+!if !$(DEBUG)
+!if $(OPTIMIZING)
+### This cranks the optimization level to maximize speed
+cdebug = -O2 $(OPTIMIZATIONS)
+!else
+cdebug =
+!endif
+!if $(SYMBOLS)
+cdebug = $(cdebug) -Zi
+!endif
+!else if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64"
+### Warnings are too many, can't support warnings into errors.
+cdebug = -Zi -Od $(DEBUGFLAGS)
+!else
+cdebug = -Zi -WX $(DEBUGFLAGS)
+!endif
+
+### Declarations common to all compiler options
+cwarn = $(WARNINGS) -D _CRT_SECURE_NO_DEPRECATE -D _CRT_NONSTDC_NO_DEPRECATE
+cflags = -nologo -c $(COMPILERFLAGS) $(cwarn) -Fp$(TMP_DIR)^\
+
+!if $(MSVCRT)
+!if $(DEBUG) && !$(UNCHECKED)
+crt = -MDd
+!else
+crt = -MD
+!endif
+!else
+!if $(DEBUG) && !$(UNCHECKED)
+crt = -MTd
+!else
+crt = -MT
+!endif
+!endif
+
+TCL_INCLUDES = -I"$(WINDIR)" -I"$(GENERICDIR)" -I"$(TOMMATHDIR)"
+TCL_DEFINES = -DTCL_TOMMATH -DMP_PREC=4 -Dinline=__inline -DHAVE_ZLIB=1
+BASE_CFLAGS = $(cflags) $(cdebug) $(crt) $(TCL_INCLUDES) $(TCL_DEFINES)
+CON_CFLAGS = $(cflags) $(cdebug) $(crt) -DCONSOLE
+TCL_CFLAGS = $(BASE_CFLAGS) $(OPTDEFINES)
+STUB_CFLAGS = $(cflags) $(cdebug) $(OPTDEFINES)
+
+
+#---------------------------------------------------------------------
+# Link flags
+#---------------------------------------------------------------------
+
+!if $(DEBUG)
+ldebug = -debug -debugtype:cv
+!else
+ldebug = -release -opt:ref -opt:icf,3
+!if $(SYMBOLS)
+ldebug = $(ldebug) -debug -debugtype:cv
+!endif
+!endif
+
+### Declarations common to all linker options
+lflags = -nologo -machine:$(MACHINE) $(LINKERFLAGS) $(ldebug)
+
+!if $(PROFILE)
+lflags = $(lflags) -profile
+!endif
+
+!if $(MSVCRT) && !($(DEBUG) && !$(UNCHECKED)) && $(VCVERSION) >= 1900
+lflags = $(lflags) -nodefaultlib:libucrt.lib
+!endif
+
+!if $(ALIGN98_HACK) && !$(STATIC_BUILD)
+### Align sections for PE size savings.
+lflags = $(lflags) -opt:nowin98
+!else if !$(ALIGN98_HACK) && $(STATIC_BUILD)
+### Align sections for speed in loading by choosing the virtual page size.
+lflags = $(lflags) -align:4096
+!endif
+
+!if $(LOIMPACT)
+lflags = $(lflags) -ws:aggressive
+!endif
+
+dlllflags = $(lflags) -dll
+conlflags = $(lflags) -subsystem:console
+guilflags = $(lflags) -subsystem:windows
+
+baselibs = netapi32.lib kernel32.lib user32.lib advapi32.lib userenv.lib ws2_32.lib
+# Avoid 'unresolved external symbol __security_cookie' errors.
+# c.f. http://support.microsoft.com/?id=894573
+!if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64"
+!if $(VCVERSION) > 1399 && $(VCVERSION) < 1500
+baselibs = $(baselibs) bufferoverflowU.lib
+!endif
+!endif
+!if $(MSVCRT) && !($(DEBUG) && !$(UNCHECKED)) && $(VCVERSION) >= 1900
+baselibs = $(baselibs) ucrt.lib
+!endif
+
+#---------------------------------------------------------------------
+# TclTest flags
+#---------------------------------------------------------------------
+
+!if "$(TESTPAT)" != ""
+TESTFLAGS = $(TESTFLAGS) -file $(TESTPAT)
+!endif
+
+
+#---------------------------------------------------------------------
+# Project specific targets
+#---------------------------------------------------------------------
+
+release: setup $(TCLSH) $(TCLSTUBLIB) dlls pkgs
+core: setup $(TCLLIB) $(TCLSTUBLIB)
+shell: setup $(TCLSH)
+dlls: setup $(TCLREGLIB) $(TCLDDELIB)
+all: setup $(TCLSH) $(TCLSTUBLIB) dlls $(CAT32) pkgs
+tcltest: setup $(TCLTEST) dlls $(CAT32)
+install: install-binaries install-libraries install-docs install-pkgs
+
+test: test-core test-pkgs
+test-core: setup $(TCLTEST) dlls $(CAT32)
+ set TCL_LIBRARY=$(ROOT:\=/)/library
+!if "$(OS)" == "Windows_NT" || "$(MSVCDIR)" == "IDE"
+ $(DEBUGGER) $(TCLTEST) "$(ROOT:\=/)/tests/all.tcl" $(TESTFLAGS) -loadfile <<
+ package ifneeded dde 1.4.0 [list load "$(TCLDDELIB:\=/)" dde]
+ package ifneeded registry 1.3.1 [list load "$(TCLREGLIB:\=/)" registry]
+<<
+!else
+ @echo Please wait while the tests are collected...
+ $(TCLTEST) "$(ROOT:\=/)/tests/all.tcl" $(TESTFLAGS) -loadfile << > tests.log
+ package ifneeded dde 1.4.0 "$(TCLDDELIB:\=/)" dde]
+ package ifneeded registry 1.3.1 "$(TCLREGLIB:\=/)" registry]
+<<
+ type tests.log | more
+!endif
+
+runtest: setup $(TCLTEST) dlls $(CAT32)
+ set TCL_LIBRARY=$(ROOT:\=/)/library
+ $(DEBUGGER) $(TCLTEST) $(SCRIPT)
+
+runshell: setup $(TCLSH) dlls
+ set TCL_LIBRARY=$(ROOT:\=/)/library
+ $(DEBUGGER) $(TCLSH) $(SCRIPT)
+
+setup:
+ @if not exist $(OUT_DIR)\nul mkdir $(OUT_DIR)
+ @if not exist $(TMP_DIR)\nul mkdir $(TMP_DIR)
+
+!if !$(STATIC_BUILD)
+$(TCLIMPLIB): $(TCLLIB)
+!endif
+
+$(TCLLIB): $(TCLOBJS)
+!if $(STATIC_BUILD)
+ $(lib32) -nologo $(LINKERFLAGS) -out:$@ @<<
+$**
+<<
+!else
+ $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tcl -out:$@ \
+ $(baselibs) @<<
+$**
+<<
+ $(_VC_MANIFEST_EMBED_DLL)
+!endif
+
+$(TCLSTUBLIB): $(TCLSTUBOBJS)
+ $(lib32) -nologo $(LINKERFLAGS) -nodefaultlib -out:$@ $(TCLSTUBOBJS)
+
+$(TCLSH): $(TCLSHOBJS) $(TCLSTUBLIB) $(TCLIMPLIB)
+ $(link32) $(conlflags) -stack:2300000 -out:$@ $(baselibs) $**
+ $(_VC_MANIFEST_EMBED_EXE)
+
+$(TCLTEST): $(TCLTESTOBJS) $(TCLSTUBLIB) $(TCLIMPLIB)
+ $(link32) $(conlflags) -stack:2300000 -out:$@ $(baselibs) $**
+ $(_VC_MANIFEST_EMBED_EXE)
+
+!if $(STATIC_BUILD)
+$(TCLDDELIB): $(TMP_DIR)\tclWinDde.obj
+ $(lib32) -nologo $(LINKERFLAGS) -out:$@ $**
+!else
+$(TCLDDELIB): $(TMP_DIR)\tclWinDde.obj $(TCLSTUBLIB)
+ $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tcldde -out:$@ \
+ $** $(baselibs)
+ $(_VC_MANIFEST_EMBED_DLL)
+!endif
+
+!if $(STATIC_BUILD)
+$(TCLREGLIB): $(TMP_DIR)\tclWinReg.obj
+ $(lib32) -nologo $(LINKERFLAGS) -out:$@ $**
+!else
+$(TCLREGLIB): $(TMP_DIR)\tclWinReg.obj $(TCLSTUBLIB)
+ $(link32) $(dlllflags) -base:@$(WINDIR)\coffbase.txt,tclreg -out:$@ \
+ $** $(baselibs)
+ $(_VC_MANIFEST_EMBED_DLL)
+!endif
+
+pkgs:
+ @for /d %d in ($(PKGSDIR)\*) do \
+ @if exist "%~fd\win\makefile.vc" ( \
+ pushd "%~fd\win" & \
+ $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) &\
+ popd \
+ )
+
+test-pkgs:
+ @for /d %d in ($(PKGSDIR)\*) do \
+ @if exist "%~fd\win\makefile.vc" ( \
+ pushd "%~fd\win" & \
+ $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) test &\
+ popd \
+ )
+
+install-pkgs:
+ @for /d %d in ($(PKGSDIR)\*) do \
+ @if exist "%~fd\win\makefile.vc" ( \
+ pushd "%~fd\win" & \
+ $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) install &\
+ popd \
+ )
+
+clean-pkgs:
+ @for /d %d in ($(PKGSDIR)\*) do \
+ @if exist "%~fd\win\makefile.vc" ( \
+ pushd "%~fd\win" & \
+ $(MAKE) -$(MAKEFLAGS) -f makefile.vc TCLDIR=$(ROOT) clean &\
+ popd \
+ )
+
+$(CAT32): $(WINDIR)\cat.c
+ $(cc32) $(CON_CFLAGS) -Fo$(TMP_DIR)\ $?
+ $(link32) $(conlflags) -out:$@ -stack:16384 $(TMP_DIR)\cat.obj \
+ $(baselibs)
+ $(_VC_MANIFEST_EMBED_EXE)
+
+#---------------------------------------------------------------------
+# Regenerate the stubs files. [Development use only]
+#---------------------------------------------------------------------
+
+genstubs:
+!if !exist($(TCLSH))
+ @echo Build tclsh first!
+!else
+ $(TCLSH) $(TOOLSDIR:\=/)/genStubs.tcl $(GENERICDIR:\=/) \
+ $(GENERICDIR:\=/)/tcl.decls $(GENERICDIR:\=/)/tclInt.decls \
+ $(GENERICDIR:\=/)/tclTomMath.decls
+ $(TCLSH) $(TOOLSDIR:\=/)/genStubs.tcl $(GENERICDIR:\=/) \
+ $(GENERICDIR:\=/)/tclOO.decls
+!endif
+
+
+#----------------------------------------------------------------------
+# The following target generates the file generic/tclTomMath.h.
+# It needs to be run (and the results checked) after updating
+# to a new release of libtommath.
+#----------------------------------------------------------------------
+
+gentommath_h:
+!if !exist($(TCLSH))
+ @echo Build tclsh first!
+!else
+ $(TCLSH) "$(TOOLSDIR:\=/)/fix_tommath_h.tcl" \
+ "$(TOMMATHDIR:\=/)/tommath.h" \
+ > "$(GENERICDIR)\tclTomMath.h"
+!endif
+
+#---------------------------------------------------------------------
+# Build the Windows HTML help file.
+#---------------------------------------------------------------------
+
+# NOTE: you can define HHC on the command-line to override this
+!ifndef HHC
+HHC=""%ProgramFiles%\HTML Help Workshop\hhc.exe""
+!endif
+HTMLDIR=$(ROOT)\html
+HTMLBASE=TclTk$(VERSION)
+HHPFILE=$(HTMLDIR)\$(HTMLBASE).hhp
+CHMFILE=$(HTMLDIR)\$(HTMLBASE).chm
+
+htmlhelp: chmsetup $(CHMFILE)
+
+$(CHMFILE): $(DOCDIR)\*
+ @$(TCLSH) $(TOOLSDIR)\tcltk-man2html.tcl
+ @echo Compiling HTML help project
+ @$(HHC) <<$(HHPFILE) >NUL
+[OPTIONS]
+Compatibility=1.1 or later
+Compiled file=$(HTMLBASE).chm
+Display compile progress=no
+Error log file=$(HTMLBASE).log
+Language=0x409 English (United States)
+Title=Tcl/Tk $(DOT_VERSION) Help
+[FILES]
+contents.htm
+docs.css
+Keywords
+TclCmd
+TclLib
+TkCmd
+TkLib
+UserCmd
+<<
+
+chmsetup:
+ @if not exist $(HTMLDIR)\nul mkdir $(HTMLDIR)
+
+#-------------------------------------------------------------------------
+# Build the old-style Windows .hlp file
+#-------------------------------------------------------------------------
+
+TCLHLPBASE = $(PROJECT)$(VERSION)
+HELPFILE = $(OUT_DIR)\$(TCLHLPBASE).hlp
+HELPCNT = $(OUT_DIR)\$(TCLHLPBASE).cnt
+DOCTMP_DIR = $(OUT_DIR)\$(PROJECT)_docs
+HELPRTF = $(DOCTMP_DIR)\$(PROJECT).rtf
+MAN2HELP = $(DOCTMP_DIR)\man2help.tcl
+MAN2HELP2 = $(DOCTMP_DIR)\man2help2.tcl
+INDEX = $(DOCTMP_DIR)\index.tcl
+BMP = $(DOCTMP_DIR)\feather.bmp
+BMP_NOPATH = feather.bmp
+MAN2TCL = $(DOCTMP_DIR)\man2tcl.exe
+
+winhelp: docsetup $(HELPFILE)
+
+docsetup:
+ @if not exist $(DOCTMP_DIR)\nul mkdir $(DOCTMP_DIR)
+
+$(MAN2HELP) $(MAN2HELP2) $(INDEX) $(BMP): $(TOOLSDIR)\$$(@F)
+ @$(CPY) $(TOOLSDIR)\$(@F) $(@D)
+
+$(HELPFILE): $(HELPRTF) $(BMP)
+ cd $(DOCTMP_DIR)
+ start /wait hcrtf.exe -x <<$(PROJECT).hpj
+[OPTIONS]
+COMPRESS=12 Hall Zeck
+LCID=0x409 0x0 0x0 ; English (United States)
+TITLE=Tcl/Tk Reference Manual
+BMROOT=.
+CNT=$(@B).cnt
+HLP=$(@B).hlp
+
+[FILES]
+$(PROJECT).rtf
+
+[WINDOWS]
+main="Tcl/Tk Reference Manual",,27648,(r15263976),(r65535)
+
+[CONFIG]
+BrowseButtons()
+CreateButton(1, "Web", ExecFile("http://www.tcl.tk"))
+CreateButton(2, "SF", ExecFile("http://sf.net/projects/tcl"))
+CreateButton(3, "Wiki", ExecFile("http://wiki.tcl.tk"))
+CreateButton(4, "FAQ", ExecFile("http://www.purl.org/NET/Tcl-FAQ/"))
+<<
+ cd $(MAKEDIR)
+ @$(CPY) "$(DOCTMP_DIR)\$(@B).hlp" "$(OUT_DIR)"
+ @$(CPY) "$(DOCTMP_DIR)\$(@B).cnt" "$(OUT_DIR)"
+
+$(MAN2TCL): $(TOOLSDIR)\$$(@B).c
+ $(cc32) $(TCL_CFLAGS) -Fo$(@D)\ $(TOOLSDIR)\$(@B).c
+ $(link32) $(conlflags) -out:$@ -stack:16384 $(@D)\man2tcl.obj
+ $(_VC_MANIFEST_EMBED_EXE)
+
+$(HELPRTF): $(MAN2TCL) $(MAN2HELP) $(MAN2HELP2) $(INDEX) $(DOCDIR)\*
+ $(TCLSH) $(MAN2HELP) -bitmap $(BMP_NOPATH) $(PROJECT) $(VERSION) $(DOCDIR:\=/)
+
+install-docs:
+!if exist("$(CHMFILE)")
+ @echo Installing compiled HTML help
+ @$(CPY) "$(CHMFILE)" "$(DOC_INSTALL_DIR)\"
+!endif
+!if exist("$(HELPFILE)")
+ @echo Installing Windows help
+ @$(CPY) "$(HELPFILE)" "$(DOC_INSTALL_DIR)\"
+ @$(CPY) "$(HELPCNT)" "$(DOC_INSTALL_DIR)\"
+!endif
+
+#---------------------------------------------------------------------
+# Build tclConfig.sh for the TEA build system.
+#---------------------------------------------------------------------
+
+tclConfig: $(OUT_DIR)\tclConfig.sh
+
+$(OUT_DIR)\tclConfig.sh: $(WINDIR)\tclConfig.sh.in
+ @echo Creating tclConfig.sh
+ @nmakehlp -s << $** >$@
+@TCL_DLL_FILE@ $(TCLLIBNAME)
+@TCL_VERSION@ $(DOTVERSION)
+@TCL_MAJOR_VERSION@ $(TCL_MAJOR_VERSION)
+@TCL_MINOR_VERSION@ $(TCL_MINOR_VERSION)
+@TCL_PATCH_LEVEL@ $(TCL_PATCH_LEVEL)
+@CC@ $(CC)
+@DEFS@ $(TCL_CFLAGS)
+@CFLAGS_DEBUG@ -nologo -c -W3 -YX -Fp$(TMP_DIR)\ -MDd
+@CFLAGS_OPTIMIZE@ -nologo -c -W3 -YX -Fp$(TMP_DIR)\ -MD
+@LDFLAGS_DEBUG@ -nologo -machine:$(MACHINE) -debug -debugtype:cv
+@LDFLAGS_OPTIMIZE@ -nologo -machine:$(MACHINE) -release -opt:ref -opt:icf,3
+@TCL_DBGX@ $(SUFX)
+@TCL_LIB_FILE@ $(PROJECT)$(VERSION)$(SUFX).lib
+@TCL_NEEDS_EXP_FILE@
+@LIBS@ $(baselibs)
+@prefix@ $(_INSTALLDIR)
+@exec_prefix@ $(BIN_INSTALL_DIR)
+@SHLIB_CFLAGS@
+@STLIB_CFLAGS@
+@CFLAGS_WARNING@ -W3
+@EXTRA_CFLAGS@ -YX
+@SHLIB_LD@ $(link32) $(dlllflags)
+@STLIB_LD@ $(lib32) -nologo
+@SHLIB_LD_LIBS@ $(baselibs)
+@SHLIB_SUFFIX@ .dll
+@DL_LIBS@
+@LDFLAGS@
+@TCL_LD_SEARCH_FLAGS@
+@LIBOBJS@
+@RANLIB@
+@TCL_LIB_FLAG@
+@TCL_BUILD_LIB_SPEC@
+@TCL_LIB_SPEC@ $(LIB_INSTALL_DIR)\$(PROJECT)$(VERSION)$(SUFX).lib
+@TCL_INCLUDE_SPEC@ -I$(INCLUDE_INSTALL_DIR)
+@TCL_LIB_VERSIONS_OK@
+@TCL_SRC_DIR@ $(ROOT)
+@TCL_PACKAGE_PATH@
+@TCL_STUB_LIB_FILE@ $(TCLSTUBLIBNAME)
+@TCL_STUB_LIB_FLAG@ $(TCLSTUBLIBNAME)
+@TCL_STUB_LIB_SPEC@ -L$(LIB_INSTALL_DIR) $(TCLSTUBLIBNAME)
+@TCL_THREADS@ $(TCL_THREADS)
+@TCL_BUILD_STUB_LIB_SPEC@ -L$(OUT_DIR) $(TCLSTUBLIBNAME)
+@TCL_BUILD_STUB_LIB_PATH@ $(TCLSTUBLIB)
+@TCL_STUB_LIB_PATH@ $(LIB_INSTALL_DIR)\$(TCLSTUBLIBNAME)
+@CFG_TCL_EXPORT_FILE_SUFFIX@ $(VERSION)$(SUFX).lib
+@CFG_TCL_SHARED_LIB_SUFFIX@ $(VERSION)$(SUFX).dll
+@CFG_TCL_UNSHARED_LIB_SUFFIX@ $(VERSION)$(SUFX).lib
+!if $(STATIC_BUILD)
+@TCL_SHARED_BUILD@ 0
+!else
+@TCL_SHARED_BUILD@ 1
+!endif
+<<
+
+
+#---------------------------------------------------------------------
+# The following target generates the file generic/tclDate.c
+# from the yacc grammar found in generic/tclGetDate.y. This is
+# only run by hand as yacc is not available in all environments.
+# The name of the .c file is different than the name of the .y file
+# so that make doesn't try to automatically regenerate the .c file.
+#---------------------------------------------------------------------
+
+gendate:
+ bison --output-file=$(GENERICDIR)/tclDate.c \
+ --name-prefix=TclDate \
+ $(GENERICDIR)/tclGetDate.y
+
+#---------------------------------------------------------------------
+# Special case object file targets
+#---------------------------------------------------------------------
+
+$(TMP_DIR)\testMain.obj: $(WINDIR)\tclAppInit.c
+ $(cc32) $(TCL_CFLAGS) -DTCL_TEST \
+ -DTCL_USE_STATIC_PACKAGES=$(TCL_USE_STATIC_PACKAGES) \
+ -Fo$@ $?
+
+$(TMP_DIR)\tclMain2.obj: $(GENERICDIR)\tclMain.c
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -DTCL_ASCII_MAIN \
+ -Fo$@ $?
+
+$(TMP_DIR)\tclTest.obj: $(GENERICDIR)\tclTest.c
+ $(cc32) $(TCL_CFLAGS) -Fo$@ $?
+
+$(TMP_DIR)\tclTestObj.obj: $(GENERICDIR)\tclTestObj.c
+ $(cc32) $(TCL_CFLAGS) -Fo$@ $?
+
+$(TMP_DIR)\tclWinTest.obj: $(WINDIR)\tclWinTest.c
+ $(cc32) $(TCL_CFLAGS) -Fo$@ $?
+
+$(TMP_DIR)\tclZlib.obj: $(GENERICDIR)\tclZlib.c
+ $(cc32) $(TCL_CFLAGS) -I$(COMPATDIR)\zlib -DBUILD_tcl -Fo$@ $?
+
+$(TMP_DIR)\tclPkgConfig.obj: $(GENERICDIR)\tclPkgConfig.c
+ $(cc32) -DBUILD_tcl $(TCL_CFLAGS) \
+ -DCFG_INSTALL_LIBDIR="\"$(LIB_INSTALL_DIR:\=\\)\"" \
+ -DCFG_INSTALL_BINDIR="\"$(BIN_INSTALL_DIR:\=\\)\"" \
+ -DCFG_INSTALL_SCRDIR="\"$(SCRIPT_INSTALL_DIR:\=\\)\"" \
+ -DCFG_INSTALL_INCDIR="\"$(INCLUDE_INSTALL_DIR:\=\\)\"" \
+ -DCFG_INSTALL_DOCDIR="\"$(DOC_INSTALL_DIR:\=\\)\"" \
+ -DCFG_RUNTIME_LIBDIR="\"$(LIB_INSTALL_DIR:\=\\)\"" \
+ -DCFG_RUNTIME_BINDIR="\"$(BIN_INSTALL_DIR:\=\\)\"" \
+ -DCFG_RUNTIME_SCRDIR="\"$(SCRIPT_INSTALL_DIR:\=\\)\"" \
+ -DCFG_RUNTIME_INCDIR="\"$(INCLUDE_INSTALL_DIR:\=\\)\"" \
+ -DCFG_RUNTIME_DOCDIR="\"$(DOC_INSTALL_DIR:\=\\)\"" \
+ -Fo$@ $?
+
+$(TMP_DIR)\tclAppInit.obj: $(WINDIR)\tclAppInit.c
+ $(cc32) $(TCL_CFLAGS) \
+ -DTCL_USE_STATIC_PACKAGES=$(TCL_USE_STATIC_PACKAGES) \
+ -Fo$@ $?
+
+### The following objects should be built using the stub interfaces
+### *ALL* extensions need to built with -DTCL_THREADS=1
+
+$(TMP_DIR)\tclWinReg.obj: $(WINDIR)\tclWinReg.c
+!if $(STATIC_BUILD)
+ $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DSTATIC_BUILD -Fo$@ $?
+!else
+ $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DUSE_TCL_STUBS -Fo$@ $?
+!endif
+
+
+$(TMP_DIR)\tclWinDde.obj: $(WINDIR)\tclWinDde.c
+!if $(STATIC_BUILD)
+ $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DSTATIC_BUILD -Fo$@ $?
+!else
+ $(cc32) $(TCL_CFLAGS) -DTCL_THREADS=1 -DUSE_TCL_STUBS -Fo$@ $?
+!endif
+
+
+### The following objects are part of the stub library and should not
+### be built as DLL objects. -Zl is used to avoid a dependency on any
+### specific C run-time.
+
+$(TMP_DIR)\tclStubLib.obj: $(GENERICDIR)\tclStubLib.c
+ $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $?
+
+$(TMP_DIR)\tclTomMathStubLib.obj: $(GENERICDIR)\tclTomMathStubLib.c
+ $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $?
+
+$(TMP_DIR)\tclOOStubLib.obj: $(GENERICDIR)\tclOOStubLib.c
+ $(cc32) $(STUB_CFLAGS) -Zl -DSTATIC_BUILD $(TCL_INCLUDES) -Fo$@ $?
+
+$(TMP_DIR)\tclsh.exe.manifest: $(WINDIR)\tclsh.exe.manifest.in
+ @nmakehlp -s << $** >$@
+@MACHINE@ $(MACHINE:IX86=X86)
+@TCL_WIN_VERSION@ $(DOTVERSION).0.0
+<<
+
+#---------------------------------------------------------------------
+# Generate the source dependencies. Having dependency rules will
+# improve incremental build accuracy without having to resort to a
+# full rebuild just because some non-global header file like
+# tclCompile.h was changed. These rules aren't needed when building
+# from scratch.
+#---------------------------------------------------------------------
+
+depend:
+!if !exist($(TCLSH))
+ @echo Build tclsh first!
+!else
+ $(TCLSH) $(TOOLSDIR:\=/)/mkdepend.tcl -vc32 -out:"$(OUT_DIR)\depend.mk" \
+ -passthru:"-DBUILD_tcl $(TCL_INCLUDES)" $(GENERICDIR),$$(GENERICDIR) \
+ $(COMPATDIR),$$(COMPATDIR) $(TOMMATHDIR),$$(TOMMATHDIR) $(WINDIR),$$(WINDIR) @<<
+$(TCLOBJS)
+<<
+!endif
+
+#---------------------------------------------------------------------
+# Dependency rules
+#---------------------------------------------------------------------
+
+!if exist("$(OUT_DIR)\depend.mk")
+!include "$(OUT_DIR)\depend.mk"
+!message *** Dependency rules in use.
+!else
+!message *** Dependency rules are not being used.
+!endif
+
+### add a spacer in the output
+!message
+
+
+#---------------------------------------------------------------------
+# Implicit rules. A limitation exists with nmake that requires that
+# source directory can not contain spaces in the path. This an
+# absolute.
+#---------------------------------------------------------------------
+
+{$(WINDIR)}.c{$(TMP_DIR)}.obj::
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<<
+$<
+<<
+
+{$(TOMMATHDIR)}.c{$(TMP_DIR)}.obj::
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<<
+$<
+<<
+
+{$(GENERICDIR)}.c{$(TMP_DIR)}.obj::
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<<
+$<
+<<
+
+{$(COMPATDIR)}.c{$(TMP_DIR)}.obj::
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<<
+$<
+<<
+
+{$(COMPATDIR)\zlib}.c{$(TMP_DIR)}.obj::
+ $(cc32) $(TCL_CFLAGS) -DBUILD_tcl -Fo$(TMP_DIR)\ @<<
+$<
+<<
+
+{$(WINDIR)}.rc{$(TMP_DIR)}.res:
+ $(rc32) -fo $@ -r -i "$(GENERICDIR)" -i "$(TMP_DIR)" \
+ -d DEBUG=$(DEBUG) -d UNCHECKED=$(UNCHECKED) \
+ -d TCL_THREADS=$(TCL_THREADS) \
+ -d STATIC_BUILD=$(STATIC_BUILD) \
+ $<
+
+$(TMP_DIR)\tclsh.res: $(TMP_DIR)\tclsh.exe.manifest
+
+.SUFFIXES:
+.SUFFIXES:.c .rc
+
+
+#---------------------------------------------------------------------
+# Installation.
+#---------------------------------------------------------------------
+
+install-binaries:
+ @echo Installing to '$(_INSTALLDIR)'
+ @echo Installing $(TCLLIBNAME)
+!if "$(TCLLIB)" != "$(TCLIMPLIB)"
+ @$(CPY) "$(TCLLIB)" "$(BIN_INSTALL_DIR)\"
+!endif
+ @$(CPY) "$(TCLIMPLIB)" "$(LIB_INSTALL_DIR)\"
+!if exist($(TCLSH))
+ @echo Installing $(TCLSHNAME)
+ @$(CPY) "$(TCLSH)" "$(BIN_INSTALL_DIR)\"
+!endif
+ @echo Installing $(TCLSTUBLIBNAME)
+ @$(CPY) "$(TCLSTUBLIB)" "$(LIB_INSTALL_DIR)\"
+
+#" emacs fix
+
+install-libraries: tclConfig install-msgs install-tzdata
+ @if not exist "$(SCRIPT_INSTALL_DIR)$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.2$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.2"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.3$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.3"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5"
+ @if not exist "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6$(NULL)" \
+ $(MKDIR) "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6"
+ @echo Installing header files
+ @$(CPY) "$(GENERICDIR)\tcl.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclDecls.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclOO.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclOODecls.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclPlatDecls.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclTomMath.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(GENERICDIR)\tclTomMathDecls.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(TOMMATHDIR)\tommath_class.h" "$(INCLUDE_INSTALL_DIR)\"
+ @$(CPY) "$(TOMMATHDIR)\tommath_superclass.h" "$(INCLUDE_INSTALL_DIR)\"
+ @echo Installing library files to $(SCRIPT_INSTALL_DIR)
+ @$(CPY) "$(ROOT)\library\history.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\init.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\clock.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\tm.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\parray.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\safe.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\tclIndex" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\package.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\word.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(ROOT)\library\auto.tcl" "$(SCRIPT_INSTALL_DIR)\"
+ @$(CPY) "$(OUT_DIR)\tclConfig.sh" "$(LIB_INSTALL_DIR)\"
+ @$(CPY) "$(WINDIR)\tclooConfig.sh" "$(LIB_INSTALL_DIR)\"
+ @echo Installing library http1.0 directory
+ @$(CPY) "$(ROOT)\library\http1.0\*.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\http1.0\"
+ @echo Installing library opt0.4 directory
+ @$(CPY) "$(ROOT)\library\opt\*.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\opt0.4\"
+ @echo Installing package http $(PKG_HTTP_VER) as a Tcl Module
+ @$(COPY) "$(ROOT)\library\http\http.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.6\http-$(PKG_HTTP_VER).tm"
+ @echo Installing package msgcat $(PKG_MSGCAT_VER) as a Tcl Module
+ @$(COPY) "$(ROOT)\library\msgcat\msgcat.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5\msgcat-$(PKG_MSGCAT_VER).tm"
+ @echo Installing package tcltest $(PKG_TCLTEST_VER) as a Tcl Module
+ @$(COPY) "$(ROOT)\library\tcltest\tcltest.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.5\tcltest-$(PKG_TCLTEST_VER).tm"
+ @echo Installing package platform $(PKG_PLATFORM_VER) as a Tcl Module
+ @$(COPY) "$(ROOT)\library\platform\platform.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform-$(PKG_PLATFORM_VER).tm"
+ @echo Installing package platform::shell $(PKG_SHELL_VER) as a Tcl Module
+ @$(COPY) "$(ROOT)\library\platform\shell.tcl" \
+ "$(SCRIPT_INSTALL_DIR)\..\tcl8\8.4\platform\shell-$(PKG_SHELL_VER).tm"
+ @echo Installing $(TCLDDELIBNAME)
+!if $(STATIC_BUILD)
+!if !$(TCL_USE_STATIC_PACKAGES)
+ @$(CPY) "$(TCLDDELIB)" "$(LIB_INSTALL_DIR)\"
+!endif
+!else
+ @$(CPY) "$(TCLDDELIB)" "$(LIB_INSTALL_DIR)\dde$(DDEDOTVERSION)\"
+ @$(CPY) "$(ROOT)\library\dde\pkgIndex.tcl" \
+ "$(LIB_INSTALL_DIR)\dde$(DDEDOTVERSION)\"
+!endif
+ @echo Installing $(TCLREGLIBNAME)
+!if $(STATIC_BUILD)
+!if !$(TCL_USE_STATIC_PACKAGES)
+ @$(CPY) "$(TCLREGLIB)" "$(LIB_INSTALL_DIR)\"
+!endif
+!else
+ @$(CPY) "$(TCLREGLIB)" "$(LIB_INSTALL_DIR)\reg$(REGDOTVERSION)\"
+ @$(CPY) "$(ROOT)\library\reg\pkgIndex.tcl" \
+ "$(LIB_INSTALL_DIR)\reg$(REGDOTVERSION)\"
+!endif
+ @echo Installing encodings
+ @$(CPY) "$(ROOT)\library\encoding\*.enc" \
+ "$(SCRIPT_INSTALL_DIR)\encoding\"
+
+#" emacs fix
+
+install-tzdata:
+ @echo Installing time zone data
+ @set TCL_LIBRARY=$(ROOT:\=/)/library
+ @$(TCLSH_NATIVE) "$(ROOT:\=/)/tools/installData.tcl" \
+ "$(ROOT:\=/)/library/tzdata" "$(SCRIPT_INSTALL_DIR)/tzdata"
+
+install-msgs:
+ @echo Installing message catalogs
+ @set TCL_LIBRARY=$(ROOT:\=/)/library
+ @$(TCLSH_NATIVE) "$(ROOT:\=/)/tools/installData.tcl" \
+ "$(ROOT:\=/)/library/msgs" "$(SCRIPT_INSTALL_DIR)/msgs"
+
+#---------------------------------------------------------------------
+# Clean up
+#---------------------------------------------------------------------
+
+tidy:
+!if "$(TCLLIB)" != "$(TCLIMPLIB)"
+ @echo Removing $(TCLLIB) ...
+ @if exist $(TCLLIB) del $(TCLLIB)
+!endif
+ @echo Removing $(TCLIMPLIB) ...
+ @if exist $(TCLIMPLIB) del $(TCLIMPLIB)
+ @echo Removing $(TCLSH) ...
+ @if exist $(TCLSH) del $(TCLSH)
+ @echo Removing $(TCLTEST) ...
+ @if exist $(TCLTEST) del $(TCLTEST)
+ @echo Removing $(TCLDDELIB) ...
+ @if exist $(TCLDDELIB) del $(TCLDDELIB)
+ @echo Removing $(TCLREGLIB) ...
+ @if exist $(TCLREGLIB) del $(TCLREGLIB)
+
+clean: clean-pkgs
+ @echo Cleaning $(TMP_DIR)\* ...
+ @if exist $(TMP_DIR)\nul $(RMDIR) $(TMP_DIR)
+ @echo Cleaning $(WINDIR)\nmakehlp.obj ...
+ @if exist $(WINDIR)\nmakehlp.obj del $(WINDIR)\nmakehlp.obj
+ @echo Cleaning $(WINDIR)\nmakehlp.exe ...
+ @if exist $(WINDIR)\nmakehlp.exe del $(WINDIR)\nmakehlp.exe
+ @echo Cleaning $(WINDIR)\_junk.pch ...
+ @if exist $(WINDIR)\_junk.pch del $(WINDIR)\_junk.pch
+ @echo Cleaning $(WINDIR)\vercl.x ...
+ @if exist $(WINDIR)\vercl.x del $(WINDIR)\vercl.x
+ @echo Cleaning $(WINDIR)\vercl.i ...
+ @if exist $(WINDIR)\vercl.i del $(WINDIR)\vercl.i
+ @echo Cleaning $(WINDIR)\versions.vc ...
+ @if exist $(WINDIR)\versions.vc del $(WINDIR)\versions.vc
+
+realclean: hose
+
+hose:
+ @echo Hosing $(OUT_DIR)\* ...
+ @if exist $(OUT_DIR)\nul $(RMDIR) $(OUT_DIR)
+
+# Local Variables:
+# mode: makefile
+# End:
diff --git a/win/rules.vc b/win/rules.vc index 1513198..d4c2f35 100644 --- a/win/rules.vc +++ b/win/rules.vc @@ -1,698 +1,698 @@ -#------------------------------------------------------------------------------ -# rules.vc -- -# -# Microsoft Visual C++ makefile include for decoding the commandline -# macros. This file does not need editing to build Tcl. -# -# See the file "license.terms" for information on usage and redistribution -# of this file, and for a DISCLAIMER OF ALL WARRANTIES. -# -# Copyright (c) 2001-2003 David Gravereaux. -# Copyright (c) 2003-2008 Patrick Thoyts -#------------------------------------------------------------------------------ - -!ifndef _RULES_VC -_RULES_VC = 1 - -cc32 = $(CC) # built-in default. -link32 = link -lib32 = lib -rc32 = $(RC) # built-in default. - -!ifndef INSTALLDIR -### Assume the normal default. -_INSTALLDIR = C:\Program Files\Tcl -!else -### Fix the path separators. -_INSTALLDIR = $(INSTALLDIR:/=\) -!endif - -#---------------------------------------------------------- -# Set the proper copy method to avoid overwrite questions -# to the user when copying files and selecting the right -# "delete all" method. -#---------------------------------------------------------- - -!if "$(OS)" == "Windows_NT" -RMDIR = rmdir /S /Q -ERRNULL = 2>NUL -!if ![ver | find "4.0" > nul] -CPY = echo y | xcopy /i >NUL -COPY = copy >NUL -!else -CPY = xcopy /i /y >NUL -COPY = copy /y >NUL -!endif -!else # "$(OS)" != "Windows_NT" -CPY = xcopy /i >_JUNK.OUT # On Win98 NUL does not work here. -COPY = copy >_JUNK.OUT # On Win98 NUL does not work here. -RMDIR = deltree /Y -NULL = \NUL # Used in testing directory existence -ERRNULL = >NUL # Win9x shell cannot redirect stderr -!endif -MKDIR = mkdir - -#------------------------------------------------------------------------------ -# Determine the host and target architectures and compiler version. -#------------------------------------------------------------------------------ - -_HASH=^# -_VC_MANIFEST_EMBED_EXE= -_VC_MANIFEST_EMBED_DLL= -VCVER=0 -!if ![echo VCVERSION=_MSC_VER > vercl.x] \ - && ![echo $(_HASH)if defined(_M_IX86) >> vercl.x] \ - && ![echo ARCH=IX86 >> vercl.x] \ - && ![echo $(_HASH)elif defined(_M_AMD64) >> vercl.x] \ - && ![echo ARCH=AMD64 >> vercl.x] \ - && ![echo $(_HASH)endif >> vercl.x] \ - && ![cl -nologo -TC -P vercl.x $(ERRNULL)] -!include vercl.i -!if ![echo VCVER= ^\> vercl.vc] \ - && ![set /a $(VCVERSION) / 100 - 6 >> vercl.vc] -!include vercl.vc -!endif -!endif -!if ![del $(ERRNUL) /q/f vercl.x vercl.i vercl.vc] -!endif - -!if ![reg query HKLM\Hardware\Description\System\CentralProcessor\0 /v Identifier | findstr /i x86] -NATIVE_ARCH=IX86 -!else -NATIVE_ARCH=AMD64 -!endif - -# Since MSVC8 we must deal with manifest resources. -!if $(VCVERSION) >= 1400 -_VC_MANIFEST_EMBED_EXE=if exist $@.manifest mt -nologo -manifest $@.manifest -outputresource:$@;1 -_VC_MANIFEST_EMBED_DLL=if exist $@.manifest mt -nologo -manifest $@.manifest -outputresource:$@;2 -!endif - -!ifndef MACHINE -MACHINE=$(ARCH) -!endif - -!ifndef CFG_ENCODING -CFG_ENCODING = \"cp1252\" -!endif - -!message =============================================================================== - -#---------------------------------------------------------- -# build the helper app we need to overcome nmake's limiting -# environment. -#---------------------------------------------------------- - -!if !exist(nmakehlp.exe) -!if [$(cc32) -nologo nmakehlp.c -link -subsystem:console > nul] -!endif -!endif - -#---------------------------------------------------------- -# Test for compiler features -#---------------------------------------------------------- - -### test for optimizations -!if [nmakehlp -c -Ot] -!message *** Compiler has 'Optimizations' -OPTIMIZING = 1 -!else -!message *** Compiler does not have 'Optimizations' -OPTIMIZING = 0 -!endif - -OPTIMIZATIONS = - -!if [nmakehlp -c -Ot] -OPTIMIZATIONS = $(OPTIMIZATIONS) -Ot -!endif - -!if [nmakehlp -c -Oi] -OPTIMIZATIONS = $(OPTIMIZATIONS) -Oi -!endif - -!if [nmakehlp -c -Op] -OPTIMIZATIONS = $(OPTIMIZATIONS) -Op -!endif - -!if [nmakehlp -c -fp:strict] -OPTIMIZATIONS = $(OPTIMIZATIONS) -fp:strict -!endif - -!if [nmakehlp -c -Gs] -OPTIMIZATIONS = $(OPTIMIZATIONS) -Gs -!endif - -!if [nmakehlp -c -GS] -OPTIMIZATIONS = $(OPTIMIZATIONS) -GS -!endif - -!if [nmakehlp -c -GL] -OPTIMIZATIONS = $(OPTIMIZATIONS) -GL -!endif - -DEBUGFLAGS = - -!if [nmakehlp -c -RTC1] -DEBUGFLAGS = $(DEBUGFLAGS) -RTC1 -!elseif [nmakehlp -c -GZ] -DEBUGFLAGS = $(DEBUGFLAGS) -GZ -!endif - -COMPILERFLAGS =-W3 -DUNICODE -D_UNICODE - -# In v13 -GL and -YX are incompatible. -!if [nmakehlp -c -YX] -!if ![nmakehlp -c -GL] -OPTIMIZATIONS = $(OPTIMIZATIONS) -YX -!endif -!endif - -!if "$(MACHINE)" == "IX86" -### test for pentium errata -!if [nmakehlp -c -QI0f] -!message *** Compiler has 'Pentium 0x0f fix' -COMPILERFLAGS = $(COMPILERFLAGS) -QI0f -!else -!message *** Compiler does not have 'Pentium 0x0f fix' -!endif -!endif - -!if "$(MACHINE)" == "IA64" -### test for Itanium errata -!if [nmakehlp -c -QIA64_Bx] -!message *** Compiler has 'B-stepping errata workarounds' -COMPILERFLAGS = $(COMPILERFLAGS) -QIA64_Bx -!else -!message *** Compiler does not have 'B-stepping errata workarounds' -!endif -!endif - -!if "$(MACHINE)" == "IX86" -### test for -align:4096, when align:512 will do. -!if [nmakehlp -l -opt:nowin98] -!message *** Linker has 'Win98 alignment problem' -ALIGN98_HACK = 1 -!else -!message *** Linker does not have 'Win98 alignment problem' -ALIGN98_HACK = 0 -!endif -!else -ALIGN98_HACK = 0 -!endif - -LINKERFLAGS = - -!if [nmakehlp -l -ltcg] -LINKERFLAGS =-ltcg -!endif - -#---------------------------------------------------------- -# Decode the options requested. -#---------------------------------------------------------- - -!if "$(OPTS)" == "" || [nmakehlp -f "$(OPTS)" "none"] -STATIC_BUILD = 0 -TCL_THREADS = 1 -DEBUG = 0 -SYMBOLS = 0 -PROFILE = 0 -PGO = 0 -MSVCRT = 1 -LOIMPACT = 0 -TCL_USE_STATIC_PACKAGES = 0 -USE_THREAD_ALLOC = 1 -UNCHECKED = 0 -!else -!if [nmakehlp -f $(OPTS) "static"] -!message *** Doing static -STATIC_BUILD = 1 -!else -STATIC_BUILD = 0 -!endif -!if [nmakehlp -f $(OPTS) "msvcrt"] -!message *** Doing msvcrt -MSVCRT = 1 -!else -!if !$(STATIC_BUILD) -MSVCRT = 1 -!else -MSVCRT = 0 -!endif -!endif -!if [nmakehlp -f $(OPTS) "staticpkg"] && $(STATIC_BUILD) -!message *** Doing staticpkg -TCL_USE_STATIC_PACKAGES = 1 -!else -TCL_USE_STATIC_PACKAGES = 0 -!endif -!if [nmakehlp -f $(OPTS) "nothreads"] -!message *** Compile explicitly for non-threaded tcl -TCL_THREADS = 0 -USE_THREAD_ALLOC= 0 -!else -TCL_THREADS = 1 -USE_THREAD_ALLOC= 1 -!endif -!if [nmakehlp -f $(OPTS) "symbols"] -!message *** Doing symbols -DEBUG = 1 -!else -DEBUG = 0 -!endif -!if [nmakehlp -f $(OPTS) "pdbs"] -!message *** Doing pdbs -SYMBOLS = 1 -!else -SYMBOLS = 0 -!endif -!if [nmakehlp -f $(OPTS) "profile"] -!message *** Doing profile -PROFILE = 1 -!else -PROFILE = 0 -!endif -!if [nmakehlp -f $(OPTS) "pgi"] -!message *** Doing profile guided optimization instrumentation -PGO = 1 -!elseif [nmakehlp -f $(OPTS) "pgo"] -!message *** Doing profile guided optimization -PGO = 2 -!else -PGO = 0 -!endif -!if [nmakehlp -f $(OPTS) "loimpact"] -!message *** Doing loimpact -LOIMPACT = 1 -!else -LOIMPACT = 0 -!endif -!if [nmakehlp -f $(OPTS) "thrdalloc"] -!message *** Doing thrdalloc -USE_THREAD_ALLOC = 1 -!endif -!if [nmakehlp -f $(OPTS) "tclalloc"] -!message *** Doing tclalloc -USE_THREAD_ALLOC = 0 -!endif -!if [nmakehlp -f $(OPTS) "unchecked"] -!message *** Doing unchecked -UNCHECKED = 1 -!else -UNCHECKED = 0 -!endif -!endif - -#---------------------------------------------------------- -# Figure-out how to name our intermediate and output directories. -# We wouldn't want different builds to use the same .obj files -# by accident. -#---------------------------------------------------------- - -#---------------------------------------- -# Naming convention: -# t = full thread support. -# s = static library (as opposed to an -# import library) -# g = linked to the debug enabled C -# run-time. -# x = special static build when it -# links to the dynamic C run-time. -#---------------------------------------- -SUFX = tsgx - -!if $(DEBUG) -BUILDDIRTOP = Debug -!else -BUILDDIRTOP = Release -!endif - -!if "$(MACHINE)" != "IX86" -BUILDDIRTOP =$(BUILDDIRTOP)_$(MACHINE) -!endif -!if $(VCVER) > 6 -BUILDDIRTOP =$(BUILDDIRTOP)_VC$(VCVER) -!endif - -!if !$(DEBUG) || $(DEBUG) && $(UNCHECKED) -SUFX = $(SUFX:g=) -!endif - -TMP_DIRFULL = .\$(BUILDDIRTOP)\$(PROJECT)_ThreadedDynamicStaticX - -!if !$(STATIC_BUILD) -TMP_DIRFULL = $(TMP_DIRFULL:Static=) -SUFX = $(SUFX:s=) -EXT = dll -TMP_DIRFULL = $(TMP_DIRFULL:X=) -SUFX = $(SUFX:x=) -!else -TMP_DIRFULL = $(TMP_DIRFULL:Dynamic=) -EXT = lib -!if !$(MSVCRT) -TMP_DIRFULL = $(TMP_DIRFULL:X=) -SUFX = $(SUFX:x=) -!endif -!endif - -!if !$(TCL_THREADS) -TMP_DIRFULL = $(TMP_DIRFULL:Threaded=) -SUFX = $(SUFX:t=) -!endif - -!ifndef TMP_DIR -TMP_DIR = $(TMP_DIRFULL) -!ifndef OUT_DIR -OUT_DIR = .\$(BUILDDIRTOP) -!endif -!else -!ifndef OUT_DIR -OUT_DIR = $(TMP_DIR) -!endif -!endif - - -#---------------------------------------------------------- -# Decode the statistics requested. -#---------------------------------------------------------- - -!if "$(STATS)" == "" || [nmakehlp -f "$(STATS)" "none"] -TCL_MEM_DEBUG = 0 -TCL_COMPILE_DEBUG = 0 -!else -!if [nmakehlp -f $(STATS) "memdbg"] -!message *** Doing memdbg -TCL_MEM_DEBUG = 1 -!else -TCL_MEM_DEBUG = 0 -!endif -!if [nmakehlp -f $(STATS) "compdbg"] -!message *** Doing compdbg -TCL_COMPILE_DEBUG = 1 -!else -TCL_COMPILE_DEBUG = 0 -!endif -!endif - - -#---------------------------------------------------------- -# Decode the checks requested. -#---------------------------------------------------------- - -!if "$(CHECKS)" == "" || [nmakehlp -f "$(CHECKS)" "none"] -TCL_NO_DEPRECATED = 0 -WARNINGS = -W3 -!else -!if [nmakehlp -f $(CHECKS) "nodep"] -!message *** Doing nodep check -TCL_NO_DEPRECATED = 1 -!else -TCL_NO_DEPRECATED = 0 -!endif -!if [nmakehlp -f $(CHECKS) "fullwarn"] -!message *** Doing full warnings check -WARNINGS = -W4 -!if [nmakehlp -l -warn:3] -LINKERFLAGS = $(LINKERFLAGS) -warn:3 -!endif -!else -WARNINGS = -W3 -!endif -!if [nmakehlp -f $(CHECKS) "64bit"] && [nmakehlp -c -Wp64] -!message *** Doing 64bit portability warnings -WARNINGS = $(WARNINGS) -Wp64 -!endif -!endif - -!if $(PGO) > 1 -!if [nmakehlp -l -ltcg:pgoptimize] -LINKERFLAGS = $(LINKERFLAGS:-ltcg=) -ltcg:pgoptimize -!else -MSG=^ -This compiler does not support profile guided optimization. -!error $(MSG) -!endif -!elseif $(PGO) > 0 -!if [nmakehlp -l -ltcg:pginstrument] -LINKERFLAGS = $(LINKERFLAGS:-ltcg=) -ltcg:pginstrument -!else -MSG=^ -This compiler does not support profile guided optimization. -!error $(MSG) -!endif -!endif - -#---------------------------------------------------------- -# Set our defines now armed with our options. -#---------------------------------------------------------- - -OPTDEFINES = -DTCL_CFGVAL_ENCODING=$(CFG_ENCODING) -DSTDC_HEADERS - -!if $(TCL_MEM_DEBUG) -OPTDEFINES = $(OPTDEFINES) -DTCL_MEM_DEBUG -!endif -!if $(TCL_COMPILE_DEBUG) -OPTDEFINES = $(OPTDEFINES) -DTCL_COMPILE_DEBUG -DTCL_COMPILE_STATS -!endif -!if $(TCL_THREADS) -OPTDEFINES = $(OPTDEFINES) -DTCL_THREADS=1 -!if $(USE_THREAD_ALLOC) -OPTDEFINES = $(OPTDEFINES) -DUSE_THREAD_ALLOC=1 -!endif -!endif -!if $(STATIC_BUILD) -OPTDEFINES = $(OPTDEFINES) -DSTATIC_BUILD -!endif -!if $(TCL_NO_DEPRECATED) -OPTDEFINES = $(OPTDEFINES) -DTCL_NO_DEPRECATED -!endif - -!if !$(DEBUG) -OPTDEFINES = $(OPTDEFINES) -DNDEBUG -!if $(OPTIMIZING) -OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_OPTIMIZED -!endif -!endif -!if $(PROFILE) -OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_PROFILED -!endif -!if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64" -OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_DO64BIT -!endif -!if $(VCVERSION) < 1300 -OPTDEFINES = $(OPTDEFINES) -DNO_STRTOI64 -!endif - -#---------------------------------------------------------- -# Locate the Tcl headers to build against -#---------------------------------------------------------- - -!if "$(PROJECT)" == "tcl" - -_TCL_H = ..\generic\tcl.h - -!else - -# If INSTALLDIR set to tcl root dir then reset to the lib dir. -!if exist("$(_INSTALLDIR)\include\tcl.h") -_INSTALLDIR=$(_INSTALLDIR)\lib -!endif - -!if !defined(TCLDIR) -!if exist("$(_INSTALLDIR)\..\include\tcl.h") -TCLINSTALL = 1 -_TCLDIR = $(_INSTALLDIR)\.. -_TCL_H = $(_INSTALLDIR)\..\include\tcl.h -TCLDIR = $(_INSTALLDIR)\.. -!else -MSG=^ -Failed to find tcl.h. Set the TCLDIR macro. -!error $(MSG) -!endif -!else -_TCLDIR = $(TCLDIR:/=\) -!if exist("$(_TCLDIR)\include\tcl.h") -TCLINSTALL = 1 -_TCL_H = $(_TCLDIR)\include\tcl.h -!elseif exist("$(_TCLDIR)\generic\tcl.h") -TCLINSTALL = 0 -_TCL_H = $(_TCLDIR)\generic\tcl.h -!else -MSG =^ -Failed to find tcl.h. The TCLDIR macro does not appear correct. -!error $(MSG) -!endif -!endif -!endif - -#-------------------------------------------------------------- -# Extract various version numbers from tcl headers -# The generated file is then included in the makefile. -#-------------------------------------------------------------- - -!if [echo REM = This file is generated from rules.vc > versions.vc] -!endif -!if [echo TCL_MAJOR_VERSION = \>> versions.vc] \ - && [nmakehlp -V "$(_TCL_H)" TCL_MAJOR_VERSION >> versions.vc] -!endif -!if [echo TCL_MINOR_VERSION = \>> versions.vc] \ - && [nmakehlp -V "$(_TCL_H)" TCL_MINOR_VERSION >> versions.vc] -!endif -!if [echo TCL_PATCH_LEVEL = \>> versions.vc] \ - && [nmakehlp -V "$(_TCL_H)" TCL_PATCH_LEVEL >> versions.vc] -!endif - -# If building the tcl core then we need additional package versions -!if "$(PROJECT)" == "tcl" -!if [echo PKG_HTTP_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\http\pkgIndex.tcl http >> versions.vc] -!endif -!if [echo PKG_TCLTEST_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\tcltest\pkgIndex.tcl tcltest >> versions.vc] -!endif -!if [echo PKG_MSGCAT_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\msgcat\pkgIndex.tcl msgcat >> versions.vc] -!endif -!if [echo PKG_PLATFORM_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\platform\pkgIndex.tcl "platform " >> versions.vc] -!endif -!if [echo PKG_SHELL_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\platform\pkgIndex.tcl "platform::shell" >> versions.vc] -!endif -!if [echo PKG_DDE_VER = \>> versions.vc] \ - && [nmakehlp -V ..\library\dde\pkgIndex.tcl "dde " >> versions.vc] -!endif -!if [echo PKG_REG_VER =\>> versions.vc] \ - && [nmakehlp -V ..\library\reg\pkgIndex.tcl registry >> versions.vc] -!endif -!endif - -!include versions.vc - -#-------------------------------------------------------------- -# Setup tcl version dependent stuff headers -#-------------------------------------------------------------- - -!if "$(PROJECT)" != "tcl" - -TCL_VERSION = $(TCL_MAJOR_VERSION)$(TCL_MINOR_VERSION) - -!if $(TCLINSTALL) -TCLSH = "$(_TCLDIR)\bin\tclsh$(TCL_VERSION)$(SUFX).exe" -!if !exist($(TCLSH)) && $(TCL_THREADS) -TCLSH = "$(_TCLDIR)\bin\tclsh$(TCL_VERSION)t$(SUFX).exe" -!endif -TCLSTUBLIB = "$(_TCLDIR)\lib\tclstub$(TCL_VERSION).lib" -TCLIMPLIB = "$(_TCLDIR)\lib\tcl$(TCL_VERSION)$(SUFX).lib" -TCL_LIBRARY = $(_TCLDIR)\lib -TCLREGLIB = "$(_TCLDIR)\lib\tclreg13$(SUFX:t=).lib" -TCLDDELIB = "$(_TCLDIR)\lib\tcldde14$(SUFX:t=).lib" -COFFBASE = \must\have\tcl\sources\to\build\this\target -TCLTOOLSDIR = \must\have\tcl\sources\to\build\this\target -TCL_INCLUDES = -I"$(_TCLDIR)\include" -!else -TCLSH = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclsh$(TCL_VERSION)$(SUFX).exe" -!if !exist($(TCLSH)) && $(TCL_THREADS) -TCLSH = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclsh$(TCL_VERSION)t$(SUFX).exe" -!endif -TCLSTUBLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclstub$(TCL_VERSION).lib" -TCLIMPLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tcl$(TCL_VERSION)$(SUFX).lib" -TCL_LIBRARY = $(_TCLDIR)\library -TCLREGLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclreg13$(SUFX:t=).lib" -TCLDDELIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tcldde14$(SUFX:t=).lib" -COFFBASE = "$(_TCLDIR)\win\coffbase.txt" -TCLTOOLSDIR = $(_TCLDIR)\tools -TCL_INCLUDES = -I"$(_TCLDIR)\generic" -I"$(_TCLDIR)\win" -!endif - -!endif - -#------------------------------------------------------------------------- -# Locate the Tk headers to build against -#------------------------------------------------------------------------- - -!if "$(PROJECT)" == "tk" -_TK_H = ..\generic\tk.h -_INSTALLDIR = $(_INSTALLDIR)\.. -!endif - -!ifdef PROJECT_REQUIRES_TK -!if !defined(TKDIR) -!if exist("$(_INSTALLDIR)\..\include\tk.h") -TKINSTALL = 1 -_TKDIR = $(_INSTALLDIR)\.. -_TK_H = $(_TKDIR)\include\tk.h -TKDIR = $(_TKDIR) -!elseif exist("$(_TCLDIR)\include\tk.h") -TKINSTALL = 1 -_TKDIR = $(_TCLDIR) -_TK_H = $(_TKDIR)\include\tk.h -TKDIR = $(_TKDIR) -!endif -!else -_TKDIR = $(TKDIR:/=\) -!if exist("$(_TKDIR)\include\tk.h") -TKINSTALL = 1 -_TK_H = $(_TKDIR)\include\tk.h -!elseif exist("$(_TKDIR)\generic\tk.h") -TKINSTALL = 0 -_TK_H = $(_TKDIR)\generic\tk.h -!else -MSG =^ -Failed to find tk.h. The TKDIR macro does not appear correct. -!error $(MSG) -!endif -!endif -!endif - -#------------------------------------------------------------------------- -# Extract Tk version numbers -#------------------------------------------------------------------------- - -!if defined(PROJECT_REQUIRES_TK) || "$(PROJECT)" == "tk" - -!if [echo TK_MAJOR_VERSION = \>> versions.vc] \ - && [nmakehlp -V $(_TK_H) TK_MAJOR_VERSION >> versions.vc] -!endif -!if [echo TK_MINOR_VERSION = \>> versions.vc] \ - && [nmakehlp -V $(_TK_H) TK_MINOR_VERSION >> versions.vc] -!endif -!if [echo TK_PATCH_LEVEL = \>> versions.vc] \ - && [nmakehlp -V $(_TK_H) TK_PATCH_LEVEL >> versions.vc] -!endif - -!include versions.vc - -TK_DOTVERSION = $(TK_MAJOR_VERSION).$(TK_MINOR_VERSION) -TK_VERSION = $(TK_MAJOR_VERSION)$(TK_MINOR_VERSION) - -!if "$(PROJECT)" != "tk" -!if $(TKINSTALL) -WISH = "$(_TKDIR)\bin\wish$(TK_VERSION)$(SUFX).exe" -TKSTUBLIB = "$(_TKDIR)\lib\tkstub$(TK_VERSION).lib" -TKIMPLIB = "$(_TKDIR)\lib\tk$(TK_VERSION)$(SUFX).lib" -TK_INCLUDES = -I"$(_TKDIR)\include" -!else -WISH = "$(_TKDIR)\win\$(BUILDDIRTOP)\wish$(TCL_VERSION)$(SUFX).exe" -TKSTUBLIB = "$(_TKDIR)\win\$(BUILDDIRTOP)\tkstub$(TCL_VERSION).lib" -TKIMPLIB = "$(_TKDIR)\win\$(BUILDDIRTOP)\tk$(TCL_VERSION)$(SUFX).lib" -TK_INCLUDES = -I"$(_TKDIR)\generic" -I"$(_TKDIR)\win" -I"$(_TKDIR)\xlib" -!endif -!endif - -!endif - -#---------------------------------------------------------- -# Display stats being used. -#---------------------------------------------------------- - -!message *** Intermediate directory will be '$(TMP_DIR)' -!message *** Output directory will be '$(OUT_DIR)' -!message *** Suffix for binaries will be '$(SUFX)' -!message *** Optional defines are '$(OPTDEFINES)' -!message *** Compiler version $(VCVER). Target machine is $(MACHINE) -!message *** Host architecture is $(NATIVE_ARCH) -!message *** Compiler options '$(COMPILERFLAGS) $(OPTIMIZATIONS) $(DEBUGFLAGS) $(WARNINGS)' -!message *** Link options '$(LINKERFLAGS)' - -!endif +#------------------------------------------------------------------------------
+# rules.vc --
+#
+# Microsoft Visual C++ makefile include for decoding the commandline
+# macros. This file does not need editing to build Tcl.
+#
+# See the file "license.terms" for information on usage and redistribution
+# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
+#
+# Copyright (c) 2001-2003 David Gravereaux.
+# Copyright (c) 2003-2008 Patrick Thoyts
+#------------------------------------------------------------------------------
+
+!ifndef _RULES_VC
+_RULES_VC = 1
+
+cc32 = $(CC) # built-in default.
+link32 = link
+lib32 = lib
+rc32 = $(RC) # built-in default.
+
+!ifndef INSTALLDIR
+### Assume the normal default.
+_INSTALLDIR = C:\Program Files\Tcl
+!else
+### Fix the path separators.
+_INSTALLDIR = $(INSTALLDIR:/=\)
+!endif
+
+#----------------------------------------------------------
+# Set the proper copy method to avoid overwrite questions
+# to the user when copying files and selecting the right
+# "delete all" method.
+#----------------------------------------------------------
+
+!if "$(OS)" == "Windows_NT"
+RMDIR = rmdir /S /Q
+ERRNULL = 2>NUL
+!if ![ver | find "4.0" > nul]
+CPY = echo y | xcopy /i >NUL
+COPY = copy >NUL
+!else
+CPY = xcopy /i /y >NUL
+COPY = copy /y >NUL
+!endif
+!else # "$(OS)" != "Windows_NT"
+CPY = xcopy /i >_JUNK.OUT # On Win98 NUL does not work here.
+COPY = copy >_JUNK.OUT # On Win98 NUL does not work here.
+RMDIR = deltree /Y
+NULL = \NUL # Used in testing directory existence
+ERRNULL = >NUL # Win9x shell cannot redirect stderr
+!endif
+MKDIR = mkdir
+
+#------------------------------------------------------------------------------
+# Determine the host and target architectures and compiler version.
+#------------------------------------------------------------------------------
+
+_HASH=^#
+_VC_MANIFEST_EMBED_EXE=
+_VC_MANIFEST_EMBED_DLL=
+VCVER=0
+!if ![echo VCVERSION=_MSC_VER > vercl.x] \
+ && ![echo $(_HASH)if defined(_M_IX86) >> vercl.x] \
+ && ![echo ARCH=IX86 >> vercl.x] \
+ && ![echo $(_HASH)elif defined(_M_AMD64) >> vercl.x] \
+ && ![echo ARCH=AMD64 >> vercl.x] \
+ && ![echo $(_HASH)endif >> vercl.x] \
+ && ![cl -nologo -TC -P vercl.x $(ERRNULL)]
+!include vercl.i
+!if ![echo VCVER= ^\> vercl.vc] \
+ && ![set /a $(VCVERSION) / 100 - 6 >> vercl.vc]
+!include vercl.vc
+!endif
+!endif
+!if ![del $(ERRNUL) /q/f vercl.x vercl.i vercl.vc]
+!endif
+
+!if ![reg query HKLM\Hardware\Description\System\CentralProcessor\0 /v Identifier | findstr /i x86]
+NATIVE_ARCH=IX86
+!else
+NATIVE_ARCH=AMD64
+!endif
+
+# Since MSVC8 we must deal with manifest resources.
+!if $(VCVERSION) >= 1400
+_VC_MANIFEST_EMBED_EXE=if exist $@.manifest mt -nologo -manifest $@.manifest -outputresource:$@;1
+_VC_MANIFEST_EMBED_DLL=if exist $@.manifest mt -nologo -manifest $@.manifest -outputresource:$@;2
+!endif
+
+!ifndef MACHINE
+MACHINE=$(ARCH)
+!endif
+
+!ifndef CFG_ENCODING
+CFG_ENCODING = \"cp1252\"
+!endif
+
+!message ===============================================================================
+
+#----------------------------------------------------------
+# build the helper app we need to overcome nmake's limiting
+# environment.
+#----------------------------------------------------------
+
+!if !exist(nmakehlp.exe)
+!if [$(cc32) -nologo nmakehlp.c -link -subsystem:console > nul]
+!endif
+!endif
+
+#----------------------------------------------------------
+# Test for compiler features
+#----------------------------------------------------------
+
+### test for optimizations
+!if [nmakehlp -c -Ot]
+!message *** Compiler has 'Optimizations'
+OPTIMIZING = 1
+!else
+!message *** Compiler does not have 'Optimizations'
+OPTIMIZING = 0
+!endif
+
+OPTIMIZATIONS =
+
+!if [nmakehlp -c -Ot]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -Ot
+!endif
+
+!if [nmakehlp -c -Oi]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -Oi
+!endif
+
+!if [nmakehlp -c -Op]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -Op
+!endif
+
+!if [nmakehlp -c -fp:strict]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -fp:strict
+!endif
+
+!if [nmakehlp -c -Gs]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -Gs
+!endif
+
+!if [nmakehlp -c -GS]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -GS
+!endif
+
+!if [nmakehlp -c -GL]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -GL
+!endif
+
+DEBUGFLAGS =
+
+!if [nmakehlp -c -RTC1]
+DEBUGFLAGS = $(DEBUGFLAGS) -RTC1
+!elseif [nmakehlp -c -GZ]
+DEBUGFLAGS = $(DEBUGFLAGS) -GZ
+!endif
+
+COMPILERFLAGS =-W3 -DUNICODE -D_UNICODE
+
+# In v13 -GL and -YX are incompatible.
+!if [nmakehlp -c -YX]
+!if ![nmakehlp -c -GL]
+OPTIMIZATIONS = $(OPTIMIZATIONS) -YX
+!endif
+!endif
+
+!if "$(MACHINE)" == "IX86"
+### test for pentium errata
+!if [nmakehlp -c -QI0f]
+!message *** Compiler has 'Pentium 0x0f fix'
+COMPILERFLAGS = $(COMPILERFLAGS) -QI0f
+!else
+!message *** Compiler does not have 'Pentium 0x0f fix'
+!endif
+!endif
+
+!if "$(MACHINE)" == "IA64"
+### test for Itanium errata
+!if [nmakehlp -c -QIA64_Bx]
+!message *** Compiler has 'B-stepping errata workarounds'
+COMPILERFLAGS = $(COMPILERFLAGS) -QIA64_Bx
+!else
+!message *** Compiler does not have 'B-stepping errata workarounds'
+!endif
+!endif
+
+!if "$(MACHINE)" == "IX86"
+### test for -align:4096, when align:512 will do.
+!if [nmakehlp -l -opt:nowin98]
+!message *** Linker has 'Win98 alignment problem'
+ALIGN98_HACK = 1
+!else
+!message *** Linker does not have 'Win98 alignment problem'
+ALIGN98_HACK = 0
+!endif
+!else
+ALIGN98_HACK = 0
+!endif
+
+LINKERFLAGS =
+
+!if [nmakehlp -l -ltcg]
+LINKERFLAGS =-ltcg
+!endif
+
+#----------------------------------------------------------
+# Decode the options requested.
+#----------------------------------------------------------
+
+!if "$(OPTS)" == "" || [nmakehlp -f "$(OPTS)" "none"]
+STATIC_BUILD = 0
+TCL_THREADS = 1
+DEBUG = 0
+SYMBOLS = 0
+PROFILE = 0
+PGO = 0
+MSVCRT = 1
+LOIMPACT = 0
+TCL_USE_STATIC_PACKAGES = 0
+USE_THREAD_ALLOC = 1
+UNCHECKED = 0
+!else
+!if [nmakehlp -f $(OPTS) "static"]
+!message *** Doing static
+STATIC_BUILD = 1
+!else
+STATIC_BUILD = 0
+!endif
+!if [nmakehlp -f $(OPTS) "msvcrt"]
+!message *** Doing msvcrt
+MSVCRT = 1
+!else
+!if !$(STATIC_BUILD)
+MSVCRT = 1
+!else
+MSVCRT = 0
+!endif
+!endif
+!if [nmakehlp -f $(OPTS) "staticpkg"] && $(STATIC_BUILD)
+!message *** Doing staticpkg
+TCL_USE_STATIC_PACKAGES = 1
+!else
+TCL_USE_STATIC_PACKAGES = 0
+!endif
+!if [nmakehlp -f $(OPTS) "nothreads"]
+!message *** Compile explicitly for non-threaded tcl
+TCL_THREADS = 0
+USE_THREAD_ALLOC= 0
+!else
+TCL_THREADS = 1
+USE_THREAD_ALLOC= 1
+!endif
+!if [nmakehlp -f $(OPTS) "symbols"]
+!message *** Doing symbols
+DEBUG = 1
+!else
+DEBUG = 0
+!endif
+!if [nmakehlp -f $(OPTS) "pdbs"]
+!message *** Doing pdbs
+SYMBOLS = 1
+!else
+SYMBOLS = 0
+!endif
+!if [nmakehlp -f $(OPTS) "profile"]
+!message *** Doing profile
+PROFILE = 1
+!else
+PROFILE = 0
+!endif
+!if [nmakehlp -f $(OPTS) "pgi"]
+!message *** Doing profile guided optimization instrumentation
+PGO = 1
+!elseif [nmakehlp -f $(OPTS) "pgo"]
+!message *** Doing profile guided optimization
+PGO = 2
+!else
+PGO = 0
+!endif
+!if [nmakehlp -f $(OPTS) "loimpact"]
+!message *** Doing loimpact
+LOIMPACT = 1
+!else
+LOIMPACT = 0
+!endif
+!if [nmakehlp -f $(OPTS) "thrdalloc"]
+!message *** Doing thrdalloc
+USE_THREAD_ALLOC = 1
+!endif
+!if [nmakehlp -f $(OPTS) "tclalloc"]
+!message *** Doing tclalloc
+USE_THREAD_ALLOC = 0
+!endif
+!if [nmakehlp -f $(OPTS) "unchecked"]
+!message *** Doing unchecked
+UNCHECKED = 1
+!else
+UNCHECKED = 0
+!endif
+!endif
+
+#----------------------------------------------------------
+# Figure-out how to name our intermediate and output directories.
+# We wouldn't want different builds to use the same .obj files
+# by accident.
+#----------------------------------------------------------
+
+#----------------------------------------
+# Naming convention:
+# t = full thread support.
+# s = static library (as opposed to an
+# import library)
+# g = linked to the debug enabled C
+# run-time.
+# x = special static build when it
+# links to the dynamic C run-time.
+#----------------------------------------
+SUFX = tsgx
+
+!if $(DEBUG)
+BUILDDIRTOP = Debug
+!else
+BUILDDIRTOP = Release
+!endif
+
+!if "$(MACHINE)" != "IX86"
+BUILDDIRTOP =$(BUILDDIRTOP)_$(MACHINE)
+!endif
+!if $(VCVER) > 6
+BUILDDIRTOP =$(BUILDDIRTOP)_VC$(VCVER)
+!endif
+
+!if !$(DEBUG) || $(DEBUG) && $(UNCHECKED)
+SUFX = $(SUFX:g=)
+!endif
+
+TMP_DIRFULL = .\$(BUILDDIRTOP)\$(PROJECT)_ThreadedDynamicStaticX
+
+!if !$(STATIC_BUILD)
+TMP_DIRFULL = $(TMP_DIRFULL:Static=)
+SUFX = $(SUFX:s=)
+EXT = dll
+TMP_DIRFULL = $(TMP_DIRFULL:X=)
+SUFX = $(SUFX:x=)
+!else
+TMP_DIRFULL = $(TMP_DIRFULL:Dynamic=)
+EXT = lib
+!if !$(MSVCRT)
+TMP_DIRFULL = $(TMP_DIRFULL:X=)
+SUFX = $(SUFX:x=)
+!endif
+!endif
+
+!if !$(TCL_THREADS)
+TMP_DIRFULL = $(TMP_DIRFULL:Threaded=)
+SUFX = $(SUFX:t=)
+!endif
+
+!ifndef TMP_DIR
+TMP_DIR = $(TMP_DIRFULL)
+!ifndef OUT_DIR
+OUT_DIR = .\$(BUILDDIRTOP)
+!endif
+!else
+!ifndef OUT_DIR
+OUT_DIR = $(TMP_DIR)
+!endif
+!endif
+
+
+#----------------------------------------------------------
+# Decode the statistics requested.
+#----------------------------------------------------------
+
+!if "$(STATS)" == "" || [nmakehlp -f "$(STATS)" "none"]
+TCL_MEM_DEBUG = 0
+TCL_COMPILE_DEBUG = 0
+!else
+!if [nmakehlp -f $(STATS) "memdbg"]
+!message *** Doing memdbg
+TCL_MEM_DEBUG = 1
+!else
+TCL_MEM_DEBUG = 0
+!endif
+!if [nmakehlp -f $(STATS) "compdbg"]
+!message *** Doing compdbg
+TCL_COMPILE_DEBUG = 1
+!else
+TCL_COMPILE_DEBUG = 0
+!endif
+!endif
+
+
+#----------------------------------------------------------
+# Decode the checks requested.
+#----------------------------------------------------------
+
+!if "$(CHECKS)" == "" || [nmakehlp -f "$(CHECKS)" "none"]
+TCL_NO_DEPRECATED = 0
+WARNINGS = -W3
+!else
+!if [nmakehlp -f $(CHECKS) "nodep"]
+!message *** Doing nodep check
+TCL_NO_DEPRECATED = 1
+!else
+TCL_NO_DEPRECATED = 0
+!endif
+!if [nmakehlp -f $(CHECKS) "fullwarn"]
+!message *** Doing full warnings check
+WARNINGS = -W4
+!if [nmakehlp -l -warn:3]
+LINKERFLAGS = $(LINKERFLAGS) -warn:3
+!endif
+!else
+WARNINGS = -W3
+!endif
+!if [nmakehlp -f $(CHECKS) "64bit"] && [nmakehlp -c -Wp64]
+!message *** Doing 64bit portability warnings
+WARNINGS = $(WARNINGS) -Wp64
+!endif
+!endif
+
+!if $(PGO) > 1
+!if [nmakehlp -l -ltcg:pgoptimize]
+LINKERFLAGS = $(LINKERFLAGS:-ltcg=) -ltcg:pgoptimize
+!else
+MSG=^
+This compiler does not support profile guided optimization.
+!error $(MSG)
+!endif
+!elseif $(PGO) > 0
+!if [nmakehlp -l -ltcg:pginstrument]
+LINKERFLAGS = $(LINKERFLAGS:-ltcg=) -ltcg:pginstrument
+!else
+MSG=^
+This compiler does not support profile guided optimization.
+!error $(MSG)
+!endif
+!endif
+
+#----------------------------------------------------------
+# Set our defines now armed with our options.
+#----------------------------------------------------------
+
+OPTDEFINES = -DTCL_CFGVAL_ENCODING=$(CFG_ENCODING) -DSTDC_HEADERS
+
+!if $(TCL_MEM_DEBUG)
+OPTDEFINES = $(OPTDEFINES) -DTCL_MEM_DEBUG
+!endif
+!if $(TCL_COMPILE_DEBUG)
+OPTDEFINES = $(OPTDEFINES) -DTCL_COMPILE_DEBUG -DTCL_COMPILE_STATS
+!endif
+!if $(TCL_THREADS)
+OPTDEFINES = $(OPTDEFINES) -DTCL_THREADS=1
+!if $(USE_THREAD_ALLOC)
+OPTDEFINES = $(OPTDEFINES) -DUSE_THREAD_ALLOC=1
+!endif
+!endif
+!if $(STATIC_BUILD)
+OPTDEFINES = $(OPTDEFINES) -DSTATIC_BUILD
+!endif
+!if $(TCL_NO_DEPRECATED)
+OPTDEFINES = $(OPTDEFINES) -DTCL_NO_DEPRECATED
+!endif
+
+!if !$(DEBUG)
+OPTDEFINES = $(OPTDEFINES) -DNDEBUG
+!if $(OPTIMIZING)
+OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_OPTIMIZED
+!endif
+!endif
+!if $(PROFILE)
+OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_PROFILED
+!endif
+!if "$(MACHINE)" == "IA64" || "$(MACHINE)" == "AMD64"
+OPTDEFINES = $(OPTDEFINES) -DTCL_CFG_DO64BIT
+!endif
+!if $(VCVERSION) < 1300
+OPTDEFINES = $(OPTDEFINES) -DNO_STRTOI64
+!endif
+
+#----------------------------------------------------------
+# Locate the Tcl headers to build against
+#----------------------------------------------------------
+
+!if "$(PROJECT)" == "tcl"
+
+_TCL_H = ..\generic\tcl.h
+
+!else
+
+# If INSTALLDIR set to tcl root dir then reset to the lib dir.
+!if exist("$(_INSTALLDIR)\include\tcl.h")
+_INSTALLDIR=$(_INSTALLDIR)\lib
+!endif
+
+!if !defined(TCLDIR)
+!if exist("$(_INSTALLDIR)\..\include\tcl.h")
+TCLINSTALL = 1
+_TCLDIR = $(_INSTALLDIR)\..
+_TCL_H = $(_INSTALLDIR)\..\include\tcl.h
+TCLDIR = $(_INSTALLDIR)\..
+!else
+MSG=^
+Failed to find tcl.h. Set the TCLDIR macro.
+!error $(MSG)
+!endif
+!else
+_TCLDIR = $(TCLDIR:/=\)
+!if exist("$(_TCLDIR)\include\tcl.h")
+TCLINSTALL = 1
+_TCL_H = $(_TCLDIR)\include\tcl.h
+!elseif exist("$(_TCLDIR)\generic\tcl.h")
+TCLINSTALL = 0
+_TCL_H = $(_TCLDIR)\generic\tcl.h
+!else
+MSG =^
+Failed to find tcl.h. The TCLDIR macro does not appear correct.
+!error $(MSG)
+!endif
+!endif
+!endif
+
+#--------------------------------------------------------------
+# Extract various version numbers from tcl headers
+# The generated file is then included in the makefile.
+#--------------------------------------------------------------
+
+!if [echo REM = This file is generated from rules.vc > versions.vc]
+!endif
+!if [echo TCL_MAJOR_VERSION = \>> versions.vc] \
+ && [nmakehlp -V "$(_TCL_H)" TCL_MAJOR_VERSION >> versions.vc]
+!endif
+!if [echo TCL_MINOR_VERSION = \>> versions.vc] \
+ && [nmakehlp -V "$(_TCL_H)" TCL_MINOR_VERSION >> versions.vc]
+!endif
+!if [echo TCL_PATCH_LEVEL = \>> versions.vc] \
+ && [nmakehlp -V "$(_TCL_H)" TCL_PATCH_LEVEL >> versions.vc]
+!endif
+
+# If building the tcl core then we need additional package versions
+!if "$(PROJECT)" == "tcl"
+!if [echo PKG_HTTP_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\http\pkgIndex.tcl http >> versions.vc]
+!endif
+!if [echo PKG_TCLTEST_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\tcltest\pkgIndex.tcl tcltest >> versions.vc]
+!endif
+!if [echo PKG_MSGCAT_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\msgcat\pkgIndex.tcl msgcat >> versions.vc]
+!endif
+!if [echo PKG_PLATFORM_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\platform\pkgIndex.tcl "platform " >> versions.vc]
+!endif
+!if [echo PKG_SHELL_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\platform\pkgIndex.tcl "platform::shell" >> versions.vc]
+!endif
+!if [echo PKG_DDE_VER = \>> versions.vc] \
+ && [nmakehlp -V ..\library\dde\pkgIndex.tcl "dde " >> versions.vc]
+!endif
+!if [echo PKG_REG_VER =\>> versions.vc] \
+ && [nmakehlp -V ..\library\reg\pkgIndex.tcl registry >> versions.vc]
+!endif
+!endif
+
+!include versions.vc
+
+#--------------------------------------------------------------
+# Setup tcl version dependent stuff headers
+#--------------------------------------------------------------
+
+!if "$(PROJECT)" != "tcl"
+
+TCL_VERSION = $(TCL_MAJOR_VERSION)$(TCL_MINOR_VERSION)
+
+!if $(TCLINSTALL)
+TCLSH = "$(_TCLDIR)\bin\tclsh$(TCL_VERSION)$(SUFX).exe"
+!if !exist($(TCLSH)) && $(TCL_THREADS)
+TCLSH = "$(_TCLDIR)\bin\tclsh$(TCL_VERSION)t$(SUFX).exe"
+!endif
+TCLSTUBLIB = "$(_TCLDIR)\lib\tclstub$(TCL_VERSION).lib"
+TCLIMPLIB = "$(_TCLDIR)\lib\tcl$(TCL_VERSION)$(SUFX).lib"
+TCL_LIBRARY = $(_TCLDIR)\lib
+TCLREGLIB = "$(_TCLDIR)\lib\tclreg13$(SUFX:t=).lib"
+TCLDDELIB = "$(_TCLDIR)\lib\tcldde14$(SUFX:t=).lib"
+COFFBASE = \must\have\tcl\sources\to\build\this\target
+TCLTOOLSDIR = \must\have\tcl\sources\to\build\this\target
+TCL_INCLUDES = -I"$(_TCLDIR)\include"
+!else
+TCLSH = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclsh$(TCL_VERSION)$(SUFX).exe"
+!if !exist($(TCLSH)) && $(TCL_THREADS)
+TCLSH = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclsh$(TCL_VERSION)t$(SUFX).exe"
+!endif
+TCLSTUBLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclstub$(TCL_VERSION).lib"
+TCLIMPLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tcl$(TCL_VERSION)$(SUFX).lib"
+TCL_LIBRARY = $(_TCLDIR)\library
+TCLREGLIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tclreg13$(SUFX:t=).lib"
+TCLDDELIB = "$(_TCLDIR)\win\$(BUILDDIRTOP)\tcldde14$(SUFX:t=).lib"
+COFFBASE = "$(_TCLDIR)\win\coffbase.txt"
+TCLTOOLSDIR = $(_TCLDIR)\tools
+TCL_INCLUDES = -I"$(_TCLDIR)\generic" -I"$(_TCLDIR)\win"
+!endif
+
+!endif
+
+#-------------------------------------------------------------------------
+# Locate the Tk headers to build against
+#-------------------------------------------------------------------------
+
+!if "$(PROJECT)" == "tk"
+_TK_H = ..\generic\tk.h
+_INSTALLDIR = $(_INSTALLDIR)\..
+!endif
+
+!ifdef PROJECT_REQUIRES_TK
+!if !defined(TKDIR)
+!if exist("$(_INSTALLDIR)\..\include\tk.h")
+TKINSTALL = 1
+_TKDIR = $(_INSTALLDIR)\..
+_TK_H = $(_TKDIR)\include\tk.h
+TKDIR = $(_TKDIR)
+!elseif exist("$(_TCLDIR)\include\tk.h")
+TKINSTALL = 1
+_TKDIR = $(_TCLDIR)
+_TK_H = $(_TKDIR)\include\tk.h
+TKDIR = $(_TKDIR)
+!endif
+!else
+_TKDIR = $(TKDIR:/=\)
+!if exist("$(_TKDIR)\include\tk.h")
+TKINSTALL = 1
+_TK_H = $(_TKDIR)\include\tk.h
+!elseif exist("$(_TKDIR)\generic\tk.h")
+TKINSTALL = 0
+_TK_H = $(_TKDIR)\generic\tk.h
+!else
+MSG =^
+Failed to find tk.h. The TKDIR macro does not appear correct.
+!error $(MSG)
+!endif
+!endif
+!endif
+
+#-------------------------------------------------------------------------
+# Extract Tk version numbers
+#-------------------------------------------------------------------------
+
+!if defined(PROJECT_REQUIRES_TK) || "$(PROJECT)" == "tk"
+
+!if [echo TK_MAJOR_VERSION = \>> versions.vc] \
+ && [nmakehlp -V $(_TK_H) TK_MAJOR_VERSION >> versions.vc]
+!endif
+!if [echo TK_MINOR_VERSION = \>> versions.vc] \
+ && [nmakehlp -V $(_TK_H) TK_MINOR_VERSION >> versions.vc]
+!endif
+!if [echo TK_PATCH_LEVEL = \>> versions.vc] \
+ && [nmakehlp -V $(_TK_H) TK_PATCH_LEVEL >> versions.vc]
+!endif
+
+!include versions.vc
+
+TK_DOTVERSION = $(TK_MAJOR_VERSION).$(TK_MINOR_VERSION)
+TK_VERSION = $(TK_MAJOR_VERSION)$(TK_MINOR_VERSION)
+
+!if "$(PROJECT)" != "tk"
+!if $(TKINSTALL)
+WISH = "$(_TKDIR)\bin\wish$(TK_VERSION)$(SUFX).exe"
+TKSTUBLIB = "$(_TKDIR)\lib\tkstub$(TK_VERSION).lib"
+TKIMPLIB = "$(_TKDIR)\lib\tk$(TK_VERSION)$(SUFX).lib"
+TK_INCLUDES = -I"$(_TKDIR)\include"
+!else
+WISH = "$(_TKDIR)\win\$(BUILDDIRTOP)\wish$(TCL_VERSION)$(SUFX).exe"
+TKSTUBLIB = "$(_TKDIR)\win\$(BUILDDIRTOP)\tkstub$(TCL_VERSION).lib"
+TKIMPLIB = "$(_TKDIR)\win\$(BUILDDIRTOP)\tk$(TCL_VERSION)$(SUFX).lib"
+TK_INCLUDES = -I"$(_TKDIR)\generic" -I"$(_TKDIR)\win" -I"$(_TKDIR)\xlib"
+!endif
+!endif
+
+!endif
+
+#----------------------------------------------------------
+# Display stats being used.
+#----------------------------------------------------------
+
+!message *** Intermediate directory will be '$(TMP_DIR)'
+!message *** Output directory will be '$(OUT_DIR)'
+!message *** Suffix for binaries will be '$(SUFX)'
+!message *** Optional defines are '$(OPTDEFINES)'
+!message *** Compiler version $(VCVER). Target machine is $(MACHINE)
+!message *** Host architecture is $(NATIVE_ARCH)
+!message *** Compiler options '$(COMPILERFLAGS) $(OPTIMIZATIONS) $(DEBUGFLAGS) $(WARNINGS)'
+!message *** Link options '$(LINKERFLAGS)'
+
+!endif
diff --git a/win/tcl.dsp b/win/tcl.dsp index 57ec6bf..96d5893 100644 --- a/win/tcl.dsp +++ b/win/tcl.dsp @@ -1,1567 +1,1567 @@ -# Microsoft Developer Studio Project File - Name="tcl" - Package Owner=<4> -# Microsoft Developer Studio Generated Build File, Format Version 6.00 -# ** DO NOT EDIT ** - -# TARGTYPE "Win32 (x86) External Target" 0x0106 - -CFG=tcl - Win32 Debug Static -!MESSAGE This is not a valid makefile. To build this project using NMAKE, -!MESSAGE use the Export Makefile command and run -!MESSAGE -!MESSAGE NMAKE /f "tcl.mak". -!MESSAGE -!MESSAGE You can specify a configuration when running NMAKE -!MESSAGE by defining the macro CFG on the command line. For example: -!MESSAGE -!MESSAGE NMAKE /f "tcl.mak" CFG="tcl - Win32 Debug Static" -!MESSAGE -!MESSAGE Possible choices for configuration are: -!MESSAGE -!MESSAGE "tcl - Win32 Release" (based on "Win32 (x86) External Target") -!MESSAGE "tcl - Win32 Debug" (based on "Win32 (x86) External Target") -!MESSAGE "tcl - Win32 Debug Static" (based on "Win32 (x86) External Target") -!MESSAGE "tcl - Win32 Release Static" (based on "Win32 (x86) External Target") -!MESSAGE - -# Begin Project -# PROP AllowPerConfigDependencies 0 -# PROP Scc_ProjName "" -# PROP Scc_LocalPath "" - -!IF "$(CFG)" == "tcl - Win32 Release" - -# PROP BASE Use_MFC 0 -# PROP BASE Use_Debug_Libraries 0 -# PROP BASE Output_Dir "Release" -# PROP BASE Intermediate_Dir "Release\tcl_Dynamic" -# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=none MSVCDIR=IDE" -# PROP BASE Rebuild_Opt "-a" -# PROP BASE Target_File "Release\tclsh85.exe" -# PROP BASE Bsc_Name "" -# PROP BASE Target_Dir "" -# PROP Use_MFC 0 -# PROP Use_Debug_Libraries 0 -# PROP Output_Dir "Release" -# PROP Intermediate_Dir "Release\tcl_Dynamic" -# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=threads MSVCDIR=IDE" -# PROP Rebuild_Opt "clean release" -# PROP Target_File "Release\tclsh85t.exe" -# PROP Bsc_Name "" -# PROP Target_Dir "" - -!ELSEIF "$(CFG)" == "tcl - Win32 Debug" - -# PROP BASE Use_MFC 0 -# PROP BASE Use_Debug_Libraries 1 -# PROP BASE Output_Dir "Debug" -# PROP BASE Intermediate_Dir "Debug\tcl_Dynamic" -# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols MSVCDIR=IDE" -# PROP BASE Rebuild_Opt "-a" -# PROP BASE Target_File "Debug\tclsh85g.exe" -# PROP BASE Bsc_Name "" -# PROP BASE Target_Dir "" -# PROP Use_MFC 0 -# PROP Use_Debug_Libraries 1 -# PROP Output_Dir "Debug" -# PROP Intermediate_Dir "Debug\tcl_Dynamic" -# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=threads,symbols MSVCDIR=IDE" -# PROP Rebuild_Opt "clean release" -# PROP Target_File "Debug\tclsh85tg.exe" -# PROP Bsc_Name "" -# PROP Target_Dir "" - -!ELSEIF "$(CFG)" == "tcl - Win32 Debug Static" - -# PROP BASE Use_MFC 0 -# PROP BASE Use_Debug_Libraries 1 -# PROP BASE Output_Dir "Debug" -# PROP BASE Intermediate_Dir "Debug\tcl_Static" -# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols,static MSVCDIR=IDE" -# PROP BASE Rebuild_Opt "-a" -# PROP BASE Target_File "Debug\tclsh85sg.exe" -# PROP BASE Bsc_Name "" -# PROP BASE Target_Dir "" -# PROP Use_MFC 0 -# PROP Use_Debug_Libraries 1 -# PROP Output_Dir "Debug" -# PROP Intermediate_Dir "Debug\tcl_Static" -# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols,static MSVCDIR=IDE" -# PROP Rebuild_Opt "-a" -# PROP Target_File "Debug\tclsh85sg.exe" -# PROP Bsc_Name "" -# PROP Target_Dir "" - -!ELSEIF "$(CFG)" == "tcl - Win32 Release Static" - -# PROP BASE Use_MFC 0 -# PROP BASE Use_Debug_Libraries 0 -# PROP BASE Output_Dir "Release" -# PROP BASE Intermediate_Dir "Release\tcl_Static" -# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=static MSVCDIR=IDE" -# PROP BASE Rebuild_Opt "-a" -# PROP BASE Target_File "Release\tclsh85s.exe" -# PROP BASE Bsc_Name "" -# PROP BASE Target_Dir "" -# PROP Use_MFC 0 -# PROP Use_Debug_Libraries 0 -# PROP Output_Dir "Release" -# PROP Intermediate_Dir "Release\tcl_Static" -# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=static MSVCDIR=IDE" -# PROP Rebuild_Opt "-a" -# PROP Target_File "Release\tclsh85s.exe" -# PROP Bsc_Name "" -# PROP Target_Dir "" - -!ENDIF - -# Begin Target - -# Name "tcl - Win32 Release" -# Name "tcl - Win32 Debug" -# Name "tcl - Win32 Debug Static" -# Name "tcl - Win32 Release Static" - -!IF "$(CFG)" == "tcl - Win32 Release" - -!ELSEIF "$(CFG)" == "tcl - Win32 Debug" - -!ELSEIF "$(CFG)" == "tcl - Win32 Debug Static" - -!ELSEIF "$(CFG)" == "tcl - Win32 Release Static" - -!ENDIF - -# Begin Group "compat" - -# PROP Default_Filter "" -# Begin Source File - -SOURCE=..\compat\dirent.h -# End Source File -# Begin Source File - -SOURCE=..\compat\dirent2.h -# End Source File -# Begin Source File - -SOURCE=..\compat\dlfcn.h -# End Source File -# Begin Source File - -SOURCE=..\compat\fixstrtod.c -# End Source File -# Begin Source File - -SOURCE=..\compat\float.h -# End Source File -# Begin Source File - -SOURCE=..\compat\gettod.c -# End Source File -# Begin Source File - -SOURCE=..\compat\limits.h -# End Source File -# Begin Source File - -SOURCE=..\compat\memcmp.c -# End Source File -# Begin Source File - -SOURCE=..\compat\opendir.c -# End Source File -# Begin Source File - -SOURCE=..\compat\README -# End Source File -# Begin Source File - -SOURCE=..\compat\stdlib.h -# End Source File -# Begin Source File - -SOURCE=..\compat\string.h -# End Source File -# Begin Source File - -SOURCE=..\compat\strncasecmp.c -# End Source File -# Begin Source File - -SOURCE=..\compat\strstr.c -# End Source File -# Begin Source File - -SOURCE=..\compat\strtod.c -# End Source File -# Begin Source File - -SOURCE=..\compat\strtol.c -# End Source File -# Begin Source File - -SOURCE=..\compat\strtoul.c -# End Source File -# Begin Source File - -SOURCE=..\compat\tclErrno.h -# End Source File -# Begin Source File - -SOURCE=..\compat\unistd.h -# End Source File -# Begin Source File - -SOURCE=..\compat\waitpid.c -# End Source File -# End Group -# Begin Group "doc" - -# PROP Default_Filter "" -# Begin Source File - -SOURCE=..\doc\Access.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\AddErrInfo.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\after.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Alloc.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\AllowExc.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\append.n -# End Source File -# Begin Source File - -SOURCE=..\doc\AppInit.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\array.n -# End Source File -# Begin Source File - -SOURCE=..\doc\AssocData.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Async.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\BackgdErr.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Backslash.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\bgerror.n -# End Source File -# Begin Source File - -SOURCE=..\doc\binary.n -# End Source File -# Begin Source File - -SOURCE=..\doc\BoolObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\break.n -# End Source File -# Begin Source File - -SOURCE=..\doc\ByteArrObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CallDel.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\case.n -# End Source File -# Begin Source File - -SOURCE=..\doc\catch.n -# End Source File -# Begin Source File - -SOURCE=..\doc\cd.n -# End Source File -# Begin Source File - -SOURCE=..\doc\ChnlStack.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\clock.n -# End Source File -# Begin Source File - -SOURCE=..\doc\close.n -# End Source File -# Begin Source File - -SOURCE=..\doc\CmdCmplt.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Concat.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\concat.n -# End Source File -# Begin Source File - -SOURCE=..\doc\continue.n -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtChannel.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtChnlHdlr.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtCloseHdlr.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtCommand.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtFileHdlr.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtInterp.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtMathFnc.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtObjCmd.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtSlave.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtTimerHdlr.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\CrtTrace.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\dde.n -# End Source File -# Begin Source File - -SOURCE=..\doc\DetachPids.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\DoOneEvent.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\DoubleObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\DoWhenIdle.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\DString.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\DumpActiveMemory.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Encoding.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\encoding.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Environment.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\eof.n -# End Source File -# Begin Source File - -SOURCE=..\doc\error.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Eval.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\eval.n -# End Source File -# Begin Source File - -SOURCE=..\doc\exec.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Exit.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\exit.n -# End Source File -# Begin Source File - -SOURCE=..\doc\expr.n -# End Source File -# Begin Source File - -SOURCE=..\doc\ExprLong.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\ExprLongObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\fblocked.n -# End Source File -# Begin Source File - -SOURCE=..\doc\fconfigure.n -# End Source File -# Begin Source File - -SOURCE=..\doc\fcopy.n -# End Source File -# Begin Source File - -SOURCE=..\doc\file.n -# End Source File -# Begin Source File - -SOURCE=..\doc\fileevent.n -# End Source File -# Begin Source File - -SOURCE=..\doc\filename.n -# End Source File -# Begin Source File - -SOURCE=..\doc\FileSystem.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\FindExec.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\flush.n -# End Source File -# Begin Source File - -SOURCE=..\doc\for.n -# End Source File -# Begin Source File - -SOURCE=..\doc\foreach.n -# End Source File -# Begin Source File - -SOURCE=..\doc\format.n -# End Source File -# Begin Source File - -SOURCE=..\doc\GetCwd.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\GetHostName.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\GetIndex.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\GetInt.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\GetOpnFl.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\gets.n -# End Source File -# Begin Source File - -SOURCE=..\doc\GetStdChan.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\GetVersion.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\glob.n -# End Source File -# Begin Source File - -SOURCE=..\doc\global.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Hash.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\history.n -# End Source File -# Begin Source File - -SOURCE=..\doc\http.n -# End Source File -# Begin Source File - -SOURCE=..\doc\if.n -# End Source File -# Begin Source File - -SOURCE=..\doc\incr.n -# End Source File -# Begin Source File - -SOURCE=..\doc\info.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Init.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\InitStubs.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Interp.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\interp.n -# End Source File -# Begin Source File - -SOURCE=..\doc\IntObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\join.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lappend.n -# End Source File -# Begin Source File - -SOURCE=..\doc\library.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lindex.n -# End Source File -# Begin Source File - -SOURCE=..\doc\LinkVar.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\linsert.n -# End Source File -# Begin Source File - -SOURCE=..\doc\list.n -# End Source File -# Begin Source File - -SOURCE=..\doc\ListObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\llength.n -# End Source File -# Begin Source File - -SOURCE=..\doc\load.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lrange.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lreplace.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lsearch.n -# End Source File -# Begin Source File - -SOURCE=..\doc\lsort.n -# End Source File -# Begin Source File - -SOURCE=..\doc\man.macros -# End Source File -# Begin Source File - -SOURCE=..\doc\memory.n -# End Source File -# Begin Source File - -SOURCE=..\doc\msgcat.n -# End Source File -# Begin Source File - -SOURCE=..\doc\namespace.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Notifier.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Object.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\ObjectType.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\open.n -# End Source File -# Begin Source File - -SOURCE=..\doc\OpenFileChnl.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\OpenTcp.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\package.n -# End Source File -# Begin Source File - -SOURCE=..\doc\packagens.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Panic.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\ParseCmd.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\pid.n -# End Source File -# Begin Source File - -SOURCE=..\doc\pkgMkIndex.n -# End Source File -# Begin Source File - -SOURCE=..\doc\PkgRequire.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Preserve.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\PrintDbl.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\proc.n -# End Source File -# Begin Source File - -SOURCE=..\doc\puts.n -# End Source File -# Begin Source File - -SOURCE=..\doc\pwd.n -# End Source File -# Begin Source File - -SOURCE=..\doc\re_syntax.n -# End Source File -# Begin Source File - -SOURCE=..\doc\read.n -# End Source File -# Begin Source File - -SOURCE=..\doc\RecEvalObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\RecordEval.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\RegExp.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\regexp.n -# End Source File -# Begin Source File - -SOURCE=..\doc\registry.n -# End Source File -# Begin Source File - -SOURCE=..\doc\regsub.n -# End Source File -# Begin Source File - -SOURCE=..\doc\rename.n -# End Source File -# Begin Source File - -SOURCE=..\doc\return.n -# End Source File -# Begin Source File - -SOURCE=..\doc\safe.n -# End Source File -# Begin Source File - -SOURCE=..\doc\SaveResult.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\scan.n -# End Source File -# Begin Source File - -SOURCE=..\doc\seek.n -# End Source File -# Begin Source File - -SOURCE=..\doc\set.n -# End Source File -# Begin Source File - -SOURCE=..\doc\SetErrno.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\SetRecLmt.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\SetResult.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\SetVar.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Signal.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Sleep.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\socket.n -# End Source File -# Begin Source File - -SOURCE=..\doc\source.n -# End Source File -# Begin Source File - -SOURCE=..\doc\SourceRCFile.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\split.n -# End Source File -# Begin Source File - -SOURCE=..\doc\SplitList.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\SplitPath.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\StaticPkg.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\StdChannels.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\string.n -# End Source File -# Begin Source File - -SOURCE=..\doc\StringObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\StrMatch.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\subst.n -# End Source File -# Begin Source File - -SOURCE=..\doc\SubstObj.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\switch.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Tcl.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Tcl_Main.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\TCL_MEM_DEBUG.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\tclsh.1 -# End Source File -# Begin Source File - -SOURCE=..\doc\tcltest.n -# End Source File -# Begin Source File - -SOURCE=..\doc\tclvars.n -# End Source File -# Begin Source File - -SOURCE=..\doc\tell.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Thread.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\time.n -# End Source File -# Begin Source File - -SOURCE=..\doc\ToUpper.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\trace.n -# End Source File -# Begin Source File - -SOURCE=..\doc\TraceVar.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\Translate.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\UniCharIsAlpha.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\unknown.n -# End Source File -# Begin Source File - -SOURCE=..\doc\unset.n -# End Source File -# Begin Source File - -SOURCE=..\doc\update.n -# End Source File -# Begin Source File - -SOURCE=..\doc\uplevel.n -# End Source File -# Begin Source File - -SOURCE=..\doc\UpVar.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\upvar.n -# End Source File -# Begin Source File - -SOURCE=..\doc\Utf.3 -# End Source File -# Begin Source File - -SOURCE=..\doc\variable.n -# End Source File -# Begin Source File - -SOURCE=..\doc\vwait.n -# End Source File -# Begin Source File - -SOURCE=..\doc\while.n -# End Source File -# Begin Source File - -SOURCE=..\doc\WrongNumArgs.3 -# End Source File -# End Group -# Begin Group "generic" - -# PROP Default_Filter "" -# Begin Source File - -SOURCE=..\generic\README -# End Source File -# Begin Source File - -SOURCE=..\generic\regc_color.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regc_cvec.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regc_lex.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regc_locale.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regc_nfa.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regcomp.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regcustom.h -# End Source File -# Begin Source File - -SOURCE=..\generic\rege_dfa.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regerror.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regerrs.h -# End Source File -# Begin Source File - -SOURCE=..\generic\regex.h -# End Source File -# Begin Source File - -SOURCE=..\generic\regexec.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regfree.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regfronts.c -# End Source File -# Begin Source File - -SOURCE=..\generic\regguts.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tcl.decls -# End Source File -# Begin Source File - -SOURCE=..\generic\tcl.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclAlloc.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclAsync.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclBasic.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclBinary.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCkalloc.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclClock.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCmdAH.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCmdIL.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCmdMZ.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCompCmds.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCompExpr.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCompile.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclCompile.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclDate.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclDecls.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclEncoding.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclEnv.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclEvent.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclExecute.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclFCmd.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclFileName.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclGet.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclGetDate.y -# End Source File -# Begin Source File - -SOURCE=..\generic\tclHash.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclHistory.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIndexObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclInt.decls -# End Source File -# Begin Source File - -SOURCE=..\generic\tclInt.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIntDecls.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclInterp.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIntPlatDecls.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIO.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIO.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIOCmd.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIOGT.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIOSock.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclIOUtil.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclLink.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclListObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclLiteral.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclLoad.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclLoadNone.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclMain.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclNamesp.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclNotify.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPanic.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclParse.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPipe.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPkg.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPlatDecls.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPort.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPosixStr.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclPreserve.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclProc.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclRegexp.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclRegexp.h -# End Source File -# Begin Source File - -SOURCE=..\generic\tclResolve.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclResult.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclScan.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclStringObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclStubInit.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclStubLib.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclOOStubLib.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclTomMathStubLib.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclTest.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclTestObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclTestProcBodyObj.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclThread.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclThreadJoin.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclThreadTest.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclTimer.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclUniData.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclUtf.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclUtil.c -# End Source File -# Begin Source File - -SOURCE=..\generic\tclVar.c -# End Source File -# End Group -# Begin Group "library" - -# PROP Default_Filter "" -# Begin Source File - -SOURCE=..\library\auto.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\history.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\init.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\ldAout.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\package.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\parray.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\safe.tcl -# End Source File -# Begin Source File - -SOURCE=..\library\tclIndex -# End Source File -# Begin Source File - -SOURCE=..\library\word.tcl -# End Source File -# End Group -# Begin Group "mac" - -# PROP Default_Filter "" -# End Group -# Begin Group "tests" - -# PROP Default_Filter "" -# End Group -# Begin Group "tools" - -# PROP Default_Filter "" -# End Group -# Begin Group "unix" - -# PROP Default_Filter "" -# End Group -# Begin Group "win" - -# PROP Default_Filter "" -# Begin Source File - -SOURCE=.\aclocal.m4 -# End Source File -# Begin Source File - -SOURCE=.\cat.c -# End Source File -# Begin Source File - -SOURCE=.\configure -# End Source File -# Begin Source File - -SOURCE=.\configure.in -# End Source File -# Begin Source File - -SOURCE=.\makefile.bc -# End Source File -# Begin Source File - -SOURCE=.\Makefile.in -# End Source File -# Begin Source File - -SOURCE=.\makefile.vc -# End Source File -# Begin Source File - -SOURCE=.\mkd.bat -# End Source File -# Begin Source File - -SOURCE=.\README -# End Source File -# Begin Source File - -SOURCE=.\README.binary -# End Source File -# Begin Source File - -SOURCE=.\rmd.bat -# End Source File -# Begin Source File - -SOURCE=.\rules.vc -# End Source File -# Begin Source File - -SOURCE=.\tcl.hpj.in -# End Source File -# Begin Source File - -SOURCE=.\tcl.m4 -# End Source File -# Begin Source File - -SOURCE=.\tcl.rc -# End Source File -# Begin Source File - -SOURCE=.\tclAppInit.c -# End Source File -# Begin Source File - -SOURCE=.\tclConfig.sh.in -# End Source File -# Begin Source File - -SOURCE=.\tclsh.ico -# End Source File -# Begin Source File - -SOURCE=.\tclsh.rc -# End Source File -# Begin Source File - -SOURCE=.\tclWin32Dll.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinChan.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinConsole.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinDde.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinError.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinFCmd.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinFile.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinInit.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinInt.h -# End Source File -# Begin Source File - -SOURCE=.\tclWinLoad.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinNotify.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinPipe.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinPort.h -# End Source File -# Begin Source File - -SOURCE=.\tclWinReg.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinSerial.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinSock.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinTest.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinThrd.c -# End Source File -# Begin Source File - -SOURCE=.\tclWinTime.c -# End Source File -# End Group -# End Target -# End Project +# Microsoft Developer Studio Project File - Name="tcl" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) External Target" 0x0106
+
+CFG=tcl - Win32 Debug Static
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "tcl.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "tcl.mak" CFG="tcl - Win32 Debug Static"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "tcl - Win32 Release" (based on "Win32 (x86) External Target")
+!MESSAGE "tcl - Win32 Debug" (based on "Win32 (x86) External Target")
+!MESSAGE "tcl - Win32 Debug Static" (based on "Win32 (x86) External Target")
+!MESSAGE "tcl - Win32 Release Static" (based on "Win32 (x86) External Target")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+
+!IF "$(CFG)" == "tcl - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release\tcl_Dynamic"
+# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=none MSVCDIR=IDE"
+# PROP BASE Rebuild_Opt "-a"
+# PROP BASE Target_File "Release\tclsh85.exe"
+# PROP BASE Bsc_Name ""
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release\tcl_Dynamic"
+# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=threads MSVCDIR=IDE"
+# PROP Rebuild_Opt "clean release"
+# PROP Target_File "Release\tclsh85t.exe"
+# PROP Bsc_Name ""
+# PROP Target_Dir ""
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug\tcl_Dynamic"
+# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols MSVCDIR=IDE"
+# PROP BASE Rebuild_Opt "-a"
+# PROP BASE Target_File "Debug\tclsh85g.exe"
+# PROP BASE Bsc_Name ""
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug\tcl_Dynamic"
+# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=threads,symbols MSVCDIR=IDE"
+# PROP Rebuild_Opt "clean release"
+# PROP Target_File "Debug\tclsh85tg.exe"
+# PROP Bsc_Name ""
+# PROP Target_Dir ""
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Debug Static"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug\tcl_Static"
+# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols,static MSVCDIR=IDE"
+# PROP BASE Rebuild_Opt "-a"
+# PROP BASE Target_File "Debug\tclsh85sg.exe"
+# PROP BASE Bsc_Name ""
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug\tcl_Static"
+# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=symbols,static MSVCDIR=IDE"
+# PROP Rebuild_Opt "-a"
+# PROP Target_File "Debug\tclsh85sg.exe"
+# PROP Bsc_Name ""
+# PROP Target_Dir ""
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Release Static"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release\tcl_Static"
+# PROP BASE Cmd_Line "nmake -nologo -f makefile.vc OPTS=static MSVCDIR=IDE"
+# PROP BASE Rebuild_Opt "-a"
+# PROP BASE Target_File "Release\tclsh85s.exe"
+# PROP BASE Bsc_Name ""
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release\tcl_Static"
+# PROP Cmd_Line "nmake -nologo -f makefile.vc OPTS=static MSVCDIR=IDE"
+# PROP Rebuild_Opt "-a"
+# PROP Target_File "Release\tclsh85s.exe"
+# PROP Bsc_Name ""
+# PROP Target_Dir ""
+
+!ENDIF
+
+# Begin Target
+
+# Name "tcl - Win32 Release"
+# Name "tcl - Win32 Debug"
+# Name "tcl - Win32 Debug Static"
+# Name "tcl - Win32 Release Static"
+
+!IF "$(CFG)" == "tcl - Win32 Release"
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Debug"
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Debug Static"
+
+!ELSEIF "$(CFG)" == "tcl - Win32 Release Static"
+
+!ENDIF
+
+# Begin Group "compat"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\compat\dirent.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\dirent2.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\dlfcn.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\fixstrtod.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\float.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\gettod.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\limits.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\memcmp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\opendir.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\README
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\stdlib.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\string.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\strncasecmp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\strstr.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\strtod.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\strtol.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\strtoul.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\tclErrno.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\unistd.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\compat\waitpid.c
+# End Source File
+# End Group
+# Begin Group "doc"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\doc\Access.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\AddErrInfo.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\after.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Alloc.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\AllowExc.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\append.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\AppInit.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\array.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\AssocData.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Async.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\BackgdErr.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Backslash.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\bgerror.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\binary.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\BoolObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\break.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ByteArrObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CallDel.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\case.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\catch.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\cd.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ChnlStack.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\clock.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\close.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CmdCmplt.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Concat.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\concat.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\continue.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtChannel.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtChnlHdlr.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtCloseHdlr.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtCommand.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtFileHdlr.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtInterp.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtMathFnc.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtObjCmd.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtSlave.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtTimerHdlr.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\CrtTrace.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\dde.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DetachPids.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DoOneEvent.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DoubleObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DoWhenIdle.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DString.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\DumpActiveMemory.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Encoding.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\encoding.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Environment.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\eof.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\error.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Eval.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\eval.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\exec.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Exit.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\exit.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\expr.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ExprLong.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ExprLongObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\fblocked.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\fconfigure.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\fcopy.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\file.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\fileevent.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\filename.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\FileSystem.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\FindExec.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\flush.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\for.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\foreach.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\format.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetCwd.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetHostName.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetIndex.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetInt.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetOpnFl.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\gets.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetStdChan.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\GetVersion.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\glob.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\global.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Hash.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\history.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\http.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\if.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\incr.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\info.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Init.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\InitStubs.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Interp.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\interp.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\IntObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\join.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lappend.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\library.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lindex.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\LinkVar.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\linsert.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\list.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ListObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\llength.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\load.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lrange.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lreplace.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lsearch.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\lsort.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\man.macros
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\memory.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\msgcat.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\namespace.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Notifier.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Object.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ObjectType.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\open.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\OpenFileChnl.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\OpenTcp.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\package.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\packagens.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Panic.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ParseCmd.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\pid.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\pkgMkIndex.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\PkgRequire.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Preserve.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\PrintDbl.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\proc.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\puts.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\pwd.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\re_syntax.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\read.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\RecEvalObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\RecordEval.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\RegExp.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\regexp.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\registry.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\regsub.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\rename.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\return.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\safe.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SaveResult.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\scan.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\seek.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\set.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SetErrno.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SetRecLmt.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SetResult.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SetVar.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Signal.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Sleep.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\socket.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\source.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SourceRCFile.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\split.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SplitList.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SplitPath.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\StaticPkg.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\StdChannels.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\string.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\StringObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\StrMatch.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\subst.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\SubstObj.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\switch.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Tcl.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Tcl_Main.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\TCL_MEM_DEBUG.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\tclsh.1
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\tcltest.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\tclvars.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\tell.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Thread.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\time.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\ToUpper.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\trace.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\TraceVar.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Translate.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\UniCharIsAlpha.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\unknown.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\unset.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\update.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\uplevel.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\UpVar.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\upvar.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\Utf.3
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\variable.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\vwait.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\while.n
+# End Source File
+# Begin Source File
+
+SOURCE=..\doc\WrongNumArgs.3
+# End Source File
+# End Group
+# Begin Group "generic"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\generic\README
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regc_color.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regc_cvec.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regc_lex.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regc_locale.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regc_nfa.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regcomp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regcustom.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\rege_dfa.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regerror.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regerrs.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regex.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regexec.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regfree.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regfronts.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\regguts.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tcl.decls
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tcl.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclAlloc.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclAsync.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclBasic.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclBinary.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCkalloc.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclClock.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCmdAH.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCmdIL.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCmdMZ.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCompCmds.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCompExpr.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCompile.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclCompile.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclDate.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclDecls.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclEncoding.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclEnv.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclEvent.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclExecute.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclFCmd.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclFileName.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclGet.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclGetDate.y
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclHash.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclHistory.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIndexObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclInt.decls
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclInt.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIntDecls.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclInterp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIntPlatDecls.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIO.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIO.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIOCmd.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIOGT.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIOSock.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclIOUtil.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclLink.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclListObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclLiteral.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclLoad.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclLoadNone.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclMain.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclNamesp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclNotify.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPanic.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclParse.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPipe.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPkg.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPlatDecls.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPort.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPosixStr.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclPreserve.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclProc.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclRegexp.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclRegexp.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclResolve.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclResult.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclScan.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclStringObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclStubInit.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclStubLib.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclOOStubLib.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclTomMathStubLib.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclTest.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclTestObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclTestProcBodyObj.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclThread.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclThreadJoin.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclThreadTest.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclTimer.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclUniData.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclUtf.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclUtil.c
+# End Source File
+# Begin Source File
+
+SOURCE=..\generic\tclVar.c
+# End Source File
+# End Group
+# Begin Group "library"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\library\auto.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\history.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\init.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\ldAout.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\package.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\parray.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\safe.tcl
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\tclIndex
+# End Source File
+# Begin Source File
+
+SOURCE=..\library\word.tcl
+# End Source File
+# End Group
+# Begin Group "mac"
+
+# PROP Default_Filter ""
+# End Group
+# Begin Group "tests"
+
+# PROP Default_Filter ""
+# End Group
+# Begin Group "tools"
+
+# PROP Default_Filter ""
+# End Group
+# Begin Group "unix"
+
+# PROP Default_Filter ""
+# End Group
+# Begin Group "win"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=.\aclocal.m4
+# End Source File
+# Begin Source File
+
+SOURCE=.\cat.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\configure
+# End Source File
+# Begin Source File
+
+SOURCE=.\configure.in
+# End Source File
+# Begin Source File
+
+SOURCE=.\makefile.bc
+# End Source File
+# Begin Source File
+
+SOURCE=.\Makefile.in
+# End Source File
+# Begin Source File
+
+SOURCE=.\makefile.vc
+# End Source File
+# Begin Source File
+
+SOURCE=.\mkd.bat
+# End Source File
+# Begin Source File
+
+SOURCE=.\README
+# End Source File
+# Begin Source File
+
+SOURCE=.\README.binary
+# End Source File
+# Begin Source File
+
+SOURCE=.\rmd.bat
+# End Source File
+# Begin Source File
+
+SOURCE=.\rules.vc
+# End Source File
+# Begin Source File
+
+SOURCE=.\tcl.hpj.in
+# End Source File
+# Begin Source File
+
+SOURCE=.\tcl.m4
+# End Source File
+# Begin Source File
+
+SOURCE=.\tcl.rc
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclAppInit.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclConfig.sh.in
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclsh.ico
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclsh.rc
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWin32Dll.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinChan.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinConsole.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinDde.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinError.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinFCmd.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinFile.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinInit.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinInt.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinLoad.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinNotify.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinPipe.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinPort.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinReg.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinSerial.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinSock.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinTest.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinThrd.c
+# End Source File
+# Begin Source File
+
+SOURCE=.\tclWinTime.c
+# End Source File
+# End Group
+# End Target
+# End Project
diff --git a/win/tcl.dsw b/win/tcl.dsw index fa93b00..1c16fad 100644 --- a/win/tcl.dsw +++ b/win/tcl.dsw @@ -1,29 +1,29 @@ -Microsoft Developer Studio Workspace File, Format Version 6.00 -# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE! - -############################################################################### - -Project: "tcl"=.\tcl.dsp - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ -}}} - -############################################################################### - -Global: - -Package=<5> -{{{ -}}} - -Package=<3> -{{{ -}}} - -############################################################################### - +Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "tcl"=.\tcl.dsp - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/win/tcl.hpj.in b/win/tcl.hpj.in index 3bdccbe..a94cea6 100644 --- a/win/tcl.hpj.in +++ b/win/tcl.hpj.in @@ -1,19 +1,19 @@ -; This file is maintained by HCW. Do not modify this file directly. - -[OPTIONS] -HCW=0 -LCID=0x409 0x0 0x0 ;English (United States) -REPORT=Yes -TITLE=Tcl/Tk Reference Manual -CNT=tcl86.cnt -COPYRIGHT=Copyright © 2000 Ajuba Solutions -HLP=tcl86.hlp - -[FILES] -tcl.rtf - -[WINDOWS] -main="Tcl/Tk Reference Manual",,0 - -[CONFIG] -BrowseButtons() +; This file is maintained by HCW. Do not modify this file directly.
+
+[OPTIONS]
+HCW=0
+LCID=0x409 0x0 0x0 ;English (United States)
+REPORT=Yes
+TITLE=Tcl/Tk Reference Manual
+CNT=tcl86.cnt
+COPYRIGHT=Copyright © 2000 Ajuba Solutions
+HLP=tcl86.hlp
+
+[FILES]
+tcl.rtf
+
+[WINDOWS]
+main="Tcl/Tk Reference Manual",,0
+
+[CONFIG]
+BrowseButtons()
@@ -559,7 +559,7 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ EXTRA_CFLAGS="" AC_DEFINE(MODULE_SCOPE, [extern], [No need to mark inidividual symbols as hidden]) - AC_CHECK_PROG(CYGPATH, cygpath, cygpath -w, echo) + AC_CHECK_PROG(CYGPATH, cygpath, cygpath -m, echo) SHLIB_SUFFIX=".dll" @@ -673,7 +673,7 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ if test "${GCC}" = "yes" ; then SHLIB_LD="" SHLIB_LD_LIBS='${LIBS}' - LIBS="-lnetapi32 -lkernel32 -luser32 -ladvapi32 -lws2_32" + LIBS="-lnetapi32 -lkernel32 -luser32 -ladvapi32 -luserenv -lws2_32" # mingw needs to link ole32 and oleaut32 for [send], but MSVC doesn't LIBS_GUI="-lgdi32 -lcomdlg32 -limm32 -lcomctl32 -lshell32 -luuid -lole32 -loleaut32" STLIB_LD='${AR} cr' @@ -791,6 +791,13 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ # Add SHLIB_LD_LIBS to the Make rule, not here. LIBRARIES="\${SHARED_LIBRARIES}" EXESUFFIX="\${DBGX}.exe" + case "x`echo \${VisualStudioVersion}`" in + x1[[4-9]]*) + lflags="${lflags} -nodefaultlib:libucrt.lib" + ;; + *) + ;; + esac fi MAKE_DLL="\${SHLIB_LD} \$(LDFLAGS) -out:\[$]@" # DLLSUFFIX is separate because it is the building block for @@ -827,7 +834,16 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ fi fi - LIBS="netapi32.lib kernel32.lib user32.lib advapi32.lib ws2_32.lib" + LIBS="netapi32.lib kernel32.lib user32.lib advapi32.lib userenv.lib ws2_32.lib" + + case "x`echo \${VisualStudioVersion}`" in + x1[[4-9]]*) + LIBS="$LIBS ucrt.lib" + ;; + *) + ;; + esac + if test "$do64bit" != "no" ; then # The space-based-path will work for the Makefile, but will # not work if AC_TRY_COMPILE is called. TEA has the @@ -842,7 +858,7 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ CFLAGS_DEBUG="-nologo -Zi -Od ${runtime}d" # Do not use -O2 for Win64 - this has proved buggy in code gen. CFLAGS_OPTIMIZE="-nologo -O1 ${runtime}" - lflags="-nologo -MACHINE:${MACHINE} -LIBPATH:\"${MSSDK}/Lib/${MACHINE}\"" + lflags="${lflags} -nologo -MACHINE:${MACHINE} -LIBPATH:\"${MSSDK}/Lib/${MACHINE}\"" LINKBIN="\"${PATH64}/link.exe\"" # Avoid 'unresolved external symbol __security_cookie' errors. # c.f. http://support.microsoft.com/?id=894573 @@ -854,7 +870,7 @@ AC_DEFUN([SC_CONFIG_CFLAGS], [ CFLAGS_DEBUG="-nologo -Z7 -Od -WX ${runtime}d" # -O2 - create fast code (/Og /Oi /Ot /Oy /Ob2 /Gs /GF /Gy) CFLAGS_OPTIMIZE="-nologo -O2 ${runtime}" - lflags="-nologo" + lflags="${lflags} -nologo" LINKBIN="link" fi @@ -48,7 +48,7 @@ BEGIN VALUE "LegalCopyright", "Copyright \251 2001 by ActiveState Corporation, et al\0" VALUE "ProductName", "Tcl " TCL_VERSION " for Windows\0" VALUE "ProductVersion", TCL_PATCH_LEVEL - END + END END BLOCK "VarFileInfo" BEGIN diff --git a/win/tclAppInit.c b/win/tclAppInit.c index 7fd4c32..4169f3b 100644 --- a/win/tclAppInit.c +++ b/win/tclAppInit.c @@ -16,7 +16,9 @@ #include "tcl.h" #define WIN32_LEAN_AND_MEAN +#define STRICT /* See MSDN Article Q83456 */ #include <windows.h> +#undef STRICT #undef WIN32_LEAN_AND_MEAN #include <locale.h> #include <stdlib.h> diff --git a/win/tclWinConsole.c b/win/tclWinConsole.c index 63150ef..ab55035 100644 --- a/win/tclWinConsole.c +++ b/win/tclWinConsole.c @@ -220,8 +220,20 @@ ReadConsoleBytes( BOOL result; int tcharsize = sizeof(TCHAR); - result = ReadConsole(hConsole, lpBuffer, nbytes / tcharsize, &ntchars, - NULL); + /* + * If user types a Ctrl-Break or Ctrl-C, ReadConsole will return + * success with ntchars == 0 and GetLastError() will be + * ERROR_OPERATION_ABORTED. We do not want to treat this case + * as EOF so we will loop around again. If no Ctrl signal handlers + * have been established, the default signal OS handler in a separate + * thread will terminate the program. If a Ctrl signal handler + * has been established (through an extension for example), it + * will run and take whatever action it deems appropriate. + */ + do { + result = ReadConsole(hConsole, lpBuffer, nbytes / tcharsize, &ntchars, + NULL); + } while (result && ntchars == 0 && GetLastError() == ERROR_OPERATION_ABORTED); if (nbytesread != NULL) { *nbytesread = ntchars * tcharsize; } diff --git a/win/tclWinError.c b/win/tclWinError.c index 4d3250d..30079b9 100644 --- a/win/tclWinError.c +++ b/win/tclWinError.c @@ -381,7 +381,7 @@ TclWinConvertError( *---------------------------------------------------------------------- */ -void +TCL_NORETURN void tclWinDebugPanic( const char *format, ...) { diff --git a/win/tclWinFile.c b/win/tclWinFile.c index d6ca348..25c6ea4 100644 --- a/win/tclWinFile.c +++ b/win/tclWinFile.c @@ -17,7 +17,11 @@ #include <winioctl.h> #include <shlobj.h> #include <lm.h> /* For TclpGetUserHome(). */ +#include <userenv.h> /* For TclpGetUserHome(). */ +#ifdef _MSC_VER +# pragma comment(lib, "userenv.lib") +#endif /* * The number of 100-ns intervals between the Windows system epoch (1601-01-01 * on the proleptic Gregorian calendar) and the Posix epoch (1970-01-01). @@ -172,7 +176,7 @@ static int WinLink(const TCHAR *LinkSource, const TCHAR *LinkTarget, int linkAction); static int WinSymLinkDirectory(const TCHAR *LinkDirectory, const TCHAR *LinkTarget); -MODULE_SCOPE void tclWinDebugPanic(const char *format, ...); +MODULE_SCOPE TCL_NORETURN void tclWinDebugPanic(const char *format, ...); /* *-------------------------------------------------------------------- @@ -668,7 +672,7 @@ NativeReadReparse( HANDLE hFile; DWORD returnedLength; - hFile = CreateFile(linkDirPath, desiredAccess, 0, NULL, OPEN_EXISTING, + hFile = CreateFile(linkDirPath, desiredAccess, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_OPEN_REPARSE_POINT | FILE_FLAG_BACKUP_SEMANTICS, NULL); if (hFile == INVALID_HANDLE_VALUE) { @@ -789,7 +793,7 @@ NativeWriteReparse( *---------------------------------------------------------------------- */ -void +TCL_NORETURN void tclWinDebugPanic( const char *format, ...) { @@ -1461,12 +1465,16 @@ TclpGetUserHome( } else { /* * User exists but has no home dir. Return - * "{Windows Drive}:/users/default". + * "{GetProfilesDirectory}/<user>". */ - - GetWindowsDirectoryW(buf, MAX_PATH); - Tcl_UniCharToUtfDString(buf, 2, bufferPtr); - TclDStringAppendLiteral(bufferPtr, "/users/default"); + DWORD i, size = MAX_PATH; + GetProfilesDirectoryW(buf, &size); + for (i = 0; i < size; ++i){ + if (buf[i] == '\\') buf[i] = '/'; + } + Tcl_UniCharToUtfDString(buf, size-1, bufferPtr); + Tcl_DStringAppend(bufferPtr, "/", -1); + Tcl_DStringAppend(bufferPtr, name, -1); } result = Tcl_DStringValue(bufferPtr); NetApiBufferFree((void *) uiPtr); @@ -2897,7 +2905,7 @@ ClientData TclNativeCreateNativeRep( Tcl_Obj *pathPtr) { - WCHAR *nativePathPtr; + WCHAR *nativePathPtr = NULL; const char *str; Tcl_Obj *validPathPtr; size_t len; @@ -2914,6 +2922,7 @@ TclNativeCreateNativeRep( if (validPathPtr == NULL) { return NULL; } + /* refCount of validPathPtr was already incremented in Tcl_FSGetTranslatedPath */ } else { /* * Make sure the normalized path is set. @@ -2923,6 +2932,7 @@ TclNativeCreateNativeRep( if (validPathPtr == NULL) { return NULL; } + /* validPathPtr returned from Tcl_FSGetNormalizedPath is owned by Tcl, so incr refCount here */ Tcl_IncrRefCount(validPathPtr); } @@ -2931,7 +2941,7 @@ TclNativeCreateNativeRep( if (strlen(str)!=(unsigned int)len) { /* String contains NUL-bytes. This is invalid. */ - return 0; + goto done; } /* For a reserved device, strip a possible postfix ':' */ len = WinIsReserved(str); @@ -2940,13 +2950,13 @@ TclNativeCreateNativeRep( * 0xC0 0x80 (== overlong NUL). See bug [3118489]: NUL in filenames */ len = MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, str, -1, 0, 0); if (len==0) { - return 0; + goto done; } } /* Overallocate 6 chars, making some room for extended paths */ wp = nativePathPtr = ckalloc( (len+6) * sizeof(WCHAR) ); if (nativePathPtr==0) { - return 0; + goto done; } MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, str, -1, nativePathPtr, len+1); /* @@ -2997,6 +3007,10 @@ TclNativeCreateNativeRep( } ++wp; } + + done: + + TclDecrRefCount(validPathPtr); return nativePathPtr; } diff --git a/win/tclWinLoad.c b/win/tclWinLoad.c index 3e11224..26512b1 100644 --- a/win/tclWinLoad.c +++ b/win/tclWinLoad.c @@ -102,37 +102,39 @@ TclpDlopen( * better if there was a way to get what DLLs */ - switch (lastError) { - case ERROR_MOD_NOT_FOUND: - Tcl_SetErrorCode(interp, "WIN_LOAD", "MOD_NOT_FOUND", NULL); - goto notFoundMsg; - case ERROR_DLL_NOT_FOUND: - Tcl_SetErrorCode(interp, "WIN_LOAD", "DLL_NOT_FOUND", NULL); - notFoundMsg: - Tcl_AppendToObj(errMsg, "this library or a dependent library" - " could not be found in library path", -1); - break; - case ERROR_PROC_NOT_FOUND: - Tcl_SetErrorCode(interp, "WIN_LOAD", "PROC_NOT_FOUND", NULL); - Tcl_AppendToObj(errMsg, "A function specified in the import" - " table could not be resolved by the system. Windows" - " is not telling which one, I'm sorry.", -1); - break; - case ERROR_INVALID_DLL: - Tcl_SetErrorCode(interp, "WIN_LOAD", "INVALID_DLL", NULL); - Tcl_AppendToObj(errMsg, "this library or a dependent library" - " is damaged", -1); - break; - case ERROR_DLL_INIT_FAILED: - Tcl_SetErrorCode(interp, "WIN_LOAD", "DLL_INIT_FAILED", NULL); - Tcl_AppendToObj(errMsg, "the library initialization" - " routine failed", -1); - break; - default: - TclWinConvertError(lastError); - Tcl_AppendToObj(errMsg, Tcl_PosixError(interp), -1); + if (interp) { + switch (lastError) { + case ERROR_MOD_NOT_FOUND: + Tcl_SetErrorCode(interp, "WIN_LOAD", "MOD_NOT_FOUND", NULL); + goto notFoundMsg; + case ERROR_DLL_NOT_FOUND: + Tcl_SetErrorCode(interp, "WIN_LOAD", "DLL_NOT_FOUND", NULL); + notFoundMsg: + Tcl_AppendToObj(errMsg, "this library or a dependent library" + " could not be found in library path", -1); + break; + case ERROR_PROC_NOT_FOUND: + Tcl_SetErrorCode(interp, "WIN_LOAD", "PROC_NOT_FOUND", NULL); + Tcl_AppendToObj(errMsg, "A function specified in the import" + " table could not be resolved by the system. Windows" + " is not telling which one, I'm sorry.", -1); + break; + case ERROR_INVALID_DLL: + Tcl_SetErrorCode(interp, "WIN_LOAD", "INVALID_DLL", NULL); + Tcl_AppendToObj(errMsg, "this library or a dependent library" + " is damaged", -1); + break; + case ERROR_DLL_INIT_FAILED: + Tcl_SetErrorCode(interp, "WIN_LOAD", "DLL_INIT_FAILED", NULL); + Tcl_AppendToObj(errMsg, "the library initialization" + " routine failed", -1); + break; + default: + TclWinConvertError(lastError); + Tcl_AppendToObj(errMsg, Tcl_PosixError(interp), -1); + } + Tcl_SetObjResult(interp, errMsg); } - Tcl_SetObjResult(interp, errMsg); return TCL_ERROR; } diff --git a/win/tclWinPipe.c b/win/tclWinPipe.c index a9eec6d..aff8836 100644 --- a/win/tclWinPipe.c +++ b/win/tclWinPipe.c @@ -50,7 +50,7 @@ TCL_DECLARE_MUTEX(pipeMutex) * used in a pipeline. */ -typedef struct WinFile { +typedef struct { int type; /* One of the file types defined above. */ HANDLE handle; /* Open file handle. */ } WinFile; @@ -148,7 +148,7 @@ typedef struct PipeInfo { * synchronized with the readable object. */ } PipeInfo; -typedef struct ThreadSpecificData { +typedef struct { /* * The following pointer refers to the head of the list of pipes that are * being watched for file events. @@ -164,7 +164,7 @@ static Tcl_ThreadDataKey dataKey; * events are generated. */ -typedef struct PipeEvent { +typedef struct { Tcl_Event header; /* Information that is standard for all * events. */ PipeInfo *infoPtr; /* Pointer to pipe info structure. Note that @@ -2653,7 +2653,7 @@ Tcl_PidObjCmd( if (objc == 1) { Tcl_SetObjResult(interp, Tcl_NewWideIntObj((unsigned) getpid())); } else { - chan = Tcl_GetChannel(interp, Tcl_GetStringFromObj(objv[1], NULL), + chan = Tcl_GetChannel(interp, Tcl_GetString(objv[1]), NULL); if (chan == (Tcl_Channel) NULL) { return TCL_ERROR; @@ -3106,9 +3106,9 @@ TclpOpenTemporaryFile( } namePtr += length * sizeof(TCHAR); if (basenameObj) { - const char *string = Tcl_GetStringFromObj(basenameObj, &length); + const char *string = Tcl_GetString(basenameObj); - Tcl_WinUtfToTChar(string, length, &buf); + Tcl_WinUtfToTChar(string, basenameObj->length, &buf); memcpy(namePtr, Tcl_DStringValue(&buf), Tcl_DStringLength(&buf)); namePtr += Tcl_DStringLength(&buf); Tcl_DStringFree(&buf); diff --git a/win/tclWinReg.c b/win/tclWinReg.c index 327e4a3..56aa991 100644 --- a/win/tclWinReg.c +++ b/win/tclWinReg.c @@ -49,15 +49,6 @@ #endif /* - * TCL_STORAGE_CLASS is set unconditionally to DLLEXPORT because the - * Registry_Init declaration is in the source file itself, which is only - * accessed when we are building a library. - */ - -#undef TCL_STORAGE_CLASS -#define TCL_STORAGE_CLASS DLLEXPORT - -/* * The following macros convert between different endian ints. */ @@ -140,8 +131,8 @@ static int SetValue(Tcl_Interp *interp, Tcl_Obj *keyNameObj, Tcl_Obj *valueNameObj, Tcl_Obj *dataObj, Tcl_Obj *typeObj, REGSAM mode); -EXTERN int Registry_Init(Tcl_Interp *interp); -EXTERN int Registry_Unload(Tcl_Interp *interp, int flags); +DLLEXPORT int Registry_Init(Tcl_Interp *interp); +DLLEXPORT int Registry_Unload(Tcl_Interp *interp, int flags); /* *---------------------------------------------------------------------- @@ -172,7 +163,7 @@ Registry_Init( cmd = Tcl_CreateObjCommand(interp, "registry", RegistryObjCmd, interp, DeleteCmd); Tcl_SetAssocData(interp, REGISTRY_ASSOC_KEY, NULL, cmd); - return Tcl_PkgProvide(interp, "registry", "1.3.0"); + return Tcl_PkgProvide(interp, "registry", "1.3.1"); } /* @@ -415,7 +406,6 @@ DeleteKey( const TCHAR *nativeTail; HKEY rootKey, subkey; DWORD result; - int length; Tcl_DString buf; REGSAM saveMode = mode; @@ -423,8 +413,8 @@ DeleteKey( * Find the parent of the key being deleted and open it. */ - keyName = Tcl_GetStringFromObj(keyNameObj, &length); - buffer = ckalloc(length + 1); + keyName = Tcl_GetString(keyNameObj); + buffer = ckalloc(keyNameObj->length + 1); strcpy(buffer, keyName); if (ParseKeyName(interp, buffer, &hostName, &rootKey, @@ -509,7 +499,7 @@ DeleteValue( { HKEY key; char *valueName; - int length; + size_t length; DWORD result; Tcl_DString ds; @@ -522,7 +512,8 @@ DeleteValue( return TCL_ERROR; } - valueName = Tcl_GetStringFromObj(valueNameObj, &length); + valueName = Tcl_GetString(valueNameObj); + length = valueNameObj->length; Tcl_WinUtfToTChar(valueName, length, &ds); result = RegDeleteValue(key, (const TCHAR *)Tcl_DStringValue(&ds)); Tcl_DStringFree(&ds); @@ -664,7 +655,7 @@ GetType( Tcl_DString ds; const char *valueName; const TCHAR *nativeValue; - int length; + size_t length; /* * Attempt to open the key for reading. @@ -679,7 +670,8 @@ GetType( * Get the type of the value. */ - valueName = Tcl_GetStringFromObj(valueNameObj, &length); + valueName = Tcl_GetString(valueNameObj); + length = valueNameObj->length; nativeValue = Tcl_WinUtfToTChar(valueName, length, &ds); result = RegQueryValueEx(key, nativeValue, NULL, &type, NULL, NULL); @@ -736,7 +728,7 @@ GetValue( const TCHAR *nativeValue; DWORD result, length, type; Tcl_DString data, buf; - int nameLen; + size_t nameLen; /* * Attempt to open the key for reading. @@ -761,7 +753,8 @@ GetValue( Tcl_DStringSetLength(&data, TCL_DSTRING_STATIC_SIZE - 1); length = TCL_DSTRING_STATIC_SIZE/sizeof(TCHAR) - 1; - valueName = Tcl_GetStringFromObj(valueNameObj, &nameLen); + valueName = Tcl_GetString(valueNameObj); + nameLen = valueNameObj->length; nativeValue = Tcl_WinUtfToTChar(valueName, nameLen, &buf); result = RegQueryValueEx(key, nativeValue, NULL, &type, @@ -951,11 +944,12 @@ OpenKey( HKEY *keyPtr) /* Returned HKEY. */ { char *keyName, *buffer, *hostName; - int length; + size_t length; HKEY rootKey; DWORD result; - keyName = Tcl_GetStringFromObj(keyNameObj, &length); + keyName = Tcl_GetString(keyNameObj); + length = keyNameObj->length; buffer = ckalloc(length + 1); strcpy(buffer, keyName); @@ -1255,7 +1249,8 @@ SetValue( Tcl_Obj *typeObj, /* Type of data to be written. */ REGSAM mode) /* Mode flags to pass. */ { - int type, length; + int type; + size_t length; DWORD result; HKEY key; const char *valueName; @@ -1275,7 +1270,8 @@ SetValue( return TCL_ERROR; } - valueName = Tcl_GetStringFromObj(valueNameObj, &length); + valueName = Tcl_GetString(valueNameObj); + length = valueNameObj->length; valueName = (char *) Tcl_WinUtfToTChar(valueName, length, &nameBuf); if (type == REG_DWORD || type == REG_DWORD_BIG_ENDIAN) { @@ -1309,8 +1305,9 @@ SetValue( Tcl_DStringInit(&data); for (i = 0; i < objc; i++) { - const char *bytes = Tcl_GetStringFromObj(objv[i], &length); + const char *bytes = Tcl_GetString(objv[i]); + length = objv[i]->length; Tcl_DStringAppend(&data, bytes, length); /* @@ -1329,8 +1326,9 @@ SetValue( Tcl_DStringFree(&buf); } else if (type == REG_SZ || type == REG_EXPAND_SZ) { Tcl_DString buf; - const char *data = Tcl_GetStringFromObj(dataObj, &length); + const char *data = Tcl_GetString(dataObj); + length = dataObj->length; data = (char *) Tcl_WinUtfToTChar(data, length, &buf); /* @@ -1345,14 +1343,15 @@ SetValue( Tcl_DStringFree(&buf); } else { BYTE *data; + int bytelength; /* * Store binary data in the registry. */ - data = (BYTE *) Tcl_GetByteArrayFromObj(dataObj, &length); + data = (BYTE *) Tcl_GetByteArrayFromObj(dataObj, &bytelength); result = RegSetValueEx(key, (TCHAR *) valueName, 0, - (DWORD) type, data, (DWORD) length); + (DWORD) type, data, (DWORD) bytelength); } Tcl_DStringFree(&nameBuf); @@ -1392,24 +1391,25 @@ BroadcastValue( { LRESULT result; DWORD_PTR sendResult; - UINT timeout = 3000; - int len; + int timeout = 3000; + size_t len; + int unilen; const char *str; Tcl_Obj *objPtr; if (objc == 3) { - str = Tcl_GetStringFromObj(objv[1], &len); - if ((len < 2) || (*str != '-') - || strncmp(str, "-timeout", (size_t) len)) { + str = Tcl_GetString(objv[1]); + len = objv[1]->length; + if ((len < 2) || (*str != '-') || strncmp(str, "-timeout", len)) { return TCL_BREAK; } - if (Tcl_GetIntFromObj(interp, objv[2], (int *) &timeout) != TCL_OK) { + if (Tcl_GetIntFromObj(interp, objv[2], &timeout) != TCL_OK) { return TCL_ERROR; } } - str = Tcl_GetStringFromObj(objv[0], &len); - if (len == 0) { + str = (char*)Tcl_GetUnicodeFromObj(objv[0], &unilen); + if (unilen == 0) { str = NULL; } @@ -1417,8 +1417,8 @@ BroadcastValue( * Use the ignore the result. */ - result = SendMessageTimeoutA(HWND_BROADCAST, WM_SETTINGCHANGE, - (WPARAM) 0, (LPARAM) str, SMTO_ABORTIFHUNG, timeout, &sendResult); + result = SendMessageTimeout(HWND_BROADCAST, WM_SETTINGCHANGE, + (WPARAM) 0, (LPARAM) str, SMTO_ABORTIFHUNG, (UINT) timeout, &sendResult); objPtr = Tcl_NewObj(); Tcl_ListObjAppendElement(NULL, objPtr, Tcl_NewLongObj((long) result)); |