| 1 | #!./perl -w
|
|---|
| 2 |
|
|---|
| 3 | BEGIN {
|
|---|
| 4 | chdir 't' if -d 't';
|
|---|
| 5 | @INC = '../lib';
|
|---|
| 6 | }
|
|---|
| 7 |
|
|---|
| 8 | my $debug = 1;
|
|---|
| 9 |
|
|---|
| 10 | ##
|
|---|
| 11 | ## If the markers used are changed (search for "MARKER1" in regcomp.c),
|
|---|
| 12 | ## update only these two variables, and leave the {#} in the @death/@warning
|
|---|
| 13 | ## arrays below. The {#} is a meta-marker -- it marks where the marker should
|
|---|
| 14 | ## go.
|
|---|
| 15 |
|
|---|
| 16 | my $marker1 = "<-- HERE";
|
|---|
| 17 | my $marker2 = " <-- HERE ";
|
|---|
| 18 |
|
|---|
| 19 | ##
|
|---|
| 20 | ## Key-value pairs of code/error of code that should have fatal errors.
|
|---|
| 21 | ##
|
|---|
| 22 |
|
|---|
| 23 | eval 'use Config'; # assume defaults if fail
|
|---|
| 24 | our %Config;
|
|---|
| 25 | my $inf_m1 = ($Config{reg_infty} || 32767) - 1;
|
|---|
| 26 | my $inf_p1 = $inf_m1 + 2;
|
|---|
| 27 | my @death =
|
|---|
| 28 | (
|
|---|
| 29 | '/[[=foo=]]/' => 'POSIX syntax [= =] is reserved for future extensions in regex; marked by {#} in m/[[=foo=]{#}]/',
|
|---|
| 30 |
|
|---|
| 31 | '/(?<= .*)/' => 'Variable length lookbehind not implemented in regex; marked by {#} in m/(?<= .*){#}/',
|
|---|
| 32 |
|
|---|
| 33 | '/(?<= x{1000})/' => 'Lookbehind longer than 255 not implemented in regex; marked by {#} in m/(?<= x{1000}){#}/',
|
|---|
| 34 |
|
|---|
| 35 | '/(?@)/' => 'Sequence (?@...) not implemented in regex; marked by {#} in m/(?@{#})/',
|
|---|
| 36 |
|
|---|
| 37 | '/(?{ 1/' => 'Sequence (?{...}) not terminated or not {}-balanced in regex; marked by {#} in m/(?{{#} 1/',
|
|---|
| 38 |
|
|---|
| 39 | '/(?(1x))/' => 'Switch condition not recognized in regex; marked by {#} in m/(?(1x{#}))/',
|
|---|
| 40 |
|
|---|
| 41 | '/(?(1)x|y|z)/' => 'Switch (?(condition)... contains too many branches in regex; marked by {#} in m/(?(1)x|y|{#}z)/',
|
|---|
| 42 |
|
|---|
| 43 | '/(?(x)y|x)/' => 'Unknown switch condition (?(x) in regex; marked by {#} in m/(?({#}x)y|x)/',
|
|---|
| 44 |
|
|---|
| 45 | '/(?/' => 'Sequence (? incomplete in regex; marked by {#} in m/(?{#}/',
|
|---|
| 46 |
|
|---|
| 47 | '/(?;x/' => 'Sequence (?;...) not recognized in regex; marked by {#} in m/(?;{#}x/',
|
|---|
| 48 | '/(?<;x/' => 'Sequence (?<;...) not recognized in regex; marked by {#} in m/(?<;{#}x/',
|
|---|
| 49 |
|
|---|
| 50 | '/((x)/' => 'Unmatched ( in regex; marked by {#} in m/({#}(x)/',
|
|---|
| 51 |
|
|---|
| 52 | "/x{$inf_p1}/" => "Quantifier in {,} bigger than $inf_m1 in regex; marked by {#} in m/x{{#}$inf_p1}/",
|
|---|
| 53 |
|
|---|
| 54 | '/x{3,1}/' => 'Can\'t do {n,m} with n > m in regex; marked by {#} in m/x{3,1}{#}/',
|
|---|
| 55 |
|
|---|
| 56 | '/x**/' => 'Nested quantifiers in regex; marked by {#} in m/x**{#}/',
|
|---|
| 57 |
|
|---|
| 58 | '/x[/' => 'Unmatched [ in regex; marked by {#} in m/x[{#}/',
|
|---|
| 59 |
|
|---|
| 60 | '/*/', => 'Quantifier follows nothing in regex; marked by {#} in m/*{#}/',
|
|---|
| 61 |
|
|---|
| 62 | '/\p{x/' => 'Missing right brace on \p{} in regex; marked by {#} in m/\p{{#}x/',
|
|---|
| 63 |
|
|---|
| 64 | '/[\p{x]/' => 'Missing right brace on \p{} in regex; marked by {#} in m/[\p{{#}x]/',
|
|---|
| 65 |
|
|---|
| 66 | '/(x)\2/' => 'Reference to nonexistent group in regex; marked by {#} in m/(x)\2{#}/',
|
|---|
| 67 |
|
|---|
| 68 | 'my $m = "\\\"; $m =~ $m', => 'Trailing \ in regex m/\/',
|
|---|
| 69 |
|
|---|
| 70 | '/\x{1/' => 'Missing right brace on \x{} in regex; marked by {#} in m/\x{{#}1/',
|
|---|
| 71 |
|
|---|
| 72 | '/[\x{X]/' => 'Missing right brace on \x{} in regex; marked by {#} in m/[\x{{#}X]/',
|
|---|
| 73 |
|
|---|
| 74 | '/[[:barf:]]/' => 'POSIX class [:barf:] unknown in regex; marked by {#} in m/[[:barf:]{#}]/',
|
|---|
| 75 |
|
|---|
| 76 | '/[[=barf=]]/' => 'POSIX syntax [= =] is reserved for future extensions in regex; marked by {#} in m/[[=barf=]{#}]/',
|
|---|
| 77 |
|
|---|
| 78 | '/[[.barf.]]/' => 'POSIX syntax [. .] is reserved for future extensions in regex; marked by {#} in m/[[.barf.]{#}]/',
|
|---|
| 79 |
|
|---|
| 80 | '/[z-a]/' => 'Invalid [] range "z-a" in regex; marked by {#} in m/[z-a{#}]/',
|
|---|
| 81 |
|
|---|
| 82 | '/\p/' => 'Empty \p{} in regex; marked by {#} in m/\p{#}/',
|
|---|
| 83 |
|
|---|
| 84 | '/\P{}/' => 'Empty \P{} in regex; marked by {#} in m/\P{{#}}/',
|
|---|
| 85 | );
|
|---|
| 86 |
|
|---|
| 87 | ##
|
|---|
| 88 | ## Key-value pairs of code/error of code that should have non-fatal warnings.
|
|---|
| 89 | ##
|
|---|
| 90 | @warning = (
|
|---|
| 91 | "m/(?p{ 'a' })/" => "(?p{}) is deprecated - use (??{}) in regex; marked by {#} in m/(?p{#}{ 'a' })/",
|
|---|
| 92 |
|
|---|
| 93 | 'm/\b*/' => '\b* matches null string many times in regex; marked by {#} in m/\b*{#}/',
|
|---|
| 94 |
|
|---|
| 95 | 'm/[:blank:]/' => 'POSIX syntax [: :] belongs inside character classes in regex; marked by {#} in m/[:blank:]{#}/',
|
|---|
| 96 |
|
|---|
| 97 | "m'[\\y]'" => 'Unrecognized escape \y in character class passed through in regex; marked by {#} in m/[\y{#}]/',
|
|---|
| 98 |
|
|---|
| 99 | 'm/[a-\d]/' => 'False [] range "a-\d" in regex; marked by {#} in m/[a-\d{#}]/',
|
|---|
| 100 | 'm/[\w-x]/' => 'False [] range "\w-" in regex; marked by {#} in m/[\w-{#}x]/',
|
|---|
| 101 | 'm/[a-\pM]/' => 'False [] range "a-\pM" in regex; marked by {#} in m/[a-\pM{#}]/',
|
|---|
| 102 | 'm/[\pM-x]/' => 'False [] range "\pM-" in regex; marked by {#} in m/[\pM-{#}x]/',
|
|---|
| 103 | "m'\\y'" => 'Unrecognized escape \y passed through in regex; marked by {#} in m/\y{#}/',
|
|---|
| 104 | );
|
|---|
| 105 |
|
|---|
| 106 | my $total = (@death + @warning)/2;
|
|---|
| 107 |
|
|---|
| 108 | # utf8 is a noop on EBCDIC platforms, it is not fatal
|
|---|
| 109 | my $Is_EBCDIC = (ord('A') == 193);
|
|---|
| 110 | if ($Is_EBCDIC) {
|
|---|
| 111 | my @utf8_death = grep(/utf8/, @death);
|
|---|
| 112 | $total = $total - @utf8_death;
|
|---|
| 113 | }
|
|---|
| 114 |
|
|---|
| 115 | print "1..$total\n";
|
|---|
| 116 |
|
|---|
| 117 | my $count = 0;
|
|---|
| 118 |
|
|---|
| 119 | while (@death)
|
|---|
| 120 | {
|
|---|
| 121 | my $regex = shift @death;
|
|---|
| 122 | my $result = shift @death;
|
|---|
| 123 | # skip the utf8 test on EBCDIC since they do not die
|
|---|
| 124 | next if ($Is_EBCDIC && $regex =~ /utf8/);
|
|---|
| 125 | $count++;
|
|---|
| 126 |
|
|---|
| 127 | $_ = "x";
|
|---|
| 128 | eval $regex;
|
|---|
| 129 | if (not $@) {
|
|---|
| 130 | print "# oops, $regex didn't die\nnot ok $count\n";
|
|---|
| 131 | next;
|
|---|
| 132 | }
|
|---|
| 133 | chomp $@;
|
|---|
| 134 | $result =~ s/{\#}/$marker1/;
|
|---|
| 135 | $result =~ s/{\#}/$marker2/;
|
|---|
| 136 | $result .= " at ";
|
|---|
| 137 | if ($@ !~ /^\Q$result/) {
|
|---|
| 138 | print "# For $regex, expected:\n# $result\n# Got:\n# $@\n#\nnot ";
|
|---|
| 139 | }
|
|---|
| 140 | print "ok $count - $regex\n";
|
|---|
| 141 | }
|
|---|
| 142 |
|
|---|
| 143 |
|
|---|
| 144 | our $warning;
|
|---|
| 145 | $SIG{__WARN__} = sub { $warning = shift };
|
|---|
| 146 |
|
|---|
| 147 | while (@warning)
|
|---|
| 148 | {
|
|---|
| 149 | $count++;
|
|---|
| 150 | my $regex = shift @warning;
|
|---|
| 151 | my $result = shift @warning;
|
|---|
| 152 |
|
|---|
| 153 | undef $warning;
|
|---|
| 154 | $_ = "x";
|
|---|
| 155 | eval $regex;
|
|---|
| 156 |
|
|---|
| 157 | if ($@)
|
|---|
| 158 | {
|
|---|
| 159 | print "# oops, $regex died with:\n#\t$@#\nnot ok $count\n";
|
|---|
| 160 | next;
|
|---|
| 161 | }
|
|---|
| 162 |
|
|---|
| 163 | if (not $warning)
|
|---|
| 164 | {
|
|---|
| 165 | print "# oops, $regex didn't generate a warning\nnot ok $count\n";
|
|---|
| 166 | next;
|
|---|
| 167 | }
|
|---|
| 168 | $result =~ s/{\#}/$marker1/;
|
|---|
| 169 | $result =~ s/{\#}/$marker2/;
|
|---|
| 170 | $result .= " at ";
|
|---|
| 171 | if ($warning !~ /^\Q$result/)
|
|---|
| 172 | {
|
|---|
| 173 | print <<"EOM";
|
|---|
| 174 | # For $regex, expected:
|
|---|
| 175 | # $result
|
|---|
| 176 | # Got:
|
|---|
| 177 | # $warning
|
|---|
| 178 | #
|
|---|
| 179 | not ok $count
|
|---|
| 180 | EOM
|
|---|
| 181 | next;
|
|---|
| 182 | }
|
|---|
| 183 | print "ok $count - $regex\n";
|
|---|
| 184 | }
|
|---|
| 185 |
|
|---|
| 186 |
|
|---|
| 187 |
|
|---|