summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorstanton <stanton>1998-10-21 20:39:57 (GMT)
committerstanton <stanton>1998-10-21 20:39:57 (GMT)
commit7e7056e21d0a0d9fa39bdfd742e82b101a6c4b7c (patch)
tree99e08a09e1567ade05e7bc7edac3758b3695d424
parent966ff877247e93fbe6e641cfa77df19d03cfe932 (diff)
downloadtcl-7e7056e21d0a0d9fa39bdfd742e82b101a6c4b7c.zip
tcl-7e7056e21d0a0d9fa39bdfd742e82b101a6c4b7c.tar.gz
tcl-7e7056e21d0a0d9fa39bdfd742e82b101a6c4b7c.tar.bz2
Integrated latest regexp changes from Henry Spencer.
Moved regexp related declarations out of tclInt.h and into tclRegexp.h. Added "encoding" command.
-rw-r--r--changes6
-rw-r--r--doc/encoding.n79
-rw-r--r--generic/chr.h48
-rw-r--r--generic/locale.c675
-rw-r--r--generic/regc_color.c (renamed from generic/color.c)298
-rw-r--r--generic/regc_cvec.c143
-rw-r--r--generic/regc_lex.c (renamed from generic/lex.c)336
-rw-r--r--generic/regc_locale.c426
-rw-r--r--generic/regc_nfa.c (renamed from generic/nfa.c)410
-rw-r--r--generic/regcomp.c (renamed from generic/compile.c)610
-rw-r--r--generic/regcustom.h90
-rw-r--r--generic/regerror.c82
-rw-r--r--generic/regerrs.h19
-rw-r--r--generic/regex.h299
-rw-r--r--generic/regexec.c (renamed from generic/exec.c)459
-rw-r--r--generic/regfree.c25
-rw-r--r--generic/regfronts.c56
-rw-r--r--generic/regguts.h (renamed from generic/guts.h)260
-rw-r--r--generic/tclBasic.c4
-rw-r--r--generic/tclCmdAH.c121
-rw-r--r--generic/tclCmdIL.c3
-rw-r--r--generic/tclCmdMZ.c51
-rw-r--r--generic/tclEncoding.c60
-rw-r--r--generic/tclFileName.c3
-rw-r--r--generic/tclInt.h46
-rw-r--r--generic/tclRegexp.c283
-rw-r--r--generic/tclRegexp.h219
-rw-r--r--generic/tclTest.c334
-rw-r--r--tests/cmdAH.test633
-rw-r--r--tests/encoding.test314
-rw-r--r--tests/regexp.test10
-rw-r--r--tests/regexp2.test3176
-rw-r--r--tests/regexp3.test3295
-rw-r--r--tests/regtests.test867
-rw-r--r--unix/Makefile.in28
-rw-r--r--win/makefile.bc8
-rw-r--r--win/makefile.vc8
37 files changed, 4508 insertions, 9276 deletions
diff --git a/changes b/changes
index 3afdf02..d9ff620 100644
--- a/changes
+++ b/changes
@@ -1,6 +1,6 @@
Recent user-visible changes to Tcl:
-RCS: @(#) $Id: changes,v 1.1.2.6 1998/10/16 01:28:25 stanton Exp $
+RCS: @(#) $Id: changes,v 1.1.2.7 1998/10/21 20:39:57 stanton Exp $
1. No more [command1] [command2] construct for grouping multiple
commands on a single command line.
@@ -3925,3 +3925,7 @@ and lowercase all of the other characters. (stanton)
10/15/98 (bug fix) Changed regexp and string commands to properly
handle case folding according to the Unicode character
tables. (stanton)
+
+10/21/98 (new feature) Added an "encoding" command to facilitate
+translations of strings between different character encodings. See
+the encoding.n manual entry for more details. (stanton)
diff --git a/doc/encoding.n b/doc/encoding.n
new file mode 100644
index 0000000..f63f4b2
--- /dev/null
+++ b/doc/encoding.n
@@ -0,0 +1,79 @@
+'\"
+'\" Copyright (c) 1998 by Scriptics Corporation.
+'\"
+'\" See the file "license.terms" for information on usage and redistribution
+'\" of this file, and for a DISCLAIMER OF ALL WARRANTIES.
+'\"
+'\" RCS: @(#) $Id: encoding.n,v 1.1.2.1 1998/10/21 20:39:58 stanton Exp $
+'\"
+.so man.macros
+.TH encoding n "8.1" Tcl "Tcl Built-In Commands"
+.BS
+.SH NAME
+encoding \- Manipulate encodings
+.SH SYNOPSIS
+\fBencoding \fIoption\fR ?\fIarg arg ...\fR?
+.BE
+
+.SH INTRODUCTION
+.PP
+Strings in Tcl are encoded using 16-bit Unicode characters. Different
+operating system interfaces or applications may generate strings in
+other encodings such as Shift-JIS. The \fBencoding\fR command helps
+to bridge the gap between Unicode and these other formats.
+
+.SH DESCRIPTION
+.PP
+Performs one of several encoding related operations, depending on
+\fIoption\fR. The legal \fIoption\fRs are:
+.TP
+\fBencoding convertfrom ?\fIencoding\fR? \fIdata\fR
+Convert \fIdata\fR to Unicode from the specified \fIencoding\fR. The
+characters in \fIdata\fR are treated as binary data where the lower
+8-bits of each character is taken as a single byte. The resulting
+sequence of bytes is treated as a string in the specified
+\fIencoding\fR. If \fIencoding\fR is not specified, the current
+system encoding is used.
+.TP
+\fBencoding convertto ?\fIencoding\fR? \fIstring\fR
+Convert \fIstring\fR from Unicode to the specified \fIencoding\fR.
+The result is a sequence of bytes that represents the converted
+string. Each byte is stored in the lower 8-bits of a Unicode
+character. If \fIencoding\fR is not specified, the current
+system encoding is used.
+.TP
+\fBencoding names\fR
+Returns a list containing the names of all of the encodings that are
+currently available.
+.TP
+\fBencoding system\fR ?\fIencoding\fR?
+Set the system encoding to \fIencoding\fR. If \fIencoding\fR is
+omitted then the command returns the current system encoding. The
+system encoding is used whenever Tcl passes strings to system calls.
+
+.SH EXAMPLE
+.PP
+It is common practice to write script files using a text editor that
+produces output in the euc-jp encoding, which represents the ASCII
+characters as singe bytes and Japanese characters as two bytes. This
+makes it easy to embed literal strings that correspond to non-ASCII
+characters by simply typing the strings in place in the script.
+However, because the \fBsource\fR command always reads files using the
+ISO8859-1 encoding, Tcl will treat each byte in the file as a separate
+character that maps to the 00 page in Unicode. The
+resulting Tcl strings will not contain the expected Japanese
+characters. Instead, they will contain a sequence of Latin-1
+characters that correspond to the bytes of the original string. The
+\fBencoding\fR command can be used to convert this string to the
+expected Japanese Unicode characters. For example,
+.CS
+ set s [encoding convertfrom euc-jp "\\xA4\\xCF"]
+.CE
+would return the Unicode string "\\u306F", which is the Hiragana
+letter HA.
+
+.SH "SEE ALSO"
+Tcl_GetEncoding
+
+.SH KEYWORDS
+encoding
diff --git a/generic/chr.h b/generic/chr.h
deleted file mode 100644
index 6a21159..0000000
--- a/generic/chr.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * chr.h --
- *
- * Regexp package file: Unichar version of stuff related to the
- * nature of a character.
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: chr.h,v 1.1.2.2 1998/10/03 01:56:40 stanton Exp $
- */
-
-typedef Tcl_UniChar chr; /* internal character type */
-typedef int pchr; /* what it promotes to */
-typedef unsigned uchr; /* unsigned type big enough to hold a chr */
-#define CHRBITS (sizeof(Tcl_UniChar) * CHAR_BIT) /* bits in a chr */
-#define CHR(c) (UCHAR(c)) /* turn a char literal into a chr literal */
-#define DIGITVAL(c) ((c)-'0') /* turn a chr digit into its value */
-
-/*
- * char names for the externally-visible functions
- */
-#define compile re_ucomp
-#define exec re_uexec
diff --git a/generic/locale.c b/generic/locale.c
deleted file mode 100644
index ca56fc4..0000000
--- a/generic/locale.c
+++ /dev/null
@@ -1,675 +0,0 @@
-/*
- * locale.c --
- *
- * Regexp package file:
- * collating-element handling and other locale-specific stuff
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: locale.c,v 1.1.2.2 1998/10/03 01:56:41 stanton Exp $
- */
-
-/*
- * This is largely dummy code, since it needs locale interfaces. The
- * dummy code implements more or less the C locale. Parts of the code
- * are marked "dummy" and "generic" in hopes of making the situation
- * clearer.
- *
- * As a hack for testing, if REG_FAKE is turned on, we add a single
- * collating element ch between c and d, and a single equivalence class
- * containing x and y.
- *
- * The type "celt" is an entirely opaque non-array type -- it need not be
- * an integer type, it could be (say) a pointer -- which has distinct values
- * for all chrs and all collating elements. The only things the outside
- * world does to celts are copying them around and comparing them for
- * equality; everything else is done in this file. There need be no "null"
- * value for celt. The dummy code uses wint_t as celt, with WEOF as the
- * celt code for ch (ugh!).
- */
-
-/*
- * dummy:
- ^ #def MAXCE 2 // longest CE code is prepared to handle
- ^ typedef wint_t celt; // type holding distinct codes for all chrs, all CEs
- */
-
-/* dummy: character-name table */
-static struct cname {
- char *name;
- char code;
-} cnames[] = {
- {"NUL", '\0'},
- {"SOH", '\001'},
- {"STX", '\002'},
- {"ETX", '\003'},
- {"EOT", '\004'},
- {"ENQ", '\005'},
- {"ACK", '\006'},
- {"BEL", '\007'},
- {"alert", '\007'},
- {"BS", '\010'},
- {"backspace", '\b'},
- {"HT", '\011'},
- {"tab", '\t'},
- {"LF", '\012'},
- {"newline", '\n'},
- {"VT", '\013'},
- {"vertical-tab", '\v'},
- {"FF", '\014'},
- {"form-feed", '\f'},
- {"CR", '\015'},
- {"carriage-return", '\r'},
- {"SO", '\016'},
- {"SI", '\017'},
- {"DLE", '\020'},
- {"DC1", '\021'},
- {"DC2", '\022'},
- {"DC3", '\023'},
- {"DC4", '\024'},
- {"NAK", '\025'},
- {"SYN", '\026'},
- {"ETB", '\027'},
- {"CAN", '\030'},
- {"EM", '\031'},
- {"SUB", '\032'},
- {"ESC", '\033'},
- {"IS4", '\034'},
- {"FS", '\034'},
- {"IS3", '\035'},
- {"GS", '\035'},
- {"IS2", '\036'},
- {"RS", '\036'},
- {"IS1", '\037'},
- {"US", '\037'},
- {"space", ' '},
- {"exclamation-mark", '!'},
- {"quotation-mark", '"'},
- {"number-sign", '#'},
- {"dollar-sign", '$'},
- {"percent-sign", '%'},
- {"ampersand", '&'},
- {"apostrophe", '\''},
- {"left-parenthesis", '('},
- {"right-parenthesis", ')'},
- {"asterisk", '*'},
- {"plus-sign", '+'},
- {"comma", ','},
- {"hyphen", '-'},
- {"hyphen-minus", '-'},
- {"period", '.'},
- {"full-stop", '.'},
- {"slash", '/'},
- {"solidus", '/'},
- {"zero", '0'},
- {"one", '1'},
- {"two", '2'},
- {"three", '3'},
- {"four", '4'},
- {"five", '5'},
- {"six", '6'},
- {"seven", '7'},
- {"eight", '8'},
- {"nine", '9'},
- {"colon", ':'},
- {"semicolon", ';'},
- {"less-than-sign", '<'},
- {"equals-sign", '='},
- {"greater-than-sign", '>'},
- {"question-mark", '?'},
- {"commercial-at", '@'},
- {"left-square-bracket", '['},
- {"backslash", '\\'},
- {"reverse-solidus", '\\'},
- {"right-square-bracket", ']'},
- {"circumflex", '^'},
- {"circumflex-accent", '^'},
- {"underscore", '_'},
- {"low-line", '_'},
- {"grave-accent", '`'},
- {"left-brace", '{'},
- {"left-curly-bracket", '{'},
- {"vertical-line", '|'},
- {"right-brace", '}'},
- {"right-curly-bracket", '}'},
- {"tilde", '~'},
- {"DEL", '\177'},
- {NULL, 0}
-};
-
-/* dummy: character-class table */
-static struct cclass {
- char *name;
- char *chars;
- int hasch;
-} cclasses[] = {
- {"alnum", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789", 1},
- {"alpha", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz",
- 1},
- {"blank", " \t", 0},
- {"cntrl", "\007\b\t\n\v\f\r\1\2\3\4\5\6\16\17\20\21\22\23\24\
-\25\26\27\30\31\32\33\34\35\36\37\177", 0},
- {"digit", "0123456789", 0},
- {"graph", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
- 1},
- {"lower", "abcdefghijklmnopqrstuvwxyz",
- 1},
- {"print", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
-0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~ ",
- 1},
- {"punct", "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
- 0},
- {"space", "\t\n\v\f\r ", 0},
- {"upper", "ABCDEFGHIJKLMNOPQRSTUVWXYZ",
- 0},
- {"xdigit", "0123456789ABCDEFabcdef",
- 0},
- {NULL, 0, 0}
-};
-
-#define CH WEOF /* dummy */
-
-/*
- - nces - how many distinct collating elements are there?
- * This is pure dummy code, although a straight "return 0" is definitely
- * what's wanted for all locales lucky enough not to have these stupid
- * things. Case counterparts should be included.
- ^ static int nces(struct vars *);
- */
-static int
-nces(v)
-struct vars *v;
-{
- return (v->cflags&REG_FAKE) ? 1 : 0;
-}
-
-/*
- - nleaders - how many chrs can be first chrs of collating elements?
- * This is pure dummy code, although a straight "return 0" is definitely
- * what's wanted for all locales lucky enough not to have these stupid
- * things. Case counterparts should be included.
- ^ static int nleaders(struct vars *);
- */
-static int
-nleaders(v)
-struct vars *v;
-{
- return (v->cflags&REG_FAKE) ? 1 : 0;
-}
-
-/*
- - allces - return a cvec with all the collating elements of the locale
- * This would be kind of costly if there were large numbers of them; with
- * any luck, that case does not occur in reality. Note that case variants
- * should be included; "all" means *all*.
- * This is pure dummy code.
- ^ static struct cvec *allces(struct vars *, struct cvec *);
- */
-static struct cvec *
-allces(v, cv)
-struct vars *v;
-struct cvec *cv; /* this is supposed to have enough room */
-{
- assert(cv->cespace > 0);
- (VOID) clearcvec(cv);
- if (v->cflags&REG_FAKE)
- addce(cv, ch());
- return cv;
-}
-
-/*
- - element - map collating-element name to celt
- ^ static celt element(struct vars *, chr *, chr *);
- */
-static celt
-element(v, startp, endp)
-struct vars *v;
-chr *startp; /* points to start of name */
-chr *endp; /* points just past end of name */
-{
- register struct cname *cn;
- register size_t len;
- Tcl_DString ds;
- char *name;
-
- /* generic: one-chr names stand for themselves */
- assert(startp < endp);
- len = endp - startp;
- if (len == 1)
- return *startp;
-
- NOTE(REG_ULOCALE);
-
- /*
- * INTL: ISO only, search table
- */
-
- Tcl_DStringInit(&ds);
- name = TclUniCharToUtfDString(startp, (int) len, &ds);
-
- for (cn = cnames; cn->name != NULL; cn++) {
- if (strlen(cn->name) == len && strncmp(cn->name, name, len) == 0) {
- return UCHAR(cn->code);
- }
- }
- Tcl_DStringFree(&ds);
-
- /*
- * Special case for testing.
- */
-
- if ((v->cflags&REG_FAKE) && len == 2) {
- if (*startp == 'c' && *(startp+1) == 'h')
- return (celt) CH;
- }
-
- /* generic: couldn't find it */
- ERR(REG_ECOLLATE);
- return 0;
-}
-
-/*
- - range - supply cvec for a range, including legality check
- * Must include case counterparts on request.
- ^ static struct cvec *range(struct vars *, celt, celt, int);
- */
-static struct cvec *
-range(v, a, b, cases)
-struct vars *v;
-celt a;
-celt b; /* might equal a */
-int cases; /* case-independent? */
-{
- int nchrs;
- int appendch;
- struct cvec *cv;
- celt c;
-
- /* generic: legality check */
- if (a != b && !before(a, b)) {
- ERR(REG_ERANGE);
- return NULL;
- }
-
- /* mostly dummy: compute vector length, note presence of ch */
- appendch = 0;
- if (a == (celt) CH) {
- if (b == (celt) CH) {
- a = 'c';
- b = a - 1; /* kludge to get no chrs */
- appendch = 1;
- } else {
- a = 'd';
- appendch = 1;
- }
- } else {
- if (b == CH) {
- appendch = 1;
- b = 'c';
- } else {
- if ((v->cflags&REG_FAKE) && a <= 'c' && b >= 'd')
- appendch = 1;
- }
- }
- nchrs = b - a + 1;
- if (cases)
- nchrs *= 2;
- cv = getcvec(v, nchrs, appendch);
- NOERRN();
-
- /* mostly dummy: fill in vector */
- for (c = a; c <= b; c++) {
- addchr(cv, c);
- if (cases) {
- if (TclUniCharIsUpper((Tcl_UniChar)c))
- addchr(cv, (chr)Tcl_UniCharToLower(
- (Tcl_UniChar)c));
- else if (TclUniCharIsLower((Tcl_UniChar)c))
- addchr(cv, (chr)Tcl_UniCharToUpper(
- (Tcl_UniChar)c));
- }
- }
- if (appendch)
- addce(cv, ch());
-
- return cv;
-}
-
-/*
- - before - is celt x before celt y, for purposes of range legality?
- * This is all dummy code.
- ^ static int before(celt, celt);
- */
-static int /* predicate */
-before(x, y)
-celt x;
-celt y;
-{
- int isxch = (x == CH);
- int isych = (y == CH);
-
- if (!isxch && !isych && x < y)
- return 1;
- if (isxch && !isych && y >= 'd')
- return 1;
- if (!isxch && isych && x <= 'c')
- return 1;
- return 0;
-}
-
-/*
- - eclass - supply cvec for an equivalence class
- * Must include case counterparts on request.
- * This is all dummy code.
- ^ static struct cvec *eclass(struct vars *, celt, int);
- */
-static struct cvec *
-eclass(v, c, cases)
-struct vars *v;
-celt c;
-int cases; /* all cases? */
-{
- struct cvec *cv;
-
- if (c == CH) {
- cv = getcvec(v, 0, 1);
- assert(cv != NULL);
- addce(cv, ch());
- return cv;
- }
-
- if ((v->cflags&REG_FAKE) && (c == 'x' || c == 'y')) {
- cv = getcvec(v, 4, 0);
- assert(cv != NULL);
- addchr(cv, (chr)'x');
- addchr(cv, (chr)'y');
- if (cases) {
- addchr(cv, (chr)'X');
- addchr(cv, (chr)'Y');
- }
- return cv;
- }
-
- /* no equivalence class by that name */
- if (cases)
- return allcases(v, c);
- cv = getcvec(v, 1, 0);
- assert(cv != NULL);
- addchr(cv, (chr)c);
- return cv;
-}
-
-/*
- - cclass - supply cvec for a character class
- * Must include case counterparts on request.
- * This is all dummy code.
- ^ static struct cvec *cclass(struct vars *, chr *, chr *, int);
- */
-static struct cvec *
-cclass(v, startp, endp, cases)
-struct vars *v;
-chr *startp; /* where the name starts */
-chr *endp; /* just past the end of the name */
-int cases; /* case-independent? */
-{
- size_t len;
- register char *p;
- register struct cclass *cc;
- int hasch;
- struct cvec *cv;
- Tcl_DString ds;
- char *name;
-
- /* check out the name */
- len = endp - startp;
-
- Tcl_DStringInit(&ds);
- name = TclUniCharToUtfDString(startp, (int) len, &ds);
-
- if (cases && len == 5 && (strncmp("lower", name, 5) == 0 ||
- strncmp("upper", name, 5) == 0))
- name = "alpha";
- for (cc = cclasses; cc->name != NULL; cc++) {
- if (strlen(cc->name) == len && strncmp(cc->name, name, len) == 0) {
- break;
- }
- }
- Tcl_DStringFree(&ds);
-
- if (cc->name == NULL) {
- ERR(REG_ECTYPE);
- return NULL;
- }
-
- /* set up vector */
- hasch = (v->cflags&REG_FAKE) ? cc->hasch : 0;
- cv = getcvec(v, (int) strlen(cc->chars), hasch);
- if (cv == NULL) {
- ERR(REG_ESPACE);
- return NULL;
- }
-
- /* fill it in */
- for (p = cc->chars; *p != '\0'; p++)
- addchr(cv, (chr)*p);
- if (hasch)
- addce(cv, ch());
-
- return cv;
-}
-
-/*
- - allcases - supply cvec for all case counterparts of a chr (including itself)
- * This is a shortcut, preferably an efficient one, for simple characters;
- * messy cases are done via range().
- * This is all dummy code.
- ^ static struct cvec *allcases(struct vars *, pchr);
- */
-static struct cvec *
-allcases(v, c)
-struct vars *v;
-pchr c;
-{
- struct cvec *cv = getcvec(v, 2, 0);
-
- assert(cv != NULL);
- addchr(cv, c);
- if (TclUniCharIsUpper((Tcl_UniChar)c))
- addchr(cv, (chr)Tcl_UniCharToLower((Tcl_UniChar)c));
- else if (TclUniCharIsLower((Tcl_UniChar)c))
- addchr(cv, (chr)Tcl_UniCharToUpper((Tcl_UniChar)c));
-
- return cv;
-}
-
-/*
- - sncmp - case-independent chr-string compare
- * REG_ICASE backrefs need this. It should preferably be efficient.
- * This is all dummy code.
- ^ static int sncmp(CONST chr *, CONST chr *, size_t);
- */
-static int /* -1, 0, 1 for <, =, > */
-sncmp(x, y, len)
-CONST chr *x;
-CONST chr *y;
-size_t len; /* maximum length of comparison */
-{
- int diff;
- size_t i;
-
- for (i = 0; i < len; i++) {
- diff = Tcl_UniCharToLower(x[i]) - Tcl_UniCharToLower(y[i]);
- if (diff) {
- return diff;
- }
- }
- return 0;
-}
-
-/*
- * Utility functions for handling cvecs
- */
-
-/*
- - newcvec - allocate a new cvec
- ^ static struct cvec *newcvec(int, int);
- */
-static struct cvec *
-newcvec(nchrs, nces)
-int nchrs; /* to hold this many chrs... */
-int nces; /* ... and this many CEs */
-{
- size_t n;
- size_t nc;
- struct cvec *cv;
-
- nc = (size_t)nchrs + (size_t)nces*(MAXCE+1);
- n = sizeof(struct cvec) + (size_t)(nces-1)*sizeof(chr *) +
- nc*sizeof(chr);
- cv = (struct cvec *)ckalloc(n);
- if (cv == NULL)
- return NULL;
- cv->chrspace = nc;
- cv->chrs = (chr *)&cv->ces[nces]; /* chrs just after CE ptrs */
- cv->cespace = nces;
- return clearcvec(cv);
-}
-
-/*
- - clearcvec - clear a possibly-new cvec
- * Returns pointer as convenience.
- ^ static struct cvec *clearcvec(struct cvec *);
- */
-static struct cvec *
-clearcvec(cv)
-struct cvec *cv;
-{
- int i;
-
- assert(cv != NULL);
- cv->nchrs = 0;
- assert(cv->chrs == (chr *)&cv->ces[cv->cespace]);
- cv->nces = 0;
- cv->ncechrs = 0;
- for (i = 0; i < cv->cespace; i++)
- cv->ces[i] = NULL;
-
- return cv;
-}
-
-/*
- - addchr - add a chr to a cvec
- ^ static VOID addchr(struct cvec *, pchr);
- */
-static VOID
-addchr(cv, c)
-struct cvec *cv;
-pchr c;
-{
- assert(cv->nchrs < cv->chrspace - cv->ncechrs);
- cv->chrs[cv->nchrs++] = (chr) c;
-}
-
-/*
- - addce - add a CE to a cvec
- ^ static VOID addce(struct cvec *, chr *);
- */
-static VOID
-addce(cv, startp)
-struct cvec *cv;
-chr *startp; /* 0-terminated text */
-{
- int n = wcslen(startp);
- int i;
- chr *s;
- chr *d;
-
- assert(n > 0);
- assert(cv->nchrs + n < cv->chrspace - cv->ncechrs);
- assert(cv->nces < cv->cespace);
- d = &cv->chrs[cv->chrspace - cv->ncechrs - n - 1];
- cv->ces[cv->nces++] = d;
- for (s = startp, i = n; i > 0; s++, i--)
- *d++ = *s;
- *d = 0; /* endmarker */
- assert(d == &cv->chrs[cv->chrspace - cv->ncechrs]);
- cv->ncechrs += n + 1;
-}
-
-/*
- - haschr - does a cvec contain this chr?
- ^ static int haschr(struct cvec *, pchr);
- */
-static int /* predicate */
-haschr(cv, c)
-struct cvec *cv;
-pchr c;
-{
- int i;
- chr *p;
-
- for (p = cv->chrs, i = cv->nchrs; i > 0; p++, i--)
- if (*p == c)
- return 1;
- return 0;
-}
-
-/*
- - getcvec - get a cvec, remembering it as v->cv
- ^ static struct cvec *getcvec(struct vars *, int, int);
- */
-static struct cvec *
-getcvec(v, nchrs, nces)
-struct vars *v;
-int nchrs; /* to hold this many chrs... */
-int nces; /* ... and this many CEs */
-{
- if (v->cv != NULL && nchrs <= v->cv->chrspace && nces <= v->cv->cespace)
- return clearcvec(v->cv);
-
- if (v->cv != NULL)
- freecvec(v->cv);
- v->cv = newcvec(nchrs, nces);
- if (v->cv == NULL)
- ERR(REG_ESPACE);
-
- return v->cv;
-}
-
-/*
- - freecvec - free a cvec
- ^ static VOID freecvec(struct cvec *);
- */
-static VOID
-freecvec(cv)
-struct cvec *cv;
-{
- ckfree((char *)cv);
-}
diff --git a/generic/color.c b/generic/regc_color.c
index fa640f9..4a8a87c 100644
--- a/generic/color.c
+++ b/generic/regc_color.c
@@ -1,85 +1,25 @@
/*
- * color.c --
+ * colorings of characters
+ * This file is #included by regcomp.c.
*
- * Regexp package file: colorings of characters.
- * Note that there are some incestuous relationships between this code and
- * NFA arc maintenance, which perhaps ought to be cleaned up sometime.
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: color.c,v 1.1.2.2 1998/10/03 01:56:40 stanton Exp $
+ * Note that there are some incestuous relationships between this code and
+ * NFA arc maintenance, which perhaps ought to be cleaned up sometime.
*/
+
+
/*
- * The innards.
- */
-struct colors {
- color ccolor[BYTTAB];
-};
-struct ptrs {
- union tree *pptr[BYTTAB];
-};
-union tree {
- struct colors colors;
- struct ptrs ptrs;
-};
-#define tcolor colors.ccolor
-#define tptr ptrs.pptr
-/*
- * Some of the function prototypes need this.
- ^ union tree;
+ * If this declaration draws a complaint about a negative array size,
+ * then CHRBITS is defined incorrectly for the chr type.
*/
+static char isCHRBITSright[NEGIFNOT(sizeof(chr)*CHAR_BIT == CHRBITS)];
+
+
+
+#define CISERR() VISERR(cm->v)
+#define CERR(e) VERR(cm->v, (e))
-struct colordesc {
- uchr nchrs; /* number of chars of this color */
- color sub; /* open subcolor of this one, or NOSUB */
-# define NOSUB COLORLESS
- struct arc *arcs; /* color chain */
-# define UNUSEDCOLOR(cd) ((cd)->nchrs == 0 && (cd)->sub == NOSUB)
- int flags;
-# define PSEUDO 1 /* pseudocolor, no real chars */
-};
-
-struct colormap {
- int magic;
-# define CMMAGIC 0x876
- struct vars *v; /* for error reporting */
- color rest;
- int filled; /* has it been filled? */
- int ncds; /* number of colordescs */
- struct colordesc *cd;
-# define CDEND(cm) (&(cm)->cd[(cm)->ncds])
-# define NINLINECDS 10
- struct colordesc cds[NINLINECDS];
- union tree tree[NBYTS]; /* tree top, plus fill blocks */
-};
-#ifdef COMPILE
/*
- newcm - get new colormap
@@ -96,7 +36,7 @@ struct vars *v;
union tree *nextt;
struct colordesc *cd;
- cm = (struct colormap *)ckalloc(sizeof(struct colormap));
+ cm = (struct colormap *)MALLOC(sizeof(struct colormap));
if (cm == NULL) {
ERR(REG_ESPACE);
return NULL;
@@ -114,15 +54,13 @@ struct vars *v;
cd->arcs = NULL;
cd->flags = 0;
}
- cm->cd[WHITE].nchrs = WCHAR_MAX - WCHAR_MIN;
+ cm->cd[WHITE].nchrs = CHR_MAX - CHR_MIN + 1;
/* treetop starts as NULLs if there are lower levels */
t = cm->tree;
- if (NBYTS > 1) {
- for (i = BYTTAB-1; i >= 0; i--)
- t->tptr[i] = NULL;
- }
-
+ if (NBYTS > 1)
+ for (i = BYTTAB-1; i >= 0; i--)
+ t->tptr[i] = NULL;
/* if no lower levels, treetop and last fill block are the same */
/* fill blocks point to next fill block... */
@@ -149,13 +87,11 @@ freecm(cm)
struct colormap *cm;
{
cm->magic = 0;
- if (NBYTS > 1) {
- cmtreefree(cm, cm->tree, 0);
- }
- if (cm->cd != cm->cds) {
- ckfree((char *)cm->cd);
- }
- ckfree((char *) cm); /* mem leak (CCS). */
+ if (NBYTS > 1)
+ cmtreefree(cm, cm->tree, 0);
+ if (cm->cd != cm->cds)
+ FREE(cm->cd);
+ FREE(cm);
}
/*
@@ -176,10 +112,9 @@ int level; /* level number (top == 0) of this block */
for (i = BYTTAB-1; i >= 0; i--) {
t = tree->tptr[i];
if (t != NULL && t != fillt) {
- if ((int) level < (int) NBYTS-2) { /* more pointer blocks below */
+ if (level < NBYTS-2) /* more pointer blocks below */
cmtreefree(cm, t, level+1);
- }
- ckfree((char *) t);
+ FREE(t);
}
}
}
@@ -221,17 +156,13 @@ int level; /* level number (top == 0) of this block */
t = tree->tptr[i];
if (t == fillt) /* oops */
{}
- else if (t == NULL) {
+ else if (t == NULL)
tree->tptr[i] = fillt;
- }
- else if ((int) level < (int) NBYTS-2) {/* more pointer blocks below */
+ else if (level < NBYTS-2) /* more pointer blocks below */
cmtreefill(cm, t, level+1);
- }
}
}
-#endif /* ifdef COMPILE */
-
/*
- getcolor - get the color of a character from a colormap
^ static color getcolor(struct colormap *, pchr);
@@ -261,8 +192,6 @@ pchr c;
return cm->rest;
}
-#ifdef COMPILE
-
/*
- setcolor - set the color of a character in a colormap
^ static color setcolor(struct colormap *, pchr, pcolor);
@@ -283,7 +212,7 @@ pcolor co;
color prev;
assert(cm->magic == CMMAGIC);
- if (VISERR(cm->v) || co == COLORLESS)
+ if (CISERR() || co == COLORLESS)
return COLORLESS;
t = cm->tree;
@@ -293,10 +222,10 @@ pcolor co;
t = t->tptr[b];
if (t == NULL) { /* fell off an incomplete part */
bottom = (shift <= BYTBITS) ? 1 : 0;
- t = (union tree *)ckalloc((bottom) ?
+ t = (union tree *)MALLOC((bottom) ?
sizeof(struct colors) : sizeof(struct ptrs));
if (t == NULL) {
- VERR(cm->v, REG_ESPACE);
+ CERR(REG_ESPACE);
return COLORLESS;
}
if (bottom)
@@ -312,7 +241,7 @@ pcolor co;
b = uc & BYTMASK;
prev = t->tcolor[b];
- t->tcolor[b] = (color) co;
+ t->tcolor[b] = (color)co;
return prev;
}
@@ -328,7 +257,7 @@ struct colormap *cm;
struct colordesc *end;
struct colordesc *lastused;
- if (VISERR(cm->v))
+ if (CISERR())
return COLORLESS;
lastused = NULL;
@@ -337,7 +266,7 @@ struct colormap *cm;
if (!UNUSEDCOLOR(cd))
lastused = cd;
assert(lastused != NULL);
- return (color) (lastused - cm->cd);
+ return (color)(lastused - cm->cd);
}
/*
@@ -352,31 +281,31 @@ struct colormap *cm;
struct colordesc *cd;
struct colordesc *end;
struct colordesc *firstnew;
- int n;
+ size_t n;
- if (VISERR(cm->v))
+ if (CISERR())
return COLORLESS;
end = CDEND(cm);
for (cd = cm->cd; cd < end; cd++)
if (UNUSEDCOLOR(cd)) {
assert(cd->arcs == NULL);
- return (color) (cd - cm->cd);
+ return (color)(cd - cm->cd);
}
/* oops, must allocate more */
n = cm->ncds * 2;
if (cm->cd == cm->cds) {
- cd = (struct colordesc *)ckalloc(sizeof(struct colordesc) * n);
+ cd = (struct colordesc *)MALLOC(sizeof(struct colordesc) * n);
if (cd != NULL)
- memcpy((VOID *)cd, (VOID *)cm->cds, cm->ncds *
+ memcpy(VS(cd), VS(cm->cds), cm->ncds *
sizeof(struct colordesc));
} else {
- cd = (struct colordesc *)ckrealloc((VOID *)cm->cd,
- sizeof(struct colordesc) * n);
+ cd = (struct colordesc *)REALLOC(cm->cd,
+ n * sizeof(struct colordesc));
}
if (cd == NULL) {
- VERR(cm->v, REG_ESPACE);
+ CERR(REG_ESPACE);
return COLORLESS;
}
cm->cd = cd;
@@ -390,7 +319,7 @@ struct colormap *cm;
cd->flags = 0;
}
assert(firstnew < CDEND(cm) && UNUSEDCOLOR(firstnew));
- return (color) (firstnew - cm->cd);
+ return (color)(firstnew - cm->cd);
}
/*
@@ -404,7 +333,7 @@ struct colormap *cm;
color co;
co = newcolor(cm);
- if (VISERR(cm->v))
+ if (CISERR())
return COLORLESS;
cm->cd[co].nchrs = 1;
cm->cd[co].flags = PSEUDO;
@@ -459,22 +388,22 @@ struct colormap *cm;
color co;
color sco;
- for (cd = cm->cd, co = 0; cd < end; cd++, co++) {
- sco = cd->sub;
- if (sco == NOSUB) {
- /* has no subcolor, no further action */
- } else if (sco == co) {
- /* is subcolor, let parent deal with it */
- } else if (cd->nchrs == 0) {
- /* parent empty, its arcs change color to subcolor */
- cd->sub = NOSUB;
- scd = &cm->cd[sco];
- assert(scd->nchrs > 0);
- assert(scd->sub == sco);
- scd->sub = NOSUB;
- while ((a = cd->arcs) != NULL) {
- assert(a->co == co);
- /* uncolorchain(cm, a); */
+ for (cd = cm->cd, co = 0; cd < end; cd++, co++) {
+ sco = cd->sub;
+ if (sco == NOSUB) {
+ /* has no subcolor, no further action */
+ } else if (sco == co) {
+ /* is subcolor, let parent deal with it */
+ } else if (cd->nchrs == 0) {
+ /* parent empty, its arcs change color to subcolor */
+ cd->sub = NOSUB;
+ scd = &cm->cd[sco];
+ assert(scd->nchrs > 0);
+ assert(scd->sub == sco);
+ scd->sub = NOSUB;
+ while ((a = cd->arcs) != NULL) {
+ assert(a->co == co);
+ /* uncolorchain(cm, a); */
cd->arcs = a->colorchain;
a->co = sco;
/* colorchain(cm, a); */
@@ -483,11 +412,11 @@ struct colormap *cm;
}
} else {
/* parent's arcs must gain parallel subcolor arcs */
- cd->sub = NOSUB;
- scd = &cm->cd[sco];
- assert(scd->nchrs > 0);
- assert(scd->sub == sco);
- scd->sub = NOSUB;
+ cd->sub = NOSUB;
+ scd = &cm->cd[sco];
+ assert(scd->nchrs > 0);
+ assert(scd->sub == sco);
+ scd->sub = NOSUB;
for (a = cd->arcs; a != NULL; a = a->colorchain) {
assert(a->co == co);
newarc(nfa, a->type, sco, a->from, a->to);
@@ -558,11 +487,11 @@ pchr c;
^ struct state *, struct state *);
*/
static VOID
-rainbow(nfa, cm, type, exc, from, to)
+rainbow(nfa, cm, type, but, from, to)
struct nfa *nfa;
struct colormap *cm;
int type;
-pcolor exc; /* COLORLESS if no exceptions */
+pcolor but; /* COLORLESS if no exceptions */
struct state *from;
struct state *to;
{
@@ -570,8 +499,8 @@ struct state *to;
struct colordesc *end = CDEND(cm);
color co;
- for (cd = cm->cd, co = 0; cd < end && !VISERR(nfa->v); cd++, co++)
- if (!UNUSEDCOLOR(cd) && cd->sub != co && co != exc &&
+ for (cd = cm->cd, co = 0; cd < end && !CISERR(); cd++, co++)
+ if (!UNUSEDCOLOR(cd) && cd->sub != co && co != but &&
!(cd->flags&PSEUDO))
newarc(nfa, type, co, from, to);
}
@@ -596,10 +525,95 @@ struct state *to;
color co;
assert(of != from);
- for (cd = cm->cd, co = 0; cd < end && !VISERR(nfa->v); cd++, co++)
+ for (cd = cm->cd, co = 0; cd < end && !CISERR(); cd++, co++)
if (!UNUSEDCOLOR(cd) && !(cd->flags&PSEUDO))
if (findarc(of, PLAIN, co) == NULL)
newarc(nfa, type, co, from, to);
}
-#endif /* ifdef COMPILE */
+
+
+#ifdef REG_DEBUG
+
+/*
+ - dumpcolors - debugging output
+ ^ static VOID dumpcolors(struct colormap *, FILE *);
+ */
+static VOID
+dumpcolors(cm, f)
+struct colormap *cm;
+FILE *f;
+{
+ struct colordesc *cd;
+ struct colordesc *end;
+ color co;
+ chr c;
+
+ if (cm->filled) {
+ fprintf(f, "filled\n");
+ if (NBYTS > 1)
+ fillcheck(cm, cm->tree, 0, f);
+ }
+ end = CDEND(cm);
+ for (cd = cm->cd + 1, co = 1; cd < end; cd++, co++) /* skip 0 */
+ if (cd->nchrs > 0) {
+ if (cd->flags&PSEUDO)
+ fprintf(f, "#%2ld(ps): ", (long)co);
+ else
+ fprintf(f, "#%2ld(%2d): ", (long)co, cd->nchrs);
+ for (c = CHR_MIN; c < CHR_MAX; c++)
+ if (getcolor(cm, c) == co)
+ dumpchr(c, f);
+ assert(c == CHR_MAX);
+ if (getcolor(cm, c) == co)
+ dumpchr(c, f);
+ fprintf(f, "\n");
+ }
+}
+
+/*
+ - fillcheck - check proper filling of a tree
+ ^ static VOID fillcheck(struct colormap *, union tree *, int, FILE *);
+ */
+static VOID
+fillcheck(cm, tree, level, f)
+struct colormap *cm;
+union tree *tree;
+int level; /* level number (top == 0) of this block */
+FILE *f;
+{
+ int i;
+ union tree *t;
+ union tree *fillt = &cm->tree[level+1];
+
+ assert(level < NBYTS-1); /* this level has pointers */
+ for (i = BYTTAB-1; i >= 0; i--) {
+ t = tree->tptr[i];
+ if (t == NULL)
+ fprintf(f, "NULL found in filled tree!\n");
+ else if (t == fillt)
+ {}
+ else if (level < NBYTS-2) /* more pointer blocks below */
+ fillcheck(cm, t, level+1, f);
+ }
+}
+
+/*
+ - dumpchr - print a chr
+ * Kind of char-centric but works well enough for debug use.
+ ^ static VOID dumpchr(pchr, FILE *);
+ */
+static VOID
+dumpchr(c, f)
+pchr c;
+FILE *f;
+{
+ if (c == '\\')
+ fprintf(f, "\\\\");
+ else if (c > ' ' && c <= '~')
+ putc((char)c, f);
+ else
+ fprintf(f, "\\0%lo", (long)c);
+}
+
+#endif /* ifdef REG_DEBUG */
diff --git a/generic/regc_cvec.c b/generic/regc_cvec.c
new file mode 100644
index 0000000..0650883
--- /dev/null
+++ b/generic/regc_cvec.c
@@ -0,0 +1,143 @@
+/*
+ * Utility functions for handling cvecs
+ * This file is #included by regcomp.c.
+ */
+
+/*
+ - newcvec - allocate a new cvec
+ ^ static struct cvec *newcvec(int, int);
+ */
+static struct cvec *
+newcvec(nchrs, nmcces)
+int nchrs; /* to hold this many chrs... */
+int nmcces; /* ... and this many MCCEs */
+{
+ size_t n;
+ size_t nc;
+ struct cvec *cv;
+
+ nc = (size_t)nchrs + (size_t)nmcces*(MAXMCCE+1);
+ n = sizeof(struct cvec) + (size_t)(nmcces-1)*sizeof(chr *) +
+ nc*sizeof(chr);
+ cv = (struct cvec *)MALLOC(n);
+ if (cv == NULL)
+ return NULL;
+ cv->chrspace = nc;
+ cv->chrs = (chr *)&cv->mcces[nmcces]; /* chrs just after MCCE ptrs */
+ cv->mccespace = nmcces;
+ return clearcvec(cv);
+}
+
+/*
+ - clearcvec - clear a possibly-new cvec
+ * Returns pointer as convenience.
+ ^ static struct cvec *clearcvec(struct cvec *);
+ */
+static struct cvec *
+clearcvec(cv)
+struct cvec *cv;
+{
+ int i;
+
+ assert(cv != NULL);
+ cv->nchrs = 0;
+ assert(cv->chrs == (chr *)&cv->mcces[cv->mccespace]);
+ cv->nmcces = 0;
+ cv->nmccechrs = 0;
+ for (i = 0; i < cv->mccespace; i++)
+ cv->mcces[i] = NULL;
+
+ return cv;
+}
+
+/*
+ - addchr - add a chr to a cvec
+ ^ static VOID addchr(struct cvec *, pchr);
+ */
+static VOID
+addchr(cv, c)
+struct cvec *cv;
+pchr c;
+{
+ assert(cv->nchrs < cv->chrspace - cv->nmccechrs);
+ cv->chrs[cv->nchrs++] = (chr)c;
+}
+
+/*
+ - addmcce - add an MCCE to a cvec
+ ^ static VOID addmcce(struct cvec *, chr *, chr *);
+ */
+static VOID
+addmcce(cv, startp, endp)
+struct cvec *cv;
+chr *startp; /* beginning of text */
+chr *endp; /* just past end of text */
+{
+ int n = endp - startp;
+ int i;
+ chr *s;
+ chr *d;
+
+ assert(n > 0);
+ assert(cv->nchrs + n < cv->chrspace - cv->nmccechrs);
+ assert(cv->nmcces < cv->mccespace);
+ d = &cv->chrs[cv->chrspace - cv->nmccechrs - n - 1];
+ cv->mcces[cv->nmcces++] = d;
+ for (s = startp, i = n; i > 0; s++, i--)
+ *d++ = *s;
+ *d++ = 0; /* endmarker */
+ assert(d == &cv->chrs[cv->chrspace - cv->nmccechrs]);
+ cv->nmccechrs += n + 1;
+}
+
+/*
+ - haschr - does a cvec contain this chr?
+ ^ static int haschr(struct cvec *, pchr);
+ */
+static int /* predicate */
+haschr(cv, c)
+struct cvec *cv;
+pchr c;
+{
+ int i;
+ chr *p;
+
+ for (p = cv->chrs, i = cv->nchrs; i > 0; p++, i--)
+ if (*p == c)
+ return 1;
+ return 0;
+}
+
+/*
+ - getcvec - get a cvec, remembering it as v->cv
+ ^ static struct cvec *getcvec(struct vars *, int, int);
+ */
+static struct cvec *
+getcvec(v, nchrs, nmcces)
+struct vars *v;
+int nchrs; /* to hold this many chrs... */
+int nmcces; /* ... and this many MCCEs */
+{
+ if (v->cv != NULL && nchrs <= v->cv->chrspace &&
+ nmcces <= v->cv->mccespace)
+ return clearcvec(v->cv);
+
+ if (v->cv != NULL)
+ freecvec(v->cv);
+ v->cv = newcvec(nchrs, nmcces);
+ if (v->cv == NULL)
+ ERR(REG_ESPACE);
+
+ return v->cv;
+}
+
+/*
+ - freecvec - free a cvec
+ ^ static VOID freecvec(struct cvec *);
+ */
+static VOID
+freecvec(cv)
+struct cvec *cv;
+{
+ FREE(cv);
+}
diff --git a/generic/lex.c b/generic/regc_lex.c
index 7ae3ccc..820b404 100644
--- a/generic/lex.c
+++ b/generic/regc_lex.c
@@ -1,36 +1,6 @@
/*
- * lex --
- *
- * Regexp package file: lexical analyzer - #included in other source
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: lex.c,v 1.1.2.2 1998/10/03 01:56:40 stanton Exp $
+ * lexical analyzer
+ * This file is #included by regcomp.c.
*/
/* scanning macros (know about v) */
@@ -58,8 +28,11 @@
#define L_CEL 7 /* collating element */
#define L_ECL 8 /* equivalence class */
#define L_CCL 9 /* character class */
-#define INTO(c) (v->lexcon = (c))
-#define _IN(con) (v->lexcon == (con))
+#define INTOCON(c) (v->lexcon = (c))
+#define INCON(con) (v->lexcon == (con))
+
+/* construct pointer past end of chr array */
+#define ENDOF(array) ((array) + sizeof(array)/sizeof(chr))
/*
- lexstart - set up lexical stuff, scan leading options
@@ -67,19 +40,20 @@
*/
static VOID
lexstart(v)
-register struct vars *v;
+struct vars *v;
{
prefixes(v); /* may turn on new type bits etc. */
NOERR();
if (v->cflags&REG_QUOTE) {
- v->cflags &= ~(REG_EXTENDED|REG_ADVF|REG_EXPANDED);
- INTO(L_Q);
- } else if (v->cflags&REG_EXTENDED)
- INTO(L_ERE);
- else {
- v->cflags &= ~REG_ADVF;
- INTO(L_BRE);
+ assert(!(v->cflags&(REG_ADVANCED|REG_EXPANDED|REG_NEWLINE)));
+ INTOCON(L_Q);
+ } else if (v->cflags&REG_EXTENDED) {
+ assert(!(v->cflags&REG_QUOTE));
+ INTOCON(L_ERE);
+ } else {
+ assert(!(v->cflags&(REG_QUOTE|REG_ADVF)));
+ INTOCON(L_BRE);
}
v->nexttype = EMPTY; /* remember we were at the start */
@@ -104,11 +78,14 @@ struct vars *v;
case CHR('?'): /* "***?" error, msg shows version */
ERR(REG_BADPAT);
return; /* proceed no further */
+ break;
case CHR('='): /* "***=" shifts to literal string */
NOTE(REG_UNONPOSIX);
v->cflags |= REG_QUOTE;
+ v->cflags &= ~(REG_ADVANCED|REG_EXPANDED|REG_NEWLINE);
v->now += 4;
return; /* and there can be no more prefixes */
+ break;
case CHR(':'): /* "***:" shifts to AREs */
NOTE(REG_UNONPOSIX);
v->cflags |= REG_ADVANCED;
@@ -117,26 +94,28 @@ struct vars *v;
default: /* otherwise *** is just an error */
ERR(REG_BADRPT);
return;
+ break;
}
- /* BREs and plain EREs don't get any other favors */
+ /* BREs and EREs don't get embedded options */
if ((v->cflags&REG_ADVANCED) != REG_ADVANCED)
return;
- /* embedded options */
- if (HAVE(3) && NEXT2('(', '?') && iswalpha(*(v->now + 2))) {
+ /* embedded options (AREs only) */
+ if (HAVE(3) && NEXT2('(', '?') && iscalpha(*(v->now + 2))) {
NOTE(REG_UNONPOSIX);
v->now += 2;
- for (; !ATEOS() && iswalpha(*v->now); v->now++)
+ for (; !ATEOS() && iscalpha(*v->now); v->now++)
switch (*v->now) {
case CHR('b'): /* BREs (but why???) */
- v->cflags &= ~REG_EXTENDED;
+ v->cflags &= ~(REG_ADVANCED|REG_QUOTE);
break;
case CHR('c'): /* case sensitive */
v->cflags &= ~REG_ICASE;
break;
case CHR('e'): /* plain EREs */
- v->cflags &= ~REG_ADVF;
+ v->cflags |= REG_EXTENDED;
+ v->cflags &= ~(REG_ADVF|REG_QUOTE);
break;
case CHR('i'): /* case insensitive */
v->cflags |= REG_ICASE;
@@ -151,6 +130,7 @@ struct vars *v;
break;
case CHR('q'): /* literal string */
v->cflags |= REG_QUOTE;
+ v->cflags &= ~REG_ADVANCED;
break;
case CHR('s'): /* single line, \n ordinary */
v->cflags &= ~REG_NEWLINE;
@@ -174,6 +154,8 @@ struct vars *v;
return;
}
v->now++;
+ if (v->cflags&REG_QUOTE)
+ v->cflags &= ~(REG_EXPANDED|REG_NEWLINE);
}
}
@@ -181,67 +163,68 @@ struct vars *v;
- lexnest - "call a subroutine", interpolating string at the lexical level
* Note, this is not a very general facility. There are a number of
* implicit assumptions about what sorts of strings can be subroutines.
- ^ static VOID lexnest(struct vars *, chr *);
+ ^ static VOID lexnest(struct vars *, chr *, chr *);
*/
static VOID
-lexnest(v, s)
+lexnest(v, beginp, endp)
struct vars *v;
-chr *s;
+chr *beginp; /* start of interpolation */
+chr *endp; /* one past end of interpolation */
{
assert(v->savenow == NULL); /* only one level of nesting */
v->savenow = v->now;
v->savestop = v->stop;
- v->now = s;
- v->stop = s + wcslen(s);
+ v->now = beginp;
+ v->stop = endp;
}
/*
- * string CONSTants to interpolate as expansions of things like \d
+ * string constants to interpolate as expansions of things like \d
*/
static chr backd[] = { /* \d */
CHR('['), CHR('['), CHR(':'),
CHR('d'), CHR('i'), CHR('g'), CHR('i'), CHR('t'),
- CHR(':'), CHR(']'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR(']')
};
static chr backD[] = { /* \D */
CHR('['), CHR('^'), CHR('['), CHR(':'),
CHR('d'), CHR('i'), CHR('g'), CHR('i'), CHR('t'),
- CHR(':'), CHR(']'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR(']')
};
static chr brbackd[] = { /* \d within brackets */
CHR('['), CHR(':'),
CHR('d'), CHR('i'), CHR('g'), CHR('i'), CHR('t'),
- CHR(':'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']')
};
static chr backs[] = { /* \s */
CHR('['), CHR('['), CHR(':'),
CHR('s'), CHR('p'), CHR('a'), CHR('c'), CHR('e'),
- CHR(':'), CHR(']'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR(']')
};
static chr backS[] = { /* \S */
CHR('['), CHR('^'), CHR('['), CHR(':'),
CHR('s'), CHR('p'), CHR('a'), CHR('c'), CHR('e'),
- CHR(':'), CHR(']'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR(']')
};
static chr brbacks[] = { /* \s within brackets */
CHR('['), CHR(':'),
CHR('s'), CHR('p'), CHR('a'), CHR('c'), CHR('e'),
- CHR(':'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']')
};
static chr backw[] = { /* \w */
CHR('['), CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR('_'), CHR(']')
};
static chr backW[] = { /* \W */
CHR('['), CHR('^'), CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_'), CHR(']'), CHR('\0')
+ CHR(':'), CHR(']'), CHR('_'), CHR(']')
};
static chr brbackw[] = { /* \w within brackets */
CHR('['), CHR(':'),
CHR('a'), CHR('l'), CHR('n'), CHR('u'), CHR('m'),
- CHR(':'), CHR(']'), CHR('_'), CHR('\0')
+ CHR(':'), CHR(']'), CHR('_')
};
/*
@@ -253,7 +236,7 @@ static VOID
lexword(v)
struct vars *v;
{
- lexnest(v, backw);
+ lexnest(v, backw, ENDOF(backw));
}
/*
@@ -262,9 +245,9 @@ struct vars *v;
*/
static int /* 1 normal, 0 failure */
next(v)
-register struct vars *v;
+struct vars *v;
{
- register chr c;
+ chr c;
/* errors yield an infinite sequence of failures */
if (ISERR())
@@ -298,14 +281,17 @@ register struct vars *v;
case L_BRE:
case L_Q:
RET(EOS);
+ break;
case L_EBND:
case L_BBND:
FAILW(REG_EBRACE);
+ break;
case L_BRACK:
case L_CEL:
case L_ECL:
case L_CCL:
FAILW(REG_EBRACK);
+ break;
}
assert(NOTREACHED);
}
@@ -317,22 +303,26 @@ register struct vars *v;
switch (v->lexcon) {
case L_BRE: /* punt BREs to separate function */
return brenext(v, c);
+ break;
case L_ERE: /* see below */
break;
case L_Q: /* literal strings are easy */
RETV(PLAIN, c);
+ break;
case L_BBND: /* bounds are fairly simple */
case L_EBND:
switch (c) {
case CHR('0'): case CHR('1'): case CHR('2'): case CHR('3'):
case CHR('4'): case CHR('5'): case CHR('6'): case CHR('7'):
case CHR('8'): case CHR('9'):
- RETV(DIGIT, (chr) DIGITVAL(c));
+ RETV(DIGIT, (chr)DIGITVAL(c));
+ break;
case CHR(','):
RET(',');
+ break;
case CHR('}'): /* ERE bound ends with } */
- if (_IN(L_EBND)) {
- INTO(L_ERE);
+ if (INCON(L_EBND)) {
+ INTOCON(L_ERE);
if ((v->cflags&REG_ADVF) && NEXT1('?')) {
v->now++;
NOTE(REG_UNONPOSIX);
@@ -341,25 +331,32 @@ register struct vars *v;
RETV('}', 1);
} else
FAILW(REG_BADBR);
+ break;
case CHR('\\'): /* BRE bound ends with \} */
- if (_IN(L_BBND) && NEXT1('}')) {
+ if (INCON(L_BBND) && NEXT1('}')) {
v->now++;
- INTO(L_BRE);
+ INTOCON(L_BRE);
RET('}');
} else
FAILW(REG_BADBR);
+ break;
default:
FAILW(REG_BADBR);
+ break;
}
+ assert(NOTREACHED);
+ break;
case L_BRACK: /* brackets are not too hard */
switch (c) {
case CHR(']'):
if (LASTTYPE('['))
RETV(PLAIN, c);
else {
- INTO((v->cflags&REG_EXTENDED) ? L_ERE : L_BRE);
+ INTOCON((v->cflags&REG_EXTENDED) ?
+ L_ERE : L_BRE);
RET(']');
}
+ break;
case CHR('\\'):
NOTE(REG_UBBS);
if (!(v->cflags&REG_ADVF))
@@ -367,85 +364,109 @@ register struct vars *v;
NOTE(REG_UNONPOSIX);
if (ATEOS())
FAILW(REG_EESCAPE);
- (VOID) lexescape(v);
+ (DISCARD) lexescape(v);
switch (v->nexttype) { /* not all escapes okay here */
case PLAIN:
return 1;
+ break;
case CCLASS:
switch (v->nextvalue) {
- case 'd': lexnest(v, brbackd); break;
- case 's': lexnest(v, brbacks); break;
- case 'w': lexnest(v, brbackw); break;
+ case 'd':
+ lexnest(v, brbackd, ENDOF(brbackd));
+ break;
+ case 's':
+ lexnest(v, brbacks, ENDOF(brbacks));
+ break;
+ case 'w':
+ lexnest(v, brbackw, ENDOF(brbackw));
+ break;
default:
FAILW(REG_EESCAPE);
+ break;
}
/* lexnest done, back up and try again */
v->nexttype = v->lasttype;
return next(v);
+ break;
}
/* not one of the acceptable escapes */
FAILW(REG_EESCAPE);
+ break;
case CHR('-'):
if (LASTTYPE('[') || NEXT1(']'))
RETV(PLAIN, c);
else
RETV(RANGE, c);
+ break;
case CHR('['):
if (ATEOS())
FAILW(REG_EBRACK);
switch (*v->now++) {
case CHR('.'):
- INTO(L_CEL);
+ INTOCON(L_CEL);
/* might or might not be locale-specific */
RET(COLLEL);
+ break;
case CHR('='):
- INTO(L_ECL);
+ INTOCON(L_ECL);
NOTE(REG_ULOCALE);
RET(ECLASS);
+ break;
case CHR(':'):
- INTO(L_CCL);
+ INTOCON(L_CCL);
NOTE(REG_ULOCALE);
RET(CCLASS);
+ break;
default: /* oops */
v->now--;
RETV(PLAIN, c);
+ break;
}
+ assert(NOTREACHED);
+ break;
default:
RETV(PLAIN, c);
+ break;
}
+ assert(NOTREACHED);
+ break;
case L_CEL: /* collating elements are easy */
if (c == CHR('.') && NEXT1(']')) {
v->now++;
- INTO(L_BRACK);
+ INTOCON(L_BRACK);
RETV(END, '.');
} else
RETV(PLAIN, c);
+ break;
case L_ECL: /* ditto equivalence classes */
if (c == CHR('=') && NEXT1(']')) {
v->now++;
- INTO(L_BRACK);
+ INTOCON(L_BRACK);
RETV(END, '=');
} else
RETV(PLAIN, c);
+ break;
case L_CCL: /* ditto character classes */
if (c == CHR(':') && NEXT1(']')) {
v->now++;
- INTO(L_BRACK);
+ INTOCON(L_BRACK);
RETV(END, ':');
} else
RETV(PLAIN, c);
+ break;
default:
assert(NOTREACHED);
break;
}
/* that got rid of everything except EREs */
- assert(_IN(L_ERE));
+ assert(INCON(L_ERE));
/* deal with EREs, except for backslashes */
switch (c) {
case CHR('|'):
RET('|');
+ break;
case CHR('*'):
if ((v->cflags&REG_ADVF) && NEXT1('?')) {
v->now++;
@@ -453,6 +474,7 @@ register struct vars *v;
RETV('*', 0);
}
RETV('*', 1);
+ break;
case CHR('+'):
if ((v->cflags&REG_ADVF) && NEXT1('?')) {
v->now++;
@@ -460,6 +482,7 @@ register struct vars *v;
RETV('+', 0);
}
RETV('+', 1);
+ break;
case CHR('?'):
if ((v->cflags&REG_ADVF) && NEXT1('?')) {
v->now++;
@@ -467,18 +490,21 @@ register struct vars *v;
RETV('?', 0);
}
RETV('?', 1);
+ break;
case CHR('{'): /* bounds start or plain character */
if (v->cflags&REG_EXPANDED)
skip(v);
- if (ATEOS() || !iswdigit(*v->now)) {
+ if (ATEOS() || !iscdigit(*v->now)) {
NOTE(REG_UBRACES);
NOTE(REG_UUNSPEC);
RETV(PLAIN, c);
} else {
NOTE(REG_UBOUNDS);
- INTO(L_EBND);
+ INTOCON(L_EBND);
RET('{');
}
+ assert(NOTREACHED);
+ break;
case CHR('('): /* parenthesis, or advanced extension */
if ((v->cflags&REG_ADVF) && NEXT1('?')) {
NOTE(REG_UNONPOSIX);
@@ -486,6 +512,7 @@ register struct vars *v;
switch (*v->now++) {
case CHR(':'): /* non-capturing paren */
RETV('(', 0);
+ break;
case CHR('#'): /* comment */
while (!ATEOS() && *v->now != CHR(')'))
v->now++;
@@ -493,28 +520,37 @@ register struct vars *v;
v->now++;
assert(v->nexttype == v->lasttype);
return next(v);
+ break;
case CHR('='): /* positive lookahead */
NOTE(REG_ULOOKAHEAD);
RETV(LACON, 1);
+ break;
case CHR('!'): /* negative lookahead */
NOTE(REG_ULOOKAHEAD);
RETV(LACON, 0);
+ break;
case CHR('<'): /* prefer short */
RETV(PREFER, 0);
+ break;
case CHR('>'): /* prefer long */
RETV(PREFER, 1);
+ break;
default:
FAILW(REG_BADRPT);
+ break;
}
+ assert(NOTREACHED);
}
- if (v->cflags&REG_NOSUB) {
- RETV('(', 0); /* all parens non-capturing */
- }
- RETV('(', 1);
+ if (v->cflags&REG_NOSUB)
+ RETV('(', 0); /* all parens non-capturing */
+ else
+ RETV('(', 1);
+ break;
case CHR(')'):
if (LASTTYPE('('))
NOTE(REG_UUNSPEC);
RETV(')', c);
+ break;
case CHR('['): /* easy except for [[:<:]] and [[:>:]] */
if (HAVE(6) && *(v->now+0) == CHR('[') &&
*(v->now+1) == CHR(':') &&
@@ -528,49 +564,55 @@ register struct vars *v;
NOTE(REG_UNONPOSIX);
RET((c == CHR('<')) ? '<' : '>');
}
- INTO(L_BRACK);
+ INTOCON(L_BRACK);
if (NEXT1('^')) {
v->now++;
RETV('[', 0);
}
RETV('[', 1);
+ break;
case CHR('.'):
RET('.');
+ break;
case CHR('^'):
RET('^');
+ break;
case CHR('$'):
RET('$');
+ break;
case CHR('\\'): /* mostly punt backslashes to code below */
if (ATEOS())
FAILW(REG_EESCAPE);
break;
default: /* ordinary character */
RETV(PLAIN, c);
+ break;
}
/* ERE backslash handling; backslash already eaten */
assert(!ATEOS());
if (!(v->cflags&REG_ADVF)) { /* only AREs have non-trivial escapes */
- if (iswalnum(*v->now)) {
+ if (iscalnum(*v->now)) {
NOTE(REG_UBSALNUM);
NOTE(REG_UUNSPEC);
}
RETV(PLAIN, *v->now++);
}
- (VOID) lexescape(v);
+ (DISCARD) lexescape(v);
if (ISERR())
FAILW(REG_EESCAPE);
if (v->nexttype == CCLASS) { /* fudge at lexical level */
switch (v->nextvalue) {
- case 'd': lexnest(v, backd); break;
- case 'D': lexnest(v, backD); break;
- case 's': lexnest(v, backs); break;
- case 'S': lexnest(v, backS); break;
- case 'w': lexnest(v, backw); break;
- case 'W': lexnest(v, backW); break;
+ case 'd': lexnest(v, backd, ENDOF(backd)); break;
+ case 'D': lexnest(v, backD, ENDOF(backD)); break;
+ case 's': lexnest(v, backs, ENDOF(backs)); break;
+ case 'S': lexnest(v, backS, ENDOF(backS)); break;
+ case 'w': lexnest(v, backw, ENDOF(backw)); break;
+ case 'W': lexnest(v, backW, ENDOF(backW)); break;
default:
assert(NOTREACHED);
FAILW(REG_ASSERT);
+ break;
}
/* lexnest done, back up and try again */
v->nexttype = v->lasttype;
@@ -591,10 +633,10 @@ struct vars *v;
{
chr c;
static chr alert[] = {
- CHR('a'), CHR('l'), CHR('e'), CHR('r'), CHR('t'), CHR('\0')
+ CHR('a'), CHR('l'), CHR('e'), CHR('r'), CHR('t')
};
static chr esc[] = {
- CHR('E'), CHR('S'), CHR('C'), CHR('\0')
+ CHR('E'), CHR('S'), CHR('C')
};
chr *save;
@@ -602,79 +644,102 @@ struct vars *v;
assert(!ATEOS());
c = *v->now++;
- if (!iswalnum(c))
+ if (!iscalnum(c))
RETV(PLAIN, c);
NOTE(REG_UNONPOSIX);
switch (c) {
case CHR('a'):
- RETV(PLAIN, chrnamed(v, alert, CHR('\007')));
+ RETV(PLAIN, chrnamed(v, alert, ENDOF(alert), CHR('\007')));
+ break;
case CHR('A'):
RETV(SBEGIN, 0);
+ break;
case CHR('b'):
RETV(PLAIN, CHR('\b'));
+ break;
+ case CHR('B'):
+ RETV(PLAIN, CHR('\\'));
+ break;
case CHR('c'):
NOTE(REG_UUNPORT);
if (ATEOS())
FAILW(REG_EESCAPE);
- RETV(PLAIN, (chr) (*v->now++ & 037));
+ RETV(PLAIN, (chr)(*v->now++ & 037));
+ break;
case CHR('d'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 'd');
+ break;
case CHR('D'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 'D');
+ break;
case CHR('e'):
NOTE(REG_UUNPORT);
- RETV(PLAIN, chrnamed(v, esc, CHR('\033')));
- case CHR('E'):
- RETV(PLAIN, CHR('\\'));
+ RETV(PLAIN, chrnamed(v, esc, ENDOF(esc), CHR('\033')));
+ break;
case CHR('f'):
RETV(PLAIN, CHR('\f'));
+ break;
case CHR('n'):
RETV(PLAIN, CHR('\n'));
+ break;
case CHR('r'):
RETV(PLAIN, CHR('\r'));
+ break;
case CHR('s'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 's');
+ break;
case CHR('S'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 'S');
+ break;
case CHR('t'):
RETV(PLAIN, CHR('\t'));
+ break;
case CHR('u'):
c = lexdigits(v, 16, 4, 4);
if (ISERR())
FAILW(REG_EESCAPE);
RETV(PLAIN, c);
+ break;
case CHR('U'):
c = lexdigits(v, 16, 8, 8);
if (ISERR())
FAILW(REG_EESCAPE);
RETV(PLAIN, c);
+ break;
case CHR('v'):
RETV(PLAIN, CHR('\v'));
+ break;
case CHR('w'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 'w');
+ break;
case CHR('W'):
NOTE(REG_ULOCALE);
RETV(CCLASS, 'W');
+ break;
case CHR('x'):
NOTE(REG_UUNPORT);
c = lexdigits(v, 16, 1, 255); /* REs >255 long outside spec */
if (ISERR())
FAILW(REG_EESCAPE);
RETV(PLAIN, c);
+ break;
case CHR('y'):
NOTE(REG_ULOCALE);
RETV(WBDRY, 0);
+ break;
case CHR('Y'):
NOTE(REG_ULOCALE);
RETV(NWBDRY, 0);
+ break;
case CHR('Z'):
RETV(SEND, 0);
+ break;
case CHR('1'): case CHR('2'): case CHR('3'): case CHR('4'):
case CHR('5'): case CHR('6'): case CHR('7'): case CHR('8'):
case CHR('9'):
@@ -686,7 +751,7 @@ struct vars *v;
/* ugly heuristic (first test is "exactly 1 digit?") */
if (v->now - save == 0 || (int)c <= v->nsubexp) {
NOTE(REG_UBACKREF);
- RETV(BACKREF, (chr) c);
+ RETV(BACKREF, (chr)c);
}
/* oops, doesn't look like it's a backref after all... */
v->now = save;
@@ -698,10 +763,13 @@ struct vars *v;
if (ISERR())
FAILW(REG_EESCAPE);
RETV(PLAIN, c);
+ break;
default:
- assert(iswalpha(c));
+ assert(iscalpha(c));
FAILW(REG_EESCAPE); /* unknown alphabetic escape */
+ break;
}
+ assert(NOTREACHED);
}
/*
@@ -715,7 +783,7 @@ int base;
int minlen;
int maxlen;
{
- uchr n; /* unsigned to aVOID overflow misbehavior */
+ uchr n; /* unsigned to avoid overflow misbehavior */
int len;
chr c;
int d;
@@ -764,16 +832,17 @@ int maxlen;
*/
static int /* 1 normal, 0 failure */
brenext(v, pc)
-register struct vars *v;
-register pchr pc;
+struct vars *v;
+pchr pc;
{
- register chr c = (chr) pc;
+ chr c = (chr)pc;
switch (c) {
case CHR('*'):
if (LASTTYPE(EMPTY) || LASTTYPE('(') || LASTTYPE('^'))
RETV(PLAIN, c);
RET('*');
+ break;
case CHR('['):
if (HAVE(6) && *(v->now+0) == CHR('[') &&
*(v->now+1) == CHR(':') &&
@@ -787,14 +856,16 @@ register pchr pc;
NOTE(REG_UNONPOSIX);
RET((c == CHR('<')) ? '<' : '>');
}
- INTO(L_BRACK);
+ INTOCON(L_BRACK);
if (NEXT1('^')) {
v->now++;
RETV('[', 0);
}
RETV('[', 1);
+ break;
case CHR('.'):
RET('.');
+ break;
case CHR('^'):
if (LASTTYPE(EMPTY))
RET('^');
@@ -803,6 +874,7 @@ register pchr pc;
RET('^');
}
RETV(PLAIN, c);
+ break;
case CHR('$'):
if (v->cflags&REG_EXPANDED)
skip(v);
@@ -813,10 +885,12 @@ register pchr pc;
RET('$');
}
RETV(PLAIN, c);
+ break;
case CHR('\\'):
break; /* see below */
default:
RETV(PLAIN, c);
+ break;
}
assert(c == CHR('\\'));
@@ -827,31 +901,40 @@ register pchr pc;
c = *v->now++;
switch (c) {
case CHR('{'):
- INTO(L_BBND);
+ INTOCON(L_BBND);
NOTE(REG_UBOUNDS);
RET('{');
+ break;
case CHR('('):
RETV('(', 1);
+ break;
case CHR(')'):
RETV(')', c);
+ break;
case CHR('<'):
NOTE(REG_UNONPOSIX);
RET('<');
+ break;
case CHR('>'):
NOTE(REG_UNONPOSIX);
RET('>');
+ break;
case CHR('1'): case CHR('2'): case CHR('3'): case CHR('4'):
case CHR('5'): case CHR('6'): case CHR('7'): case CHR('8'):
case CHR('9'):
NOTE(REG_UBACKREF);
- RETV(BACKREF, (chr) DIGITVAL(c));
+ RETV(BACKREF, (chr)DIGITVAL(c));
+ break;
default:
- if (iswalnum(c)) {
+ if (iscalnum(c)) {
NOTE(REG_UBSALNUM);
NOTE(REG_UUNSPEC);
}
RETV(PLAIN, c);
+ break;
}
+
+ assert(NOTREACHED);
}
/*
@@ -867,14 +950,14 @@ struct vars *v;
assert(v->cflags&REG_EXPANDED);
for (;;) {
- while (!ATEOS() && iswspace(*v->now))
+ while (!ATEOS() && iscspace(*v->now))
v->now++;
if (ATEOS() || *v->now != CHR('#'))
break; /* NOTE BREAK OUT */
assert(NEXT1('#'));
while (!ATEOS() && *v->now != CHR('\n'))
v->now++;
- /* leave the newline to be picked up by the iswspace loop */
+ /* leave the newline to be picked up by the iscspace loop */
}
if (v->now != start)
@@ -884,7 +967,7 @@ struct vars *v;
/*
- newline - return the chr for a newline
* This helps confine use of CHR to this source file.
- ^ static chr newline(VOID);
+ ^ static chr newline(NOPARMS);
*/
static chr
newline()
@@ -895,7 +978,7 @@ newline()
/*
- ch - return the chr sequence for locale.c's fake collating element ch
* This helps confine use of CHR to this source file.
- ^ static chr *ch(VOID);
+ ^ static chr *ch(NOPARMS);
*/
static chr *
ch()
@@ -909,12 +992,13 @@ ch()
- 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.
- ^ static chr chrnamed(struct vars *, chr *, pchr);
+ ^ static chr chrnamed(struct vars *, chr *, chr *, pchr);
*/
static chr
-chrnamed(v, name, lastresort)
+chrnamed(v, startp, endp, lastresort)
struct vars *v;
-chr *name;
+chr *startp; /* start of name */
+chr *endp; /* just past end of name */
pchr lastresort; /* what to return if name lookup fails */
{
celt c;
@@ -924,15 +1008,15 @@ pchr lastresort; /* what to return if name lookup fails */
errsave = v->err;
v->err = 0;
- c = element(v, name, name+wcslen(name));
+ c = element(v, startp, endp);
e = v->err;
v->err = errsave;
if (e != 0)
- return (chr) lastresort;
+ return (chr)lastresort;
cv = range(v, c, c, 0);
if (cv->nchrs == 0)
- return (chr) lastresort;
+ return (chr)lastresort;
return cv->chrs[0];
}
diff --git a/generic/regc_locale.c b/generic/regc_locale.c
new file mode 100644
index 0000000..769241f
--- /dev/null
+++ b/generic/regc_locale.c
@@ -0,0 +1,426 @@
+/*
+ * locale-specific stuff, including MCCE handling
+ * This file is #included by regcomp.c.
+ *
+ * No MCCEs for Tcl. The handling of character names and classes is
+ * still ASCII-centric, and needs to be extended to handle full Unicode.
+ */
+
+/* ASCII character-name table */
+static struct cname {
+ char *name;
+ char code;
+} cnames[] = {
+ {"NUL", '\0'},
+ {"SOH", '\001'},
+ {"STX", '\002'},
+ {"ETX", '\003'},
+ {"EOT", '\004'},
+ {"ENQ", '\005'},
+ {"ACK", '\006'},
+ {"BEL", '\007'},
+ {"alert", '\007'},
+ {"BS", '\010'},
+ {"backspace", '\b'},
+ {"HT", '\011'},
+ {"tab", '\t'},
+ {"LF", '\012'},
+ {"newline", '\n'},
+ {"VT", '\013'},
+ {"vertical-tab", '\v'},
+ {"FF", '\014'},
+ {"form-feed", '\f'},
+ {"CR", '\015'},
+ {"carriage-return", '\r'},
+ {"SO", '\016'},
+ {"SI", '\017'},
+ {"DLE", '\020'},
+ {"DC1", '\021'},
+ {"DC2", '\022'},
+ {"DC3", '\023'},
+ {"DC4", '\024'},
+ {"NAK", '\025'},
+ {"SYN", '\026'},
+ {"ETB", '\027'},
+ {"CAN", '\030'},
+ {"EM", '\031'},
+ {"SUB", '\032'},
+ {"ESC", '\033'},
+ {"IS4", '\034'},
+ {"FS", '\034'},
+ {"IS3", '\035'},
+ {"GS", '\035'},
+ {"IS2", '\036'},
+ {"RS", '\036'},
+ {"IS1", '\037'},
+ {"US", '\037'},
+ {"space", ' '},
+ {"exclamation-mark", '!'},
+ {"quotation-mark", '"'},
+ {"number-sign", '#'},
+ {"dollar-sign", '$'},
+ {"percent-sign", '%'},
+ {"ampersand", '&'},
+ {"apostrophe", '\''},
+ {"left-parenthesis", '('},
+ {"right-parenthesis", ')'},
+ {"asterisk", '*'},
+ {"plus-sign", '+'},
+ {"comma", ','},
+ {"hyphen", '-'},
+ {"hyphen-minus", '-'},
+ {"period", '.'},
+ {"full-stop", '.'},
+ {"slash", '/'},
+ {"solidus", '/'},
+ {"zero", '0'},
+ {"one", '1'},
+ {"two", '2'},
+ {"three", '3'},
+ {"four", '4'},
+ {"five", '5'},
+ {"six", '6'},
+ {"seven", '7'},
+ {"eight", '8'},
+ {"nine", '9'},
+ {"colon", ':'},
+ {"semicolon", ';'},
+ {"less-than-sign", '<'},
+ {"equals-sign", '='},
+ {"greater-than-sign", '>'},
+ {"question-mark", '?'},
+ {"commercial-at", '@'},
+ {"left-square-bracket", '['},
+ {"backslash", '\\'},
+ {"reverse-solidus", '\\'},
+ {"right-square-bracket", ']'},
+ {"circumflex", '^'},
+ {"circumflex-accent", '^'},
+ {"underscore", '_'},
+ {"low-line", '_'},
+ {"grave-accent", '`'},
+ {"left-brace", '{'},
+ {"left-curly-bracket", '{'},
+ {"vertical-line", '|'},
+ {"right-brace", '}'},
+ {"right-curly-bracket", '}'},
+ {"tilde", '~'},
+ {"DEL", '\177'},
+ {NULL, 0}
+};
+
+/* ASCII character-class table */
+static struct cclass {
+ char *name;
+ char *chars;
+ int hasch;
+} cclasses[] = {
+ {"alnum", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
+0123456789", 1},
+ {"alpha", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz",
+ 1},
+ {"blank", " \t", 0},
+ {"cntrl", "\007\b\t\n\v\f\r\1\2\3\4\5\6\16\17\20\21\22\23\24\
+\25\26\27\30\31\32\33\34\35\36\37\177", 0},
+ {"digit", "0123456789", 0},
+ {"graph", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
+0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
+ 1},
+ {"lower", "abcdefghijklmnopqrstuvwxyz",
+ 1},
+ {"print", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\
+0123456789!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~ ",
+ 1},
+ {"punct", "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~",
+ 0},
+ {"space", "\t\n\v\f\r ", 0},
+ {"upper", "ABCDEFGHIJKLMNOPQRSTUVWXYZ",
+ 0},
+ {"xdigit", "0123456789ABCDEFabcdef",
+ 0},
+ {NULL, 0, 0}
+};
+
+#define CH NOCELT
+
+/*
+ - nmcces - how many distinct MCCEs are there?
+ ^ static int nmcces(struct vars *);
+ */
+static int
+nmcces(v)
+struct vars *v;
+{
+ return 0;
+}
+
+/*
+ - nleaders - how many chrs can be first chrs of MCCEs?
+ ^ static int nleaders(struct vars *);
+ */
+static int
+nleaders(v)
+struct vars *v;
+{
+ return 0;
+}
+
+/*
+ - allmcces - return a cvec with all the MCCEs of the locale
+ ^ static struct cvec *allmcces(struct vars *, struct cvec *);
+ */
+static struct cvec *
+allmcces(v, cv)
+struct vars *v;
+struct cvec *cv; /* this is supposed to have enough room */
+{
+ return clearcvec(cv);
+}
+
+/*
+ - element - map collating-element name to celt
+ ^ static celt element(struct vars *, chr *, chr *);
+ */
+static celt
+element(v, startp, endp)
+struct vars *v;
+chr *startp; /* points to start of name */
+chr *endp; /* points just past end of name */
+{
+ struct cname *cn;
+ size_t len;
+ Tcl_DString ds;
+ char *np;
+
+ /* generic: one-chr names stand for themselves */
+ assert(startp < endp);
+ len = endp - startp;
+ if (len == 1)
+ return *startp;
+
+ NOTE(REG_ULOCALE);
+
+ /* search table */
+ Tcl_DStringInit(&ds);
+ np = TclUniCharToUtfDString(startp, (int)len, &ds);
+ for (cn = cnames; cn->name != NULL; cn++)
+ if (strlen(cn->name) == len && strncmp(cn->name, np, len) == 0)
+ break; /* NOTE BREAK OUT */
+ Tcl_DStringFree(&ds);
+ if (cn->name != NULL)
+ return CHR(cn->code);
+
+ /* couldn't find it */
+ ERR(REG_ECOLLATE);
+ return 0;
+}
+
+/*
+ - range - supply cvec for a range, including legality check
+ ^ static struct cvec *range(struct vars *, celt, celt, int);
+ */
+static struct cvec *
+range(v, a, b, cases)
+struct vars *v;
+celt a;
+celt b; /* might equal a */
+int cases; /* case-independent? */
+{
+ int nchrs;
+ struct cvec *cv;
+ celt c, lc, uc, tc;
+
+ if (a != b && !before(a, b)) {
+ ERR(REG_ERANGE);
+ return NULL;
+ }
+
+ nchrs = b - a + 1;
+ if (cases)
+ nchrs *= 2;
+ cv = getcvec(v, nchrs, 0);
+ NOERRN();
+
+ for (c = a; c <= b; c++) {
+ addchr(cv, c);
+ if (cases) {
+ lc = Tcl_UniCharToLower((chr)c);
+ uc = Tcl_UniCharToUpper((chr)c);
+ tc = Tcl_UniCharToTitle((chr)c);
+ if (c != lc) {
+ addchr(cv, lc);
+ }
+ if (c != uc) {
+ addchr(cv, uc);
+ }
+ if (c != tc && tc != uc) {
+ addchr(cv, tc);
+ }
+ }
+ }
+
+ return cv;
+}
+
+/*
+ - before - is celt x before celt y, for purposes of range legality?
+ ^ static int before(celt, celt);
+ */
+static int /* predicate */
+before(x, y)
+celt x;
+celt y;
+{
+ /* trivial because no MCCEs */
+ if (x < y)
+ return 1;
+ return 0;
+}
+
+/*
+ - eclass - supply cvec for an equivalence class
+ * Must include case counterparts on request.
+ ^ static struct cvec *eclass(struct vars *, celt, int);
+ */
+static struct cvec *
+eclass(v, c, cases)
+struct vars *v;
+celt c;
+int cases; /* all cases? */
+{
+ struct cvec *cv;
+
+ /* crude fake equivalence class for testing */
+ if ((v->cflags&REG_FAKEEC) && c == 'x') {
+ cv = getcvec(v, 4, 0);
+ addchr(cv, (chr)'x');
+ addchr(cv, (chr)'y');
+ if (cases) {
+ addchr(cv, (chr)'X');
+ addchr(cv, (chr)'Y');
+ }
+ return cv;
+ }
+
+ /* otherwise, none */
+ if (cases)
+ return allcases(v, c);
+ cv = getcvec(v, 1, 0);
+ assert(cv != NULL);
+ addchr(cv, (chr)c);
+ return cv;
+}
+
+/*
+ - cclass - supply cvec for a character class
+ * Must include case counterparts on request.
+ ^ static struct cvec *cclass(struct vars *, chr *, chr *, int);
+ */
+static struct cvec *
+cclass(v, startp, endp, cases)
+struct vars *v;
+chr *startp; /* where the name starts */
+chr *endp; /* just past the end of the name */
+int cases; /* case-independent? */
+{
+ size_t len;
+ char *p;
+ struct cclass *cc;
+ struct cvec *cv;
+ Tcl_DString ds;
+ char *np;
+
+ /* find the name */
+ len = endp - startp;
+ Tcl_DStringInit(&ds);
+ np = TclUniCharToUtfDString(startp, (int)len, &ds);
+ if (cases && len == 5 && (strncmp("lower", np, 5) == 0 ||
+ strncmp("upper", np, 5) == 0))
+ np = "alpha";
+ for (cc = cclasses; cc->name != NULL; cc++)
+ if (strlen(cc->name) == len && strncmp(cc->name, np, len) == 0)
+ break; /* NOTE BREAK OUT */
+ Tcl_DStringFree(&ds);
+ if (cc->name == NULL) {
+ ERR(REG_ECTYPE);
+ return NULL;
+ }
+
+ /* set up vector */
+ cv = getcvec(v, (int)strlen(cc->chars), 0);
+ if (cv == NULL) {
+ ERR(REG_ESPACE);
+ return NULL;
+ }
+
+ /* fill it in */
+ for (p = cc->chars; *p != '\0'; p++)
+ addchr(cv, (chr)*p);
+
+ return cv;
+}
+
+/*
+ - allcases - supply cvec for all case counterparts of a chr (including itself)
+ * This is a shortcut, preferably an efficient one, for simple characters;
+ * messy cases are done via range().
+ ^ static struct cvec *allcases(struct vars *, pchr);
+ */
+static struct cvec *
+allcases(v, pc)
+struct vars *v;
+pchr pc;
+{
+ struct cvec *cv = getcvec(v, 2, 0);
+ chr c = (chr)pc;
+
+ assert(cv != NULL);
+ addchr(cv, c);
+ if (TclUniCharIsUpper(c))
+ addchr(cv, Tcl_UniCharToLower(c));
+ else if (TclUniCharIsLower(c))
+ addchr(cv, Tcl_UniCharToUpper(c));
+
+ return cv;
+}
+
+/*
+ - cmp - chr-substring compare
+ * Backrefs need this. It should preferably be efficient.
+ * Note that it does not need to report anything except equal/unequal.
+ * Note also that the length is exact, and the comparison should not
+ * stop at embedded NULs!
+ ^ static int cmp(CONST chr *, CONST chr *, size_t);
+ */
+static int /* 0 for equal, nonzero for unequal */
+cmp(x, y, len)
+CONST chr *x;
+CONST chr *y;
+size_t len; /* exact length of comparison */
+{
+ return memcmp(VS(x), VS(y), len*sizeof(chr));
+}
+
+/*
+ - casecmp - case-independent chr-substring compare
+ * REG_ICASE backrefs need this. It should preferably be efficient.
+ * Note that it does not need to report anything except equal/unequal.
+ * Note also that the length is exact, and the comparison should not
+ * stop at embedded NULs!
+ ^ static int casecmp(CONST chr *, CONST chr *, size_t);
+ */
+static int /* 0 for equal, nonzero for unequal */
+casecmp(x, y, len)
+CONST chr *x;
+CONST chr *y;
+size_t len; /* exact length of comparison */
+{
+ size_t i;
+ CONST chr *xp;
+ CONST chr *yp;
+
+ for (xp = x, yp = y, i = len; i > 0; i--)
+ if (Tcl_UniCharToLower(*xp++) != Tcl_UniCharToLower(*yp++))
+ return 1;
+ return 0;
+}
diff --git a/generic/nfa.c b/generic/regc_nfa.c
index f6b8967..14ee077 100644
--- a/generic/nfa.c
+++ b/generic/regc_nfa.c
@@ -1,57 +1,29 @@
/*
- * nfa.c --
+ * NFA utilities.
+ * This file is #included by regcomp.c.
*
- * Regexp package file:
- * NFA utilities. One or two things that technically ought to be
- * in here are actually in color.c, thanks to some incestuous
- * relationships in the color chains.
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: nfa.c,v 1.1.2.2 1998/10/03 01:56:41 stanton Exp $
+ * One or two things that technically ought to be in here
+ * are actually in color.c, thanks to some incestuous relationships in
+ * the color chains.
*/
#define NISERR() VISERR(nfa->v)
+#define NERR(e) VERR(nfa->v, (e))
/*
- newnfa - set up an NFA
- * Caution: colormap must be set up already.
- ^ static struct nfa *newnfa(struct vars *, struct nfa *);
+ ^ static struct nfa *newnfa(struct vars *, struct colormap *, struct nfa *);
*/
static struct nfa * /* the NFA, or NULL */
-newnfa(v, parent)
+newnfa(v, cm, parent)
struct vars *v;
+struct colormap *cm;
struct nfa *parent; /* NULL if primary NFA */
{
struct nfa *nfa;
- nfa = (struct nfa *)ckalloc(sizeof(struct nfa));
+ nfa = (struct nfa *)MALLOC(sizeof(struct nfa));
if (nfa == NULL)
return NULL;
@@ -59,6 +31,7 @@ struct nfa *parent; /* NULL if primary NFA */
nfa->slast = NULL;
nfa->free = NULL;
nfa->nstates = 0;
+ nfa->cm = cm;
nfa->v = v;
nfa->bos[0] = nfa->bos[1] = COLORLESS;
nfa->eos[0] = nfa->eos[1] = COLORLESS;
@@ -72,10 +45,10 @@ struct nfa *parent; /* NULL if primary NFA */
freenfa(nfa);
return NULL;
}
- rainbow(nfa, nfa->v->cm, PLAIN, COLORLESS, nfa->pre, nfa->init);
+ rainbow(nfa, nfa->cm, PLAIN, COLORLESS, nfa->pre, nfa->init);
newarc(nfa, '^', 1, nfa->pre, nfa->init);
newarc(nfa, '^', 0, nfa->pre, nfa->init);
- rainbow(nfa, nfa->v->cm, PLAIN, COLORLESS, nfa->final, nfa->post);
+ rainbow(nfa, nfa->cm, PLAIN, COLORLESS, nfa->final, nfa->post);
newarc(nfa, '$', 1, nfa->final, nfa->post);
newarc(nfa, '$', 0, nfa->final, nfa->post);
@@ -109,7 +82,7 @@ struct nfa *nfa;
nfa->nstates = -1;
nfa->pre = NULL;
nfa->post = NULL;
- ckfree((char *)nfa);
+ FREE(nfa);
}
/*
@@ -128,14 +101,11 @@ int flag;
s = nfa->free;
nfa->free = s->next;
} else {
- s = (struct state *)ckalloc(sizeof(struct state));
+ s = (struct state *)MALLOC(sizeof(struct state));
if (s == NULL) {
- VERR(nfa->v, REG_ESPACE);
+ NERR(REG_ESPACE);
return NULL;
}
-
- /* memleak (CCS). */
-
s->oas.next = NULL;
s->free = &s->oas.a[0];
for (i = 0; i < ABSIZE; i++) {
@@ -240,12 +210,12 @@ struct state *s;
assert(s->no == FREESTATE);
for (ab = s->oas.next; ab != NULL; ab = abnext) {
abnext = ab->next;
- ckfree((char *)ab);
+ FREE(ab);
}
s->ins = NULL;
s->outs = NULL;
s->next = NULL;
- ckfree((char *)s);
+ FREE(s);
}
/*
@@ -276,7 +246,7 @@ struct state *to;
assert(a != NULL);
a->type = t;
- a->co = (color) co;
+ a->co = (color)co;
a->to = to;
a->from = from;
@@ -295,7 +265,7 @@ struct state *to;
to->nins++;
if (COLORED(a) && nfa->parent == NULL)
- colorchain(nfa->v->cm, a);
+ colorchain(nfa->cm, a);
return;
}
@@ -315,9 +285,9 @@ struct state *s;
/* if none at hand, get more */
if (s->free == NULL) {
- new = (struct arcbatch *)ckalloc(sizeof(struct arcbatch));
+ new = (struct arcbatch *)MALLOC(sizeof(struct arcbatch));
if (new == NULL) {
- VERR(nfa->v, REG_ESPACE);
+ NERR(REG_ESPACE);
return NULL;
}
new->next = s->oas.next;
@@ -354,7 +324,7 @@ struct arc *victim;
/* take it off color chain if necessary */
if (COLORED(victim) && nfa->parent == NULL)
- uncolorchain(nfa->v->cm, victim);
+ uncolorchain(nfa->cm, victim);
/* take it off source's out-chain */
assert(from != NULL);
@@ -680,10 +650,10 @@ struct nfa *nfa;
{
/* false colors for BOS, BOL, EOS, EOL */
if (nfa->parent == NULL) {
- nfa->bos[0] = pseudocolor(nfa->v->cm);
- nfa->bos[1] = pseudocolor(nfa->v->cm);
- nfa->eos[0] = pseudocolor(nfa->v->cm);
- nfa->eos[1] = pseudocolor(nfa->v->cm);
+ nfa->bos[0] = pseudocolor(nfa->cm);
+ nfa->bos[1] = pseudocolor(nfa->cm);
+ nfa->eos[0] = pseudocolor(nfa->cm);
+ nfa->eos[1] = pseudocolor(nfa->cm);
} else {
assert(nfa->parent->bos[0] != COLORLESS);
nfa->bos[0] = nfa->parent->bos[0];
@@ -698,42 +668,41 @@ struct nfa *nfa;
/*
- optimize - optimize an NFA
- ^ static VOID optimize(struct nfa *);
+ ^ static int optimize(struct nfa *, FILE *);
*/
-static VOID
-optimize(nfa)
+static int /* re_info bits */
+optimize(nfa, f)
struct nfa *nfa;
+FILE *f; /* for debug output; NULL none */
{
- int verbose = (nfa->v->cflags&REG_PROGRESS) ? 1 : 0;
- int info;
+ int verbose = (f != NULL) ? 1 : 0;
if (verbose)
- printf("\ninitial cleanup:\n");
+ fprintf(f, "\ninitial cleanup:\n");
cleanup(nfa); /* may simplify situation */
- if (nfa->v->cflags&REG_PROGRESS)
- dumpnfa(nfa, stdout);
if (verbose)
- printf("\nempties:\n");
- fixempties(nfa); /* get rid of EMPTY arcs */
+ dumpnfa(nfa, f);
+ if (verbose)
+ fprintf(f, "\nempties:\n");
+ fixempties(nfa, f); /* get rid of EMPTY arcs */
if (verbose)
- printf("\nconstraints:\n");
- pullback(nfa); /* pull back constraints backward */
- pushfwd(nfa); /* push fwd constraints forward */
+ fprintf(f, "\nconstraints:\n");
+ pullback(nfa, f); /* pull back constraints backward */
+ pushfwd(nfa, f); /* push fwd constraints forward */
if (verbose)
- printf("\nfinal cleanup:\n");
+ fprintf(f, "\nfinal cleanup:\n");
cleanup(nfa); /* final tidying */
- info = analyze(nfa->v, nfa); /* and analysis */
- if (nfa->parent == NULL)
- nfa->v->re->re_info |= info;
+ return analyze(nfa); /* and analysis */
}
/*
- pullback - pull back constraints backward to (with luck) eliminate them
- ^ static VOID pullback(struct nfa *);
+ ^ static VOID pullback(struct nfa *, FILE *);
*/
static VOID
-pullback(nfa)
+pullback(nfa, f)
struct nfa *nfa;
+FILE *f; /* for debug output; NULL none */
{
struct state *s;
struct state *nexts;
@@ -754,8 +723,8 @@ struct nfa *nfa;
assert(nexta == NULL || s->no != FREESTATE);
}
}
- if (progress && (nfa->v->cflags&REG_PROGRESS))
- dumpnfa(nfa, stdout);
+ if (progress && f != NULL)
+ dumpnfa(nfa, f);
} while (progress && !NISERR());
if (NISERR())
return;
@@ -799,7 +768,7 @@ struct arc *con;
return 1;
}
- /* first, clone from state if necessary to aVOID other outarcs */
+ /* first, clone from state if necessary to avoid other outarcs */
if (from->nouts > 1) {
s = newstate(nfa);
if (NISERR())
@@ -846,11 +815,12 @@ struct arc *con;
/*
- pushfwd - push forward constraints forward to (with luck) eliminate them
- ^ static VOID pushfwd(struct nfa *);
+ ^ static VOID pushfwd(struct nfa *, FILE *);
*/
static VOID
-pushfwd(nfa)
+pushfwd(nfa, f)
struct nfa *nfa;
+FILE *f; /* for debug output; NULL none */
{
struct state *s;
struct state *nexts;
@@ -871,8 +841,8 @@ struct nfa *nfa;
assert(nexta == NULL || s->no != FREESTATE);
}
}
- if (progress && (nfa->v->cflags&REG_PROGRESS))
- dumpnfa(nfa, stdout);
+ if (progress && f != NULL)
+ dumpnfa(nfa, f);
} while (progress && !NISERR());
if (NISERR())
return;
@@ -916,7 +886,7 @@ struct arc *con;
return 1;
}
- /* first, clone to state if necessary to aVOID other inarcs */
+ /* first, clone to state if necessary to avoid other inarcs */
if (to->nins > 1) {
s = newstate(nfa);
if (NISERR())
@@ -978,11 +948,13 @@ struct arc *a;
case CA('^', PLAIN): /* newlines are handled separately */
case CA('$', PLAIN):
return INCOMPATIBLE;
+ break;
case CA(AHEAD, PLAIN): /* color constraints meet colors */
case CA(BEHIND, PLAIN):
if (con->co == a->co)
return SATISFIED;
return INCOMPATIBLE;
+ break;
case CA('^', '^'): /* collision, similar constraints */
case CA('$', '$'):
case CA(AHEAD, AHEAD):
@@ -990,11 +962,13 @@ struct arc *a;
if (con->co == a->co) /* true duplication */
return SATISFIED;
return INCOMPATIBLE;
+ break;
case CA('^', BEHIND): /* collision, dissimilar constraints */
case CA(BEHIND, '^'):
case CA('$', AHEAD):
case CA(AHEAD, '$'):
return INCOMPATIBLE;
+ break;
case CA('^', '$'): /* constraints passing each other */
case CA('^', AHEAD):
case CA(BEHIND, '$'):
@@ -1008,18 +982,20 @@ struct arc *a;
case CA('$', LACON):
case CA(AHEAD, LACON):
return COMPATIBLE;
+ break;
}
assert(NOTREACHED);
- return INCOMPATIBLE; /* keep compiler from complaining */
+ return INCOMPATIBLE; /* for benefit of blind compilers */
}
/*
- fixempties - get rid of EMPTY arcs
- ^ static VOID fixempties(struct nfa *);
+ ^ static VOID fixempties(struct nfa *, FILE *);
*/
static VOID
-fixempties(nfa)
+fixempties(nfa, f)
struct nfa *nfa;
+FILE *f; /* for debug output; NULL none */
{
struct state *s;
struct state *nexts;
@@ -1039,8 +1015,8 @@ struct nfa *nfa;
assert(nexta == NULL || s->no != FREESTATE);
}
}
- if (progress && (nfa->v->cflags&REG_PROGRESS))
- dumpnfa(nfa, stdout);
+ if (progress && f != NULL)
+ dumpnfa(nfa, f);
} while (progress && !NISERR());
}
@@ -1176,11 +1152,10 @@ struct state *mark; /* the value to mark with */
/*
- analyze - ascertain potentially-useful facts about an optimized NFA
- ^ static int analyze(struct vars *, struct nfa *);
+ ^ static int analyze(struct nfa *);
*/
static int /* re_info bits to be ORed in */
-analyze(v, nfa)
-struct vars *v;
+analyze(nfa)
struct nfa *nfa;
{
struct arc *a;
@@ -1219,11 +1194,10 @@ struct state *end;
/*
- compact - compact an NFA
- ^ static VOID compact(struct vars *, struct nfa *, struct cnfa *);
+ ^ static VOID compact(struct nfa *, struct cnfa *);
*/
static VOID
-compact(v, nfa, cnfa)
-struct vars *v;
+compact(nfa, cnfa)
struct nfa *nfa;
struct cnfa *cnfa;
{
@@ -1234,7 +1208,7 @@ struct cnfa *cnfa;
struct carc *ca;
struct carc *first;
- assert (!ISERR());
+ assert (!NISERR());
nstates = 0;
narcs = 0;
@@ -1243,14 +1217,14 @@ struct cnfa *cnfa;
narcs += s->nouts + 1;
}
- cnfa->states = (struct carc **)ckalloc(nstates * sizeof(struct carc *));
- cnfa->arcs = (struct carc *)ckalloc(narcs * sizeof(struct carc));
+ 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->states != NULL)
- ckfree((char *)cnfa->states);
+ FREE(cnfa->states);
if (cnfa->arcs != NULL)
- ckfree((char *)cnfa->arcs);
- ERR(REG_ESPACE);
+ FREE(cnfa->arcs);
+ NERR(REG_ESPACE);
return;
}
cnfa->nstates = nstates;
@@ -1260,13 +1234,12 @@ struct cnfa *cnfa;
cnfa->bos[1] = nfa->bos[1];
cnfa->eos[0] = nfa->eos[0];
cnfa->eos[1] = nfa->eos[1];
- cnfa->ncolors = maxcolor(v->cm) + 1;
- cnfa->haslacons = 0;
- cnfa->leftanch = 1; /* tentatively */
+ cnfa->ncolors = maxcolor(nfa->cm) + 1;
+ cnfa->flags = LEFTANCH; /* tentatively */
ca = cnfa->arcs;
for (s = nfa->states; s != NULL; s = s->next) {
- assert((size_t) s->no < nstates);
+ assert((size_t)s->no < nstates);
cnfa->states[s->no] = ca;
first = ca;
for (a = s->outs; a != NULL; a = a->outchain)
@@ -1278,10 +1251,10 @@ struct cnfa *cnfa;
break;
case LACON:
assert(s->no != cnfa->pre);
- ca->co = (color) (a->co + cnfa->ncolors);
+ ca->co = (color)(cnfa->ncolors + a->co);
ca->to = a->to->no;
ca++;
- cnfa->haslacons = 1;
+ cnfa->flags |= HASLACONS;
break;
default:
assert(NOTREACHED);
@@ -1297,9 +1270,9 @@ struct cnfa *cnfa;
for (a = nfa->pre->outs; a != NULL; a = a->outchain)
if (a->type == PLAIN && a->co != nfa->bos[0] &&
- a->co != nfa->bos[1])
- cnfa->leftanch = 0;
- }
+ a->co != nfa->bos[1])
+ cnfa->flags &= ~LEFTANCH;
+}
/*
- carcsort - sort compacted-NFA arcs by color
@@ -1341,11 +1314,12 @@ int dynalloc; /* is the cnfa struct itself dynamic? */
{
assert(cnfa->nstates != 0); /* not empty already */
cnfa->nstates = 0;
- ckfree((char *)cnfa->states);
- ckfree((char *)cnfa->arcs);
+ FREE(cnfa->states);
+ FREE(cnfa->arcs);
if (dynalloc)
- ckfree((char *)cnfa);
+ FREE(cnfa);
}
+
/*
- dumpnfa - dump an NFA in human-readable form
^ static VOID dumpnfa(struct nfa *, FILE *);
@@ -1355,7 +1329,159 @@ dumpnfa(nfa, f)
struct nfa *nfa;
FILE *f;
{
+#ifdef REG_DEBUG
+ struct state *s;
+
+ fprintf(f, "pre %d, post %d", nfa->pre->no, nfa->post->no);
+ if (nfa->bos[0] != COLORLESS)
+ fprintf(f, ", bos [%ld]", (long)nfa->bos[0]);
+ if (nfa->bos[1] != COLORLESS)
+ fprintf(f, ", bol [%ld]", (long)nfa->bos[1]);
+ if (nfa->eos[0] != COLORLESS)
+ fprintf(f, ", eos [%ld]", (long)nfa->eos[0]);
+ if (nfa->eos[1] != COLORLESS)
+ fprintf(f, ", eol [%ld]", (long)nfa->eos[1]);
+ fprintf(f, "\n");
+ for (s = nfa->states; s != NULL; s = s->next)
+ dumpstate(s, f);
+ if (nfa->parent == NULL)
+ dumpcolors(nfa->cm, f);
+ fflush(f);
+#endif
}
+
+#ifdef REG_DEBUG /* subordinates of dumpnfa */
+
+/*
+ - dumpstate - dump an NFA state in human-readable form
+ ^ static VOID dumpstate(struct state *, FILE *);
+ */
+static VOID
+dumpstate(s, f)
+struct state *s;
+FILE *f;
+{
+ struct arc *a;
+
+ fprintf(f, "%d%s%c", s->no, (s->tmp != NULL) ? "T" : "",
+ (s->flag) ? s->flag : '.');
+ if (s->prev != NULL && s->prev->next != s)
+ fprintf(f, "\tstate chain bad\n");
+ if (s->nouts == 0)
+ fprintf(f, "\tno out arcs\n");
+ else
+ dumparcs(s, f);
+ fflush(f);
+ for (a = s->ins; a != NULL; a = a->inchain) {
+ if (a->to != s)
+ fprintf(f, "\tlink from %d to %d on %d's in-chain\n",
+ a->from->no, a->to->no, s->no);
+ }
+}
+
+/*
+ - dumparcs - dump out-arcs in human-readable form
+ ^ static VOID dumparcs(struct state *, FILE *);
+ */
+static VOID
+dumparcs(s, f)
+struct state *s;
+FILE *f;
+{
+ int pos;
+
+ 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(a, s, f, pos)
+struct arc *a;
+struct state *s;
+FILE *f;
+int pos; /* initial print position */
+{
+ if (a->outchain != NULL)
+ pos = dumprarcs(a->outchain, s, f, pos);
+ dumparc(a, s, f);
+ if (pos == 5) {
+ fprintf(f, "\n");
+ pos = 1;
+ } else
+ pos++;
+ return pos;
+}
+
+/*
+ - dumparc - dump one outarc in readable form, including prefixing tab
+ ^ static VOID dumparc(struct arc *, struct state *, FILE *);
+ */
+static VOID
+dumparc(a, s, f)
+struct arc *a;
+struct state *s;
+FILE *f;
+{
+ struct arc *aa;
+ struct arcbatch *ab;
+
+ fprintf(f, "\t");
+ switch (a->type) {
+ case PLAIN:
+ fprintf(f, "[%ld]", (long)a->co);
+ break;
+ case AHEAD:
+ fprintf(f, ">%ld>", (long)a->co);
+ break;
+ case BEHIND:
+ fprintf(f, "<%ld<", (long)a->co);
+ break;
+ case LACON:
+ fprintf(f, ":%ld:", (long)a->co);
+ break;
+ case '^':
+ case '$':
+ fprintf(f, "%c%d", a->type, (int)a->co);
+ break;
+ case EMPTY:
+ break;
+ default:
+ fprintf(f, "0x%x/0%lo", a->type, (long)a->co);
+ break;
+ }
+ if (a->from != s)
+ fprintf(f, "?%d?", a->from->no);
+ for (ab = &a->from->oas; ab != NULL; ab = ab->next) {
+ for (aa = &ab->a[0]; aa < &ab->a[ABSIZE]; aa++)
+ if (aa == a)
+ break; /* NOTE BREAK OUT */
+ if (aa < &ab->a[ABSIZE]) /* propagate break */
+ break; /* NOTE BREAK OUT */
+ }
+ if (ab == NULL)
+ fprintf(f, "?!?"); /* not in allocated space */
+ fprintf(f, "->");
+ if (a->to == NULL) {
+ fprintf(f, "NULL");
+ return;
+ }
+ fprintf(f, "%d", a->to->no);
+ for (aa = a->to->ins; aa != NULL; aa = aa->inchain)
+ if (aa == a)
+ break; /* NOTE BREAK OUT */
+ if (aa == NULL)
+ fprintf(f, "?!?"); /* missing from in-chain */
+}
+
+#endif /* ifdef REG_DEBUG */
+
/*
- dumpcnfa - dump a compacted NFA in human-readable form
^ static VOID dumpcnfa(struct cnfa *, FILE *);
@@ -1365,4 +1491,62 @@ dumpcnfa(cnfa, f)
struct cnfa *cnfa;
FILE *f;
{
+#ifdef REG_DEBUG
+ int st;
+
+ fprintf(f, "pre %d, post %d", cnfa->pre, cnfa->post);
+ if (cnfa->bos[0] != COLORLESS)
+ fprintf(f, ", bos [%ld]", (long)cnfa->bos[0]);
+ if (cnfa->bos[1] != COLORLESS)
+ fprintf(f, ", bol [%ld]", (long)cnfa->bos[1]);
+ if (cnfa->eos[0] != COLORLESS)
+ fprintf(f, ", eos [%ld]", (long)cnfa->eos[0]);
+ if (cnfa->eos[1] != COLORLESS)
+ fprintf(f, ", eol [%ld]", (long)cnfa->eos[1]);
+ if (cnfa->flags&HASLACONS)
+ fprintf(f, ", haslacons");
+ if (cnfa->flags&LEFTANCH)
+ fprintf(f, ", leftanch");
+ fprintf(f, "\n");
+ for (st = 0; st < cnfa->nstates; st++)
+ dumpcstate(st, cnfa->states[st], cnfa, f);
+ fflush(f);
+#endif
}
+
+#ifdef REG_DEBUG /* subordinates of dumpcnfa */
+
+/*
+ - dumpcstate - dump a compacted-NFA state in human-readable form
+ ^ static VOID dumpcstate(int, struct carc *, struct cnfa *, FILE *);
+ */
+static VOID
+dumpcstate(st, ca, cnfa, f)
+int st;
+struct carc *ca;
+struct cnfa *cnfa;
+FILE *f;
+{
+ int i;
+ int pos;
+
+ fprintf(f, "%d.", st);
+ pos = 1;
+ for (i = 0; ca[i].co != COLORLESS; i++) {
+ if (ca[i].co < cnfa->ncolors)
+ fprintf(f, "\t[%ld]->%d", (long)ca[i].co, ca[i].to);
+ else
+ fprintf(f, "\t:%ld:->%d", (long)ca[i].co-cnfa->ncolors,
+ ca[i].to);
+ if (pos == 5) {
+ fprintf(f, "\n");
+ pos = 1;
+ } else
+ pos++;
+ }
+ if (i == 0 || pos != 1)
+ fprintf(f, "\n");
+ fflush(f);
+}
+
+#endif /* ifdef REG_DEBUG */
diff --git a/generic/compile.c b/generic/regcomp.c
index ee12d04..2a13172 100644
--- a/generic/compile.c
+++ b/generic/regcomp.c
@@ -1,51 +1,16 @@
/*
- * compile.c --
- *
- * Regexp package file: re_*comp and friends - compile REs
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: compile.c,v 1.1.2.2 1998/10/03 01:56:40 stanton Exp $
+ * re_*comp and friends - compile REs
+ * This file #includes several others (see the bottom).
*/
-#include "tclInt.h"
-#include <assert.h>
-#include "tclPort.h"
-#include "tclRegexp.h"
-#include "chr.h"
-#include "guts.h"
+#include "regguts.h"
/*
* forward declarations, up here so forward datatypes etc. are defined early
*/
/* =====^!^===== begin forwards =====^!^===== */
/* automatically gathered by fwd; do not hand-edit */
-/* === compile.c === */
+/* === regcomp.c === */
int compile _ANSI_ARGS_((regex_t *, CONST chr *, size_t, int));
static VOID moresubs _ANSI_ARGS_((struct vars *, int));
static int freev _ANSI_ARGS_((struct vars *, int));
@@ -63,53 +28,34 @@ static color nlcolor _ANSI_ARGS_((struct vars *));
static VOID wordchrs _ANSI_ARGS_((struct vars *));
static struct subre subre _ANSI_ARGS_((struct state *, struct state *, int, int, struct rtree *));
static struct rtree *newrt _ANSI_ARGS_((struct vars *));
-static VOID freert _ANSI_ARGS_((struct rtree *));
-static VOID freertnode _ANSI_ARGS_((struct rtree *));
+static VOID freert _ANSI_ARGS_((struct vars *, struct rtree *));
+static VOID freertnode _ANSI_ARGS_((struct vars *, struct rtree *));
static VOID optrt _ANSI_ARGS_((struct vars *, struct rtree *));
static int numrt _ANSI_ARGS_((struct rtree *, int));
-static VOID nfatree _ANSI_ARGS_((struct vars *, struct rtree *));
-static VOID nfanode _ANSI_ARGS_((struct vars *, struct subre *));
+static VOID markrt _ANSI_ARGS_((struct rtree *));
+static VOID cleanrt _ANSI_ARGS_((struct vars *));
+static VOID nfatree _ANSI_ARGS_((struct vars *, struct rtree *, FILE *));
+static VOID nfanode _ANSI_ARGS_((struct vars *, struct subre *, FILE *));
static int newlacon _ANSI_ARGS_((struct vars *, struct state *, struct state *, int));
static VOID freelacons _ANSI_ARGS_((struct subre *, int));
static VOID rfree _ANSI_ARGS_((regex_t *));
static VOID dump _ANSI_ARGS_((regex_t *, FILE *));
static VOID dumprt _ANSI_ARGS_((struct rtree *, FILE *, int));
static VOID rtdump _ANSI_ARGS_((struct rtree *, FILE *, int, int));
-/* === lex.c === */
+/* === regc_lex.c === */
static VOID lexstart _ANSI_ARGS_((struct vars *));
static VOID prefixes _ANSI_ARGS_((struct vars *));
-static VOID lexnest _ANSI_ARGS_((struct vars *, chr *));
+static VOID lexnest _ANSI_ARGS_((struct vars *, chr *, chr *));
static VOID lexword _ANSI_ARGS_((struct vars *));
static int next _ANSI_ARGS_((struct vars *));
static int lexescape _ANSI_ARGS_((struct vars *));
static chr lexdigits _ANSI_ARGS_((struct vars *, int, int, int));
static int brenext _ANSI_ARGS_((struct vars *, pchr));
static VOID skip _ANSI_ARGS_((struct vars *));
-static chr newline _ANSI_ARGS_((VOID));
-static chr *ch _ANSI_ARGS_((VOID));
-static chr chrnamed _ANSI_ARGS_((struct vars *, chr *, pchr));
-/* === locale.c === */
-#define MAXCE 2 /* longest CE code is prepared to handle */
-typedef wint_t celt; /* type holding distinct codes for all chrs, all CEs */
-static int nces _ANSI_ARGS_((struct vars *));
-static int nleaders _ANSI_ARGS_((struct vars *));
-static struct cvec *allces _ANSI_ARGS_((struct vars *, struct cvec *));
-static celt element _ANSI_ARGS_((struct vars *, chr *, chr *));
-static struct cvec *range _ANSI_ARGS_((struct vars *, celt, celt, int));
-static int before _ANSI_ARGS_((celt, celt));
-static struct cvec *eclass _ANSI_ARGS_((struct vars *, celt, int));
-static struct cvec *cclass _ANSI_ARGS_((struct vars *, chr *, chr *, int));
-static struct cvec *allcases _ANSI_ARGS_((struct vars *, pchr));
-static int sncmp _ANSI_ARGS_((CONST chr *, CONST chr *, size_t));
-static struct cvec *newcvec _ANSI_ARGS_((int, int));
-static struct cvec *clearcvec _ANSI_ARGS_((struct cvec *));
-static VOID addchr _ANSI_ARGS_((struct cvec *, pchr));
-static VOID addce _ANSI_ARGS_((struct cvec *, chr *));
-static int haschr _ANSI_ARGS_((struct cvec *, pchr));
-static struct cvec *getcvec _ANSI_ARGS_((struct vars *, int, int));
-static VOID freecvec _ANSI_ARGS_((struct cvec *));
-/* === color.c === */
-union tree;
+static chr newline _ANSI_ARGS_((NOPARMS));
+static chr *ch _ANSI_ARGS_((NOPARMS));
+static chr chrnamed _ANSI_ARGS_((struct vars *, chr *, chr *, pchr));
+/* === regc_color.c === */
static struct colormap *newcm _ANSI_ARGS_((struct vars *));
static VOID freecm _ANSI_ARGS_((struct colormap *));
static VOID cmtreefree _ANSI_ARGS_((struct colormap *, union tree *, int));
@@ -127,8 +73,11 @@ static VOID uncolorchain _ANSI_ARGS_((struct colormap *, struct arc *));
static int singleton _ANSI_ARGS_((struct colormap *, pchr c));
static VOID rainbow _ANSI_ARGS_((struct nfa *, struct colormap *, int, pcolor, struct state *, struct state *));
static VOID colorcomplement _ANSI_ARGS_((struct nfa *, struct colormap *, int, struct state *, struct state *, struct state *));
-/* === nfa.c === */
-static struct nfa *newnfa _ANSI_ARGS_((struct vars *, struct nfa *));
+static VOID dumpcolors _ANSI_ARGS_((struct colormap *, FILE *));
+static VOID fillcheck _ANSI_ARGS_((struct colormap *, union tree *, int, FILE *));
+static VOID dumpchr _ANSI_ARGS_((pchr, FILE *));
+/* === regc_nfa.c === */
+static struct nfa *newnfa _ANSI_ARGS_((struct vars *, struct colormap *, struct nfa *));
static VOID freenfa _ANSI_ARGS_((struct nfa *));
static struct state *newfstate _ANSI_ARGS_((struct nfa *, int flag));
static struct state *newstate _ANSI_ARGS_((struct nfa *));
@@ -151,27 +100,52 @@ static VOID dupnfa _ANSI_ARGS_((struct nfa *, struct state *, struct state *, st
static VOID duptraverse _ANSI_ARGS_((struct nfa *, struct state *, struct state *));
static VOID cleartraverse _ANSI_ARGS_((struct nfa *, struct state *));
static VOID specialcolors _ANSI_ARGS_((struct nfa *));
-static VOID optimize _ANSI_ARGS_((struct nfa *));
-static VOID pullback _ANSI_ARGS_((struct nfa *));
+static int optimize _ANSI_ARGS_((struct nfa *, FILE *));
+static VOID pullback _ANSI_ARGS_((struct nfa *, FILE *));
static int pull _ANSI_ARGS_((struct nfa *, struct arc *));
-static VOID pushfwd _ANSI_ARGS_((struct nfa *));
+static VOID pushfwd _ANSI_ARGS_((struct nfa *, FILE *));
static int push _ANSI_ARGS_((struct nfa *, struct arc *));
#define INCOMPATIBLE 1 /* destroys arc */
#define SATISFIED 2 /* constraint satisfied */
#define COMPATIBLE 3 /* compatible but not satisfied yet */
static int combine _ANSI_ARGS_((struct arc *, struct arc *));
-static VOID fixempties _ANSI_ARGS_((struct nfa *));
+static VOID fixempties _ANSI_ARGS_((struct nfa *, FILE *));
static int unempty _ANSI_ARGS_((struct nfa *, struct arc *));
static VOID cleanup _ANSI_ARGS_((struct nfa *));
static VOID markreachable _ANSI_ARGS_((struct nfa *, struct state *, struct state *, struct state *));
static VOID markcanreach _ANSI_ARGS_((struct nfa *, struct state *, struct state *, struct state *));
-static int analyze _ANSI_ARGS_((struct vars *, struct nfa *));
+static int analyze _ANSI_ARGS_((struct nfa *));
static int isempty _ANSI_ARGS_((struct state *, struct state *));
-static VOID compact _ANSI_ARGS_((struct vars *, struct nfa *, struct cnfa *));
+static VOID compact _ANSI_ARGS_((struct nfa *, struct cnfa *));
static VOID carcsort _ANSI_ARGS_((struct carc *, struct carc *));
static VOID freecnfa _ANSI_ARGS_((struct cnfa *, int));
static VOID dumpnfa _ANSI_ARGS_((struct nfa *, FILE *));
+static VOID dumpstate _ANSI_ARGS_((struct state *, FILE *));
+static VOID dumparcs _ANSI_ARGS_((struct state *, FILE *));
+static int dumprarcs _ANSI_ARGS_((struct arc *, struct state *, FILE *, int));
+static VOID dumparc _ANSI_ARGS_((struct arc *, struct state *, FILE *));
static VOID dumpcnfa _ANSI_ARGS_((struct cnfa *, FILE *));
+static VOID dumpcstate _ANSI_ARGS_((int, struct carc *, struct cnfa *, FILE *));
+/* === regc_cvec.c === */
+static struct cvec *newcvec _ANSI_ARGS_((int, int));
+static struct cvec *clearcvec _ANSI_ARGS_((struct cvec *));
+static VOID addchr _ANSI_ARGS_((struct cvec *, pchr));
+static VOID addmcce _ANSI_ARGS_((struct cvec *, chr *, chr *));
+static int haschr _ANSI_ARGS_((struct cvec *, pchr));
+static struct cvec *getcvec _ANSI_ARGS_((struct vars *, int, int));
+static VOID freecvec _ANSI_ARGS_((struct cvec *));
+/* === regc_locale.c === */
+static int nmcces _ANSI_ARGS_((struct vars *));
+static int nleaders _ANSI_ARGS_((struct vars *));
+static struct cvec *allmcces _ANSI_ARGS_((struct vars *, struct cvec *));
+static celt element _ANSI_ARGS_((struct vars *, chr *, chr *));
+static struct cvec *range _ANSI_ARGS_((struct vars *, celt, celt, int));
+static int before _ANSI_ARGS_((celt, celt));
+static struct cvec *eclass _ANSI_ARGS_((struct vars *, celt, int));
+static struct cvec *cclass _ANSI_ARGS_((struct vars *, chr *, chr *, int));
+static struct cvec *allcases _ANSI_ARGS_((struct vars *, pchr));
+static int cmp _ANSI_ARGS_((CONST chr *, CONST chr *, size_t));
+static int casecmp _ANSI_ARGS_((CONST chr *, CONST chr *, size_t));
/* automatically gathered by fwd; do not hand-edit */
/* =====^!^===== end forwards =====^!^===== */
@@ -199,12 +173,14 @@ struct vars {
color nlcolor; /* color of newline */
struct state *wordchrs; /* state in nfa holding word-char outarcs */
struct rtree *tree; /* subexpression tree */
+ struct rtree *treechain; /* all tree nodes allocated */
+ struct rtree *treefree; /* any free tree nodes */
int ntree; /* number of tree nodes */
struct cvec *cv; /* utility cvec */
- struct cvec *ces; /* collating-element information */
-# define ISCELEADER(v,c) (v->ces != NULL && haschr(v->ces, (c)))
- struct state *cepbegin; /* state in nfa, start of CE prototypes */
- struct state *cepend; /* state in nfa, end of CE prototypes */
+ struct cvec *mcces; /* collating-element information */
+# define ISCELEADER(v,c) (v->mcces != NULL && haschr(v->mcces, (c)))
+ struct state *mccepbegin; /* in nfa, start of MCCE prototypes */
+ struct state *mccepend; /* in nfa, end of MCCE prototypes */
struct subre *lacons; /* lookahead-constraint vector */
int nlacons; /* size of lacons */
int usedshorter; /* used short-preferring quantifiers */
@@ -220,7 +196,7 @@ struct vars {
((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()) goto end;} /* NOERR with retval */
+#define NOERRN() {if (ISERR()) return NULL;} /* NOERR with retval */
#define INSIST(c, e) ((c) ? 0 : ERR(e)) /* if condition false, error */
#define NOTE(b) (v->re->re_info |= (b)) /* note visible condition */
#define EMPTYARC(x, y) newarc(v->nfa, EMPTY, 0, x, y)
@@ -259,22 +235,6 @@ static struct fns functions = {
/*
- - regfree - free an RE (actually, just overall coordination)
- */
-VOID
-regfree(re)
-regex_t *re;
-{
- if (re == NULL || re->re_magic != REMAGIC)
- return; /* no way we can report it, really */
-
- /* free it, calling internal routine that knows details */
- (*((struct fns *)re->re_fns)->free)(re);
-
- re->re_magic = 0;
-}
-
-/*
- compile - compile regular expression
^ int compile(regex_t *, CONST chr *, size_t, int);
*/
@@ -289,25 +249,20 @@ int flags;
struct vars *v = &var;
struct guts *g;
int i;
+ size_t j;
+ FILE *debug = (flags&REG_PROGRESS) ? stdout : (FILE *)NULL;
# define CNOERR() { if (ISERR()) return freev(v, v->err); }
- if (re == NULL) {
- return REG_INVARG;
- }
-
- /*
- * Init re to known state, because we will try to free it if
- * compilation fails.
- */
-
- re->re_magic = 0;
-
/* sanity checks */
- if (string == NULL ||
- ((flags&REG_EXTENDED) && (flags&REG_QUOTE)) ||
- (!(flags&REG_EXTENDED) && (flags&REG_ADVF))) {
- return REG_INVARG;
- }
+
+ if (re == NULL || string == NULL)
+ return REG_INVARG;
+ assert(REG_ADVANCED == (REG_EXTENDED|REG_ADVF));
+ if ((flags&REG_QUOTE) &&
+ (flags&(REG_ADVANCED|REG_EXPANDED|REG_NEWLINE)))
+ return REG_INVARG;
+ if (!(flags&REG_EXTENDED) && (flags&REG_ADVF))
+ return REG_INVARG;
/* initial setup (after which freev() is callable) */
v->re = re;
@@ -319,27 +274,31 @@ int flags;
v->nsubexp = 0;
v->subs = v->sub10;
v->nsubs = 10;
- for (i = 0; (size_t) i < v->nsubs; i++)
- v->subs[i] = NULL;
+ for (j = 0; j < v->nsubs; j++)
+ v->subs[j] = NULL;
v->nfa = NULL;
v->cm = NULL;
v->nlcolor = COLORLESS;
v->wordchrs = NULL;
v->tree = NULL;
+ v->treechain = NULL;
+ v->treefree = NULL;
v->cv = NULL;
- v->ces = NULL;
+ v->mcces = NULL;
v->lacons = NULL;
v->nlacons = 0;
+ re->re_magic = REMAGIC;
re->re_info = 0; /* bits get set during parse */
+ re->re_csize = sizeof(chr);
re->re_guts = NULL;
- re->re_fns = NULL;
+ re->re_fns = VS(&functions);
/* more complex setup, malloced things */
- v->cm = newcm(v); /* colormap must precede nfa... */
+ v->cm = newcm(v);
CNOERR();
- v->nfa = newnfa(v, (struct nfa *)NULL); /* ...newnfa() uses it */
+ v->nfa = newnfa(v, v->cm, (struct nfa *)NULL);
CNOERR();
- re->re_guts = ckalloc(sizeof(struct guts));
+ re->re_guts = VS(MALLOC(sizeof(struct guts)));
if (re->re_guts == NULL)
return freev(v, REG_ESPACE);
g = (struct guts *)re->re_guts;
@@ -351,19 +310,17 @@ int flags;
v->cv = newcvec(100, 10);
if (v->cv == NULL)
return freev(v, REG_ESPACE);
- i = nces(v);
+ i = nmcces(v);
if (i > 0) {
- v->ces = newcvec(nleaders(v), i);
+ v->mcces = newcvec(nleaders(v), i);
CNOERR();
- v->ces = allces(v, v->ces);
- leaders(v, v->ces);
+ v->mcces = allmcces(v, v->mcces);
+ leaders(v, v->mcces);
}
CNOERR();
/* parsing */
lexstart(v); /* also handles prefixes */
- if (SEE(EOS)) /* empty RE is illegal */
- return freev(v, REG_EMPTY);
v->tree = parse(v, EOS, PLAIN, v->nfa->init, v->nfa->final, NONEYET);
assert(SEE(EOS)); /* even if error; ISERR() => SEE(EOS) */
CNOERR();
@@ -371,38 +328,40 @@ int flags;
/* finish setup of nfa and its subre tree */
specialcolors(v->nfa);
CNOERR();
- if (flags&REG_PROGRESS) {
- dumpnfa(v->nfa, stdout);
- dumprt(v->tree, stdout, 1);
+ if (debug != NULL) {
+ dumpnfa(v->nfa, debug);
+ dumprt(v->tree, debug, 1);
}
v->usedshorter = 0;
optrt(v, v->tree);
- if (v->tree != NULL)
+ if (v->tree != NULL) {
v->ntree = numrt(v->tree, 1);
- else
+ markrt(v->tree);
+ } else
v->ntree = 0;
- if (flags&REG_PROGRESS) {
- printf("-->\n");
- dumprt(v->tree, stdout, 1);
+ cleanrt(v);
+ if (debug != NULL) {
+ fprintf(debug, "-->\n");
+ dumprt(v->tree, debug, 1);
}
/* build compacted NFAs for tree, lacons, main nfa */
- nfatree(v, v->tree);
- if (flags&REG_PROGRESS) {
- printf("---->\n");
- dumprt(v->tree, stdout, 1);
+ nfatree(v, v->tree, debug);
+ if (debug != NULL) {
+ fprintf(debug, "---->\n");
+ dumprt(v->tree, debug, 1);
}
CNOERR();
assert(v->nlacons == 0 || v->lacons != NULL);
for (i = 1; i < v->nlacons; i++)
- nfanode(v, &v->lacons[i]);
+ nfanode(v, &v->lacons[i], debug);
CNOERR();
- optimize(v->nfa); /* removes unreachable states */
+ re->re_info |= optimize(v->nfa, debug);
CNOERR();
if (v->nfa->post->nins <= 0)
return freev(v, REG_IMPOSS); /* end unreachable! */
assert(v->nfa->pre->nouts > 0);
- compact(v, v->nfa, &g->cnfa);
+ compact(v->nfa, &g->cnfa);
CNOERR();
freenfa(v->nfa);
v->nfa = NULL;
@@ -412,13 +371,8 @@ int flags;
CNOERR();
/* looks okay, package it up */
- re->re_magic = REMAGIC;
re->re_nsub = v->nsubexp;
- /* re_info is already set */
- re->re_csize = sizeof(chr);
- re->re_guts = (VOID *)g;
- re->re_fns = (VOID *)&functions;
- v->re = NULL;
+ v->re = NULL; /* freev no longer frees re */
g->magic = GUTSMAGIC;
g->cflags = v->cflags;
g->info = re->re_info;
@@ -428,7 +382,7 @@ int flags;
g->tree = v->tree;
v->tree = NULL;
g->ntree = v->ntree;
- g->compare = (v->cflags&REG_ICASE) ? sncmp : wcsncmp;
+ g->compare = (v->cflags&REG_ICASE) ? casecmp : cmp;
g->lacons = v->lacons;
v->lacons = NULL;
g->nlacons = v->nlacons;
@@ -453,16 +407,15 @@ int wanted; /* want enough room for this one */
struct subre **p;
size_t n;
- assert((size_t)wanted >= v->nsubs);
+ assert(wanted > 0 && (size_t)wanted >= v->nsubs);
n = (size_t)wanted * 3 / 2 + 1;
if (v->subs == v->sub10) {
- p = (struct subre **)ckalloc(n * sizeof(struct subre *));
+ p = (struct subre **)MALLOC(n * sizeof(struct subre *));
if (p != NULL)
- memcpy((VOID *)p, (VOID *)v->subs,
+ memcpy(VS(p), VS(v->subs),
v->nsubs * sizeof(struct subre *));
} else
- p = (struct subre **) ckrealloc((VOID *)v->subs,
- n * sizeof(struct subre *));
+ p = REALLOC(v->subs, n * sizeof(struct subre *));
if (p == NULL) {
ERR(REG_ESPACE);
return;
@@ -476,8 +429,8 @@ int wanted; /* want enough room for this one */
/*
- freev - free vars struct's substructures where necessary
- * Does optional error-number setting, and returns error code, to make
- * error code terser.
+ * Optionally does error-number setting, and always returns error code
+ * (if any), to make error-handling code terser.
^ static int freev(struct vars *, int);
*/
static int
@@ -488,20 +441,22 @@ int err;
if (v->re != NULL)
rfree(v->re);
if (v->subs != v->sub10)
- ckfree((char *)v->subs);
+ FREE(v->subs);
if (v->nfa != NULL)
freenfa(v->nfa);
if (v->cm != NULL)
freecm(v->cm);
if (v->tree != NULL)
- freert(v->tree);
+ freert(v, v->tree);
+ if (v->treechain != NULL)
+ cleanrt(v);
if (v->cv != NULL)
freecvec(v->cv);
- if (v->ces != NULL)
- freecvec(v->ces);
+ if (v->mcces != NULL)
+ freecvec(v->mcces);
if (v->lacons != NULL)
freelacons(v->lacons, v->nlacons);
- ERR(err);
+ ERR(err); /* nop if err==0 */
return v->err;
}
@@ -510,6 +465,9 @@ int err;
- parse - parse an RE
* Arguably this is too big and too complex and ought to be divided up.
* However, the code is somewhat intertwined...
+ *
+ * Note that it is no longer necessary to be rigorous about freeing tree
+ * nodes on error exits, as the tree machinery keeps track of them.
^ static struct rtree *parse(struct vars *, int, int, struct state *,
^ struct state *, int);
*/
@@ -531,7 +489,6 @@ int pprefer; /* parent's short/long preference */
# define ARCV(t, val) newarc(v->nfa, t, val, lp, rp)
int m, n;
int emptybranch; /* is there anything in this branch yet? */
- color co;
struct rtree *branches; /* top level */
struct rtree *branch; /* current branch */
struct subre *now; /* current subtree's top */
@@ -545,11 +502,10 @@ int pprefer; /* parent's short/long preference */
assert(stopper == ')' || stopper == EOS);
- branch = NULL; /* lint. */
- rt1 = NULL; /* lint. */
-
capture = 0;
branches = newrt(v);
+ branch = branches;
+ rt1 = NULL; /* shut up lint */
firstbranch = 1;
NOERRN();
do {
@@ -557,27 +513,17 @@ int pprefer; /* parent's short/long preference */
emptybranch = 1; /* tentatively */
left = newstate(v->nfa);
right = newstate(v->nfa);
- if (!firstbranch)
+ NOERRN();
+ if (!firstbranch) {
rt1 = newrt(v);
-#if 1
- if (ISERR()) {
- freert(rt1);
- freert(branches); /* mem leak (CCS). */
- return NULL;
+ NOERRN();
+ branch->next = rt1;
+ branch = rt1;
}
-#else
- NOERRN();
-#endif
EMPTYARC(init, left);
EMPTYARC(right, final);
lp = left;
rp = right;
- if (firstbranch)
- branch = branches;
- else {
- branch->next = rt1;
- branch = rt1;
- }
branch->op = '|';
now = &branch->left;
*now = subre(left, right, NONEYET, 0, (struct rtree *)NULL);
@@ -609,7 +555,7 @@ int pprefer; /* parent's short/long preference */
sub.subno = v->nsubexp;
if ((size_t)sub.subno >= v->nsubs)
moresubs(v, sub.subno);
- assert((size_t) sub.subno < v->nsubs);
+ assert((size_t)sub.subno < v->nsubs);
} else
sub.subno = 0;
NEXT();
@@ -661,7 +607,7 @@ int pprefer; /* parent's short/long preference */
assert(SEE(')') || ISERR());
NEXT();
m = newlacon(v, s, s2, m);
- freert(rt1);
+ freert(v, rt1);
NOERRN();
ARCV(LACON, m);
constraint = 1;
@@ -696,10 +642,10 @@ int pprefer; /* parent's short/long preference */
NEXT();
break;
case '.':
- co = (color) ((v->cflags&REG_NLSTOP)
- ? nlcolor(v)
- : COLORLESS);
- rainbow(v->nfa, v->cm, PLAIN, co, lp, rp);
+ rainbow(v->nfa, v->cm, PLAIN,
+ (v->cflags&REG_NLSTOP) ?
+ nlcolor(v) : COLORLESS,
+ lp, rp);
NEXT();
break;
case '^':
@@ -804,13 +750,19 @@ int pprefer; /* parent's short/long preference */
constraint = 1;
break;
case ')': /* unbalanced paren */
+#ifdef POSIX_MISTAKE
if (!(v->cflags&REG_EXTENDED) ||
(v->cflags&REG_ADVF)) {
- ERR(REG_EPAREN);
- goto end;
+ ERR(REG_EPAREN);
+ return NULL;
}
NOTE(REG_UPBOTCH);
/* fallthrough into case PLAIN */
+#else
+ ERR(REG_EPAREN);
+ return NULL;
+ break;
+#endif
case PLAIN:
onechr(v, v->nextvalue, lp, rp);
okcolors(v->nfa, v->cm);
@@ -822,10 +774,12 @@ int pprefer; /* parent's short/long preference */
case '?':
case '{':
ERR(REG_BADRPT);
- goto end;
+ return NULL;
+ break;
default:
ERR(REG_ASSERT);
- goto end;
+ return NULL;
+ break;
}
/* ...possibly followed by a quantifier */
@@ -858,13 +812,13 @@ int pprefer; /* parent's short/long preference */
n = INFINITY;
if (m > n) {
ERR(REG_BADBR);
- goto end;
+ return NULL;
}
} else
n = m;
if (!SEE('}')) { /* gets errors too */
ERR(REG_BADBR);
- goto end;
+ return NULL;
}
if (m != n)
sub.prefer = (v->nextvalue) ? LONGER :
@@ -880,19 +834,19 @@ int pprefer; /* parent's short/long preference */
/* constraints may not be quantified */
if (constraint) {
ERR(REG_BADRPT);
- goto end;
+ return NULL;
}
/* annoying special case: {0,0} cancels everything */
if (m == 0 && n == 0 && sub.begin != NULL) {
- freert(now->tree);
+ freert(v, now->tree);
now->tree = NULL;
sub.begin = NULL; /* no substructure */
sub.prefer = NONEYET;
/* the repeat() below will do the rest */
}
- /* if no substructure, aVOID hard part */
+ /* if no substructure, avoid hard part */
if (now->prefer == NONEYET)
now->prefer = sub.prefer;
if (sub.begin == NULL && (sub.prefer == NONEYET ||
@@ -983,8 +937,8 @@ int pprefer; /* parent's short/long preference */
t->tree = rt1;
rt1->op = 'b';
rt1->left.subno = sub.subno;
- rt1->left.min = (short) m;
- rt1->left.max = (short) n;
+ rt1->left.min = (short)m;
+ rt1->left.max = (short)n;
rt1->left.prefer = sub.prefer;
continue; /* NOTE CONTINUE */
}
@@ -1036,14 +990,13 @@ int pprefer; /* parent's short/long preference */
branch->op = ',';
else {
branches = branch->left.tree; /* might be NULL */
- freertnode(branch);
+ freertnode(v, branch);
}
}
if (capture) /* actually a catchall flag */
return branches;
- end: /* mem leak (CCS) */
- freert(branches);
+ freert(v, branches);
return NULL;
}
@@ -1197,7 +1150,7 @@ struct state *rp;
struct state *s;
struct arc *a; /* arc from lp */
struct arc *ba; /* arc from left, from bracket() */
- struct arc *pa; /* CE-prototype arc */
+ struct arc *pa; /* MCCE-prototype arc */
color co;
chr *p;
int i;
@@ -1213,16 +1166,16 @@ struct state *rp;
/* easy part of complementing */
colorcomplement(v->nfa, v->cm, PLAIN, left, lp, rp);
NOERR();
- if (v->ces == NULL) { /* no CEs -- we're done */
+ if (v->mcces == NULL) { /* no MCCEs -- we're done */
dropstate(v->nfa, left);
assert(right->nins == 0);
freestate(v->nfa, right);
return;
}
- /* but complementing gets messy in the presence of CEs... */
+ /* but complementing gets messy in the presence of MCCEs... */
NOTE(REG_ULOCALE);
- for (p = v->ces->chrs, i = v->ces->nchrs; i > 0; p++, i--) {
+ for (p = v->mcces->chrs, i = v->mcces->nchrs; i > 0; p++, i--) {
co = getcolor(v->cm, *p);
a = findarc(lp, PLAIN, co);
ba = findarc(left, PLAIN, co);
@@ -1236,7 +1189,7 @@ struct state *rp;
NOERR();
newarc(v->nfa, PLAIN, co, lp, s);
NOERR();
- pa = findarc(v->cepbegin, PLAIN, co);
+ pa = findarc(v->mccepbegin, PLAIN, co);
assert(pa != NULL);
if (ba == NULL) { /* easy case, need all of them */
cloneouts(v->nfa, pa->to, s, rp, PLAIN);
@@ -1288,10 +1241,11 @@ struct state *rp;
case RANGE: /* a-b-c or other botch */
ERR(REG_ERANGE);
return;
+ break;
case PLAIN:
c[0] = v->nextvalue;
NEXT();
- /* shortcut for ordinary chr (not range, not CE leader) */
+ /* shortcut for ordinary chr (not range, not MCCE leader) */
if (!SEE(RANGE) && !ISCELEADER(v, c[0])) {
onechr(v, c[0], lp, rp);
return;
@@ -1318,6 +1272,7 @@ struct state *rp;
NOERR();
dovec(v, cv, lp, rp);
return;
+ break;
case CCLASS:
startp = v->now;
endp = scanplain(v);
@@ -1327,9 +1282,11 @@ struct state *rp;
NOERR();
dovec(v, cv, lp, rp);
return;
+ break;
default:
ERR(REG_ASSERT);
return;
+ break;
}
if (SEE(RANGE)) {
@@ -1353,6 +1310,7 @@ struct state *rp;
default:
ERR(REG_ERANGE);
return;
+ break;
}
} else
endc = startc;
@@ -1407,35 +1365,35 @@ leaders(v, cv)
struct vars *v;
struct cvec *cv;
{
- int ce;
+ int mcce;
chr *p;
chr leader;
struct state *s;
struct arc *a;
- v->cepbegin = newstate(v->nfa);
- v->cepend = newstate(v->nfa);
+ v->mccepbegin = newstate(v->nfa);
+ v->mccepend = newstate(v->nfa);
NOERR();
- for (ce = 0; ce < cv->nces; ce++) {
- p = cv->ces[ce];
+ for (mcce = 0; mcce < cv->nmcces; mcce++) {
+ p = cv->mcces[mcce];
leader = *p;
if (!haschr(cv, leader)) {
addchr(cv, leader);
s = newstate(v->nfa);
newarc(v->nfa, PLAIN, subcolor(v->cm, leader),
- v->cepbegin, s);
+ v->mccepbegin, s);
okcolors(v->nfa, v->cm);
} else {
- a = findarc(v->cepbegin, PLAIN,
+ a = findarc(v->mccepbegin, PLAIN,
getcolor(v->cm, leader));
assert(a != NULL);
s = a->to;
- assert(s != v->cepend);
+ assert(s != v->mccepend);
}
p++;
- assert(*p != 0 && *(p+1) == 0); /* only 2-char CEs at present */
- newarc(v->nfa, PLAIN, subcolor(v->cm, *p), s, v->cepend);
+ assert(*p != 0 && *(p+1) == 0); /* only 2-char MCCEs for now */
+ newarc(v->nfa, PLAIN, subcolor(v->cm, *p), s, v->mccepend);
okcolors(v->nfa, v->cm);
}
}
@@ -1463,7 +1421,7 @@ struct state *rp;
/*
- dovec - fill in arcs for each element of a cvec
- * This one has to handle the messy cases, like CEs and CE leaders.
+ * This one has to handle the messy cases, like MCCEs and MCCE leaders.
^ static VOID dovec(struct vars *, struct cvec *, struct state *,
^ struct state *);
*/
@@ -1493,11 +1451,11 @@ struct state *rp;
assert(singleton(v->cm, *p));
*np++ = *p;
}
- cv->nchrs = np - cv->chrs; /* only CE leaders remain */
- if (cv->nchrs == 0 && cv->nces == 0)
+ cv->nchrs = np - cv->chrs; /* only MCCE leaders remain */
+ if (cv->nchrs == 0 && cv->nmcces == 0)
return;
- /* deal with the CE leaders */
+ /* deal with the MCCE leaders */
NOTE(REG_ULOCALE);
for (p = cv->chrs, i = cv->nchrs; i > 0; p++, i--) {
co = getcolor(v->cm, *p);
@@ -1510,7 +1468,7 @@ struct state *rp;
newarc(v->nfa, PLAIN, co, lp, s);
NOERR();
}
- pa = findarc(v->cepbegin, PLAIN, co);
+ pa = findarc(v->mccepbegin, PLAIN, co);
assert(pa != NULL);
ps = pa->to;
newarc(v->nfa, '$', 1, s, rp);
@@ -1519,9 +1477,9 @@ struct state *rp;
NOERR();
}
- /* and the CEs */
- for (i = 0; i < cv->nces; i++) {
- p = cv->ces[i];
+ /* and the MCCEs */
+ for (i = 0; i < cv->nmcces; i++) {
+ p = cv->mcces[i];
assert(singleton(v->cm, *p));
co = getcolor(v->cm, *p++);
a = findarc(lp, PLAIN, co);
@@ -1587,7 +1545,7 @@ struct vars *v;
NEXT();
assert(v->savenow != NULL && SEE('['));
bracket(v, left, right);
- assert(((v->savenow != NULL) && SEE(']')) || ISERR());
+ assert((v->savenow != NULL && SEE(']')) || ISERR());
NEXT();
NOERR();
v->wordchrs = left;
@@ -1626,14 +1584,23 @@ static struct rtree *
newrt(v)
struct vars *v;
{
- struct rtree *rt = (struct rtree *)ckalloc(sizeof(struct rtree));
-
- if (rt == NULL) {
- ERR(REG_ESPACE);
- return NULL;
+ struct rtree *rt;
+
+ rt = v->treefree;
+ if (rt != NULL)
+ v->treefree = rt->next;
+ else {
+ rt = (struct rtree *)MALLOC(sizeof(struct rtree));
+ if (rt == NULL) {
+ ERR(REG_ESPACE);
+ return NULL;
+ }
+ rt->chain = v->treechain;
+ v->treechain = rt;
}
rt->op = '?'; /* invalid */
+ rt->flags = 0;
rt->no = 0;
rt->left.begin = NULL;
rt->left.end = NULL;
@@ -1650,36 +1617,39 @@ struct vars *v;
rt->right.tree = NULL;
ZAPCNFA(rt->right.cnfa);
rt->next = NULL;
+
return rt;
}
/*
- freert - free a subRE subtree
- ^ static VOID freert(struct rtree *);
+ ^ static VOID freert(struct vars *, struct rtree *);
*/
static VOID
-freert(rt)
+freert(v, rt)
+struct vars *v; /* might be NULL */
struct rtree *rt;
{
if (rt == NULL)
return;
if (rt->left.tree != NULL)
- freert(rt->left.tree);
+ freert(v, rt->left.tree);
if (rt->right.tree != NULL)
- freert(rt->right.tree);
+ freert(v, rt->right.tree);
if (rt->next != NULL)
- freert(rt->next);
+ freert(v, rt->next);
- freertnode(rt);
+ freertnode(v, rt);
}
/*
- freertnode - free one node in a subRE subtree
- ^ static VOID freertnode(struct rtree *);
+ ^ static VOID freertnode(struct vars *, struct rtree *);
*/
static VOID
-freertnode(rt)
+freertnode(v, rt)
+struct vars *v; /* might be NULL */
struct rtree *rt;
{
if (rt == NULL)
@@ -1689,8 +1659,13 @@ struct rtree *rt;
freecnfa(&rt->left.cnfa, 0);
if (!NULLCNFA(rt->right.cnfa))
freecnfa(&rt->right.cnfa, 0);
+ rt->flags = 0;
- ckfree((char *)rt);
+ if (v != NULL) {
+ rt->next = v->treefree;
+ v->treefree = rt;
+ } else
+ FREE(rt);
}
/*
@@ -1721,7 +1696,7 @@ struct rtree *rt;
subno = rt->left.subno;
rt->left = t->left;
assert(NULLCNFA(t->left.cnfa));
- freertnode(t);
+ freertnode(v, t);
if (subno != 0) {
assert(rt->left.subno == 0 && subno > 0);
rt->left.subno = subno;
@@ -1739,7 +1714,7 @@ struct rtree *rt;
subno = rt->right.subno;
rt->right = t->left;
assert(NULLCNFA(t->right.cnfa));
- freertnode(t);
+ freertnode(v, t);
if (subno != 0) {
assert(rt->right.subno == 0 && subno > 0);
rt->right.subno = subno;
@@ -1800,7 +1775,7 @@ int start; /* starting point for subtree numbers */
assert(rt != NULL);
i = start;
- rt->no = (short) i++;
+ rt->no = (short)i++;
if (rt->left.tree != NULL)
i = numrt(rt->left.tree, i);
if (rt->right.tree != NULL)
@@ -1811,54 +1786,95 @@ int start; /* starting point for subtree numbers */
}
/*
+ - markrt - mark tree nodes as INUSE
+ ^ static VOID markrt(struct rtree *);
+ */
+static VOID
+markrt(rt)
+struct rtree *rt;
+{
+ assert(rt != NULL);
+
+ rt->flags |= INUSE;
+ if (rt->left.tree != NULL)
+ markrt(rt->left.tree);
+ if (rt->right.tree != NULL)
+ markrt(rt->right.tree);
+ if (rt->next != NULL)
+ markrt(rt->next);
+}
+
+/*
+ - cleanrt - free any tree nodes not marked INUSE
+ ^ static VOID cleanrt(struct vars *);
+ */
+static VOID
+cleanrt(v)
+struct vars *v;
+{
+ struct rtree *rt;
+ struct rtree *next;
+
+ for (rt = v->treechain; rt != NULL; rt = next) {
+ next = rt->next;
+ if (!(rt->flags&INUSE))
+ FREE(rt);
+ }
+ v->treechain = NULL;
+ v->treefree = NULL; /* just on general principles */
+}
+
+/*
- nfatree - turn a subRE subtree into a tree of compacted NFAs
- ^ static VOID nfatree(struct vars *, struct rtree *);
+ ^ static VOID nfatree(struct vars *, struct rtree *, FILE *);
*/
static VOID
-nfatree(v, rt)
+nfatree(v, rt, f)
struct vars *v;
struct rtree *rt;
+FILE *f; /* for debug output */
{
if (rt == NULL)
return;
if (rt->left.begin != NULL)
- nfanode(v, &rt->left);
+ nfanode(v, &rt->left, f);
if (rt->left.tree != NULL)
- nfatree(v, rt->left.tree);
+ nfatree(v, rt->left.tree, f);
if (rt->right.begin != NULL)
- nfanode(v, &rt->right);
+ nfanode(v, &rt->right, f);
if (rt->right.tree != NULL)
- nfatree(v, rt->right.tree);
+ nfatree(v, rt->right.tree, f);
if (rt->next != NULL)
- nfatree(v, rt->next);
+ nfatree(v, rt->next, f);
}
/*
- nfanode - do one NFA for nfatree
- ^ static VOID nfanode(struct vars *, struct subre *);
+ ^ static VOID nfanode(struct vars *, struct subre *, FILE *);
*/
static VOID
-nfanode(v, sub)
+nfanode(v, sub, f)
struct vars *v;
struct subre *sub;
+FILE *f; /* for debug output */
{
struct nfa *nfa;
if (sub->begin == NULL)
return;
- nfa = newnfa(v, v->nfa);
+ nfa = newnfa(v, v->cm, v->nfa);
NOERR();
dupnfa(nfa, sub->begin, sub->end, nfa->init, nfa->final);
if (!ISERR()) {
specialcolors(nfa);
- optimize(nfa);
+ (DISCARD) optimize(nfa, f);
}
if (!ISERR())
- compact(v, nfa, &sub->cnfa);
+ compact(nfa, &sub->cnfa);
freenfa(nfa);
}
@@ -1877,11 +1893,11 @@ int pos;
struct subre *sub;
if (v->nlacons == 0) {
- v->lacons = (struct subre *)ckalloc(2 * sizeof(struct subre));
+ v->lacons = (struct subre *)MALLOC(2 * sizeof(struct subre));
n = 1; /* skip 0th */
v->nlacons = 2;
} else {
- v->lacons = (struct subre *)ckrealloc((VOID *) v->lacons,
+ v->lacons = (struct subre *)REALLOC(v->lacons,
(v->nlacons+1)*sizeof(struct subre));
n = v->nlacons++;
}
@@ -1909,10 +1925,11 @@ int n;
struct subre *sub;
int i;
+ assert(n > 0);
for (sub = subs + 1, i = n - 1; i > 0; sub++, i--)
if (!NULLCNFA(sub->cnfa))
freecnfa(&sub->cnfa, 0);
- ckfree((char *)subs);
+ FREE(subs);
}
/*
@@ -1921,11 +1938,15 @@ int n;
*/
static VOID
rfree(re)
-regex_t *re; /* regfree has validated it */
+regex_t *re;
{
- struct guts *g = (struct guts *)re->re_guts;
+ struct guts *g;
- re->re_magic = 0; /* invalidate it */
+ if (re == NULL || re->re_magic != REMAGIC)
+ return;
+
+ re->re_magic = 0; /* invalidate RE */
+ g = (struct guts *)re->re_guts;
re->re_guts = NULL;
re->re_fns = NULL;
g->magic = 0;
@@ -1934,10 +1955,50 @@ regex_t *re; /* regfree has validated it */
if (g->cm != NULL)
freecm(g->cm);
if (g->tree != NULL)
- freert(g->tree);
+ freert((struct vars *)NULL, g->tree);
if (g->lacons != NULL)
freelacons(g->lacons, g->nlacons);
- ckfree((char *)g);
+ FREE(g);
+}
+
+/*
+ - dump - dump an RE in human-readable form
+ ^ static VOID dump(regex_t *, FILE *);
+ */
+static VOID
+dump(re, f)
+regex_t *re;
+FILE *f;
+{
+#ifdef REG_DEBUG
+ struct guts *g;
+ int i;
+
+ if (re->re_magic != REMAGIC)
+ fprintf(f, "bad magic number (0x%x not 0x%x)\n", re->re_magic,
+ REMAGIC);
+ if (re->re_guts == NULL) {
+ fprintf(f, "NULL guts!!!\n");
+ return;
+ }
+ g = (struct guts *)re->re_guts;
+ if (g->magic != GUTSMAGIC)
+ fprintf(f, "bad guts magic number (0x%x not 0x%x)\n", g->magic,
+ GUTSMAGIC);
+
+ fprintf(f, "nsub %d, info 0%o, csize %d, ntree %d, usedshort %d\n",
+ re->re_nsub, re->re_info, re->re_csize, g->ntree,
+ g->usedshorter);
+
+ dumpcolors(g->cm, f);
+ dumpcnfa(&g->cnfa, f);
+ for (i = 1; i < g->nlacons; i++) {
+ fprintf(f, "la%d (%s):\n", i,
+ (g->lacons[i].subno) ? "positive" : "negative");
+ dumpcnfa(&g->lacons[i].cnfa, f);
+ }
+ dumprt(g->tree, f, 0);
+#endif
}
/*
@@ -2068,22 +2129,9 @@ int level;
}
}
-/*
- - dump - dump an RE in human-readable form
- ^ static VOID dump(regex_t *, FILE *);
- */
-static VOID
-dump(re, f)
-regex_t *re;
-FILE *f;
-{
-}
-
-#undef NOERRN
-#define NOERRN() {if (ISERR()) return NULL;} /* NOERR with retval */
-
#define COMPILE 1
-#include "lex.c"
-#include "color.c"
-#include "locale.c"
-#include "nfa.c"
+#include "regc_lex.c"
+#include "regc_color.c"
+#include "regc_nfa.c"
+#include "regc_cvec.c"
+#include "regc_locale.c"
diff --git a/generic/regcustom.h b/generic/regcustom.h
new file mode 100644
index 0000000..0fda25f
--- /dev/null
+++ b/generic/regcustom.h
@@ -0,0 +1,90 @@
+/* headers (which also pick up the standard ones, or equivalents) */
+#include "tclInt.h"
+#include "tclPort.h"
+
+/* overrides for regguts.h definitions */
+/* function-pointer declarations */
+#define FUNCPTR(name, args) (*name) _ANSI_ARGS_(args)
+#define MALLOC(n) ckalloc(n)
+#define FREE(p) ckfree(VS(p))
+#define REALLOC(p,n) ckrealloc(VS(p),n)
+
+
+
+/*
+ * Do not insert extras between the "begin" and "end" lines -- this
+ * chunk is automatically extracted to be fitted into regex.h.
+ */
+/* --- begin --- */
+/* ensure certain things don't sneak in from system headers */
+#ifdef __REG_WIDE_T
+#undef __REG_WIDE_T
+#endif
+#ifdef __REG_WIDE_COMPILE
+#undef __REG_WIDE_COMPILE
+#endif
+#ifdef __REG_WIDE_EXEC
+#undef __REG_WIDE_EXEC
+#endif
+#ifdef __REG_REGOFF_T
+#undef __REG_REGOFF_T
+#endif
+#ifdef __REG_VOID_T
+#undef __REG_VOID_T
+#endif
+#ifdef __REG_CONST
+#undef __REG_CONST
+#endif
+/* interface types */
+#define __REG_WIDE_T Tcl_UniChar
+#define __REG_WIDE_COMPILE re_ucomp
+#define __REG_WIDE_EXEC re_uexec
+#define __REG_REGOFF_T long /* not really right, but good enough... */
+#define __REG_VOID_T VOID
+#define __REG_CONST CONST
+#ifndef __REG_NOFRONT
+#define __REG_NOFRONT /* don't want regcomp() and regexec() */
+#endif
+#ifndef __REG_NOCHAR
+#define __REG_NOCHAR /* or the char versions */
+#endif
+/* --- end --- */
+
+
+
+/* internal character type and related */
+typedef Tcl_UniChar chr; /* the type itself */
+typedef int pchr; /* what it promotes to */
+typedef unsigned uchr; /* unsigned type that will hold a chr */
+typedef int celt; /* type to hold chr, MCCE number, or NOCELT */
+#define NOCELT (-1) /* celt value which is not valid chr or MCCE */
+#define CHR(c) (UCHAR(c)) /* turn char literal into chr literal */
+#define DIGITVAL(c) ((c)-'0') /* turn chr digit into its value */
+#define CHRBITS 16 /* bits in a chr; must not use sizeof */
+#define CHR_MIN 0x0000 /* smallest and largest chr; the value */
+#define CHR_MAX 0xffff /* CHR_MAX-CHR_MIN+1 should fit in uchr */
+
+/* functions operating on chr */
+#define iscalnum(x) TclUniCharIsAlnum(x)
+#define iscalpha(x) TclUniCharIsAlpha(x)
+#define iscdigit(x) TclUniCharIsDigit(x)
+#define iscspace(x) TclUniCharIsSpace(x)
+
+/* name the external functions */
+#define compile re_ucomp
+#define exec re_uexec
+#ifdef notdef
+#define regfree re_ufree
+#define regerror re_uerror
+#endif
+
+/*
+ * Implement a mistake in the original POSIX.2: in EREs, and only in EREs
+ * (AREs do not support this botch), an unbalanced right parenthesis is an
+ * ordinary character rather than an error. This was unintentional, and
+ * will be fixed someday.
+ */
+#define POSIX_MISTAKE /* sigh */
+
+/* and pick up the standard header */
+#include "regex.h"
diff --git a/generic/regerror.c b/generic/regerror.c
new file mode 100644
index 0000000..5eb67a7
--- /dev/null
+++ b/generic/regerror.c
@@ -0,0 +1,82 @@
+/*
+ * regerror - error-code expansion
+ */
+
+#include "regguts.h"
+
+/* unknown-error explanation */
+static char unk[] = "*** unknown regex error code 0x%x ***";
+
+/* struct to map among codes, code names, and explanations */
+static struct rerr {
+ int code;
+ char *name;
+ char *explain;
+} rerrs[] = {
+ /* the actual table is built from regex.h */
+# include "regerrs.h"
+ -1, "", "oops", /* explanation special-cased in code */
+};
+
+/*
+ - regerror - the interface to error numbers
+ */
+/* ARGSUSED */
+size_t /* actual space needed (including NUL) */
+regerror(errcode, preg, errbuf, errbuf_size)
+int errcode; /* error code, or REG_ATOI or REG_ITOA */
+const regex_t *preg; /* associated regex_t (unused at present) */
+char *errbuf; /* result buffer (unless errbuf_size==0) */
+size_t errbuf_size; /* available space in errbuf, can be 0 */
+{
+ struct rerr *r;
+ char *msg;
+ char convbuf[sizeof(unk)+50]; /* 50 = plenty for int */
+ size_t len;
+ int icode;
+
+ switch (errcode) {
+ case REG_ATOI: /* convert name to number */
+ for (r = rerrs; r->code >= 0; r++)
+ if (strcmp(r->name, errbuf) == 0)
+ break;
+ sprintf(convbuf, "%d", r->code); /* -1 for unknown */
+ msg = convbuf;
+ break;
+ case REG_ITOA: /* convert number to name */
+ icode = atoi(errbuf); /* not our problem if this fails */
+ for (r = rerrs; r->code >= 0; r++)
+ if (r->code == icode)
+ break;
+ if (r->code >= 0)
+ msg = r->name;
+ else { /* unknown; tell him the number */
+ sprintf(convbuf, "REG_%u", (unsigned)icode);
+ msg = convbuf;
+ }
+ break;
+ default: /* a real, normal error code */
+ for (r = rerrs; r->code >= 0; r++)
+ if (r->code == errcode)
+ break;
+ if (r->code >= 0)
+ msg = r->explain;
+ else { /* unknown; say so */
+ sprintf(convbuf, unk, errcode);
+ msg = convbuf;
+ }
+ break;
+ }
+
+ len = strlen(msg) + 1; /* space needed, including NUL */
+ if (errbuf_size > 0) {
+ if (errbuf_size > len)
+ strcpy(errbuf, msg);
+ else { /* truncate to fit */
+ strncpy(errbuf, msg, errbuf_size-1);
+ errbuf[errbuf_size-1] = '\0';
+ }
+ }
+
+ return len;
+}
diff --git a/generic/regerrs.h b/generic/regerrs.h
new file mode 100644
index 0000000..8298597
--- /dev/null
+++ b/generic/regerrs.h
@@ -0,0 +1,19 @@
+REG_OKAY, "REG_OKAY", "no errors detected",
+REG_NOMATCH, "REG_NOMATCH", "failed to match",
+REG_BADPAT, "REG_BADPAT", "invalid regexp (reg version 0.1)",
+REG_ECOLLATE, "REG_ECOLLATE", "invalid collating element",
+REG_ECTYPE, "REG_ECTYPE", "invalid character class",
+REG_EESCAPE, "REG_EESCAPE", "invalid escape \\ sequence",
+REG_ESUBREG, "REG_ESUBREG", "invalid backreference number",
+REG_EBRACK, "REG_EBRACK", "brackets [] not balanced",
+REG_EPAREN, "REG_EPAREN", "parentheses () not balanced",
+REG_EBRACE, "REG_EBRACE", "braces {} not balanced",
+REG_BADBR, "REG_BADBR", "invalid repetition count(s)",
+REG_ERANGE, "REG_ERANGE", "invalid character range",
+REG_ESPACE, "REG_ESPACE", "out of memory",
+REG_BADRPT, "REG_BADRPT", "quantifier operand invalid",
+REG_ASSERT, "REG_ASSERT", "\"can't happen\" -- you found a bug",
+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_IMPOSS, "REG_IMPOSS", "can never match",
diff --git a/generic/regex.h b/generic/regex.h
new file mode 100644
index 0000000..6f61dd3
--- /dev/null
+++ b/generic/regex.h
@@ -0,0 +1,299 @@
+#ifndef _REGEX_H_
+#define _REGEX_H_ /* never again */
+/*
+ * regular expressions
+ *
+ * Prototypes etc. marked with "^" within comments get gathered up (and
+ * possibly edited) by the regfwd program and inserted near the bottom of
+ * this file.
+ *
+ * We offer the option of declaring one wide-character version of the
+ * RE functions as well as the char versions. To do that, define
+ * __REG_WIDE_T to the type of wide characters (unfortunately, there
+ * is no consensus that wchar_t is suitable) and __REG_WIDE_COMPILE and
+ * __REG_WIDE_EXEC to the names to be used for the compile and execute
+ * functions (suggestion: re_Xcomp and re_Xexec, where X is a letter
+ * suggestive of the wide type, e.g. re_ucomp and re_uexec for Unicode).
+ * For cranky old compilers, it may be necessary to do something like:
+ * #define __REG_WIDE_COMPILE(a,b,c,d) re_Xcomp(a,b,c,d)
+ * #define __REG_WIDE_EXEC(a,b,c,d,e,f) re_Xexec(a,b,c,d,e,f)
+ * rather than just #defining the names as parameterless macros.
+ *
+ * For some specialized purposes, it may be desirable to suppress the
+ * declarations of the "front end" functions, regcomp() and regexec(),
+ * or of the char versions of the compile and execute functions. To
+ * suppress the front-end functions, define __REG_NOFRONT. To suppress
+ * the char versions, define __REG_NOCHAR.
+ *
+ * The right place to do those defines (and some others you may want, see
+ * below) would be <sys/types.h>. If you don't have control of that file,
+ * the right place to add your own defines to this file is marked below.
+ * This is normally done automatically, by the makefile and regmkhdr, based
+ * on the contents of regcustom.h.
+ */
+
+
+
+/*
+ * voodoo for C++
+ */
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+
+/*
+ * Add your own defines, if needed, here. The --- stuff is for automatic
+ * generation of this file from regproto.h and regcustom.h.
+ */
+/* --- begin --- */
+/* ensure certain things don't sneak in from system headers */
+#ifdef __REG_WIDE_T
+#undef __REG_WIDE_T
+#endif
+#ifdef __REG_WIDE_COMPILE
+#undef __REG_WIDE_COMPILE
+#endif
+#ifdef __REG_WIDE_EXEC
+#undef __REG_WIDE_EXEC
+#endif
+#ifdef __REG_REGOFF_T
+#undef __REG_REGOFF_T
+#endif
+#ifdef __REG_VOID_T
+#undef __REG_VOID_T
+#endif
+#ifdef __REG_CONST
+#undef __REG_CONST
+#endif
+/* interface types */
+#define __REG_WIDE_T Tcl_UniChar
+#define __REG_WIDE_COMPILE re_ucomp
+#define __REG_WIDE_EXEC re_uexec
+#define __REG_REGOFF_T long /* not really right, but good enough... */
+#define __REG_VOID_T VOID
+#define __REG_CONST CONST
+#ifndef __REG_NOFRONT
+#define __REG_NOFRONT /* don't want regcomp() and regexec() */
+#endif
+#ifndef __REG_NOCHAR
+#define __REG_NOCHAR /* or the char versions */
+#endif
+/* --- end --- */
+
+
+/*
+ * interface types etc.
+ */
+
+/*
+ * regoff_t has to be large enough to hold either off_t or ssize_t,
+ * and must be signed; it's only a guess that long is suitable, so we
+ * offer <sys/types.h> an override.
+ */
+#ifdef __REG_REGOFF_T
+typedef __REG_REGOFF_T regoff_t;
+#else
+typedef long regoff_t;
+#endif
+
+/*
+ * For benefit of old compilers, we offer <sys/types.h> the option of
+ * overriding the `void' type used to declare nonexistent return types.
+ */
+#ifdef __REG_VOID_T
+typedef __REG_VOID_T re_void;
+#else
+typedef void re_void;
+#endif
+
+/*
+ * Also for benefit of old compilers, <sys/types.h> can supply a macro
+ * which expands to a substitute for `const'.
+ */
+#ifndef __REG_CONST
+#define __REG_CONST const
+#endif
+
+
+
+/*
+ * other interface types
+ */
+
+/* the biggie, a compiled RE (or rather, a front end to same) */
+typedef struct {
+ int re_magic; /* magic number */
+ size_t re_nsub; /* number of subexpressions */
+ int re_info; /* information about RE */
+# define REG_UBACKREF 000001
+# define REG_ULOOKAHEAD 000002
+# define REG_UBOUNDS 000004
+# define REG_UBRACES 000010
+# define REG_UBSALNUM 000020
+# define REG_UPBOTCH 000040
+# define REG_UBBS 000100
+# define REG_UNONPOSIX 000200
+# define REG_UUNSPEC 000400
+# define REG_UUNPORT 001000
+# define REG_ULOCALE 002000
+# define REG_UEMPTYMATCH 004000
+ int re_csize; /* sizeof(character) */
+ char *re_endp; /* backward compatibility kludge */
+ /* the rest is opaque pointers to hidden innards */
+ char *re_guts; /* `char *' is more portable than `void *' */
+ char *re_fns;
+} regex_t;
+
+/* result reporting (may acquire more fields later) */
+typedef struct {
+ regoff_t rm_so; /* start of substring */
+ regoff_t rm_eo; /* end of substring */
+} regmatch_t;
+
+/* supplementary control and reporting (placeholder for later work) */
+typedef struct {
+ int rm_dummy;
+} rm_detail_t;
+
+
+
+/*
+ * compilation
+ ^ #ifndef __REG_NOCHAR
+ ^ int re_comp(regex_t *, __REG_CONST char *, size_t, int);
+ ^ #endif
+ ^ #ifndef __REG_NOFRONT
+ ^ int regcomp(regex_t *, __REG_CONST char *, int);
+ ^ #endif
+ ^ #ifdef __REG_WIDE_T
+ ^ int __REG_WIDE_COMPILE(regex_t *, __REG_CONST __REG_WIDE_T *, size_t, int);
+ ^ #endif
+ */
+#define REG_BASIC 000000 /* BREs (convenience) */
+#define REG_EXTENDED 000001 /* EREs */
+#define REG_ADVF 000002 /* advanced features in EREs */
+#define REG_ADVANCED 000003 /* AREs (which are also EREs) */
+#define REG_QUOTE 000004 /* no special characters, none */
+#define REG_NOSPEC REG_QUOTE /* historical synonym */
+#define REG_ICASE 000010 /* ignore case */
+#define REG_NOSUB 000020 /* don't care about subexpressions */
+#define REG_EXPANDED 000040 /* expanded format, white space & comments */
+#define REG_NLSTOP 000100 /* \n doesn't match . or [^ ] */
+#define REG_NLANCH 000200 /* ^ matches after \n, $ before */
+#define REG_NEWLINE 000300 /* newlines are line terminators */
+#define REG_PEND 000400 /* ugh -- backward-compatibility hack */
+#define REG_DUMP 004000 /* none of your business :-) */
+#define REG_FAKEEC 010000 /* none of your business :-) */
+#define REG_PROGRESS 020000 /* none of your business :-) */
+
+
+
+/*
+ * execution
+ ^ #ifndef __REG_NOCHAR
+ ^ int re_exec(regex_t *, __REG_CONST char *, size_t,
+ ^ rm_detail_t *, size_t, regmatch_t [], int);
+ ^ #endif
+ ^ #ifndef __REG_NOFRONT
+ ^ int regexec(regex_t *, __REG_CONST char *, size_t, regmatch_t [], int);
+ ^ #endif
+ ^ #ifdef __REG_WIDE_T
+ ^ int __REG_WIDE_EXEC(regex_t *, __REG_CONST __REG_WIDE_T *, size_t,
+ ^ rm_detail_t *, size_t, regmatch_t [], int);
+ ^ #endif
+ */
+#define REG_NOTBOL 0001 /* BOS is not BOL */
+#define REG_NOTEOL 0002 /* EOS is not EOL */
+#define REG_STARTEND 0004 /* backward compatibility kludge */
+#define REG_FTRACE 0010 /* none of your business */
+#define REG_MTRACE 0020 /* none of your business */
+#define REG_SMALL 0040 /* none of your business */
+
+
+
+/*
+ * misc generics (may be more functions here eventually)
+ ^ re_void regfree(regex_t *);
+ */
+
+
+
+/*
+ * error reporting
+ * Be careful if modifying the list of error codes -- the table used by
+ * regerror() is generated automatically from this file!
+ *
+ * Note that there is no wide-char variant of regerror at this time; what
+ * kind of character is used for error reports is independent of what kind
+ * is used in matching.
+ *
+ ^ extern size_t regerror(int, __REG_CONST regex_t *, char *, size_t);
+ */
+#define REG_OKAY 0 /* no errors detected */
+#define REG_NOMATCH 1 /* failed to match */
+#define REG_BADPAT 2 /* invalid regexp */
+#define REG_ECOLLATE 3 /* invalid collating element */
+#define REG_ECTYPE 4 /* invalid character class */
+#define REG_EESCAPE 5 /* invalid escape \ sequence */
+#define REG_ESUBREG 6 /* invalid backreference number */
+#define REG_EBRACK 7 /* brackets [] not balanced */
+#define REG_EPAREN 8 /* parentheses () not balanced */
+#define REG_EBRACE 9 /* braces {} not balanced */
+#define REG_BADBR 10 /* invalid repetition count(s) */
+#define REG_ERANGE 11 /* invalid character range */
+#define REG_ESPACE 12 /* out of memory */
+#define REG_BADRPT 13 /* quantifier operand invalid */
+#define REG_ASSERT 15 /* "can't happen" -- you found a bug */
+#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_IMPOSS 19 /* can never match */
+/* two specials for debugging and testing */
+#define REG_ATOI 101 /* convert error-code name to number */
+#define REG_ITOA 102 /* convert error-code number to name */
+
+
+
+/*
+ * the prototypes, as possibly munched by regfwd
+ */
+/* =====^!^===== begin forwards =====^!^===== */
+/* automatically gathered by fwd; do not hand-edit */
+/* === regproto.h === */
+#ifndef __REG_NOCHAR
+int re_comp _ANSI_ARGS_((regex_t *, __REG_CONST char *, size_t, int));
+#endif
+#ifndef __REG_NOFRONT
+int regcomp _ANSI_ARGS_((regex_t *, __REG_CONST char *, int));
+#endif
+#ifdef __REG_WIDE_T
+int __REG_WIDE_COMPILE _ANSI_ARGS_((regex_t *, __REG_CONST __REG_WIDE_T *, size_t, int));
+#endif
+#ifndef __REG_NOCHAR
+int re_exec _ANSI_ARGS_((regex_t *, __REG_CONST char *, size_t, rm_detail_t *, size_t, regmatch_t [], int));
+#endif
+#ifndef __REG_NOFRONT
+int regexec _ANSI_ARGS_((regex_t *, __REG_CONST char *, size_t, regmatch_t [], int));
+#endif
+#ifdef __REG_WIDE_T
+int __REG_WIDE_EXEC _ANSI_ARGS_((regex_t *, __REG_CONST __REG_WIDE_T *, size_t, rm_detail_t *, size_t, regmatch_t [], int));
+#endif
+re_void regfree _ANSI_ARGS_((regex_t *));
+extern size_t regerror _ANSI_ARGS_((int, __REG_CONST regex_t *, char *, size_t));
+/* automatically gathered by fwd; do not hand-edit */
+/* =====^!^===== end forwards =====^!^===== */
+
+
+
+/*
+ * more C++ voodoo
+ */
+#ifdef __cplusplus
+}
+#endif
+
+
+
+#endif
diff --git a/generic/exec.c b/generic/regexec.c
index 92439aa..4220062 100644
--- a/generic/exec.c
+++ b/generic/regexec.c
@@ -1,43 +1,9 @@
/*
- * exec.c --
- *
- * Regexp package file: re_*exec and friends - match REs
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: exec.c,v 1.1.2.2 1998/10/05 17:38:26 stanton Exp $
+ * re_*exec and friends - match REs
*/
-#include "tclInt.h"
-#include <assert.h>
-#include "tclRegexp.h"
-#include "chr.h"
-#include "guts.h"
+#include "regguts.h"
+
/* internal variables, bundled for easy passing around */
@@ -75,6 +41,7 @@ struct sset { /* state set */
int flags;
# define STARTER 01 /* the initial state set */
# define POSTSTATE 02 /* includes the goal state */
+# define LOCKED 04 /* locked in cache */
struct arcp ins; /* chain of inarcs pointing here */
chr *lastseen; /* last entered on arrival here */
struct sset **outs; /* outarc vector indexed by color */
@@ -95,6 +62,7 @@ struct dfa {
struct cnfa *cnfa;
struct colormap *cm;
chr *lastpost; /* location of last cache-flushed success */
+ struct sset *search; /* replacement-search-pointer memory */
};
#define CACHE 200
@@ -107,8 +75,8 @@ struct dfa {
*/
/* =====^!^===== begin forwards =====^!^===== */
/* automatically gathered by fwd; do not hand-edit */
-/* === exec.c === */
-int exec _ANSI_ARGS_((regex_t *, CONST chr *, size_t, size_t, regmatch_t [], int));
+/* === regexec.c === */
+int exec _ANSI_ARGS_((regex_t *, CONST chr *, size_t, rm_detail_t *, size_t, regmatch_t [], int));
static int find _ANSI_ARGS_((struct vars *, struct cnfa *, struct colormap *));
static int cfind _ANSI_ARGS_((struct vars *, struct cnfa *, struct colormap *));
static VOID zapmatches _ANSI_ARGS_((regmatch_t *, size_t));
@@ -130,13 +98,10 @@ static struct dfa *newdfa _ANSI_ARGS_((struct vars *, struct cnfa *, struct colo
static VOID freedfa _ANSI_ARGS_((struct dfa *));
static unsigned hash _ANSI_ARGS_((unsigned *, int));
static struct sset *initialize _ANSI_ARGS_((struct vars *, struct dfa *, chr *));
-static struct sset *miss _ANSI_ARGS_((struct vars *, struct dfa *, struct sset *, pcolor, chr *));
+static struct sset *miss _ANSI_ARGS_((struct vars *, struct dfa *, struct sset *, pcolor, chr *, chr *));
static int lacon _ANSI_ARGS_((struct vars *, struct cnfa *, chr *, pcolor));
-static struct sset *getvacant _ANSI_ARGS_((struct vars *, struct dfa *));
-static struct sset *pickss _ANSI_ARGS_((struct vars *, struct dfa *));
-/* === color.c === */
-union tree;
-static color getcolor _ANSI_ARGS_((struct colormap *, pchr));
+static struct sset *getvacant _ANSI_ARGS_((struct vars *, struct dfa *, chr *, chr *));
+static struct sset *pickss _ANSI_ARGS_((struct vars *, struct dfa *, chr *, chr *));
/* automatically gathered by fwd; do not hand-edit */
/* =====^!^===== end forwards =====^!^===== */
@@ -144,13 +109,15 @@ static color getcolor _ANSI_ARGS_((struct colormap *, pchr));
/*
- exec - match regular expression
- ^ int exec(regex_t *, CONST chr *, size_t, size_t, regmatch_t [], int);
+ ^ int exec(regex_t *, CONST chr *, size_t, rm_detail_t *,
+ ^ size_t, regmatch_t [], int);
*/
int
-exec(re, string, len, nmatch, pmatch, flags)
+exec(re, string, len, details, nmatch, pmatch, flags)
regex_t *re;
CONST chr *string;
size_t len;
+rm_detail_t *details; /* hook for future elaboration */
size_t nmatch;
regmatch_t pmatch[];
int flags;
@@ -177,9 +144,9 @@ int flags;
if (v->g->cflags&REG_NOSUB)
nmatch = 0; /* override client */
v->nmatch = nmatch;
- if (complications && v->nmatch < (size_t)(v->g->nsub + 1)) {
+ if (complications && v->nmatch < v->g->nsub + 1) {
/* need work area bigger than what user gave us */
- v->pmatch = (regmatch_t *)ckalloc((v->g->nsub + 1) *
+ v->pmatch = (regmatch_t *)MALLOC((v->g->nsub + 1) *
sizeof(regmatch_t));
if (v->pmatch == NULL)
return REG_ESPACE;
@@ -190,10 +157,10 @@ int flags;
v->stop = (chr *)string + len;
v->err = 0;
if (complications) {
- v->mem1 = (regoff_t *)ckalloc(2*v->g->ntree*sizeof(regoff_t));
+ v->mem1 = (regoff_t *)MALLOC(2*v->g->ntree*sizeof(regoff_t));
if (v->mem1 == NULL) {
if (v->pmatch != pmatch)
- ckfree((char *)v->pmatch);
+ FREE(v->pmatch);
return REG_ESPACE;
}
v->mem2 = v->mem1 + v->g->ntree;
@@ -208,12 +175,12 @@ int flags;
if (st == REG_OKAY && v->pmatch != pmatch && nmatch > 0) {
zapmatches(pmatch, nmatch);
n = (nmatch < v->nmatch) ? nmatch : v->nmatch;
- memcpy((VOID *)pmatch, (VOID *)v->pmatch, n*sizeof(regmatch_t));
+ memcpy(VS(pmatch), VS(v->pmatch), n*sizeof(regmatch_t));
}
if (v->pmatch != pmatch)
- ckfree((char *)v->pmatch);
+ FREE(v->pmatch);
if (v->mem1 != NULL)
- ckfree((char *)v->mem1);
+ FREE(v->mem1);
return st;
}
@@ -230,15 +197,14 @@ struct colormap *cm;
struct dfa *d = newdfa(v, cnfa, cm);
chr *begin;
chr *end;
- chr *stop = (cnfa->leftanch) ? v->start : v->stop;
+ chr *stop = (cnfa->flags&LEFTANCH) ? v->start : v->stop;
if (d == NULL)
return v->err;
for (begin = v->start; begin <= stop; begin++) {
- if (v->eflags&REG_MTRACE)
- printf("\ntrying at %ld\n", (long)OFF(begin));
- end = longest(v, d, begin, v->stop);
+ MDEBUG(("\ntrying at %ld\n", (long)OFF(begin)));
+ end = longest(v, d, begin, v->stop);
if (end != NULL) {
if (v->nmatch > 0) {
v->pmatch[0].rm_so = OFF(begin);
@@ -249,11 +215,15 @@ struct colormap *cm;
zapmatches(v->pmatch, v->nmatch);
return dissect(v, v->g->tree, begin, end);
}
+ if (ISERR())
+ return v->err;
return REG_OKAY;
}
}
freedfa(d);
+ if (ISERR())
+ return v->err;
return REG_NOMATCH;
}
@@ -270,7 +240,7 @@ struct colormap *cm;
struct dfa *d = newdfa(v, cnfa, cm);
chr *begin;
chr *end;
- chr *stop = (cnfa->leftanch) ? v->start : v->stop;
+ chr *stop = (cnfa->flags&LEFTANCH) ? v->start : v->stop;
chr *estop;
int er;
int usedis = (v->g->tree == NULL || v->g->tree->op == '|') ? 0 : 1;
@@ -281,12 +251,11 @@ struct colormap *cm;
if (!v->g->usedshorter)
usedis = 0;
for (begin = v->start; begin <= stop; begin++) {
- if (v->eflags&REG_MTRACE)
- printf("\ntrying at %ld\n", (long)OFF(begin));
+ MDEBUG(("\ntrying at %ld\n", (long)OFF(begin)));
if (usedis) {
v->mem = v->mem1;
zapmem(v, v->g->tree);
- }
+ }
estop = v->stop;
for (;;) {
if (usedis) {
@@ -296,8 +265,7 @@ struct colormap *cm;
end = longest(v, d, begin, estop);
if (end == NULL)
break; /* NOTE BREAK OUT */
- if (v->eflags&REG_MTRACE)
- printf("tentative end %ld\n", (long)OFF(end));
+ MDEBUG(("tentative end %ld\n", (long)OFF(end)));
zapmatches(v->pmatch, v->nmatch);
v->mem = v->mem2;
zapmem(v, v->g->tree);
@@ -309,7 +277,10 @@ struct colormap *cm;
v->pmatch[0].rm_eo = OFF(end);
}
freedfa(d);
+ if (ISERR())
+ return v->err;
return REG_OKAY;
+ break;
case REG_NOMATCH:
/* go around and try again */
if (!usedis) {
@@ -324,11 +295,14 @@ struct colormap *cm;
default:
freedfa(d);
return er;
+ break;
}
}
}
freedfa(d);
+ if (ISERR())
+ return v->err;
return REG_NOMATCH;
}
@@ -343,7 +317,7 @@ size_t n;
{
size_t i;
- for (i = 1; i < n; i++) {
+ for (i = n-1; i > 0; i--) {
p[i].rm_so = -1;
p[i].rm_eo = -1;
}
@@ -399,8 +373,7 @@ chr *end;
if ((size_t)n >= v->nmatch)
return;
- if (v->eflags&REG_MTRACE)
- printf("setting %d\n", n);
+ MDEBUG(("setting %d\n", n));
v->pmatch[n].rm_so = OFF(begin);
v->pmatch[n].rm_eo = OFF(end);
}
@@ -423,8 +396,7 @@ chr *end; /* end of same */
if (rt == NULL)
return REG_OKAY;
- if (v->eflags&REG_MTRACE)
- printf("substring %ld-%ld\n", (long)OFF(begin), (long)OFF(end));
+ MDEBUG(("substring %ld-%ld\n", (long)OFF(begin), (long)OFF(end)));
/* alternatives -- punt to auxiliary */
if (rt->op == '|')
@@ -439,8 +411,7 @@ chr *end; /* end of same */
/* in some cases, there may be no right side... */
if (rt->right.cnfa.nstates == 0) {
- if (v->eflags&REG_MTRACE)
- printf("singleton\n");
+ MDEBUG(("singleton\n"));
if (longest(v, d, begin, end) != end) {
freedfa(d);
return REG_ASSERT;
@@ -466,16 +437,14 @@ chr *end; /* end of same */
freedfa(d2);
return REG_ASSERT;
}
- if (v->eflags&REG_MTRACE)
- printf("tentative midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("tentative midpoint %ld\n", (long)OFF(mid)));
/* iterate until satisfaction or failure */
while (longest(v, d2, mid, end) != end) {
/* that midpoint didn't work, find a new one */
if (mid == begin) {
/* all possibilities exhausted! */
- if (v->eflags&REG_MTRACE)
- printf("no midpoint!\n");
+ MDEBUG(("no midpoint!\n"));
freedfa(d);
freedfa(d2);
return REG_ASSERT;
@@ -483,19 +452,16 @@ chr *end; /* end of same */
mid = longest(v, d, begin, mid-1);
if (mid == NULL) {
/* failed to find a new one! */
- if (v->eflags&REG_MTRACE)
- printf("failed midpoint!\n");
+ MDEBUG(("failed midpoint!\n"));
freedfa(d);
freedfa(d2);
return REG_ASSERT;
}
- if (v->eflags&REG_MTRACE)
- printf("new midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("new midpoint %ld\n", (long)OFF(mid)));
}
/* satisfaction */
- if (v->eflags&REG_MTRACE)
- printf("successful\n");
+ MDEBUG(("successful\n"));
freedfa(d);
freedfa(d2);
assert(rt->left.subno >= 0);
@@ -526,15 +492,13 @@ chr *end; /* end of same */
assert(rt->op == '|');
for (i = 0; rt != NULL; rt = rt->next, i++) {
- if (v->eflags&REG_MTRACE)
- printf("trying %dth\n", i);
+ MDEBUG(("trying %dth\n", i));
assert(rt->left.begin != NULL);
d = newdfa(v, &rt->left.cnfa, v->g->cm);
if (ISERR())
return v->err;
if (longest(v, d, begin, end) == end) {
- if (v->eflags&REG_MTRACE)
- printf("success\n");
+ MDEBUG(("success\n"));
freedfa(d);
assert(rt->left.subno >= 0);
subset(v, &rt->left, begin, end);
@@ -565,8 +529,7 @@ chr *end; /* end of same */
if (rt == NULL)
return REG_OKAY;
- if (v->eflags&REG_MTRACE)
- printf("csubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end));
+ MDEBUG(("csubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end)));
/* punt various cases to auxiliaries */
if (rt->op == '|') /* alternatives */
@@ -590,8 +553,7 @@ chr *end; /* end of same */
freedfa(d);
return v->err;
}
- if (v->eflags&REG_MTRACE)
- printf("cconcat %d\n", rt->no);
+ MDEBUG(("cconcat %d\n", rt->no));
/* pick a tentative midpoint */
if (v->mem[rt->no] == 0) {
@@ -601,14 +563,12 @@ chr *end; /* end of same */
freedfa(d2);
return REG_NOMATCH;
}
- if (v->eflags&REG_MTRACE)
- printf("tentative midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("tentative midpoint %ld\n", (long)OFF(mid)));
subset(v, &rt->left, begin, mid);
v->mem[rt->no] = (mid - begin) + 1;
} else {
mid = begin + (v->mem[rt->no] - 1);
- if (v->eflags&REG_MTRACE)
- printf("working midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("working midpoint %ld\n", (long)OFF(mid)));
}
/* iterate until satisfaction or failure */
@@ -628,8 +588,7 @@ chr *end; /* end of same */
/* that midpoint didn't work, find a new one */
if (mid == begin) {
/* all possibilities exhausted */
- if (v->eflags&REG_MTRACE)
- printf("%d no midpoint\n", rt->no);
+ MDEBUG(("%d no midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return REG_NOMATCH;
@@ -637,15 +596,12 @@ chr *end; /* end of same */
mid = longest(v, d, begin, mid-1);
if (mid == NULL) {
/* failed to find a new one */
- if (v->eflags&REG_MTRACE)
- printf("%d failed midpoint\n", rt->no);
+ MDEBUG(("%d failed midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return REG_NOMATCH;
}
- if (v->eflags&REG_MTRACE)
- printf("%d: new midpoint %ld\n", rt->no,
- (long)OFF(mid));
+ MDEBUG(("%d: new midpoint %ld\n", rt->no, (long)OFF(mid)));
subset(v, &rt->left, begin, mid);
v->mem[rt->no] = (mid - begin) + 1;
zapmem(v, rt->left.tree);
@@ -653,8 +609,7 @@ chr *end; /* end of same */
}
/* satisfaction */
- if (v->eflags&REG_MTRACE)
- printf("successful\n");
+ MDEBUG(("successful\n"));
freedfa(d);
freedfa(d2);
subset(v, &rt->right, mid, end);
@@ -694,8 +649,7 @@ chr *end; /* end of same */
freedfa(d);
return v->err;
}
- if (v->eflags&REG_MTRACE)
- printf("crev %d\n", rt->no);
+ MDEBUG(("crev %d\n", rt->no));
/* pick a tentative midpoint */
if (v->mem[rt->no] == 0) {
@@ -705,14 +659,12 @@ chr *end; /* end of same */
freedfa(d2);
return REG_NOMATCH;
}
- if (v->eflags&REG_MTRACE)
- printf("tentative midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("tentative midpoint %ld\n", (long)OFF(mid)));
subset(v, &rt->left, begin, mid);
v->mem[rt->no] = (mid - begin) + 1;
} else {
mid = begin + (v->mem[rt->no] - 1);
- if (v->eflags&REG_MTRACE)
- printf("working midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("working midpoint %ld\n", (long)OFF(mid)));
}
/* iterate until satisfaction or failure */
@@ -732,8 +684,7 @@ chr *end; /* end of same */
/* that midpoint didn't work, find a new one */
if (mid == end) {
/* all possibilities exhausted */
- if (v->eflags&REG_MTRACE)
- printf("%d no midpoint\n", rt->no);
+ MDEBUG(("%d no midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return REG_NOMATCH;
@@ -741,15 +692,12 @@ chr *end; /* end of same */
mid = shortest(v, d, begin, mid+1, end);
if (mid == NULL) {
/* failed to find a new one */
- if (v->eflags&REG_MTRACE)
- printf("%d failed midpoint\n", rt->no);
+ MDEBUG(("%d failed midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return REG_NOMATCH;
}
- if (v->eflags&REG_MTRACE)
- printf("%d: new midpoint %ld\n", rt->no,
- (long)OFF(mid));
+ MDEBUG(("%d: new midpoint %ld\n", rt->no, (long)OFF(mid)));
subset(v, &rt->left, begin, mid);
v->mem[rt->no] = (mid - begin) + 1;
zapmem(v, rt->left.tree);
@@ -757,8 +705,7 @@ chr *end; /* end of same */
}
/* satisfaction */
- if (v->eflags&REG_MTRACE)
- printf("successful\n");
+ MDEBUG(("successful\n"));
freedfa(d);
freedfa(d2);
subset(v, &rt->right, mid, end);
@@ -782,8 +729,7 @@ chr *end; /* end of same */
assert(rt != NULL);
assert(rt->op == ',');
assert(rt->right.cnfa.nstates == 0);
- if (v->eflags&REG_MTRACE)
- printf("csingleton %d\n", rt->no);
+ MDEBUG(("csingleton %d\n", rt->no));
assert(rt->left.cnfa.nstates > 0);
@@ -796,8 +742,7 @@ chr *end; /* end of same */
}
freedfa(d);
v->mem[rt->no] = 1;
- if (v->eflags&REG_MTRACE)
- printf("csingleton matched\n");
+ MDEBUG(("csingleton matched\n"));
}
er = cdissect(v, rt->left.tree, begin, end);
@@ -830,10 +775,10 @@ chr *end; /* end of same */
assert(rt != NULL);
assert(rt->op == 'b');
assert(rt->right.cnfa.nstates == 0);
+ assert(n >= 0);
assert((size_t)n < v->nmatch);
- if (v->eflags&REG_MTRACE)
- printf("cbackref n%d %d{%d-%d}\n", rt->no, n, min, max);
+ MDEBUG(("cbackref n%d %d{%d-%d}\n", rt->no, n, min, max));
if (v->pmatch[n].rm_so == -1)
return REG_NOMATCH;
@@ -853,6 +798,7 @@ chr *end; /* end of same */
}
/* and too-short string */
+ assert(end >= begin);
if ((size_t)(end - begin) < len)
return REG_NOMATCH;
stop = end - len;
@@ -864,8 +810,7 @@ chr *end; /* end of same */
break;
i++;
}
- if (v->eflags&REG_MTRACE)
- printf("cbackref found %d\n", i);
+ MDEBUG(("cbackref found %d\n", i));
/* and sort it out */
if (p != end) /* didn't consume all of it */
@@ -898,8 +843,7 @@ chr *end; /* end of same */
if (v->mem[rt->no] == TRIED)
return caltdissect(v, rt->next, begin, end);
- if (v->eflags&REG_MTRACE)
- printf("calt n%d\n", rt->no);
+ MDEBUG(("calt n%d\n", rt->no));
assert(rt->left.begin != NULL);
if (v->mem[rt->no] == UNTRIED) {
@@ -912,8 +856,7 @@ chr *end; /* end of same */
return caltdissect(v, rt->next, begin, end);
}
freedfa(d);
- if (v->eflags&REG_MTRACE)
- printf("calt matched\n");
+ MDEBUG(("calt matched\n"));
v->mem[rt->no] = TRYING;
}
@@ -949,8 +892,7 @@ chr *end; /* end of same */
if (rt == NULL)
return begin;
- if (v->eflags&REG_MTRACE)
- printf("dsubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end));
+ MDEBUG(("dsubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end)));
/* punt various cases to auxiliaries */
if (rt->right.cnfa.nstates == 0) /* no RHS */
@@ -970,8 +912,7 @@ chr *end; /* end of same */
freedfa(d);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("dconcat %d\n", rt->no);
+ MDEBUG(("dconcat %d\n", rt->no));
/* pick a tentative midpoint */
if (v->mem[rt->no] == 0) {
@@ -981,13 +922,11 @@ chr *end; /* end of same */
freedfa(d2);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("tentative midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("tentative midpoint %ld\n", (long)OFF(mid)));
v->mem[rt->no] = (mid - begin) + 1;
} else {
mid = begin + (v->mem[rt->no] - 1);
- if (v->eflags&REG_MTRACE)
- printf("working midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("working midpoint %ld\n", (long)OFF(mid)));
}
/* iterate until satisfaction or failure */
@@ -1010,8 +949,7 @@ chr *end; /* end of same */
/* that midpoint didn't work, find a new one */
if (mid == begin) {
/* all possibilities exhausted */
- if (v->eflags&REG_MTRACE)
- printf("%d no midpoint\n", rt->no);
+ MDEBUG(("%d no midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return NULL;
@@ -1019,22 +957,18 @@ chr *end; /* end of same */
mid = longest(v, d, begin, mid-1);
if (mid == NULL) {
/* failed to find a new one */
- if (v->eflags&REG_MTRACE)
- printf("%d failed midpoint\n", rt->no);
+ MDEBUG(("%d failed midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("%d: new midpoint %ld\n", rt->no,
- (long)OFF(mid));
+ MDEBUG(("%d: new midpoint %ld\n", rt->no, (long)OFF(mid)));
v->mem[rt->no] = (mid - begin) + 1;
zapmem(v, rt->right.tree);
}
/* satisfaction */
- if (v->eflags&REG_MTRACE)
- printf("successful\n");
+ MDEBUG(("successful\n"));
freedfa(d);
freedfa(d2);
return ret;
@@ -1060,8 +994,7 @@ chr *end; /* end of same */
if (rt == NULL)
return begin;
- if (v->eflags&REG_MTRACE)
- printf("rsubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end));
+ MDEBUG(("rsubstr %ld-%ld\n", (long)OFF(begin), (long)OFF(end)));
/* concatenation -- need to split the substring between parts */
assert(rt->op == ',');
@@ -1075,8 +1008,7 @@ chr *end; /* end of same */
freedfa(d);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("dconcat %d\n", rt->no);
+ MDEBUG(("dconcat %d\n", rt->no));
/* pick a tentative midpoint */
if (v->mem[rt->no] == 0) {
@@ -1086,13 +1018,11 @@ chr *end; /* end of same */
freedfa(d2);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("tentative midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("tentative midpoint %ld\n", (long)OFF(mid)));
v->mem[rt->no] = (mid - begin) + 1;
} else {
mid = begin + (v->mem[rt->no] - 1);
- if (v->eflags&REG_MTRACE)
- printf("working midpoint %ld\n", (long)OFF(mid));
+ MDEBUG(("working midpoint %ld\n", (long)OFF(mid)));
}
/* iterate until satisfaction or failure */
@@ -1115,8 +1045,7 @@ chr *end; /* end of same */
/* that midpoint didn't work, find a new one */
if (mid == end) {
/* all possibilities exhausted */
- if (v->eflags&REG_MTRACE)
- printf("%d no midpoint\n", rt->no);
+ MDEBUG(("%d no midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return NULL;
@@ -1124,22 +1053,18 @@ chr *end; /* end of same */
mid = shortest(v, d, begin, mid+1, end);
if (mid == NULL) {
/* failed to find a new one */
- if (v->eflags&REG_MTRACE)
- printf("%d failed midpoint\n", rt->no);
+ MDEBUG(("%d failed midpoint\n", rt->no));
freedfa(d);
freedfa(d2);
return NULL;
}
- if (v->eflags&REG_MTRACE)
- printf("%d: new midpoint %ld\n", rt->no,
- (long)OFF(mid));
+ MDEBUG(("%d: new midpoint %ld\n", rt->no, (long)OFF(mid)));
v->mem[rt->no] = (mid - begin) + 1;
zapmem(v, rt->right.tree);
}
/* satisfaction */
- if (v->eflags&REG_MTRACE)
- printf("successful\n");
+ MDEBUG(("successful\n"));
freedfa(d);
freedfa(d2);
return ret;
@@ -1162,8 +1087,7 @@ chr *end; /* end of same */
assert(rt != NULL);
assert(rt->op == ',');
assert(rt->right.cnfa.nstates == 0);
- if (v->eflags&REG_MTRACE)
- printf("dsingleton %d\n", rt->no);
+ MDEBUG(("dsingleton %d\n", rt->no));
assert(rt->left.cnfa.nstates > 0);
@@ -1180,8 +1104,8 @@ chr *end; /* end of same */
else
ret = shortest(v, d, begin, begin, end);
freedfa(d);
- if (ret != NULL && (v->eflags&REG_MTRACE))
- printf("dsingleton matched\n");
+ if (ret != NULL)
+ MDEBUG(("dsingleton matched\n"));
return ret;
}
@@ -1210,18 +1134,15 @@ chr *stop; /* match must end at or before here */
cp = start;
/* startup */
- if (v->eflags&REG_FTRACE)
- printf("+++ startup +++\n");
+ FDEBUG(("+++ startup +++\n"));
if (cp == v->start) {
co = d->cnfa->bos[(v->eflags&REG_NOTBOL) ? 0 : 1];
- if (v->eflags&REG_FTRACE)
- printf("color %ld\n", (long)co);
+ FDEBUG(("color %ld\n", (long)co));
} else {
- co = getcolor(cm, *(cp - 1));
- if (v->eflags&REG_FTRACE)
- printf("char %c, color %ld\n", (char)*(cp-1), (long)co);
+ co = GETCOLOR(cm, *(cp - 1));
+ FDEBUG(("char %c, color %ld\n", (char)*(cp-1), (long)co));
}
- css = miss(v, d, css, co, cp);
+ css = miss(v, d, css, co, cp, start);
if (css == NULL)
return NULL;
css->lastseen = cp;
@@ -1229,12 +1150,12 @@ chr *stop; /* match must end at or before here */
/* main loop */
if (v->eflags&REG_FTRACE)
while (cp < realstop) {
- printf("+++ at c%d +++\n", css - d->ssets);
- co = getcolor(cm, *cp);
- printf("char %c, color %ld\n", (char)*cp, (long)co);
+ FDEBUG(("+++ at c%d +++\n", css - d->ssets));
+ co = GETCOLOR(cm, *cp);
+ FDEBUG(("char %c, color %ld\n", (char)*cp, (long)co));
ss = css->outs[co];
if (ss == NULL) {
- ss = miss(v, d, css, co, cp);
+ ss = miss(v, d, css, co, cp+1, start);
if (ss == NULL)
break; /* NOTE BREAK OUT */
}
@@ -1244,10 +1165,10 @@ chr *stop; /* match must end at or before here */
}
else
while (cp < realstop) {
- co = getcolor(cm, *cp);
+ co = GETCOLOR(cm, *cp);
ss = css->outs[co];
if (ss == NULL) {
- ss = miss(v, d, css, co, cp+1);
+ ss = miss(v, d, css, co, cp+1, start);
if (ss == NULL)
break; /* NOTE BREAK OUT */
}
@@ -1257,13 +1178,11 @@ chr *stop; /* match must end at or before here */
}
/* shutdown */
- if (v->eflags&REG_FTRACE)
- printf("+++ shutdown at c%d +++\n", css - d->ssets);
+ FDEBUG(("+++ shutdown at c%d +++\n", css - d->ssets));
if (cp == v->stop && stop == v->stop) {
co = d->cnfa->eos[(v->eflags&REG_NOTEOL) ? 0 : 1];
- if (v->eflags&REG_FTRACE)
- printf("color %ld\n", (long)co);
- ss = miss(v, d, css, co, cp);
+ FDEBUG(("color %ld\n", (long)co));
+ ss = miss(v, d, css, co, cp, start);
/* special case: match ended at eol? */
if (ss != NULL && (ss->flags&POSTSTATE))
return cp;
@@ -1300,7 +1219,7 @@ chr *max; /* match must end at or before here */
chr *realmax = (max == v->stop) ? max : max + 1;
color co;
struct sset *css;
- struct sset *ss = NULL;
+ struct sset *ss;
struct colormap *cm = d->cm;
/* initialize */
@@ -1308,31 +1227,29 @@ chr *max; /* match must end at or before here */
cp = start;
/* startup */
- if (v->eflags&REG_FTRACE)
- printf("--- startup ---\n");
+ FDEBUG(("--- startup ---\n"));
if (cp == v->start) {
co = d->cnfa->bos[(v->eflags&REG_NOTBOL) ? 0 : 1];
- if (v->eflags&REG_FTRACE)
- printf("color %ld\n", (long)co);
+ FDEBUG(("color %ld\n", (long)co));
} else {
- co = getcolor(cm, *(cp - 1));
- if (v->eflags&REG_FTRACE)
- printf("char %c, color %ld\n", (char)*(cp-1), (long)co);
+ co = GETCOLOR(cm, *(cp - 1));
+ FDEBUG(("char %c, color %ld\n", (char)*(cp-1), (long)co));
}
- css = miss(v, d, css, co, cp);
+ css = miss(v, d, css, co, cp, start);
if (css == NULL)
return NULL;
css->lastseen = cp;
+ ss = css;
/* main loop */
if (v->eflags&REG_FTRACE)
while (cp < realmax) {
- printf("--- at c%d ---\n", css - d->ssets);
- co = getcolor(cm, *cp);
- printf("char %c, color %ld\n", (char)*cp, (long)co);
+ FDEBUG(("--- at c%d ---\n", css - d->ssets));
+ co = GETCOLOR(cm, *cp);
+ FDEBUG(("char %c, color %ld\n", (char)*cp, (long)co));
ss = css->outs[co];
if (ss == NULL) {
- ss = miss(v, d, css, co, cp);
+ ss = miss(v, d, css, co, cp+1, start);
if (ss == NULL)
break; /* NOTE BREAK OUT */
}
@@ -1344,10 +1261,10 @@ chr *max; /* match must end at or before here */
}
else
while (cp < realmax) {
- co = getcolor(cm, *cp);
+ co = GETCOLOR(cm, *cp);
ss = css->outs[co];
if (ss == NULL) {
- ss = miss(v, d, css, co, cp+1);
+ ss = miss(v, d, css, co, cp+1, start);
if (ss == NULL)
break; /* NOTE BREAK OUT */
}
@@ -1366,13 +1283,11 @@ chr *max; /* match must end at or before here */
}
/* shutdown */
- if (v->eflags&REG_FTRACE)
- printf("--- shutdown at c%d ---\n", css - d->ssets);
+ FDEBUG(("--- shutdown at c%d ---\n", css - d->ssets));
if (cp == v->stop && max == v->stop) {
co = d->cnfa->eos[(v->eflags&REG_NOTEOL) ? 0 : 1];
- if (v->eflags&REG_FTRACE)
- printf("color %ld\n", (long)co);
- ss = miss(v, d, css, co, cp);
+ FDEBUG(("color %ld\n", (long)co));
+ ss = miss(v, d, css, co, cp, start);
/* special case: match ended at eol? */
if (ss != NULL && (ss->flags&POSTSTATE))
return cp;
@@ -1392,7 +1307,7 @@ struct vars *v;
struct cnfa *cnfa;
struct colormap *cm;
{
- struct dfa *d = (struct dfa *)ckalloc(sizeof(struct dfa));
+ struct dfa *d = (struct dfa *)MALLOC(sizeof(struct dfa));
int wordsper = (cnfa->nstates + UBITS - 1) / UBITS;
struct sset *ss;
int i;
@@ -1403,13 +1318,13 @@ struct colormap *cm;
return NULL;
}
- d->ssets = (struct sset *)ckalloc(CACHE * sizeof(struct sset));
- d->statesarea = (unsigned *)ckalloc((CACHE+WORK) * wordsper *
+ d->ssets = (struct sset *)MALLOC(CACHE * sizeof(struct sset));
+ d->statesarea = (unsigned *)MALLOC((CACHE+WORK) * wordsper *
sizeof(unsigned));
d->work = &d->statesarea[CACHE * wordsper];
- d->outsarea = (struct sset **)ckalloc(CACHE * cnfa->ncolors *
+ d->outsarea = (struct sset **)MALLOC(CACHE * cnfa->ncolors *
sizeof(struct sset *));
- d->incarea = (struct arcp *)ckalloc(CACHE * cnfa->ncolors *
+ d->incarea = (struct arcp *)MALLOC(CACHE * cnfa->ncolors *
sizeof(struct arcp));
if (d->ssets == NULL || d->statesarea == NULL || d->outsarea == NULL ||
d->incarea == NULL) {
@@ -1426,6 +1341,7 @@ struct colormap *cm;
d->cnfa = cnfa;
d->cm = cm;
d->lastpost = NULL;
+ d->search = d->ssets;
for (ss = d->ssets, i = 0; i < d->nssets; ss++, i++) {
/* initialization of most fields is done as needed */
@@ -1446,14 +1362,14 @@ freedfa(d)
struct dfa *d;
{
if (d->ssets != NULL)
- ckfree((char *)d->ssets);
+ FREE(d->ssets);
if (d->statesarea != NULL)
- ckfree((char *)d->statesarea);
+ FREE(d->statesarea);
if (d->outsarea != NULL)
- ckfree((char *)d->outsarea);
+ FREE(d->outsarea);
if (d->incarea != NULL)
- ckfree((char *)d->incarea);
- ckfree((char *)d);
+ FREE(d->incarea);
+ FREE(d);
}
/*
@@ -1492,7 +1408,7 @@ chr *start;
if (d->nssused > 0 && (d->ssets[0].flags&STARTER))
ss = &d->ssets[0];
else { /* no, must (re)build it */
- ss = getvacant(v, d);
+ ss = getvacant(v, d, start, start);
for (i = 0; i < d->wordsper; i++)
ss->states[i] = 0;
BSET(ss->states, d->cnfa->pre);
@@ -1512,15 +1428,16 @@ chr *start;
/*
- miss - handle a cache miss
^ static struct sset *miss(struct vars *, struct dfa *, struct sset *,
- ^ pcolor, chr *);
+ ^ pcolor, chr *, chr *);
*/
static struct sset * /* NULL if goes to empty set */
-miss(v, d, css, co, cp)
+miss(v, d, css, co, cp, start)
struct vars *v; /* used only for debug flags */
struct dfa *d;
struct sset *css;
pcolor co;
chr *cp; /* next chr */
+chr *start; /* where the attempt got started */
{
struct cnfa *cnfa = d->cnfa;
int i;
@@ -1534,12 +1451,10 @@ chr *cp; /* next chr */
/* for convenience, we can be called even if it might not be a miss */
if (css->outs[co] != NULL) {
- if (v->eflags&REG_FTRACE)
- printf("hit\n");
+ FDEBUG(("hit\n"));
return css->outs[co];
}
- if (v->eflags&REG_FTRACE)
- printf("miss\n");
+ FDEBUG(("miss\n"));
/* first, what set of states would we end up in? */
for (i = 0; i < d->wordsper; i++)
@@ -1554,10 +1469,9 @@ chr *cp; /* next chr */
gotstate = 1;
if (ca->to == cnfa->post)
ispost = 1;
- if (v->eflags&REG_FTRACE)
- printf("%d -> %d\n", i, ca->to);
+ FDEBUG(("%d -> %d\n", i, ca->to));
}
- dolacons = (gotstate) ? cnfa->haslacons : 0;
+ dolacons = (gotstate) ? (cnfa->flags&HASLACONS) : 0;
didlacons = 0;
while (dolacons) { /* transitive closure */
dolacons = 0;
@@ -1574,9 +1488,7 @@ chr *cp; /* next chr */
didlacons = 1;
if (ca->to == cnfa->post)
ispost = 1;
- if (v->eflags&REG_FTRACE)
- printf("%d :-> %d\n",
- i, ca->to);
+ FDEBUG(("%d :> %d\n",i,ca->to));
}
}
if (!gotstate)
@@ -1585,14 +1497,13 @@ chr *cp; /* next chr */
/* next, is that in the cache? */
for (p = d->ssets, i = d->nssused; i > 0; p++, i--)
- if (p->hash == h && memcmp((VOID *)d->work, (VOID *)p->states,
+ if (p->hash == h && memcmp(VS(d->work), VS(p->states),
d->wordsper*sizeof(unsigned)) == 0) {
- if (v->eflags&REG_FTRACE)
- printf("cached c%d\n", p - d->ssets);
+ FDEBUG(("cached c%d\n", p - d->ssets));
break; /* NOTE BREAK OUT */
}
if (i == 0) { /* nope, need a new cache entry */
- p = getvacant(v, d);
+ p = getvacant(v, d, cp, start);
assert(p != css);
for (i = 0; i < d->wordsper; i++)
p->states[i] = d->work[i];
@@ -1605,7 +1516,7 @@ chr *cp; /* next chr */
css->outs[co] = p;
css->inchain[co] = p->ins;
p->ins.ss = css;
- p->ins.co = (color) co;
+ p->ins.co = (color)co;
}
return p;
}
@@ -1615,10 +1526,10 @@ chr *cp; /* next chr */
^ static int lacon(struct vars *, struct cnfa *, chr *, pcolor);
*/
static int /* predicate: constraint satisfied? */
-lacon(v, pcnfa, precp, co)
+lacon(v, pcnfa, cp, co)
struct vars *v;
struct cnfa *pcnfa; /* parent cnfa */
-chr *precp; /* points to previous chr */
+chr *cp;
pcolor co; /* "color" of the lookahead constraint */
{
int n;
@@ -1628,18 +1539,16 @@ pcolor co; /* "color" of the lookahead constraint */
n = co - pcnfa->ncolors;
assert(n < v->g->nlacons && v->g->lacons != NULL);
- if (v->eflags&REG_FTRACE)
- printf("=== testing lacon %d\n", n);
+ FDEBUG(("=== testing lacon %d\n", n));
sub = &v->g->lacons[n];
d = newdfa(v, &sub->cnfa, v->g->cm);
if (d == NULL) {
ERR(REG_ESPACE);
return 0;
}
- end = longest(v, d, precp, v->stop);
+ end = longest(v, d, cp, v->stop);
freedfa(d);
- if (v->eflags&REG_FTRACE)
- printf("=== lacon %d match %d\n", n, (end != NULL));
+ FDEBUG(("=== lacon %d match %d\n", n, (end != NULL)));
return (sub->subno) ? (end != NULL) : (end == NULL);
}
@@ -1647,12 +1556,14 @@ pcolor co; /* "color" of the lookahead constraint */
- getvacant - get a vacant state set
* This routine clears out the inarcs and outarcs, but does not otherwise
* clear the innards of the state set -- that's up to the caller.
- ^ static struct sset *getvacant(struct vars *, struct dfa *);
+ ^ static struct sset *getvacant(struct vars *, struct dfa *, chr *, chr *);
*/
static struct sset *
-getvacant(v, d)
+getvacant(v, d, cp, start)
struct vars *v; /* used only for debug flags */
struct dfa *d;
+chr *cp;
+chr *start;
{
int i;
struct sset *ss;
@@ -1661,15 +1572,14 @@ struct dfa *d;
struct arcp lastap;
color co;
- ss = pickss(v, d);
+ ss = pickss(v, d, cp, start);
+ assert(!(ss->flags&LOCKED));
/* clear out its inarcs, including self-referential ones */
ap = ss->ins;
while ((p = ap.ss) != NULL) {
co = ap.co;
- if (v->eflags&REG_FTRACE)
- printf("zapping c%d's %ld outarc\n", p - d->ssets,
- (long)co);
+ FDEBUG(("zapping c%d's %ld outarc\n", p - d->ssets, (long)co));
p->outs[co] = NULL;
ap = p->inchain[co];
p->inchain[co].ss = NULL; /* paranoia */
@@ -1682,9 +1592,7 @@ struct dfa *d;
assert(p != ss); /* not self-referential */
if (p == NULL)
continue; /* NOTE CONTINUE */
- if (v->eflags&REG_FTRACE)
- printf("deleting outarc %d from c%d's inarc chain\n",
- i, p - d->ssets);
+ FDEBUG(("del outarc %d from c%d's in chn\n", i, p - d->ssets));
if (p->ins.ss == ss && p->ins.co == i)
p->ins = ss->inchain[i];
else {
@@ -1710,23 +1618,25 @@ struct dfa *d;
/*
- pickss - pick the next stateset to be used
- ^ static struct sset *pickss(struct vars *, struct dfa *);
+ ^ static struct sset *pickss(struct vars *, struct dfa *, chr *, chr *);
*/
static struct sset *
-pickss(v, d)
+pickss(v, d, cp, start)
struct vars *v; /* used only for debug flags */
struct dfa *d;
+chr *cp;
+chr *start;
{
int i;
struct sset *ss;
- struct sset *oldest;
+ struct sset *end;
+ chr *ancient;
/* shortcut for cases where cache isn't full */
if (d->nssused < d->nssets) {
ss = &d->ssets[d->nssused];
d->nssused++;
- if (v->eflags&REG_FTRACE)
- printf("new c%d\n", ss - d->ssets);
+ FDEBUG(("new c%d\n", ss - d->ssets));
/* must make innards consistent */
ss->ins.ss = NULL;
for (i = 0; i < d->ncolors; i++) {
@@ -1734,21 +1644,32 @@ struct dfa *d;
ss->inchain[i].ss = NULL;
}
ss->flags = 0;
- ss->ins.co = 0;
return ss;
}
- /* look for oldest */
- oldest = d->ssets;
- for (ss = d->ssets, i = d->nssets; i > 0; ss++, i--) {
- if (ss->lastseen != oldest->lastseen && (ss->lastseen == NULL ||
- ss->lastseen < oldest->lastseen))
- oldest = ss;
- }
- if (v->eflags&REG_FTRACE)
- printf("replacing c%d\n", oldest - d->ssets);
- return oldest;
-}
+ /* look for oldest, or old enough anyway */
+ if (cp - start > d->nssets*3/4) /* oldest 25% are expendable */
+ ancient = cp - d->nssets*3/4;
+ else
+ ancient = start;
+ for (ss = d->search, end = &d->ssets[d->nssets]; ss < end; ss++)
+ if ((ss->lastseen == NULL || ss->lastseen < ancient) &&
+ !(ss->flags&LOCKED)) {
+ d->search = ss + 1;
+ FDEBUG(("replacing c%d\n", ss - d->ssets));
+ return ss;
+ }
+ for (ss = d->ssets, end = d->search; ss < end; ss++)
+ if ((ss->lastseen == NULL || ss->lastseen < ancient) &&
+ !(ss->flags&LOCKED)) {
+ d->search = ss + 1;
+ FDEBUG(("replacing c%d\n", ss - d->ssets));
+ return ss;
+ }
-#define EXEC 1
-#include "color.c"
+ /* nobody's old enough?!? -- something's really wrong */
+ FDEBUG(("can't find victim to replace!\n"));
+ assert(NOTREACHED);
+ ERR(REG_ASSERT);
+ return d->ssets;
+}
diff --git a/generic/regfree.c b/generic/regfree.c
new file mode 100644
index 0000000..a5c3f0b
--- /dev/null
+++ b/generic/regfree.c
@@ -0,0 +1,25 @@
+/*
+ * regfree - free an RE
+ *
+ * You might think that this could be incorporated into regcomp.c, and
+ * that would be a reasonable idea... except that this is a generic
+ * function (with a generic name), applicable to all compiled REs
+ * regardless of the size of their characters, whereas the stuff in
+ * regcomp.c gets compiled once per character size.
+ */
+
+#include "regguts.h"
+
+/*
+ - regfree - free an RE (generic function, punts to RE-specific function)
+ *
+ * Ignoring invocation with NULL is a convenience.
+ */
+VOID
+regfree(re)
+regex_t *re;
+{
+ if (re == NULL)
+ return;
+ (*((struct fns *)re->re_fns)->free)(re);
+}
diff --git a/generic/regfronts.c b/generic/regfronts.c
new file mode 100644
index 0000000..a9bd556
--- /dev/null
+++ b/generic/regfronts.c
@@ -0,0 +1,56 @@
+/*
+ * regcomp and regexec - front ends to re_ routines
+ *
+ * Mostly for implementation of backward-compatibility kludges. Note
+ * that these routines exist ONLY in char versions.
+ */
+
+#include "regguts.h"
+
+/*
+ - regcomp - compile regular expression
+ */
+int
+regcomp(re, str, flags)
+regex_t *re;
+CONST char *str;
+int flags;
+{
+ size_t len;
+ int f = flags;
+
+ if (f&REG_PEND) {
+ len = re->re_endp - str;
+ f &= ~REG_PEND;
+ } else
+ len = strlen(str);
+
+ return re_comp(re, str, len, f);
+}
+
+/*
+ - regexec - execute regular expression
+ */
+int
+regexec(re, str, nmatch, pmatch, flags)
+regex_t *re;
+CONST char *str;
+size_t nmatch;
+regmatch_t pmatch[];
+int flags;
+{
+ CONST char *start;
+ size_t len;
+ int f = flags;
+
+ if (f&REG_STARTEND) {
+ start = str + pmatch[0].rm_so;
+ len = pmatch[0].rm_eo - pmatch[0].rm_so;
+ f &= ~REG_STARTEND;
+ } else {
+ start = str;
+ len = strlen(str);
+ }
+
+ return re_exec(re, start, len, nmatch, pmatch, f);
+}
diff --git a/generic/guts.h b/generic/regguts.h
index 7b847ac..1490d44 100644
--- a/generic/guts.h
+++ b/generic/regguts.h
@@ -1,54 +1,119 @@
/*
- * guts.h --
- *
- * Regexp package file: Misc. utilities.
- *
- * Copyright (c) 1998 Henry Spencer. All rights reserved.
- *
- * Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
- *
- * Redistribution and use in source and binary forms -- with or without
- * modification -- are permitted for any purpose, provided that
- * redistributions in source form retain this entire copyright notice and
- * indicate the origin and nature of any modifications.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
- * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
- * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
- * HENRY SPENCER BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
- * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
- * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Copyright (c) 1998 by Sun Microsystems, Inc.
- *
- * See the file "license.terms" for information on usage and redistribution
- * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- *
- * RCS: @(#) $Id: guts.h,v 1.1.2.2 1998/10/03 01:56:40 stanton Exp $
+ * Internal interface definitions, etc., for the regex package
*/
-#include "tclInt.h"
-#define NOTREACHED 0
-#define xxx 1
+/*
+ * Environmental customization. It should not (I hope) be necessary to
+ * alter the file you are now reading -- regcustom.h should handle it all,
+ * given care here and elsewhere.
+ */
+#include "regcustom.h"
+
+
+
+/*
+ * Things that regcustom.h might override.
+ */
+
+/* standard header files (NULL is a reasonable indicator for them) */
+#ifndef NULL
+#include <stdio.h>
+#include <stdlib.h>
+#include <ctype.h>
+#include <limits.h>
+#include <string.h>
+#endif
+
+/* assertions */
+#ifndef assert
+#include <assert.h>
+#endif
+
+/* voids */
+#ifndef VOID
+#define VOID void /* for function return values */
+#endif
+#ifndef DISCARD
+#define DISCARD VOID /* for throwing values away */
+#endif
+#ifndef PVOID
+#define PVOID VOID * /* generic pointer */
+#endif
+#ifndef VS
+#define VS(x) ((PVOID)(x)) /* cast something to generic ptr */
+#endif
+#ifndef NOPARMS
+#define NOPARMS VOID /* for empty parm lists */
+#endif
+
+/* function-pointer declarator */
+#ifndef FUNCPTR
+#if __STDC__ >= 1
+#define FUNCPTR(name, args) (*name)args
+#else
+#define FUNCPTR(name, args) (*name)()
+#endif
+#endif
+
+/* memory allocation */
+#ifndef MALLOC
+#define MALLOC(n) malloc(n)
+#endif
+#ifndef REALLOC
+#define REALLOC(p, n) realloc(VS(p), n)
+#endif
+#ifndef FREE
+#define FREE(p) free(VS(p))
+#endif
+
+/* want size of a char in bits, and max value in bounded quantifiers */
+#ifndef CHAR_BIT
+#include <limits.h>
+#endif
#ifndef _POSIX2_RE_DUP_MAX
-#define _POSIX2_RE_DUP_MAX 255
+#define _POSIX2_RE_DUP_MAX 255 /* normally from <limits.h> */
#endif
+
+
+
+/*
+ * misc
+ */
+
+#define NOTREACHED 0
+#define xxx 1
+
#define DUPMAX _POSIX2_RE_DUP_MAX
#define INFINITY (DUPMAX+1)
-/* bitmap manipulation */
+#define REMAGIC 0xfed7 /* magic number for main struct */
+
+
+
+/*
+ * debugging facilities
+ */
+#ifdef REG_DEBUG
+#define FDEBUG(arglist) { if (v->eflags&REG_FTRACE) printf arglist; }
+#define MDEBUG(arglist) { if (v->eflags&REG_MTRACE) printf arglist; }
+#else
+#define FDEBUG(arglist) {}
+#define MDEBUG(arglist) {}
+#endif
+
+
+
+/*
+ * bitmap manipulation
+ */
#define UBITS (CHAR_BIT * sizeof(unsigned))
#define BSET(uv, sn) ((uv)[(sn)/UBITS] |= (unsigned)1 << ((sn)%UBITS))
#define ISBSET(uv, sn) ((uv)[(sn)/UBITS] & ((unsigned)1 << ((sn)%UBITS)))
+
+
/*
* Map a truth value into -1 for false, 1 for true. This is so it is
* possible to write compile-time assertions by declaring a dummy array
@@ -56,14 +121,13 @@
*/
#define NEGIFNOT(x) (2*!!(x) - 1) /* !! ensures 0 or 1 */
+
+
/*
* We dissect a chr into byts for colormap table indexing. Here we define
* a byt, which will be the same as a byte on most machines... The exact
* size of a byt is not critical, but about 8 bits is good, and extraction
* of 8-bit chunks is sometimes especially fast.
- *
- * Changes in several places are needed to handle an increase in MAXBYTS.
- * Those places check whether MAXBYTS is larger than they expect.
*/
#ifndef BYTBITS
#define BYTBITS 8 /* bits in a byt */
@@ -71,7 +135,9 @@
#define BYTTAB (1<<BYTBITS) /* size of table with one entry per byt value */
#define BYTMASK (BYTTAB-1) /* bit mask for byt */
#define NBYTS ((CHRBITS+BYTBITS-1)/BYTBITS)
-#define MAXBYTS 8 /* maximum NBYTS the code can handle */
+/* the definition of GETCOLOR(), below, assumes NBYTS <= 4 */
+
+
/*
* As soon as possible, we map chrs into equivalence classes -- "colors" --
@@ -81,22 +147,96 @@ typedef short color; /* colors of characters */
typedef int pcolor; /* what color promotes to */
#define COLORLESS (-1) /* impossible color */
#define WHITE 0 /* default color, parent of all others */
-struct colormap; /* forward def for master type */
+
+
/*
- * Interface definitions for locale-interface functions in locale.c
+ * A colormap is a tree -- more precisely, a DAG -- indexed at each level
+ * by a byt of the chr, to map the chr to a color efficiently. Because
+ * lower sections of the tree can be shared, it can exploit the usual
+ * sparseness of such a mapping table. The final tree is always NBYTS
+ * levels deep (at present it may be shallower during construction, but
+ * it is always "filled" to full depth at the end of that, using pointers
+ * to "fill blocks" which are entirely WHITE in color).
+ */
+
+/* the tree itself */
+struct colors {
+ color ccolor[BYTTAB];
+};
+struct ptrs {
+ union tree *pptr[BYTTAB];
+};
+union tree {
+ struct colors colors;
+ struct ptrs ptrs;
+};
+#define tcolor colors.ccolor
+#define tptr ptrs.pptr
+
+/* internal per-color structure for the color machinery */
+struct colordesc {
+ uchr nchrs; /* number of chars of this color */
+ color sub; /* open subcolor of this one, or NOSUB */
+# define NOSUB COLORLESS
+ struct arc *arcs; /* color chain */
+# define UNUSEDCOLOR(cd) ((cd)->nchrs == 0 && (cd)->sub == NOSUB)
+ int flags;
+# define PSEUDO 1 /* pseudocolor, no real chars */
+};
+
+/* the color map itself */
+struct colormap {
+ int magic;
+# define CMMAGIC 0x876
+ struct vars *v; /* for compile error reporting */
+ color rest;
+ int filled; /* has it been filled? */
+ size_t ncds; /* number of colordescs */
+ struct colordesc *cd;
+# define CDEND(cm) (&(cm)->cd[(cm)->ncds])
+# define NINLINECDS ((size_t)10)
+ struct colordesc cds[NINLINECDS];
+ union tree tree[NBYTS]; /* tree top, plus fill blocks */
+};
+
+/* optimization magic to do fast chr->color mapping */
+#define B0(c) ((c) & BYTMASK)
+#define B1(c) (((c)>>BYTBITS) & BYTMASK)
+#define B2(c) (((c)>>(2*BYTBITS)) & BYTMASK)
+#define B3(c) (((c)>>(3*BYTBITS)) & BYTMASK)
+#if NBYTS == 1
+#define GETCOLOR(cm, c) ((cm)->tree->tcolor[B0(c)])
+#endif
+#if NBYTS == 2
+#define GETCOLOR(cm, c) ((cm)->tree->tptr[B1(c)]->tcolor[B0(c)])
+#endif
+#if NBYTS == 4
+#define GETCOLOR(cm, c) ((cm)->tree->tptr[B3(c)]->tptr[B2(c)]->tptr[B1(c)]->tcolor[B0(c)])
+#endif
+
+
+
+/*
+ * Interface definitions for locale-interface functions in locale.c.
+ * Multi-character collating elements (MCCEs) cause most of the trouble.
*/
struct cvec {
int nchrs; /* number of chrs */
int chrspace; /* number of chrs possible */
chr *chrs; /* pointer to vector of chrs */
- int nces; /* number of multichr collating elements */
- int cespace; /* number of CEs possible */
- int ncechrs; /* number of chrs used for CEs */
- chr *ces[1]; /* pointers to 0-terminated CEs */
+ int nmcces; /* number of MCCEs */
+ int mccespace; /* number of MCCEs possible */
+ int nmccechrs; /* number of chrs used for MCCEs */
+ chr *mcces[1]; /* pointers to 0-terminated MCCEs */
/* and both batches of chrs are on the end */
};
+/* caution: this value cannot be changed easily */
+#define MAXMCCE 2 /* length of longest MCCE */
+
+
+
/*
* definitions for NFA internal representation
*
@@ -147,12 +287,15 @@ struct nfa {
struct state *states; /* state-chain header */
struct state *slast; /* tail of the chain */
struct state *free; /* free list */
+ 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 */
struct vars *v; /* simplifies compile error reporting */
struct nfa *parent; /* parent NFA, if any */
};
+
+
/*
* definitions for compacted NFA
*/
@@ -164,8 +307,9 @@ struct carc {
struct cnfa {
int nstates; /* number of states */
int ncolors; /* number of colors */
- int haslacons; /* does it use lookahead constraints? */
- int leftanch; /* is it anchored on the left? */
+ int flags;
+# define HASLACONS 01 /* uses lookahead constraints */
+# define LEFTANCH 02 /* anchored on left */
int pre; /* setup state number */
int post; /* teardown state number */
color bos[2]; /* colors, if any, assigned to BOS and BOL */
@@ -176,6 +320,8 @@ struct cnfa {
#define ZAPCNFA(cnfa) ((cnfa).nstates = 0)
#define NULLCNFA(cnfa) ((cnfa).nstates == 0)
+
+
/*
* definitions for subexpression tree
* The intrepid code-reader is hereby warned that the subexpression tree
@@ -198,20 +344,27 @@ struct subre {
struct rtree {
char op; /* operator: '|', ',' */
- short no; /* node numbering */
+ char flags;
+# define INUSE 01 /* in use in the tree */
+ short no; /* index into retry memory */
struct subre left;
struct rtree *next; /* for '|' */
struct subre right; /* for ',' */
+ struct rtree *chain; /* for bookkeeping and error cleanup */
};
+
+
/*
* table of function pointers for generic manipulation functions
* A regex_t's re_fns points to one of these.
*/
struct fns {
- VOID (*free) _ANSI_ARGS_((regex_t *));
+ VOID FUNCPTR(free, (regex_t *));
};
+
+
/*
* the insides of a regex_t, hidden behind a void *
*/
@@ -220,13 +373,12 @@ struct guts {
# define GUTSMAGIC 0xfed9
int cflags; /* copy of compile flags */
int info; /* copy of re_info */
- int nsub; /* copy of re_nsub */
+ size_t nsub; /* copy of re_nsub */
struct cnfa cnfa;
struct rtree *tree;
int ntree;
struct colormap *cm;
- int (*compare) _ANSI_ARGS_((CONST chr *, CONST chr *, size_t));
- /* string-compare function */
+ int FUNCPTR(compare, (CONST chr *, CONST chr *, size_t));
struct subre *lacons; /* lookahead-constraint vector */
int nlacons; /* size of lacons */
int usedshorter; /* used non-greedy quantifiers? */
diff --git a/generic/tclBasic.c b/generic/tclBasic.c
index e8fa7ad..fcc1f93 100644
--- a/generic/tclBasic.c
+++ b/generic/tclBasic.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.
*
- * RCS: @(#) $Id: tclBasic.c,v 1.1.2.3 1998/09/30 20:46:21 stanton Exp $
+ * RCS: @(#) $Id: tclBasic.c,v 1.1.2.4 1998/10/21 20:40:02 stanton Exp $
*/
#include "tclInt.h"
@@ -77,6 +77,8 @@ static CmdInfo builtInCmds[] = {
(CompileProc *) NULL, 1},
{"continue", (Tcl_CmdProc *) NULL, Tcl_ContinueObjCmd,
TclCompileContinueCmd, 1},
+ {"encoding", (Tcl_CmdProc *) NULL, Tcl_EncodingObjCmd,
+ (CompileProc *) NULL, 1},
{"error", (Tcl_CmdProc *) NULL, Tcl_ErrorObjCmd,
(CompileProc *) NULL, 1},
{"eval", (Tcl_CmdProc *) NULL, Tcl_EvalObjCmd,
diff --git a/generic/tclCmdAH.c b/generic/tclCmdAH.c
index f17b8fc..54a3046 100644
--- a/generic/tclCmdAH.c
+++ b/generic/tclCmdAH.c
@@ -11,7 +11,7 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclCmdAH.c,v 1.1.2.3 1998/09/28 20:24:18 stanton Exp $
+ * RCS: @(#) $Id: tclCmdAH.c,v 1.1.2.4 1998/10/21 20:40:03 stanton Exp $
*/
#include "tclInt.h"
@@ -343,7 +343,7 @@ Tcl_CdObjCmd(dummy, interp, objc, objv)
* Tcl_ConcatObjCmd --
*
* This object-based procedure is invoked to process the "concat" Tcl
- * command. See the user documentation for details on what it does/
+ * command. See the user documentation for details on what it does.
*
* Results:
* A standard Tcl object result.
@@ -407,6 +407,123 @@ Tcl_ContinueObjCmd(dummy, interp, objc, objv)
/*
*----------------------------------------------------------------------
*
+ * Tcl_EncodingObjCmd --
+ *
+ * This command manipulates encodings.
+ *
+ * Results:
+ * A standard Tcl result.
+ *
+ * Side effects:
+ * See the user documentation.
+ *
+ *----------------------------------------------------------------------
+ */
+
+int
+Tcl_EncodingObjCmd(dummy, interp, objc, objv)
+ ClientData dummy; /* Not used. */
+ Tcl_Interp *interp; /* Current interpreter. */
+ int objc; /* Number of arguments. */
+ Tcl_Obj *CONST objv[]; /* Argument objects. */
+{
+ int index, length;
+ Tcl_Encoding encoding;
+ char *string;
+ Tcl_DString ds;
+ Tcl_Obj *resultPtr;
+
+ static char *optionStrings[] = {
+ "convertfrom", "convertto", "names", "system",
+ NULL
+ };
+ enum options {
+ ENC_CONVERTFROM, ENC_CONVERTTO, ENC_NAMES, ENC_SYSTEM
+ };
+
+ if (objc < 2) {
+ Tcl_WrongNumArgs(interp, 1, objv, "option ?arg ...?");
+ return TCL_ERROR;
+ }
+ if (Tcl_GetIndexFromObj(interp, objv[1], optionStrings, "option", 0,
+ &index) != TCL_OK) {
+ return TCL_ERROR;
+ }
+
+ switch ((enum options) index) {
+ case ENC_CONVERTTO:
+ case ENC_CONVERTFROM: {
+ char *name;
+ Tcl_Obj *data;
+ if (objc == 3) {
+ name = NULL;
+ data = objv[2];
+ } else if (objc == 4) {
+ name = Tcl_GetString(objv[2]);
+ data = objv[3];
+ } else {
+ Tcl_WrongNumArgs(interp, 2, objv, "?encoding? data");
+ return TCL_ERROR;
+ }
+
+ encoding = Tcl_GetEncoding(interp, name);
+ if (!encoding) {
+ return TCL_ERROR;
+ }
+
+ if ((enum options) index == ENC_CONVERTFROM) {
+ /*
+ * Treat the string as binary data.
+ */
+
+ string = (char *) Tcl_GetByteArrayFromObj(data, &length);
+ Tcl_ExternalToUtfDString(encoding, string, length, &ds);
+ Tcl_DStringResult(interp, &ds);
+ } else {
+ /*
+ * Store the result as binary data.
+ */
+
+ string = Tcl_GetStringFromObj(data, &length);
+ Tcl_UtfToExternalDString(encoding, string, length, &ds);
+ resultPtr = Tcl_GetObjResult(interp);
+ Tcl_SetByteArrayObj(resultPtr,
+ (unsigned char *) Tcl_DStringValue(&ds),
+ Tcl_DStringLength(&ds));
+ Tcl_DStringFree(&ds);
+ }
+
+ Tcl_FreeEncoding(encoding);
+ break;
+ }
+ case ENC_NAMES: {
+ if (objc > 2) {
+ Tcl_WrongNumArgs(interp, 2, objv, NULL);
+ return TCL_ERROR;
+ }
+ Tcl_GetEncodingNames(interp);
+ break;
+ }
+ case ENC_SYSTEM: {
+ if (objc > 3) {
+ Tcl_WrongNumArgs(interp, 2, objv, "?encoding?");
+ return TCL_ERROR;
+ }
+ if (objc == 2) {
+ Tcl_SetResult(interp, Tcl_GetEncodingName(NULL), TCL_STATIC);
+ } else {
+ return Tcl_SetSystemEncoding(interp,
+ Tcl_GetStringFromObj(objv[2], NULL));
+ }
+ break;
+ }
+ }
+ return TCL_OK;
+}
+
+/*
+ *----------------------------------------------------------------------
+ *
* Tcl_ErrorObjCmd --
*
* This procedure is invoked to process the "error" Tcl command.
diff --git a/generic/tclCmdIL.c b/generic/tclCmdIL.c
index f47fb1e..6b4cc39 100644
--- a/generic/tclCmdIL.c
+++ b/generic/tclCmdIL.c
@@ -13,12 +13,13 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclCmdIL.c,v 1.1.2.2 1998/09/24 23:58:42 stanton Exp $
+ * RCS: @(#) $Id: tclCmdIL.c,v 1.1.2.3 1998/10/21 20:40:04 stanton Exp $
*/
#include "tclInt.h"
#include "tclPort.h"
#include "tclCompile.h"
+#include "tclRegexp.h"
/*
* During execution of the "lsort" command, structures of the following
diff --git a/generic/tclCmdMZ.c b/generic/tclCmdMZ.c
index 8a3b6d5..9f46efc 100644
--- a/generic/tclCmdMZ.c
+++ b/generic/tclCmdMZ.c
@@ -12,12 +12,13 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclCmdMZ.c,v 1.1.2.3 1998/10/16 01:16:57 stanton Exp $
+ * RCS: @(#) $Id: tclCmdMZ.c,v 1.1.2.4 1998/10/21 20:40:05 stanton Exp $
*/
#include "tclInt.h"
#include "tclPort.h"
#include "tclCompile.h"
+#include "tclRegexp.h"
/*
* Structure used to hold information about variable traces:
@@ -108,20 +109,26 @@ Tcl_RegexpObjCmd(dummy, interp, objc, objv)
int objc; /* Number of arguments. */
Tcl_Obj *CONST objv[]; /* Argument objects. */
{
- int i, result, indices, flags, stringLength, wLen, match;
+ int i, result, indices, stringLength, wLen, match, about;
+ int hasxflags, cflags, eflags;
Tcl_RegExp regExpr;
char *string;
Tcl_DString stringBuffer, valueBuffer;
Tcl_UniChar *wStart;
static char *options[] = {
- "-indices", "-nocase", "--", (char *) NULL
+ "-indices", "-nocase", "-about", "-expanded",
+ "-unsupported0", "--", (char *) NULL
};
enum options {
- REGEXP_INDICES, REGEXP_NOCASE, REGEXP_LAST
+ REGEXP_INDICES, REGEXP_NOCASE, REGEXP_ABOUT, REGEXP_EXPANDED,
+ REGEXP_XFLAGS, REGEXP_LAST
};
indices = 0;
- flags = 0;
+ about = 0;
+ cflags = REG_ADVANCED;
+ eflags = 0;
+ hasxflags = 0;
for (i = 1; i < objc; i++) {
char *name;
@@ -141,7 +148,19 @@ Tcl_RegexpObjCmd(dummy, interp, objc, objv)
break;
}
case REGEXP_NOCASE: {
- flags |= REG_ICASE;
+ cflags |= REG_ICASE;
+ break;
+ }
+ case REGEXP_ABOUT: {
+ about = 1;
+ break;
+ }
+ case REGEXP_EXPANDED: {
+ cflags |= REG_EXPANDED;
+ break;
+ }
+ case REGEXP_XFLAGS: {
+ hasxflags = 1;
break;
}
case REGEXP_LAST: {
@@ -152,7 +171,7 @@ Tcl_RegexpObjCmd(dummy, interp, objc, objv)
}
endOfForLoop:
- if (objc - i < 2) {
+ if (objc - i < hasxflags + 2 - about) {
Tcl_WrongNumArgs(interp, 1, objv,
"?switches? exp string ?matchVar? ?subMatchVar subMatchVar ...?");
return TCL_ERROR;
@@ -160,11 +179,25 @@ Tcl_RegexpObjCmd(dummy, interp, objc, objv)
objc -= i;
objv += i;
- regExpr = TclRegCompObj(interp, objv[0], flags | REG_ADVANCED);
+ if (hasxflags) {
+ string = Tcl_GetStringFromObj(objv[0], &stringLength);
+ TclRegXflags(string, stringLength, &cflags, &eflags);
+ objc--;
+ objv++;
+ }
+
+ regExpr = TclRegCompObj(interp, objv[0], cflags);
if (regExpr == NULL) {
return TCL_ERROR;
}
+ if (about) {
+ if (TclRegAbout(interp, regExpr) < 0) {
+ return TCL_ERROR;
+ }
+ return TCL_OK;
+ }
+
result = TCL_OK;
string = Tcl_GetStringFromObj(objv[1], &stringLength);
@@ -174,7 +207,7 @@ Tcl_RegexpObjCmd(dummy, interp, objc, objv)
wStart = TclUtfToUniCharDString(string, stringLength, &stringBuffer);
wLen = Tcl_DStringLength(&stringBuffer) / sizeof(Tcl_UniChar);
- match = TclRegExpExecUniChar(interp, regExpr, wStart, wLen, 0);
+ match = TclRegExpExecUniChar(interp, regExpr, wStart, wLen, eflags);
if (match < 0) {
result = TCL_ERROR;
goto done;
diff --git a/generic/tclEncoding.c b/generic/tclEncoding.c
index 9b3f18d..06da42e 100644
--- a/generic/tclEncoding.c
+++ b/generic/tclEncoding.c
@@ -8,7 +8,7 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclEncoding.c,v 1.1.2.2 1998/10/03 01:56:41 stanton Exp $
+ * RCS: @(#) $Id: tclEncoding.c,v 1.1.2.3 1998/10/21 20:40:05 stanton Exp $
*/
#include "tclInt.h"
@@ -136,8 +136,8 @@ typedef struct EscapeEncodingData {
#define ENCODING_ESCAPE 3
/*
- * Hash table that keeps track of all loaded TextEncodings. Keys are
- * the string names that represent the encoding, values are (TextEncoding *).
+ * Hash table that keeps track of all loaded Encodings. Keys are
+ * the string names that represent the encoding, values are (Encoding *).
*/
static Tcl_HashTable encodingTable;
@@ -277,6 +277,23 @@ TclInitEncodingSubsystem()
Tcl_CreateEncoding(&type);
}
+
+/*
+ *----------------------------------------------------------------------
+ *
+ * TclFinalizeEncodingSubsystem --
+ *
+ * Release the state associated with the encoding subsystem.
+ *
+ * Results:
+ * None.
+ *
+ * Side effects:
+ * Frees all of the encodings.
+ *
+ *----------------------------------------------------------------------
+ */
+
void
TclFinalizeEncodingSubsystem()
{
@@ -515,6 +532,11 @@ Tcl_GetEncodingNames(interp)
Tcl_DStringFree(&pwdString);
}
+ /*
+ * Clear any values placed in the result by globbing.
+ */
+
+ Tcl_ResetResult(interp);
resultPtr = Tcl_GetObjResult(interp);
hPtr = Tcl_FirstHashEntry(&table, &search);
@@ -573,9 +595,9 @@ Tcl_SetSystemEncoding(interp, name)
return TCL_ERROR;
}
}
- Tcl_FreeEncoding(systemEncoding);
Tcl_MutexLock(&encodingMutex);
+ Tcl_FreeEncoding(systemEncoding);
systemEncoding = encoding;
Tcl_MutexUnlock(&encodingMutex);
@@ -1009,7 +1031,7 @@ LoadEncodingFile(interp, name)
pathPtr = TclGetLibraryPath();
if (pathPtr == NULL) {
- return NULL;
+ goto unknown;
}
objc = 0;
Tcl_ListObjGetElements(NULL, pathPtr, &objc, &objv);
@@ -1023,10 +1045,7 @@ LoadEncodingFile(interp, name)
}
if (chan == NULL) {
- if (interp != NULL) {
- Tcl_AppendResult(interp, "unknown encoding \"", name, "\"", NULL);
- }
- return NULL;
+ goto unknown;
}
Tcl_SetChannelOption(NULL, chan, "-encoding", "utf-8");
@@ -1070,7 +1089,30 @@ LoadEncodingFile(interp, name)
}
Tcl_Close(NULL, chan);
return encoding;
+
+ unknown:
+ if (interp != NULL) {
+ Tcl_AppendResult(interp, "unknown encoding \"", name, "\"", NULL);
+ }
+ return NULL;
}
+
+/*
+ *----------------------------------------------------------------------
+ *
+ * OpenEncodingFile --
+ *
+ * Look for the file encoding/<name>.enc in the specified
+ * directory.
+ *
+ * Results:
+ * Returns an open file channel if the file exists.
+ *
+ * Side effects:
+ * None.
+ *
+ *----------------------------------------------------------------------
+ */
static Tcl_Channel
OpenEncodingFile(dir, name)
diff --git a/generic/tclFileName.c b/generic/tclFileName.c
index 01fefa7..55832ab 100644
--- a/generic/tclFileName.c
+++ b/generic/tclFileName.c
@@ -9,11 +9,12 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclFileName.c,v 1.1.2.3 1998/10/06 00:36:56 stanton Exp $
+ * RCS: @(#) $Id: tclFileName.c,v 1.1.2.4 1998/10/21 20:40:05 stanton Exp $
*/
#include "tclInt.h"
#include "tclPort.h"
+#include "tclRegexp.h"
/*
* This variable indicates whether the cleanup procedure has been
diff --git a/generic/tclInt.h b/generic/tclInt.h
index 140a2eb..0babdfd 100644
--- a/generic/tclInt.h
+++ b/generic/tclInt.h
@@ -10,7 +10,7 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclInt.h,v 1.1.2.6 1998/10/16 01:16:57 stanton Exp $
+ * RCS: @(#) $Id: tclInt.h,v 1.1.2.7 1998/10/21 20:40:06 stanton Exp $
*/
#ifndef _TCLINT
@@ -774,48 +774,6 @@ typedef struct MathFunc {
} MathFunc;
/*
- *---------------------------------------------------------------------------
- * Definitions of flags used in regexp compilation and execution that need
- * to be visible to the rest of the Tcl core. Definitions that are
- * entirely private to the regexp package live in tclRegexp.h.
- *---------------------------------------------------------------------------
- */
-
-/*
- *Compilation flags.
- */
-
-#define REG_BASIC 000000 /* BREs (convenience) */
-#define REG_EXTENDED 000001 /* EREs */
-#define REG_ADVF 000002 /* advanced features in EREs */
-#define REG_ADVANCED 000003 /* AREs (which are also EREs) */
-#define REG_QUOTE 000004 /* no special characters, none */
-#define REG_NOSPEC REG_QUOTE /* historical synonym */
-#define REG_ICASE 000010 /* ignore case */
-#define REG_NOSUB 000020 /* don't care about subexpressions */
-#define REG_EXPANDED 000040 /* expanded format, white space & comments */
-#define REG_NLSTOP 000100 /* \n doesn't match . or [^ ] */
-#define REG_NLANCH 000200 /* ^ matches after \n, $ before */
-#define REG_NEWLINE 000300 /* newlines are line terminators */
-
-/*
- * Execution flags.
- */
-
-#define REG_NOTBOL 0001 /* BOS is not BOL */
-#define REG_NOTEOL 0002 /* EOS is not EOL */
-
-EXTERN Tcl_RegExp TclRegCompObj _ANSI_ARGS_((Tcl_Interp *interp,
- Tcl_Obj *patObj, int flags));
-EXTERN int TclRegExpExecUniChar _ANSI_ARGS_((Tcl_Interp *interp,
- Tcl_RegExp re, CONST Tcl_UniChar *uniString,
- int numChars, int flags));
-EXTERN int TclRegExpMatchObj _ANSI_ARGS_((Tcl_Interp *interp,
- char *string, Tcl_Obj *patObj));
-EXTERN void TclRegExpRangeUniChar _ANSI_ARGS_((Tcl_RegExp re,
- int index, int *startPtr, int *endPtr));
-
-/*
* Threads support.
* These routines are used to implement Tcl_GetThreadData.
*/
@@ -2161,6 +2119,8 @@ EXTERN int Tcl_ConcatObjCmd _ANSI_ARGS_((ClientData clientData,
Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[]));
EXTERN int Tcl_ContinueObjCmd _ANSI_ARGS_((ClientData clientData,
Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[]));
+EXTERN int Tcl_EncodingObjCmd _ANSI_ARGS_((ClientData clientData,
+ Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[]));
EXTERN int Tcl_EofObjCmd _ANSI_ARGS_((ClientData clientData,
Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[]));
EXTERN int Tcl_ErrorObjCmd _ANSI_ARGS_((ClientData clientData,
diff --git a/generic/tclRegexp.c b/generic/tclRegexp.c
index 44b575c..d65b19a 100644
--- a/generic/tclRegexp.c
+++ b/generic/tclRegexp.c
@@ -4,12 +4,13 @@
* This file contains the public interfaces to the Tcl regular
* expression mechanism.
*
+ * Copyright (c) 1998 by Scriptics Corporation.
* Copyright (c) 1998 by Sun Microsystems, Inc.
*
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclRegexp.c,v 1.1.2.2 1998/10/03 01:56:41 stanton Exp $
+ * RCS: @(#) $Id: tclRegexp.c,v 1.1.2.3 1998/10/21 20:40:06 stanton Exp $
*/
#include "tclInt.h"
@@ -337,6 +338,7 @@ TclRegExpExecUniChar(interp, re, wString, numChars, flags)
TclRegexp *regexpPtr = (TclRegexp *) re;
status = re_uexec(&regexpPtr->re, wString, (size_t) numChars,
+ (rm_detail_t *)NULL,
regexpPtr->re.re_nsub + 1, regexpPtr->matches, flags);
/*
@@ -528,6 +530,83 @@ TclRegCompObj(interp, objPtr, flags)
/*
*----------------------------------------------------------------------
*
+ * TclRegAbout --
+ *
+ * Return information about a compiled regular expression.
+ *
+ * Results:
+ * The return value is -1 for failure, 0 for success, although at
+ * the moment there's nothing that could fail. On success, a list
+ * is left in the interp's result: first element is the subexpression
+ * count, second is a list of re_info bit names.
+ *
+ * Side effects:
+ * None.
+ *
+ *----------------------------------------------------------------------
+ */
+
+int
+TclRegAbout(interp, re)
+ Tcl_Interp *interp; /* For use in variable assignment. */
+ Tcl_RegExp re; /* The compiled regular expression. */
+{
+ TclRegexp *regexpPtr = (TclRegexp *)re;
+ char buf[TCL_INTEGER_SPACE];
+ static struct infoname {
+ int bit;
+ char *text;
+ } infonames[] = {
+ REG_UBACKREF, "REG_UBACKREF",
+ REG_ULOOKAHEAD, "REG_ULOOKAHEAD",
+ REG_UBOUNDS, "REG_UBOUNDS",
+ REG_UBRACES, "REG_UBRACES",
+ REG_UBSALNUM, "REG_UBSALNUM",
+ REG_UPBOTCH, "REG_UPBOTCH",
+ REG_UBBS, "REG_UBBS",
+ REG_UNONPOSIX, "REG_UNONPOSIX",
+ REG_UUNSPEC, "REG_UUNSPEC",
+ REG_UUNPORT, "REG_UUNPORT",
+ REG_ULOCALE, "REG_ULOCALE",
+ REG_UEMPTYMATCH, "REG_UEMPTYMATCH",
+ 0, "",
+ };
+ struct infoname *inf;
+ int n;
+
+ Tcl_ResetResult(interp);
+
+ sprintf(buf, "%u", (unsigned)(regexpPtr->re.re_nsub));
+ Tcl_AppendElement(interp, buf);
+
+ /*
+ * Must count bits before generating list, because we must know
+ * whether {} are needed before we start appending names.
+ */
+ n = 0;
+ for (inf = infonames; inf->bit != 0; inf++) {
+ if (regexpPtr->re.re_info&inf->bit) {
+ n++;
+ }
+ }
+ if (n != 1) {
+ Tcl_AppendResult(interp, " {", NULL);
+ }
+ for (inf = infonames; inf->bit != 0; inf++) {
+ if (regexpPtr->re.re_info&inf->bit) {
+ Tcl_AppendElement(interp, inf->text);
+ }
+ }
+ if (n != 1) {
+ Tcl_AppendResult(interp, "}", NULL);
+ }
+
+ return 0;
+}
+
+/*
+ *----------------------------------------------------------------------
+ *
* TclRegError --
*
* Generate an error message based on the regexp status code.
@@ -536,7 +615,7 @@ TclRegCompObj(interp, objPtr, flags)
* Places an error in the interpreter.
*
* Side effects:
- * None.
+ * Sets errorCode as well.
*
*----------------------------------------------------------------------
*/
@@ -547,66 +626,19 @@ TclRegError(interp, msg, status)
char *msg; /* Message to prepend to error. */
int status; /* Status code to report. */
{
- char *errMsg;
-
- switch(status) {
- case REG_BADPAT:
- errMsg = "invalid regular expression";
- break;
- case REG_ECOLLATE:
- errMsg = "invalid collating element";
- break;
- case REG_ECTYPE:
- errMsg = "invalid character class";
- break;
- case REG_EESCAPE:
- errMsg = "invalid escape sequence";
- break;
- case REG_ESUBREG:
- errMsg = "invalid backreference number";
- break;
- case REG_EBRACK:
- errMsg = "unmatched []";
- break;
- case REG_EPAREN:
- errMsg = "unmatched ()";
- break;
- case REG_EBRACE:
- errMsg = "unmatched {}";
- break;
- case REG_BADBR:
- errMsg = "invalid repetition count(s)";
- break;
- case REG_ERANGE:
- errMsg = "invalid character range";
- break;
- case REG_ESPACE:
- errMsg = "out of memory";
- break;
- case REG_BADRPT:
- errMsg = "?+* follows nothing";
- break;
- case REG_ASSERT:
- errMsg = "\"can't happen\" -- you found a bug";
- break;
- case REG_INVARG:
- errMsg = "invalid argument to regex routine";
- break;
- case REG_MIXED:
- errMsg = "char RE applied to wchar_t string (etc.)";
- break;
- case REG_BADOPT:
- errMsg = "invalid embedded option";
- break;
- case REG_IMPOSS:
- errMsg = "can never match";
- break;
- default:
- errMsg = "\"can't happen\" -- you found an undefined error code";
- break;
- }
+ char buf[100]; /* ample in practice */
+ char cbuf[100]; /* lots in practice */
+ size_t n;
+ char *p;
+
Tcl_ResetResult(interp);
- Tcl_AppendResult(interp, msg, errMsg, NULL);
+ n = regerror(status, (regex_t *)NULL, buf, sizeof(buf));
+ p = (n > sizeof(buf)) ? "..." : "";
+ Tcl_AppendResult(interp, msg, buf, p, NULL);
+
+ sprintf(cbuf, "%d", status);
+ (VOID) regerror(REG_ITOA, (regex_t *)NULL, cbuf, sizeof(cbuf));
+ Tcl_SetErrorCode(interp, "REGEXP", cbuf, buf, NULL);
}
@@ -749,36 +781,15 @@ CompileRegexp(interp, string, length, flags)
if (status != REG_OKAY) {
/*
- * Warning, the following is a hack to allow empty regexp.
- * The goal is to compile a non-empty regexp that will always
- * find one empty match. If you use "(?:)" (an empty pair of
- * non-capturing parentheses) instead, that will avoid both the
- * overhead and the subexpression report.
- */
-
- if (status == REG_EMPTY) {
- static Tcl_UniChar uniEmpty[] = {'(', '?', ':', ')', '\0'};
-
- uniString = uniEmpty;
- numChars = 4;
- status = re_ucomp(&regexpPtr->re, uniString, (size_t) numChars,
- REG_ADVANCED);
- }
-
- /*
* Clean up and report errors in the interpreter, if possible.
*/
-
- if (status != REG_OKAY) {
- regfree(&regexpPtr->re);
- ckfree((char *)regexpPtr);
- if (interp) {
- TclRegError(interp,
- "couldn't compile regular expression pattern: ",
- status);
- }
- return NULL;
+ ckfree((char *)regexpPtr);
+ if (interp) {
+ TclRegError(interp,
+ "couldn't compile regular expression pattern: ",
+ status);
}
+ return NULL;
}
/*
@@ -791,4 +802,100 @@ CompileRegexp(interp, string, length, flags)
return regexpPtr;
}
+
+/*
+ *---------------------------------------------------------------------------
+ *
+ * TclRegXflags --
+ *
+ * Parse a string of extended regexp flag letters, for testing.
+ *
+ * Results:
+ * No return value (you're on your own for errors here).
+ *
+ * Side effects:
+ * Modifies *cflagsPtr, a regcomp flags word, and *eflagsPtr, a
+ * regexec flags word, as appropriate.
+ *
+ *----------------------------------------------------------------------
+ */
+VOID
+TclRegXflags(string, length, cflagsPtr, eflagsPtr)
+ char *string; /* The string of flags. */
+ int length; /* The length of the string in bytes. */
+ int *cflagsPtr; /* compile flags word */
+ int *eflagsPtr; /* exec flags word */
+{
+ int i;
+ int cflags;
+ int eflags;
+
+ cflags = *cflagsPtr;
+ eflags = *eflagsPtr;
+ for (i = 0; i < length; i++) {
+ switch (string[i]) {
+ case 'a': {
+ cflags |= REG_ADVF;
+ break;
+ }
+ case 'b': {
+ cflags &= ~REG_ADVANCED;
+ break;
+ }
+ case 'e': {
+ cflags &= ~REG_ADVANCED;
+ cflags |= REG_EXTENDED;
+ break;
+ }
+ case 'q': {
+ cflags &= ~REG_ADVANCED;
+ cflags |= REG_QUOTE;
+ break;
+ }
+ case 'i': {
+ cflags |= REG_ICASE;
+ break;
+ }
+ case 'o': { /* o for opaque */
+ cflags |= REG_NOSUB;
+ break;
+ }
+ case 'x': {
+ cflags |= REG_EXPANDED;
+ break;
+ }
+ case 'p': {
+ cflags |= REG_NLSTOP;
+ break;
+ }
+ case 'w': {
+ cflags |= REG_NLANCH;
+ break;
+ }
+ case 'n': {
+ cflags |= REG_NEWLINE;
+ break;
+ }
+ case '+': {
+ cflags |= REG_FAKEEC;
+ break;
+ }
+ case '^': {
+ eflags |= REG_NOTBOL;
+ break;
+ }
+ case '$': {
+ eflags |= REG_NOTEOL;
+ break;
+ }
+ case '%': {
+ eflags |= REG_SMALL;
+ break;
+ }
+ }
+ }
+
+ *cflagsPtr = cflags;
+ *eflagsPtr = eflags;
+}
diff --git a/generic/tclRegexp.h b/generic/tclRegexp.h
index be5cb77..9e56730 100644
--- a/generic/tclRegexp.h
+++ b/generic/tclRegexp.h
@@ -7,8 +7,9 @@
* Copyright (c) 1998 Henry Spencer. All rights reserved.
*
* Development of this software was funded, in part, by Cray Research Inc.,
- * UUNET Communications Services Inc., and Sun Microsystems Inc., none of
- * whom are responsible for the results. The author thanks all of them.
+ * UUNET Communications Services Inc., Sun Microsystems Inc., and
+ * Scriptics Corporation, none of whom are responsible for the results.
+ * The author thanks all of them.
*
* Redistribution and use in source and binary forms -- with or without
* modification -- are permitted for any purpose, provided that
@@ -26,20 +27,19 @@
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
+ * Copyright (c) 1998 by Scriptics Corporation.
* Copyright (c) 1998 by Sun Microsystems, Inc.
*
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclRegexp.h,v 1.1.2.2 1998/09/24 23:59:02 stanton Exp $
+ * RCS: @(#) $Id: tclRegexp.h,v 1.1.2.3 1998/10/21 20:40:06 stanton Exp $
*/
#ifndef _TCLREGEXP
#define _TCLREGEXP
-#ifndef _TCLINT
-#include "tclInt.h"
-#endif
+#include "regcustom.h"
#ifdef BUILD_tcl
# undef TCL_STORAGE_CLASS
@@ -47,190 +47,6 @@
#endif
/*
- * The following definitions were culled from wctype.h and wchar.h.
- * Those two header files are now gone. Eventually we should replace all
- * instances of, e.g., iswalnum() with TclUniCharIsAlnum() in the regexp
- * code.
- */
-
-#undef wint_t
-#define wint_t int
-
-#undef WEOF
-#undef WCHAR_MIN
-#undef WCHAR_MAX
-
-#define WEOF -1
-#define WCHAR_MIN 0x0000
-#define WCHAR_MAX 0xffff
-
-#undef iswalnum
-#undef iswalpha
-#undef iswdigit
-#undef iswspace
-
-#define iswalnum(x) TclUniCharIsAlnum(x)
-#define iswalpha(x) TclUniCharIsAlpha(x)
-#define iswdigit(x) TclUniCharIsDigit(x)
-#define iswspace(x) TclUniCharIsSpace(x)
-
-#undef wcslen
-#undef wcsncmp
-
-#define wcslen TclUniCharLen
-#define wcsncmp TclUniCharNcmp
-
-/*
- * The following definitions were added by JO to make Tcl compile
- * under SunOS, where off_t and wchar_t aren't defined; perhaps all of
- * the code below can be collapsed into a few simple definitions?
- */
-
-#ifndef __RE_REGOFF_T
-# define __RE_REGOFF_T int
-#endif
-#ifndef __RE_WCHAR_T
-# define __RE_WCHAR_T Tcl_UniChar
-#endif
-
-/*
- * regoff_t has to be large enough to hold either off_t or ssize_t,
- * and must be signed; it's only a guess that off_t is big enough, so we
- * offer an override.
- */
-#ifdef __RE_REGOFF_T
-typedef __RE_REGOFF_T regoff_t; /* offset type for result reporting */
-#else
-typedef off_t regoff_t;
-#endif
-
-/*
- * We offer the option of using a non-wchar_t type in the w prototypes so
- * that <regex.h> can be included without first including (e.g.) <wchar.h>.
- * Note that __RE_WCHAR_T must in fact be the same type as wchar_t!
- */
-#ifdef __RE_WCHAR_T
-typedef __RE_WCHAR_T re_wchar; /* internal name for the type */
-#else
-typedef wchar_t re_wchar;
-#endif
-
-#define REMAGIC 0xfed7
-
-/*
- * other interface types
- */
-
-/* the biggie, a compiled RE (or rather, a front end to same) */
-typedef struct {
- int re_magic; /* magic number */
- size_t re_nsub; /* number of subexpressions */
- int re_info; /* information about RE */
-# define REG_UBACKREF 000001
-# define REG_ULOOKAHEAD 000002
-# define REG_UBOUNDS 000004
-# define REG_UBRACES 000010
-# define REG_UBSALNUM 000020
-# define REG_UPBOTCH 000040
-# define REG_UBBS 000100
-# define REG_UNONPOSIX 000200
-# define REG_UUNSPEC 000400
-# define REG_UUNPORT 001000
-# define REG_ULOCALE 002000
-# define REG_UEMPTYMATCH 004000
- int re_csize; /* sizeof(character) */
- VOID *re_guts; /* none of your business :-) */
- VOID *re_fns; /* none of your business :-) */
-} regex_t;
-
-/* result reporting (may acquire more fields later) */
-typedef struct {
- regoff_t rm_so; /* start of substring */
- regoff_t rm_eo; /* end of substring */
-} regmatch_t;
-
-
-
-/*
- * compilation
- ^ int regcomp(regex_t *, const char *, int);
- ^ int re_comp(regex_t *, const char *, size_t, int);
- ^ #ifndef __RE_NOWIDE
- ^ int re_wcomp(regex_t *, const re_wchar *, size_t, int);
- ^ #endif
- */
-
-#define REG_DUMP 004000 /* none of your business :-) */
-#define REG_FAKE 010000 /* none of your business :-) */
-#define REG_PROGRESS 020000 /* none of your business :-) */
-
-
-
-/*
- * execution
- ^ int regexec(regex_t *, const char *, size_t, regmatch_t [], int);
- ^ int re_exec(regex_t *, const char *, size_t, size_t, regmatch_t [], int);
- ^ #ifndef __RE_NOWIDE
- ^ int re_wexec(regex_t *, const re_wchar *, size_t, size_t, regmatch_t [], int);
- ^ #endif
- */
-#define REG_FTRACE 0010 /* none of your business */
-#define REG_MTRACE 0020 /* none of your business */
-#define REG_SMALL 0040 /* none of your business */
-
-/*
- * error reporting
- * Be careful if modifying the list of error codes -- the table used by
- * regerror() is generated automatically from this file!
- *
- * Note that there is no wchar_t variant of regerror at this time; what
- * kind of character is used for error reports is independent of what kind
- * is used in matching.
- *
- ^ extern size_t regerror(int, const regex_t *, char *, size_t);
- */
-#define REG_OKAY 0 /* no errors detected */
-#define REG_NOMATCH 1 /* regexec() failed to match */
-#define REG_BADPAT 2 /* invalid regular expression */
-#define REG_ECOLLATE 3 /* invalid collating element */
-#define REG_ECTYPE 4 /* invalid character class */
-#define REG_EESCAPE 5 /* invalid escape \ sequence */
-#define REG_ESUBREG 6 /* invalid backreference number */
-#define REG_EBRACK 7 /* brackets [] not balanced */
-#define REG_EPAREN 8 /* parentheses () not balanced */
-#define REG_EBRACE 9 /* braces {} not balanced */
-#define REG_BADBR 10 /* invalid repetition count(s) */
-#define REG_ERANGE 11 /* invalid character range */
-#define REG_ESPACE 12 /* out of memory */
-#define REG_BADRPT 13 /* quantifier operand invalid */
-#define REG_EMPTY 14 /* empty regular expression */
-#define REG_ASSERT 15 /* "can't happen" -- you found a bug */
-#define REG_INVARG 16 /* invalid argument to regex routine */
-#define REG_MIXED 17 /* char RE applied to wchar_t string (etc.) */
-#define REG_BADOPT 18 /* invalid embedded option */
-#define REG_IMPOSS 19 /* can never match */
-/* two specials for debugging and testing */
-#define REG_ATOI 101 /* convert error-code name to number */
-#define REG_ITOA 102 /* convert error-code number to name */
-
-
-
-/*
- * the prototypes, as possibly munched by fwd
- */
-/* =====^!^===== begin forwards =====^!^===== */
-/* automatically gathered by fwd; do not hand-edit */
-/* === regex.h === */
-EXTERN int re_ucomp _ANSI_ARGS_((regex_t *, const Tcl_UniChar *,
- size_t, int));
-EXTERN int re_uexec _ANSI_ARGS_((regex_t *, const Tcl_UniChar *,
- size_t, size_t, regmatch_t [], int));
-EXTERN VOID regfree _ANSI_ARGS_((regex_t *));
-EXTERN size_t regerror _ANSI_ARGS_((int, const regex_t *, char *, size_t));
-/* automatically gathered by fwd; do not hand-edit */
-/* =====^!^===== end forwards =====^!^===== */
-
-/*
* The TclRegexp structure encapsulates a compiled regex_t,
* the flags that were used to compile it, and an array of pointers
* that are used to indicate subexpressions after a call to Tcl_RegExpExec.
@@ -251,6 +67,24 @@ typedef struct TclRegexp {
} TclRegexp;
/*
+ * Functions exported for use within the rest of Tcl.
+ */
+
+EXTERN Tcl_RegExp TclRegCompObj _ANSI_ARGS_((Tcl_Interp *interp,
+ Tcl_Obj *patObj, int flags));
+EXTERN int TclRegAbout _ANSI_ARGS_((Tcl_Interp *interp,
+ Tcl_RegExp re));
+EXTERN VOID TclRegXflags _ANSI_ARGS_((char *string, int length,
+ int *cflagsPtr, int *eflagsPtr));
+EXTERN int TclRegExpExecUniChar _ANSI_ARGS_((Tcl_Interp *interp,
+ Tcl_RegExp re, CONST Tcl_UniChar *uniString,
+ int numChars, int flags));
+EXTERN int TclRegExpMatchObj _ANSI_ARGS_((Tcl_Interp *interp,
+ char *string, Tcl_Obj *patObj));
+EXTERN void TclRegExpRangeUniChar _ANSI_ARGS_((Tcl_RegExp re,
+ int index, int *startPtr, int *endPtr));
+
+/*
* Functions exported from the regexp package for the test package to use.
*/
@@ -258,8 +92,3 @@ EXTERN void TclRegError _ANSI_ARGS_((Tcl_Interp *interp, char *msg,
int status));
#endif /* _TCLREGEXP */
-
-
-
-
-
diff --git a/generic/tclTest.c b/generic/tclTest.c
index 8da6785..2136b7c 100644
--- a/generic/tclTest.c
+++ b/generic/tclTest.c
@@ -12,14 +12,13 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclTest.c,v 1.1.2.2 1998/09/24 23:59:02 stanton Exp $
+ * RCS: @(#) $Id: tclTest.c,v 1.1.2.3 1998/10/21 20:40:07 stanton Exp $
*/
#define TCL_TEST
#include "tclInt.h"
#include "tclPort.h"
-#include "tclRegexp.h" /* To test internals of regexp package. */
#include <locale.h>
/*
@@ -245,9 +244,6 @@ static int TestparsevarObjCmd _ANSI_ARGS_((ClientData dummy,
static int TestparsevarnameObjCmd _ANSI_ARGS_((ClientData dummy,
Tcl_Interp *interp, int objc,
Tcl_Obj *CONST objv[]));
-static int TestregexpObjCmd _ANSI_ARGS_((ClientData dummy,
- Tcl_Interp *interp, int objc,
- Tcl_Obj *CONST objv[]));
static int TestsaveresultCmd _ANSI_ARGS_((ClientData dummy,
Tcl_Interp *interp, int objc,
Tcl_Obj *CONST objv[]));
@@ -398,8 +394,6 @@ Tcltest_Init(interp)
(ClientData) 0, (Tcl_CmdDeleteProc *) NULL);
Tcl_CreateObjCommand(interp, "testparsevarname", TestparsevarnameObjCmd,
(ClientData) 0, (Tcl_CmdDeleteProc *) NULL);
- Tcl_CreateObjCommand(interp, "testregexp", TestregexpObjCmd,
- (ClientData) 0, (Tcl_CmdDeleteProc *) NULL);
Tcl_CreateObjCommand(interp, "testsaveresult", TestsaveresultCmd,
(ClientData) 0, (Tcl_CmdDeleteProc *) NULL);
Tcl_CreateCommand(interp, "testsetassocdata", TestsetassocdataCmd,
@@ -1317,19 +1311,15 @@ TestencodingObjCmd(dummy, interp, objc, objv)
Tcl_Obj *CONST objv[]; /* Argument objects. */
{
Tcl_Encoding encoding;
- Tcl_DString ds;
int index, length;
char *string;
- Tcl_Obj *resultPtr;
TclEncoding *encodingPtr;
static char *optionStrings[] = {
- "create", "delete", "toutf", "fromutf",
- "names", "system", "path",
+ "create", "delete", "path",
NULL
};
enum options {
- ENC_CREATE, ENC_DELETE, ENC_TOUTF, ENC_FROMUTF,
- ENC_NAMES, ENC_SYSTEM, ENC_PATH
+ ENC_CREATE, ENC_DELETE, ENC_PATH
};
if (Tcl_GetIndexFromObj(interp, objv[1], optionStrings, "option", 0,
@@ -1376,79 +1366,6 @@ TestencodingObjCmd(dummy, interp, objc, objv)
Tcl_FreeEncoding(encoding);
break;
}
- case ENC_TOUTF: {
- if (objc < 3) {
- return TCL_ERROR;
- }
- if (objc == 3) {
- string = "iso8859-1";
- } else {
- string = Tcl_GetString(objv[3]);
- }
- encoding = Tcl_GetEncoding(NULL, string);
-
- string = (char *) Tcl_GetByteArrayFromObj(objv[2], &length);
- Tcl_ExternalToUtfDString(encoding, string, length, &ds);
-
- /*
- * If the encoding performs a Tcl_Eval() (which is the case for
- * encodings created by the "encoding create" command, the
- * resultPtr from the interp will be invalidated and we need to
- * get it again.
- */
-
- resultPtr = Tcl_GetObjResult(interp);
- Tcl_SetStringObj(resultPtr, Tcl_DStringValue(&ds),
- Tcl_DStringLength(&ds));
- Tcl_DStringFree(&ds);
- Tcl_FreeEncoding(encoding);
- break;
- }
- case ENC_FROMUTF: {
- if (objc < 3) {
- return TCL_ERROR;
- }
- if (objc == 3) {
- string = "iso8859-1";
- } else {
- string = Tcl_GetString(objv[3]);
- }
- encoding = Tcl_GetEncoding(NULL, string);
-
- string = Tcl_GetStringFromObj(objv[2], &length);
- Tcl_UtfToExternalDString(encoding, string, length, &ds);
-
- /*
- * If the encoding performs a Tcl_Eval() (which is the case for
- * encodings created by the "encoding create" command, the
- * resultPtr from the interp will be invalidated and we need to
- * get it again.
- */
-
- resultPtr = Tcl_GetObjResult(interp);
- Tcl_SetByteArrayObj(resultPtr,
- (unsigned char *) Tcl_DStringValue(&ds),
- Tcl_DStringLength(&ds));
- Tcl_DStringFree(&ds);
- Tcl_FreeEncoding(encoding);
- break;
- }
-
- case ENC_NAMES: {
- Tcl_GetEncodingNames(interp);
- break;
- }
- case ENC_SYSTEM: {
- if (objc == 2) {
- Tcl_SetResult(interp, Tcl_GetEncodingName(NULL), TCL_STATIC);
- } else {
- char *str;
-
- str = Tcl_GetStringFromObj(objv[2], NULL);
- return Tcl_SetSystemEncoding(interp, str);
- }
- break;
- }
case ENC_PATH: {
if (objc == 2) {
Tcl_SetObjResult(interp, TclGetLibraryPath());
@@ -2584,251 +2501,6 @@ TestparsevarnameObjCmd(clientData, interp, objc, objv)
/*
*----------------------------------------------------------------------
*
- * TestregexpObjCmd --
- *
- * This procedure implements the "testregexp" command. It is
- * used to give a direct interface for regexp flags.
- *
- * Results:
- * A standard Tcl result.
- *
- * Side effects:
- * None.
- *
- *----------------------------------------------------------------------
- */
-
-static int
-TestregexpObjCmd(dummy, interp, objc, objv)
- ClientData dummy; /* Not used. */
- Tcl_Interp *interp; /* Current interpreter. */
- int objc; /* Number of arguments. */
- Tcl_Obj *CONST objv[]; /* Argument objects. */
-{
- TclRegexp *regExpr;
- char *string, *flagString, *start, *end;
- int flags, match, i, j;
-
- if (objc < 4) {
- Tcl_WrongNumArgs(interp, 1, objv,
- "flags exp string ?subMatchVar subMatchVar ...?");
- return TCL_ERROR;
- }
- flagString = Tcl_GetString(objv[1]);
- string = Tcl_GetString(objv[3]);
-
- flags = RegGetCompFlags(flagString);
- regExpr = (TclRegexp *) TclRegCompObj(interp, objv[2], flags);
- if (regExpr == NULL) {
- return TCL_ERROR;
- }
-
- flags = RegGetExecFlags(flagString);
- if (flags == -1) {
- /*
- * Do not try to match the string.
- */
-
- match = 0;
- } else {
- Tcl_DString stringBuffer;
- Tcl_UniChar *uniString;
- int numChars;
-
- /*
- * Remember the UTF-8 string so Tcl_RegExpRange() can convert the
- * matches from character to byte offsets.
- */
-
- regExpr->string = string;
-
- Tcl_DStringInit(&stringBuffer);
- uniString = TclUtfToUniCharDString(string, -1, &stringBuffer);
- numChars = Tcl_DStringLength(&stringBuffer) / sizeof(Tcl_UniChar);
-
- match = TclRegExpExecUniChar(interp, (Tcl_RegExp) regExpr, uniString,
- numChars, flags);
- Tcl_DStringFree(&stringBuffer);
-
- if (match < 0) {
- return TCL_ERROR;
- }
- if (flags & REG_NOSUB) {
- for (i = 0; i <= (int) regExpr->re.re_nsub; i++) {
- regExpr->matches[i].rm_so = -1;
- regExpr->matches[i].rm_eo = -1;
- }
- }
- }
- if (!match) {
- /*
- * Set the interpreter's object result to an integer object w/ value 0.
- */
-
- Tcl_SetIntObj(Tcl_GetObjResult(interp), 0);
- return TCL_OK;
- }
-
- /*
- * If additional variable names have been specified, return
- * index information in those variables.
- */
-
- for (i = 0, j = 4; j < objc; i++, j++) {
- char *result;
- char *currentString = Tcl_GetString(objv[j]);
-
- Tcl_RegExpRange((Tcl_RegExp) regExpr, i, &start, &end);
- if (start == NULL) {
- result = Tcl_SetVar(interp, currentString, "", 0);
- } else {
- char savedChar, *first, *last;
- char *tempString = Tcl_GetString(objv[3]);
- first = tempString + (start - string);
- last = tempString + (end - string);
- if (first == last) { /* don't modify argument */
- result = Tcl_SetVar(interp, currentString, "", 0);
- } else {
- savedChar = *last;
- *last = 0;
- result = Tcl_SetVar(interp, currentString, first, 0);
- *last = savedChar;
- }
- }
- if (result == NULL) {
- Tcl_AppendResult(interp, "couldn't set variable \"",
- currentString, "\"", (char *) NULL);
- return TCL_ERROR;
- }
- }
-
- /*
- * Set the interpreter's object result to an integer object w/ value 1.
- */
-
- Tcl_SetIntObj(Tcl_GetObjResult(interp), 1);
- return TCL_OK;
-}
-
-/*
- *----------------------------------------------------------------------
- *
- * RegGetCompFlags --
- *
- * Internal interface to regular expression compile flags.
- * Converts a string of chars to a single flag.
- *
- * Results:
- * Returns a flags for regular expression compilation.
- *
- * Side effects:
- * None.
- *
- *----------------------------------------------------------------------
- */
-static int
-RegGetCompFlags(s)
- char *s;
-{
- char c;
- register char *p;
- int result = REG_ADVANCED;
-
- for (p = s; (c = *p) != '\0'; p++)
- switch (c) {
- case 'a':
- result |= REG_ADVF;
- break;
- case 'b':
- result &= ~REG_ADVANCED;
- break;
- case 'e':
- result &= ~REG_ADVF;
- result |= REG_EXTENDED;
- break;
- case 'i':
- result |= REG_ICASE;
- break;
- case 'm':
- case 'n':
- result |= REG_NEWLINE;
- break;
- case 'p':
- result |= REG_NLSTOP;
- break;
- case 'q':
- result &= ~REG_ADVANCED;
- result |= REG_QUOTE;
- break;
- case 's':
- result |= REG_NOSUB;
- break;
- case 'w':
- result |= REG_NLANCH;
- break;
- case 'x':
- result |= REG_EXPANDED;
- break;
- case '+':
- result |= REG_FAKE;
- break;
- case ',':
- result |= REG_PROGRESS;
- break;
- }
- return result;
-}
-
-/*
- *----------------------------------------------------------------------
- *
- * RegGetExecFlags --
- *
- * Internal interface to regular expression exec flags.
- * Converts a string of chars to a single flag.
- *
- * Results:
- * Returns a flags for regular expression matching.
- *
- * Side effects:
- * None.
- *
- *----------------------------------------------------------------------
- */
-static int
-RegGetExecFlags(s)
- char *s;
-{
- char c;
- register char *p;
- int result = 0;
-
- for (p = s; (c = *p) != '\0'; p++)
- switch (c) {
- case '^':
- result |= REG_NOTBOL;
- break;
- case '$':
- result |= REG_NOTEOL;
- break;
- case ';':
- result |= REG_FTRACE;
- break;
- case ':':
- result |= REG_MTRACE;
- break;
- case '.':
- result |= REG_SMALL;
- break;
- case '/':
- return -1;
- }
- return result;
-}
-
-/*
- *----------------------------------------------------------------------
- *
* TestsetassocdataCmd --
*
* This procedure implements the "testsetassocdata" command. It is used
diff --git a/tests/cmdAH.test b/tests/cmdAH.test
index 2e473fe..d3c054f 100644
--- a/tests/cmdAH.test
+++ b/tests/cmdAH.test
@@ -9,17 +9,33 @@
# See the file "license.terms" for information on usage and redistribution
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
-# RCS: @(#) $Id: cmdAH.test,v 1.1.2.2 1998/09/24 23:59:20 stanton Exp $
+# RCS: @(#) $Id: cmdAH.test,v 1.1.2.3 1998/10/21 20:40:07 stanton Exp $
if {[string compare test [info procs test]] == 1} then {source defs}
global env
catch {set platform [testgetplatform]}
-test cmdAH-1.1 {Tcl_CdObjCmd} {
+test cmdAH-0.1 {Tcl_BreakObjCmd, errors} {
+ list [catch {break foo} msg] $msg
+} {1 {wrong # args: should be "break"}}
+test cmdAH-0.2 {Tcl_BreakObjCmd, success} {
+ list [catch {break} msg] $msg
+} {3 {}}
+
+# Tcl_CaseObjCmd is tested in case.test
+
+test cmdAH-1.1 {Tcl_CatchObjCmd, errors} {
+ list [catch {catch} msg] $msg
+} {1 {wrong # args: should be "catch command ?varName?"}}
+test cmdAH-1.2 {Tcl_CatchObjCmd, errors} {
+ list [catch {catch foo bar baz} msg] $msg
+} {1 {wrong # args: should be "catch command ?varName?"}}
+
+test cmdAH-2.1 {Tcl_CdObjCmd} {
list [catch {cd foo bar} msg] $msg
} {1 {wrong # args: should be "cd ?dirName?"}}
-test cmdAH-1.2 {Tcl_CdObjCmd} {
+test cmdAH-2.2 {Tcl_CdObjCmd} {
file delete -force foo
file mkdir foo
cd foo
@@ -28,7 +44,7 @@ test cmdAH-1.2 {Tcl_CdObjCmd} {
file delete foo
set result
} foo
-test cmdAH-1.3 {Tcl_CdObjCmd} {
+test cmdAH-2.3 {Tcl_CdObjCmd} {
global env
set oldpwd [pwd]
set temp $env(HOME)
@@ -42,7 +58,7 @@ test cmdAH-1.3 {Tcl_CdObjCmd} {
set env(HOME) $temp
set result
} 1
-test cmdAH-1.4 {Tcl_CdObjCmd} {
+test cmdAH-2.4 {Tcl_CdObjCmd} {
global env
set oldpwd [pwd]
set temp $env(HOME)
@@ -56,31 +72,107 @@ test cmdAH-1.4 {Tcl_CdObjCmd} {
set env(HOME) $temp
set result
} 1
-test cmdAH-1.5 {Tcl_CdObjCmd} {
+test cmdAH-2.5 {Tcl_CdObjCmd} {
list [catch {cd ~~} msg] $msg
} {1 {user "~" doesn't exist}}
-test cmdAH-1.6 {Tcl_CdObjCmd} {
+test cmdAH-2.6 {Tcl_CdObjCmd} {
list [catch {cd _foobar} msg] $msg
} {1 {couldn't change working directory to "_foobar": no such file or directory}}
+test cmdAH-2.7 {Tcl_ConcatObjCmd} {
+ concat
+} {}
+test cmdAH-2.8 {Tcl_ConcatObjCmd} {
+ concat a
+} a
+test cmdAH-2.9 {Tcl_ConcatObjCmd} {
+ concat a {b c}
+} {a b c}
+
+test cmdAH-3.1 {Tcl_ContinueObjCmd, errors} {
+ list [catch {continue foo} msg] $msg
+} {1 {wrong # args: should be "continue"}}
+test cmdAH-3.2 {Tcl_ContinueObjCmd, success} {
+ list [catch {continue} msg] $msg
+} {4 {}}
+
+test cmdAH-4.1 {Tcl_EncodingObjCmd} {
+ list [catch {encoding} msg] $msg
+} {1 {wrong # args: should be "encoding option ?arg ...?"}}
+test cmdAH-4.2 {Tcl_EncodingObjCmd} {
+ list [catch {encoding foo} msg] $msg
+} {1 {bad option "foo": must be convertfrom, convertto, names, or system}}
+test cmdAH-4.3 {Tcl_EncodingObjCmd} {
+ list [catch {encoding convertto} msg] $msg
+} {1 {wrong # args: should be "encoding convertto ?encoding? data"}}
+test cmdAH-4.4 {Tcl_EncodingObjCmd} {
+ list [catch {encoding convertto foo bar} msg] $msg
+} {1 {unknown encoding "foo"}}
+test cmdAH-4.5 {Tcl_EncodingObjCmd} {
+ set system [encoding system]
+ encoding system jis0208
+ set x [encoding convertto \u4e4e]
+ encoding system $system
+ set x
+} 8C
+test cmdAH-4.6 {Tcl_EncodingObjCmd} {
+ set system [encoding system]
+ encoding system identity
+ set x [encoding convertto jis0208 \u4e4e]
+ encoding system $system
+ set x
+} 8C
+test cmdAH-4.7 {Tcl_EncodingObjCmd} {
+ list [catch {encoding convertfrom} msg] $msg
+} {1 {wrong # args: should be "encoding convertfrom ?encoding? data"}}
+test cmdAH-4.8 {Tcl_EncodingObjCmd} {
+ list [catch {encoding convertfrom foo bar} msg] $msg
+} {1 {unknown encoding "foo"}}
+test cmdAH-4.9 {Tcl_EncodingObjCmd} {
+ set system [encoding system]
+ encoding system jis0208
+ set x [encoding convertfrom 8C]
+ encoding system $system
+ set x
+} \u4e4e
+test cmdAH-4.10 {Tcl_EncodingObjCmd} {
+ set system [encoding system]
+ encoding system identity
+ set x [encoding convertfrom jis0208 8C]
+ encoding system $system
+ set x
+} \u4e4e
+test cmdAH-4.11 {Tcl_EncodingObjCmd} {
+ list [catch {encoding names foo} msg] $msg
+} {1 {wrong # args: should be "encoding names"}}
+test cmdAH-4.12 {Tcl_EncodingObjCmd} {
+ list [catch {encoding system foo bar} msg] $msg
+} {1 {wrong # args: should be "encoding system ?encoding?"}}
+test cmdAH-4.13 {Tcl_EncodingObjCmd} {
+ set system [encoding system]
+ encoding system identity
+ set x [encoding system]
+ encoding system $system
+ set x
+} identity
-test cmdAH-2.1 {Tcl_FileObjCmd} {
+test cmdAH-5.1 {Tcl_FileObjCmd} {
list [catch file msg] $msg
} {1 {wrong # args: should be "file option ?arg ...?"}}
-test cmdAH-2.2 {Tcl_FileObjCmd} {
+test cmdAH-5.2 {Tcl_FileObjCmd} {
list [catch {file x} msg] $msg
} {1 {bad option "x": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-2.3 {Tcl_FileObjCmd} {
+test cmdAH-5.3 {Tcl_FileObjCmd} {
list [catch {file atime} msg] $msg
} {1 {wrong # args: should be "file atime name"}}
#volume
-test cmdAH-3.1 {Tcl_FileObjCmd: volumes} {
+test cmdAH-6.1 {Tcl_FileObjCmd: volumes} {
list [catch {file volumes x} msg] $msg
} {1 {wrong # args: should be "file volumes"}}
-test cmdAH-3.2 {Tcl_FileObjCmd: volumes} {
+test cmdAH-6.2 {Tcl_FileObjCmd: volumes} {
set volumeList [file volumes]
if { [llength $volumeList] == 0 } {
set result 0
@@ -88,18 +180,18 @@ test cmdAH-3.2 {Tcl_FileObjCmd: volumes} {
set result 1
}
} {1}
-test cmdAH-3.3 {Tcl_FileObjCmd: volumes} {macOrUnix} {
+test cmdAH-6.3 {Tcl_FileObjCmd: volumes} {macOrUnix} {
set volumeList [file volumes]
catch [list glob -nocomplain [lindex $volumeList 0]*]
} {0}
-test cmdAH-3.4 {Tcl_FileObjCmd: volumes} {pcOnly} {
+test cmdAH-6.4 {Tcl_FileObjCmd: volumes} {pcOnly} {
set volumeList [string tolower [file volumes]]
list [catch {lsearch $volumeList "c:/"} element] [expr $element != -1] [catch {list glob -nocomplain [lindex $volumeList $element]*}]
} {0 1 0}
# attributes
-test cmdAH-4.1 {Tcl_FileObjCmd - file attrs} {
+test cmdAH-7.1 {Tcl_FileObjCmd - file attrs} {
catch {file delete -force foo.file}
close [open foo.file w]
list [catch {file attributes foo.file}] [file delete -force foo.file]
@@ -111,175 +203,175 @@ if {[info commands testsetplatform] == {}} {
puts "This application hasn't been compiled with the \"testsetplatform\""
puts "command, so I can't test Tcl_FileObjCmd etc."
} else {
-test cmdAH-5.1 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.1 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname a b} msg] $msg
} {1 {wrong # args: should be "file dirname name"}}
-test cmdAH-5.2 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.2 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname /a/b
} /a
-test cmdAH-5.3 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.3 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname {}
} .
-test cmdAH-5.4 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.4 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
file dirname {}
} :
-test cmdAH-5.5 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.5 {Tcl_FileObjCmd: dirname} {
testsetplatform win
file dirname {}
} .
-test cmdAH-5.6 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.6 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname .def
} .
-test cmdAH-5.7 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.7 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
file dirname a
} :
-test cmdAH-5.8 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.8 {Tcl_FileObjCmd: dirname} {
testsetplatform win
file dirname a
} .
-test cmdAH-5.9 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.9 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname a/b/c.d
} a/b
-test cmdAH-5.10 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.10 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname a/b.c/d
} a/b.c
-test cmdAH-5.11 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.11 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
file dirname /.
} /
-test cmdAH-5.12 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.12 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname /} msg] $msg
} {0 /}
-test cmdAH-5.13 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.13 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname /foo} msg] $msg
} {0 /}
-test cmdAH-5.14 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.14 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname //foo} msg] $msg
} {0 /}
-test cmdAH-5.15 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.15 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname //foo/bar} msg] $msg
} {0 /foo}
-test cmdAH-5.16 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.16 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname {//foo\/bar/baz}} msg] $msg
} {0 {/foo\/bar}}
-test cmdAH-5.17 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.17 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname {//foo\/bar/baz/blat}} msg] $msg
} {0 {/foo\/bar/baz}}
-test cmdAH-5.18 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.18 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname /foo//} msg] $msg
} {0 /}
-test cmdAH-5.19 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.19 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname ./a} msg] $msg
} {0 .}
-test cmdAH-5.20 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.20 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname a/.a} msg] $msg
} {0 a}
-test cmdAH-5.21 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.21 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname c:foo} msg] $msg
} {0 c:}
-test cmdAH-5.22 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.22 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname c:} msg] $msg
} {0 c:}
-test cmdAH-5.23 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.23 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname c:/} msg] $msg
} {0 c:/}
-test cmdAH-5.24 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.24 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname {c:\foo}} msg] $msg
} {0 c:/}
-test cmdAH-5.25 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.25 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname {//foo/bar/baz}} msg] $msg
} {0 //foo/bar}
-test cmdAH-5.26 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.26 {Tcl_FileObjCmd: dirname} {
testsetplatform windows
list [catch {file dirname {//foo/bar}} msg] $msg
} {0 //foo/bar}
-test cmdAH-5.27 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.27 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname :} msg] $msg
} {0 :}
-test cmdAH-5.28 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.28 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname :Foo} msg] $msg
} {0 :}
-test cmdAH-5.29 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.29 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname Foo:} msg] $msg
} {0 Foo:}
-test cmdAH-5.30 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.30 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname Foo:bar} msg] $msg
} {0 Foo:}
-test cmdAH-5.31 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.31 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname :Foo:bar} msg] $msg
} {0 :Foo}
-test cmdAH-5.32 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.32 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname ::} msg] $msg
} {0 :}
-test cmdAH-5.33 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.33 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname :::} msg] $msg
} {0 ::}
-test cmdAH-5.34 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.34 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname /foo/bar/} msg] $msg
} {0 foo:}
-test cmdAH-5.35 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.35 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname /foo/bar} msg] $msg
} {0 foo:}
-test cmdAH-5.36 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.36 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname /foo} msg] $msg
} {0 foo:}
-test cmdAH-5.37 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.37 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname foo} msg] $msg
} {0 :}
-test cmdAH-5.38 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.38 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname ~/foo} msg] $msg
} {0 ~}
-test cmdAH-5.39 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.39 {Tcl_FileObjCmd: dirname} {
testsetplatform unix
list [catch {file dirname ~bar/foo} msg] $msg
} {0 ~bar}
-test cmdAH-5.40 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.40 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname ~bar/foo} msg] $msg
} {0 ~bar:}
-test cmdAH-5.41 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.41 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname ~/foo} msg] $msg
} {0 ~:}
-test cmdAH-5.42 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.42 {Tcl_FileObjCmd: dirname} {
testsetplatform mac
list [catch {file dirname ~:baz} msg] $msg
} {0 ~:}
-test cmdAH-5.43 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.43 {Tcl_FileObjCmd: dirname} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -288,7 +380,7 @@ test cmdAH-5.43 {Tcl_FileObjCmd: dirname} {
set env(HOME) $temp
set result
} {0 /home}
-test cmdAH-5.44 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.44 {Tcl_FileObjCmd: dirname} {
global env
set temp $env(HOME)
set env(HOME) "~"
@@ -297,7 +389,7 @@ test cmdAH-5.44 {Tcl_FileObjCmd: dirname} {
set env(HOME) $temp
set result
} {0 ~}
-test cmdAH-5.45 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.45 {Tcl_FileObjCmd: dirname} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -306,7 +398,7 @@ test cmdAH-5.45 {Tcl_FileObjCmd: dirname} {
set env(HOME) $temp
set result
} {0 /home}
-test cmdAH-5.46 {Tcl_FileObjCmd: dirname} {
+test cmdAH-8.46 {Tcl_FileObjCmd: dirname} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -318,171 +410,171 @@ test cmdAH-5.46 {Tcl_FileObjCmd: dirname} {
# tail
-test cmdAH-6.1 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.1 {Tcl_FileObjCmd: tail} {
testsetplatform unix
list [catch {file tail a b} msg] $msg
} {1 {wrong # args: should be "file tail name"}}
-test cmdAH-6.2 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.2 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail /a/b
} b
-test cmdAH-6.3 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.3 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail {}
} {}
-test cmdAH-6.4 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.4 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail {}
} {}
-test cmdAH-6.5 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.5 {Tcl_FileObjCmd: tail} {
testsetplatform win
file tail {}
} {}
-test cmdAH-6.6 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.6 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail .def
} .def
-test cmdAH-6.7 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.7 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail a
} a
-test cmdAH-6.8 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.8 {Tcl_FileObjCmd: tail} {
testsetplatform win
file tail a
} a
-test cmdAH-6.9 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.9 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file ta a/b/c.d
} c.d
-test cmdAH-6.10 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.10 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail a/b.c/d
} d
-test cmdAH-6.11 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.11 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail /.
} .
-test cmdAH-6.12 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.12 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail /
} {}
-test cmdAH-6.13 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.13 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail /foo
} foo
-test cmdAH-6.14 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.14 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail //foo
} foo
-test cmdAH-6.15 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.15 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail //foo/bar
} bar
-test cmdAH-6.16 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.16 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail {//foo\/bar/baz}
} baz
-test cmdAH-6.17 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.17 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail {//foo\/bar/baz/blat}
} blat
-test cmdAH-6.18 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.18 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail /foo//
} foo
-test cmdAH-6.19 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.19 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail ./a
} a
-test cmdAH-6.20 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.20 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail a/.a
} .a
-test cmdAH-6.21 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.21 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:foo
} foo
-test cmdAH-6.22 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.22 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:
} {}
-test cmdAH-6.23 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.23 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:/
} {}
-test cmdAH-6.24 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.24 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail {c:\foo}
} foo
-test cmdAH-6.25 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.25 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail {//foo/bar/baz}
} baz
-test cmdAH-6.26 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.26 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail {//foo/bar}
} {}
-test cmdAH-6.27 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.27 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail :
} :
-test cmdAH-6.28 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.28 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail :Foo
} Foo
-test cmdAH-6.29 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.29 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail Foo:
} {}
-test cmdAH-6.30 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.30 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail Foo:bar
} bar
-test cmdAH-6.31 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.31 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail :Foo:bar
} bar
-test cmdAH-6.32 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.32 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail ::
} ::
-test cmdAH-6.33 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.33 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail :::
} ::
-test cmdAH-6.34 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.34 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail /foo/bar/
} bar
-test cmdAH-6.35 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.35 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail /foo/bar
} bar
-test cmdAH-6.36 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.36 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail /foo
} {}
-test cmdAH-6.37 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.37 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail foo
} foo
-test cmdAH-6.38 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.38 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail ~:foo
} foo
-test cmdAH-6.39 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.39 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail ~bar:foo
} foo
-test cmdAH-6.40 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.40 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail ~bar/foo
} foo
-test cmdAH-6.41 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.41 {Tcl_FileObjCmd: tail} {
testsetplatform mac
file tail ~/foo
} foo
-test cmdAH-6.42 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.42 {Tcl_FileObjCmd: tail} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -491,7 +583,7 @@ test cmdAH-6.42 {Tcl_FileObjCmd: tail} {
set env(HOME) $temp
set result
} test
-test cmdAH-6.43 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.43 {Tcl_FileObjCmd: tail} {
global env
set temp $env(HOME)
set env(HOME) "~"
@@ -500,7 +592,7 @@ test cmdAH-6.43 {Tcl_FileObjCmd: tail} {
set env(HOME) $temp
set result
} {}
-test cmdAH-6.44 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.44 {Tcl_FileObjCmd: tail} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -509,7 +601,7 @@ test cmdAH-6.44 {Tcl_FileObjCmd: tail} {
set env(HOME) $temp
set result
} test
-test cmdAH-6.45 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.45 {Tcl_FileObjCmd: tail} {
global env
set temp $env(HOME)
set env(HOME) "/home/test"
@@ -518,166 +610,166 @@ test cmdAH-6.45 {Tcl_FileObjCmd: tail} {
set env(HOME) $temp
set result
} test
-test cmdAH-6.46 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.46 {Tcl_FileObjCmd: tail} {
testsetplatform unix
file tail {f.oo\bar/baz.bat}
} baz.bat
-test cmdAH-6.47 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.47 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:foo
} foo
-test cmdAH-6.48 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.48 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:
} {}
-test cmdAH-6.49 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.49 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail c:/foo
} foo
-test cmdAH-6.50 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.50 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail {c:/foo\bar}
} bar
-test cmdAH-6.51 {Tcl_FileObjCmd: tail} {
+test cmdAH-9.51 {Tcl_FileObjCmd: tail} {
testsetplatform windows
file tail {foo\bar}
} bar
# rootname
-test cmdAH-7.1 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.1 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
list [catch {file rootname a b} msg] $msg
} {1 {wrong # args: should be "file rootname name"}}
-test cmdAH-7.2 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.2 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname {}
} {}
-test cmdAH-7.3 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.3 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file ro foo
} foo
-test cmdAH-7.4 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.4 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname foo.
} foo
-test cmdAH-7.5 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.5 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname .foo
} {}
-test cmdAH-7.6 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.6 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname abc.def
} abc
-test cmdAH-7.7 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.7 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname abc.def.ghi
} abc.def
-test cmdAH-7.8 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.8 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname a/b/c.d
} a/b/c
-test cmdAH-7.9 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.9 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname a/b.c/d
} a/b.c/d
-test cmdAH-7.10 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.10 {Tcl_FileObjCmd: rootname} {
testsetplatform unix
file rootname a/b.c/
} a/b.c/
-test cmdAH-7.11 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.11 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file ro foo
} foo
-test cmdAH-7.12 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.12 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname {}
} {}
-test cmdAH-7.13 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.13 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname foo.
} foo
-test cmdAH-7.14 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.14 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname .foo
} {}
-test cmdAH-7.15 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.15 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname abc.def
} abc
-test cmdAH-7.16 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.16 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname abc.def.ghi
} abc.def
-test cmdAH-7.17 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.17 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname a:b:c.d
} a:b:c
-test cmdAH-7.18 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.18 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname a:b.c:d
} a:b.c:d
-test cmdAH-7.19 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.19 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname a/b/c.d
} a/b/c
-test cmdAH-7.20 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.20 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname a/b.c/d
} a/b.c/d
-test cmdAH-7.21 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.21 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname /a.b
} /a
-test cmdAH-7.22 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.22 {Tcl_FileObjCmd: rootname} {
testsetplatform mac
file rootname foo.c:
} foo.c:
-test cmdAH-7.23 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.23 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname {}
} {}
-test cmdAH-7.24 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.24 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file ro foo
} foo
-test cmdAH-7.25 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.25 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname foo.
} foo
-test cmdAH-7.26 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.26 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname .foo
} {}
-test cmdAH-7.27 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.27 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname abc.def
} abc
-test cmdAH-7.28 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.28 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname abc.def.ghi
} abc.def
-test cmdAH-7.29 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.29 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a/b/c.d
} a/b/c
-test cmdAH-7.30 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.30 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a/b.c/d
} a/b.c/d
-test cmdAH-7.31 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.31 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a\\b.c\\
} a\\b.c\\
-test cmdAH-7.32 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.32 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a\\b\\c.d
} a\\b\\c
-test cmdAH-7.33 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.33 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a\\b.c\\d
} a\\b.c\\d
-test cmdAH-7.34 {Tcl_FileObjCmd: rootname} {
+test cmdAH-10.34 {Tcl_FileObjCmd: rootname} {
testsetplatform windows
file rootname a\\b.c\\
} a\\b.c\\
@@ -695,139 +787,139 @@ foreach outer { {} a .a a. a.a } {
# extension
-test cmdAH-8.1 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.1 {Tcl_FileObjCmd: extension} {
testsetplatform unix
list [catch {file extension a b} msg] $msg
} {1 {wrong # args: should be "file extension name"}}
-test cmdAH-8.2 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.2 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension {}
} {}
-test cmdAH-8.3 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.3 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file ext foo
} {}
-test cmdAH-8.4 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.4 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension foo.
} .
-test cmdAH-8.5 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.5 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension .foo
} .foo
-test cmdAH-8.6 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.6 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension abc.def
} .def
-test cmdAH-8.7 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.7 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension abc.def.ghi
} .ghi
-test cmdAH-8.8 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.8 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension a/b/c.d
} .d
-test cmdAH-8.9 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.9 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension a/b.c/d
} {}
-test cmdAH-8.10 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.10 {Tcl_FileObjCmd: extension} {
testsetplatform unix
file extension a/b.c/
} {}
-test cmdAH-8.11 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.11 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file ext foo
} {}
-test cmdAH-8.12 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.12 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension {}
} {}
-test cmdAH-8.13 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.13 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension foo.
} .
-test cmdAH-8.14 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.14 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension .foo
} .foo
-test cmdAH-8.15 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.15 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension abc.def
} .def
-test cmdAH-8.16 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.16 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension abc.def.ghi
} .ghi
-test cmdAH-8.17 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.17 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension a:b:c.d
} .d
-test cmdAH-8.18 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.18 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension a:b.c:d
} {}
-test cmdAH-8.19 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.19 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension a/b/c.d
} .d
-test cmdAH-8.20 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.20 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension a/b.c/d
} {}
-test cmdAH-8.21 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.21 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension /a.b
} .b
-test cmdAH-8.22 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.22 {Tcl_FileObjCmd: extension} {
testsetplatform mac
file extension foo.c:
} {}
-test cmdAH-8.23 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.23 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension {}
} {}
-test cmdAH-8.24 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.24 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file ext foo
} {}
-test cmdAH-8.25 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.25 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension foo.
} .
-test cmdAH-8.26 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.26 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension .foo
} .foo
-test cmdAH-8.27 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.27 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension abc.def
} .def
-test cmdAH-8.28 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.28 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension abc.def.ghi
} .ghi
-test cmdAH-8.29 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.29 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a/b/c.d
} .d
-test cmdAH-8.30 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.30 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a/b.c/d
} {}
-test cmdAH-8.31 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.31 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a\\b.c\\
} {}
-test cmdAH-8.32 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.32 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a\\b\\c.d
} .d
-test cmdAH-8.33 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.33 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a\\b.c\\d
} {}
-test cmdAH-8.34 {Tcl_FileObjCmd: extension} {
+test cmdAH-11.34 {Tcl_FileObjCmd: extension} {
testsetplatform windows
file extension a\\b.c\\
} {}
@@ -844,56 +936,56 @@ foreach value {a..b a...b a.c..b ..b} result {..b ...b ..b ..b} {
# pathtype
-test cmdAH-9.1 {Tcl_FileObjCmd: pathtype} {
+test cmdAH-12.1 {Tcl_FileObjCmd: pathtype} {
testsetplatform unix
list [catch {file pathtype a b} msg] $msg
} {1 {wrong # args: should be "file pathtype name"}}
-test cmdAH-9.2 {Tcl_FileObjCmd: pathtype} {
+test cmdAH-12.2 {Tcl_FileObjCmd: pathtype} {
testsetplatform unix
file pathtype /a
} absolute
-test cmdAH-9.3 {Tcl_FileObjCmd: pathtype} {
+test cmdAH-12.3 {Tcl_FileObjCmd: pathtype} {
testsetplatform unix
file p a
} relative
-test cmdAH-9.4 {Tcl_FileObjCmd: pathtype} {
+test cmdAH-12.4 {Tcl_FileObjCmd: pathtype} {
testsetplatform windows
file pathtype c:a
} volumerelative
# split
-test cmdAH-10.1 {Tcl_FileObjCmd: split} {
+test cmdAH-13.1 {Tcl_FileObjCmd: split} {
testsetplatform unix
list [catch {file split a b} msg] $msg
} {1 {wrong # args: should be "file split name"}}
-test cmdAH-10.2 {Tcl_FileObjCmd: split} {
+test cmdAH-13.2 {Tcl_FileObjCmd: split} {
testsetplatform unix
file split a
} a
-test cmdAH-10.3 {Tcl_FileObjCmd: split} {
+test cmdAH-13.3 {Tcl_FileObjCmd: split} {
testsetplatform unix
file split a/b
} {a b}
# join
-test cmdAH-11.1 {Tcl_FileObjCmd: join} {
+test cmdAH-14.1 {Tcl_FileObjCmd: join} {
testsetplatform unix
file join a
} a
-test cmdAH-11.2 {Tcl_FileObjCmd: join} {
+test cmdAH-14.2 {Tcl_FileObjCmd: join} {
testsetplatform unix
file join a b
} a/b
-test cmdAH-11.3 {Tcl_FileObjCmd: join} {
+test cmdAH-14.3 {Tcl_FileObjCmd: join} {
testsetplatform unix
file join a b c d
} a/b/c/d
# error handling of Tcl_TranslateFileName
-test cmdAH-12.1 {Tcl_FileObjCmd} {
+test cmdAH-15.1 {Tcl_FileObjCmd} {
testsetplatform unix
list [catch {file atime ~_bad_user} msg] $msg
} {1 {user "_bad_user" doesn't exist}}
@@ -910,29 +1002,29 @@ if {[info commands testchmod] == {}} {
makeFile abcde gorp.file
makeDirectory dir.file
-test cmdAH-13.1 {Tcl_FileObjCmd: readable} {
+test cmdAH-16.1 {Tcl_FileObjCmd: readable} {
list [catch {file readable a b} msg] $msg
} {1 {wrong # args: should be "file readable name"}}
testchmod 444 gorp.file
-test cmdAH-13.2 {Tcl_FileObjCmd: readable} {
+test cmdAH-16.2 {Tcl_FileObjCmd: readable} {
file readable gorp.file
} 1
testchmod 333 gorp.file
-test cmdAH-13.3 {Tcl_FileObjCmd: readable} {unixOnly && !root} {
+test cmdAH-16.3 {Tcl_FileObjCmd: readable} {unixOnly && !root} {
file reada gorp.file
} 0
# writable
-test cmdAH-14.1 {Tcl_FileObjCmd: writable} {
+test cmdAH-17.1 {Tcl_FileObjCmd: writable} {
list [catch {file writable a b} msg] $msg
} {1 {wrong # args: should be "file writable name"}}
testchmod 555 gorp.file
-test cmdAH-14.2 {Tcl_FileObjCmd: writable} {!root} {
+test cmdAH-17.2 {Tcl_FileObjCmd: writable} {!root} {
file writable gorp.file
} 0
testchmod 222 gorp.file
-test cmdAH-14.3 {Tcl_FileObjCmd: writable} {
+test cmdAH-17.3 {Tcl_FileObjCmd: writable} {
file writable gorp.file
} 1
@@ -942,13 +1034,13 @@ file delete -force dir.file gorp.file
file mkdir dir.file
makeFile abcde gorp.file
-test cmdAH-15.1 {Tcl_FileObjCmd: executable} {
+test cmdAH-18.1 {Tcl_FileObjCmd: executable} {
list [catch {file executable a b} msg] $msg
} {1 {wrong # args: should be "file executable name"}}
-test cmdAH-15.2 {Tcl_FileObjCmd: executable} {
+test cmdAH-18.2 {Tcl_FileObjCmd: executable} {
file executable gorp.file
} 0
-test cmdAH-15.3 {Tcl_FileObjCmd: executable} {unix} {
+test cmdAH-18.3 {Tcl_FileObjCmd: executable} {unix} {
# Only on unix will setting the execute bit on a regular file
# cause that file to be executable.
@@ -956,14 +1048,14 @@ test cmdAH-15.3 {Tcl_FileObjCmd: executable} {unix} {
file exe gorp.file
} 1
-test cmdAH-15.4 {Tcl_FileObjCmd: executable} {mac} {
+test cmdAH-18.4 {Tcl_FileObjCmd: executable} {mac} {
# On mac, the only executable files are of type APPL.
set x [file exe gorp.file]
file attrib gorp.file -type APPL
lappend x [file exe gorp.file]
} {0 1}
-test cmdAH-15.5 {Tcl_FileObjCmd: executable} {pc} {
+test cmdAH-18.5 {Tcl_FileObjCmd: executable} {pc} {
# On pc, must be a .exe, .com, etc.
set x [file exe gorp.file]
@@ -972,7 +1064,7 @@ test cmdAH-15.5 {Tcl_FileObjCmd: executable} {pc} {
file delete gorp.exe
set x
} {0 1}
-test cmdAH-15.6 {Tcl_FileObjCmd: executable} {
+test cmdAH-18.6 {Tcl_FileObjCmd: executable} {
# Directories are always executable.
file exe dir.file
@@ -985,11 +1077,11 @@ file delete link.file
# exists
-test cmdAH-16.1 {Tcl_FileObjCmd: exists} {
+test cmdAH-19.1 {Tcl_FileObjCmd: exists} {
list [catch {file exists a b} msg] $msg
} {1 {wrong # args: should be "file exists name"}}
-test cmdAH-16.2 {Tcl_FileObjCmd: exists} {file exists gorp.file} 0
-test cmdAH-16.3 {Tcl_FileObjCmd: exists} {
+test cmdAH-19.2 {Tcl_FileObjCmd: exists} {file exists gorp.file} 0
+test cmdAH-19.3 {Tcl_FileObjCmd: exists} {
file exists [file join dir.file gorp.file]
} 0
catch {
@@ -997,10 +1089,10 @@ catch {
makeDirectory dir.file
makeFile 12345 [file join dir.file gorp.file]
}
-test cmdAH-16.4 {Tcl_FileObjCmd: exists} {
+test cmdAH-19.4 {Tcl_FileObjCmd: exists} {
file exists gorp.file
} 1
-test cmdAH-16.5 {Tcl_FileObjCmd: exists} {
+test cmdAH-19.5 {Tcl_FileObjCmd: exists} {
file exists [file join dir.file gorp.file]
} 1
@@ -1009,24 +1101,24 @@ if {[info commands testsetplatform] == {}} {
puts "This application hasn't been compiled with the \"testsetplatform\""
puts "command, so I can't test Tcl_FileObjCmd etc."
} else {
-test cmdAH-16.6 {Tcl_FileObjCmd: nativename} {
+test cmdAH-19.6 {Tcl_FileObjCmd: nativename} {
testsetplatform unix
list [catch {file nativename a/b} msg] $msg [testsetplatform $platform]
} {0 a/b {}}
-test cmdAH-16.7 {Tcl_FileObjCmd: nativename} {
+test cmdAH-19.7 {Tcl_FileObjCmd: nativename} {
testsetplatform windows
list [catch {file nativename a/b} msg] $msg [testsetplatform $platform]
} {0 {a\b} {}}
-test cmdAH-16.8 {Tcl_FileObjCmd: nativename} {
+test cmdAH-19.8 {Tcl_FileObjCmd: nativename} {
testsetplatform mac
list [catch {file nativename a/b} msg] $msg [testsetplatform $platform]
} {0 :a:b {}}
}
-test cmdAH-16.9 {Tcl_FileObjCmd: ~ : exists} {
+test cmdAH-19.9 {Tcl_FileObjCmd: ~ : exists} {
file exists ~nOsUcHuSeR
} 0
-test cmdAH-16.10 {Tcl_FileObjCmd: ~ : nativename} {
+test cmdAH-19.10 {Tcl_FileObjCmd: ~ : nativename} {
# should probably be 0 in fact...
catch {file nativename ~nOsUcHuSeR}
} 1
@@ -1042,7 +1134,7 @@ if {$tcl_platform(platform) == "unix"} {
makeFile 12345 /tmp/tcl.foo.dir/file
exec chmod 000 /tmp/tcl.foo.dir
if {$user != "root"} {
- test cmdAH-16.11 {Tcl_FileObjCmd: exists} {
+ test cmdAH-19.11 {Tcl_FileObjCmd: exists} {
file exists /tmp/tcl.foo.dir/file
} 0
}
@@ -1060,65 +1152,65 @@ catch {exec chmod 765 gorp.file}
# atime
-test cmdAH-17.1 {Tcl_FileObjCmd: atime} {
+test cmdAH-20.1 {Tcl_FileObjCmd: atime} {
list [catch {file atime a b} msg] $msg
} {1 {wrong # args: should be "file atime name"}}
-test cmdAH-17.2 {Tcl_FileObjCmd: atime} {
+test cmdAH-20.2 {Tcl_FileObjCmd: atime} {
catch {unset stat}
file stat gorp.file stat
list [expr {[file mtime gorp.file] == $stat(mtime)}] \
[expr {[file atime gorp.file] == $stat(atime)}]
} {1 1}
-test cmdAH-17.3 {Tcl_FileObjCmd: atime} {
+test cmdAH-20.3 {Tcl_FileObjCmd: atime} {
string tolower [list [catch {file atime _bogus_} msg] \
$msg $errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
# isdirectory
-test cmdAH-18.1 {Tcl_FileObjCmd: isdirectory} {
+test cmdAH-21.1 {Tcl_FileObjCmd: isdirectory} {
list [catch {file isdirectory a b} msg] $msg
} {1 {wrong # args: should be "file isdirectory name"}}
-test cmdAH-18.2 {Tcl_FileObjCmd: isdirectory} {
+test cmdAH-21.2 {Tcl_FileObjCmd: isdirectory} {
file isdirectory gorp.file
} 0
-test cmdAH-18.3 {Tcl_FileObjCmd: isdirectory} {
+test cmdAH-21.3 {Tcl_FileObjCmd: isdirectory} {
file isd dir.file
} 1
# isfile
-test cmdAH-19.1 {Tcl_FileObjCmd: isfile} {
+test cmdAH-22.1 {Tcl_FileObjCmd: isfile} {
list [catch {file isfile a b} msg] $msg
} {1 {wrong # args: should be "file isfile name"}}
-test cmdAH-19.2 {Tcl_FileObjCmd: isfile} {file isfile gorp.file} 1
-test cmdAH-19.3 {Tcl_FileObjCmd: isfile} {file isfile dir.file} 0
+test cmdAH-22.2 {Tcl_FileObjCmd: isfile} {file isfile gorp.file} 1
+test cmdAH-22.3 {Tcl_FileObjCmd: isfile} {file isfile dir.file} 0
# lstat and readlink: don't run these tests everywhere, since not all
# sites will have symbolic links
catch {exec ln -s gorp.file link.file}
-test cmdAH-20.1 {Tcl_FileObjCmd: lstat} {
+test cmdAH-23.1 {Tcl_FileObjCmd: lstat} {
list [catch {file lstat a} msg] $msg
} {1 {wrong # args: should be "file lstat name varName"}}
-test cmdAH-20.2 {Tcl_FileObjCmd: lstat} {
+test cmdAH-23.2 {Tcl_FileObjCmd: lstat} {
list [catch {file lstat a b c} msg] $msg
} {1 {wrong # args: should be "file lstat name varName"}}
-test cmdAH-20.3 {Tcl_FileObjCmd: lstat} {unixOnly nonPortable} {
+test cmdAH-23.3 {Tcl_FileObjCmd: lstat} {unixOnly nonPortable} {
catch {unset stat}
file lstat link.file stat
lsort [array names stat]
} {atime ctime dev gid ino mode mtime nlink size type uid}
-test cmdAH-20.4 {Tcl_FileObjCmd: lstat} {unixOnly nonPortable} {
+test cmdAH-23.4 {Tcl_FileObjCmd: lstat} {unixOnly nonPortable} {
catch {unset stat}
file lstat link.file stat
list $stat(nlink) [expr $stat(mode)&0777] $stat(type)
} {1 511 link}
-test cmdAH-20.5 {Tcl_FileObjCmd: lstat errors} {nonPortable} {
+test cmdAH-23.5 {Tcl_FileObjCmd: lstat errors} {nonPortable} {
string tolower [list [catch {file lstat _bogus_ stat} msg] \
$msg $errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
-test cmdAH-20.6 {Tcl_FileObjCmd: lstat errors} {
+test cmdAH-23.6 {Tcl_FileObjCmd: lstat errors} {
catch {unset x}
set x 44
list [catch {file lstat gorp.file x} msg] $msg $errorCode
@@ -1127,10 +1219,10 @@ catch {unset stat}
# mtime
-test cmdAH-21.1 {Tcl_FileObjCmd: mtime} {
+test cmdAH-24.1 {Tcl_FileObjCmd: mtime} {
list [catch {file mtime a b} msg] $msg
} {1 {wrong # args: should be "file mtime name"}}
-test cmdAH-21.2 {Tcl_FileObjCmd: mtime} {
+test cmdAH-24.2 {Tcl_FileObjCmd: mtime} {
set old [file mtime gorp.file]
after 2000
set f [open gorp.file w]
@@ -1139,17 +1231,17 @@ test cmdAH-21.2 {Tcl_FileObjCmd: mtime} {
set new [file mtime gorp.file]
expr {($new > $old) && ($new <= ($old+5))}
} {1}
-test cmdAH-21.3 {Tcl_FileObjCmd: mtime} {
+test cmdAH-24.3 {Tcl_FileObjCmd: mtime} {
catch {unset stat}
file stat gorp.file stat
list [expr {[file mtime gorp.file] == $stat(mtime)}] \
[expr {[file atime gorp.file] == $stat(atime)}]
} {1 1}
-test cmdAH-21.4 {Tcl_FileObjCmd: mtime} {
+test cmdAH-24.4 {Tcl_FileObjCmd: mtime} {
string tolower [list [catch {file mtime _bogus_} msg] $msg \
$errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
-test cmdAH-21.5 {Tcl_FileObjCmd: mtime} {
+test cmdAH-24.5 {Tcl_FileObjCmd: mtime} {
# Under Unix, use a file in /tmp to avoid clock skew due to NFS.
# On other platforms, just use a file in the local directory.
@@ -1172,43 +1264,43 @@ test cmdAH-21.5 {Tcl_FileObjCmd: mtime} {
# owned
-test cmdAH-22.1 {Tcl_FileObjCmd: owned} {
+test cmdAH-25.1 {Tcl_FileObjCmd: owned} {
list [catch {file owned a b} msg] $msg
} {1 {wrong # args: should be "file owned name"}}
-test cmdAH-22.2 {Tcl_FileObjCmd: owned} {
+test cmdAH-25.2 {Tcl_FileObjCmd: owned} {
file owned gorp.file
} 1
-test cmdAH-22.3 {Tcl_FileObjCmd: owned} {unixOnly && !root} {
+test cmdAH-25.3 {Tcl_FileObjCmd: owned} {unixOnly && !root} {
file owned /
} 0
# readlink
-test cmdAH-23.1 {Tcl_FileObjCmd: readlink} {
+test cmdAH-26.1 {Tcl_FileObjCmd: readlink} {
list [catch {file readlink a b} msg] $msg
} {1 {wrong # args: should be "file readlink name"}}
-test cmdAH-23.2 {Tcl_FileObjCmd: readlink} {unixOnly nonPortable} {
+test cmdAH-26.2 {Tcl_FileObjCmd: readlink} {unixOnly nonPortable} {
file readlink link.file
} gorp.file
-test cmdAH-23.3 {Tcl_FileObjCmd: readlink errors} {unixOnly nonPortable} {
+test cmdAH-26.3 {Tcl_FileObjCmd: readlink errors} {unixOnly nonPortable} {
list [catch {file readlink _bogus_} msg] [string tolower $msg] \
[string tolower $errorCode]
} {1 {could not readlink "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
-test cmdAH-23.4 {Tcl_FileObjCmd: readlink errors} {macOnly nonPortable} {
+test cmdAH-26.4 {Tcl_FileObjCmd: readlink errors} {macOnly nonPortable} {
list [catch {file readlink _bogus_} msg] [string tolower $msg] \
[string tolower $errorCode]
} {1 {could not readlink "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
-test cmdAH-23.5 {Tcl_FileObjCmd: readlink errors} {pcOnly nonPortable} {
+test cmdAH-26.5 {Tcl_FileObjCmd: readlink errors} {pcOnly nonPortable} {
list [catch {file readlink _bogus_} msg] [string tolower $msg] \
[string tolower $errorCode]
} {1 {could not readlink "_bogus_": invalid argument} {posix einval {invalid argument}}}
# size
-test cmdAH-24.1 {Tcl_FileObjCmd: size} {
+test cmdAH-27.1 {Tcl_FileObjCmd: size} {
list [catch {file size a b} msg] $msg
} {1 {wrong # args: should be "file size name"}}
-test cmdAH-24.2 {Tcl_FileObjCmd: size} {
+test cmdAH-27.2 {Tcl_FileObjCmd: size} {
set oldsize [file size gorp.file]
set f [open gorp.file a]
fconfigure $f -translation lf -eofchar {}
@@ -1216,7 +1308,7 @@ test cmdAH-24.2 {Tcl_FileObjCmd: size} {
close $f
expr {[file size gorp.file] - $oldsize}
} {10}
-test cmdAH-24.3 {Tcl_FileObjCmd: size} {
+test cmdAH-27.3 {Tcl_FileObjCmd: size} {
string tolower [list [catch {file size _bogus_} msg] $msg \
$errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
@@ -1227,37 +1319,37 @@ catch {testsetplatform $platform}
makeFile "Test string" gorp.file
catch {exec chmod 765 gorp.file}
-test cmdAH-25.1 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.1 {Tcl_FileObjCmd: stat} {
list [catch {file stat _bogus_} msg] $msg $errorCode
} {1 {wrong # args: should be "file stat name varName"} NONE}
-test cmdAH-25.2 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.2 {Tcl_FileObjCmd: stat} {
list [catch {file stat _bogus_ a b} msg] $msg $errorCode
} {1 {wrong # args: should be "file stat name varName"} NONE}
-test cmdAH-25.3 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.3 {Tcl_FileObjCmd: stat} {
catch {unset stat}
file stat gorp.file stat
lsort [array names stat]
} {atime ctime dev gid ino mode mtime nlink size type uid}
-test cmdAH-25.4 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.4 {Tcl_FileObjCmd: stat} {
catch {unset stat}
file stat gorp.file stat
list $stat(nlink) $stat(size) $stat(type)
} {1 12 file}
-test cmdAH-25.5 {Tcl_FileObjCmd: stat} {unix} {
+test cmdAH-28.5 {Tcl_FileObjCmd: stat} {unix} {
catch {unset stat}
file stat gorp.file stat
expr $stat(mode)&0777
} {501}
-test cmdAH-25.6 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.6 {Tcl_FileObjCmd: stat} {
string tolower [list [catch {file stat _bogus_ stat} msg] \
$msg $errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
-test cmdAH-25.7 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.7 {Tcl_FileObjCmd: stat} {
catch {unset x}
set x 44
list [catch {file stat gorp.file x} msg] $msg $errorCode
} {1 {can't set "x(dev)": variable isn't array} NONE}
-test cmdAH-25.8 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.8 {Tcl_FileObjCmd: stat} {
# Sign extension of purported unsigned short to int.
close [open foo.test w]
@@ -1266,7 +1358,7 @@ test cmdAH-25.8 {Tcl_FileObjCmd: stat} {
file delete foo.test
set x
} 1
-test cmdAH-25.9 {Tcl_FileObjCmd: stat} {pc} {
+test cmdAH-28.9 {Tcl_FileObjCmd: stat} {pc} {
# stat of root directory was failing.
# don't care about answer, just that test runs.
@@ -1282,7 +1374,7 @@ test cmdAH-25.9 {Tcl_FileObjCmd: stat} {pc} {
file stat c:/ stat
file stat c:/. stat
} {}
-test cmdAH-25.10 {Tcl_FileObjCmd: stat} {pc nonPortable} {
+test cmdAH-28.10 {Tcl_FileObjCmd: stat} {pc nonPortable} {
# stat of root directory was failing.
# don't care about answer, just that test runs.
@@ -1290,7 +1382,7 @@ test cmdAH-25.10 {Tcl_FileObjCmd: stat} {pc nonPortable} {
file stat //bisque/tcl/ stat
file stat //bisque/tcl/. stat
} {}
-test cmdAH-25.11 {Tcl_FileObjCmd: stat} {pc nonPortable} {
+test cmdAH-28.11 {Tcl_FileObjCmd: stat} {pc nonPortable} {
# stat of network directory was returning id of current local drive.
set old [pwd]
@@ -1300,7 +1392,7 @@ test cmdAH-25.11 {Tcl_FileObjCmd: stat} {pc nonPortable} {
cd $old
expr {$stat(dev) == 2}
} 0
-test cmdAH-25.12 {Tcl_FileObjCmd: stat} {
+test cmdAH-28.12 {Tcl_FileObjCmd: stat} {
# stat(mode) with S_IFREG flag was returned as a negative number
# if mode_t was a short instead of an unsigned short.
@@ -1315,49 +1407,49 @@ catch {unset stat}
file delete link.file
-test cmdAH-26.1 {Tcl_FileObjCmd: type} {
+test cmdAH-29.1 {Tcl_FileObjCmd: type} {
list [catch {file size a b} msg] $msg
} {1 {wrong # args: should be "file size name"}}
-test cmdAH-26.2 {Tcl_FileObjCmd: type} {
+test cmdAH-29.2 {Tcl_FileObjCmd: type} {
file type dir.file
} directory
-test cmdAH-26.3 {Tcl_FileObjCmd: type} {
+test cmdAH-29.3 {Tcl_FileObjCmd: type} {
file type gorp.file
} file
-test cmdAH-26.4 {Tcl_FileObjCmd: type} {unixOnly nonPortable} {
+test cmdAH-29.4 {Tcl_FileObjCmd: type} {unixOnly nonPortable} {
exec ln -s a/b/c link.file
set result [file type link.file]
file delete link.file
set result
} link
-test cmdAH-26.5 {Tcl_FileObjCmd: type} {
+test cmdAH-29.5 {Tcl_FileObjCmd: type} {
string tolower [list [catch {file type _bogus_} msg] $msg $errorCode]
} {1 {could not read "_bogus_": no such file or directory} {posix enoent {no such file or directory}}}
# Error conditions
-test cmdAH-27.1 {error conditions} {
+test cmdAH-30.1 {error conditions} {
list [catch {file gorp x} msg] $msg
} {1 {bad option "gorp": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.2 {error conditions} {
+test cmdAH-30.2 {error conditions} {
list [catch {file ex x} msg] $msg
} {1 {ambiguous option "ex": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.3 {error conditions} {
+test cmdAH-30.3 {error conditions} {
list [catch {file is x} msg] $msg
} {1 {ambiguous option "is": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.4 {error conditions} {
+test cmdAH-30.4 {error conditions} {
list [catch {file z x} msg] $msg
} {1 {bad option "z": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.5 {error conditions} {
+test cmdAH-30.5 {error conditions} {
list [catch {file read x} msg] $msg
} {1 {ambiguous option "read": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.6 {error conditions} {
+test cmdAH-30.6 {error conditions} {
list [catch {file s x} msg] $msg
} {1 {ambiguous option "s": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.7 {error conditions} {
+test cmdAH-30.7 {error conditions} {
list [catch {file t x} msg] $msg
} {1 {ambiguous option "t": must be atime, attributes, copy, delete, dirname, executable, exists, extension, isdirectory, isfile, join, lstat, mtime, mkdir, nativename, owned, pathtype, readable, readlink, rename, rootname, size, split, stat, tail, type, volumes, or writable}}
-test cmdAH-27.8 {error conditions} {
+test cmdAH-30.8 {error conditions} {
list [catch {file dirname ~woohgy} msg] $msg
} {1 {user "woohgy" doesn't exist}}
@@ -1370,3 +1462,4 @@ file delete gorp.file
file delete link.file
return
+
diff --git a/tests/encoding.test b/tests/encoding.test
index 824ae48..e0f2521 100644
--- a/tests/encoding.test
+++ b/tests/encoding.test
@@ -23,83 +23,139 @@ proc fromutf {args} {
lappend x "fromutf $args"
}
-test encoding-1.1 {InitEncoding} {
-} {}
+# TclInitEncodingSubsystem is tested by the rest of this file
+# TclFinalizeEncodingSubsystem is not currently tested
-test encoding-3.1 {Tcl_CreateEncodingType: new} {
- testencoding create foo {toutf 1} {fromutf 2}
- set x {}
- testencoding toutf abcd foo
- testencoding fromutf abcd foo
- testencoding delete foo
- set x
-} {{toutf 1} {fromutf 2}}
-test encoding-3.2 {Tcl_CreateEncodingType: replace encoding} {
- testencoding create foo {toutf a} {fromutf b}
+test encoding-1.1 {Tcl_GetEncoding: system encoding} {
+ testencoding create foo toutf fromutf
+ set old [encoding system]
+ encoding system foo
set x {}
- testencoding toutf abcd foo
- testencoding fromutf abcd foo
+ encoding convertto abcd
+ encoding system $old
testencoding delete foo
set x
-} {{toutf a} {fromutf b}}
-
-test encoding-4.1 {Tcl_GetTextEncoding: existing encoding} {
+} {{fromutf }}
+test encoding-1.2 {Tcl_GetEncoding: existing encoding} {
testencoding create foo toutf fromutf
set x {}
- testencoding fromutf abcd foo
+ encoding convertto foo abcd
testencoding delete foo
set x
} {{fromutf }}
-test encoding-4.2 {Tcl_GetTextEncoding: load encoding} {
- list [testencoding fromutf \u4e4e jis0208] \
- [testencoding toutf 8C jis0208]
+test encoding-1.3 {Tcl_GetEncoding: load encoding} {
+ list [encoding convertto jis0208 \u4e4e] \
+ [encoding convertfrom jis0208 8C]
} "8C \u4e4e"
-test encoding-5.1 {Tcl_GetTextEncodingName} {
- set old [testencoding system]
- testencoding system jis0208
- set x [testencoding system]
- testencoding system identity
- testencoding system $old
+test encoding-2.1 {Tcl_FreeEncoding: refcount == 0} {
+ encoding convertto jis0208 \u4e4e
+} {8C}
+test encoding-2.2 {Tcl_FreeEncoding: refcount != 0} {
+ set system [encoding system]
+ set path [testencoding path]
+ encoding system jis0208 ;# incr ref count
+ testencoding path .
+ set x [encoding convertto jis0208 \u4e4e] ;# old one found
+ encoding system identity
+ lappend x [catch {encoding convertto jis0208 \u4e4e} msg] $msg
+ encoding system identity
+ testencoding path $path
+ encoding system $system
+ set x
+} {8C 1 {unknown encoding "jis0208"}}
+
+test encoding-3.1 {Tcl_GetEncodingName, NULL} {
+ set old [encoding system]
+ encoding system jis0208
+ set x [encoding system]
+ encoding system $old
+ set x
+} {jis0208}
+test encoding-3.2 {Tcl_GetEncodingName, non-null} {
+ set old [fconfigure stdout -encoding]
+ fconfigure stdout -encoding jis0208
+ set x [fconfigure stdout -encoding]
+ fconfigure stdout -encoding $old
set x
} {jis0208}
-test encoding-6.1 {Tcl_FreeTextEncoding: refcount == 0} {
- testencoding fromutf \u4e4e jis0208
-} {8C}
-test encoding-6.2 {Tcl_FreeTextEncoding: refcount != 0} {
- set system [testencoding system]
+test encoding-4.1 {Tcl_GetEncodingNames} {
+ file mkdir tmp/encoding
+ close [open tmp/encoding/junk.enc w]
+ close [open tmp/encoding/junk2.enc w]
+ cd tmp
set path [testencoding path]
- testencoding system jis0208 ;# incr ref count
testencoding path .
- set x [testencoding fromutf \u4e4e jis0208] ;# old one found
- testencoding system identity
- lappend x [testencoding fromutf \u4e4e jis0208]
- testencoding system identity
+ set x [encoding names]
testencoding path $path
- testencoding system $system
+ cd ..
+ file delete -force tmp
set x
-} "8C \xe4\xb9\x8e"
-
-test encoding-7.1 {Tcl_SetSystemTextEncoding} {
- set old [testencoding system]
- testencoding system jis0208
- set x [testencoding fromutf \u4e4e snarky]
- testencoding system identity
- testencoding system $old
+} {junk utf-8 cp1252 junk2 identity unicode iso8859-1}
+
+
+test encoding-5.1 {Tcl_SetSystemEncoding} {
+ set old [encoding system]
+ encoding system jis0208
+ set x [encoding convertto \u4e4e]
+ encoding system identity
+ encoding system $old
set x
} {8C}
-test encoding-7.2 {Tcl_SetSystemTextEncoding: test ref count} {
- set old [testencoding system]
- testencoding system $old
- string compare $old [testencoding system]
+test encoding-5.2 {Tcl_SetSystemEncoding: test ref count} {
+ set old [encoding system]
+ encoding system $old
+ string compare $old [encoding system]
} {0}
+test encoding-6.1 {Tcl_CreateEncoding: new} {
+ testencoding create foo {toutf 1} {fromutf 2}
+ set x {}
+ encoding convertfrom foo abcd
+ encoding convertto foo abcd
+ testencoding delete foo
+ set x
+} {{toutf 1} {fromutf 2}}
+test encoding-6.2 {Tcl_CreateEncoding: replace encoding} {
+ testencoding create foo {toutf a} {fromutf b}
+ set x {}
+ encoding convertfrom foo abcd
+ encoding convertto foo abcd
+ testencoding delete foo
+ set x
+} {{toutf a} {fromutf b}}
+
+test encoding-7.1 {Tcl_ExternalToUtfDString: small buffer} {
+ encoding convertfrom jis0208 8c8c8c8c
+} "\u543e\u543e\u543e\u543e"
+test encoding-7.2 {Tcl_UtfToExternalDString: big buffer} {
+ set a 8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C
+ append a $a
+ append a $a
+ append a $a
+ append a $a
+ set x [encoding convertfrom jis0208 $a]
+ list [string length $x] [string index $x 0]
+} "512 \u4e4e"
+
+test encoding-8.1 {Tcl_ExternalToUtf} {
+ set f [open dummy w]
+ fconfigure $f -translation binary -encoding iso8859-1
+ puts -nonewline $f "ab\x8c\xc1g"
+ close $f
+ set f [open dummy r]
+ fconfigure $f -translation binary -encoding shiftjis
+ set x [read $f]
+ close $f
+ file delete dummy
+ set x
+} "ab\u4e4eg"
-test encoding-8.1 {Tcl_UtfToExternalDString: small buffer} {
- testencoding fromutf "\u543e\u543e\u543e\u543e" jis0208
+test encoding-9.1 {Tcl_UtfToExternalDString: small buffer} {
+ encoding convertto jis0208 "\u543e\u543e\u543e\u543e"
} {8c8c8c8c}
-test encoding-8.2 {Tcl_UtfToExternalDString: big buffer} {
+test encoding-9.2 {Tcl_UtfToExternalDString: big buffer} {
set a \u4e4e\u4e4e\u4e4e\u4e4e\u4e4e\u4e4e\u4e4e\u4e4e
append a $a
append a $a
@@ -107,121 +163,125 @@ test encoding-8.2 {Tcl_UtfToExternalDString: big buffer} {
append a $a
append a $a
append a $a
- set x [testencoding fromutf $a jis0208]
+ set x [encoding convertto jis0208 $a]
list [string length $x] [string range $x 0 1]
} "1024 8C"
test encoding-10.1 {Tcl_UtfToExternal} {
-} {}
-
-test encoding-11.1 {Tcl_ExternalToUtfDString: small buffer} {
- testencoding toutf 8c8c8c8c jis0208
-} "\u543e\u543e\u543e\u543e"
-test encoding-11.2 {Tcl_UtfToExternalDString: big buffer} {
- set a 8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C8C
- append a $a
- append a $a
- append a $a
- append a $a
- set x [testencoding toutf $a jis0208]
- list [string length $x] [string index $x 0]
-} "512 \u4e4e"
-
-test encoding-13.1 {Tcl_ExternalToUtf} {
-} {}
+ set f [open dummy w]
+ fconfigure $f -translation binary -encoding shiftjis
+ puts -nonewline $f "ab\u4e4eg"
+ close $f
+ set f [open dummy r]
+ fconfigure $f -translation binary -encoding iso8859-1
+ set x [read $f]
+ close $f
+ file delete dummy
+ set x
+} "ab\x8c\xc1g"
-test encoding-14.1 {LoadEncodingTable: no encoding path} {
- set system [testencoding system]
+test encoding-11.1 {LoadEncodingFile: unknown encoding} {
+ set system [encoding system]
set path [testencoding path]
- testencoding system iso8859-1
+ encoding system iso8859-1
testencoding path {}
- set x [testencoding fromutf \u4e4e jis0208]
+ set x [list [catch {encoding convertto jis0208 \u4e4e} msg] $msg]
testencoding path $path
- testencoding system $system
- list $x [testencoding fromutf \u4e4e jis0208]
-} "? 8C"
-test encoding-14.2 {LoadEncodingTable: table file} {
- testencoding fromutf \u4e4e jis0208
-} {8C}
-test encoding-14.3 {LoadEncodingTable: escape file} {
- testencoding fromutf \u4e4e iso2022
+ encoding system $system
+ lappend x [encoding convertto jis0208 \u4e4e]
+} {1 {unknown encoding "jis0208"} 8C}
+test encoding-11.2 {LoadEncodingFile: single-byte} {
+ encoding convertfrom jis0201 \xa1
+} "\uff61"
+test encoding-11.3 {LoadEncodingFile: double-byte} {
+ encoding convertfrom jis0208 8C
+} "\u4e4e"
+test encoding-11.4 {LoadEncodingFile: multi-byte} {
+ encoding convertfrom shiftjis \x8c\xc1
+} "\u4e4e"
+test encoding-11.5 {LoadEncodingFile: escape file} {
+ encoding convertto iso2022 \u4e4e
} "\x1b(B\x1b$@8C"
-
-test encoding-15.1 {LoadConvertTable: bad file} {
- set system [testencoding system]
+test encoding-11.6 {LoadEncodingFile: invalid file} {
+ set system [encoding system]
set path [testencoding path]
- testencoding system identity
- testencoding path .
- file mkdir encoding
- set f [open encoding/splat.enc w]
+ encoding system identity
+ testencoding path tmp
+ file mkdir tmp/encoding
+ set f [open tmp/encoding/splat.enc w]
fconfigure $f -translation binary
puts $f "abcdefghijklmnop"
close $f
- set x [testencoding fromutf \u4e4e splat]
- file delete encoding/splat.enc
+ set x [list [catch {encoding convertto splat \u4e4e} msg] $msg]
+ file delete -force tmp
catch {file delete encoding}
testencoding path $path
- testencoding system $system
+ encoding system $system
set x
-} "\xe4\xb9\x8e"
-test encoding-15.2 {LoadConvertTable: normal encoding} {
- set x [testencoding fromutf \u120 iso8859-3]
- append x [testencoding fromutf \ud5 iso8859-3]
- append x [testencoding toutf \xd5 iso8859-3]
+} {1 {invalid encoding file "splat"}}
+
+# OpenEncodingFile is fully tested by the rest of the tests in this file.
+
+test encoding-12.1 {LoadTableEncoding: normal encoding} {
+ set x [encoding convertto iso8859-3 \u120]
+ append x [encoding convertto iso8859-3 \ud5]
+ append x [encoding convertfrom iso8859-3 \xd5]
} "\xd5?\u120"
-test encoding-15.3 {LoadConvertTable: single-byte encoding} {
- set x [testencoding fromutf ab\u0120g iso8859-3]
- append x [testencoding toutf ab\xd5g iso8859-3]
+test encoding-12.2 {LoadTableEncoding: single-byte encoding} {
+ set x [encoding convertto iso8859-3 ab\u0120g]
+ append x [encoding convertfrom iso8859-3 ab\xd5g]
} "ab\xd5gab\u120g"
-test encoding-15.4 {LoadConvertTable: multi-byte encoding} {
- set x [testencoding fromutf ab\u4e4eg shiftjis]
- append x [testencoding toutf ab\x8c\xc1g shiftjis]
+test encoding-12.3 {LoadTableEncoding: multi-byte encoding} {
+ set x [encoding convertto shiftjis ab\u4e4eg]
+ append x [encoding convertfrom shiftjis ab\x8c\xc1g]
} "ab\x8c\xc1gab\u4e4eg"
-test encoding-15.5 {LoadConvertTable: double-byte encoding} {
- set x [testencoding fromutf \u4e4e\u3b1 jis0208]
- append x [testencoding toutf 8C&A jis0208]
+test encoding-12.4 {LoadTableEncoding: double-byte encoding} {
+ set x [encoding convertto jis0208 \u4e4e\u3b1]
+ append x [encoding convertfrom jis0208 8C&A]
} "8C&A\u4e4e\u3b1"
-test encoding-15.6 {LoadConvertTable: symbol encoding} {
- set x [testencoding fromutf \u3b3 symbol]
- append x [testencoding fromutf \u67 symbol]
- append x [testencoding toutf \x67 symbol]
+test encoding-12.5 {LoadTableEncoding: symbol encoding} {
+ set x [encoding convertto symbol \u3b3]
+ append x [encoding convertto symbol \u67]
+ append x [encoding convertfrom symbol \x67]
} "\x67\x67\u3b3"
-test encoding-16.1 {LoadEscapeTable} {
- set x [testencoding fromutf ab\u4e4e\u68d9g iso2022]
+test encoding-13.1 {LoadEscapeTable} {
+ set x [encoding convertto iso2022 ab\u4e4e\u68d9g]
} "\x1b(Bab\x1b$@8C\x1b$(DD%\x1b(Bg"
-test encoding-17.1 {BinaryProc} {
- testencoding fromutf \x12\x34\x56\xff\x69 identity
+test encoding-14.1 {BinaryProc} {
+ encoding convertto identity \x12\x34\x56\xff\x69
} "\x12\x34\x56\xc3\xbf\x69"
-test encoding-18.1 {UtfToUtfProc} {
- testencoding fromutf \xa3 utf-8
+test encoding-15.1 {UtfToUtfProc} {
+ encoding convertto utf-8 \xa3
} "\xc2\xa3"
-test encoding-19.1 {UnicodeToUtfProc} {
- testencoding toutf NN unicode
+test encoding-16.1 {UnicodeToUtfProc} {
+ encoding convertfrom unicode NN
} "\u4e4e"
-test encoding-20.1 {UtfToUnicodeProc} {
+test encoding-17.1 {UtfToUnicodeProc} {
} {}
-test encoding-21.1 {TableToUtfProc} {
+test encoding-18.1 {TableToUtfProc} {
} {}
-test encoding-22.1 {UtfToTableProc} {
+test encoding-19.1 {TableFromUtfProc} {
} {}
-test encoding-23.1 {TableFreeProc} {
+test encoding-20.1 {TableFreefProc} {
} {}
-test encoding-24.1 {EscapeToUtfProc} {
+test encoding-21.1 {EscapeToUtfProc} {
} {}
-test encoding-25.1 {UtfToEscapeProc} {
+test encoding-22.1 {EscapeFromUtfProc} {
} {}
-test encoding-26.1 {EscapeFreeProc} {
-} {}
+# EscapeFreeProc, GetTableEncoding, unilen
+# are fully tested by the rest of this file
return
+
+
diff --git a/tests/regexp.test b/tests/regexp.test
index 873ab4d..a97a258 100644
--- a/tests/regexp.test
+++ b/tests/regexp.test
@@ -10,7 +10,7 @@
# See the file "license.terms" for information on usage and redistribution
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
-# RCS: @(#) $Id: regexp.test,v 1.1.2.2 1998/09/24 23:59:34 stanton Exp $
+# RCS: @(#) $Id: regexp.test,v 1.1.2.3 1998/10/21 20:40:08 stanton Exp $
if {[string compare test [info procs test]] == 1} then {source defs}
@@ -183,13 +183,13 @@ test regexp-6.2 {regexp errors} {
} {1 {wrong # args: should be "regexp ?switches? exp string ?matchVar? ?subMatchVar subMatchVar ...?"}}
test regexp-6.3 {regexp errors} {
list [catch {regexp -gorp a} msg] $msg
-} {1 {bad switch "-gorp": must be -indices, -nocase, or --}}
+} {1 {bad switch "-gorp": must be -indices, -nocase, -about, -expanded, or --}}
test regexp-6.4 {regexp errors} {
list [catch {regexp a( b} msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
+} {1 {couldn't compile regular expression pattern: parentheses () not balanced}}
test regexp-6.5 {regexp errors} {
list [catch {regexp a( b} msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
+} {1 {couldn't compile regular expression pattern: parentheses () not balanced}}
test regexp-6.6 {regexp errors} {
list [catch {regexp a a f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1 f1} msg] $msg
} {0 1}
@@ -328,7 +328,7 @@ test regexp-10.5 {regsub errors} {
} {1 {bad switch "-gorp": must be -all, -nocase, or --}}
test regexp-10.6 {regsub errors} {
list [catch {regsub -nocase a( b c d} msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
+} {1 {couldn't compile regular expression pattern: parentheses () not balanced}}
test regexp-10.7 {regsub errors} {
catch {unset f1}
set f1 44
diff --git a/tests/regexp2.test b/tests/regexp2.test
deleted file mode 100644
index eb99f76..0000000
--- a/tests/regexp2.test
+++ /dev/null
@@ -1,3176 +0,0 @@
-# Commands covered: regexp
-#
-# This Tcl-generated file contains tests for the regexp tcl command.
-# Sourcing this file into Tcl runs the tests and generates output for
-# errors. No output means no errors were found. Setting VERBOSE to
-# -1 will run tests that are known to fail.
-#
-# Copyright (c) 1998 Sun Microsystems, Inc.
-#
-# See the file "license.terms" for information on usage and redistribution
-# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
-#
-# SCCS: @(#) regexp2.test 1.4 98/01/22 14:47:42
-
-proc print {arg} {puts $arg}
-
-if {[string compare test [info procs test]] == 1} {
- source defs ; set VERBOSE -1
-}
-
-if {$VERBOSE != -1} {
- proc print {arg} {}
-}
-
-#
-# The remainder of this file is Tcl tests that have been
-# converted from Henry Spencer's regexp test suite.
-#
-
-# This file is a sequence of regression tests, one per line. The first
-# field is the RE, the second flags, the third a string to match the RE
-# against, the fourth the expected match, and subsequent fields the
-# expected substring matches. No fourth field means match not expected;
-# no later fields mean no substrings expected. If the "*" flag is set
-# (see below), the third field is the name of the compile error expected,
-# less the leading "REG_". Any field may be written as "" to signify an
-# empty string. Fourth and subsequent fields may have a suffix "@11"
-# (any decimal integer) indicating the offset where the match is expected;
-# fifth and subsequent fields may be "@" indicating no match is expected
-# for that subexpression.
-
-
-# The flag characters are complex and a bit eclectic. Generally speaking,
-# lowercase letters are compile options, uppercase are expected re_info
-# bits, and nonalphabetics are match options, controls for how the test is
-# run, or debugging options. The one small surprise is that AREs are the
-# default, and you must explicitly request lesser flavors of RE. The flags
-# are as follows. Be warned that a number of them are specific to this
-# RE implementation. It is admitted that some are not very mnemonic.
-#
-# - no-op (placeholder)
-# = map characters in all other fields (see below)
-# > map characters in later fields (see below)
-# * compile error expected (third field is error type)
-# / compile only, do not attempt match
-# [2 expect 2 (any decimal integer) subexpressions
-# + provide fake ch collating element and xy equiv class
-# , turn on compile tracing (probably not useful in this file)
-# ; turn on automaton tracing (probably not useful in this file)
-# : turn on match tracing (probably not useful in this file)
-# . force small state-set cache in matcher (to test cache replace)
-# ^ beginning of string is not beginning of line
-# $ end of string is not end of line
-#
-# & test as both BRE and ARE
-# b BRE
-# e ERE
-# q literal string, no metacharacters at all
-#
-# i case-independent matching
-# s no subexpression capture
-# p newlines are half-magic, excluded from . and [^ only
-# w newlines are half-magic, significant to ^ and $ only
-# n newlines are fully magic, both effects
-# x expanded RE syntax
-#
-# A backslash-_a_lphanumeric seen
-# B ERE/ARE literal-_b_race heuristic used
-# E backslash (_e_scape) seen within []
-# H looka_h_ead constraint seen
-# L _l_ocale-specific construct seen
-# M unportable (_m_achine-specific) construct seen
-# N RE can match empty (_n_ull) string
-# P non-_P_OSIX construct seen
-# Q {} _q_uantifier seen
-# R back _r_eference seen
-# S POSIX-un_s_pecified syntax seen
-# U saw original-POSIX botch: unmatched right paren in ERE (_u_gh)
-
-
-# The character-mapping flag causes some transformations to be done
-# before processing. This is mostly to get funny characters into the
-# strings. Specifically:
-#
-# _ becomes space
-# A becomes \007 (some compilers lack \a)
-# B becomes \b
-# E becomes \033
-# F becomes \f
-# N becomes \n
-# R becomes \r
-# T becomes \t
-# V becomes \v
-
-
-# The two areas we can't easily test are memory-allocation failures (which
-# are hard to provoke on command) and embedded NULs (which the current test
-# program can't easily do; that should be fixed).
-
-
-
-
-
-
-# basic sanity checks
-test regexp-1.81 {converted from line 81} {
- catch {unset var}
- list [catch {
- set match [regexp -- abc abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.82 {converted from line 82} {
- catch {unset var}
- list [catch {
- set match [regexp -- abc def ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.83 {converted from line 83} {
- catch {unset var}
- list [catch {
- set match [regexp -- abc xyabxabce var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# invalid option combinations
-# skipping char mapping test from line 86
-print {... skip test from line 86: a qe* INVARG}
-# skipping char mapping test from line 87
-print {... skip test from line 87: a ba* INVARG}
-
-
-# basic syntax
-# skipping the empty-re test from line 90
-
-test regexp-1.91 {converted from line 91} {
- catch {unset var}
- list [catch {
- set match [regexp -- a| a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.92 {converted from line 92} {
- catch {unset var}
- list [catch {
- set match [regexp -- a|b a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.93 {converted from line 93} {
- catch {unset var}
- list [catch {
- set match [regexp -- a|b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.94 {converted from line 94} {
- catch {unset var}
- list [catch {
- set match [regexp -- a||b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.95 {converted from line 95} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# parentheses
-test regexp-1.98 {converted from line 98} {
- catch {unset var}
- list [catch {
- set match [regexp -- (a)e ae var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ae a}}
-
-test regexp-1.99 {converted from line 99} {
- catch {unset var}
- list [catch {
- set match [regexp -- (a)e ae var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ae}}
-
-test regexp-1.100 {converted from line 100} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\(a\)b} ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab a}}
-
-test regexp-1.101 {converted from line 101} {
- catch {unset var}
- list [catch {
- set match [regexp -- a((b)c) abc var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc bc b}}
-
-test regexp-1.102 {converted from line 102} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)(c) abc var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc b c}}
-
-test regexp-1.103 {converted from line 103} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.104 {converted from line 104} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\(b} EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-# sigh, we blew it on the specs here... someday this will be fixed in POSIX,
-# but meanwhile, it's fixed in AREs
-
-test regexp-1.107 {converted from line 107} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?e)a)b a)b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a)b}}
-
-test regexp-1.108 {converted from line 108} {
- catch {unset var}
- list [catch {
- set match [regexp -- a)b EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.109 {converted from line 109} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\)b} EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.110 {converted from line 110} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:b)c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.111 {converted from line 111} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?e)a(?:b)c BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.112 {converted from line 112} {
- catch {unset var}
- list [catch {
- set match [regexp -- a()b ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab {}}}
-
-test regexp-1.113 {converted from line 113} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:)b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.114 {converted from line 114} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(|b)c ac var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.115 {converted from line 115} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b|)c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-
-
-# simple one-char matching (full mess of brackets done later)
-test regexp-1.118 {converted from line 118} {
- catch {unset var}
- list [catch {
- set match [regexp -- a.b axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.119 {converted from line 119} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?n)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.120 {converted from line 120} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[bc]d} abd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abd}}
-
-test regexp-1.121 {converted from line 121} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[bc]d} acd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 acd}}
-
-test regexp-1.122 {converted from line 122} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[bc]d} aed ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.123 {converted from line 123} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[^bc]d} abd ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.124 {converted from line 124} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[^bc]d} aed var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aed}}
-
-test regexp-1.125 {converted from line 125} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?p)a[^bc]d} {a
-d} ]
- list $match
- } msg] $msg
-} {0 0}
-
-
-
-# some context-dependent syntax (and some not)
-test regexp-1.128 {converted from line 128} {
- catch {unset var}
- list [catch {
- set match [regexp -- * BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.129 {converted from line 129} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)* * var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 *}}
-
-test regexp-1.130 {converted from line 130} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\(*\)} * var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 * *}}
-
-test regexp-1.131 {converted from line 131} {
- catch {unset var}
- list [catch {
- set match [regexp -- (*) BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.132 {converted from line 132} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)^* * var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 *}}
-
-test regexp-1.133 {converted from line 133} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.134 {converted from line 134} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^b ^b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.135 {converted from line 135} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)x^ x^ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 x^}}
-
-test regexp-1.136 {converted from line 136} {
- catch {unset var}
- list [catch {
- set match [regexp -- x^ IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-test regexp-1.137 {converted from line 137} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)
-^} {x
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {
-}}}
-
-test regexp-1.138 {converted from line 138} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\(^b\)} ^b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.139 {converted from line 139} {
- catch {unset var}
- list [catch {
- set match [regexp -- (^b) b var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 b b}}
-
-test regexp-1.140 {converted from line 140} {
- catch {unset var}
- list [catch {
- set match [regexp -- {x$} x var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 x}}
-
-test regexp-1.141 {converted from line 141} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\(x$\)} x var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 x x}}
-
-test regexp-1.142 {converted from line 142} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(x$)} x var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 x x}}
-
-test regexp-1.143 {converted from line 143} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)x$y} {x$y} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {x$y}}}
-
-test regexp-1.144 {converted from line 144} {
- catch {unset var}
- list [catch {
- set match [regexp -- {x$y} IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-test regexp-1.145 {converted from line 145} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)x$
-} {x
-} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {x
-}}}
-
-test regexp-1.146 {converted from line 146} {
- catch {unset var}
- list [catch {
- set match [regexp -- + BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.147 {converted from line 147} {
- catch {unset var}
- list [catch {
- set match [regexp -- ? BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# simple quantifiers
-test regexp-1.150 {converted from line 150} {
- catch {unset var}
- list [catch {
- set match [regexp -- a* aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aa}}
-
-test regexp-1.151 {converted from line 151} {
- catch {unset var}
- list [catch {
- set match [regexp -- a* b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.152 {converted from line 152} {
- catch {unset var}
- list [catch {
- set match [regexp -- a+ aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aa}}
-
-test regexp-1.153 {converted from line 153} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.154 {converted from line 154} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.155 {converted from line 155} {
- catch {unset var}
- list [catch {
- set match [regexp -- ** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.156 {converted from line 156} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)** *** var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ***}}
-
-test regexp-1.157 {converted from line 157} {
- catch {unset var}
- list [catch {
- set match [regexp -- a** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.158 {converted from line 158} {
- catch {unset var}
- list [catch {
- set match [regexp -- a**b BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.159 {converted from line 159} {
- catch {unset var}
- list [catch {
- set match [regexp -- *** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.160 {converted from line 160} {
- catch {unset var}
- list [catch {
- set match [regexp -- a++ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.161 {converted from line 161} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?+ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.162 {converted from line 162} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.163 {converted from line 163} {
- catch {unset var}
- list [catch {
- set match [regexp -- a+* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.164 {converted from line 164} {
- catch {unset var}
- list [catch {
- set match [regexp -- a*+ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# braces are messy
-test regexp-1.167 {converted from line 167} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,1} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.168 {converted from line 168} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,1} ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.169 {converted from line 169} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,0} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.170 {converted from line 170} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,2,3} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.171 {converted from line 171} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{257} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.172 {converted from line 172} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1000} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.173 {converted from line 173} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\{1 EBRACE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched {}}}
-
-test regexp-1.174 {converted from line 174} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1n} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.175 {converted from line 175} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\{b a\{b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\{b}}
-
-test regexp-1.176 {converted from line 176} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\{ a\{ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\{}}
-
-test regexp-1.177 {converted from line 177} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\{0,1\}b} cb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.178 {converted from line 178} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\{0,1} EBRACE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched {}}}
-
-test regexp-1.179 {converted from line 179} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\{0,1\\ BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.180 {converted from line 180} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.181 {converted from line 181} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,0}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.182 {converted from line 182} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,1}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.183 {converted from line 183} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,2}b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.184 {converted from line 184} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,2}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.185 {converted from line 185} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{0,}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.186 {converted from line 186} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,1}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.187 {converted from line 187} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,3}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaab}}
-
-test regexp-1.188 {converted from line 188} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,3}b b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.189 {converted from line 189} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{1,}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.190 {converted from line 190} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{2,3}b ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.191 {converted from line 191} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{2,3}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaab}}
-
-test regexp-1.192 {converted from line 192} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{2,}b ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.193 {converted from line 193} {
- catch {unset var}
- list [catch {
- set match [regexp -- a{2,}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaaab}}
-
-
-
-# brackets are too
-test regexp-1.196 {converted from line 196} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[bc]} ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.197 {converted from line 197} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[-]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-}}
-
-test regexp-1.198 {converted from line 198} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[.-.]]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-}}
-
-test regexp-1.199 {converted from line 199} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[.zero.]]} a0 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0}}
-
-test regexp-1.200 {converted from line 200} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[.zero.]-9]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-test regexp-1.201 {converted from line 201} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[0-[.9.]]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-# skipping char mapping test from line 202
-print {... skip test from line 202: a&&=x=&& &+L ax ax}
-# skipping char mapping test from line 203
-print {... skip test from line 203: a&&=x=&& &+L ay ay}
-# skipping char mapping test from line 204
-print {... skip test from line 204: a&&=x=&& &+L az}
-test regexp-1.205 {converted from line 205} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[0-[=x=]]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.206 {converted from line 206} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:digit:]]} a0 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0}}
-
-test regexp-1.207 {converted from line 207} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:woopsie:]]} ECTYPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character class}}
-
-test regexp-1.208 {converted from line 208} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:digit:]]} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.209 {converted from line 209} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[0-[:digit:]]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.210 {converted from line 210} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:<:]]a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.211 {converted from line 211} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:>:]]} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.212 {converted from line 212} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[..]]b} ECOLLATE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid collating element}}
-
-test regexp-1.213 {converted from line 213} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[==]]b} ECOLLATE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid collating element}}
-
-test regexp-1.214 {converted from line 214} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[::]]b} ECTYPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character class}}
-
-test regexp-1.215 {converted from line 215} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[.a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.216 {converted from line 216} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[=a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.217 {converted from line 217} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.218 {converted from line 218} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.219 {converted from line 219} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[b} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.220 {converted from line 220} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[b-} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.221 {converted from line 221} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[b-c} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.222 {converted from line 222} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[b-c]} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.223 {converted from line 223} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[b-b]} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.224 {converted from line 224} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[1-2]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-test regexp-1.225 {converted from line 225} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[c-b]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.226 {converted from line 226} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[a-b-c]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.227 {converted from line 227} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[--?]b} a?b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a?b}}
-
-test regexp-1.228 {converted from line 228} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[---]b} a-b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-b}}
-
-test regexp-1.229 {converted from line 229} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[]b]c} a\]c var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\]c}}
-
-test regexp-1.230 {converted from line 230} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\]]b} a\]b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\]b}}
-
-test regexp-1.231 {converted from line 231} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a[\]]b} a\]b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.232 {converted from line 232} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a[\]]b} {a\]b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\]b}}}
-
-test regexp-1.233 {converted from line 233} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)a[\]]b} {a\]b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\]b}}}
-
-test regexp-1.234 {converted from line 234} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.235 {converted from line 235} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.236 {converted from line 236} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.237 {converted from line 237} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\Z]b} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.238 {converted from line 238} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[b]c} {a[c} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a[c}}}
-
-
-
-# anchors and newlines
-test regexp-1.241 {converted from line 241} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^a a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-# skipping char mapping test from line 242
-print {... skip test from line 242: ^a &^ a}
-test regexp-1.243 {converted from line 243} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^ a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.244 {converted from line 244} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a$} aba var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-# skipping char mapping test from line 245
-print {... skip test from line 245: a$ &$ a}
-test regexp-1.246 {converted from line 246} {
- catch {unset var}
- list [catch {
- set match [regexp -- {$} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.247 {converted from line 247} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?n)^a a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.248 {converted from line 248} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?n)^a {b
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.249 {converted from line 249} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?w)^a {a
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-# skipping char mapping test from line 250
-print {... skip test from line 250: ^a &=n^ aNa a@2}
-test regexp-1.251 {converted from line 251} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)a$} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.252 {converted from line 252} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)a$} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.253 {converted from line 253} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)a$} {a
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.254 {converted from line 254} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^^ a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.255 {converted from line 255} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)^^ ^ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ^}}
-
-test regexp-1.256 {converted from line 256} {
- catch {unset var}
- list [catch {
- set match [regexp -- {$$} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.257 {converted from line 257} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)$$} {$} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {$}}}
-
-test regexp-1.258 {converted from line 258} {
- catch {unset var}
- list [catch {
- set match [regexp -- {^$} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.259 {converted from line 259} {
- catch {unset var}
- list [catch {
- set match [regexp -- {^$} a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.260 {converted from line 260} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?n)^$} {a
-
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.261 {converted from line 261} {
- catch {unset var}
- list [catch {
- set match [regexp -- {$^} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.262 {converted from line 262} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)$^} {$^} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {$^}}}
-
-test regexp-1.263 {converted from line 263} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\Aa} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-# skipping char mapping test from line 264
-print {... skip test from line 264: \\Aa ^P a a}
-# skipping char mapping test from line 265
-print {... skip test from line 265: \\Aa ^nP> bNa}
-test regexp-1.266 {converted from line 266} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Z} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-# skipping char mapping test from line 267
-print {... skip test from line 267: a\\Z $P a a}
-# skipping char mapping test from line 268
-print {... skip test from line 268: a\\Z $nP> aNb}
-test regexp-1.269 {converted from line 269} {
- catch {unset var}
- list [catch {
- set match [regexp -- ^* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.270 {converted from line 270} {
- catch {unset var}
- list [catch {
- set match [regexp -- {$*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.271 {converted from line 271} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\A*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.272 {converted from line 272} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\Z*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# boundary constraints
-test regexp-1.275 {converted from line 275} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:<:]]a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.276 {converted from line 276} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:<:]]a} -a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.277 {converted from line 277} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:<:]]a} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.278 {converted from line 278} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:>:]]} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.279 {converted from line 279} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:>:]]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.280 {converted from line 280} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[[:>:]]} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.281 {converted from line 281} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\<a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.282 {converted from line 282} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\<a} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.283 {converted from line 283} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\>} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.284 {converted from line 284} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\>} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.285 {converted from line 285} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\ya} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.286 {converted from line 286} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\ya} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.287 {converted from line 287} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\y} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.288 {converted from line 288} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\y} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.289 {converted from line 289} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Y} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.290 {converted from line 290} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Y} a- ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.291 {converted from line 291} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Y} a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.292 {converted from line 292} {
- catch {unset var}
- list [catch {
- set match [regexp -- {-\Y} -a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.293 {converted from line 293} {
- catch {unset var}
- list [catch {
- set match [regexp -- {-\Y} -% var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 -}}
-
-test regexp-1.294 {converted from line 294} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\Y-} a- ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.295 {converted from line 295} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:<:]]*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.296 {converted from line 296} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[[:>:]]*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.297 {converted from line 297} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\<*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.298 {converted from line 298} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)\>*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.299 {converted from line 299} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\y*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.300 {converted from line 300} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\Y*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# character classes
-test regexp-1.303 {converted from line 303} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\db} a0b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0b}}
-
-test regexp-1.304 {converted from line 304} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\db} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.305 {converted from line 305} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Db} a0b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.306 {converted from line 306} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Db} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.307 {converted from line 307} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\sb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.308 {converted from line 308} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\sb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.309 {converted from line 309} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\sb} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.310 {converted from line 310} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\sb} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.311 {converted from line 311} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Sb} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.312 {converted from line 312} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Sb} {a b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.313 {converted from line 313} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\wb} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.314 {converted from line 314} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\wb} a-b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.315 {converted from line 315} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Wb} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.316 {converted from line 316} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Wb} a-b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-b}}
-
-test regexp-1.317 {converted from line 317} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\y\w+z\y} adze-guz var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 guz}}
-
-test regexp-1.318 {converted from line 318} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\d]b} a1b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a1b}}
-
-test regexp-1.319 {converted from line 319} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\s]b} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.320 {converted from line 320} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a[\w]b} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-
-
-# escapes
-test regexp-1.323 {converted from line 323} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\\ EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.324 {converted from line 324} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\<b} a<b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a<b}}
-
-test regexp-1.325 {converted from line 325} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)a\<b} a<b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a<b}}
-
-test regexp-1.326 {converted from line 326} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\wb} awb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 awb}}
-
-test regexp-1.327 {converted from line 327} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)a\wb} awb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 awb}}
-
-test regexp-1.328 {converted from line 328} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\ab} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.329 {converted from line 329} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\bb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.330 {converted from line 330} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\chb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.331 {converted from line 331} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\cHb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.332 {converted from line 332} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\e} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.333 {converted from line 333} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\Eb} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.334 {converted from line 334} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\fb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.335 {converted from line 335} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\nb} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.336 {converted from line 336} {
- catch {unset var}
- list [catch {
- set match [regexp -- a\rb a\u000Db var(0)]
- list $match $var(0)
- } msg] $msg
-} [subst {0 {1 {a\u000Db}}}]
-
-test regexp-1.337 {converted from line 337} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\tb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.338 {converted from line 338} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\u0008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.339 {converted from line 339} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\u008x} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.340 {converted from line 340} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\u00088x} a8x var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a8x}}
-
-test regexp-1.341 {converted from line 341} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\U00000008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.342 {converted from line 342} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\U0000008x} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.343 {converted from line 343} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\vb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.344 {converted from line 344} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\x08x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.345 {converted from line 345} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\xx} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.346 {converted from line 346} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\x0008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.347 {converted from line 347} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\z} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.348 {converted from line 348} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\010b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# back references (ugh)
-test regexp-1.351 {converted from line 351} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b*)c\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbcbb bb}}
-
-test regexp-1.352 {converted from line 352} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b*)c\1} ac var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.353 {converted from line 353} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b*)c\1} abbcb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.354 {converted from line 354} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b*)\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.355 {converted from line 355} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b|bb)\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.356 {converted from line 356} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1} abb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.357 {converted from line 357} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1} abc ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.358 {converted from line 358} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1} abcabb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.359 {converted from line 359} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])*\1} abc ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.360 {converted from line 360} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1} abB ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.361 {converted from line 361} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?i)a([bc])\1} abB var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abB b}}
-
-test regexp-1.362 {converted from line 362} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1+} abbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbb b}}
-
-test regexp-1.363 {converted from line 363} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1{3,4}} abbbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbb b}}
-
-test regexp-1.364 {converted from line 364} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1{3,4}} abbb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.365 {converted from line 365} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1*} abbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbb b}}
-
-test regexp-1.366 {converted from line 366} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])\1*} ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab b}}
-
-test regexp-1.367 {converted from line 367} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a([bc])(\1*)} ab var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 ab b {}}}
-
-test regexp-1.368 {converted from line 368} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a((b)\1)} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.369 {converted from line 369} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b)c\2} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.370 {converted from line 370} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\(b*\)c\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbcbb bb}}
-
-
-
-# is it an octal escape or a back reference...?
-# initial zero is always octal
-test regexp-1.374 {converted from line 374} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\010b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.375 {converted from line 375} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\0070b} a0b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0b}}
-
-test regexp-1.376 {converted from line 376} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\07b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.377 {converted from line 377} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\07c} abbbbbbbbbbc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10)
- } msg] $msg
-} {0 {1 abbbbbbbbbbc b b b b b b b b b b}}
-
-# a single digit is always a backref
-test regexp-1.381 {converted from line 381} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\7b} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-# otherwise it's a backref only if within range (barf!)
-test regexp-1.383 {converted from line 383} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\10b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.384 {converted from line 384} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\101b} aAb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aAb}}
-
-test regexp-1.385 {converted from line 385} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\10c} abbbbbbbbbbbc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbc b b b b b b b b b b}}
-
-# but we're fussy about border cases -- guys who want octal should use the zero
-test regexp-1.389 {converted from line 389} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a((((((((((b\10))))))))))c} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-# BREs don't have octal, EREs don't have backrefs
-test regexp-1.391 {converted from line 391} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a\12b} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.392 {converted from line 392} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?b)a\12b} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.393 {converted from line 393} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)a\12b} a12b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a12b}}
-
-
-
-# expanded syntax
-test regexp-1.396 {converted from line 396} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b c} abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.397 {converted from line 397} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b #oops
-c d} abcd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abcd}}
-
-test regexp-1.398 {converted from line 398} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a\ b\ c} {a b c} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b c}}}
-
-test regexp-1.399 {converted from line 399} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b\#c} ab#c var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab#c}}
-
-test regexp-1.400 {converted from line 400} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b[c d]e} {ab e} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {ab e}}}
-
-test regexp-1.401 {converted from line 401} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b[c#d]e} ab#e var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab#e}}
-
-test regexp-1.402 {converted from line 402} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b[c#d]e} abde var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abde}}
-
-test regexp-1.403 {converted from line 403} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?x)ab\{\ d ab\{d var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab\{d}}
-
-test regexp-1.404 {converted from line 404} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)ab{ 1 , 2 }c} abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# misc. syntax
-test regexp-1.407 {converted from line 407} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?#comment)b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# unmatchable REs
-test regexp-1.410 {converted from line 410} {
- catch {unset var}
- list [catch {
- set match [regexp -- a^b IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-
-
-# case independence
-test regexp-1.413 {converted from line 413} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?i)ab Ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 Ab}}
-
-test regexp-1.414 {converted from line 414} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?i)a[bc]} aC var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aC}}
-
-test regexp-1.415 {converted from line 415} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?i)a[^bc]} aB ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.416 {converted from line 416} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?i)a[b-d]} aC var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aC}}
-
-test regexp-1.417 {converted from line 417} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?i)a[^b-d]} aC ]
- list $match
- } msg] $msg
-} {0 0}
-
-
-
-# inline options
-test regexp-1.420 {converted from line 420} {
- catch {unset var}
- list [catch {
- set match [regexp -- ***? BADPAT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid regular expression}}
-
-# skipping test with metasyntax from line 421
-
-test regexp-1.422 {converted from line 422} {
- catch {unset var}
- list [catch {
- set match [regexp -- ***=a*b a*b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a*b}}
-
-# skipping test with metasyntax from line 423
-
-# skipping test with metasyntax from line 424
-
-# skipping test with metasyntax from line 425
-
-test regexp-1.426 {converted from line 426} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?b)a+b a+b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a+b}}
-
-# skipping test with metasyntax from line 427
-
-# skipping test with metasyntax from line 428
-
-# skipping test with metasyntax from line 429
-
-# skipping test with metasyntax from line 430
-
-test regexp-1.431 {converted from line 431} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?e)\W+} WW var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 WW}}
-
-test regexp-1.432 {converted from line 432} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?i)a+ Aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 Aa}}
-
-test regexp-1.433 {converted from line 433} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?m)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.434 {converted from line 434} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?m)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.435 {converted from line 435} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?n)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.436 {converted from line 436} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?n)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.437 {converted from line 437} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?p)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.438 {converted from line 438} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?p)^b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.439 {converted from line 439} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?q)a+b a+b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a+b}}
-
-# skipping test with metasyntax from line 440
-
-# skipping test with metasyntax from line 441
-
-test regexp-1.442 {converted from line 442} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?w)a.b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.443 {converted from line 443} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?w)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.444 {converted from line 444} {
- catch {unset var}
- list [catch {
- set match [regexp -- {(?x)a b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.445 {converted from line 445} {
- catch {unset var}
- list [catch {
- set match [regexp -- (?z)ab BADOPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid embedded option}}
-
-
-
-# capturing
-test regexp-1.448 {converted from line 448} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.449 {converted from line 449} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:b)c xabc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.450 {converted from line 450} {
- catch {unset var}
- list [catch {
- set match [regexp -- a((b))c xabcy var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc b b}}
-
-test regexp-1.451 {converted from line 451} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:(b))c abcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.452 {converted from line 452} {
- catch {unset var}
- list [catch {
- set match [regexp -- a((?:b))c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.453 {converted from line 453} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:(?:b))c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.454 {converted from line 454} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b){0}c ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.455 {converted from line 455} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)c(d)e abcde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcde b d}}
-
-test regexp-1.456 {converted from line 456} {
- catch {unset var}
- list [catch {
- set match [regexp -- (b)c(d)e bcde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 bcde b d}}
-
-test regexp-1.457 {converted from line 457} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)(d)e abde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abde b d}}
-
-test regexp-1.458 {converted from line 458} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)c(d) abcd var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcd b d}}
-
-test regexp-1.459 {converted from line 459} {
- catch {unset var}
- list [catch {
- set match [regexp -- (ab)(cd) xabcdy var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcd ab cd}}
-
-test regexp-1.460 {converted from line 460} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.461 {converted from line 461} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c xacy var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.462 {converted from line 462} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c(d)?e xabcdey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcde b d}}
-
-test regexp-1.463 {converted from line 463} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c(d)?e xacdey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 acde {} d}}
-
-test regexp-1.464 {converted from line 464} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c(d)?e xabcey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abce b {}}}
-
-test regexp-1.465 {converted from line 465} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)?c(d)?e xacey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 ace {} {}}}
-
-test regexp-1.466 {converted from line 466} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)*c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.467 {converted from line 467} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)*c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.468 {converted from line 468} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)*c xacy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.469 {converted from line 469} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b*)c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc bbb}}
-
-test regexp-1.470 {converted from line 470} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b*)c xacy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.471 {converted from line 471} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)+c xacy ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.472 {converted from line 472} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)+c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.473 {converted from line 473} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b)+c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.474 {converted from line 474} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b+)c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc bbb}}
-
-test regexp-1.475 {converted from line 475} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b){2,3}c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.476 {converted from line 476} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b){2,3}c xabbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbc b}}
-
-test regexp-1.477 {converted from line 477} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(b){2,3}c xabcy ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.478 {converted from line 478} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\y(\w+)\y} {-- abc-} var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc abc}}
-
-test regexp-1.479 {converted from line 479} {
- catch {unset var}
- list [catch {
- set match [regexp -- a((b|c)d+)+ abacdbd var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 acdbd bd b}}
-
-test regexp-1.480 {converted from line 480} {
- catch {unset var}
- list [catch {
- set match [regexp -- (.*).* abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc abc}}
-
-test regexp-1.481 {converted from line 481} {
- catch {unset var}
- list [catch {
- set match [regexp -- (a*)* bc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 {} {}}}
-
-
-
-# collating elements (ugh)
-# skipping char mapping test from line 484
-print {... skip test from line 484: a&c&e &+L ace ace}
-# skipping char mapping test from line 485
-print {... skip test from line 485: a&c&h &+* IMPOSS}
-# skipping char mapping test from line 486
-print {... skip test from line 486: a&&.ch.&& &+L ach ach}
-# skipping char mapping test from line 487
-print {... skip test from line 487: a&&.ch.&& &+L ace}
-# skipping char mapping test from line 488
-print {... skip test from line 488: a&c&.ch.&& &+L ac ac}
-# skipping char mapping test from line 489
-print {... skip test from line 489: a&c&.ch.&& &+L ace ac}
-# skipping char mapping test from line 490
-print {... skip test from line 490: a&c&.ch.&& &+L ache ach}
-# skipping char mapping test from line 491
-print {... skip test from line 491: a&^c&e &+L ace}
-# skipping char mapping test from line 492
-print {... skip test from line 492: a&^c&e &+L abe abe}
-# skipping char mapping test from line 493
-print {... skip test from line 493: a&^c&e &+L ache ache}
-# skipping char mapping test from line 494
-print {... skip test from line 494: a&^&.ch.&& &+L ach}
-# skipping char mapping test from line 495
-print {... skip test from line 495: a&^&.ch.&& &+L ace ac}
-# skipping char mapping test from line 496
-print {... skip test from line 496: a&^&.ch.&& &+L ac ac}
-# skipping char mapping test from line 497
-print {... skip test from line 497: a&^&.ch.&& &+L abe ab}
-# skipping char mapping test from line 498
-print {... skip test from line 498: a&^c&.ch.&& &+L ach}
-# skipping char mapping test from line 499
-print {... skip test from line 499: a&^c&.ch.&& &+L ace}
-# skipping char mapping test from line 500
-print {... skip test from line 500: a&^c&.ch.&& &+L ac}
-# skipping char mapping test from line 501
-print {... skip test from line 501: a&^c&.ch.&& &+L abe ab}
-# skipping char mapping test from line 502
-print {... skip test from line 502: a&^b& &+L ac ac}
-# skipping char mapping test from line 503
-print {... skip test from line 503: a&^b& &+L ace ac}
-# skipping char mapping test from line 504
-print {... skip test from line 504: a&^b& &+L ach ach}
-# skipping char mapping test from line 505
-print {... skip test from line 505: a&^b& &+L abe}
-
-
-# lookahead
-test regexp-1.508 {converted from line 508} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?=b)b* ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.509 {converted from line 509} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?=b)b* a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.510 {converted from line 510} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?!b)b* ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.511 {converted from line 511} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?!b)b* a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-
-
-# non-greedy quantifiers
-test regexp-1.514 {converted from line 514} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab+? abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.515 {converted from line 515} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab+?c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.516 {converted from line 516} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab*? abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.517 {converted from line 517} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab*?c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.518 {converted from line 518} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab?? ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.519 {converted from line 519} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab??c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.520 {converted from line 520} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab{2,4}? abbbb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abb}}
-
-test regexp-1.521 {converted from line 521} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab{2,4}?c abbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbc}}
-
-
-
-# xxx mixed quantifiers (incl |)
-
-
-# attempts to trick the matcher into accepting a short match
-test regexp-1.526 {converted from line 526} {
- catch {unset var}
- list [catch {
- set match [regexp -- (week|wee)(night|knights) weeknights var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 weeknights wee knights}}
-
-test regexp-1.527 {converted from line 527} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(bc*).*\1} abccbccb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abccbccb b}}
-
-test regexp-1.528 {converted from line 528} {
- catch {unset var}
- list [catch {
- set match [regexp -- {a(b.[bc]*)+} abcbd var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abcbd bd}}
-
-
-
-# implementation misc.
-# duplicate arcs are suppressed
-test regexp-1.532 {converted from line 532} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(?:b|b)c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# boundary busters
-# color-descriptor allocation and arc allocation both change at 10
-test regexp-1.536 {converted from line 536} {
- catch {unset var}
- list [catch {
- set match [regexp -- abcdefghijkl abcdefghijkl var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abcdefghijkl}}
-
-# subexpression tracking at 10
-test regexp-1.538 {converted from line 538} {
- catch {unset var}
- list [catch {
- set match [regexp -- a(((((((((((((b)))))))))))))c abc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10) var(11) var(12) var(13)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10) $var(11) $var(12) $var(13)
- } msg] $msg
-} {0 {1 abc b b b b b b b b b b b b b}}
-
-# state-set handling changes slightly at unsigned size (might be 64...)
-# (also stresses arc allocation)
-test regexp-1.544 {converted from line 544} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab{1,100}c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.545 {converted from line 545} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab{1,100}c abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc}}
-
-test regexp-1.548 {converted from line 548} {
- catch {unset var}
- list [catch {
- set match [regexp -- ab{1,100}c abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc}}
-
-# force small cache and bust it, several ways
-test regexp-1.552 {converted from line 552} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\w+abcdefgh} xyzabcdefgh var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 xyzabcdefgh}}
-
-test regexp-1.553 {converted from line 553} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\w+abcdefgh} xyzabcdefgh var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 xyzabcdefgh}}
-
-test regexp-1.554 {converted from line 554} {
- catch {unset var}
- list [catch {
- set match [regexp -- {\w+(abcdefgh)?} xyz var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 xyz {}}}
-
-
-
-# make color/subcolor relationship go back and forth
-test regexp-1.557 {converted from line 557} {
- catch {unset var}
- list [catch {
- set match [regexp -- {[ab][ab][ab]} aba var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aba}}
-
-
-
-# misc.
-test regexp-1.560 {converted from line 560} {
- catch {unset var}
- list [catch {
- set match [regexp -- *** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.561 {converted from line 561} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?b* abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abb}}
-
-test regexp-1.562 {converted from line 562} {
- catch {unset var}
- list [catch {
- set match [regexp -- a?b* bb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 bb}}
-
diff --git a/tests/regexp3.test b/tests/regexp3.test
deleted file mode 100644
index 31f0b11..0000000
--- a/tests/regexp3.test
+++ /dev/null
@@ -1,3295 +0,0 @@
-# Commands covered: testregexp
-#
-# This Tcl-generated file contains tests for the testregexp tcl command.
-# Sourcing this file into Tcl runs the tests and generates output for
-# errors. No output means no errors were found. Setting VERBOSE to
-# -1 will run tests that are known to fail.
-#
-# Copyright (c) 1998 Sun Microsystems, Inc.
-#
-# See the file "license.terms" for information on usage and redistribution
-# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
-#
-# SCCS: @(#) regexp3.test 1.4 98/01/22 14:47:51
-
-proc print {arg} {puts $arg}
-
-if {[string compare test [info procs test]] == 1} {
- source defs ; set VERBOSE -1
-}
-
-if {$VERBOSE != -1} {
- proc print {arg} {}
-}
-
-#
-# The remainder of this file is Tcl tests that have been
-# converted from Henry Spencer's regexp test suite.
-#
-
-# This file is a sequence of regression tests, one per line. The first
-# field is the RE, the second flags, the third a string to match the RE
-# against, the fourth the expected match, and subsequent fields the
-# expected substring matches. No fourth field means match not expected;
-# no later fields mean no substrings expected. If the "*" flag is set
-# (see below), the third field is the name of the compile error expected,
-# less the leading "REG_". Any field may be written as "" to signify an
-# empty string. Fourth and subsequent fields may have a suffix "@11"
-# (any decimal integer) indicating the offset where the match is expected;
-# fifth and subsequent fields may be "@" indicating no match is expected
-# for that subexpression.
-
-
-# The flag characters are complex and a bit eclectic. Generally speaking,
-# lowercase letters are compile options, uppercase are expected re_info
-# bits, and nonalphabetics are match options, controls for how the test is
-# run, or debugging options. The one small surprise is that AREs are the
-# default, and you must explicitly request lesser flavors of RE. The flags
-# are as follows. Be warned that a number of them are specific to this
-# RE implementation. It is admitted that some are not very mnemonic.
-#
-# - no-op (placeholder)
-# = map characters in all other fields (see below)
-# > map characters in later fields (see below)
-# * compile error expected (third field is error type)
-# / compile only, do not attempt match
-# [2 expect 2 (any decimal integer) subexpressions
-# + provide fake ch collating element and xy equiv class
-# , turn on compile tracing (probably not useful in this file)
-# ; turn on automaton tracing (probably not useful in this file)
-# : turn on match tracing (probably not useful in this file)
-# . force small state-set cache in matcher (to test cache replace)
-# ^ beginning of string is not beginning of line
-# $ end of string is not end of line
-#
-# & test as both BRE and ARE
-# b BRE
-# e ERE
-# q literal string, no metacharacters at all
-#
-# i case-independent matching
-# s no subexpression capture
-# p newlines are half-magic, excluded from . and [^ only
-# w newlines are half-magic, significant to ^ and $ only
-# n newlines are fully magic, both effects
-# x expanded RE syntax
-#
-# A backslash-_a_lphanumeric seen
-# B ERE/ARE literal-_b_race heuristic used
-# E backslash (_e_scape) seen within []
-# H looka_h_ead constraint seen
-# L _l_ocale-specific construct seen
-# M unportable (_m_achine-specific) construct seen
-# N RE can match empty (_n_ull) string
-# P non-_P_OSIX construct seen
-# Q {} _q_uantifier seen
-# R back _r_eference seen
-# S POSIX-un_s_pecified syntax seen
-# U saw original-POSIX botch: unmatched right paren in ERE (_u_gh)
-
-
-# The character-mapping flag causes some transformations to be done
-# before processing. This is mostly to get funny characters into the
-# strings. Specifically:
-#
-# _ becomes space
-# A becomes \007 (some compilers lack \a)
-# B becomes \b
-# E becomes \033
-# F becomes \f
-# N becomes \n
-# R becomes \r
-# T becomes \t
-# V becomes \v
-
-
-# The two areas we can't easily test are memory-allocation failures (which
-# are hard to provoke on command) and embedded NULs (which the current test
-# program can't easily do; that should be fixed).
-
-
-
-
-
-
-# basic sanity checks
-test regexp-1.81 {converted from line 81} {
- catch {unset var}
- list [catch {
- set match [testregexp & abc abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.82 {converted from line 82} {
- catch {unset var}
- list [catch {
- set match [testregexp & abc def ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.83 {converted from line 83} {
- catch {unset var}
- list [catch {
- set match [testregexp & abc xyabxabce var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# invalid option combinations
-test regexp-1.86 {converted from line 86} {
- catch {unset var}
- list [catch {
- set match [testregexp qe a INVARG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid argument to regex routine}}
-
-test regexp-1.87 {converted from line 87} {
- catch {unset var}
- list [catch {
- set match [testregexp ba a INVARG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid argument to regex routine}}
-
-
-
-# basic syntax
-# skipping the empty-re test from line 90
-
-test regexp-1.91 {converted from line 91} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a| a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.92 {converted from line 92} {
- catch {unset var}
- list [catch {
- set match [testregexp - a|b a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.93 {converted from line 93} {
- catch {unset var}
- list [catch {
- set match [testregexp - a|b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.94 {converted from line 94} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a||b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.95 {converted from line 95} {
- catch {unset var}
- list [catch {
- set match [testregexp & ab ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# parentheses
-test regexp-1.98 {converted from line 98} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (a)e ae var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ae a}}
-
-test regexp-1.99 {converted from line 99} {
- catch {unset var}
- list [catch {
- set match [testregexp s (a)e ae ]
- list $match
- } msg] $msg
-} {0 1}
-
-test regexp-1.100 {converted from line 100} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\(a\)b} ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab a}}
-
-test regexp-1.101 {converted from line 101} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a((b)c) abc var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc bc b}}
-
-test regexp-1.102 {converted from line 102} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b)(c) abc var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc b c}}
-
-test regexp-1.103 {converted from line 103} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.104 {converted from line 104} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\(b} EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-# sigh, we blew it on the specs here... someday this will be fixed in POSIX,
-# but meanwhile, it's fixed in AREs
-
-test regexp-1.107 {converted from line 107} {
- catch {unset var}
- list [catch {
- set match [testregexp e a)b a)b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a)b}}
-
-test regexp-1.108 {converted from line 108} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a)b EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.109 {converted from line 109} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\)b} EPAREN ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched ()}}
-
-test regexp-1.110 {converted from line 110} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:b)c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.111 {converted from line 111} {
- catch {unset var}
- list [catch {
- set match [testregexp e a(?:b)c BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.112 {converted from line 112} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a()b ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab {}}}
-
-test regexp-1.113 {converted from line 113} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:)b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.114 {converted from line 114} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(|b)c ac var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.115 {converted from line 115} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b|)c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-
-
-# simple one-char matching (full mess of brackets done later)
-test regexp-1.118 {converted from line 118} {
- catch {unset var}
- list [catch {
- set match [testregexp & a.b axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.119 {converted from line 119} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.120 {converted from line 120} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[bc]d} abd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abd}}
-
-test regexp-1.121 {converted from line 121} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[bc]d} acd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 acd}}
-
-test regexp-1.122 {converted from line 122} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[bc]d} aed ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.123 {converted from line 123} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[^bc]d} abd ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.124 {converted from line 124} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[^bc]d} aed var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aed}}
-
-test regexp-1.125 {converted from line 125} {
- catch {unset var}
- list [catch {
- set match [testregexp &=p {a[^bc]d} {a
-d} ]
- list $match
- } msg] $msg
-} {0 0}
-
-
-
-# some context-dependent syntax (and some not)
-test regexp-1.128 {converted from line 128} {
- catch {unset var}
- list [catch {
- set match [testregexp {} * BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.129 {converted from line 129} {
- catch {unset var}
- list [catch {
- set match [testregexp b * * var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 *}}
-
-test regexp-1.130 {converted from line 130} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\(*\)} * var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 * *}}
-
-test regexp-1.131 {converted from line 131} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (*) BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.132 {converted from line 132} {
- catch {unset var}
- list [catch {
- set match [testregexp b ^* * var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 *}}
-
-test regexp-1.133 {converted from line 133} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ^* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.134 {converted from line 134} {
- catch {unset var}
- list [catch {
- set match [testregexp & ^b ^b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.135 {converted from line 135} {
- catch {unset var}
- list [catch {
- set match [testregexp b x^ x^ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 x^}}
-
-test regexp-1.136 {converted from line 136} {
- catch {unset var}
- list [catch {
- set match [testregexp {} x^ IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-test regexp-1.137 {converted from line 137} {
- catch {unset var}
- list [catch {
- set match [testregexp n= {
-^} {x
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {
-}}}
-
-test regexp-1.138 {converted from line 138} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\(^b\)} ^b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.139 {converted from line 139} {
- catch {unset var}
- list [catch {
- set match [testregexp - (^b) b var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 b b}}
-
-test regexp-1.140 {converted from line 140} {
- catch {unset var}
- list [catch {
- set match [testregexp & {x$} x var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 x}}
-
-test regexp-1.141 {converted from line 141} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\(x$\)} x var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 x x}}
-
-test regexp-1.142 {converted from line 142} {
- catch {unset var}
- list [catch {
- set match [testregexp - {(x$)} x var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 x x}}
-
-test regexp-1.143 {converted from line 143} {
- catch {unset var}
- list [catch {
- set match [testregexp b {x$y} {x$y} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {x$y}}}
-
-test regexp-1.144 {converted from line 144} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {x$y} IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-test regexp-1.145 {converted from line 145} {
- catch {unset var}
- list [catch {
- set match [testregexp n= {x$
-} {x
-} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {x
-}}}
-
-test regexp-1.146 {converted from line 146} {
- catch {unset var}
- list [catch {
- set match [testregexp {} + BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.147 {converted from line 147} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ? BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# simple quantifiers
-test regexp-1.150 {converted from line 150} {
- catch {unset var}
- list [catch {
- set match [testregexp & a* aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aa}}
-
-test regexp-1.151 {converted from line 151} {
- catch {unset var}
- list [catch {
- set match [testregexp & a* b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.152 {converted from line 152} {
- catch {unset var}
- list [catch {
- set match [testregexp - a+ aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aa}}
-
-test regexp-1.153 {converted from line 153} {
- catch {unset var}
- list [catch {
- set match [testregexp - a?b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.154 {converted from line 154} {
- catch {unset var}
- list [catch {
- set match [testregexp - a?b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.155 {converted from line 155} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.156 {converted from line 156} {
- catch {unset var}
- list [catch {
- set match [testregexp b ** *** var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ***}}
-
-test regexp-1.157 {converted from line 157} {
- catch {unset var}
- list [catch {
- set match [testregexp & a** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.158 {converted from line 158} {
- catch {unset var}
- list [catch {
- set match [testregexp & a**b BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.159 {converted from line 159} {
- catch {unset var}
- list [catch {
- set match [testregexp & *** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.160 {converted from line 160} {
- catch {unset var}
- list [catch {
- set match [testregexp - a++ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.161 {converted from line 161} {
- catch {unset var}
- list [catch {
- set match [testregexp - a?+ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.162 {converted from line 162} {
- catch {unset var}
- list [catch {
- set match [testregexp - a?* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.163 {converted from line 163} {
- catch {unset var}
- list [catch {
- set match [testregexp - a+* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.164 {converted from line 164} {
- catch {unset var}
- list [catch {
- set match [testregexp - a*+ BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# braces are messy
-test regexp-1.167 {converted from line 167} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,1} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.168 {converted from line 168} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,1} ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.169 {converted from line 169} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,0} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.170 {converted from line 170} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,2,3} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.171 {converted from line 171} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{257} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.172 {converted from line 172} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1000} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.173 {converted from line 173} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a\{1 EBRACE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched {}}}
-
-test regexp-1.174 {converted from line 174} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1n} BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.175 {converted from line 175} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a\{b a\{b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\{b}}
-
-test regexp-1.176 {converted from line 176} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a\{ a\{ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\{}}
-
-test regexp-1.177 {converted from line 177} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\{0,1\}b} cb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.178 {converted from line 178} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\{0,1} EBRACE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched {}}}
-
-test regexp-1.179 {converted from line 179} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a\{0,1\\ BADBR ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid repetition count(s)}}
-
-test regexp-1.180 {converted from line 180} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.181 {converted from line 181} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,0}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.182 {converted from line 182} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,1}b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.183 {converted from line 183} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,2}b b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.184 {converted from line 184} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,2}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.185 {converted from line 185} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{0,}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.186 {converted from line 186} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,1}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.187 {converted from line 187} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,3}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaab}}
-
-test regexp-1.188 {converted from line 188} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,3}b b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.189 {converted from line 189} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{1,}b aab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aab}}
-
-test regexp-1.190 {converted from line 190} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{2,3}b ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.191 {converted from line 191} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{2,3}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaab}}
-
-test regexp-1.192 {converted from line 192} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{2,}b ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.193 {converted from line 193} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a{2,}b aaaab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aaaab}}
-
-
-
-# brackets are too
-test regexp-1.196 {converted from line 196} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[bc]} ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.197 {converted from line 197} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[-]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-}}
-
-test regexp-1.198 {converted from line 198} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[.-.]]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-}}
-
-test regexp-1.199 {converted from line 199} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[.zero.]]} a0 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0}}
-
-test regexp-1.200 {converted from line 200} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[.zero.]-9]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-test regexp-1.201 {converted from line 201} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[0-[.9.]]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-# skipping char mapping test from line 202
-print {... skip test from line 202: a&&=x=&& &+L ax ax}
-# skipping char mapping test from line 203
-print {... skip test from line 203: a&&=x=&& &+L ay ay}
-# skipping char mapping test from line 204
-print {... skip test from line 204: a&&=x=&& &+L az}
-test regexp-1.205 {converted from line 205} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[0-[=x=]]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.206 {converted from line 206} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:digit:]]} a0 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0}}
-
-test regexp-1.207 {converted from line 207} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:woopsie:]]} ECTYPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character class}}
-
-test regexp-1.208 {converted from line 208} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:digit:]]} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.209 {converted from line 209} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[0-[:digit:]]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.210 {converted from line 210} {
- catch {unset var}
- list [catch {
- set match [testregexp & {[[:<:]]a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.211 {converted from line 211} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:>:]]} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.212 {converted from line 212} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[..]]b} ECOLLATE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid collating element}}
-
-test regexp-1.213 {converted from line 213} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[==]]b} ECOLLATE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid collating element}}
-
-test regexp-1.214 {converted from line 214} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[::]]b} ECTYPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character class}}
-
-test regexp-1.215 {converted from line 215} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[.a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.216 {converted from line 216} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[=a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.217 {converted from line 217} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:a} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.218 {converted from line 218} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.219 {converted from line 219} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[b} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.220 {converted from line 220} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[b-} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.221 {converted from line 221} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[b-c} EBRACK ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: unmatched []}}
-
-test regexp-1.222 {converted from line 222} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[b-c]} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.223 {converted from line 223} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[b-b]} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.224 {converted from line 224} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[1-2]} a2 var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a2}}
-
-test regexp-1.225 {converted from line 225} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[c-b]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.226 {converted from line 226} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[a-b-c]} ERANGE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid character range}}
-
-test regexp-1.227 {converted from line 227} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[--?]b} a?b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a?b}}
-
-test regexp-1.228 {converted from line 228} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[---]b} a-b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-b}}
-
-test regexp-1.229 {converted from line 229} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[]b]c} a\]c var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\]c}}
-
-test regexp-1.230 {converted from line 230} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a[\]]b} a\]b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a\]b}}
-
-test regexp-1.231 {converted from line 231} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a[\]]b} a\]b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.232 {converted from line 232} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a[\]]b} {a\]b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\]b}}}
-
-test regexp-1.233 {converted from line 233} {
- catch {unset var}
- list [catch {
- set match [testregexp e {a[\]]b} {a\]b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\]b}}}
-
-test regexp-1.234 {converted from line 234} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.235 {converted from line 235} {
- catch {unset var}
- list [catch {
- set match [testregexp e {a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.236 {converted from line 236} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a[\\]b} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.237 {converted from line 237} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a[\Z]b} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.238 {converted from line 238} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[b]c} {a[c} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a[c}}}
-
-
-
-# anchors and newlines
-test regexp-1.241 {converted from line 241} {
- catch {unset var}
- list [catch {
- set match [testregexp & ^a a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.242 {converted from line 242} {
- catch {unset var}
- list [catch {
- set match [testregexp &^ ^a a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.243 {converted from line 243} {
- catch {unset var}
- list [catch {
- set match [testregexp & ^ a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.244 {converted from line 244} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a$} aba var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.245 {converted from line 245} {
- catch {unset var}
- list [catch {
- set match [testregexp {&$} {a$} a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.246 {converted from line 246} {
- catch {unset var}
- list [catch {
- set match [testregexp & {$} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.247 {converted from line 247} {
- catch {unset var}
- list [catch {
- set match [testregexp &n ^a a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.248 {converted from line 248} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n ^a {b
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.249 {converted from line 249} {
- catch {unset var}
- list [catch {
- set match [testregexp &=w ^a {a
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.250 {converted from line 250} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n^ ^a {a
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.251 {converted from line 251} {
- catch {unset var}
- list [catch {
- set match [testregexp &n {a$} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.252 {converted from line 252} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n {a$} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.253 {converted from line 253} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n {a$} {a
-a} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.254 {converted from line 254} {
- catch {unset var}
- list [catch {
- set match [testregexp - ^^ a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.255 {converted from line 255} {
- catch {unset var}
- list [catch {
- set match [testregexp b ^^ ^ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ^}}
-
-test regexp-1.256 {converted from line 256} {
- catch {unset var}
- list [catch {
- set match [testregexp - {$$} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.257 {converted from line 257} {
- catch {unset var}
- list [catch {
- set match [testregexp b {$$} {$} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {$}}}
-
-test regexp-1.258 {converted from line 258} {
- catch {unset var}
- list [catch {
- set match [testregexp & {^$} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.259 {converted from line 259} {
- catch {unset var}
- list [catch {
- set match [testregexp & {^$} a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.260 {converted from line 260} {
- catch {unset var}
- list [catch {
- set match [testregexp &=n {^$} {a
-
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.261 {converted from line 261} {
- catch {unset var}
- list [catch {
- set match [testregexp - {$^} {} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {}}}
-
-test regexp-1.262 {converted from line 262} {
- catch {unset var}
- list [catch {
- set match [testregexp b {$^} {$^} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {$^}}}
-
-test regexp-1.263 {converted from line 263} {
- catch {unset var}
- list [catch {
- set match [testregexp - {\Aa} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.264 {converted from line 264} {
- catch {unset var}
- list [catch {
- set match [testregexp ^ {\Aa} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.265 {converted from line 265} {
- catch {unset var}
- list [catch {
- set match [testregexp ^n> {\Aa} {b
-a} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.266 {converted from line 266} {
- catch {unset var}
- list [catch {
- set match [testregexp - {a\Z} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.267 {converted from line 267} {
- catch {unset var}
- list [catch {
- set match [testregexp {$} {a\Z} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.268 {converted from line 268} {
- catch {unset var}
- list [catch {
- set match [testregexp {$n>} {a\Z} {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.269 {converted from line 269} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ^* BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.270 {converted from line 270} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {$*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.271 {converted from line 271} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\A*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.272 {converted from line 272} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\Z*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# boundary constraints
-test regexp-1.275 {converted from line 275} {
- catch {unset var}
- list [catch {
- set match [testregexp & {[[:<:]]a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.276 {converted from line 276} {
- catch {unset var}
- list [catch {
- set match [testregexp & {[[:<:]]a} -a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.277 {converted from line 277} {
- catch {unset var}
- list [catch {
- set match [testregexp & {[[:<:]]a} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.278 {converted from line 278} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:>:]]} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.279 {converted from line 279} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:>:]]} a- var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.280 {converted from line 280} {
- catch {unset var}
- list [catch {
- set match [testregexp & {a[[:>:]]} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.281 {converted from line 281} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\<a} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.282 {converted from line 282} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\<a} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.283 {converted from line 283} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\>} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.284 {converted from line 284} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\>} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.285 {converted from line 285} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\ya} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.286 {converted from line 286} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\ya} ba ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.287 {converted from line 287} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\y} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.288 {converted from line 288} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\y} ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.289 {converted from line 289} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Y} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.290 {converted from line 290} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Y} a- ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.291 {converted from line 291} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Y} a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.292 {converted from line 292} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {-\Y} -a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.293 {converted from line 293} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {-\Y} -% var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 -}}
-
-test regexp-1.294 {converted from line 294} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\Y-} a- ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.295 {converted from line 295} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {[[:<:]]*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.296 {converted from line 296} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {[[:>:]]*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.297 {converted from line 297} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\<*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.298 {converted from line 298} {
- catch {unset var}
- list [catch {
- set match [testregexp b {\>*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.299 {converted from line 299} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\y*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.300 {converted from line 300} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\Y*} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-
-
-# character classes
-test regexp-1.303 {converted from line 303} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\db} a0b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0b}}
-
-test regexp-1.304 {converted from line 304} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\db} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.305 {converted from line 305} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Db} a0b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.306 {converted from line 306} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Db} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.307 {converted from line 307} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\sb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.308 {converted from line 308} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\sb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.309 {converted from line 309} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\sb} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.310 {converted from line 310} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\sb} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.311 {converted from line 311} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Sb} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.312 {converted from line 312} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\Sb} {a b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.313 {converted from line 313} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\wb} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-test regexp-1.314 {converted from line 314} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\wb} a-b ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.315 {converted from line 315} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Wb} axb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.316 {converted from line 316} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Wb} a-b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a-b}}
-
-test regexp-1.317 {converted from line 317} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {\y\w+z\y} adze-guz var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 guz}}
-
-test regexp-1.318 {converted from line 318} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a[\d]b} a1b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a1b}}
-
-test regexp-1.319 {converted from line 319} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a[\s]b} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.320 {converted from line 320} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a[\w]b} axb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 axb}}
-
-
-
-# escapes
-test regexp-1.323 {converted from line 323} {
- catch {unset var}
- list [catch {
- set match [testregexp & a\\ EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.324 {converted from line 324} {
- catch {unset var}
- list [catch {
- set match [testregexp - {a\<b} a<b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a<b}}
-
-test regexp-1.325 {converted from line 325} {
- catch {unset var}
- list [catch {
- set match [testregexp e {a\<b} a<b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a<b}}
-
-test regexp-1.326 {converted from line 326} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\wb} awb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 awb}}
-
-test regexp-1.327 {converted from line 327} {
- catch {unset var}
- list [catch {
- set match [testregexp e {a\wb} awb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 awb}}
-
-test regexp-1.328 {converted from line 328} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\ab} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.329 {converted from line 329} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\bb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.330 {converted from line 330} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\chb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.331 {converted from line 331} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\cHb} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.332 {converted from line 332} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\e} a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.333 {converted from line 333} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\Eb} {a\b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a\b}}}
-
-test regexp-1.334 {converted from line 334} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\fb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.335 {converted from line 335} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\nb} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.336 {converted from line 336} {
- catch {unset var}
- list [catch {
- set match [testregexp = a\rb a\u000Db var(0)]
- list $match $var(0)
- } msg] $msg
-} [subst {0 {1 {a\u000Db}}}]
-
-test regexp-1.337 {converted from line 337} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\tb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.338 {converted from line 338} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\u0008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.339 {converted from line 339} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\u008x} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.340 {converted from line 340} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\u00088x} a8x var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a8x}}
-
-test regexp-1.341 {converted from line 341} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\U00000008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.342 {converted from line 342} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\U0000008x} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.343 {converted from line 343} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\vb} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.344 {converted from line 344} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\x08x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.345 {converted from line 345} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\xx} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.346 {converted from line 346} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\x0008x} ax var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ax}}
-
-test regexp-1.347 {converted from line 347} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\z} EESCAPE ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid escape sequence}}
-
-test regexp-1.348 {converted from line 348} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\010b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# back references (ugh)
-test regexp-1.351 {converted from line 351} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b*)c\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbcbb bb}}
-
-test regexp-1.352 {converted from line 352} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b*)c\1} ac var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.353 {converted from line 353} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b*)c\1} abbcb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.354 {converted from line 354} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b*)\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.355 {converted from line 355} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b|bb)\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.356 {converted from line 356} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1} abb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.357 {converted from line 357} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1} abc ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.358 {converted from line 358} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1} abcabb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abb b}}
-
-test regexp-1.359 {converted from line 359} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])*\1} abc ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.360 {converted from line 360} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1} abB ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.361 {converted from line 361} {
- catch {unset var}
- list [catch {
- set match [testregexp i {a([bc])\1} abB var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abB b}}
-
-test regexp-1.362 {converted from line 362} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1+} abbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbb b}}
-
-test regexp-1.363 {converted from line 363} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1{3,4}} abbbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbb b}}
-
-test regexp-1.364 {converted from line 364} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1{3,4}} abbb ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.365 {converted from line 365} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1*} abbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbb b}}
-
-test regexp-1.366 {converted from line 366} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])\1*} ab var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ab b}}
-
-test regexp-1.367 {converted from line 367} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a([bc])(\1*)} ab var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 ab b {}}}
-
-test regexp-1.368 {converted from line 368} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a((b)\1)} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.369 {converted from line 369} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b)c\2} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.370 {converted from line 370} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\(b*\)c\1} abbcbb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbcbb bb}}
-
-
-
-# is it an octal escape or a back reference...?
-# initial zero is always octal
-test regexp-1.374 {converted from line 374} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\010b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.375 {converted from line 375} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\0070b} a0b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a0b}}
-
-test regexp-1.376 {converted from line 376} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\07b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.377 {converted from line 377} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\07c} abbbbbbbbbbc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10)
- } msg] $msg
-} {0 {1 abbbbbbbbbbc b b b b b b b b b b}}
-
-# a single digit is always a backref
-test regexp-1.381 {converted from line 381} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\7b} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-# otherwise it's a backref only if within range (barf!)
-test regexp-1.383 {converted from line 383} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\10b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.384 {converted from line 384} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a\101b} aAb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aAb}}
-
-test regexp-1.385 {converted from line 385} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\10c} abbbbbbbbbbbc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbc b b b b b b b b b b}}
-
-# but we're fussy about border cases -- guys who want octal should use the zero
-test regexp-1.389 {converted from line 389} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a((((((((((b\10))))))))))c} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-# BREs don't have octal, EREs don't have backrefs
-test regexp-1.391 {converted from line 391} {
- catch {unset var}
- list [catch {
- set match [testregexp = {a\12b} {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.392 {converted from line 392} {
- catch {unset var}
- list [catch {
- set match [testregexp b {a\12b} ESUBREG ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid backreference number}}
-
-test regexp-1.393 {converted from line 393} {
- catch {unset var}
- list [catch {
- set match [testregexp e {a\12b} a12b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a12b}}
-
-
-
-# expanded syntax
-test regexp-1.396 {converted from line 396} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b c} abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.397 {converted from line 397} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b #oops
-c d} abcd var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abcd}}
-
-test regexp-1.398 {converted from line 398} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a\ b\ c} {a b c} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b c}}}
-
-test regexp-1.399 {converted from line 399} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b\#c} ab#c var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab#c}}
-
-test regexp-1.400 {converted from line 400} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b[c d]e} {ab e} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {ab e}}}
-
-test regexp-1.401 {converted from line 401} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b[c#d]e} ab#e var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab#e}}
-
-test regexp-1.402 {converted from line 402} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {a b[c#d]e} abde var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abde}}
-
-test regexp-1.403 {converted from line 403} {
- catch {unset var}
- list [catch {
- set match [testregexp =x ab\{\ d ab\{d var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab\{d}}
-
-test regexp-1.404 {converted from line 404} {
- catch {unset var}
- list [catch {
- set match [testregexp =x {ab{ 1 , 2 }c} abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# misc. syntax
-test regexp-1.407 {converted from line 407} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?#comment)b ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-
-
-# unmatchable REs
-test regexp-1.410 {converted from line 410} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a^b IMPOSS ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: can never match}}
-
-
-
-# case independence
-test regexp-1.413 {converted from line 413} {
- catch {unset var}
- list [catch {
- set match [testregexp &i ab Ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 Ab}}
-
-test regexp-1.414 {converted from line 414} {
- catch {unset var}
- list [catch {
- set match [testregexp &i {a[bc]} aC var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aC}}
-
-test regexp-1.415 {converted from line 415} {
- catch {unset var}
- list [catch {
- set match [testregexp &i {a[^bc]} aB ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.416 {converted from line 416} {
- catch {unset var}
- list [catch {
- set match [testregexp &i {a[b-d]} aC var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aC}}
-
-test regexp-1.417 {converted from line 417} {
- catch {unset var}
- list [catch {
- set match [testregexp &i {a[^b-d]} aC ]
- list $match
- } msg] $msg
-} {0 0}
-
-
-
-# inline options
-test regexp-1.420 {converted from line 420} {
- catch {unset var}
- list [catch {
- set match [testregexp & ***? BADPAT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid regular expression}}
-
-test regexp-1.421 {converted from line 421} {
- catch {unset var}
- list [catch {
- set match [testregexp q ***? ***? var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ***?}}
-
-test regexp-1.422 {converted from line 422} {
- catch {unset var}
- list [catch {
- set match [testregexp & ***=a*b a*b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a*b}}
-
-test regexp-1.423 {converted from line 423} {
- catch {unset var}
- list [catch {
- set match [testregexp q ***=a*b ***=a*b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ***=a*b}}
-
-test regexp-1.424 {converted from line 424} {
- catch {unset var}
- list [catch {
- set match [testregexp b {***:\w+} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.425 {converted from line 425} {
- catch {unset var}
- list [catch {
- set match [testregexp e {***:\w+} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.426 {converted from line 426} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (?b)a+b a+b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a+b}}
-
-test regexp-1.427 {converted from line 427} {
- catch {unset var}
- list [catch {
- set match [testregexp e {(?b)\w+} BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.428 {converted from line 428} {
- catch {unset var}
- list [catch {
- set match [testregexp b {(?b)\w+} (?b)w+ var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 (?b)w+}}
-
-test regexp-1.429 {converted from line 429} {
- catch {unset var}
- list [catch {
- set match [testregexp i (?c)a a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.430 {converted from line 430} {
- catch {unset var}
- list [catch {
- set match [testregexp i (?c)a A ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.431 {converted from line 431} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {(?e)\W+} WW var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 WW}}
-
-test regexp-1.432 {converted from line 432} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (?i)a+ Aa var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 Aa}}
-
-test regexp-1.433 {converted from line 433} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?m)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.434 {converted from line 434} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?m)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.435 {converted from line 435} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?n)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.436 {converted from line 436} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?n)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.437 {converted from line 437} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?p)a.b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.438 {converted from line 438} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?p)^b {a
-b} ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.439 {converted from line 439} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (?q)a+b a+b var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a+b}}
-
-test regexp-1.440 {converted from line 440} {
- catch {unset var}
- list [catch {
- set match [testregexp n= (?s)a.b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.441 {converted from line 441} {
- catch {unset var}
- list [catch {
- set match [testregexp x= {(?t)a b} {a b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a b}}}
-
-test regexp-1.442 {converted from line 442} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?w)a.b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 {a
-b}}}
-
-test regexp-1.443 {converted from line 443} {
- catch {unset var}
- list [catch {
- set match [testregexp = (?w)^b {a
-b} var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 b}}
-
-test regexp-1.444 {converted from line 444} {
- catch {unset var}
- list [catch {
- set match [testregexp = {(?x)a b} ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.445 {converted from line 445} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (?z)ab BADOPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: invalid embedded option}}
-
-
-
-# capturing
-test regexp-1.448 {converted from line 448} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.449 {converted from line 449} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:b)c xabc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.450 {converted from line 450} {
- catch {unset var}
- list [catch {
- set match [testregexp - a((b))c xabcy var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abc b b}}
-
-test regexp-1.451 {converted from line 451} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:(b))c abcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.452 {converted from line 452} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a((?:b))c abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.453 {converted from line 453} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:(?:b))c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.454 {converted from line 454} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b){0}c ac var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.455 {converted from line 455} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)c(d)e abcde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcde b d}}
-
-test regexp-1.456 {converted from line 456} {
- catch {unset var}
- list [catch {
- set match [testregexp - (b)c(d)e bcde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 bcde b d}}
-
-test regexp-1.457 {converted from line 457} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)(d)e abde var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abde b d}}
-
-test regexp-1.458 {converted from line 458} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)c(d) abcd var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcd b d}}
-
-test regexp-1.459 {converted from line 459} {
- catch {unset var}
- list [catch {
- set match [testregexp - (ab)(cd) xabcdy var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcd ab cd}}
-
-test regexp-1.460 {converted from line 460} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.461 {converted from line 461} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c xacy var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ac}}
-
-test regexp-1.462 {converted from line 462} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c(d)?e xabcdey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abcde b d}}
-
-test regexp-1.463 {converted from line 463} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c(d)?e xacdey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 acde {} d}}
-
-test regexp-1.464 {converted from line 464} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c(d)?e xabcey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 abce b {}}}
-
-test regexp-1.465 {converted from line 465} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)?c(d)?e xacey var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 ace {} {}}}
-
-test regexp-1.466 {converted from line 466} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)*c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.467 {converted from line 467} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)*c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.468 {converted from line 468} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)*c xacy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.469 {converted from line 469} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b*)c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc bbb}}
-
-test regexp-1.470 {converted from line 470} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b*)c xacy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 ac {}}}
-
-test regexp-1.471 {converted from line 471} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)+c xacy ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.472 {converted from line 472} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)+c xabcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc b}}
-
-test regexp-1.473 {converted from line 473} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b)+c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.474 {converted from line 474} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(b+)c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc bbb}}
-
-test regexp-1.475 {converted from line 475} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b){2,3}c xabbbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbbc b}}
-
-test regexp-1.476 {converted from line 476} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b){2,3}c xabbcy var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abbc b}}
-
-test regexp-1.477 {converted from line 477} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(b){2,3}c xabcy ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.478 {converted from line 478} {
- catch {unset var}
- list [catch {
- set match [testregexp = {\y(\w+)\y} {-- abc-} var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc abc}}
-
-test regexp-1.479 {converted from line 479} {
- catch {unset var}
- list [catch {
- set match [testregexp - a((b|c)d+)+ abacdbd var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 acdbd bd b}}
-
-test regexp-1.480 {converted from line 480} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (.*).* abc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abc abc}}
-
-test regexp-1.481 {converted from line 481} {
- catch {unset var}
- list [catch {
- set match [testregexp {} (a*)* bc var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 {} {}}}
-
-
-
-# collating elements (ugh)
-# skipping char mapping test from line 484
-print {... skip test from line 484: a&c&e &+L ace ace}
-# skipping char mapping test from line 485
-print {... skip test from line 485: a&c&h &+* IMPOSS}
-# skipping char mapping test from line 486
-print {... skip test from line 486: a&&.ch.&& &+L ach ach}
-# skipping char mapping test from line 487
-print {... skip test from line 487: a&&.ch.&& &+L ace}
-# skipping char mapping test from line 488
-print {... skip test from line 488: a&c&.ch.&& &+L ac ac}
-# skipping char mapping test from line 489
-print {... skip test from line 489: a&c&.ch.&& &+L ace ac}
-# skipping char mapping test from line 490
-print {... skip test from line 490: a&c&.ch.&& &+L ache ach}
-# skipping char mapping test from line 491
-print {... skip test from line 491: a&^c&e &+L ace}
-# skipping char mapping test from line 492
-print {... skip test from line 492: a&^c&e &+L abe abe}
-# skipping char mapping test from line 493
-print {... skip test from line 493: a&^c&e &+L ache ache}
-# skipping char mapping test from line 494
-print {... skip test from line 494: a&^&.ch.&& &+L ach}
-# skipping char mapping test from line 495
-print {... skip test from line 495: a&^&.ch.&& &+L ace ac}
-# skipping char mapping test from line 496
-print {... skip test from line 496: a&^&.ch.&& &+L ac ac}
-# skipping char mapping test from line 497
-print {... skip test from line 497: a&^&.ch.&& &+L abe ab}
-# skipping char mapping test from line 498
-print {... skip test from line 498: a&^c&.ch.&& &+L ach}
-# skipping char mapping test from line 499
-print {... skip test from line 499: a&^c&.ch.&& &+L ace}
-# skipping char mapping test from line 500
-print {... skip test from line 500: a&^c&.ch.&& &+L ac}
-# skipping char mapping test from line 501
-print {... skip test from line 501: a&^c&.ch.&& &+L abe ab}
-# skipping char mapping test from line 502
-print {... skip test from line 502: a&^b& &+L ac ac}
-# skipping char mapping test from line 503
-print {... skip test from line 503: a&^b& &+L ace ac}
-# skipping char mapping test from line 504
-print {... skip test from line 504: a&^b& &+L ach ach}
-# skipping char mapping test from line 505
-print {... skip test from line 505: a&^b& &+L abe}
-
-
-# lookahead
-test regexp-1.508 {converted from line 508} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?=b)b* ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.509 {converted from line 509} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?=b)b* a ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.510 {converted from line 510} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?!b)b* ab ]
- list $match
- } msg] $msg
-} {0 0}
-
-test regexp-1.511 {converted from line 511} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?!b)b* a var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-
-
-# non-greedy quantifiers
-test regexp-1.514 {converted from line 514} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab+? abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 ab}}
-
-test regexp-1.515 {converted from line 515} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab+?c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.516 {converted from line 516} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab*? abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.517 {converted from line 517} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab*?c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.518 {converted from line 518} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab?? ab var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 a}}
-
-test regexp-1.519 {converted from line 519} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab??c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-test regexp-1.520 {converted from line 520} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab{2,4}? abbbb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abb}}
-
-test regexp-1.521 {converted from line 521} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab{2,4}?c abbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbc}}
-
-
-
-# xxx mixed quantifiers (incl |)
-
-
-# attempts to trick the matcher into accepting a short match
-test regexp-1.526 {converted from line 526} {
- catch {unset var}
- list [catch {
- set match [testregexp - (week|wee)(night|knights) weeknights var(0) var(1) var(2)]
- list $match $var(0) $var(1) $var(2)
- } msg] $msg
-} {0 {1 weeknights wee knights}}
-
-test regexp-1.527 {converted from line 527} {
- catch {unset var}
- list [catch {
- set match [testregexp {} {a(bc*).*\1} abccbccb var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abccbccb b}}
-
-test regexp-1.528 {converted from line 528} {
- catch {unset var}
- list [catch {
- set match [testregexp - {a(b.[bc]*)+} abcbd var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 abcbd bd}}
-
-
-
-# implementation misc.
-# duplicate arcs are suppressed
-test regexp-1.532 {converted from line 532} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a(?:b|b)c abc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abc}}
-
-
-
-# boundary busters
-# color-descriptor allocation and arc allocation both change at 10
-test regexp-1.536 {converted from line 536} {
- catch {unset var}
- list [catch {
- set match [testregexp & abcdefghijkl abcdefghijkl var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abcdefghijkl}}
-
-# subexpression tracking at 10
-test regexp-1.538 {converted from line 538} {
- catch {unset var}
- list [catch {
- set match [testregexp - a(((((((((((((b)))))))))))))c abc var(0) var(1) var(2) var(3) var(4) var(5) var(6) var(7) var(8) var(9) var(10) var(11) var(12) var(13)]
- list $match $var(0) $var(1) $var(2) $var(3) $var(4) $var(5) $var(6) $var(7) $var(8) $var(9) $var(10) $var(11) $var(12) $var(13)
- } msg] $msg
-} {0 {1 abc b b b b b b b b b b b b b}}
-
-# state-set handling changes slightly at unsigned size (might be 64...)
-# (also stresses arc allocation)
-test regexp-1.544 {converted from line 544} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab{1,100}c abbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbc}}
-
-test regexp-1.545 {converted from line 545} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab{1,100}c abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc}}
-
-test regexp-1.548 {converted from line 548} {
- catch {unset var}
- list [catch {
- set match [testregexp {} ab{1,100}c abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc}}
-
-# force small cache and bust it, several ways
-test regexp-1.552 {converted from line 552} {
- catch {unset var}
- list [catch {
- set match [testregexp - {\w+abcdefgh} xyzabcdefgh var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 xyzabcdefgh}}
-
-test regexp-1.553 {converted from line 553} {
- catch {unset var}
- list [catch {
- set match [testregexp . {\w+abcdefgh} xyzabcdefgh var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 xyzabcdefgh}}
-
-test regexp-1.554 {converted from line 554} {
- catch {unset var}
- list [catch {
- set match [testregexp . {\w+(abcdefgh)?} xyz var(0) var(1)]
- list $match $var(0) $var(1)
- } msg] $msg
-} {0 {1 xyz {}}}
-
-
-
-# make color/subcolor relationship go back and forth
-test regexp-1.557 {converted from line 557} {
- catch {unset var}
- list [catch {
- set match [testregexp & {[ab][ab][ab]} aba var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 aba}}
-
-
-
-# misc.
-test regexp-1.560 {converted from line 560} {
- catch {unset var}
- list [catch {
- set match [testregexp & *** BADRPT ]
- list $match
- } msg] $msg
-} {1 {couldn't compile regular expression pattern: ?+* follows nothing}}
-
-test regexp-1.561 {converted from line 561} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a?b* abb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 abb}}
-
-test regexp-1.562 {converted from line 562} {
- catch {unset var}
- list [catch {
- set match [testregexp {} a?b* bb var(0)]
- list $match $var(0)
- } msg] $msg
-} {0 {1 bb}}
-
diff --git a/tests/regtests.test b/tests/regtests.test
new file mode 100644
index 0000000..02efa79
--- /dev/null
+++ b/tests/regtests.test
@@ -0,0 +1,867 @@
+# regexp tests
+
+if {[string compare test [info procs test]] == 1} then {source defs}
+
+# This file uses some custom procedures, defined below, for regexp regression
+# testing. The name of the procedure indicates the general nature of the
+# test: e for compile error expected, f for match failure expected, m
+# for a successful match, and i for a successful match with -indices (used
+# in checking things like nonparticipating subexpressions). There is also
+# a "doing" procedure which sets up title and major test number for each
+# block of tests, and an "xx" procedure which ignores its arguments and
+# arranges for the next invocation of "doing" to announce that some tests
+# were bypassed (which is better than just commenting them out).
+
+# The first 3 arguments are constant: a minor number (which often gets
+# a letter or two suffixed to it internally), some flags, and the RE itself.
+# For e, the remaining argument is the name of the compile error expected,
+# less the leading "REG_". For the rest, the next argument is the string
+# to try the match against. Remaining arguments are the substring expected
+# to be matched, and any substrings expected to be matched by subexpressions.
+# (For f, these arguments are optional, and if present are ignored except
+# that they indicate how many subexpressions should be presents in the RE.)
+# It is an error for the number of subexpression arguments to be wrong.
+# Cases involving nonparticipating subexpressions, checking where empty
+# substrings are located, etc. should be done using i.
+
+# The flag characters are complex and a bit eclectic. Generally speaking,
+# lowercase letters are compile options, uppercase are expected re_info
+# bits, and nonalphabetics are match options, controls for how the test is
+# run, or testing options. The one small surprise is that AREs are the
+# default, and you must explicitly request lesser flavors of RE. The flags
+# are as follows. It is admitted that some are not very mnemonic.
+# There are some others which are purely debugging tools and are not
+# useful in this file.
+#
+# - no-op (placeholder)
+# + provide fake xy equivalence class
+# % force small state-set cache in matcher (to test cache replace)
+# ^ beginning of string is not beginning of line
+# $ end of string is not end of line
+#
+# & test as both ARE and BRE
+# b BRE
+# e ERE
+# a turn advanced-features bit on (error unless ERE already)
+# q literal string, no metacharacters at all
+#
+# i case-independent matching
+# o ("opaque") no subexpression capture
+# p newlines are half-magic, excluded from . and [^ only
+# w newlines are half-magic, significant to ^ and $ only
+# n newlines are fully magic, both effects
+# x expanded RE syntax
+#
+# A backslash-_a_lphanumeric seen
+# B ERE/ARE literal-_b_race heuristic used
+# E backslash (_e_scape) seen within []
+# H looka_h_ead constraint seen
+# L _l_ocale-specific construct seen
+# M unportable (_m_achine-specific) construct seen
+# N RE can match empty (_n_ull) string
+# P non-_P_OSIX construct seen
+# Q {} _q_uantifier seen
+# R back _r_eference seen
+# S POSIX-un_s_pecified syntax seen
+# U saw original-POSIX botch: unmatched right paren in ERE (_u_gh)
+
+# The one area we can't easily test is memory-allocation failures (which
+# are hard to provoke on command). Embedded NULs also are not tested at
+# the moment, but this is a historical accident which should be fixed.
+
+
+
+# test procedures and related
+
+set ask "about"
+set xflags "unsupported0"
+set testbypassed 0
+
+# re_info abbreviation mapping table
+set infonames(A) "REG_UBSALNUM"
+set infonames(B) "REG_UBRACES"
+set infonames(E) "REG_UBBS"
+set infonames(H) "REG_ULOOKAHEAD"
+set infonames(L) "REG_ULOCALE"
+set infonames(M) "REG_UUNPORT"
+set infonames(N) "REG_UEMPTYMATCH"
+set infonames(P) "REG_UNONPOSIX"
+set infonames(Q) "REG_UBOUNDS"
+set infonames(R) "REG_UBACKREF"
+set infonames(S) "REG_UUNSPEC"
+set infonames(U) "REG_UPBOTCH"
+set infonameorder "RHQBAUEPSMLN" ;# must match bit order, lsb first
+
+# set major test number and description
+proc doing {major desc} {
+ global prefix description testbypassed
+
+ if {$testbypassed != 0} {
+ puts stdout "!!! bypassed $testbypassed tests in\
+ regexp-$major, `$description'"
+ }
+
+ set prefix regexp-$major
+ set description "regexp $desc"
+ set testbypassed 0
+}
+
+# build test number (internal)
+proc tno {testid} {
+ return [lindex $testid 0]
+}
+
+# build description, with possible modifiers (internal)
+proc desc {testid} {
+ global description
+
+ set d $description
+ if {[llength $testid] > 1} {
+ set d "([lreplace $testid 0 0]) $d"
+ }
+ return $d
+}
+
+# build trailing options and flags argument from a flags string (internal)
+proc flags {fl} {
+ global xflags
+
+ set args [list]
+ set flags ""
+ foreach f [split $fl ""] {
+ switch -exact -- $f {
+ "i" { lappend args "-nocase" }
+ "x" { lappend args "-expanded" }
+ "-" { }
+ default { append flags $f }
+ }
+ }
+ if {[string compare $flags ""] != 0} {
+ lappend args -$xflags $flags
+ }
+ return $args
+}
+
+# build info-flags list from a flags string (internal)
+proc infoflags {fl} {
+ global infonames infonameorder
+
+ set ret [list]
+ foreach f [split $infonameorder ""] {
+ if {[string first $f $fl] >= 0} {
+ lappend ret $infonames($f)
+ }
+ }
+ return $ret
+}
+
+# compilation error expected
+proc e {testid flags re err} {
+ global prefix ask errorCode
+
+ # if &, test as both ARE and BRE
+ set amp [string first "&" $flags]
+ if {$amp >= 0} {
+ set f [string range $flags 0 [expr $amp - 1]]
+ append f [string range $flags [expr $amp + 1] end]
+ e [linsert $testid end ARE] ${f} $re $err
+ e [linsert $testid end BRE] ${f}b $re $err
+ return
+ }
+
+ set cmd [concat [list regexp -$ask] [flags $flags] [list $re]]
+ set run "list \[catch \{$cmd\}\] \[lindex \$errorCode 1\]"
+ test $prefix.[tno $testid] [desc $testid] $run [list 1 REG_$err]
+}
+
+# match failure expected
+proc f {testid flags re target args} {
+ global prefix description ask
+
+ # if &, test as both ARE and BRE
+ set amp [string first "&" $flags]
+ if {$amp >= 0} {
+ set f [string range $flags 0 [expr $amp - 1]]
+ append f [string range $flags [expr $amp + 1] end]
+ eval [linsert $args 0 f [linsert $testid end ARE] ${f} $re \
+ $target]
+ eval [linsert $args 0 f [linsert $testid end BRE] ${f}b $re \
+ $target]
+ return
+ }
+
+ set f [flags $flags]
+ set infoflags [infoflags $flags]
+ set ccmd [concat [list regexp -$ask] $f [list $re]]
+ set nsub [expr [llength $args] - 1]
+ if {$nsub == -1} {
+ # didn't tell us number of subexps
+ set ccmd "lreplace \[$ccmd\] 0 0"
+ set info [list $infoflags]
+ } else {
+ set info [list $nsub $infoflags]
+ }
+ lappend testid "compile"
+ test $prefix.[tno $testid] [desc $testid] $ccmd $info
+
+ set testid [lreplace $testid end end "execute"]
+ set ecmd [concat [list regexp] $f [list $re $target]]
+ test $prefix.[tno $testid] [desc $testid] $ecmd 0
+}
+
+# match expected, internal routine that does the work
+# parameters like the "real" routines except they don't have "opts",
+# which is a possibly-empty list of switches for the regexp match attempt
+proc matchexpected {opts testid flags re target args} {
+ global prefix description ask
+
+ # if &, test as both BRE and ARE
+ set amp [string first "&" $flags]
+ if {$amp >= 0} {
+ set f [string range $flags 0 [expr $amp - 1]]
+ append f [string range $flags [expr $amp + 1] end]
+ eval [concat [list matchexpected $opts \
+ [linsert $testid end ARE] ${f} $re $target] $args]
+ eval [concat [list matchexpected $opts \
+ [linsert $testid end BRE] ${f}b $re $target] $args]
+ return
+ }
+
+ set f [flags $flags]
+ set infoflags [infoflags $flags]
+ set ccmd [concat [list regexp -$ask] $f [list $re]]
+ set ecmd [concat [list regexp] $opts $f [list $re $target]]
+
+ set nsub [expr [llength $args] - 1]
+ set names [list]
+ set refs ""
+ for {set i 0} {$i <= $nsub} {incr i} {
+ if {$i == 0} {
+ set name match
+ } else {
+ set name sub$i
+ }
+ lappend names $name
+ append refs " \$$name"
+ set $name ""
+ }
+ if {[string first "o" $flags] >= 0} { ;# REG_NOSUB
+ set nsub 0 ;# unsigned value cannot be -1
+ }
+ set ecmd [concat $ecmd $names]
+ set erun "list \[$ecmd\] $refs"
+ set result [concat [list 1] $args]
+
+ set info [list $nsub $infoflags]
+ lappend testid "compile"
+ test $prefix.[tno $testid] [desc $testid] $ccmd $info
+ set testid [lreplace $testid end end "execute"]
+ test $prefix.[tno $testid] [desc $testid] $erun $result
+}
+
+# match expected (no missing, empty, or ambiguous submatches)
+# m testno flags re target mat submat ...
+proc m {args} {
+ eval matchexpected [linsert $args 0 [list]]
+}
+
+# match expected (full fanciness)
+# i testno flags re target mat submat ...
+proc i {args} {
+ eval matchexpected [linsert $args 0 [list "-indices"]]
+}
+
+# test temporarily unimplemented
+proc xx {args} {
+ global testbypassed
+
+ incr testbypassed
+}
+
+
+
+# the tests themselves
+
+
+
+# support functions and preliminary misc.
+# This is sensitive to changes in message wording, but we really have to
+# test the code->message expansion at least once.
+test regexp-0.1 "regexp error reporting" {
+ list [catch {regexp (*) ign} msg] $msg
+} {1 {couldn't compile regular expression pattern: quantifier operand invalid}}
+
+
+
+doing 1 "basic sanity checks"
+m 1 & abc abc abc
+f 2 & abc def
+m 3 & abc xyabxabce abc
+
+
+
+doing 2 "invalid option combinations"
+e 1 qe a INVARG
+e 2 qa a INVARG
+e 3 qx a INVARG
+e 4 qn a INVARG
+e 5 ba a INVARG
+
+
+
+doing 3 "basic syntax"
+i 1 &NS "" a {0 -1}
+m 2 NS a| a a
+m 3 - a|b a a
+m 4 - a|b b b
+m 5 NS a||b b b
+m 6 & ab ab ab
+
+
+
+doing 4 "parentheses"
+m 1 - (a)e ae ae a
+m 2 o (a)e ae
+m 3 b {\(a\)b} ab ab a
+m 4 - a((b)c) abc abc bc b
+m 5 - a(b)(c) abc abc b c
+e 6 - a(b EPAREN
+e 7 b {a\(b} EPAREN
+# sigh, we blew it on the specs here... someday this will be fixed in POSIX,
+# but meanwhile, it's fixed in AREs
+m 8 eU a)b a)b a)b
+e 9 - a)b EPAREN
+e 10 b {a\)b} EPAREN
+m 11 P a(?:b)c abc abc
+e 12 e a(?:b)c BADRPT
+i 13 S a()b ab {0 1} {1 0}
+m 14 SP a(?:)b ab ab
+i 15 S a(|b)c ac {0 1} {1 0}
+m 16 S a(b|)c abc abc b
+
+
+
+doing 5 "simple one-char matching"
+# general case of brackets done later
+m 1 & a.b axb axb
+f 2 &n "a.b" "a\nb"
+m 3 & {a[bc]d} abd abd
+m 4 & {a[bc]d} acd acd
+f 5 & {a[bc]d} aed
+f 6 & {a[^bc]d} abd
+m 7 & {a[^bc]d} aed aed
+f 8 &p "a\[^bc]d" "a\nd"
+
+
+
+doing 6 "context-dependent syntax"
+# plus odds and ends
+e 1 - * BADRPT
+m 2 b * * *
+m 3 b {\(*\)} * * *
+e 4 - (*) BADRPT
+m 5 b ^* * *
+e 6 - ^* BADRPT
+f 7 & ^b ^b
+m 8 b x^ x^ x^
+e 9 - x^ IMPOSS
+m 10 n "\n^" "x\nb" "\n"
+f 11 bS {\(^b\)} ^b
+m 12 - (^b) b b b
+m 13 & {x$} x x
+m 14 bS {\(x$\)} x x x
+m 15 - {(x$)} x x x
+m 16 b {x$y} "x\$y" "x\$y"
+e 17 - {x$y} IMPOSS
+m 18 n "x\$\n" "x\n" "x\n"
+e 19 - + BADRPT
+e 20 - ? BADRPT
+
+
+
+doing 7 "simple quantifiers"
+m 1 &N a* aa aa
+i 2 &N a* b {0 -1}
+m 3 - a+ aa aa
+m 4 - a?b ab ab
+m 5 - a?b b b
+e 6 - ** BADRPT
+m 7 bN ** *** ***
+e 8 & a** BADRPT
+e 9 & a**b BADRPT
+e 10 & *** BADRPT
+e 11 * a++ BADRPT
+e 12 * a?+ BADRPT
+e 13 * a?* BADRPT
+e 14 * a+* BADRPT
+e 15 * a*+ BADRPT
+
+
+
+doing 8 "braces"
+m 1 NQ "a{0,1}" "" ""
+m 2 NQ "a{0,1}" ac a
+e 3 - "a{1,0}" BADBR
+e 4 - "a{1,2,3}" BADBR
+e 5 - "a{257}" BADBR
+e 6 - "a{1000}" BADBR
+e 7 - "a{1" EBRACE
+e 8 - "a{1n}" BADBR
+m 9 BS "a{b" "a\{b" "a\{b"
+m 10 BS "a{" "a\{" "a\{"
+m 11 bQ {a\{0,1\}b} cb b
+e 12 b {a\{0,1} EBRACE
+e 13 - "a{0,1\\" BADBR
+m 14 Q "a{0}b" ab b
+m 15 Q "a{0,0}b" ab b
+m 16 Q "a{0,1}b" ab ab
+m 17 Q "a{0,2}b" b b
+m 18 Q "a{0,2}b" aab aab
+m 19 Q "a{0,}b" aab aab
+m 20 Q "a{1,1}b" aab ab
+m 21 Q "a{1,3}b" aaaab aaab
+f 22 Q "a{1,3}b" b
+m 23 Q "a{1,}b" aab aab
+f 24 Q "a{2,3}b" ab
+m 25 Q "a{2,3}b" aaaab aaab
+f 26 Q "a{2,}b" ab
+m 27 Q "a{2,}b" aaaab aaaab
+
+
+
+doing 9 "brackets"
+m 1 & {a[bc]} ac ac
+m 2 & {a[-]} a- a-
+m 3 & {a[[.-.]]} a- a-
+m 4 &L {a[[.zero.]]} a0 a0
+m 5 &LM {a[[.zero.]-9]} a2 a2
+m 6 &M {a[0-[.9.]]} a2 a2
+m 7 &+L {a[[=x=]]} ax ax
+m 8 &+L {a[[=x=]]} ay ay
+f 9 &+L {a[[=x=]]} az
+e 10 & {a[0-[=x=]]} ERANGE
+m 11 &L {a[[:digit:]]} a0 a0
+e 12 & {a[[:woopsie:]]} ECTYPE
+f 13 &L {a[[:digit:]]} ab
+e 14 & {a[0-[:digit:]]} ERANGE
+m 15 &LP {[[:<:]]a} a a
+m 16 &LP {a[[:>:]]} a a
+e 17 & {a[[..]]b} ECOLLATE
+e 18 & {a[[==]]b} ECOLLATE
+e 19 & {a[[::]]b} ECTYPE
+e 20 & {a[[.a} EBRACK
+e 21 & {a[[=a} EBRACK
+e 22 & {a[[:a} EBRACK
+e 23 & {a[} EBRACK
+e 24 & {a[b} EBRACK
+e 25 & {a[b-} EBRACK
+e 26 & {a[b-c} EBRACK
+m 27 &M {a[b-c]} ab ab
+m 28 & {a[b-b]} ab ab
+m 29 &M {a[1-2]} a2 a2
+e 30 & {a[c-b]} ERANGE
+e 31 & {a[a-b-c]} ERANGE
+m 32 &M {a[--?]b} a?b a?b
+m 33 & {a[---]b} a-b a-b
+m 34 & {a[]b]c} a]c a]c
+m 35 EP {a[\]]b} a]b a]b
+f 36 bE {a[\]]b} a]b
+m 37 bE {a[\]]b} "a\\]b" "a\\]b"
+m 38 eE {a[\]]b} "a\\]b" "a\\]b"
+m 39 EP {a[\\]b} "a\\b" "a\\b"
+m 40 eE {a[\\]b} "a\\b" "a\\b"
+m 41 bE {a[\\]b} "a\\b" "a\\b"
+e 42 - {a[\Z]b} EESCAPE
+m 43 & {a[[b]c} "a\[c" "a\[c"
+
+
+
+doing 10 "anchors and newlines"
+m 1 & ^a a a
+f 2 &^ ^a a
+i 3 &N ^ a {0 -1}
+i 4 & {a$} aba {2 2}
+f 5 {&$} {a$} a
+i 6 &N {$} ab {2 1}
+m 7 &n ^a a a
+m 8 &n "^a" "b\na" "a"
+i 9 &w "^a" "a\na" {0 0}
+i 10 &n^ "^a" "a\na" {2 2}
+m 11 &n {a$} a a
+m 12 &n "a\$" "a\nb" "a"
+i 13 &n "a\$" "a\na" {0 0}
+i 14 N ^^ a {0 -1}
+m 15 b ^^ ^ ^
+i 16 N {$$} a {1 0}
+m 17 b {$$} "\$" "\$"
+m 18 &N {^$} "" ""
+f 19 &N {^$} a
+i 20 &nN "^\$" "a\n\nb" {2 1}
+m 21 N {$^} "" ""
+m 22 b {$^} "\$^" "\$^"
+m 23 P {\Aa} a a
+m 24 ^P {\Aa} a a
+f 25 ^nP {\Aa} "b\na"
+m 26 P {a\Z} a a
+m 27 {$P} {a\Z} a a
+f 28 {$nP} {a\Z} "a\nb"
+e 29 - ^* BADRPT
+e 30 - {$*} BADRPT
+e 31 - {\A*} BADRPT
+e 32 - {\Z*} BADRPT
+
+
+
+doing 11 "boundary constraints"
+m 1 &LP {[[:<:]]a} a a
+m 2 &LP {[[:<:]]a} -a a
+f 3 &LP {[[:<:]]a} ba
+m 4 &LP {a[[:>:]]} a a
+m 5 &LP {a[[:>:]]} a- a
+f 6 &LP {a[[:>:]]} ab
+m 7 bLP {\<a} a a
+f 8 bLP {\<a} ba
+m 9 bLP {a\>} a a
+f 10 bLP {a\>} ab
+m 11 LP {\ya} a a
+f 12 LP {\ya} ba
+m 13 LP {a\y} a a
+f 14 LP {a\y} ab
+m 15 LP {a\Y} ab a
+f 16 LP {a\Y} a-
+f 17 LP {a\Y} a
+f 18 LP {-\Y} -a
+m 19 LP {-\Y} -% -
+f 20 LP {\Y-} a-
+e 21 - {[[:<:]]*} BADRPT
+e 22 - {[[:>:]]*} BADRPT
+e 23 b {\<*} BADRPT
+e 24 b {\>*} BADRPT
+e 25 - {\y*} BADRPT
+e 26 - {\Y*} BADRPT
+
+
+
+doing 12 "character classes"
+m 1 LP {a\db} a0b a0b
+f 2 LP {a\db} axb
+f 3 LP {a\Db} a0b
+m 4 LP {a\Db} axb axb
+m 5 LP "a\\sb" "a b" "a b"
+m 6 LP "a\\sb" "a\tb" "a\tb"
+m 7 LP "a\\sb" "a\nb" "a\nb"
+f 8 LP {a\sb} axb
+m 9 LP {a\Sb} axb axb
+f 10 LP "a\\Sb" "a b"
+m 11 LP {a\wb} axb axb
+f 12 LP {a\wb} a-b
+f 13 LP {a\Wb} axb
+m 14 LP {a\Wb} a-b a-b
+m 15 LP {\y\w+z\y} adze-guz guz
+m 16 LPE {a[\d]b} a1b a1b
+m 17 LPE "a\[\\s]b" "a b" "a b"
+m 18 LPE {a[\w]b} axb axb
+
+
+
+doing 13 "escapes"
+e 1 & "a\\" EESCAPE
+m 2 - {a\<b} a<b a<b
+m 3 e {a\<b} a<b a<b
+m 4 bAS {a\wb} awb awb
+m 5 eAS {a\wb} awb awb
+m 6 PL "a\\ab" "a\007b" "a\007b"
+m 7 P "a\\bb" "a\bb" "a\bb"
+m 8 P {a\Bb} "a\\b" "a\\b"
+m 9 MP "a\\chb" "a\bb" "a\bb"
+m 10 MP "a\\cHb" "a\bb" "a\bb"
+m 11 LMP "a\\e" "a\033" "a\033"
+m 12 P "a\\fb" "a\fb" "a\fb"
+m 13 P "a\\nb" "a\nb" "a\nb"
+m 14 P "a\\rb" "a\rb" "a\rb"
+m 15 P "a\\tb" "a\tb" "a\tb"
+m 16 P "a\\u0008x" "a\bx" "a\bx"
+e 17 - {a\u008x} EESCAPE
+m 18 P "a\\u00088x" "a\b8x" "a\b8x"
+m 19 P "a\\U00000008x" "a\bx" "a\bx"
+e 20 - {a\U0000008x} EESCAPE
+m 21 P "a\\vb" "a\vb" "a\vb"
+m 22 MP "a\\x08x" "a\bx" "a\bx"
+e 23 - {a\xx} EESCAPE
+m 24 MP "a\\x0008x" "a\bx" "a\bx"
+e 25 - {a\z} EESCAPE
+m 26 MP "a\\010b" "a\bb" "a\bb"
+
+
+
+doing 14 "back references"
+# ugh
+m 1 {R[1P} {a(b*)c\1} abbcbb abbcbb bb
+m 2 {R[1P} {a(b*)c\1} ac ac ""
+f 3 {R[1P} {a(b*)c\1} abbcb
+m 4 {R[1P} {a(b*)\1} abbcbb abb b
+m 5 {R[1P} {a(b|bb)\1} abbcbb abb b
+m 6 {R[1P} {a([bc])\1} abb abb b
+f 7 {R[1P} {a([bc])\1} abc
+m 8 {R[1P} {a([bc])\1} abcabb abb b
+f 9 {R[1P} {a([bc])*\1} abc
+f 10 {R[1P} {a([bc])\1} abB
+m 11 {iR[1P} {a([bc])\1} abB abB b
+m 12 {R[1P} {a([bc])\1+} abbb abbb b
+m 13 {QR[1P} "a(\[bc])\\1{3,4}" abbbb abbbb b
+f 14 {QR[1P} "a(\[bc])\\1{3,4}" abbb
+m 15 {R[1P} {a([bc])\1*} abbb abbb b
+m 16 {R[1P} {a([bc])\1*} ab ab b
+m 17 {R[2P} {a([bc])(\1*)} ab ab b ""
+e 18 - {a((b)\1)} ESUBREG
+e 19 - {a(b)c\2} ESUBREG
+m 20 {bR[1} {a\(b*\)c\1} abbcbb abbcbb bb
+
+
+
+doing 15 "octal escapes vs back references"
+# initial zero is always octal
+m 1 MP "a\\010b" "a\bb" "a\bb"
+m 2 MP "a\\0070b" "a\0070b" "a\0070b"
+m 3 MP "a\\07b" "a\007b" "a\007b"
+m 4 MP "a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\\07c" "abbbbbbbbbb\007c" \
+ "abbbbbbbbbb\007c" "b" "b" "b" "b" "b" "b" \
+ "b" "b" "b" "b"
+# a single digit is always a backref
+e 5 - {a\7b} ESUBREG
+# otherwise it's a backref only if within range (barf!)
+m 6 MP "a\\10b" "a\bb" "a\bb"
+m 7 MP {a\101b} aAb aAb
+m 8 RP {a(b)(b)(b)(b)(b)(b)(b)(b)(b)(b)\10c} abbbbbbbbbbbc \
+ abbbbbbbbbbbc b b b b b b b \
+ b b b
+# but we're fussy about border cases -- guys who want octal should use the zero
+e 9 - {a((((((((((b\10))))))))))c} ESUBREG
+# BREs don't have octal, EREs don't have backrefs
+m 10 MP "a\\12b" "a\nb" "a\nb"
+e 11 b {a\12b} ESUBREG
+m 12 eAS {a\12b} a12b a12b
+
+
+
+doing 16 "expanded syntax"
+m 1 xP "a b c" "abc" "abc"
+m 2 xP "a b #oops\nc\td" "abcd" "abcd"
+m 3 x "a\\ b\\\tc" "a b\tc" "a b\tc"
+m 4 xP "a b\\#c" "ab#c" "ab#c"
+m 5 xP "a b\[c d]e" "ab e" "ab e"
+m 6 xP "a b\[c#d]e" "ab#e" "ab#e"
+m 7 xP "a b\[c#d]e" "abde" "abde"
+m 8 xSPB "ab{ d" "ab\{d" "ab\{d"
+m 9 xPQ "ab{ 1 , 2 }c" "abc" "abc"
+
+
+
+doing 17 "misc syntax"
+m 1 P a(?#comment)b ab ab
+
+
+
+doing 18 "unmatchable REs"
+e 1 - a^b IMPOSS
+
+
+
+doing 19 "case independence"
+m 1 &i ab Ab Ab
+m 2 &i {a[bc]} aC aC
+f 3 &i {a[^bc]} aB
+m 4 &iM {a[b-d]} aC aC
+f 5 &iM {a[^b-d]} aC
+
+
+
+doing 20 "directors and embedded options"
+e 1 & ***? BADPAT
+m 2 q ***? ***? ***?
+m 3 &P ***=a*b a*b a*b
+m 4 q ***=a*b ***=a*b ***=a*b
+m 5 bLP {***:\w+} ab ab
+m 6 eLP {***:\w+} ab ab
+e 7 & ***:***=a*b BADRPT
+m 8 &P ***:(?b)a+b a+b a+b
+m 9 P (?b)a+b a+b a+b
+e 10 e {(?b)\w+} BADRPT
+m 11 bAS {(?b)\w+} (?b)w+ (?b)w+
+m 12 iP (?c)a a a
+f 13 iP (?c)a A
+m 14 APS {(?e)\W+} WW WW
+m 15 P (?i)a+ Aa Aa
+f 16 P "(?m)a.b" "a\nb"
+m 17 P "(?m)^b" "a\nb" "b"
+f 18 P "(?n)a.b" "a\nb"
+m 19 P "(?n)^b" "a\nb" "b"
+f 20 P "(?p)a.b" "a\nb"
+f 21 P "(?p)^b" "a\nb"
+m 22 P (?q)a+b a+b a+b
+m 23 nP "(?s)a.b" "a\nb" "a\nb"
+m 24 xP "(?t)a b" "a b" "a b"
+m 25 P "(?w)a.b" "a\nb" "a\nb"
+m 26 P "(?w)^b" "a\nb" "b"
+m 27 P "(?x)a b" "ab" "ab"
+e 28 - (?z)ab BADOPT
+m 29 P (?ici)a+ Aa Aa
+e 30 P (?i)(?q)a+ BADRPT
+m 31 P (?q)(?i)a+ (?i)a+ (?i)a+
+m 32 P (?qe)a+ a a
+m 33 xP "(?q)a b" "a b" "a b"
+m 34 P "(?qx)a b" "a b" "a b"
+m 35 P (?qi)ab Ab Ab
+
+
+
+doing 21 "capturing"
+m 1 - a(b)c abc abc b
+m 2 P a(?:b)c xabc abc
+m 3 - a((b))c xabcy abc b b
+m 4 P a(?:(b))c abcy abc b
+m 5 P a((?:b))c abc abc b
+m 6 P a(?:(?:b))c abc abc
+i 7 Q "a(b){0}c" ac {0 1} {-1 -1}
+m 8 - a(b)c(d)e abcde abcde b d
+m 9 - (b)c(d)e bcde bcde b d
+m 10 - a(b)(d)e abde abde b d
+m 11 - a(b)c(d) abcd abcd b d
+m 12 - (ab)(cd) xabcdy abcd ab cd
+m 13 - a(b)?c xabcy abc b
+i 14 - a(b)?c xacy {1 2} {-1 -1}
+m 15 - a(b)?c(d)?e xabcdey abcde b d
+i 16 - a(b)?c(d)?e xacdey {1 4} {-1 -1} {3 3}
+i 17 - a(b)?c(d)?e xabcey {1 4} {2 2} {-1 -1}
+i 18 - a(b)?c(d)?e xacey {1 3} {-1 -1} {-1 -1}
+m 19 - a(b)*c xabcy abc b
+i 20 - a(b)*c xabbbcy {1 5} {4 4}
+i 21 - a(b)*c xacy {1 2} {-1 -1}
+m 22 - a(b*)c xabbbcy abbbc bbb
+m 23 - a(b*)c xacy ac ""
+f 24 - a(b)+c xacy
+m 25 - a(b)+c xabcy abc b
+i 26 - a(b)+c xabbbcy {1 5} {4 4}
+m 27 - a(b+)c xabbbcy abbbc bbb
+i 28 Q "a(b){2,3}c" xabbbcy {1 5} {4 4}
+i 29 Q "a(b){2,3}c" xabbcy {1 4} {3 3}
+f 30 Q "a(b){2,3}c" xabcy
+m 31 LP "\\y(\\w+)\\y" "-- abc-" "abc" "abc"
+m 32 - a((b|c)d+)+ abacdbd acdbd bd b
+m 33 N (.*).* abc abc abc
+m 34 N (a*)* bc "" ""
+
+
+
+doing 22 "multicharacter collating elements"
+# again ugh
+# currently disabled because the fake MCCE we use for testing is unavailable
+xx m 1 &+L {a[c]e} ace ace
+xx e 2 &+ {a[c]h} IMPOSS
+xx m 3 &+L {a[[.ch.]]} ach ach
+xx f 4 &+L {a[[.ch.]]} ace
+xx m 5 &+L {a[c[.ch.]]} ac ac
+xx m 6 &+L {a[c[.ch.]]} ace ac
+xx m 7 &+L {a[c[.ch.]]} ache ach
+xx f 8 &+L {a[^c]e} ace
+xx m 9 &+L {a[^c]e} abe abe
+xx m 10 &+L {a[^c]e} ache ache
+xx f 11 &+L {a[^[.ch.]]} ach
+xx m 12 &+L {a[^[.ch.]]} ace ac
+xx m 13 &+L {a[^[.ch.]]} ac ac
+xx m 14 &+L {a[^[.ch.]]} abe ab
+xx f 15 &+L {a[^c[.ch.]]} ach
+xx f 16 &+L {a[^c[.ch.]]} ace
+xx f 17 &+L {a[^c[.ch.]]} ac
+xx m 18 &+L {a[^c[.ch.]]} abe ab
+xx m 19 &+L {a[^b]} ac ac
+xx m 20 &+L {a[^b]} ace ac
+xx m 21 &+L {a[^b]} ach ach
+xx f 22 &+L {a[^b]} abe
+
+
+
+doing 23 "lookahead constraints"
+m 1 HP a(?=b)b* ab ab
+f 2 HP a(?=b)b* a
+m 3 HP a(?=b)b*(?=c)c* abc abc
+f 4 HP a(?=b)b*(?=c)c* ab
+f 5 HP a(?!b)b* ab
+m 6 HP a(?!b)b* a a
+m 7 HP (?=b)b b b
+f 8 HP (?=b)b a
+
+
+
+doing 24 "non-greedy quantifiers"
+m 1 P ab+? abb ab
+m 2 P ab+?c abbc abbc
+m 3 P ab*? abb a
+m 4 P ab*?c abbc abbc
+m 5 P ab?? ab a
+m 6 P ab??c abc abc
+m 7 PQ "ab{2,4}?" abbbb abb
+m 8 PQ "ab{2,4}?c" abbbbc abbbbc
+
+
+
+doing 25 "mixed quantifiers"
+xx to be done, actually
+xx should include |
+
+
+
+doing 26 "tricky cases"
+# attempts to trick the matcher into accepting a short match
+m 1 - (week|wee)(night|knights) weeknights weeknights \
+ wee knights
+m 2 RP {a(bc*).*\1} abccbccb abccbccb b
+m 3 - {a(b.[bc]*)+} abcbd abcbd bd
+
+
+
+doing 27 "implementation misc."
+# duplicate arcs are suppressed
+m 1 P a(?:b|b)c abc abc
+# make color/subcolor relationship go back and forth
+m 2 & {[ab][ab][ab]} aba aba
+m 3 & {[ab][ab][ab][ab][ab][ab][ab]} abababa abababa
+
+
+
+doing 28 "boundary busters etc."
+# color-descriptor allocation changes at 10
+m 1 & abcdefghijkl abcdefghijkl abcdefghijkl
+# so does arc allocation
+m 2 P a(?:b|c|d|e|f|g|h|i|j|k|l|m)n agn agn
+# subexpression tracking also at 10
+m 3 - a(((((((((((((b)))))))))))))c abc abc b b b b b b b b b b b b b
+# state-set handling changes slightly at unsigned size (might be 64...)
+# (also stresses arc allocation)
+m 4 Q "ab{1,100}c" abbc abbc
+m 5 Q "ab{1,100}c" abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc \
+ abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc
+m 6 Q "ab{1,100}c" \
+ abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc \
+ abbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbc
+# force small cache and bust it, several ways
+m 7 LP {\w+abcdefgh} xyzabcdefgh xyzabcdefgh
+m 8 %LP {\w+abcdefgh} xyzabcdefgh xyzabcdefgh
+m 9 %LP {\w+abcdefghijklmnopqrst} xyzabcdefghijklmnopqrst \
+ xyzabcdefghijklmnopqrst
+i 10 %LP {\w+(abcdefgh)?} xyz {0 2} {-1 -1}
+i 11 %LP {\w+(abcdefgh)?} xyzabcdefg {0 9} {-1 -1}
+i 12 %LP {\w+(abcdefghijklmnopqrst)?} xyzabcdefghijklmnopqrs \
+ {0 21} {-1 -1}
+
+
+
+doing 29 "misc. oddities and old bugs"
+e 1 & *** BADRPT
+m 2 N a?b* abb abb
+m 3 N a?b* bb bb
+
+
+
+doing 0 "flush" ;# to flush any leftover complaints
+return
diff --git a/unix/Makefile.in b/unix/Makefile.in
index 8063f87..fd2bdbc 100644
--- a/unix/Makefile.in
+++ b/unix/Makefile.in
@@ -5,7 +5,7 @@
# "autoconf" program (constructs like "@foo@" will get replaced in the
# actual Makefile.
#
-# RCS: @(#) $Id: Makefile.in,v 1.1.2.3 1998/10/06 02:59:06 stanton Exp $
+# RCS: @(#) $Id: Makefile.in,v 1.1.2.4 1998/10/21 20:40:12 stanton Exp $
# Current Tcl version; used in various names.
@@ -241,7 +241,7 @@ TCLTEST_OBJS = tclTestInit.o tclTest.o tclTestObj.o tclTestProcBodyObj.o \
XTTEST_OBJS = tclTest.o tclTestObj.o tclUnixTest.o tclXtNotify.o \
tclXtTest.o xtTestInit.o
-GENERIC_OBJS = compile.o exec.o panic.o \
+GENERIC_OBJS = regcomp.o regexec.o regfree.o regerror.o panic.o \
tclAsync.o tclBasic.o tclBinary.o \
tclCkalloc.o tclClock.o tclCmdAH.o tclCmdIL.o tclCmdMZ.o \
tclCompCmds.o tclCompExpr.o tclCompile.o tclDate.o tclEncoding.o \
@@ -264,8 +264,10 @@ GENERIC_HDRS = \
$(GENERIC_DIR)/tclPatch.h
GENERIC_SRCS = \
- $(GENERIC_DIR)/compile.c \
- $(GENERIC_DIR)/exec.c \
+ $(GENERIC_DIR)/regcomp.c \
+ $(GENERIC_DIR)/regexec.c \
+ $(GENERIC_DIR)/regfree.c \
+ $(GENERIC_DIR)/regerror.c \
$(GENERIC_DIR)/tclAsync.c \
$(GENERIC_DIR)/tclBasic.c \
$(GENERIC_DIR)/tclBinary.c \
@@ -609,11 +611,21 @@ xtTestInit.o: $(UNIX_DIR)/tclAppInit.c
panic.o: $(GENERIC_DIR)/panic.c
$(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/panic.c
-compile.o: $(GENERIC_DIR)/compile.c $(GENERIC_DIR)/lex.c $(GENERIC_DIR)/color.c $(GENERIC_DIR)/locale.c $(GENERIC_DIR)/nfa.c
- $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/compile.c
+REGHDRS=$(GENERIC_DIR)/regex.h $(GENERIC_DIR)/regguts.h \
+ $(GENERIC_DIR)/regcustom.h
+regcomp.o: $(REGHDRS) $(GENERIC_DIR)/regcomp.c $(GENERIC_DIR)/regc_lex.c \
+ $(GENERIC_DIR)/regc_color.c $(GENERIC_DIR)/regc_locale.c \
+ $(GENERIC_DIR)/regc_nfa.c $(GENERIC_DIR)/regc_cvec.c
+ $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/regcomp.c
-exec.o: $(GENERIC_DIR)/exec.c
- $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/exec.c
+regexec.o: $(REGHDRS) $(GENERIC_DIR)/regexec.c
+ $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/regexec.c
+
+regfree.o: $(REGHDRS) $(GENERIC_DIR)/regfree.c
+ $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/regfree.c
+
+regerror.o: $(REGHDRS) $(GENERIC_DIR)/regerrs.h $(GENERIC_DIR)/regerror.c
+ $(CC) -c $(CC_SWITCHES) $(GENERIC_DIR)/regerror.c
tclAppInit.o: $(UNIX_DIR)/tclAppInit.c
$(CC) -c $(CC_SWITCHES) $(UNIX_DIR)/tclAppInit.c
diff --git a/win/makefile.bc b/win/makefile.bc
index cb0a936..abdf5d9 100644
--- a/win/makefile.bc
+++ b/win/makefile.bc
@@ -1,5 +1,5 @@
# Copyright (c) 1995-1996 Sun Microsystems, Inc.
-# RCS: @(#) $Id: makefile.bc,v 1.1.2.2 1998/09/24 23:59:49 stanton Exp $
+# RCS: @(#) $Id: makefile.bc,v 1.1.2.3 1998/10/21 20:40:12 stanton Exp $
#
# Borland C++ 4.5 makefile
#
@@ -57,8 +57,10 @@ TCLTESTOBJS = \
$(TMPDIR)\testMain.obj
TCLOBJS = \
- $(TMPDIR)\compile.obj \
- $(TMPDIR)\exec.obj \
+ $(TMPDIR)\regcomp.obj \
+ $(TMPDIR)\regexec.obj \
+ $(TMPDIR)\regfree.obj \
+ $(TMPDIR)\regerror.obj \
$(TMPDIR)\panic.obj \
$(TMPDIR)\strftime.obj \
$(TMPDIR)\tclAlloc.obj \
diff --git a/win/makefile.vc b/win/makefile.vc
index 754163c..9ef9052 100644
--- a/win/makefile.vc
+++ b/win/makefile.vc
@@ -4,7 +4,7 @@
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
# Copyright (c) 1995-1996 Sun Microsystems, Inc.
-# RCS: @(#) $Id: makefile.vc,v 1.1.2.5 1998/10/06 02:59:06 stanton Exp $
+# RCS: @(#) $Id: makefile.vc,v 1.1.2.6 1998/10/21 20:40:13 stanton Exp $
# Does not depend on the presence of any environment variables in
# order to compile tcl; all needed information is derived from
@@ -116,8 +116,10 @@ TCLTESTOBJS = \
$(TMPDIR)\testMain.obj
TCLOBJS = \
- $(TMPDIR)\compile.obj \
- $(TMPDIR)\exec.obj \
+ $(TMPDIR)\regcomp.obj \
+ $(TMPDIR)\regexec.obj \
+ $(TMPDIR)\regfree.obj \
+ $(TMPDIR)\regerror.obj \
$(TMPDIR)\panic.obj \
$(TMPDIR)\strftime.obj \
$(TMPDIR)\tclAlloc.obj \