aboutsummaryrefslogtreecommitdiff
path: root/posix
diff options
context:
space:
mode:
Diffstat (limited to 'posix')
-rw-r--r--posix/BOOST.tests834
-rw-r--r--posix/Makefile21
-rw-r--r--posix/PCRE.tests2369
-rw-r--r--posix/tst-boost.c227
-rw-r--r--posix/tst-pcre.c241
5 files changed, 3688 insertions, 4 deletions
diff --git a/posix/BOOST.tests b/posix/BOOST.tests
new file mode 100644
index 0000000000..32b6c921ad
--- /dev/null
+++ b/posix/BOOST.tests
@@ -0,0 +1,834 @@
+;
+;
+; this file contains a script of tests to run through regress.exe
+;
+; comments start with a semicolon and proceed to the end of the line
+;
+; changes to regular expression compile flags start with a "-" as the first
+; non-whitespace character and consist of a list of the printable names
+; of the flags, for example "match_default"
+;
+; Other lines contain a test to perform using the current flag status
+; the first token contains the expression to compile, the second the string
+; to match it against. If the second string is "!" then the expression should
+; not compile, that is the first string is an invalid regular expression.
+; This is then followed by a list of integers that specify what should match,
+; each pair represents the starting and ending positions of a subexpression
+; starting with the zeroth subexpression (the whole match).
+; A value of -1 indicates that the subexpression should not take part in the
+; match at all, if the first value is -1 then no part of the expression should
+; match the string.
+;
+; Tests taken from BOOST testsuite and adapted to glibc regex.
+;
+; Boost Software License - Version 1.0 - August 17th, 2003
+;
+; Permission is hereby granted, free of charge, to any person or organization
+; obtaining a copy of the software and accompanying documentation covered by
+; this license (the "Software") to use, reproduce, display, distribute,
+; execute, and transmit the Software, and to prepare derivative works of the
+; Software, and to permit third-parties to whom the Software is furnished to
+; do so, all subject to the following:
+;
+; The copyright notices in the Software and this entire statement, including
+; the above license grant, this restriction and the following disclaimer,
+; must be included in all copies of the Software, in whole or in part, and
+; all derivative works of the Software, unless such copies or derivative
+; works are solely in the form of machine-executable object code generated by
+; a source language processor.
+;
+; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+; FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT
+; SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE
+; FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE,
+; ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+; DEALINGS IN THE SOFTWARE.
+;
+
+- match_default normal REG_EXTENDED
+
+;
+; try some really simple literals:
+a a 0 1
+Z Z 0 1
+Z aaa -1 -1
+Z xxxxZZxxx 4 5
+
+; and some simple brackets:
+(a) zzzaazz 3 4 3 4
+() zzz 0 0 0 0
+() "" 0 0 0 0
+( !
+) ) 0 1
+(aa !
+aa) baa)b 1 4
+a b -1 -1
+\(\) () 0 2
+\(a\) (a) 0 3
+\() () 0 2
+(\) !
+p(a)rameter ABCparameterXYZ 3 12 4 5
+[pq](a)rameter ABCparameterXYZ 3 12 4 5
+
+; now try escaped brackets:
+- match_default bk_parens REG_BASIC
+\(a\) zzzaazz 3 4 3 4
+\(\) zzz 0 0 0 0
+\(\) "" 0 0 0 0
+\( !
+\) !
+\(aa !
+aa\) !
+() () 0 2
+(a) (a) 0 3
+(\) !
+\() !
+
+; now move on to "." wildcards
+- match_default normal REG_EXTENDED REG_STARTEND
+. a 0 1
+. \n 0 1
+. \r 0 1
+. \0 0 1
+
+;
+; now move on to the repetion ops,
+; starting with operator *
+- match_default normal REG_EXTENDED
+a* b 0 0
+ab* a 0 1
+ab* ab 0 2
+ab* sssabbbbbbsss 3 10
+ab*c* a 0 1
+ab*c* abbb 0 4
+ab*c* accc 0 4
+ab*c* abbcc 0 5
+*a !
+\<* !
+\>* !
+\n* \n\n 0 2
+\** ** 0 2
+\* * 0 1
+
+; now try operator +
+ab+ a -1 -1
+ab+ ab 0 2
+ab+ sssabbbbbbsss 3 10
+ab+c+ a -1 -1
+ab+c+ abbb -1 -1
+ab+c+ accc -1 -1
+ab+c+ abbcc 0 5
++a !
+\<+ !
+\>+ !
+\n+ \n\n 0 2
+\+ + 0 1
+\+ ++ 0 1
+\++ ++ 0 2
+
+; now try operator ?
+- match_default normal REG_EXTENDED
+a? b 0 0
+ab? a 0 1
+ab? ab 0 2
+ab? sssabbbbbbsss 3 5
+ab?c? a 0 1
+ab?c? abbb 0 2
+ab?c? accc 0 2
+ab?c? abcc 0 3
+?a !
+\<? !
+\>? !
+\n? \n\n 0 1
+\? ? 0 1
+\? ?? 0 1
+\?? ?? 0 1
+
+; now try operator {}
+- match_default normal REG_EXTENDED
+a{2} a -1 -1
+a{2} aa 0 2
+a{2} aaa 0 2
+a{2,} a -1 -1
+a{2,} aa 0 2
+a{2,} aaaaa 0 5
+a{2,4} a -1 -1
+a{2,4} aa 0 2
+a{2,4} aaa 0 3
+a{2,4} aaaa 0 4
+a{2,4} aaaaa 0 4
+a{} !
+a{2 !
+a} a} 0 2
+\{\} {} 0 2
+
+- match_default normal REG_BASIC
+a\{2\} a -1 -1
+a\{2\} aa 0 2
+a\{2\} aaa 0 2
+a\{2,\} a -1 -1
+a\{2,\} aa 0 2
+a\{2,\} aaaaa 0 5
+a\{2,4\} a -1 -1
+a\{2,4\} aa 0 2
+a\{2,4\} aaa 0 3
+a\{2,4\} aaaa 0 4
+a\{2,4\} aaaaa 0 4
+{} {} 0 2
+
+; now test the alternation operator |
+- match_default normal REG_EXTENDED
+a|b a 0 1
+a|b b 0 1
+a(b|c) ab 0 2 1 2
+a(b|c) ac 0 2 1 2
+a(b|c) ad -1 -1 -1 -1
+a\| a| 0 2
+
+; now test the set operator []
+- match_default normal REG_EXTENDED
+; try some literals first
+[abc] a 0 1
+[abc] b 0 1
+[abc] c 0 1
+[abc] d -1 -1
+[^bcd] a 0 1
+[^bcd] b -1 -1
+[^bcd] d -1 -1
+[^bcd] e 0 1
+a[b]c abc 0 3
+a[ab]c abc 0 3
+a[^ab]c adc 0 3
+a[]b]c a]c 0 3
+a[[b]c a[c 0 3
+a[-b]c a-c 0 3
+a[^]b]c adc 0 3
+a[^-b]c adc 0 3
+a[b-]c a-c 0 3
+a[b !
+a[] !
+
+; then some ranges
+[b-e] a -1 -1
+[b-e] b 0 1
+[b-e] e 0 1
+[b-e] f -1 -1
+[^b-e] a 0 1
+[^b-e] b -1 -1
+[^b-e] e -1 -1
+[^b-e] f 0 1
+a[1-3]c a2c 0 3
+a[3-1]c !
+a[1-3-5]c !
+a[1- !
+
+; and some classes
+a[[:alpha:]]c abc 0 3
+a[[:unknown:]]c !
+a[[: !
+a[[:alpha !
+a[[:alpha:] !
+a[[:alpha,:] !
+a[[:]:]]b !
+a[[:-:]]b !
+a[[:alph:]] !
+a[[:alphabet:]] !
+[[:alnum:]]+ -%@a0X_- 3 6
+[[:alpha:]]+ -%@aX_0- 3 5
+[[:blank:]]+ "a \tb" 1 4
+[[:cntrl:]]+ a\n\tb 1 3
+[[:digit:]]+ a019b 1 4
+[[:graph:]]+ " a%b " 1 4
+[[:lower:]]+ AabC 1 3
+; This test fails with STLPort, disable for now as this is a corner case anyway...
+;[[:print:]]+ "\na b\n" 1 4
+[[:punct:]]+ " %-&\t" 1 4
+[[:space:]]+ "a \n\t\rb" 1 5
+[[:upper:]]+ aBCd 1 3
+[[:xdigit:]]+ p0f3Cx 1 5
+
+; now test flag settings:
+- escape_in_lists REG_NO_POSIX_TEST
+[\n] \n 0 1
+- REG_NO_POSIX_TEST
+
+; line anchors
+- match_default normal REG_EXTENDED
+^ab ab 0 2
+^ab xxabxx -1 -1
+ab$ ab 0 2
+ab$ abxx -1 -1
+- match_default match_not_bol match_not_eol normal REG_EXTENDED REG_NOTBOL REG_NOTEOL
+^ab ab -1 -1
+^ab xxabxx -1 -1
+ab$ ab -1 -1
+ab$ abxx -1 -1
+
+; back references
+- match_default normal REG_PERL
+a(b)\2c !
+a(b\1)c !
+a(b*)c\1d abbcbbd 0 7 1 3
+a(b*)c\1d abbcbd -1 -1
+a(b*)c\1d abbcbbbd -1 -1
+^(.)\1 abc -1 -1
+a([bc])\1d abcdabbd 4 8 5 6
+; strictly speaking this is at best ambiguous, at worst wrong, this is what most
+; re implimentations will match though.
+a(([bc])\2)*d abbccd 0 6 3 5 3 4
+
+a(([bc])\2)*d abbcbd -1 -1
+a((b)*\2)*d abbbd 0 5 1 4 2 3
+; perl only:
+(ab*)[ab]*\1 ababaaa 0 7 0 1
+(a)\1bcd aabcd 0 5 0 1
+(a)\1bc*d aabcd 0 5 0 1
+(a)\1bc*d aabd 0 4 0 1
+(a)\1bc*d aabcccd 0 7 0 1
+(a)\1bc*[ce]d aabcccd 0 7 0 1
+^(a)\1b(c)*cd$ aabcccd 0 7 0 1 4 5
+
+; posix only:
+- match_default extended REG_EXTENDED
+(ab*)[ab]*\1 ababaaa 0 7 0 1
+
+;
+; word operators:
+\w a 0 1
+\w z 0 1
+\w A 0 1
+\w Z 0 1
+\w _ 0 1
+\w } -1 -1
+\w ` -1 -1
+\w [ -1 -1
+\w @ -1 -1
+; non-word:
+\W a -1 -1
+\W z -1 -1
+\W A -1 -1
+\W Z -1 -1
+\W _ -1 -1
+\W } 0 1
+\W ` 0 1
+\W [ 0 1
+\W @ 0 1
+; word start:
+\<abcd " abcd" 2 6
+\<ab cab -1 -1
+\<ab "\nab" 1 3
+\<tag ::tag 2 5
+;word end:
+abc\> abc 0 3
+abc\> abcd -1 -1
+abc\> abc\n 0 3
+abc\> abc:: 0 3
+; word boundary:
+\babcd " abcd" 2 6
+\bab cab -1 -1
+\bab "\nab" 1 3
+\btag ::tag 2 5
+abc\b abc 0 3
+abc\b abcd -1 -1
+abc\b abc\n 0 3
+abc\b abc:: 0 3
+; within word:
+\B ab 1 1
+a\Bb ab 0 2
+a\B ab 0 1
+a\B a -1 -1
+a\B "a " -1 -1
+
+;
+; buffer operators:
+\`abc abc 0 3
+\`abc \nabc -1 -1
+\`abc " abc" -1 -1
+abc\' abc 0 3
+abc\' abc\n -1 -1
+abc\' "abc " -1 -1
+
+;
+; now follows various complex expressions designed to try and bust the matcher:
+a(((b)))c abc 0 3 1 2 1 2 1 2
+a(b|(c))d abd 0 3 1 2 -1 -1
+a(b|(c))d acd 0 3 1 2 1 2
+a(b*|c)d abbd 0 4 1 3
+; just gotta have one DFA-buster, of course
+a[ab]{20} aaaaabaaaabaaaabaaaab 0 21
+; and an inline expansion in case somebody gets tricky
+a[ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab] aaaaabaaaabaaaabaaaab 0 21
+; and in case somebody just slips in an NFA...
+a[ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab][ab](wee|week)(knights|night) aaaaabaaaabaaaabaaaabweeknights 0 31 21 24 24 31
+; one really big one
+1234567890123456789012345678901234567890123456789012345678901234567890 a1234567890123456789012345678901234567890123456789012345678901234567890b 1 71
+; fish for problems as brackets go past 8
+[ab][cd][ef][gh][ij][kl][mn] xacegikmoq 1 8
+[ab][cd][ef][gh][ij][kl][mn][op] xacegikmoq 1 9
+[ab][cd][ef][gh][ij][kl][mn][op][qr] xacegikmoqy 1 10
+[ab][cd][ef][gh][ij][kl][mn][op][q] xacegikmoqy 1 10
+; and as parenthesis go past 9:
+(a)(b)(c)(d)(e)(f)(g)(h) zabcdefghi 1 9 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9
+(a)(b)(c)(d)(e)(f)(g)(h)(i) zabcdefghij 1 10 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9 9 10
+(a)(b)(c)(d)(e)(f)(g)(h)(i)(j) zabcdefghijk 1 11 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9 9 10 10 11
+(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k) zabcdefghijkl 1 12 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9 9 10 10 11 11 12
+(a)d|(b)c abc 1 3 -1 -1 1 2
+_+((www)|(ftp)|(mailto)):_* "_wwwnocolon _mailto:" 12 20 13 19 -1 -1 -1 -1 13 19
+
+; subtleties of matching
+;a(b)?c\1d acd 0 3 -1 -1
+; POSIX is about the following test:
+a(b)?c\1d acd -1 -1 -1 -1
+a(b?c)+d accd 0 4 2 3
+(wee|week)(knights|night) weeknights 0 10 0 3 3 10
+.* abc 0 3
+a(b|(c))d abd 0 3 1 2 -1 -1
+a(b|(c))d acd 0 3 1 2 1 2
+a(b*|c|e)d abbd 0 4 1 3
+a(b*|c|e)d acd 0 3 1 2
+a(b*|c|e)d ad 0 2 1 1
+a(b?)c abc 0 3 1 2
+a(b?)c ac 0 2 1 1
+a(b+)c abc 0 3 1 2
+a(b+)c abbbc 0 5 1 4
+a(b*)c ac 0 2 1 1
+(a|ab)(bc([de]+)f|cde) abcdef 0 6 0 1 1 6 3 5
+a([bc]?)c abc 0 3 1 2
+a([bc]?)c ac 0 2 1 1
+a([bc]+)c abc 0 3 1 2
+a([bc]+)c abcc 0 4 1 3
+a([bc]+)bc abcbc 0 5 1 3
+a(bb+|b)b abb 0 3 1 2
+a(bbb+|bb+|b)b abb 0 3 1 2
+a(bbb+|bb+|b)b abbb 0 4 1 3
+a(bbb+|bb+|b)bb abbb 0 4 1 2
+(.*).* abcdef 0 6 0 6
+(a*)* bc 0 0 0 0
+xyx*xz xyxxxxyxxxz 5 11
+
+; do we get the right subexpression when it is used more than once?
+a(b|c)*d ad 0 2 -1 -1
+a(b|c)*d abcd 0 4 2 3
+a(b|c)+d abd 0 3 1 2
+a(b|c)+d abcd 0 4 2 3
+a(b|c?)+d ad 0 2 1 1
+a(b|c){0,0}d ad 0 2 -1 -1
+a(b|c){0,1}d ad 0 2 -1 -1
+a(b|c){0,1}d abd 0 3 1 2
+a(b|c){0,2}d ad 0 2 -1 -1
+a(b|c){0,2}d abcd 0 4 2 3
+a(b|c){0,}d ad 0 2 -1 -1
+a(b|c){0,}d abcd 0 4 2 3
+a(b|c){1,1}d abd 0 3 1 2
+a(b|c){1,2}d abd 0 3 1 2
+a(b|c){1,2}d abcd 0 4 2 3
+a(b|c){1,}d abd 0 3 1 2
+a(b|c){1,}d abcd 0 4 2 3
+a(b|c){2,2}d acbd 0 4 2 3
+a(b|c){2,2}d abcd 0 4 2 3
+a(b|c){2,4}d abcd 0 4 2 3
+a(b|c){2,4}d abcbd 0 5 3 4
+a(b|c){2,4}d abcbcd 0 6 4 5
+a(b|c){2,}d abcd 0 4 2 3
+a(b|c){2,}d abcbd 0 5 3 4
+; perl only:
+a(b|c?)+d abcd 0 4 3 3
+a(b+|((c)*))+d abd 0 3 2 2 2 2 -1 -1
+a(b+|((c)*))+d abcd 0 4 3 3 3 3 2 3
+
+; posix only:
+- match_default extended REG_EXTENDED REG_STARTEND
+
+; XXX FIXME the following 4 tests fail ATM
+;a(b|c?)+d abcd 0 4 2 3
+;a(b|((c)*))+d abcd 0 4 2 3 2 3 2 3
+;a(b+|((c)*))+d abd 0 3 1 2 -1 -1 -1 -1
+;a(b+|((c)*))+d abcd 0 4 2 3 2 3 2 3
+
+a(b|((c)*))+d ad 0 2 1 1 1 1 -1 -1
+
+; XXX FIXME the following 3 tests fail ATM
+;a(b|((c)*))*d abcd 0 4 2 3 2 3 2 3
+;a(b+|((c)*))*d abd 0 3 1 2 -1 -1 -1 -1
+;a(b+|((c)*))*d abcd 0 4 2 3 2 3 2 3
+
+a(b|((c)*))*d ad 0 2 1 1 1 1 -1 -1
+
+- match_default normal REG_PERL
+; try to match C++ syntax elements:
+; line comment:
+//[^\n]* "++i //here is a line comment\n" 4 28
+; block comment:
+/\*([^*]|\*+[^*/])*\*+/ "/* here is a block comment */" 0 29 26 27
+/\*([^*]|\*+[^*/])*\*+/ "/**/" 0 4 -1 -1
+/\*([^*]|\*+[^*/])*\*+/ "/***/" 0 5 -1 -1
+/\*([^*]|\*+[^*/])*\*+/ "/****/" 0 6 -1 -1
+/\*([^*]|\*+[^*/])*\*+/ "/*****/" 0 7 -1 -1
+/\*([^*]|\*+[^*/])*\*+/ "/*****/*/" 0 7 -1 -1
+; preprossor directives:
+^[[:blank:]]*#([^\n]*\\[[:space:]]+)*[^\n]* "#define some_symbol" 0 19 -1 -1
+^[[:blank:]]*#([^\n]*\\[[:space:]]+)*[^\n]* "#define some_symbol(x) #x" 0 25 -1 -1
+; perl only:
+^[[:blank:]]*#([^\n]*\\[[:space:]]+)*[^\n]* "#define some_symbol(x) \\ \r\n foo();\\\r\n printf(#x);" 0 53 30 42
+; literals:
+((0x[[:xdigit:]]+)|([[:digit:]]+))u?((int(8|16|32|64))|L)? 0xFF 0 4 0 4 0 4 -1 -1 -1 -1 -1 -1 -1 -1
+((0x[[:xdigit:]]+)|([[:digit:]]+))u?((int(8|16|32|64))|L)? 35 0 2 0 2 -1 -1 0 2 -1 -1 -1 -1 -1 -1
+((0x[[:xdigit:]]+)|([[:digit:]]+))u?((int(8|16|32|64))|L)? 0xFFu 0 5 0 4 0 4 -1 -1 -1 -1 -1 -1 -1 -1
+((0x[[:xdigit:]]+)|([[:digit:]]+))u?((int(8|16|32|64))|L)? 0xFFL 0 5 0 4 0 4 -1 -1 4 5 -1 -1 -1 -1
+((0x[[:xdigit:]]+)|([[:digit:]]+))u?((int(8|16|32|64))|L)? 0xFFFFFFFFFFFFFFFFuint64 0 24 0 18 0 18 -1 -1 19 24 19 24 22 24
+; strings:
+'([^\\']|\\.)*' '\\x3A' 0 6 4 5
+'([^\\']|\\.)*' '\\'' 0 4 1 3
+'([^\\']|\\.)*' '\\n' 0 4 1 3
+
+; finally try some case insensitive matches:
+- match_default normal REG_EXTENDED REG_ICASE
+; upper and lower have no meaning here so they fail, however these
+; may compile with other libraries...
+;[[:lower:]] !
+;[[:upper:]] !
+0123456789@abcdefghijklmnopqrstuvwxyz\[\\\]\^_`ABCDEFGHIJKLMNOPQRSTUVWXYZ\{\|\} 0123456789@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]\^_`abcdefghijklmnopqrstuvwxyz\{\|\} 0 72
+
+; known and suspected bugs:
+- match_default normal REG_EXTENDED
+\( ( 0 1
+\) ) 0 1
+\$ $ 0 1
+\^ ^ 0 1
+\. . 0 1
+\* * 0 1
+\+ + 0 1
+\? ? 0 1
+\[ [ 0 1
+\] ] 0 1
+\| | 0 1
+\\ \\ 0 1
+# # 0 1
+\# # 0 1
+a- a- 0 2
+\- - 0 1
+\{ { 0 1
+\} } 0 1
+0 0 0 1
+1 1 0 1
+9 9 0 1
+b b 0 1
+B B 0 1
+< < 0 1
+> > 0 1
+w w 0 1
+W W 0 1
+` ` 0 1
+' ' 0 1
+\n \n 0 1
+, , 0 1
+a a 0 1
+f f 0 1
+n n 0 1
+r r 0 1
+t t 0 1
+v v 0 1
+c c 0 1
+x x 0 1
+: : 0 1
+(\.[[:alnum:]]+){2} "w.a.b " 1 5 3 5
+
+- match_default normal REG_EXTENDED REG_ICASE
+a A 0 1
+A a 0 1
+[abc]+ abcABC 0 6
+[ABC]+ abcABC 0 6
+[a-z]+ abcABC 0 6
+[A-Z]+ abzANZ 0 6
+[a-Z]+ abzABZ 0 6
+[A-z]+ abzABZ 0 6
+[[:lower:]]+ abyzABYZ 0 8
+[[:upper:]]+ abzABZ 0 6
+[[:alpha:]]+ abyzABYZ 0 8
+[[:alnum:]]+ 09abyzABYZ 0 10
+
+; word start:
+\<abcd " abcd" 2 6
+\<ab cab -1 -1
+\<ab "\nab" 1 3
+\<tag ::tag 2 5
+;word end:
+abc\> abc 0 3
+abc\> abcd -1 -1
+abc\> abc\n 0 3
+abc\> abc:: 0 3
+
+; collating elements and rewritten set code:
+- match_default normal REG_EXTENDED REG_STARTEND
+;[[.zero.]] 0 0 1
+;[[.one.]] 1 0 1
+;[[.two.]] 2 0 1
+;[[.three.]] 3 0 1
+[[.a.]] baa 1 2
+;[[.right-curly-bracket.]] } 0 1
+;[[.NUL.]] \0 0 1
+[[:<:]z] !
+[a[:>:]] !
+[[=a=]] a 0 1
+;[[=right-curly-bracket=]] } 0 1
+- match_default normal REG_EXTENDED REG_STARTEND REG_ICASE
+[[.A.]] A 0 1
+[[.A.]] a 0 1
+[[.A.]-b]+ AaBb 0 4
+[A-[.b.]]+ AaBb 0 4
+[[.a.]-B]+ AaBb 0 4
+[a-[.B.]]+ AaBb 0 4
+- match_default normal REG_EXTENDED REG_STARTEND
+[[.a.]-c]+ abcd 0 3
+[a-[.c.]]+ abcd 0 3
+[[:alpha:]-a] !
+[a-[:alpha:]] !
+
+; try mutli-character ligatures:
+;[[.ae.]] ae 0 2
+;[[.ae.]] aE -1 -1
+;[[.AE.]] AE 0 2
+;[[.Ae.]] Ae 0 2
+;[[.ae.]-b] a -1 -1
+;[[.ae.]-b] b 0 1
+;[[.ae.]-b] ae 0 2
+;[a-[.ae.]] a 0 1
+;[a-[.ae.]] b -1 -1
+;[a-[.ae.]] ae 0 2
+- match_default normal REG_EXTENDED REG_STARTEND REG_ICASE
+;[[.ae.]] AE 0 2
+;[[.ae.]] Ae 0 2
+;[[.AE.]] Ae 0 2
+;[[.Ae.]] aE 0 2
+;[[.AE.]-B] a -1 -1
+;[[.Ae.]-b] b 0 1
+;[[.Ae.]-b] B 0 1
+;[[.ae.]-b] AE 0 2
+
+- match_default normal REG_EXTENDED REG_STARTEND REG_NO_POSIX_TEST
+\s+ "ab ab" 2 5
+\S+ " abc " 2 5
+
+- match_default normal REG_EXTENDED REG_STARTEND
+\`abc abc 0 3
+\`abc aabc -1 -1
+abc\' abc 0 3
+abc\' abcd -1 -1
+abc\' abc\n\n -1 -1
+abc\' abc 0 3
+
+; extended repeat checking to exercise new algorithms:
+ab.*xy abxy_ 0 4
+ab.*xy ab_xy_ 0 5
+ab.*xy abxy 0 4
+ab.*xy ab_xy 0 5
+ab.* ab 0 2
+ab.* ab__ 0 4
+
+ab.{2,5}xy ab__xy_ 0 6
+ab.{2,5}xy ab____xy_ 0 8
+ab.{2,5}xy ab_____xy_ 0 9
+ab.{2,5}xy ab__xy 0 6
+ab.{2,5}xy ab_____xy 0 9
+ab.{2,5} ab__ 0 4
+ab.{2,5} ab_______ 0 7
+ab.{2,5}xy ab______xy -1 -1
+ab.{2,5}xy ab_xy -1 -1
+
+ab.*?xy abxy_ 0 4
+ab.*?xy ab_xy_ 0 5
+ab.*?xy abxy 0 4
+ab.*?xy ab_xy 0 5
+ab.*? ab 0 2
+ab.*? ab__ 0 4
+
+ab.{2,5}?xy ab__xy_ 0 6
+ab.{2,5}?xy ab____xy_ 0 8
+ab.{2,5}?xy ab_____xy_ 0 9
+ab.{2,5}?xy ab__xy 0 6
+ab.{2,5}?xy ab_____xy 0 9
+ab.{2,5}? ab__ 0 4
+ab.{2,5}? ab_______ 0 7
+ab.{2,5}?xy ab______xy -1 -1
+ab.{2,5}xy ab_xy -1 -1
+
+; again but with slower algorithm variant:
+- match_default REG_EXTENDED
+; now again for single character repeats:
+
+ab_*xy abxy_ 0 4
+ab_*xy ab_xy_ 0 5
+ab_*xy abxy 0 4
+ab_*xy ab_xy 0 5
+ab_* ab 0 2
+ab_* ab__ 0 4
+
+ab_{2,5}xy ab__xy_ 0 6
+ab_{2,5}xy ab____xy_ 0 8
+ab_{2,5}xy ab_____xy_ 0 9
+ab_{2,5}xy ab__xy 0 6
+ab_{2,5}xy ab_____xy 0 9
+ab_{2,5} ab__ 0 4
+ab_{2,5} ab_______ 0 7
+ab_{2,5}xy ab______xy -1 -1
+ab_{2,5}xy ab_xy -1 -1
+
+ab_*?xy abxy_ 0 4
+ab_*?xy ab_xy_ 0 5
+ab_*?xy abxy 0 4
+ab_*?xy ab_xy 0 5
+ab_*? ab 0 2
+ab_*? ab__ 0 4
+
+ab_{2,5}?xy ab__xy_ 0 6
+ab_{2,5}?xy ab____xy_ 0 8
+ab_{2,5}?xy ab_____xy_ 0 9
+ab_{2,5}?xy ab__xy 0 6
+ab_{2,5}?xy ab_____xy 0 9
+ab_{2,5}? ab__ 0 4
+ab_{2,5}? ab_______ 0 7
+ab_{2,5}?xy ab______xy -1 -1
+ab_{2,5}xy ab_xy -1 -1
+
+; and again for sets:
+ab[_,;]*xy abxy_ 0 4
+ab[_,;]*xy ab_xy_ 0 5
+ab[_,;]*xy abxy 0 4
+ab[_,;]*xy ab_xy 0 5
+ab[_,;]* ab 0 2
+ab[_,;]* ab__ 0 4
+
+ab[_,;]{2,5}xy ab__xy_ 0 6
+ab[_,;]{2,5}xy ab____xy_ 0 8
+ab[_,;]{2,5}xy ab_____xy_ 0 9
+ab[_,;]{2,5}xy ab__xy 0 6
+ab[_,;]{2,5}xy ab_____xy 0 9
+ab[_,;]{2,5} ab__ 0 4
+ab[_,;]{2,5} ab_______ 0 7
+ab[_,;]{2,5}xy ab______xy -1 -1
+ab[_,;]{2,5}xy ab_xy -1 -1
+
+ab[_,;]*?xy abxy_ 0 4
+ab[_,;]*?xy ab_xy_ 0 5
+ab[_,;]*?xy abxy 0 4
+ab[_,;]*?xy ab_xy 0 5
+ab[_,;]*? ab 0 2
+ab[_,;]*? ab__ 0 4
+
+ab[_,;]{2,5}?xy ab__xy_ 0 6
+ab[_,;]{2,5}?xy ab____xy_ 0 8
+ab[_,;]{2,5}?xy ab_____xy_ 0 9
+ab[_,;]{2,5}?xy ab__xy 0 6
+ab[_,;]{2,5}?xy ab_____xy 0 9
+ab[_,;]{2,5}? ab__ 0 4
+ab[_,;]{2,5}? ab_______ 0 7
+ab[_,;]{2,5}?xy ab______xy -1 -1
+ab[_,;]{2,5}xy ab_xy -1 -1
+
+; and again for tricky sets with digraphs:
+;ab[_[.ae.]]*xy abxy_ 0 4
+;ab[_[.ae.]]*xy ab_xy_ 0 5
+;ab[_[.ae.]]*xy abxy 0 4
+;ab[_[.ae.]]*xy ab_xy 0 5
+;ab[_[.ae.]]* ab 0 2
+;ab[_[.ae.]]* ab__ 0 4
+
+;ab[_[.ae.]]{2,5}xy ab__xy_ 0 6
+;ab[_[.ae.]]{2,5}xy ab____xy_ 0 8
+;ab[_[.ae.]]{2,5}xy ab_____xy_ 0 9
+;ab[_[.ae.]]{2,5}xy ab__xy 0 6
+;ab[_[.ae.]]{2,5}xy ab_____xy 0 9
+;ab[_[.ae.]]{2,5} ab__ 0 4
+;ab[_[.ae.]]{2,5} ab_______ 0 7
+;ab[_[.ae.]]{2,5}xy ab______xy -1 -1
+;ab[_[.ae.]]{2,5}xy ab_xy -1 -1
+
+;ab[_[.ae.]]*?xy abxy_ 0 4
+;ab[_[.ae.]]*?xy ab_xy_ 0 5
+;ab[_[.ae.]]*?xy abxy 0 4
+;ab[_[.ae.]]*?xy ab_xy 0 5
+;ab[_[.ae.]]*? ab 0 2
+;ab[_[.ae.]]*? ab__ 0 2
+
+;ab[_[.ae.]]{2,5}?xy ab__xy_ 0 6
+;ab[_[.ae.]]{2,5}?xy ab____xy_ 0 8
+;ab[_[.ae.]]{2,5}?xy ab_____xy_ 0 9
+;ab[_[.ae.]]{2,5}?xy ab__xy 0 6
+;ab[_[.ae.]]{2,5}?xy ab_____xy 0 9
+;ab[_[.ae.]]{2,5}? ab__ 0 4
+;ab[_[.ae.]]{2,5}? ab_______ 0 4
+;ab[_[.ae.]]{2,5}?xy ab______xy -1 -1
+;ab[_[.ae.]]{2,5}xy ab_xy -1 -1
+
+; new bugs detected in spring 2003:
+- normal match_continuous REG_NO_POSIX_TEST
+b abc 1 2
+
+() abc 0 0 0 0
+^() abc 0 0 0 0
+^()+ abc 0 0 0 0
+^(){1} abc 0 0 0 0
+^(){2} abc 0 0 0 0
+^((){2}) abc 0 0 0 0 0 0
+() "" 0 0 0 0
+()\1 "" 0 0 0 0
+()\1 a 0 0 0 0
+a()\1b ab 0 2 1 1
+a()b\1 ab 0 2 1 1
+
+; subtleties of matching with no sub-expressions marked
+- normal match_nosubs REG_NO_POSIX_TEST
+a(b?c)+d accd 0 4
+(wee|week)(knights|night) weeknights 0 10
+.* abc 0 3
+a(b|(c))d abd 0 3
+a(b|(c))d acd 0 3
+a(b*|c|e)d abbd 0 4
+a(b*|c|e)d acd 0 3
+a(b*|c|e)d ad 0 2
+a(b?)c abc 0 3
+a(b?)c ac 0 2
+a(b+)c abc 0 3
+a(b+)c abbbc 0 5
+a(b*)c ac 0 2
+(a|ab)(bc([de]+)f|cde) abcdef 0 6
+a([bc]?)c abc 0 3
+a([bc]?)c ac 0 2
+a([bc]+)c abc 0 3
+a([bc]+)c abcc 0 4
+a([bc]+)bc abcbc 0 5
+a(bb+|b)b abb 0 3
+a(bbb+|bb+|b)b abb 0 3
+a(bbb+|bb+|b)b abbb 0 4
+a(bbb+|bb+|b)bb abbb 0 4
+(.*).* abcdef 0 6
+(a*)* bc 0 0
+
+- normal nosubs REG_NO_POSIX_TEST
+a(b?c)+d accd 0 4
+(wee|week)(knights|night) weeknights 0 10
+.* abc 0 3
+a(b|(c))d abd 0 3
+a(b|(c))d acd 0 3
+a(b*|c|e)d abbd 0 4
+a(b*|c|e)d acd 0 3
+a(b*|c|e)d ad 0 2
+a(b?)c abc 0 3
+a(b?)c ac 0 2
+a(b+)c abc 0 3
+a(b+)c abbbc 0 5
+a(b*)c ac 0 2
+(a|ab)(bc([de]+)f|cde) abcdef 0 6
+a([bc]?)c abc 0 3
+a([bc]?)c ac 0 2
+a([bc]+)c abc 0 3
+a([bc]+)c abcc 0 4
+a([bc]+)bc abcbc 0 5
+a(bb+|b)b abb 0 3
+a(bbb+|bb+|b)b abb 0 3
+a(bbb+|bb+|b)b abbb 0 4
+a(bbb+|bb+|b)bb abbb 0 4
+(.*).* abcdef 0 6
+(a*)* bc 0 0
+
diff --git a/posix/Makefile b/posix/Makefile
index c74b631241..95f34f92dd 100644
--- a/posix/Makefile
+++ b/posix/Makefile
@@ -34,7 +34,8 @@ distribute := confstr.h TESTS TESTS2C.sed testcases.h \
PTESTS PTESTS2C.sed ptestcases.h \
globtest.c globtest.sh wordexp-tst.sh annexc.c fnmatch_loop.c \
spawn_int.h tst-getconf.sh regcomp.c regexec.c regex_internal.c \
- regex_internal.h fork.h rxspencer/tests rxspencer/COPYRIGHT
+ regex_internal.h fork.h rxspencer/tests rxspencer/COPYRIGHT \
+ PCRE.tests BOOST.tests
routines := \
uname \
@@ -78,7 +79,8 @@ tests := tstgetopt testfnm runtests runptests \
bug-regex8 bug-regex9 bug-regex10 bug-regex11 bug-regex12 \
bug-regex13 bug-regex14 bug-regex15 bug-regex16 \
bug-regex17 bug-regex18 bug-regex19 bug-regex20 \
- bug-regex21 tst-nice tst-nanosleep transbug tst-rxspencer
+ bug-regex21 tst-nice tst-nanosleep transbug tst-rxspencer \
+ tst-pcre tst-boost
ifeq (yes,$(build-shared))
test-srcs := globtest
tests += wordexp-test tst-exec tst-spawn
@@ -94,7 +96,8 @@ generated := $(addprefix wordexp-test-result, 1 2 3 4 5 6 7 8 9 10) \
annexc annexc.out wordexp-tst.out bug-regex2-mem \
bug-regex2.mtrace bug-regex14-mem bug-regex14.mtrace \
bug-regex21-mem bug-regex21.mtrace \
- tst-rxspencer-mem tst-rxspencer.mtrace tst-getconf.out
+ tst-rxspencer-mem tst-rxspencer.mtrace tst-getconf.out \
+ tst-pcre-mem tst-pcre.mtrace tst-boost-mem tst-boost.mtrace
include ../Rules
@@ -161,6 +164,8 @@ bug-regex19-ENV = LOCPATH=$(common-objpfx)localedata
bug-regex20-ENV = LOCPATH=$(common-objpfx)localedata
tst-rxspencer-ARGS = --utf8 rxspencer/tests
tst-rxspencer-ENV = LOCPATH=$(common-objpfx)localedata
+tst-pcre-ARGS = PCRE.tests
+tst-boost-ARGS = BOOST.tests
testcases.h: TESTS TESTS2C.sed
sed -f TESTS2C.sed < $< > $@T
@@ -182,7 +187,7 @@ tests: $(objpfx)annexc.out
ifeq (no,$(cross-compiling))
tests: $(objpfx)bug-regex2-mem $(objpfx)bug-regex14-mem \
$(objpfx)bug-regex21-mem $(objpfx)tst-rxspencer-mem \
- $(objpfx)tst-getconf.out
+ $(objpfx)tst-pcre-mem $(objpfx)tst-boost-mem $(objpfx)tst-getconf.out
endif
$(objpfx)annexc.out: $(objpfx)annexc
@@ -217,6 +222,14 @@ $(objpfx)tst-rxspencer-mem: $(objpfx)tst-rxspencer.out
> /dev/null
$(common-objpfx)malloc/mtrace $(objpfx)tst-rxspencer.mtrace > $@
+tst-pcre-ENV = MALLOC_TRACE=$(objpfx)tst-pcre.mtrace
+$(objpfx)tst-pcre-mem: $(objpfx)tst-pcre.out
+ $(common-objpfx)malloc/mtrace $(objpfx)tst-pcre.mtrace > $@
+
+tst-boost-ENV = MALLOC_TRACE=$(objpfx)tst-boost.mtrace
+$(objpfx)tst-boost-mem: $(objpfx)tst-boost.out
+ $(common-objpfx)malloc/mtrace $(objpfx)tst-boost.mtrace > $@
+
$(objpfx)tst-getconf.out: tst-getconf.sh $(objpfx)getconf
$(SHELL) -e $< $(common-objpfx) $(elf-objpfx) $(rtld-installed-name)
diff --git a/posix/PCRE.tests b/posix/PCRE.tests
new file mode 100644
index 0000000000..182f29f7a1
--- /dev/null
+++ b/posix/PCRE.tests
@@ -0,0 +1,2369 @@
+# PCRE version 4.4 21-August-2003
+
+# Tests taken from PCRE and modified to suit glibc regex.
+#
+# PCRE LICENCE
+# ------------
+#
+# PCRE is a library of functions to support regular expressions whose syntax
+# and semantics are as close as possible to those of the Perl 5 language.
+#
+# Written by: Philip Hazel <ph10@cam.ac.uk>
+#
+# University of Cambridge Computing Service,
+# Cambridge, England. Phone: +44 1223 334714.
+#
+# Copyright (c) 1997-2003 University of Cambridge
+#
+# Permission is granted to anyone to use this software for any purpose on any
+# computer system, and to redistribute it freely, subject to the following
+# restrictions:
+#
+# 1. This software is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+#
+# 2. The origin of this software must not be misrepresented, either by
+# explicit claim or by omission. In practice, this means that if you use
+# PCRE in software that you distribute to others, commercially or
+# otherwise, you must put a sentence like this
+#
+# Regular expression support is provided by the PCRE library package,
+# which is open source software, written by Philip Hazel, and copyright
+# by the University of Cambridge, England.
+#
+# somewhere reasonably visible in your documentation and in any relevant
+# files or online help data or similar. A reference to the ftp site for
+# the source, that is, to
+#
+# ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/
+#
+# should also be given in the documentation. However, this condition is not
+# intended to apply to whole chains of software. If package A includes PCRE,
+# it must acknowledge it, but if package B is software that includes package
+# A, the condition is not imposed on package B (unless it uses PCRE
+# independently).
+#
+# 3. Altered versions must be plainly marked as such, and must not be
+# misrepresented as being the original software.
+#
+# 4. If PCRE is embedded in any software that is released under the GNU
+# General Purpose Licence (GPL), or Lesser General Purpose Licence (LGPL),
+# then the terms of that licence shall supersede any condition above with
+# which it is incompatible.
+#
+# The documentation for PCRE, supplied in the "doc" directory, is distributed
+# under the same terms as the software itself.
+#
+# End
+#
+
+/the quick brown fox/
+ the quick brown fox
+ 0: the quick brown fox
+ The quick brown FOX
+No match
+ What do you know about the quick brown fox?
+ 0: the quick brown fox
+ What do you know about THE QUICK BROWN FOX?
+No match
+
+/The quick brown fox/i
+ the quick brown fox
+ 0: the quick brown fox
+ The quick brown FOX
+ 0: The quick brown FOX
+ What do you know about the quick brown fox?
+ 0: the quick brown fox
+ What do you know about THE QUICK BROWN FOX?
+ 0: THE QUICK BROWN FOX
+
+/a*abc?xyz+pqr{3}ab{2,}xy{4,5}pq{0,6}AB{0,}zz/
+ abxyzpqrrrabbxyyyypqAzz
+ 0: abxyzpqrrrabbxyyyypqAzz
+ abxyzpqrrrabbxyyyypqAzz
+ 0: abxyzpqrrrabbxyyyypqAzz
+ aabxyzpqrrrabbxyyyypqAzz
+ 0: aabxyzpqrrrabbxyyyypqAzz
+ aaabxyzpqrrrabbxyyyypqAzz
+ 0: aaabxyzpqrrrabbxyyyypqAzz
+ aaaabxyzpqrrrabbxyyyypqAzz
+ 0: aaaabxyzpqrrrabbxyyyypqAzz
+ abcxyzpqrrrabbxyyyypqAzz
+ 0: abcxyzpqrrrabbxyyyypqAzz
+ aabcxyzpqrrrabbxyyyypqAzz
+ 0: aabcxyzpqrrrabbxyyyypqAzz
+ aaabcxyzpqrrrabbxyyyypAzz
+ 0: aaabcxyzpqrrrabbxyyyypAzz
+ aaabcxyzpqrrrabbxyyyypqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqAzz
+ aaabcxyzpqrrrabbxyyyypqqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqqAzz
+ aaabcxyzpqrrrabbxyyyypqqqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqqqAzz
+ aaabcxyzpqrrrabbxyyyypqqqqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqqqqAzz
+ aaabcxyzpqrrrabbxyyyypqqqqqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqqqqqAzz
+ aaabcxyzpqrrrabbxyyyypqqqqqqAzz
+ 0: aaabcxyzpqrrrabbxyyyypqqqqqqAzz
+ aaaabcxyzpqrrrabbxyyyypqAzz
+ 0: aaaabcxyzpqrrrabbxyyyypqAzz
+ abxyzzpqrrrabbxyyyypqAzz
+ 0: abxyzzpqrrrabbxyyyypqAzz
+ aabxyzzzpqrrrabbxyyyypqAzz
+ 0: aabxyzzzpqrrrabbxyyyypqAzz
+ aaabxyzzzzpqrrrabbxyyyypqAzz
+ 0: aaabxyzzzzpqrrrabbxyyyypqAzz
+ aaaabxyzzzzpqrrrabbxyyyypqAzz
+ 0: aaaabxyzzzzpqrrrabbxyyyypqAzz
+ abcxyzzpqrrrabbxyyyypqAzz
+ 0: abcxyzzpqrrrabbxyyyypqAzz
+ aabcxyzzzpqrrrabbxyyyypqAzz
+ 0: aabcxyzzzpqrrrabbxyyyypqAzz
+ aaabcxyzzzzpqrrrabbxyyyypqAzz
+ 0: aaabcxyzzzzpqrrrabbxyyyypqAzz
+ aaaabcxyzzzzpqrrrabbxyyyypqAzz
+ 0: aaaabcxyzzzzpqrrrabbxyyyypqAzz
+ aaaabcxyzzzzpqrrrabbbxyyyypqAzz
+ 0: aaaabcxyzzzzpqrrrabbbxyyyypqAzz
+ aaaabcxyzzzzpqrrrabbbxyyyyypqAzz
+ 0: aaaabcxyzzzzpqrrrabbbxyyyyypqAzz
+ aaabcxyzpqrrrabbxyyyypABzz
+ 0: aaabcxyzpqrrrabbxyyyypABzz
+ aaabcxyzpqrrrabbxyyyypABBzz
+ 0: aaabcxyzpqrrrabbxyyyypABBzz
+ >>>aaabxyzpqrrrabbxyyyypqAzz
+ 0: aaabxyzpqrrrabbxyyyypqAzz
+ >aaaabxyzpqrrrabbxyyyypqAzz
+ 0: aaaabxyzpqrrrabbxyyyypqAzz
+ >>>>abcxyzpqrrrabbxyyyypqAzz
+ 0: abcxyzpqrrrabbxyyyypqAzz
+ *** Failers
+No match
+ abxyzpqrrabbxyyyypqAzz
+No match
+ abxyzpqrrrrabbxyyyypqAzz
+No match
+ abxyzpqrrrabxyyyypqAzz
+No match
+ aaaabcxyzzzzpqrrrabbbxyyyyyypqAzz
+No match
+ aaaabcxyzzzzpqrrrabbbxyyypqAzz
+No match
+ aaabcxyzpqrrrabbxyyyypqqqqqqqAzz
+No match
+
+/^(abc){1,2}zz/
+ abczz
+ 0: abczz
+ 1: abc
+ abcabczz
+ 0: abcabczz
+ 1: abc
+ *** Failers
+No match
+ zz
+No match
+ abcabcabczz
+No match
+ >>abczz
+No match
+
+/^(b+|a){1,2}c/
+ bc
+ 0: bc
+ 1: b
+ bbc
+ 0: bbc
+ 1: bb
+ bbbc
+ 0: bbbc
+ 1: bbb
+ bac
+ 0: bac
+ 1: a
+ bbac
+ 0: bbac
+ 1: a
+ aac
+ 0: aac
+ 1: a
+ abbbbbbbbbbbc
+ 0: abbbbbbbbbbbc
+ 1: bbbbbbbbbbb
+ bbbbbbbbbbbac
+ 0: bbbbbbbbbbbac
+ 1: a
+ *** Failers
+No match
+ aaac
+No match
+ abbbbbbbbbbbac
+No match
+
+/^[]cde]/
+ ]thing
+ 0: ]
+ cthing
+ 0: c
+ dthing
+ 0: d
+ ething
+ 0: e
+ *** Failers
+No match
+ athing
+No match
+ fthing
+No match
+
+/^[^]cde]/
+ athing
+ 0: a
+ fthing
+ 0: f
+ *** Failers
+ 0: *
+ ]thing
+No match
+ cthing
+No match
+ dthing
+No match
+ ething
+No match
+
+/^[0-9]+$/
+ 0
+ 0: 0
+ 1
+ 0: 1
+ 2
+ 0: 2
+ 3
+ 0: 3
+ 4
+ 0: 4
+ 5
+ 0: 5
+ 6
+ 0: 6
+ 7
+ 0: 7
+ 8
+ 0: 8
+ 9
+ 0: 9
+ 10
+ 0: 10
+ 100
+ 0: 100
+ *** Failers
+No match
+ abc
+No match
+
+/^.*nter/
+ enter
+ 0: enter
+ inter
+ 0: inter
+ uponter
+ 0: uponter
+
+/^xxx[0-9]+$/
+ xxx0
+ 0: xxx0
+ xxx1234
+ 0: xxx1234
+ *** Failers
+No match
+ xxx
+No match
+
+/^.+[0-9][0-9][0-9]$/
+ x123
+ 0: x123
+ xx123
+ 0: xx123
+ 123456
+ 0: 123456
+ *** Failers
+No match
+ 123
+No match
+ x1234
+ 0: x1234
+
+/^([^!]+)!(.+)=apquxz\.ixr\.zzz\.ac\.uk$/
+ abc!pqr=apquxz.ixr.zzz.ac.uk
+ 0: abc!pqr=apquxz.ixr.zzz.ac.uk
+ 1: abc
+ 2: pqr
+ *** Failers
+No match
+ !pqr=apquxz.ixr.zzz.ac.uk
+No match
+ abc!=apquxz.ixr.zzz.ac.uk
+No match
+ abc!pqr=apquxz:ixr.zzz.ac.uk
+No match
+ abc!pqr=apquxz.ixr.zzz.ac.ukk
+No match
+
+/:/
+ Well, we need a colon: somewhere
+ 0: :
+ *** Fail if we don't
+No match
+
+/([0-9a-f:]+)$/i
+ 0abc
+ 0: 0abc
+ 1: 0abc
+ abc
+ 0: abc
+ 1: abc
+ fed
+ 0: fed
+ 1: fed
+ E
+ 0: E
+ 1: E
+ ::
+ 0: ::
+ 1: ::
+ 5f03:12C0::932e
+ 0: 5f03:12C0::932e
+ 1: 5f03:12C0::932e
+ fed def
+ 0: def
+ 1: def
+ Any old stuff
+ 0: ff
+ 1: ff
+ *** Failers
+No match
+ 0zzz
+No match
+ gzzz
+No match
+ Any old rubbish
+No match
+
+/^.*\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})$/
+ .1.2.3
+ 0: .1.2.3
+ 1: 1
+ 2: 2
+ 3: 3
+ A.12.123.0
+ 0: A.12.123.0
+ 1: 12
+ 2: 123
+ 3: 0
+ *** Failers
+No match
+ .1.2.3333
+No match
+ 1.2.3
+No match
+ 1234.2.3
+No match
+
+/^([0-9]+)\s+IN\s+SOA\s+(\S+)\s+(\S+)\s*\(\s*$/
+ 1 IN SOA non-sp1 non-sp2(
+ 0: 1 IN SOA non-sp1 non-sp2(
+ 1: 1
+ 2: non-sp1
+ 3: non-sp2
+ 1 IN SOA non-sp1 non-sp2 (
+ 0: 1 IN SOA non-sp1 non-sp2 (
+ 1: 1
+ 2: non-sp1
+ 3: non-sp2
+ *** Failers
+No match
+ 1IN SOA non-sp1 non-sp2(
+No match
+
+/^[a-zA-Z0-9][a-zA-Z0-9-]*(\.[a-zA-Z0-9][a-zA-z0-9-]*)*\.$/
+ a.
+ 0: a.
+ Z.
+ 0: Z.
+ 2.
+ 0: 2.
+ ab-c.pq-r.
+ 0: ab-c.pq-r.
+ 1: .pq-r
+ sxk.zzz.ac.uk.
+ 0: sxk.zzz.ac.uk.
+ 1: .uk
+ x-.y-.
+ 0: x-.y-.
+ 1: .y-
+ *** Failers
+No match
+ -abc.peq.
+No match
+
+/^\*\.[a-z]([a-z0-9-]*[a-z0-9]+)?(\.[a-z]([a-z0-9-]*[a-z0-9]+)?)*$/
+ *.a
+ 0: *.a
+ *.b0-a
+ 0: *.b0-a
+ 1: 0-a
+ *.c3-b.c
+ 0: *.c3-b.c
+ 1: 3-b
+ 2: .c
+ *.c-a.b-c
+ 0: *.c-a.b-c
+ 1: -a
+ 2: .b-c
+ 3: -c
+ *** Failers
+No match
+ *.0
+No match
+ *.a-
+No match
+ *.a-b.c-
+No match
+ *.c-a.0-c
+No match
+
+/^[0-9a-f](\.[0-9a-f])*$/i
+ a.b.c.d
+ 0: a.b.c.d
+ 1: .d
+ A.B.C.D
+ 0: A.B.C.D
+ 1: .D
+ a.b.c.1.2.3.C
+ 0: a.b.c.1.2.3.C
+ 1: .C
+
+/^".*"\s*(;.*)?$/
+ "1234"
+ 0: "1234"
+ "abcd" ;
+ 0: "abcd" ;
+ 1: ;
+ "" ; rhubarb
+ 0: "" ; rhubarb
+ 1: ; rhubarb
+ *** Failers
+No match
+ "1234" : things
+No match
+
+/^(a(b(c)))(d(e(f)))(h(i(j)))(k(l(m)))$/
+ abcdefhijklm
+ 0: abcdefhijklm
+ 1: abc
+ 2: bc
+ 3: c
+ 4: def
+ 5: ef
+ 6: f
+ 7: hij
+ 8: ij
+ 9: j
+10: klm
+11: lm
+12: m
+
+/^a*\w/
+ z
+ 0: z
+ az
+ 0: az
+ aaaz
+ 0: aaaz
+ a
+ 0: a
+ aa
+ 0: aa
+ aaaa
+ 0: aaaa
+ a+
+ 0: a
+ aa+
+ 0: aa
+
+/^a+\w/
+ az
+ 0: az
+ aaaz
+ 0: aaaz
+ aa
+ 0: aa
+ aaaa
+ 0: aaaa
+ aa+
+ 0: aa
+
+/^[0-9]{8}\w{2,}/
+ 1234567890
+ 0: 1234567890
+ 12345678ab
+ 0: 12345678ab
+ 12345678__
+ 0: 12345678__
+ *** Failers
+No match
+ 1234567
+No match
+
+/^[aeiou0-9]{4,5}$/
+ uoie
+ 0: uoie
+ 1234
+ 0: 1234
+ 12345
+ 0: 12345
+ aaaaa
+ 0: aaaaa
+ *** Failers
+No match
+ 123456
+No match
+
+/\`(abc|def)=(\1){2,3}\'/
+ abc=abcabc
+ 0: abc=abcabc
+ 1: abc
+ 2: abc
+ def=defdefdef
+ 0: def=defdefdef
+ 1: def
+ 2: def
+ *** Failers
+No match
+ abc=defdef
+No match
+
+/(cat(a(ract|tonic)|erpillar)) \1()2(3)/
+ cataract cataract23
+ 0: cataract cataract23
+ 1: cataract
+ 2: aract
+ 3: ract
+ 4:
+ 5: 3
+ catatonic catatonic23
+ 0: catatonic catatonic23
+ 1: catatonic
+ 2: atonic
+ 3: tonic
+ 4:
+ 5: 3
+ caterpillar caterpillar23
+ 0: caterpillar caterpillar23
+ 1: caterpillar
+ 2: erpillar
+ 3: <unset>
+ 4:
+ 5: 3
+
+
+/^From +([^ ]+) +[a-zA-Z][a-zA-Z][a-zA-Z] +[a-zA-Z][a-zA-Z][a-zA-Z] +[0-9]?[0-9] +[0-9][0-9]:[0-9][0-9]/
+ From abcd Mon Sep 01 12:33:02 1997
+ 0: From abcd Mon Sep 01 12:33
+ 1: abcd
+
+/^From\s+\S+\s+([a-zA-Z]{3}\s+){2}[0-9]{1,2}\s+[0-9][0-9]:[0-9][0-9]/
+ From abcd Mon Sep 01 12:33:02 1997
+ 0: From abcd Mon Sep 01 12:33
+ 1: Sep
+ From abcd Mon Sep 1 12:33:02 1997
+ 0: From abcd Mon Sep 1 12:33
+ 1: Sep
+ *** Failers
+No match
+ From abcd Sep 01 12:33:02 1997
+No match
+
+/^(a)\1{2,3}(.)/
+ aaab
+ 0: aaab
+ 1: a
+ 2: b
+ aaaab
+ 0: aaaab
+ 1: a
+ 2: b
+ aaaaab
+ 0: aaaaa
+ 1: a
+ 2: a
+ aaaaaab
+ 0: aaaaa
+ 1: a
+ 2: a
+
+/^[ab]{1,3}(ab*|b)/
+ aabbbbb
+ 0: aabbbbb
+ 1: abbbbb
+
+/^(cow|)\1(bell)/
+ cowcowbell
+ 0: cowcowbell
+ 1: cow
+ 2: bell
+ bell
+ 0: bell
+ 1:
+ 2: bell
+ *** Failers
+No match
+ cowbell
+No match
+
+/^(a|)\1+b/
+ aab
+ 0: aab
+ 1: a
+ aaaab
+ 0: aaaab
+ 1: a
+ b
+ 0: b
+ 1:
+ *** Failers
+No match
+ ab
+No match
+
+/^(a|)\1{2}b/
+ aaab
+ 0: aaab
+ 1: a
+ b
+ 0: b
+ 1:
+ *** Failers
+No match
+ ab
+No match
+ aab
+No match
+ aaaab
+No match
+
+/^(a|)\1{2,3}b/
+ aaab
+ 0: aaab
+ 1: a
+ aaaab
+ 0: aaaab
+ 1: a
+ b
+ 0: b
+ 1:
+ *** Failers
+No match
+ ab
+No match
+ aab
+No match
+ aaaaab
+No match
+
+/ab{1,3}bc/
+ abbbbc
+ 0: abbbbc
+ abbbc
+ 0: abbbc
+ abbc
+ 0: abbc
+ *** Failers
+No match
+ abc
+No match
+ abbbbbc
+No match
+
+/([^.]*)\.([^:]*):[T ]+(.*)/
+ track1.title:TBlah blah blah
+ 0: track1.title:TBlah blah blah
+ 1: track1
+ 2: title
+ 3: Blah blah blah
+
+/([^.]*)\.([^:]*):[T ]+(.*)/i
+ track1.title:TBlah blah blah
+ 0: track1.title:TBlah blah blah
+ 1: track1
+ 2: title
+ 3: Blah blah blah
+
+/([^.]*)\.([^:]*):[t ]+(.*)/i
+ track1.title:TBlah blah blah
+ 0: track1.title:TBlah blah blah
+ 1: track1
+ 2: title
+ 3: Blah blah blah
+
+/^abc$/
+ abc
+ 0: abc
+ *** Failers
+No match
+
+/[-az]+/
+ az-
+ 0: az-
+ *** Failers
+ 0: a
+ b
+No match
+
+/[az-]+/
+ za-
+ 0: za-
+ *** Failers
+ 0: a
+ b
+No match
+
+/[a-z]+/
+ abcdxyz
+ 0: abcdxyz
+
+/[0-9-]+/
+ 12-34
+ 0: 12-34
+ *** Failers
+No match
+ aaa
+No match
+
+/(abc)\1/i
+ abcabc
+ 0: abcabc
+ 1: abc
+ ABCabc
+ 0: ABCabc
+ 1: ABC
+ abcABC
+ 0: abcABC
+ 1: abc
+
+/a{0}bc/
+ bc
+ 0: bc
+
+/^([^a])([^b])([^c]*)([^d]{3,4})/
+ baNOTccccd
+ 0: baNOTcccc
+ 1: b
+ 2: a
+ 3: NOT
+ 4: cccc
+ baNOTcccd
+ 0: baNOTccc
+ 1: b
+ 2: a
+ 3: NOT
+ 4: ccc
+ baNOTccd
+ 0: baNOTcc
+ 1: b
+ 2: a
+ 3: NO
+ 4: Tcc
+ bacccd
+ 0: baccc
+ 1: b
+ 2: a
+ 3:
+ 4: ccc
+ *** Failers
+ 0: *** Failers
+ 1: *
+ 2: *
+ 3: * Fail
+ 4: ers
+ anything
+No match
+ baccd
+No match
+
+/[^a]/
+ Abc
+ 0: A
+
+/[^a]/i
+ Abc
+ 0: b
+
+/[^a]+/
+ AAAaAbc
+ 0: AAA
+
+/[^a]+/i
+ AAAaAbc
+ 0: bc
+
+/[^k]$/
+ abc
+ 0: c
+ *** Failers
+ 0: s
+ abk
+No match
+
+/[^k]{2,3}$/
+ abc
+ 0: abc
+ kbc
+ 0: bc
+ kabc
+ 0: abc
+ *** Failers
+ 0: ers
+ abk
+No match
+ akb
+No match
+ akk
+No match
+
+/^[0-9]{8,}@.+[^k]$/
+ 12345678@a.b.c.d
+ 0: 12345678@a.b.c.d
+ 123456789@x.y.z
+ 0: 123456789@x.y.z
+ *** Failers
+No match
+ 12345678@x.y.uk
+No match
+ 1234567@a.b.c.d
+No match
+
+/(a)\1{8,}/
+ aaaaaaaaa
+ 0: aaaaaaaaa
+ 1: a
+ aaaaaaaaaa
+ 0: aaaaaaaaaa
+ 1: a
+ *** Failers
+No match
+ aaaaaaa
+No match
+
+/[^a]/
+ aaaabcd
+ 0: b
+ aaAabcd
+ 0: A
+
+/[^a]/i
+ aaaabcd
+ 0: b
+ aaAabcd
+ 0: b
+
+/[^az]/
+ aaaabcd
+ 0: b
+ aaAabcd
+ 0: A
+
+/[^az]/i
+ aaaabcd
+ 0: b
+ aaAabcd
+ 0: b
+
+/P[^*]TAIRE[^*]{1,6}LL/
+ xxxxxxxxxxxPSTAIREISLLxxxxxxxxx
+ 0: PSTAIREISLL
+
+/P[^*]TAIRE[^*]{1,}LL/
+ xxxxxxxxxxxPSTAIREISLLxxxxxxxxx
+ 0: PSTAIREISLL
+
+/(\.[0-9][0-9][1-9]?)[0-9]+/
+ 1.230003938
+ 0: .230003938
+ 1: .23
+ 1.875000282
+ 0: .875000282
+ 1: .875
+ 1.235
+ 0: .235
+ 1: .23
+
+/\b(foo)\s+(\w+)/i
+ Food is on the foo table
+ 0: foo table
+ 1: foo
+ 2: table
+
+/foo(.*)bar/
+ The food is under the bar in the barn.
+ 0: food is under the bar in the bar
+ 1: d is under the bar in the
+
+/(.*)([0-9]*)/
+ I have 2 numbers: 53147
+ 0: I have 2 numbers: 53147
+ 1: I have 2 numbers: 53147
+ 2:
+
+/(.*)([0-9]+)/
+ I have 2 numbers: 53147
+ 0: I have 2 numbers: 53147
+ 1: I have 2 numbers: 5314
+ 2: 7
+
+/(.*)([0-9]+)$/
+ I have 2 numbers: 53147
+ 0: I have 2 numbers: 53147
+ 1: I have 2 numbers: 5314
+ 2: 7
+
+/(.*)\b([0-9]+)$/
+ I have 2 numbers: 53147
+ 0: I have 2 numbers: 53147
+ 1: I have 2 numbers:
+ 2: 53147
+
+/(.*[^0-9])([0-9]+)$/
+ I have 2 numbers: 53147
+ 0: I have 2 numbers: 53147
+ 1: I have 2 numbers:
+ 2: 53147
+
+/[[:digit:]][[:digit:]]\/[[:digit:]][[:digit:]]\/[[:digit:]][[:digit:]][[:digit:]][[:digit:]]/
+ 01/01/2000
+ 0: 01/01/2000
+
+/^(a){0,0}/
+ bcd
+ 0:
+ abc
+ 0:
+ aab
+ 0:
+
+/^(a){0,1}/
+ bcd
+ 0:
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: a
+ 1: a
+
+/^(a){0,2}/
+ bcd
+ 0:
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+
+/^(a){0,3}/
+ bcd
+ 0:
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+ aaa
+ 0: aaa
+ 1: a
+
+/^(a){0,}/
+ bcd
+ 0:
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+ aaa
+ 0: aaa
+ 1: a
+ aaaaaaaa
+ 0: aaaaaaaa
+ 1: a
+
+/^(a){1,1}/
+ bcd
+No match
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: a
+ 1: a
+
+/^(a){1,2}/
+ bcd
+No match
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+
+/^(a){1,3}/
+ bcd
+No match
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+ aaa
+ 0: aaa
+ 1: a
+
+/^(a){1,}/
+ bcd
+No match
+ abc
+ 0: a
+ 1: a
+ aab
+ 0: aa
+ 1: a
+ aaa
+ 0: aaa
+ 1: a
+ aaaaaaaa
+ 0: aaaaaaaa
+ 1: a
+
+/^[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/
+ 123456654321
+ 0: 123456654321
+
+/^[[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]][[:digit:]]/
+ 123456654321
+ 0: 123456654321
+
+/^[abc]{12}/
+ abcabcabcabc
+ 0: abcabcabcabc
+
+/^[a-c]{12}/
+ abcabcabcabc
+ 0: abcabcabcabc
+
+/^(a|b|c){12}/
+ abcabcabcabc
+ 0: abcabcabcabc
+ 1: c
+
+/^[abcdefghijklmnopqrstuvwxy0123456789]/
+ n
+ 0: n
+ *** Failers
+No match
+ z
+No match
+
+/abcde{0,0}/
+ abcd
+ 0: abcd
+ *** Failers
+No match
+ abce
+No match
+
+/ab[cd]{0,0}e/
+ abe
+ 0: abe
+ *** Failers
+No match
+ abcde
+No match
+
+/ab(c){0,0}d/
+ abd
+ 0: abd
+ *** Failers
+No match
+ abcd
+No match
+
+/a(b*)/
+ a
+ 0: a
+ 1:
+ ab
+ 0: ab
+ 1: b
+ abbbb
+ 0: abbbb
+ 1: bbbb
+ *** Failers
+ 0: a
+ 1:
+ bbbbb
+No match
+
+/ab[0-9]{0}e/
+ abe
+ 0: abe
+ *** Failers
+No match
+ ab1e
+No match
+
+/(A|B)*CD/
+ CD
+ 0: CD
+
+/(AB)*\1/
+ ABABAB
+ 0: ABABAB
+ 1: AB
+
+/([0-9]+)(\w)/
+ 12345a
+ 0: 12345a
+ 1: 12345
+ 2: a
+ 12345+
+ 0: 12345
+ 1: 1234
+ 2: 5
+
+/(abc|)+/
+ abc
+ 0: abc
+ 1:
+ abcabc
+ 0: abcabc
+ 1:
+ abcabcabc
+ 0: abcabcabc
+ 1:
+ xyz
+ 0:
+ 1:
+
+/([a]*)*/
+ a
+ 0: a
+ 1:
+ aaaaa
+ 0: aaaaa
+ 1:
+
+/([ab]*)*/
+ a
+ 0: a
+ 1:
+ b
+ 0: b
+ 1:
+ ababab
+ 0: ababab
+ 1:
+ aaaabcde
+ 0: aaaab
+ 1:
+ bbbb
+ 0: bbbb
+ 1:
+
+/([^a]*)*/
+ b
+ 0: b
+ 1:
+ bbbb
+ 0: bbbb
+ 1:
+ aaa
+ 0:
+ 1:
+
+/([^ab]*)*/
+ cccc
+ 0: cccc
+ 1:
+ abab
+ 0:
+ 1:
+
+/abc/
+ abc
+ 0: abc
+ xabcy
+ 0: abc
+ ababc
+ 0: abc
+ *** Failers
+No match
+ xbc
+No match
+ axc
+No match
+ abx
+No match
+
+/ab*c/
+ abc
+ 0: abc
+
+/ab*bc/
+ abc
+ 0: abc
+ abbc
+ 0: abbc
+ abbbbc
+ 0: abbbbc
+
+/.{1}/
+ abbbbc
+ 0: a
+
+/.{3,4}/
+ abbbbc
+ 0: abbb
+
+/ab{0,}bc/
+ abbbbc
+ 0: abbbbc
+
+/ab+bc/
+ abbc
+ 0: abbc
+ *** Failers
+No match
+ abc
+No match
+ abq
+No match
+
+/ab+bc/
+ abbbbc
+ 0: abbbbc
+
+/ab{1,}bc/
+ abbbbc
+ 0: abbbbc
+
+/ab{1,3}bc/
+ abbbbc
+ 0: abbbbc
+
+/ab{3,4}bc/
+ abbbbc
+ 0: abbbbc
+
+/ab{4,5}bc/
+ *** Failers
+No match
+ abq
+No match
+ abbbbc
+No match
+
+/ab?bc/
+ abbc
+ 0: abbc
+ abc
+ 0: abc
+
+/ab{0,1}bc/
+ abc
+ 0: abc
+
+/ab?c/
+ abc
+ 0: abc
+
+/ab{0,1}c/
+ abc
+ 0: abc
+
+/^abc$/
+ abc
+ 0: abc
+ *** Failers
+No match
+ abbbbc
+No match
+ abcc
+No match
+
+/^abc/
+ abcc
+ 0: abc
+
+/abc$/
+ aabc
+ 0: abc
+ *** Failers
+No match
+ aabc
+ 0: abc
+ aabcd
+No match
+
+/^/
+ abc
+ 0:
+
+/$/
+ abc
+ 0:
+
+/a.c/
+ abc
+ 0: abc
+ axc
+ 0: axc
+
+/a.*c/
+ axyzc
+ 0: axyzc
+
+/a[bc]d/
+ abd
+ 0: abd
+ *** Failers
+No match
+ axyzd
+No match
+ abc
+No match
+
+/a[b-d]e/
+ ace
+ 0: ace
+
+/a[b-d]/
+ aac
+ 0: ac
+
+/a[-b]/
+ a-
+ 0: a-
+
+/a[b-]/
+ a-
+ 0: a-
+
+/a[]]b/
+ a]b
+ 0: a]b
+
+/a[^bc]d/
+ aed
+ 0: aed
+ *** Failers
+No match
+ abd
+No match
+ abd
+No match
+
+/a[^-b]c/
+ adc
+ 0: adc
+
+/a[^]b]c/
+ adc
+ 0: adc
+ *** Failers
+No match
+ a-c
+ 0: a-c
+ a]c
+No match
+
+/\ba\b/
+ a-
+ 0: a
+ -a
+ 0: a
+ -a-
+ 0: a
+
+/\by\b/
+ *** Failers
+No match
+ xy
+No match
+ yz
+No match
+ xyz
+No match
+
+/\Ba\B/
+ *** Failers
+ 0: a
+ a-
+No match
+ -a
+No match
+ -a-
+No match
+
+/\By\b/
+ xy
+ 0: y
+
+/\by\B/
+ yz
+ 0: y
+
+/\By\B/
+ xyz
+ 0: y
+
+/\w/
+ a
+ 0: a
+
+/\W/
+ -
+ 0: -
+ *** Failers
+ 0: *
+ -
+ 0: -
+ a
+No match
+
+/a\sb/
+ a b
+ 0: a b
+
+/a\Sb/
+ a-b
+ 0: a-b
+ *** Failers
+No match
+ a-b
+ 0: a-b
+ a b
+No match
+
+/[0-9]/
+ 1
+ 0: 1
+
+/[^0-9]/
+ -
+ 0: -
+ *** Failers
+ 0: *
+ -
+ 0: -
+ 1
+No match
+
+/ab|cd/
+ abc
+ 0: ab
+ abcd
+ 0: ab
+
+/()ef/
+ def
+ 0: ef
+ 1:
+
+/a\(b/
+ a(b
+ 0: a(b
+
+/a\(*b/
+ ab
+ 0: ab
+ a((b
+ 0: a((b
+
+/((a))/
+ abc
+ 0: a
+ 1: a
+ 2: a
+
+/(a)b(c)/
+ abc
+ 0: abc
+ 1: a
+ 2: c
+
+/a+b+c/
+ aabbabc
+ 0: abc
+
+/a{1,}b{1,}c/
+ aabbabc
+ 0: abc
+
+/(a+|b)*/
+ ab
+ 0: ab
+ 1: b
+
+/(a+|b){0,}/
+ ab
+ 0: ab
+ 1: b
+
+/(a+|b)+/
+ ab
+ 0: ab
+ 1: b
+
+/(a+|b){1,}/
+ ab
+ 0: ab
+ 1: b
+
+/(a+|b)?/
+ ab
+ 0: a
+ 1: a
+
+/(a+|b){0,1}/
+ ab
+ 0: a
+ 1: a
+
+/[^ab]*/
+ cde
+ 0: cde
+
+/abc/
+ *** Failers
+No match
+ b
+No match
+
+
+/a*/
+
+
+/([abc])*d/
+ abbbcd
+ 0: abbbcd
+ 1: c
+
+/([abc])*bcd/
+ abcd
+ 0: abcd
+ 1: a
+
+/a|b|c|d|e/
+ e
+ 0: e
+
+/(a|b|c|d|e)f/
+ ef
+ 0: ef
+ 1: e
+
+/abcd*efg/
+ abcdefg
+ 0: abcdefg
+
+/ab*/
+ xabyabbbz
+ 0: ab
+ xayabbbz
+ 0: a
+
+/(ab|cd)e/
+ abcde
+ 0: cde
+ 1: cd
+
+/[abhgefdc]ij/
+ hij
+ 0: hij
+
+/(abc|)ef/
+ abcdef
+ 0: ef
+ 1:
+
+/(a|b)c*d/
+ abcd
+ 0: bcd
+ 1: b
+
+/(ab|ab*)bc/
+ abc
+ 0: abc
+ 1: a
+
+/a([bc]*)c*/
+ abc
+ 0: abc
+ 1: bc
+
+/a([bc]*)(c*d)/
+ abcd
+ 0: abcd
+ 1: bc
+ 2: d
+
+/a([bc]+)(c*d)/
+ abcd
+ 0: abcd
+ 1: bc
+ 2: d
+
+/a([bc]*)(c+d)/
+ abcd
+ 0: abcd
+ 1: b
+ 2: cd
+
+/a[bcd]*dcdcde/
+ adcdcde
+ 0: adcdcde
+
+/a[bcd]+dcdcde/
+ *** Failers
+No match
+ abcde
+No match
+ adcdcde
+No match
+
+/(ab|a)b*c/
+ abc
+ 0: abc
+ 1: ab
+
+/((a)(b)c)(d)/
+ abcd
+ 0: abcd
+ 1: abc
+ 2: a
+ 3: b
+ 4: d
+
+/[a-zA-Z_][a-zA-Z0-9_]*/
+ alpha
+ 0: alpha
+
+/^a(bc+|b[eh])g|.h$/
+ abh
+ 0: bh
+
+/(bc+d$|ef*g.|h?i(j|k))/
+ effgz
+ 0: effgz
+ 1: effgz
+ ij
+ 0: ij
+ 1: ij
+ 2: j
+ reffgz
+ 0: effgz
+ 1: effgz
+ *** Failers
+No match
+ effg
+No match
+ bcdd
+No match
+
+/((((((((((a))))))))))/
+ a
+ 0: a
+ 1: a
+ 2: a
+ 3: a
+ 4: a
+ 5: a
+ 6: a
+ 7: a
+ 8: a
+ 9: a
+10: a
+
+/((((((((((a))))))))))\9/
+ aa
+ 0: aa
+ 1: a
+ 2: a
+ 3: a
+ 4: a
+ 5: a
+ 6: a
+ 7: a
+ 8: a
+ 9: a
+10: a
+
+/(((((((((a)))))))))/
+ a
+ 0: a
+ 1: a
+ 2: a
+ 3: a
+ 4: a
+ 5: a
+ 6: a
+ 7: a
+ 8: a
+ 9: a
+
+/multiple words of text/
+ *** Failers
+No match
+ aa
+No match
+ uh-uh
+No match
+
+/multiple words/
+ multiple words, yeah
+ 0: multiple words
+
+/(.*)c(.*)/
+ abcde
+ 0: abcde
+ 1: ab
+ 2: de
+
+/\((.*), (.*)\)/
+ (a, b)
+ 0: (a, b)
+ 1: a
+ 2: b
+
+/abcd/
+ abcd
+ 0: abcd
+
+/a(bc)d/
+ abcd
+ 0: abcd
+ 1: bc
+
+/a[-]?c/
+ ac
+ 0: ac
+
+/(abc)\1/
+ abcabc
+ 0: abcabc
+ 1: abc
+
+/([a-c]*)\1/
+ abcabc
+ 0: abcabc
+ 1: abc
+
+/(a)|\1/
+ a
+ 0: a
+ 1: a
+ *** Failers
+ 0: a
+ 1: a
+ ab
+ 0: a
+ 1: a
+ x
+No match
+
+/abc/i
+ ABC
+ 0: ABC
+ XABCY
+ 0: ABC
+ ABABC
+ 0: ABC
+ *** Failers
+No match
+ aaxabxbaxbbx
+No match
+ XBC
+No match
+ AXC
+No match
+ ABX
+No match
+
+/ab*c/i
+ ABC
+ 0: ABC
+
+/ab*bc/i
+ ABC
+ 0: ABC
+ ABBC
+ 0: ABBC
+
+/ab+bc/i
+ *** Failers
+No match
+ ABC
+No match
+ ABQ
+No match
+
+/ab+bc/i
+ ABBBBC
+ 0: ABBBBC
+
+/^abc$/i
+ ABC
+ 0: ABC
+ *** Failers
+No match
+ ABBBBC
+No match
+ ABCC
+No match
+
+/^abc/i
+ ABCC
+ 0: ABC
+
+/abc$/i
+ AABC
+ 0: ABC
+
+/^/i
+ ABC
+ 0:
+
+/$/i
+ ABC
+ 0:
+
+/a.c/i
+ ABC
+ 0: ABC
+ AXC
+ 0: AXC
+
+/a.*c/i
+ *** Failers
+No match
+ AABC
+ 0: AABC
+ AXYZD
+No match
+
+/a[bc]d/i
+ ABD
+ 0: ABD
+
+/a[b-d]e/i
+ ACE
+ 0: ACE
+ *** Failers
+No match
+ ABC
+No match
+ ABD
+No match
+
+/a[b-d]/i
+ AAC
+ 0: AC
+
+/a[-b]/i
+ A-
+ 0: A-
+
+/a[b-]/i
+ A-
+ 0: A-
+
+/a[]]b/i
+ A]B
+ 0: A]B
+
+/a[^bc]d/i
+ AED
+ 0: AED
+
+/a[^-b]c/i
+ ADC
+ 0: ADC
+ *** Failers
+No match
+ ABD
+No match
+ A-C
+No match
+
+/a[^]b]c/i
+ ADC
+ 0: ADC
+
+/ab|cd/i
+ ABC
+ 0: AB
+ ABCD
+ 0: AB
+
+/()ef/i
+ DEF
+ 0: EF
+ 1:
+
+/$b/i
+ *** Failers
+No match
+ A]C
+No match
+ B
+No match
+
+/a\(b/i
+ A(B
+ 0: A(B
+
+/a\(*b/i
+ AB
+ 0: AB
+ A((B
+ 0: A((B
+
+/((a))/i
+ ABC
+ 0: A
+ 1: A
+ 2: A
+
+/(a)b(c)/i
+ ABC
+ 0: ABC
+ 1: A
+ 2: C
+
+/a+b+c/i
+ AABBABC
+ 0: ABC
+
+/a{1,}b{1,}c/i
+ AABBABC
+ 0: ABC
+
+/(a+|b)*/i
+ AB
+ 0: AB
+ 1: B
+
+/(a+|b){0,}/i
+ AB
+ 0: AB
+ 1: B
+
+/(a+|b)+/i
+ AB
+ 0: AB
+ 1: B
+
+/(a+|b){1,}/i
+ AB
+ 0: AB
+ 1: B
+
+/(a+|b)?/i
+ AB
+ 0: A
+ 1: A
+
+/(a+|b){0,1}/i
+ AB
+ 0: A
+ 1: A
+
+/[^ab]*/i
+ CDE
+ 0: CDE
+
+/([abc])*d/i
+ ABBBCD
+ 0: ABBBCD
+ 1: C
+
+/([abc])*bcd/i
+ ABCD
+ 0: ABCD
+ 1: A
+
+/a|b|c|d|e/i
+ E
+ 0: E
+
+/(a|b|c|d|e)f/i
+ EF
+ 0: EF
+ 1: E
+
+/abcd*efg/i
+ ABCDEFG
+ 0: ABCDEFG
+
+/ab*/i
+ XABYABBBZ
+ 0: AB
+ XAYABBBZ
+ 0: A
+
+/(ab|cd)e/i
+ ABCDE
+ 0: CDE
+ 1: CD
+
+/[abhgefdc]ij/i
+ HIJ
+ 0: HIJ
+
+/^(ab|cd)e/i
+ ABCDE
+No match
+
+/(abc|)ef/i
+ ABCDEF
+ 0: EF
+ 1:
+
+/(a|b)c*d/i
+ ABCD
+ 0: BCD
+ 1: B
+
+/(ab|ab*)bc/i
+ ABC
+ 0: ABC
+ 1: A
+
+/a([bc]*)c*/i
+ ABC
+ 0: ABC
+ 1: BC
+
+/a([bc]*)(c*d)/i
+ ABCD
+ 0: ABCD
+ 1: BC
+ 2: D
+
+/a([bc]+)(c*d)/i
+ ABCD
+ 0: ABCD
+ 1: BC
+ 2: D
+
+/a([bc]*)(c+d)/i
+ ABCD
+ 0: ABCD
+ 1: B
+ 2: CD
+
+/a[bcd]*dcdcde/i
+ ADCDCDE
+ 0: ADCDCDE
+
+/a[bcd]+dcdcde/i
+
+/(ab|a)b*c/i
+ ABC
+ 0: ABC
+ 1: AB
+
+/((a)(b)c)(d)/i
+ ABCD
+ 0: ABCD
+ 1: ABC
+ 2: A
+ 3: B
+ 4: D
+
+/[a-zA-Z_][a-zA-Z0-9_]*/i
+ ALPHA
+ 0: ALPHA
+
+/^a(bc+|b[eh])g|.h$/i
+ ABH
+ 0: BH
+
+/(bc+d$|ef*g.|h?i(j|k))/i
+ EFFGZ
+ 0: EFFGZ
+ 1: EFFGZ
+ IJ
+ 0: IJ
+ 1: IJ
+ 2: J
+ REFFGZ
+ 0: EFFGZ
+ 1: EFFGZ
+ *** Failers
+No match
+ ADCDCDE
+No match
+ EFFG
+No match
+ BCDD
+No match
+
+/((((((((((a))))))))))/i
+ A
+ 0: A
+ 1: A
+ 2: A
+ 3: A
+ 4: A
+ 5: A
+ 6: A
+ 7: A
+ 8: A
+ 9: A
+10: A
+
+/((((((((((a))))))))))\9/i
+ AA
+ 0: AA
+ 1: A
+ 2: A
+ 3: A
+ 4: A
+ 5: A
+ 6: A
+ 7: A
+ 8: A
+ 9: A
+10: A
+
+/(((((((((a)))))))))/i
+ A
+ 0: A
+ 1: A
+ 2: A
+ 3: A
+ 4: A
+ 5: A
+ 6: A
+ 7: A
+ 8: A
+ 9: A
+
+/multiple words of text/i
+ *** Failers
+No match
+ AA
+No match
+ UH-UH
+No match
+
+/multiple words/i
+ MULTIPLE WORDS, YEAH
+ 0: MULTIPLE WORDS
+
+/(.*)c(.*)/i
+ ABCDE
+ 0: ABCDE
+ 1: AB
+ 2: DE
+
+/\((.*), (.*)\)/i
+ (A, B)
+ 0: (A, B)
+ 1: A
+ 2: B
+
+/abcd/i
+ ABCD
+ 0: ABCD
+
+/a(bc)d/i
+ ABCD
+ 0: ABCD
+ 1: BC
+
+/a[-]?c/i
+ AC
+ 0: AC
+
+/(abc)\1/i
+ ABCABC
+ 0: ABCABC
+ 1: ABC
+
+/([a-c]*)\1/i
+ ABCABC
+ 0: ABCABC
+ 1: ABC
+
+/((foo)|(bar))*/
+ foobar
+ 0: foobar
+ 1: bar
+ 2: foo
+ 3: bar
+
+/^(.+)?B/
+ AB
+ 0: AB
+ 1: A
+
+/^([^a-z])|(\^)$/
+ .
+ 0: .
+ 1: .
+
+/^[<>]&/
+ <&OUT
+ 0: <&
+
+/^(){3,5}/
+ abc
+ 0:
+ 1:
+
+/^(a+)*ax/
+ aax
+ 0: aax
+ 1: a
+
+/^((a|b)+)*ax/
+ aax
+ 0: aax
+ 1: a
+ 2: a
+
+/^((a|bc)+)*ax/
+ aax
+ 0: aax
+ 1: a
+ 2: a
+
+/(a|x)*ab/
+ cab
+ 0: ab
+
+/(a)*ab/
+ cab
+ 0: ab
+
+/(ab)[0-9]\1/i
+ Ab4ab
+ 0: Ab4ab
+ 1: Ab
+ ab4Ab
+ 0: ab4Ab
+ 1: ab
+
+/foo\w*[0-9]{4}baz/
+ foobar1234baz
+ 0: foobar1234baz
+
+/(\w+:)+/
+ one:
+ 0: one:
+ 1: one:
+
+/((\w|:)+::)?(\w+)$/
+ abcd
+ 0: abcd
+ 1: <unset>
+ 2: <unset>
+ 3: abcd
+ xy:z:::abcd
+ 0: xy:z:::abcd
+ 1: xy:z:::
+ 2: :
+ 3: abcd
+
+/^[^bcd]*(c+)/
+ aexycd
+ 0: aexyc
+ 1: c
+
+/(a*)b+/
+ caab
+ 0: aab
+ 1: aa
+
+/((\w|:)+::)?(\w+)$/
+ abcd
+ 0: abcd
+ 1: <unset>
+ 2: <unset>
+ 3: abcd
+ xy:z:::abcd
+ 0: xy:z:::abcd
+ 1: xy:z:::
+ 2: :
+ 3: abcd
+ *** Failers
+ 0: Failers
+ 1: <unset>
+ 2: <unset>
+ 3: Failers
+ abcd:
+No match
+ abcd:
+No match
+
+/^[^bcd]*(c+)/
+ aexycd
+ 0: aexyc
+ 1: c
+
+/((Z)+|A)*/
+ ZABCDEFG
+ 0: ZA
+ 1: A
+ 2: Z
+
+/(Z()|A)*/
+ ZABCDEFG
+ 0: ZA
+ 1: A
+ 2:
+
+/(Z(())|A)*/
+ ZABCDEFG
+ 0: ZA
+ 1: A
+ 2:
+ 3:
+
+/(.*)[0-9]+\1/
+ abc123abc
+ 0: abc123abc
+ 1: abc
+ abc123bc
+ 0: bc123bc
+ 1: bc
+
+/((.*))[0-9]+\1/
+ abc123abc
+ 0: abc123abc
+ 1: abc
+ 2: abc
+ abc123bc
+ 0: bc123bc
+ 1: bc
+ 2: bc
diff --git a/posix/tst-boost.c b/posix/tst-boost.c
new file mode 100644
index 0000000000..8446a2e54e
--- /dev/null
+++ b/posix/tst-boost.c
@@ -0,0 +1,227 @@
+/* Regular expression tests.
+ Copyright (C) 2003 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, write to the Free
+ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+ 02111-1307 USA. */
+
+#include <sys/types.h>
+#include <mcheck.h>
+#include <regex.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+void
+frob_escapes (char *src, int pattern)
+{
+ char *dst;
+
+ for (dst = src; *src != '\0'; dst++, src++)
+ {
+ if (*src == '\\')
+ {
+ switch (src[1])
+ {
+ case 't':
+ src++;
+ *dst = '\t';
+ continue;
+ case 'n':
+ src++;
+ *dst = '\n';
+ continue;
+ case 'r':
+ src++;
+ *dst = '\r';
+ continue;
+ case '\\':
+ case '^':
+ case '{':
+ case '|':
+ case '}':
+ if (!pattern)
+ {
+ src++;
+ *dst = *src;
+ continue;
+ }
+ break;
+ }
+ }
+ if (src != dst)
+ *dst = *src;
+ }
+ *dst = '\0';
+}
+
+int
+main (int argc, char **argv)
+{
+ int ret = 0, n;
+ char *line = NULL;
+ size_t line_len = 0;
+ ssize_t len;
+ FILE *f;
+ char *pattern, *string;
+ int flags = REG_EXTENDED;
+ int eflags = 0;
+ regex_t re;
+ regmatch_t rm[20];
+
+ mtrace ();
+
+ if (argc < 2)
+ {
+ fprintf (stderr, "Missing test filename\n");
+ return 1;
+ }
+
+ f = fopen (argv[1], "r");
+ if (f == NULL)
+ {
+ fprintf (stderr, "Couldn't open %s\n", argv[1]);
+ return 1;
+ }
+
+ while ((len = getline (&line, &line_len, f)) > 0)
+ {
+ char *p, *q;
+ int i;
+
+ if (line[len - 1] == '\n')
+ line[--len] = '\0';
+
+ puts (line);
+
+ if (line[0] == ';')
+ continue;
+
+ if (line[0] == '\0')
+ continue;
+
+ if (line[0] == '-')
+ {
+ if (strstr (line, "REG_BASIC"))
+ flags = 0;
+ else
+ flags = REG_EXTENDED;
+ if (strstr (line, "REG_ICASE"))
+ flags |= REG_ICASE;
+ if (strstr (line, "REG_NEWLINE"))
+ flags |= REG_NEWLINE;
+ eflags = 0;
+ if (strstr (line, "REG_NOTBOL"))
+ eflags |= REG_NOTBOL;
+ if (strstr (line, "REG_NOTEOL"))
+ eflags |= REG_NOTEOL;
+ continue;
+ }
+
+ pattern = line + strspn (line, " \t");
+ if (*pattern == '\0')
+ continue;
+ p = pattern + strcspn (pattern, " \t");
+ if (*p == '\0')
+ continue;
+ *p++ = '\0';
+
+ string = p + strspn (p, " \t");
+ if (*string == '\0')
+ continue;
+ if (*string == '"')
+ {
+ string++;
+ p = strchr (string, '"');
+ if (p == NULL)
+ continue;
+ *p++ = '\0';
+ }
+ else
+ {
+ p = string + strcspn (string, " \t");
+ if (*string == '!')
+ string = NULL;
+ else if (*p == '\0')
+ continue;
+ else
+ *p++ = '\0';
+ }
+
+ frob_escapes (pattern, 1);
+ if (string != NULL)
+ frob_escapes (string, 0);
+
+ n = regcomp (&re, pattern, flags);
+ if (n != 0)
+ {
+ if (string != NULL)
+ {
+ char buf[500];
+ regerror (n, &re, buf, sizeof (buf));
+ printf ("FAIL regcomp unexpectedly failed: %s\n",
+ buf);
+ ret = 1;
+ }
+ continue;
+ }
+ else if (string == NULL)
+ {
+ regfree (&re);
+ puts ("FAIL regcomp unpexpectedly succeeded");
+ ret = 1;
+ continue;
+ }
+
+ if (regexec (&re, string, 20, rm, eflags))
+ {
+ for (i = 0; i < 20; ++i)
+ {
+ rm[i].rm_so = -1;
+ rm[i].rm_eo = -1;
+ }
+ }
+
+ regfree (&re);
+
+ for (i = 0; i < 20 && *p != '\0'; ++i)
+ {
+ int rm_so, rm_eo;
+
+ rm_so = strtol (p, &q, 10);
+ if (p == q)
+ break;
+ p = q;
+
+ rm_eo = strtol (p, &q, 10);
+ if (p == q)
+ break;
+ p = q;
+
+ if (rm[i].rm_so != rm_so || rm[i].rm_eo != rm_eo)
+ {
+ printf ("FAIL rm[%d] %d..%d != expected %d..%d\n",
+ i, rm[i].rm_so, rm[i].rm_eo, rm_so, rm_eo);
+ ret = 1;
+ break;
+ }
+ }
+ }
+
+ free (line);
+ fclose (f);
+ return ret;
+}
diff --git a/posix/tst-pcre.c b/posix/tst-pcre.c
new file mode 100644
index 0000000000..3780a09454
--- /dev/null
+++ b/posix/tst-pcre.c
@@ -0,0 +1,241 @@
+/* Regular expression tests.
+ Copyright (C) 2003 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, write to the Free
+ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+ 02111-1307 USA. */
+
+#include <sys/types.h>
+#include <mcheck.h>
+#include <regex.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+int
+main (int argc, char **argv)
+{
+ int ret = 0;
+ char *line = NULL;
+ size_t line_len = 0;
+ ssize_t len;
+ FILE *f;
+ char *pattern = NULL, *string = NULL;
+ regmatch_t rm[20];
+ size_t pattern_alloced = 0, string_alloced = 0;
+ int ignorecase = 0;
+ int pattern_valid = 0, rm_valid = 0;
+ size_t linenum;
+
+ mtrace ();
+
+ if (argc < 2)
+ {
+ fprintf (stderr, "Missing test filename\n");
+ return 1;
+ }
+
+ f = fopen (argv[1], "r");
+ if (f == NULL)
+ {
+ fprintf (stderr, "Couldn't open %s\n", argv[1]);
+ return 1;
+ }
+
+ if ((len = getline (&line, &line_len, f)) <= 0
+ || strncmp (line, "# PCRE", 6) != 0)
+ {
+ fprintf (stderr, "Not a PCRE test file\n");
+ fclose (f);
+ free (line);
+ return 1;
+ }
+
+ linenum = 1;
+
+ while ((len = getline (&line, &line_len, f)) > 0)
+ {
+ char *p;
+ unsigned long num;
+
+ ++linenum;
+
+ if (line[len - 1] == '\n')
+ line[--len] = '\0';
+
+ if (line[0] == '#')
+ continue;
+
+ if (line[0] == '\0')
+ {
+ /* End of test. */
+ ignorecase = 0;
+ pattern_valid = 0;
+ rm_valid = 0;
+ continue;
+ }
+
+ if (line[0] == '/')
+ {
+ /* Pattern. */
+ p = strrchr (line + 1, '/');
+
+ pattern_valid = 0;
+ rm_valid = 0;
+ if (p == NULL)
+ {
+ printf ("%zd: Invalid pattern line: %s\n", linenum, line);
+ ret = 1;
+ continue;
+ }
+
+ if (p[1] == 'i' && p[2] == '\0')
+ ignorecase = 1;
+ else if (p[1] != '\0')
+ {
+ printf ("%zd: Invalid pattern line: %s\n", linenum, line);
+ ret = 1;
+ continue;
+ }
+
+ if (pattern_alloced < (size_t) (p - line))
+ {
+ pattern = realloc (pattern, p - line);
+ if (pattern == NULL)
+ {
+ printf ("%zd: Cannot record pattern: %m\n", linenum);
+ ret = 1;
+ break;
+ }
+ pattern_alloced = p - line;
+ }
+
+ memcpy (pattern, line + 1, p - line - 1);
+ pattern[p - line - 1] = '\0';
+ pattern_valid = 1;
+ continue;
+ }
+
+ if (strncmp (line, " ", 4) == 0)
+ {
+ regex_t re;
+ int n;
+
+ if (!pattern_valid)
+ {
+ printf ("%zd: No previous valid pattern %s\n", linenum, line);
+ continue;
+ }
+
+ if (string_alloced < (size_t) (len - 3))
+ {
+ string = realloc (string, len - 3);
+ if (string == NULL)
+ {
+ printf ("%zd: Cannot record search string: %m\n", linenum);
+ ret = 1;
+ break;
+ }
+ string_alloced = len - 3;
+ }
+
+ memcpy (string, line + 4, len - 3);
+
+ n = regcomp (&re, pattern,
+ REG_EXTENDED | (ignorecase ? REG_ICASE : 0));
+ if (n != 0)
+ {
+ char buf[500];
+ regerror (n, &re, buf, sizeof (buf));
+ printf ("%zd: regcomp failed for %s: %s\n",
+ linenum, pattern, buf);
+ ret = 1;
+ continue;
+ }
+
+ if (regexec (&re, string, 20, rm, 0))
+ {
+ rm[0].rm_so = -1;
+ rm[0].rm_eo = -1;
+ }
+
+ regfree (&re);
+ rm_valid = 1;
+ continue;
+ }
+
+ if (!rm_valid)
+ {
+ printf ("%zd: No preceeding pattern or search string\n", linenum);
+ ret = 1;
+ continue;
+ }
+
+ if (strcmp (line, "No match") == 0)
+ {
+ if (rm[0].rm_so != -1 || rm[0].rm_eo != -1)
+ {
+ printf ("%zd: /%s/ on %s unexpectedly matched %d..%d\n",
+ linenum, pattern, string, rm[0].rm_so, rm[0].rm_eo);
+ ret = 1;
+ }
+
+ continue;
+ }
+
+ p = line;
+ if (*p == ' ')
+ ++p;
+
+ num = strtoul (p, &p, 10);
+ if (num >= 20 || *p != ':' || p[1] != ' ')
+ {
+ printf ("%zd: Invalid line %s\n", linenum, line);
+ ret = 1;
+ continue;
+ }
+
+ if (rm[num].rm_so == -1 || rm[num].rm_eo == -1)
+ {
+ if (strcmp (p + 2, "<unset>") != 0)
+ {
+ printf ("%zd: /%s/ on %s unexpectedly failed to match register %ld %d..%d\n",
+ linenum, pattern, string, num,
+ rm[num].rm_so, rm[num].rm_eo);
+ ret = 1;
+ }
+ continue;
+ }
+
+ if (rm[num].rm_eo < rm[num].rm_so
+ || rm[num].rm_eo - rm[num].rm_so != len - (p + 2 - line)
+ || strncmp (p + 2, string + rm[num].rm_so,
+ rm[num].rm_eo - rm[num].rm_so) != 0)
+ {
+ printf ("%zd: /%s/ on %s unexpectedly failed to match %s for register %ld %d..%d\n",
+ linenum, pattern, string, p + 2, num,
+ rm[num].rm_so, rm[num].rm_eo);
+ ret = 1;
+ continue;
+ }
+ }
+
+ free (pattern);
+ free (string);
+ free (line);
+ fclose (f);
+ return ret;
+}