File Coverage

blib/lib/Eutf2.pm
Criterion Covered Total %
statement 1045 3228 32.3
branch 1095 2770 39.5
condition 122 355 34.3
subroutine 55 110 50.0
pod 7 74 9.4
total 2324 6537 35.5


line stmt bran cond sub pod time code
1             package Eutf2;
2 306     306   1792 use strict;
  306         1057  
  306         9357  
3             ######################################################################
4             #
5             # Eutf2 - Run-time routines for UTF2.pm
6             #
7             # http://search.cpan.org/dist/Char-UTF2/
8             #
9             # Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2018, 2019 INABA Hitoshi
10             ######################################################################
11              
12 306     306   4634 use 5.00503; # Galapagos Consensus 1998 for primetools
  306         858  
13             # use 5.008001; # Lancaster Consensus 2013 for toolchains
14              
15             # 12.3. Delaying use Until Runtime
16             # in Chapter 12. Packages, Libraries, and Modules
17             # of ISBN 0-596-00313-7 Perl Cookbook, 2nd Edition.
18             # (and so on)
19              
20             # Version numbers should be boring
21             # http://www.dagolden.com/index.php/369/version-numbers-should-be-boring/
22             # For the impatient, the disinterested or those who just want to follow
23             # a recipe, my advice for all modules is this:
24             # our $VERSION = "0.001"; # or "0.001_001" for a dev release
25             # $VERSION = eval $VERSION; # No!! because '1.10' makes '1.1'
26              
27 306     306   1533 use vars qw($VERSION);
  306         1864  
  306         43706  
28             $VERSION = '1.13';
29             $VERSION = $VERSION;
30              
31             BEGIN {
32 306 50   306   2420 if ($^X =~ / jperl /oxmsi) {
33 0         0 die __FILE__, ": needs perl(not jperl) 5.00503 or later. (\$^X==$^X)\n";
34             }
35 306         546 if (CORE::ord('A') == 193) {
36             die __FILE__, ": is not US-ASCII script (may be EBCDIC or EBCDIK script).\n";
37             }
38 306         41482 if (CORE::ord('A') != 0x41) {
39             die __FILE__, ": is not US-ASCII script (must be US-ASCII script).\n";
40             }
41             }
42              
43             BEGIN {
44              
45             # instead of utf8.pm
46 306     306   22752 CORE::eval q{
  306     306   1950  
  306     78   589  
  306         51351  
  0         0  
  0         0  
  0         0  
  0         0  
47             no warnings qw(redefine);
48             *utf8::upgrade = sub { CORE::length $_[0] };
49             *utf8::downgrade = sub { 1 };
50             *utf8::encode = sub { };
51             *utf8::decode = sub { 1 };
52             *utf8::is_utf8 = sub { };
53             *utf8::valid = sub { 1 };
54             };
55 306 50       137038 if ($@) {
56 0         0 *utf8::upgrade = sub { CORE::length $_[0] };
  0         0  
57 0         0 *utf8::downgrade = sub { 1 };
  0         0  
58 0         0 *utf8::encode = sub { };
59 0         0 *utf8::decode = sub { 1 };
  0         0  
60 0         0 *utf8::is_utf8 = sub { };
61 0         0 *utf8::valid = sub { 1 };
  0         0  
62             }
63             }
64              
65             # instead of Symbol.pm
66 0         0 BEGIN {
67             sub gensym () {
68 0     0 0 0 return \do { local *_ };
  0         0  
69             }
70              
71             sub qualify ($$) {
72 0     0 0 0 my($name) = @_;
73              
74 0 0       0 if (ref $name) {
    0          
    0          
    0          
    0          
    0          
    0          
75 0         0 return $name;
76             }
77             elsif (Eutf2::index($name,'::') >= 0) {
78 0         0 return $name;
79             }
80             elsif (Eutf2::index($name,"'") >= 0) {
81 0         0 return $name;
82             }
83              
84             # special character, "^xyz"
85             elsif ($name =~ /\A \^ [ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz_]+ \z/x) {
86              
87             # RGS 2001-11-05 : translate leading ^X to control-char
88 0         0 $name =~ s{\A \^ ([ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz_]) }{'qq(\c'.$1.')'}xee;
  0         0  
89 0         0 return 'main::' . $name;
90             }
91              
92             # Global names
93             elsif ($name =~ /\A (?: ARGV | ARGVOUT | ENV | INC | SIG | STDERR | STDIN | STDOUT ) \z/x) {
94 0         0 return 'main::' . $name;
95             }
96              
97             # or other
98             elsif ($name =~ /\A [^ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz] \z/x) {
99 0         0 return 'main::' . $name;
100             }
101              
102             elsif (defined $_[1]) {
103 0         0 return $_[1] . '::' . $name;
104             }
105             else {
106 0         0 return (caller)[0] . '::' . $name;
107             }
108             }
109              
110             sub qualify_to_ref ($;$) {
111 0 0   0 0 0 if (defined $_[1]) {
112 306     306   3168 no strict qw(refs);
  306         545  
  306         21526  
113 0         0 return \*{ qualify $_[0], $_[1] };
  0         0  
114             }
115             else {
116 306     306   1818 no strict qw(refs);
  306     0   529  
  306         58361  
117 0         0 return \*{ qualify $_[0], (caller)[0] };
  0         0  
118             }
119             }
120             }
121              
122             # P.714 29.2.39. flock
123             # in Chapter 29: Functions
124             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
125              
126             # P.863 flock
127             # in Chapter 27: Functions
128             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
129              
130             sub LOCK_SH() {1}
131             sub LOCK_EX() {2}
132             sub LOCK_UN() {8}
133             sub LOCK_NB() {4}
134              
135             # instead of Carp.pm
136             sub carp;
137             sub croak;
138             sub cluck;
139             sub confess;
140              
141             # 6.18. Matching Multiple-Byte Characters
142             # in Chapter 6. Pattern Matching
143             # of ISBN 978-1-56592-243-3 Perl Perl Cookbook.
144             # (and so on)
145              
146             # regexp of character
147             my $your_char = q{(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF]|[\x00-\x7F\xF5-\xFF]};
148 306     306   2039 use vars qw($qq_char); $qq_char = qr/\\c[\x40-\x5F]|\\?(?:$your_char)/oxms;
  306         587  
  306         21261  
149 306     306   2823 use vars qw($q_char); $q_char = qr/$your_char/oxms;
  306         556  
  306         3841929  
150              
151             #
152             # UTF-8 character range per length
153             #
154             my %range_tr = ();
155              
156             #
157             # UTF-8 case conversion
158             #
159             my %lc = ();
160             @lc{qw(A B C D E F G H I J K L M N O P Q R S T U V W X Y Z)} =
161             qw(a b c d e f g h i j k l m n o p q r s t u v w x y z);
162             my %uc = ();
163             @uc{qw(a b c d e f g h i j k l m n o p q r s t u v w x y z)} =
164             qw(A B C D E F G H I J K L M N O P Q R S T U V W X Y Z);
165             my %fc = ();
166             @fc{qw(A B C D E F G H I J K L M N O P Q R S T U V W X Y Z)} =
167             qw(a b c d e f g h i j k l m n o p q r s t u v w x y z);
168              
169             if (0) {
170             }
171              
172             elsif (__PACKAGE__ =~ / \b Eutf2 \z/oxms) {
173             %range_tr = (
174             1 => [ [0x00..0x7F],
175             [0xF5..0xFF], # malformed octet
176             ],
177             2 => [ [0xC2..0xDF],[0x80..0xBF],
178             ],
179             3 => [ [0xE0..0xE0],[0xA0..0xBF],[0x80..0xBF],
180             [0xE1..0xEC],[0x80..0xBF],[0x80..0xBF],
181             [0xED..0xED],[0x80..0x9F],[0x80..0xBF],
182             [0xEE..0xEF],[0x80..0xBF],[0x80..0xBF],
183             ],
184             4 => [ [0xF0..0xF0],[0x90..0xBF],[0x80..0xBF],[0x80..0xBF],
185             [0xF1..0xF3],[0x80..0xBF],[0x80..0xBF],[0x80..0xBF],
186             [0xF4..0xF4],[0x80..0x8F],[0x80..0xBF],[0x80..0xBF],
187             ],
188             );
189              
190             # CaseFolding-12.0.0.txt
191             # Date: 2019-01-22, 08:18:22 GMT
192             # c 2019 UnicodeR, Inc.
193             # Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries.
194             # For terms of use, see http://www.unicode.org/terms_of_use.html
195             #
196             # Unicode Character Database
197             # For documentation, see http://www.unicode.org/reports/tr44/
198              
199             # you can use "make_CaseFolding.pl" to update this hash
200              
201             %fc = (
202             "\x41" => "\x61", # LATIN CAPITAL LETTER A
203             "\x42" => "\x62", # LATIN CAPITAL LETTER B
204             "\x43" => "\x63", # LATIN CAPITAL LETTER C
205             "\x44" => "\x64", # LATIN CAPITAL LETTER D
206             "\x45" => "\x65", # LATIN CAPITAL LETTER E
207             "\x46" => "\x66", # LATIN CAPITAL LETTER F
208             "\x47" => "\x67", # LATIN CAPITAL LETTER G
209             "\x48" => "\x68", # LATIN CAPITAL LETTER H
210             "\x49" => "\x69", # LATIN CAPITAL LETTER I
211             "\x4A" => "\x6A", # LATIN CAPITAL LETTER J
212             "\x4B" => "\x6B", # LATIN CAPITAL LETTER K
213             "\x4C" => "\x6C", # LATIN CAPITAL LETTER L
214             "\x4D" => "\x6D", # LATIN CAPITAL LETTER M
215             "\x4E" => "\x6E", # LATIN CAPITAL LETTER N
216             "\x4F" => "\x6F", # LATIN CAPITAL LETTER O
217             "\x50" => "\x70", # LATIN CAPITAL LETTER P
218             "\x51" => "\x71", # LATIN CAPITAL LETTER Q
219             "\x52" => "\x72", # LATIN CAPITAL LETTER R
220             "\x53" => "\x73", # LATIN CAPITAL LETTER S
221             "\x54" => "\x74", # LATIN CAPITAL LETTER T
222             "\x55" => "\x75", # LATIN CAPITAL LETTER U
223             "\x56" => "\x76", # LATIN CAPITAL LETTER V
224             "\x57" => "\x77", # LATIN CAPITAL LETTER W
225             "\x58" => "\x78", # LATIN CAPITAL LETTER X
226             "\x59" => "\x79", # LATIN CAPITAL LETTER Y
227             "\x5A" => "\x7A", # LATIN CAPITAL LETTER Z
228             "\xC2\xB5" => "\xCE\xBC", # MICRO SIGN
229             "\xC3\x80" => "\xC3\xA0", # LATIN CAPITAL LETTER A WITH GRAVE
230             "\xC3\x81" => "\xC3\xA1", # LATIN CAPITAL LETTER A WITH ACUTE
231             "\xC3\x82" => "\xC3\xA2", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX
232             "\xC3\x83" => "\xC3\xA3", # LATIN CAPITAL LETTER A WITH TILDE
233             "\xC3\x84" => "\xC3\xA4", # LATIN CAPITAL LETTER A WITH DIAERESIS
234             "\xC3\x85" => "\xC3\xA5", # LATIN CAPITAL LETTER A WITH RING ABOVE
235             "\xC3\x86" => "\xC3\xA6", # LATIN CAPITAL LETTER AE
236             "\xC3\x87" => "\xC3\xA7", # LATIN CAPITAL LETTER C WITH CEDILLA
237             "\xC3\x88" => "\xC3\xA8", # LATIN CAPITAL LETTER E WITH GRAVE
238             "\xC3\x89" => "\xC3\xA9", # LATIN CAPITAL LETTER E WITH ACUTE
239             "\xC3\x8A" => "\xC3\xAA", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX
240             "\xC3\x8B" => "\xC3\xAB", # LATIN CAPITAL LETTER E WITH DIAERESIS
241             "\xC3\x8C" => "\xC3\xAC", # LATIN CAPITAL LETTER I WITH GRAVE
242             "\xC3\x8D" => "\xC3\xAD", # LATIN CAPITAL LETTER I WITH ACUTE
243             "\xC3\x8E" => "\xC3\xAE", # LATIN CAPITAL LETTER I WITH CIRCUMFLEX
244             "\xC3\x8F" => "\xC3\xAF", # LATIN CAPITAL LETTER I WITH DIAERESIS
245             "\xC3\x90" => "\xC3\xB0", # LATIN CAPITAL LETTER ETH
246             "\xC3\x91" => "\xC3\xB1", # LATIN CAPITAL LETTER N WITH TILDE
247             "\xC3\x92" => "\xC3\xB2", # LATIN CAPITAL LETTER O WITH GRAVE
248             "\xC3\x93" => "\xC3\xB3", # LATIN CAPITAL LETTER O WITH ACUTE
249             "\xC3\x94" => "\xC3\xB4", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX
250             "\xC3\x95" => "\xC3\xB5", # LATIN CAPITAL LETTER O WITH TILDE
251             "\xC3\x96" => "\xC3\xB6", # LATIN CAPITAL LETTER O WITH DIAERESIS
252             "\xC3\x98" => "\xC3\xB8", # LATIN CAPITAL LETTER O WITH STROKE
253             "\xC3\x99" => "\xC3\xB9", # LATIN CAPITAL LETTER U WITH GRAVE
254             "\xC3\x9A" => "\xC3\xBA", # LATIN CAPITAL LETTER U WITH ACUTE
255             "\xC3\x9B" => "\xC3\xBB", # LATIN CAPITAL LETTER U WITH CIRCUMFLEX
256             "\xC3\x9C" => "\xC3\xBC", # LATIN CAPITAL LETTER U WITH DIAERESIS
257             "\xC3\x9D" => "\xC3\xBD", # LATIN CAPITAL LETTER Y WITH ACUTE
258             "\xC3\x9E" => "\xC3\xBE", # LATIN CAPITAL LETTER THORN
259             "\xC3\x9F" => "\x73\x73", # LATIN SMALL LETTER SHARP S
260             "\xC4\x80" => "\xC4\x81", # LATIN CAPITAL LETTER A WITH MACRON
261             "\xC4\x82" => "\xC4\x83", # LATIN CAPITAL LETTER A WITH BREVE
262             "\xC4\x84" => "\xC4\x85", # LATIN CAPITAL LETTER A WITH OGONEK
263             "\xC4\x86" => "\xC4\x87", # LATIN CAPITAL LETTER C WITH ACUTE
264             "\xC4\x88" => "\xC4\x89", # LATIN CAPITAL LETTER C WITH CIRCUMFLEX
265             "\xC4\x8A" => "\xC4\x8B", # LATIN CAPITAL LETTER C WITH DOT ABOVE
266             "\xC4\x8C" => "\xC4\x8D", # LATIN CAPITAL LETTER C WITH CARON
267             "\xC4\x8E" => "\xC4\x8F", # LATIN CAPITAL LETTER D WITH CARON
268             "\xC4\x90" => "\xC4\x91", # LATIN CAPITAL LETTER D WITH STROKE
269             "\xC4\x92" => "\xC4\x93", # LATIN CAPITAL LETTER E WITH MACRON
270             "\xC4\x94" => "\xC4\x95", # LATIN CAPITAL LETTER E WITH BREVE
271             "\xC4\x96" => "\xC4\x97", # LATIN CAPITAL LETTER E WITH DOT ABOVE
272             "\xC4\x98" => "\xC4\x99", # LATIN CAPITAL LETTER E WITH OGONEK
273             "\xC4\x9A" => "\xC4\x9B", # LATIN CAPITAL LETTER E WITH CARON
274             "\xC4\x9C" => "\xC4\x9D", # LATIN CAPITAL LETTER G WITH CIRCUMFLEX
275             "\xC4\x9E" => "\xC4\x9F", # LATIN CAPITAL LETTER G WITH BREVE
276             "\xC4\xA0" => "\xC4\xA1", # LATIN CAPITAL LETTER G WITH DOT ABOVE
277             "\xC4\xA2" => "\xC4\xA3", # LATIN CAPITAL LETTER G WITH CEDILLA
278             "\xC4\xA4" => "\xC4\xA5", # LATIN CAPITAL LETTER H WITH CIRCUMFLEX
279             "\xC4\xA6" => "\xC4\xA7", # LATIN CAPITAL LETTER H WITH STROKE
280             "\xC4\xA8" => "\xC4\xA9", # LATIN CAPITAL LETTER I WITH TILDE
281             "\xC4\xAA" => "\xC4\xAB", # LATIN CAPITAL LETTER I WITH MACRON
282             "\xC4\xAC" => "\xC4\xAD", # LATIN CAPITAL LETTER I WITH BREVE
283             "\xC4\xAE" => "\xC4\xAF", # LATIN CAPITAL LETTER I WITH OGONEK
284             "\xC4\xB0" => "\x69\xCC\x87", # LATIN CAPITAL LETTER I WITH DOT ABOVE
285             "\xC4\xB2" => "\xC4\xB3", # LATIN CAPITAL LIGATURE IJ
286             "\xC4\xB4" => "\xC4\xB5", # LATIN CAPITAL LETTER J WITH CIRCUMFLEX
287             "\xC4\xB6" => "\xC4\xB7", # LATIN CAPITAL LETTER K WITH CEDILLA
288             "\xC4\xB9" => "\xC4\xBA", # LATIN CAPITAL LETTER L WITH ACUTE
289             "\xC4\xBB" => "\xC4\xBC", # LATIN CAPITAL LETTER L WITH CEDILLA
290             "\xC4\xBD" => "\xC4\xBE", # LATIN CAPITAL LETTER L WITH CARON
291             "\xC4\xBF" => "\xC5\x80", # LATIN CAPITAL LETTER L WITH MIDDLE DOT
292             "\xC5\x81" => "\xC5\x82", # LATIN CAPITAL LETTER L WITH STROKE
293             "\xC5\x83" => "\xC5\x84", # LATIN CAPITAL LETTER N WITH ACUTE
294             "\xC5\x85" => "\xC5\x86", # LATIN CAPITAL LETTER N WITH CEDILLA
295             "\xC5\x87" => "\xC5\x88", # LATIN CAPITAL LETTER N WITH CARON
296             "\xC5\x89" => "\xCA\xBC\x6E", # LATIN SMALL LETTER N PRECEDED BY APOSTROPHE
297             "\xC5\x8A" => "\xC5\x8B", # LATIN CAPITAL LETTER ENG
298             "\xC5\x8C" => "\xC5\x8D", # LATIN CAPITAL LETTER O WITH MACRON
299             "\xC5\x8E" => "\xC5\x8F", # LATIN CAPITAL LETTER O WITH BREVE
300             "\xC5\x90" => "\xC5\x91", # LATIN CAPITAL LETTER O WITH DOUBLE ACUTE
301             "\xC5\x92" => "\xC5\x93", # LATIN CAPITAL LIGATURE OE
302             "\xC5\x94" => "\xC5\x95", # LATIN CAPITAL LETTER R WITH ACUTE
303             "\xC5\x96" => "\xC5\x97", # LATIN CAPITAL LETTER R WITH CEDILLA
304             "\xC5\x98" => "\xC5\x99", # LATIN CAPITAL LETTER R WITH CARON
305             "\xC5\x9A" => "\xC5\x9B", # LATIN CAPITAL LETTER S WITH ACUTE
306             "\xC5\x9C" => "\xC5\x9D", # LATIN CAPITAL LETTER S WITH CIRCUMFLEX
307             "\xC5\x9E" => "\xC5\x9F", # LATIN CAPITAL LETTER S WITH CEDILLA
308             "\xC5\xA0" => "\xC5\xA1", # LATIN CAPITAL LETTER S WITH CARON
309             "\xC5\xA2" => "\xC5\xA3", # LATIN CAPITAL LETTER T WITH CEDILLA
310             "\xC5\xA4" => "\xC5\xA5", # LATIN CAPITAL LETTER T WITH CARON
311             "\xC5\xA6" => "\xC5\xA7", # LATIN CAPITAL LETTER T WITH STROKE
312             "\xC5\xA8" => "\xC5\xA9", # LATIN CAPITAL LETTER U WITH TILDE
313             "\xC5\xAA" => "\xC5\xAB", # LATIN CAPITAL LETTER U WITH MACRON
314             "\xC5\xAC" => "\xC5\xAD", # LATIN CAPITAL LETTER U WITH BREVE
315             "\xC5\xAE" => "\xC5\xAF", # LATIN CAPITAL LETTER U WITH RING ABOVE
316             "\xC5\xB0" => "\xC5\xB1", # LATIN CAPITAL LETTER U WITH DOUBLE ACUTE
317             "\xC5\xB2" => "\xC5\xB3", # LATIN CAPITAL LETTER U WITH OGONEK
318             "\xC5\xB4" => "\xC5\xB5", # LATIN CAPITAL LETTER W WITH CIRCUMFLEX
319             "\xC5\xB6" => "\xC5\xB7", # LATIN CAPITAL LETTER Y WITH CIRCUMFLEX
320             "\xC5\xB8" => "\xC3\xBF", # LATIN CAPITAL LETTER Y WITH DIAERESIS
321             "\xC5\xB9" => "\xC5\xBA", # LATIN CAPITAL LETTER Z WITH ACUTE
322             "\xC5\xBB" => "\xC5\xBC", # LATIN CAPITAL LETTER Z WITH DOT ABOVE
323             "\xC5\xBD" => "\xC5\xBE", # LATIN CAPITAL LETTER Z WITH CARON
324             "\xC5\xBF" => "\x73", # LATIN SMALL LETTER LONG S
325             "\xC6\x81" => "\xC9\x93", # LATIN CAPITAL LETTER B WITH HOOK
326             "\xC6\x82" => "\xC6\x83", # LATIN CAPITAL LETTER B WITH TOPBAR
327             "\xC6\x84" => "\xC6\x85", # LATIN CAPITAL LETTER TONE SIX
328             "\xC6\x86" => "\xC9\x94", # LATIN CAPITAL LETTER OPEN O
329             "\xC6\x87" => "\xC6\x88", # LATIN CAPITAL LETTER C WITH HOOK
330             "\xC6\x89" => "\xC9\x96", # LATIN CAPITAL LETTER AFRICAN D
331             "\xC6\x8A" => "\xC9\x97", # LATIN CAPITAL LETTER D WITH HOOK
332             "\xC6\x8B" => "\xC6\x8C", # LATIN CAPITAL LETTER D WITH TOPBAR
333             "\xC6\x8E" => "\xC7\x9D", # LATIN CAPITAL LETTER REVERSED E
334             "\xC6\x8F" => "\xC9\x99", # LATIN CAPITAL LETTER SCHWA
335             "\xC6\x90" => "\xC9\x9B", # LATIN CAPITAL LETTER OPEN E
336             "\xC6\x91" => "\xC6\x92", # LATIN CAPITAL LETTER F WITH HOOK
337             "\xC6\x93" => "\xC9\xA0", # LATIN CAPITAL LETTER G WITH HOOK
338             "\xC6\x94" => "\xC9\xA3", # LATIN CAPITAL LETTER GAMMA
339             "\xC6\x96" => "\xC9\xA9", # LATIN CAPITAL LETTER IOTA
340             "\xC6\x97" => "\xC9\xA8", # LATIN CAPITAL LETTER I WITH STROKE
341             "\xC6\x98" => "\xC6\x99", # LATIN CAPITAL LETTER K WITH HOOK
342             "\xC6\x9C" => "\xC9\xAF", # LATIN CAPITAL LETTER TURNED M
343             "\xC6\x9D" => "\xC9\xB2", # LATIN CAPITAL LETTER N WITH LEFT HOOK
344             "\xC6\x9F" => "\xC9\xB5", # LATIN CAPITAL LETTER O WITH MIDDLE TILDE
345             "\xC6\xA0" => "\xC6\xA1", # LATIN CAPITAL LETTER O WITH HORN
346             "\xC6\xA2" => "\xC6\xA3", # LATIN CAPITAL LETTER OI
347             "\xC6\xA4" => "\xC6\xA5", # LATIN CAPITAL LETTER P WITH HOOK
348             "\xC6\xA6" => "\xCA\x80", # LATIN LETTER YR
349             "\xC6\xA7" => "\xC6\xA8", # LATIN CAPITAL LETTER TONE TWO
350             "\xC6\xA9" => "\xCA\x83", # LATIN CAPITAL LETTER ESH
351             "\xC6\xAC" => "\xC6\xAD", # LATIN CAPITAL LETTER T WITH HOOK
352             "\xC6\xAE" => "\xCA\x88", # LATIN CAPITAL LETTER T WITH RETROFLEX HOOK
353             "\xC6\xAF" => "\xC6\xB0", # LATIN CAPITAL LETTER U WITH HORN
354             "\xC6\xB1" => "\xCA\x8A", # LATIN CAPITAL LETTER UPSILON
355             "\xC6\xB2" => "\xCA\x8B", # LATIN CAPITAL LETTER V WITH HOOK
356             "\xC6\xB3" => "\xC6\xB4", # LATIN CAPITAL LETTER Y WITH HOOK
357             "\xC6\xB5" => "\xC6\xB6", # LATIN CAPITAL LETTER Z WITH STROKE
358             "\xC6\xB7" => "\xCA\x92", # LATIN CAPITAL LETTER EZH
359             "\xC6\xB8" => "\xC6\xB9", # LATIN CAPITAL LETTER EZH REVERSED
360             "\xC6\xBC" => "\xC6\xBD", # LATIN CAPITAL LETTER TONE FIVE
361             "\xC7\x84" => "\xC7\x86", # LATIN CAPITAL LETTER DZ WITH CARON
362             "\xC7\x85" => "\xC7\x86", # LATIN CAPITAL LETTER D WITH SMALL LETTER Z WITH CARON
363             "\xC7\x87" => "\xC7\x89", # LATIN CAPITAL LETTER LJ
364             "\xC7\x88" => "\xC7\x89", # LATIN CAPITAL LETTER L WITH SMALL LETTER J
365             "\xC7\x8A" => "\xC7\x8C", # LATIN CAPITAL LETTER NJ
366             "\xC7\x8B" => "\xC7\x8C", # LATIN CAPITAL LETTER N WITH SMALL LETTER J
367             "\xC7\x8D" => "\xC7\x8E", # LATIN CAPITAL LETTER A WITH CARON
368             "\xC7\x8F" => "\xC7\x90", # LATIN CAPITAL LETTER I WITH CARON
369             "\xC7\x91" => "\xC7\x92", # LATIN CAPITAL LETTER O WITH CARON
370             "\xC7\x93" => "\xC7\x94", # LATIN CAPITAL LETTER U WITH CARON
371             "\xC7\x95" => "\xC7\x96", # LATIN CAPITAL LETTER U WITH DIAERESIS AND MACRON
372             "\xC7\x97" => "\xC7\x98", # LATIN CAPITAL LETTER U WITH DIAERESIS AND ACUTE
373             "\xC7\x99" => "\xC7\x9A", # LATIN CAPITAL LETTER U WITH DIAERESIS AND CARON
374             "\xC7\x9B" => "\xC7\x9C", # LATIN CAPITAL LETTER U WITH DIAERESIS AND GRAVE
375             "\xC7\x9E" => "\xC7\x9F", # LATIN CAPITAL LETTER A WITH DIAERESIS AND MACRON
376             "\xC7\xA0" => "\xC7\xA1", # LATIN CAPITAL LETTER A WITH DOT ABOVE AND MACRON
377             "\xC7\xA2" => "\xC7\xA3", # LATIN CAPITAL LETTER AE WITH MACRON
378             "\xC7\xA4" => "\xC7\xA5", # LATIN CAPITAL LETTER G WITH STROKE
379             "\xC7\xA6" => "\xC7\xA7", # LATIN CAPITAL LETTER G WITH CARON
380             "\xC7\xA8" => "\xC7\xA9", # LATIN CAPITAL LETTER K WITH CARON
381             "\xC7\xAA" => "\xC7\xAB", # LATIN CAPITAL LETTER O WITH OGONEK
382             "\xC7\xAC" => "\xC7\xAD", # LATIN CAPITAL LETTER O WITH OGONEK AND MACRON
383             "\xC7\xAE" => "\xC7\xAF", # LATIN CAPITAL LETTER EZH WITH CARON
384             "\xC7\xB0" => "\x6A\xCC\x8C", # LATIN SMALL LETTER J WITH CARON
385             "\xC7\xB1" => "\xC7\xB3", # LATIN CAPITAL LETTER DZ
386             "\xC7\xB2" => "\xC7\xB3", # LATIN CAPITAL LETTER D WITH SMALL LETTER Z
387             "\xC7\xB4" => "\xC7\xB5", # LATIN CAPITAL LETTER G WITH ACUTE
388             "\xC7\xB6" => "\xC6\x95", # LATIN CAPITAL LETTER HWAIR
389             "\xC7\xB7" => "\xC6\xBF", # LATIN CAPITAL LETTER WYNN
390             "\xC7\xB8" => "\xC7\xB9", # LATIN CAPITAL LETTER N WITH GRAVE
391             "\xC7\xBA" => "\xC7\xBB", # LATIN CAPITAL LETTER A WITH RING ABOVE AND ACUTE
392             "\xC7\xBC" => "\xC7\xBD", # LATIN CAPITAL LETTER AE WITH ACUTE
393             "\xC7\xBE" => "\xC7\xBF", # LATIN CAPITAL LETTER O WITH STROKE AND ACUTE
394             "\xC8\x80" => "\xC8\x81", # LATIN CAPITAL LETTER A WITH DOUBLE GRAVE
395             "\xC8\x82" => "\xC8\x83", # LATIN CAPITAL LETTER A WITH INVERTED BREVE
396             "\xC8\x84" => "\xC8\x85", # LATIN CAPITAL LETTER E WITH DOUBLE GRAVE
397             "\xC8\x86" => "\xC8\x87", # LATIN CAPITAL LETTER E WITH INVERTED BREVE
398             "\xC8\x88" => "\xC8\x89", # LATIN CAPITAL LETTER I WITH DOUBLE GRAVE
399             "\xC8\x8A" => "\xC8\x8B", # LATIN CAPITAL LETTER I WITH INVERTED BREVE
400             "\xC8\x8C" => "\xC8\x8D", # LATIN CAPITAL LETTER O WITH DOUBLE GRAVE
401             "\xC8\x8E" => "\xC8\x8F", # LATIN CAPITAL LETTER O WITH INVERTED BREVE
402             "\xC8\x90" => "\xC8\x91", # LATIN CAPITAL LETTER R WITH DOUBLE GRAVE
403             "\xC8\x92" => "\xC8\x93", # LATIN CAPITAL LETTER R WITH INVERTED BREVE
404             "\xC8\x94" => "\xC8\x95", # LATIN CAPITAL LETTER U WITH DOUBLE GRAVE
405             "\xC8\x96" => "\xC8\x97", # LATIN CAPITAL LETTER U WITH INVERTED BREVE
406             "\xC8\x98" => "\xC8\x99", # LATIN CAPITAL LETTER S WITH COMMA BELOW
407             "\xC8\x9A" => "\xC8\x9B", # LATIN CAPITAL LETTER T WITH COMMA BELOW
408             "\xC8\x9C" => "\xC8\x9D", # LATIN CAPITAL LETTER YOGH
409             "\xC8\x9E" => "\xC8\x9F", # LATIN CAPITAL LETTER H WITH CARON
410             "\xC8\xA0" => "\xC6\x9E", # LATIN CAPITAL LETTER N WITH LONG RIGHT LEG
411             "\xC8\xA2" => "\xC8\xA3", # LATIN CAPITAL LETTER OU
412             "\xC8\xA4" => "\xC8\xA5", # LATIN CAPITAL LETTER Z WITH HOOK
413             "\xC8\xA6" => "\xC8\xA7", # LATIN CAPITAL LETTER A WITH DOT ABOVE
414             "\xC8\xA8" => "\xC8\xA9", # LATIN CAPITAL LETTER E WITH CEDILLA
415             "\xC8\xAA" => "\xC8\xAB", # LATIN CAPITAL LETTER O WITH DIAERESIS AND MACRON
416             "\xC8\xAC" => "\xC8\xAD", # LATIN CAPITAL LETTER O WITH TILDE AND MACRON
417             "\xC8\xAE" => "\xC8\xAF", # LATIN CAPITAL LETTER O WITH DOT ABOVE
418             "\xC8\xB0" => "\xC8\xB1", # LATIN CAPITAL LETTER O WITH DOT ABOVE AND MACRON
419             "\xC8\xB2" => "\xC8\xB3", # LATIN CAPITAL LETTER Y WITH MACRON
420             "\xC8\xBA" => "\xE2\xB1\xA5", # LATIN CAPITAL LETTER A WITH STROKE
421             "\xC8\xBB" => "\xC8\xBC", # LATIN CAPITAL LETTER C WITH STROKE
422             "\xC8\xBD" => "\xC6\x9A", # LATIN CAPITAL LETTER L WITH BAR
423             "\xC8\xBE" => "\xE2\xB1\xA6", # LATIN CAPITAL LETTER T WITH DIAGONAL STROKE
424             "\xC9\x81" => "\xC9\x82", # LATIN CAPITAL LETTER GLOTTAL STOP
425             "\xC9\x83" => "\xC6\x80", # LATIN CAPITAL LETTER B WITH STROKE
426             "\xC9\x84" => "\xCA\x89", # LATIN CAPITAL LETTER U BAR
427             "\xC9\x85" => "\xCA\x8C", # LATIN CAPITAL LETTER TURNED V
428             "\xC9\x86" => "\xC9\x87", # LATIN CAPITAL LETTER E WITH STROKE
429             "\xC9\x88" => "\xC9\x89", # LATIN CAPITAL LETTER J WITH STROKE
430             "\xC9\x8A" => "\xC9\x8B", # LATIN CAPITAL LETTER SMALL Q WITH HOOK TAIL
431             "\xC9\x8C" => "\xC9\x8D", # LATIN CAPITAL LETTER R WITH STROKE
432             "\xC9\x8E" => "\xC9\x8F", # LATIN CAPITAL LETTER Y WITH STROKE
433             "\xCD\x85" => "\xCE\xB9", # COMBINING GREEK YPOGEGRAMMENI
434             "\xCD\xB0" => "\xCD\xB1", # GREEK CAPITAL LETTER HETA
435             "\xCD\xB2" => "\xCD\xB3", # GREEK CAPITAL LETTER ARCHAIC SAMPI
436             "\xCD\xB6" => "\xCD\xB7", # GREEK CAPITAL LETTER PAMPHYLIAN DIGAMMA
437             "\xCD\xBF" => "\xCF\xB3", # GREEK CAPITAL LETTER YOT
438             "\xCE\x86" => "\xCE\xAC", # GREEK CAPITAL LETTER ALPHA WITH TONOS
439             "\xCE\x88" => "\xCE\xAD", # GREEK CAPITAL LETTER EPSILON WITH TONOS
440             "\xCE\x89" => "\xCE\xAE", # GREEK CAPITAL LETTER ETA WITH TONOS
441             "\xCE\x8A" => "\xCE\xAF", # GREEK CAPITAL LETTER IOTA WITH TONOS
442             "\xCE\x8C" => "\xCF\x8C", # GREEK CAPITAL LETTER OMICRON WITH TONOS
443             "\xCE\x8E" => "\xCF\x8D", # GREEK CAPITAL LETTER UPSILON WITH TONOS
444             "\xCE\x8F" => "\xCF\x8E", # GREEK CAPITAL LETTER OMEGA WITH TONOS
445             "\xCE\x90" => "\xCE\xB9\xCC\x88\xCC\x81", # GREEK SMALL LETTER IOTA WITH DIALYTIKA AND TONOS
446             "\xCE\x91" => "\xCE\xB1", # GREEK CAPITAL LETTER ALPHA
447             "\xCE\x92" => "\xCE\xB2", # GREEK CAPITAL LETTER BETA
448             "\xCE\x93" => "\xCE\xB3", # GREEK CAPITAL LETTER GAMMA
449             "\xCE\x94" => "\xCE\xB4", # GREEK CAPITAL LETTER DELTA
450             "\xCE\x95" => "\xCE\xB5", # GREEK CAPITAL LETTER EPSILON
451             "\xCE\x96" => "\xCE\xB6", # GREEK CAPITAL LETTER ZETA
452             "\xCE\x97" => "\xCE\xB7", # GREEK CAPITAL LETTER ETA
453             "\xCE\x98" => "\xCE\xB8", # GREEK CAPITAL LETTER THETA
454             "\xCE\x99" => "\xCE\xB9", # GREEK CAPITAL LETTER IOTA
455             "\xCE\x9A" => "\xCE\xBA", # GREEK CAPITAL LETTER KAPPA
456             "\xCE\x9B" => "\xCE\xBB", # GREEK CAPITAL LETTER LAMDA
457             "\xCE\x9C" => "\xCE\xBC", # GREEK CAPITAL LETTER MU
458             "\xCE\x9D" => "\xCE\xBD", # GREEK CAPITAL LETTER NU
459             "\xCE\x9E" => "\xCE\xBE", # GREEK CAPITAL LETTER XI
460             "\xCE\x9F" => "\xCE\xBF", # GREEK CAPITAL LETTER OMICRON
461             "\xCE\xA0" => "\xCF\x80", # GREEK CAPITAL LETTER PI
462             "\xCE\xA1" => "\xCF\x81", # GREEK CAPITAL LETTER RHO
463             "\xCE\xA3" => "\xCF\x83", # GREEK CAPITAL LETTER SIGMA
464             "\xCE\xA4" => "\xCF\x84", # GREEK CAPITAL LETTER TAU
465             "\xCE\xA5" => "\xCF\x85", # GREEK CAPITAL LETTER UPSILON
466             "\xCE\xA6" => "\xCF\x86", # GREEK CAPITAL LETTER PHI
467             "\xCE\xA7" => "\xCF\x87", # GREEK CAPITAL LETTER CHI
468             "\xCE\xA8" => "\xCF\x88", # GREEK CAPITAL LETTER PSI
469             "\xCE\xA9" => "\xCF\x89", # GREEK CAPITAL LETTER OMEGA
470             "\xCE\xAA" => "\xCF\x8A", # GREEK CAPITAL LETTER IOTA WITH DIALYTIKA
471             "\xCE\xAB" => "\xCF\x8B", # GREEK CAPITAL LETTER UPSILON WITH DIALYTIKA
472             "\xCE\xB0" => "\xCF\x85\xCC\x88\xCC\x81", # GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND TONOS
473             "\xCF\x82" => "\xCF\x83", # GREEK SMALL LETTER FINAL SIGMA
474             "\xCF\x8F" => "\xCF\x97", # GREEK CAPITAL KAI SYMBOL
475             "\xCF\x90" => "\xCE\xB2", # GREEK BETA SYMBOL
476             "\xCF\x91" => "\xCE\xB8", # GREEK THETA SYMBOL
477             "\xCF\x95" => "\xCF\x86", # GREEK PHI SYMBOL
478             "\xCF\x96" => "\xCF\x80", # GREEK PI SYMBOL
479             "\xCF\x98" => "\xCF\x99", # GREEK LETTER ARCHAIC KOPPA
480             "\xCF\x9A" => "\xCF\x9B", # GREEK LETTER STIGMA
481             "\xCF\x9C" => "\xCF\x9D", # GREEK LETTER DIGAMMA
482             "\xCF\x9E" => "\xCF\x9F", # GREEK LETTER KOPPA
483             "\xCF\xA0" => "\xCF\xA1", # GREEK LETTER SAMPI
484             "\xCF\xA2" => "\xCF\xA3", # COPTIC CAPITAL LETTER SHEI
485             "\xCF\xA4" => "\xCF\xA5", # COPTIC CAPITAL LETTER FEI
486             "\xCF\xA6" => "\xCF\xA7", # COPTIC CAPITAL LETTER KHEI
487             "\xCF\xA8" => "\xCF\xA9", # COPTIC CAPITAL LETTER HORI
488             "\xCF\xAA" => "\xCF\xAB", # COPTIC CAPITAL LETTER GANGIA
489             "\xCF\xAC" => "\xCF\xAD", # COPTIC CAPITAL LETTER SHIMA
490             "\xCF\xAE" => "\xCF\xAF", # COPTIC CAPITAL LETTER DEI
491             "\xCF\xB0" => "\xCE\xBA", # GREEK KAPPA SYMBOL
492             "\xCF\xB1" => "\xCF\x81", # GREEK RHO SYMBOL
493             "\xCF\xB4" => "\xCE\xB8", # GREEK CAPITAL THETA SYMBOL
494             "\xCF\xB5" => "\xCE\xB5", # GREEK LUNATE EPSILON SYMBOL
495             "\xCF\xB7" => "\xCF\xB8", # GREEK CAPITAL LETTER SHO
496             "\xCF\xB9" => "\xCF\xB2", # GREEK CAPITAL LUNATE SIGMA SYMBOL
497             "\xCF\xBA" => "\xCF\xBB", # GREEK CAPITAL LETTER SAN
498             "\xCF\xBD" => "\xCD\xBB", # GREEK CAPITAL REVERSED LUNATE SIGMA SYMBOL
499             "\xCF\xBE" => "\xCD\xBC", # GREEK CAPITAL DOTTED LUNATE SIGMA SYMBOL
500             "\xCF\xBF" => "\xCD\xBD", # GREEK CAPITAL REVERSED DOTTED LUNATE SIGMA SYMBOL
501             "\xD0\x80" => "\xD1\x90", # CYRILLIC CAPITAL LETTER IE WITH GRAVE
502             "\xD0\x81" => "\xD1\x91", # CYRILLIC CAPITAL LETTER IO
503             "\xD0\x82" => "\xD1\x92", # CYRILLIC CAPITAL LETTER DJE
504             "\xD0\x83" => "\xD1\x93", # CYRILLIC CAPITAL LETTER GJE
505             "\xD0\x84" => "\xD1\x94", # CYRILLIC CAPITAL LETTER UKRAINIAN IE
506             "\xD0\x85" => "\xD1\x95", # CYRILLIC CAPITAL LETTER DZE
507             "\xD0\x86" => "\xD1\x96", # CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I
508             "\xD0\x87" => "\xD1\x97", # CYRILLIC CAPITAL LETTER YI
509             "\xD0\x88" => "\xD1\x98", # CYRILLIC CAPITAL LETTER JE
510             "\xD0\x89" => "\xD1\x99", # CYRILLIC CAPITAL LETTER LJE
511             "\xD0\x8A" => "\xD1\x9A", # CYRILLIC CAPITAL LETTER NJE
512             "\xD0\x8B" => "\xD1\x9B", # CYRILLIC CAPITAL LETTER TSHE
513             "\xD0\x8C" => "\xD1\x9C", # CYRILLIC CAPITAL LETTER KJE
514             "\xD0\x8D" => "\xD1\x9D", # CYRILLIC CAPITAL LETTER I WITH GRAVE
515             "\xD0\x8E" => "\xD1\x9E", # CYRILLIC CAPITAL LETTER SHORT U
516             "\xD0\x8F" => "\xD1\x9F", # CYRILLIC CAPITAL LETTER DZHE
517             "\xD0\x90" => "\xD0\xB0", # CYRILLIC CAPITAL LETTER A
518             "\xD0\x91" => "\xD0\xB1", # CYRILLIC CAPITAL LETTER BE
519             "\xD0\x92" => "\xD0\xB2", # CYRILLIC CAPITAL LETTER VE
520             "\xD0\x93" => "\xD0\xB3", # CYRILLIC CAPITAL LETTER GHE
521             "\xD0\x94" => "\xD0\xB4", # CYRILLIC CAPITAL LETTER DE
522             "\xD0\x95" => "\xD0\xB5", # CYRILLIC CAPITAL LETTER IE
523             "\xD0\x96" => "\xD0\xB6", # CYRILLIC CAPITAL LETTER ZHE
524             "\xD0\x97" => "\xD0\xB7", # CYRILLIC CAPITAL LETTER ZE
525             "\xD0\x98" => "\xD0\xB8", # CYRILLIC CAPITAL LETTER I
526             "\xD0\x99" => "\xD0\xB9", # CYRILLIC CAPITAL LETTER SHORT I
527             "\xD0\x9A" => "\xD0\xBA", # CYRILLIC CAPITAL LETTER KA
528             "\xD0\x9B" => "\xD0\xBB", # CYRILLIC CAPITAL LETTER EL
529             "\xD0\x9C" => "\xD0\xBC", # CYRILLIC CAPITAL LETTER EM
530             "\xD0\x9D" => "\xD0\xBD", # CYRILLIC CAPITAL LETTER EN
531             "\xD0\x9E" => "\xD0\xBE", # CYRILLIC CAPITAL LETTER O
532             "\xD0\x9F" => "\xD0\xBF", # CYRILLIC CAPITAL LETTER PE
533             "\xD0\xA0" => "\xD1\x80", # CYRILLIC CAPITAL LETTER ER
534             "\xD0\xA1" => "\xD1\x81", # CYRILLIC CAPITAL LETTER ES
535             "\xD0\xA2" => "\xD1\x82", # CYRILLIC CAPITAL LETTER TE
536             "\xD0\xA3" => "\xD1\x83", # CYRILLIC CAPITAL LETTER U
537             "\xD0\xA4" => "\xD1\x84", # CYRILLIC CAPITAL LETTER EF
538             "\xD0\xA5" => "\xD1\x85", # CYRILLIC CAPITAL LETTER HA
539             "\xD0\xA6" => "\xD1\x86", # CYRILLIC CAPITAL LETTER TSE
540             "\xD0\xA7" => "\xD1\x87", # CYRILLIC CAPITAL LETTER CHE
541             "\xD0\xA8" => "\xD1\x88", # CYRILLIC CAPITAL LETTER SHA
542             "\xD0\xA9" => "\xD1\x89", # CYRILLIC CAPITAL LETTER SHCHA
543             "\xD0\xAA" => "\xD1\x8A", # CYRILLIC CAPITAL LETTER HARD SIGN
544             "\xD0\xAB" => "\xD1\x8B", # CYRILLIC CAPITAL LETTER YERU
545             "\xD0\xAC" => "\xD1\x8C", # CYRILLIC CAPITAL LETTER SOFT SIGN
546             "\xD0\xAD" => "\xD1\x8D", # CYRILLIC CAPITAL LETTER E
547             "\xD0\xAE" => "\xD1\x8E", # CYRILLIC CAPITAL LETTER YU
548             "\xD0\xAF" => "\xD1\x8F", # CYRILLIC CAPITAL LETTER YA
549             "\xD1\xA0" => "\xD1\xA1", # CYRILLIC CAPITAL LETTER OMEGA
550             "\xD1\xA2" => "\xD1\xA3", # CYRILLIC CAPITAL LETTER YAT
551             "\xD1\xA4" => "\xD1\xA5", # CYRILLIC CAPITAL LETTER IOTIFIED E
552             "\xD1\xA6" => "\xD1\xA7", # CYRILLIC CAPITAL LETTER LITTLE YUS
553             "\xD1\xA8" => "\xD1\xA9", # CYRILLIC CAPITAL LETTER IOTIFIED LITTLE YUS
554             "\xD1\xAA" => "\xD1\xAB", # CYRILLIC CAPITAL LETTER BIG YUS
555             "\xD1\xAC" => "\xD1\xAD", # CYRILLIC CAPITAL LETTER IOTIFIED BIG YUS
556             "\xD1\xAE" => "\xD1\xAF", # CYRILLIC CAPITAL LETTER KSI
557             "\xD1\xB0" => "\xD1\xB1", # CYRILLIC CAPITAL LETTER PSI
558             "\xD1\xB2" => "\xD1\xB3", # CYRILLIC CAPITAL LETTER FITA
559             "\xD1\xB4" => "\xD1\xB5", # CYRILLIC CAPITAL LETTER IZHITSA
560             "\xD1\xB6" => "\xD1\xB7", # CYRILLIC CAPITAL LETTER IZHITSA WITH DOUBLE GRAVE ACCENT
561             "\xD1\xB8" => "\xD1\xB9", # CYRILLIC CAPITAL LETTER UK
562             "\xD1\xBA" => "\xD1\xBB", # CYRILLIC CAPITAL LETTER ROUND OMEGA
563             "\xD1\xBC" => "\xD1\xBD", # CYRILLIC CAPITAL LETTER OMEGA WITH TITLO
564             "\xD1\xBE" => "\xD1\xBF", # CYRILLIC CAPITAL LETTER OT
565             "\xD2\x80" => "\xD2\x81", # CYRILLIC CAPITAL LETTER KOPPA
566             "\xD2\x8A" => "\xD2\x8B", # CYRILLIC CAPITAL LETTER SHORT I WITH TAIL
567             "\xD2\x8C" => "\xD2\x8D", # CYRILLIC CAPITAL LETTER SEMISOFT SIGN
568             "\xD2\x8E" => "\xD2\x8F", # CYRILLIC CAPITAL LETTER ER WITH TICK
569             "\xD2\x90" => "\xD2\x91", # CYRILLIC CAPITAL LETTER GHE WITH UPTURN
570             "\xD2\x92" => "\xD2\x93", # CYRILLIC CAPITAL LETTER GHE WITH STROKE
571             "\xD2\x94" => "\xD2\x95", # CYRILLIC CAPITAL LETTER GHE WITH MIDDLE HOOK
572             "\xD2\x96" => "\xD2\x97", # CYRILLIC CAPITAL LETTER ZHE WITH DESCENDER
573             "\xD2\x98" => "\xD2\x99", # CYRILLIC CAPITAL LETTER ZE WITH DESCENDER
574             "\xD2\x9A" => "\xD2\x9B", # CYRILLIC CAPITAL LETTER KA WITH DESCENDER
575             "\xD2\x9C" => "\xD2\x9D", # CYRILLIC CAPITAL LETTER KA WITH VERTICAL STROKE
576             "\xD2\x9E" => "\xD2\x9F", # CYRILLIC CAPITAL LETTER KA WITH STROKE
577             "\xD2\xA0" => "\xD2\xA1", # CYRILLIC CAPITAL LETTER BASHKIR KA
578             "\xD2\xA2" => "\xD2\xA3", # CYRILLIC CAPITAL LETTER EN WITH DESCENDER
579             "\xD2\xA4" => "\xD2\xA5", # CYRILLIC CAPITAL LIGATURE EN GHE
580             "\xD2\xA6" => "\xD2\xA7", # CYRILLIC CAPITAL LETTER PE WITH MIDDLE HOOK
581             "\xD2\xA8" => "\xD2\xA9", # CYRILLIC CAPITAL LETTER ABKHASIAN HA
582             "\xD2\xAA" => "\xD2\xAB", # CYRILLIC CAPITAL LETTER ES WITH DESCENDER
583             "\xD2\xAC" => "\xD2\xAD", # CYRILLIC CAPITAL LETTER TE WITH DESCENDER
584             "\xD2\xAE" => "\xD2\xAF", # CYRILLIC CAPITAL LETTER STRAIGHT U
585             "\xD2\xB0" => "\xD2\xB1", # CYRILLIC CAPITAL LETTER STRAIGHT U WITH STROKE
586             "\xD2\xB2" => "\xD2\xB3", # CYRILLIC CAPITAL LETTER HA WITH DESCENDER
587             "\xD2\xB4" => "\xD2\xB5", # CYRILLIC CAPITAL LIGATURE TE TSE
588             "\xD2\xB6" => "\xD2\xB7", # CYRILLIC CAPITAL LETTER CHE WITH DESCENDER
589             "\xD2\xB8" => "\xD2\xB9", # CYRILLIC CAPITAL LETTER CHE WITH VERTICAL STROKE
590             "\xD2\xBA" => "\xD2\xBB", # CYRILLIC CAPITAL LETTER SHHA
591             "\xD2\xBC" => "\xD2\xBD", # CYRILLIC CAPITAL LETTER ABKHASIAN CHE
592             "\xD2\xBE" => "\xD2\xBF", # CYRILLIC CAPITAL LETTER ABKHASIAN CHE WITH DESCENDER
593             "\xD3\x80" => "\xD3\x8F", # CYRILLIC LETTER PALOCHKA
594             "\xD3\x81" => "\xD3\x82", # CYRILLIC CAPITAL LETTER ZHE WITH BREVE
595             "\xD3\x83" => "\xD3\x84", # CYRILLIC CAPITAL LETTER KA WITH HOOK
596             "\xD3\x85" => "\xD3\x86", # CYRILLIC CAPITAL LETTER EL WITH TAIL
597             "\xD3\x87" => "\xD3\x88", # CYRILLIC CAPITAL LETTER EN WITH HOOK
598             "\xD3\x89" => "\xD3\x8A", # CYRILLIC CAPITAL LETTER EN WITH TAIL
599             "\xD3\x8B" => "\xD3\x8C", # CYRILLIC CAPITAL LETTER KHAKASSIAN CHE
600             "\xD3\x8D" => "\xD3\x8E", # CYRILLIC CAPITAL LETTER EM WITH TAIL
601             "\xD3\x90" => "\xD3\x91", # CYRILLIC CAPITAL LETTER A WITH BREVE
602             "\xD3\x92" => "\xD3\x93", # CYRILLIC CAPITAL LETTER A WITH DIAERESIS
603             "\xD3\x94" => "\xD3\x95", # CYRILLIC CAPITAL LIGATURE A IE
604             "\xD3\x96" => "\xD3\x97", # CYRILLIC CAPITAL LETTER IE WITH BREVE
605             "\xD3\x98" => "\xD3\x99", # CYRILLIC CAPITAL LETTER SCHWA
606             "\xD3\x9A" => "\xD3\x9B", # CYRILLIC CAPITAL LETTER SCHWA WITH DIAERESIS
607             "\xD3\x9C" => "\xD3\x9D", # CYRILLIC CAPITAL LETTER ZHE WITH DIAERESIS
608             "\xD3\x9E" => "\xD3\x9F", # CYRILLIC CAPITAL LETTER ZE WITH DIAERESIS
609             "\xD3\xA0" => "\xD3\xA1", # CYRILLIC CAPITAL LETTER ABKHASIAN DZE
610             "\xD3\xA2" => "\xD3\xA3", # CYRILLIC CAPITAL LETTER I WITH MACRON
611             "\xD3\xA4" => "\xD3\xA5", # CYRILLIC CAPITAL LETTER I WITH DIAERESIS
612             "\xD3\xA6" => "\xD3\xA7", # CYRILLIC CAPITAL LETTER O WITH DIAERESIS
613             "\xD3\xA8" => "\xD3\xA9", # CYRILLIC CAPITAL LETTER BARRED O
614             "\xD3\xAA" => "\xD3\xAB", # CYRILLIC CAPITAL LETTER BARRED O WITH DIAERESIS
615             "\xD3\xAC" => "\xD3\xAD", # CYRILLIC CAPITAL LETTER E WITH DIAERESIS
616             "\xD3\xAE" => "\xD3\xAF", # CYRILLIC CAPITAL LETTER U WITH MACRON
617             "\xD3\xB0" => "\xD3\xB1", # CYRILLIC CAPITAL LETTER U WITH DIAERESIS
618             "\xD3\xB2" => "\xD3\xB3", # CYRILLIC CAPITAL LETTER U WITH DOUBLE ACUTE
619             "\xD3\xB4" => "\xD3\xB5", # CYRILLIC CAPITAL LETTER CHE WITH DIAERESIS
620             "\xD3\xB6" => "\xD3\xB7", # CYRILLIC CAPITAL LETTER GHE WITH DESCENDER
621             "\xD3\xB8" => "\xD3\xB9", # CYRILLIC CAPITAL LETTER YERU WITH DIAERESIS
622             "\xD3\xBA" => "\xD3\xBB", # CYRILLIC CAPITAL LETTER GHE WITH STROKE AND HOOK
623             "\xD3\xBC" => "\xD3\xBD", # CYRILLIC CAPITAL LETTER HA WITH HOOK
624             "\xD3\xBE" => "\xD3\xBF", # CYRILLIC CAPITAL LETTER HA WITH STROKE
625             "\xD4\x80" => "\xD4\x81", # CYRILLIC CAPITAL LETTER KOMI DE
626             "\xD4\x82" => "\xD4\x83", # CYRILLIC CAPITAL LETTER KOMI DJE
627             "\xD4\x84" => "\xD4\x85", # CYRILLIC CAPITAL LETTER KOMI ZJE
628             "\xD4\x86" => "\xD4\x87", # CYRILLIC CAPITAL LETTER KOMI DZJE
629             "\xD4\x88" => "\xD4\x89", # CYRILLIC CAPITAL LETTER KOMI LJE
630             "\xD4\x8A" => "\xD4\x8B", # CYRILLIC CAPITAL LETTER KOMI NJE
631             "\xD4\x8C" => "\xD4\x8D", # CYRILLIC CAPITAL LETTER KOMI SJE
632             "\xD4\x8E" => "\xD4\x8F", # CYRILLIC CAPITAL LETTER KOMI TJE
633             "\xD4\x90" => "\xD4\x91", # CYRILLIC CAPITAL LETTER REVERSED ZE
634             "\xD4\x92" => "\xD4\x93", # CYRILLIC CAPITAL LETTER EL WITH HOOK
635             "\xD4\x94" => "\xD4\x95", # CYRILLIC CAPITAL LETTER LHA
636             "\xD4\x96" => "\xD4\x97", # CYRILLIC CAPITAL LETTER RHA
637             "\xD4\x98" => "\xD4\x99", # CYRILLIC CAPITAL LETTER YAE
638             "\xD4\x9A" => "\xD4\x9B", # CYRILLIC CAPITAL LETTER QA
639             "\xD4\x9C" => "\xD4\x9D", # CYRILLIC CAPITAL LETTER WE
640             "\xD4\x9E" => "\xD4\x9F", # CYRILLIC CAPITAL LETTER ALEUT KA
641             "\xD4\xA0" => "\xD4\xA1", # CYRILLIC CAPITAL LETTER EL WITH MIDDLE HOOK
642             "\xD4\xA2" => "\xD4\xA3", # CYRILLIC CAPITAL LETTER EN WITH MIDDLE HOOK
643             "\xD4\xA4" => "\xD4\xA5", # CYRILLIC CAPITAL LETTER PE WITH DESCENDER
644             "\xD4\xA6" => "\xD4\xA7", # CYRILLIC CAPITAL LETTER SHHA WITH DESCENDER
645             "\xD4\xA8" => "\xD4\xA9", # CYRILLIC CAPITAL LETTER EN WITH LEFT HOOK
646             "\xD4\xAA" => "\xD4\xAB", # CYRILLIC CAPITAL LETTER DZZHE
647             "\xD4\xAC" => "\xD4\xAD", # CYRILLIC CAPITAL LETTER DCHE
648             "\xD4\xAE" => "\xD4\xAF", # CYRILLIC CAPITAL LETTER EL WITH DESCENDER
649             "\xD4\xB1" => "\xD5\xA1", # ARMENIAN CAPITAL LETTER AYB
650             "\xD4\xB2" => "\xD5\xA2", # ARMENIAN CAPITAL LETTER BEN
651             "\xD4\xB3" => "\xD5\xA3", # ARMENIAN CAPITAL LETTER GIM
652             "\xD4\xB4" => "\xD5\xA4", # ARMENIAN CAPITAL LETTER DA
653             "\xD4\xB5" => "\xD5\xA5", # ARMENIAN CAPITAL LETTER ECH
654             "\xD4\xB6" => "\xD5\xA6", # ARMENIAN CAPITAL LETTER ZA
655             "\xD4\xB7" => "\xD5\xA7", # ARMENIAN CAPITAL LETTER EH
656             "\xD4\xB8" => "\xD5\xA8", # ARMENIAN CAPITAL LETTER ET
657             "\xD4\xB9" => "\xD5\xA9", # ARMENIAN CAPITAL LETTER TO
658             "\xD4\xBA" => "\xD5\xAA", # ARMENIAN CAPITAL LETTER ZHE
659             "\xD4\xBB" => "\xD5\xAB", # ARMENIAN CAPITAL LETTER INI
660             "\xD4\xBC" => "\xD5\xAC", # ARMENIAN CAPITAL LETTER LIWN
661             "\xD4\xBD" => "\xD5\xAD", # ARMENIAN CAPITAL LETTER XEH
662             "\xD4\xBE" => "\xD5\xAE", # ARMENIAN CAPITAL LETTER CA
663             "\xD4\xBF" => "\xD5\xAF", # ARMENIAN CAPITAL LETTER KEN
664             "\xD5\x80" => "\xD5\xB0", # ARMENIAN CAPITAL LETTER HO
665             "\xD5\x81" => "\xD5\xB1", # ARMENIAN CAPITAL LETTER JA
666             "\xD5\x82" => "\xD5\xB2", # ARMENIAN CAPITAL LETTER GHAD
667             "\xD5\x83" => "\xD5\xB3", # ARMENIAN CAPITAL LETTER CHEH
668             "\xD5\x84" => "\xD5\xB4", # ARMENIAN CAPITAL LETTER MEN
669             "\xD5\x85" => "\xD5\xB5", # ARMENIAN CAPITAL LETTER YI
670             "\xD5\x86" => "\xD5\xB6", # ARMENIAN CAPITAL LETTER NOW
671             "\xD5\x87" => "\xD5\xB7", # ARMENIAN CAPITAL LETTER SHA
672             "\xD5\x88" => "\xD5\xB8", # ARMENIAN CAPITAL LETTER VO
673             "\xD5\x89" => "\xD5\xB9", # ARMENIAN CAPITAL LETTER CHA
674             "\xD5\x8A" => "\xD5\xBA", # ARMENIAN CAPITAL LETTER PEH
675             "\xD5\x8B" => "\xD5\xBB", # ARMENIAN CAPITAL LETTER JHEH
676             "\xD5\x8C" => "\xD5\xBC", # ARMENIAN CAPITAL LETTER RA
677             "\xD5\x8D" => "\xD5\xBD", # ARMENIAN CAPITAL LETTER SEH
678             "\xD5\x8E" => "\xD5\xBE", # ARMENIAN CAPITAL LETTER VEW
679             "\xD5\x8F" => "\xD5\xBF", # ARMENIAN CAPITAL LETTER TIWN
680             "\xD5\x90" => "\xD6\x80", # ARMENIAN CAPITAL LETTER REH
681             "\xD5\x91" => "\xD6\x81", # ARMENIAN CAPITAL LETTER CO
682             "\xD5\x92" => "\xD6\x82", # ARMENIAN CAPITAL LETTER YIWN
683             "\xD5\x93" => "\xD6\x83", # ARMENIAN CAPITAL LETTER PIWR
684             "\xD5\x94" => "\xD6\x84", # ARMENIAN CAPITAL LETTER KEH
685             "\xD5\x95" => "\xD6\x85", # ARMENIAN CAPITAL LETTER OH
686             "\xD5\x96" => "\xD6\x86", # ARMENIAN CAPITAL LETTER FEH
687             "\xD6\x87" => "\xD5\xA5\xD6\x82", # ARMENIAN SMALL LIGATURE ECH YIWN
688             "\xE1\x82\xA0" => "\xE2\xB4\x80", # GEORGIAN CAPITAL LETTER AN
689             "\xE1\x82\xA1" => "\xE2\xB4\x81", # GEORGIAN CAPITAL LETTER BAN
690             "\xE1\x82\xA2" => "\xE2\xB4\x82", # GEORGIAN CAPITAL LETTER GAN
691             "\xE1\x82\xA3" => "\xE2\xB4\x83", # GEORGIAN CAPITAL LETTER DON
692             "\xE1\x82\xA4" => "\xE2\xB4\x84", # GEORGIAN CAPITAL LETTER EN
693             "\xE1\x82\xA5" => "\xE2\xB4\x85", # GEORGIAN CAPITAL LETTER VIN
694             "\xE1\x82\xA6" => "\xE2\xB4\x86", # GEORGIAN CAPITAL LETTER ZEN
695             "\xE1\x82\xA7" => "\xE2\xB4\x87", # GEORGIAN CAPITAL LETTER TAN
696             "\xE1\x82\xA8" => "\xE2\xB4\x88", # GEORGIAN CAPITAL LETTER IN
697             "\xE1\x82\xA9" => "\xE2\xB4\x89", # GEORGIAN CAPITAL LETTER KAN
698             "\xE1\x82\xAA" => "\xE2\xB4\x8A", # GEORGIAN CAPITAL LETTER LAS
699             "\xE1\x82\xAB" => "\xE2\xB4\x8B", # GEORGIAN CAPITAL LETTER MAN
700             "\xE1\x82\xAC" => "\xE2\xB4\x8C", # GEORGIAN CAPITAL LETTER NAR
701             "\xE1\x82\xAD" => "\xE2\xB4\x8D", # GEORGIAN CAPITAL LETTER ON
702             "\xE1\x82\xAE" => "\xE2\xB4\x8E", # GEORGIAN CAPITAL LETTER PAR
703             "\xE1\x82\xAF" => "\xE2\xB4\x8F", # GEORGIAN CAPITAL LETTER ZHAR
704             "\xE1\x82\xB0" => "\xE2\xB4\x90", # GEORGIAN CAPITAL LETTER RAE
705             "\xE1\x82\xB1" => "\xE2\xB4\x91", # GEORGIAN CAPITAL LETTER SAN
706             "\xE1\x82\xB2" => "\xE2\xB4\x92", # GEORGIAN CAPITAL LETTER TAR
707             "\xE1\x82\xB3" => "\xE2\xB4\x93", # GEORGIAN CAPITAL LETTER UN
708             "\xE1\x82\xB4" => "\xE2\xB4\x94", # GEORGIAN CAPITAL LETTER PHAR
709             "\xE1\x82\xB5" => "\xE2\xB4\x95", # GEORGIAN CAPITAL LETTER KHAR
710             "\xE1\x82\xB6" => "\xE2\xB4\x96", # GEORGIAN CAPITAL LETTER GHAN
711             "\xE1\x82\xB7" => "\xE2\xB4\x97", # GEORGIAN CAPITAL LETTER QAR
712             "\xE1\x82\xB8" => "\xE2\xB4\x98", # GEORGIAN CAPITAL LETTER SHIN
713             "\xE1\x82\xB9" => "\xE2\xB4\x99", # GEORGIAN CAPITAL LETTER CHIN
714             "\xE1\x82\xBA" => "\xE2\xB4\x9A", # GEORGIAN CAPITAL LETTER CAN
715             "\xE1\x82\xBB" => "\xE2\xB4\x9B", # GEORGIAN CAPITAL LETTER JIL
716             "\xE1\x82\xBC" => "\xE2\xB4\x9C", # GEORGIAN CAPITAL LETTER CIL
717             "\xE1\x82\xBD" => "\xE2\xB4\x9D", # GEORGIAN CAPITAL LETTER CHAR
718             "\xE1\x82\xBE" => "\xE2\xB4\x9E", # GEORGIAN CAPITAL LETTER XAN
719             "\xE1\x82\xBF" => "\xE2\xB4\x9F", # GEORGIAN CAPITAL LETTER JHAN
720             "\xE1\x83\x80" => "\xE2\xB4\xA0", # GEORGIAN CAPITAL LETTER HAE
721             "\xE1\x83\x81" => "\xE2\xB4\xA1", # GEORGIAN CAPITAL LETTER HE
722             "\xE1\x83\x82" => "\xE2\xB4\xA2", # GEORGIAN CAPITAL LETTER HIE
723             "\xE1\x83\x83" => "\xE2\xB4\xA3", # GEORGIAN CAPITAL LETTER WE
724             "\xE1\x83\x84" => "\xE2\xB4\xA4", # GEORGIAN CAPITAL LETTER HAR
725             "\xE1\x83\x85" => "\xE2\xB4\xA5", # GEORGIAN CAPITAL LETTER HOE
726             "\xE1\x83\x87" => "\xE2\xB4\xA7", # GEORGIAN CAPITAL LETTER YN
727             "\xE1\x83\x8D" => "\xE2\xB4\xAD", # GEORGIAN CAPITAL LETTER AEN
728             "\xE1\x8F\xB8" => "\xE1\x8F\xB0", # CHEROKEE SMALL LETTER YE
729             "\xE1\x8F\xB9" => "\xE1\x8F\xB1", # CHEROKEE SMALL LETTER YI
730             "\xE1\x8F\xBA" => "\xE1\x8F\xB2", # CHEROKEE SMALL LETTER YO
731             "\xE1\x8F\xBB" => "\xE1\x8F\xB3", # CHEROKEE SMALL LETTER YU
732             "\xE1\x8F\xBC" => "\xE1\x8F\xB4", # CHEROKEE SMALL LETTER YV
733             "\xE1\x8F\xBD" => "\xE1\x8F\xB5", # CHEROKEE SMALL LETTER MV
734             "\xE1\xB2\x80" => "\xD0\xB2", # CYRILLIC SMALL LETTER ROUNDED VE
735             "\xE1\xB2\x81" => "\xD0\xB4", # CYRILLIC SMALL LETTER LONG-LEGGED DE
736             "\xE1\xB2\x82" => "\xD0\xBE", # CYRILLIC SMALL LETTER NARROW O
737             "\xE1\xB2\x83" => "\xD1\x81", # CYRILLIC SMALL LETTER WIDE ES
738             "\xE1\xB2\x84" => "\xD1\x82", # CYRILLIC SMALL LETTER TALL TE
739             "\xE1\xB2\x85" => "\xD1\x82", # CYRILLIC SMALL LETTER THREE-LEGGED TE
740             "\xE1\xB2\x86" => "\xD1\x8A", # CYRILLIC SMALL LETTER TALL HARD SIGN
741             "\xE1\xB2\x87" => "\xD1\xA3", # CYRILLIC SMALL LETTER TALL YAT
742             "\xE1\xB2\x88" => "\xEA\x99\x8B", # CYRILLIC SMALL LETTER UNBLENDED UK
743             "\xE1\xB2\x90" => "\xE1\x83\x90", # GEORGIAN MTAVRULI CAPITAL LETTER AN
744             "\xE1\xB2\x91" => "\xE1\x83\x91", # GEORGIAN MTAVRULI CAPITAL LETTER BAN
745             "\xE1\xB2\x92" => "\xE1\x83\x92", # GEORGIAN MTAVRULI CAPITAL LETTER GAN
746             "\xE1\xB2\x93" => "\xE1\x83\x93", # GEORGIAN MTAVRULI CAPITAL LETTER DON
747             "\xE1\xB2\x94" => "\xE1\x83\x94", # GEORGIAN MTAVRULI CAPITAL LETTER EN
748             "\xE1\xB2\x95" => "\xE1\x83\x95", # GEORGIAN MTAVRULI CAPITAL LETTER VIN
749             "\xE1\xB2\x96" => "\xE1\x83\x96", # GEORGIAN MTAVRULI CAPITAL LETTER ZEN
750             "\xE1\xB2\x97" => "\xE1\x83\x97", # GEORGIAN MTAVRULI CAPITAL LETTER TAN
751             "\xE1\xB2\x98" => "\xE1\x83\x98", # GEORGIAN MTAVRULI CAPITAL LETTER IN
752             "\xE1\xB2\x99" => "\xE1\x83\x99", # GEORGIAN MTAVRULI CAPITAL LETTER KAN
753             "\xE1\xB2\x9A" => "\xE1\x83\x9A", # GEORGIAN MTAVRULI CAPITAL LETTER LAS
754             "\xE1\xB2\x9B" => "\xE1\x83\x9B", # GEORGIAN MTAVRULI CAPITAL LETTER MAN
755             "\xE1\xB2\x9C" => "\xE1\x83\x9C", # GEORGIAN MTAVRULI CAPITAL LETTER NAR
756             "\xE1\xB2\x9D" => "\xE1\x83\x9D", # GEORGIAN MTAVRULI CAPITAL LETTER ON
757             "\xE1\xB2\x9E" => "\xE1\x83\x9E", # GEORGIAN MTAVRULI CAPITAL LETTER PAR
758             "\xE1\xB2\x9F" => "\xE1\x83\x9F", # GEORGIAN MTAVRULI CAPITAL LETTER ZHAR
759             "\xE1\xB2\xA0" => "\xE1\x83\xA0", # GEORGIAN MTAVRULI CAPITAL LETTER RAE
760             "\xE1\xB2\xA1" => "\xE1\x83\xA1", # GEORGIAN MTAVRULI CAPITAL LETTER SAN
761             "\xE1\xB2\xA2" => "\xE1\x83\xA2", # GEORGIAN MTAVRULI CAPITAL LETTER TAR
762             "\xE1\xB2\xA3" => "\xE1\x83\xA3", # GEORGIAN MTAVRULI CAPITAL LETTER UN
763             "\xE1\xB2\xA4" => "\xE1\x83\xA4", # GEORGIAN MTAVRULI CAPITAL LETTER PHAR
764             "\xE1\xB2\xA5" => "\xE1\x83\xA5", # GEORGIAN MTAVRULI CAPITAL LETTER KHAR
765             "\xE1\xB2\xA6" => "\xE1\x83\xA6", # GEORGIAN MTAVRULI CAPITAL LETTER GHAN
766             "\xE1\xB2\xA7" => "\xE1\x83\xA7", # GEORGIAN MTAVRULI CAPITAL LETTER QAR
767             "\xE1\xB2\xA8" => "\xE1\x83\xA8", # GEORGIAN MTAVRULI CAPITAL LETTER SHIN
768             "\xE1\xB2\xA9" => "\xE1\x83\xA9", # GEORGIAN MTAVRULI CAPITAL LETTER CHIN
769             "\xE1\xB2\xAA" => "\xE1\x83\xAA", # GEORGIAN MTAVRULI CAPITAL LETTER CAN
770             "\xE1\xB2\xAB" => "\xE1\x83\xAB", # GEORGIAN MTAVRULI CAPITAL LETTER JIL
771             "\xE1\xB2\xAC" => "\xE1\x83\xAC", # GEORGIAN MTAVRULI CAPITAL LETTER CIL
772             "\xE1\xB2\xAD" => "\xE1\x83\xAD", # GEORGIAN MTAVRULI CAPITAL LETTER CHAR
773             "\xE1\xB2\xAE" => "\xE1\x83\xAE", # GEORGIAN MTAVRULI CAPITAL LETTER XAN
774             "\xE1\xB2\xAF" => "\xE1\x83\xAF", # GEORGIAN MTAVRULI CAPITAL LETTER JHAN
775             "\xE1\xB2\xB0" => "\xE1\x83\xB0", # GEORGIAN MTAVRULI CAPITAL LETTER HAE
776             "\xE1\xB2\xB1" => "\xE1\x83\xB1", # GEORGIAN MTAVRULI CAPITAL LETTER HE
777             "\xE1\xB2\xB2" => "\xE1\x83\xB2", # GEORGIAN MTAVRULI CAPITAL LETTER HIE
778             "\xE1\xB2\xB3" => "\xE1\x83\xB3", # GEORGIAN MTAVRULI CAPITAL LETTER WE
779             "\xE1\xB2\xB4" => "\xE1\x83\xB4", # GEORGIAN MTAVRULI CAPITAL LETTER HAR
780             "\xE1\xB2\xB5" => "\xE1\x83\xB5", # GEORGIAN MTAVRULI CAPITAL LETTER HOE
781             "\xE1\xB2\xB6" => "\xE1\x83\xB6", # GEORGIAN MTAVRULI CAPITAL LETTER FI
782             "\xE1\xB2\xB7" => "\xE1\x83\xB7", # GEORGIAN MTAVRULI CAPITAL LETTER YN
783             "\xE1\xB2\xB8" => "\xE1\x83\xB8", # GEORGIAN MTAVRULI CAPITAL LETTER ELIFI
784             "\xE1\xB2\xB9" => "\xE1\x83\xB9", # GEORGIAN MTAVRULI CAPITAL LETTER TURNED GAN
785             "\xE1\xB2\xBA" => "\xE1\x83\xBA", # GEORGIAN MTAVRULI CAPITAL LETTER AIN
786             "\xE1\xB2\xBD" => "\xE1\x83\xBD", # GEORGIAN MTAVRULI CAPITAL LETTER AEN
787             "\xE1\xB2\xBE" => "\xE1\x83\xBE", # GEORGIAN MTAVRULI CAPITAL LETTER HARD SIGN
788             "\xE1\xB2\xBF" => "\xE1\x83\xBF", # GEORGIAN MTAVRULI CAPITAL LETTER LABIAL SIGN
789             "\xE1\xB8\x80" => "\xE1\xB8\x81", # LATIN CAPITAL LETTER A WITH RING BELOW
790             "\xE1\xB8\x82" => "\xE1\xB8\x83", # LATIN CAPITAL LETTER B WITH DOT ABOVE
791             "\xE1\xB8\x84" => "\xE1\xB8\x85", # LATIN CAPITAL LETTER B WITH DOT BELOW
792             "\xE1\xB8\x86" => "\xE1\xB8\x87", # LATIN CAPITAL LETTER B WITH LINE BELOW
793             "\xE1\xB8\x88" => "\xE1\xB8\x89", # LATIN CAPITAL LETTER C WITH CEDILLA AND ACUTE
794             "\xE1\xB8\x8A" => "\xE1\xB8\x8B", # LATIN CAPITAL LETTER D WITH DOT ABOVE
795             "\xE1\xB8\x8C" => "\xE1\xB8\x8D", # LATIN CAPITAL LETTER D WITH DOT BELOW
796             "\xE1\xB8\x8E" => "\xE1\xB8\x8F", # LATIN CAPITAL LETTER D WITH LINE BELOW
797             "\xE1\xB8\x90" => "\xE1\xB8\x91", # LATIN CAPITAL LETTER D WITH CEDILLA
798             "\xE1\xB8\x92" => "\xE1\xB8\x93", # LATIN CAPITAL LETTER D WITH CIRCUMFLEX BELOW
799             "\xE1\xB8\x94" => "\xE1\xB8\x95", # LATIN CAPITAL LETTER E WITH MACRON AND GRAVE
800             "\xE1\xB8\x96" => "\xE1\xB8\x97", # LATIN CAPITAL LETTER E WITH MACRON AND ACUTE
801             "\xE1\xB8\x98" => "\xE1\xB8\x99", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX BELOW
802             "\xE1\xB8\x9A" => "\xE1\xB8\x9B", # LATIN CAPITAL LETTER E WITH TILDE BELOW
803             "\xE1\xB8\x9C" => "\xE1\xB8\x9D", # LATIN CAPITAL LETTER E WITH CEDILLA AND BREVE
804             "\xE1\xB8\x9E" => "\xE1\xB8\x9F", # LATIN CAPITAL LETTER F WITH DOT ABOVE
805             "\xE1\xB8\xA0" => "\xE1\xB8\xA1", # LATIN CAPITAL LETTER G WITH MACRON
806             "\xE1\xB8\xA2" => "\xE1\xB8\xA3", # LATIN CAPITAL LETTER H WITH DOT ABOVE
807             "\xE1\xB8\xA4" => "\xE1\xB8\xA5", # LATIN CAPITAL LETTER H WITH DOT BELOW
808             "\xE1\xB8\xA6" => "\xE1\xB8\xA7", # LATIN CAPITAL LETTER H WITH DIAERESIS
809             "\xE1\xB8\xA8" => "\xE1\xB8\xA9", # LATIN CAPITAL LETTER H WITH CEDILLA
810             "\xE1\xB8\xAA" => "\xE1\xB8\xAB", # LATIN CAPITAL LETTER H WITH BREVE BELOW
811             "\xE1\xB8\xAC" => "\xE1\xB8\xAD", # LATIN CAPITAL LETTER I WITH TILDE BELOW
812             "\xE1\xB8\xAE" => "\xE1\xB8\xAF", # LATIN CAPITAL LETTER I WITH DIAERESIS AND ACUTE
813             "\xE1\xB8\xB0" => "\xE1\xB8\xB1", # LATIN CAPITAL LETTER K WITH ACUTE
814             "\xE1\xB8\xB2" => "\xE1\xB8\xB3", # LATIN CAPITAL LETTER K WITH DOT BELOW
815             "\xE1\xB8\xB4" => "\xE1\xB8\xB5", # LATIN CAPITAL LETTER K WITH LINE BELOW
816             "\xE1\xB8\xB6" => "\xE1\xB8\xB7", # LATIN CAPITAL LETTER L WITH DOT BELOW
817             "\xE1\xB8\xB8" => "\xE1\xB8\xB9", # LATIN CAPITAL LETTER L WITH DOT BELOW AND MACRON
818             "\xE1\xB8\xBA" => "\xE1\xB8\xBB", # LATIN CAPITAL LETTER L WITH LINE BELOW
819             "\xE1\xB8\xBC" => "\xE1\xB8\xBD", # LATIN CAPITAL LETTER L WITH CIRCUMFLEX BELOW
820             "\xE1\xB8\xBE" => "\xE1\xB8\xBF", # LATIN CAPITAL LETTER M WITH ACUTE
821             "\xE1\xB9\x80" => "\xE1\xB9\x81", # LATIN CAPITAL LETTER M WITH DOT ABOVE
822             "\xE1\xB9\x82" => "\xE1\xB9\x83", # LATIN CAPITAL LETTER M WITH DOT BELOW
823             "\xE1\xB9\x84" => "\xE1\xB9\x85", # LATIN CAPITAL LETTER N WITH DOT ABOVE
824             "\xE1\xB9\x86" => "\xE1\xB9\x87", # LATIN CAPITAL LETTER N WITH DOT BELOW
825             "\xE1\xB9\x88" => "\xE1\xB9\x89", # LATIN CAPITAL LETTER N WITH LINE BELOW
826             "\xE1\xB9\x8A" => "\xE1\xB9\x8B", # LATIN CAPITAL LETTER N WITH CIRCUMFLEX BELOW
827             "\xE1\xB9\x8C" => "\xE1\xB9\x8D", # LATIN CAPITAL LETTER O WITH TILDE AND ACUTE
828             "\xE1\xB9\x8E" => "\xE1\xB9\x8F", # LATIN CAPITAL LETTER O WITH TILDE AND DIAERESIS
829             "\xE1\xB9\x90" => "\xE1\xB9\x91", # LATIN CAPITAL LETTER O WITH MACRON AND GRAVE
830             "\xE1\xB9\x92" => "\xE1\xB9\x93", # LATIN CAPITAL LETTER O WITH MACRON AND ACUTE
831             "\xE1\xB9\x94" => "\xE1\xB9\x95", # LATIN CAPITAL LETTER P WITH ACUTE
832             "\xE1\xB9\x96" => "\xE1\xB9\x97", # LATIN CAPITAL LETTER P WITH DOT ABOVE
833             "\xE1\xB9\x98" => "\xE1\xB9\x99", # LATIN CAPITAL LETTER R WITH DOT ABOVE
834             "\xE1\xB9\x9A" => "\xE1\xB9\x9B", # LATIN CAPITAL LETTER R WITH DOT BELOW
835             "\xE1\xB9\x9C" => "\xE1\xB9\x9D", # LATIN CAPITAL LETTER R WITH DOT BELOW AND MACRON
836             "\xE1\xB9\x9E" => "\xE1\xB9\x9F", # LATIN CAPITAL LETTER R WITH LINE BELOW
837             "\xE1\xB9\xA0" => "\xE1\xB9\xA1", # LATIN CAPITAL LETTER S WITH DOT ABOVE
838             "\xE1\xB9\xA2" => "\xE1\xB9\xA3", # LATIN CAPITAL LETTER S WITH DOT BELOW
839             "\xE1\xB9\xA4" => "\xE1\xB9\xA5", # LATIN CAPITAL LETTER S WITH ACUTE AND DOT ABOVE
840             "\xE1\xB9\xA6" => "\xE1\xB9\xA7", # LATIN CAPITAL LETTER S WITH CARON AND DOT ABOVE
841             "\xE1\xB9\xA8" => "\xE1\xB9\xA9", # LATIN CAPITAL LETTER S WITH DOT BELOW AND DOT ABOVE
842             "\xE1\xB9\xAA" => "\xE1\xB9\xAB", # LATIN CAPITAL LETTER T WITH DOT ABOVE
843             "\xE1\xB9\xAC" => "\xE1\xB9\xAD", # LATIN CAPITAL LETTER T WITH DOT BELOW
844             "\xE1\xB9\xAE" => "\xE1\xB9\xAF", # LATIN CAPITAL LETTER T WITH LINE BELOW
845             "\xE1\xB9\xB0" => "\xE1\xB9\xB1", # LATIN CAPITAL LETTER T WITH CIRCUMFLEX BELOW
846             "\xE1\xB9\xB2" => "\xE1\xB9\xB3", # LATIN CAPITAL LETTER U WITH DIAERESIS BELOW
847             "\xE1\xB9\xB4" => "\xE1\xB9\xB5", # LATIN CAPITAL LETTER U WITH TILDE BELOW
848             "\xE1\xB9\xB6" => "\xE1\xB9\xB7", # LATIN CAPITAL LETTER U WITH CIRCUMFLEX BELOW
849             "\xE1\xB9\xB8" => "\xE1\xB9\xB9", # LATIN CAPITAL LETTER U WITH TILDE AND ACUTE
850             "\xE1\xB9\xBA" => "\xE1\xB9\xBB", # LATIN CAPITAL LETTER U WITH MACRON AND DIAERESIS
851             "\xE1\xB9\xBC" => "\xE1\xB9\xBD", # LATIN CAPITAL LETTER V WITH TILDE
852             "\xE1\xB9\xBE" => "\xE1\xB9\xBF", # LATIN CAPITAL LETTER V WITH DOT BELOW
853             "\xE1\xBA\x80" => "\xE1\xBA\x81", # LATIN CAPITAL LETTER W WITH GRAVE
854             "\xE1\xBA\x82" => "\xE1\xBA\x83", # LATIN CAPITAL LETTER W WITH ACUTE
855             "\xE1\xBA\x84" => "\xE1\xBA\x85", # LATIN CAPITAL LETTER W WITH DIAERESIS
856             "\xE1\xBA\x86" => "\xE1\xBA\x87", # LATIN CAPITAL LETTER W WITH DOT ABOVE
857             "\xE1\xBA\x88" => "\xE1\xBA\x89", # LATIN CAPITAL LETTER W WITH DOT BELOW
858             "\xE1\xBA\x8A" => "\xE1\xBA\x8B", # LATIN CAPITAL LETTER X WITH DOT ABOVE
859             "\xE1\xBA\x8C" => "\xE1\xBA\x8D", # LATIN CAPITAL LETTER X WITH DIAERESIS
860             "\xE1\xBA\x8E" => "\xE1\xBA\x8F", # LATIN CAPITAL LETTER Y WITH DOT ABOVE
861             "\xE1\xBA\x90" => "\xE1\xBA\x91", # LATIN CAPITAL LETTER Z WITH CIRCUMFLEX
862             "\xE1\xBA\x92" => "\xE1\xBA\x93", # LATIN CAPITAL LETTER Z WITH DOT BELOW
863             "\xE1\xBA\x94" => "\xE1\xBA\x95", # LATIN CAPITAL LETTER Z WITH LINE BELOW
864             "\xE1\xBA\x96" => "\x68\xCC\xB1", # LATIN SMALL LETTER H WITH LINE BELOW
865             "\xE1\xBA\x97" => "\x74\xCC\x88", # LATIN SMALL LETTER T WITH DIAERESIS
866             "\xE1\xBA\x98" => "\x77\xCC\x8A", # LATIN SMALL LETTER W WITH RING ABOVE
867             "\xE1\xBA\x99" => "\x79\xCC\x8A", # LATIN SMALL LETTER Y WITH RING ABOVE
868             "\xE1\xBA\x9A" => "\x61\xCA\xBE", # LATIN SMALL LETTER A WITH RIGHT HALF RING
869             "\xE1\xBA\x9B" => "\xE1\xB9\xA1", # LATIN SMALL LETTER LONG S WITH DOT ABOVE
870             "\xE1\xBA\x9E" => "\x73\x73", # LATIN CAPITAL LETTER SHARP S
871             "\xE1\xBA\xA0" => "\xE1\xBA\xA1", # LATIN CAPITAL LETTER A WITH DOT BELOW
872             "\xE1\xBA\xA2" => "\xE1\xBA\xA3", # LATIN CAPITAL LETTER A WITH HOOK ABOVE
873             "\xE1\xBA\xA4" => "\xE1\xBA\xA5", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND ACUTE
874             "\xE1\xBA\xA6" => "\xE1\xBA\xA7", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND GRAVE
875             "\xE1\xBA\xA8" => "\xE1\xBA\xA9", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND HOOK ABOVE
876             "\xE1\xBA\xAA" => "\xE1\xBA\xAB", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND TILDE
877             "\xE1\xBA\xAC" => "\xE1\xBA\xAD", # LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND DOT BELOW
878             "\xE1\xBA\xAE" => "\xE1\xBA\xAF", # LATIN CAPITAL LETTER A WITH BREVE AND ACUTE
879             "\xE1\xBA\xB0" => "\xE1\xBA\xB1", # LATIN CAPITAL LETTER A WITH BREVE AND GRAVE
880             "\xE1\xBA\xB2" => "\xE1\xBA\xB3", # LATIN CAPITAL LETTER A WITH BREVE AND HOOK ABOVE
881             "\xE1\xBA\xB4" => "\xE1\xBA\xB5", # LATIN CAPITAL LETTER A WITH BREVE AND TILDE
882             "\xE1\xBA\xB6" => "\xE1\xBA\xB7", # LATIN CAPITAL LETTER A WITH BREVE AND DOT BELOW
883             "\xE1\xBA\xB8" => "\xE1\xBA\xB9", # LATIN CAPITAL LETTER E WITH DOT BELOW
884             "\xE1\xBA\xBA" => "\xE1\xBA\xBB", # LATIN CAPITAL LETTER E WITH HOOK ABOVE
885             "\xE1\xBA\xBC" => "\xE1\xBA\xBD", # LATIN CAPITAL LETTER E WITH TILDE
886             "\xE1\xBA\xBE" => "\xE1\xBA\xBF", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND ACUTE
887             "\xE1\xBB\x80" => "\xE1\xBB\x81", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND GRAVE
888             "\xE1\xBB\x82" => "\xE1\xBB\x83", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND HOOK ABOVE
889             "\xE1\xBB\x84" => "\xE1\xBB\x85", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND TILDE
890             "\xE1\xBB\x86" => "\xE1\xBB\x87", # LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND DOT BELOW
891             "\xE1\xBB\x88" => "\xE1\xBB\x89", # LATIN CAPITAL LETTER I WITH HOOK ABOVE
892             "\xE1\xBB\x8A" => "\xE1\xBB\x8B", # LATIN CAPITAL LETTER I WITH DOT BELOW
893             "\xE1\xBB\x8C" => "\xE1\xBB\x8D", # LATIN CAPITAL LETTER O WITH DOT BELOW
894             "\xE1\xBB\x8E" => "\xE1\xBB\x8F", # LATIN CAPITAL LETTER O WITH HOOK ABOVE
895             "\xE1\xBB\x90" => "\xE1\xBB\x91", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND ACUTE
896             "\xE1\xBB\x92" => "\xE1\xBB\x93", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND GRAVE
897             "\xE1\xBB\x94" => "\xE1\xBB\x95", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND HOOK ABOVE
898             "\xE1\xBB\x96" => "\xE1\xBB\x97", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND TILDE
899             "\xE1\xBB\x98" => "\xE1\xBB\x99", # LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND DOT BELOW
900             "\xE1\xBB\x9A" => "\xE1\xBB\x9B", # LATIN CAPITAL LETTER O WITH HORN AND ACUTE
901             "\xE1\xBB\x9C" => "\xE1\xBB\x9D", # LATIN CAPITAL LETTER O WITH HORN AND GRAVE
902             "\xE1\xBB\x9E" => "\xE1\xBB\x9F", # LATIN CAPITAL LETTER O WITH HORN AND HOOK ABOVE
903             "\xE1\xBB\xA0" => "\xE1\xBB\xA1", # LATIN CAPITAL LETTER O WITH HORN AND TILDE
904             "\xE1\xBB\xA2" => "\xE1\xBB\xA3", # LATIN CAPITAL LETTER O WITH HORN AND DOT BELOW
905             "\xE1\xBB\xA4" => "\xE1\xBB\xA5", # LATIN CAPITAL LETTER U WITH DOT BELOW
906             "\xE1\xBB\xA6" => "\xE1\xBB\xA7", # LATIN CAPITAL LETTER U WITH HOOK ABOVE
907             "\xE1\xBB\xA8" => "\xE1\xBB\xA9", # LATIN CAPITAL LETTER U WITH HORN AND ACUTE
908             "\xE1\xBB\xAA" => "\xE1\xBB\xAB", # LATIN CAPITAL LETTER U WITH HORN AND GRAVE
909             "\xE1\xBB\xAC" => "\xE1\xBB\xAD", # LATIN CAPITAL LETTER U WITH HORN AND HOOK ABOVE
910             "\xE1\xBB\xAE" => "\xE1\xBB\xAF", # LATIN CAPITAL LETTER U WITH HORN AND TILDE
911             "\xE1\xBB\xB0" => "\xE1\xBB\xB1", # LATIN CAPITAL LETTER U WITH HORN AND DOT BELOW
912             "\xE1\xBB\xB2" => "\xE1\xBB\xB3", # LATIN CAPITAL LETTER Y WITH GRAVE
913             "\xE1\xBB\xB4" => "\xE1\xBB\xB5", # LATIN CAPITAL LETTER Y WITH DOT BELOW
914             "\xE1\xBB\xB6" => "\xE1\xBB\xB7", # LATIN CAPITAL LETTER Y WITH HOOK ABOVE
915             "\xE1\xBB\xB8" => "\xE1\xBB\xB9", # LATIN CAPITAL LETTER Y WITH TILDE
916             "\xE1\xBB\xBA" => "\xE1\xBB\xBB", # LATIN CAPITAL LETTER MIDDLE-WELSH LL
917             "\xE1\xBB\xBC" => "\xE1\xBB\xBD", # LATIN CAPITAL LETTER MIDDLE-WELSH V
918             "\xE1\xBB\xBE" => "\xE1\xBB\xBF", # LATIN CAPITAL LETTER Y WITH LOOP
919             "\xE1\xBC\x88" => "\xE1\xBC\x80", # GREEK CAPITAL LETTER ALPHA WITH PSILI
920             "\xE1\xBC\x89" => "\xE1\xBC\x81", # GREEK CAPITAL LETTER ALPHA WITH DASIA
921             "\xE1\xBC\x8A" => "\xE1\xBC\x82", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND VARIA
922             "\xE1\xBC\x8B" => "\xE1\xBC\x83", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND VARIA
923             "\xE1\xBC\x8C" => "\xE1\xBC\x84", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND OXIA
924             "\xE1\xBC\x8D" => "\xE1\xBC\x85", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND OXIA
925             "\xE1\xBC\x8E" => "\xE1\xBC\x86", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND PERISPOMENI
926             "\xE1\xBC\x8F" => "\xE1\xBC\x87", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND PERISPOMENI
927             "\xE1\xBC\x98" => "\xE1\xBC\x90", # GREEK CAPITAL LETTER EPSILON WITH PSILI
928             "\xE1\xBC\x99" => "\xE1\xBC\x91", # GREEK CAPITAL LETTER EPSILON WITH DASIA
929             "\xE1\xBC\x9A" => "\xE1\xBC\x92", # GREEK CAPITAL LETTER EPSILON WITH PSILI AND VARIA
930             "\xE1\xBC\x9B" => "\xE1\xBC\x93", # GREEK CAPITAL LETTER EPSILON WITH DASIA AND VARIA
931             "\xE1\xBC\x9C" => "\xE1\xBC\x94", # GREEK CAPITAL LETTER EPSILON WITH PSILI AND OXIA
932             "\xE1\xBC\x9D" => "\xE1\xBC\x95", # GREEK CAPITAL LETTER EPSILON WITH DASIA AND OXIA
933             "\xE1\xBC\xA8" => "\xE1\xBC\xA0", # GREEK CAPITAL LETTER ETA WITH PSILI
934             "\xE1\xBC\xA9" => "\xE1\xBC\xA1", # GREEK CAPITAL LETTER ETA WITH DASIA
935             "\xE1\xBC\xAA" => "\xE1\xBC\xA2", # GREEK CAPITAL LETTER ETA WITH PSILI AND VARIA
936             "\xE1\xBC\xAB" => "\xE1\xBC\xA3", # GREEK CAPITAL LETTER ETA WITH DASIA AND VARIA
937             "\xE1\xBC\xAC" => "\xE1\xBC\xA4", # GREEK CAPITAL LETTER ETA WITH PSILI AND OXIA
938             "\xE1\xBC\xAD" => "\xE1\xBC\xA5", # GREEK CAPITAL LETTER ETA WITH DASIA AND OXIA
939             "\xE1\xBC\xAE" => "\xE1\xBC\xA6", # GREEK CAPITAL LETTER ETA WITH PSILI AND PERISPOMENI
940             "\xE1\xBC\xAF" => "\xE1\xBC\xA7", # GREEK CAPITAL LETTER ETA WITH DASIA AND PERISPOMENI
941             "\xE1\xBC\xB8" => "\xE1\xBC\xB0", # GREEK CAPITAL LETTER IOTA WITH PSILI
942             "\xE1\xBC\xB9" => "\xE1\xBC\xB1", # GREEK CAPITAL LETTER IOTA WITH DASIA
943             "\xE1\xBC\xBA" => "\xE1\xBC\xB2", # GREEK CAPITAL LETTER IOTA WITH PSILI AND VARIA
944             "\xE1\xBC\xBB" => "\xE1\xBC\xB3", # GREEK CAPITAL LETTER IOTA WITH DASIA AND VARIA
945             "\xE1\xBC\xBC" => "\xE1\xBC\xB4", # GREEK CAPITAL LETTER IOTA WITH PSILI AND OXIA
946             "\xE1\xBC\xBD" => "\xE1\xBC\xB5", # GREEK CAPITAL LETTER IOTA WITH DASIA AND OXIA
947             "\xE1\xBC\xBE" => "\xE1\xBC\xB6", # GREEK CAPITAL LETTER IOTA WITH PSILI AND PERISPOMENI
948             "\xE1\xBC\xBF" => "\xE1\xBC\xB7", # GREEK CAPITAL LETTER IOTA WITH DASIA AND PERISPOMENI
949             "\xE1\xBD\x88" => "\xE1\xBD\x80", # GREEK CAPITAL LETTER OMICRON WITH PSILI
950             "\xE1\xBD\x89" => "\xE1\xBD\x81", # GREEK CAPITAL LETTER OMICRON WITH DASIA
951             "\xE1\xBD\x8A" => "\xE1\xBD\x82", # GREEK CAPITAL LETTER OMICRON WITH PSILI AND VARIA
952             "\xE1\xBD\x8B" => "\xE1\xBD\x83", # GREEK CAPITAL LETTER OMICRON WITH DASIA AND VARIA
953             "\xE1\xBD\x8C" => "\xE1\xBD\x84", # GREEK CAPITAL LETTER OMICRON WITH PSILI AND OXIA
954             "\xE1\xBD\x8D" => "\xE1\xBD\x85", # GREEK CAPITAL LETTER OMICRON WITH DASIA AND OXIA
955             "\xE1\xBD\x90" => "\xCF\x85\xCC\x93", # GREEK SMALL LETTER UPSILON WITH PSILI
956             "\xE1\xBD\x92" => "\xCF\x85\xCC\x93\xCC\x80", # GREEK SMALL LETTER UPSILON WITH PSILI AND VARIA
957             "\xE1\xBD\x94" => "\xCF\x85\xCC\x93\xCC\x81", # GREEK SMALL LETTER UPSILON WITH PSILI AND OXIA
958             "\xE1\xBD\x96" => "\xCF\x85\xCC\x93\xCD\x82", # GREEK SMALL LETTER UPSILON WITH PSILI AND PERISPOMENI
959             "\xE1\xBD\x99" => "\xE1\xBD\x91", # GREEK CAPITAL LETTER UPSILON WITH DASIA
960             "\xE1\xBD\x9B" => "\xE1\xBD\x93", # GREEK CAPITAL LETTER UPSILON WITH DASIA AND VARIA
961             "\xE1\xBD\x9D" => "\xE1\xBD\x95", # GREEK CAPITAL LETTER UPSILON WITH DASIA AND OXIA
962             "\xE1\xBD\x9F" => "\xE1\xBD\x97", # GREEK CAPITAL LETTER UPSILON WITH DASIA AND PERISPOMENI
963             "\xE1\xBD\xA8" => "\xE1\xBD\xA0", # GREEK CAPITAL LETTER OMEGA WITH PSILI
964             "\xE1\xBD\xA9" => "\xE1\xBD\xA1", # GREEK CAPITAL LETTER OMEGA WITH DASIA
965             "\xE1\xBD\xAA" => "\xE1\xBD\xA2", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND VARIA
966             "\xE1\xBD\xAB" => "\xE1\xBD\xA3", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND VARIA
967             "\xE1\xBD\xAC" => "\xE1\xBD\xA4", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND OXIA
968             "\xE1\xBD\xAD" => "\xE1\xBD\xA5", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND OXIA
969             "\xE1\xBD\xAE" => "\xE1\xBD\xA6", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND PERISPOMENI
970             "\xE1\xBD\xAF" => "\xE1\xBD\xA7", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND PERISPOMENI
971             "\xE1\xBE\x80" => "\xE1\xBC\x80\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH PSILI AND YPOGEGRAMMENI
972             "\xE1\xBE\x81" => "\xE1\xBC\x81\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH DASIA AND YPOGEGRAMMENI
973             "\xE1\xBE\x82" => "\xE1\xBC\x82\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH PSILI AND VARIA AND YPOGEGRAMMENI
974             "\xE1\xBE\x83" => "\xE1\xBC\x83\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH DASIA AND VARIA AND YPOGEGRAMMENI
975             "\xE1\xBE\x84" => "\xE1\xBC\x84\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH PSILI AND OXIA AND YPOGEGRAMMENI
976             "\xE1\xBE\x85" => "\xE1\xBC\x85\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH DASIA AND OXIA AND YPOGEGRAMMENI
977             "\xE1\xBE\x86" => "\xE1\xBC\x86\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI
978             "\xE1\xBE\x87" => "\xE1\xBC\x87\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI
979             "\xE1\xBE\x88" => "\xE1\xBC\x80\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND PROSGEGRAMMENI
980             "\xE1\xBE\x89" => "\xE1\xBC\x81\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND PROSGEGRAMMENI
981             "\xE1\xBE\x8A" => "\xE1\xBC\x82\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND VARIA AND PROSGEGRAMMENI
982             "\xE1\xBE\x8B" => "\xE1\xBC\x83\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND VARIA AND PROSGEGRAMMENI
983             "\xE1\xBE\x8C" => "\xE1\xBC\x84\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND OXIA AND PROSGEGRAMMENI
984             "\xE1\xBE\x8D" => "\xE1\xBC\x85\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND OXIA AND PROSGEGRAMMENI
985             "\xE1\xBE\x8E" => "\xE1\xBC\x86\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI
986             "\xE1\xBE\x8F" => "\xE1\xBC\x87\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI
987             "\xE1\xBE\x90" => "\xE1\xBC\xA0\xCE\xB9", # GREEK SMALL LETTER ETA WITH PSILI AND YPOGEGRAMMENI
988             "\xE1\xBE\x91" => "\xE1\xBC\xA1\xCE\xB9", # GREEK SMALL LETTER ETA WITH DASIA AND YPOGEGRAMMENI
989             "\xE1\xBE\x92" => "\xE1\xBC\xA2\xCE\xB9", # GREEK SMALL LETTER ETA WITH PSILI AND VARIA AND YPOGEGRAMMENI
990             "\xE1\xBE\x93" => "\xE1\xBC\xA3\xCE\xB9", # GREEK SMALL LETTER ETA WITH DASIA AND VARIA AND YPOGEGRAMMENI
991             "\xE1\xBE\x94" => "\xE1\xBC\xA4\xCE\xB9", # GREEK SMALL LETTER ETA WITH PSILI AND OXIA AND YPOGEGRAMMENI
992             "\xE1\xBE\x95" => "\xE1\xBC\xA5\xCE\xB9", # GREEK SMALL LETTER ETA WITH DASIA AND OXIA AND YPOGEGRAMMENI
993             "\xE1\xBE\x96" => "\xE1\xBC\xA6\xCE\xB9", # GREEK SMALL LETTER ETA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI
994             "\xE1\xBE\x97" => "\xE1\xBC\xA7\xCE\xB9", # GREEK SMALL LETTER ETA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI
995             "\xE1\xBE\x98" => "\xE1\xBC\xA0\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH PSILI AND PROSGEGRAMMENI
996             "\xE1\xBE\x99" => "\xE1\xBC\xA1\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH DASIA AND PROSGEGRAMMENI
997             "\xE1\xBE\x9A" => "\xE1\xBC\xA2\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH PSILI AND VARIA AND PROSGEGRAMMENI
998             "\xE1\xBE\x9B" => "\xE1\xBC\xA3\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH DASIA AND VARIA AND PROSGEGRAMMENI
999             "\xE1\xBE\x9C" => "\xE1\xBC\xA4\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH PSILI AND OXIA AND PROSGEGRAMMENI
1000             "\xE1\xBE\x9D" => "\xE1\xBC\xA5\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH DASIA AND OXIA AND PROSGEGRAMMENI
1001             "\xE1\xBE\x9E" => "\xE1\xBC\xA6\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI
1002             "\xE1\xBE\x9F" => "\xE1\xBC\xA7\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI
1003             "\xE1\xBE\xA0" => "\xE1\xBD\xA0\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH PSILI AND YPOGEGRAMMENI
1004             "\xE1\xBE\xA1" => "\xE1\xBD\xA1\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH DASIA AND YPOGEGRAMMENI
1005             "\xE1\xBE\xA2" => "\xE1\xBD\xA2\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH PSILI AND VARIA AND YPOGEGRAMMENI
1006             "\xE1\xBE\xA3" => "\xE1\xBD\xA3\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH DASIA AND VARIA AND YPOGEGRAMMENI
1007             "\xE1\xBE\xA4" => "\xE1\xBD\xA4\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH PSILI AND OXIA AND YPOGEGRAMMENI
1008             "\xE1\xBE\xA5" => "\xE1\xBD\xA5\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH DASIA AND OXIA AND YPOGEGRAMMENI
1009             "\xE1\xBE\xA6" => "\xE1\xBD\xA6\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI
1010             "\xE1\xBE\xA7" => "\xE1\xBD\xA7\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI
1011             "\xE1\xBE\xA8" => "\xE1\xBD\xA0\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND PROSGEGRAMMENI
1012             "\xE1\xBE\xA9" => "\xE1\xBD\xA1\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND PROSGEGRAMMENI
1013             "\xE1\xBE\xAA" => "\xE1\xBD\xA2\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND VARIA AND PROSGEGRAMMENI
1014             "\xE1\xBE\xAB" => "\xE1\xBD\xA3\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND VARIA AND PROSGEGRAMMENI
1015             "\xE1\xBE\xAC" => "\xE1\xBD\xA4\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND OXIA AND PROSGEGRAMMENI
1016             "\xE1\xBE\xAD" => "\xE1\xBD\xA5\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND OXIA AND PROSGEGRAMMENI
1017             "\xE1\xBE\xAE" => "\xE1\xBD\xA6\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI
1018             "\xE1\xBE\xAF" => "\xE1\xBD\xA7\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI
1019             "\xE1\xBE\xB2" => "\xE1\xBD\xB0\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH VARIA AND YPOGEGRAMMENI
1020             "\xE1\xBE\xB3" => "\xCE\xB1\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH YPOGEGRAMMENI
1021             "\xE1\xBE\xB4" => "\xCE\xAC\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH OXIA AND YPOGEGRAMMENI
1022             "\xE1\xBE\xB6" => "\xCE\xB1\xCD\x82", # GREEK SMALL LETTER ALPHA WITH PERISPOMENI
1023             "\xE1\xBE\xB7" => "\xCE\xB1\xCD\x82\xCE\xB9", # GREEK SMALL LETTER ALPHA WITH PERISPOMENI AND YPOGEGRAMMENI
1024             "\xE1\xBE\xB8" => "\xE1\xBE\xB0", # GREEK CAPITAL LETTER ALPHA WITH VRACHY
1025             "\xE1\xBE\xB9" => "\xE1\xBE\xB1", # GREEK CAPITAL LETTER ALPHA WITH MACRON
1026             "\xE1\xBE\xBA" => "\xE1\xBD\xB0", # GREEK CAPITAL LETTER ALPHA WITH VARIA
1027             "\xE1\xBE\xBB" => "\xE1\xBD\xB1", # GREEK CAPITAL LETTER ALPHA WITH OXIA
1028             "\xE1\xBE\xBC" => "\xCE\xB1\xCE\xB9", # GREEK CAPITAL LETTER ALPHA WITH PROSGEGRAMMENI
1029             "\xE1\xBE\xBE" => "\xCE\xB9", # GREEK PROSGEGRAMMENI
1030             "\xE1\xBF\x82" => "\xE1\xBD\xB4\xCE\xB9", # GREEK SMALL LETTER ETA WITH VARIA AND YPOGEGRAMMENI
1031             "\xE1\xBF\x83" => "\xCE\xB7\xCE\xB9", # GREEK SMALL LETTER ETA WITH YPOGEGRAMMENI
1032             "\xE1\xBF\x84" => "\xCE\xAE\xCE\xB9", # GREEK SMALL LETTER ETA WITH OXIA AND YPOGEGRAMMENI
1033             "\xE1\xBF\x86" => "\xCE\xB7\xCD\x82", # GREEK SMALL LETTER ETA WITH PERISPOMENI
1034             "\xE1\xBF\x87" => "\xCE\xB7\xCD\x82\xCE\xB9", # GREEK SMALL LETTER ETA WITH PERISPOMENI AND YPOGEGRAMMENI
1035             "\xE1\xBF\x88" => "\xE1\xBD\xB2", # GREEK CAPITAL LETTER EPSILON WITH VARIA
1036             "\xE1\xBF\x89" => "\xE1\xBD\xB3", # GREEK CAPITAL LETTER EPSILON WITH OXIA
1037             "\xE1\xBF\x8A" => "\xE1\xBD\xB4", # GREEK CAPITAL LETTER ETA WITH VARIA
1038             "\xE1\xBF\x8B" => "\xE1\xBD\xB5", # GREEK CAPITAL LETTER ETA WITH OXIA
1039             "\xE1\xBF\x8C" => "\xCE\xB7\xCE\xB9", # GREEK CAPITAL LETTER ETA WITH PROSGEGRAMMENI
1040             "\xE1\xBF\x92" => "\xCE\xB9\xCC\x88\xCC\x80", # GREEK SMALL LETTER IOTA WITH DIALYTIKA AND VARIA
1041             "\xE1\xBF\x93" => "\xCE\xB9\xCC\x88\xCC\x81", # GREEK SMALL LETTER IOTA WITH DIALYTIKA AND OXIA
1042             "\xE1\xBF\x96" => "\xCE\xB9\xCD\x82", # GREEK SMALL LETTER IOTA WITH PERISPOMENI
1043             "\xE1\xBF\x97" => "\xCE\xB9\xCC\x88\xCD\x82", # GREEK SMALL LETTER IOTA WITH DIALYTIKA AND PERISPOMENI
1044             "\xE1\xBF\x98" => "\xE1\xBF\x90", # GREEK CAPITAL LETTER IOTA WITH VRACHY
1045             "\xE1\xBF\x99" => "\xE1\xBF\x91", # GREEK CAPITAL LETTER IOTA WITH MACRON
1046             "\xE1\xBF\x9A" => "\xE1\xBD\xB6", # GREEK CAPITAL LETTER IOTA WITH VARIA
1047             "\xE1\xBF\x9B" => "\xE1\xBD\xB7", # GREEK CAPITAL LETTER IOTA WITH OXIA
1048             "\xE1\xBF\xA2" => "\xCF\x85\xCC\x88\xCC\x80", # GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND VARIA
1049             "\xE1\xBF\xA3" => "\xCF\x85\xCC\x88\xCC\x81", # GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND OXIA
1050             "\xE1\xBF\xA4" => "\xCF\x81\xCC\x93", # GREEK SMALL LETTER RHO WITH PSILI
1051             "\xE1\xBF\xA6" => "\xCF\x85\xCD\x82", # GREEK SMALL LETTER UPSILON WITH PERISPOMENI
1052             "\xE1\xBF\xA7" => "\xCF\x85\xCC\x88\xCD\x82", # GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND PERISPOMENI
1053             "\xE1\xBF\xA8" => "\xE1\xBF\xA0", # GREEK CAPITAL LETTER UPSILON WITH VRACHY
1054             "\xE1\xBF\xA9" => "\xE1\xBF\xA1", # GREEK CAPITAL LETTER UPSILON WITH MACRON
1055             "\xE1\xBF\xAA" => "\xE1\xBD\xBA", # GREEK CAPITAL LETTER UPSILON WITH VARIA
1056             "\xE1\xBF\xAB" => "\xE1\xBD\xBB", # GREEK CAPITAL LETTER UPSILON WITH OXIA
1057             "\xE1\xBF\xAC" => "\xE1\xBF\xA5", # GREEK CAPITAL LETTER RHO WITH DASIA
1058             "\xE1\xBF\xB2" => "\xE1\xBD\xBC\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH VARIA AND YPOGEGRAMMENI
1059             "\xE1\xBF\xB3" => "\xCF\x89\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH YPOGEGRAMMENI
1060             "\xE1\xBF\xB4" => "\xCF\x8E\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH OXIA AND YPOGEGRAMMENI
1061             "\xE1\xBF\xB6" => "\xCF\x89\xCD\x82", # GREEK SMALL LETTER OMEGA WITH PERISPOMENI
1062             "\xE1\xBF\xB7" => "\xCF\x89\xCD\x82\xCE\xB9", # GREEK SMALL LETTER OMEGA WITH PERISPOMENI AND YPOGEGRAMMENI
1063             "\xE1\xBF\xB8" => "\xE1\xBD\xB8", # GREEK CAPITAL LETTER OMICRON WITH VARIA
1064             "\xE1\xBF\xB9" => "\xE1\xBD\xB9", # GREEK CAPITAL LETTER OMICRON WITH OXIA
1065             "\xE1\xBF\xBA" => "\xE1\xBD\xBC", # GREEK CAPITAL LETTER OMEGA WITH VARIA
1066             "\xE1\xBF\xBB" => "\xE1\xBD\xBD", # GREEK CAPITAL LETTER OMEGA WITH OXIA
1067             "\xE1\xBF\xBC" => "\xCF\x89\xCE\xB9", # GREEK CAPITAL LETTER OMEGA WITH PROSGEGRAMMENI
1068             "\xE2\x84\xA6" => "\xCF\x89", # OHM SIGN
1069             "\xE2\x84\xAA" => "\x6B", # KELVIN SIGN
1070             "\xE2\x84\xAB" => "\xC3\xA5", # ANGSTROM SIGN
1071             "\xE2\x84\xB2" => "\xE2\x85\x8E", # TURNED CAPITAL F
1072             "\xE2\x85\xA0" => "\xE2\x85\xB0", # ROMAN NUMERAL ONE
1073             "\xE2\x85\xA1" => "\xE2\x85\xB1", # ROMAN NUMERAL TWO
1074             "\xE2\x85\xA2" => "\xE2\x85\xB2", # ROMAN NUMERAL THREE
1075             "\xE2\x85\xA3" => "\xE2\x85\xB3", # ROMAN NUMERAL FOUR
1076             "\xE2\x85\xA4" => "\xE2\x85\xB4", # ROMAN NUMERAL FIVE
1077             "\xE2\x85\xA5" => "\xE2\x85\xB5", # ROMAN NUMERAL SIX
1078             "\xE2\x85\xA6" => "\xE2\x85\xB6", # ROMAN NUMERAL SEVEN
1079             "\xE2\x85\xA7" => "\xE2\x85\xB7", # ROMAN NUMERAL EIGHT
1080             "\xE2\x85\xA8" => "\xE2\x85\xB8", # ROMAN NUMERAL NINE
1081             "\xE2\x85\xA9" => "\xE2\x85\xB9", # ROMAN NUMERAL TEN
1082             "\xE2\x85\xAA" => "\xE2\x85\xBA", # ROMAN NUMERAL ELEVEN
1083             "\xE2\x85\xAB" => "\xE2\x85\xBB", # ROMAN NUMERAL TWELVE
1084             "\xE2\x85\xAC" => "\xE2\x85\xBC", # ROMAN NUMERAL FIFTY
1085             "\xE2\x85\xAD" => "\xE2\x85\xBD", # ROMAN NUMERAL ONE HUNDRED
1086             "\xE2\x85\xAE" => "\xE2\x85\xBE", # ROMAN NUMERAL FIVE HUNDRED
1087             "\xE2\x85\xAF" => "\xE2\x85\xBF", # ROMAN NUMERAL ONE THOUSAND
1088             "\xE2\x86\x83" => "\xE2\x86\x84", # ROMAN NUMERAL REVERSED ONE HUNDRED
1089             "\xE2\x92\xB6" => "\xE2\x93\x90", # CIRCLED LATIN CAPITAL LETTER A
1090             "\xE2\x92\xB7" => "\xE2\x93\x91", # CIRCLED LATIN CAPITAL LETTER B
1091             "\xE2\x92\xB8" => "\xE2\x93\x92", # CIRCLED LATIN CAPITAL LETTER C
1092             "\xE2\x92\xB9" => "\xE2\x93\x93", # CIRCLED LATIN CAPITAL LETTER D
1093             "\xE2\x92\xBA" => "\xE2\x93\x94", # CIRCLED LATIN CAPITAL LETTER E
1094             "\xE2\x92\xBB" => "\xE2\x93\x95", # CIRCLED LATIN CAPITAL LETTER F
1095             "\xE2\x92\xBC" => "\xE2\x93\x96", # CIRCLED LATIN CAPITAL LETTER G
1096             "\xE2\x92\xBD" => "\xE2\x93\x97", # CIRCLED LATIN CAPITAL LETTER H
1097             "\xE2\x92\xBE" => "\xE2\x93\x98", # CIRCLED LATIN CAPITAL LETTER I
1098             "\xE2\x92\xBF" => "\xE2\x93\x99", # CIRCLED LATIN CAPITAL LETTER J
1099             "\xE2\x93\x80" => "\xE2\x93\x9A", # CIRCLED LATIN CAPITAL LETTER K
1100             "\xE2\x93\x81" => "\xE2\x93\x9B", # CIRCLED LATIN CAPITAL LETTER L
1101             "\xE2\x93\x82" => "\xE2\x93\x9C", # CIRCLED LATIN CAPITAL LETTER M
1102             "\xE2\x93\x83" => "\xE2\x93\x9D", # CIRCLED LATIN CAPITAL LETTER N
1103             "\xE2\x93\x84" => "\xE2\x93\x9E", # CIRCLED LATIN CAPITAL LETTER O
1104             "\xE2\x93\x85" => "\xE2\x93\x9F", # CIRCLED LATIN CAPITAL LETTER P
1105             "\xE2\x93\x86" => "\xE2\x93\xA0", # CIRCLED LATIN CAPITAL LETTER Q
1106             "\xE2\x93\x87" => "\xE2\x93\xA1", # CIRCLED LATIN CAPITAL LETTER R
1107             "\xE2\x93\x88" => "\xE2\x93\xA2", # CIRCLED LATIN CAPITAL LETTER S
1108             "\xE2\x93\x89" => "\xE2\x93\xA3", # CIRCLED LATIN CAPITAL LETTER T
1109             "\xE2\x93\x8A" => "\xE2\x93\xA4", # CIRCLED LATIN CAPITAL LETTER U
1110             "\xE2\x93\x8B" => "\xE2\x93\xA5", # CIRCLED LATIN CAPITAL LETTER V
1111             "\xE2\x93\x8C" => "\xE2\x93\xA6", # CIRCLED LATIN CAPITAL LETTER W
1112             "\xE2\x93\x8D" => "\xE2\x93\xA7", # CIRCLED LATIN CAPITAL LETTER X
1113             "\xE2\x93\x8E" => "\xE2\x93\xA8", # CIRCLED LATIN CAPITAL LETTER Y
1114             "\xE2\x93\x8F" => "\xE2\x93\xA9", # CIRCLED LATIN CAPITAL LETTER Z
1115             "\xE2\xB0\x80" => "\xE2\xB0\xB0", # GLAGOLITIC CAPITAL LETTER AZU
1116             "\xE2\xB0\x81" => "\xE2\xB0\xB1", # GLAGOLITIC CAPITAL LETTER BUKY
1117             "\xE2\xB0\x82" => "\xE2\xB0\xB2", # GLAGOLITIC CAPITAL LETTER VEDE
1118             "\xE2\xB0\x83" => "\xE2\xB0\xB3", # GLAGOLITIC CAPITAL LETTER GLAGOLI
1119             "\xE2\xB0\x84" => "\xE2\xB0\xB4", # GLAGOLITIC CAPITAL LETTER DOBRO
1120             "\xE2\xB0\x85" => "\xE2\xB0\xB5", # GLAGOLITIC CAPITAL LETTER YESTU
1121             "\xE2\xB0\x86" => "\xE2\xB0\xB6", # GLAGOLITIC CAPITAL LETTER ZHIVETE
1122             "\xE2\xB0\x87" => "\xE2\xB0\xB7", # GLAGOLITIC CAPITAL LETTER DZELO
1123             "\xE2\xB0\x88" => "\xE2\xB0\xB8", # GLAGOLITIC CAPITAL LETTER ZEMLJA
1124             "\xE2\xB0\x89" => "\xE2\xB0\xB9", # GLAGOLITIC CAPITAL LETTER IZHE
1125             "\xE2\xB0\x8A" => "\xE2\xB0\xBA", # GLAGOLITIC CAPITAL LETTER INITIAL IZHE
1126             "\xE2\xB0\x8B" => "\xE2\xB0\xBB", # GLAGOLITIC CAPITAL LETTER I
1127             "\xE2\xB0\x8C" => "\xE2\xB0\xBC", # GLAGOLITIC CAPITAL LETTER DJERVI
1128             "\xE2\xB0\x8D" => "\xE2\xB0\xBD", # GLAGOLITIC CAPITAL LETTER KAKO
1129             "\xE2\xB0\x8E" => "\xE2\xB0\xBE", # GLAGOLITIC CAPITAL LETTER LJUDIJE
1130             "\xE2\xB0\x8F" => "\xE2\xB0\xBF", # GLAGOLITIC CAPITAL LETTER MYSLITE
1131             "\xE2\xB0\x90" => "\xE2\xB1\x80", # GLAGOLITIC CAPITAL LETTER NASHI
1132             "\xE2\xB0\x91" => "\xE2\xB1\x81", # GLAGOLITIC CAPITAL LETTER ONU
1133             "\xE2\xB0\x92" => "\xE2\xB1\x82", # GLAGOLITIC CAPITAL LETTER POKOJI
1134             "\xE2\xB0\x93" => "\xE2\xB1\x83", # GLAGOLITIC CAPITAL LETTER RITSI
1135             "\xE2\xB0\x94" => "\xE2\xB1\x84", # GLAGOLITIC CAPITAL LETTER SLOVO
1136             "\xE2\xB0\x95" => "\xE2\xB1\x85", # GLAGOLITIC CAPITAL LETTER TVRIDO
1137             "\xE2\xB0\x96" => "\xE2\xB1\x86", # GLAGOLITIC CAPITAL LETTER UKU
1138             "\xE2\xB0\x97" => "\xE2\xB1\x87", # GLAGOLITIC CAPITAL LETTER FRITU
1139             "\xE2\xB0\x98" => "\xE2\xB1\x88", # GLAGOLITIC CAPITAL LETTER HERU
1140             "\xE2\xB0\x99" => "\xE2\xB1\x89", # GLAGOLITIC CAPITAL LETTER OTU
1141             "\xE2\xB0\x9A" => "\xE2\xB1\x8A", # GLAGOLITIC CAPITAL LETTER PE
1142             "\xE2\xB0\x9B" => "\xE2\xB1\x8B", # GLAGOLITIC CAPITAL LETTER SHTA
1143             "\xE2\xB0\x9C" => "\xE2\xB1\x8C", # GLAGOLITIC CAPITAL LETTER TSI
1144             "\xE2\xB0\x9D" => "\xE2\xB1\x8D", # GLAGOLITIC CAPITAL LETTER CHRIVI
1145             "\xE2\xB0\x9E" => "\xE2\xB1\x8E", # GLAGOLITIC CAPITAL LETTER SHA
1146             "\xE2\xB0\x9F" => "\xE2\xB1\x8F", # GLAGOLITIC CAPITAL LETTER YERU
1147             "\xE2\xB0\xA0" => "\xE2\xB1\x90", # GLAGOLITIC CAPITAL LETTER YERI
1148             "\xE2\xB0\xA1" => "\xE2\xB1\x91", # GLAGOLITIC CAPITAL LETTER YATI
1149             "\xE2\xB0\xA2" => "\xE2\xB1\x92", # GLAGOLITIC CAPITAL LETTER SPIDERY HA
1150             "\xE2\xB0\xA3" => "\xE2\xB1\x93", # GLAGOLITIC CAPITAL LETTER YU
1151             "\xE2\xB0\xA4" => "\xE2\xB1\x94", # GLAGOLITIC CAPITAL LETTER SMALL YUS
1152             "\xE2\xB0\xA5" => "\xE2\xB1\x95", # GLAGOLITIC CAPITAL LETTER SMALL YUS WITH TAIL
1153             "\xE2\xB0\xA6" => "\xE2\xB1\x96", # GLAGOLITIC CAPITAL LETTER YO
1154             "\xE2\xB0\xA7" => "\xE2\xB1\x97", # GLAGOLITIC CAPITAL LETTER IOTATED SMALL YUS
1155             "\xE2\xB0\xA8" => "\xE2\xB1\x98", # GLAGOLITIC CAPITAL LETTER BIG YUS
1156             "\xE2\xB0\xA9" => "\xE2\xB1\x99", # GLAGOLITIC CAPITAL LETTER IOTATED BIG YUS
1157             "\xE2\xB0\xAA" => "\xE2\xB1\x9A", # GLAGOLITIC CAPITAL LETTER FITA
1158             "\xE2\xB0\xAB" => "\xE2\xB1\x9B", # GLAGOLITIC CAPITAL LETTER IZHITSA
1159             "\xE2\xB0\xAC" => "\xE2\xB1\x9C", # GLAGOLITIC CAPITAL LETTER SHTAPIC
1160             "\xE2\xB0\xAD" => "\xE2\xB1\x9D", # GLAGOLITIC CAPITAL LETTER TROKUTASTI A
1161             "\xE2\xB0\xAE" => "\xE2\xB1\x9E", # GLAGOLITIC CAPITAL LETTER LATINATE MYSLITE
1162             "\xE2\xB1\xA0" => "\xE2\xB1\xA1", # LATIN CAPITAL LETTER L WITH DOUBLE BAR
1163             "\xE2\xB1\xA2" => "\xC9\xAB", # LATIN CAPITAL LETTER L WITH MIDDLE TILDE
1164             "\xE2\xB1\xA3" => "\xE1\xB5\xBD", # LATIN CAPITAL LETTER P WITH STROKE
1165             "\xE2\xB1\xA4" => "\xC9\xBD", # LATIN CAPITAL LETTER R WITH TAIL
1166             "\xE2\xB1\xA7" => "\xE2\xB1\xA8", # LATIN CAPITAL LETTER H WITH DESCENDER
1167             "\xE2\xB1\xA9" => "\xE2\xB1\xAA", # LATIN CAPITAL LETTER K WITH DESCENDER
1168             "\xE2\xB1\xAB" => "\xE2\xB1\xAC", # LATIN CAPITAL LETTER Z WITH DESCENDER
1169             "\xE2\xB1\xAD" => "\xC9\x91", # LATIN CAPITAL LETTER ALPHA
1170             "\xE2\xB1\xAE" => "\xC9\xB1", # LATIN CAPITAL LETTER M WITH HOOK
1171             "\xE2\xB1\xAF" => "\xC9\x90", # LATIN CAPITAL LETTER TURNED A
1172             "\xE2\xB1\xB0" => "\xC9\x92", # LATIN CAPITAL LETTER TURNED ALPHA
1173             "\xE2\xB1\xB2" => "\xE2\xB1\xB3", # LATIN CAPITAL LETTER W WITH HOOK
1174             "\xE2\xB1\xB5" => "\xE2\xB1\xB6", # LATIN CAPITAL LETTER HALF H
1175             "\xE2\xB1\xBE" => "\xC8\xBF", # LATIN CAPITAL LETTER S WITH SWASH TAIL
1176             "\xE2\xB1\xBF" => "\xC9\x80", # LATIN CAPITAL LETTER Z WITH SWASH TAIL
1177             "\xE2\xB2\x80" => "\xE2\xB2\x81", # COPTIC CAPITAL LETTER ALFA
1178             "\xE2\xB2\x82" => "\xE2\xB2\x83", # COPTIC CAPITAL LETTER VIDA
1179             "\xE2\xB2\x84" => "\xE2\xB2\x85", # COPTIC CAPITAL LETTER GAMMA
1180             "\xE2\xB2\x86" => "\xE2\xB2\x87", # COPTIC CAPITAL LETTER DALDA
1181             "\xE2\xB2\x88" => "\xE2\xB2\x89", # COPTIC CAPITAL LETTER EIE
1182             "\xE2\xB2\x8A" => "\xE2\xB2\x8B", # COPTIC CAPITAL LETTER SOU
1183             "\xE2\xB2\x8C" => "\xE2\xB2\x8D", # COPTIC CAPITAL LETTER ZATA
1184             "\xE2\xB2\x8E" => "\xE2\xB2\x8F", # COPTIC CAPITAL LETTER HATE
1185             "\xE2\xB2\x90" => "\xE2\xB2\x91", # COPTIC CAPITAL LETTER THETHE
1186             "\xE2\xB2\x92" => "\xE2\xB2\x93", # COPTIC CAPITAL LETTER IAUDA
1187             "\xE2\xB2\x94" => "\xE2\xB2\x95", # COPTIC CAPITAL LETTER KAPA
1188             "\xE2\xB2\x96" => "\xE2\xB2\x97", # COPTIC CAPITAL LETTER LAULA
1189             "\xE2\xB2\x98" => "\xE2\xB2\x99", # COPTIC CAPITAL LETTER MI
1190             "\xE2\xB2\x9A" => "\xE2\xB2\x9B", # COPTIC CAPITAL LETTER NI
1191             "\xE2\xB2\x9C" => "\xE2\xB2\x9D", # COPTIC CAPITAL LETTER KSI
1192             "\xE2\xB2\x9E" => "\xE2\xB2\x9F", # COPTIC CAPITAL LETTER O
1193             "\xE2\xB2\xA0" => "\xE2\xB2\xA1", # COPTIC CAPITAL LETTER PI
1194             "\xE2\xB2\xA2" => "\xE2\xB2\xA3", # COPTIC CAPITAL LETTER RO
1195             "\xE2\xB2\xA4" => "\xE2\xB2\xA5", # COPTIC CAPITAL LETTER SIMA
1196             "\xE2\xB2\xA6" => "\xE2\xB2\xA7", # COPTIC CAPITAL LETTER TAU
1197             "\xE2\xB2\xA8" => "\xE2\xB2\xA9", # COPTIC CAPITAL LETTER UA
1198             "\xE2\xB2\xAA" => "\xE2\xB2\xAB", # COPTIC CAPITAL LETTER FI
1199             "\xE2\xB2\xAC" => "\xE2\xB2\xAD", # COPTIC CAPITAL LETTER KHI
1200             "\xE2\xB2\xAE" => "\xE2\xB2\xAF", # COPTIC CAPITAL LETTER PSI
1201             "\xE2\xB2\xB0" => "\xE2\xB2\xB1", # COPTIC CAPITAL LETTER OOU
1202             "\xE2\xB2\xB2" => "\xE2\xB2\xB3", # COPTIC CAPITAL LETTER DIALECT-P ALEF
1203             "\xE2\xB2\xB4" => "\xE2\xB2\xB5", # COPTIC CAPITAL LETTER OLD COPTIC AIN
1204             "\xE2\xB2\xB6" => "\xE2\xB2\xB7", # COPTIC CAPITAL LETTER CRYPTOGRAMMIC EIE
1205             "\xE2\xB2\xB8" => "\xE2\xB2\xB9", # COPTIC CAPITAL LETTER DIALECT-P KAPA
1206             "\xE2\xB2\xBA" => "\xE2\xB2\xBB", # COPTIC CAPITAL LETTER DIALECT-P NI
1207             "\xE2\xB2\xBC" => "\xE2\xB2\xBD", # COPTIC CAPITAL LETTER CRYPTOGRAMMIC NI
1208             "\xE2\xB2\xBE" => "\xE2\xB2\xBF", # COPTIC CAPITAL LETTER OLD COPTIC OOU
1209             "\xE2\xB3\x80" => "\xE2\xB3\x81", # COPTIC CAPITAL LETTER SAMPI
1210             "\xE2\xB3\x82" => "\xE2\xB3\x83", # COPTIC CAPITAL LETTER CROSSED SHEI
1211             "\xE2\xB3\x84" => "\xE2\xB3\x85", # COPTIC CAPITAL LETTER OLD COPTIC SHEI
1212             "\xE2\xB3\x86" => "\xE2\xB3\x87", # COPTIC CAPITAL LETTER OLD COPTIC ESH
1213             "\xE2\xB3\x88" => "\xE2\xB3\x89", # COPTIC CAPITAL LETTER AKHMIMIC KHEI
1214             "\xE2\xB3\x8A" => "\xE2\xB3\x8B", # COPTIC CAPITAL LETTER DIALECT-P HORI
1215             "\xE2\xB3\x8C" => "\xE2\xB3\x8D", # COPTIC CAPITAL LETTER OLD COPTIC HORI
1216             "\xE2\xB3\x8E" => "\xE2\xB3\x8F", # COPTIC CAPITAL LETTER OLD COPTIC HA
1217             "\xE2\xB3\x90" => "\xE2\xB3\x91", # COPTIC CAPITAL LETTER L-SHAPED HA
1218             "\xE2\xB3\x92" => "\xE2\xB3\x93", # COPTIC CAPITAL LETTER OLD COPTIC HEI
1219             "\xE2\xB3\x94" => "\xE2\xB3\x95", # COPTIC CAPITAL LETTER OLD COPTIC HAT
1220             "\xE2\xB3\x96" => "\xE2\xB3\x97", # COPTIC CAPITAL LETTER OLD COPTIC GANGIA
1221             "\xE2\xB3\x98" => "\xE2\xB3\x99", # COPTIC CAPITAL LETTER OLD COPTIC DJA
1222             "\xE2\xB3\x9A" => "\xE2\xB3\x9B", # COPTIC CAPITAL LETTER OLD COPTIC SHIMA
1223             "\xE2\xB3\x9C" => "\xE2\xB3\x9D", # COPTIC CAPITAL LETTER OLD NUBIAN SHIMA
1224             "\xE2\xB3\x9E" => "\xE2\xB3\x9F", # COPTIC CAPITAL LETTER OLD NUBIAN NGI
1225             "\xE2\xB3\xA0" => "\xE2\xB3\xA1", # COPTIC CAPITAL LETTER OLD NUBIAN NYI
1226             "\xE2\xB3\xA2" => "\xE2\xB3\xA3", # COPTIC CAPITAL LETTER OLD NUBIAN WAU
1227             "\xE2\xB3\xAB" => "\xE2\xB3\xAC", # COPTIC CAPITAL LETTER CRYPTOGRAMMIC SHEI
1228             "\xE2\xB3\xAD" => "\xE2\xB3\xAE", # COPTIC CAPITAL LETTER CRYPTOGRAMMIC GANGIA
1229             "\xE2\xB3\xB2" => "\xE2\xB3\xB3", # COPTIC CAPITAL LETTER BOHAIRIC KHEI
1230             "\xEA\x99\x80" => "\xEA\x99\x81", # CYRILLIC CAPITAL LETTER ZEMLYA
1231             "\xEA\x99\x82" => "\xEA\x99\x83", # CYRILLIC CAPITAL LETTER DZELO
1232             "\xEA\x99\x84" => "\xEA\x99\x85", # CYRILLIC CAPITAL LETTER REVERSED DZE
1233             "\xEA\x99\x86" => "\xEA\x99\x87", # CYRILLIC CAPITAL LETTER IOTA
1234             "\xEA\x99\x88" => "\xEA\x99\x89", # CYRILLIC CAPITAL LETTER DJERV
1235             "\xEA\x99\x8A" => "\xEA\x99\x8B", # CYRILLIC CAPITAL LETTER MONOGRAPH UK
1236             "\xEA\x99\x8C" => "\xEA\x99\x8D", # CYRILLIC CAPITAL LETTER BROAD OMEGA
1237             "\xEA\x99\x8E" => "\xEA\x99\x8F", # CYRILLIC CAPITAL LETTER NEUTRAL YER
1238             "\xEA\x99\x90" => "\xEA\x99\x91", # CYRILLIC CAPITAL LETTER YERU WITH BACK YER
1239             "\xEA\x99\x92" => "\xEA\x99\x93", # CYRILLIC CAPITAL LETTER IOTIFIED YAT
1240             "\xEA\x99\x94" => "\xEA\x99\x95", # CYRILLIC CAPITAL LETTER REVERSED YU
1241             "\xEA\x99\x96" => "\xEA\x99\x97", # CYRILLIC CAPITAL LETTER IOTIFIED A
1242             "\xEA\x99\x98" => "\xEA\x99\x99", # CYRILLIC CAPITAL LETTER CLOSED LITTLE YUS
1243             "\xEA\x99\x9A" => "\xEA\x99\x9B", # CYRILLIC CAPITAL LETTER BLENDED YUS
1244             "\xEA\x99\x9C" => "\xEA\x99\x9D", # CYRILLIC CAPITAL LETTER IOTIFIED CLOSED LITTLE YUS
1245             "\xEA\x99\x9E" => "\xEA\x99\x9F", # CYRILLIC CAPITAL LETTER YN
1246             "\xEA\x99\xA0" => "\xEA\x99\xA1", # CYRILLIC CAPITAL LETTER REVERSED TSE
1247             "\xEA\x99\xA2" => "\xEA\x99\xA3", # CYRILLIC CAPITAL LETTER SOFT DE
1248             "\xEA\x99\xA4" => "\xEA\x99\xA5", # CYRILLIC CAPITAL LETTER SOFT EL
1249             "\xEA\x99\xA6" => "\xEA\x99\xA7", # CYRILLIC CAPITAL LETTER SOFT EM
1250             "\xEA\x99\xA8" => "\xEA\x99\xA9", # CYRILLIC CAPITAL LETTER MONOCULAR O
1251             "\xEA\x99\xAA" => "\xEA\x99\xAB", # CYRILLIC CAPITAL LETTER BINOCULAR O
1252             "\xEA\x99\xAC" => "\xEA\x99\xAD", # CYRILLIC CAPITAL LETTER DOUBLE MONOCULAR O
1253             "\xEA\x9A\x80" => "\xEA\x9A\x81", # CYRILLIC CAPITAL LETTER DWE
1254             "\xEA\x9A\x82" => "\xEA\x9A\x83", # CYRILLIC CAPITAL LETTER DZWE
1255             "\xEA\x9A\x84" => "\xEA\x9A\x85", # CYRILLIC CAPITAL LETTER ZHWE
1256             "\xEA\x9A\x86" => "\xEA\x9A\x87", # CYRILLIC CAPITAL LETTER CCHE
1257             "\xEA\x9A\x88" => "\xEA\x9A\x89", # CYRILLIC CAPITAL LETTER DZZE
1258             "\xEA\x9A\x8A" => "\xEA\x9A\x8B", # CYRILLIC CAPITAL LETTER TE WITH MIDDLE HOOK
1259             "\xEA\x9A\x8C" => "\xEA\x9A\x8D", # CYRILLIC CAPITAL LETTER TWE
1260             "\xEA\x9A\x8E" => "\xEA\x9A\x8F", # CYRILLIC CAPITAL LETTER TSWE
1261             "\xEA\x9A\x90" => "\xEA\x9A\x91", # CYRILLIC CAPITAL LETTER TSSE
1262             "\xEA\x9A\x92" => "\xEA\x9A\x93", # CYRILLIC CAPITAL LETTER TCHE
1263             "\xEA\x9A\x94" => "\xEA\x9A\x95", # CYRILLIC CAPITAL LETTER HWE
1264             "\xEA\x9A\x96" => "\xEA\x9A\x97", # CYRILLIC CAPITAL LETTER SHWE
1265             "\xEA\x9A\x98" => "\xEA\x9A\x99", # CYRILLIC CAPITAL LETTER DOUBLE O
1266             "\xEA\x9A\x9A" => "\xEA\x9A\x9B", # CYRILLIC CAPITAL LETTER CROSSED O
1267             "\xEA\x9C\xA2" => "\xEA\x9C\xA3", # LATIN CAPITAL LETTER EGYPTOLOGICAL ALEF
1268             "\xEA\x9C\xA4" => "\xEA\x9C\xA5", # LATIN CAPITAL LETTER EGYPTOLOGICAL AIN
1269             "\xEA\x9C\xA6" => "\xEA\x9C\xA7", # LATIN CAPITAL LETTER HENG
1270             "\xEA\x9C\xA8" => "\xEA\x9C\xA9", # LATIN CAPITAL LETTER TZ
1271             "\xEA\x9C\xAA" => "\xEA\x9C\xAB", # LATIN CAPITAL LETTER TRESILLO
1272             "\xEA\x9C\xAC" => "\xEA\x9C\xAD", # LATIN CAPITAL LETTER CUATRILLO
1273             "\xEA\x9C\xAE" => "\xEA\x9C\xAF", # LATIN CAPITAL LETTER CUATRILLO WITH COMMA
1274             "\xEA\x9C\xB2" => "\xEA\x9C\xB3", # LATIN CAPITAL LETTER AA
1275             "\xEA\x9C\xB4" => "\xEA\x9C\xB5", # LATIN CAPITAL LETTER AO
1276             "\xEA\x9C\xB6" => "\xEA\x9C\xB7", # LATIN CAPITAL LETTER AU
1277             "\xEA\x9C\xB8" => "\xEA\x9C\xB9", # LATIN CAPITAL LETTER AV
1278             "\xEA\x9C\xBA" => "\xEA\x9C\xBB", # LATIN CAPITAL LETTER AV WITH HORIZONTAL BAR
1279             "\xEA\x9C\xBC" => "\xEA\x9C\xBD", # LATIN CAPITAL LETTER AY
1280             "\xEA\x9C\xBE" => "\xEA\x9C\xBF", # LATIN CAPITAL LETTER REVERSED C WITH DOT
1281             "\xEA\x9D\x80" => "\xEA\x9D\x81", # LATIN CAPITAL LETTER K WITH STROKE
1282             "\xEA\x9D\x82" => "\xEA\x9D\x83", # LATIN CAPITAL LETTER K WITH DIAGONAL STROKE
1283             "\xEA\x9D\x84" => "\xEA\x9D\x85", # LATIN CAPITAL LETTER K WITH STROKE AND DIAGONAL STROKE
1284             "\xEA\x9D\x86" => "\xEA\x9D\x87", # LATIN CAPITAL LETTER BROKEN L
1285             "\xEA\x9D\x88" => "\xEA\x9D\x89", # LATIN CAPITAL LETTER L WITH HIGH STROKE
1286             "\xEA\x9D\x8A" => "\xEA\x9D\x8B", # LATIN CAPITAL LETTER O WITH LONG STROKE OVERLAY
1287             "\xEA\x9D\x8C" => "\xEA\x9D\x8D", # LATIN CAPITAL LETTER O WITH LOOP
1288             "\xEA\x9D\x8E" => "\xEA\x9D\x8F", # LATIN CAPITAL LETTER OO
1289             "\xEA\x9D\x90" => "\xEA\x9D\x91", # LATIN CAPITAL LETTER P WITH STROKE THROUGH DESCENDER
1290             "\xEA\x9D\x92" => "\xEA\x9D\x93", # LATIN CAPITAL LETTER P WITH FLOURISH
1291             "\xEA\x9D\x94" => "\xEA\x9D\x95", # LATIN CAPITAL LETTER P WITH SQUIRREL TAIL
1292             "\xEA\x9D\x96" => "\xEA\x9D\x97", # LATIN CAPITAL LETTER Q WITH STROKE THROUGH DESCENDER
1293             "\xEA\x9D\x98" => "\xEA\x9D\x99", # LATIN CAPITAL LETTER Q WITH DIAGONAL STROKE
1294             "\xEA\x9D\x9A" => "\xEA\x9D\x9B", # LATIN CAPITAL LETTER R ROTUNDA
1295             "\xEA\x9D\x9C" => "\xEA\x9D\x9D", # LATIN CAPITAL LETTER RUM ROTUNDA
1296             "\xEA\x9D\x9E" => "\xEA\x9D\x9F", # LATIN CAPITAL LETTER V WITH DIAGONAL STROKE
1297             "\xEA\x9D\xA0" => "\xEA\x9D\xA1", # LATIN CAPITAL LETTER VY
1298             "\xEA\x9D\xA2" => "\xEA\x9D\xA3", # LATIN CAPITAL LETTER VISIGOTHIC Z
1299             "\xEA\x9D\xA4" => "\xEA\x9D\xA5", # LATIN CAPITAL LETTER THORN WITH STROKE
1300             "\xEA\x9D\xA6" => "\xEA\x9D\xA7", # LATIN CAPITAL LETTER THORN WITH STROKE THROUGH DESCENDER
1301             "\xEA\x9D\xA8" => "\xEA\x9D\xA9", # LATIN CAPITAL LETTER VEND
1302             "\xEA\x9D\xAA" => "\xEA\x9D\xAB", # LATIN CAPITAL LETTER ET
1303             "\xEA\x9D\xAC" => "\xEA\x9D\xAD", # LATIN CAPITAL LETTER IS
1304             "\xEA\x9D\xAE" => "\xEA\x9D\xAF", # LATIN CAPITAL LETTER CON
1305             "\xEA\x9D\xB9" => "\xEA\x9D\xBA", # LATIN CAPITAL LETTER INSULAR D
1306             "\xEA\x9D\xBB" => "\xEA\x9D\xBC", # LATIN CAPITAL LETTER INSULAR F
1307             "\xEA\x9D\xBD" => "\xE1\xB5\xB9", # LATIN CAPITAL LETTER INSULAR G
1308             "\xEA\x9D\xBE" => "\xEA\x9D\xBF", # LATIN CAPITAL LETTER TURNED INSULAR G
1309             "\xEA\x9E\x80" => "\xEA\x9E\x81", # LATIN CAPITAL LETTER TURNED L
1310             "\xEA\x9E\x82" => "\xEA\x9E\x83", # LATIN CAPITAL LETTER INSULAR R
1311             "\xEA\x9E\x84" => "\xEA\x9E\x85", # LATIN CAPITAL LETTER INSULAR S
1312             "\xEA\x9E\x86" => "\xEA\x9E\x87", # LATIN CAPITAL LETTER INSULAR T
1313             "\xEA\x9E\x8B" => "\xEA\x9E\x8C", # LATIN CAPITAL LETTER SALTILLO
1314             "\xEA\x9E\x8D" => "\xC9\xA5", # LATIN CAPITAL LETTER TURNED H
1315             "\xEA\x9E\x90" => "\xEA\x9E\x91", # LATIN CAPITAL LETTER N WITH DESCENDER
1316             "\xEA\x9E\x92" => "\xEA\x9E\x93", # LATIN CAPITAL LETTER C WITH BAR
1317             "\xEA\x9E\x96" => "\xEA\x9E\x97", # LATIN CAPITAL LETTER B WITH FLOURISH
1318             "\xEA\x9E\x98" => "\xEA\x9E\x99", # LATIN CAPITAL LETTER F WITH STROKE
1319             "\xEA\x9E\x9A" => "\xEA\x9E\x9B", # LATIN CAPITAL LETTER VOLAPUK AE
1320             "\xEA\x9E\x9C" => "\xEA\x9E\x9D", # LATIN CAPITAL LETTER VOLAPUK OE
1321             "\xEA\x9E\x9E" => "\xEA\x9E\x9F", # LATIN CAPITAL LETTER VOLAPUK UE
1322             "\xEA\x9E\xA0" => "\xEA\x9E\xA1", # LATIN CAPITAL LETTER G WITH OBLIQUE STROKE
1323             "\xEA\x9E\xA2" => "\xEA\x9E\xA3", # LATIN CAPITAL LETTER K WITH OBLIQUE STROKE
1324             "\xEA\x9E\xA4" => "\xEA\x9E\xA5", # LATIN CAPITAL LETTER N WITH OBLIQUE STROKE
1325             "\xEA\x9E\xA6" => "\xEA\x9E\xA7", # LATIN CAPITAL LETTER R WITH OBLIQUE STROKE
1326             "\xEA\x9E\xA8" => "\xEA\x9E\xA9", # LATIN CAPITAL LETTER S WITH OBLIQUE STROKE
1327             "\xEA\x9E\xAA" => "\xC9\xA6", # LATIN CAPITAL LETTER H WITH HOOK
1328             "\xEA\x9E\xAB" => "\xC9\x9C", # LATIN CAPITAL LETTER REVERSED OPEN E
1329             "\xEA\x9E\xAC" => "\xC9\xA1", # LATIN CAPITAL LETTER SCRIPT G
1330             "\xEA\x9E\xAD" => "\xC9\xAC", # LATIN CAPITAL LETTER L WITH BELT
1331             "\xEA\x9E\xAE" => "\xC9\xAA", # LATIN CAPITAL LETTER SMALL CAPITAL I
1332             "\xEA\x9E\xB0" => "\xCA\x9E", # LATIN CAPITAL LETTER TURNED K
1333             "\xEA\x9E\xB1" => "\xCA\x87", # LATIN CAPITAL LETTER TURNED T
1334             "\xEA\x9E\xB2" => "\xCA\x9D", # LATIN CAPITAL LETTER J WITH CROSSED-TAIL
1335             "\xEA\x9E\xB3" => "\xEA\xAD\x93", # LATIN CAPITAL LETTER CHI
1336             "\xEA\x9E\xB4" => "\xEA\x9E\xB5", # LATIN CAPITAL LETTER BETA
1337             "\xEA\x9E\xB6" => "\xEA\x9E\xB7", # LATIN CAPITAL LETTER OMEGA
1338             "\xEA\x9E\xB8" => "\xEA\x9E\xB9", # LATIN CAPITAL LETTER U WITH STROKE
1339             "\xEA\x9E\xBA" => "\xEA\x9E\xBB", # LATIN CAPITAL LETTER GLOTTAL A
1340             "\xEA\x9E\xBC" => "\xEA\x9E\xBD", # LATIN CAPITAL LETTER GLOTTAL I
1341             "\xEA\x9E\xBE" => "\xEA\x9E\xBF", # LATIN CAPITAL LETTER GLOTTAL U
1342             "\xEA\x9F\x82" => "\xEA\x9F\x83", # LATIN CAPITAL LETTER ANGLICANA W
1343             "\xEA\x9F\x84" => "\xEA\x9E\x94", # LATIN CAPITAL LETTER C WITH PALATAL HOOK
1344             "\xEA\x9F\x85" => "\xCA\x82", # LATIN CAPITAL LETTER S WITH HOOK
1345             "\xEA\x9F\x86" => "\xE1\xB6\x8E", # LATIN CAPITAL LETTER Z WITH PALATAL HOOK
1346             "\xEA\xAD\xB0" => "\xE1\x8E\xA0", # CHEROKEE SMALL LETTER A
1347             "\xEA\xAD\xB1" => "\xE1\x8E\xA1", # CHEROKEE SMALL LETTER E
1348             "\xEA\xAD\xB2" => "\xE1\x8E\xA2", # CHEROKEE SMALL LETTER I
1349             "\xEA\xAD\xB3" => "\xE1\x8E\xA3", # CHEROKEE SMALL LETTER O
1350             "\xEA\xAD\xB4" => "\xE1\x8E\xA4", # CHEROKEE SMALL LETTER U
1351             "\xEA\xAD\xB5" => "\xE1\x8E\xA5", # CHEROKEE SMALL LETTER V
1352             "\xEA\xAD\xB6" => "\xE1\x8E\xA6", # CHEROKEE SMALL LETTER GA
1353             "\xEA\xAD\xB7" => "\xE1\x8E\xA7", # CHEROKEE SMALL LETTER KA
1354             "\xEA\xAD\xB8" => "\xE1\x8E\xA8", # CHEROKEE SMALL LETTER GE
1355             "\xEA\xAD\xB9" => "\xE1\x8E\xA9", # CHEROKEE SMALL LETTER GI
1356             "\xEA\xAD\xBA" => "\xE1\x8E\xAA", # CHEROKEE SMALL LETTER GO
1357             "\xEA\xAD\xBB" => "\xE1\x8E\xAB", # CHEROKEE SMALL LETTER GU
1358             "\xEA\xAD\xBC" => "\xE1\x8E\xAC", # CHEROKEE SMALL LETTER GV
1359             "\xEA\xAD\xBD" => "\xE1\x8E\xAD", # CHEROKEE SMALL LETTER HA
1360             "\xEA\xAD\xBE" => "\xE1\x8E\xAE", # CHEROKEE SMALL LETTER HE
1361             "\xEA\xAD\xBF" => "\xE1\x8E\xAF", # CHEROKEE SMALL LETTER HI
1362             "\xEA\xAE\x80" => "\xE1\x8E\xB0", # CHEROKEE SMALL LETTER HO
1363             "\xEA\xAE\x81" => "\xE1\x8E\xB1", # CHEROKEE SMALL LETTER HU
1364             "\xEA\xAE\x82" => "\xE1\x8E\xB2", # CHEROKEE SMALL LETTER HV
1365             "\xEA\xAE\x83" => "\xE1\x8E\xB3", # CHEROKEE SMALL LETTER LA
1366             "\xEA\xAE\x84" => "\xE1\x8E\xB4", # CHEROKEE SMALL LETTER LE
1367             "\xEA\xAE\x85" => "\xE1\x8E\xB5", # CHEROKEE SMALL LETTER LI
1368             "\xEA\xAE\x86" => "\xE1\x8E\xB6", # CHEROKEE SMALL LETTER LO
1369             "\xEA\xAE\x87" => "\xE1\x8E\xB7", # CHEROKEE SMALL LETTER LU
1370             "\xEA\xAE\x88" => "\xE1\x8E\xB8", # CHEROKEE SMALL LETTER LV
1371             "\xEA\xAE\x89" => "\xE1\x8E\xB9", # CHEROKEE SMALL LETTER MA
1372             "\xEA\xAE\x8A" => "\xE1\x8E\xBA", # CHEROKEE SMALL LETTER ME
1373             "\xEA\xAE\x8B" => "\xE1\x8E\xBB", # CHEROKEE SMALL LETTER MI
1374             "\xEA\xAE\x8C" => "\xE1\x8E\xBC", # CHEROKEE SMALL LETTER MO
1375             "\xEA\xAE\x8D" => "\xE1\x8E\xBD", # CHEROKEE SMALL LETTER MU
1376             "\xEA\xAE\x8E" => "\xE1\x8E\xBE", # CHEROKEE SMALL LETTER NA
1377             "\xEA\xAE\x8F" => "\xE1\x8E\xBF", # CHEROKEE SMALL LETTER HNA
1378             "\xEA\xAE\x90" => "\xE1\x8F\x80", # CHEROKEE SMALL LETTER NAH
1379             "\xEA\xAE\x91" => "\xE1\x8F\x81", # CHEROKEE SMALL LETTER NE
1380             "\xEA\xAE\x92" => "\xE1\x8F\x82", # CHEROKEE SMALL LETTER NI
1381             "\xEA\xAE\x93" => "\xE1\x8F\x83", # CHEROKEE SMALL LETTER NO
1382             "\xEA\xAE\x94" => "\xE1\x8F\x84", # CHEROKEE SMALL LETTER NU
1383             "\xEA\xAE\x95" => "\xE1\x8F\x85", # CHEROKEE SMALL LETTER NV
1384             "\xEA\xAE\x96" => "\xE1\x8F\x86", # CHEROKEE SMALL LETTER QUA
1385             "\xEA\xAE\x97" => "\xE1\x8F\x87", # CHEROKEE SMALL LETTER QUE
1386             "\xEA\xAE\x98" => "\xE1\x8F\x88", # CHEROKEE SMALL LETTER QUI
1387             "\xEA\xAE\x99" => "\xE1\x8F\x89", # CHEROKEE SMALL LETTER QUO
1388             "\xEA\xAE\x9A" => "\xE1\x8F\x8A", # CHEROKEE SMALL LETTER QUU
1389             "\xEA\xAE\x9B" => "\xE1\x8F\x8B", # CHEROKEE SMALL LETTER QUV
1390             "\xEA\xAE\x9C" => "\xE1\x8F\x8C", # CHEROKEE SMALL LETTER SA
1391             "\xEA\xAE\x9D" => "\xE1\x8F\x8D", # CHEROKEE SMALL LETTER S
1392             "\xEA\xAE\x9E" => "\xE1\x8F\x8E", # CHEROKEE SMALL LETTER SE
1393             "\xEA\xAE\x9F" => "\xE1\x8F\x8F", # CHEROKEE SMALL LETTER SI
1394             "\xEA\xAE\xA0" => "\xE1\x8F\x90", # CHEROKEE SMALL LETTER SO
1395             "\xEA\xAE\xA1" => "\xE1\x8F\x91", # CHEROKEE SMALL LETTER SU
1396             "\xEA\xAE\xA2" => "\xE1\x8F\x92", # CHEROKEE SMALL LETTER SV
1397             "\xEA\xAE\xA3" => "\xE1\x8F\x93", # CHEROKEE SMALL LETTER DA
1398             "\xEA\xAE\xA4" => "\xE1\x8F\x94", # CHEROKEE SMALL LETTER TA
1399             "\xEA\xAE\xA5" => "\xE1\x8F\x95", # CHEROKEE SMALL LETTER DE
1400             "\xEA\xAE\xA6" => "\xE1\x8F\x96", # CHEROKEE SMALL LETTER TE
1401             "\xEA\xAE\xA7" => "\xE1\x8F\x97", # CHEROKEE SMALL LETTER DI
1402             "\xEA\xAE\xA8" => "\xE1\x8F\x98", # CHEROKEE SMALL LETTER TI
1403             "\xEA\xAE\xA9" => "\xE1\x8F\x99", # CHEROKEE SMALL LETTER DO
1404             "\xEA\xAE\xAA" => "\xE1\x8F\x9A", # CHEROKEE SMALL LETTER DU
1405             "\xEA\xAE\xAB" => "\xE1\x8F\x9B", # CHEROKEE SMALL LETTER DV
1406             "\xEA\xAE\xAC" => "\xE1\x8F\x9C", # CHEROKEE SMALL LETTER DLA
1407             "\xEA\xAE\xAD" => "\xE1\x8F\x9D", # CHEROKEE SMALL LETTER TLA
1408             "\xEA\xAE\xAE" => "\xE1\x8F\x9E", # CHEROKEE SMALL LETTER TLE
1409             "\xEA\xAE\xAF" => "\xE1\x8F\x9F", # CHEROKEE SMALL LETTER TLI
1410             "\xEA\xAE\xB0" => "\xE1\x8F\xA0", # CHEROKEE SMALL LETTER TLO
1411             "\xEA\xAE\xB1" => "\xE1\x8F\xA1", # CHEROKEE SMALL LETTER TLU
1412             "\xEA\xAE\xB2" => "\xE1\x8F\xA2", # CHEROKEE SMALL LETTER TLV
1413             "\xEA\xAE\xB3" => "\xE1\x8F\xA3", # CHEROKEE SMALL LETTER TSA
1414             "\xEA\xAE\xB4" => "\xE1\x8F\xA4", # CHEROKEE SMALL LETTER TSE
1415             "\xEA\xAE\xB5" => "\xE1\x8F\xA5", # CHEROKEE SMALL LETTER TSI
1416             "\xEA\xAE\xB6" => "\xE1\x8F\xA6", # CHEROKEE SMALL LETTER TSO
1417             "\xEA\xAE\xB7" => "\xE1\x8F\xA7", # CHEROKEE SMALL LETTER TSU
1418             "\xEA\xAE\xB8" => "\xE1\x8F\xA8", # CHEROKEE SMALL LETTER TSV
1419             "\xEA\xAE\xB9" => "\xE1\x8F\xA9", # CHEROKEE SMALL LETTER WA
1420             "\xEA\xAE\xBA" => "\xE1\x8F\xAA", # CHEROKEE SMALL LETTER WE
1421             "\xEA\xAE\xBB" => "\xE1\x8F\xAB", # CHEROKEE SMALL LETTER WI
1422             "\xEA\xAE\xBC" => "\xE1\x8F\xAC", # CHEROKEE SMALL LETTER WO
1423             "\xEA\xAE\xBD" => "\xE1\x8F\xAD", # CHEROKEE SMALL LETTER WU
1424             "\xEA\xAE\xBE" => "\xE1\x8F\xAE", # CHEROKEE SMALL LETTER WV
1425             "\xEA\xAE\xBF" => "\xE1\x8F\xAF", # CHEROKEE SMALL LETTER YA
1426             "\xEF\xAC\x80" => "\x66\x66", # LATIN SMALL LIGATURE FF
1427             "\xEF\xAC\x81" => "\x66\x69", # LATIN SMALL LIGATURE FI
1428             "\xEF\xAC\x82" => "\x66\x6C", # LATIN SMALL LIGATURE FL
1429             "\xEF\xAC\x83" => "\x66\x66\x69", # LATIN SMALL LIGATURE FFI
1430             "\xEF\xAC\x84" => "\x66\x66\x6C", # LATIN SMALL LIGATURE FFL
1431             "\xEF\xAC\x85" => "\x73\x74", # LATIN SMALL LIGATURE LONG S T
1432             "\xEF\xAC\x86" => "\x73\x74", # LATIN SMALL LIGATURE ST
1433             "\xEF\xAC\x93" => "\xD5\xB4\xD5\xB6", # ARMENIAN SMALL LIGATURE MEN NOW
1434             "\xEF\xAC\x94" => "\xD5\xB4\xD5\xA5", # ARMENIAN SMALL LIGATURE MEN ECH
1435             "\xEF\xAC\x95" => "\xD5\xB4\xD5\xAB", # ARMENIAN SMALL LIGATURE MEN INI
1436             "\xEF\xAC\x96" => "\xD5\xBE\xD5\xB6", # ARMENIAN SMALL LIGATURE VEW NOW
1437             "\xEF\xAC\x97" => "\xD5\xB4\xD5\xAD", # ARMENIAN SMALL LIGATURE MEN XEH
1438             "\xEF\xBC\xA1" => "\xEF\xBD\x81", # FULLWIDTH LATIN CAPITAL LETTER A
1439             "\xEF\xBC\xA2" => "\xEF\xBD\x82", # FULLWIDTH LATIN CAPITAL LETTER B
1440             "\xEF\xBC\xA3" => "\xEF\xBD\x83", # FULLWIDTH LATIN CAPITAL LETTER C
1441             "\xEF\xBC\xA4" => "\xEF\xBD\x84", # FULLWIDTH LATIN CAPITAL LETTER D
1442             "\xEF\xBC\xA5" => "\xEF\xBD\x85", # FULLWIDTH LATIN CAPITAL LETTER E
1443             "\xEF\xBC\xA6" => "\xEF\xBD\x86", # FULLWIDTH LATIN CAPITAL LETTER F
1444             "\xEF\xBC\xA7" => "\xEF\xBD\x87", # FULLWIDTH LATIN CAPITAL LETTER G
1445             "\xEF\xBC\xA8" => "\xEF\xBD\x88", # FULLWIDTH LATIN CAPITAL LETTER H
1446             "\xEF\xBC\xA9" => "\xEF\xBD\x89", # FULLWIDTH LATIN CAPITAL LETTER I
1447             "\xEF\xBC\xAA" => "\xEF\xBD\x8A", # FULLWIDTH LATIN CAPITAL LETTER J
1448             "\xEF\xBC\xAB" => "\xEF\xBD\x8B", # FULLWIDTH LATIN CAPITAL LETTER K
1449             "\xEF\xBC\xAC" => "\xEF\xBD\x8C", # FULLWIDTH LATIN CAPITAL LETTER L
1450             "\xEF\xBC\xAD" => "\xEF\xBD\x8D", # FULLWIDTH LATIN CAPITAL LETTER M
1451             "\xEF\xBC\xAE" => "\xEF\xBD\x8E", # FULLWIDTH LATIN CAPITAL LETTER N
1452             "\xEF\xBC\xAF" => "\xEF\xBD\x8F", # FULLWIDTH LATIN CAPITAL LETTER O
1453             "\xEF\xBC\xB0" => "\xEF\xBD\x90", # FULLWIDTH LATIN CAPITAL LETTER P
1454             "\xEF\xBC\xB1" => "\xEF\xBD\x91", # FULLWIDTH LATIN CAPITAL LETTER Q
1455             "\xEF\xBC\xB2" => "\xEF\xBD\x92", # FULLWIDTH LATIN CAPITAL LETTER R
1456             "\xEF\xBC\xB3" => "\xEF\xBD\x93", # FULLWIDTH LATIN CAPITAL LETTER S
1457             "\xEF\xBC\xB4" => "\xEF\xBD\x94", # FULLWIDTH LATIN CAPITAL LETTER T
1458             "\xEF\xBC\xB5" => "\xEF\xBD\x95", # FULLWIDTH LATIN CAPITAL LETTER U
1459             "\xEF\xBC\xB6" => "\xEF\xBD\x96", # FULLWIDTH LATIN CAPITAL LETTER V
1460             "\xEF\xBC\xB7" => "\xEF\xBD\x97", # FULLWIDTH LATIN CAPITAL LETTER W
1461             "\xEF\xBC\xB8" => "\xEF\xBD\x98", # FULLWIDTH LATIN CAPITAL LETTER X
1462             "\xEF\xBC\xB9" => "\xEF\xBD\x99", # FULLWIDTH LATIN CAPITAL LETTER Y
1463             "\xEF\xBC\xBA" => "\xEF\xBD\x9A", # FULLWIDTH LATIN CAPITAL LETTER Z
1464             "\xF0\x90\x90\x80" => "\xF0\x90\x90\xA8", # DESERET CAPITAL LETTER LONG I
1465             "\xF0\x90\x90\x81" => "\xF0\x90\x90\xA9", # DESERET CAPITAL LETTER LONG E
1466             "\xF0\x90\x90\x82" => "\xF0\x90\x90\xAA", # DESERET CAPITAL LETTER LONG A
1467             "\xF0\x90\x90\x83" => "\xF0\x90\x90\xAB", # DESERET CAPITAL LETTER LONG AH
1468             "\xF0\x90\x90\x84" => "\xF0\x90\x90\xAC", # DESERET CAPITAL LETTER LONG O
1469             "\xF0\x90\x90\x85" => "\xF0\x90\x90\xAD", # DESERET CAPITAL LETTER LONG OO
1470             "\xF0\x90\x90\x86" => "\xF0\x90\x90\xAE", # DESERET CAPITAL LETTER SHORT I
1471             "\xF0\x90\x90\x87" => "\xF0\x90\x90\xAF", # DESERET CAPITAL LETTER SHORT E
1472             "\xF0\x90\x90\x88" => "\xF0\x90\x90\xB0", # DESERET CAPITAL LETTER SHORT A
1473             "\xF0\x90\x90\x89" => "\xF0\x90\x90\xB1", # DESERET CAPITAL LETTER SHORT AH
1474             "\xF0\x90\x90\x8A" => "\xF0\x90\x90\xB2", # DESERET CAPITAL LETTER SHORT O
1475             "\xF0\x90\x90\x8B" => "\xF0\x90\x90\xB3", # DESERET CAPITAL LETTER SHORT OO
1476             "\xF0\x90\x90\x8C" => "\xF0\x90\x90\xB4", # DESERET CAPITAL LETTER AY
1477             "\xF0\x90\x90\x8D" => "\xF0\x90\x90\xB5", # DESERET CAPITAL LETTER OW
1478             "\xF0\x90\x90\x8E" => "\xF0\x90\x90\xB6", # DESERET CAPITAL LETTER WU
1479             "\xF0\x90\x90\x8F" => "\xF0\x90\x90\xB7", # DESERET CAPITAL LETTER YEE
1480             "\xF0\x90\x90\x90" => "\xF0\x90\x90\xB8", # DESERET CAPITAL LETTER H
1481             "\xF0\x90\x90\x91" => "\xF0\x90\x90\xB9", # DESERET CAPITAL LETTER PEE
1482             "\xF0\x90\x90\x92" => "\xF0\x90\x90\xBA", # DESERET CAPITAL LETTER BEE
1483             "\xF0\x90\x90\x93" => "\xF0\x90\x90\xBB", # DESERET CAPITAL LETTER TEE
1484             "\xF0\x90\x90\x94" => "\xF0\x90\x90\xBC", # DESERET CAPITAL LETTER DEE
1485             "\xF0\x90\x90\x95" => "\xF0\x90\x90\xBD", # DESERET CAPITAL LETTER CHEE
1486             "\xF0\x90\x90\x96" => "\xF0\x90\x90\xBE", # DESERET CAPITAL LETTER JEE
1487             "\xF0\x90\x90\x97" => "\xF0\x90\x90\xBF", # DESERET CAPITAL LETTER KAY
1488             "\xF0\x90\x90\x98" => "\xF0\x90\x91\x80", # DESERET CAPITAL LETTER GAY
1489             "\xF0\x90\x90\x99" => "\xF0\x90\x91\x81", # DESERET CAPITAL LETTER EF
1490             "\xF0\x90\x90\x9A" => "\xF0\x90\x91\x82", # DESERET CAPITAL LETTER VEE
1491             "\xF0\x90\x90\x9B" => "\xF0\x90\x91\x83", # DESERET CAPITAL LETTER ETH
1492             "\xF0\x90\x90\x9C" => "\xF0\x90\x91\x84", # DESERET CAPITAL LETTER THEE
1493             "\xF0\x90\x90\x9D" => "\xF0\x90\x91\x85", # DESERET CAPITAL LETTER ES
1494             "\xF0\x90\x90\x9E" => "\xF0\x90\x91\x86", # DESERET CAPITAL LETTER ZEE
1495             "\xF0\x90\x90\x9F" => "\xF0\x90\x91\x87", # DESERET CAPITAL LETTER ESH
1496             "\xF0\x90\x90\xA0" => "\xF0\x90\x91\x88", # DESERET CAPITAL LETTER ZHEE
1497             "\xF0\x90\x90\xA1" => "\xF0\x90\x91\x89", # DESERET CAPITAL LETTER ER
1498             "\xF0\x90\x90\xA2" => "\xF0\x90\x91\x8A", # DESERET CAPITAL LETTER EL
1499             "\xF0\x90\x90\xA3" => "\xF0\x90\x91\x8B", # DESERET CAPITAL LETTER EM
1500             "\xF0\x90\x90\xA4" => "\xF0\x90\x91\x8C", # DESERET CAPITAL LETTER EN
1501             "\xF0\x90\x90\xA5" => "\xF0\x90\x91\x8D", # DESERET CAPITAL LETTER ENG
1502             "\xF0\x90\x90\xA6" => "\xF0\x90\x91\x8E", # DESERET CAPITAL LETTER OI
1503             "\xF0\x90\x90\xA7" => "\xF0\x90\x91\x8F", # DESERET CAPITAL LETTER EW
1504             "\xF0\x90\x92\xB0" => "\xF0\x90\x93\x98", # OSAGE CAPITAL LETTER A
1505             "\xF0\x90\x92\xB1" => "\xF0\x90\x93\x99", # OSAGE CAPITAL LETTER AI
1506             "\xF0\x90\x92\xB2" => "\xF0\x90\x93\x9A", # OSAGE CAPITAL LETTER AIN
1507             "\xF0\x90\x92\xB3" => "\xF0\x90\x93\x9B", # OSAGE CAPITAL LETTER AH
1508             "\xF0\x90\x92\xB4" => "\xF0\x90\x93\x9C", # OSAGE CAPITAL LETTER BRA
1509             "\xF0\x90\x92\xB5" => "\xF0\x90\x93\x9D", # OSAGE CAPITAL LETTER CHA
1510             "\xF0\x90\x92\xB6" => "\xF0\x90\x93\x9E", # OSAGE CAPITAL LETTER EHCHA
1511             "\xF0\x90\x92\xB7" => "\xF0\x90\x93\x9F", # OSAGE CAPITAL LETTER E
1512             "\xF0\x90\x92\xB8" => "\xF0\x90\x93\xA0", # OSAGE CAPITAL LETTER EIN
1513             "\xF0\x90\x92\xB9" => "\xF0\x90\x93\xA1", # OSAGE CAPITAL LETTER HA
1514             "\xF0\x90\x92\xBA" => "\xF0\x90\x93\xA2", # OSAGE CAPITAL LETTER HYA
1515             "\xF0\x90\x92\xBB" => "\xF0\x90\x93\xA3", # OSAGE CAPITAL LETTER I
1516             "\xF0\x90\x92\xBC" => "\xF0\x90\x93\xA4", # OSAGE CAPITAL LETTER KA
1517             "\xF0\x90\x92\xBD" => "\xF0\x90\x93\xA5", # OSAGE CAPITAL LETTER EHKA
1518             "\xF0\x90\x92\xBE" => "\xF0\x90\x93\xA6", # OSAGE CAPITAL LETTER KYA
1519             "\xF0\x90\x92\xBF" => "\xF0\x90\x93\xA7", # OSAGE CAPITAL LETTER LA
1520             "\xF0\x90\x93\x80" => "\xF0\x90\x93\xA8", # OSAGE CAPITAL LETTER MA
1521             "\xF0\x90\x93\x81" => "\xF0\x90\x93\xA9", # OSAGE CAPITAL LETTER NA
1522             "\xF0\x90\x93\x82" => "\xF0\x90\x93\xAA", # OSAGE CAPITAL LETTER O
1523             "\xF0\x90\x93\x83" => "\xF0\x90\x93\xAB", # OSAGE CAPITAL LETTER OIN
1524             "\xF0\x90\x93\x84" => "\xF0\x90\x93\xAC", # OSAGE CAPITAL LETTER PA
1525             "\xF0\x90\x93\x85" => "\xF0\x90\x93\xAD", # OSAGE CAPITAL LETTER EHPA
1526             "\xF0\x90\x93\x86" => "\xF0\x90\x93\xAE", # OSAGE CAPITAL LETTER SA
1527             "\xF0\x90\x93\x87" => "\xF0\x90\x93\xAF", # OSAGE CAPITAL LETTER SHA
1528             "\xF0\x90\x93\x88" => "\xF0\x90\x93\xB0", # OSAGE CAPITAL LETTER TA
1529             "\xF0\x90\x93\x89" => "\xF0\x90\x93\xB1", # OSAGE CAPITAL LETTER EHTA
1530             "\xF0\x90\x93\x8A" => "\xF0\x90\x93\xB2", # OSAGE CAPITAL LETTER TSA
1531             "\xF0\x90\x93\x8B" => "\xF0\x90\x93\xB3", # OSAGE CAPITAL LETTER EHTSA
1532             "\xF0\x90\x93\x8C" => "\xF0\x90\x93\xB4", # OSAGE CAPITAL LETTER TSHA
1533             "\xF0\x90\x93\x8D" => "\xF0\x90\x93\xB5", # OSAGE CAPITAL LETTER DHA
1534             "\xF0\x90\x93\x8E" => "\xF0\x90\x93\xB6", # OSAGE CAPITAL LETTER U
1535             "\xF0\x90\x93\x8F" => "\xF0\x90\x93\xB7", # OSAGE CAPITAL LETTER WA
1536             "\xF0\x90\x93\x90" => "\xF0\x90\x93\xB8", # OSAGE CAPITAL LETTER KHA
1537             "\xF0\x90\x93\x91" => "\xF0\x90\x93\xB9", # OSAGE CAPITAL LETTER GHA
1538             "\xF0\x90\x93\x92" => "\xF0\x90\x93\xBA", # OSAGE CAPITAL LETTER ZA
1539             "\xF0\x90\x93\x93" => "\xF0\x90\x93\xBB", # OSAGE CAPITAL LETTER ZHA
1540             "\xF0\x90\xB2\x80" => "\xF0\x90\xB3\x80", # OLD HUNGARIAN CAPITAL LETTER A
1541             "\xF0\x90\xB2\x81" => "\xF0\x90\xB3\x81", # OLD HUNGARIAN CAPITAL LETTER AA
1542             "\xF0\x90\xB2\x82" => "\xF0\x90\xB3\x82", # OLD HUNGARIAN CAPITAL LETTER EB
1543             "\xF0\x90\xB2\x83" => "\xF0\x90\xB3\x83", # OLD HUNGARIAN CAPITAL LETTER AMB
1544             "\xF0\x90\xB2\x84" => "\xF0\x90\xB3\x84", # OLD HUNGARIAN CAPITAL LETTER EC
1545             "\xF0\x90\xB2\x85" => "\xF0\x90\xB3\x85", # OLD HUNGARIAN CAPITAL LETTER ENC
1546             "\xF0\x90\xB2\x86" => "\xF0\x90\xB3\x86", # OLD HUNGARIAN CAPITAL LETTER ECS
1547             "\xF0\x90\xB2\x87" => "\xF0\x90\xB3\x87", # OLD HUNGARIAN CAPITAL LETTER ED
1548             "\xF0\x90\xB2\x88" => "\xF0\x90\xB3\x88", # OLD HUNGARIAN CAPITAL LETTER AND
1549             "\xF0\x90\xB2\x89" => "\xF0\x90\xB3\x89", # OLD HUNGARIAN CAPITAL LETTER E
1550             "\xF0\x90\xB2\x8A" => "\xF0\x90\xB3\x8A", # OLD HUNGARIAN CAPITAL LETTER CLOSE E
1551             "\xF0\x90\xB2\x8B" => "\xF0\x90\xB3\x8B", # OLD HUNGARIAN CAPITAL LETTER EE
1552             "\xF0\x90\xB2\x8C" => "\xF0\x90\xB3\x8C", # OLD HUNGARIAN CAPITAL LETTER EF
1553             "\xF0\x90\xB2\x8D" => "\xF0\x90\xB3\x8D", # OLD HUNGARIAN CAPITAL LETTER EG
1554             "\xF0\x90\xB2\x8E" => "\xF0\x90\xB3\x8E", # OLD HUNGARIAN CAPITAL LETTER EGY
1555             "\xF0\x90\xB2\x8F" => "\xF0\x90\xB3\x8F", # OLD HUNGARIAN CAPITAL LETTER EH
1556             "\xF0\x90\xB2\x90" => "\xF0\x90\xB3\x90", # OLD HUNGARIAN CAPITAL LETTER I
1557             "\xF0\x90\xB2\x91" => "\xF0\x90\xB3\x91", # OLD HUNGARIAN CAPITAL LETTER II
1558             "\xF0\x90\xB2\x92" => "\xF0\x90\xB3\x92", # OLD HUNGARIAN CAPITAL LETTER EJ
1559             "\xF0\x90\xB2\x93" => "\xF0\x90\xB3\x93", # OLD HUNGARIAN CAPITAL LETTER EK
1560             "\xF0\x90\xB2\x94" => "\xF0\x90\xB3\x94", # OLD HUNGARIAN CAPITAL LETTER AK
1561             "\xF0\x90\xB2\x95" => "\xF0\x90\xB3\x95", # OLD HUNGARIAN CAPITAL LETTER UNK
1562             "\xF0\x90\xB2\x96" => "\xF0\x90\xB3\x96", # OLD HUNGARIAN CAPITAL LETTER EL
1563             "\xF0\x90\xB2\x97" => "\xF0\x90\xB3\x97", # OLD HUNGARIAN CAPITAL LETTER ELY
1564             "\xF0\x90\xB2\x98" => "\xF0\x90\xB3\x98", # OLD HUNGARIAN CAPITAL LETTER EM
1565             "\xF0\x90\xB2\x99" => "\xF0\x90\xB3\x99", # OLD HUNGARIAN CAPITAL LETTER EN
1566             "\xF0\x90\xB2\x9A" => "\xF0\x90\xB3\x9A", # OLD HUNGARIAN CAPITAL LETTER ENY
1567             "\xF0\x90\xB2\x9B" => "\xF0\x90\xB3\x9B", # OLD HUNGARIAN CAPITAL LETTER O
1568             "\xF0\x90\xB2\x9C" => "\xF0\x90\xB3\x9C", # OLD HUNGARIAN CAPITAL LETTER OO
1569             "\xF0\x90\xB2\x9D" => "\xF0\x90\xB3\x9D", # OLD HUNGARIAN CAPITAL LETTER NIKOLSBURG OE
1570             "\xF0\x90\xB2\x9E" => "\xF0\x90\xB3\x9E", # OLD HUNGARIAN CAPITAL LETTER RUDIMENTA OE
1571             "\xF0\x90\xB2\x9F" => "\xF0\x90\xB3\x9F", # OLD HUNGARIAN CAPITAL LETTER OEE
1572             "\xF0\x90\xB2\xA0" => "\xF0\x90\xB3\xA0", # OLD HUNGARIAN CAPITAL LETTER EP
1573             "\xF0\x90\xB2\xA1" => "\xF0\x90\xB3\xA1", # OLD HUNGARIAN CAPITAL LETTER EMP
1574             "\xF0\x90\xB2\xA2" => "\xF0\x90\xB3\xA2", # OLD HUNGARIAN CAPITAL LETTER ER
1575             "\xF0\x90\xB2\xA3" => "\xF0\x90\xB3\xA3", # OLD HUNGARIAN CAPITAL LETTER SHORT ER
1576             "\xF0\x90\xB2\xA4" => "\xF0\x90\xB3\xA4", # OLD HUNGARIAN CAPITAL LETTER ES
1577             "\xF0\x90\xB2\xA5" => "\xF0\x90\xB3\xA5", # OLD HUNGARIAN CAPITAL LETTER ESZ
1578             "\xF0\x90\xB2\xA6" => "\xF0\x90\xB3\xA6", # OLD HUNGARIAN CAPITAL LETTER ET
1579             "\xF0\x90\xB2\xA7" => "\xF0\x90\xB3\xA7", # OLD HUNGARIAN CAPITAL LETTER ENT
1580             "\xF0\x90\xB2\xA8" => "\xF0\x90\xB3\xA8", # OLD HUNGARIAN CAPITAL LETTER ETY
1581             "\xF0\x90\xB2\xA9" => "\xF0\x90\xB3\xA9", # OLD HUNGARIAN CAPITAL LETTER ECH
1582             "\xF0\x90\xB2\xAA" => "\xF0\x90\xB3\xAA", # OLD HUNGARIAN CAPITAL LETTER U
1583             "\xF0\x90\xB2\xAB" => "\xF0\x90\xB3\xAB", # OLD HUNGARIAN CAPITAL LETTER UU
1584             "\xF0\x90\xB2\xAC" => "\xF0\x90\xB3\xAC", # OLD HUNGARIAN CAPITAL LETTER NIKOLSBURG UE
1585             "\xF0\x90\xB2\xAD" => "\xF0\x90\xB3\xAD", # OLD HUNGARIAN CAPITAL LETTER RUDIMENTA UE
1586             "\xF0\x90\xB2\xAE" => "\xF0\x90\xB3\xAE", # OLD HUNGARIAN CAPITAL LETTER EV
1587             "\xF0\x90\xB2\xAF" => "\xF0\x90\xB3\xAF", # OLD HUNGARIAN CAPITAL LETTER EZ
1588             "\xF0\x90\xB2\xB0" => "\xF0\x90\xB3\xB0", # OLD HUNGARIAN CAPITAL LETTER EZS
1589             "\xF0\x90\xB2\xB1" => "\xF0\x90\xB3\xB1", # OLD HUNGARIAN CAPITAL LETTER ENT-SHAPED SIGN
1590             "\xF0\x90\xB2\xB2" => "\xF0\x90\xB3\xB2", # OLD HUNGARIAN CAPITAL LETTER US
1591             "\xF0\x91\xA2\xA0" => "\xF0\x91\xA3\x80", # WARANG CITI CAPITAL LETTER NGAA
1592             "\xF0\x91\xA2\xA1" => "\xF0\x91\xA3\x81", # WARANG CITI CAPITAL LETTER A
1593             "\xF0\x91\xA2\xA2" => "\xF0\x91\xA3\x82", # WARANG CITI CAPITAL LETTER WI
1594             "\xF0\x91\xA2\xA3" => "\xF0\x91\xA3\x83", # WARANG CITI CAPITAL LETTER YU
1595             "\xF0\x91\xA2\xA4" => "\xF0\x91\xA3\x84", # WARANG CITI CAPITAL LETTER YA
1596             "\xF0\x91\xA2\xA5" => "\xF0\x91\xA3\x85", # WARANG CITI CAPITAL LETTER YO
1597             "\xF0\x91\xA2\xA6" => "\xF0\x91\xA3\x86", # WARANG CITI CAPITAL LETTER II
1598             "\xF0\x91\xA2\xA7" => "\xF0\x91\xA3\x87", # WARANG CITI CAPITAL LETTER UU
1599             "\xF0\x91\xA2\xA8" => "\xF0\x91\xA3\x88", # WARANG CITI CAPITAL LETTER E
1600             "\xF0\x91\xA2\xA9" => "\xF0\x91\xA3\x89", # WARANG CITI CAPITAL LETTER O
1601             "\xF0\x91\xA2\xAA" => "\xF0\x91\xA3\x8A", # WARANG CITI CAPITAL LETTER ANG
1602             "\xF0\x91\xA2\xAB" => "\xF0\x91\xA3\x8B", # WARANG CITI CAPITAL LETTER GA
1603             "\xF0\x91\xA2\xAC" => "\xF0\x91\xA3\x8C", # WARANG CITI CAPITAL LETTER KO
1604             "\xF0\x91\xA2\xAD" => "\xF0\x91\xA3\x8D", # WARANG CITI CAPITAL LETTER ENY
1605             "\xF0\x91\xA2\xAE" => "\xF0\x91\xA3\x8E", # WARANG CITI CAPITAL LETTER YUJ
1606             "\xF0\x91\xA2\xAF" => "\xF0\x91\xA3\x8F", # WARANG CITI CAPITAL LETTER UC
1607             "\xF0\x91\xA2\xB0" => "\xF0\x91\xA3\x90", # WARANG CITI CAPITAL LETTER ENN
1608             "\xF0\x91\xA2\xB1" => "\xF0\x91\xA3\x91", # WARANG CITI CAPITAL LETTER ODD
1609             "\xF0\x91\xA2\xB2" => "\xF0\x91\xA3\x92", # WARANG CITI CAPITAL LETTER TTE
1610             "\xF0\x91\xA2\xB3" => "\xF0\x91\xA3\x93", # WARANG CITI CAPITAL LETTER NUNG
1611             "\xF0\x91\xA2\xB4" => "\xF0\x91\xA3\x94", # WARANG CITI CAPITAL LETTER DA
1612             "\xF0\x91\xA2\xB5" => "\xF0\x91\xA3\x95", # WARANG CITI CAPITAL LETTER AT
1613             "\xF0\x91\xA2\xB6" => "\xF0\x91\xA3\x96", # WARANG CITI CAPITAL LETTER AM
1614             "\xF0\x91\xA2\xB7" => "\xF0\x91\xA3\x97", # WARANG CITI CAPITAL LETTER BU
1615             "\xF0\x91\xA2\xB8" => "\xF0\x91\xA3\x98", # WARANG CITI CAPITAL LETTER PU
1616             "\xF0\x91\xA2\xB9" => "\xF0\x91\xA3\x99", # WARANG CITI CAPITAL LETTER HIYO
1617             "\xF0\x91\xA2\xBA" => "\xF0\x91\xA3\x9A", # WARANG CITI CAPITAL LETTER HOLO
1618             "\xF0\x91\xA2\xBB" => "\xF0\x91\xA3\x9B", # WARANG CITI CAPITAL LETTER HORR
1619             "\xF0\x91\xA2\xBC" => "\xF0\x91\xA3\x9C", # WARANG CITI CAPITAL LETTER HAR
1620             "\xF0\x91\xA2\xBD" => "\xF0\x91\xA3\x9D", # WARANG CITI CAPITAL LETTER SSUU
1621             "\xF0\x91\xA2\xBE" => "\xF0\x91\xA3\x9E", # WARANG CITI CAPITAL LETTER SII
1622             "\xF0\x91\xA2\xBF" => "\xF0\x91\xA3\x9F", # WARANG CITI CAPITAL LETTER VIYO
1623             "\xF0\x96\xB9\x80" => "\xF0\x96\xB9\xA0", # MEDEFAIDRIN CAPITAL LETTER M
1624             "\xF0\x96\xB9\x81" => "\xF0\x96\xB9\xA1", # MEDEFAIDRIN CAPITAL LETTER S
1625             "\xF0\x96\xB9\x82" => "\xF0\x96\xB9\xA2", # MEDEFAIDRIN CAPITAL LETTER V
1626             "\xF0\x96\xB9\x83" => "\xF0\x96\xB9\xA3", # MEDEFAIDRIN CAPITAL LETTER W
1627             "\xF0\x96\xB9\x84" => "\xF0\x96\xB9\xA4", # MEDEFAIDRIN CAPITAL LETTER ATIU
1628             "\xF0\x96\xB9\x85" => "\xF0\x96\xB9\xA5", # MEDEFAIDRIN CAPITAL LETTER Z
1629             "\xF0\x96\xB9\x86" => "\xF0\x96\xB9\xA6", # MEDEFAIDRIN CAPITAL LETTER KP
1630             "\xF0\x96\xB9\x87" => "\xF0\x96\xB9\xA7", # MEDEFAIDRIN CAPITAL LETTER P
1631             "\xF0\x96\xB9\x88" => "\xF0\x96\xB9\xA8", # MEDEFAIDRIN CAPITAL LETTER T
1632             "\xF0\x96\xB9\x89" => "\xF0\x96\xB9\xA9", # MEDEFAIDRIN CAPITAL LETTER G
1633             "\xF0\x96\xB9\x8A" => "\xF0\x96\xB9\xAA", # MEDEFAIDRIN CAPITAL LETTER F
1634             "\xF0\x96\xB9\x8B" => "\xF0\x96\xB9\xAB", # MEDEFAIDRIN CAPITAL LETTER I
1635             "\xF0\x96\xB9\x8C" => "\xF0\x96\xB9\xAC", # MEDEFAIDRIN CAPITAL LETTER K
1636             "\xF0\x96\xB9\x8D" => "\xF0\x96\xB9\xAD", # MEDEFAIDRIN CAPITAL LETTER A
1637             "\xF0\x96\xB9\x8E" => "\xF0\x96\xB9\xAE", # MEDEFAIDRIN CAPITAL LETTER J
1638             "\xF0\x96\xB9\x8F" => "\xF0\x96\xB9\xAF", # MEDEFAIDRIN CAPITAL LETTER E
1639             "\xF0\x96\xB9\x90" => "\xF0\x96\xB9\xB0", # MEDEFAIDRIN CAPITAL LETTER B
1640             "\xF0\x96\xB9\x91" => "\xF0\x96\xB9\xB1", # MEDEFAIDRIN CAPITAL LETTER C
1641             "\xF0\x96\xB9\x92" => "\xF0\x96\xB9\xB2", # MEDEFAIDRIN CAPITAL LETTER U
1642             "\xF0\x96\xB9\x93" => "\xF0\x96\xB9\xB3", # MEDEFAIDRIN CAPITAL LETTER YU
1643             "\xF0\x96\xB9\x94" => "\xF0\x96\xB9\xB4", # MEDEFAIDRIN CAPITAL LETTER L
1644             "\xF0\x96\xB9\x95" => "\xF0\x96\xB9\xB5", # MEDEFAIDRIN CAPITAL LETTER Q
1645             "\xF0\x96\xB9\x96" => "\xF0\x96\xB9\xB6", # MEDEFAIDRIN CAPITAL LETTER HP
1646             "\xF0\x96\xB9\x97" => "\xF0\x96\xB9\xB7", # MEDEFAIDRIN CAPITAL LETTER NY
1647             "\xF0\x96\xB9\x98" => "\xF0\x96\xB9\xB8", # MEDEFAIDRIN CAPITAL LETTER X
1648             "\xF0\x96\xB9\x99" => "\xF0\x96\xB9\xB9", # MEDEFAIDRIN CAPITAL LETTER D
1649             "\xF0\x96\xB9\x9A" => "\xF0\x96\xB9\xBA", # MEDEFAIDRIN CAPITAL LETTER OE
1650             "\xF0\x96\xB9\x9B" => "\xF0\x96\xB9\xBB", # MEDEFAIDRIN CAPITAL LETTER N
1651             "\xF0\x96\xB9\x9C" => "\xF0\x96\xB9\xBC", # MEDEFAIDRIN CAPITAL LETTER R
1652             "\xF0\x96\xB9\x9D" => "\xF0\x96\xB9\xBD", # MEDEFAIDRIN CAPITAL LETTER O
1653             "\xF0\x96\xB9\x9E" => "\xF0\x96\xB9\xBE", # MEDEFAIDRIN CAPITAL LETTER AI
1654             "\xF0\x96\xB9\x9F" => "\xF0\x96\xB9\xBF", # MEDEFAIDRIN CAPITAL LETTER Y
1655             "\xF0\x9E\xA4\x80" => "\xF0\x9E\xA4\xA2", # ADLAM CAPITAL LETTER ALIF
1656             "\xF0\x9E\xA4\x81" => "\xF0\x9E\xA4\xA3", # ADLAM CAPITAL LETTER DAALI
1657             "\xF0\x9E\xA4\x82" => "\xF0\x9E\xA4\xA4", # ADLAM CAPITAL LETTER LAAM
1658             "\xF0\x9E\xA4\x83" => "\xF0\x9E\xA4\xA5", # ADLAM CAPITAL LETTER MIIM
1659             "\xF0\x9E\xA4\x84" => "\xF0\x9E\xA4\xA6", # ADLAM CAPITAL LETTER BA
1660             "\xF0\x9E\xA4\x85" => "\xF0\x9E\xA4\xA7", # ADLAM CAPITAL LETTER SINNYIIYHE
1661             "\xF0\x9E\xA4\x86" => "\xF0\x9E\xA4\xA8", # ADLAM CAPITAL LETTER PE
1662             "\xF0\x9E\xA4\x87" => "\xF0\x9E\xA4\xA9", # ADLAM CAPITAL LETTER BHE
1663             "\xF0\x9E\xA4\x88" => "\xF0\x9E\xA4\xAA", # ADLAM CAPITAL LETTER RA
1664             "\xF0\x9E\xA4\x89" => "\xF0\x9E\xA4\xAB", # ADLAM CAPITAL LETTER E
1665             "\xF0\x9E\xA4\x8A" => "\xF0\x9E\xA4\xAC", # ADLAM CAPITAL LETTER FA
1666             "\xF0\x9E\xA4\x8B" => "\xF0\x9E\xA4\xAD", # ADLAM CAPITAL LETTER I
1667             "\xF0\x9E\xA4\x8C" => "\xF0\x9E\xA4\xAE", # ADLAM CAPITAL LETTER O
1668             "\xF0\x9E\xA4\x8D" => "\xF0\x9E\xA4\xAF", # ADLAM CAPITAL LETTER DHA
1669             "\xF0\x9E\xA4\x8E" => "\xF0\x9E\xA4\xB0", # ADLAM CAPITAL LETTER YHE
1670             "\xF0\x9E\xA4\x8F" => "\xF0\x9E\xA4\xB1", # ADLAM CAPITAL LETTER WAW
1671             "\xF0\x9E\xA4\x90" => "\xF0\x9E\xA4\xB2", # ADLAM CAPITAL LETTER NUN
1672             "\xF0\x9E\xA4\x91" => "\xF0\x9E\xA4\xB3", # ADLAM CAPITAL LETTER KAF
1673             "\xF0\x9E\xA4\x92" => "\xF0\x9E\xA4\xB4", # ADLAM CAPITAL LETTER YA
1674             "\xF0\x9E\xA4\x93" => "\xF0\x9E\xA4\xB5", # ADLAM CAPITAL LETTER U
1675             "\xF0\x9E\xA4\x94" => "\xF0\x9E\xA4\xB6", # ADLAM CAPITAL LETTER JIIM
1676             "\xF0\x9E\xA4\x95" => "\xF0\x9E\xA4\xB7", # ADLAM CAPITAL LETTER CHI
1677             "\xF0\x9E\xA4\x96" => "\xF0\x9E\xA4\xB8", # ADLAM CAPITAL LETTER HA
1678             "\xF0\x9E\xA4\x97" => "\xF0\x9E\xA4\xB9", # ADLAM CAPITAL LETTER QAAF
1679             "\xF0\x9E\xA4\x98" => "\xF0\x9E\xA4\xBA", # ADLAM CAPITAL LETTER GA
1680             "\xF0\x9E\xA4\x99" => "\xF0\x9E\xA4\xBB", # ADLAM CAPITAL LETTER NYA
1681             "\xF0\x9E\xA4\x9A" => "\xF0\x9E\xA4\xBC", # ADLAM CAPITAL LETTER TU
1682             "\xF0\x9E\xA4\x9B" => "\xF0\x9E\xA4\xBD", # ADLAM CAPITAL LETTER NHA
1683             "\xF0\x9E\xA4\x9C" => "\xF0\x9E\xA4\xBE", # ADLAM CAPITAL LETTER VA
1684             "\xF0\x9E\xA4\x9D" => "\xF0\x9E\xA4\xBF", # ADLAM CAPITAL LETTER KHA
1685             "\xF0\x9E\xA4\x9E" => "\xF0\x9E\xA5\x80", # ADLAM CAPITAL LETTER GBE
1686             "\xF0\x9E\xA4\x9F" => "\xF0\x9E\xA5\x81", # ADLAM CAPITAL LETTER ZAL
1687             "\xF0\x9E\xA4\xA0" => "\xF0\x9E\xA5\x82", # ADLAM CAPITAL LETTER KPO
1688             "\xF0\x9E\xA4\xA1" => "\xF0\x9E\xA5\x83", # ADLAM CAPITAL LETTER SHA
1689             );
1690             }
1691              
1692             else {
1693             croak "Don't know my package name '@{[__PACKAGE__]}'";
1694             }
1695              
1696             #
1697             # @ARGV wildcard globbing
1698             #
1699             sub import {
1700              
1701 0 0   0   0 if ($^O =~ /\A (?: MSWin32 | NetWare | symbian | dos ) \z/oxms) {
1702 0         0 my @argv = ();
1703 0         0 for (@ARGV) {
1704              
1705             # has space
1706 0 0       0 if (/\A (?:$q_char)*? [ ] /oxms) {
    0          
1707 0 0       0 if (my @glob = Eutf2::glob(qq{"$_"})) {
1708 0         0 push @argv, @glob;
1709             }
1710             else {
1711 0         0 push @argv, $_;
1712             }
1713             }
1714              
1715             # has wildcard metachar
1716             elsif (/\A (?:$q_char)*? [*?] /oxms) {
1717 0 0       0 if (my @glob = Eutf2::glob($_)) {
1718 0         0 push @argv, @glob;
1719             }
1720             else {
1721 0         0 push @argv, $_;
1722             }
1723             }
1724              
1725             # no wildcard globbing
1726             else {
1727 0         0 push @argv, $_;
1728             }
1729             }
1730 0         0 @ARGV = @argv;
1731             }
1732              
1733 0         0 *Char::ord = \&UTF2::ord;
1734 0         0 *Char::ord_ = \&UTF2::ord_;
1735 0         0 *Char::reverse = \&UTF2::reverse;
1736 0         0 *Char::getc = \&UTF2::getc;
1737 0         0 *Char::length = \&UTF2::length;
1738 0         0 *Char::substr = \&UTF2::substr;
1739 0         0 *Char::index = \&UTF2::index;
1740 0         0 *Char::rindex = \&UTF2::rindex;
1741 0         0 *Char::eval = \&UTF2::eval;
1742 0         0 *Char::escape = \&UTF2::escape;
1743 0         0 *Char::escape_token = \&UTF2::escape_token;
1744 0         0 *Char::escape_script = \&UTF2::escape_script;
1745             }
1746              
1747             # P.230 Care with Prototypes
1748             # in Chapter 6: Subroutines
1749             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
1750             #
1751             # If you aren't careful, you can get yourself into trouble with prototypes.
1752             # But if you are careful, you can do a lot of neat things with them. This is
1753             # all very powerful, of course, and should only be used in moderation to make
1754             # the world a better place.
1755              
1756             # P.332 Care with Prototypes
1757             # in Chapter 7: Subroutines
1758             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
1759             #
1760             # If you aren't careful, you can get yourself into trouble with prototypes.
1761             # But if you are careful, you can do a lot of neat things with them. This is
1762             # all very powerful, of course, and should only be used in moderation to make
1763             # the world a better place.
1764              
1765             #
1766             # Prototypes of subroutines
1767             #
1768       0     sub unimport {}
1769             sub Eutf2::split(;$$$);
1770             sub Eutf2::tr($$$$;$);
1771             sub Eutf2::chop(@);
1772             sub Eutf2::index($$;$);
1773             sub Eutf2::rindex($$;$);
1774             sub Eutf2::lcfirst(@);
1775             sub Eutf2::lcfirst_();
1776             sub Eutf2::lc(@);
1777             sub Eutf2::lc_();
1778             sub Eutf2::ucfirst(@);
1779             sub Eutf2::ucfirst_();
1780             sub Eutf2::uc(@);
1781             sub Eutf2::uc_();
1782             sub Eutf2::fc(@);
1783             sub Eutf2::fc_();
1784             sub Eutf2::ignorecase;
1785             sub Eutf2::classic_character_class;
1786             sub Eutf2::capture;
1787             sub Eutf2::chr(;$);
1788             sub Eutf2::chr_();
1789             sub Eutf2::glob($);
1790             sub Eutf2::glob_();
1791              
1792             sub UTF2::ord(;$);
1793             sub UTF2::ord_();
1794             sub UTF2::reverse(@);
1795             sub UTF2::getc(;*@);
1796             sub UTF2::length(;$);
1797             sub UTF2::substr($$;$$);
1798             sub UTF2::index($$;$);
1799             sub UTF2::rindex($$;$);
1800             sub UTF2::escape(;$);
1801              
1802             #
1803             # Regexp work
1804             #
1805 306         35278 use vars qw(
1806             $re_a
1807             $re_t
1808             $re_n
1809             $re_r
1810 306     306   3639 );
  306         694  
1811              
1812             #
1813             # Character class
1814             #
1815 306         4582935 use vars qw(
1816             $dot
1817             $dot_s
1818             $eD
1819             $eS
1820             $eW
1821             $eH
1822             $eV
1823             $eR
1824             $eN
1825             $not_alnum
1826             $not_alpha
1827             $not_ascii
1828             $not_blank
1829             $not_cntrl
1830             $not_digit
1831             $not_graph
1832             $not_lower
1833             $not_lower_i
1834             $not_print
1835             $not_punct
1836             $not_space
1837             $not_upper
1838             $not_upper_i
1839             $not_word
1840             $not_xdigit
1841             $eb
1842             $eB
1843 306     306   2118 );
  306         640  
1844              
1845             ${Eutf2::dot} = qr{(?>[^\x80-\xFF\x0A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1846             ${Eutf2::dot_s} = qr{(?>[^\x80-\xFF]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1847             ${Eutf2::eD} = qr{(?>[^\x80-\xFF0-9]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1848              
1849             # Vertical tabs are now whitespace
1850             # \s in a regex now matches a vertical tab in all circumstances.
1851             # http://search.cpan.org/dist/perl-5.18.0/pod/perldelta.pod#Vertical_tabs_are_now_whitespace
1852             # ${Eutf2::eS} = qr{(?>[^\x80-\xFF\x09\x0A \x0C\x0D\x20]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1853             # ${Eutf2::eS} = qr{(?>[^\x80-\xFF\x09\x0A\x0B\x0C\x0D\x20]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1854             ${Eutf2::eS} = qr{(?>[^\x80-\xFF\s]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1855              
1856             ${Eutf2::eW} = qr{(?>[^\x80-\xFF0-9A-Z_a-z]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1857             ${Eutf2::eH} = qr{(?>[^\x80-\xFF\x09\x20]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1858             ${Eutf2::eV} = qr{(?>[^\x80-\xFF\x0A\x0B\x0C\x0D]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1859             ${Eutf2::eR} = qr{(?>\x0D\x0A|[\x0A\x0D])};
1860             ${Eutf2::eN} = qr{(?>[^\x80-\xFF\x0A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1861             ${Eutf2::not_alnum} = qr{(?>[^\x80-\xFF\x30-\x39\x41-\x5A\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1862             ${Eutf2::not_alpha} = qr{(?>[^\x80-\xFF\x41-\x5A\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1863             ${Eutf2::not_ascii} = qr{(?>[^\x80-\xFF\x00-\x7F]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1864             ${Eutf2::not_blank} = qr{(?>[^\x80-\xFF\x09\x20]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1865             ${Eutf2::not_cntrl} = qr{(?>[^\x80-\xFF\x00-\x1F\x7F]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1866             ${Eutf2::not_digit} = qr{(?>[^\x80-\xFF\x30-\x39]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1867             ${Eutf2::not_graph} = qr{(?>[^\x80-\xFF\x21-\x7F]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1868             ${Eutf2::not_lower} = qr{(?>[^\x80-\xFF\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1869             ${Eutf2::not_lower_i} = qr{(?>[^\x80-\xFF\x41-\x5A\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])}; # Perl 5.16 compatible
1870             # ${Eutf2::not_lower_i} = qr{(?>[^\x80-\xFF]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])}; # older Perl compatible
1871             ${Eutf2::not_print} = qr{(?>[^\x80-\xFF\x20-\x7F]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1872             ${Eutf2::not_punct} = qr{(?>[^\x80-\xFF\x21-\x2F\x3A-\x3F\x40\x5B-\x5F\x60\x7B-\x7E]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1873             ${Eutf2::not_space} = qr{(?>[^\x80-\xFF\s\x0B]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1874             ${Eutf2::not_upper} = qr{(?>[^\x80-\xFF\x41-\x5A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1875             ${Eutf2::not_upper_i} = qr{(?>[^\x80-\xFF\x41-\x5A\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])}; # Perl 5.16 compatible
1876             # ${Eutf2::not_upper_i} = qr{(?>[^\x80-\xFF]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])}; # older Perl compatible
1877             ${Eutf2::not_word} = qr{(?>[^\x80-\xFF\x30-\x39\x41-\x5A\x5F\x61-\x7A]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1878             ${Eutf2::not_xdigit} = qr{(?>[^\x80-\xFF\x30-\x39\x41-\x46\x61-\x66]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])};
1879             ${Eutf2::eb} = qr{(?:\A(?=[0-9A-Z_a-z])|(?<=[\x00-\x2F\x40\x5B-\x5E\x60\x7B-\xFF])(?=[0-9A-Z_a-z])|(?<=[0-9A-Z_a-z])(?=[\x00-\x2F\x40\x5B-\x5E\x60\x7B-\xFF]|\z))};
1880             ${Eutf2::eB} = qr{(?:(?<=[0-9A-Z_a-z])(?=[0-9A-Z_a-z])|(?<=[\x00-\x2F\x40\x5B-\x5E\x60\x7B-\xFF])(?=[\x00-\x2F\x40\x5B-\x5E\x60\x7B-\xFF]))};
1881              
1882             # avoid: Name "Eutf2::foo" used only once: possible typo at here.
1883             ${Eutf2::dot} = ${Eutf2::dot};
1884             ${Eutf2::dot_s} = ${Eutf2::dot_s};
1885             ${Eutf2::eD} = ${Eutf2::eD};
1886             ${Eutf2::eS} = ${Eutf2::eS};
1887             ${Eutf2::eW} = ${Eutf2::eW};
1888             ${Eutf2::eH} = ${Eutf2::eH};
1889             ${Eutf2::eV} = ${Eutf2::eV};
1890             ${Eutf2::eR} = ${Eutf2::eR};
1891             ${Eutf2::eN} = ${Eutf2::eN};
1892             ${Eutf2::not_alnum} = ${Eutf2::not_alnum};
1893             ${Eutf2::not_alpha} = ${Eutf2::not_alpha};
1894             ${Eutf2::not_ascii} = ${Eutf2::not_ascii};
1895             ${Eutf2::not_blank} = ${Eutf2::not_blank};
1896             ${Eutf2::not_cntrl} = ${Eutf2::not_cntrl};
1897             ${Eutf2::not_digit} = ${Eutf2::not_digit};
1898             ${Eutf2::not_graph} = ${Eutf2::not_graph};
1899             ${Eutf2::not_lower} = ${Eutf2::not_lower};
1900             ${Eutf2::not_lower_i} = ${Eutf2::not_lower_i};
1901             ${Eutf2::not_print} = ${Eutf2::not_print};
1902             ${Eutf2::not_punct} = ${Eutf2::not_punct};
1903             ${Eutf2::not_space} = ${Eutf2::not_space};
1904             ${Eutf2::not_upper} = ${Eutf2::not_upper};
1905             ${Eutf2::not_upper_i} = ${Eutf2::not_upper_i};
1906             ${Eutf2::not_word} = ${Eutf2::not_word};
1907             ${Eutf2::not_xdigit} = ${Eutf2::not_xdigit};
1908             ${Eutf2::eb} = ${Eutf2::eb};
1909             ${Eutf2::eB} = ${Eutf2::eB};
1910              
1911             #
1912             # UTF-8 split
1913             #
1914             sub Eutf2::split(;$$$) {
1915              
1916             # P.794 29.2.161. split
1917             # in Chapter 29: Functions
1918             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
1919              
1920             # P.951 split
1921             # in Chapter 27: Functions
1922             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
1923              
1924 0     0 0 0 my $pattern = $_[0];
1925 0         0 my $string = $_[1];
1926 0         0 my $limit = $_[2];
1927              
1928             # if $pattern is also omitted or is the literal space, " "
1929 0 0       0 if (not defined $pattern) {
1930 0         0 $pattern = ' ';
1931             }
1932              
1933             # if $string is omitted, the function splits the $_ string
1934 0 0       0 if (not defined $string) {
1935 0 0       0 if (defined $_) {
1936 0         0 $string = $_;
1937             }
1938             else {
1939 0         0 $string = '';
1940             }
1941             }
1942              
1943 0         0 my @split = ();
1944              
1945             # when string is empty
1946 0 0       0 if ($string eq '') {
    0          
1947              
1948             # resulting list value in list context
1949 0 0       0 if (wantarray) {
1950 0         0 return @split;
1951             }
1952              
1953             # count of substrings in scalar context
1954             else {
1955 0 0       0 carp "Use of implicit split to \@_ is deprecated" if $^W;
1956 0         0 @_ = @split;
1957 0         0 return scalar @_;
1958             }
1959             }
1960              
1961             # split's first argument is more consistently interpreted
1962             #
1963             # After some changes earlier in v5.17, split's behavior has been simplified:
1964             # if the PATTERN argument evaluates to a string containing one space, it is
1965             # treated the way that a literal string containing one space once was.
1966             # http://search.cpan.org/dist/perl-5.18.0/pod/perldelta.pod#split's_first_argument_is_more_consistently_interpreted
1967              
1968             # if $pattern is also omitted or is the literal space, " ", the function splits
1969             # on whitespace, /\s+/, after skipping any leading whitespace
1970             # (and so on)
1971              
1972             elsif ($pattern eq ' ') {
1973 0 0       0 if (not defined $limit) {
1974 0         0 return CORE::split(' ', $string);
1975             }
1976             else {
1977 0         0 return CORE::split(' ', $string, $limit);
1978             }
1979             }
1980              
1981             # if $limit is negative, it is treated as if an arbitrarily large $limit has been specified
1982 0 0 0     0 if ((not defined $limit) or ($limit <= 0)) {
    0          
1983              
1984             # a pattern capable of matching either the null string or something longer than the
1985             # null string will split the value of $string into separate characters wherever it
1986             # matches the null string between characters
1987             # (and so on)
1988              
1989 0 0       0 if ('' =~ / \A $pattern \z /xms) {
1990 0         0 my $last_subexpression_offsets = _last_subexpression_offsets($pattern);
1991 0         0 my $limit = scalar(() = $string =~ /($pattern)/oxmsg);
1992              
1993             # P.1024 Appendix W.10 Multibyte Processing
1994             # of ISBN 1-56592-224-7 CJKV Information Processing
1995             # (and so on)
1996              
1997             # the //m modifier is assumed when you split on the pattern /^/
1998             # (and so on)
1999              
2000             # V
2001 0   0     0 while ((--$limit > 0) and ($string =~ s/\A((?:$q_char)+?)$pattern//m)) {
2002              
2003             # if the $pattern contains parentheses, then the substring matched by each pair of parentheses
2004             # is included in the resulting list, interspersed with the fields that are ordinarily returned
2005             # (and so on)
2006              
2007 0         0 local $@;
2008 0         0 for (my $digit=1; $digit <= ($last_subexpression_offsets + 1); $digit++) {
2009 0         0 push @split, CORE::eval('$' . $digit);
2010             }
2011             }
2012             }
2013              
2014             else {
2015 0         0 my $last_subexpression_offsets = _last_subexpression_offsets($pattern);
2016              
2017             # V
2018 0         0 while ($string =~ s/\A((?:$q_char)*?)$pattern//m) {
2019 0         0 local $@;
2020 0         0 for (my $digit=1; $digit <= ($last_subexpression_offsets + 1); $digit++) {
2021 0         0 push @split, CORE::eval('$' . $digit);
2022             }
2023             }
2024             }
2025             }
2026              
2027             elsif ($limit > 0) {
2028 0 0       0 if ('' =~ / \A $pattern \z /xms) {
2029 0         0 my $last_subexpression_offsets = _last_subexpression_offsets($pattern);
2030 0   0     0 while ((--$limit > 0) and (CORE::length($string) > 0)) {
2031              
2032             # V
2033 0 0       0 if ($string =~ s/\A((?:$q_char)+?)$pattern//m) {
2034 0         0 local $@;
2035 0         0 for (my $digit=1; $digit <= ($last_subexpression_offsets + 1); $digit++) {
2036 0         0 push @split, CORE::eval('$' . $digit);
2037             }
2038             }
2039             }
2040             }
2041             else {
2042 0         0 my $last_subexpression_offsets = _last_subexpression_offsets($pattern);
2043 0   0     0 while ((--$limit > 0) and (CORE::length($string) > 0)) {
2044              
2045             # V
2046 0 0       0 if ($string =~ s/\A((?:$q_char)*?)$pattern//m) {
2047 0         0 local $@;
2048 0         0 for (my $digit=1; $digit <= ($last_subexpression_offsets + 1); $digit++) {
2049 0         0 push @split, CORE::eval('$' . $digit);
2050             }
2051             }
2052             }
2053             }
2054             }
2055              
2056 0 0       0 if (CORE::length($string) > 0) {
2057 0         0 push @split, $string;
2058             }
2059              
2060             # if $_[2] (NOT "$limit") is omitted or zero, trailing null fields are stripped from the result
2061 0 0 0     0 if ((not defined $_[2]) or ($_[2] == 0)) {
2062 0   0     0 while ((scalar(@split) >= 1) and ($split[-1] eq '')) {
2063 0         0 pop @split;
2064             }
2065             }
2066              
2067             # resulting list value in list context
2068 0 0       0 if (wantarray) {
2069 0         0 return @split;
2070             }
2071              
2072             # count of substrings in scalar context
2073             else {
2074 0 0       0 carp "Use of implicit split to \@_ is deprecated" if $^W;
2075 0         0 @_ = @split;
2076 0         0 return scalar @_;
2077             }
2078             }
2079              
2080             #
2081             # get last subexpression offsets
2082             #
2083             sub _last_subexpression_offsets {
2084 0     0   0 my $pattern = $_[0];
2085              
2086             # remove comment
2087 0         0 $pattern =~ s/\(\?\# .*? \)//oxmsg;
2088              
2089 0         0 my $modifier = '';
2090 0 0       0 if ($pattern =~ /\(\?\^? ([\-A-Za-z]+) :/oxms) {
2091 0         0 $modifier = $1;
2092 0         0 $modifier =~ s/-[A-Za-z]*//;
2093             }
2094              
2095             # with /x modifier
2096 0         0 my @char = ();
2097 0 0       0 if ($modifier =~ /x/oxms) {
2098 0         0 @char = $pattern =~ /\G((?>
2099             [^\x80-\xFF\\\#\[\(]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
2100             \\ $q_char |
2101             \# (?>[^\n]*) $ |
2102             \[ (?>(?:[^\x80-\xFF\\\]]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF]|\\\\|\\\]|$q_char)+) \] |
2103             \(\? |
2104             $q_char
2105             ))/oxmsg;
2106             }
2107              
2108             # without /x modifier
2109             else {
2110 0         0 @char = $pattern =~ /\G((?>
2111             [^\x80-\xFF\\\[\(]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
2112             \\ $q_char |
2113             \[ (?>(?:[^\x80-\xFF\\\]]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF]|\\\\|\\\]|$q_char)+) \] |
2114             \(\? |
2115             $q_char
2116             ))/oxmsg;
2117             }
2118              
2119 0         0 return scalar grep { $_ eq '(' } @char;
  0         0  
2120             }
2121              
2122             #
2123             # UTF-8 transliteration (tr///)
2124             #
2125             sub Eutf2::tr($$$$;$) {
2126              
2127 0     0 0 0 my $bind_operator = $_[1];
2128 0         0 my $searchlist = $_[2];
2129 0         0 my $replacementlist = $_[3];
2130 0   0     0 my $modifier = $_[4] || '';
2131              
2132 0 0       0 if ($modifier =~ /r/oxms) {
2133 0 0       0 if ($bind_operator =~ / !~ /oxms) {
2134 0         0 croak "Using !~ with tr///r doesn't make sense";
2135             }
2136             }
2137              
2138 0         0 my @char = $_[0] =~ /\G (?>$q_char) /oxmsg;
2139 0         0 my @searchlist = _charlist_tr($searchlist);
2140 0         0 my @replacementlist = _charlist_tr($replacementlist);
2141              
2142 0         0 my %tr = ();
2143 0         0 for (my $i=0; $i <= $#searchlist; $i++) {
2144 0 0       0 if (not exists $tr{$searchlist[$i]}) {
2145 0 0 0     0 if (defined $replacementlist[$i] and ($replacementlist[$i] ne '')) {
    0 0        
    0          
2146 0         0 $tr{$searchlist[$i]} = $replacementlist[$i];
2147             }
2148             elsif ($modifier =~ /d/oxms) {
2149 0         0 $tr{$searchlist[$i]} = '';
2150             }
2151             elsif (defined $replacementlist[-1] and ($replacementlist[-1] ne '')) {
2152 0         0 $tr{$searchlist[$i]} = $replacementlist[-1];
2153             }
2154             else {
2155 0         0 $tr{$searchlist[$i]} = $searchlist[$i];
2156             }
2157             }
2158             }
2159              
2160 0         0 my $tr = 0;
2161 0         0 my $replaced = '';
2162 0 0       0 if ($modifier =~ /c/oxms) {
2163 0         0 while (defined(my $char = shift @char)) {
2164 0 0       0 if (not exists $tr{$char}) {
2165 0 0       0 if (defined $replacementlist[0]) {
2166 0         0 $replaced .= $replacementlist[0];
2167             }
2168 0         0 $tr++;
2169 0 0       0 if ($modifier =~ /s/oxms) {
2170 0   0     0 while (@char and (not exists $tr{$char[0]})) {
2171 0         0 shift @char;
2172 0         0 $tr++;
2173             }
2174             }
2175             }
2176             else {
2177 0         0 $replaced .= $char;
2178             }
2179             }
2180             }
2181             else {
2182 0         0 while (defined(my $char = shift @char)) {
2183 0 0       0 if (exists $tr{$char}) {
2184 0         0 $replaced .= $tr{$char};
2185 0         0 $tr++;
2186 0 0       0 if ($modifier =~ /s/oxms) {
2187 0   0     0 while (@char and (exists $tr{$char[0]}) and ($tr{$char[0]} eq $tr{$char})) {
      0        
2188 0         0 shift @char;
2189 0         0 $tr++;
2190             }
2191             }
2192             }
2193             else {
2194 0         0 $replaced .= $char;
2195             }
2196             }
2197             }
2198              
2199 0 0       0 if ($modifier =~ /r/oxms) {
2200 0         0 return $replaced;
2201             }
2202             else {
2203 0         0 $_[0] = $replaced;
2204 0 0       0 if ($bind_operator =~ / !~ /oxms) {
2205 0         0 return not $tr;
2206             }
2207             else {
2208 0         0 return $tr;
2209             }
2210             }
2211             }
2212              
2213             #
2214             # UTF-8 chop
2215             #
2216             sub Eutf2::chop(@) {
2217              
2218 0     0 0 0 my $chop;
2219 0 0       0 if (@_ == 0) {
2220 0         0 my @char = /\G (?>$q_char) /oxmsg;
2221 0         0 $chop = pop @char;
2222 0         0 $_ = join '', @char;
2223             }
2224             else {
2225 0         0 for (@_) {
2226 0         0 my @char = /\G (?>$q_char) /oxmsg;
2227 0         0 $chop = pop @char;
2228 0         0 $_ = join '', @char;
2229             }
2230             }
2231 0         0 return $chop;
2232             }
2233              
2234             #
2235             # UTF-8 index by octet
2236             #
2237             sub Eutf2::index($$;$) {
2238              
2239 0     0 1 0 my($str,$substr,$position) = @_;
2240 0   0     0 $position ||= 0;
2241 0         0 my $pos = 0;
2242              
2243 0         0 while ($pos < CORE::length($str)) {
2244 0 0       0 if (CORE::substr($str,$pos,CORE::length($substr)) eq $substr) {
2245 0 0       0 if ($pos >= $position) {
2246 0         0 return $pos;
2247             }
2248             }
2249 0 0       0 if (CORE::substr($str,$pos) =~ /\A ($q_char) /oxms) {
2250 0         0 $pos += CORE::length($1);
2251             }
2252             else {
2253 0         0 $pos += 1;
2254             }
2255             }
2256 0         0 return -1;
2257             }
2258              
2259             #
2260             # UTF-8 reverse index
2261             #
2262             sub Eutf2::rindex($$;$) {
2263              
2264 0     0 0 0 my($str,$substr,$position) = @_;
2265 0   0     0 $position ||= CORE::length($str) - 1;
2266 0         0 my $pos = 0;
2267 0         0 my $rindex = -1;
2268              
2269 0   0     0 while (($pos < CORE::length($str)) and ($pos <= $position)) {
2270 0 0       0 if (CORE::substr($str,$pos,CORE::length($substr)) eq $substr) {
2271 0         0 $rindex = $pos;
2272             }
2273 0 0       0 if (CORE::substr($str,$pos) =~ /\A ($q_char) /oxms) {
2274 0         0 $pos += CORE::length($1);
2275             }
2276             else {
2277 0         0 $pos += 1;
2278             }
2279             }
2280 0         0 return $rindex;
2281             }
2282              
2283             #
2284             # UTF-8 lower case first with parameter
2285             #
2286             sub Eutf2::lcfirst(@) {
2287 0 0   0 0 0 if (@_) {
2288 0         0 my $s = shift @_;
2289 0 0 0     0 if (@_ and wantarray) {
2290 0         0 return Eutf2::lc(CORE::substr($s,0,1)) . CORE::substr($s,1), @_;
2291             }
2292             else {
2293 0         0 return Eutf2::lc(CORE::substr($s,0,1)) . CORE::substr($s,1);
2294             }
2295             }
2296             else {
2297 0         0 return Eutf2::lc(CORE::substr($_,0,1)) . CORE::substr($_,1);
2298             }
2299             }
2300              
2301             #
2302             # UTF-8 lower case first without parameter
2303             #
2304             sub Eutf2::lcfirst_() {
2305 0     0 0 0 return Eutf2::lc(CORE::substr($_,0,1)) . CORE::substr($_,1);
2306             }
2307              
2308             #
2309             # UTF-8 lower case with parameter
2310             #
2311             sub Eutf2::lc(@) {
2312 0 0   0 0 0 if (@_) {
2313 0         0 my $s = shift @_;
2314 0 0 0     0 if (@_ and wantarray) {
2315 0 0       0 return join('', map {defined($lc{$_}) ? $lc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg)), @_;
  0         0  
2316             }
2317             else {
2318 0 0       0 return join('', map {defined($lc{$_}) ? $lc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg));
  0         0  
2319             }
2320             }
2321             else {
2322 0         0 return Eutf2::lc_();
2323             }
2324             }
2325              
2326             #
2327             # UTF-8 lower case without parameter
2328             #
2329             sub Eutf2::lc_() {
2330 0     0 0 0 my $s = $_;
2331 0 0       0 return join '', map {defined($lc{$_}) ? $lc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg);
  0         0  
2332             }
2333              
2334             #
2335             # UTF-8 upper case first with parameter
2336             #
2337             sub Eutf2::ucfirst(@) {
2338 0 0   0 0 0 if (@_) {
2339 0         0 my $s = shift @_;
2340 0 0 0     0 if (@_ and wantarray) {
2341 0         0 return Eutf2::uc(CORE::substr($s,0,1)) . CORE::substr($s,1), @_;
2342             }
2343             else {
2344 0         0 return Eutf2::uc(CORE::substr($s,0,1)) . CORE::substr($s,1);
2345             }
2346             }
2347             else {
2348 0         0 return Eutf2::uc(CORE::substr($_,0,1)) . CORE::substr($_,1);
2349             }
2350             }
2351              
2352             #
2353             # UTF-8 upper case first without parameter
2354             #
2355             sub Eutf2::ucfirst_() {
2356 0     0 0 0 return Eutf2::uc(CORE::substr($_,0,1)) . CORE::substr($_,1);
2357             }
2358              
2359             #
2360             # UTF-8 upper case with parameter
2361             #
2362             sub Eutf2::uc(@) {
2363 0 50   2478 0 0 if (@_) {
2364 2478         3200 my $s = shift @_;
2365 2478 50 33     2734 if (@_ and wantarray) {
2366 2478 0       3753 return join('', map {defined($uc{$_}) ? $uc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg)), @_;
  0         0  
2367             }
2368             else {
2369 0 100       0 return join('', map {defined($uc{$_}) ? $uc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg));
  2478         6912  
2370             }
2371             }
2372             else {
2373 2478         6989 return Eutf2::uc_();
2374             }
2375             }
2376              
2377             #
2378             # UTF-8 upper case without parameter
2379             #
2380             sub Eutf2::uc_() {
2381 0     0 0 0 my $s = $_;
2382 0 0       0 return join '', map {defined($uc{$_}) ? $uc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg);
  0         0  
2383             }
2384              
2385             #
2386             # UTF-8 fold case with parameter
2387             #
2388             sub Eutf2::fc(@) {
2389 0 50   2525 0 0 if (@_) {
2390 2525         3123 my $s = shift @_;
2391 2525 50 33     2665 if (@_ and wantarray) {
2392 2525 0       3830 return join('', map {defined($fc{$_}) ? $fc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg)), @_;
  0         0  
2393             }
2394             else {
2395 0 100       0 return join('', map {defined($fc{$_}) ? $fc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg));
  2525         6556  
2396             }
2397             }
2398             else {
2399 2525         7659 return Eutf2::fc_();
2400             }
2401             }
2402              
2403             #
2404             # UTF-8 fold case without parameter
2405             #
2406             sub Eutf2::fc_() {
2407 0     0 0 0 my $s = $_;
2408 0 0       0 return join '', map {defined($fc{$_}) ? $fc{$_} : $_} ($s =~ /\G ($q_char) /oxmsg);
  0         0  
2409             }
2410              
2411             #
2412             # UTF-8 regexp capture
2413             #
2414             {
2415             sub Eutf2::capture {
2416 0     0 1 0 return $_[0];
2417             }
2418             }
2419              
2420             #
2421             # UTF-8 regexp ignore case modifier
2422             #
2423             sub Eutf2::ignorecase {
2424              
2425 0     0 0 0 my @string = @_;
2426 0         0 my $metachar = qr/[\@\\|[\]{]/oxms;
2427              
2428             # ignore case of $scalar or @array
2429 0         0 for my $string (@string) {
2430              
2431             # split regexp
2432 0         0 my @char = $string =~ /\G (?>\[\^|\\$q_char|$q_char) /oxmsg;
2433              
2434             # unescape character
2435 0         0 for (my $i=0; $i <= $#char; $i++) {
2436 0 0       0 next if not defined $char[$i];
2437              
2438             # open character class [...]
2439 0 0       0 if ($char[$i] eq '[') {
    0          
    0          
    0          
2440 0         0 my $left = $i;
2441              
2442             # [] make die "unmatched [] in regexp ...\n"
2443              
2444 0 0       0 if ($char[$i+1] eq ']') {
2445 0         0 $i++;
2446             }
2447              
2448 0         0 while (1) {
2449 0 0       0 if (++$i > $#char) {
2450 0         0 croak "Unmatched [] in regexp";
2451             }
2452 0 0       0 if ($char[$i] eq ']') {
2453 0         0 my $right = $i;
2454 0         0 my @charlist = charlist_qr(@char[$left+1..$right-1], 'i');
2455              
2456             # escape character
2457 0         0 for my $char (@charlist) {
2458 0 0       0 if (0) {
2459             }
2460              
2461 0         0 elsif ($char =~ /\A [.|)] \z/oxms) {
2462 0         0 $char = '\\' . $char;
2463             }
2464             }
2465              
2466             # [...]
2467 0         0 splice @char, $left, $right-$left+1, '(?:' . join('|', @charlist) . ')';
2468              
2469 0         0 $i = $left;
2470 0         0 last;
2471             }
2472             }
2473             }
2474              
2475             # open character class [^...]
2476             elsif ($char[$i] eq '[^') {
2477 0         0 my $left = $i;
2478              
2479             # [^] make die "unmatched [] in regexp ...\n"
2480              
2481 0 0       0 if ($char[$i+1] eq ']') {
2482 0         0 $i++;
2483             }
2484              
2485 0         0 while (1) {
2486 0 0       0 if (++$i > $#char) {
2487 0         0 croak "Unmatched [] in regexp";
2488             }
2489 0 0       0 if ($char[$i] eq ']') {
2490 0         0 my $right = $i;
2491 0         0 my @charlist = charlist_not_qr(@char[$left+1..$right-1], 'i');
2492              
2493             # escape character
2494 0         0 for my $char (@charlist) {
2495 0 0       0 if (0) {
2496             }
2497              
2498 0         0 elsif ($char =~ /\A [.|)] \z/oxms) {
2499 0         0 $char = '\\' . $char;
2500             }
2501             }
2502              
2503             # [^...]
2504 0         0 splice @char, $left, $right-$left+1, '(?!' . join('|', @charlist) . ")(?:$your_char)";
2505              
2506 0         0 $i = $left;
2507 0         0 last;
2508             }
2509             }
2510             }
2511              
2512             # rewrite classic character class or escape character
2513             elsif (my $char = classic_character_class($char[$i])) {
2514 0         0 $char[$i] = $char;
2515             }
2516              
2517             # with /i modifier
2518             elsif ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) {
2519 0         0 my $uc = Eutf2::uc($char[$i]);
2520 0         0 my $fc = Eutf2::fc($char[$i]);
2521 0 0       0 if ($uc ne $fc) {
2522 0 0       0 if (CORE::length($fc) == 1) {
2523 0         0 $char[$i] = '[' . $uc . $fc . ']';
2524             }
2525             else {
2526 0         0 $char[$i] = '(?:' . $uc . '|' . $fc . ')';
2527             }
2528             }
2529             }
2530             }
2531              
2532             # characterize
2533 0         0 for (my $i=0; $i <= $#char; $i++) {
2534 0 0       0 next if not defined $char[$i];
2535              
2536 0 0       0 if (0) {
2537             }
2538              
2539             # quote character before ? + * {
2540 0 0       0 elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
2541 0 0       0 if ($char[$i-1] !~ /\A [\x00-\xFF] \z/oxms) {
2542 0         0 $char[$i-1] = '(?:' . $char[$i-1] . ')';
2543             }
2544             }
2545             }
2546              
2547 0         0 $string = join '', @char;
2548             }
2549              
2550             # make regexp string
2551 0         0 return @string;
2552             }
2553              
2554             #
2555             # classic character class ( \D \S \W \d \s \w \C \X \H \V \h \v \R \N \b \B )
2556             #
2557             sub Eutf2::classic_character_class {
2558 0     2820 0 0 my($char) = @_;
2559              
2560             return {
2561             '\D' => '${Eutf2::eD}',
2562             '\S' => '${Eutf2::eS}',
2563             '\W' => '${Eutf2::eW}',
2564             '\d' => '[0-9]',
2565              
2566             # Before Perl 5.6, \s only matched the five whitespace characters
2567             # tab, newline, form-feed, carriage return, and the space character
2568             # itself, which, taken together, is the character class [\t\n\f\r ].
2569              
2570             # Vertical tabs are now whitespace
2571             # \s in a regex now matches a vertical tab in all circumstances.
2572             # http://search.cpan.org/dist/perl-5.18.0/pod/perldelta.pod#Vertical_tabs_are_now_whitespace
2573             # \t \n \v \f \r space
2574             # '\s' => '[\x09\x0A \x0C\x0D\x20]',
2575             # '\s' => '[\x09\x0A\x0B\x0C\x0D\x20]',
2576             '\s' => '\s',
2577              
2578             '\w' => '[0-9A-Z_a-z]',
2579             '\C' => '[\x00-\xFF]',
2580             '\X' => 'X',
2581              
2582             # \h \v \H \V
2583              
2584             # P.114 Character Class Shortcuts
2585             # in Chapter 7: In the World of Regular Expressions
2586             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
2587              
2588             # P.357 13.2.3 Whitespace
2589             # in Chapter 13: perlrecharclass: Perl Regular Expression Character Classes
2590             # of ISBN-13: 978-1-906966-02-7 The Perl Language Reference Manual (for Perl version 5.12.1)
2591             #
2592             # 0x00009 CHARACTER TABULATION h s
2593             # 0x0000a LINE FEED (LF) vs
2594             # 0x0000b LINE TABULATION v
2595             # 0x0000c FORM FEED (FF) vs
2596             # 0x0000d CARRIAGE RETURN (CR) vs
2597             # 0x00020 SPACE h s
2598              
2599             # P.196 Table 5-9. Alphanumeric regex metasymbols
2600             # in Chapter 5. Pattern Matching
2601             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
2602              
2603             # (and so on)
2604              
2605             '\H' => '${Eutf2::eH}',
2606             '\V' => '${Eutf2::eV}',
2607             '\h' => '[\x09\x20]',
2608             '\v' => '[\x0A\x0B\x0C\x0D]',
2609             '\R' => '${Eutf2::eR}',
2610              
2611             # \N
2612             #
2613             # http://perldoc.perl.org/perlre.html
2614             # Character Classes and other Special Escapes
2615             # Any character but \n (experimental). Not affected by /s modifier
2616              
2617             '\N' => '${Eutf2::eN}',
2618              
2619             # \b \B
2620              
2621             # P.180 Boundaries: The \b and \B Assertions
2622             # in Chapter 5: Pattern Matching
2623             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
2624              
2625             # P.219 Boundaries: The \b and \B Assertions
2626             # in Chapter 5: Pattern Matching
2627             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
2628              
2629             # \b really means (?:(?<=\w)(?!\w)|(?
2630             # or (?:(?<=\A|\W)(?=\w)|(?<=\w)(?=\W|\z))
2631             '\b' => '${Eutf2::eb}',
2632              
2633             # \B really means (?:(?<=\w)(?=\w)|(?
2634             # or (?:(?<=\w)(?=\w)|(?<=\W)(?=\W))
2635             '\B' => '${Eutf2::eB}',
2636              
2637 2820   100     3964 }->{$char} || '';
2638             }
2639              
2640             #
2641             # prepare UTF-8 characters per length
2642             #
2643              
2644             # 1 octet characters
2645             my @chars1 = ();
2646             sub chars1 {
2647 2820 0   0 0 143237 if (@chars1) {
2648 0         0 return @chars1;
2649             }
2650 0 0       0 if (exists $range_tr{1}) {
2651 0         0 my @ranges = @{ $range_tr{1} };
  0         0  
2652 0         0 while (my @range = splice(@ranges,0,1)) {
2653 0         0 for my $oct0 (@{$range[0]}) {
  0         0  
2654 0         0 push @chars1, pack 'C', $oct0;
2655             }
2656             }
2657             }
2658 0         0 return @chars1;
2659             }
2660              
2661             # 2 octets characters
2662             my @chars2 = ();
2663             sub chars2 {
2664 0 0   0 0 0 if (@chars2) {
2665 0         0 return @chars2;
2666             }
2667 0 0       0 if (exists $range_tr{2}) {
2668 0         0 my @ranges = @{ $range_tr{2} };
  0         0  
2669 0         0 while (my @range = splice(@ranges,0,2)) {
2670 0         0 for my $oct0 (@{$range[0]}) {
  0         0  
2671 0         0 for my $oct1 (@{$range[1]}) {
  0         0  
2672 0         0 push @chars2, pack 'CC', $oct0,$oct1;
2673             }
2674             }
2675             }
2676             }
2677 0         0 return @chars2;
2678             }
2679              
2680             # 3 octets characters
2681             my @chars3 = ();
2682             sub chars3 {
2683 0 0   0 0 0 if (@chars3) {
2684 0         0 return @chars3;
2685             }
2686 0 0       0 if (exists $range_tr{3}) {
2687 0         0 my @ranges = @{ $range_tr{3} };
  0         0  
2688 0         0 while (my @range = splice(@ranges,0,3)) {
2689 0         0 for my $oct0 (@{$range[0]}) {
  0         0  
2690 0         0 for my $oct1 (@{$range[1]}) {
  0         0  
2691 0         0 for my $oct2 (@{$range[2]}) {
  0         0  
2692 0         0 push @chars3, pack 'CCC', $oct0,$oct1,$oct2;
2693             }
2694             }
2695             }
2696             }
2697             }
2698 0         0 return @chars3;
2699             }
2700              
2701             # 4 octets characters
2702             my @chars4 = ();
2703             sub chars4 {
2704 0 0   0 0 0 if (@chars4) {
2705 0         0 return @chars4;
2706             }
2707 0 0       0 if (exists $range_tr{4}) {
2708 0         0 my @ranges = @{ $range_tr{4} };
  0         0  
2709 0         0 while (my @range = splice(@ranges,0,4)) {
2710 0         0 for my $oct0 (@{$range[0]}) {
  0         0  
2711 0         0 for my $oct1 (@{$range[1]}) {
  0         0  
2712 0         0 for my $oct2 (@{$range[2]}) {
  0         0  
2713 0         0 for my $oct3 (@{$range[3]}) {
  0         0  
2714 0         0 push @chars4, pack 'CCCC', $oct0,$oct1,$oct2,$oct3;
2715             }
2716             }
2717             }
2718             }
2719             }
2720             }
2721 0         0 return @chars4;
2722             }
2723              
2724             #
2725             # UTF-8 open character list for tr
2726             #
2727             sub _charlist_tr {
2728              
2729 0     0   0 local $_ = shift @_;
2730              
2731             # unescape character
2732 0         0 my @char = ();
2733 0         0 while (not /\G \z/oxmsgc) {
2734 0 0       0 if (/\G (\\0?55|\\x2[Dd]|\\-) /oxmsgc) {
    0          
    0          
    0          
    0          
    0          
    0          
2735 0         0 push @char, '\-';
2736             }
2737             elsif (/\G \\ ([0-7]{2,3}) /oxmsgc) {
2738 0         0 push @char, CORE::chr(oct $1);
2739             }
2740             elsif (/\G \\x ([0-9A-Fa-f]{1,2}) /oxmsgc) {
2741 0         0 push @char, CORE::chr(hex $1);
2742             }
2743             elsif (/\G \\c ([\x40-\x5F]) /oxmsgc) {
2744 0         0 push @char, CORE::chr(CORE::ord($1) & 0x1F);
2745             }
2746             elsif (/\G (\\ [0nrtfbae]) /oxmsgc) {
2747             push @char, {
2748             '\0' => "\0",
2749             '\n' => "\n",
2750             '\r' => "\r",
2751             '\t' => "\t",
2752             '\f' => "\f",
2753             '\b' => "\x08", # \b means backspace in character class
2754             '\a' => "\a",
2755             '\e' => "\e",
2756 0         0 }->{$1};
2757             }
2758             elsif (/\G \\ ($q_char) /oxmsgc) {
2759 0         0 push @char, $1;
2760             }
2761             elsif (/\G ($q_char) /oxmsgc) {
2762 0         0 push @char, $1;
2763             }
2764             }
2765              
2766             # join separated multiple-octet
2767 0         0 @char = join('',@char) =~ /\G (?>\\-|$q_char) /oxmsg;
2768              
2769             # unescape '-'
2770 0         0 my @i = ();
2771 0         0 for my $i (0 .. $#char) {
2772 0 0       0 if ($char[$i] eq '\-') {
    0          
2773 0         0 $char[$i] = '-';
2774             }
2775             elsif ($char[$i] eq '-') {
2776 0 0 0     0 if ((0 < $i) and ($i < $#char)) {
2777 0         0 push @i, $i;
2778             }
2779             }
2780             }
2781              
2782             # open character list (reverse for splice)
2783 0         0 for my $i (CORE::reverse @i) {
2784 0         0 my @range = ();
2785              
2786             # range error
2787 0 0 0     0 if ((CORE::length($char[$i-1]) > CORE::length($char[$i+1])) or ($char[$i-1] gt $char[$i+1])) {
2788 0         0 croak "Invalid tr/// range \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2789             }
2790              
2791             # range of multiple-octet code
2792 0 0       0 if (CORE::length($char[$i-1]) == 1) {
    0          
    0          
    0          
2793 0 0       0 if (CORE::length($char[$i+1]) == 1) {
    0          
    0          
    0          
2794 0 0       0 push @range, grep {($char[$i-1] le $_) and ($_ le $char[$i+1])} chars1();
  0         0  
2795             }
2796             elsif (CORE::length($char[$i+1]) == 2) {
2797 0         0 push @range, grep {$char[$i-1] le $_} chars1();
  0         0  
2798 0         0 push @range, grep {$_ le $char[$i+1]} chars2();
  0         0  
2799             }
2800             elsif (CORE::length($char[$i+1]) == 3) {
2801 0         0 push @range, grep {$char[$i-1] le $_} chars1();
  0         0  
2802 0         0 push @range, chars2();
2803 0         0 push @range, grep {$_ le $char[$i+1]} chars3();
  0         0  
2804             }
2805             elsif (CORE::length($char[$i+1]) == 4) {
2806 0         0 push @range, grep {$char[$i-1] le $_} chars1();
  0         0  
2807 0         0 push @range, chars2();
2808 0         0 push @range, chars3();
2809 0         0 push @range, grep {$_ le $char[$i+1]} chars4();
  0         0  
2810             }
2811             else {
2812 0         0 croak "Invalid tr/// range (over 4octets) \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2813             }
2814             }
2815             elsif (CORE::length($char[$i-1]) == 2) {
2816 0 0       0 if (CORE::length($char[$i+1]) == 2) {
    0          
    0          
2817 0 0       0 push @range, grep {($char[$i-1] le $_) and ($_ le $char[$i+1])} chars2();
  0         0  
2818             }
2819             elsif (CORE::length($char[$i+1]) == 3) {
2820 0         0 push @range, grep {$char[$i-1] le $_} chars2();
  0         0  
2821 0         0 push @range, grep {$_ le $char[$i+1]} chars3();
  0         0  
2822             }
2823             elsif (CORE::length($char[$i+1]) == 4) {
2824 0         0 push @range, grep {$char[$i-1] le $_} chars2();
  0         0  
2825 0         0 push @range, chars3();
2826 0         0 push @range, grep {$_ le $char[$i+1]} chars4();
  0         0  
2827             }
2828             else {
2829 0         0 croak "Invalid tr/// range (over 4octets) \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2830             }
2831             }
2832             elsif (CORE::length($char[$i-1]) == 3) {
2833 0 0       0 if (CORE::length($char[$i+1]) == 3) {
    0          
2834 0 0       0 push @range, grep {($char[$i-1] le $_) and ($_ le $char[$i+1])} chars3();
  0         0  
2835             }
2836             elsif (CORE::length($char[$i+1]) == 4) {
2837 0         0 push @range, grep {$char[$i-1] le $_} chars3();
  0         0  
2838 0         0 push @range, grep {$_ le $char[$i+1]} chars4();
  0         0  
2839             }
2840             else {
2841 0         0 croak "Invalid tr/// range (over 4octets) \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2842             }
2843             }
2844             elsif (CORE::length($char[$i-1]) == 4) {
2845 0 0       0 if (CORE::length($char[$i+1]) == 4) {
2846 0 0       0 push @range, grep {($char[$i-1] le $_) and ($_ le $char[$i+1])} chars4();
  0         0  
2847             }
2848             else {
2849 0         0 croak "Invalid tr/// range (over 4octets) \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2850             }
2851             }
2852             else {
2853 0         0 croak "Invalid tr/// range (over 4octets) \"\\x" . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]) . '"';
2854             }
2855              
2856 0         0 splice @char, $i-1, 3, @range;
2857             }
2858              
2859 0         0 return @char;
2860             }
2861              
2862             #
2863             # UTF-8 open character class
2864             #
2865             sub _cc {
2866 0 50   933   0 if (scalar(@_) == 0) {
    100          
    50          
2867 933         1955 die __FILE__, ": subroutine cc got no parameter.\n";
2868             }
2869             elsif (scalar(@_) == 1) {
2870 0         0 return sprintf('\x%02X',$_[0]);
2871             }
2872             elsif (scalar(@_) == 2) {
2873 482 50       1374 if ($_[0] > $_[1]) {
    100          
    50          
2874 451         875 die __FILE__, ": subroutine cc got \$_[0] > \$_[1] parameters).\n";
2875             }
2876             elsif ($_[0] == $_[1]) {
2877 0         0 return sprintf('\x%02X',$_[0]);
2878             }
2879             elsif (($_[0]+1) == $_[1]) {
2880 40         94 return sprintf('[\\x%02X\\x%02X]',$_[0],$_[1]);
2881             }
2882             else {
2883 0         0 return sprintf('[\\x%02X-\\x%02X]',$_[0],$_[1]);
2884             }
2885             }
2886             else {
2887 411         1707 die __FILE__, ": subroutine cc got 3 or more parameters (@{[scalar(@_)]} parameters).\n";
  0         0  
2888             }
2889             }
2890              
2891             #
2892             # UTF-8 octet range
2893             #
2894             sub _octets {
2895 0     577   0 my $length = shift @_;
2896              
2897 577 100       878 if ($length == 1) {
    100          
    50          
    0          
2898 577         1445 my($a1) = unpack 'C', $_[0];
2899 406         1041 my($z1) = unpack 'C', $_[1];
2900              
2901 406 50       695 if ($a1 > $z1) {
2902 406         876 croak 'Invalid [] range in regexp (CORE::ord(A) > CORE::ord(B)) ' . '\x' . unpack('H*',$a1) . '-\x' . unpack('H*',$z1);
2903             }
2904              
2905 0 50       0 if ($a1 == $z1) {
    50          
2906 406         968 return sprintf('\x%02X',$a1);
2907             }
2908             elsif (($a1+1) == $z1) {
2909 0         0 return sprintf('\x%02X\x%02X',$a1,$z1);
2910             }
2911             else {
2912 0         0 return sprintf('\x%02X-\x%02X',$a1,$z1);
2913             }
2914             }
2915             elsif ($length == 2) {
2916 406         2329 my($a1,$a2) = unpack 'CC', $_[0];
2917 20         50 my($z1,$z2) = unpack 'CC', $_[1];
2918 20         36 my($A1,$A2) = unpack 'CC', $_[2];
2919 20         36 my($Z1,$Z2) = unpack 'CC', $_[3];
2920              
2921 20 50       33 if ($a1 == $z1) {
    50          
2922             return (
2923             # 11111111 222222222222
2924             # A A Z
2925 20         51 _cc($a1) . _cc($a2,$z2), # a2-z2
2926             );
2927             }
2928             elsif (($a1+1) == $z1) {
2929             return (
2930             # 11111111111 222222222222
2931             # A Z A Z
2932 0         0 _cc($a1) . _cc($a2,$Z2), # a2-
2933             _cc( $z1) . _cc($A2,$z2), # -z2
2934             );
2935             }
2936             else {
2937             return (
2938             # 1111111111111111 222222222222
2939             # A Z A Z
2940 0         0 _cc($a1) . _cc($a2,$Z2), # a2-
2941             _cc($a1+1,$z1-1) . _cc($A2,$Z2), # -
2942             _cc( $z1) . _cc($A2,$z2), # -z2
2943             );
2944             }
2945             }
2946             elsif ($length == 3) {
2947 20         45 my($a1,$a2,$a3) = unpack 'CCC', $_[0];
2948 151         413 my($z1,$z2,$z3) = unpack 'CCC', $_[1];
2949 151         328 my($A1,$A2,$A3) = unpack 'CCC', $_[2];
2950 151         272 my($Z1,$Z2,$Z3) = unpack 'CCC', $_[3];
2951              
2952 151 100       258 if ($a1 == $z1) {
    50          
2953 151 100       298 if ($a2 == $z2) {
    50          
2954             return (
2955             # 11111111 22222222 333333333333
2956             # A A A Z
2957 131         430 _cc($a1) . _cc($a2) . _cc($a3,$z3), # a3-z3
2958             );
2959             }
2960             elsif (($a2+1) == $z2) {
2961             return (
2962             # 11111111 22222222222 333333333333
2963             # A A Z A Z
2964 111         311 _cc($a1) . _cc($a2) . _cc($a3,$Z3), # a3-
2965             _cc($a1) . _cc( $z2) . _cc($A3,$z3), # -z3
2966             );
2967             }
2968             else {
2969             return (
2970             # 11111111 2222222222222222 333333333333
2971             # A A Z A Z
2972 0         0 _cc($a1) . _cc($a2) . _cc($a3,$Z3), # a3-
2973             _cc($a1) . _cc($a2+1,$z2-1) . _cc($A3,$Z3), # -
2974             _cc($a1) . _cc( $z2) . _cc($A3,$z3), # -z3
2975             );
2976             }
2977             }
2978             elsif (($a1+1) == $z1) {
2979             return (
2980             # 11111111111 22222222222222 333333333333
2981             # A Z A Z A Z
2982 20         37 _cc($a1) . _cc($a2) . _cc($a3,$Z3), # a3-
2983             _cc($a1) . _cc($a2+1,$Z2) . _cc($A3,$Z3), # -
2984             _cc( $z1) . _cc($A2,$z2-1) . _cc($A3,$Z3), # -
2985             _cc( $z1) . _cc( $z2) . _cc($A3,$z3), # -z3
2986             );
2987             }
2988             else {
2989             return (
2990             # 1111111111111111 22222222222222 333333333333
2991             # A Z A Z A Z
2992 0         0 _cc($a1) . _cc($a2) . _cc($a3,$Z3), # a3-
2993             _cc($a1) . _cc($a2+1,$Z2) . _cc($A3,$Z3), # -
2994             _cc($a1+1,$z1-1) . _cc($A2,$Z2) . _cc($A3,$Z3), # -
2995             _cc( $z1) . _cc($A2,$z2-1) . _cc($A3,$Z3), # -
2996             _cc( $z1) . _cc( $z2) . _cc($A3,$z3), # -z3
2997             );
2998             }
2999             }
3000             elsif ($length == 4) {
3001 20         32 my($a1,$a2,$a3,$a4) = unpack 'CCCC', $_[0];
3002 0         0 my($z1,$z2,$z3,$z4) = unpack 'CCCC', $_[1];
3003 0         0 my($A1,$A2,$A3,$A4) = unpack 'CCCC', $_[0];
3004 0         0 my($Z1,$Z2,$Z3,$Z4) = unpack 'CCCC', $_[1];
3005              
3006 0 0       0 if ($a1 == $z1) {
    0          
3007 0 0       0 if ($a2 == $z2) {
    0          
3008 0 0       0 if ($a3 == $z3) {
    0          
3009             return (
3010             # 11111111 22222222 33333333 444444444444
3011             # A A A A Z
3012 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$z4), # a4-z4
3013             );
3014             }
3015             elsif (($a3+1) == $z3) {
3016             return (
3017             # 11111111 22222222 33333333333 444444444444
3018             # A A A Z A Z
3019 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3020             _cc($a1) . _cc($a2) . _cc( $z3) . _cc($A4,$z4), # -z4
3021             );
3022             }
3023             else {
3024             return (
3025             # 11111111 22222222 3333333333333333 444444444444
3026             # A A A Z A Z
3027 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3028             _cc($a1) . _cc($a2) . _cc($a3+1,$z3-1) . _cc($A4,$Z4), # -
3029             _cc($a1) . _cc($a2) . _cc( $z3) . _cc($A4,$z4), # -z4
3030             );
3031             }
3032             }
3033             elsif (($a2+1) == $z2) {
3034             return (
3035             # 11111111 22222222222 33333333333333 444444444444
3036             # A A Z A Z A Z
3037 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3038             _cc($a1) . _cc($a2) . _cc($a3+1,$Z3) . _cc($A4,$Z4), # -
3039             _cc($a1) . _cc( $z2) . _cc($A3,$z3-1) . _cc($A4,$Z4), # -
3040             _cc($a1) . _cc( $z2) . _cc( $z3) . _cc($A4,$z4), # -z4
3041             );
3042             }
3043             else {
3044             return (
3045             # 11111111 2222222222222222 33333333333333 444444444444
3046             # A A Z A Z A Z
3047 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3048             _cc($a1) . _cc($a2) . _cc($a3+1,$Z3) . _cc($A4,$Z4), # -
3049             _cc($a1) . _cc($a2+1,$z2-1) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3050             _cc($a1) . _cc( $z2) . _cc($A3,$z3-1) . _cc($A4,$Z4), # -
3051             _cc($a1) . _cc( $z2) . _cc( $z3) . _cc($A4,$z4), # -z4
3052             );
3053             }
3054             }
3055             elsif (($a1+1) == $z1) {
3056             return (
3057             # 11111111111 22222222222222 33333333333333 444444444444
3058             # A Z A Z A Z A Z
3059 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3060             _cc($a1) . _cc($a2) . _cc($a3+1,$Z3) . _cc($A4,$Z4), # -
3061             _cc($a1) . _cc($a2+1,$Z2) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3062             _cc( $z1) . _cc($A2,$z2-1) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3063             _cc( $z1) . _cc( $z2) . _cc($A3,$z3-1) . _cc($A4,$Z4), # -
3064             _cc( $z1) . _cc( $z2) . _cc( $z3) . _cc($A4,$z4), # -z4
3065             );
3066             }
3067             else {
3068             return (
3069             # 1111111111111111 22222222222222 33333333333333 444444444444
3070             # A Z A Z A Z A Z
3071 0         0 _cc($a1) . _cc($a2) . _cc($a3) . _cc($a4,$Z4), # a4-
3072             _cc($a1) . _cc($a2) . _cc($a3+1,$Z3) . _cc($A4,$Z4), # -
3073             _cc($a1) . _cc($a2+1,$Z2) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3074             _cc($a1+1,$z1-1) . _cc($A2,$Z2) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3075             _cc( $z1) . _cc($A2,$z2-1) . _cc($A3,$Z3) . _cc($A4,$Z4), # -
3076             _cc( $z1) . _cc( $z2) . _cc($A3,$z3-1) . _cc($A4,$Z4), # -
3077             _cc( $z1) . _cc( $z2) . _cc( $z3) . _cc($A4,$z4), # -z4
3078             );
3079             }
3080             }
3081             else {
3082 0         0 die __FILE__, ": subroutine _octets got invalid length ($length).\n";
3083             }
3084             }
3085              
3086             #
3087             # UTF-8 range regexp
3088             #
3089             sub _range_regexp {
3090 0     537   0 my($length,$first,$last) = @_;
3091              
3092 537         1281 my @range_regexp = ();
3093 537 50       738 if (not exists $range_tr{$length}) {
3094 537         1182 return @range_regexp;
3095             }
3096              
3097 0         0 my @ranges = @{ $range_tr{$length} };
  537         689  
3098 537         1246 while (my @range = splice(@ranges,0,$length)) {
3099 537         1467 my $min = '';
3100 1316         1802 my $max = '';
3101 1316         1384 for (my $i=0; $i < $length; $i++) {
3102 1316         2215 $min .= pack 'C', $range[$i][0];
3103 2384         4045 $max .= pack 'C', $range[$i][-1];
3104             }
3105              
3106             # min___max
3107             # FIRST_____________LAST
3108             # (nothing)
3109              
3110 2384 100 66     4070 if ($max lt $first) {
    100 100        
    50 33        
    100 100        
    100 66        
    100 66        
    50 66        
3111             }
3112              
3113             # **********
3114             # min_________max
3115             # FIRST_____________LAST
3116             # **********
3117              
3118             elsif (($min le $first) and ($first le $max) and ($max le $last)) {
3119 1316         10161 push @range_regexp, _octets($length,$first,$max,$min,$max);
3120             }
3121              
3122             # **********************
3123             # min________________max
3124             # FIRST_____________LAST
3125             # **********************
3126              
3127             elsif (($min eq $first) and ($max eq $last)) {
3128 28         71 push @range_regexp, _octets($length,$first,$last,$min,$max);
3129             }
3130              
3131             # *********
3132             # min___max
3133             # FIRST_____________LAST
3134             # *********
3135              
3136             elsif (($first le $min) and ($max le $last)) {
3137 0         0 push @range_regexp, _octets($length,$min,$max,$min,$max);
3138             }
3139              
3140             # **********************
3141             # min__________________________max
3142             # FIRST_____________LAST
3143             # **********************
3144              
3145             elsif (($min le $first) and ($last le $max)) {
3146 60         102 push @range_regexp, _octets($length,$first,$last,$min,$max);
3147             }
3148              
3149             # *********
3150             # min________max
3151             # FIRST_____________LAST
3152             # *********
3153              
3154             elsif (($first le $min) and ($min le $last) and ($last le $max)) {
3155 469         1077 push @range_regexp, _octets($length,$min,$last,$min,$max);
3156             }
3157              
3158             # min___max
3159             # FIRST_____________LAST
3160             # (nothing)
3161              
3162             elsif ($last lt $min) {
3163             }
3164              
3165             else {
3166 20         64 die __FILE__, ": subroutine _range_regexp panic.\n";
3167             }
3168             }
3169              
3170 0         0 return @range_regexp;
3171             }
3172              
3173             #
3174             # UTF-8 open character list for qr and not qr
3175             #
3176             sub _charlist {
3177              
3178 537     770   1171 my $modifier = pop @_;
3179 770         1158 my @char = @_;
3180              
3181 770 100       1590 my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
3182              
3183             # unescape character
3184 770         1698 for (my $i=0; $i <= $#char; $i++) {
3185              
3186             # escape - to ...
3187 770 100 100     2467 if ($char[$i] eq '-') {
    50          
    50          
    50          
    50          
    50          
    100          
    50          
    100          
    100          
    100          
    100          
3188 2660 100 100     19194 if ((0 < $i) and ($i < $#char)) {
3189 522         1707 $char[$i] = '...';
3190             }
3191             }
3192              
3193             # octal escape sequence
3194             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
3195 497         1029 $char[$i] = octchr($1);
3196             }
3197              
3198             # hexadecimal escape sequence
3199             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
3200 0         0 $char[$i] = hexchr($1);
3201             }
3202              
3203             # \b{...} --> b\{...}
3204             # \B{...} --> B\{...}
3205             # \N{CHARNAME} --> N\{CHARNAME}
3206             # \p{PROPERTY} --> p\{PROPERTY}
3207             # \P{PROPERTY} --> P\{PROPERTY}
3208             elsif ($char[$i] =~ /\A \\ ([bBNpP]) ( \{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
3209 0         0 $char[$i] = $1 . '\\' . $2;
3210             }
3211              
3212             # \p, \P, \X --> p, P, X
3213             elsif ($char[$i] =~ /\A \\ ( [pPX] ) \z/oxms) {
3214 0         0 $char[$i] = $1;
3215             }
3216              
3217             elsif ($char[$i] =~ /\A \\ ([0-7]{2,3}) \z/oxms) {
3218 0         0 $char[$i] = CORE::chr oct $1;
3219             }
3220             elsif ($char[$i] =~ /\A \\x ([0-9A-Fa-f]{1,2}) \z/oxms) {
3221 0         0 $char[$i] = CORE::chr hex $1;
3222             }
3223             elsif ($char[$i] =~ /\A \\c ([\x40-\x5F]) \z/oxms) {
3224 206         707 $char[$i] = CORE::chr(CORE::ord($1) & 0x1F);
3225             }
3226             elsif ($char[$i] =~ /\A (\\ [0nrtfbaedswDSWHVhvR]) \z/oxms) {
3227             $char[$i] = {
3228             '\0' => "\0",
3229             '\n' => "\n",
3230             '\r' => "\r",
3231             '\t' => "\t",
3232             '\f' => "\f",
3233             '\b' => "\x08", # \b means backspace in character class
3234             '\a' => "\a",
3235             '\e' => "\e",
3236             '\d' => '[0-9]',
3237              
3238             # Vertical tabs are now whitespace
3239             # \s in a regex now matches a vertical tab in all circumstances.
3240             # http://search.cpan.org/dist/perl-5.18.0/pod/perldelta.pod#Vertical_tabs_are_now_whitespace
3241             # \t \n \v \f \r space
3242             # '\s' => '[\x09\x0A \x0C\x0D\x20]',
3243             # '\s' => '[\x09\x0A\x0B\x0C\x0D\x20]',
3244             '\s' => '\s',
3245              
3246             '\w' => '[0-9A-Z_a-z]',
3247             '\D' => '${Eutf2::eD}',
3248             '\S' => '${Eutf2::eS}',
3249             '\W' => '${Eutf2::eW}',
3250              
3251             '\H' => '${Eutf2::eH}',
3252             '\V' => '${Eutf2::eV}',
3253             '\h' => '[\x09\x20]',
3254             '\v' => '[\x0A\x0B\x0C\x0D]',
3255             '\R' => '${Eutf2::eR}',
3256              
3257 0         0 }->{$1};
3258             }
3259              
3260             # POSIX-style character classes
3261             elsif ($ignorecase and ($char[$i] =~ /\A ( \[\: \^? (?:lower|upper) :\] ) \z/oxms)) {
3262             $char[$i] = {
3263              
3264             '[:lower:]' => '[\x41-\x5A\x61-\x7A]',
3265             '[:upper:]' => '[\x41-\x5A\x61-\x7A]',
3266             '[:^lower:]' => '${Eutf2::not_lower_i}',
3267             '[:^upper:]' => '${Eutf2::not_upper_i}',
3268              
3269 33         549 }->{$1};
3270             }
3271             elsif ($char[$i] =~ /\A ( \[\: \^? (?:alnum|alpha|ascii|blank|cntrl|digit|graph|lower|print|punct|space|upper|word|xdigit) :\] ) \z/oxms) {
3272             $char[$i] = {
3273              
3274             '[:alnum:]' => '[\x30-\x39\x41-\x5A\x61-\x7A]',
3275             '[:alpha:]' => '[\x41-\x5A\x61-\x7A]',
3276             '[:ascii:]' => '[\x00-\x7F]',
3277             '[:blank:]' => '[\x09\x20]',
3278             '[:cntrl:]' => '[\x00-\x1F\x7F]',
3279             '[:digit:]' => '[\x30-\x39]',
3280             '[:graph:]' => '[\x21-\x7F]',
3281             '[:lower:]' => '[\x61-\x7A]',
3282             '[:print:]' => '[\x20-\x7F]',
3283             '[:punct:]' => '[\x21-\x2F\x3A-\x3F\x40\x5B-\x5F\x60\x7B-\x7E]',
3284              
3285             # P.174 POSIX-Style Character Classes
3286             # in Chapter 5: Pattern Matching
3287             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
3288              
3289             # P.311 11.2.4 Character Classes and other Special Escapes
3290             # in Chapter 11: perlre: Perl regular expressions
3291             # of ISBN-13: 978-1-906966-02-7 The Perl Language Reference Manual (for Perl version 5.12.1)
3292              
3293             # P.210 POSIX-Style Character Classes
3294             # in Chapter 5: Pattern Matching
3295             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
3296              
3297             '[:space:]' => '[\s\x0B]', # "\s" plus vertical tab ("\cK")
3298              
3299             '[:upper:]' => '[\x41-\x5A]',
3300             '[:word:]' => '[\x30-\x39\x41-\x5A\x5F\x61-\x7A]',
3301             '[:xdigit:]' => '[\x30-\x39\x41-\x46\x61-\x66]',
3302             '[:^alnum:]' => '${Eutf2::not_alnum}',
3303             '[:^alpha:]' => '${Eutf2::not_alpha}',
3304             '[:^ascii:]' => '${Eutf2::not_ascii}',
3305             '[:^blank:]' => '${Eutf2::not_blank}',
3306             '[:^cntrl:]' => '${Eutf2::not_cntrl}',
3307             '[:^digit:]' => '${Eutf2::not_digit}',
3308             '[:^graph:]' => '${Eutf2::not_graph}',
3309             '[:^lower:]' => '${Eutf2::not_lower}',
3310             '[:^print:]' => '${Eutf2::not_print}',
3311             '[:^punct:]' => '${Eutf2::not_punct}',
3312             '[:^space:]' => '${Eutf2::not_space}',
3313             '[:^upper:]' => '${Eutf2::not_upper}',
3314             '[:^word:]' => '${Eutf2::not_word}',
3315             '[:^xdigit:]' => '${Eutf2::not_xdigit}',
3316              
3317 8         57 }->{$1};
3318             }
3319             elsif ($char[$i] =~ /\A \\ ($q_char) \z/oxms) {
3320 70         1387 $char[$i] = $1;
3321             }
3322             }
3323              
3324             # open character list
3325 7         42 my @singleoctet = ();
3326 770         1288 my @multipleoctet = ();
3327 770         973 for (my $i=0; $i <= $#char; ) {
3328              
3329             # escaped -
3330 770 100 100     1716 if (defined($char[$i+1]) and ($char[$i+1] eq '...')) {
    100          
    100          
    50          
    50          
    100          
3331 2163         8647 $i += 1;
3332 497         657 next;
3333             }
3334              
3335             # make range regexp
3336             elsif ($char[$i] eq '...') {
3337              
3338             # range error
3339 497 50       905 if (CORE::length($char[$i-1]) > CORE::length($char[$i+1])) {
    100          
3340 497         1831 croak 'Invalid [] range in regexp (length(A) > length(B)) ' . '\x' . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]);
3341             }
3342             elsif (CORE::length($char[$i-1]) == CORE::length($char[$i+1])) {
3343 0 50       0 if ($char[$i-1] gt $char[$i+1]) {
3344 477         1119 croak 'Invalid [] range in regexp (CORE::ord(A) > CORE::ord(B)) ' . '\x' . unpack('H*',$char[$i-1]) . '-\x' . unpack('H*',$char[$i+1]);
3345             }
3346             }
3347              
3348             # make range regexp per length
3349 0         0 for my $length (CORE::length($char[$i-1]) .. CORE::length($char[$i+1])) {
3350 497         1403 my @regexp = ();
3351              
3352             # is first and last
3353 537 100 100     696 if (($length == CORE::length($char[$i-1])) and ($length == CORE::length($char[$i+1]))) {
    100 66        
    100          
    50          
3354 537         1913 push @regexp, _range_regexp($length, $char[$i-1], $char[$i+1]);
3355             }
3356              
3357             # is first
3358             elsif ($length == CORE::length($char[$i-1])) {
3359 477         1204 push @regexp, _range_regexp($length, $char[$i-1], "\xFF" x $length);
3360             }
3361              
3362             # is inside in first and last
3363             elsif ((CORE::length($char[$i-1]) < $length) and ($length < CORE::length($char[$i+1]))) {
3364 20         72 push @regexp, _range_regexp($length, "\x00" x $length, "\xFF" x $length);
3365             }
3366              
3367             # is last
3368             elsif ($length == CORE::length($char[$i+1])) {
3369 20         73 push @regexp, _range_regexp($length, "\x00" x $length, $char[$i+1]);
3370             }
3371              
3372             else {
3373 20         62 die __FILE__, ": subroutine make_regexp panic.\n";
3374             }
3375              
3376 0 100       0 if ($length == 1) {
3377 537         1052 push @singleoctet, @regexp;
3378             }
3379             else {
3380 386         848 push @multipleoctet, @regexp;
3381             }
3382             }
3383              
3384 151         342 $i += 2;
3385             }
3386              
3387             # with /i modifier
3388             elsif ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) {
3389 497 100       1018 if ($modifier =~ /i/oxms) {
3390 764         1126 my $uc = Eutf2::uc($char[$i]);
3391 192         313 my $fc = Eutf2::fc($char[$i]);
3392 192 50       325 if ($uc ne $fc) {
3393 192 50       288 if (CORE::length($fc) == 1) {
3394 192         255 push @singleoctet, $uc, $fc;
3395             }
3396             else {
3397 192         341 push @singleoctet, $uc;
3398 0         0 push @multipleoctet, $fc;
3399             }
3400             }
3401             else {
3402 0         0 push @singleoctet, $char[$i];
3403             }
3404             }
3405             else {
3406 0         0 push @singleoctet, $char[$i];
3407             }
3408 572         819 $i += 1;
3409             }
3410              
3411             # single character of single octet code
3412             elsif ($char[$i] =~ /\A (?: \\h ) \z/oxms) {
3413 764         1395 push @singleoctet, "\t", "\x20";
3414 0         0 $i += 1;
3415             }
3416             elsif ($char[$i] =~ /\A (?: \\v ) \z/oxms) {
3417 0         0 push @singleoctet, "\x0A", "\x0B", "\x0C", "\x0D";
3418 0         0 $i += 1;
3419             }
3420             elsif ($char[$i] =~ /\A (?: \\d | \\s | \\w ) \z/oxms) {
3421 0         0 push @singleoctet, $char[$i];
3422 2         6 $i += 1;
3423             }
3424              
3425             # single character of multiple-octet code
3426             else {
3427 2         5 push @multipleoctet, $char[$i];
3428 403         705 $i += 1;
3429             }
3430             }
3431              
3432             # quote metachar
3433 403         643 for (@singleoctet) {
3434 770 50       1882 if ($_ eq '...') {
    100          
    100          
    100          
    100          
3435 1364         5457 $_ = '-';
3436             }
3437             elsif (/\A \n \z/oxms) {
3438 0         0 $_ = '\n';
3439             }
3440             elsif (/\A \r \z/oxms) {
3441 8         36 $_ = '\r';
3442             }
3443             elsif (/\A ([\x00-\x20\x7F-\xFF]) \z/oxms) {
3444 8         20 $_ = sprintf('\x%02X', CORE::ord $1);
3445             }
3446             elsif (/\A [\x00-\xFF] \z/oxms) {
3447 1         6 $_ = quotemeta $_;
3448             }
3449             }
3450              
3451             # return character list
3452 939         1402 return \@singleoctet, \@multipleoctet;
3453             }
3454              
3455             #
3456             # UTF-8 octal escape sequence
3457             #
3458             sub octchr {
3459 770     5 0 2610 my($octdigit) = @_;
3460              
3461 5         19 my @binary = ();
3462 5         9 for my $octal (split(//,$octdigit)) {
3463             push @binary, {
3464             '0' => '000',
3465             '1' => '001',
3466             '2' => '010',
3467             '3' => '011',
3468             '4' => '100',
3469             '5' => '101',
3470             '6' => '110',
3471             '7' => '111',
3472 5         45 }->{$octal};
3473             }
3474 50         197 my $binary = join '', @binary;
3475              
3476             my $octchr = {
3477             # 1234567
3478             1 => pack('B*', "0000000$binary"),
3479             2 => pack('B*', "000000$binary"),
3480             3 => pack('B*', "00000$binary"),
3481             4 => pack('B*', "0000$binary"),
3482             5 => pack('B*', "000$binary"),
3483             6 => pack('B*', "00$binary"),
3484             7 => pack('B*', "0$binary"),
3485             0 => pack('B*', "$binary"),
3486              
3487 5         19 }->{CORE::length($binary) % 8};
3488              
3489 5         81 return $octchr;
3490             }
3491              
3492             #
3493             # UTF-8 hexadecimal escape sequence
3494             #
3495             sub hexchr {
3496 5     5 0 20 my($hexdigit) = @_;
3497              
3498             my $hexchr = {
3499             1 => pack('H*', "0$hexdigit"),
3500             0 => pack('H*', "$hexdigit"),
3501              
3502 5         16 }->{CORE::length($_[0]) % 2};
3503              
3504 5         47 return $hexchr;
3505             }
3506              
3507             #
3508             # UTF-8 open character list for qr
3509             #
3510             sub charlist_qr {
3511              
3512 5     531 0 17 my $modifier = pop @_;
3513 531         959 my @char = @_;
3514              
3515 531         1288 my($singleoctet, $multipleoctet) = _charlist(@char, $modifier);
3516 531         1746 my @singleoctet = @$singleoctet;
3517 531         1103 my @multipleoctet = @$multipleoctet;
3518              
3519             # return character list
3520 531 100       821 if (scalar(@singleoctet) >= 1) {
3521              
3522             # with /i modifier
3523 531 100       1175 if ($modifier =~ m/i/oxms) {
3524 384         809 my %singleoctet_ignorecase = ();
3525 107         163 for (@singleoctet) {
3526 107   66     161 while (s/ \A \\x(..) - \\x(..) //oxms or s/ \A \\x((..)) //oxms) {
3527 272         851 for my $ord (hex($1) .. hex($2)) {
3528 80         277 my $char = CORE::chr($ord);
3529 1091         1384 my $uc = Eutf2::uc($char);
3530 1091         1425 my $fc = Eutf2::fc($char);
3531 1091 100       1508 if ($uc eq $fc) {
3532 1091         1556 $singleoctet_ignorecase{unpack 'C*', $char} = 1;
3533             }
3534             else {
3535 502 50       1171 if (CORE::length($fc) == 1) {
3536 589         731 $singleoctet_ignorecase{unpack 'C*', $uc} = 1;
3537 589         1121 $singleoctet_ignorecase{unpack 'C*', $fc} = 1;
3538             }
3539             else {
3540 589         1392 $singleoctet_ignorecase{unpack 'C*', $uc} = 1;
3541 0         0 push @multipleoctet, join '', map {sprintf('\x%02X',$_)} unpack 'C*', $fc;
  0         0  
3542             }
3543             }
3544             }
3545             }
3546 0 100       0 if ($_ ne '') {
3547 272         457 $singleoctet_ignorecase{unpack 'C*', $_} = 1;
3548             }
3549             }
3550 192         454 my $i = 0;
3551 107         140 my @singleoctet_ignorecase = ();
3552 107         157 for my $ord (0 .. 255) {
3553 107 100       178 if (exists $singleoctet_ignorecase{$ord}) {
3554 27392         30484 push @{$singleoctet_ignorecase[$i]}, $ord;
  1622         1436  
3555             }
3556             else {
3557 1622         2353 $i++;
3558             }
3559             }
3560 25770         25208 @singleoctet = ();
3561 107         188 for my $range (@singleoctet_ignorecase) {
3562 107 100       237 if (ref $range) {
3563 11367 50       16844 if (scalar(@{$range}) == 1) {
  214 50       213  
3564 214         334 push @singleoctet, sprintf('\x%02X', @{$range}[0]);
  0         0  
3565             }
3566 0         0 elsif (scalar(@{$range}) == 2) {
3567 214         275 push @singleoctet, sprintf('\x%02X\x%02X', @{$range}[0], @{$range}[-1]);
  0         0  
  0         0  
3568             }
3569             else {
3570 0         0 push @singleoctet, sprintf('\x%02X-\x%02X', @{$range}[0], @{$range}[-1]);
  214         257  
  214         236  
3571             }
3572             }
3573             }
3574             }
3575              
3576 214         915 my $not_anchor = '';
3577 384         592 $not_anchor = '(?!(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF]))';
3578              
3579 384         488 push @multipleoctet, join('', $not_anchor, '[', @singleoctet, ']' );
3580             }
3581 384 100       1024 if (scalar(@multipleoctet) >= 2) {
3582 531         1116 return '(?:' . join('|', @multipleoctet) . ')';
3583             }
3584             else {
3585 102         650 return $multipleoctet[0];
3586             }
3587             }
3588              
3589             #
3590             # UTF-8 open character list for not qr
3591             #
3592             sub charlist_not_qr {
3593              
3594 429     239 0 1854 my $modifier = pop @_;
3595 239         400 my @char = @_;
3596              
3597 239         537 my($singleoctet, $multipleoctet) = _charlist(@char, $modifier);
3598 239         518 my @singleoctet = @$singleoctet;
3599 239         490 my @multipleoctet = @$multipleoctet;
3600              
3601             # with /i modifier
3602 239 100       354 if ($modifier =~ m/i/oxms) {
3603 239         509 my %singleoctet_ignorecase = ();
3604 128         163 for (@singleoctet) {
3605 128   66     183 while (s/ \A \\x(..) - \\x(..) //oxms or s/ \A \\x((..)) //oxms) {
3606 272         824 for my $ord (hex($1) .. hex($2)) {
3607 80         254 my $char = CORE::chr($ord);
3608 1091         1403 my $uc = Eutf2::uc($char);
3609 1091         1445 my $fc = Eutf2::fc($char);
3610 1091 100       1526 if ($uc eq $fc) {
3611 1091         1510 $singleoctet_ignorecase{unpack 'C*', $char} = 1;
3612             }
3613             else {
3614 502 50       1097 if (CORE::length($fc) == 1) {
3615 589         704 $singleoctet_ignorecase{unpack 'C*', $uc} = 1;
3616 589         1080 $singleoctet_ignorecase{unpack 'C*', $fc} = 1;
3617             }
3618             else {
3619 589         1339 $singleoctet_ignorecase{unpack 'C*', $uc} = 1;
3620 0         0 push @multipleoctet, join '', map {sprintf('\x%02X',$_)} unpack 'C*', $fc;
  0         0  
3621             }
3622             }
3623             }
3624             }
3625 0 100       0 if ($_ ne '') {
3626 272         423 $singleoctet_ignorecase{unpack 'C*', $_} = 1;
3627             }
3628             }
3629 192         410 my $i = 0;
3630 128         156 my @singleoctet_ignorecase = ();
3631 128         160 for my $ord (0 .. 255) {
3632 128 100       178 if (exists $singleoctet_ignorecase{$ord}) {
3633 32768         36643 push @{$singleoctet_ignorecase[$i]}, $ord;
  1622         1409  
3634             }
3635             else {
3636 1622         2429 $i++;
3637             }
3638             }
3639 31146         30824 @singleoctet = ();
3640 128         167 for my $range (@singleoctet_ignorecase) {
3641 128 100       263 if (ref $range) {
3642 11367 50       16757 if (scalar(@{$range}) == 1) {
  214 50       221  
3643 214         307 push @singleoctet, sprintf('\x%02X', @{$range}[0]);
  0         0  
3644             }
3645 0         0 elsif (scalar(@{$range}) == 2) {
3646 214         267 push @singleoctet, sprintf('\x%02X\x%02X', @{$range}[0], @{$range}[-1]);
  0         0  
  0         0  
3647             }
3648             else {
3649 0         0 push @singleoctet, sprintf('\x%02X-\x%02X', @{$range}[0], @{$range}[-1]);
  214         225  
  214         247  
3650             }
3651             }
3652             }
3653             }
3654              
3655             # return character list
3656 214 100       989 if (scalar(@multipleoctet) >= 1) {
3657 239 100       473 if (scalar(@singleoctet) >= 1) {
3658              
3659             # any character other than multiple-octet and single octet character class
3660 114         182 return '(?!' . join('|', @multipleoctet) . ')(?:[^\x80-\xFF' . join('', @singleoctet) . ']|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])';
3661             }
3662             else {
3663              
3664             # any character other than multiple-octet character class
3665 70         485 return '(?!' . join('|', @multipleoctet) . ")(?:$your_char)";
3666             }
3667             }
3668             else {
3669 44 50       274 if (scalar(@singleoctet) >= 1) {
3670              
3671             # any character other than single octet character class
3672 125         207 return '(?:[^\x80-\xFF' . join('', @singleoctet) . ']|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])';
3673             }
3674             else {
3675              
3676             # any character
3677 125         724 return "(?:$your_char)";
3678             }
3679             }
3680             }
3681              
3682             #
3683             # open file in read mode
3684             #
3685             sub _open_r {
3686 0     612   0 my(undef,$file) = @_;
3687 306     306   5438 use Fcntl qw(O_RDONLY);
  306         5575  
  306         57835  
3688 612         1867 return CORE::sysopen($_[0], $file, &O_RDONLY);
3689             }
3690              
3691             #
3692             # open file in append mode
3693             #
3694             sub _open_a {
3695 612     306   25947 my(undef,$file) = @_;
3696 306     306   4204 use Fcntl qw(O_WRONLY O_APPEND O_CREAT);
  306         753  
  306         1449669  
3697 306         992 return CORE::sysopen($_[0], $file, &O_WRONLY|&O_APPEND|&O_CREAT);
3698             }
3699              
3700             #
3701             # safe system
3702             #
3703             sub _systemx {
3704              
3705             # P.707 29.2.33. exec
3706             # in Chapter 29: Functions
3707             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
3708             #
3709             # Be aware that in older releases of Perl, exec (and system) did not flush
3710             # your output buffer, so you needed to enable command buffering by setting $|
3711             # on one or more filehandles to avoid lost output in the case of exec, or
3712             # misordererd output in the case of system. This situation was largely remedied
3713             # in the 5.6 release of Perl. (So, 5.005 release not yet.)
3714              
3715             # P.855 exec
3716             # in Chapter 27: Functions
3717             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
3718             #
3719             # In very old release of Perl (before v5.6), exec (and system) did not flush
3720             # your output buffer, so you needed to enable command buffering by setting $|
3721             # on one or more filehandles to avoid lost output with exec or misordered
3722             # output with system.
3723              
3724 306     306   51251 $| = 1;
3725              
3726             # P.565 23.1.2. Cleaning Up Your Environment
3727             # in Chapter 23: Security
3728             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
3729              
3730             # P.656 Cleaning Up Your Environment
3731             # in Chapter 20: Security
3732             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
3733              
3734             # local $ENV{'PATH'} = '.';
3735 306         1045 local @ENV{qw(IFS CDPATH ENV BASH_ENV)}; # Make %ENV safer
3736              
3737             # P.707 29.2.33. exec
3738             # in Chapter 29: Functions
3739             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
3740             #
3741             # As we mentioned earlier, exec treats a discrete list of arguments as an
3742             # indication that it should bypass shell processing. However, there is one
3743             # place where you might still get tripped up. The exec call (and system, too)
3744             # will not distinguish between a single scalar argument and an array containing
3745             # only one element.
3746             #
3747             # @args = ("echo surprise"); # just one element in list
3748             # exec @args # still subject to shell escapes
3749             # or die "exec: $!"; # because @args == 1
3750             #
3751             # To avoid this, you can use the PATHNAME syntax, explicitly duplicating the
3752             # first argument as the pathname, which forces the rest of the arguments to be
3753             # interpreted as a list, even if there is only one of them:
3754             #
3755             # exec { $args[0] } @args # safe even with one-argument list
3756             # or die "can't exec @args: $!";
3757              
3758             # P.855 exec
3759             # in Chapter 27: Functions
3760             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
3761             #
3762             # As we mentioned earlier, exec treats a discrete list of arguments as a
3763             # directive to bypass shell processing. However, there is one place where
3764             # you might still get tripped up. The exec call (and system, too) cannot
3765             # distinguish between a single scalar argument and an array containing
3766             # only one element.
3767             #
3768             # @args = ("echo surprise"); # just one element in list
3769             # exec @args # still subject to shell escapes
3770             # || die "exec: $!"; # because @args == 1
3771             #
3772             # To avoid this, use the PATHNAME syntax, explicitly duplicating the first
3773             # argument as the pathname, which forces the rest of the arguments to be
3774             # interpreted as a list, even if there is only one of them:
3775             #
3776             # exec { $args[0] } @args # safe even with one-argument list
3777             # || die "can't exec @args: $!";
3778              
3779 306         2654 return CORE::system { $_[0] } @_; # safe even with one-argument list
  306         620  
3780             }
3781              
3782             #
3783             # UTF-8 order to character (with parameter)
3784             #
3785             sub Eutf2::chr(;$) {
3786              
3787 306 0   0 0 40100239 my $c = @_ ? $_[0] : $_;
3788              
3789 0 0       0 if ($c == 0x00) {
3790 0         0 return "\x00";
3791             }
3792             else {
3793 0         0 my @chr = ();
3794 0         0 while ($c > 0) {
3795 0         0 unshift @chr, ($c % 0x100);
3796 0         0 $c = int($c / 0x100);
3797             }
3798 0         0 return pack 'C*', @chr;
3799             }
3800             }
3801              
3802             #
3803             # UTF-8 order to character (without parameter)
3804             #
3805             sub Eutf2::chr_() {
3806              
3807 0     0 0 0 my $c = $_;
3808              
3809 0 0       0 if ($c == 0x00) {
3810 0         0 return "\x00";
3811             }
3812             else {
3813 0         0 my @chr = ();
3814 0         0 while ($c > 0) {
3815 0         0 unshift @chr, ($c % 0x100);
3816 0         0 $c = int($c / 0x100);
3817             }
3818 0         0 return pack 'C*', @chr;
3819             }
3820             }
3821              
3822             #
3823             # UTF-8 path globbing (with parameter)
3824             #
3825             sub Eutf2::glob($) {
3826              
3827 0 0   0 0 0 if (wantarray) {
3828 0         0 my @glob = _DOS_like_glob(@_);
3829 0         0 for my $glob (@glob) {
3830 0         0 $glob =~ s{ \A (?:\./)+ }{}oxms;
3831             }
3832 0         0 return @glob;
3833             }
3834             else {
3835 0         0 my $glob = _DOS_like_glob(@_);
3836 0         0 $glob =~ s{ \A (?:\./)+ }{}oxms;
3837 0         0 return $glob;
3838             }
3839             }
3840              
3841             #
3842             # UTF-8 path globbing (without parameter)
3843             #
3844             sub Eutf2::glob_() {
3845              
3846 0 0   0 0 0 if (wantarray) {
3847 0         0 my @glob = _DOS_like_glob();
3848 0         0 for my $glob (@glob) {
3849 0         0 $glob =~ s{ \A (?:\./)+ }{}oxms;
3850             }
3851 0         0 return @glob;
3852             }
3853             else {
3854 0         0 my $glob = _DOS_like_glob();
3855 0         0 $glob =~ s{ \A (?:\./)+ }{}oxms;
3856 0         0 return $glob;
3857             }
3858             }
3859              
3860             #
3861             # UTF-8 path globbing via File::DosGlob 1.10
3862             #
3863             # Often I confuse "_dosglob" and "_doglob".
3864             # So, I renamed "_dosglob" to "_DOS_like_glob".
3865             #
3866             my %iter;
3867             my %entries;
3868             sub _DOS_like_glob {
3869              
3870             # context (keyed by second cxix argument provided by core)
3871 0     0   0 my($expr,$cxix) = @_;
3872              
3873             # glob without args defaults to $_
3874 0 0       0 $expr = $_ if not defined $expr;
3875              
3876             # represents the current user's home directory
3877             #
3878             # 7.3. Expanding Tildes in Filenames
3879             # in Chapter 7. File Access
3880             # of ISBN 0-596-00313-7 Perl Cookbook, 2nd Edition.
3881             #
3882             # and File::HomeDir, File::HomeDir::Windows module
3883              
3884             # DOS-like system
3885 0 0       0 if ($^O =~ /\A (?: MSWin32 | NetWare | symbian | dos ) \z/oxms) {
3886 0         0 $expr =~ s{ \A ~ (?= [^/\\] ) }
  0         0  
3887             { my_home_MSWin32() }oxmse;
3888             }
3889              
3890             # UNIX-like system
3891 0 0 0     0 else {
  0         0  
3892             $expr =~ s{ \A ~ ( (?:[^\x80-\xFF/]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])* ) }
3893             { $1 ? (CORE::eval(q{(getpwnam($1))[7]})||my_home()) : my_home() }oxmse;
3894             }
3895 0 0       0  
3896 0 0       0 # assume global context if not provided one
3897             $cxix = '_G_' if not defined $cxix;
3898             $iter{$cxix} = 0 if not exists $iter{$cxix};
3899 0 0       0  
3900 0         0 # if we're just beginning, do it all first
3901             if ($iter{$cxix} == 0) {
3902             $entries{$cxix} = [ _do_glob(1, _parse_line($expr)) ];
3903             }
3904 0 0       0  
3905 0         0 # chuck it all out, quick or slow
3906 0         0 if (wantarray) {
  0         0  
3907             delete $iter{$cxix};
3908             return @{delete $entries{$cxix}};
3909 0 0       0 }
  0         0  
3910 0         0 else {
  0         0  
3911             if ($iter{$cxix} = scalar @{$entries{$cxix}}) {
3912             return shift @{$entries{$cxix}};
3913             }
3914 0         0 else {
3915 0         0 # return undef for EOL
3916 0         0 delete $iter{$cxix};
3917             delete $entries{$cxix};
3918             return undef;
3919             }
3920             }
3921             }
3922              
3923             #
3924             # UTF-8 path globbing subroutine
3925             #
3926 0     0   0 sub _do_glob {
3927 0         0  
3928 0         0 my($cond,@expr) = @_;
3929             my @glob = ();
3930             my $fix_drive_relative_paths = 0;
3931 0         0  
3932 0 0       0 OUTER:
3933 0 0       0 for my $expr (@expr) {
3934             next OUTER if not defined $expr;
3935 0         0 next OUTER if $expr eq '';
3936 0         0  
3937 0         0 my @matched = ();
3938 0         0 my @globdir = ();
3939 0         0 my $head = '.';
3940             my $pathsep = '/';
3941             my $tail;
3942 0 0       0  
3943 0         0 # if argument is within quotes strip em and do no globbing
3944 0 0       0 if ($expr =~ /\A " ((?:$q_char)*?) " \z/oxms) {
3945 0 0       0 $expr = $1;
3946 0         0 if ($cond eq 'd') {
3947             if (-d $expr) {
3948             push @glob, $expr;
3949             }
3950 0 0       0 }
3951 0         0 else {
3952             if (-e $expr) {
3953             push @glob, $expr;
3954 0         0 }
3955             }
3956             next OUTER;
3957             }
3958              
3959 0 0       0 # wildcards with a drive prefix such as h:*.pm must be changed
3960 0 0       0 # to h:./*.pm to expand correctly
3961 0         0 if ($^O =~ /\A (?: MSWin32 | NetWare | symbian | dos ) \z/oxms) {
3962             if ($expr =~ s# \A ((?:[A-Za-z]:)?) ([^\x80-\xFF/\\]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF]) #$1./$2#oxms) {
3963             $fix_drive_relative_paths = 1;
3964             }
3965 0 0       0 }
3966 0 0       0  
3967 0         0 if (($head, $tail) = _parse_path($expr,$pathsep)) {
3968 0         0 if ($tail eq '') {
3969             push @glob, $expr;
3970 0 0       0 next OUTER;
3971 0 0       0 }
3972 0         0 if ($head =~ / \A (?:$q_char)*? [*?] /oxms) {
  0         0  
3973 0         0 if (@globdir = _do_glob('d', $head)) {
3974             push @glob, _do_glob($cond, map {"$_$pathsep$tail"} @globdir);
3975             next OUTER;
3976 0 0 0     0 }
3977 0         0 }
3978             if ($head eq '' or $head =~ /\A [A-Za-z]: \z/oxms) {
3979 0         0 $head .= $pathsep;
3980             }
3981             $expr = $tail;
3982             }
3983 0 0       0  
3984 0 0       0 # If file component has no wildcards, we can avoid opendir
3985 0         0 if ($expr !~ / \A (?:$q_char)*? [*?] /oxms) {
3986             if ($head eq '.') {
3987 0 0 0     0 $head = '';
3988 0         0 }
3989             if ($head ne '' and ($head =~ / \G ($q_char) /oxmsg)[-1] ne $pathsep) {
3990 0         0 $head .= $pathsep;
3991 0 0       0 }
3992 0 0       0 $head .= $expr;
3993 0         0 if ($cond eq 'd') {
3994             if (-d $head) {
3995             push @glob, $head;
3996             }
3997 0 0       0 }
3998 0         0 else {
3999             if (-e $head) {
4000             push @glob, $head;
4001 0         0 }
4002             }
4003 0 0       0 next OUTER;
4004 0         0 }
4005 0         0 opendir(*DIR, $head) or next OUTER;
4006             my @leaf = readdir DIR;
4007 0 0       0 closedir DIR;
4008 0         0  
4009             if ($head eq '.') {
4010 0 0 0     0 $head = '';
4011 0         0 }
4012             if ($head ne '' and ($head =~ / \G ($q_char) /oxmsg)[-1] ne $pathsep) {
4013             $head .= $pathsep;
4014 0         0 }
4015 0         0  
4016 0         0 my $pattern = '';
4017             while ($expr =~ / \G ($q_char) /oxgc) {
4018             my $char = $1;
4019              
4020             # 6.9. Matching Shell Globs as Regular Expressions
4021             # in Chapter 6. Pattern Matching
4022             # of ISBN 0-596-00313-7 Perl Cookbook, 2nd Edition.
4023 0 0       0 # (and so on)
    0          
    0          
4024 0         0  
4025             if ($char eq '*') {
4026             $pattern .= "(?:$your_char)*",
4027 0         0 }
4028             elsif ($char eq '?') {
4029             $pattern .= "(?:$your_char)?", # DOS style
4030             # $pattern .= "(?:$your_char)", # UNIX style
4031 0         0 }
4032             elsif ((my $fc = Eutf2::fc($char)) ne $char) {
4033             $pattern .= $fc;
4034 0         0 }
4035             else {
4036             $pattern .= quotemeta $char;
4037 0     0   0 }
  0         0  
4038             }
4039             my $matchsub = sub { Eutf2::fc($_[0]) =~ /\A $pattern \z/xms };
4040              
4041             # if ($@) {
4042             # print STDERR "$0: $@\n";
4043             # next OUTER;
4044             # }
4045 0         0  
4046 0 0 0     0 INNER:
4047 0         0 for my $leaf (@leaf) {
4048             if ($leaf eq '.' or $leaf eq '..') {
4049 0 0 0     0 next INNER;
4050 0         0 }
4051             if ($cond eq 'd' and not -d "$head$leaf") {
4052             next INNER;
4053 0 0       0 }
4054 0         0  
4055 0         0 if (&$matchsub($leaf)) {
4056             push @matched, "$head$leaf";
4057             next INNER;
4058             }
4059              
4060             # [DOS compatibility special case]
4061 0 0 0     0 # Failed, add a trailing dot and try again, but only...
      0        
4062              
4063             if (Eutf2::index($leaf,'.') == -1 and # if name does not have a dot in it *and*
4064             CORE::length($leaf) <= 8 and # name is shorter than or equal to 8 chars *and*
4065 0 0       0 Eutf2::index($pattern,'\\.') != -1 # pattern has a dot.
4066 0         0 ) {
4067 0         0 if (&$matchsub("$leaf.")) {
4068             push @matched, "$head$leaf";
4069             next INNER;
4070             }
4071 0 0       0 }
4072 0         0 }
4073             if (@matched) {
4074             push @glob, @matched;
4075 0 0       0 }
4076 0         0 }
4077 0         0 if ($fix_drive_relative_paths) {
4078             for my $glob (@glob) {
4079             $glob =~ s# \A ([A-Za-z]:) \./ #$1#oxms;
4080 0         0 }
4081             }
4082             return @glob;
4083             }
4084              
4085             #
4086             # UTF-8 parse line
4087             #
4088 0     0   0 sub _parse_line {
4089              
4090 0         0 my($line) = @_;
4091 0         0  
4092 0         0 $line .= ' ';
4093             my @piece = ();
4094             while ($line =~ /
4095             " ( (?>(?: [^\x80-\xFF"] |(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] )* ) ) " (?>\s+) |
4096             ( (?>(?: [^\x80-\xFF"\s]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] )* ) ) (?>\s+)
4097 0 0       0 /oxmsg
4098             ) {
4099 0         0 push @piece, defined($1) ? $1 : $2;
4100             }
4101             return @piece;
4102             }
4103              
4104             #
4105             # UTF-8 parse path
4106             #
4107 0     0   0 sub _parse_path {
4108              
4109 0         0 my($path,$pathsep) = @_;
4110 0         0  
4111 0         0 $path .= '/';
4112             my @subpath = ();
4113             while ($path =~ /
4114             ((?: [^\x80-\xFF\/\\]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] )+?) [\/\\]
4115 0         0 /oxmsg
4116             ) {
4117             push @subpath, $1;
4118 0         0 }
4119 0         0  
4120 0         0 my $tail = pop @subpath;
4121             my $head = join $pathsep, @subpath;
4122             return $head, $tail;
4123             }
4124              
4125             #
4126             # via File::HomeDir::Windows 1.00
4127             #
4128             sub my_home_MSWin32 {
4129              
4130             # A lot of unix people and unix-derived tools rely on
4131 0 0 0 0 0 0 # the ability to overload HOME. We will support it too
    0 0        
    0 0        
      0        
      0        
4132 0         0 # so that they can replace raw HOME calls with File::HomeDir.
4133             if (exists $ENV{'HOME'} and $ENV{'HOME'}) {
4134             return $ENV{'HOME'};
4135             }
4136              
4137 0         0 # Do we have a user profile?
4138             elsif (exists $ENV{'USERPROFILE'} and $ENV{'USERPROFILE'}) {
4139             return $ENV{'USERPROFILE'};
4140             }
4141              
4142 0         0 # Some Windows use something like $ENV{'HOME'}
4143             elsif (exists $ENV{'HOMEDRIVE'} and exists $ENV{'HOMEPATH'} and $ENV{'HOMEDRIVE'} and $ENV{'HOMEPATH'}) {
4144             return join '', $ENV{'HOMEDRIVE'}, $ENV{'HOMEPATH'};
4145 0         0 }
4146              
4147             return undef;
4148             }
4149              
4150             #
4151             # via File::HomeDir::Unix 1.00
4152 0     0 0 0 #
4153             sub my_home {
4154 0 0 0     0 my $home;
    0 0        
4155 0         0  
4156             if (exists $ENV{'HOME'} and defined $ENV{'HOME'}) {
4157             $home = $ENV{'HOME'};
4158             }
4159              
4160             # This is from the original code, but I'm guessing
4161 0         0 # it means "login directory" and exists on some Unixes.
4162             elsif (exists $ENV{'LOGDIR'} and $ENV{'LOGDIR'}) {
4163             $home = $ENV{'LOGDIR'};
4164             }
4165              
4166             ### More-desperate methods
4167              
4168 0         0 # Light desperation on any (Unixish) platform
4169             else {
4170             $home = CORE::eval q{ (getpwuid($<))[7] };
4171             }
4172              
4173 0 0 0     0 # On Unix in general, a non-existant home means "no home"
4174 0         0 # For example, "nobody"-like users might use /nonexistant
4175             if (defined $home and ! -d($home)) {
4176 0         0 $home = undef;
4177             }
4178             return $home;
4179             }
4180              
4181             #
4182             # ${^PREMATCH}, $PREMATCH, $` the string preceding what was matched
4183 0     0 0 0 #
4184             sub Eutf2::PREMATCH {
4185             return $`;
4186             }
4187              
4188             #
4189             # ${^MATCH}, $MATCH, $& the string that matched
4190 0     0 0 0 #
4191             sub Eutf2::MATCH {
4192             return $&;
4193             }
4194              
4195             #
4196             # ${^POSTMATCH}, $POSTMATCH, $' the string following what was matched
4197 0     0 0 0 #
4198             sub Eutf2::POSTMATCH {
4199             return $';
4200             }
4201              
4202             #
4203             # UTF-8 character to order (with parameter)
4204             #
4205 0 0   0 1 0 sub UTF2::ord(;$) {
4206              
4207 0 0       0 local $_ = shift if @_;
4208 0         0  
4209 0         0 if (/\A ($q_char) /oxms) {
4210 0         0 my @ord = unpack 'C*', $1;
4211 0         0 my $ord = 0;
4212             while (my $o = shift @ord) {
4213 0         0 $ord = $ord * 0x100 + $o;
4214             }
4215             return $ord;
4216 0         0 }
4217             else {
4218             return CORE::ord $_;
4219             }
4220             }
4221              
4222             #
4223             # UTF-8 character to order (without parameter)
4224             #
4225 0 0   0 0 0 sub UTF2::ord_() {
4226 0         0  
4227 0         0 if (/\A ($q_char) /oxms) {
4228 0         0 my @ord = unpack 'C*', $1;
4229 0         0 my $ord = 0;
4230             while (my $o = shift @ord) {
4231 0         0 $ord = $ord * 0x100 + $o;
4232             }
4233             return $ord;
4234 0         0 }
4235             else {
4236             return CORE::ord $_;
4237             }
4238             }
4239              
4240             #
4241             # UTF-8 reverse
4242             #
4243 0 0   0 0 0 sub UTF2::reverse(@) {
4244 0         0  
4245             if (wantarray) {
4246             return CORE::reverse @_;
4247             }
4248             else {
4249              
4250             # One of us once cornered Larry in an elevator and asked him what
4251             # problem he was solving with this, but he looked as far off into
4252             # the distance as he could in an elevator and said, "It seemed like
4253 0         0 # a good idea at the time."
4254              
4255             return join '', CORE::reverse(join('',@_) =~ /\G ($q_char) /oxmsg);
4256             }
4257             }
4258              
4259             #
4260             # UTF-8 getc (with parameter, without parameter)
4261             #
4262 0     0 0 0 sub UTF2::getc(;*@) {
4263 0 0       0  
4264 0 0 0     0 my($package) = caller;
4265             my $fh = @_ ? qualify_to_ref(shift,$package) : \*STDIN;
4266 0         0 croak 'Too many arguments for UTF2::getc' if @_ and not wantarray;
  0         0  
4267 0         0  
4268 0         0 my @length = sort { $a <=> $b } keys %range_tr;
4269 0         0 my $getc = '';
4270 0 0       0 for my $length ($length[0] .. $length[-1]) {
4271 0 0       0 $getc .= CORE::getc($fh);
4272 0 0       0 if (exists $range_tr{CORE::length($getc)}) {
4273             if ($getc =~ /\A ${Eutf2::dot_s} \z/oxms) {
4274             return wantarray ? ($getc,@_) : $getc;
4275             }
4276 0 0       0 }
4277             }
4278             return wantarray ? ($getc,@_) : $getc;
4279             }
4280              
4281             #
4282             # UTF-8 length by character
4283             #
4284 0 0   0 1 0 sub UTF2::length(;$) {
4285              
4286 0         0 local $_ = shift if @_;
4287 0         0  
4288             local @_ = /\G ($q_char) /oxmsg;
4289             return scalar @_;
4290             }
4291              
4292             #
4293             # UTF-8 substr by character
4294             #
4295             BEGIN {
4296              
4297             # P.232 The lvalue Attribute
4298             # in Chapter 6: Subroutines
4299             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
4300              
4301             # P.336 The lvalue Attribute
4302             # in Chapter 7: Subroutines
4303             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
4304              
4305             # P.144 8.4 Lvalue subroutines
4306             # in Chapter 8: perlsub: Perl subroutines
4307 306 50 0 306 1 277997 # of ISBN-13: 978-1-906966-02-7 The Perl Language Reference Manual (for Perl version 5.12.1)
  0 0   0   0  
  0 0       0  
  0 0       0  
  0 0       0  
  0 0       0  
  0 0       0  
  0 0       0  
  0 0       0  
  0 0       0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
  0         0  
4308              
4309             CORE::eval sprintf(<<'END', ($] >= 5.014000) ? ':lvalue' : '');
4310             # vv----------------------*******
4311             sub UTF2::substr($$;$$) %s {
4312              
4313             my @char = $_[0] =~ /\G (?>$q_char) /oxmsg;
4314              
4315             # If the substring is beyond either end of the string, substr() returns the undefined
4316             # value and produces a warning. When used as an lvalue, specifying a substring that
4317             # is entirely outside the string raises an exception.
4318             # http://perldoc.perl.org/functions/substr.html
4319              
4320             # A return with no argument returns the scalar value undef in scalar context,
4321             # an empty list () in list context, and (naturally) nothing at all in void
4322             # context.
4323              
4324             my $offset = $_[1];
4325             if (($offset > scalar(@char)) or ($offset < (-1 * scalar(@char)))) {
4326             return;
4327             }
4328              
4329             # substr($string,$offset,$length,$replacement)
4330             if (@_ == 4) {
4331             my(undef,undef,$length,$replacement) = @_;
4332             my $substr = join '', splice(@char, $offset, $length, $replacement);
4333             $_[0] = join '', @char;
4334              
4335             # return $substr; this doesn't work, don't say "return"
4336             $substr;
4337             }
4338              
4339             # substr($string,$offset,$length)
4340             elsif (@_ == 3) {
4341             my(undef,undef,$length) = @_;
4342             my $octet_offset = 0;
4343             my $octet_length = 0;
4344             if ($offset == 0) {
4345             $octet_offset = 0;
4346             }
4347             elsif ($offset > 0) {
4348             $octet_offset = CORE::length(join '', @char[0..$offset-1]);
4349             }
4350             else {
4351             $octet_offset = -1 * CORE::length(join '', @char[$#char+$offset+1..$#char]);
4352             }
4353             if ($length == 0) {
4354             $octet_length = 0;
4355             }
4356             elsif ($length > 0) {
4357             $octet_length = CORE::length(join '', @char[$offset..$offset+$length-1]);
4358             }
4359             else {
4360             $octet_length = -1 * CORE::length(join '', @char[$#char+$length+1..$#char]);
4361             }
4362             CORE::substr($_[0], $octet_offset, $octet_length);
4363             }
4364              
4365             # substr($string,$offset)
4366             else {
4367             my $octet_offset = 0;
4368             if ($offset == 0) {
4369             $octet_offset = 0;
4370             }
4371             elsif ($offset > 0) {
4372             $octet_offset = CORE::length(join '', @char[0..$offset-1]);
4373             }
4374             else {
4375             $octet_offset = -1 * CORE::length(join '', @char[$#char+$offset+1..$#char]);
4376             }
4377             CORE::substr($_[0], $octet_offset);
4378             }
4379             }
4380             END
4381             }
4382              
4383             #
4384             # UTF-8 index by character
4385             #
4386 0     0 1 0 sub UTF2::index($$;$) {
4387 0 0       0  
4388 0         0 my $index;
4389             if (@_ == 3) {
4390             $index = Eutf2::index($_[0], $_[1], CORE::length(UTF2::substr($_[0], 0, $_[2])));
4391 0         0 }
4392             else {
4393             $index = Eutf2::index($_[0], $_[1]);
4394 0 0       0 }
4395 0         0  
4396             if ($index == -1) {
4397             return -1;
4398 0         0 }
4399             else {
4400             return UTF2::length(CORE::substr $_[0], 0, $index);
4401             }
4402             }
4403              
4404             #
4405             # UTF-8 rindex by character
4406             #
4407 0     0 1 0 sub UTF2::rindex($$;$) {
4408 0 0       0  
4409 0         0 my $rindex;
4410             if (@_ == 3) {
4411             $rindex = Eutf2::rindex($_[0], $_[1], CORE::length(UTF2::substr($_[0], 0, $_[2])));
4412 0         0 }
4413             else {
4414             $rindex = Eutf2::rindex($_[0], $_[1]);
4415 0 0       0 }
4416 0         0  
4417             if ($rindex == -1) {
4418             return -1;
4419 0         0 }
4420             else {
4421             return UTF2::length(CORE::substr $_[0], 0, $rindex);
4422             }
4423             }
4424              
4425 306     306   2636 # when 'm//', '/' means regexp match 'm//' and '?' means regexp match '??'
  306         2363  
  306         49347  
4426             # when 'div', '/' means division operator and '?' means conditional operator (condition ? then : else)
4427             use vars qw($slash); $slash = 'm//';
4428              
4429             # ord() to ord() or UTF2::ord()
4430             my $function_ord = 'ord';
4431              
4432             # ord to ord or UTF2::ord_
4433             my $function_ord_ = 'ord';
4434              
4435             # reverse to reverse or UTF2::reverse
4436             my $function_reverse = 'reverse';
4437              
4438             # getc to getc or UTF2::getc
4439             my $function_getc = 'getc';
4440              
4441             # P.1023 Appendix W.9 Multibyte Anchoring
4442             # of ISBN 1-56592-224-7 CJKV Information Processing
4443              
4444 306     306   5975 my $anchor = '';
  306     0   2325  
  306         18695440  
4445              
4446             use vars qw($nest);
4447              
4448             # regexp of nested parens in qqXX
4449              
4450             # P.340 Matching Nested Constructs with Embedded Code
4451             # in Chapter 7: Perl
4452             # of ISBN 0-596-00289-0 Mastering Regular Expressions, Second edition
4453              
4454             my $qq_paren = qr{(?{local $nest=0}) (?>(?:
4455             [^\x80-\xFF\\()] |
4456             \( (?{$nest++}) |
4457             \) (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4458             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4459             \\ [^\x80-\xFFc] |
4460             \\c[\x40-\x5F] |
4461             \\ (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4462             [\x00-\xFF]
4463             }xms;
4464              
4465             my $qq_brace = qr{(?{local $nest=0}) (?>(?:
4466             [^\x80-\xFF\\{}] |
4467             \{ (?{$nest++}) |
4468             \} (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4469             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4470             \\ [^\x80-\xFFc] |
4471             \\c[\x40-\x5F] |
4472             \\ (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4473             [\x00-\xFF]
4474             }xms;
4475              
4476             my $qq_bracket = qr{(?{local $nest=0}) (?>(?:
4477             [^\x80-\xFF\\\[\]] |
4478             \[ (?{$nest++}) |
4479             \] (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4480             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4481             \\ [^\x80-\xFFc] |
4482             \\c[\x40-\x5F] |
4483             \\ (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4484             [\x00-\xFF]
4485             }xms;
4486              
4487             my $qq_angle = qr{(?{local $nest=0}) (?>(?:
4488             [^\x80-\xFF\\<>] |
4489             \< (?{$nest++}) |
4490             \> (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4491             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4492             \\ [^\x80-\xFFc] |
4493             \\c[\x40-\x5F] |
4494             \\ (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4495             [\x00-\xFF]
4496             }xms;
4497              
4498             my $qq_scalar = qr{(?: \{ (?:$qq_brace)*? \} |
4499             (?: ::)? (?:
4500             (?> [a-zA-Z_][a-zA-Z_0-9]* (?: ::[a-zA-Z_][a-zA-Z_0-9]*)* )
4501             (?>(?: \[ (?: \$\[ | \$\] | $qq_char )*? \] | \{ (?:$qq_brace)*? \} )*)
4502             (?>(?: (?: -> )? (?: [\$\@\%\&\*]\* | \$\#\* | [\@\%]? \[ (?: \$\[ | \$\] | $qq_char )*? \] | [\@\%\*]? \{ (?:$qq_brace)*? \} ) )*)
4503             ))
4504             }xms;
4505              
4506             my $qq_variable = qr{(?: \{ (?:$qq_brace)*? \} |
4507             (?: ::)? (?:
4508             (?>[0-9]+) |
4509             [^\x80-\xFFa-zA-Z_0-9\[\]] |
4510             ^[A-Z] |
4511             (?> [a-zA-Z_][a-zA-Z_0-9]* (?: ::[a-zA-Z_][a-zA-Z_0-9]*)* )
4512             (?>(?: \[ (?: \$\[ | \$\] | $qq_char )*? \] | \{ (?:$qq_brace)*? \} )*)
4513             (?>(?: (?: -> )? (?: [\$\@\%\&\*]\* | \$\#\* | [\@\%]? \[ (?: \$\[ | \$\] | $qq_char )*? \] | [\@\%\*]? \{ (?:$qq_brace)*? \} ) )*)
4514             ))
4515             }xms;
4516              
4517             my $qq_substr = qr{(?> Char::substr | UTF2::substr | CORE::substr | substr ) (?>\s*) \( $qq_paren \)
4518             }xms;
4519              
4520             # regexp of nested parens in qXX
4521             my $q_paren = qr{(?{local $nest=0}) (?>(?:
4522             [^\x80-\xFF()] |
4523             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4524             \( (?{$nest++}) |
4525             \) (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4526             [\x00-\xFF]
4527             }xms;
4528              
4529             my $q_brace = qr{(?{local $nest=0}) (?>(?:
4530             [^\x80-\xFF\{\}] |
4531             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4532             \{ (?{$nest++}) |
4533             \} (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4534             [\x00-\xFF]
4535             }xms;
4536              
4537             my $q_bracket = qr{(?{local $nest=0}) (?>(?:
4538             [^\x80-\xFF\[\]] |
4539             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4540             \[ (?{$nest++}) |
4541             \] (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4542             [\x00-\xFF]
4543             }xms;
4544              
4545             my $q_angle = qr{(?{local $nest=0}) (?>(?:
4546             [^\x80-\xFF<>] |
4547             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
4548             \< (?{$nest++}) |
4549             \> (?(?{$nest>0})(?{$nest--})|(?!)))*) (?(?{$nest!=0})(?!)) |
4550             [\x00-\xFF]
4551             }xms;
4552              
4553             my $matched = '';
4554             my $s_matched = '';
4555              
4556             my $tr_variable = ''; # variable of tr///
4557             my $sub_variable = ''; # variable of s///
4558             my $bind_operator = ''; # =~ or !~
4559              
4560             my @heredoc = (); # here document
4561             my @heredoc_delimiter = ();
4562             my $here_script = ''; # here script
4563              
4564             #
4565             # escape UTF-8 script
4566 0 50   306 0 0 #
4567             sub UTF2::escape(;$) {
4568             local($_) = $_[0] if @_;
4569              
4570             # P.359 The Study Function
4571             # in Chapter 7: Perl
4572 306         974 # of ISBN 0-596-00289-0 Mastering Regular Expressions, Second edition
4573              
4574             study $_; # Yes, I studied study yesterday.
4575              
4576             # while all script
4577              
4578             # 6.14. Matching from Where the Last Pattern Left Off
4579             # in Chapter 6. Pattern Matching
4580             # of ISBN 0-596-00313-7 Perl Cookbook, 2nd Edition.
4581             # (and so on)
4582              
4583             # one member of Tag-team
4584             #
4585             # P.128 Start of match (or end of previous match): \G
4586             # P.130 Advanced Use of \G with Perl
4587             # in Chapter 3: Overview of Regular Expression Features and Flavors
4588             # P.255 Use leading anchors
4589             # P.256 Expose ^ and \G at the front expressions
4590             # in Chapter 6: Crafting an Efficient Expression
4591             # P.315 "Tag-team" matching with /gc
4592             # in Chapter 7: Perl
4593 306         607 # of ISBN 0-596-00289-0 Mastering Regular Expressions, Second edition
4594 306         518  
4595 306         1121 my $e_script = '';
4596             while (not /\G \z/oxgc) { # member
4597             $e_script .= UTF2::escape_token();
4598 135221         195913 }
4599              
4600             return $e_script;
4601             }
4602              
4603             #
4604             # escape UTF-8 token of script
4605             #
4606             sub UTF2::escape_token {
4607              
4608 306     135221 0 4826 # \n output here document
4609              
4610             my $ignore_modules = join('|', qw(
4611             utf8
4612             bytes
4613             charnames
4614             I18N::Japanese
4615             I18N::Collate
4616             I18N::JExt
4617             File::DosGlob
4618             Wild
4619             Wildcard
4620             Japanese
4621             ));
4622              
4623             # another member of Tag-team
4624             #
4625             # P.315 "Tag-team" matching with /gc
4626             # in Chapter 7: Perl
4627 135221 100 100     150758 # of ISBN 0-596-00289-0 Mastering Regular Expressions, Second edition
    100 100        
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    50          
    100          
    50          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    100          
    50          
    100          
    100          
    100          
    100          
    50          
    100          
    100          
    100          
    50          
    100          
    100          
    100          
    50          
    50          
    50          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    50          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    50          
    50          
    50          
    100          
    50          
    50          
    100          
    50          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    100          
    100          
    100          
    50          
    50          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    100          
    50          
    100          
    50          
    50          
    50          
    100          
    50          
    50          
    100          
    100          
    100          
    50          
4628 135221         6407616  
4629 22128 100       25937 if (/\G ( \n ) /oxgc) { # another member (and so on)
4630 22128         36002 my $heredoc = '';
4631             if (scalar(@heredoc_delimiter) >= 1) {
4632 191         245 $slash = 'm//';
4633 191         357  
4634             $heredoc = join '', @heredoc;
4635             @heredoc = ();
4636 191         313  
4637 191         325 # skip here document
4638             for my $heredoc_delimiter (@heredoc_delimiter) {
4639 199         1181 /\G .*? \n $heredoc_delimiter \n/xmsgc;
4640             }
4641 191         318 @heredoc_delimiter = ();
4642              
4643 191         257 $here_script = '';
4644             }
4645             return "\n" . $heredoc;
4646             }
4647 22128         63484  
4648             # ignore space, comment
4649             elsif (/\G ((?>\s+)|\#.*) /oxgc) { return $1; }
4650              
4651             # if (, elsif (, unless (, while (, until (, given (, and when (
4652              
4653             # given, when
4654              
4655             # P.225 The given Statement
4656             # in Chapter 15: Smart Matching and given-when
4657             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
4658              
4659             # P.133 The given Statement
4660             # in Chapter 4: Statements and Declarations
4661             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
4662 36018         114121  
4663 2398         3664 elsif (/\G ( (?: if | elsif | unless | while | until | given | when ) (?>\s*) \( ) /oxgc) {
4664             $slash = 'm//';
4665             return $1;
4666             }
4667              
4668             # scalar variable ($scalar = ...) =~ tr///;
4669             # scalar variable ($scalar = ...) =~ s///;
4670              
4671             # state
4672              
4673             # P.68 Persistent, Private Variables
4674             # in Chapter 4: Subroutines
4675             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
4676              
4677             # P.160 Persistent Lexically Scoped Variables: state
4678             # in Chapter 4: Statements and Declarations
4679             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
4680              
4681             # (and so on)
4682 2398         7070  
4683             elsif (/\G ( \( (?>\s*) (?: local \b | my \b | our \b | state \b )? (?>\s*) \$ $qq_scalar ) /oxgc) {
4684 139 50       370 my $e_string = e_string($1);
    50          
4685 139         6787  
4686 0         0 if (/\G ( (?>\s*) = $qq_paren \) ) ( (?>\s*) (?: =~ | !~ ) (?>\s*) ) (?= (?: tr | y ) \b ) /oxgc) {
4687 0         0 $tr_variable = $e_string . e_string($1);
4688 0         0 $bind_operator = $2;
4689             $slash = 'm//';
4690             return '';
4691 0         0 }
4692 0         0 elsif (/\G ( (?>\s*) = $qq_paren \) ) ( (?>\s*) (?: =~ | !~ ) (?>\s*) ) (?= s \b ) /oxgc) {
4693 0         0 $sub_variable = $e_string . e_string($1);
4694 0         0 $bind_operator = $2;
4695             $slash = 'm//';
4696             return '';
4697 0         0 }
4698 139         267 else {
4699             $slash = 'div';
4700             return $e_string;
4701             }
4702             }
4703              
4704 139         577 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
4705 4         18 elsif (/\G ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH \b | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) /oxmsgc) {
4706             $slash = 'div';
4707             return q{Eutf2::PREMATCH()};
4708             }
4709              
4710 4         14 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
4711 28         116 elsif (/\G ( \$& | \$\{&\} | \$ (?>\s*) MATCH \b | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) /oxmsgc) {
4712             $slash = 'div';
4713             return q{Eutf2::MATCH()};
4714             }
4715              
4716 28         80 # $', ${'} --> $', ${'}
4717 1         2 elsif (/\G ( \$' | \$\{'\} ) /oxmsgc) {
4718             $slash = 'div';
4719             return $1;
4720             }
4721              
4722 1         3 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
4723 3         6 elsif (/\G ( \$ (?>\s*) POSTMATCH \b | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) /oxmsgc) {
4724             $slash = 'div';
4725             return q{Eutf2::POSTMATCH()};
4726             }
4727              
4728             # scalar variable $scalar =~ tr///;
4729             # scalar variable $scalar =~ s///;
4730             # substr() =~ tr///;
4731 3         10 # substr() =~ s///;
4732             elsif (/\G ( \$ $qq_scalar | $qq_substr ) /oxgc) {
4733 2318 100       5230 my $scalar = e_string($1);
    100          
4734 2318         8842  
4735 9         18 if (/\G ( (?>\s*) (?: =~ | !~ ) (?>\s*) ) (?= (?: tr | y ) \b ) /oxgc) {
4736 9         16 $tr_variable = $scalar;
4737 9         13 $bind_operator = $1;
4738             $slash = 'm//';
4739             return '';
4740 9         28 }
4741 95         211 elsif (/\G ( (?>\s*) (?: =~ | !~ ) (?>\s*) ) (?= s \b ) /oxgc) {
4742 95         203 $sub_variable = $scalar;
4743 95         147 $bind_operator = $1;
4744             $slash = 'm//';
4745             return '';
4746 95         385 }
4747 2214         3051 else {
4748             $slash = 'div';
4749             return $scalar;
4750             }
4751             }
4752              
4753 2214         6099 # end of statement
4754             elsif (/\G ( [,;] ) /oxgc) {
4755             $slash = 'm//';
4756 9208         13346  
4757             # clear tr/// variable
4758             $tr_variable = '';
4759 9208         10341  
4760             # clear s/// variable
4761 9208         9984 $sub_variable = '';
4762              
4763 9208         9593 $bind_operator = '';
4764              
4765             return $1;
4766             }
4767              
4768 9208         29750 # bareword
4769             elsif (/\G ( \{ (?>\s*) (?: tr | index | rindex | reverse ) (?>\s*) \} ) /oxmsgc) {
4770             return $1;
4771             }
4772              
4773 0         0 # $0 --> $0
4774 2         4 elsif (/\G ( \$ 0 ) /oxmsgc) {
4775             $slash = 'div';
4776             return $1;
4777 2         8 }
4778 0         0 elsif (/\G ( \$ \{ (?>\s*) 0 (?>\s*) \} ) /oxmsgc) {
4779             $slash = 'div';
4780             return $1;
4781             }
4782              
4783 0         0 # $$ --> $$
4784 1         2 elsif (/\G ( \$ \$ ) (?![\w\{]) /oxmsgc) {
4785             $slash = 'div';
4786             return $1;
4787             }
4788              
4789             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
4790 1         4 # $1, $2, $3 --> $1, $2, $3 otherwise
4791 57         128 elsif (/\G \$ ((?>[1-9][0-9]*)) /oxmsgc) {
4792             $slash = 'div';
4793             return e_capture($1);
4794 57         297 }
4795 0         0 elsif (/\G \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} /oxmsgc) {
4796             $slash = 'div';
4797             return e_capture($1);
4798             }
4799              
4800 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
4801 0         0 elsif (/\G \$ ( \$ (?> [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ .+? \] ) /oxmsgc) {
4802             $slash = 'div';
4803             return e_capture($1.'->'.$2);
4804             }
4805              
4806 0         0 # $$foo{ ... } --> $ $foo->{ ... }
4807 0         0 elsif (/\G \$ ( \$ (?> [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ .+? \} ) /oxmsgc) {
4808             $slash = 'div';
4809             return e_capture($1.'->'.$2);
4810             }
4811              
4812 0         0 # $$foo
4813 0         0 elsif (/\G \$ ( \$ (?> [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) /oxmsgc) {
4814             $slash = 'div';
4815             return e_capture($1);
4816             }
4817              
4818 0         0 # ${ foo }
4819 0         0 elsif (/\G \$ (?>\s*) \{ ( (?>\s*) (?> [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* ) (?>\s*) ) \} /oxmsgc) {
4820             $slash = 'div';
4821             return '${' . $1 . '}';
4822             }
4823              
4824 0         0 # ${ ... }
4825 0         0 elsif (/\G \$ (?>\s*) \{ (?>\s*) ( $qq_brace ) (?>\s*) \} /oxmsgc) {
4826             $slash = 'div';
4827             return e_capture($1);
4828             }
4829              
4830             # variable or function
4831 0         0 # $ @ % & * $ #
4832 27         49 elsif (/\G ( (?: [\$\@\%\&\*] | \$\# | -> | \b sub \b) (?>\s*) (?: split | chop | index | rindex | lc | uc | fc | chr | ord | reverse | getc | tr | y | q | qq | qx | qw | m | s | qr | glob | lstat | opendir | stat | unlink | chdir ) ) \b /oxmsgc) {
4833             $slash = 'div';
4834             return $1;
4835             }
4836             # $ $ $ $ $ $ $ $ $ $ $ $ $ $
4837 27         91 # $ @ # \ ' " / ? ( ) [ ] < >
4838 90         172 elsif (/\G ( \$[\$\@\#\\\'\"\/\?\(\)\[\]\<\>] ) /oxmsgc) {
4839             $slash = 'div';
4840             return $1;
4841             }
4842              
4843 90         316 # while ()
4844             elsif (/\G \b (while (?>\s*) \( (?>\s*) <[\$]?[A-Za-z_][A-Za-z_0-9]*> (?>\s*) \)) \b /oxgc) {
4845             return $1;
4846             }
4847              
4848             # while () --- glob
4849              
4850             # avoid "Error: Runtime exception" of perl version 5.005_03
4851 0         0  
4852             elsif (/\G \b while (?>\s*) \( (?>\s*) < ((?:[^\x80-\xFF>\0\a\e\f\n\r\t]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])+?) > (?>\s*) \) \b /oxgc) {
4853             return 'while ($_ = Eutf2::glob("' . $1 . '"))';
4854             }
4855              
4856 0         0 # while (glob)
4857             elsif (/\G \b while (?>\s*) \( (?>\s*) glob (?>\s*) \) /oxgc) {
4858             return 'while ($_ = Eutf2::glob_)';
4859             }
4860              
4861 0         0 # while (glob(WILDCARD))
4862             elsif (/\G \b while (?>\s*) \( (?>\s*) glob \b /oxgc) {
4863             return 'while ($_ = Eutf2::glob';
4864             }
4865 0         0  
  401         919  
4866             # doit if, doit unless, doit while, doit until, doit for, doit when
4867             elsif (/\G \b ( if | unless | while | until | for | when ) \b /oxgc) { $slash = 'm//'; return $1; }
4868 401         1522  
  19         32  
4869 19         61 # subroutines of package Eutf2
  0         0  
4870 0         0 elsif (/\G \b (CORE:: | ->(>?\s*) (?: atan2 | [a-z]{2,})) \b /oxgc) { $slash = 'm//'; return $1; }
  13         21  
4871 13         32 elsif (/\G \b Char::eval (?= (?>\s*) \{ ) /oxgc) { $slash = 'm//'; return 'eval'; }
  0         0  
4872 0         0 elsif (/\G \b UTF2::eval (?= (?>\s*) \{ ) /oxgc) { $slash = 'm//'; return 'eval'; }
  114         178  
4873 114         314 elsif (/\G \b Char::eval \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'eval Char::escape'; }
  2         3  
4874 2         6 elsif (/\G \b UTF2::eval \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'eval UTF2::escape'; }
  2         5  
4875 2         8 elsif (/\G \b bytes::substr \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'substr'; }
  2         3  
4876 2         6 elsif (/\G \b chop \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::chop'; }
  0         0  
4877 0         0 elsif (/\G \b bytes::index \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'index'; }
  2         6  
4878 2         5 elsif (/\G \b Char::index \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Char::index'; }
  2         3  
4879 2         7 elsif (/\G \b UTF2::index \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'UTF2::index'; }
  2         4  
4880 2         6 elsif (/\G \b index \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::index'; }
  0         0  
4881 0         0 elsif (/\G \b bytes::rindex \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'rindex'; }
  2         4  
4882 2         6 elsif (/\G \b Char::rindex \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Char::rindex'; }
  2         5  
4883 2         5 elsif (/\G \b UTF2::rindex \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'UTF2::rindex'; }
  1         2  
4884 1         3 elsif (/\G \b rindex \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::rindex'; }
  0         0  
4885 0         0 elsif (/\G \b lc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::lc'; }
  0         0  
4886 0         0 elsif (/\G \b lcfirst (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::lcfirst'; }
  0         0  
4887 0         0 elsif (/\G \b uc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::uc'; }
  7         12  
4888             elsif (/\G \b ucfirst (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::ucfirst'; }
4889             elsif (/\G \b fc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::fc'; }
4890 7         20  
  0         0  
4891 0         0 # "-s '' ..." means file test "-s 'filename' ..." (not means "- s/// ...")
  0         0  
4892 0         0 elsif (/\G -s (?>\s*) (\") ((?:$qq_char)+?) (\") /oxgc) { $slash = 'm//'; return '-s ' . e_qq('', $1,$3,$2); }
  0         0  
4893 0         0 elsif (/\G -s (?>\s+) qq (?>\s*) (\#) ((?:$qq_char)+?) (\#) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
  0         0  
4894 0         0 elsif (/\G -s (?>\s+) qq (?>\s*) (\() ((?:$qq_paren)+?) (\)) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
  0         0  
4895 0         0 elsif (/\G -s (?>\s+) qq (?>\s*) (\{) ((?:$qq_brace)+?) (\}) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
  0         0  
4896 0         0 elsif (/\G -s (?>\s+) qq (?>\s*) (\[) ((?:$qq_bracket)+?) (\]) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
  0         0  
4897             elsif (/\G -s (?>\s+) qq (?>\s*) (\<) ((?:$qq_angle)+?) (\>) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
4898 0         0 elsif (/\G -s (?>\s+) qq (?>\s*) (\S) ((?:$qq_char)+?) (\1) /oxgc) { $slash = 'm//'; return '-s ' . e_qq('qq',$1,$3,$2); }
  0         0  
4899 0         0  
  0         0  
4900 0         0 elsif (/\G -s (?>\s*) (\') ((?:\\\'|\\\\|$q_char)+?) (\') /oxgc) { $slash = 'm//'; return '-s ' . e_q ('', $1,$3,$2); }
  0         0  
4901 0         0 elsif (/\G -s (?>\s+) q (?>\s*) (\#) ((?:\\\#|\\\\|$q_char)+?) (\#) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
  0         0  
4902 0         0 elsif (/\G -s (?>\s+) q (?>\s*) (\() ((?:\\\)|\\\\|$q_paren)+?) (\)) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
  0         0  
4903 0         0 elsif (/\G -s (?>\s+) q (?>\s*) (\{) ((?:\\\}|\\\\|$q_brace)+?) (\}) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
  0         0  
4904 0         0 elsif (/\G -s (?>\s+) q (?>\s*) (\[) ((?:\\\]|\\\\|$q_bracket)+?) (\]) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
  0         0  
4905             elsif (/\G -s (?>\s+) q (?>\s*) (\<) ((?:\\\>|\\\\|$q_angle)+?) (\>) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
4906             elsif (/\G -s (?>\s+) q (?>\s*) (\S) ((?:\\\1|\\\\|$q_char)+?) (\1) /oxgc) { $slash = 'm//'; return '-s ' . e_q ('q', $1,$3,$2); }
4907 0         0  
  0         0  
4908 0         0 elsif (/\G -s (?>\s*) (\$ (?> \w+ (?: ::\w+)* ) (?: (?: ->)? (?: [\$\@\%\&\*]\* | \$\#\* | \( (?:$qq_paren)*? \) | [\@\%\*]? \{ (?:$qq_brace)+? \} | [\@\%]? \[ (?:$qq_bracket)+? \] ) )*) /oxgc)
  0         0  
4909 0         0 { $slash = 'm//'; return "-s $1"; }
  0         0  
4910 0         0 elsif (/\G -s (?>\s*) \( ((?:$qq_paren)*?) \) /oxgc) { $slash = 'm//'; return "-s ($1)"; }
  0         0  
4911             elsif (/\G -s (?= (?>\s+) [a-z]+) /oxgc) { $slash = 'm//'; return '-s'; }
4912 0         0 elsif (/\G -s (?>\s+) ((?>\w+)) /oxgc) { $slash = 'm//'; return "-s $1"; }
  2         4  
4913 2         6  
  2         5  
4914 2         5 elsif (/\G \b bytes::length (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'length'; }
  36         68  
4915 36         116 elsif (/\G \b bytes::chr (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'chr'; }
  2         3  
4916 2         7 elsif (/\G \b chr (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::chr'; }
  2         5  
4917 2         9 elsif (/\G \b bytes::ord (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'div'; return 'ord'; }
  0         0  
4918 0         0 elsif (/\G \b ord (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'div'; return $function_ord; }
  0         0  
4919 0         0 elsif (/\G \b glob (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $slash = 'm//'; return 'Eutf2::glob'; }
  0         0  
4920 0         0 elsif (/\G \b lc \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::lc_'; }
  0         0  
4921 0         0 elsif (/\G \b lcfirst \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::lcfirst_'; }
  0         0  
4922 0         0 elsif (/\G \b uc \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::uc_'; }
  0         0  
4923 0         0 elsif (/\G \b ucfirst \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::ucfirst_'; }
  0         0  
4924             elsif (/\G \b fc \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::fc_'; }
4925 0         0 elsif (/\G -s \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return '-s '; }
  0         0  
4926 0         0  
  0         0  
4927 0         0 elsif (/\G \b bytes::length \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'length'; }
  0         0  
4928 0         0 elsif (/\G \b bytes::chr \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'chr'; }
  0         0  
4929 0         0 elsif (/\G \b chr \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::chr_'; }
  2         8  
4930 2         10 elsif (/\G \b bytes::ord \b (?! (?>\s*) => ) /oxgc) { $slash = 'div'; return 'ord'; }
  0         0  
4931 0         0 elsif (/\G \b ord \b (?! (?>\s*) => ) /oxgc) { $slash = 'div'; return $function_ord_; }
  4         7  
4932 4         13 elsif (/\G \b glob \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return 'Eutf2::glob_'; }
  8         19  
4933             elsif (/\G \b reverse \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return $function_reverse; }
4934             elsif (/\G \b getc \b (?! (?>\s*) => ) /oxgc) { $slash = 'm//'; return $function_getc; }
4935 8         30 # split
4936             elsif (/\G \b (split) \b (?! (?>\s*) => ) /oxgc) {
4937 120         246 $slash = 'm//';
4938 120         204  
4939 120         463 my $e = '';
4940             while (/\G ( (?>\s+) | \( | \#.* ) /oxgc) {
4941             $e .= $1;
4942             }
4943 117 100       470  
  120 100       13329  
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    100          
    50          
    100          
    50          
    50          
    50          
4944             # end of split
4945             if (/\G (?= [,;\)\}\]] ) /oxgc) { return 'Eutf2::split' . $e; }
4946 3         14  
4947             # split scalar value
4948             elsif (/\G ( [\$\@\&\*] $qq_scalar ) /oxgc) { return 'Eutf2::split' . $e . e_string($1); }
4949 1         7  
4950 0         0 # split literal space
4951 0         0 elsif (/\G \b qq (\#) [ ] (\#) /oxgc) { return 'Eutf2::split' . $e . qq {qq$1 $2}; }
4952 0         0 elsif (/\G \b qq ((?>\s*)) (\() [ ] (\)) /oxgc) { return 'Eutf2::split' . $e . qq{$1qq$2 $3}; }
4953 0         0 elsif (/\G \b qq ((?>\s*)) (\{) [ ] (\}) /oxgc) { return 'Eutf2::split' . $e . qq{$1qq$2 $3}; }
4954 0         0 elsif (/\G \b qq ((?>\s*)) (\[) [ ] (\]) /oxgc) { return 'Eutf2::split' . $e . qq{$1qq$2 $3}; }
4955 0         0 elsif (/\G \b qq ((?>\s*)) (\<) [ ] (\>) /oxgc) { return 'Eutf2::split' . $e . qq{$1qq$2 $3}; }
4956 0         0 elsif (/\G \b qq ((?>\s*)) (\S) [ ] (\2) /oxgc) { return 'Eutf2::split' . $e . qq{$1qq$2 $3}; }
4957 0         0 elsif (/\G \b q (\#) [ ] (\#) /oxgc) { return 'Eutf2::split' . $e . qq {q$1 $2}; }
4958 0         0 elsif (/\G \b q ((?>\s*)) (\() [ ] (\)) /oxgc) { return 'Eutf2::split' . $e . qq {$1q$2 $3}; }
4959 0         0 elsif (/\G \b q ((?>\s*)) (\{) [ ] (\}) /oxgc) { return 'Eutf2::split' . $e . qq {$1q$2 $3}; }
4960 0         0 elsif (/\G \b q ((?>\s*)) (\[) [ ] (\]) /oxgc) { return 'Eutf2::split' . $e . qq {$1q$2 $3}; }
4961 0         0 elsif (/\G \b q ((?>\s*)) (\<) [ ] (\>) /oxgc) { return 'Eutf2::split' . $e . qq {$1q$2 $3}; }
4962 13         73 elsif (/\G \b q ((?>\s*)) (\S) [ ] (\2) /oxgc) { return 'Eutf2::split' . $e . qq {$1q$2 $3}; }
4963             elsif (/\G ' [ ] ' /oxgc) { return 'Eutf2::split' . $e . qq {' '}; }
4964             elsif (/\G " [ ] " /oxgc) { return 'Eutf2::split' . $e . qq {" "}; }
4965              
4966 2 0       10 # split qq//
  0         0  
4967             elsif (/\G \b (qq) \b /oxgc) {
4968 0         0 if (/\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq# # --> qr # #
4969 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
4970 0         0 while (not /\G \z/oxgc) {
4971 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
4972 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq ( ) --> qr ( )
4973 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq { } --> qr { }
4974 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq [ ] --> qr [ ]
4975 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq < > --> qr < >
4976             elsif (/\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) /oxgc) { return e_split($e.'qr','{','}',$2,''); } # qq | | --> qr { }
4977 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { return e_split($e.'qr',$1,$3,$2,''); } # qq * * --> qr * *
4978             }
4979             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
4980             }
4981             }
4982              
4983 0 50       0 # split qr//
  12         839  
4984             elsif (/\G \b (qr) \b /oxgc) {
4985 0         0 if (/\G (\#) ((?:$qq_char)*?) (\#) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1,$3,$2,$4); } # qr# #
4986 12 50       64 else {
  12 50       6803  
    50          
    50          
    50          
    50          
    50          
    50          
4987 0         0 while (not /\G \z/oxgc) {
4988 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
4989 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # qr ( )
4990 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # qr { }
4991 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # qr [ ]
4992 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # qr < >
4993 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([imosxpadlunbB]*) /oxgc) { return e_split_q($e.'qr',$1, $3, $2,$4); } # qr ' '
4994             elsif (/\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr','{','}',$2,$4); } # qr | | --> qr { }
4995 12         90 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # qr * *
4996             }
4997             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
4998             }
4999             }
5000              
5001 0 0       0 # split q//
  0         0  
5002             elsif (/\G \b (q) \b /oxgc) {
5003 0         0 if (/\G (\#) ((?:\\\#|\\\\|$q_char)*?) (\#) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q# # --> qr # #
5004 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
5005 0         0 while (not /\G \z/oxgc) {
5006 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5007 0         0 elsif (/\G (\() ((?:\\\\|\\\)|\\\(|$q_paren)*?) (\)) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q ( ) --> qr ( )
5008 0         0 elsif (/\G (\{) ((?:\\\\|\\\}|\\\{|$q_brace)*?) (\}) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q { } --> qr { }
5009 0         0 elsif (/\G (\[) ((?:\\\\|\\\]|\\\[|$q_bracket)*?) (\]) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q [ ] --> qr [ ]
5010 0         0 elsif (/\G (\<) ((?:\\\\|\\\>|\\\<|$q_angle)*?) (\>) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q < > --> qr < >
5011             elsif (/\G ([*\-:?\\^|]) ((?:$q_char)*?) (\1) /oxgc) { return e_split_q($e.'qr','{','}',$2,''); } # q | | --> qr { }
5012 0         0 elsif (/\G (\S) ((?:\\\\|\\\1| $q_char)*?) (\1) /oxgc) { return e_split_q($e.'qr',$1,$3,$2,''); } # q * * --> qr * *
5013             }
5014             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5015             }
5016             }
5017              
5018 0 50       0 # split m//
  24         984  
5019             elsif (/\G \b (m) \b /oxgc) {
5020 0         0 if (/\G (\#) ((?:$qq_char)*?) (\#) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1,$3,$2,$4); } # m# # --> qr # #
5021 24 50       99 else {
  24 50       7872  
    50          
    50          
    50          
    50          
    50          
    50          
5022 0         0 while (not /\G \z/oxgc) {
5023 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5024 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # m ( ) --> qr ( )
5025 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # m { } --> qr { }
5026 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # m [ ] --> qr [ ]
5027 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # m < > --> qr < >
5028 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cgimosxpadlunbB]*) /oxgc) { return e_split_q($e.'qr',$1, $3, $2,$4); } # m ' ' --> qr ' '
5029             elsif (/\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr','{','}',$2,$4); } # m | | --> qr { }
5030 24         141 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { return e_split ($e.'qr',$1, $3, $2,$4); } # m * * --> qr * *
5031             }
5032             die __FILE__, ": Search pattern not terminated\n";
5033             }
5034             }
5035              
5036 0         0 # split ''
5037 0         0 elsif (/\G (\') /oxgc) {
5038 0 0       0 my $q_string = '';
  0 0       0  
    0          
    0          
5039 0         0 while (not /\G \z/oxgc) {
5040 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5041 0         0 elsif (/\G (\\\') /oxgc) { $q_string .= $1; } # splitqr'' --> split qr''
5042             elsif (/\G \' /oxgc) { return e_split_q($e.q{ qr},"'","'",$q_string,''); } # ' ' --> qr ' '
5043 0         0 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5044             }
5045             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5046             }
5047              
5048 0         0 # split ""
5049 0         0 elsif (/\G (\") /oxgc) {
5050 0 0       0 my $qq_string = '';
  0 0       0  
    0          
    0          
5051 0         0 while (not /\G \z/oxgc) {
5052 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
5053 0         0 elsif (/\G (\\\") /oxgc) { $qq_string .= $1; } # splitqr"" --> split qr""
5054             elsif (/\G \" /oxgc) { return e_split($e.q{ qr},'"','"',$qq_string,''); } # " " --> qr " "
5055 0         0 elsif (/\G ($q_char) /oxgc) { $qq_string .= $1; }
5056             }
5057             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5058             }
5059              
5060 0         0 # split //
5061 65         172 elsif (/\G (\/) /oxgc) {
5062 65 50       207 my $regexp = '';
  434 50       2765  
    100          
    50          
5063 0         0 while (not /\G \z/oxgc) {
5064 0         0 if (/\G (\\\\) /oxgc) { $regexp .= $1; }
5065 65         293 elsif (/\G (\\\/) /oxgc) { $regexp .= $1; } # splitqr// --> split qr//
5066             elsif (/\G \/ ([cgimosxpadlunbB]*) /oxgc) { return e_split($e.q{ qr}, '/','/',$regexp,$1); } # / / --> qr / /
5067 369         802 elsif (/\G ($q_char) /oxgc) { $regexp .= $1; }
5068             }
5069             die __FILE__, ": Search pattern not terminated\n";
5070             }
5071             }
5072              
5073             # tr/// or y///
5074              
5075             # about [cdsrbB]* (/B modifier)
5076             #
5077             # P.559 appendix C
5078             # of ISBN 4-89052-384-7 Programming perl
5079             # (Japanese title is: Perl puroguramingu)
5080 0         0  
5081             elsif (/\G \b ( tr | y ) \b /oxgc) {
5082             my $ope = $1;
5083 11 50       24  
5084 11         273 # $1 $2 $3 $4 $5 $6
5085 0         0 if (/\G (\#) ((?:$qq_char)*?) (\#) ((?:$qq_char)*?) (\#) ([cdsrbB]*) /oxgc) { # tr# # #
5086             my @tr = ($tr_variable,$2);
5087             return e_tr(@tr,'',$4,$6);
5088 0         0 }
5089 11         22 else {
5090 11 50       28 my $e = '';
  11 50       1572  
    50          
    50          
    50          
    50          
5091             while (not /\G \z/oxgc) {
5092 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5093 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) /oxgc) {
5094 0 0       0 my @tr = ($tr_variable,$2);
  0 0       0  
    0          
    0          
    0          
    0          
5095 0         0 while (not /\G \z/oxgc) {
5096 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5097 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr ( ) ( )
5098 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr ( ) { }
5099 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr ( ) [ ]
5100             elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr ( ) < >
5101 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr ( ) * *
5102             }
5103             die __FILE__, ": Transliteration replacement not terminated\n";
5104 0         0 }
5105 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) {
5106 0 0       0 my @tr = ($tr_variable,$2);
  0 0       0  
    0          
    0          
    0          
    0          
5107 0         0 while (not /\G \z/oxgc) {
5108 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5109 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr { } ( )
5110 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr { } { }
5111 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr { } [ ]
5112             elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr { } < >
5113 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr { } * *
5114             }
5115             die __FILE__, ": Transliteration replacement not terminated\n";
5116 0         0 }
5117 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) {
5118 0 0       0 my @tr = ($tr_variable,$2);
  0 0       0  
    0          
    0          
    0          
    0          
5119 0         0 while (not /\G \z/oxgc) {
5120 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5121 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr [ ] ( )
5122 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr [ ] { }
5123 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr [ ] [ ]
5124             elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr [ ] < >
5125 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr [ ] * *
5126             }
5127             die __FILE__, ": Transliteration replacement not terminated\n";
5128 0         0 }
5129 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) {
5130 0 0       0 my @tr = ($tr_variable,$2);
  0 0       0  
    0          
    0          
    0          
    0          
5131 0         0 while (not /\G \z/oxgc) {
5132 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5133 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr < > ( )
5134 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr < > { }
5135 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr < > [ ]
5136             elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr < > < >
5137 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cdsrbB]*) /oxgc) { return e_tr(@tr,$e,$2,$4); } # tr < > * *
5138             }
5139             die __FILE__, ": Transliteration replacement not terminated\n";
5140             }
5141 0         0 # $1 $2 $3 $4 $5 $6
5142 11         49 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ((?:$qq_char)*?) (\1) ([cdsrbB]*) /oxgc) { # tr * * *
5143             my @tr = ($tr_variable,$2);
5144             return e_tr(@tr,'',$4,$6);
5145 11         36 }
5146             }
5147             die __FILE__, ": Transliteration pattern not terminated\n";
5148             }
5149             }
5150              
5151 0         0 # qq//
5152             elsif (/\G \b (qq) \b /oxgc) {
5153             my $ope = $1;
5154 3822 100       8079  
5155 3822         6932 # if (/\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { return e_qq($ope,$1,$3,$2); } # qq# #
5156 40         201 if (/\G (\#) /oxgc) { # qq# #
5157 40 100       195 my $qq_string = '';
  1948 50       6931  
    100          
    50          
5158 80         159 while (not /\G \z/oxgc) {
5159 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
5160 40         88 elsif (/\G (\\\#) /oxgc) { $qq_string .= $1; }
5161             elsif (/\G (\#) /oxgc) { return e_qq($ope,'#','#',$qq_string); }
5162 1828         4048 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5163             }
5164             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5165             }
5166 0         0  
5167 3782         5024 else {
5168 3782 50       10358 my $e = '';
  3782 50       13509  
    100          
    50          
    100          
    50          
5169             while (not /\G \z/oxgc) {
5170             if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5171              
5172 0         0 # elsif (/\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qq ( )
5173 0         0 elsif (/\G (\() /oxgc) { # qq ( )
5174 0         0 my $qq_string = '';
5175 0 0       0 local $nest = 1;
  0 0       0  
    0          
    0          
    0          
5176 0         0 while (not /\G \z/oxgc) {
5177 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
  0         0  
5178             elsif (/\G (\\\)) /oxgc) { $qq_string .= $1; }
5179 0 0       0 elsif (/\G (\() /oxgc) { $qq_string .= $1; $nest++; }
  0         0  
5180 0         0 elsif (/\G (\)) /oxgc) {
5181             if (--$nest == 0) { return $e . e_qq($ope,'(',')',$qq_string); }
5182 0         0 else { $qq_string .= $1; }
5183             }
5184 0         0 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5185             }
5186             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5187             }
5188              
5189 0         0 # elsif (/\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qq { }
5190 3724         4797 elsif (/\G (\{) /oxgc) { # qq { }
5191 3724         5007 my $qq_string = '';
5192 3724 100       8388 local $nest = 1;
  155735 50       528876  
    100          
    100          
    50          
5193 792         1527 while (not /\G \z/oxgc) {
5194 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
  1384         2138  
5195             elsif (/\G (\\\}) /oxgc) { $qq_string .= $1; }
5196 1384 100       2332 elsif (/\G (\{) /oxgc) { $qq_string .= $1; $nest++; }
  5108         7309  
5197 3724         7291 elsif (/\G (\}) /oxgc) {
5198             if (--$nest == 0) { return $e . e_qq($ope,'{','}',$qq_string); }
5199 1384         2763 else { $qq_string .= $1; }
5200             }
5201 148451         275357 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5202             }
5203             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5204             }
5205              
5206 0         0 # elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qq [ ]
5207 0         0 elsif (/\G (\[) /oxgc) { # qq [ ]
5208 0         0 my $qq_string = '';
5209 0 0       0 local $nest = 1;
  0 0       0  
    0          
    0          
    0          
5210 0         0 while (not /\G \z/oxgc) {
5211 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
  0         0  
5212             elsif (/\G (\\\]) /oxgc) { $qq_string .= $1; }
5213 0 0       0 elsif (/\G (\[) /oxgc) { $qq_string .= $1; $nest++; }
  0         0  
5214 0         0 elsif (/\G (\]) /oxgc) {
5215             if (--$nest == 0) { return $e . e_qq($ope,'[',']',$qq_string); }
5216 0         0 else { $qq_string .= $1; }
5217             }
5218 0         0 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5219             }
5220             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5221             }
5222              
5223 0         0 # elsif (/\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qq < >
5224 38         62 elsif (/\G (\<) /oxgc) { # qq < >
5225 38         66 my $qq_string = '';
5226 38 100       154 local $nest = 1;
  1418 50       5912  
    50          
    100          
    50          
5227 22         52 while (not /\G \z/oxgc) {
5228 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
  0         0  
5229             elsif (/\G (\\\>) /oxgc) { $qq_string .= $1; }
5230 0 50       0 elsif (/\G (\<) /oxgc) { $qq_string .= $1; $nest++; }
  38         85  
5231 38         101 elsif (/\G (\>) /oxgc) {
5232             if (--$nest == 0) { return $e . e_qq($ope,'<','>',$qq_string); }
5233 0         0 else { $qq_string .= $1; }
5234             }
5235 1358         2541 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5236             }
5237             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5238             }
5239              
5240 0         0 # elsif (/\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qq * *
5241 20         33 elsif (/\G (\S) /oxgc) { # qq * *
5242 20         24 my $delimiter = $1;
5243 20 50       31 my $qq_string = '';
  840 50       2460  
    100          
    50          
5244 0         0 while (not /\G \z/oxgc) {
5245 0         0 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
5246 20         39 elsif (/\G (\\\Q$delimiter\E) /oxgc) { $qq_string .= $1; }
5247             elsif (/\G (\Q$delimiter\E) /oxgc) { return $e . e_qq($ope,$delimiter,$delimiter,$qq_string); }
5248 820         1588 elsif (/\G ($qq_char) /oxgc) { $qq_string .= $1; }
5249             }
5250             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5251 0         0 }
5252             }
5253             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5254             }
5255             }
5256              
5257 0         0 # qr//
5258 36 50       89 elsif (/\G \b (qr) \b /oxgc) {
5259 36         438 my $ope = $1;
5260             if (/\G (\#) ((?:$qq_char)*?) (\#) ([imosxpadlunbB]*) /oxgc) { # qr# # #
5261             return e_qr($ope,$1,$3,$2,$4);
5262 0         0 }
5263 36         66 else {
5264 36 50       85 my $e = '';
  36 50       3692  
    100          
    50          
    50          
    100          
    50          
    50          
5265 0         0 while (not /\G \z/oxgc) {
5266 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5267 1         11 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # qr ( )
5268 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # qr { }
5269 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # qr [ ]
5270 2         11 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # qr < >
5271 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([imosxpadlunbB]*) /oxgc) { return $e . e_qr_q($ope,$1, $3, $2,$4); } # qr ' '
5272             elsif (/\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,'{','}',$2,$4); } # qr | | --> qr { }
5273 33         108 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # qr * *
5274             }
5275             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5276             }
5277             }
5278              
5279 0         0 # qw//
5280 34 50       90 elsif (/\G \b (qw) \b /oxgc) {
5281 34         90 my $ope = $1;
5282             if (/\G (\#) (.*?) (\#) /oxmsgc) { # qw# #
5283             return e_qw($ope,$1,$3,$2);
5284 0         0 }
5285 34         58 else {
5286 34 50       103 my $e = '';
  34 50       206  
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
5287             while (not /\G \z/oxgc) {
5288 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5289 34         114  
5290             elsif (/\G (\() ([^(]*?) (\)) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw ( )
5291 0         0 elsif (/\G (\() ((?:$q_paren)*?) (\)) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw ( )
5292 0         0  
5293             elsif (/\G (\{) ([^{]*?) (\}) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw { }
5294 0         0 elsif (/\G (\{) ((?:$q_brace)*?) (\}) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw { }
5295 0         0  
5296             elsif (/\G (\[) ([^[]*?) (\]) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw [ ]
5297 0         0 elsif (/\G (\[) ((?:$q_bracket)*?) (\]) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw [ ]
5298 0         0  
5299             elsif (/\G (\<) ([^<]*?) (\>) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw < >
5300 0         0 elsif (/\G (\<) ((?:$q_angle)*?) (\>) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw < >
5301 0         0  
5302             elsif (/\G ([\x21-\x3F]) (.*?) (\1) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw * *
5303 0         0 elsif (/\G (\S) ((?:$q_char)*?) (\1) /oxmsgc) { return $e . e_qw($ope,$1,$3,$2); } # qw * *
5304             }
5305             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5306             }
5307             }
5308              
5309 0         0 # qx//
5310 2 50       6 elsif (/\G \b (qx) \b /oxgc) {
5311 2         63 my $ope = $1;
5312             if (/\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { # qx# #
5313             return e_qq($ope,$1,$3,$2);
5314 0         0 }
5315 2         5 else {
5316 2 50       6 my $e = '';
  2 50       192  
    50          
    0          
    0          
    0          
    0          
5317 0         0 while (not /\G \z/oxgc) {
5318 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5319 2         5 elsif (/\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qx ( )
5320 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qx { }
5321 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qx [ ]
5322 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qx < >
5323             elsif (/\G (\') ((?:$qq_char)*?) (\') /oxgc) { return $e . e_q ($ope,$1,$3,$2); } # qx ' '
5324 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { return $e . e_qq($ope,$1,$3,$2); } # qx * *
5325             }
5326             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5327             }
5328             }
5329              
5330 0         0 # q//
5331             elsif (/\G \b (q) \b /oxgc) {
5332             my $ope = $1;
5333              
5334             # if (/\G (\#) ((?:\\\#|\\\\|$q_char)*?) (\#) /oxgc) { return e_q($ope,$1,$3,$2); } # q# #
5335              
5336             # avoid "Error: Runtime exception" of perl version 5.005_03
5337 527 50       1391 # (and so on)
5338 527         1444  
5339 0         0 if (/\G (\#) /oxgc) { # q# #
5340 0 0       0 my $q_string = '';
  0 0       0  
    0          
    0          
5341 0         0 while (not /\G \z/oxgc) {
5342 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5343 0         0 elsif (/\G (\\\#) /oxgc) { $q_string .= $1; }
5344             elsif (/\G (\#) /oxgc) { return e_q($ope,'#','#',$q_string); }
5345 0         0 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5346             }
5347             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5348             }
5349 0         0  
5350 527         1026 else {
5351 527 50       1783 my $e = '';
  527 50       3257  
    100          
    50          
    100          
    50          
5352             while (not /\G \z/oxgc) {
5353             if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5354              
5355 0         0 # elsif (/\G (\() ((?:\\\)|\\\\|$q_paren)*?) (\)) /oxgc) { return $e . e_q($ope,$1,$3,$2); } # q ( )
5356 0         0 elsif (/\G (\() /oxgc) { # q ( )
5357 0         0 my $q_string = '';
5358 0 0       0 local $nest = 1;
  0 0       0  
    0          
    0          
    0          
    0          
5359 0         0 while (not /\G \z/oxgc) {
5360 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5361 0         0 elsif (/\G (\\\)) /oxgc) { $q_string .= $1; }
  0         0  
5362             elsif (/\G (\\\() /oxgc) { $q_string .= $1; }
5363 0 0       0 elsif (/\G (\() /oxgc) { $q_string .= $1; $nest++; }
  0         0  
5364 0         0 elsif (/\G (\)) /oxgc) {
5365             if (--$nest == 0) { return $e . e_q($ope,'(',')',$q_string); }
5366 0         0 else { $q_string .= $1; }
5367             }
5368 0         0 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5369             }
5370             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5371             }
5372              
5373 0         0 # elsif (/\G (\{) ((?:\\\}|\\\\|$q_brace)*?) (\}) /oxgc) { return $e . e_q($ope,$1,$3,$2); } # q { }
5374 521         898 elsif (/\G (\{) /oxgc) { # q { }
5375 521         919 my $q_string = '';
5376 521 50       1418 local $nest = 1;
  8128 50       42560  
    50          
    100          
    100          
    50          
5377 0         0 while (not /\G \z/oxgc) {
5378 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5379 0         0 elsif (/\G (\\\}) /oxgc) { $q_string .= $1; }
  114         175  
5380             elsif (/\G (\\\{) /oxgc) { $q_string .= $1; }
5381 114 100       206 elsif (/\G (\{) /oxgc) { $q_string .= $1; $nest++; }
  635         1394  
5382 521         1545 elsif (/\G (\}) /oxgc) {
5383             if (--$nest == 0) { return $e . e_q($ope,'{','}',$q_string); }
5384 114         276 else { $q_string .= $1; }
5385             }
5386 7379         15074 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5387             }
5388             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5389             }
5390              
5391 0         0 # elsif (/\G (\[) ((?:\\\]|\\\\|$q_bracket)*?) (\]) /oxgc) { return $e . e_q($ope,$1,$3,$2); } # q [ ]
5392 0         0 elsif (/\G (\[) /oxgc) { # q [ ]
5393 0         0 my $q_string = '';
5394 0 0       0 local $nest = 1;
  0 0       0  
    0          
    0          
    0          
    0          
5395 0         0 while (not /\G \z/oxgc) {
5396 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5397 0         0 elsif (/\G (\\\]) /oxgc) { $q_string .= $1; }
  0         0  
5398             elsif (/\G (\\\[) /oxgc) { $q_string .= $1; }
5399 0 0       0 elsif (/\G (\[) /oxgc) { $q_string .= $1; $nest++; }
  0         0  
5400 0         0 elsif (/\G (\]) /oxgc) {
5401             if (--$nest == 0) { return $e . e_q($ope,'[',']',$q_string); }
5402 0         0 else { $q_string .= $1; }
5403             }
5404 0         0 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5405             }
5406             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5407             }
5408              
5409 0         0 # elsif (/\G (\<) ((?:\\\>|\\\\|$q_angle)*?) (\>) /oxgc) { return $e . e_q($ope,$1,$3,$2); } # q < >
5410 5         11 elsif (/\G (\<) /oxgc) { # q < >
5411 5         11 my $q_string = '';
5412 5 50       19 local $nest = 1;
  82 50       511  
    50          
    50          
    100          
    50          
5413 0         0 while (not /\G \z/oxgc) {
5414 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5415 0         0 elsif (/\G (\\\>) /oxgc) { $q_string .= $1; }
  0         0  
5416             elsif (/\G (\\\<) /oxgc) { $q_string .= $1; }
5417 0 50       0 elsif (/\G (\<) /oxgc) { $q_string .= $1; $nest++; }
  5         15  
5418 5         16 elsif (/\G (\>) /oxgc) {
5419             if (--$nest == 0) { return $e . e_q($ope,'<','>',$q_string); }
5420 0         0 else { $q_string .= $1; }
5421             }
5422 77         160 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5423             }
5424             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5425             }
5426              
5427 0         0 # elsif (/\G (\S) ((?:\\\1|\\\\|$q_char)*?) (\1) /oxgc) { return $e . e_q($ope,$1,$3,$2); } # q * *
5428 1         3 elsif (/\G (\S) /oxgc) { # q * *
5429 1         2 my $delimiter = $1;
5430 1 50       4 my $q_string = '';
  14 50       96  
    100          
    50          
5431 0         0 while (not /\G \z/oxgc) {
5432 0         0 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5433 1         4 elsif (/\G (\\\Q$delimiter\E) /oxgc) { $q_string .= $1; }
5434             elsif (/\G (\Q$delimiter\E) /oxgc) { return $e . e_q($ope,$delimiter,$delimiter,$q_string); }
5435 13         26 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5436             }
5437             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5438 0         0 }
5439             }
5440             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5441             }
5442             }
5443              
5444 0         0 # m//
5445 269 50       614 elsif (/\G \b (m) \b /oxgc) {
5446 269         2769 my $ope = $1;
5447             if (/\G (\#) ((?:$qq_char)*?) (\#) ([cgimosxpadlunbB]*) /oxgc) { # m# #
5448             return e_qr($ope,$1,$3,$2,$4);
5449 0         0 }
5450 269         457 else {
5451 269 50       759 my $e = '';
  269 50       29338  
    50          
    50          
    50          
    100          
    100          
    50          
    50          
5452 0         0 while (not /\G \z/oxgc) {
5453 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5454 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m ( )
5455 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m { }
5456 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m [ ]
5457 18         62 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m < >
5458 13         48 elsif (/\G (\?) ((?:$qq_char)*?) (\?) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m ? ?
5459 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr_q($ope,$1, $3, $2,$4); } # m ' '
5460             elsif (/\G ([*\-:\\^|]) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,'{','}',$2,$4); } # m | | --> m { }
5461 238         871 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { return $e . e_qr ($ope,$1, $3, $2,$4); } # m * *
5462             }
5463             die __FILE__, ": Search pattern not terminated\n";
5464             }
5465             }
5466              
5467             # s///
5468              
5469             # about [cegimosxpradlunbB]* (/cg modifier)
5470             #
5471             # P.67 Pattern-Matching Operators
5472             # of ISBN 0-596-00241-6 Perl in a Nutshell, Second Edition.
5473 0         0  
5474             elsif (/\G \b (s) \b /oxgc) {
5475             my $ope = $1;
5476 132 100       358  
5477 132         6734 # $1 $2 $3 $4 $5 $6
5478             if (/\G (\#) ((?:$qq_char)*?) (\#) ((?:$qq_char)*?) (\#) ([cegimosxpradlunbB]*) /oxgc) { # s# # #
5479             return e_sub($sub_variable,$1,$2,$3,$3,$4,$5,$6);
5480 1         6 }
5481 131         333 else {
5482 131 50       447 my $e = '';
  131 50       50041  
    50          
    50          
    50          
    100          
    100          
    50          
    50          
5483             while (not /\G \z/oxgc) {
5484 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5485 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) /oxgc) {
5486 0 0       0 my @s = ($1,$2,$3);
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
5487             while (not /\G \z/oxgc) {
5488 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5489 0         0 # $1 $2 $3 $4
5490 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5491 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5492 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5493 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5494 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5495 0         0 elsif (/\G (\$) ((?:$qq_char)*?) (\$) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5496 0         0 elsif (/\G (\:) ((?:$qq_char)*?) (\:) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5497             elsif (/\G (\@) ((?:$qq_char)*?) (\@) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5498 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5499             }
5500             die __FILE__, ": Substitution replacement not terminated\n";
5501 0         0 }
5502 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) {
5503 0 0       0 my @s = ($1,$2,$3);
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
5504             while (not /\G \z/oxgc) {
5505 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5506 0         0 # $1 $2 $3 $4
5507 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5508 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5509 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5510 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5511 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5512 0         0 elsif (/\G (\$) ((?:$qq_char)*?) (\$) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5513 0         0 elsif (/\G (\:) ((?:$qq_char)*?) (\:) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5514             elsif (/\G (\@) ((?:$qq_char)*?) (\@) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5515 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5516             }
5517             die __FILE__, ": Substitution replacement not terminated\n";
5518 0         0 }
5519 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) {
5520 0 0       0 my @s = ($1,$2,$3);
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
5521             while (not /\G \z/oxgc) {
5522 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5523 0         0 # $1 $2 $3 $4
5524 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5525 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5526 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5527 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5528 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5529             elsif (/\G (\$) ((?:$qq_char)*?) (\$) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5530 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5531             }
5532             die __FILE__, ": Substitution replacement not terminated\n";
5533 0         0 }
5534 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) {
5535 0 0       0 my @s = ($1,$2,$3);
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
5536             while (not /\G \z/oxgc) {
5537 0         0 if (/\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
5538 0         0 # $1 $2 $3 $4
5539 0         0 elsif (/\G (\() ((?:$qq_paren)*?) (\)) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5540 0         0 elsif (/\G (\{) ((?:$qq_brace)*?) (\}) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5541 0         0 elsif (/\G (\[) ((?:$qq_bracket)*?) (\]) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5542 0         0 elsif (/\G (\<) ((?:$qq_angle)*?) (\>) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5543 0         0 elsif (/\G (\') ((?:$qq_char)*?) (\') ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5544 0         0 elsif (/\G (\$) ((?:$qq_char)*?) (\$) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5545 0         0 elsif (/\G (\:) ((?:$qq_char)*?) (\:) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5546             elsif (/\G (\@) ((?:$qq_char)*?) (\@) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5547 0         0 elsif (/\G (\S) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) { return e_sub($sub_variable,@s,$1,$2,$3,$4); }
5548             }
5549             die __FILE__, ": Substitution replacement not terminated\n";
5550             }
5551 0         0 # $1 $2 $3 $4 $5 $6
5552             elsif (/\G (\') ((?:$qq_char)*?) (\') ((?:$qq_char)*?) (\') ([cegimosxpradlunbB]*) /oxgc) {
5553             return e_sub($sub_variable,$1,$2,$3,$3,$4,$5,$6);
5554             }
5555 22         62 # $1 $2 $3 $4 $5 $6
5556             elsif (/\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) {
5557             return e_sub($sub_variable,'{',$2,'}','{',$4,'}',$6); # s | | | --> s { } { }
5558             }
5559 2         15 # $1 $2 $3 $4 $5 $6
5560             elsif (/\G (\$) ((?:$qq_char)*?) (\1) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) {
5561             return e_sub($sub_variable,$1,$2,$3,$3,$4,$5,$6);
5562             }
5563 0         0 # $1 $2 $3 $4 $5 $6
5564             elsif (/\G (\S) ((?:$qq_char)*?) (\1) ((?:$qq_char)*?) (\1) ([cegimosxpradlunbB]*) /oxgc) {
5565             return e_sub($sub_variable,$1,$2,$3,$3,$4,$5,$6);
5566 107         567 }
5567             }
5568             die __FILE__, ": Substitution pattern not terminated\n";
5569             }
5570             }
5571 0         0  
5572 0         0 # require ignore module
5573 0         0 elsif (/\G \b require ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [#\n]) /oxmsgc) { return "# require$1$2"; }
5574             elsif (/\G \b require ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [^\x80-\xFF#]) /oxmsgc) { return "# require$1\n$2"; }
5575             elsif (/\G \b require ((?>\s+) (?:$ignore_modules)) \b /oxmsgc) { return "# require$1"; }
5576 0         0  
5577 43         344 # use strict; --> use strict; no strict qw(refs);
5578 0         0 elsif (/\G \b use ((?>\s+) strict .*? ;) ([ \t]* [#\n]) /oxmsgc) { return "use$1 no strict qw(refs);$2"; }
5579             elsif (/\G \b use ((?>\s+) strict .*? ;) ([ \t]* [^\x80-\xFF#]) /oxmsgc) { return "use$1 no strict qw(refs);\n$2"; }
5580             elsif (/\G \b use ((?>\s+) strict) \b /oxmsgc) { return "use$1; no strict qw(refs)"; }
5581              
5582 0 50 33     0 # use 5.12.0; --> use 5.12.0; no strict qw(refs);
      33        
5583 3         41 elsif (/\G \b use (?>\s+) ((?>([1-9][0-9_]*)(?:\.([0-9_]+))*)) (?>\s*) ; /oxmsgc) {
5584             if (($2 >= 6) or (($2 == 5) and ($3 ge '012'))) {
5585             return "use $1; no strict qw(refs);";
5586 0         0 }
5587             else {
5588             return "use $1;";
5589             }
5590 3 0 0     21 }
      0        
5591 0         0 elsif (/\G \b use (?>\s+) ((?>v([0-9][0-9_]*)(?:\.([0-9_]+))*)) (?>\s*) ; /oxmsgc) {
5592             if (($2 >= 6) or (($2 == 5) and ($3 >= 12))) {
5593             return "use $1; no strict qw(refs);";
5594 0         0 }
5595             else {
5596             return "use $1;";
5597             }
5598             }
5599 0         0  
5600 2         12 # ignore use module
5601 0         0 elsif (/\G \b use ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [#\n]) /oxmsgc) { return "# use$1$2"; }
5602             elsif (/\G \b use ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [^\x80-\xFF#]) /oxmsgc) { return "# use$1\n$2"; }
5603             elsif (/\G \b use ((?>\s+) (?:$ignore_modules)) \b /oxmsgc) { return "# use$1"; }
5604 0         0  
5605 0         0 # ignore no module
5606 0         0 elsif (/\G \b no ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [#\n]) /oxmsgc) { return "# no$1$2"; }
5607             elsif (/\G \b no ((?>\s+) (?:$ignore_modules) .*? ;) ([ \t]* [^\x80-\xFF#]) /oxmsgc) { return "# no$1\n$2"; }
5608             elsif (/\G \b no ((?>\s+) (?:$ignore_modules)) \b /oxmsgc) { return "# no$1"; }
5609 0         0  
5610             # use else
5611             elsif (/\G \b use \b /oxmsgc) { return "use"; }
5612 0         0  
5613             # use else
5614             elsif (/\G \b no \b /oxmsgc) { return "no"; }
5615              
5616 2         10 # ''
5617 1589         3015 elsif (/\G (?
5618 1589 100       3932 my $q_string = '';
  10558 100       57391  
    100          
    50          
5619 4         11 while (not /\G \z/oxgc) {
5620 48         89 if (/\G (\\\\) /oxgc) { $q_string .= $1; }
5621 1589         3593 elsif (/\G (\\\') /oxgc) { $q_string .= $1; }
5622             elsif (/\G \' /oxgc) { return e_q('', "'","'",$q_string); }
5623 8917         17717 elsif (/\G ($q_char) /oxgc) { $q_string .= $1; }
5624             }
5625             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5626             }
5627              
5628 0         0 # ""
5629 5587         10500 elsif (/\G (\") /oxgc) {
5630 5587 100       13091 my $qq_string = '';
  86921 100       265726  
    100          
    50          
5631 109         256 while (not /\G \z/oxgc) {
5632 12         23 if (/\G (\\\\) /oxgc) { $qq_string .= $1; }
5633 5587         11623 elsif (/\G (\\\") /oxgc) { $qq_string .= $1; }
5634             elsif (/\G \" /oxgc) { return e_qq('', '"','"',$qq_string); }
5635 81213         153466 elsif (/\G ($q_char) /oxgc) { $qq_string .= $1; }
5636             }
5637             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5638             }
5639              
5640 0         0 # ``
5641 1         3 elsif (/\G (\`) /oxgc) {
5642 1 50       5 my $qx_string = '';
  19 50       108  
    100          
    50          
5643 0         0 while (not /\G \z/oxgc) {
5644 0         0 if (/\G (\\\\) /oxgc) { $qx_string .= $1; }
5645 1         4 elsif (/\G (\\\`) /oxgc) { $qx_string .= $1; }
5646             elsif (/\G \` /oxgc) { return e_qq('', '`','`',$qx_string); }
5647 18         36 elsif (/\G ($q_char) /oxgc) { $qx_string .= $1; }
5648             }
5649             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
5650             }
5651              
5652 0         0 # // --- not divide operator (num / num), not defined-or
5653 1069         2632 elsif (($slash eq 'm//') and /\G (\/) /oxgc) {
5654 1069 100       3625 my $regexp = '';
  10235 50       39629  
    100          
    50          
5655 1         4 while (not /\G \z/oxgc) {
5656 0         0 if (/\G (\\\\) /oxgc) { $regexp .= $1; }
5657 1069         3451 elsif (/\G (\\\/) /oxgc) { $regexp .= $1; }
5658             elsif (/\G \/ ([cgimosxpadlunbB]*) /oxgc) { return e_qr('', '/','/',$regexp,$1); }
5659 9165         18205 elsif (/\G ($q_char) /oxgc) { $regexp .= $1; }
5660             }
5661             die __FILE__, ": Search pattern not terminated\n";
5662             }
5663              
5664 0         0 # ?? --- not conditional operator (condition ? then : else)
5665 18         34 elsif (($slash eq 'm//') and /\G (\?) /oxgc) {
5666 18 50       56 my $regexp = '';
  82 50       448  
    100          
    50          
5667 0         0 while (not /\G \z/oxgc) {
5668 0         0 if (/\G (\\\\) /oxgc) { $regexp .= $1; }
5669 18         49 elsif (/\G (\\\?) /oxgc) { $regexp .= $1; }
5670             elsif (/\G \? ([cgimosxpadlunbB]*) /oxgc) { return e_qr('m','?','?',$regexp,$1); }
5671 64         142 elsif (/\G ($q_char) /oxgc) { $regexp .= $1; }
5672             }
5673             die __FILE__, ": Search pattern not terminated\n";
5674             }
5675 0         0  
  0         0  
5676             # <<>> (a safer ARGV)
5677             elsif (/\G ( <<>> ) /oxgc) { $slash = 'm//'; return $1; }
5678 0         0  
  0         0  
5679             # << (bit shift) --- not here document
5680             elsif (/\G ( << (?>\s*) ) (?= [0-9\$\@\&] ) /oxgc) { $slash = 'm//'; return $1; }
5681              
5682 0         0 # <<~'HEREDOC'
5683 6         11 elsif (/\G ( <<~ [\t ]* '([a-zA-Z_0-9]*)' ) /oxgc) {
5684 6         11 $slash = 'm//';
5685             my $here_quote = $1;
5686             my $delimiter = $2;
5687 6 50       8  
5688 6         14 # get here document
5689 6         19 if ($here_script eq '') {
5690             $here_script = CORE::substr $_, pos $_;
5691 6 50       28 $here_script =~ s/.*?\n//oxm;
5692 6         66 }
5693 6         15 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
5694 6         8 my $heredoc = $1;
5695 6         45 my $indent = $2;
5696 6         19 $heredoc =~ s{^$indent}{}msg; # no /ox
5697             push @heredoc, $heredoc . qq{\n$delimiter\n};
5698             push @heredoc_delimiter, qq{\\s*$delimiter};
5699 6         12 }
5700             else {
5701 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5702             }
5703             return qq{<<'$delimiter'};
5704             }
5705              
5706             # <<~\HEREDOC
5707              
5708             # P.66 2.6.6. "Here" Documents
5709             # in Chapter 2: Bits and Pieces
5710             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
5711              
5712             # P.73 "Here" Documents
5713             # in Chapter 2: Bits and Pieces
5714             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
5715 6         23  
5716 3         6 elsif (/\G ( <<~ \\([a-zA-Z_0-9]+) ) /oxgc) {
5717 3         5 $slash = 'm//';
5718             my $here_quote = $1;
5719             my $delimiter = $2;
5720 3 50       7  
5721 3         7 # get here document
5722 3         21 if ($here_script eq '') {
5723             $here_script = CORE::substr $_, pos $_;
5724 3 50       17 $here_script =~ s/.*?\n//oxm;
5725 3         35 }
5726 3         7 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
5727 3         7 my $heredoc = $1;
5728 3         65 my $indent = $2;
5729 3         12 $heredoc =~ s{^$indent}{}msg; # no /ox
5730             push @heredoc, $heredoc . qq{\n$delimiter\n};
5731             push @heredoc_delimiter, qq{\\s*$delimiter};
5732 3         19 }
5733             else {
5734 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5735             }
5736             return qq{<<\\$delimiter};
5737             }
5738              
5739 3         15 # <<~"HEREDOC"
5740 6         10 elsif (/\G ( <<~ [\t ]* "([a-zA-Z_0-9]*)" ) /oxgc) {
5741 6         11 $slash = 'm//';
5742             my $here_quote = $1;
5743             my $delimiter = $2;
5744 6 50       8  
5745 6         12 # get here document
5746 6         34 if ($here_script eq '') {
5747             $here_script = CORE::substr $_, pos $_;
5748 6 50       28 $here_script =~ s/.*?\n//oxm;
5749 6         53 }
5750 6         13 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
5751 6         6 my $heredoc = $1;
5752 6         41 my $indent = $2;
5753 6         17 $heredoc =~ s{^$indent}{}msg; # no /ox
5754             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
5755             push @heredoc_delimiter, qq{\\s*$delimiter};
5756 6         13 }
5757             else {
5758 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5759             }
5760             return qq{<<"$delimiter"};
5761             }
5762              
5763 6         23 # <<~HEREDOC
5764 3         7 elsif (/\G ( <<~ ([a-zA-Z_0-9]+) ) /oxgc) {
5765 3         5 $slash = 'm//';
5766             my $here_quote = $1;
5767             my $delimiter = $2;
5768 3 50       5  
5769 3         8 # get here document
5770 3         12 if ($here_script eq '') {
5771             $here_script = CORE::substr $_, pos $_;
5772 3 50       13 $here_script =~ s/.*?\n//oxm;
5773 3         34 }
5774 3         7 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
5775 3         4 my $heredoc = $1;
5776 3         33 my $indent = $2;
5777 3         10 $heredoc =~ s{^$indent}{}msg; # no /ox
5778             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
5779             push @heredoc_delimiter, qq{\\s*$delimiter};
5780 3         7 }
5781             else {
5782 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5783             }
5784             return qq{<<$delimiter};
5785             }
5786              
5787 3         11 # <<~`HEREDOC`
5788 6         12 elsif (/\G ( <<~ [\t ]* `([a-zA-Z_0-9]*)` ) /oxgc) {
5789 6         19 $slash = 'm//';
5790             my $here_quote = $1;
5791             my $delimiter = $2;
5792 6 50       9  
5793 6         14 # get here document
5794 6         22 if ($here_script eq '') {
5795             $here_script = CORE::substr $_, pos $_;
5796 6 50       28 $here_script =~ s/.*?\n//oxm;
5797 6         61 }
5798 6         13 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
5799 6         8 my $heredoc = $1;
5800 6         56 my $indent = $2;
5801 6         16 $heredoc =~ s{^$indent}{}msg; # no /ox
5802             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
5803             push @heredoc_delimiter, qq{\\s*$delimiter};
5804 6         14 }
5805             else {
5806 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5807             }
5808             return qq{<<`$delimiter`};
5809             }
5810              
5811 6         21 # <<'HEREDOC'
5812 80         157 elsif (/\G ( << '([a-zA-Z_0-9]*)' ) /oxgc) {
5813 80         153 $slash = 'm//';
5814             my $here_quote = $1;
5815             my $delimiter = $2;
5816 80 100       128  
5817 80         151 # get here document
5818 77         390 if ($here_script eq '') {
5819             $here_script = CORE::substr $_, pos $_;
5820 77 50       377 $here_script =~ s/.*?\n//oxm;
5821 80         590 }
5822 80         260 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
5823             push @heredoc, $1 . qq{\n$delimiter\n};
5824             push @heredoc_delimiter, $delimiter;
5825 80         133 }
5826             else {
5827 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5828             }
5829             return $here_quote;
5830             }
5831              
5832             # <<\HEREDOC
5833              
5834             # P.66 2.6.6. "Here" Documents
5835             # in Chapter 2: Bits and Pieces
5836             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
5837              
5838             # P.73 "Here" Documents
5839             # in Chapter 2: Bits and Pieces
5840             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
5841 80         313  
5842 2         18 elsif (/\G ( << \\([a-zA-Z_0-9]+) ) /oxgc) {
5843 2         6 $slash = 'm//';
5844             my $here_quote = $1;
5845             my $delimiter = $2;
5846 2 100       3  
5847 2         6 # get here document
5848 1         6 if ($here_script eq '') {
5849             $here_script = CORE::substr $_, pos $_;
5850 1 50       6 $here_script =~ s/.*?\n//oxm;
5851 2         38 }
5852 2         10 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
5853             push @heredoc, $1 . qq{\n$delimiter\n};
5854             push @heredoc_delimiter, $delimiter;
5855 2         5 }
5856             else {
5857 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5858             }
5859             return $here_quote;
5860             }
5861              
5862 2         8 # <<"HEREDOC"
5863 39         98 elsif (/\G ( << "([a-zA-Z_0-9]*)" ) /oxgc) {
5864 39         91 $slash = 'm//';
5865             my $here_quote = $1;
5866             my $delimiter = $2;
5867 39 100       69  
5868 39         97 # get here document
5869 38         226 if ($here_script eq '') {
5870             $here_script = CORE::substr $_, pos $_;
5871 38 50       252 $here_script =~ s/.*?\n//oxm;
5872 39         450 }
5873 39         135 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
5874             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
5875             push @heredoc_delimiter, $delimiter;
5876 39         90 }
5877             else {
5878 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5879             }
5880             return $here_quote;
5881             }
5882              
5883 39         156 # <
5884 54         157 elsif (/\G ( << ([a-zA-Z_0-9]+) ) /oxgc) {
5885 54         116 $slash = 'm//';
5886             my $here_quote = $1;
5887             my $delimiter = $2;
5888 54 100       99  
5889 54         149 # get here document
5890 51         305 if ($here_script eq '') {
5891             $here_script = CORE::substr $_, pos $_;
5892 51 50       402 $here_script =~ s/.*?\n//oxm;
5893 54         743 }
5894 54         190 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
5895             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
5896             push @heredoc_delimiter, $delimiter;
5897 54         130 }
5898             else {
5899 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5900             }
5901             return $here_quote;
5902             }
5903              
5904 54         219 # <<`HEREDOC`
5905 0         0 elsif (/\G ( << `([a-zA-Z_0-9]*)` ) /oxgc) {
5906 0         0 $slash = 'm//';
5907             my $here_quote = $1;
5908             my $delimiter = $2;
5909 0 0       0  
5910 0         0 # get here document
5911 0         0 if ($here_script eq '') {
5912             $here_script = CORE::substr $_, pos $_;
5913 0 0       0 $here_script =~ s/.*?\n//oxm;
5914 0         0 }
5915 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
5916             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
5917             push @heredoc_delimiter, $delimiter;
5918 0         0 }
5919             else {
5920 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
5921             }
5922             return $here_quote;
5923             }
5924              
5925 0         0 # <<= <=> <= < operator
5926             elsif (/\G ( <<= | <=> | <= | < ) (?= (?>\s*) [A-Za-z_0-9'"`\$\@\&\*\(\+\-] )/oxgc) {
5927             return $1;
5928             }
5929              
5930 12         69 #
5931             elsif (/\G (<[\$]?[A-Za-z_][A-Za-z_0-9]*>) /oxgc) {
5932             return $1;
5933             }
5934              
5935             # --- glob
5936              
5937             # avoid "Error: Runtime exception" of perl version 5.005_03
5938 0         0  
5939             elsif (/\G < ((?:[^\x80-\xFF>\0\a\e\f\n\r\t]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF])+?) > /oxgc) {
5940             return 'Eutf2::glob("' . $1 . '")';
5941             }
5942 0         0  
5943             # __DATA__
5944             elsif (/\G ^ ( __DATA__ \n .*) \z /oxmsgc) { return $1; }
5945 0         0  
5946             # __END__
5947             elsif (/\G ^ ( __END__ \n .*) \z /oxmsgc) { return $1; }
5948              
5949             # \cD Control-D
5950              
5951             # P.68 2.6.8. Other Literal Tokens
5952             # in Chapter 2: Bits and Pieces
5953             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
5954              
5955             # P.76 Other Literal Tokens
5956             # in Chapter 2: Bits and Pieces
5957 306         2325 # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
5958              
5959             elsif (/\G ( \cD .*) \z /oxmsgc) { return $1; }
5960 0         0  
5961             # \cZ Control-Z
5962             elsif (/\G ( \cZ .*) \z /oxmsgc) { return $1; }
5963              
5964             # any operator before div
5965             elsif (/\G (
5966             -- | \+\+ |
5967 0         0 [\)\}\]]
  8556         16312  
5968              
5969             ) /oxgc) { $slash = 'div'; return $1; }
5970              
5971             # yada-yada or triple-dot operator
5972             elsif (/\G (
5973 8556         35744 \.\.\.
  7         13  
5974              
5975             ) /oxgc) { $slash = 'm//'; return q{die('Unimplemented')}; }
5976              
5977             # any operator before m//
5978              
5979             # //, //= (defined-or)
5980              
5981             # P.164 Logical Operators
5982             # in Chapter 10: More Control Structures
5983             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
5984              
5985             # P.119 C-Style Logical (Short-Circuit) Operators
5986             # in Chapter 3: Unary and Binary Operators
5987             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
5988              
5989             # (and so on)
5990              
5991             # ~~
5992              
5993             # P.221 The Smart Match Operator
5994             # in Chapter 15: Smart Matching and given-when
5995             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
5996              
5997             # P.112 Smartmatch Operator
5998             # in Chapter 3: Unary and Binary Operators
5999             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
6000              
6001             # (and so on)
6002              
6003             elsif (/\G ((?>
6004              
6005             !~~ | !~ | != | ! |
6006             %= | % |
6007             &&= | && | &= | &\.= | &\. | & |
6008             -= | -> | - |
6009             :(?>\s*)= |
6010             : |
6011             <<>> |
6012             <<= | <=> | <= | < |
6013             == | => | =~ | = |
6014             >>= | >> | >= | > |
6015             \*\*= | \*\* | \*= | \* |
6016             \+= | \+ |
6017             \.\. | \.= | \. |
6018             \/\/= | \/\/ |
6019             \/= | \/ |
6020             \? |
6021             \\ |
6022             \^= | \^\.= | \^\. | \^ |
6023             \b x= |
6024             \|\|= | \|\| | \|= | \|\.= | \|\. | \| |
6025             ~~ | ~\. | ~ |
6026             \b(?: and | cmp | eq | ge | gt | le | lt | ne | not | or | xor | x )\b |
6027             \b(?: print )\b |
6028              
6029 7         25 [,;\(\{\[]
  16324         31201  
6030              
6031             )) /oxgc) { $slash = 'm//'; return $1; }
6032 16324         69258  
  23499         41678  
6033             # other any character
6034             elsif (/\G ($q_char) /oxgc) { $slash = 'div'; return $1; }
6035              
6036 23499         111491 # system error
6037             else {
6038             die __FILE__, ": Oops, this shouldn't happen!\n";
6039             }
6040             }
6041              
6042 0     2512 0 0 # escape UTF-8 string
6043 2512         5696 sub e_string {
6044             my($string) = @_;
6045 2512         3523 my $e_string = '';
6046              
6047             local $slash = 'm//';
6048              
6049             # P.1024 Appendix W.10 Multibyte Processing
6050             # of ISBN 1-56592-224-7 CJKV Information Processing
6051 2512         3391 # (and so on)
6052              
6053             my @char = $string =~ / \G (?>[^\x80-\xFF\\]|\\$q_char|$q_char) /oxmsg;
6054 2512 100 66     66284  
6055 2512 50       11694 # without { ... }
6056 2473         5140 if (not (grep(/\A \{ \z/xms, @char) and grep(/\A \} \z/xms, @char))) {
6057             if ($string !~ /<
6058             return $string;
6059             }
6060             }
6061 2473         5837  
6062 39 50       134 E_STRING_LOOP:
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    50          
    100          
    50          
6063             while ($string !~ /\G \z/oxgc) {
6064             if (0) {
6065             }
6066 293         29384  
6067 0         0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> @{[Eutf2::PREMATCH()]}
6068 0         0 elsif ($string =~ /\G ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH \b | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) /oxmsgc) {
6069             $e_string .= q{Eutf2::PREMATCH()};
6070             $slash = 'div';
6071             }
6072              
6073 0         0 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> @{[Eutf2::MATCH()]}
6074 0         0 elsif ($string =~ /\G ( \$& | \$\{&\} | \$ (?>\s*) MATCH \b | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) /oxmsgc) {
6075             $e_string .= q{Eutf2::MATCH()};
6076             $slash = 'div';
6077             }
6078              
6079 0         0 # $', ${'} --> $', ${'}
6080 0         0 elsif ($string =~ /\G ( \$' | \$\{'\} ) /oxmsgc) {
6081             $e_string .= $1;
6082             $slash = 'div';
6083             }
6084              
6085 0         0 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> @{[Eutf2::POSTMATCH()]}
6086 0         0 elsif ($string =~ /\G ( \$ (?>\s*) POSTMATCH \b | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) /oxmsgc) {
6087             $e_string .= q{Eutf2::POSTMATCH()};
6088             $slash = 'div';
6089             }
6090              
6091 0         0 # bareword
6092 0         0 elsif ($string =~ /\G ( \{ (?>\s*) (?: tr | index | rindex | reverse ) (?>\s*) \} ) /oxmsgc) {
6093             $e_string .= $1;
6094             $slash = 'div';
6095             }
6096              
6097 0         0 # $0 --> $0
6098 0         0 elsif ($string =~ /\G ( \$ 0 ) /oxmsgc) {
6099             $e_string .= $1;
6100             $slash = 'div';
6101 0         0 }
6102 0         0 elsif ($string =~ /\G ( \$ \{ (?>\s*) 0 (?>\s*) \} ) /oxmsgc) {
6103             $e_string .= $1;
6104             $slash = 'div';
6105             }
6106              
6107 0         0 # $$ --> $$
6108 0         0 elsif ($string =~ /\G ( \$ \$ ) (?![\w\{]) /oxmsgc) {
6109             $e_string .= $1;
6110             $slash = 'div';
6111             }
6112              
6113             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
6114 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
6115 0         0 elsif ($string =~ /\G \$ ((?>[1-9][0-9]*)) /oxmsgc) {
6116             $e_string .= e_capture($1);
6117             $slash = 'div';
6118 0         0 }
6119 0         0 elsif ($string =~ /\G \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} /oxmsgc) {
6120             $e_string .= e_capture($1);
6121             $slash = 'div';
6122             }
6123              
6124 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
6125 0         0 elsif ($string =~ /\G \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ .+? \] ) /oxmsgc) {
6126             $e_string .= e_capture($1.'->'.$2);
6127             $slash = 'div';
6128             }
6129              
6130 0         0 # $$foo{ ... } --> $ $foo->{ ... }
6131 0         0 elsif ($string =~ /\G \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ .+? \} ) /oxmsgc) {
6132             $e_string .= e_capture($1.'->'.$2);
6133             $slash = 'div';
6134             }
6135              
6136 0         0 # $$foo
6137 0         0 elsif ($string =~ /\G \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) /oxmsgc) {
6138             $e_string .= e_capture($1);
6139             $slash = 'div';
6140             }
6141              
6142 0         0 # ${ foo }
6143 0         0 elsif ($string =~ /\G \$ (?>\s*) \{ ((?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* )) \} /oxmsgc) {
6144             $e_string .= '${' . $1 . '}';
6145             $slash = 'div';
6146             }
6147              
6148 0         0 # ${ ... }
6149 3         10 elsif ($string =~ /\G \$ (?>\s*) \{ (?>\s*) ( $qq_brace ) (?>\s*) \} /oxmsgc) {
6150             $e_string .= e_capture($1);
6151             $slash = 'div';
6152             }
6153              
6154             # variable or function
6155 3         18 # $ @ % & * $ #
6156 1         4 elsif ($string =~ /\G ( (?: [\$\@\%\&\*] | \$\# | -> | \b sub \b) (?>\s*) (?: split | chop | index | rindex | lc | uc | fc | chr | ord | reverse | getc | tr | y | q | qq | qx | qw | m | s | qr | glob | lstat | opendir | stat | unlink | chdir ) ) \b /oxmsgc) {
6157             $e_string .= $1;
6158             $slash = 'div';
6159             }
6160             # $ $ $ $ $ $ $ $ $ $ $ $ $ $
6161 1         6 # $ @ # \ ' " / ? ( ) [ ] < >
6162 0         0 elsif ($string =~ /\G ( \$[\$\@\#\\\'\"\/\?\(\)\[\]\<\>] ) /oxmsgc) {
6163             $e_string .= $1;
6164             $slash = 'div';
6165             }
6166 0         0  
  0         0  
6167 0         0 # subroutines of package Eutf2
  0         0  
6168 0         0 elsif ($string =~ /\G \b (CORE:: | ->(>?\s*) (?: atan2 | [a-z]{2,})) \b /oxgc) { $e_string .= $1; $slash = 'm//'; }
  0         0  
6169 0         0 elsif ($string =~ /\G \b Char::eval (?= (?>\s*) \{ ) /oxgc) { $e_string .= 'eval'; $slash = 'm//'; }
  0         0  
6170 0         0 elsif ($string =~ /\G \b UTF2::eval (?= (?>\s*) \{ ) /oxgc) { $e_string .= 'eval'; $slash = 'm//'; }
  0         0  
6171 0         0 elsif ($string =~ /\G \b Char::eval \b /oxgc) { $e_string .= 'eval Char::escape'; $slash = 'm//'; }
  0         0  
6172 0         0 elsif ($string =~ /\G \b UTF2::eval \b /oxgc) { $e_string .= 'eval UTF2::escape'; $slash = 'm//'; }
  0         0  
6173 0         0 elsif ($string =~ /\G \b bytes::substr \b /oxgc) { $e_string .= 'substr'; $slash = 'm//'; }
  0         0  
6174 0         0 elsif ($string =~ /\G \b chop \b /oxgc) { $e_string .= 'Eutf2::chop'; $slash = 'm//'; }
  0         0  
6175 0         0 elsif ($string =~ /\G \b bytes::index \b /oxgc) { $e_string .= 'index'; $slash = 'm//'; }
  0         0  
6176 0         0 elsif ($string =~ /\G \b Char::index \b /oxgc) { $e_string .= 'Char::index'; $slash = 'm//'; }
  0         0  
6177 0         0 elsif ($string =~ /\G \b UTF2::index \b /oxgc) { $e_string .= 'UTF2::index'; $slash = 'm//'; }
  0         0  
6178 0         0 elsif ($string =~ /\G \b index \b /oxgc) { $e_string .= 'Eutf2::index'; $slash = 'm//'; }
  0         0  
6179 0         0 elsif ($string =~ /\G \b bytes::rindex \b /oxgc) { $e_string .= 'rindex'; $slash = 'm//'; }
  0         0  
6180 0         0 elsif ($string =~ /\G \b Char::rindex \b /oxgc) { $e_string .= 'Char::rindex'; $slash = 'm//'; }
  0         0  
6181 0         0 elsif ($string =~ /\G \b UTF2::rindex \b /oxgc) { $e_string .= 'UTF2::rindex'; $slash = 'm//'; }
  0         0  
6182 0         0 elsif ($string =~ /\G \b rindex \b /oxgc) { $e_string .= 'Eutf2::rindex'; $slash = 'm//'; }
  0         0  
6183 0         0 elsif ($string =~ /\G \b lc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::lc'; $slash = 'm//'; }
  0         0  
6184 0         0 elsif ($string =~ /\G \b lcfirst (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::lcfirst'; $slash = 'm//'; }
  0         0  
6185 0         0 elsif ($string =~ /\G \b uc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::uc'; $slash = 'm//'; }
  0         0  
6186             elsif ($string =~ /\G \b ucfirst (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::ucfirst'; $slash = 'm//'; }
6187             elsif ($string =~ /\G \b fc (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::fc'; $slash = 'm//'; }
6188 0         0  
  0         0  
6189 0         0 # "-s '' ..." means file test "-s 'filename' ..." (not means "- s/// ...")
  0         0  
6190 0         0 elsif ($string =~ /\G -s (?>\s*) (\") ((?:$qq_char)+?) (\") /oxgc) { $e_string .= '-s ' . e_qq('', $1,$3,$2); $slash = 'm//'; }
  0         0  
6191 0         0 elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\#) ((?:$qq_char)+?) (\#) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
  0         0  
6192 0         0 elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\() ((?:$qq_paren)+?) (\)) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
  0         0  
6193 0         0 elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\{) ((?:$qq_brace)+?) (\}) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
  0         0  
6194 0         0 elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\[) ((?:$qq_bracket)+?) (\]) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
  0         0  
6195             elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\<) ((?:$qq_angle)+?) (\>) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
6196 0         0 elsif ($string =~ /\G -s (?>\s+) qq (?>\s*) (\S) ((?:$qq_char)+?) (\1) /oxgc) { $e_string .= '-s ' . e_qq('qq',$1,$3,$2); $slash = 'm//'; }
  0         0  
6197 0         0  
  0         0  
6198 0         0 elsif ($string =~ /\G -s (?>\s*) (\') ((?:\\\'|\\\\|$q_char)+?) (\') /oxgc) { $e_string .= '-s ' . e_q ('', $1,$3,$2); $slash = 'm//'; }
  0         0  
6199 0         0 elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\#) ((?:\\\#|\\\\|$q_char)+?) (\#) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
  0         0  
6200 0         0 elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\() ((?:\\\)|\\\\|$q_paren)+?) (\)) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
  0         0  
6201 0         0 elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\{) ((?:\\\}|\\\\|$q_brace)+?) (\}) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
  0         0  
6202 0         0 elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\[) ((?:\\\]|\\\\|$q_bracket)+?) (\]) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
  0         0  
6203             elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\<) ((?:\\\>|\\\\|$q_angle)+?) (\>) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
6204             elsif ($string =~ /\G -s (?>\s+) q (?>\s*) (\S) ((?:\\\1|\\\\|$q_char)+?) (\1) /oxgc) { $e_string .= '-s ' . e_q ('q', $1,$3,$2); $slash = 'm//'; }
6205 0         0  
  0         0  
6206 0         0 elsif ($string =~ /\G -s (?>\s*) (\$ (?> \w+ (?: ::\w+)*) (?: (?: ->)? (?: [\$\@\%\&\*]\* | \$\#\* | \( (?:$qq_paren)*? \) | [\@\%\*]? \{ (?:$qq_brace)+? \} | [\@\%]? \[ (?:$qq_bracket)+? \] ))*) /oxgc)
  0         0  
6207 0         0 { $e_string .= "-s $1"; $slash = 'm//'; }
  0         0  
6208 0         0 elsif ($string =~ /\G -s (?>\s*) \( ((?:$qq_paren)*?) \) /oxgc) { $e_string .= "-s ($1)"; $slash = 'm//'; }
  0         0  
6209             elsif ($string =~ /\G -s (?= (?>\s+) [a-z]+) /oxgc) { $e_string .= '-s'; $slash = 'm//'; }
6210 0         0 elsif ($string =~ /\G -s (?>\s+) ((?>\w+)) /oxgc) { $e_string .= "-s $1"; $slash = 'm//'; }
  0         0  
6211 0         0  
  0         0  
6212 0         0 elsif ($string =~ /\G \b bytes::length (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'length'; $slash = 'm//'; }
  0         0  
6213 0         0 elsif ($string =~ /\G \b bytes::chr (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'chr'; $slash = 'm//'; }
  0         0  
6214 0         0 elsif ($string =~ /\G \b chr (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::chr'; $slash = 'm//'; }
  0         0  
6215 0         0 elsif ($string =~ /\G \b bytes::ord (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'ord'; $slash = 'div'; }
  0         0  
6216 0         0 elsif ($string =~ /\G \b ord (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= $function_ord; $slash = 'div'; }
  0         0  
6217 0         0 elsif ($string =~ /\G \b glob (?= (?>\s+)[A-Za-z_]|(?>\s*)['"`\$\@\&\*\(]) /oxgc) { $e_string .= 'Eutf2::glob'; $slash = 'm//'; }
  0         0  
6218 0         0 elsif ($string =~ /\G \b lc \b /oxgc) { $e_string .= 'Eutf2::lc_'; $slash = 'm//'; }
  0         0  
6219 0         0 elsif ($string =~ /\G \b lcfirst \b /oxgc) { $e_string .= 'Eutf2::lcfirst_'; $slash = 'm//'; }
  0         0  
6220 0         0 elsif ($string =~ /\G \b uc \b /oxgc) { $e_string .= 'Eutf2::uc_'; $slash = 'm//'; }
  0         0  
6221 0         0 elsif ($string =~ /\G \b ucfirst \b /oxgc) { $e_string .= 'Eutf2::ucfirst_'; $slash = 'm//'; }
  0         0  
6222             elsif ($string =~ /\G \b fc \b /oxgc) { $e_string .= 'Eutf2::fc_'; $slash = 'm//'; }
6223 0         0 elsif ($string =~ /\G -s \b /oxgc) { $e_string .= '-s '; $slash = 'm//'; }
  0         0  
6224 0         0  
  0         0  
6225 0         0 elsif ($string =~ /\G \b bytes::length \b /oxgc) { $e_string .= 'length'; $slash = 'm//'; }
  0         0  
6226 0         0 elsif ($string =~ /\G \b bytes::chr \b /oxgc) { $e_string .= 'chr'; $slash = 'm//'; }
  0         0  
6227 0         0 elsif ($string =~ /\G \b chr \b /oxgc) { $e_string .= 'Eutf2::chr_'; $slash = 'm//'; }
  0         0  
6228 0         0 elsif ($string =~ /\G \b bytes::ord \b /oxgc) { $e_string .= 'ord'; $slash = 'div'; }
  0         0  
6229 0         0 elsif ($string =~ /\G \b ord \b /oxgc) { $e_string .= $function_ord_; $slash = 'div'; }
  0         0  
6230 0         0 elsif ($string =~ /\G \b glob \b /oxgc) { $e_string .= 'Eutf2::glob_'; $slash = 'm//'; }
  0         0  
6231             elsif ($string =~ /\G \b reverse \b /oxgc) { $e_string .= $function_reverse; $slash = 'm//'; }
6232             elsif ($string =~ /\G \b getc \b /oxgc) { $e_string .= $function_getc; $slash = 'm//'; }
6233 0         0 # split
6234             elsif ($string =~ /\G \b (split) \b (?! (?>\s*) => ) /oxgc) {
6235 0         0 $slash = 'm//';
6236 0         0  
6237 0         0 my $e = '';
6238             while ($string =~ /\G ( (?>\s+) | \( | \#.* ) /oxgc) {
6239             $e .= $1;
6240             }
6241 0 0       0  
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
    0          
6242             # end of split
6243             if ($string =~ /\G (?= [,;\)\}\]] ) /oxgc) { return 'Eutf2::split' . $e; }
6244 0         0  
  0         0  
6245             # split scalar value
6246             elsif ($string =~ /\G ( [\$\@\&\*] $qq_scalar ) /oxgc) { $e_string .= 'Eutf2::split' . $e . e_string($1); next E_STRING_LOOP; }
6247 0         0  
  0         0  
6248 0         0 # split literal space
  0         0  
6249 0         0 elsif ($string =~ /\G \b qq (\#) [ ] (\#) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {qq$1 $2}; next E_STRING_LOOP; }
  0         0  
6250 0         0 elsif ($string =~ /\G \b qq ((?>\s*)) (\() [ ] (\)) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq{$1qq$2 $3}; next E_STRING_LOOP; }
  0         0  
6251 0         0 elsif ($string =~ /\G \b qq ((?>\s*)) (\{) [ ] (\}) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq{$1qq$2 $3}; next E_STRING_LOOP; }
  0         0  
6252 0         0 elsif ($string =~ /\G \b qq ((?>\s*)) (\[) [ ] (\]) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq{$1qq$2 $3}; next E_STRING_LOOP; }
  0         0  
6253 0         0 elsif ($string =~ /\G \b qq ((?>\s*)) (\<) [ ] (\>) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq{$1qq$2 $3}; next E_STRING_LOOP; }
  0         0  
6254 0         0 elsif ($string =~ /\G \b qq ((?>\s*)) (\S) [ ] (\2) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq{$1qq$2 $3}; next E_STRING_LOOP; }
  0         0  
6255 0         0 elsif ($string =~ /\G \b q (\#) [ ] (\#) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {q$1 $2}; next E_STRING_LOOP; }
  0         0  
6256 0         0 elsif ($string =~ /\G \b q ((?>\s*)) (\() [ ] (\)) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {$1q$2 $3}; next E_STRING_LOOP; }
  0         0  
6257 0         0 elsif ($string =~ /\G \b q ((?>\s*)) (\{) [ ] (\}) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {$1q$2 $3}; next E_STRING_LOOP; }
  0         0  
6258 0         0 elsif ($string =~ /\G \b q ((?>\s*)) (\[) [ ] (\]) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {$1q$2 $3}; next E_STRING_LOOP; }
  0         0  
6259 0         0 elsif ($string =~ /\G \b q ((?>\s*)) (\<) [ ] (\>) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {$1q$2 $3}; next E_STRING_LOOP; }
  0         0  
6260 0         0 elsif ($string =~ /\G \b q ((?>\s*)) (\S) [ ] (\2) /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {$1q$2 $3}; next E_STRING_LOOP; }
  0         0  
6261             elsif ($string =~ /\G ' [ ] ' /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {' '}; next E_STRING_LOOP; }
6262             elsif ($string =~ /\G " [ ] " /oxgc) { $e_string .= 'Eutf2::split' . $e . qq {" "}; next E_STRING_LOOP; }
6263              
6264 0 0       0 # split qq//
  0         0  
  0         0  
6265             elsif ($string =~ /\G \b (qq) \b /oxgc) {
6266 0         0 if ($string =~ /\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq# # --> qr # #
6267 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
6268 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6269 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e_string .= $e . $1; }
  0         0  
6270 0         0 elsif ($string =~ /\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq ( ) --> qr ( )
  0         0  
6271 0         0 elsif ($string =~ /\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq { } --> qr { }
  0         0  
6272 0         0 elsif ($string =~ /\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq [ ] --> qr [ ]
  0         0  
6273 0         0 elsif ($string =~ /\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq < > --> qr < >
  0         0  
6274             elsif ($string =~ /\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) /oxgc) { $e_string .= e_split($e.'qr','{','}',$2,''); next E_STRING_LOOP; } # qq | | --> qr { }
6275 0         0 elsif ($string =~ /\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { $e_string .= e_split($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # qq * * --> qr * *
6276             }
6277             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6278             }
6279             }
6280              
6281 0 0       0 # split qr//
  0         0  
  0         0  
6282             elsif ($string =~ /\G \b (qr) \b /oxgc) {
6283 0         0 if ($string =~ /\G (\#) ((?:$qq_char)*?) (\#) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1,$3,$2,$4); next E_STRING_LOOP; } # qr# #
6284 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
6285 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6286 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e_string .= $e . $1; }
  0         0  
6287 0         0 elsif ($string =~ /\G (\() ((?:$qq_paren)*?) (\)) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr ( )
  0         0  
6288 0         0 elsif ($string =~ /\G (\{) ((?:$qq_brace)*?) (\}) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr { }
  0         0  
6289 0         0 elsif ($string =~ /\G (\[) ((?:$qq_bracket)*?) (\]) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr [ ]
  0         0  
6290 0         0 elsif ($string =~ /\G (\<) ((?:$qq_angle)*?) (\>) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr < >
  0         0  
6291 0         0 elsif ($string =~ /\G (\') ((?:$qq_char)*?) (\') ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split_q($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr ' '
  0         0  
6292             elsif ($string =~ /\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr','{','}',$2,$4); next E_STRING_LOOP; } # qr | | --> qr { }
6293 0         0 elsif ($string =~ /\G (\S) ((?:$qq_char)*?) (\1) ([imosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # qr * *
6294             }
6295             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6296             }
6297             }
6298              
6299 0 0       0 # split q//
  0         0  
  0         0  
6300             elsif ($string =~ /\G \b (q) \b /oxgc) {
6301 0         0 if ($string =~ /\G (\#) ((?:\\\#|\\\\|$q_char)*?) (\#) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q# # --> qr # #
6302 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
6303 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6304 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e_string .= $e . $1; }
  0         0  
6305 0         0 elsif ($string =~ /\G (\() ((?:\\\\|\\\)|\\\(|$q_paren)*?) (\)) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q ( ) --> qr ( )
  0         0  
6306 0         0 elsif ($string =~ /\G (\{) ((?:\\\\|\\\}|\\\{|$q_brace)*?) (\}) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q { } --> qr { }
  0         0  
6307 0         0 elsif ($string =~ /\G (\[) ((?:\\\\|\\\]|\\\[|$q_bracket)*?) (\]) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q [ ] --> qr [ ]
  0         0  
6308 0         0 elsif ($string =~ /\G (\<) ((?:\\\\|\\\>|\\\<|$q_angle)*?) (\>) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q < > --> qr < >
  0         0  
6309             elsif ($string =~ /\G ([*\-:?\\^|]) ((?:$q_char)*?) (\1) /oxgc) { $e_string .= e_split_q($e.'qr','{','}',$2,''); next E_STRING_LOOP; } # q | | --> qr { }
6310 0         0 elsif ($string =~ /\G (\S) ((?:\\\\|\\\1| $q_char)*?) (\1) /oxgc) { $e_string .= e_split_q($e.'qr',$1,$3,$2,''); next E_STRING_LOOP; } # q * * --> qr * *
6311             }
6312             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6313             }
6314             }
6315              
6316 0 0       0 # split m//
  0         0  
  0         0  
6317             elsif ($string =~ /\G \b (m) \b /oxgc) {
6318 0         0 if ($string =~ /\G (\#) ((?:$qq_char)*?) (\#) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1,$3,$2,$4); next E_STRING_LOOP; } # m# # --> qr # #
6319 0 0       0 else {
  0 0       0  
    0          
    0          
    0          
    0          
    0          
    0          
6320 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6321 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e_string .= $e . $1; }
  0         0  
6322 0         0 elsif ($string =~ /\G (\() ((?:$qq_paren)*?) (\)) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m ( ) --> qr ( )
  0         0  
6323 0         0 elsif ($string =~ /\G (\{) ((?:$qq_brace)*?) (\}) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m { } --> qr { }
  0         0  
6324 0         0 elsif ($string =~ /\G (\[) ((?:$qq_bracket)*?) (\]) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m [ ] --> qr [ ]
  0         0  
6325 0         0 elsif ($string =~ /\G (\<) ((?:$qq_angle)*?) (\>) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m < > --> qr < >
  0         0  
6326 0         0 elsif ($string =~ /\G (\') ((?:$qq_char)*?) (\') ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split_q($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m ' ' --> qr ' '
  0         0  
6327             elsif ($string =~ /\G ([*\-:?\\^|]) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr','{','}',$2,$4); next E_STRING_LOOP; } # m | | --> qr { }
6328 0         0 elsif ($string =~ /\G (\S) ((?:$qq_char)*?) (\1) ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split ($e.'qr',$1, $3, $2,$4); next E_STRING_LOOP; } # m * * --> qr * *
6329             }
6330             die __FILE__, ": Search pattern not terminated\n";
6331             }
6332             }
6333              
6334 0         0 # split ''
6335 0         0 elsif ($string =~ /\G (\') /oxgc) {
6336 0 0       0 my $q_string = '';
  0 0       0  
    0          
    0          
6337 0         0 while ($string !~ /\G \z/oxgc) {
6338 0         0 if ($string =~ /\G (\\\\) /oxgc) { $q_string .= $1; }
  0         0  
6339 0         0 elsif ($string =~ /\G (\\\') /oxgc) { $q_string .= $1; } # splitqr'' --> split qr''
6340             elsif ($string =~ /\G \' /oxgc) { $e_string .= e_split_q($e.q{ qr},"'","'",$q_string,''); next E_STRING_LOOP; } # ' ' --> qr ' '
6341 0         0 elsif ($string =~ /\G ($q_char) /oxgc) { $q_string .= $1; }
6342             }
6343             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6344             }
6345              
6346 0         0 # split ""
6347 0         0 elsif ($string =~ /\G (\") /oxgc) {
6348 0 0       0 my $qq_string = '';
  0 0       0  
    0          
    0          
6349 0         0 while ($string !~ /\G \z/oxgc) {
6350 0         0 if ($string =~ /\G (\\\\) /oxgc) { $qq_string .= $1; }
  0         0  
6351 0         0 elsif ($string =~ /\G (\\\") /oxgc) { $qq_string .= $1; } # splitqr"" --> split qr""
6352             elsif ($string =~ /\G \" /oxgc) { $e_string .= e_split($e.q{ qr},'"','"',$qq_string,''); next E_STRING_LOOP; } # " " --> qr " "
6353 0         0 elsif ($string =~ /\G ($q_char) /oxgc) { $qq_string .= $1; }
6354             }
6355             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6356             }
6357              
6358 0         0 # split //
6359 0         0 elsif ($string =~ /\G (\/) /oxgc) {
6360 0 0       0 my $regexp = '';
  0 0       0  
    0          
    0          
6361 0         0 while ($string !~ /\G \z/oxgc) {
6362 0         0 if ($string =~ /\G (\\\\) /oxgc) { $regexp .= $1; }
  0         0  
6363 0         0 elsif ($string =~ /\G (\\\/) /oxgc) { $regexp .= $1; } # splitqr// --> split qr//
6364             elsif ($string =~ /\G \/ ([cgimosxpadlunbB]*) /oxgc) { $e_string .= e_split($e.q{ qr}, '/','/',$regexp,$1); next E_STRING_LOOP; } # / / --> qr / /
6365 0         0 elsif ($string =~ /\G ($q_char) /oxgc) { $regexp .= $1; }
6366             }
6367             die __FILE__, ": Search pattern not terminated\n";
6368             }
6369             }
6370              
6371 0         0 # qq//
6372 0 0       0 elsif ($string =~ /\G \b (qq) \b /oxgc) {
6373 0         0 my $ope = $1;
6374             if ($string =~ /\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { # qq# #
6375             $e_string .= e_qq($ope,$1,$3,$2);
6376 0         0 }
6377 0         0 else {
6378 0 0       0 my $e = '';
  0 0       0  
    0          
    0          
    0          
    0          
6379 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6380 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
  0         0  
6381 0         0 elsif ($string =~ /\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qq ( )
  0         0  
6382 0         0 elsif ($string =~ /\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qq { }
  0         0  
6383 0         0 elsif ($string =~ /\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qq [ ]
  0         0  
6384             elsif ($string =~ /\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qq < >
6385 0         0 elsif ($string =~ /\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qq * *
6386             }
6387             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6388             }
6389             }
6390              
6391 0         0 # qx//
6392 0 0       0 elsif ($string =~ /\G \b (qx) \b /oxgc) {
6393 0         0 my $ope = $1;
6394             if ($string =~ /\G (\#) ((?:$qq_char)*?) (\#) /oxgc) { # qx# #
6395             $e_string .= e_qq($ope,$1,$3,$2);
6396 0         0 }
6397 0         0 else {
6398 0 0       0 my $e = '';
  0 0       0  
    0          
    0          
    0          
    0          
    0          
6399 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6400 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
  0         0  
6401 0         0 elsif ($string =~ /\G (\() ((?:$qq_paren)*?) (\)) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qx ( )
  0         0  
6402 0         0 elsif ($string =~ /\G (\{) ((?:$qq_brace)*?) (\}) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qx { }
  0         0  
6403 0         0 elsif ($string =~ /\G (\[) ((?:$qq_bracket)*?) (\]) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qx [ ]
  0         0  
6404 0         0 elsif ($string =~ /\G (\<) ((?:$qq_angle)*?) (\>) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qx < >
  0         0  
6405             elsif ($string =~ /\G (\') ((?:$qq_char)*?) (\') /oxgc) { $e_string .= $e . e_q ($ope,$1,$3,$2); next E_STRING_LOOP; } # qx ' '
6406 0         0 elsif ($string =~ /\G (\S) ((?:$qq_char)*?) (\1) /oxgc) { $e_string .= $e . e_qq($ope,$1,$3,$2); next E_STRING_LOOP; } # qx * *
6407             }
6408             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6409             }
6410             }
6411              
6412 0         0 # q//
6413 0 0       0 elsif ($string =~ /\G \b (q) \b /oxgc) {
6414 0         0 my $ope = $1;
6415             if ($string =~ /\G (\#) ((?:\\\#|\\\\|$q_char)*?) (\#) /oxgc) { # q# #
6416             $e_string .= e_q($ope,$1,$3,$2);
6417 0         0 }
6418 0         0 else {
6419 0 0       0 my $e = '';
  0 0       0  
    0          
    0          
    0          
    0          
6420 0         0 while ($string !~ /\G \z/oxgc) {
  0         0  
6421 0         0 if ($string =~ /\G ((?>\s+)|\#.*) /oxgc) { $e .= $1; }
  0         0  
6422 0         0 elsif ($string =~ /\G (\() ((?:\\\\|\\\)|\\\(|$q_paren)*?) (\)) /oxgc) { $e_string .= $e . e_q($ope,$1,$3,$2); next E_STRING_LOOP; } # q ( )
  0         0  
6423 0         0 elsif ($string =~ /\G (\{) ((?:\\\\|\\\}|\\\{|$q_brace)*?) (\}) /oxgc) { $e_string .= $e . e_q($ope,$1,$3,$2); next E_STRING_LOOP; } # q { }
  0         0  
6424 0         0 elsif ($string =~ /\G (\[) ((?:\\\\|\\\]|\\\[|$q_bracket)*?) (\]) /oxgc) { $e_string .= $e . e_q($ope,$1,$3,$2); next E_STRING_LOOP; } # q [ ]
  0         0  
6425             elsif ($string =~ /\G (\<) ((?:\\\\|\\\>|\\\<|$q_angle)*?) (\>) /oxgc) { $e_string .= $e . e_q($ope,$1,$3,$2); next E_STRING_LOOP; } # q < >
6426 0         0 elsif ($string =~ /\G (\S) ((?:\\\\|\\\1| $q_char)*?) (\1) /oxgc) { $e_string .= $e . e_q($ope,$1,$3,$2); next E_STRING_LOOP; } # q * *
6427             }
6428             die __FILE__, ": Can't find string terminator anywhere before EOF\n";
6429             }
6430             }
6431 0         0  
6432             # ''
6433             elsif ($string =~ /\G (?
6434 12         42  
6435             # ""
6436             elsif ($string =~ /\G (\") ((?:$qq_char)*?) (\") /oxgc) { $e_string .= e_qq('',$1,$3,$2); }
6437 6         23  
6438             # ``
6439             elsif ($string =~ /\G (\`) ((?:$qq_char)*?) (\`) /oxgc) { $e_string .= e_qq('',$1,$3,$2); }
6440 0         0  
6441             # <<>> (a safer ARGV)
6442             elsif ($string =~ /\G ( <<>> ) /oxgc) { $e_string .= $1; }
6443 0         0  
6444             # <<= <=> <= < operator
6445             elsif ($string =~ /\G ( <<= | <=> | <= | < ) (?= (?>\s*) [A-Za-z_0-9'"`\$\@\&\*\(\+\-] )/oxgc) { $e_string .= $1; }
6446 0         0  
6447             #
6448             elsif ($string =~ /\G (<[\$]?[A-Za-z_][A-Za-z_0-9]*>) /oxgc) { $e_string .= $1; }
6449              
6450 0         0 # --- glob
6451             elsif ($string =~ /\G < ((?:$q_char)+?) > /oxgc) {
6452             $e_string .= 'Eutf2::glob("' . $1 . '")';
6453             }
6454              
6455 0         0 # << (bit shift) --- not here document
6456 0         0 elsif ($string =~ /\G ( << (?>\s*) ) (?= [0-9\$\@\&] ) /oxgc) {
6457             $slash = 'm//';
6458             $e_string .= $1;
6459             }
6460              
6461 0         0 # <<~'HEREDOC'
6462 0         0 elsif ($string =~ /\G ( <<~ [\t ]* '([a-zA-Z_0-9]*)' ) /oxgc) {
6463 0         0 $slash = 'm//';
6464             my $here_quote = $1;
6465             my $delimiter = $2;
6466 0 0       0  
6467 0         0 # get here document
6468 0         0 if ($here_script eq '') {
6469             $here_script = CORE::substr $_, pos $_;
6470 0 0       0 $here_script =~ s/.*?\n//oxm;
6471 0         0 }
6472 0         0 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
6473 0         0 my $heredoc = $1;
6474 0         0 my $indent = $2;
6475 0         0 $heredoc =~ s{^$indent}{}msg; # no /ox
6476             push @heredoc, $heredoc . qq{\n$delimiter\n};
6477             push @heredoc_delimiter, qq{\\s*$delimiter};
6478 0         0 }
6479             else {
6480 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6481             }
6482             $e_string .= qq{<<'$delimiter'};
6483             }
6484              
6485 0         0 # <<~\HEREDOC
6486 0         0 elsif ($string =~ /\G ( <<~ \\([a-zA-Z_0-9]+) ) /oxgc) {
6487 0         0 $slash = 'm//';
6488             my $here_quote = $1;
6489             my $delimiter = $2;
6490 0 0       0  
6491 0         0 # get here document
6492 0         0 if ($here_script eq '') {
6493             $here_script = CORE::substr $_, pos $_;
6494 0 0       0 $here_script =~ s/.*?\n//oxm;
6495 0         0 }
6496 0         0 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
6497 0         0 my $heredoc = $1;
6498 0         0 my $indent = $2;
6499 0         0 $heredoc =~ s{^$indent}{}msg; # no /ox
6500             push @heredoc, $heredoc . qq{\n$delimiter\n};
6501             push @heredoc_delimiter, qq{\\s*$delimiter};
6502 0         0 }
6503             else {
6504 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6505             }
6506             $e_string .= qq{<<\\$delimiter};
6507             }
6508              
6509 0         0 # <<~"HEREDOC"
6510 0         0 elsif ($string =~ /\G ( <<~ [\t ]* "([a-zA-Z_0-9]*)" ) /oxgc) {
6511 0         0 $slash = 'm//';
6512             my $here_quote = $1;
6513             my $delimiter = $2;
6514 0 0       0  
6515 0         0 # get here document
6516 0         0 if ($here_script eq '') {
6517             $here_script = CORE::substr $_, pos $_;
6518 0 0       0 $here_script =~ s/.*?\n//oxm;
6519 0         0 }
6520 0         0 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
6521 0         0 my $heredoc = $1;
6522 0         0 my $indent = $2;
6523 0         0 $heredoc =~ s{^$indent}{}msg; # no /ox
6524             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
6525             push @heredoc_delimiter, qq{\\s*$delimiter};
6526 0         0 }
6527             else {
6528 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6529             }
6530             $e_string .= qq{<<"$delimiter"};
6531             }
6532              
6533 0         0 # <<~HEREDOC
6534 0         0 elsif ($string =~ /\G ( <<~ ([a-zA-Z_0-9]+) ) /oxgc) {
6535 0         0 $slash = 'm//';
6536             my $here_quote = $1;
6537             my $delimiter = $2;
6538 0 0       0  
6539 0         0 # get here document
6540 0         0 if ($here_script eq '') {
6541             $here_script = CORE::substr $_, pos $_;
6542 0 0       0 $here_script =~ s/.*?\n//oxm;
6543 0         0 }
6544 0         0 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
6545 0         0 my $heredoc = $1;
6546 0         0 my $indent = $2;
6547 0         0 $heredoc =~ s{^$indent}{}msg; # no /ox
6548             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
6549             push @heredoc_delimiter, qq{\\s*$delimiter};
6550 0         0 }
6551             else {
6552 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6553             }
6554             $e_string .= qq{<<$delimiter};
6555             }
6556              
6557 0         0 # <<~`HEREDOC`
6558 0         0 elsif ($string =~ /\G ( <<~ [\t ]* `([a-zA-Z_0-9]*)` ) /oxgc) {
6559 0         0 $slash = 'm//';
6560             my $here_quote = $1;
6561             my $delimiter = $2;
6562 0 0       0  
6563 0         0 # get here document
6564 0         0 if ($here_script eq '') {
6565             $here_script = CORE::substr $_, pos $_;
6566 0 0       0 $here_script =~ s/.*?\n//oxm;
6567 0         0 }
6568 0         0 if ($here_script =~ s/\A (.*?) \n ([\t ]*) $delimiter \n //xms) {
6569 0         0 my $heredoc = $1;
6570 0         0 my $indent = $2;
6571 0         0 $heredoc =~ s{^$indent}{}msg; # no /ox
6572             push @heredoc, e_heredoc($heredoc) . qq{\n$delimiter\n};
6573             push @heredoc_delimiter, qq{\\s*$delimiter};
6574 0         0 }
6575             else {
6576 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6577             }
6578             $e_string .= qq{<<`$delimiter`};
6579             }
6580              
6581 0         0 # <<'HEREDOC'
6582 0         0 elsif ($string =~ /\G ( << '([a-zA-Z_0-9]*)' ) /oxgc) {
6583 0         0 $slash = 'm//';
6584             my $here_quote = $1;
6585             my $delimiter = $2;
6586 0 0       0  
6587 0         0 # get here document
6588 0         0 if ($here_script eq '') {
6589             $here_script = CORE::substr $_, pos $_;
6590 0 0       0 $here_script =~ s/.*?\n//oxm;
6591 0         0 }
6592 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
6593             push @heredoc, $1 . qq{\n$delimiter\n};
6594             push @heredoc_delimiter, $delimiter;
6595 0         0 }
6596             else {
6597 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6598             }
6599             $e_string .= $here_quote;
6600             }
6601              
6602 0         0 # <<\HEREDOC
6603 0         0 elsif ($string =~ /\G ( << \\([a-zA-Z_0-9]+) ) /oxgc) {
6604 0         0 $slash = 'm//';
6605             my $here_quote = $1;
6606             my $delimiter = $2;
6607 0 0       0  
6608 0         0 # get here document
6609 0         0 if ($here_script eq '') {
6610             $here_script = CORE::substr $_, pos $_;
6611 0 0       0 $here_script =~ s/.*?\n//oxm;
6612 0         0 }
6613 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
6614             push @heredoc, $1 . qq{\n$delimiter\n};
6615             push @heredoc_delimiter, $delimiter;
6616 0         0 }
6617             else {
6618 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6619             }
6620             $e_string .= $here_quote;
6621             }
6622              
6623 0         0 # <<"HEREDOC"
6624 0         0 elsif ($string =~ /\G ( << "([a-zA-Z_0-9]*)" ) /oxgc) {
6625 0         0 $slash = 'm//';
6626             my $here_quote = $1;
6627             my $delimiter = $2;
6628 0 0       0  
6629 0         0 # get here document
6630 0         0 if ($here_script eq '') {
6631             $here_script = CORE::substr $_, pos $_;
6632 0 0       0 $here_script =~ s/.*?\n//oxm;
6633 0         0 }
6634 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
6635             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
6636             push @heredoc_delimiter, $delimiter;
6637 0         0 }
6638             else {
6639 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6640             }
6641             $e_string .= $here_quote;
6642             }
6643              
6644 0         0 # <
6645 0         0 elsif ($string =~ /\G ( << ([a-zA-Z_0-9]+) ) /oxgc) {
6646 0         0 $slash = 'm//';
6647             my $here_quote = $1;
6648             my $delimiter = $2;
6649 0 0       0  
6650 0         0 # get here document
6651 0         0 if ($here_script eq '') {
6652             $here_script = CORE::substr $_, pos $_;
6653 0 0       0 $here_script =~ s/.*?\n//oxm;
6654 0         0 }
6655 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
6656             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
6657             push @heredoc_delimiter, $delimiter;
6658 0         0 }
6659             else {
6660 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6661             }
6662             $e_string .= $here_quote;
6663             }
6664              
6665 0         0 # <<`HEREDOC`
6666 0         0 elsif ($string =~ /\G ( << `([a-zA-Z_0-9]*)` ) /oxgc) {
6667 0         0 $slash = 'm//';
6668             my $here_quote = $1;
6669             my $delimiter = $2;
6670 0 0       0  
6671 0         0 # get here document
6672 0         0 if ($here_script eq '') {
6673             $here_script = CORE::substr $_, pos $_;
6674 0 0       0 $here_script =~ s/.*?\n//oxm;
6675 0         0 }
6676 0         0 if ($here_script =~ s/\A (.*?) \n $delimiter \n //xms) {
6677             push @heredoc, e_heredoc($1) . qq{\n$delimiter\n};
6678             push @heredoc_delimiter, $delimiter;
6679 0         0 }
6680             else {
6681 0         0 die __FILE__, ": Can't find string terminator $delimiter anywhere before EOF\n";
6682             }
6683             $e_string .= $here_quote;
6684             }
6685              
6686             # any operator before div
6687             elsif ($string =~ /\G (
6688             -- | \+\+ |
6689 0         0 [\)\}\]]
  40         76  
6690              
6691             ) /oxgc) { $slash = 'div'; $e_string .= $1; }
6692              
6693             # yada-yada or triple-dot operator
6694             elsif ($string =~ /\G (
6695 40         197 \.\.\.
  0         0  
6696              
6697             ) /oxgc) { $slash = 'm//'; $e_string .= q{die('Unimplemented')}; }
6698              
6699             # any operator before m//
6700             elsif ($string =~ /\G ((?>
6701              
6702             !~~ | !~ | != | ! |
6703             %= | % |
6704             &&= | && | &= | &\.= | &\. | & |
6705             -= | -> | - |
6706             :(?>\s*)= |
6707             : |
6708             <<>> |
6709             <<= | <=> | <= | < |
6710             == | => | =~ | = |
6711             >>= | >> | >= | > |
6712             \*\*= | \*\* | \*= | \* |
6713             \+= | \+ |
6714             \.\. | \.= | \. |
6715             \/\/= | \/\/ |
6716             \/= | \/ |
6717             \? |
6718             \\ |
6719             \^= | \^\.= | \^\. | \^ |
6720             \b x= |
6721             \|\|= | \|\| | \|= | \|\.= | \|\. | \| |
6722             ~~ | ~\. | ~ |
6723             \b(?: and | cmp | eq | ge | gt | le | lt | ne | not | or | xor | x )\b |
6724             \b(?: print )\b |
6725              
6726 0         0 [,;\(\{\[]
  50         99  
6727              
6728             )) /oxgc) { $slash = 'm//'; $e_string .= $1; }
6729 50         200  
6730             # other any character
6731             elsif ($string =~ /\G ($q_char) /oxgc) { $e_string .= $1; }
6732              
6733 181         969 # system error
6734             else {
6735             die __FILE__, ": Oops, this shouldn't happen!\n";
6736             }
6737 0         0 }
6738              
6739             return $e_string;
6740             }
6741              
6742             #
6743             # character class
6744 39     2935 0 193 #
6745             sub character_class {
6746 2935 100       5163 my($char,$modifier) = @_;
6747 2935 100       4504  
6748 115         221 if ($char eq '.') {
6749             if ($modifier =~ /s/) {
6750             return '${Eutf2::dot_s}';
6751 23         62 }
6752             else {
6753             return '${Eutf2::dot}';
6754             }
6755 92         194 }
6756             else {
6757             return Eutf2::classic_character_class($char);
6758             }
6759             }
6760              
6761             #
6762             # escape capture ($1, $2, $3, ...)
6763             #
6764 2820     469 0 5388 sub e_capture {
6765              
6766             return join '', '${', $_[0], '}';
6767             }
6768              
6769             #
6770             # escape transliteration (tr/// or y///)
6771 469     11 0 1944 #
6772 11         64 sub e_tr {
6773 11   100     25 my($variable,$charclass,$e,$charclass2,$modifier) = @_;
6774             my $e_tr = '';
6775 11         33 $modifier ||= '';
6776              
6777             $slash = 'div';
6778 11         20  
6779             # quote character class 1
6780             $charclass = q_tr($charclass);
6781 11         27  
6782             # quote character class 2
6783             $charclass2 = q_tr($charclass2);
6784 11 50       20  
6785 11 0       36 # /b /B modifier
6786 0         0 if ($modifier =~ tr/bB//d) {
6787             if ($variable eq '') {
6788             $e_tr = qq{tr$charclass$e$charclass2$modifier};
6789 0         0 }
6790             else {
6791             $e_tr = qq{$variable${bind_operator}tr$charclass$e$charclass2$modifier};
6792             }
6793 0 100       0 }
6794 11         24 else {
6795             if ($variable eq '') {
6796             $e_tr = qq{Eutf2::tr(\$_,' =~ ',$charclass,$e$charclass2,'$modifier')};
6797 2         9 }
6798             else {
6799             $e_tr = qq{Eutf2::tr($variable,'$bind_operator',$charclass,$e$charclass2,'$modifier')};
6800             }
6801             }
6802 9         42  
6803 11         17 # clear tr/// variable
6804             $tr_variable = '';
6805 11         14 $bind_operator = '';
6806              
6807             return $e_tr;
6808             }
6809              
6810             #
6811             # quote for escape transliteration (tr/// or y///)
6812 11     22 0 101 #
6813             sub q_tr {
6814             my($charclass) = @_;
6815 22 50       30  
    0          
    0          
    0          
    0          
    0          
6816 22         51 # quote character class
6817             if ($charclass !~ /'/oxms) {
6818             return e_q('', "'", "'", $charclass); # --> q' '
6819 22         35 }
6820             elsif ($charclass !~ /\//oxms) {
6821             return e_q('q', '/', '/', $charclass); # --> q/ /
6822 0         0 }
6823             elsif ($charclass !~ /\#/oxms) {
6824             return e_q('q', '#', '#', $charclass); # --> q# #
6825 0         0 }
6826             elsif ($charclass !~ /[\<\>]/oxms) {
6827             return e_q('q', '<', '>', $charclass); # --> q< >
6828 0         0 }
6829             elsif ($charclass !~ /[\(\)]/oxms) {
6830             return e_q('q', '(', ')', $charclass); # --> q( )
6831 0         0 }
6832             elsif ($charclass !~ /[\{\}]/oxms) {
6833             return e_q('q', '{', '}', $charclass); # --> q{ }
6834 0         0 }
6835 0 0       0 else {
6836 0         0 for my $char (qw( ! " $ % & * + . : = ? @ ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
6837             if ($charclass !~ /\Q$char\E/xms) {
6838             return e_q('q', $char, $char, $charclass);
6839             }
6840             }
6841 0         0 }
6842              
6843             return e_q('q', '{', '}', $charclass);
6844             }
6845              
6846             #
6847             # escape q string (q//, '')
6848 0     2150 0 0 #
6849             sub e_q {
6850 2150         5137 my($ope,$delimiter,$end_delimiter,$string) = @_;
6851              
6852 2150         2877 $slash = 'div';
6853              
6854             return join '', $ope, $delimiter, $string, $end_delimiter;
6855             }
6856              
6857             #
6858             # escape qq string (qq//, "", qx//, ``)
6859 2150     9533 0 9979 #
6860             sub e_qq {
6861 9533         19575 my($ope,$delimiter,$end_delimiter,$string) = @_;
6862              
6863 9533         11434 $slash = 'div';
6864 9533         10280  
6865             my $left_e = 0;
6866             my $right_e = 0;
6867 9533         9860  
6868             # split regexp
6869             my @char = $string =~ /\G((?>
6870             [^\x80-\xFF\\\$]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
6871             \\x\{ (?>[0-9A-Fa-f]+) \} |
6872             \\o\{ (?>[0-7]+) \} |
6873             \\N\{ (?>[^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} |
6874             \\ $q_char |
6875             \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} |
6876             \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} |
6877             \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} |
6878             \$ (?>\s* [0-9]+) |
6879             \$ (?>\s*) \{ (?>\s* [0-9]+ \s*) \} |
6880             \$ \$ (?![\w\{]) |
6881             \$ (?>\s*) \$ (?>\s*) $qq_variable |
6882             $q_char
6883 9533         346988 ))/oxmsg;
6884              
6885             for (my $i=0; $i <= $#char; $i++) {
6886 9533 50 66     28082  
    50 33        
    100          
    100          
    50          
6887 225573         694067 # "\L\u" --> "\u\L"
6888             if (($char[$i] eq '\L') and ($char[$i+1] eq '\u')) {
6889             @char[$i,$i+1] = @char[$i+1,$i];
6890             }
6891              
6892 0         0 # "\U\l" --> "\l\U"
6893             elsif (($char[$i] eq '\U') and ($char[$i+1] eq '\l')) {
6894             @char[$i,$i+1] = @char[$i+1,$i];
6895             }
6896              
6897 0         0 # octal escape sequence
6898             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
6899             $char[$i] = Eutf2::octchr($1);
6900             }
6901              
6902 1         5 # hexadecimal escape sequence
6903             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
6904             $char[$i] = Eutf2::hexchr($1);
6905             }
6906              
6907 1         5 # \N{CHARNAME} --> N{CHARNAME}
6908             elsif ($char[$i] =~ /\A \\ ( N\{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
6909             $char[$i] = $1;
6910 0 100       0 }
    50          
    50          
    50          
    100          
    100          
    50          
    100          
    50          
    50          
    100          
    50          
    50          
    100          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    50          
    50          
6911              
6912             if (0) {
6913             }
6914              
6915             # \F
6916             #
6917             # P.69 Table 2-6. Translation escapes
6918             # in Chapter 2: Bits and Pieces
6919             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
6920             # (and so on)
6921 225573         1737654  
6922 0 50       0 # \u \l \U \L \F \Q \E
6923 602         1216 elsif ($char[$i] =~ /\A ([<>]) \z/oxms) {
6924             if ($right_e < $left_e) {
6925             $char[$i] = '\\' . $char[$i];
6926             }
6927             }
6928             elsif ($char[$i] eq '\u') {
6929              
6930             # "STRING @{[ LIST EXPR ]} MORE STRING"
6931              
6932             # P.257 Other Tricks You Can Do with Hard References
6933             # in Chapter 8: References
6934             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
6935              
6936             # P.353 Other Tricks You Can Do with Hard References
6937             # in Chapter 8: References
6938             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
6939              
6940 0         0 # (and so on)
6941 0         0  
6942             $char[$i] = '@{[Eutf2::ucfirst qq<';
6943             $left_e++;
6944 0         0 }
6945 0         0 elsif ($char[$i] eq '\l') {
6946             $char[$i] = '@{[Eutf2::lcfirst qq<';
6947             $left_e++;
6948 0         0 }
6949 0         0 elsif ($char[$i] eq '\U') {
6950             $char[$i] = '@{[Eutf2::uc qq<';
6951             $left_e++;
6952 0         0 }
6953 6         8 elsif ($char[$i] eq '\L') {
6954             $char[$i] = '@{[Eutf2::lc qq<';
6955             $left_e++;
6956 6         17 }
6957 23         29 elsif ($char[$i] eq '\F') {
6958             $char[$i] = '@{[Eutf2::fc qq<';
6959             $left_e++;
6960 23         39 }
6961 0         0 elsif ($char[$i] eq '\Q') {
6962             $char[$i] = '@{[CORE::quotemeta qq<';
6963             $left_e++;
6964 0 50       0 }
6965 26         48 elsif ($char[$i] eq '\E') {
6966 26         30 if ($right_e < $left_e) {
6967             $char[$i] = '>]}';
6968             $right_e++;
6969 26         38 }
6970             else {
6971             $char[$i] = '';
6972             }
6973 0         0 }
6974 0 0       0 elsif ($char[$i] eq '\Q') {
6975 0         0 while (1) {
6976             if (++$i > $#char) {
6977 0 0       0 last;
6978 0         0 }
6979             if ($char[$i] eq '\E') {
6980             last;
6981             }
6982             }
6983             }
6984             elsif ($char[$i] eq '\E') {
6985             }
6986              
6987             # $0 --> $0
6988             elsif ($char[$i] =~ /\A \$ 0 \z/oxms) {
6989             }
6990             elsif ($char[$i] =~ /\A \$ \{ (?>\s*) 0 (?>\s*) \} \z/oxms) {
6991             }
6992              
6993             # $$ --> $$
6994             elsif ($char[$i] =~ /\A \$\$ \z/oxms) {
6995             }
6996              
6997             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
6998 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
6999             elsif ($char[$i] =~ /\A \$ ((?>[1-9][0-9]*)) \z/oxms) {
7000             $char[$i] = e_capture($1);
7001 409         833 }
7002             elsif ($char[$i] =~ /\A \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
7003             $char[$i] = e_capture($1);
7004             }
7005              
7006 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
7007             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ (?:$qq_bracket)*? \] ) \z/oxms) {
7008             $char[$i] = e_capture($1.'->'.$2);
7009             }
7010              
7011 0         0 # $$foo{ ... } --> $ $foo->{ ... }
7012             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ (?:$qq_brace)*? \} ) \z/oxms) {
7013             $char[$i] = e_capture($1.'->'.$2);
7014             }
7015              
7016 0         0 # $$foo
7017             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) \z/oxms) {
7018             $char[$i] = e_capture($1);
7019             }
7020              
7021 0         0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
7022             elsif ($char[$i] =~ /\A ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) \z/oxmsgc) {
7023             $char[$i] = '@{[Eutf2::PREMATCH()]}';
7024             }
7025              
7026 44         114 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
7027             elsif ($char[$i] =~ /\A ( \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) \z/oxmsgc) {
7028             $char[$i] = '@{[Eutf2::MATCH()]}';
7029             }
7030              
7031 45         119 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
7032             elsif ($char[$i] =~ /\A ( \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) \z/oxmsgc) {
7033             $char[$i] = '@{[Eutf2::POSTMATCH()]}';
7034             }
7035              
7036             # ${ foo } --> ${ foo }
7037             elsif ($char[$i] =~ /\A \$ (?>\s*) \{ (?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* ) \} \z/oxms) {
7038             }
7039              
7040 33         88 # ${ ... }
7041             elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ( .+ ) \} \z/oxms) {
7042             $char[$i] = e_capture($1);
7043             }
7044             }
7045 0 100       0  
7046 9533         16629 # return string
7047             if ($left_e > $right_e) {
7048 3         19 return join '', $ope, $delimiter, @char, '>]}' x ($left_e - $right_e), $end_delimiter;
7049             }
7050             return join '', $ope, $delimiter, @char, $end_delimiter;
7051             }
7052              
7053             #
7054             # escape qw string (qw//)
7055 9530     34 0 65799 #
7056             sub e_qw {
7057 34         159 my($ope,$delimiter,$end_delimiter,$string) = @_;
7058              
7059             $slash = 'div';
7060 34         63  
  34         363  
7061 856 50       1217 # choice again delimiter
    0          
    0          
    0          
    0          
7062 34         182 my %octet = map {$_ => 1} ($string =~ /\G ([\x00-\xFF]) /oxmsg);
7063             if (not $octet{$end_delimiter}) {
7064             return join '', $ope, $delimiter, $string, $end_delimiter;
7065 34         213 }
7066             elsif (not $octet{')'}) {
7067             return join '', $ope, '(', $string, ')';
7068 0         0 }
7069             elsif (not $octet{'}'}) {
7070             return join '', $ope, '{', $string, '}';
7071 0         0 }
7072             elsif (not $octet{']'}) {
7073             return join '', $ope, '[', $string, ']';
7074 0         0 }
7075             elsif (not $octet{'>'}) {
7076             return join '', $ope, '<', $string, '>';
7077 0         0 }
7078 0 0       0 else {
7079 0         0 for my $char (qw( ! " $ % & * + - . / : = ? @ ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
7080             if (not $octet{$char}) {
7081             return join '', $ope, $char, $string, $char;
7082             }
7083             }
7084             }
7085 0         0  
7086 0         0 # qw/AAA BBB C'CC/ --> ('AAA', 'BBB', 'C\'CC')
7087 0         0 my @string = CORE::split(/\s+/, $string);
7088 0         0 for my $string (@string) {
7089 0 0       0 my @octet = $string =~ /\G ([\x00-\xFF]) /oxmsg;
7090 0         0 for my $octet (@octet) {
7091             if ($octet =~ /\A (['\\]) \z/oxms) {
7092             $octet = '\\' . $1;
7093 0         0 }
7094             }
7095 0         0 $string = join '', @octet;
  0         0  
7096             }
7097             return join '', '(', (join ', ', map { "'$_'" } @string), ')';
7098             }
7099              
7100             #
7101             # escape here document (<<"HEREDOC", <
7102 0     108 0 0 #
7103             sub e_heredoc {
7104 108         273 my($string) = @_;
7105              
7106 108         216 $slash = 'm//';
7107              
7108 108         357 my $metachar = qr/[\@\\|]/oxms; # '|' is for <<`HEREDOC`
7109 108         181  
7110             my $left_e = 0;
7111             my $right_e = 0;
7112 108         144  
7113             # split regexp
7114             my @char = $string =~ /\G((?>
7115             [^\x80-\xFF\\\$]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
7116             \\x\{ (?>[0-9A-Fa-f]+) \} |
7117             \\o\{ (?>[0-7]+) \} |
7118             \\N\{ (?>[^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} |
7119             \\ $q_char |
7120             \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} |
7121             \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} |
7122             \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} |
7123             \$ (?>\s* [0-9]+) |
7124             \$ (?>\s*) \{ (?>\s* [0-9]+ \s*) \} |
7125             \$ \$ (?![\w\{]) |
7126             \$ (?>\s*) \$ (?>\s*) $qq_variable |
7127             $q_char
7128 108         16471 ))/oxmsg;
7129              
7130             for (my $i=0; $i <= $#char; $i++) {
7131 108 50 66     717  
    50 33        
    100          
    100          
    50          
7132 3305         9885 # "\L\u" --> "\u\L"
7133             if (($char[$i] eq '\L') and ($char[$i+1] eq '\u')) {
7134             @char[$i,$i+1] = @char[$i+1,$i];
7135             }
7136              
7137 0         0 # "\U\l" --> "\l\U"
7138             elsif (($char[$i] eq '\U') and ($char[$i+1] eq '\l')) {
7139             @char[$i,$i+1] = @char[$i+1,$i];
7140             }
7141              
7142 0         0 # octal escape sequence
7143             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
7144             $char[$i] = Eutf2::octchr($1);
7145             }
7146              
7147 1         5 # hexadecimal escape sequence
7148             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
7149             $char[$i] = Eutf2::hexchr($1);
7150             }
7151              
7152 1         3 # \N{CHARNAME} --> N{CHARNAME}
7153             elsif ($char[$i] =~ /\A \\ ( N\{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
7154             $char[$i] = $1;
7155 0 100       0 }
    50          
    50          
    50          
    100          
    50          
    50          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    50          
    50          
7156              
7157             if (0) {
7158             }
7159 3305         28293  
7160 0 50       0 # \u \l \U \L \F \Q \E
7161 72         132 elsif ($char[$i] =~ /\A ([<>]) \z/oxms) {
7162             if ($right_e < $left_e) {
7163             $char[$i] = '\\' . $char[$i];
7164             }
7165 0         0 }
7166 0         0 elsif ($char[$i] eq '\u') {
7167             $char[$i] = '@{[Eutf2::ucfirst qq<';
7168             $left_e++;
7169 0         0 }
7170 0         0 elsif ($char[$i] eq '\l') {
7171             $char[$i] = '@{[Eutf2::lcfirst qq<';
7172             $left_e++;
7173 0         0 }
7174 0         0 elsif ($char[$i] eq '\U') {
7175             $char[$i] = '@{[Eutf2::uc qq<';
7176             $left_e++;
7177 0         0 }
7178 6         9 elsif ($char[$i] eq '\L') {
7179             $char[$i] = '@{[Eutf2::lc qq<';
7180             $left_e++;
7181 6         12 }
7182 0         0 elsif ($char[$i] eq '\F') {
7183             $char[$i] = '@{[Eutf2::fc qq<';
7184             $left_e++;
7185 0         0 }
7186 0         0 elsif ($char[$i] eq '\Q') {
7187             $char[$i] = '@{[CORE::quotemeta qq<';
7188             $left_e++;
7189 0 50       0 }
7190 3         7 elsif ($char[$i] eq '\E') {
7191 3         3 if ($right_e < $left_e) {
7192             $char[$i] = '>]}';
7193             $right_e++;
7194 3         6 }
7195             else {
7196             $char[$i] = '';
7197             }
7198 0         0 }
7199 0 0       0 elsif ($char[$i] eq '\Q') {
7200 0         0 while (1) {
7201             if (++$i > $#char) {
7202 0 0       0 last;
7203 0         0 }
7204             if ($char[$i] eq '\E') {
7205             last;
7206             }
7207             }
7208             }
7209             elsif ($char[$i] eq '\E') {
7210             }
7211              
7212             # $0 --> $0
7213             elsif ($char[$i] =~ /\A \$ 0 \z/oxms) {
7214             }
7215             elsif ($char[$i] =~ /\A \$ \{ (?>\s*) 0 (?>\s*) \} \z/oxms) {
7216             }
7217              
7218             # $$ --> $$
7219             elsif ($char[$i] =~ /\A \$\$ \z/oxms) {
7220             }
7221              
7222             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
7223 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
7224             elsif ($char[$i] =~ /\A \$ ((?>[1-9][0-9]*)) \z/oxms) {
7225             $char[$i] = e_capture($1);
7226 0         0 }
7227             elsif ($char[$i] =~ /\A \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
7228             $char[$i] = e_capture($1);
7229             }
7230              
7231 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
7232             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ (?:$qq_bracket)*? \] ) \z/oxms) {
7233             $char[$i] = e_capture($1.'->'.$2);
7234             }
7235              
7236 0         0 # $$foo{ ... } --> $ $foo->{ ... }
7237             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ (?:$qq_brace)*? \} ) \z/oxms) {
7238             $char[$i] = e_capture($1.'->'.$2);
7239             }
7240              
7241 0         0 # $$foo
7242             elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) \z/oxms) {
7243             $char[$i] = e_capture($1);
7244             }
7245              
7246 0         0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
7247             elsif ($char[$i] =~ /\A ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) \z/oxmsgc) {
7248             $char[$i] = '@{[Eutf2::PREMATCH()]}';
7249             }
7250              
7251 8         58 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
7252             elsif ($char[$i] =~ /\A ( \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) \z/oxmsgc) {
7253             $char[$i] = '@{[Eutf2::MATCH()]}';
7254             }
7255              
7256 8         67 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
7257             elsif ($char[$i] =~ /\A ( \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) \z/oxmsgc) {
7258             $char[$i] = '@{[Eutf2::POSTMATCH()]}';
7259             }
7260              
7261             # ${ foo } --> ${ foo }
7262             elsif ($char[$i] =~ /\A \$ (?>\s*) \{ (?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* ) \} \z/oxms) {
7263             }
7264              
7265 6         41 # ${ ... }
7266             elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ( .+ ) \} \z/oxms) {
7267             $char[$i] = e_capture($1);
7268             }
7269             }
7270 0 100       0  
7271 108         239 # return string
7272             if ($left_e > $right_e) {
7273 3         22 return join '', @char, '>]}' x ($left_e - $right_e);
7274             }
7275             return join '', @char;
7276             }
7277              
7278             #
7279             # escape regexp (m//, qr//)
7280 105     1377 0 825 #
7281 1377   100     5625 sub e_qr {
7282             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
7283 1377         4740 $modifier ||= '';
7284 1377 50       2312  
7285 1377         2927 $modifier =~ tr/p//d;
7286 0         0 if ($modifier =~ /([adlu])/oxms) {
7287 0 0       0 my $line = 0;
7288 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
7289 0         0 if ($filename ne __FILE__) {
7290             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
7291             last;
7292 0         0 }
7293             }
7294             die qq{Unsupported modifier "$1" used at line $line.\n};
7295 0         0 }
7296              
7297             $slash = 'div';
7298 1377 100       2063  
    100          
7299 1377         3784 # literal null string pattern
7300 8         10 if ($string eq '') {
7301 8         10 $modifier =~ tr/bB//d;
7302             $modifier =~ tr/i//d;
7303             return join '', $ope, $delimiter, $end_delimiter, $modifier;
7304             }
7305              
7306             # /b /B modifier
7307             elsif ($modifier =~ tr/bB//d) {
7308 8 50       41  
7309 25         71 # choice again delimiter
7310 0         0 if ($delimiter =~ / [\@:] /oxms) {
  0         0  
7311 0 0       0 my @char = $string =~ /\G ([\x00-\xFF]) /oxmsg;
    0          
    0          
    0          
7312 0         0 my %octet = map {$_ => 1} @char;
7313 0         0 if (not $octet{')'}) {
7314             $delimiter = '(';
7315             $end_delimiter = ')';
7316 0         0 }
7317 0         0 elsif (not $octet{'}'}) {
7318             $delimiter = '{';
7319             $end_delimiter = '}';
7320 0         0 }
7321 0         0 elsif (not $octet{']'}) {
7322             $delimiter = '[';
7323             $end_delimiter = ']';
7324 0         0 }
7325 0         0 elsif (not $octet{'>'}) {
7326             $delimiter = '<';
7327             $end_delimiter = '>';
7328 0         0 }
7329 0 0       0 else {
7330 0         0 for my $char (qw( ! " $ % & * + - . / = ? ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
7331 0         0 if (not $octet{$char}) {
7332 0         0 $delimiter = $char;
7333             $end_delimiter = $char;
7334             last;
7335             }
7336             }
7337             }
7338 0 100 100     0 }
7339 25         155  
7340             if (($ope =~ /\A m? \z/oxms) and ($delimiter eq '?')) {
7341             return join '', $ope, $delimiter, $string, $matched, $end_delimiter, $modifier;
7342 4         34 }
7343             else {
7344             return join '', $ope, $delimiter, '(?:', $string, ')', $matched, $end_delimiter, $modifier;
7345             }
7346 21 100       167 }
7347 1344         2906  
7348             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
7349             my $metachar = qr/[\@\\|[\]{^]/oxms;
7350 1344         4554  
7351             # split regexp
7352             my @char = $string =~ /\G((?>
7353             [^\x80-\xFF\\\$\@\[\(]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
7354             \\x (?>[0-9A-Fa-f]{1,2}) |
7355             \\ (?>[0-7]{2,3}) |
7356             \\c [\x40-\x5F] |
7357             \\x\{ (?>[0-9A-Fa-f]+) \} |
7358             \\o\{ (?>[0-7]+) \} |
7359             \\[bBNpP]\{ (?>[^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} |
7360             \\ $q_char |
7361             \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} |
7362             \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} |
7363             \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} |
7364             [\$\@] $qq_variable |
7365             \$ (?>\s* [0-9]+) |
7366             \$ (?>\s*) \{ (?>\s* [0-9]+ \s*) \} |
7367             \$ \$ (?![\w\{]) |
7368             \$ (?>\s*) \$ (?>\s*) $qq_variable |
7369             \[\^ |
7370             \[\: (?>[a-z]+) :\] |
7371             \[\:\^ (?>[a-z]+) :\] |
7372             \(\? |
7373             $q_char
7374             ))/oxmsg;
7375 1344 50       191495  
7376 1344         8542 # choice again delimiter
  0         0  
7377 0 0       0 if ($delimiter =~ / [\@:] /oxms) {
    0          
    0          
    0          
7378 0         0 my %octet = map {$_ => 1} @char;
7379 0         0 if (not $octet{')'}) {
7380             $delimiter = '(';
7381             $end_delimiter = ')';
7382 0         0 }
7383 0         0 elsif (not $octet{'}'}) {
7384             $delimiter = '{';
7385             $end_delimiter = '}';
7386 0         0 }
7387 0         0 elsif (not $octet{']'}) {
7388             $delimiter = '[';
7389             $end_delimiter = ']';
7390 0         0 }
7391 0         0 elsif (not $octet{'>'}) {
7392             $delimiter = '<';
7393             $end_delimiter = '>';
7394 0         0 }
7395 0 0       0 else {
7396 0         0 for my $char (qw( ! " $ % & * + - . / = ? ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
7397 0         0 if (not $octet{$char}) {
7398 0         0 $delimiter = $char;
7399             $end_delimiter = $char;
7400             last;
7401             }
7402             }
7403             }
7404 0         0 }
7405 1344         2023  
7406 1344         1680 my $left_e = 0;
7407             my $right_e = 0;
7408             for (my $i=0; $i <= $#char; $i++) {
7409 1344 50 66     3203  
    50 66        
    100          
    100          
    100          
    100          
7410 3231         16258 # "\L\u" --> "\u\L"
7411             if (($char[$i] eq '\L') and ($char[$i+1] eq '\u')) {
7412             @char[$i,$i+1] = @char[$i+1,$i];
7413             }
7414              
7415 0         0 # "\U\l" --> "\l\U"
7416             elsif (($char[$i] eq '\U') and ($char[$i+1] eq '\l')) {
7417             @char[$i,$i+1] = @char[$i+1,$i];
7418             }
7419              
7420 0         0 # octal escape sequence
7421             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
7422             $char[$i] = Eutf2::octchr($1);
7423             }
7424              
7425 1         6 # hexadecimal escape sequence
7426             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
7427             $char[$i] = Eutf2::hexchr($1);
7428             }
7429              
7430             # \b{...} --> b\{...}
7431             # \B{...} --> B\{...}
7432             # \N{CHARNAME} --> N\{CHARNAME}
7433             # \p{PROPERTY} --> p\{PROPERTY}
7434 1         4 # \P{PROPERTY} --> P\{PROPERTY}
7435             elsif ($char[$i] =~ /\A \\ ([bBNpP]) ( \{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
7436             $char[$i] = $1 . '\\' . $2;
7437             }
7438              
7439 6         21 # \p, \P, \X --> p, P, X
7440             elsif ($char[$i] =~ /\A \\ ( [pPX] ) \z/oxms) {
7441             $char[$i] = $1;
7442 4 100 100     10 }
    100 100        
    100 100        
    100          
    100          
    100          
    50          
    50          
    100          
    100          
    100          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    50          
    50          
    100          
    100          
7443              
7444             if (0) {
7445             }
7446 3231         9408  
7447 0 50 33     0 # join separated multiple-octet
    50 33        
    50 33        
      33        
      66        
      33        
7448 6         87 elsif ($char[$i] =~ /\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms) {
7449             if ( ($i+3 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+3]) == 3) and (CORE::eval(sprintf '"%s%s%s%s"', @char[$i..$i+3]) =~ /\A $q_char \z/oxms)) {
7450             $char[$i] .= join '', splice @char, $i+1, 3;
7451 0         0 }
7452             elsif (($i+2 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+2]) == 2) and (CORE::eval(sprintf '"%s%s%s"', @char[$i..$i+2]) =~ /\A $q_char \z/oxms)) {
7453             $char[$i] .= join '', splice @char, $i+1, 2;
7454 0         0 }
7455             elsif (($i+1 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, $char[$i+1 ]) == 1) and (CORE::eval(sprintf '"%s%s"', @char[$i..$i+1]) =~ /\A $q_char \z/oxms)) {
7456             $char[$i] .= join '', splice @char, $i+1, 1;
7457             }
7458             }
7459              
7460 0         0 # open character class [...]
7461             elsif ($char[$i] eq '[') {
7462             my $left = $i;
7463              
7464             # [] make die "Unmatched [] in regexp ...\n"
7465 598 100       827 # (and so on)
7466 598         1320  
7467             if ($char[$i+1] eq ']') {
7468             $i++;
7469 3         6 }
7470 598 50       713  
7471 2607         3558 while (1) {
7472             if (++$i > $#char) {
7473 0 100       0 die __FILE__, ": Unmatched [] in regexp\n";
7474 2607         3994 }
7475             if ($char[$i] eq ']') {
7476             my $right = $i;
7477 598 100       701  
7478 598         2856 # [...]
  90         196  
7479             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
7480             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
7481 270         430 }
7482             else {
7483             splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
7484 508         1826 }
7485 598         1041  
7486             $i = $left;
7487             last;
7488             }
7489             }
7490             }
7491              
7492 598         1567 # open character class [^...]
7493             elsif ($char[$i] eq '[^') {
7494             my $left = $i;
7495              
7496             # [^] make die "Unmatched [] in regexp ...\n"
7497 328 100       400 # (and so on)
7498 328         779  
7499             if ($char[$i+1] eq ']') {
7500             $i++;
7501 5         10 }
7502 328 50       366  
7503 1447         1931 while (1) {
7504             if (++$i > $#char) {
7505 0 100       0 die __FILE__, ": Unmatched [] in regexp\n";
7506 1447         1990 }
7507             if ($char[$i] eq ']') {
7508             my $right = $i;
7509 328 100       374  
7510 328         1630 # [^...]
  90         201  
7511             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
7512             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_not_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
7513 270         514 }
7514             else {
7515             splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
7516 238         831 }
7517 328         597  
7518             $i = $left;
7519             last;
7520             }
7521             }
7522             }
7523              
7524 328         845 # rewrite character class or escape character
7525             elsif (my $char = character_class($char[$i],$modifier)) {
7526             $char[$i] = $char;
7527             }
7528              
7529 215 50       522 # /i modifier
7530 44         81 elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
7531             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
7532             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
7533 44         82 }
7534             else {
7535             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
7536             }
7537             }
7538              
7539 0 50       0 # \u \l \U \L \F \Q \E
7540 1         5 elsif ($char[$i] =~ /\A [<>] \z/oxms) {
7541             if ($right_e < $left_e) {
7542             $char[$i] = '\\' . $char[$i];
7543             }
7544 0         0 }
7545 0         0 elsif ($char[$i] eq '\u') {
7546             $char[$i] = '@{[Eutf2::ucfirst qq<';
7547             $left_e++;
7548 0         0 }
7549 0         0 elsif ($char[$i] eq '\l') {
7550             $char[$i] = '@{[Eutf2::lcfirst qq<';
7551             $left_e++;
7552 0         0 }
7553 1         2 elsif ($char[$i] eq '\U') {
7554             $char[$i] = '@{[Eutf2::uc qq<';
7555             $left_e++;
7556 1         3 }
7557 1         2 elsif ($char[$i] eq '\L') {
7558             $char[$i] = '@{[Eutf2::lc qq<';
7559             $left_e++;
7560 1         3 }
7561 16         28 elsif ($char[$i] eq '\F') {
7562             $char[$i] = '@{[Eutf2::fc qq<';
7563             $left_e++;
7564 16         32 }
7565 20         35 elsif ($char[$i] eq '\Q') {
7566             $char[$i] = '@{[CORE::quotemeta qq<';
7567             $left_e++;
7568 20 50       41 }
7569 38         95 elsif ($char[$i] eq '\E') {
7570 38         52 if ($right_e < $left_e) {
7571             $char[$i] = '>]}';
7572             $right_e++;
7573 38         91 }
7574             else {
7575             $char[$i] = '';
7576             }
7577 0         0 }
7578 0 0       0 elsif ($char[$i] eq '\Q') {
7579 0         0 while (1) {
7580             if (++$i > $#char) {
7581 0 0       0 last;
7582 0         0 }
7583             if ($char[$i] eq '\E') {
7584             last;
7585             }
7586             }
7587             }
7588             elsif ($char[$i] eq '\E') {
7589             }
7590              
7591 0 0       0 # $0 --> $0
7592 0         0 elsif ($char[$i] =~ /\A \$ 0 \z/oxms) {
7593             if ($ignorecase) {
7594             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7595             }
7596 0 0       0 }
7597 0         0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) 0 (?>\s*) \} \z/oxms) {
7598             if ($ignorecase) {
7599             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7600             }
7601             }
7602              
7603             # $$ --> $$
7604             elsif ($char[$i] =~ /\A \$\$ \z/oxms) {
7605             }
7606              
7607             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
7608 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
7609 0 0       0 elsif ($char[$i] =~ /\A \$ ((?>[1-9][0-9]*)) \z/oxms) {
7610 0         0 $char[$i] = e_capture($1);
7611             if ($ignorecase) {
7612             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7613             }
7614 0         0 }
7615 0 0       0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
7616 0         0 $char[$i] = e_capture($1);
7617             if ($ignorecase) {
7618             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7619             }
7620             }
7621              
7622 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
7623 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ (?:$qq_bracket)*? \] ) \z/oxms) {
7624 0         0 $char[$i] = e_capture($1.'->'.$2);
7625             if ($ignorecase) {
7626             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7627             }
7628             }
7629              
7630 0         0 # $$foo{ ... } --> $ $foo->{ ... }
7631 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ (?:$qq_brace)*? \} ) \z/oxms) {
7632 0         0 $char[$i] = e_capture($1.'->'.$2);
7633             if ($ignorecase) {
7634             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7635             }
7636             }
7637              
7638 0         0 # $$foo
7639 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) \z/oxms) {
7640 0         0 $char[$i] = e_capture($1);
7641             if ($ignorecase) {
7642             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7643             }
7644             }
7645              
7646 0 50       0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
7647 8         167 elsif ($char[$i] =~ /\A ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) \z/oxmsgc) {
7648             if ($ignorecase) {
7649             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::PREMATCH())]}';
7650 0         0 }
7651             else {
7652             $char[$i] = '@{[Eutf2::PREMATCH()]}';
7653             }
7654             }
7655              
7656 8 50       33 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
7657 8         162 elsif ($char[$i] =~ /\A ( \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) \z/oxmsgc) {
7658             if ($ignorecase) {
7659             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::MATCH())]}';
7660 0         0 }
7661             else {
7662             $char[$i] = '@{[Eutf2::MATCH()]}';
7663             }
7664             }
7665              
7666 8 50       31 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
7667 6         102 elsif ($char[$i] =~ /\A ( \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) \z/oxmsgc) {
7668             if ($ignorecase) {
7669             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::POSTMATCH())]}';
7670 0         0 }
7671             else {
7672             $char[$i] = '@{[Eutf2::POSTMATCH()]}';
7673             }
7674             }
7675              
7676 6 0       22 # ${ foo }
7677 0         0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ((?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* )) \} \z/oxms) {
7678             if ($ignorecase) {
7679             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7680             }
7681             }
7682              
7683 0         0 # ${ ... }
7684 0 0       0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ( .+ ) \} \z/oxms) {
7685 0         0 $char[$i] = e_capture($1);
7686             if ($ignorecase) {
7687             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7688             }
7689             }
7690              
7691 0         0 # $scalar or @array
7692 42 100       112 elsif ($char[$i] =~ /\A [\$\@].+ /oxms) {
7693 42         124 $char[$i] = e_string($char[$i]);
7694             if ($ignorecase) {
7695             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
7696             }
7697             }
7698              
7699 9 100 66     30 # quote character before ? + * {
    50          
7700             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
7701             if ($char[$i-1] =~ /\A (?:[\x00-\xFF]|\\[0-7]{2,3}|\\x[0-9-A-Fa-f]{1,2}) \z/oxms) {
7702 188         1439 }
7703 0 0       0 elsif (($ope =~ /\A m? \z/oxms) and ($delimiter eq '?')) {
7704 0         0 my $char = $char[$i-1];
7705             if ($char[$i] eq '{') {
7706             die __FILE__, qq{: "MULTIBYTE{n}" should be "(MULTIBYTE){n}" in m?? (and shift \$1,\$2,\$3,...) ($char){n}\n};
7707 0         0 }
7708             else {
7709             die __FILE__, qq{: "MULTIBYTE$char[$i]" should be "(MULTIBYTE)$char[$i]" in m?? (and shift \$1,\$2,\$3,...) ($char)$char[$i]\n};
7710             }
7711 0         0 }
7712             else {
7713             $char[$i-1] = '(?:' . $char[$i-1] . ')';
7714             }
7715             }
7716             }
7717 187         765  
7718 1344 50       2377 # make regexp string
7719 1344 0 0     2688 $modifier =~ tr/i//d;
7720 0         0 if ($left_e > $right_e) {
7721             if (($ope =~ /\A m? \z/oxms) and ($delimiter eq '?')) {
7722             return join '', $ope, $delimiter, $anchor, @char, '>]}' x ($left_e - $right_e), $matched, $end_delimiter, $modifier;
7723 0         0 }
7724             else {
7725             return join '', $ope, $delimiter, $anchor, '(?:', @char, '>]}' x ($left_e - $right_e), ')', $matched, $end_delimiter, $modifier;
7726 0 100 100     0 }
7727 1344         6905 }
7728             if (($ope =~ /\A m? \z/oxms) and ($delimiter eq '?')) {
7729             return join '', $ope, $delimiter, $anchor, @char, $matched, $end_delimiter, $modifier;
7730 32         259 }
7731             else {
7732             return join '', $ope, $delimiter, $anchor, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
7733             }
7734             }
7735              
7736             #
7737             # double quote stuff
7738 1312     540 0 11642 #
7739             sub qq_stuff {
7740             my($delimiter,$end_delimiter,$stuff) = @_;
7741 540 100       781  
7742 540         1072 # scalar variable or array variable
7743             if ($stuff =~ /\A [\$\@] /oxms) {
7744             return $stuff;
7745             }
7746 300         969  
  240         568  
7747 320         775 # quote by delimiter
7748 240 50       578 my %octet = map {$_ => 1} ($stuff =~ /\G ([\x00-\xFF]) /oxmsg);
7749 240 50       404 for my $char (qw( ! " $ % & * + - . / : = ? @ ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
7750 240 50       397 next if $char eq $delimiter;
7751 240         414 next if $char eq $end_delimiter;
7752             if (not $octet{$char}) {
7753             return join '', 'qq', $char, $stuff, $char;
7754 240         896 }
7755             }
7756             return join '', 'qq', '<', $stuff, '>';
7757             }
7758              
7759             #
7760             # escape regexp (m'', qr'', and m''b, qr''b)
7761 0     15 0 0 #
7762 15   100     76 sub e_qr_q {
7763             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
7764 15         69 $modifier ||= '';
7765 15 50       30  
7766 15         37 $modifier =~ tr/p//d;
7767 0         0 if ($modifier =~ /([adlu])/oxms) {
7768 0 0       0 my $line = 0;
7769 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
7770 0         0 if ($filename ne __FILE__) {
7771             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
7772             last;
7773 0         0 }
7774             }
7775             die qq{Unsupported modifier "$1" used at line $line.\n};
7776 0         0 }
7777              
7778             $slash = 'div';
7779 15 100       27  
    100          
7780 15         43 # literal null string pattern
7781 8         13 if ($string eq '') {
7782 8         9 $modifier =~ tr/bB//d;
7783             $modifier =~ tr/i//d;
7784             return join '', $ope, $delimiter, $end_delimiter, $modifier;
7785             }
7786              
7787 8         35 # with /b /B modifier
7788             elsif ($modifier =~ tr/bB//d) {
7789             return e_qr_qb($ope,$delimiter,$end_delimiter,$string,$modifier);
7790             }
7791              
7792 3         11 # without /b /B modifier
7793             else {
7794             return e_qr_qt($ope,$delimiter,$end_delimiter,$string,$modifier);
7795             }
7796             }
7797              
7798             #
7799             # escape regexp (m'', qr'')
7800 4     4 0 22 #
7801             sub e_qr_qt {
7802 4 50       40 my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
7803              
7804             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
7805 4         14  
7806             # split regexp
7807             my @char = $string =~ /\G((?>
7808             [^\x80-\xFF\\\[\$\@\/] |
7809             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
7810             \[\^ |
7811             \[\: (?>[a-z]+) \:\] |
7812             \[\:\^ (?>[a-z]+) \:\] |
7813             [\$\@\/] |
7814             \\ (?:$q_char) |
7815             (?:$q_char)
7816             ))/oxmsg;
7817 4         436  
7818 4 50 33     35 # unescape character
    50 33        
    50 66        
    50          
    50          
    50          
7819             for (my $i=0; $i <= $#char; $i++) {
7820             if (0) {
7821             }
7822 5         42  
7823 0         0 # open character class [...]
7824 0 0       0 elsif ($char[$i] eq '[') {
7825 0         0 my $left = $i;
7826             if ($char[$i+1] eq ']') {
7827 0         0 $i++;
7828 0 0       0 }
7829 0         0 while (1) {
7830             if (++$i > $#char) {
7831 0 0       0 die __FILE__, ": Unmatched [] in regexp\n";
7832 0         0 }
7833             if ($char[$i] eq ']') {
7834             my $right = $i;
7835 0         0  
7836             # [...]
7837 0         0 splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
7838 0         0  
7839             $i = $left;
7840             last;
7841             }
7842             }
7843             }
7844              
7845 0         0 # open character class [^...]
7846 0 0       0 elsif ($char[$i] eq '[^') {
7847 0         0 my $left = $i;
7848             if ($char[$i+1] eq ']') {
7849 0         0 $i++;
7850 0 0       0 }
7851 0         0 while (1) {
7852             if (++$i > $#char) {
7853 0 0       0 die __FILE__, ": Unmatched [] in regexp\n";
7854 0         0 }
7855             if ($char[$i] eq ']') {
7856             my $right = $i;
7857 0         0  
7858             # [^...]
7859 0         0 splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
7860 0         0  
7861             $i = $left;
7862             last;
7863             }
7864             }
7865             }
7866              
7867 0         0 # escape $ @ / and \
7868             elsif ($char[$i] =~ /\A [\$\@\/\\] \z/oxms) {
7869             $char[$i] = '\\' . $char[$i];
7870             }
7871              
7872 0         0 # rewrite character class or escape character
7873             elsif (my $char = character_class($char[$i],$modifier)) {
7874             $char[$i] = $char;
7875             }
7876              
7877 0 0       0 # /i modifier
7878 0         0 elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
7879             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
7880             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
7881 0         0 }
7882             else {
7883             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
7884             }
7885             }
7886              
7887 0 0       0 # quote character before ? + * {
7888             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
7889             if ($char[$i-1] =~ /\A [\x00-\xFF] \z/oxms) {
7890 0         0 }
7891             else {
7892             $char[$i-1] = '(?:' . $char[$i-1] . ')';
7893             }
7894             }
7895 0         0 }
7896 4         8  
7897             $delimiter = '/';
7898 4         7 $end_delimiter = '/';
7899 4         7  
7900             $modifier =~ tr/i//d;
7901             return join '', $ope, $delimiter, $anchor, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
7902             }
7903              
7904             #
7905             # escape regexp (m''b, qr''b)
7906 4     3 0 52 #
7907             sub e_qr_qb {
7908             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
7909 3         8  
7910             # split regexp
7911             my @char = $string =~ /\G ((?>[^\\]|\\\\|[\x00-\xFF])) /oxmsg;
7912 3         15  
7913 3 50       10 # unescape character
    50          
7914             for (my $i=0; $i <= $#char; $i++) {
7915             if (0) {
7916             }
7917 9         32  
7918             # remain \\
7919             elsif ($char[$i] eq '\\\\') {
7920             }
7921              
7922 0         0 # escape $ @ / and \
7923             elsif ($char[$i] =~ /\A [\$\@\/\\] \z/oxms) {
7924             $char[$i] = '\\' . $char[$i];
7925             }
7926 0         0 }
7927 3         5  
7928 3         5 $delimiter = '/';
7929             $end_delimiter = '/';
7930             return join '', $ope, $delimiter, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
7931             }
7932              
7933             #
7934             # escape regexp (s/here//)
7935 3     110 0 20 #
7936 110   100     365 sub e_s1 {
7937             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
7938 110         495 $modifier ||= '';
7939 110 50       205  
7940 110         368 $modifier =~ tr/p//d;
7941 0         0 if ($modifier =~ /([adlu])/oxms) {
7942 0 0       0 my $line = 0;
7943 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
7944 0         0 if ($filename ne __FILE__) {
7945             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
7946             last;
7947 0         0 }
7948             }
7949             die qq{Unsupported modifier "$1" used at line $line.\n};
7950 0         0 }
7951              
7952             $slash = 'div';
7953 110 100       238  
    100          
7954 110         419 # literal null string pattern
7955 8         9 if ($string eq '') {
7956 8         11 $modifier =~ tr/bB//d;
7957             $modifier =~ tr/i//d;
7958             return join '', $ope, $delimiter, $end_delimiter, $modifier;
7959             }
7960              
7961             # /b /B modifier
7962             elsif ($modifier =~ tr/bB//d) {
7963 8 50       48  
7964 1         3 # choice again delimiter
7965 0         0 if ($delimiter =~ / [\@:] /oxms) {
  0         0  
7966 0 0       0 my @char = $string =~ /\G ([\x00-\xFF]) /oxmsg;
    0          
    0          
    0          
7967 0         0 my %octet = map {$_ => 1} @char;
7968 0         0 if (not $octet{')'}) {
7969             $delimiter = '(';
7970             $end_delimiter = ')';
7971 0         0 }
7972 0         0 elsif (not $octet{'}'}) {
7973             $delimiter = '{';
7974             $end_delimiter = '}';
7975 0         0 }
7976 0         0 elsif (not $octet{']'}) {
7977             $delimiter = '[';
7978             $end_delimiter = ']';
7979 0         0 }
7980 0         0 elsif (not $octet{'>'}) {
7981             $delimiter = '<';
7982             $end_delimiter = '>';
7983 0         0 }
7984 0 0       0 else {
7985 0         0 for my $char (qw( ! " $ % & * + - . / = ? ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
7986 0         0 if (not $octet{$char}) {
7987 0         0 $delimiter = $char;
7988             $end_delimiter = $char;
7989             last;
7990             }
7991             }
7992             }
7993 0         0 }
7994 1         1  
7995             my $prematch = '';
7996             return join '', $ope, $delimiter, $prematch, '(?:', $string, ')', $matched, $end_delimiter, $modifier;
7997 1 100       9 }
7998 101         329  
7999             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
8000             my $metachar = qr/[\@\\|[\]{^]/oxms;
8001 101         579  
8002             # split regexp
8003             my @char = $string =~ /\G((?>
8004             [^\x80-\xFF\\\$\@\[\(]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
8005             \\ (?>[1-9][0-9]*) |
8006             \\g (?>\s*) (?>[1-9][0-9]*) |
8007             \\g (?>\s*) \{ (?>\s*) (?>[1-9][0-9]*) (?>\s*) \} |
8008             \\g (?>\s*) \{ (?>\s*) - (?>\s*) (?>[1-9][0-9]*) (?>\s*) \} |
8009             \\x (?>[0-9A-Fa-f]{1,2}) |
8010             \\ (?>[0-7]{2,3}) |
8011             \\c [\x40-\x5F] |
8012             \\x\{ (?>[0-9A-Fa-f]+) \} |
8013             \\o\{ (?>[0-7]+) \} |
8014             \\[bBNpP]\{ (?>[^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} |
8015             \\ $q_char |
8016             \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} |
8017             \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} |
8018             \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} |
8019             [\$\@] $qq_variable |
8020             \$ (?>\s* [0-9]+) |
8021             \$ (?>\s*) \{ (?>\s* [0-9]+ \s*) \} |
8022             \$ \$ (?![\w\{]) |
8023             \$ (?>\s*) \$ (?>\s*) $qq_variable |
8024             \[\^ |
8025             \[\: (?>[a-z]+) :\] |
8026             \[\:\^ (?>[a-z]+) :\] |
8027             \(\? |
8028             $q_char
8029             ))/oxmsg;
8030 101 50       77607  
8031 101         2163 # choice again delimiter
  0         0  
8032 0 0       0 if ($delimiter =~ / [\@:] /oxms) {
    0          
    0          
    0          
8033 0         0 my %octet = map {$_ => 1} @char;
8034 0         0 if (not $octet{')'}) {
8035             $delimiter = '(';
8036             $end_delimiter = ')';
8037 0         0 }
8038 0         0 elsif (not $octet{'}'}) {
8039             $delimiter = '{';
8040             $end_delimiter = '}';
8041 0         0 }
8042 0         0 elsif (not $octet{']'}) {
8043             $delimiter = '[';
8044             $end_delimiter = ']';
8045 0         0 }
8046 0         0 elsif (not $octet{'>'}) {
8047             $delimiter = '<';
8048             $end_delimiter = '>';
8049 0         0 }
8050 0 0       0 else {
8051 0         0 for my $char (qw( ! " $ % & * + - . / = ? ^ ` | ~ ), "\x00".."\x1F", "\x7F", "\xFF") {
8052 0         0 if (not $octet{$char}) {
8053 0         0 $delimiter = $char;
8054             $end_delimiter = $char;
8055             last;
8056             }
8057             }
8058             }
8059             }
8060 0         0  
  101         328  
8061             # count '('
8062 425         869 my $parens = grep { $_ eq '(' } @char;
8063 101         166  
8064 101         158 my $left_e = 0;
8065             my $right_e = 0;
8066             for (my $i=0; $i <= $#char; $i++) {
8067 101 50 33     354  
    50 33        
    100          
    100          
    50          
    50          
8068 346         12875 # "\L\u" --> "\u\L"
8069             if (($char[$i] eq '\L') and ($char[$i+1] eq '\u')) {
8070             @char[$i,$i+1] = @char[$i+1,$i];
8071             }
8072              
8073 0         0 # "\U\l" --> "\l\U"
8074             elsif (($char[$i] eq '\U') and ($char[$i+1] eq '\l')) {
8075             @char[$i,$i+1] = @char[$i+1,$i];
8076             }
8077              
8078 0         0 # octal escape sequence
8079             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
8080             $char[$i] = Eutf2::octchr($1);
8081             }
8082              
8083 1         5 # hexadecimal escape sequence
8084             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
8085             $char[$i] = Eutf2::hexchr($1);
8086             }
8087              
8088             # \b{...} --> b\{...}
8089             # \B{...} --> B\{...}
8090             # \N{CHARNAME} --> N\{CHARNAME}
8091             # \p{PROPERTY} --> p\{PROPERTY}
8092 1         4 # \P{PROPERTY} --> P\{PROPERTY}
8093             elsif ($char[$i] =~ /\A \\ ([bBNpP]) ( \{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
8094             $char[$i] = $1 . '\\' . $2;
8095             }
8096              
8097 0         0 # \p, \P, \X --> p, P, X
8098             elsif ($char[$i] =~ /\A \\ ( [pPX] ) \z/oxms) {
8099             $char[$i] = $1;
8100 0 50 66     0 }
    100 66        
    50 100        
    100          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    50          
    50          
    100          
    100          
8101              
8102             if (0) {
8103             }
8104 346         1487  
8105 0 0 0     0 # join separated multiple-octet
    0 0        
    0 0        
      0        
      0        
      0        
8106 0         0 elsif ($char[$i] =~ /\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms) {
8107             if ( ($i+3 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+3]) == 3) and (CORE::eval(sprintf '"%s%s%s%s"', @char[$i..$i+3]) =~ /\A $q_char \z/oxms)) {
8108             $char[$i] .= join '', splice @char, $i+1, 3;
8109 0         0 }
8110             elsif (($i+2 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+2]) == 2) and (CORE::eval(sprintf '"%s%s%s"', @char[$i..$i+2]) =~ /\A $q_char \z/oxms)) {
8111             $char[$i] .= join '', splice @char, $i+1, 2;
8112 0         0 }
8113             elsif (($i+1 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, $char[$i+1 ]) == 1) and (CORE::eval(sprintf '"%s%s"', @char[$i..$i+1]) =~ /\A $q_char \z/oxms)) {
8114             $char[$i] .= join '', splice @char, $i+1, 1;
8115             }
8116             }
8117              
8118 0         0 # open character class [...]
8119 20 50       33 elsif ($char[$i] eq '[') {
8120 20         72 my $left = $i;
8121             if ($char[$i+1] eq ']') {
8122 0         0 $i++;
8123 20 50       33 }
8124 79         128 while (1) {
8125             if (++$i > $#char) {
8126 0 100       0 die __FILE__, ": Unmatched [] in regexp\n";
8127 79         293 }
8128             if ($char[$i] eq ']') {
8129             my $right = $i;
8130 20 50       32  
8131 20         133 # [...]
  0         0  
8132             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
8133             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
8134 0         0 }
8135             else {
8136             splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
8137 20         92 }
8138 20         40  
8139             $i = $left;
8140             last;
8141             }
8142             }
8143             }
8144              
8145 20         63 # open character class [^...]
8146 0 0       0 elsif ($char[$i] eq '[^') {
8147 0         0 my $left = $i;
8148             if ($char[$i+1] eq ']') {
8149 0         0 $i++;
8150 0 0       0 }
8151 0         0 while (1) {
8152             if (++$i > $#char) {
8153 0 0       0 die __FILE__, ": Unmatched [] in regexp\n";
8154 0         0 }
8155             if ($char[$i] eq ']') {
8156             my $right = $i;
8157 0 0       0  
8158 0         0 # [^...]
  0         0  
8159             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
8160             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_not_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
8161 0         0 }
8162             else {
8163             splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
8164 0         0 }
8165 0         0  
8166             $i = $left;
8167             last;
8168             }
8169             }
8170             }
8171              
8172 0         0 # rewrite character class or escape character
8173             elsif (my $char = character_class($char[$i],$modifier)) {
8174             $char[$i] = $char;
8175             }
8176              
8177 11 50       25 # /i modifier
8178 3         7 elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
8179             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
8180             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
8181 3         7 }
8182             else {
8183             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
8184             }
8185             }
8186              
8187 0 50       0 # \u \l \U \L \F \Q \E
8188 8         26 elsif ($char[$i] =~ /\A [<>] \z/oxms) {
8189             if ($right_e < $left_e) {
8190             $char[$i] = '\\' . $char[$i];
8191             }
8192 0         0 }
8193 0         0 elsif ($char[$i] eq '\u') {
8194             $char[$i] = '@{[Eutf2::ucfirst qq<';
8195             $left_e++;
8196 0         0 }
8197 0         0 elsif ($char[$i] eq '\l') {
8198             $char[$i] = '@{[Eutf2::lcfirst qq<';
8199             $left_e++;
8200 0         0 }
8201 0         0 elsif ($char[$i] eq '\U') {
8202             $char[$i] = '@{[Eutf2::uc qq<';
8203             $left_e++;
8204 0         0 }
8205 0         0 elsif ($char[$i] eq '\L') {
8206             $char[$i] = '@{[Eutf2::lc qq<';
8207             $left_e++;
8208 0         0 }
8209 0         0 elsif ($char[$i] eq '\F') {
8210             $char[$i] = '@{[Eutf2::fc qq<';
8211             $left_e++;
8212 0         0 }
8213 5         10 elsif ($char[$i] eq '\Q') {
8214             $char[$i] = '@{[CORE::quotemeta qq<';
8215             $left_e++;
8216 5 50       11 }
8217 5         16 elsif ($char[$i] eq '\E') {
8218 5         6 if ($right_e < $left_e) {
8219             $char[$i] = '>]}';
8220             $right_e++;
8221 5         13 }
8222             else {
8223             $char[$i] = '';
8224             }
8225 0         0 }
8226 0 0       0 elsif ($char[$i] eq '\Q') {
8227 0         0 while (1) {
8228             if (++$i > $#char) {
8229 0 0       0 last;
8230 0         0 }
8231             if ($char[$i] eq '\E') {
8232             last;
8233             }
8234             }
8235             }
8236             elsif ($char[$i] eq '\E') {
8237             }
8238              
8239             # \0 --> \0
8240             elsif ($char[$i] =~ /\A \\ (?>\s*) 0 \z/oxms) {
8241             }
8242              
8243             # \g{N}, \g{-N}
8244              
8245             # P.108 Using Simple Patterns
8246             # in Chapter 7: In the World of Regular Expressions
8247             # of ISBN 978-0-596-52010-6 Learning Perl, Fifth Edition
8248              
8249             # P.221 Capturing
8250             # in Chapter 5: Pattern Matching
8251             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
8252              
8253             # \g{-1}, \g{-2}, \g{-3} --> \g{-1}, \g{-2}, \g{-3}
8254             elsif ($char[$i] =~ /\A \\g (?>\s*) \{ (?>\s*) - (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
8255             }
8256              
8257             # \g{1}, \g{2}, \g{3} --> \g{2}, \g{3}, \g{4} (only when multibyte anchoring is enable)
8258             elsif ($char[$i] =~ /\A \\g (?>\s*) \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
8259             }
8260              
8261             # \g1, \g2, \g3 --> \g2, \g3, \g4 (only when multibyte anchoring is enable)
8262             elsif ($char[$i] =~ /\A \\g (?>\s*) ((?>[1-9][0-9]*)) \z/oxms) {
8263             }
8264              
8265             # \1, \2, \3 --> \2, \3, \4 (only when multibyte anchoring is enable)
8266             elsif ($char[$i] =~ /\A \\ (?>\s*) ((?>[1-9][0-9]*)) \z/oxms) {
8267             }
8268              
8269 0 0       0 # $0 --> $0
8270 0         0 elsif ($char[$i] =~ /\A \$ 0 \z/oxms) {
8271             if ($ignorecase) {
8272             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8273             }
8274 0 0       0 }
8275 0         0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) 0 (?>\s*) \} \z/oxms) {
8276             if ($ignorecase) {
8277             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8278             }
8279             }
8280              
8281             # $$ --> $$
8282             elsif ($char[$i] =~ /\A \$\$ \z/oxms) {
8283             }
8284              
8285             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
8286 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
8287 0 0       0 elsif ($char[$i] =~ /\A \$ ((?>[1-9][0-9]*)) \z/oxms) {
8288 0         0 $char[$i] = e_capture($1);
8289             if ($ignorecase) {
8290             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8291             }
8292 0         0 }
8293 0 0       0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
8294 0         0 $char[$i] = e_capture($1);
8295             if ($ignorecase) {
8296             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8297             }
8298             }
8299              
8300 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
8301 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ (?:$qq_bracket)*? \] ) \z/oxms) {
8302 0         0 $char[$i] = e_capture($1.'->'.$2);
8303             if ($ignorecase) {
8304             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8305             }
8306             }
8307              
8308 0         0 # $$foo{ ... } --> $ $foo->{ ... }
8309 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ (?:$qq_brace)*? \} ) \z/oxms) {
8310 0         0 $char[$i] = e_capture($1.'->'.$2);
8311             if ($ignorecase) {
8312             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8313             }
8314             }
8315              
8316 0         0 # $$foo
8317 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) \z/oxms) {
8318 0         0 $char[$i] = e_capture($1);
8319             if ($ignorecase) {
8320             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8321             }
8322             }
8323              
8324 0 50       0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
8325 4         17 elsif ($char[$i] =~ /\A ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) \z/oxmsgc) {
8326             if ($ignorecase) {
8327             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::PREMATCH())]}';
8328 0         0 }
8329             else {
8330             $char[$i] = '@{[Eutf2::PREMATCH()]}';
8331             }
8332             }
8333              
8334 4 50       16 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
8335 4         15 elsif ($char[$i] =~ /\A ( \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) \z/oxmsgc) {
8336             if ($ignorecase) {
8337             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::MATCH())]}';
8338 0         0 }
8339             else {
8340             $char[$i] = '@{[Eutf2::MATCH()]}';
8341             }
8342             }
8343              
8344 4 50       14 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
8345 3         11 elsif ($char[$i] =~ /\A ( \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) \z/oxmsgc) {
8346             if ($ignorecase) {
8347             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::POSTMATCH())]}';
8348 0         0 }
8349             else {
8350             $char[$i] = '@{[Eutf2::POSTMATCH()]}';
8351             }
8352             }
8353              
8354 3 0       11 # ${ foo }
8355 0         0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ((?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* )) \} \z/oxms) {
8356             if ($ignorecase) {
8357             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8358             }
8359             }
8360              
8361 0         0 # ${ ... }
8362 0 0       0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ( .+ ) \} \z/oxms) {
8363 0         0 $char[$i] = e_capture($1);
8364             if ($ignorecase) {
8365             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8366             }
8367             }
8368              
8369 0         0 # $scalar or @array
8370 9 50       38 elsif ($char[$i] =~ /\A [\$\@].+ /oxms) {
8371 9         53 $char[$i] = e_string($char[$i]);
8372             if ($ignorecase) {
8373             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
8374             }
8375             }
8376              
8377 0 50       0 # quote character before ? + * {
8378             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
8379             if ($char[$i-1] =~ /\A (?:[\x00-\xFF]|\\[0-7]{2,3}|\\x[0-9-A-Fa-f]{1,2}) \z/oxms) {
8380 23         124 }
8381             else {
8382             $char[$i-1] = '(?:' . $char[$i-1] . ')';
8383             }
8384             }
8385             }
8386 23         131  
8387 101         247 # make regexp string
8388 101 50       189 my $prematch = '';
8389 101         300 $modifier =~ tr/i//d;
8390             if ($left_e > $right_e) {
8391 0         0 return join '', $ope, $delimiter, $prematch, '(?:', @char, '>]}' x ($left_e - $right_e), ')', $matched, $end_delimiter, $modifier;
8392             }
8393             return join '', $ope, $delimiter, $prematch, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
8394             }
8395              
8396             #
8397             # escape regexp (s'here'' or s'here''b)
8398 101     22 0 1259 #
8399 22   100     52 sub e_s1_q {
8400             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
8401 22         68 $modifier ||= '';
8402 22 50       29  
8403 22         49 $modifier =~ tr/p//d;
8404 0         0 if ($modifier =~ /([adlu])/oxms) {
8405 0 0       0 my $line = 0;
8406 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
8407 0         0 if ($filename ne __FILE__) {
8408             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
8409             last;
8410 0         0 }
8411             }
8412             die qq{Unsupported modifier "$1" used at line $line.\n};
8413 0         0 }
8414              
8415             $slash = 'div';
8416 22 100       34  
    100          
8417 22         58 # literal null string pattern
8418 8         9 if ($string eq '') {
8419 8         10 $modifier =~ tr/bB//d;
8420             $modifier =~ tr/i//d;
8421             return join '', $ope, $delimiter, $end_delimiter, $modifier;
8422             }
8423              
8424 8         41 # with /b /B modifier
8425             elsif ($modifier =~ tr/bB//d) {
8426             return e_s1_qb($ope,$delimiter,$end_delimiter,$string,$modifier);
8427             }
8428              
8429 1         3 # without /b /B modifier
8430             else {
8431             return e_s1_qt($ope,$delimiter,$end_delimiter,$string,$modifier);
8432             }
8433             }
8434              
8435             #
8436             # escape regexp (s'here'')
8437 13     13 0 33 #
8438             sub e_s1_qt {
8439 13 50       27 my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
8440              
8441             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
8442 13         39  
8443             # split regexp
8444             my @char = $string =~ /\G((?>
8445             [^\x80-\xFF\\\[\$\@\/] |
8446             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
8447             \[\^ |
8448             \[\: (?>[a-z]+) \:\] |
8449             \[\:\^ (?>[a-z]+) \:\] |
8450             [\$\@\/] |
8451             \\ (?:$q_char) |
8452             (?:$q_char)
8453             ))/oxmsg;
8454 13         462  
8455 13 50 33     49 # unescape character
    50 33        
    50 66        
    100          
    50          
    50          
8456             for (my $i=0; $i <= $#char; $i++) {
8457             if (0) {
8458             }
8459 25         95  
8460 0         0 # open character class [...]
8461 0 0       0 elsif ($char[$i] eq '[') {
8462 0         0 my $left = $i;
8463             if ($char[$i+1] eq ']') {
8464 0         0 $i++;
8465 0 0       0 }
8466 0         0 while (1) {
8467             if (++$i > $#char) {
8468 0 0       0 die __FILE__, ": Unmatched [] in regexp\n";
8469 0         0 }
8470             if ($char[$i] eq ']') {
8471             my $right = $i;
8472 0         0  
8473             # [...]
8474 0         0 splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
8475 0         0  
8476             $i = $left;
8477             last;
8478             }
8479             }
8480             }
8481              
8482 0         0 # open character class [^...]
8483 0 0       0 elsif ($char[$i] eq '[^') {
8484 0         0 my $left = $i;
8485             if ($char[$i+1] eq ']') {
8486 0         0 $i++;
8487 0 0       0 }
8488 0         0 while (1) {
8489             if (++$i > $#char) {
8490 0 0       0 die __FILE__, ": Unmatched [] in regexp\n";
8491 0         0 }
8492             if ($char[$i] eq ']') {
8493             my $right = $i;
8494 0         0  
8495             # [^...]
8496 0         0 splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
8497 0         0  
8498             $i = $left;
8499             last;
8500             }
8501             }
8502             }
8503              
8504 0         0 # escape $ @ / and \
8505             elsif ($char[$i] =~ /\A [\$\@\/\\] \z/oxms) {
8506             $char[$i] = '\\' . $char[$i];
8507             }
8508              
8509 0         0 # rewrite character class or escape character
8510             elsif (my $char = character_class($char[$i],$modifier)) {
8511             $char[$i] = $char;
8512             }
8513              
8514 6 0       13 # /i modifier
8515 0         0 elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
8516             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
8517             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
8518 0         0 }
8519             else {
8520             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
8521             }
8522             }
8523              
8524 0 0       0 # quote character before ? + * {
8525             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
8526             if ($char[$i-1] =~ /\A [\x00-\xFF] \z/oxms) {
8527 0         0 }
8528             else {
8529             $char[$i-1] = '(?:' . $char[$i-1] . ')';
8530             }
8531             }
8532 0         0 }
8533 13         21  
8534 13         28 $modifier =~ tr/i//d;
8535 13         16 $delimiter = '/';
8536 13         41 $end_delimiter = '/';
8537             my $prematch = '';
8538             return join '', $ope, $delimiter, $prematch, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
8539             }
8540              
8541             #
8542             # escape regexp (s'here''b)
8543 13     1 0 94 #
8544             sub e_s1_qb {
8545             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
8546 1         2  
8547             # split regexp
8548             my @char = $string =~ /\G (?>[^\\]|\\\\|[\x00-\xFF]) /oxmsg;
8549 1         5  
8550 1 50       4 # unescape character
    50          
8551             for (my $i=0; $i <= $#char; $i++) {
8552             if (0) {
8553             }
8554 3         10  
8555             # remain \\
8556             elsif ($char[$i] eq '\\\\') {
8557             }
8558              
8559 0         0 # escape $ @ / and \
8560             elsif ($char[$i] =~ /\A [\$\@\/\\] \z/oxms) {
8561             $char[$i] = '\\' . $char[$i];
8562             }
8563 0         0 }
8564 1         2  
8565 1         2 $delimiter = '/';
8566 1         1 $end_delimiter = '/';
8567             my $prematch = '';
8568             return join '', $ope, $delimiter, $prematch, '(?:', @char, ')', $matched, $end_delimiter, $modifier;
8569             }
8570              
8571             #
8572             # escape regexp (s''here')
8573 1     17 0 7 #
8574             sub e_s2_q {
8575 17         36 my($ope,$delimiter,$end_delimiter,$string) = @_;
8576              
8577 17         24 $slash = 'div';
8578 17         211  
8579 17 100       73 my @char = $string =~ / \G (?>[^\x80-\xFF\\]|\\\\|$q_char) /oxmsg;
    100          
8580             for (my $i=0; $i <= $#char; $i++) {
8581             if (0) {
8582             }
8583 9         32  
8584             # not escape \\
8585             elsif ($char[$i] =~ /\A \\\\ \z/oxms) {
8586             }
8587              
8588 0         0 # escape $ @ / and \
8589             elsif ($char[$i] =~ /\A [\$\@\/\\] \z/oxms) {
8590             $char[$i] = '\\' . $char[$i];
8591             }
8592 5         14 }
8593              
8594             return join '', $ope, $delimiter, @char, $end_delimiter;
8595             }
8596              
8597             #
8598             # escape regexp (s/here/and here/modifier)
8599 17     132 0 59 #
8600 132   100     1185 sub e_sub {
8601             my($variable,$delimiter1,$pattern,$end_delimiter1,$delimiter2,$replacement,$end_delimiter2,$modifier) = @_;
8602 132         619 $modifier ||= '';
8603 132 50       258  
8604 132         374 $modifier =~ tr/p//d;
8605 0         0 if ($modifier =~ /([adlu])/oxms) {
8606 0 0       0 my $line = 0;
8607 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
8608 0         0 if ($filename ne __FILE__) {
8609             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
8610             last;
8611 0         0 }
8612             }
8613             die qq{Unsupported modifier "$1" used at line $line.\n};
8614 0 100       0 }
8615 132         348  
8616 37         54 if ($variable eq '') {
8617             $variable = '$_';
8618             $bind_operator = ' =~ ';
8619 37         46 }
8620              
8621             $slash = 'div';
8622              
8623             # P.128 Start of match (or end of previous match): \G
8624             # P.130 Advanced Use of \G with Perl
8625             # in Chapter 3: Overview of Regular Expression Features and Flavors
8626             # P.312 Iterative Matching: Scalar Context, with /g
8627             # in Chapter 7: Perl
8628             # of ISBN 0-596-00289-0 Mastering Regular Expressions, Second edition
8629              
8630             # P.181 Where You Left Off: The \G Assertion
8631             # in Chapter 5: Pattern Matching
8632             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
8633              
8634             # P.220 Where You Left Off: The \G Assertion
8635             # in Chapter 5: Pattern Matching
8636 132         481 # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
8637 132         220  
8638             my $e_modifier = $modifier =~ tr/e//d;
8639 132         228 my $r_modifier = $modifier =~ tr/r//d;
8640 132 50       206  
8641 132         431 my $my = '';
8642 0         0 if ($variable =~ s/\A \( (?>\s*) ( (?>(?: local \b | my \b | our \b | state \b )?) .+ ) \) \z/$1/oxms) {
8643 0         0 $my = $variable;
8644             $variable =~ s/ (?: local \b | my \b | our \b | state \b ) (?>\s*) //oxms;
8645             $variable =~ s/ = .+ \z//oxms;
8646 0         0 }
8647 132         468  
8648             (my $variable_basename = $variable) =~ s/ [\[\{].* \z//oxms;
8649             $variable_basename =~ s/ \s+ \z//oxms;
8650 132         350  
8651 132 100       199 # quote replacement string
8652 132         316 my $e_replacement = '';
8653 17         32 if ($e_modifier >= 1) {
8654             $e_replacement = e_qq('', '', '', $replacement);
8655             $e_modifier--;
8656 17 100       24 }
8657 115         369 else {
8658             if ($delimiter2 eq "'") {
8659             $e_replacement = e_s2_q('qq', '/', '/', $replacement);
8660 17         39 }
8661             else {
8662             $e_replacement = e_qq ('qq', $delimiter2, $end_delimiter2, $replacement);
8663             }
8664 98         281 }
8665              
8666             my $sub = '';
8667 132 100       242  
8668 132 100       386 # with /r
8669             if ($r_modifier) {
8670             if (0) {
8671             }
8672 8         27  
8673 0 50       0 # s///gr without multibyte anchoring
8674             elsif ($modifier =~ /g/oxms) {
8675             $sub = sprintf(
8676             # 1 2 3 4 5
8677             q,
8678              
8679             $variable, # 1
8680             ($delimiter1 eq "'") ? # 2
8681             e_s1_q('m', $delimiter1, $end_delimiter1, $pattern, $modifier) : # :
8682             e_s1 ('m', $delimiter1, $end_delimiter1, $pattern, $modifier), # :
8683             $s_matched, # 3
8684             $e_replacement, # 4
8685             '$Eutf2::re_r=CORE::eval $Eutf2::re_r; ' x $e_modifier, # 5
8686             );
8687             }
8688              
8689             # s///r
8690 4         15 else {
8691              
8692 4 50       6 my $prematch = q{$`};
8693              
8694             $sub = sprintf(
8695             # 1 2 3 4 5 6 7
8696             q<(%s =~ %s) ? CORE::eval{%s local $^W=0; local $Eutf2::re_r=%s; %s"%s$Eutf2::re_r$'" } : %s>,
8697              
8698             $variable, # 1
8699             ($delimiter1 eq "'") ? # 2
8700             e_s1_q('m', $delimiter1, $end_delimiter1, $pattern, $modifier) : # :
8701             e_s1 ('m', $delimiter1, $end_delimiter1, $pattern, $modifier), # :
8702             $s_matched, # 3
8703             $e_replacement, # 4
8704             '$Eutf2::re_r=CORE::eval $Eutf2::re_r; ' x $e_modifier, # 5
8705             $prematch, # 6
8706             $variable, # 7
8707             );
8708             }
8709 4 50       14  
8710 8         26 # $var !~ s///r doesn't make sense
8711             if ($bind_operator =~ / !~ /oxms) {
8712             $sub = q{die("$0: Using !~ with s///r doesn't make sense"), } . $sub;
8713             }
8714             }
8715              
8716 0 100       0 # without /r
8717             else {
8718             if (0) {
8719             }
8720 124         340  
8721 0 100       0 # s///g without multibyte anchoring
    100          
8722             elsif ($modifier =~ /g/oxms) {
8723             $sub = sprintf(
8724             # 1 2 3 4 5 6 7 8
8725             q,
8726              
8727             $variable, # 1
8728             ($delimiter1 eq "'") ? # 2
8729             e_s1_q('m', $delimiter1, $end_delimiter1, $pattern, $modifier) : # :
8730             e_s1 ('m', $delimiter1, $end_delimiter1, $pattern, $modifier), # :
8731             $s_matched, # 3
8732             $e_replacement, # 4
8733             '$Eutf2::re_r=CORE::eval $Eutf2::re_r; ' x $e_modifier, # 5
8734             $variable, # 6
8735             $variable, # 7
8736             ($bind_operator =~ / !~ /oxms) ? '!' : '', # 8
8737             );
8738             }
8739              
8740             # s///
8741 29         141 else {
8742              
8743 95 100       217 my $prematch = q{$`};
    100          
8744              
8745             $sub = sprintf(
8746              
8747             ($bind_operator =~ / =~ /oxms) ?
8748              
8749             # 1 2 3 4 5 6 7 8
8750             q<(%s%s%s) ? CORE::eval{%s local $^W=0; local $Eutf2::re_r=%s; %s%s="%s$Eutf2::re_r$'"; 1 } : undef> :
8751              
8752             # 1 2 3 4 5 6 7 8
8753             q<(%s%s%s) ? 1 : CORE::eval{%s local $^W=0; local $Eutf2::re_r=%s; %s%s="%s$Eutf2::re_r$'"; undef }>,
8754              
8755             $variable, # 1
8756             $bind_operator, # 2
8757             ($delimiter1 eq "'") ? # 3
8758             e_s1_q('m', $delimiter1, $end_delimiter1, $pattern, $modifier) : # :
8759             e_s1 ('m', $delimiter1, $end_delimiter1, $pattern, $modifier), # :
8760             $s_matched, # 4
8761             $e_replacement, # 5
8762             '$Eutf2::re_r=CORE::eval $Eutf2::re_r; ' x $e_modifier, # 6
8763             $variable, # 7
8764             $prematch, # 8
8765             );
8766             }
8767             }
8768 95 50       750  
8769 132         410 # (my $foo = $bar) =~ s/// --> (my $foo = $bar, CORE::eval { ... })[1]
8770             if ($my ne '') {
8771             $sub = "($my, $sub)[1]";
8772             }
8773 0         0  
8774 132         228 # clear s/// variable
8775             $sub_variable = '';
8776 132         190 $bind_operator = '';
8777              
8778             return $sub;
8779             }
8780              
8781             #
8782             # escape regexp of split qr//
8783 132     101 0 4434 #
8784 101   100     439 sub e_split {
8785             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
8786 101         546 $modifier ||= '';
8787 101 50       167  
8788 101         413 $modifier =~ tr/p//d;
8789 0         0 if ($modifier =~ /([adlu])/oxms) {
8790 0 0       0 my $line = 0;
8791 0         0 for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
8792 0         0 if ($filename ne __FILE__) {
8793             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
8794             last;
8795 0         0 }
8796             }
8797             die qq{Unsupported modifier "$1" used at line $line.\n};
8798 0         0 }
8799              
8800             $slash = 'div';
8801 101 50       188  
8802 101         226 # /b /B modifier
8803             if ($modifier =~ tr/bB//d) {
8804             return join '', 'split', $ope, $delimiter, $string, $end_delimiter, $modifier;
8805 0 50       0 }
8806 101         256  
8807             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
8808             my $metachar = qr/[\@\\|[\]{^]/oxms;
8809 101         376  
8810             # split regexp
8811             my @char = $string =~ /\G((?>
8812             [^\x80-\xFF\\\$\@\[\(]|(?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
8813             \\x (?>[0-9A-Fa-f]{1,2}) |
8814             \\ (?>[0-7]{2,3}) |
8815             \\c [\x40-\x5F] |
8816             \\x\{ (?>[0-9A-Fa-f]+) \} |
8817             \\o\{ (?>[0-7]+) \} |
8818             \\[bBNpP]\{ (?>[^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} |
8819             \\ $q_char |
8820             \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} |
8821             \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} |
8822             \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} |
8823             [\$\@] $qq_variable |
8824             \$ (?>\s* [0-9]+) |
8825             \$ (?>\s*) \{ (?>\s* [0-9]+ \s*) \} |
8826             \$ \$ (?![\w\{]) |
8827             \$ (?>\s*) \$ (?>\s*) $qq_variable |
8828             \[\^ |
8829             \[\: (?>[a-z]+) :\] |
8830             \[\:\^ (?>[a-z]+) :\] |
8831             \(\? |
8832             $q_char
8833 101         24569 ))/oxmsg;
8834 101         838  
8835 101         147 my $left_e = 0;
8836             my $right_e = 0;
8837             for (my $i=0; $i <= $#char; $i++) {
8838 101 50 33     308  
    50 33        
    100          
    100          
    50          
    50          
8839 284         1631 # "\L\u" --> "\u\L"
8840             if (($char[$i] eq '\L') and ($char[$i+1] eq '\u')) {
8841             @char[$i,$i+1] = @char[$i+1,$i];
8842             }
8843              
8844 0         0 # "\U\l" --> "\l\U"
8845             elsif (($char[$i] eq '\U') and ($char[$i+1] eq '\l')) {
8846             @char[$i,$i+1] = @char[$i+1,$i];
8847             }
8848              
8849 0         0 # octal escape sequence
8850             elsif ($char[$i] =~ /\A \\o \{ ([0-7]+) \} \z/oxms) {
8851             $char[$i] = Eutf2::octchr($1);
8852             }
8853              
8854 1         4 # hexadecimal escape sequence
8855             elsif ($char[$i] =~ /\A \\x \{ ([0-9A-Fa-f]+) \} \z/oxms) {
8856             $char[$i] = Eutf2::hexchr($1);
8857             }
8858              
8859             # \b{...} --> b\{...}
8860             # \B{...} --> B\{...}
8861             # \N{CHARNAME} --> N\{CHARNAME}
8862             # \p{PROPERTY} --> p\{PROPERTY}
8863 1         4 # \P{PROPERTY} --> P\{PROPERTY}
8864             elsif ($char[$i] =~ /\A \\ ([bBNpP]) ( \{ ([^\x80-\xFF0-9\}][^\x80-\xFF\}]*) \} ) \z/oxms) {
8865             $char[$i] = $1 . '\\' . $2;
8866             }
8867              
8868 0         0 # \p, \P, \X --> p, P, X
8869             elsif ($char[$i] =~ /\A \\ ( [pPX] ) \z/oxms) {
8870             $char[$i] = $1;
8871 0 50 100     0 }
    100 33        
    100 33        
    100 100        
    100          
    50          
    100          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    50          
    100          
    100          
    100          
    50          
    50          
    100          
    100          
8872              
8873             if (0) {
8874             }
8875 284         1294  
8876 0 0 0     0 # join separated multiple-octet
    0 0        
    0 0        
      0        
      0        
      0        
8877 0         0 elsif ($char[$i] =~ /\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms) {
8878             if ( ($i+3 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+3]) == 3) and (CORE::eval(sprintf '"%s%s%s%s"', @char[$i..$i+3]) =~ /\A $q_char \z/oxms)) {
8879             $char[$i] .= join '', splice @char, $i+1, 3;
8880 0         0 }
8881             elsif (($i+2 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, @char[$i+1..$i+2]) == 2) and (CORE::eval(sprintf '"%s%s%s"', @char[$i..$i+2]) =~ /\A $q_char \z/oxms)) {
8882             $char[$i] .= join '', splice @char, $i+1, 2;
8883 0         0 }
8884             elsif (($i+1 <= $#char) and (grep(/\A (?: \\ [0-7]{2,3} | \\x [0-9A-Fa-f]{1,2}) \z/oxms, $char[$i+1 ]) == 1) and (CORE::eval(sprintf '"%s%s"', @char[$i..$i+1]) =~ /\A $q_char \z/oxms)) {
8885             $char[$i] .= join '', splice @char, $i+1, 1;
8886             }
8887             }
8888              
8889 0         0 # open character class [...]
8890 3 50       6 elsif ($char[$i] eq '[') {
8891 3         8 my $left = $i;
8892             if ($char[$i+1] eq ']') {
8893 0         0 $i++;
8894 3 50       5 }
8895 7         10 while (1) {
8896             if (++$i > $#char) {
8897 0 100       0 die __FILE__, ": Unmatched [] in regexp\n";
8898 7         14 }
8899             if ($char[$i] eq ']') {
8900             my $right = $i;
8901 3 50       3  
8902 3         17 # [...]
  0         0  
8903             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
8904             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
8905 0         0 }
8906             else {
8907             splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
8908 3         14 }
8909 3         3  
8910             $i = $left;
8911             last;
8912             }
8913             }
8914             }
8915              
8916 3         19 # open character class [^...]
8917 1 50       3 elsif ($char[$i] eq '[^') {
8918 1         4 my $left = $i;
8919             if ($char[$i+1] eq ']') {
8920 0         0 $i++;
8921 1 50       2 }
8922 2         4 while (1) {
8923             if (++$i > $#char) {
8924 0 100       0 die __FILE__, ": Unmatched [] in regexp\n";
8925 2         6 }
8926             if ($char[$i] eq ']') {
8927             my $right = $i;
8928 1 50       2  
8929 1         8 # [^...]
  0         0  
8930             if (grep(/\A [\$\@]/oxms,@char[$left+1..$right-1]) >= 1) {
8931             splice @char, $left, $right-$left+1, sprintf(q{@{[Eutf2::charlist_not_qr(%s,'%s')]}}, join(',', map {qq_stuff($delimiter,$end_delimiter,$_)} @char[$left+1..$right-1]), $modifier);
8932 0         0 }
8933             else {
8934             splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
8935 1         6 }
8936 1         3  
8937             $i = $left;
8938             last;
8939             }
8940             }
8941             }
8942              
8943 1         3 # rewrite character class or escape character
8944             elsif (my $char = character_class($char[$i],$modifier)) {
8945             $char[$i] = $char;
8946             }
8947              
8948             # P.794 29.2.161. split
8949             # in Chapter 29: Functions
8950             # of ISBN 0-596-00027-8 Programming Perl Third Edition.
8951              
8952             # P.951 split
8953             # in Chapter 27: Functions
8954             # of ISBN 978-0-596-00492-7 Programming Perl 4th Edition.
8955              
8956             # said "The //m modifier is assumed when you split on the pattern /^/",
8957             # but perl5.008 is not so. Therefore, this software adds //m.
8958             # (and so on)
8959              
8960 5         15 # split(m/^/) --> split(m/^/m)
8961             elsif (($char[$i] eq '^') and ($modifier !~ /m/oxms)) {
8962             $modifier .= 'm';
8963             }
8964              
8965 11 0       33 # /i modifier
8966 0         0 elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
8967             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
8968             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
8969 0         0 }
8970             else {
8971             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
8972             }
8973             }
8974              
8975 0 50       0 # \u \l \U \L \F \Q \E
8976 2         7 elsif ($char[$i] =~ /\A ([<>]) \z/oxms) {
8977             if ($right_e < $left_e) {
8978             $char[$i] = '\\' . $char[$i];
8979             }
8980 0         0 }
8981 0         0 elsif ($char[$i] eq '\u') {
8982             $char[$i] = '@{[Eutf2::ucfirst qq<';
8983             $left_e++;
8984 0         0 }
8985 0         0 elsif ($char[$i] eq '\l') {
8986             $char[$i] = '@{[Eutf2::lcfirst qq<';
8987             $left_e++;
8988 0         0 }
8989 0         0 elsif ($char[$i] eq '\U') {
8990             $char[$i] = '@{[Eutf2::uc qq<';
8991             $left_e++;
8992 0         0 }
8993 0         0 elsif ($char[$i] eq '\L') {
8994             $char[$i] = '@{[Eutf2::lc qq<';
8995             $left_e++;
8996 0         0 }
8997 0         0 elsif ($char[$i] eq '\F') {
8998             $char[$i] = '@{[Eutf2::fc qq<';
8999             $left_e++;
9000 0         0 }
9001 0         0 elsif ($char[$i] eq '\Q') {
9002             $char[$i] = '@{[CORE::quotemeta qq<';
9003             $left_e++;
9004 0 0       0 }
9005 0         0 elsif ($char[$i] eq '\E') {
9006 0         0 if ($right_e < $left_e) {
9007             $char[$i] = '>]}';
9008             $right_e++;
9009 0         0 }
9010             else {
9011             $char[$i] = '';
9012             }
9013 0         0 }
9014 0 0       0 elsif ($char[$i] eq '\Q') {
9015 0         0 while (1) {
9016             if (++$i > $#char) {
9017 0 0       0 last;
9018 0         0 }
9019             if ($char[$i] eq '\E') {
9020             last;
9021             }
9022             }
9023             }
9024             elsif ($char[$i] eq '\E') {
9025             }
9026              
9027 0 0       0 # $0 --> $0
9028 0         0 elsif ($char[$i] =~ /\A \$ 0 \z/oxms) {
9029             if ($ignorecase) {
9030             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9031             }
9032 0 0       0 }
9033 0         0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) 0 (?>\s*) \} \z/oxms) {
9034             if ($ignorecase) {
9035             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9036             }
9037             }
9038              
9039             # $$ --> $$
9040             elsif ($char[$i] =~ /\A \$\$ \z/oxms) {
9041             }
9042              
9043             # $1, $2, $3 --> $2, $3, $4 after s/// with multibyte anchoring
9044 0         0 # $1, $2, $3 --> $1, $2, $3 otherwise
9045 0 0       0 elsif ($char[$i] =~ /\A \$ ((?>[1-9][0-9]*)) \z/oxms) {
9046 0         0 $char[$i] = e_capture($1);
9047             if ($ignorecase) {
9048             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9049             }
9050 0         0 }
9051 0 0       0 elsif ($char[$i] =~ /\A \$ \{ (?>\s*) ((?>[1-9][0-9]*)) (?>\s*) \} \z/oxms) {
9052 0         0 $char[$i] = e_capture($1);
9053             if ($ignorecase) {
9054             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9055             }
9056             }
9057              
9058 0         0 # $$foo[ ... ] --> $ $foo->[ ... ]
9059 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \[ (?:$qq_bracket)*? \] ) \z/oxms) {
9060 0         0 $char[$i] = e_capture($1.'->'.$2);
9061             if ($ignorecase) {
9062             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9063             }
9064             }
9065              
9066 0         0 # $$foo{ ... } --> $ $foo->{ ... }
9067 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) ( \{ (?:$qq_brace)*? \} ) \z/oxms) {
9068 0         0 $char[$i] = e_capture($1.'->'.$2);
9069             if ($ignorecase) {
9070             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9071             }
9072             }
9073              
9074 0         0 # $$foo
9075 0 0       0 elsif ($char[$i] =~ /\A \$ ((?> \$ [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* )) \z/oxms) {
9076 0         0 $char[$i] = e_capture($1);
9077             if ($ignorecase) {
9078             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9079             }
9080             }
9081              
9082 0 50       0 # $`, ${`}, $PREMATCH, ${PREMATCH}, ${^PREMATCH} --> Eutf2::PREMATCH()
9083 12         36 elsif ($char[$i] =~ /\A ( \$` | \$\{`\} | \$ (?>\s*) PREMATCH | \$ (?>\s*) \{ (?>\s*) PREMATCH (?>\s*) \} | \$ (?>\s*) \{\^PREMATCH\} ) \z/oxmsgc) {
9084             if ($ignorecase) {
9085             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::PREMATCH())]}';
9086 0         0 }
9087             else {
9088             $char[$i] = '@{[Eutf2::PREMATCH()]}';
9089             }
9090             }
9091              
9092 12 50       68 # $&, ${&}, $MATCH, ${MATCH}, ${^MATCH} --> Eutf2::MATCH()
9093 12         35 elsif ($char[$i] =~ /\A ( \$& | \$\{&\} | \$ (?>\s*) MATCH | \$ (?>\s*) \{ (?>\s*) MATCH (?>\s*) \} | \$ (?>\s*) \{\^MATCH\} ) \z/oxmsgc) {
9094             if ($ignorecase) {
9095             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::MATCH())]}';
9096 0         0 }
9097             else {
9098             $char[$i] = '@{[Eutf2::MATCH()]}';
9099             }
9100             }
9101              
9102 12 50       69 # $POSTMATCH, ${POSTMATCH}, ${^POSTMATCH} --> Eutf2::POSTMATCH()
9103 9         22 elsif ($char[$i] =~ /\A ( \$ (?>\s*) POSTMATCH | \$ (?>\s*) \{ (?>\s*) POSTMATCH (?>\s*) \} | \$ (?>\s*) \{\^POSTMATCH\} ) \z/oxmsgc) {
9104             if ($ignorecase) {
9105             $char[$i] = '@{[Eutf2::ignorecase(Eutf2::POSTMATCH())]}';
9106 0         0 }
9107             else {
9108             $char[$i] = '@{[Eutf2::POSTMATCH()]}';
9109             }
9110             }
9111              
9112 9 0       54 # ${ foo }
9113 0         0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ((?> \s* [A-Za-z_][A-Za-z0-9_]*(?: ::[A-Za-z_][A-Za-z0-9_]*)* \s* )) \} \z/oxms) {
9114             if ($ignorecase) {
9115             $char[$i] = '@{[Eutf2::ignorecase(' . $1 . ')]}';
9116             }
9117             }
9118              
9119 0         0 # ${ ... }
9120 0 0       0 elsif ($char[$i] =~ /\A \$ (?>\s*) \{ ( .+ ) \} \z/oxms) {
9121 0         0 $char[$i] = e_capture($1);
9122             if ($ignorecase) {
9123             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9124             }
9125             }
9126              
9127 0         0 # $scalar or @array
9128 3 50       9 elsif ($char[$i] =~ /\A [\$\@].+ /oxms) {
9129 3         15 $char[$i] = e_string($char[$i]);
9130             if ($ignorecase) {
9131             $char[$i] = '@{[Eutf2::ignorecase(' . $char[$i] . ')]}';
9132             }
9133             }
9134              
9135 0 100       0 # quote character before ? + * {
9136             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
9137             if ($char[$i-1] =~ /\A (?:[\x00-\xFF]|\\[0-7]{2,3}|\\x[0-9-A-Fa-f]{1,2}) \z/oxms) {
9138 7         40 }
9139             else {
9140             $char[$i-1] = '(?:' . $char[$i-1] . ')';
9141             }
9142             }
9143             }
9144 4         23  
9145 101 50       204 # make regexp string
9146 101         226 $modifier =~ tr/i//d;
9147             if ($left_e > $right_e) {
9148 0         0 return join '', 'Eutf2::split', $ope, $delimiter, @char, '>]}' x ($left_e - $right_e), $end_delimiter, $modifier;
9149             }
9150             return join '', 'Eutf2::split', $ope, $delimiter, @char, $end_delimiter, $modifier;
9151             }
9152              
9153             #
9154             # escape regexp of split qr''
9155 101     0 0 1568 #
9156 0   0       sub e_split_q {
9157             my($ope,$delimiter,$end_delimiter,$string,$modifier) = @_;
9158 0           $modifier ||= '';
9159 0 0          
9160 0           $modifier =~ tr/p//d;
9161 0           if ($modifier =~ /([adlu])/oxms) {
9162 0 0         my $line = 0;
9163 0           for (my $i=0; my($package,$filename,$use_line,$subroutine) = caller($i); $i++) {
9164 0           if ($filename ne __FILE__) {
9165             $line = $use_line + (CORE::substr($_,0,pos($_)) =~ tr/\n//) + 1;
9166             last;
9167 0           }
9168             }
9169             die qq{Unsupported modifier "$1" used at line $line.\n};
9170 0           }
9171              
9172             $slash = 'div';
9173 0 0          
9174 0           # /b /B modifier
9175             if ($modifier =~ tr/bB//d) {
9176             return join '', 'split', $ope, $delimiter, $string, $end_delimiter, $modifier;
9177 0 0         }
9178              
9179             my $ignorecase = ($modifier =~ /i/oxms) ? 1 : 0;
9180 0            
9181             # split regexp
9182             my @char = $string =~ /\G((?>
9183             [^\x80-\xFF\\\[] |
9184             (?:[\xC2-\xDF]|[\xE0-\xE0][\xA0-\xBF]|[\xE1-\xEC][\x80-\xBF]|[\xED-\xED][\x80-\x9F]|[\xEE-\xEF][\x80-\xBF]|[\xF0-\xF0][\x90-\xBF][\x80-\xBF]|[\xF1-\xF3][\x80-\xBF][\x80-\xBF]|[\xF4-\xF4][\x80-\x8F][\x80-\xBF])[\x80-\xBF] |
9185             \[\^ |
9186             \[\: (?>[a-z]+) \:\] |
9187             \[\:\^ (?>[a-z]+) \:\] |
9188             \\ (?:$q_char) |
9189             (?:$q_char)
9190             ))/oxmsg;
9191 0            
9192 0 0 0       # unescape character
    0 0        
    0 0        
    0 0        
    0          
    0          
9193             for (my $i=0; $i <= $#char; $i++) {
9194             if (0) {
9195             }
9196 0            
9197 0           # open character class [...]
9198 0 0         elsif ($char[$i] eq '[') {
9199 0           my $left = $i;
9200             if ($char[$i+1] eq ']') {
9201 0           $i++;
9202 0 0         }
9203 0           while (1) {
9204             if (++$i > $#char) {
9205 0 0         die __FILE__, ": Unmatched [] in regexp\n";
9206 0           }
9207             if ($char[$i] eq ']') {
9208             my $right = $i;
9209 0            
9210             # [...]
9211 0           splice @char, $left, $right-$left+1, Eutf2::charlist_qr(@char[$left+1..$right-1], $modifier);
9212 0            
9213             $i = $left;
9214             last;
9215             }
9216             }
9217             }
9218              
9219 0           # open character class [^...]
9220 0 0         elsif ($char[$i] eq '[^') {
9221 0           my $left = $i;
9222             if ($char[$i+1] eq ']') {
9223 0           $i++;
9224 0 0         }
9225 0           while (1) {
9226             if (++$i > $#char) {
9227 0 0         die __FILE__, ": Unmatched [] in regexp\n";
9228 0           }
9229             if ($char[$i] eq ']') {
9230             my $right = $i;
9231 0            
9232             # [^...]
9233 0           splice @char, $left, $right-$left+1, Eutf2::charlist_not_qr(@char[$left+1..$right-1], $modifier);
9234 0            
9235             $i = $left;
9236             last;
9237             }
9238             }
9239             }
9240              
9241 0           # rewrite character class or escape character
9242             elsif (my $char = character_class($char[$i],$modifier)) {
9243             $char[$i] = $char;
9244             }
9245              
9246 0           # split(m/^/) --> split(m/^/m)
9247             elsif (($char[$i] eq '^') and ($modifier !~ /m/oxms)) {
9248             $modifier .= 'm';
9249             }
9250              
9251 0 0         # /i modifier
9252 0           elsif ($ignorecase and ($char[$i] =~ /\A [\x00-\xFF] \z/oxms) and (Eutf2::uc($char[$i]) ne Eutf2::fc($char[$i]))) {
9253             if (CORE::length(Eutf2::fc($char[$i])) == 1) {
9254             $char[$i] = '[' . Eutf2::uc($char[$i]) . Eutf2::fc($char[$i]) . ']';
9255 0           }
9256             else {
9257             $char[$i] = '(?:' . Eutf2::uc($char[$i]) . '|' . Eutf2::fc($char[$i]) . ')';
9258             }
9259             }
9260              
9261 0 0         # quote character before ? + * {
9262             elsif (($i >= 1) and ($char[$i] =~ /\A [\?\+\*\{] \z/oxms)) {
9263             if ($char[$i-1] =~ /\A [\x00-\xFF] \z/oxms) {
9264 0           }
9265             else {
9266             $char[$i-1] = '(?:' . $char[$i-1] . ')';
9267             }
9268             }
9269 0           }
9270 0            
9271             $modifier =~ tr/i//d;
9272             return join '', 'Eutf2::split', $ope, $delimiter, @char, $end_delimiter, $modifier;
9273             }
9274              
9275             #
9276             # instead of Carp::carp
9277 0     0 0   #
9278 0           sub carp {
9279             my($package,$filename,$line) = caller(1);
9280             print STDERR "@_ at $filename line $line.\n";
9281             }
9282              
9283             #
9284             # instead of Carp::croak
9285 0     0 0   #
9286 0           sub croak {
9287 0           my($package,$filename,$line) = caller(1);
9288             print STDERR "@_ at $filename line $line.\n";
9289             die "\n";
9290             }
9291              
9292             #
9293             # instead of Carp::cluck
9294 0     0 0   #
9295 0           sub cluck {
9296 0           my $i = 0;
9297 0           my @cluck = ();
9298 0           while (my($package,$filename,$line,$subroutine) = caller($i)) {
9299             push @cluck, "[$i] $filename($line) $package::$subroutine\n";
9300 0           $i++;
9301 0           }
9302 0           print STDERR CORE::reverse @cluck;
9303             print STDERR "\n";
9304             print STDERR @_;
9305             }
9306              
9307             #
9308             # instead of Carp::confess
9309 0     0 0   #
9310 0           sub confess {
9311 0           my $i = 0;
9312 0           my @confess = ();
9313 0           while (my($package,$filename,$line,$subroutine) = caller($i)) {
9314             push @confess, "[$i] $filename($line) $package::$subroutine\n";
9315 0           $i++;
9316 0           }
9317 0           print STDERR CORE::reverse @confess;
9318 0           print STDERR "\n";
9319             print STDERR @_;
9320             die "\n";
9321             }
9322              
9323             1;
9324              
9325             __END__