diff options
author | dgp <dgp@users.sourceforge.net> | 2011-04-28 14:44:47 (GMT) |
---|---|---|
committer | dgp <dgp@users.sourceforge.net> | 2011-04-28 14:44:47 (GMT) |
commit | 7fa90bb19565f59f0c918cac88e2a34bf51cd0fa (patch) | |
tree | c826199d351b0c6f0746a66124227d102686a420 | |
parent | 319c5292645aa41b4f56539f615ba5314b27c957 (diff) | |
parent | 5702e695062ec36c3addd403d748af48164db8b1 (diff) | |
download | tcl-7fa90bb19565f59f0c918cac88e2a34bf51cd0fa.zip tcl-7fa90bb19565f59f0c918cac88e2a34bf51cd0fa.tar.gz tcl-7fa90bb19565f59f0c918cac88e2a34bf51cd0fa.tar.bz2 |
New utility routines: TclIsSpaceProc() and TclCountSpaceRuns()
Use to replace calls to isspace() and their /* INTL */ risk.
-rw-r--r-- | ChangeLog | 27 | ||||
-rw-r--r-- | generic/tclCmdMZ.c | 2 | ||||
-rw-r--r-- | generic/tclInt.h | 3 | ||||
-rw-r--r-- | generic/tclListObj.c | 8 | ||||
-rw-r--r-- | generic/tclParse.c | 26 | ||||
-rwxr-xr-x | generic/tclStrToD.c | 6 | ||||
-rw-r--r-- | generic/tclUtil.c | 95 |
7 files changed, 121 insertions, 46 deletions
@@ -1,7 +1,34 @@ 2011-04-28 Don Porter <dgp@users.sourceforge.net> + * generic/tclInt.h: New utility routines: + * generic/tclParse.c: TclIsSpaceProc() and + * generic/tclUtil.c: TclCountSpaceRuns() + + * generic/tclCmdMZ.c: Use new routines to replace calls to + * generic/tclListObj.c: isspace() and their /* INTL */ risk. + * generic/tclStrToD.c: + * generic/tclStringObj.c: Improved reaction to out of memory. +2011-03-16 Jan Nijtmans <nijtmans@users.sf.net> + + * unix/tcl.m4: Make SHLIB_LD_LIBS='${LIBS}' the default and + * unix/configure: set to "" on per-platform necessary basis. + Backported from TEA, but kept all original platform code which was + removed from TEA. + +2011-03-14 Kevin B. Kenny <kennykb@acm.org> + + * tools/tclZIC.tcl (onDayOfMonth): Allow for leading zeroes + in month and day so that tzdata2011d parses correctly. + * library/tzdata/America/Havana: + * library/tzdata/America/Juneau: + * library/tzdata/America/Santiago: + * library/tzdata/Europe/Istanbul: + * library/tzdata/Pacific/Apia: + * library/tzdata/Pacific/Easter: + * library/tzdata/Pacific/Honolulu: tzdata2011d + 2011-04-27 Don Porter <dgp@users.sourceforge.net> * generic/tclCmdMZ.c: TclFreeIntRep() correction & cleanup. diff --git a/generic/tclCmdMZ.c b/generic/tclCmdMZ.c index e4a58ed..c34ce6c 100644 --- a/generic/tclCmdMZ.c +++ b/generic/tclCmdMZ.c @@ -1665,7 +1665,7 @@ StringIsCmd( * if it is the first "element" that has the failure. */ - while (isspace(UCHAR(*p))) { /* INTL: ? */ + while (TclIsSpaceProc(*p)) { p++; } TclNewStringObj(tmpStr, string1, p-string1); diff --git a/generic/tclInt.h b/generic/tclInt.h index 95a497b..7d9f066 100644 --- a/generic/tclInt.h +++ b/generic/tclInt.h @@ -2900,6 +2900,8 @@ MODULE_SCOPE void TclContinuationsEnterDerived(Tcl_Obj *objPtr, MODULE_SCOPE ContLineLoc *TclContinuationsGet(Tcl_Obj *objPtr); MODULE_SCOPE void TclContinuationsCopy(Tcl_Obj *objPtr, Tcl_Obj *originObjPtr); +MODULE_SCOPE int TclCountSpaceRuns(CONST char *bytes, int numBytes, + CONST char **endPtr); MODULE_SCOPE void TclDeleteNamespaceVars(Namespace *nsPtr); /* TIP #280 - Modified token based evulation, with line information. */ MODULE_SCOPE int TclEvalEx(Tcl_Interp *interp, const char *script, @@ -2991,6 +2993,7 @@ MODULE_SCOPE void TclInitObjSubsystem(void); MODULE_SCOPE void TclInitSubsystems(void); MODULE_SCOPE int TclInterpReady(Tcl_Interp *interp); MODULE_SCOPE int TclIsLocalScalar(const char *src, int len); +MODULE_SCOPE int TclIsSpaceProc(char byte); MODULE_SCOPE int TclJoinThread(Tcl_ThreadId id, int *result); MODULE_SCOPE void TclLimitRemoveAllHandlers(Tcl_Interp *interp); MODULE_SCOPE Tcl_Obj * TclLindexList(Tcl_Interp *interp, diff --git a/generic/tclListObj.c b/generic/tclListObj.c index 88b3a0b..9437f7e 100644 --- a/generic/tclListObj.c +++ b/generic/tclListObj.c @@ -1789,13 +1789,7 @@ SetListFromAny( * elements by counting the number of space characters in the list. */ - limit = string + length; - estCount = 1; - for (p = string; p < limit; p++) { - if (isspace(UCHAR(*p))) { /* INTL: ISO space. */ - estCount++; - } - } + estCount = TclCountSpaceRuns(string, length, &limit) + 1; /* * Allocate a new List structure with enough room for "estCount" elements. diff --git a/generic/tclParse.c b/generic/tclParse.c index 9bfe608..429d33a 100644 --- a/generic/tclParse.c +++ b/generic/tclParse.c @@ -611,6 +611,30 @@ Tcl_ParseCommand( /* *---------------------------------------------------------------------- * + * TclIsSpaceProc -- + * + * Report whether byte is in the set of whitespace characters used by + * Tcl to separate words in scripts or elements in lists. + * + * Results: + * Returns 1, if byte is in the set, 0 otherwise. + * + * Side effects: + * None. + * + *---------------------------------------------------------------------- + */ + +int +TclIsSpaceProc( + char byte) +{ + return CHAR_TYPE(byte) & (TYPE_SPACE) || byte == '\n'; +} + +/* + *---------------------------------------------------------------------- + * * ParseWhiteSpace -- * * Scans up to numBytes bytes starting at src, consuming white space @@ -1757,7 +1781,7 @@ Tcl_ParseBraces( openBrace = 0; break; case '#' : - if (openBrace && isspace(UCHAR(src[-1]))) { + if (openBrace && TclIsSpaceProc(src[-1])) { Tcl_AppendResult(parsePtr->interp, ": possible unbalanced brace in comment", NULL); goto error; diff --git a/generic/tclStrToD.c b/generic/tclStrToD.c index 205b865..59192e9 100755 --- a/generic/tclStrToD.c +++ b/generic/tclStrToD.c @@ -571,7 +571,7 @@ TclParseNumber( * I, N, and whitespace. */ - if (isspace(UCHAR(c))) { + if (TclIsSpaceProc(c)) { if (flags & TCL_PARSE_NO_WHITESPACE) { goto endgame; } @@ -1091,7 +1091,7 @@ TclParseNumber( } /* FALLTHROUGH */ case sNANPAREN: - if (isspace(UCHAR(c))) { + if (TclIsSpaceProc(c)) { break; } if (numSigDigs < 13) { @@ -1142,7 +1142,7 @@ TclParseNumber( * Accept trailing whitespace. */ - while (len != 0 && isspace(UCHAR(*p))) { + while (len != 0 && TclIsSpaceProc(*p)) { p++; len--; } diff --git a/generic/tclUtil.c b/generic/tclUtil.c index f77320b..e8eee7a 100644 --- a/generic/tclUtil.c +++ b/generic/tclUtil.c @@ -88,6 +88,58 @@ const Tcl_ObjType tclEndOffsetType = { /* *---------------------------------------------------------------------- * + * TclCountSpaceRuns -- + * + * Given 'bytes' pointing to 'numBytes' bytes, scan through them and + * count the number of whitespace runs that could be list element + * separators. If 'numBytes' is -1, scan to the terminating '\0'. + * + * Results: + * Returns the count. If 'endPtr' is not NULL, writes a pointer to + * the end of the string scanned there. + * + * Side effects: + * None. + * + *---------------------------------------------------------------------- + */ + +int +TclCountSpaceRuns( + CONST char *bytes, + int numBytes, + CONST char **endPtr) +{ + int count = 0; + + while (numBytes) { + if ((numBytes == -1) && (*bytes == '\0')) { + break; + } + if (TclIsSpaceProc(*bytes)) { + /* Space run started; bump count */ + count++; + do { + bytes++; + numBytes -= (numBytes != -1); + } while (numBytes && TclIsSpaceProc(*bytes)); + if (numBytes == 0) { + break; + } + /* (*bytes) is non-space; return to counting state */ + } + bytes++; + numBytes -= (numBytes != -1); + } + if (endPtr) { + *endPtr = bytes; + } + return count; +} + +/* + *---------------------------------------------------------------------- + * * TclFindElement -- * * Given a pointer into a Tcl list, locate the first (or next) element in @@ -154,7 +206,7 @@ TclFindElement( */ limit = (list + listLength); - while ((p < limit) && (isspace(UCHAR(*p)))) { /* INTL: ISO space. */ + while ((p < limit) && (TclIsSpaceProc(*p))) { p++; } if (p == limit) { /* no element found */ @@ -202,8 +254,7 @@ TclFindElement( } else if (openBraces == 1) { size = (p - elemStart); p++; - if ((p >= limit) - || isspace(UCHAR(*p))) { /* INTL: ISO space. */ + if ((p >= limit) || TclIsSpaceProc(*p)) { goto done; } @@ -213,8 +264,7 @@ TclFindElement( if (interp != NULL) { p2 = p; - while ((p2 < limit) - && (!isspace(UCHAR(*p2))) /* INTL: ISO space. */ + while ((p2 < limit) && (!TclIsSpaceProc(*p2)) && (p2 < p+20)) { p2++; } @@ -263,8 +313,7 @@ TclFindElement( if (inQuotes) { size = (p - elemStart); p++; - if ((p >= limit) - || isspace(UCHAR(*p))) { /* INTL: ISO space */ + if ((p >= limit) || TclIsSpaceProc(*p)) { goto done; } @@ -274,8 +323,7 @@ TclFindElement( if (interp != NULL) { p2 = p; - while ((p2 < limit) - && (!isspace(UCHAR(*p2))) /* INTL: ISO space */ + while ((p2 < limit) && (!TclIsSpaceProc(*p2)) && (p2 < p+20)) { p2++; } @@ -318,7 +366,7 @@ TclFindElement( } done: - while ((p < limit) && (isspace(UCHAR(*p)))) { /* INTL: ISO space. */ + while ((p < limit) && (TclIsSpaceProc(*p))) { p++; } *elementPtr = elemStart; @@ -416,7 +464,7 @@ Tcl_SplitList( const char ***argvPtr) /* Pointer to place to store pointer to array * of pointers to list elements. */ { - const char **argv, *l, *element; + const char **argv, *end, *element; char *p; int length, size, i, result, elSize, brace; @@ -427,29 +475,8 @@ Tcl_SplitList( * the list. */ - for (size = 2, l = list; *l != 0; l++) { - if (isspace(UCHAR(*l))) { /* INTL: ISO space. */ - size++; - - /* - * Consecutive space can only count as a single list delimiter. - */ - - while (1) { - char next = *(l + 1); - - if (next == '\0') { - break; - } - l++; - if (isspace(UCHAR(next))) { /* INTL: ISO space. */ - continue; - } - break; - } - } - } - length = l - list; + size = TclCountSpaceRuns(list, -1, &end) + 2; + length = end - list; argv = ckalloc((size * sizeof(char *)) + length + 1); for (i = 0, p = ((char *) argv) + size*sizeof(char *); *list != 0; i++) { |