From 893574b2edd855e6387d76efe956bd834f75bbbd Mon Sep 17 00:00:00 2001 From: echel0n Date: Sat, 31 May 2014 06:16:18 -0700 Subject: [PATCH] Reverted new regex changes, not compatible with enough platforms to warrent keeping. --- lib/regex/Python25/__init__.py | 1 - lib/regex/Python25/_regex.pyd | Bin 302080 -> 0 bytes lib/regex/Python26/__init__.py | 1 - lib/regex/Python26/_regex.pyd | Bin 304128 -> 0 bytes lib/regex/Python26/_regex.so | Bin 1092655 -> 0 bytes lib/regex/Python27/__init__.py | 1 - lib/regex/Python27/_regex.pyd | Bin 304128 -> 0 bytes lib/regex/Python27/_regex.so | Bin 1092775 -> 0 bytes lib/regex/__init__.py | 1 - lib/regex/_regex.c | 22557 ------------------------------ lib/regex/_regex.h | 228 - lib/regex/_regex_core.py | 4086 ------ lib/regex/_regex_unicode.c | 12748 ----------------- lib/regex/_regex_unicode.h | 218 - lib/regex/regex.py | 684 - lib/regex/test_regex.py | 3230 ----- sickbeard/name_parser/parser.py | 13 +- 17 files changed, 6 insertions(+), 43762 deletions(-) delete mode 100644 lib/regex/Python25/__init__.py delete mode 100644 lib/regex/Python25/_regex.pyd delete mode 100644 lib/regex/Python26/__init__.py delete mode 100644 lib/regex/Python26/_regex.pyd delete mode 100644 lib/regex/Python26/_regex.so delete mode 100644 lib/regex/Python27/__init__.py delete mode 100644 lib/regex/Python27/_regex.pyd delete mode 100644 lib/regex/Python27/_regex.so delete mode 100644 lib/regex/__init__.py delete mode 100644 lib/regex/_regex.c delete mode 100644 lib/regex/_regex.h delete mode 100644 lib/regex/_regex_core.py delete mode 100644 lib/regex/_regex_unicode.c delete mode 100644 lib/regex/_regex_unicode.h delete mode 100644 lib/regex/regex.py delete mode 100644 lib/regex/test_regex.py diff --git a/lib/regex/Python25/__init__.py b/lib/regex/Python25/__init__.py deleted file mode 100644 index 8b137891..00000000 --- a/lib/regex/Python25/__init__.py +++ /dev/null @@ -1 +0,0 @@ - diff --git a/lib/regex/Python25/_regex.pyd b/lib/regex/Python25/_regex.pyd deleted file mode 100644 index ad8e1c76f832426900788ce60022ac7a6f877b4d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 302080 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ɯQUedWmdZk8skkI|6R57Z-wWZH}M9ke0Nw5$iU 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 R9N0POOoFT@u77?F{C|wLp49*V diff --git a/lib/regex/Python26/__init__.py b/lib/regex/Python26/__init__.py deleted file mode 100644 index 8b137891..00000000 --- a/lib/regex/Python26/__init__.py +++ /dev/null @@ -1 +0,0 @@ - diff --git a/lib/regex/Python26/_regex.pyd b/lib/regex/Python26/_regex.pyd deleted file mode 100644 index 0616ec7da825eba630315a471dc68ed7fff0a881..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 304128 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

Q>Aj=P1 zU4hh$saH`~qpjGM(ho(y!Zo1?Mc5skE1s_v=bPm^Y0EamN<6fXL(DzgIxoE^2Y(yR z3EgTBIktx!n!b!1{`ymV*;3``A@%}kn|nTQqK^k|1{*h zWL*$>5S?ui?gNNN>elA=hePFzUJXsr*EdI2;6Z&)f53)f9YF%+zm6aY@gt>c%+r<; zj6Z(2?2FYn^TU9XJTp3BK|Ve);nOyv%>04ImAO6JXyT5m$ zpzrT*usA(whtVJ4IJvw*eE5*w`5feM{iWXcH#CbAskyiviGFakcOibgO^Dc}cm6kf z3k)URFT|z3cQOVa3ygi>B$V0Vqm+;v$bxevv|kCQ2qpZM<1dEF&U58mv~KFVW{ksv zPR2MWEl#|}wqM`{5m{cVv|Tk8m-q1QQf#L-iE~0)6X+Mz55d>Jkf_!9>DPLE0T5sN zss=AZT51NZK=4>g&0svw<+B1J)Rr2KpCv6dJp8_}rD{mGkcUvkFL4jGUB+t2a0i=R zqp;9L2-u-B;>t-}B1LiCAW{_0T%<%SJPv0iB@V?dZLk77Oj-TnRd7>U;hiJ*aAMrZ z;YksO(f4RE*qu!&Xhlb27qM*0PtQYxaL-juYJ`YaaT$I~D--~B851qdpg%ZQMuG@! zO+^;7oiw2zg5~+UP|}U#Kj^2dBT`=FNke%vdFwn9@EL!)uAsvkuQa8>42 zM)^!wi+p}EuNtqbs0mo=^~O&F4z#WMBS^7|#kn}X_)@*ti=~eP=%~+P4GY`vdvSA3 zGU6F^pi|Yq3(A$Ynz2Bc7foO*g=!?iJ?}Bqh)j;7 z8j(jv8&bi2CmJ_mEUfVK0D~7oFFdj zwN_A0G2Rncl!z@%wWsXcImwnhY2OB=nVQnA?bx?-MBk>e-XPkJGyFLsMMCREFURR5 zt4FinnLQdE1@pE$UC810vreT?&!JJ<9lb5otxta@np0_c1AJ%p>3Q%u*ci`KDpsG) zVJA-YX>?`Tr{`FGx}JSH*@xBtRv)G?azqPJ7_#S57;{9=g;3LbF3fW(Gz%ChlV9+@ zQS{t;rJ3QuR*Z0uKKi3noAO+p?4y>&o|A8kxBBKl<8rHCazT+6yN43P?@71WdqAw! zC)w%K?Q$`0W4)q#Pl3Oc>~oX5^|`z7RIEF^V!=V&YEuFC1YPgd^sZN04$GC^i3t$j zL_)v9sGzjXkiF`UU82>0mTW|~XhgkG7^c(MfLNG0snNafRJv55-d9S3O~Wd53XZj$U@>W!i>3U%R-6o=iCOrG%9p(~_QM3FB^l832P_4&v~xs|&9c zU*6gst%cJfz717_Qcir;9o?mxdE*Hf8Cl3EWyU6c7-~AItBmr>*KfCVj2AnnV4+mM z#epekPHY@I+}0RFcd$3}Q`!ACKL|TK-3dVJkP;U4pGcrUH42bf{V_ouA<$!mU6Nx7 zWCxP*nP;Vm=j8PEqV1T{U@148eVP2w?x%sz$zG^mx8VhR{8uD#!j3AZ%-YC)=3o(%(M(dt~X8ocg4k_|t4L&5SGpgSFr$sRz#)Gjnh& z+1!=6Bk?(VtPBjV!gdxcu)}6$R9HKr6P_Ffs-X2B9exyXVF?&$C;zzcXF68I1B3N9 z`6Vs4aNMCI#UGQxSOAFt5VT#eMa=6IkZ4O5$q}I(E$Y&8_&e9H)RicCD1T zNMD&Qf6lRX(iB5hHHbi+)l%Ud4IkwOxQySz^Bg>n=_nTiU`P2h3KBr-TeN@24j58% zTeNbdI<$HyAOCe|bCW3*DZj`QzNAP|4fwA^qe9D6IGMUPnR+6bdNrBapG-xQse{Q> z0q6j031fUM{JCZi*6@w-{0hWyoCw%{3Z8Qr3lQ3B&tU3&l|-~=KXX2qnE7UL4+ubAX( zG5CdurY!;N!Dp%SFz3Xrd8mwe=T0n!7#b;;*P!drlwC&oH2FInH^^5-fAs)3(a5{V zHDzzLgm?j9*x$D1H=)~dp5$%5`mVzWP|FJ3*`c+fHh1PbwBI9T!(M-f_83wwq~g<| z8|XIf7~_6q+G8@U4@4H0h-WIg9VzIqh}McZ@DP?@88{%p79_!zA!UqTpo?2xjBy2e zIal7?`qZ)`;|DnyYkbe85DAv}zGag>T+24?6FW{+>*72N#O%>0`|;z}Cs)ARZ|WjH z&+AibJIZeWZhRq|<9!15!F|PoZ^0FFP&gv|ou>twI4?B1h3ez`rVVq#z;9RX)xHPp zn>0WE+Vn9%a>n#X7HaO!c(bI_`0Lb$Yv+SSE)fn zErLVUO`7B5%UmJ1;+uzA5is)Y)emwR^uGd31rYX7^800}I zTkJ*VOWj~lh}4Z&MT#o7AF0^em{NzOyzC}n&w-uT4?qmQ>2m{`icO1KUX>Ouys?41 zU(G*AX)a`q3-AYW5%gzALvNz&dR=r1v{O?nXpyZZNY4i8uYq)4vCVHKo8KN-hEf8C zAH#}}!Fa;iq?co_1JZ{8t|p-I?vT@up+E}22)OwvnRRgJae{}N_XTmcF}2G6DHh8+ z#?hO#;S*JPzT4f(GTs>@zRVjv@CLn{z%B+S*Z~!vx!G=Z{(5Nrn=r%RTtA_|W{j^g zD)P)w5BCK60bc|T=y3z(C>?1yVw*ugIOOtUAD??4D*&IQPZRv(9rT)So#9l|eH-G( zI0A}e3An)Eon!ElgFMX!OTgn)B`cb|kKqwk|9eW?6W&!wD{W7E|AF5X4|>;#$A5UA z#xJJN75ZkF#lq-OYy>w&poxWnK}C@z8wpU1T1(y+aWN{luJ>{+ZpjBC1Iv+1-V>>M z%n_TsPoM%Q$W_{a7YQfwelPR5@z^SpSfK$*2Zt(dY86L)M}_}4Xq7z;CksU{Kul0K zO0b5D?|z|6p&~l`f~!i$70$1wn-i+Q_xUCjhaBzvVg=kM>C3@u5Z}Bszq0Md*#Ivn z%Q41z@MC>h)A|TE&M;ZuigOCo7>#)@>7WxhbAb~dVOsDV;>13Y>P^Fm?~mavOl&Tr zyu}B*wT(`Evm5y0`_V=g+<#z-Lu>CmHMo>#FJRIB<2>TLj0JaA8eFkP<>6A+M0K&g zHCns}S|x(;SD*|9IX5G<^HwlqT2F-iB*%YRvQy|Q@z`P-)yJ+!+D9KN%FTk$| zxjO?`4O5Behc&I2U(jKc!4Z_p3JgPMTA1joA4=C9Zt?(H^n%yq6p=eP$hZMuJs4D# zCSKaX<>Rw4jC08ZI18gs8Z-voAc?a8`DS?Cg2z08+{dsc{2*#P7F3!e_+7^jrNfYW z0JW7+k#s0cW~{Ks9{4@SU0Tp18~vc6R?QAM{K{WIN%TR?nM7D!5WM`{uQWZ2<}n&e zAa<^xVO&z~tOHD(!90Sks(N_t4uF`YLloF5Vav#50T{#P%_7`LhB637(RUb*hbhF6 z<1GA$&$mwVx*5`z7uYYXkT+ZP=8ebhLha%|z>3eY;SL{mP>#k7)f8teHi;w~T1e=Z zD?o6%q+y4<3oLBhTr5dn^fkG zE`3vsE&}Sn9C^e9^8%PXWd8)&kZ3*~q8Mk&D8pxtR?;V@}E7DC`jBfN+zwETN$7^AGY z0N;l)9L**Ch7{IiPy)y6AH-0JCl5Yo$J4U>1T@6p=Eh%q5cccP3K{>B!p2QuG?H5sL44|KFx8A7G25K;Q@F*-oxF00=hA@>pAH%f`X|T`h`aH^ zsCb$YG|A8JV$=ZWIigoeZSnxK{s}VkNqdy;32fWb)(WIa4qgS<&?UA7u0xZ|!Q}8z z^j-{5(BHl4^`wy?bX-(Eyq0z$pf2PX&guC9w%FX zf&QhIY2Hz53L)0$FJ2YG#3x3dM$2Zk6Z_$ceoFP-%){BlaasD;Rx>cPO`|FRiXQ^35M{w&30<=3| zqtKshXpSg1t3dkY#xUd790Z`~K5e~IA7)H-8JA!Q<68)7(92zDRae41qG|1|;PloX z#h#Lxp=ZT+t^wzX_?uFL@Qvkk`kbIoS-K2(d(ilUlhKGtg`n{gN#k_J$B<0jXWZ)4 zf9}xM=SoTkVBw)4N$F`lD22R0>&hOq?vS+Zm9)N^yfc<_d#p%RIgGhExKqhV8ekXf z>jn8QlYDx5BYBva#%W?>V-dF8@FgRLzSEwUd7~{bpL8n!leG_Et*>w0lBxn*7UVeG zz@lO)zr#`eOMKw*KHE54if|a+*=;&lZv=dp2^4HFoK7G1==!*mGCq|9_6fu-jyH~|F&jGa6!{REf_}fwpe~@Bm zg{+cmOh%7}QkH)Rc23qZjI5-%dtl9k!0f-e;Qhds zb!{60(0^}dM1JSqe9WR|=OQ7Zv7TR#-qsXEzo_acxKmpiYr3vP_HBtzflPY8Rem14 z{~6fzew{hWX!yoN@$cBBt}5S{S5K7&cZnLFeB5act8iY8jryi-=g7GugO4tI6H+

szd6?gnAi5r=x{5B-{F5(1a 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

*=e=K<2XCsd1yL%7Eh>RupUzq=y;) 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
;1-Tq<2|A9^v~k&egj8}_ije|@@e?= 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ΜS;Q%;=t7*{A9~b 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ʊl61nj?PB-8>pcHu~9 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 diff --git a/lib/regex/Python27/_regex.so b/lib/regex/Python27/_regex.so deleted file mode 100644 index 760556b7e6194a1caedb2a9c16ffc3efb9c605bf..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1092775 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

6@%JOt=py=lE<6FBa=TS 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

-j)TSGrag(9>a$6QA;?8{@pPRNKeg0el` z_Ei<RyZ#0&C2#CD?Q*Y@N{Dh9TGe~X4Q?9=0)p}yLF zaS0WaI_v?e*;8$Mp>uG_+mHkPTM)_J?_JKtrx;D;B+ zsZF*%&!ZTGv1T+!p=5zQ{bdv_U@k{axTUg|ID~3pcOlj&-QlCIxhI92HY$SdhNah1 ze~jGQ*n1xYsn*|+uUdaMoH-aRUsjwOoOMFOnb%}t_K^!a0(B@M;>68vo{nL})!GN+Nw|Jn-@qj)njLrbg2+h6!fxo< zwyzN(C-F0A=##+V1Ww*w+x!xtkD!r)j#VMgJ}fk(qf^zk+o=X2sdCJge2zl9B!NAX zkqz1L_vFG$lgyrcspmNL72az)^9bP3A2stcw{ZBt zgp^rS^5=2Y=0w|N=m<2^jXCp!PeFT+30_cOC(o3^xo0Q~k9Rj-1p*0%)RZW(%z#8` zz|BOl%f|joU{5^{DLkgV(e~hC;_%Fw{tR?7^E%g@GqyiX!FHQvtd+coY)6##Nd&`6 z%Aqr9OqV+e#u>Gk9&_e*kXqDKex{Wmt@IJQ<7kdJrf)k$O#_1k-)mMk0N(jTmXfM` z6BV^tRsKqnPcHVGv7mSW(*=$q^gi^{Gf?o|@6E-e^xR&#ht-ePpFwIWL%|E!yc(ss z06vUT^nee)5Uyan8;t_6ZjV%Dt-RNDU@*--&E?ce%Gv_`Ne9_d#8^DDw4PRPpLdF+#g+@|0s9L^U0on zYoX^|F}qjQ{w;4*9sK#~#higt_Q}a_ydsFv0`5*`9c^|8B z_%!;@n6^jgiU|bRqinYeFVVjST4UO+!&>@5RnlGf$3tWnZutnD)v?F(G!E@AO`(rq z=w%V6Cm%XA&0!Q>f=aIo(lp<^X81-avXM`uD$GEvsTIW;J=z zF&;-VZ?uiP4Ecyw=jnWe)H7Pf%CD5;OS2OwfS#KP{e9Vt{o~K^MY*%QgaLkL%i*?h z*fyv2bYRb`)LcMz9-38QB){#fBEHO;-{_9c4+y9%&+iIW3^K)2ZL)&^#IHD=}xu&?ho9O@@An zBV15<^g&Ly0t-om`XKk9@;dF8v|8h3=m%H@BQ#2eDjs6Yp)&LqIjz50SX-R|@tP`Wo;Ok%PA96zsi#mnY zcuN6FOV zD>2bl9*zC|F!l}y`(I>UC*qPu+gjumyfyWk!}t{r{>_BHf6%5YQI1nqp~^Ph%qYdh zgYO>1Ej78`2|SJ=Z3aexUzY`@{0bVn8$W2(a%R?n5FMppljv=oKVCE>BG>pCMmm`~ z)iw!2n04U0*Mr!*InKFHVBfcpux$5p?pgQ{{hratN#OBPbM}Fi&taS!9}>-11Rig3 zLA<{&VKwVBDNAh1Hg5|&QHrgL3Ab*?wAK3C^8FW`qO|4vw?Bv9!_Fi99^x>)va;6ZPKPxQrj zYBziMQq0U@@4uUf{RCWz9Q*&83ot6bPor(~`?!qY{2EM3%NxiXBGfe*Y$QCJ2^~E= zE1j8vZ0qQw5ko6xgvgP$S9I_#3|nolNXejqZ?tKPWgX{p(1|N(QvdFF)Wy4*5po|( z(NgZsn^8U&yd*jIY-Tl$R zJ+tgS?2o?xZnBbDV9$prlOs2LmN!yvzmAgI%euZ=&q3k*<%fp2`fVFqZztQjwEk)L z+dBe}yN#3YcoBE!PYr=x8{<`6@VMc918u9T*?MmG+kum9?gL!`wLU|~4m{CyZtJ<9 zwgFoe8P!hKZ1$QT!sbGHhquY1HuMpQLG{4-JV)(f!7p>1}=*c$o zK-WVj-!wJHLx^67{XxYM`Ze<#{Zz;N?z}h5FM!>L_T?M<2%sI6Z~HwCw{ZEU-_88+ znUj-kNip)=e~9>5EYIV2$i#%=J^7AHmwP()3S>UGgmYs`xaOe4Qd~%X}UkWTGQSAcJ9eGOEwtac0gI6T)bCfikDEQxY0g8^Lt_=^V>n?3$*@8HXT_) z9MU9j*%0P93#d|bl&h0%z60E5J^_lBDCGh*Ky4-|6%A(5dL)0#GETO>u=_3V$u@Lj zxA`yUuzUTCDsKib0#ATiN_*zntHa{0U#Gc5G2gOQgQW-}ncsy=3LP+KJ&?;k9Y_)U z(XM3SlTi34Yr=*9aJgm#5n&!U*_I%Sf2$LL9Gv{E+jtszpyCfhb#}{K)?prGeV?lC znE#TcVgB`m$Kyi`|L#siJpSh{y#W9FfzVO;vzLVVR}fx2{+|NLss485e{InP_-_UR zO4L#NJGLO4h4&U}PLm?r-$)1Cz6p%2?2x@`f4`jHDgQ0=!u&S?RhBf0|0h6k1Q65y zw_bc9{u#jNr2MZ{g!vzxs~JV{uX4cc%l|!`0(8&?RQWFfMko9;XNUQ}2Y;OM-{OGV z^Z#t-h4>!^MkoBo%n0)z2-Gc{c{O1m-AT#;c@?)6xsL}PSxP{!hdRFhs?v{-z7lmME;rM!sS1T z6@8p6+%jH++h<`b?oW2!{ze0%qw*IG510Rjk(x_X`ER>OgWEIzd~k=%!{t8=q)y7e za6q{H?+wztqO$Pwfg0RC3*XD{Fbn8^f5IFy8W`YTj2Yz}f9pATxe0Vlg}R97bNID* zInVqgPqT^Qeu)Ea&;1G{?m+s^{GS1wPRf52$Go*LYq`S$J|G7r~(29P=_|7&=EOKV(5yJ=ogS*UWr?XxhJ zl6R>8Q2n1xm*syag)1L=Cb}3ZKN)dL5GO1DBw?{~iM*2b@lJxy)h3Rjg~Q1<4^KZH zNB#PB8nO4pQ@^l3#QM)+phU<&O8?2Gj#WSduZjZcB0%a7#;)>q->$6_DxkGuTP?fVufx9|&tpM5TZKm4-%QT(?! z;5hux{x$r86v01g{Jr8+;xG5dK7>E6{BLz4+ROj@pHL1umH%d-bj1J9e+=^5P2}B$=`H5_pgZ#BY9j{Mk&&JD7jo{WyZZ!zO0_`F9{`{;~7_bwr@^@=vGa z9q_*b_p5a=KZHNN{GEvQ^8fW8F3A5dP&(pYNXfPSL3nxujO>5iorpO6Ke{k~pmfNe zl575i7ni>i5r_YW7v>L?j`(L&a?PLc;_`PQ(Ei%(zdV4KGCF91YQGT(9r3^O{V@Lk z;l<JIw!RTU`EC4!Ax4v6Q@1{%8NaWBIQ~ zoNj-Q5MDg_uW};V%Ri9_bS!_;KTiFdUPI|H}z0KL1f16`%hdzw4Ag>pwv0ME~9LR=5hT|1D)g9uY<8zrc`CuKphkXRg)Xl;kL0tS@}FsF-1EV2zN~nK^~X( zm-|&sHuAju%wa$~I!}IipJEkxUVix6D1OoP*JD>$pdaiFGt8yV&h2yIZVkoZChtDD z^np2@r+>D?VX4~ZsjE8SH(+y^U#}}Q<;ec9Z<~h3?GFjf?f5kT(m{K9vN6oAp77$0 zuic%9_T%f~%R!*?@%3;+C+%n42FieJm><;3thZ}Fbvk2lu0U*EFB9PkgqH8RPWUCR z3iCU^Ha@>qYc#*OLtMcM#Zk4_v&#_<%QtHL{`1l>y9&ZUGY2g8MGf;PxU(xVS@+sQS2nZm0ZTm>K5(n+nY+ivM$SG`Kzg^0Eu@ ze|vhT{2!PS=06^&ahgQlG!1UgKVi~^_@639>JHjt;Y4CCyIV2g#nC5L14j?nvD>K+ zPUw(3^}ksMtTW?Dt!e!XbN$tC(InhD5$|uiMeB=!$A5%7GeEg!Y&a8tDpJf|!037M zw-()t40@XU)A@7q|mYO!BP4)xJKh(|r7rMEHAFvE#)tljKDA8{hNc`kN2lD09Mn z-hKe~5bPG%Ww3K$C&3PdeGN9pd)|J|bKZUemfXL`9*s#);eQ0(zb8-sjI_E;ZY4YI z5-*B-E%m&enIc{C$J&onTxOiOSlquRT&C!}0Cy;8Q&{u3PQWZd8DkEIpc?iUTm(vD0|{-er1*7dx77wpmW_O==DS+JoF;^U=>2m3q@ z?Ra?qonS8`&riW#+U>l35o{9ddyvDw!fr`BZ~q#u4ZEfTd#nTa;SS&((di7nDT3A% z`1c`SkM%fj{|5GtuwApy+XG>z!mfmEhTQ{uJ?veukHOvyyqy!z+uQz0_JtU_uf>Er z<9jFu_uiQBqcPzVG2vL+Wr+VhKB)B6KgqrvL-%Vj;m-ID#J9^LB24~!Bf{iA6cHwW!xU-X#OEW)o=xJtSRJq3g@8?h9RoWw zPQ1qZTii_0^T7((bEu0p*woCVTp&^Y%&D+hMPV zZG^3brMPmqxyo>BV|^B2_1pV3A-u;O!+9dU;~gL@8j8e=I=TcULgKPne%DgMMK67Qq` zK->NU=zWBChxgAYEIyF=h^77J`{>6Jb`AXTEb*I*xWC6n=9%)F0($Z61Mgw~AdcOV zZQE@9wwjdq@L`w1_JjSR;oDMG-rxpd zeJLmxY`=hQKLGmzWFwHDoNC+tHoorrK$&eni*L}6f!nXhwjak=q9)G34^F{uDTQ2M z`{A3l8({AmX4}7*h%$|_?VF||k9|NNFru{u?gPVti?~d)-?y~>YIaW;UWif>g#I7+B#%=?aJW1 z(%_2vmErK}#`>0qU}G)vSX;LO#i|cB5nYBmsTyk=Hq@-B-3ZEJJZEF@Y|2@%e)&2S zxG31vP*XRdpBNYv{Raj)(-RO_)v|5dR%E!PuDJ=Z{l!E88)_Px*Vb&9P}vA6N?P-% zV3c~*hMLt)6BJYgw+BU2Ur|>vZdLt;l`LYhyHbtkKwT0BP#7IifnYgblpSliSL!qmhd*V-*&!BDYam_YGY@uN;~ zR@YL!kmT7@jVv~7t*#c;)hlaj8+1Unl=-?E>uR?&>&(qp6|M3*oBPZqYigU<)HVj! zHWxGnYjmrV867M()HF5AERjz(c5pz0ifFQ;sTpmR#EyK{)QJ@}4b3f$wN2d0q^PLJ zLt?9(IGF|`LEXwGPSphIH`lCKQ!R%ClnR1IK{uj=^Gd5L=2lNDDW6p}uT+KRS528x zI)AAcu*b@}u;@n8`=r|7g1u&JffN~&g6R>x#PgG=X3t*)3> zeM!ZeH_~5C@{ar+oECCfq6mv=!YU*?6Rm?4&SE)0mgAr9135uvC2OMr(Xd~0LY}p?{#R*4{ zkg$mKrPHb-OFK`8tEbJa7v2MD<8Co5-wj zpN=ep189#GnR_MM>oxgh;R-jS71yC4`duQ><70zhMJrf11teU4AMnvKW#Mvd4=t-1Il|Kon#B}CJ zkOpem)rHgppp;_ztZjn!+SD9eUQ0?UG>FC~(p2RX*)))~*Sx{QhYrOhz`s77x<#UN z?~WL?Q_|PgVV;NXJ1{6&23J9mS}DSKEp=;2YeH7zB2oz&>uNRxSxpBP=|n9XY8r!3 z4xlbHt*x&M*4C|F3pJb!X-!IxQY8+qYOLQF+`MKjG-@a&{9#+(848^<+WSu z>sEF|X>)yDL9-$Q8YCyKBPBnoJ*p|vK&4&^X~k6MK)rxd>8T#SXu6VMb4$YpCmE@- z=xvgB3_Gq;%BSi>T$9uQr7UV!I{68%T?N%TNDJ8IwY7CYspQsD3yt9yZmQ7xp>;R6 zPz9iqqdQ?eP5vNMXi(Sy#TX$aZffeC8>5{GmE##l2T;;fhN5Z|*@reZT zB)UbHF1XQ`l2~WzfbJAemQ03Q{Yzwk-69h}x5(;| zji>&T*g0;|vlpS{274-$l-|3&dwg8Oc-0{>LQ&v=?XD2uF>2^jgB&6G)LemlaCoYu4p_ia84A( zQAUVKqC`v;ZE_AON)yyyNrWkY4tKuv%I)?#fsq!z`9thUbA-Xx^?R%0-m@UE;iQ5Ag+eP zG$;daSXAP2$GAmf6Yjsu;=**KYFe z*?Y~k`&yMDKs;lZrYj703)8eb6!x<5B_t%WrwdweASE>|y=%9G?p|*O12es7hqyG} znaSbEo}yQ7(Cpm@?JqAMX$$)G?{C7$ltgSmA(QkD93)+SqO}bfGL(^UxApHf!(m3? z3N4ukF3LM{R3r>7a11P-W5-czMDv?iJgH>z6s#YomzB>T8Z&3jCP&PfBLuEv{}pEL z#TQc(gF(S`(Wu2$Me@#C5RyoEG8~u6;W{wwDfB9#dBsBSqAcM>OVwtHxKw*PbffD& z8tpPN(V*y%VY=Lw$1z^VM;>2-C(+~SqF_l;abF~m?EfOz3O4{Zh5V@s5YG`Pyy-IC z7B$2FLK7|2=ui+rFM1~p%-7mD^Eq$Zc!y2=1op?U)aG7%h2(k2do4M&%u2h_AKn5e~0rfxOc%Gg53$b z3-+tPD>-f3--o3!BL%hxY{D;Wy9bzN!TtTuZQBL+Ex5mhJqi1Hi*3J#v#_UN!*drB zYU9jvjz`C^Q1txn67mmM;rUNFF1HL?!b2X^hR=r@Nl5GhUy?}n)8LtmiCvwTxgr=0ir%76 zAI#n{1ypGyvA!Xy(EI|?4|n!4m%GG3#Ajq=3{pm857wEGt{SL#w2FL)p;3mboGV@@ z12+uW!-dulqzmW>`8Q(3MHh_}qXbR+cufL$W5&RNJ9aGIIuPT=6%`R&n(=TZ;N=c7 z)FRO~m4R1h9o`bhxCDl3DK3|wA)C+~%<^(hM`6nF432P#nG~D_Ab!?F84h&vh#o_E z{`4IgF3}D4g;{CnPfiQ!VVjaOnd4~**grW9_!_spEwFLGL6Bh}t zbj+gQ7$Kedk9K3C)pmk|a+Y^FLvJWP$5Z&oo@h>sGF;4@()3MnNpw@YbnwaD2LA48~Nm41pj!<4`$MP>FRk}h0w5tGVG7LSMJl*|)j0}H3WM=h% z4+DKKKfbNg6P;Y5_4Nn(3Z#S^3K1v|$O!WkEuclqe~Ii53_uJZ{y-sCY8pr>$PD%e zh727x%pZUb><^3_HG0fgjIyFg(BLY@Q5T$8EGCtR$q1GR8a+!X24))T2HZQK`%2}P z21{))WD+;dnGn5u_tp`!p&QSEo-%jt#l}3tm~R-BRSS$uAl`+G#A3r(Vi=bi#$`*F zF0HnfSyqi@Enl(Hs)bNjVM%3K>nv-%Wo_8Fv97)WG%v>*sb!PE;>aJ^3VxWowkdOk zGP<-fNB+R}uo%d9rMN1t5n@MNBX&j^v6D+i&#Pf~39)-mBm<7!E5tQ)vd^YT85t5n z27!lzfBwS(AN^f>?LL^+*6Xg@zyJE{5nU$^5VfYJg9mRAhsev}8)0rh0P$ZUU{ljg zH<63*&0-UUZ@GmQi?`l-_%Pu~a~qu7?~wjG6^xv_#NEo=qYQvy5sD*@xz{l=xj*pb zuYC1u_sPP4{r(5OLCKty-~1-i;jjcg7-htROog6A;iy7rS)ZCC@n9)Agv$vHZZNJb*7{fe$vzh zJ!Zs3++k=JVj|LFC0No0CIB;eG7+0Hl}VQrYWJPiLGhd@X;zJx?t{OWb@-?WP5IXS@V*f`U3XCPYk zrV&DVCs_Y8=6Bn56$EZWJwIWSt9-QJgmLO3o(IaC0+Vu&B{b{!ZtVpC#w}P`=YYi+ zoJ{V3#cdayj2@1PV4x)!&^a8X!0>pyhT9i`02H5*;4#oDlA^%z16~4ql06>7(P?53 z{oybpgS#sLbY-*#q{D_m%jsxC?Kj3)9tYs{xf7f~v?nn-*g=TfSLD7*GEcu_u6MiuX=U_(kR^`iz5kExN` zu6v)hserk7x51XaNst!WKAGa|im{Mm%lh zoUZ;&?kfR1_cys}7htEsyEi71+qpKr_`K)yArt5R!2bBnDS&Wa14nSkCAvGsPSU(c zvw9Q!&f61_X2-w32~Kt~1OaCBEe4{5qM#gSkHZJ-oi+q&+gm}yi-Z(~2TDQt_u0kZ zyc7On3hzh)3T}sQC-o1i9*{@dE~K<~(B>3My+fRP)Bekj>emqvf`FgHwF5gurp%Z) zZGZmx=Q;L=NMqYifNn9^1p_wDB+vwG`}mD`oT&eZerzXz?K&^X3FRgJr#Xv=H;_LY zS?8*F^LO5JZ=+14f#(n|5LdoozY7-j@wZQ(hI2*r=YOH1*kEy%AFtqE_xZDld)~SA zo41}lyVU-(9ryqi$)gSWw{Tk#JG3+zczt+aFG5aDyg!STOEPWjdpxu+(LKYH>G5QF zdU&#tBW&9PA39SXY&hg&Wig;I*q?Q!VbF*QNhKP|Co>a^1GI3!nnCW4&&2-6EYEDu zoC=R;uIJ);^F5WGv7*Z3S-=ZV%8JKxiOb_zxM;!RB_0p-4v(kWv&>U70}B8TPE>L{ ztJkbrOY8P^>w&x2Q@vp}ovCn2kEg!DbNOr!F9$Yn*(x%&U9tU256u-(W{2l8&(779 z+XAw5M9r`Oy|pA$$@*D$MaS3wfnw~ z)c1Qlvokyocy9Sd)i)nJintl5o)w-Ix#GzuckcZ0 zkALDh^~$S1{TVi(WlSAPBYmhem7c>@Dv0@$&kwv%mE_Ktfi`GBU1v?*AXPm#m@5sM zUv4NbH#a<;DPO(=;p5DHhE(Mps9_9IB#?OMFhi^H0J0_zw|Ej^lo0L7Q{bbtQ`s%0 zh-uU5Nv5nk7bk_YWnhlVONC}N_hK0Vxbn@D0H?gM9#wv?&pG*lB*>qX3`2))$!W>y zY9c2Y%n=sZqgX6qE%&Cwp^D*3C5jCSO%SZs#dhcPUX*#W!# zBRx;cIr=;XLEF9tPa4&{xfne$2p)%@4iPZ=;o-%=wgYa3o|oZ|nU^uPbviG*)VyrR z%*(bna$d&#Yj-?17oU%wn{y~{7{Bd6>8=inXi zW47UWm}evxN>1}s)I3aQD|Ru`$$9t`LKy8an`5RydZ;e;IhuztufXrjzsSxjm@%&X^|Ikgz`C{3Nk#P=M?%J~!u1c1mKHzA5W3zBj^#auiw za!w_|Lsy~JK~gv#ARPsIOR+P@9#;tVZg|4;EzPv7FcbsqCD9AJm^1{^{NZ38rc#hV zyf~#I2qf*y#XC^7#fa}{{-v6TKktJ2j`K*4cOQu}Q+8p&aoj!);c&KX8z(p7+*`L>n_9ZdWpoDln$nPnNc&xz?^N=8mm^PtSKkpT6#z`%UHLb zec|QM25tq$Mw8%m#w4SDW?2CE ziOaRw*kTx44PzVS9p;MlV!LrA`L7yd7(0;fox+%THT=6~?&kU5*vsi#t^rqR5Wdzh zri*>8*TK6Vc8zhpap2(eEjJuO06)e6W8V0sn{K{^c&6NX*f4GrYjE<9?NOs#m@VtY z?ZzFPpE-A8XYKBLnDCK%A-gXNfz2|=4gUMSem}d$1LTn5CSe%g_@-ezc+^<_5NI6b z2;<^Ai5_o=!F_~)G6eTgMnU|y%x}Z{9T{Z)z@2YAhNm$HVJHhQhB1>nv0*GXCO-az zaqN5FCj@Dp)Sjn|Cw}n5<0npvr)iUR)-%tFc^i#Ouy}m#`IJ+V&I`u0S;mjb4f91x z^pY{Bh4v+1HjE!LFTi-KOH!PP-!+y#78DSFf*=u+Py=OVqoXNG8meo$VW2exBamW{ zj=(B{f!#dl2!_!MskMHpNJTiT6>zv8J^LGSr!N8n8{*O!P!0^e$p;W$_ZU_(Z1NO} zpE?X_N~gg`X{WPWMiJ#R=m~@FgU)mDJQX&c60JC>kk{k(xjWxI zVOkh+wb=nrJ00Tx@A?Dellz~oL-16+-Tps4g4C4%33^0yuMCIKKV$abFqmRP&WoK$ z6Z(bPn@cwRrWr6(Or>7{{8#B0hSD!gQ|cFz+$1<9CiDxl)P#Ovnq>qpH%(G6=9nf% zNYk8W&NnNk;pD+wxX4^=x|Ynn6qBI2a2ilAGnZClK1`fN>0p-Cn9D276)SNR;aamc zW!(${uBV4Iv&{_~*@t~wW$IW4X1$BT4dx{C@>z|Iriq!p$uwt6q{?Q@E~XEGmQAKv zpJHxiY`PIfrjnm{Y(c(EbE~<{G_Nqt?UZ+zD>sU(%pK(4ImR@vM!t6mbJlM7_srUR z4Y4<`B|LNUK1aVmsMR#5i|h7Z5AOlkb>>0yhC|c0-S{O0mT>-E&@OI0OgvL=yWKSJ z5bG+4+B9>9aBbcw?lkY>{8Zd6#66@~z@%<)VbW0?jA_yl92;oQ6n^li zX+HF@x#AJ{S)~x>yt|1WYZ7pI??HxuPf7)+`;O}|xKfKCI&3P<$H}cg_z8tKi}efB zTwzW;_C53aPd+6v>G=cg{h|3iXcyR5c-CBq%6RU1F~8ni2>s&J3n@R6bY3*4%{E_} zVY*(XL_anwHs64VpP1$=%nLByQjip93E9FZC(^u%2=d8z6J=(jqZJmM|I;s6yZT?N zU!WDRq8YAn4r>^1$nNAw`HaA0uUcwo#Z4c@@EQ$3ec2>7nG+5tDK@oaUjk`;5V(lh2< zrKdbsIo&hjOy#neGnJjySXs+6l^wx|GnF8psqp>*N(F7|JZ)aE4>I_S0&ky$Z<0Nt z^K%v2527+-$KVL)@YxFOA?Q6FYz`PZQxFrmpJSW=AYwlU+;~r82fj)rc0%@$vHc~sviDic0a@kX4f6oV=n zO-JV{BF=dV>ALaGQ;Jar+P{I|v5{iCu&qMpJd`m!PZOVi+_?#8vcZHba6;;w>axcJ z*0f`7@lCK~g6Y>HtnL|>gxY>gqQ%fX?NO!fLXbt<|_VCB$Z#T!<~!)=d^pO#r*{Dm?Jkh_wrD zl-X^~wD#0dlD$@?g||ueS)x^9T(>{Px<19KI&jdkZYUK!nC@!uW0T8nuIRDp(2drY zZnCUPZ@$H{pxWGadn(=Xy5ml3)m;@9_DHO2kKAk3(On{3RKTptL|Ik+uwPNc$Fe8PD!Mxu)ZtmdK?y;tj9SYn{ZX_ ziDSqd%xY*y*7tIEcK=0`79J^l2aJukiVvi01Le}WSe!XtAn zaxZ;UNo@Y7osaMl$&8uu)MJ)9AHkNQG;=DP^AYLmY<~k=5f|9s_~PduG20u-#6QYt zxktDO@FV*sZ)+rK|dSF4AFyVG%jxKqUIXhfH$0#b%PXZ%YIySM>DVv~^h@w(XDYeJjwJTDaqBA#)EA0K-7Qn~uVJxvm7#lDcPlycV|t3zYzazy%EHvfPTDSqi(QJ|8YY zTHMN#T*;W8Tq!9WpK4+A)a&ckt-Ht&nO%|AAIR#Fn%y<0XGS;d?=lE=5X%}s@S%7KU^w6|S5~@}X;~p_z=#arMLu6&(B`=mh(6y);p;PMboQ9Ekg$@i z=N*GE+-k(|kU9Ij@V}jkT=#m7{Rxj9ZQ< zl4p?+aQOwt#UQqX27tbh*aX}^5Tbe+;(Wduf#VF^eWV-6JU-)}s(#`RG>T)@{}mJ|9i4)|E(l6+9>+)GjhcZ_KqI zMYMM9-m}-DErV;3l@&nP@ET7{>t>ezC zd(~>Ud(B$6dmXeW$82#$)n62?mJmup^1r& z7PJf{8g!dNMd94=?>2NbsB(HjmtH56zI4$MP8#22<>sq89NZ=3e15eCTNjrrSU_F)&TytrE=trtq6qLZaLB z3l9!1eU{(wbnzyc30;I`dZ@z@GUiYZX4^Q%z%Y*8S;OnXsDKX#kcl4s5zqHzD2Ap& z%v>TNB_S0{6e}SuKr10O>4eucxf=yA={Uxlnkc#_Wn^jqc+n*<(mxVdo5=QNrRDUb za3G72yspGBeu@ZqF?X50GIFJ|fYAwBj~gk2!QP}MrEnO&U=W=drfg1MtQqWi+8s!aZ1CQ9`fR z>`r@HTnHJJkdI0oVj!6{uzPohe87W|rF%x2#!U5jq}LqoWu7u00sO{08=CRSIOXZ< zPK5-xHV6TyUfomhvRl|Bcv3Iwr_c=#-InVuX?C&bbWG+vknSCr)mMylCyXO)NSOk1 zAz`#dDHzjbQF|kk;BoiMOD$4j3it>~)pbH=r*5>Op!7IXm99cY8|N?@7`w@SRtN>I zAW3){zE%N)*_>Sr;xy~yr6q#mHQj9K(le*0uT zNWMYzps!0f2A`QAGn^ja7b#i6FA`D&49^SX!3#}f^jn1!I7A2%JZ1ixn)9x%)B$3|-xy^5DVb;-HFpX}W6J3qm8 zn|;J^g|a7Uu3X_wzX(W1Kr@o&7;o{YZN~{I(MAwqY>hB`}F*6 zLmPzHX$*ZTi}nKTSB}$j$K34=`-Y4kCFDJ6`(xd+uNq1;!)19OnZok5csN1wgB(9G zgGe{Fpei=(#I8R{?}Ei-!B1%NE?0uf#iKq$@PIBaz49Ie`7LN8-@wvH!0INR=>i~MNph%AyAK;H?4{u-D#QWS2O_lqhfv2JGb1az zXKwGlc|00sWz#6oC4f0WgkxNugf8iWi3Va2=vTE=Aen&6sCfl}%pN(tf_*~y21Vo* z^cy~Y8f~ssR;^~%cqtNYUO@&|9hO~5X^H-nuD))bC)v$)qC#x z2Gp~BZ4BC}F!eiR!-h*9hz+MK=$C<6j+vR@F0wI57NA$?oItw`zg-5EmM&7Od(?cZ z1e={?FxU#cI434niD(7#?|>sI$Q=rKl>{CJND49kMX~_J+5gSc)vrE1mrP z9z2ndhVufHqaTpS5P1?hQ6RctjRg`4&LpUjqf$&Mae{MB`f;?(K!(2mqTeW^6I^Uf zuHS%HIlBZha_25uzCO1fNp!h%Rlwfl(B<*v z3KDO>;m97O40kCiB?GPuh>W?AuT#zRiW`*v%K}(}2nV{<%s?4>7I1xWU1epXwZVty z<&8aa;llLp+qZ9CUI7fZMMCVEo12xLk(HFzEh){@#n(m9`U2v}Fwrcjv2sn&t$uh& ziWf5IN{oWHkv!TjaPNtM=j83;Ukj*P4jJhgB@Q55|3CNWPU zi22GDmDGr_10WWXyNG5a$IvbS6e9ddvqZW4@tlBKN)ikWPWAu_R67syz%1h@J+OJ; z_^A%atk7j8dMg=(N3G1R46c$6S}{JZwMGW;-sL*-t;g4-WKJlW%tqO=@nuJuYOhLjjks3%1nxR&FK;nmli`5qb5O(By+MZh9PHEg zki7f|0Gh$Ahi_BulMv7beF?*E?|X-N=UsOv+;ilfd->&HdM)^yk^tJnp&K8ReqbBs zQT2Fe*uxCv$|v6=5=o2EsazrJ=22|n00Xv`5LIK*ZAMq_dW!oNJ;;1pI?+#3EHFw( z7#I9X-5@V3#ndp|%6i~>VSOr`02hXmz$S7454!uyri+Ha<*iM)$tn(BBFjBlNPPk^ z9I3PmEW|h$_-0%hFkz^FcY}+Sk7ID){7U3tWO<DX-lw10nr{;z>AGR1wfb8{Sgq_Ds+r48g*Z8i8997PTELe*0Si$ zQFX3q-3$X;D!ieR30%JL3Rm5E<<#LvZqVp$^f8RSMu>rV`G!$IcV7D| zoB?nP4P&4R8pa^_2CLAJp&HEBTXg{LaD!Bn2ta%9Xa)t0F~-<&@X`zNhEZ%xDj|6E z>SQv3!e$D*Q=MR`<6{q9PG^JdT;-d|uDT(vVC1Mnra2LyuvfpKBdZ|diAhn59!Dhf zaUMP^;YUiB)U+Jkk;$Wtj+2oQG2w_9D!3#_ z`$h6L?i_iCX0;dswC{w$jpywfy*dS7*pj^ zf*FgYqy-aZAK|03LYJGK*xrQ25fpYfEhB-#iI&kt7^HM!lR{t?GR$<$e@0gl3Z|m& z8QqB#ANHkZA|?ZaRC-2MGUgzffr1&m`w&9k5FUA6e4GQ@KSV*K=Ruv%OYaMB0W9wj zAkcpR{Bk!aggGxHcQDgcs0FjJE+q9EqFjI4Cb?%2L#X_IuQ)F=q{ zjmczS!lR@Gh2Y+g7f%DYE+M4|Lw!V5DR&oA0RB_-ivVW=teLwE0i-sb^tyqz^`iFm zC>1`M!io8T<&40GJVmdd5WV4*wM#%URLiJUe6^3>6h?^Z1_JrV=ogWDa7x#J4k8W5 zMXDpDfG~Hsc+nHjF-oDpH;yPxr}{;)7(J;+$>j7Y)IQ~|pwdpc+NKj!l<|`u>T^h9 zx{RRp3L92W3^9iS2DPyY2@fw^uwt2~mnl$|sFhaIhnU!axmH*Z#_}a>bkV3_L&IQM z0Xobr^Z)b<76U#0N&1CUN}QouOCMGKfBHqFt`ruG^x<|%TKBG9yQO_6GmhvrKY-5Q`4|l znS{NQ)Fd}PoShpC_U@gQWC|-YEdie#a;N3=z<#RX!flSUu3cSOI5{^=t5=elh0T~` zGbuR}6ehqn-X*!J-!8_5ZY$)Z=X2ZZzUlM*nWLhr|96)QU(*84gX*19ZYhdlWMbOFUN z_$VEl6xv2pyF~Iudw=(wo;f+#AVqwp!q3dj$@OO;kdu=cRJ>@ohw0O&4-bk^31C8g ze;z(d=lAF5`~3w3fuT88`uzCTcu0c*%GZ9(4zXXQ9GH$zixYn2M@EMXMR-^~fx#u; zKYT>8Trguz!Ysgx%R73Ee~{wo_tW4%2r+{|QusOEiSrkvD?gP+jN}}#cMx;I$I+4b zabO8FO!5?!P7a01prBO5kjxa)Fu+eiCZivin+Q`G=psalL!!vZ5^*mS^vo}CghL^+ z`Cu6$t!HH6$U;F33X!V??1{7^x@AO9h+9T_5gLWb-?B_#2MKOJ6$ zkJyMfu4O zK{nuvY?8Jj2~L<8#}tPKDCi^>c2Ouap}3g-!EWM2N;6^Ngb5+`aRAWbV)&%65ek;{ z#8*kDjv7@u)-Nl5V0t=!9f)&=tk7f+!%CU#G*SVO;E_eZLzB+;mrVEj%gR+H0?PRT zBQ8{^AT&c6{?eLy%!)9?kLrvZawGi|2Lq5Y`Gq1|`^jZ_OF7Msgs04r6`xJnBm)v? z0A&2a=r3IkhVtnb2Vf>nEUK72SIY-@ql$WtN*CpnIvp(FFrF+wDm*kw7Zs(QNb*&5 zIEXMom0XHLBoFSU3w`GDylYtmTCXfpQm=-@p7XU!vV17|i(Y&Jh_%(u} z%B-pdRSR!KO*0axW>N?oe7b9P3Y6 zE#brb@)fIB0`NCc^20J##1w`W+TCCYL?U-V7K)k zJ2kBbTN|cbb_3Pnqfq=qj$O>6l6_kMx;Yxww2@c!Th{j4PKvYlC z;L;~HrRWQ!`0*%u7XT|+x`{{cf{=~>*9A*milOab`b&n2f}fwj2B;g`rQtN`5q=HD z^=m-8^AoQCAaxdY>+stGxTw$zH%JIC2xxEY?CCUaY-jQ>Mq#Ixxb};P>5omeJWf-H z=Rgd#gW(Rro|OC>rd;|7fQvZYNKn9UK43cz-yY{rkJE-6zB(>SI84_A@C`xSPMMC< z6k(SQZ^R*frou17Re;$Dcg40EzABC*^m#bwFU7W56^`|a1Re4(Li}Q!7E}0AgfByQ zDTm!SxnG7O`eGc?ufS2B8;5!L?Iz@M4SpMW9scO7eIw@@2kW9iTrL`MgN91eELu?3 zO~|=hY!+L@RjnGufqKrs2v8L zZV5xheT?;Wald##;H^IKAi_tv^|Ie;Z#n(s`pc{}{eT z;1-WF>~Zk~++!;Kd*XZI`|v+0o)SM0KNQEs3A~Z_w7>@kkpJhz^WqfJ8{!4=Bm8pC zOPuOu{Fcs7@cTJGQ8Zp<_ow1#_&uF}#c%2SLi`et*YHa^zs4`==zO@vZ^ZwL2!-L~ zdxK+6qZDt#zSZvUw+`gT?E4*_zZd@|{$0E++Qb>8en-5E=X>IPJUBZ+$Py)JyW%%R-{*9E&ce{YDeKh~FwG=BMsGb7DNN1Cp%-EjJy z;rKI+EckmE*?7vo9Cmy1^9|7pu7u>Oc#Ri{O@3XjE=Dj4v$qQMVT?ybU$`OUOqM?n zp?oK;TND_BML&b;R{kv({Si9=N9>aRK%B3W@9Sc)aTwAWVo<9d3K%{@X zkulO3#WEx8(Z*u}$LPj7K|M?UjWddjpcrpVFeXCUnqSzZbj9E?$tW=<8&hDX!v6C^ z#HrNSg>RqH2sRy``HKEKEy|4<#!P(BO-e*RXB%@OAQei&6g!vUU0I?RV?%u&q%q&9 zG^&gR#`joSnuc3kV$hfAx)_ULm(WM)kaj8TU{P%>Gir?G#tMX5#Y*EC#s-pBI4$|! z6t&E46+b0pwURD{)&NdpEd9+;>8ZvkrIfu}tmU-pjP(oAjjNDy zE7}KzhZ#Ez+PUe8>k>;HhF6Hb2` zsb)vyUbnRy#X;i+)n~_Z4>UbtLdr<7>u!oVKU&bwf&q zXxwi+peWL4Mq}}9OFUdBmASrLn`#J@rd!L@h#)qMn6El<8aco^_Y|D zyDCoRxr;%gH~mG+fv80O^)Ma>9?cVf-5*Xh>D~oy=-{nb=M%yD>wnHqdElNZ{|uJ= zG`0M|!f(aWLw-B4TrUr_P4m`nbeL<=?2BGX*F#EiWLt!_jA z!yNkIjVOa39{GZXGF(@WPiD!xq_{|0hMT13m6FU=W%xow*{-tP2=0NU-xifIc(yt| z$0Ki}TvxW=fkb;K{`v#>0#-D*!w}&ga$<26)$zyonDiyBvfIjTzvE8Ryvw{hK306_ zJx9vQ_y%j)eSC%W!J`kgL)6vVf&1_yWsiQVU7`qpJRioZhv6?=25?$Q?}w)*;z|a^ zM3`<7e)4uB#Q)Bw`xnfdUKK~VxE(`<195Kx$eCS)2!Srh}BxIaROpv_l8C`H z(*hp~=OyIf_oxZ65K{vldAOv5FYY0i_$d_A12hs0{s$RUb{}3%fWuOttXetv2m<2s zz)uunb0m+T9;7J*4)MT?;rxAt!6c2L!ski=7u10(8wpI`Kx7`(mQBJFIdoT@q>PN= z-=IoSy$CTx+gJRl0R2rsn-`n^!#`@Ga>kSk#2u^=D@V#nl69|=0HQId~|azvJB9q)+Xm>T-Gp_+3rhOQ3WiSlkfDl{UQ8gk2qhpL{H& zo8g0o4iv-49gZ;IBL-hoNN2eECOCdjj#_{iF%I!$C>Ae^h+flT-7zz!DjyOCm73KQwE!-OZ~+#pk6+LfN>fucoSJ(K`JKkT+y`=x6-7tuMa^5NiY zaeUHaY!%qBiZH0ZD{2u&7Pb?(Kz;^_!aE|+;N5w3WVkCb95%b~hKVXSfV098XdkkL zYLIHL+CdMFxFAIrR`5-2+|p7io?+0PcWttI7|@FU7L#Mphq%6A%HD?2M_;5z(mYO{ zUqB9jMw-Jh4}H%*1{@I_fa~`WW*}X_@5D&`mw%rc1GQJn?Vsk-I2h09`s>IYgo(A# zHOS@e?{?$UI{3Ai+`fH#_b!0Ax^%&B`-+5~>D@DXq!bR42XT^)yC==Z!c|x}$gK<# zlc5hXuu$p~Jf3g}zXtFDKZi*Z;@fcfiM0Tz1qFfuC$U> z*F{>%a*-|DazaaERVURknVMT+@DXmG}#Bn#_jFE3CbR=@O|b&KYpXROc)Dr`P z2iT38VV>cNL?gu|MTI3^w6K6XrAxWHusDkKl}NNO5{?yXFCk&6Ac7s`v4{$nQYu6l zp7L;sssIcqEGa2ON%CURB5XI0mPP2OG7?3H1r$|P6jf1p2PcqM!DT;&R3gVb8Jrg# z0M??i0i_Vw73Ln4NCeJQ2?b&?0_^zEiJU8|h94qQ3%8LYs#p*z!Ob!B6-rc9A<8Ap zMebQI9#fEcr7*oJm#vpE{(~Ti3oRU4JS0U8VS*|uYU_-u1gRJd670he z+f|VO3Vg7t6`l%J-=JYA*1HT0!x}1oBN|3F4r5~)4j1AHm$2gsFQDdwemCqOWrj$S zkq}H_cp)Z@Afl^fFF%r3QCU$5S|QEaT6ppmRvlIN>U{9e%<85d?S@i``i7wm=nxGX zPN5aNJOJHJBbK6hg6}kg=tz{8PZXrSynIsmx(x~i(c4rH0-7gNTN zk1-@mI|aycKN?l1Sk&6XZz0)~`}(QyV#P|!j?;F8HERJlX}4kKM&Cvw-Q}C$w4uDb zTbnl{-dnPmGT{lf)DK4^++Uv!n=<2T)*}Fl`N;xX1sB8$usK(EJMzNF7^^dAHU=4H z1qIj>oJG@eFhL%4JgBOI?cgDFnhmwt2I6&z97i8=6T!63)bCAObZ1 zCTk;p&G%D8-DRBo<6)FMm<^CXqPX-;pA=V<2#50katb7<=k=6U}E)pa^4Do`K;BF|?-i z1+6cvnD#O>c5tf#>~LY`fS}j_vFSmmXrY{FDTovi8Q=qX_1Govco4i)5V9(m(Uchi zh(P%Vpx!6g!lwIs)&f-C=FHpL!v$oLM>Jq`gm#OnnB?MT*${(R@gGHGFwTXi{C#1MaxbAbl266Pv0R%=U~FaQO<*NA9`3P>7e8wWx; z#5`0+(2^Cyx;VnwpxS~uRXBh}AR#ZU9&C_a3Gd)Z6rmvI#VjBV+}nXb@g(RMWSf~N z6b`^N3Q7u8p4CIvihVIu?1vw~hI3Ga8316{!hs)&K?7hlyo{l0i69glGN`dpyix-a zCVNKI)ZkxJGm;AD7_@tSRIr+Qw*Yb>ntVk=e}z~0VPFsz0PN<3MyY9%P^S8X6{G|;`t!sac6ts6F+ zuC2CVx6>JCZi0}Ov(7#1%nM=BPib0z(Lp&jMJ}>tb#(5Fh?XC(SbBD!Xk2FRF6>e55s7ddTyu^ z7&}h17DZ_cSukND43n@U(9otB9pYC6EZqoau)|Vry~5ro^hZ1DXLLf*+)1rzb>=K= z#G0E;F+vyAqWLJXluc(~vFJ-eOGBZhxat)qh*k>8z4B`zvK$x6i!a@qAXU`}RYg(a zPOI}U19k!TSSjqXvXY8~*;g*PblbLVmtArRcU%cvDQadW>nfjB5Shx#CB0LOt?(xU z*T^In$|a_+ZWQ$d)nIbzSVm3x8kEj-`; z&Ue2D?fXA?;fFu^F^T!`lYGJpFM{&D7yk99hYtVj=fC*nuYO5Sf4%Lc-Mg`O37eM$ zez$w~?_d6d#;JyuWpKgFu-o>-W6~uMr8I08dd0|F%e0u-49i=_8pw$mq_+x}AWR$sn27l}KvR>iva9USM4l-VG=e!on1l*v6DCcb%>M*2@SLC0M4~fnBX!LUBL%1 zk0mHnrW9hb@r*^N+6avd0azi=NSi!rOcP==NutY)bZCVbi8Xke$4?wPZk%*qWxWRJ z6Q5BRF^e5~$&^4D&3S2{Ei!q^^r%KA7e?I` z-pWN-Qc{&p<*Ls_4dVUrR z6d|ZKyXUu58)w5MTEk6Z4bj)w%vb}u<^tGKgymie)#JhwM{k%yv;tNsU8@THx$H+o zl*Tnp@PS-5g=j=}^i+KVMSh@U>vFBTdivD1{_3TdX9_o}gJy{YB%5Q~)Oh*ceeqh8 zO&1QA>uF%B&|5=y4Mo2{DN##UfT5z*hLC;82TsW!$El9*V=2#Uu_BQ~|CdfqW+j5#vsvcuo z>xQE`ydHTu`rTNY9GwC=vq9QdS${)YiY2)JCdiIbHZC(mn9(SN!~}E*IKhY25Seuf zhJqmzVSV95QN|$|;2;tSfnDa9FdOJXNV`loaWagPM`rek^D1K0b7W>ntXzi{QEc#r zLXe3Z%orA92`~g5mUdvbuybJi+R|o5k_$>fgErG9Gcw1N*~K` zB*GRFovffvK2GHn1zk?0G8lM>hj|AkMji8Cydb0)7mS38aHWg(4BkS9FMLNTBk;hb z15Uv5H6Wq%N0N;^bl?+TD}1HzFd=mKh&*CUB1k|s$n2w@Uy@G{Zlc9-iB+GN<}20n z+Vl-%DiG<8kfSx&V+NqG)#$+JplBJa21TQT<3otl*3lv!Pt+&uI?k}+@%RW4%Q|vo zQ+()9EQQcCCO$TfKCS0X7&%d!;|&dy;_=B-8XBf1Aj!3ET0=u!!$|Glh*m}+3V}TF zwvP6AG&%#O4xvTc+S{TXozdE866WOKnL~!aqJ36d$82psGddkEf#U#nM{&^{QfIWy zm^(xqM2qIZjL1)q&NvAS@zz=-rnMtJ3+zl3{wL2L*dC9!#^*+%;UAClEO-0dcoIPl znIQ%!(~}aVj-sN0(FF`8S{xC}S@35%+(m0)w{Q_--a5DqA+|>&1BJ0VI(Q~Lh_{}E z1P+eJXCjHw=-gKLs&jV6kXf)Fax$p#I1=BANX$iEFi~-xIg8;{4ea?;Ey0b_MMV@< zjF+{7Z>(q~#TKsd*5aa*weyw(%I3jEMWniD@w(HZ(Q3>wR)erEx}My?iYlPPGv-hc zlp=kF4k#=MMKv{4Q5d5&^9Bz=!GOhJn88<8v;hS*5}h$5f;&5+(Tx#Ph?v(!(PC=R z;_i5S6M_LmqSL1j#>=A@o5_JUggiq=44yFrDQs_LPJ^Ru?##9sQOxFmV@pHB)&>-v z)A2w+aM4+3&pRgy{M_@JpSOJOn-CA&o=IKmrU)3>-Lo#K4hF0|$=c<_6NR@)(J5_!yZGiAxQfH|MY>WzjRiF6wb6F`=>wX`&H zIt&yE9f_RX5y6aO?fXg8aIa`v zBOjzrFR0uG{Bp6l`$Hzgb4yDIk8j0K&`RM&XAE5E#NE!0$W03<;Q9eFSS|sv` zfBB?F9-I)FqhDp@p-AN6PwAq>;-ujbiwyC+N6S`UQd;`hr!DF6&#-hCFzX1Ic!J7! z?vm6;R^4HLpf-4XuVIOTz=`2l3OB(;#2f#OytX7p$_xY)FY8+zDo6O zBp?G{`}#K`&x(;@eiImV$skghyU#@=^L7Az9`jKq;@`sS5!TY3-~P_+w?`u1C4b~b zxOcw?i#tkpmX>}$QtAT#_75~C)gR*d(azEz3pbPk5`O}OI&*yBg<~z5V z=hqQteg<7fe~Qa=j=9kXpFca4*qlZU-#?~^M~oCP@_{j+@LM+*MNXPDsdf4!oM`~G z@w#oSX-vZWY+w#$#MAlP1YF1cHUKwnXHHB6R-D-7%2lh3u=M~h^3HfQ_>1qV8^p%Z8K7thnra=RNs^JabP9 zv&X3ufNmeyGnS19C&U0#@GKY@(}j+2{wQAYBg7r z0pR6bWcgre^vbv+YMlmY$OrMyC^js!G_KdjvmAg8dycRbA9q9jy)=g8AvJ{$%8x#SQ7;FvW=t}_IMT=rrehvs7l)}vIkr++Mpb}Qa z)>(-~w4N7#BpnT+zS+cac-lD&FfE$v7$#W5O%_uQs`p6dka7)lp9A>;V9GK((1f+` z1;V1iEh1TD1J;mLkrW6KbA{b@t26~jlqq=d9 z1ezY3KMM?#jH(w;OA3*Z1knVE4?<2s(~&$Zi1aMJEJ3Bw48lp$D9)MUR>N4SQ)alh{$PO@ z6zW?DflzKfq~_~BmQzcfIwwKRsmH^f7IBnsJ$HgzmUNXX^=@A!675S12C@0O1lKWT zz$VMrPxSRO0&f9)zupu{NkR14j!D7MuiPi*BYpvaMc(Hj&V~Q@e%KZpo5%XQ<1xQ} z$Tw$)o)^yp9i=%7y8BLRn}(`So@!UQ zq56@@^3tMyd~D6^69jon`N@wxg@@tjkQ2HlU}chY^vg}EQrf|WHG(kf_g|`;$X-st z5(I%lh)T_+@#CpFL_dxE+m86B21%BDd!lbNiI2-xh6r5c==padgp z5Sv^@zVE!ABc_yeKU~vIZ(O?LxsG8vVe_5+F3fR(;7D9#dR=)zGygNy zV;@Z4a+e|Jxn}+!7xWj=$3_2yluu@}X+T4 zn$KZNSQfn>QkJdFNE6$BR&d?gHlMkD0=LUBE%XZ2-UR( zF4H8E+xTaiMifxr3tJ+rJ7ZzXvd`xuaGaF|xdT!Ei^_1IKb#A`NBIa#xKHc#v0TKy z9KS})v$k}r=UVqQS^un!Us3oeppA}LZzg)eo^gxg6UPNuO(BqSWv$KOKnjT>y8+U{n<*Biboz14*!bTE3Xv^5#uu3@ zp-2S1F+k5XWmf?_F_=>xg6QK@Hbc%n2sxB&W7bF4wJR&wOjVkNy|w&H!CRhG5pa{# zkQV6?2}vkkLU2roDAkSU0?A!A>M1=MWK z(`V#Wka<0CdSLvm|MmcG4z@V%`J2R3$Jqz^^R<4ev9x5qcdSb?=v6gqkF(QlZpAj0TRy5-?ya zaCkqRO8y>2ZcBOXg_Y_|*MkbrkECf-hw_7;+lOx z4Z8D(Bf?RRcR1X^W;7RNMus@T!*NcHs^Z?WtViZsjM<-i(NixKJpaSYOej?^UQlV^ zX%!2Nf>6ZANMID=s$2;4C_unw(YpgR#1Ta%_j@T?J04E?j)&!pi^(12Aj&TtLihAfbY!Y?&nI1NHI`SNly>{O7y@aOmt7~-(-#cr@BN)GA zO3jfN>v~isj-(S$lm4^VNQe?)XM0+I$G%{Bo3^@vT5VoMl^ z(pBNx=8`$g=$S~>$o5q)p5yDTsxGgnfgT?)uwoEe*1-b?$TI|&JJr^y1Tww>4>D2q zd{Q@ z9U|eXjjz9v?gWClv{#|Mn(i@%=hNxCkG)!S!|(1saQCaPZb0WT_D4MMHw*fEL*|3v zR52Jvh&*H#S;LmRN?rUA8s-sDOZ+ggVXrR1P- z4Z~&sjpprF&70pvPoCGOQV4by6mgF)y6zNjMUa_x?Hx=xBXqI%mE7^VPbPw~0w%)v zePx=-{;+;yokI+CLGU~3>lCSI8>C-a$_2<$mDa~AP-4KBG=&EZ5T2B@EE4#uW{|`HKt``U)v4PZ zwvpYW*v-vk(IB%VyhlMgAPVyOG#w)}Bucj;W^GeiTE?^#kM3xb!(ZS;jf&H}s61sk zlRaucbyfw6PYXpUK{9xx`fL~qq>-mT5T)S_INinDU>l&C)4lLvGz`sn#*oSu2cH{3 zN`UUhnvou;7MnTI+uJAdiM@E2$%;mlT0@#F!^PX_v|Z~Tq4^0G$!ycKpUtG#;yk;?*kPIl|JF?FV8g}oc#`c{(K}8 zZK>!izx{4A);2x4eT+9vAHz%F(Vqz~>Ls9wCdQkD08-J4l1kDn)w5v8?i!)IxngsT zI-F&_TM62X{6o??kZQzy!LZeHxEN)cs7Pcv7w3QE(qRC>VHZII;%j>lmd|oomTaBb z$EH-%5DS0$Pqtr4M^@~#C+0XR-*2CJ`70i4C-71VP2)}oJ>ZJby$1m^yD+Ui=`S7)C)I(3D)3M*|p!vL~@TNEPrU$Fv z9K@{i8-Mr(Cim1+n6m&r^xC-as^2`*@%@@-($_yd#Nq5m_>YGW{u{3hMSCB7Dy`Bl zYx9=(7OUh_=@4Un|C8$#{OLUQa=Hg8d~IBh3ifbJl};C@dQ$1w-NTL?`{c{TiH(ZU zOM_?Q8gef6cR&}UhdK?Mx2wYw z>Oh1En@^m_V zPz^jBR$$?@IAGjwUZZ{ZNF86@Q~w5z)1pVxv6iFhUx0ve9Qf&Wgw+X19{{B@jhB8X z{XB+qFZM_*Q!E2Wb`RpqSYWt@%)tl~rXCo3qQ}xH#FJx342fUJcp z=*TOkx`#NvrF4(ii|m9hgNXF!Fkk6j={TQn2$uvBpzH_JD5Hs-)fp&;iEr8$jBJfKU}}av;v@D zoTAOrBat(w9N3m(OQxQ5$E>@acEW&3k300S7RdN&uE%+I|42*g^tNe6Hdhf=18|N- znTt7;v$Sj3Db8{Pgqwd>$~`}8*EzW22e8(0AWo=zlS5HLj?m^X0Dk9Pj=&{dz9)`7ye@{T91ToAtPkza9o>GskrR%lMdKI|4 zRDId`io~bqY0NEu^=sns*S~?#o>l6bH$TUQR5{PT@Ga4uZ;L$?=>mOc+jlE3``-6| zFyx0nQkVVs2V&>^<CdP3!jO038j5bUF{2}MP1)rf zlS~c{aA9c8t;LRm@wJq5dXx(zePa_b+z%#q)c910)Syrq0cRpE1EZ)|oR0=UB-c%t zHDUG~+RlY!7iZo{!07g5(dW}*!9uD42zKC?vs{}_onQoT$#;X##s;}zqh^3V8nemm zqf4hH1jz!v03u`raXHD)sW(U&F4yP$E3{TzTnVJAxVX9oQib~hB{><+!Pdp`boPI8 zpicyKZ7ww>D@y5)Uty-#*@Q{OwM1^NxArMOm; zl7fY`8mU~_OT8B!9qTz{)@_n-pbo#W4J!IKwQ6fZB}mcJ_v|A-)S2X3IOp8pa);xh z!2@7V!7jfM13>Xka6 zy*+B=L3j{W_dbykC7nAwW znWyFpHWio|wY)v~EIIO55=zxKWcCs06llqYBP47nBUKafo-kT#$5n0pl2uJWn280x zc#A_ycm{>&{%nJfix76-1exaa|2Uv0i;f$!j70)yN{lS|DM!#2y;tNY3|I3z(ccR& zSRZA79ux!GfidV}E?=Hd?2r(KkiYYfrM}2GkP)XbxI!zCYN?pG6=<=*Q`&mQlGW5qgrr0MjbX}xAl%f9?;?4s*&Z2)cvSlfq+;sow6 z``_vGEBn)Lr1#Tx`X!p#qwjQOG=b3!$FXcno=+b;_Q(By#hCLef7yR!>Y?Ys_eVW` z{mzco0LHJK>W>Fs})?V-h)XRG8`qVQW*K#ba%-Ho8hdR20X59K0 z;K}Fpxb>w&?@ZDC>;Aa)hK+C)m6&5N6V&6@blb+x^j}aUF_OIZOBe=V9Cj>yNDtEM zl1w2+Lx4^huX142&zO~)O<2M?h)eGW_cI)`a>RnM%b{ZEds?K)m?pk4*XSijff&va z1usWa9L?$%vLARb#qcraW4p{TDcdbrOS=U}W?Xt`_SUrMDoCOr)9W9b=n@b}k;;XB8p9Cslpcwj~&id|#} zfx*udM~dn6m2l73Pb(;hJ#)$9@XkTw2p#4gUK}zloxa*1ho+}u{0b*B7DZ|?7CoGP zLytu{w$tPC*AYCLtHbpE)&m@aW{*EXOt8I3QSj~`PA6n2NR_NcM#h5d=wX%Wt=#~nk$0}J^6c{tmy_iJ5t2%w*+cLc~~F6b$i zu+a&HDnlVO-l2FXG%z$MB!a3{9o*Uev)r&yKgu5{HnTT81>Irxg-fx&0&@6_6xv0Q zKf5>tp|f3-sVV|zL(^BT3WZjeW+Jo(VzAb(TYcL4Pza;OP-s(Vb7;##2%!y~ai$s) z!ocxdRK20|&WDrJLYuauO~2qmg5JD2#Q5x#H`Ib=V)|skC{MkbP2|GpKscM$owkx!I4{~7dzEJ4)JJg+_ zyAXEh?stXWecHlM=shZQ;XUsSh2HmmNQGr6_lolmerO2vcZWhBRv)?Vqi}scj7uI6 zyCpTDkA?1XR$<5p^Fq9q(?e&8=van16Mn3QM-S7tg`rQWvuf^8OG1xGe3oof>e0s# zNx+s5gA*H>9{&t3TL*-;Z27F{Ce@+P=O%<^)_gwn1nfe0(@KRlZKOZ9YQE4HL>Ck6 zzDN^!51!Qv{Ye@$Kz1#WuZSrWdLje~wjoITkmQK+>^Hlfc;eb?pL_24&{tph79`Zt zAHs!5jmB&TOq)WhwAWcG+oz0xP+3AP#{#PEK053^`jDuvt7{lq$FW>4H2TJ2#2~Ix z%BW9;1XJG=Cu@EKL=NLRpwH-pQkSIPGiL##+u5Sep~c*JR0$`YT*tdfwPCS|%Mu&Z z(k^WQy1|xdLRN}%QIr0^ZTwc8)%nVFs%paVfo8mB$8rAfEq_2~dY|U?0yBF8j%WNDN4x{>4=#$ZH zxCLQwE?VkG$F$+F;B*@*S9R>z;r)MQTRv1J)kC}o;IMAXgYans$7qKSN?T5T*b0Cz zVCSKOhYz7*#r!jDXq^nA(+B@Yz&{dRKkUyrGY$nxx7h`lYgR`PEtO^x>VV)uno^jh zYv0`avvd&dPt;z+71~*}TKj=XTg~XSip&Xl~){x!So>=eg&f<3er^Xmal%W^LWeVX)v{aV1&b;VyKq z+I;oZxSg=X?J02=ZB4oEwWp|3@dra{?cZF{=c>|kuDjm7VV&z%-*}Vj?iiqMzU5YT z4d#1y4!mu~hQzMj%DsHgUKiH~-+329a&Hy)5XKJuJ+6C?dhh$*@4Bl#0OL6cu{)>K z-S5Wk1@i}C-hg?*51n(Rw8IP&Lw+Vy!v^<$b!F)Qb&mUh#D@v~*a1Wmu>Kx!eq5tASvS4w;LTESgcT2^fWorMkHx}Q`ZfId!4 zG(YGnM5mw!=|(;O_a48RHZqnOzv?yAe~w@OIevXh<5!GZ9|+y`v44(RZC#(I z|2MS1j$NQfTPf?1&^uVxcaLA&|96jHi_Q3zd!_zQj$e;v+UEbZ@he8bhh(qMKgX~C2gk4d zj9cCR3*%PXg8WZwKcxvhdA@EY7nt^Qp>01GE%w__jr~s;zhZQP3AqI3!+JPcA#lO* zRqWh+gzH~#q+^&nJXCbn&f$r|Iv1RT=dC(KAu$NvF^2jdAX=6Eyhvx~%rW`)PW;59@WHOBlyd%={dM z!t&rhw}}ZSuM{d9z*!Yc$muD$d>>q_`RM~>oZoQ=;u+))9^%&4C9uW99cuX--C-`y zFT=V?JE4WEuZwJUG0@05UV-R{tvgrz=)`{QJ-S zGs#*gf)VlmQk4<(vw~qd=09 zrsuv{)>f>jT!h_Cm}VCB092HZ_tm|x4%6UJS=RKa0hF^I?2`K3u-<}^u3CX3h4k&z z74Ue4I(x;)0<{90mZf|#D#r!9Pg!EsTM%7y5I%DhUb$5+W@LHdHQx`Mi)XnSjEDPh zE3iQkClo7(S-#wD>^~*l=!paqo9XK%hzyk-0_TG3P zzdpNl8rOtmBYw{>;BW-?wdv9pc;LW+Q@;li0h9 zy4fLCU4yIbah*N4fLRw>ucbx_nss=%zECgs+m5In>GM@Lsp?UqVclFa#u5wkHMT7U zSbvafYmJ4jwN)^IesbPY?zC zJJwO2o>#xTjrNOG4C@Va3iA;Q9AOOoVC!tzat3*9q%Qg%T?L488=`8`0 zzc+t)?%sTCbPOI%TN!qP;lLmBp!_Plex2TffXf0Z3ee$&3=JFv zqoo$KhCV`L{jlMU^&^HRMm7x{#m(W(V}`1cV~3)#+TP z!$wum4bvt(oAGSH6H;5D0#4tC+h>(J(`>ERL~Q9l8&}n1o8Wo4v%TzmbX&ILttoZk zMe5>9)Zk0u__E8(xJS@9xC-wC`@)xCzk>wd6+Z9J&dY z1n)4mH*5VCt=+owHX^c3KqXM$(8PKNfCEceoj3N~DErPF#H)tDyKH%PcnSIHLpD-7%wUHP5%)4`(^x? zwZ9Ct95|@w!K7YJ9d%y3_HuZRO5q6(4WifSqq3+LzXZJrZA^V{^ zrKXlII(>znk3bZ{c1{9w9E{(a?l0m#sN(}B4D9}*0xb=kXWb~#w7A5Lar`KoY&aY^ zo+tJ;kSu$;gNpubuFZ|_GqxAATC^Yq+CZvSua-`4+Q zbI2e1fHzDVF{7&^)|)^arTt`^k817B<~GvcNBIoOpciG?7+%==(~RMvmk!mz1~S6% z{_xS!#ya2|#l#?5LfW7=LITQEE|B;)_AjkR=x18sTeAI4hzm%BMr#-*XVAnn zV7M9qCnK#DVy{m=jSk|BXNIa6O~3#&aoJ#(T4kM;hK?CircUg{7QA7@r{GMqEnh}@ zGRhYV70aj(*@YElHDWBHQc$h?|LXF|{kce2Drt&g93P1N+RGFyiUE4s_``6R=C2%kpdbMJSf2RC}@4MI(@R2QFjKOj(9ry5dP6 zVR==T??bV4PbXwmpjR1z#qpu<{0!=1djwJqj1>$j7+g?bgxej@o0x!}uSsA+hAn;r zW&h%=UK11yng(X-)Pb3jJ8)bJ*vH2vSf2}ciW2823wV$c6{v>k7V&jc;M?#jvjAr} z>QK0GgaemWcFdSxmt4?3n-@ziSURw4_OdKagPQtT7itV5PgMSkSorNdO~oa2^Y<+O zEc*m|t}G!*ICQ-Jf<9X&JbCBKus*^n7H7=rj{S^#)lq&9(~OdXVx{+~qv+Mq26vP| zr#xBUucQzC3?|Mt!30n}HA9M8Hbr_LlP-A#{DC0JT zv@)AsLFChaQLi5)!(qu)>|NguyA$qRN1rWou8iL_bKUM;he7tQGmygw=a|{Uei(uG z-3M@F52)bG>}8jh4$-3A6J)K&rjN((SaHB_9u%DhaWZ}Puy-(iZ{FKk z|L2)91Sj(F*zh9PnL|(yF^sp=*F5olc6gQpS^ZDHhh}B}YKhq*DO)e6l~=fxRoK>D z6X$A~9#wL5h#n*cF#1@IY`hyjPOiU zFm%s5U%A`e3*4<36DoDFcB<4R?xh#GxLy`C864sSnR`u6`eEq7zWCJHbaE{=*h4nS z4X(nNkZ{wEn0s@~Jq7#M-JNq(T>Rb2Xb|c|uT$}hZrkPV-s8G!_U?0Co+rDj)ZO5^ z)&&adp35pe}KNacZl=-_nrkE``JIFKKzmUke?rQ-HYPx{ch<4 zVEP#B7GwVWfP41G6>gJeSaaZZEqx#?b{|w{$L~-VVHS!0G2st?3XubB{SY`G!MU;x z3b_n?>(+OPZc^{MkEwl$_%$x5u8RX_!b9BMsrlT;MHdt337TmCnX^9%{j*}C`E%~) zpZJ3N#e=J;Z<;+P654$E8t6u3wB!LfxpjMal z($zd~j~dC!H14EKcOqF!%zvJbg^yW)wOnHosWL`_F~k>FRU6=P zE~__Tqv%$MG0%8VU9HN8Y2$F8$_!Hux;%i9)zwW{d26mlWoW&uu5PjD`08d;J>vV$ zkq^MK0>PX`4wh|MZ~;-rDW+&i$e)GyS%GrXxnqD_VAIro)V!6qY!0l#VWR-^CwD-c zZ(?%Z1VVvO2r&xjwQ-!Rpj?EADiSE6sfq^L-uQV4+#Ol$!e zC3@sVcqLKB4^*OkqNr*;^ia^qgBr!1zPP2gmM2a3=!Z!v>7DgLC%c+e#{31b! zhebu=dr(g=di0$h@qDAFH|GE#DDA@dXY>)}Q6 zJJVC8AzU@+XPaUSSY_ZgXF>=B_yt07G1X83av3<@5xp>PS>Bck7Ydc{53i}P5cVik z63gOZ76$x+u!TL+z;_5sL=Cwcje23`uH+6ZV4{N9LP3mKYILHQn@kn65e^t91cnqM zJMiA|D`7E)@bhT2g#JtQg#v-nT@2AoC5RadiYh?9Aor0yl4&3zpIPp7>BI-j3Rkbs zapEsR;9){SX)&c^6ZCDH0 zT<0^@)*04VeeJ;NcwGFzll@DZ?)I3=%2M-)LL~~Kfkb$ZxQ+4{ui9v2Atm$nS=r#(pV|4{r-9RKm zb8~X0rcs?G+~F{WxRyAt`J`qv+TpNtIhQOobnR`jON`5!n@@p%;4!xFr)jwkYuTyI z%`3DdA#I5bOa@jpHm(-bc-CxOYi-#Yl2?GZY;8E))!5b8+SRydkyx&396hpWP4l{S zrzxz7EZZ0kGk;sV+Pkg&s!dJvlk3;5+^o7rE7&jCLi@%I8;tu^U2s2r`btKC?immG zw-Re9;vaW%oZi(wa#ho&Ro$!G`3AQpx6WU=dOa)*Km1#TGytG>HEnC2KYyiaYf@Wt z>1#AyoxyN6!MQkTY$reCZ^9qh2zQN*3<`jFPHAjEbA9t!&CPHkOFTNW#kz56b5h}T zCBxyf)uu(Grzqr4*Eu7*mNrj6rEzrgO3+Q_uEcx63edUdosURr$H;dn7xNoeG&lPt zWVs%6_nZ(N2|Dq3^4h4ibm-q@(i zP;+y)+9K%%ohNRIlb<0qHue}CMidw!BQM~T-z0C*$vb zWbV>s*Tdf=DXLk%`G(k_SPT`$h{z41`}mDFYIAIa=r=`njJ+vxb8Kux!F)6ETW-O! z+^*fb)ttI7_h0`yLYp%V%a{7xBy&`ckjN^@LIoA z0cy4?)@BB3>OL|s5g!t(kB@ryeUrf*`>3kaS*yBXTrW7L?ojsRXF@ALp!d`B2fBdm z-u9YI5}!|^ zkrU`{YiCl=1&?2Qr?L3OWv;T=q6tyKlh|k@Rjw$W5V11X-U(Xljkn$kx;tv4bN(Z3>DSY z&Y#XlTFq+yEZs@lq1_@e8K6J@_sW>al!hUkmbV@w9vJm zwxbG?r0)yvl~Vq{_%XcAgIB6h?~@<8jrJKozcfv8?&YaM)Bb7?tQ0<*sVDK`zRIsu+pU)RMqcjM!r{m04`A-s*#`4H z^R3JEPC~bCm?NLpv zUQDKnxXA>WWf_a*69=Is&VX$eH!bQyF+E3}(S1(WrbXwRvuP2lkFL?u8lxO`bxH5R zUKpr43@}4=4&|#@{=lF?-|NEuJO$%LFh=0zq%oLF(M3h?6h7jTL|od!Ukz?$8K|&j zRbg2KwjSm&J(a-Yak3D?3$bksau#{@Aum204Ydi2%VTgU3-17E~i|ka`h=S`3xf2EQsBps z7lML~DC!dEm*TlhL0pw^T?ru*`P?+WLtQ0wwC>n~#NF*p_=v7k*Q*qdUH(~pn;5x^5h`a3Ee;yQTCjOjyL48Yo8)1J(eOGM0 zr@pU#0P_#kkJOLB@e}Ow{#V%iR2@P-ABNQA3F_zS7kDev)i2er#J^vwm(*{-^IP>h z^?UWQ`U9x?*QEaFhu5TD!A7+|8S|e-{|os3P5rz2e`0zSTh|!7ze+0p1K4X24Eu&U zhOMB=(edVF5xz#;BvOFM8%z}8nk$NmwCQ3V5WmvIAPO7(yBXACm_p8TsswrrK9)is zqHt9w@R)PGaANM&(K)Bx?NE#*{j3zfswi9>BAczhETcPATyw3opZNJIQ6i<8~N9e#n+^UN(^*5pUv{0lt!PEZ`y{f!yD$?+3+DB40FJmt0~9U zx`YI1r`fj|<6~3RSZ=LyFh%T4bRY=Ync_@!ra7(7bll7|&S`^9yVK#!fK8{9bY?oU zoY~GC=L>4CGtW86IoX--EN~V&i=4&I67f~1N2^asK3<9RWPY)%uo=6hPM7>_Om%%~ z)n!h8?acW*&KYv%fU^d2J!6>>ucn9pI2cfmZGZLkSf8nH8dYCkc03q;JPV)ROl(Y< zma*nj%gQFzzZsNGo>HczYIn>4FLzkXhCXL59nPa706$MU*&3iTjQLq+iw}Sy2~s#mZbp@M+4b)wve^=Raq#!UYB9B@`CMFi*sbw+0l# z#z1)mXqB}1p9EEJGqU;lgSj&R_IR0zaoBS@67zoCokmTo(D8F=B}9@1L)Qa1t>yN1 zI6(i{4Y{0Eq$iwQgaQ(1q{D)b_Ln@Ma(bCMG`b@T-APDvZ9Jfd;G-2lP>B`j>}heP znAw3qC1BTOY)#PO2P4YR87*q$lMG;D7#F!MhAgo3=esxo4JZUZ!1DQBira?cW^l51q&q^xFHm~k`%UO;M^C~a7Z?0#IS9?Y=Bn|cc2G@+(}PAVmL5{ zIaSU>!-7y;A%3Gy3Dv|4!NiSs1BDhGRE;`@TSDrzxhfGZ^XO@HQGG2)1IXNMBJnj~0)Mm(Y9OhM54TGD8ut?`;oWh~vaiJna7m4AXtCsRcq^Tk_fJu|o zl^D+p$A{_?!A37u2=0bNkjW~ii2aEIlLTT+_~g)(F-_G>D|o_Fsa1@v2{w(X#wmtr zAhiaA(?iA0g`t|UJcHQ=H{&a6nxMA>?U*uoMzC^9=M><ih{46g`3sm{pV0IUwAO)1-q6B^eKaSKP6V6-28&H=sGrIxld(SZogjF1RpI0QVOKF5Ym`CCK+n zFB6-~ueee>eMf2Fs;f0>)prK2=}BFix-Rv1(=wr5fAS3r7TlP<;z>MklZ~6!3j$lS z2|?d5Mz9^eStIjq4g_w=rrjC{?4%Ft0)g8|-xb)shdRuAb^g#q*mt|up+f56nY(-w z5C}dDyvHXj^s#*8p7+|`gwc8XV_pX^=lp>a&&q&-gBsoonEFkI!4tnnoEo zL1;MGfKv_rE{$=*s*g3u^(y^2HK!f=vof?vlTTm?t0}qGqo&%JYCYFh*2e>q!E*1t zR8jda#^V8YM>r zKlXK?1Gw@VArGCCN^7oha*_^!HBl(iwCHtGIbA4SMzVpAOmG~IVJ|x)125nQsD-eC zksinl8-qrygn{-jfuBtH5#Sfuu>wF;7@)%qV<%XICRpJS0;7j;g^4kROIXmaLPS9) zh)JRkT>9mDKK?i+uT#JcD@-ca;jx4Z5bs43BQS)<DcDC4ylL86iQjFiZen7V!JVq%eAp?0lj#M=vn-R*c)XOUp_J6k_VFva+zM z4AX8!Rq?{Y_`u3Rg);M2Sy`8;tCzhi!!X%4a(GiE_M{XRj;S15Ij&{UcucTODjew* z;>`E>!pc(2u~k;KwoY$VRfVdua%5%UDU%MXRcRNR#iH)Dp_7SXXKog>E)e;Ug?<17L}Oesp6Tc zXiUot+(WM%WD$>^mZqE&@u>XhaB_Lm6m zepxka&9GrAS)BArtKy~Dq`-CcWYZwU^Jv&ui2rz1**&3X)261vq$-@=spiiq+w2vM zoSrOHTecz#>rdad^^Db#RqD)wvkK4FXVEsCUsk?d6~)UZv?fNDR9?_rzFtkQy>Qq? zl_P8COrJBqc&1ks_lmrDQDOVc3Cq+nzT1m0xdeqE0~pck3LG-~Q4Uzdc=ShKwvuz< z3Jb0eu`uRc2jI%}9N-3~aJa_j;!RJ!A%iG{6fPM|H9Vx2KGY=?#<>lcmmO9HnWGJy}Z0*hIZCj zUY-ok#3*Uj>^b3Z8#klRUog{MsAesq*<7OKo~mZWk(#y@^XgWvQZrG0> z{=xc4;o2~-qf^UiU(p7BT-(!q`a<$=)8=_FpE1)tQ=7x#v$mc+pZ=Y*EnIRAa_roa z^Ug=%HH!qee_(!xY^O9SxB!#8+Pq4sOWlhuyFARyE2}NvdPO-i&_8%64z4PP>(y7k z^AgPM*10JrIgV8>z;&WhSyzHJSL&j`VBfVSgL*yvlG=8u2g@;&=NziNlN9p>a6Qd+_j%6CY3d&|p}d#BKLX2Q6uy!`HW z>G;46{4Vdna!@$Db0@uo`fh5(!{Lhe+*9`6ec`fu%CK9XcQ)KBv)UgSd>>+HN*{f= zO?~v7bMGJUKo~dsG424o&^L!q2rHLH1<|j{zA$YEwG4Z7X)y0P9KKJ@$9Lx65yTis zScsJcES+Kh@q>CDO%oq_I0K(LKo57ymr9J@F$}gPfQKK}y2jz`k&IJqWm9irzB61F z4!e&U)2_Q7gI|cF1+LZI7sdyXflu$lhATgm@Z+DsXAYxg*rx^wvbX$7hq%5S^RmKQikcBs#MPRyUzKELycW%P3d)&joxMQ*L?0}N)wL0wi6 zqi{*D1iY^V$JOg`lf_r+#cUM3D5V(;0p-fto771N;eF-hPh&Od8Kva@#R|)0^{;;; zsGddcOWpiUow?7!vgDj|&UqeQyb#_DLpb~`lthG)3B`Ee=bSd1q9|dDax>_7BLrO# zf#keln5B&G3*RpeXwLq^cD8{Mj(;0uV=vzAO3_jf2VyjlCy6q&7hmG>4pzG zWd_W5!S5BoZ%^u1Z7#=6AfT>tFQR!@`S<+VLEDcg|31ot2?H+<-?y0Z@<*qX{tGa( z1j%~;#>)RnjTyx{$wfjoU;pymzr60c zQ_xuNdkIh97%BCe-~RTuzk|g`vVe&`KJ?=Yrvk7-5Xf61$gB{^#7VIoR=zMtp&n2+e_ZEwB6r{p3w`WNPsk82|T zMZPUA(e?4;AvoLuE8LD02;g?4<8k#z?@0;u+Wzb;?Yh?MZ?JfOx~xA*$>tEnl@$=z zEhYu0*GtR9>VL2z0tDYi{PVv+%qQ@bIzxvxHE|JyV|3AiQ>Vh)rY4N-03>s+o%Nq` z!eJ-e)P(g0?i4O8oHc8fI^~p8)W(e)IdW`j!aj43IwKef%JysQKgOVvR}pf&%ONjD zofsdK@jn0?0I)x!oPSjTz$KQI_*Yda{v8Kr9%^b-4TM$1u{BuX+`}O3+!#D$2=;E& z);hHcGb3vBXsnnvV}4lG)g=-MC!xlU#b99EI5lnBG&N<)k|j$ZKx4*?8EW?I_3P)% z!8mX(F57Jix>)-OxPd0@BAGlHB}l2M80z7V%_xmdBZnRJN;P3oxB=i`Ye+m!#cALk z5e(awFP}G0xu>4m);4n{CR-I|TIZ|zD^@ICyjU$=iiT|I%9YsS6K-iy_+tuIEnK)z z4IhpH?}!m<{CG9Ky?x}!30Mihyf`F>tXid3C6g+-Xpvg9dGn@C9Ua&NqgJo(!rr+x zYu2vC&X9HM)P@bGop$=^r>pMnZnbsmR<&&#&Lt{Lfny)ZmMvS9+R{*8pS2omW?cEM zQQw+U09_L_)#9`kCbXJ%J`W#H$iu{g=M_OFq?Oo*5@Ch*@f`!~eUl|v>a{rM49W)d zfpSZ$DEF`;+!yFhsMXY=0BUODH8nK@@c;(J2WiAmaLgGXBuOE#A(lb(K{Y5bggUJm zHBnc~*DN5Rcvu6;f}x(L_jmcKH4npk%mQzOaqcmeh^xd{P_4vA8fY42F=dgFqk%P# zVIdydJeHb)vCzkk^~Q|B-`I_X$IYHcW+56*&l}e=uBBzXH*P#M3*&)|Zy7hf#RI18 zym9aV7p;$nX4!yx-h_#=BxN+SIt6VK>7JNr=S>oB4-`$DXv~wROrA1j%GAkIsTr6G zeJbf531Ua?DfnBWaEcexTBl8$?oFFMZJO6QeL58wJbc6e54y3N?s=^yNNqzNWX}9GdfX8B=O6D#zFT;6FYEsCZWJeh`4!>J^*IU znmKdkZ2bCx*}mOuaLy9;nVx0zXzR_HJIBC0&tlYtJeQ<--aHScdGkp2U?iA@Hd%D@ zmHA$U#yxMr!iD^UbJ3y&i});9;0Y!MP!}!)23@PDy?j{WV@tgZPU2EL5T&%#^HBc_ zEYHBHo_DGz#udw#qYe~Ul?AI;t@2=8O+6boEFf8IjYY^0ZqGwKXkZ-+qC(yD$elPmHh;{UYzei*vxktX>XWs!f+( zCOX_1TkrB5@QnEi?@9yj@PW~I$2+dd0`F>L0P;=)bVkmCYjjIOjXMf)dQ$QkZB8hZ zvMtZGA*{QGLf2{Y^_Cn6TnlG6&>s!h&VqGn^Mu&R08RkSwoSB-f*@veMF`vwuZO&j zp2fB;WT6h~MomS`Y+!IugsuU1g=9mJ{6R#9XS)cnl=PtYB5;!dZQ>a)0Qh#~!p*wX zr0RLMK)p2!z`pY~dJY|>el-#5e6+uww<{ZV(?Bkvi;fwtJ>=a(tAYaAYrJb0E}h@k z2X4RPnmhO1b$37TuDkB`JYId)2fX*#4_oW^2*-Op&ye3|e0x82#)Hw=wd(`k{v5cM z=6f084;uJT4tO5>60rVo)=={!YK?-RLDAx6*p#J^?;orxv;Qjd+vDyFJu9{f8krW z7T5E>1^708*#PQyJRvc{v;m{{T?60CfcJgiKgfVb^oJIH5IwEI4G%&=33YGlP-a^M0NMzp!TLzsv&ii4pp*a^cs%`ZaAy*ZNDj@Eg`IzlGKB zeE7XE8lyIN-phZ`&RK2+gI;I~U=LdvfgUz?RE*h2l(b!Rs9oD~ilx883ix9_CXR*u zlMp~81ln19B8Aep7zzW@Z4EJ?H8uJJel#9`R4@!o9(@!6$Gt}ZH9{u_dl_2Mz9z1R zFaEdBY5)fOO&a-~N(g_HFIF3f8Y3+&t9;dDMgqhU*ffB{ezwvmfXcRkP$8<#7lrAE zfIRdEOV`-;SYRG*gUtVN10#mqc=TxktJPkM0docXH5&RboGZ~MOGcQ}CHj1cK3g&t=Sz6PMC&bb z#$*Ea^z)ZFYeKPFZ+6b4?->(&!lb|RCHizp?%5K1u7sybE;Q#yE;VOIu9OoZV|n@$ z=R??^yGErX*7lUhjp`;bbN4-eH{;<+5smG{iILmHeiu%Sk>K&&w$i`f^b9;sgnQ zU&5nLk$lCxZ@%@X&F>k}zpB1weqYB)5}qY_R({{a8I0%Ur%TFMb5i6x@+Ev%RDD)N ze;GfN?|^4UA~-X`vd@zv5u6>-U&2r21W82k1W5*Xl7y#7l=?Md#&75)vHXqVSrXZ? ztbU(ie+$^l!t)3CMjr`(6g8u~f^#U@KWoFYDK@Ry`k&RGaRNlEOzXep{Qg}^(H@*& z;g2U+ZpZnR|1dv(;Tm4^{pN|5*ZtoyAIs1zmWG?xSTS*no5M3N`lnC6V1_j7{7cla zCAb*;MNSD+g|j$e&`Hs-52su#j@k?EOT`!MSDD!9&~f6%fQ`)nN9Rhpll!YM=1QkZ ze$_Z1lmDxM+e~d2cLw@D2!8_%b~5#=J|$z{KmyaEm>6~bgwrwnH9Eu0k7ryasF6;S z{6;}s@Mxs9*%@PgJgq`sT5y`ho@d#mc%nuBGUr;_od59OjtzILnub#^Jn6!GodLB| zu%u)2gZj)I(<}*ZHcrD-$!Qo{PiviLV{$3krulGd%?pHYq4>54!^l73EEa($YL@2t z(dDpw+qP?&oQXOGF)enMJEuA;oR!WhXSK7&S?jFBkEvS?bLMxNvtHi7hX2pr+rYscUSCg=f5L1`rjuA6ZQR@*e7H6 zl=%CUOG_m!jD@J}-Y~?cWA<;S!Oz6*0}C}gJ^1V}mz8_hJv2G!^uT*gv}558<+N#6EoGBY&k>D7~fF>-U}imtuHK```<=TWFMebw*8Ss%jn^zoBVpb7_Nd3(oK|sP+YC;U z-t;COfU|FgV`rZCZ^h&0bo<=%&f_$j%X#O`Iq$*?h2a}g{ekp(;hyj4mWxVw<-+Y+ zz8O+DabCQHGqjgtF87<)1#E9$%5DBvTrsdhXVa_Kto`fMI?jo&wjr)b@e=&hb*bxd zzJs4`yth7FZ%Cy!8FORmCP(!9Xg53e7R-CX2)tt>v|G!0x7_;vZK)5WKKP;A&O7hJ z=iMIl{>b)J>Z5n?j>FVlcklSb-|$Mq^HamxV(rv_O{BRFJQ!_?qT4_uxMvpFOyk#()n{$3OPiIseI(gzezl+oLY&S*^ zerX?7vaA=QuODe&mVI&#mliHugwbIU=jLzGF_Dgl-ipz|5a;KMmtb@p#JTxW9RhK# z-ml{y9r+Akbhe{&8}6yQawSGbHmfl@npum{naetij$Cw(auw!kjE+(^U~~qeV-uZ@ zT#wPw$U8Cb!feF68*>9jqVGn`O&G~N9TgaP_a5FRgn1ukD@Hr$dW+BdG21ZO$^Rhc zLzvqzAI502^&^<=n2%!az zKIK1Sv_1I~jJ73UCJ!@r`}tclxaMyeH-(!yT(h|5a2aBZsv7O>rCusPB-(ppVR%kuDM;t&+mSY*F5hhdd>6RXuh{IzUF+* z_ywb>-_QG+`R%lC=lq*)nmEy}ckH~+N=Ng)y2=wsF7$#1X&LE`$mB9qH zdc(wt(i%jtT7%Uaq&Zl}3o2IThVvyVI?*Tjj^J7oMZtv`>I4)SgMrH4opksc!Bk7J!W;xrPglX$(v z>n2`5`2p!jN0D*ItVUNU9JNlID80p-!jY?ND&@q9{@8W@e(RQQBNI7(m35+Y9U196 zGQ~Pi==P6i>(1!H8+!ch_j*H*WSNy;_WA0<7KQFv)fNTP#k{AUyWr5|(c#hGqc_W= znVW(B;uoW{OK*=FD-|RdkOg`gk_YK{dd}$Q($SA%jQ%ba-rRTPba*@9{ncpnQs=c* zVRkBbW5Bi7U2kuMddD^FP+arwYi_`~iQkPkZNAz1aNQExLJO+8G4FL0jaiwk&TYnQ z7@C)Zejs!hi?sOLuKDma{$`1&??*mz%{9Cp6g^&A{GEKO;qGgszmIB+RzK`Unj!~V zAkhr48@)e5+j-4r?u$6D(HbCXG_Ip2>blHG-)pBzXEDm^yjt zSZ->Z%rg!X$4(eKcG7Wr@*$WwdF+@tZ&Zp0WmDo)ba*gDk3dvToH*_Elcv3*Hg#%jYCJx5d@PO*TQzm+q~oR@S9RQ^svtg&!j0$K z564X%KXJ_XG2^J<)Wn#{$4s6QJ7H@1jfDMbC2c_13AcjqA(HJ}6kt zFX@AVZ;;*V!$PkMdtzex^vdbUWMX=vGLe{`Br;dID@B_=J^99DCA(77PkK`!=Jb;Y zXAFrGeEM|jtgJj)*;Pu1Hs+L5JZc*Y$EjvF%Q(1bPfI45JT+N&TIK0=b*H>JF>@yQ zI>QU&6A6=~F4HS1owB7y_2imJ&Z@1QjhkZ17(eZinP@hNnPMr154&a*egs!@I;tzqYpKxHvB*hf-TRSMIq2UQ=Yu=?a;y z<#7dP=9s7yyiQ?5lda7e4|~bA_VnVF>*?)L7KT`BS+5U=N_B3Ju5-HQm?D}GGnDq6 zITWQ%@w4+6%l8u8ytN&4{=Kdo^2(_kon$XZU8~7oWu_1mp__uM z>@szAJ-G#SJqvnFx|F}JZt9}u=7kqi8C!2tR~uO6=%%d})Mm99q#FJ`>}0j5&V@Iv zR@d6w)3YGAphw~6FW^E0a>bam=5(vwl&@CU-`@V3)%bu>GU zy5y4PS{9xr9SS#fDvMh_zC{wgYp~6!bK@sRmhg{Z)Y`(B%4+F4ueteRQoW@4IEt+J zGcN6|B|>d)uD8{elV?h2%;+J3+SZ=8UP|>y$&I93ue8=nO}L)kW`^<^jB1~b4(~xj;=>xeu+6*>+tZdVbNR;mm#Z@| zE@4WZweH#rOvf+|jG5z*02*rQx|}Svweh}qQ`)t=>3_qp6z_`o`L(GT13ptKgpn&v z5do8~25qiK3{2~g$HjGa+`3q{9Al+iTb*SIerSR+%HMCJ*Eo$SaXp4J!VcQ|c_;oHhLQy2eKKBI1Kr4PK>k zU)|VvjgS|e@s#cL?~pxyEYI7<AUEwk8+V4O8#l?WOh& zvp3D&WZJ=3s`I2CvR%5Pb6q_4k{9f&56VtXPn$z$(`2qm6cPPZ#L<3aT_lE z{afDC|6W>zM;Mx$%bT0uH>DYi`KjZ|o8Kp=jFhZ`5oOF66Qz0UEpo}Yuu~MyQtUPA zG##Mvg*2_R;|!ZEmy3e~+Z4IX#gQYaPI-%?3GDXc7*{pxQC@!itqPAZ-sRV8_r;om zhYdgwEbpV#+r$GhGu5w{E74-4H=w*s$5{j3+}wQA^bgb~>tNH%;tJ zV~~8Lrlz@n`-K{(bI$$f9WCID85h>HX!eYlInAaiZE9REHjU(*vVY7FrcRv^6)ZFE zbV8%9PP!B(J^SN^-TLI9fU2KiAqh?u7**{K@$4xIfbqJc#vtuyXs6ya{Yn#?@P;r` zG3)ATbgJ3PpOl|Vdvg-J6s!4e{ASFs=^Ke*D&{4Z;rzIilX#nve=4Bn3p?2uxl(ub zj5I<8VYovr&kY+^u1Kz#fXpIj9?HikUO6Xs+cn)zf&Yi(CjN{| zYkT4YpD^)hb*Vz;r*PDxC%2=Q^4nNshqg0ghF{?8EKf$|P!RE&35g;~ADT(-9^)zg zVG2V{GR7;$Hrb-?o-xJ=cpG-c-O>X;^$x<0yZ6(M``_`Ycf_yV89zN9zwQ0+e@FZ? z<=dL*LGo~M1arF1cIyqwRmmm*U%j+dZi$4#TBH05zd3c2?pyfoDdq1oW4o)d*%im} zB(;d2UiVqca&?B=`}^N3)ykU1ZX7hvqW^6LKcxJaR0Wu`)mXCJ-`{TnXt1h?kTl23 zpi&vF^lasWn=5=E!;rN=ch{avze%_CDkUy-P{mQgVit{M6K}@nPE>5Y*Hfr48r=pV zh&5!#Ebe`)jiIX8UJw3aaguX~>^JZ~z{SjK4 z>zZrlnS@-oSUIVNH?yaD!5G|ETB^DF%gjU_PdJ~!hc7TlOs%&3ii=Nv;e*K4&qNRf z`%GnGDTd4iLSeCI%24gSgj&g(Ansy3J@I9RRJ5cO2kHo~-AZXT+zhj!F{8oP>G%Yu zgDwMFiLV$^JuyTuTn3h#R^)?8wu!AghVLF0oHhN|Z>{L>oskta0j@w+hMW4{YhZ@vst@4gLEZ@vz~izD>q zVROy6uY@SY!k0ouKE3Whw&vDfABu72Za(tENIIQ18 z?yDermg8YV`=+@*Vy=(6Q1yHrM74g5_jm2Z_8p!UQGELxho0eh0@ptpTD^OM<6+YK zp=lY*3r`wfJ#ZlmLZ~NUan!XqEtodrlzjM_$LiG20^VEg?Hi(|8&@&a$uYts3nZQ01 zG5k9q2|gD48lHZ5f+rm+x$4^2F+$PP3*%!a8Oq7zTEp)Yo?NgctOe^_=-2TS!xzG~ zwmoI9;@#8D-TL-B9llkC`euhD&1{~G(4W5Ef#l#x2K%Qz(U&~Vqx3>v`_M(}cIXa8nKSK+pwdDXHq;9lI#@njja3*E0~+fqe?Xwv&Gr!q;BU zKhy_rja}yA=y?a_ayd^tJWOjXi;3&|q3Njy<=%Kum!5#o^AGjG8WX!d z@XtNyX@{$6eV<z6Jfn;vkCc#Y44k3$zV(DH$ma)3Lnbitvo~F=TbdU@j>E#h+kXyG{tsY zpA9}5({p92?eO@sf;-HZ`WWBr(chgsTXCUl9rgcR#J=6d>38wlc=n>6=PGR5)d!!z zRUhct3Q;s3?lD~NbNUVv&W6?XQzrDiTt98X*9SYXf5xTe%XeSs{%q`i{681dvl8{e zE`Iv^BKReKUv}<#o{T8u;ceq%dNxAg^?Zb$jK~;yT5q0@P@IQ(&Y(W{``E*=JubfF zZM}IS!j@VtJsaWcAh-W(BaUr1d;J!v$WL_tXTugs=i}}Q9*g}$V4t?|VTIp~#Fg8R zLyL3FX#EFseS&8zz88A}`#&1@J`>Z2|GrDdyCp@($9@nymS-dqJRR|)*pGRJ;@IGy zV*6wN9Q&8pPn^$Fv7h4qv)IpL2V%c~_DfuaI0@zi#ToANE5bb;``6erv0oGVAg{(p@hU?$K|A-wjf4`@N{!i==vFBocjQuJ0pRvQS?*@P7XWQVvOieCy^|NK4 z!Z(bbH&2@>%n*JV=WoMlX0U%ppub@Jrp59onW8EU-DGCdDg&)d9fPlYEIkt&>ulET zuj3qbpP7k{F)8}ogymtZW1XLmDQWHV_cSYkJqMg^LRgp86RiC^t~NIQc+yS83x84V zcBDNML}k-;u?c#U$#CQE|Ikwj{`*Y+?ho^I=IQo*`fRccdpN~Cn!<-CxOYr9eQ?W1 zx;>LlH_mNr^lwQ__w<^lO44a7Q^4uD6zdsDV?E@bS?bed!TMM^$e58Z>I(RVUuDhe&J3i6Tp{G>t?fCRgUI={u z=RW_14xhfkUBg^BzBv6$(FCw7M3naBjt9OH4KloKRz5hKIdFydZ< zz%lVSdo$AU7A8)djHPPg#1p1WRLEj8^_Xd|cOlKoy?v}#@s)3Z>Z2s7XGvbfBwxf& zUdhwWcyoPl2Je>Bh1c}Ic^1Ff{LbVj_u2d!_?;8*@;UwN#a%swWdAZcUW}-OXX$dL zE@yM8C-r(#t|t+G<_h(U+5FDZ&ydb&2)wVUiEm@Lz@L{7PMI;G7I|bnZYcT zc^2iJMXIwX=Pc6XXD?jO4rW0-Czy@@Y{>lVh3gr??D}9fn*g&^mVlQx&L+@V!R)hx z*$u($bAmHzfHO(-%$fX~pS{cs&eFg6aXp(LX9Kb-Azfw$4f;1fdzl%WLkpY(K;>sI zGlNu9c7D1e-P#+Z(rxKfS65$WQ<{$pq}tO9gH%VVyPa!ud%82zoa%^Jdlq#zWjhE* zTwQv5(>ajnT)W#-P3hiDbGN)gM=sry?&?kTX0lza*<7dM;zx{hF4G*OI-4?Wec3+9 zUCkK+w&l|4d7XVd@++p0QP!q3%r7jw4Ih>XLM5?Em zcY>NLz0#6t%MeTz=uOe)y(HJ$MBmT@G=6VyitcJL{W{#0%e1vCq7BfL?#S}ZfvC%} z!TeNPF4a!z^O=5Cj`=-&r=UJ)O7Y*3F_$j75=&>FxpdmAsv}xwq&7_{`mcjN@4~A$ z#Rm{lyech~zs`UApR*ZJq~vt7VB#A+p_BbLq^s7A&wsNW^aV0YYC_ODeah zE8W+dgZG=V3tMuj1sRo+1~M0V2)n&>bkHO?z;2o~o$DgUTsk!`)vB>!tW9Y+U%?W>7pJ;t*R&lX!=0%P zpJww(L33(eCzme$QZ29+yg`#^x~P;V^(^Y>(D>*PCEH~NduVIUGB&%YI6X->K-VRg zF&C3=E|*EQrE}@tzMQh@Nw>IRBzvZ*}!H~cP z&M{y^BZWmn5F4<>*~W3Ext?XNHcgwDiH<}kLcPhwrdw~~BH=|hagp@0o481P*-c!V z=PVP~X3QLbFSCHIChjZ~x4}@(A!Iv^o)XaX2)VX&&w}=JmztwB+kv<#rgo;fyN6R5 z80nm8%V^l%Om9be1Qqd72n(|z0dm=Sa7l9}*Q|!0%l|z35zZ{wtP~DCGEJF|Oz)zC zzax|mmT5_65ft6+J&_16N|SsbGb4K~HaRz3Vd%8V+<7^8l)0wI1&=trh$Ikqkx)OA zb;#*Z?WC0IYU%FlYVPebbB)sM>&mod(k;<4!}}dsq?oyOr*cS$_H<8%Bt;$;AC^Yw z5FyJy{pp7TW2rfpVV+BMbf$9ii0XaXQyr~EBsmKKj3*5n7M@q3X356@axBwq=Ns4d zhD@oLih8qjuj$CSsZLWMnq^@#Vo_2IY@tM1#`fG)cS?c;A)b=}!mBIYO!Q%O%Xak; zn0W_pYimiT=m+m=wPM0M+wt^6+tWH}Scwwv?(Rr6r`yHlCR3YgF3ntD2-DNoG&hUz zGC3i|+Gu_w3l&5HzB@zzF>&JVR^j?2>)LWzMF{OicYsxbW;m-mN4UPObVhAfuz8)J zxeu|~)x5~IIQ~&5DJ*Di)rFV~sLKM)sBh- z)-E`lf>BHoat0Ji%x^V1^Z-s z44d>W>Q3X|n(FK54drxmwk6$7@ATr+tzQm_(@S5qz)lExaDK{Mx>9YL2jsR^@!&9* zol9YmARH|Po4PI}B>6j&2+#bE!jS17pw7DyH#$i{i42X zFLk^qXyF#NpoRZF1_#w6#UPzxc=RwQF37Yn9jDtCb(>2sBz7Zm*|v^F5^?FyEaMyw z58xsFBqV5mtH6#RNTW4DhXqqTd{l%|)NaRA50VQp(5nnx7NN)@!ASJsWG@(PB|wTjxomg1b_mkWS&&zrA`KOJA`ynj z>PVqpBdV|)l}kif;8U6-XoVrtTys6rdV*H$0yIe@lcJ1n2tDb}c~aL~GrBPt8Pe63 z>B%xeh)A0Tt+|wb%_hs%9zMg?*U@3Sy)D%mv{9OlpsktzrT}r2M&}dPw`Cdb&K=FO zEuHO5_o|=UQ{6Bj?wq-_NqLt`7PVN!?pv&loH|l%=8|R7rGMHw`qDw0bV6N3(Bz8d ziVBT~b2NAK_0Wn|RC;1Z26eYB=K`{7!od}0lJGQ1;Z(;Px@+zhxfIk!@0+X1B@?vu z&7~fFxz4_Mun(5Lpq-bGel_>_w+Z%=D-G%Kbh8Eg{XZG;`9jObZi`gjRM(4KC} znM-3DdQ6%=HOg<7pl=! zr1Kj)m9qBvnVyWXv3y4du#tmIcS_u8A>GwO7CixjS3eD4irGu?TwkZWr3niYkuGM% zG`B67ODIHpv%RL+J%G;)#i|v?4$ZK_+}>dB{9s;+{|p5OSl%*hC|S2hKVn6mpUpHY zJ?u?=U4piSCIaBqR8d)FDNVLc5J;^5y5zDJRnyzExptzpMZLS*vt8OaF&u51VP0wx zZA~_a84_$~$*)Vcr`;5}o!t`%T)irZ0}4x5E?L&0EsVQho(ViZ=r}2m*llSCC{{-* ztDi2YS7$g-^(`SHAru1Wk=x2%uiG4AawJm9abt{u@)^UJV z_8l449&Q87Qk-tp(HeAQIw=*GKCWG|cBNCf5Z%yc_se+{bV?DdV3(~m4cp67m_|D? zJtW#0bYv-1woU7fYz{4(xioFYB~-U&bP^1AL?U&t_0WO3){&#bdxH+xVZN7*SVieA zxED1Ok_+RxV^NFj=ww|%=Se|ls(miAt4FJZF?+(PFc;*m7ITq&l0y^zB3mE1Nz>>}o@h+P9}xYNrIh6LH8!kLTaSaklL z%zUMp%gP;9@H#ULh0cs$++d?iMR3|kXGX3bwmovRsj;TnGU-aQW9eBz{>4O9zeJSY zbaT7iWl^L;m3vYq=?J085VRcf%WcJoW*JGVV-cmywrH`Nb1dMUzDb>LFM`H~pfaK@ zVnl>d)VcI9s)>4>b`LrirMl26JsLsaXxQyg#uL%gbyC2Bk{?!6^`MK9gCo5_>@4hM zmke!3Ld25hWrMDHh@q~Ipet)O?S$GJ1KoIL@rPVub4sb9#?iguIt41pWxM>)$J*1K zlCUkep05_;s|v_*#I- z+LP^Lcxb!Xx>*6wGlA^(de#i@AS><&7%*MYiP~s-+NyVr! z_zhJPie}}!!3G&t9ffo}YXXK_TmfuAoAF&N{$cafB7J1??z8;+C{1jP33g{#*HF0(!U2T<{lWco2{P&eFm_#KGj;-QGod z?OAs2jlhh|<02Q$>5*AA;;C7;o1~}^e2bugYq~pf6edei=uWG7Nu_2JZ#dCUUo7i; zBWhkZDdzZ3M``TDFkGQ(fnU&UBUU!UsBMnLKsQC`!>--5;G$HjS(gl#R(_}>7n$L8 zQD2}%Hi8^p3vI^BsYO99-DdPgqnnxqpeS0(^t5Np{&)^8C6}J7bwMsozp}h$Yr@Rl zepDMrZ&q`(^|1EBgdPdtTO>jXC-mH0Wx~j3BIlP4a@ls8d=YaCW$0s5Ul%jrS%bQH zKF1znGag;Jpy#BZhdnZW?P;!5l+oNJ8-AMWds2O}_2t-=K{F3}!XeW`v@|P#o^+cz zlL)u;bTr2D-6;TYZqU;fu(YHBiQkT{tsL4@3%IZZ?rDcHq}+C-?fwS#b`h9e2|q7j zaPtK?bG3`G&^n*uvf0x_FXE8mLLBpajjJ!-8Hp7rmHycda z%jvm@e`gaOXZAsWY>hOv-!@y3M6vkU=(LN1%b7e+l=O#hy0BJ{PEu zLrA3**_jS?v!G`ItinlA(6fktSW*|HEP^b99ZiM{+szIZzz4l79nb=WP3FQTR!SD` z*=DJ(IX0~;GfJm$euhmIaA9AnYc8A* z9ky@kW0EXb&Fa24ttedD1ZKadBU zBKTtuH^UUvmq1n{YkITYIN0=V;b^Uwjrynqsu2Z_Xk>`>m$k^(h16jl4P_P<3}dMj zIwlCLJ)2WB&TWd_VPoc)Bl|e3F&C)=ee9N+i?q+6PiujokL6|$Td(LI#itYySi&vn z3c|V1)qXzh#7`HPLSnZEWlnqhBPl&4NCk!t=CgUPN6r(L}mfB^Uz{t$$ZwW zXb>#sQ@J*SY^fRz%CzfzRv|>umCa-6hBTUSBL0UHOxw<<*c8*8_$+7&*f~lE3+4t3 zNYUzmvS|`P1T2(BrHfZWu=j{ywUC9~H0i>gzJ+}8GC-U!fc-TRu=fOuGW^qOi!z4) zEpVbPZK2cm+M>czeo@A+hKSq8npqb_{>3K+7pD-y7sIbyC3!FI2rljpF765VCjG?= zjMxk==KW)VUO>ieP)4aUdcI%q6m%`0v+kW@TX@(;m|HHg1s&-#8?KmJdW@E)O@ow4 zXLSFjqxd%;#lHoAf6^7%r`I5iZsD8yj23Qqbw(W5FtVaTBis)6Ye%!e9*XrKx}(M+ zh2N42mEj(hMMe|DupV$~z3+ozOSouY7l5WU=4jz);*sHe8q_VaoHOB!iaYu_jF~v> zZ45eVEYzVe$=Uo|r~705!b!j7WSvSFbM$al=SM0T6PsFg-XLGWTNMj}?TMlMHtgH~ zYAC-O+zIXjcY_DPyNh?unOD@ z&IC6cPx(ZjOupdZD$?a+!|f-KF1Q=q3sy}b9dHZCBW1zisiXrgoJKm}&esp+*MfUb z9Lnzk_g7PX@E}QRSOX4#4d6zw9o!Bs1b2Z0;9l_X^r3v?>j?Ko z+7a9hZUDAE$UBXKfjOiD?!S<7gBu#jAFOF6A70AT05*b$)3hU4-VWb@8^H2u^dHy= z)?}z3H~?+~cY=H54;})m<`Vw()DLU`w}S)VesH_oU9{7Q!~?6q-QY~HAxk*9!5v^# zH}w!5JR~|evl{nB^f$O6M?OjDJ){fP^b#K20#?0&{QC$G?gR(G!{83EeLmqtUqHR5 zlg~ox1uk4feZlP)Q@=M-|F;kx+;9o}FoS$9#SI>QE9t(8`d{x-sc<*NuM_d47)VAV#-3vK{+g1f=JqQ9H|sDlnR zfcwF<;FcSx7ubFy?R*;H!5ZOB_=5+*EnwAV$^k9}_k$b2!{AP^@^r$1jbP2q!~+Mw z9pH9wH@JTb>A#tHw~!vV9ozx#yp?)@3%3z}Ch2^Deg_YO+raV45{^rQOdZpMQW)z^cb754Z(92o8J?|MMv4KFSO31$To3 z->2T-L2%~zxPL%=u;z!<6Ri3X^}K*~0~^4Ge}W&t4f~OIbBG6S7yguV!1kY!&V_{k zIrRV!{)X`2mS>?ilJD=SukerXA=q%3_DWGdumNoNGx>vu!Chd@e-RGc4VE|Iex7i` zA?g8c2X}!Rj*!3b1^O4=Y=3?ze*jzpWBl3$yqyx;_=0+Y zHIGpbumRixZUJ|K?cY6;KMW2$aU|b9k9hmY4?GC&0?WTox?l}>0Nf8&b&)} zFT#D8`h$nTM!Ek?{pAMN%Kcx|Uv6-R+|N^gxxsyM4^e-)!61kG2=xaKgEQrRf%?l0 zE|xn_{pAL?$sN3q-zhh^NAB1Q`TcT(hvbgGkT37S4JN@2WiR9#OH0kG3}uhK=}*#MsPpKf;m`t>@- zEc6{E=wqnw_7dq#gT4*=IO2Ju^3R681^ReT1V!(Fz7cv^5q%l-4bV}sLZk54yYR0K zsWzS4T==O)^!r_Srk2puVS5z1>iaq{NL5sBj;AWBHkD;6lJmw_R6$5pl(#2r6!qzI zgxfxDD353jg5HYCzVQ|1ZO&iiniQvh@IOxe&WK(IeINAVer|E$XDck}T~<+U+T#-F zhX{X?OGBV^2BDW9Gn7YF4UOnqp;toxKuERW?}5G@dT~EI1brLy&quHasA;N5HdRy+ zp{b%gmAD#ui>H%-rO!=VHIm+{_PcsS@HFk9@+^ZP_EVno{#)g_W@NsUGgGRZl&3Xu zP08|@{--=!jvdM~1qH#Pipov#w?0BqjS+86V&Lq?|81fa_^GWT*&FgxD$!}}Ey`=9 zVKb~oX7m#OAn}ceG3gJ4>6`w?zh?YUevQe|UQGW(-w0iM0N#jx5A^+sp*$i!G%Dvq z(32B}@?EZ7Z&g3vqJG{wrlq20^H{oX)42Ze6*Z|y&)Sio_(Q~>`I@2p@h<+>cuPgq z=CYQGTCF zT3LR-4f=lQu1k!s+Tnia`%2Isg}%20{VC{sO3K!2jd7^)cWXSOeqngIerZ;}Y$)oNbmE;wl;%WyWf3Wzh<~SuWcza(Sv{`u zR}SS-nVFQt*VlTsHtqc^{`>I1TK>+cUB?{5-1=8Tc~sueh&~PaTIdr(s_mcI&Br>qzHO($U`4GNo_EYp3Kt+`rB;9`b*#V_b!Qj_`X4f1AP^zMUt&Zx-Lj zFAaIsG_2}414e9^IF#S&!rvMv{4Hf2>Q7TnGtT1OMIAFQfhR={Wv8Og;5SHm8%S@J z2usvYG$P`yGKH9EPSBcQ-3{9__fCm zaSu)$^7()21tDv&z|4u`3pDq*(2~6jZe(5l=@;3JGbdzPge0 zwC7piU*xdi-z#lF4F6J1r^~d`jcpL<{$dSa>cwuEW4O4V?aPQ(?i=DmR`pw=}CS(Kzdat zI{m`S1qvj&5S4RJ5w4qX^OUdQ4@$SG3?ag_60(Fm?f97R8srDz|0qIX{F;8gIBdpj z;vJ#AJ#lSlw}PmSsJ*09Q$3W|%l#vKiIj~0+6JefPJXW>$c=>89{oj*AEM*Qjr*DL zPZf=wc`C-RCYviJ9!61+L^S7Co%Kj~8ixknBVR|tEVvFV@zj+Dew~X|3hEN;k*B|nS{BOj6?d(-!zoJQ{^!H!92TJ@_7^b=FE8W_=;q+8L^D|cJ+pH(h@3@%=!EVNoNb`e8#nJ zw7*-eoNsiBPdJ>s;;4D+0pcG%dAQ!F`aTZ*5cDs(bl)$ze5>>>x9(|;tb5jyL&L~* zkIzTtoL0#fyiaBQKfIi@`)29anvZ6deOg=)l>~N5Q@>q8{F!w_`Q_M$kG}z07RF;3 zq>bclb#~?!g5E~F0peX5#xruAe#?dN+7p+Ac8z)Q(c{G1K|G`XbyZaM((Dz`WHc_H z#lFY;7shv&`fs`EcCBEnQTS->{{#z=l&=}wgo4nQk34e(2 zr;A2;--@sDy$yQ#X)i4ug@2UrRfIS7ehKw@j_@@vF}&v48LvbCBm9G`8^!k{*3txhET;`z0tpCH70&67)qeo&AZH#M?)Z zH9AzD+bGXK{ZM|+f2%yq%*FW{Ib5Qgl&3jy?TFwikNRl_8(~$mqVniy{j|!ov!sdQ zFC%_C@pIVKPf>Yq=J&RWnY2^-A0L9At>QfZc9>UAsI6z@6WH4rZy#xwdXLVVL0&3QI(bK(+XB?-bQUL6eFO}x2byb<}4 z394!&UI$^95l?6EM!%V>{eTYX6K0==`OfXr#6L0q5wwTL*s6IP{o#A?=@aUg_;suY zAA9_Jw)Sd|2S`t6`9_~qSuo<8$D!|ouKn4FoGQ$JhL2m0vhTMx$~R1)X)|Ej6T|l3 zEFHc{CpJX*#*#fBU&1{G8_ycbpZVV^kM<`KurP|2iTw6t>mR~9`nh_!3Oc=T;aXCb~J4#GR ze=gqHFp9ML^G@a0@V}=&>rO!apYy+`KOdqzdnnJ_XshA#-)QqkVV_pxXo&cSi2s!0 zJ0tp}Da;4w4&{I9iJ<9!=o`-)$|u79XB{_UUBKqSus%*}+36^jcT?KCDNxLA^;Hpq z#*gy5ll+qBNB75GT7FtfS}yZrcUTF`sJ%K8MER-S6F6|$M}E5^_3pqv1Ny)PL-|jK zP^Cv-FI4jZqQ{r!Zi^ae?9@0?dAJ(c@W(yM74%6~CZZqc7oeV~t1xt$UH zIpv>1&x+8c=S`RfKQ#^Ib*@r!p1K|t0^x3Jlu5*IwQk$W?3;W%bkoLdiTDRYH%;7( z7RB7oZ;*Vd(nI;PwIN4hZk=MzXH0t4+xjg(}ws4y5*E*iQ<}1;4rVQ=weu+{lzmGsVbqwIs^^qjb4i%p6h_gK{+| zMlaWmlvG^}bwhw&Khevcu^FxF#A4w)-jPk#q{I}(X^6x!* z{%y+twmIpI(J!f}TnHT& z4=#az2s*bOxqTM;8U0A-qcb2~kAG$FP=3Dr&3VN|_|Hqg@8}ingtF_}dkEJ~xHA>* zBJI~)8lI=khV&@@1NdJqf3pr^7sBjwxs7Jl*{z9p8LbSfLK%H-hamr0m3=R-Jf{A{Yj~OQCXwF| z@fH*BQ`o%`pG|rL`zz4DR)Wt)oF8wA#SfI^v!(>%vH_JS)Z8qaGsYH`qT3RPZ*C+1 zh6O|U)gqylbBcpZ6YpfqKGXyFZ^8eF{7H1H&imcEFOE>EqRkO&27rjxtOq$L;BG6CrL{RNq2YoH{Iij0>HS1>f+qFAt7riYB)|ip?uj;dm zcpHevbneE1Mu;`a??&feybp3G^likuP(cgz9Cg3ual-F-8R3Trzl-o^l}NwTeofsQ znI8xbghumu3xxg98yvrsTHn1Dog_TAp>yDZJ0a0_c0y(0WVYVKf47m|-bLISI0gsx z9L%q9vrt>2Y)IQJBl$0-Ly!_N?7p4pe;DH6rSAR@ajIG8?A|DZT4SZ`WJVw}!Xdu>HklR+kI44o>5rhZNm#Y>{Fi{(PMD zDi;ssH!D5EpF}fqFn$LNN==Y{Oo!SX!eQ2`s_&RLAwQRlJRh6}eQ^Y>X`!r5(z?%+_gfN3hy9`|#p}JIQC;(xH5&%;!@y-S&zB|YGfcc}m)XWR}q-%mpTEM7j8|GP0hf1`Jp`MyXFN*^k#Dp4OwfU5Cd zB}l(mRQi!>q=MeTei`R{n!Q2x6wrJc9M7M4tEUZU(7m22ccFzZaU^O%#_Z(YSa z@KWlDUhzW7jHu1Sqtzz9Xp|^Muep)@8~%DIKYg@*Hu|s|SB>$zN~Se05$CkDL|f7T z{iXZ4i++|aGp2^|zJ4fw1@>X%#_Vg_VdHOnQTW+}uNfT5|C7QSxm?&kile+#+4;u^ z6!qgW!tW=%?h`APXCu~6v@f$(iF%|HWnV4bkxkS?`8-ZOd#)bJ|GtEL8j;Vo*gH#R zgZiE-olRJu*{3l6Hw@)p``@k4wWTxCL}2)ze1dC-@_!%Jr!f9X)F+-QSt0oHOyyHF z$`CXX#pjd7m{Y0Gb=-6A@^Sk*W`EA?>kxI*xcE(06o)%HMoy`mEyN$VeklLzV{jDB zSA}(xThA>n`+kYiFy`UYJ4(-3Y7fm9_mj_|O+)$LV7K`c=G~uvpAtFIj5n_P}o|=MTfi*&Oa*QgUztgS+xQ?C*qpU8;RuKW>bbtt#D-Ebux?W@YZOXyE3rB8^ylsCL;( z{yW|~l>aJr+b#vUf(VSWnvu3-r3ncfl9e!8njJUipGJDOa4zP`TT1VXZz@t?+zkpEch?ht2k{?!vH09yqRp&O0dny* z?j9ok%v;fqL-{bO9@560L#6ctmcz{@D{A*^I>=`Rih23_3;B%L_qFojCq?q1Rkx

EMkV5y+x&B)IWxcga+-f7lF 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 diff --git a/lib/regex/__init__.py b/lib/regex/__init__.py deleted file mode 100644 index 8b137891..00000000 --- a/lib/regex/__init__.py +++ /dev/null @@ -1 +0,0 @@ - diff --git a/lib/regex/_regex.c b/lib/regex/_regex.c deleted file mode 100644 index a40d2091..00000000 --- a/lib/regex/_regex.c +++ /dev/null @@ -1,22557 +0,0 @@ -/* Secret Labs' Regular Expression Engine - * - * regular expression matching engine - * - * partial history: - * 1999-10-24 fl created (based on existing template matcher code) - * 2000-03-06 fl first alpha, sort of - * 2000-08-01 fl fixes for 1.6b1 - * 2000-08-07 fl use PyOS_CheckStack() if available - * 2000-09-20 fl added expand method - * 2001-03-20 fl lots of fixes for 2.1b2 - * 2001-04-15 fl export copyright as Python attribute, not global - * 2001-04-28 fl added __copy__ methods (work in progress) - * 2001-05-14 fl fixes for 1.5.2 compatibility - * 2001-07-01 fl added BIGCHARSET support (from Martin von Loewis) - * 2001-10-18 fl fixed group reset issue (from Matthew Mueller) - * 2001-10-20 fl added split primitive; reenable unicode for 1.6/2.0/2.1 - * 2001-10-21 fl added sub/subn primitive - * 2001-10-24 fl added finditer primitive (for 2.2 only) - * 2001-12-07 fl fixed memory leak in sub/subn (Guido van Rossum) - * 2002-11-09 fl fixed empty sub/subn return type - * 2003-04-18 mvl fully support 4-byte codes - * 2003-10-17 gn implemented non recursive scheme - * 2009-07-26 mrab completely re-designed matcher code - * 2011-11-18 mrab added support for PEP 393 strings - * - * Copyright (c) 1997-2001 by Secret Labs AB. All rights reserved. - * - * This version of the SRE library can be redistributed under CNRI's - * Python 1.6 license. For any other use, please contact Secret Labs - * AB (info@pythonware.com). - * - * Portions of this engine have been developed in cooperation with - * CNRI. Hewlett-Packard provided funding for 1.6 integration and - * other compatibility work. - */ - -/* #define VERBOSE */ - -#if defined(VERBOSE) -#define TRACE(X) printf X; -#else -#define TRACE(X) -#endif - -#include "Python.h" -#include "structmember.h" /* offsetof */ -#include -#include "_regex.h" -#include "pyport.h" -#include "pythread.h" - -#if PY_VERSION_HEX < 0x02060000 -#if SIZEOF_SIZE_T == SIZEOF_LONG_LONG -#define T_PYSSIZET T_LONGLONG -#elif SIZEOF_SIZE_T == SIZEOF_LONG -#define T_PYSSIZET T_LONG -#else -#error size_t is the same size as neither LONG nor LONGLONG -#endif - -#endif -typedef unsigned char Py_UCS1; -typedef unsigned short Py_UCS2; - -typedef RE_UINT32 RE_CODE; - -/* Properties in the General Category. */ -#define RE_PROP_GC_CN ((RE_PROP_GC << 16) | RE_PROP_CN) -#define RE_PROP_GC_LU ((RE_PROP_GC << 16) | RE_PROP_LU) -#define RE_PROP_GC_LL ((RE_PROP_GC << 16) | RE_PROP_LL) -#define RE_PROP_GC_LT ((RE_PROP_GC << 16) | RE_PROP_LT) -#define RE_PROP_GC_P ((RE_PROP_GC << 16) | RE_PROP_P) - -/* Unlimited repeat count. */ -#define RE_UNLIMITED (~(RE_CODE)0) - -/* The status of a node. */ -typedef unsigned short RE_STATUS_T; - -/* Whether to match concurrently, i.e. release the GIL while matching. */ -#define RE_CONC_NO 0 -#define RE_CONC_YES 1 -#define RE_CONC_DEFAULT 2 - -/* the side that could truncate in a partial match. - * - * The values RE_PARTIAL_LEFT and RE_PARTIAL_RIGHT are also used as array - * indexes, so they need to be 0 and 1. - */ -#define RE_PARTIAL_NONE -1 -#define RE_PARTIAL_LEFT 0 -#define RE_PARTIAL_RIGHT 1 - -/* Flags for the kind of 'sub' call: 'sub', 'subn', 'subf', 'subfn'. */ -#define RE_SUB 0x0 -#define RE_SUBN 0x1 -#if PY_VERSION_HEX >= 0x02060000 -#define RE_SUBF 0x2 -#endif - -/* The name of this module, minus the leading underscore. */ -#define RE_MODULE "regex" - -/* Error codes. */ -#define RE_ERROR_SUCCESS 1 /* Successful match. */ -#define RE_ERROR_FAILURE 0 /* Unsuccessful match. */ -#define RE_ERROR_ILLEGAL -1 /* Illegal code. */ -#define RE_ERROR_INTERNAL -2 /* Internal error. */ -#define RE_ERROR_CONCURRENT -3 /* "concurrent" invalid. */ -#define RE_ERROR_MEMORY -4 /* Out of memory. */ -#define RE_ERROR_INTERRUPTED -5 /* Signal handler raised exception. */ -#define RE_ERROR_REPLACEMENT -6 /* Invalid replacement string. */ -#define RE_ERROR_INVALID_GROUP_REF -7 /* Invalid group reference. */ -#define RE_ERROR_GROUP_INDEX_TYPE -8 /* Group index type error. */ -#define RE_ERROR_NO_SUCH_GROUP -9 /* No such group. */ -#define RE_ERROR_INDEX -10 /* String index. */ -#define RE_ERROR_BACKTRACKING -11 /* Too much backtracking. */ -#define RE_ERROR_NOT_STRING -12 /* Not a string. */ -#define RE_ERROR_NOT_UNICODE -13 /* Not a Unicode string. */ -#define RE_ERROR_PARTIAL -15 /* Partial match. */ - -/* The number of backtrack entries per allocated block. */ -#define RE_BACKTRACK_BLOCK_SIZE 64 - -/* The maximum number of backtrack entries to allocate. */ -#define RE_MAX_BACKTRACK_ALLOC (1024 * 1024) - -/* The initial maximum capacity of the guard block. */ -#define RE_INIT_GUARDS_BLOCK_SIZE 16 - -/* The initial maximum capacity of the node list. */ -#define RE_INIT_NODE_LIST_SIZE 16 - -/* The size increment for various allocation lists. */ -#define RE_LIST_SIZE_INC 16 - -/* The initial maximum capacity of the capture groups. */ -#define RE_INIT_CAPTURE_SIZE 16 - -/* Node bitflags. */ -#define RE_POSITIVE_OP 0x1 -#define RE_ZEROWIDTH_OP 0x2 -#define RE_FUZZY_OP 0x4 -#define RE_REVERSE_OP 0x8 -#define RE_REQUIRED_OP 0x10 - -/* Guards against further matching can occur at the start of the body and the - * tail of a repeat containing a repeat. - */ -#define RE_STATUS_BODY 0x1 -#define RE_STATUS_TAIL 0x2 - -/* Whether a guard is added depends on whether there's a repeat in the body of - * the repeat or a group reference in the body or tail of the repeat. - */ -#define RE_STATUS_NEITHER 0x0 -#define RE_STATUS_REPEAT 0x4 -#define RE_STATUS_LIMITED 0x8 -#define RE_STATUS_REF 0x10 -#define RE_STATUS_VISITED_AG 0x20 -#define RE_STATUS_VISITED_REP 0x40 - -/* Whether a string node has been initialised for fast searching. */ -#define RE_STATUS_FAST_INIT 0x80 - -/* Whether a node us being used. (Additional nodes may be created while the - * pattern is being built. - */ -#define RE_STATUS_USED 0x100 - -/* Whether a node is a string node. */ -#define RE_STATUS_STRING 0x200 - -/* Whether a repeat node is within another repeat. */ -#define RE_STATUS_INNER 0x400 - -/* Various flags stored in a node status member. */ -#define RE_STATUS_SHIFT 11 - -#define RE_STATUS_FUZZY (RE_FUZZY_OP << RE_STATUS_SHIFT) -#define RE_STATUS_REVERSE (RE_REVERSE_OP << RE_STATUS_SHIFT) -#define RE_STATUS_REQUIRED (RE_REQUIRED_OP << RE_STATUS_SHIFT) - -/* The different error types for fuzzy matching. */ -#define RE_FUZZY_SUB 0 -#define RE_FUZZY_INS 1 -#define RE_FUZZY_DEL 2 -#define RE_FUZZY_ERR 3 -#define RE_FUZZY_COUNT 3 - -/* The various values in a FUZZY node. */ -#define RE_FUZZY_VAL_MAX_SUB 1 -#define RE_FUZZY_VAL_MAX_INS 2 -#define RE_FUZZY_VAL_MAX_DEL 3 -#define RE_FUZZY_VAL_MAX_ERR 4 -#define RE_FUZZY_VAL_SUB_COST 5 -#define RE_FUZZY_VAL_INS_COST 6 -#define RE_FUZZY_VAL_DEL_COST 7 -#define RE_FUZZY_VAL_MAX_COST 8 - -#define RE_FUZZY_VAL_MAX_BASE 1 -#define RE_FUZZY_VAL_COST_BASE 5 - -/* The various values in an END_FUZZY node. */ -#define RE_FUZZY_VAL_MIN_SUB 1 -#define RE_FUZZY_VAL_MIN_INS 2 -#define RE_FUZZY_VAL_MIN_DEL 3 -#define RE_FUZZY_VAL_MIN_ERR 4 - -/* The flags which will be set for full Unicode case folding. */ -#define RE_FULL_CASE_FOLDING (RE_FLAG_UNICODE | RE_FLAG_FULLCASE | RE_FLAG_IGNORECASE) - -/* The shortest string prefix for which we'll use a fast string search. */ -#define RE_MIN_FAST_LENGTH 5 - -static char copyright[] = - " RE 2.3.0 Copyright (c) 1997-2002 by Secret Labs AB "; - -/* The exception to raise on error. */ -static PyObject* error_exception; - -/* The dictionary of Unicode properties. */ -static PyObject* property_dict; - -typedef struct RE_State* RE_StatePtr; - -/* Handlers for ASCII, locale and Unicode. */ -typedef struct RE_EncodingTable { - BOOL (*has_property)(RE_CODE property, Py_UCS4 ch); - BOOL (*at_boundary)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_word_start)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_word_end)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_default_boundary)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_default_word_start)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_default_word_end)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_grapheme_boundary)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*is_line_sep)(Py_UCS4 ch); - BOOL (*at_line_start)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*at_line_end)(RE_StatePtr state, Py_ssize_t text_pos); - BOOL (*possible_turkic)(Py_UCS4 ch); - int (*all_cases)(Py_UCS4 ch, Py_UCS4* codepoints); - Py_UCS4 (*simple_case_fold)(Py_UCS4 ch); - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - int (*all_turkic_i)(Py_UCS4 ch, Py_UCS4* cases); -} RE_EncodingTable; - -/* Position within the regex and text. */ -typedef struct RE_Position { - struct RE_Node* node; - Py_ssize_t text_pos; -} RE_Position; - -/* Info about fuzzy matching. */ -typedef struct RE_FuzzyInfo { - struct RE_Node* node; - size_t counts[RE_FUZZY_COUNT + 1]; /* Add 1 for total errors. */ - size_t total_cost; -} RE_FuzzyInfo; - -/* Storage for backtrack data. */ -typedef struct RE_BacktrackData { - union { - struct { - size_t capture_change; - BOOL too_few_errors; - } atomic; - struct { - RE_Position position; - } branch; - struct { - RE_FuzzyInfo fuzzy_info; - Py_ssize_t text_pos; - RE_CODE index; - } fuzzy; - struct { - RE_Position position; - size_t count; - struct RE_Node* fuzzy_node; - BOOL too_few_errors; - } fuzzy_insert; - struct { - RE_Position position; - RE_INT8 fuzzy_type; - RE_INT8 step; - } fuzzy_item; - struct { - RE_Position position; - Py_ssize_t string_pos; - RE_INT8 fuzzy_type; - RE_INT8 folded_pos; - RE_INT8 folded_len; - RE_INT8 gfolded_pos; - RE_INT8 gfolded_len; - RE_INT8 step; - } fuzzy_string; - struct { - Py_ssize_t text_pos; - Py_ssize_t current_capture; - RE_CODE private_index; - RE_CODE public_index; - BOOL capture; - } group; - struct { - struct RE_Node* node; - size_t capture_change; - } group_call; - struct { - size_t capture_change; - BOOL too_few_errors; - } lookaround; - struct { - RE_Position position; - Py_ssize_t text_pos; - size_t count; - Py_ssize_t start; - size_t capture_change; - RE_CODE index; - } repeat; - }; - RE_UINT8 op; -} RE_BacktrackData; - -/* Storage for backtrack data is allocated in blocks for speed. */ -typedef struct RE_BacktrackBlock { - RE_BacktrackData items[RE_BACKTRACK_BLOCK_SIZE]; - struct RE_BacktrackBlock* previous; - struct RE_BacktrackBlock* next; - size_t capacity; - size_t count; -} RE_BacktrackBlock; - -/* Storage for saved groups. */ -typedef struct RE_SavedGroups { - struct RE_SavedGroups* previous; - struct RE_SavedGroups* next; - struct RE_GroupSpan* spans; - size_t* counts; -} RE_SavedGroups; - -/* Storage for info around a recursive by 'basic'match'. */ -typedef struct RE_Info { - RE_BacktrackBlock* current_backtrack_block; - size_t backtrack_count; - RE_SavedGroups* current_saved_groups; - struct RE_GroupCallFrame* current_group_call_frame; - BOOL must_advance; -} RE_Info; - -/* Storage for the next node. */ -typedef struct RE_NextNode { - struct RE_Node* node; - struct RE_Node* test; - struct RE_Node* match_next; - Py_ssize_t match_step; -} RE_NextNode; - -/* A pattern node. */ -typedef struct RE_Node { - RE_NextNode next_1; - union { - struct { - RE_NextNode next_2; - } nonstring; - struct { - /* Used only if (node->status & RE_STATUS_STRING) is true. */ - Py_ssize_t* bad_character_offset; - Py_ssize_t* good_suffix_offset; - } string; - }; - Py_ssize_t step; - size_t value_count; - RE_CODE* values; - RE_STATUS_T status; - RE_UINT8 op; - BOOL match; -} RE_Node; - -/* Info about a group's span. */ -typedef struct RE_GroupSpan { - Py_ssize_t start; - Py_ssize_t end; -} RE_GroupSpan; - -/* Span of a guard (inclusive range). */ -typedef struct RE_GuardSpan { - Py_ssize_t low; - Py_ssize_t high; - BOOL protect; -} RE_GuardSpan; - -/* Spans guarded against further matching. */ -typedef struct RE_GuardList { - size_t capacity; - size_t count; - RE_GuardSpan* spans; - Py_ssize_t last_text_pos; - size_t last_low; -} RE_GuardList; - -/* Info about a group in a context. */ -typedef struct RE_GroupData { - RE_GroupSpan span; - size_t capture_count; - size_t capture_capacity; - Py_ssize_t current_capture; - RE_GroupSpan* captures; -} RE_GroupData; - -/* Info about a repeat. */ -typedef struct RE_RepeatData { - RE_GuardList body_guard_list; - RE_GuardList tail_guard_list; - size_t count; - Py_ssize_t start; - size_t capture_change; -} RE_RepeatData; - -/* Storage for saved repeats. */ -typedef struct RE_SavedRepeats { - struct RE_SavedRepeats* previous; - struct RE_SavedRepeats* next; - RE_RepeatData* repeats; -} RE_SavedRepeats; - -/* Guards for fuzzy sections. */ -typedef struct RE_FuzzyGuards { - RE_GuardList body_guard_list; - RE_GuardList tail_guard_list; -} RE_FuzzyGuards; - -/* Info about a capture group. */ -typedef struct RE_GroupInfo { - Py_ssize_t end_index; - RE_Node* node; - BOOL referenced; - BOOL has_name; -} RE_GroupInfo; - -/* Info about a call_ref. */ -typedef struct RE_CallRefInfo { - RE_Node* node; - BOOL defined; - BOOL used; -} RE_CallRefInfo; - -/* Info about a repeat. */ -typedef struct RE_RepeatInfo { - RE_STATUS_T status; -} RE_RepeatInfo; - -/* Stack frame for a group call. */ -typedef struct RE_GroupCallFrame { - struct RE_GroupCallFrame* previous; - struct RE_GroupCallFrame* next; - RE_Node* node; - RE_GroupData* groups; - RE_RepeatData* repeats; -} RE_GroupCallFrame; - -/* Info about a string argument. */ -typedef struct RE_StringInfo { -#if PY_VERSION_HEX >= 0x02060000 - Py_buffer view; /* View of the string if it's a buffer object. */ -#endif - void* characters; /* Pointer to the characters of the string. */ - Py_ssize_t length; /* Length of the string. */ - Py_ssize_t charsize; /* Size of the characters in the string. */ - BOOL is_unicode; /* Whether the string is Unicode. */ - BOOL should_release; /* Whether the buffer should be released. */ -} RE_StringInfo; - -/* Info about where the next match was found, starting from a certain search - * position. This is used when a pattern starts with a BRANCH. - */ -#define MAX_SEARCH_POSITIONS 7 - -/* Info about a search position. */ -typedef struct { - Py_ssize_t start_pos; - Py_ssize_t match_pos; -} RE_SearchPosition; - -/* The state object used during matching. */ -typedef struct RE_State { - struct PatternObject* pattern; /* Parent PatternObject. */ - /* Info about the string being matched. */ - PyObject* string; -#if PY_VERSION_HEX >= 0x02060000 - Py_buffer view; /* View of the string if it's a buffer object. */ -#endif - Py_ssize_t charsize; - void* text; - Py_ssize_t text_length; - /* The slice of the string being searched. */ - Py_ssize_t slice_start; - Py_ssize_t slice_end; - /* Info about the capture groups. */ - RE_GroupData* groups; - Py_ssize_t lastindex; - Py_ssize_t lastgroup; - /* Info about the repeats. */ - RE_RepeatData* repeats; - Py_ssize_t search_anchor; /* Where the last match finished. */ - Py_ssize_t match_pos; /* The start position of the match. */ - Py_ssize_t text_pos; /* The current position of the match. */ - Py_ssize_t final_newline; /* The index of newline at end of string, or -1. */ - Py_ssize_t final_line_sep; /* The index of line separator at end of string, or -1. */ - /* Storage for backtrack info. */ - RE_BacktrackBlock backtrack_block; - RE_BacktrackBlock* current_backtrack_block; - Py_ssize_t backtrack_allocated; - RE_BacktrackData* backtrack; - /* Storage for saved capture groups. */ - RE_SavedGroups* first_saved_groups; - RE_SavedGroups* current_saved_groups; - RE_SavedRepeats* first_saved_repeats; - RE_SavedRepeats* current_saved_repeats; - Py_ssize_t min_width; /* The minimum width of the string to match (assuming it's not a fuzzy pattern). */ - RE_EncodingTable* encoding; /* The 'encoding' of the string being searched. */ - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - void (*set_char_at)(void* text, Py_ssize_t pos, Py_UCS4 ch); - void* (*point_to)(void* text, Py_ssize_t pos); - PyThread_type_lock lock; /* A lock for accessing the state across threads. */ - RE_FuzzyInfo fuzzy_info; /* Info about fuzzy matching. */ - size_t total_fuzzy_counts[RE_FUZZY_COUNT]; /* Totals for fuzzy matching. */ - RE_FuzzyGuards* fuzzy_guards; /* The guards for a fuzzy match. */ - size_t total_errors; /* The total number of errors of a fuzzy match. */ - size_t total_cost; /* The total cost of a fuzzy match. */ - size_t max_cost; /* The maximum permitted fuzzy cost. */ - /* The group call stack. */ - RE_GroupCallFrame* first_group_call_frame; - RE_GroupCallFrame* current_group_call_frame; - RE_GuardList* group_call_guard_list; - RE_SearchPosition search_positions[MAX_SEARCH_POSITIONS]; /* Where the search matches next. */ - size_t capture_change; /* Incremented every time a captive group changes. */ - Py_ssize_t req_pos; /* The position where the required string matched. */ - Py_ssize_t req_end; /* The end position where the required string matched. */ - int partial_side; /* The side that could truncate in a partial match. */ - RE_UINT16 iterations; /* The number of iterations the matching engine has performed since checking for KeyboardInterrupt. */ - BOOL is_unicode; /* Whether the string to be matched is Unicode. */ - BOOL should_release; /* Whether the buffer should be released. */ - BOOL overlapped; /* Whether the matches can be overlapped. */ - BOOL reverse; /* Whether it's a reverse pattern. */ - BOOL visible_captures; /* Whether the 'captures' method will be visible. */ - BOOL version_0; /* Whether to perform version_0 behaviour (same as re module). */ - BOOL must_advance; /* Whether the end of the match must advance past its start. */ - BOOL is_multithreaded; /* Whether to release the GIL while matching. */ - BOOL too_few_errors; /* Whether there were too few fuzzy errors. */ - BOOL match_all; /* Whether to match all of the string ('fullmatch'). */ -} RE_State; - -/* Storage for the regex state and thread state. - * - * Scanner objects can sometimes be shared across threads, which means that - * their RE_State structs are also shared. This isn't safe when the GIL is - * released, so in such instances we have a lock (mutex) in the RE_State struct - * to protect it during matching. We also need a thread-safe place to store the - * thread state when releasing the GIL. - */ -typedef struct RE_SafeState { - RE_State* re_state; - PyThreadState* thread_state; -} RE_SafeState; - -/* The PatternObject created from a regular expression. */ -typedef struct PatternObject { - PyObject_HEAD - PyObject* pattern; /* Pattern source (or None). */ - Py_ssize_t flags; /* Flags used when compiling pattern source. */ - PyObject* weakreflist; /* List of weak references */ - /* Nodes into which the regular expression is compiled. */ - RE_Node* start_node; - RE_Node* start_test; - size_t true_group_count; /* The true number of capture groups. */ - size_t public_group_count; /* The number of public capture groups. */ - size_t repeat_count; /* The number of repeats. */ - Py_ssize_t group_end_index; /* The number of group closures. */ - PyObject* groupindex; - PyObject* indexgroup; - PyObject* named_lists; - size_t named_lists_count; - PyObject** partial_named_lists[2]; - PyObject* named_list_indexes; - /* Storage for the pattern nodes. */ - size_t node_capacity; - size_t node_count; - RE_Node** node_list; - /* Info about the capture groups. */ - size_t group_info_capacity; - RE_GroupInfo* group_info; - /* Info about the call_refs. */ - size_t call_ref_info_capacity; - size_t call_ref_info_count; - RE_CallRefInfo* call_ref_info; - Py_ssize_t pattern_call_ref; - /* Info about the repeats. */ - size_t repeat_info_capacity; - RE_RepeatInfo* repeat_info; - Py_ssize_t min_width; /* The minimum width of the string to match (assuming it isn't a fuzzy pattern). */ - RE_EncodingTable* encoding; /* Encoding handlers. */ - RE_GroupData* groups_storage; - RE_RepeatData* repeats_storage; - size_t fuzzy_count; /* The number of fuzzy sections. */ - Py_ssize_t req_offset; /* The offset to the required string. */ - RE_Node* req_string; /* The required string. */ - BOOL is_fuzzy; /* Whether it's a fuzzy pattern. */ - BOOL do_search_start; /* Whether to do an initial search. */ - BOOL recursive; /* Whether the entire pattern is recursive. */ -} PatternObject; - -/* The MatchObject created when a match is found. */ -typedef struct MatchObject { - PyObject_HEAD - PyObject* string; /* Link to the target string or NULL if detached. */ - PyObject* substring; /* Link to (a substring of) the target string. */ - Py_ssize_t substring_offset; /* Offset into the target string. */ - PatternObject* pattern; /* Link to the regex (pattern) object. */ - Py_ssize_t pos; /* Start of current slice. */ - Py_ssize_t endpos; /* End of current slice. */ - Py_ssize_t match_start; /* Start of matched slice. */ - Py_ssize_t match_end; /* End of matched slice. */ - Py_ssize_t lastindex; /* Last group seen by the engine (-1 if none). */ - Py_ssize_t lastgroup; /* Last named group seen by the engine (-1 if none). */ - size_t group_count; /* The number of groups. */ - RE_GroupData* groups; /* The capture groups. */ - PyObject* regs; - size_t fuzzy_counts[RE_FUZZY_COUNT]; - BOOL partial; /* Whether it's a partial match. */ -} MatchObject; - -/* The ScannerObject. */ -typedef struct ScannerObject { - PyObject_HEAD - PatternObject* pattern; - RE_State state; - int status; -} ScannerObject; - -/* The SplitterObject. */ -typedef struct SplitterObject { - PyObject_HEAD - PatternObject* pattern; - RE_State state; - Py_ssize_t maxsplit; - Py_ssize_t last_pos; - Py_ssize_t split_count; - Py_ssize_t index; - int status; -} SplitterObject; - -/* Info used when compiling a pattern to nodes. */ -typedef struct RE_CompileArgs { - RE_CODE* code; /* The start of the compiled pattern. */ - RE_CODE* end_code; /* The end of the compiled pattern. */ - PatternObject* pattern; /* The pattern object. */ - Py_ssize_t min_width; /* The minimum width of the string to match (assuming it isn't a fuzzy pattern). */ - RE_Node* start; /* The start node. */ - RE_Node* end; /* The end node. */ - size_t repeat_depth; /* The nesting depth of the repeat. */ - BOOL forward; /* Whether it's a forward (not reverse) pattern. */ - BOOL visible_captures; /* Whether all of the captures will be visible. */ - BOOL has_captures; /* Whether the pattern has capture groups. */ - BOOL is_fuzzy; /* Whether the pattern (or some part of it) is fuzzy. */ - BOOL within_fuzzy; /* Whether the subpattern is within a fuzzy section. */ -} RE_CompileArgs; - -/* The string slices which will be concatenated to make the result string of - * the 'sub' method. - * - * This allows us to avoid creating a list of slices if there of fewer than 2 - * of them. Empty strings aren't recorded, so if 'list' and 'item' are both - * NULL then the result is an empty string. - */ -typedef struct JoinInfo { - PyObject* list; /* The list of slices if there are more than 2 of them. */ - PyObject* item; /* The slice if there is only 1 of them. */ - BOOL reversed; /* Whether the slices have been found in reverse order. */ - BOOL is_unicode; /* Whether the string is Unicode. */ -} JoinInfo; - -/* Info about fuzzy matching. */ -typedef struct { - RE_Node* new_node; - Py_ssize_t new_text_pos; - Py_ssize_t limit; - Py_ssize_t new_string_pos; - int step; - int new_folded_pos; - int folded_len; - int new_gfolded_pos; - int new_group_pos; - int fuzzy_type; - BOOL permit_insertion; -} RE_FuzzyData; - -/* Function types for getting info from a MatchObject. */ -typedef PyObject* (*RE_GetByIndexFunc)(MatchObject* self, Py_ssize_t index); - -/* Returns the magnitude of a 'Py_ssize_t' value. */ -Py_LOCAL_INLINE(Py_ssize_t) abs_ssize_t(Py_ssize_t x) { - return x >= 0 ? x : -x; -} - -/* Returns the minimum of 2 'Py_ssize_t' values. */ -Py_LOCAL_INLINE(Py_ssize_t) min_ssize_t(Py_ssize_t x, Py_ssize_t y) { - return x <= y ? x : y; -} - -/* Returns the maximum of 2 'Py_ssize_t' values. */ -Py_LOCAL_INLINE(Py_ssize_t) max_ssize_t(Py_ssize_t x, Py_ssize_t y) { - return x >= y ? x : y; -} - -/* Returns the minimum of 2 'size_t' values. */ -Py_LOCAL_INLINE(size_t) min_size_t(size_t x, size_t y) { - return x <= y ? x : y; -} - -/* Returns the maximum of 2 'size_t' values. */ -Py_LOCAL_INLINE(size_t) max_size_t(size_t x, size_t y) { - return x >= y ? x : y; -} - -/* Returns the 'maximum' of 2 RE_STATUS_T values. */ -Py_LOCAL_INLINE(RE_STATUS_T) max_status_2(RE_STATUS_T x, RE_STATUS_T y) { - return x >= y ? x : y; -} - -/* Returns the 'maximum' of 3 RE_STATUS_T values. */ -Py_LOCAL_INLINE(RE_STATUS_T) max_status_3(RE_STATUS_T x, RE_STATUS_T y, - RE_STATUS_T z) { - return max_status_2(x, max_status_2(y, z)); -} - -/* Returns the 'maximum' of 4 RE_STATUS_T values. */ -Py_LOCAL_INLINE(RE_STATUS_T) max_status_4(RE_STATUS_T w, RE_STATUS_T x, - RE_STATUS_T y, RE_STATUS_T z) { - return max_status_2(max_status_2(w, x), max_status_2(y, z)); -} - -/* Gets a character at a position assuming 1 byte per character. */ -static Py_UCS4 bytes1_char_at(void* text, Py_ssize_t pos) { - return *((Py_UCS1*)text + pos); -} - -/* Sets a character at a position assuming 1 byte per character. */ -static void bytes1_set_char_at(void* text, Py_ssize_t pos, Py_UCS4 ch) { - *((Py_UCS1*)text + pos) = (Py_UCS1)ch; -} - -/* Gets a pointer to a position assuming 1 byte per character. */ -static void* bytes1_point_to(void* text, Py_ssize_t pos) { - return (Py_UCS1*)text + pos; -} - -/* Gets a character at a position assuming 2 bytes per character. */ -static Py_UCS4 bytes2_char_at(void* text, Py_ssize_t pos) { - return *((Py_UCS2*)text + pos); -} - -/* Sets a character at a position assuming 2 bytes per character. */ -static void bytes2_set_char_at(void* text, Py_ssize_t pos, Py_UCS4 ch) { - *((Py_UCS2*)text + pos) = (Py_UCS2)ch; -} - -/* Gets a pointer to a position assuming 2 bytes per character. */ -static void* bytes2_point_to(void* text, Py_ssize_t pos) { - return (Py_UCS2*)text + pos; -} - -/* Gets a character at a position assuming 4 bytes per character. */ -static Py_UCS4 bytes4_char_at(void* text, Py_ssize_t pos) { - return *((Py_UCS4*)text + pos); -} - -/* Sets a character at a position assuming 4 bytes per character. */ -static void bytes4_set_char_at(void* text, Py_ssize_t pos, Py_UCS4 ch) { - *((Py_UCS4*)text + pos) = (Py_UCS4)ch; -} - -/* Gets a pointer to a position assuming 4 bytes per character. */ -static void* bytes4_point_to(void* text, Py_ssize_t pos) { - return (Py_UCS4*)text + pos; -} - -/* Default for whether a position is on a word boundary. */ -static BOOL at_boundary_always(RE_State* state, Py_ssize_t text_pos) { - return TRUE; -} - -/* Converts a BOOL to success/failure. */ -Py_LOCAL_INLINE(int) bool_as_status(BOOL value) { - return value ? RE_ERROR_SUCCESS : RE_ERROR_FAILURE; -} - -/* ASCII-specific. */ - -Py_LOCAL_INLINE(BOOL) unicode_has_property(RE_CODE property, Py_UCS4 ch); - -/* Checks whether a character has a property. */ -Py_LOCAL_INLINE(BOOL) ascii_has_property(RE_CODE property, Py_UCS4 ch) { - if (ch > RE_ASCII_MAX) { - /* Outside the ASCII range. */ - RE_UINT32 value; - - value = property & 0xFFFF; - - return value == 0; - } - - return unicode_has_property(property, ch); -} - -/* Wrapper for calling 'ascii_has_property' via a pointer. */ -static BOOL ascii_has_property_wrapper(RE_CODE property, Py_UCS4 ch) { - return ascii_has_property(property, ch); -} - -/* Checks whether there's a word character to the left. */ -Py_LOCAL_INLINE(BOOL) ascii_word_left(RE_State* state, Py_ssize_t text_pos) { - return text_pos > 0 && ascii_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos - 1)); -} - -/* Checks whether there's a word character to the right. */ -Py_LOCAL_INLINE(BOOL) ascii_word_right(RE_State* state, Py_ssize_t text_pos) { - return text_pos < state->text_length && ascii_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos)); -} - -/* Checks whether a position is on a word boundary. */ -static BOOL ascii_at_boundary(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = ascii_word_left(state, text_pos); - right = ascii_word_right(state, text_pos); - - return left != right; -} - -/* Checks whether a position is at the start of a word. */ -static BOOL ascii_at_word_start(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = ascii_word_left(state, text_pos); - right = ascii_word_right(state, text_pos); - - return !left && right; -} - -/* Checks whether a position is at the end of a word. */ -static BOOL ascii_at_word_end(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = ascii_word_left(state, text_pos); - right = ascii_word_right(state, text_pos); - - return left && !right; -} - -/* Checks whether a character is a line separator. */ -static BOOL ascii_is_line_sep(Py_UCS4 ch) { - return 0x0A <= ch && ch <= 0x0D; -} - -/* Checks whether a position is at the start of a line. */ -static BOOL ascii_at_line_start(RE_State* state, Py_ssize_t text_pos) { - Py_UCS4 ch; - - if (text_pos <= 0) - return TRUE; - - ch = state->char_at(state->text, text_pos - 1); - - if (ch == 0x0D) { - if (text_pos >= state->text_length) - return TRUE; - - /* No line break inside CRLF. */ - return state->char_at(state->text, text_pos) != 0x0A; - } - - return 0x0A <= ch && ch <= 0x0D; -} - -/* Checks whether a position is at the end of a line. */ -static BOOL ascii_at_line_end(RE_State* state, Py_ssize_t text_pos) { - Py_UCS4 ch; - - if (text_pos >= state->text_length) - return TRUE; - - ch = state->char_at(state->text, text_pos); - - if (ch == 0x0A) { - if (text_pos <= 0) - return TRUE; - - /* No line break inside CRLF. */ - return state->char_at(state->text, text_pos - 1) != 0x0D; - } - - return 0x0A <= ch && ch <= 0x0D; -} - -/* Checks whether a character could be Turkic (variants of I/i). For ASCII, it - * won't be. - */ -static BOOL ascii_possible_turkic(Py_UCS4 ch) { - return FALSE; -} - -/* Gets all the cases of a character. */ -static int ascii_all_cases(Py_UCS4 ch, Py_UCS4* codepoints) { - int count; - - count = 0; - - codepoints[count++] = ch; - - if (('A' <= ch && ch <= 'Z') || ('a' <= ch && ch <= 'z')) - /* It's a letter, so add the other case. */ - codepoints[count++] = ch ^ 0x20; - - return count; -} - -/* Returns a character with its case folded. */ -static Py_UCS4 ascii_simple_case_fold(Py_UCS4 ch) { - if ('A' <= ch && ch <= 'Z') - /* Uppercase folds to lowercase. */ - return ch ^ 0x20; - - return ch; -} - -/* Returns a character with its case folded. */ -static int ascii_full_case_fold(Py_UCS4 ch, Py_UCS4* folded) { - if ('A' <= ch && ch <= 'Z') - /* Uppercase folds to lowercase. */ - folded[0] = ch ^ 0x20; - else - folded[0] = ch; - - return 1; -} - -/* Gets all the case variants of Turkic 'I'. The given character will be listed - * first. - */ -static int ascii_all_turkic_i(Py_UCS4 ch, Py_UCS4* cases) { - int count; - - count = 0; - - cases[count++] = ch; - - if (ch != 'I') - cases[count++] = 'I'; - - if (ch != 'i') - cases[count++] = 'i'; - - return count; -} - -/* The handlers for ASCII characters. */ -static RE_EncodingTable ascii_encoding = { - ascii_has_property_wrapper, - ascii_at_boundary, - ascii_at_word_start, - ascii_at_word_end, - ascii_at_boundary, /* No special "default word boundary" for ASCII. */ - ascii_at_word_start, /* No special "default start of word" for ASCII. */ - ascii_at_word_end, /* No special "default end of a word" for ASCII. */ - at_boundary_always, /* No special "grapheme boundary" for ASCII. */ - ascii_is_line_sep, - ascii_at_line_start, - ascii_at_line_end, - ascii_possible_turkic, - ascii_all_cases, - ascii_simple_case_fold, - ascii_full_case_fold, - ascii_all_turkic_i, -}; - -/* Locale-specific. */ - -/* Checks whether a character has a property. */ -Py_LOCAL_INLINE(BOOL) locale_has_property(RE_CODE property, Py_UCS4 ch) { - RE_UINT32 value; - RE_UINT32 v; - - value = property & 0xFFFF; - - if (ch > RE_LOCALE_MAX) - /* Outside the locale range. */ - return value == 0; - - switch (property >> 16) { - case RE_PROP_ALNUM >> 16: - v = isalnum((int)ch) != 0; - break; - case RE_PROP_ALPHA >> 16: - v = isalpha((int)ch) != 0; - break; - case RE_PROP_ANY >> 16: - v = 1; - break; - case RE_PROP_ASCII >> 16: - v = ch <= RE_ASCII_MAX; - break; - case RE_PROP_BLANK >> 16: - v = ch == '\t' || ch == ' '; - break; - case RE_PROP_GC: - switch (property) { - case RE_PROP_ASSIGNED: - v = ch <= RE_LOCALE_MAX; - break; - case RE_PROP_CASEDLETTER: - v = isalpha((int)ch) ? value : 0xFFFF; - break; - case RE_PROP_CNTRL: - v = iscntrl((int)ch) ? value : 0xFFFF; - break; - case RE_PROP_DIGIT: - v = isdigit((int)ch) ? value : 0xFFFF; - break; - case RE_PROP_GC_CN: - v = ch > RE_LOCALE_MAX; - break; - case RE_PROP_GC_LL: - v = islower((int)ch) ? value : 0xFFFF; - break; - case RE_PROP_GC_LU: - v = isupper((int)ch) ? value : 0xFFFF; - break; - case RE_PROP_GC_P: - v = ispunct((int)ch) ? value : 0xFFFF; - break; - default: - v = 0xFFFF; - break; - } - break; - case RE_PROP_GRAPH >> 16: - v = isgraph((int)ch) != 0; - break; - case RE_PROP_LOWER >> 16: - v = islower((int)ch) != 0; - break; - case RE_PROP_PRINT >> 16: - v = isprint((int)ch) != 0; - break; - case RE_PROP_SPACE >> 16: - v = isspace((int)ch) != 0; - break; - case RE_PROP_UPPER >> 16: - v = isupper((int)ch) != 0; - break; - case RE_PROP_WORD >> 16: - v = ch == '_' || isalnum((int)ch) != 0; - break; - case RE_PROP_XDIGIT >> 16: - v = re_get_hex_digit(ch) != 0; - break; - default: - v = 0; - break; - } - - return v == value; -} - -/* Wrapper for calling 'locale_has_property' via a pointer. */ -static BOOL locale_has_property_wrapper(RE_CODE property, Py_UCS4 ch) { - return locale_has_property(property, ch); -} - -/* Checks whether there's a word character to the left. */ -Py_LOCAL_INLINE(BOOL) locale_word_left(RE_State* state, Py_ssize_t text_pos) { - return text_pos > 0 && locale_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos - 1)); -} - -/* Checks whether there's a word character to the right. */ -Py_LOCAL_INLINE(BOOL) locale_word_right(RE_State* state, Py_ssize_t text_pos) { - return text_pos < state->text_length && locale_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos)); -} - -/* Checks whether a position is on a word boundary. */ -static BOOL locale_at_boundary(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = locale_word_left(state, text_pos); - right = locale_word_right(state, text_pos); - - return left != right; -} - -/* Checks whether a position is at the start of a word. */ -static BOOL locale_at_word_start(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = locale_word_left(state, text_pos); - right = locale_word_right(state, text_pos); - - return !left && right; -} - -/* Checks whether a position is at the end of a word. */ -static BOOL locale_at_word_end(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = locale_word_left(state, text_pos); - right = locale_word_right(state, text_pos); - - return left && !right; -} - -/* Checks whether a character could be Turkic (variants of I/i). */ -static BOOL locale_possible_turkic(Py_UCS4 ch) { - return toupper((int)ch) == 'I' || tolower((int)ch) == 'i'; -} - -/* Gets all the cases of a character. */ -static int locale_all_cases(Py_UCS4 ch, Py_UCS4* codepoints) { - int count; - Py_UCS4 other; - - count = 0; - - codepoints[count++] = ch; - - other = (Py_UCS4)toupper((int)ch); - if (other != ch) - codepoints[count++] = other; - - other = (Py_UCS4)tolower((int)ch); - if (other != ch) - codepoints[count++] = other; - - return count; -} - -/* Returns a character with its case folded. */ -static Py_UCS4 locale_simple_case_fold(Py_UCS4 ch) { - if (ch <= RE_LOCALE_MAX) - return (Py_UCS4)tolower((int)ch); - - return ch; -} - -/* Returns a character with its case folded. */ -static int locale_full_case_fold(Py_UCS4 ch, Py_UCS4* folded) { - if (ch <= RE_LOCALE_MAX) - folded[0] = (Py_UCS4)tolower((int)ch); - else - folded[0] = ch; - - return 1; -} - -/* Gets all the case variants of Turkic 'I'. The given character will be listed - * first. - */ -static int locale_all_turkic_i(Py_UCS4 ch, Py_UCS4* cases) { - int count; - Py_UCS4 other; - - count = 0; - - cases[count++] = ch; - - if (ch != 'I') - cases[count++] = 'I'; - - if (ch != 'i') - cases[count++] = 'i'; - - /* Uppercase 'i' will be either dotted (Turkic) or dotless (non-Turkic). */ - other = (Py_UCS4)toupper('i'); - if (other != ch && other != 'I') - cases[count++] = other; - - /* Lowercase 'I' will be either dotless (Turkic) or dotted (non-Turkic). */ - other = (Py_UCS4)tolower('I'); - if (other != ch && other != 'i') - cases[count++] = other; - - return count; -} - -/* The handlers for locale characters. */ -static RE_EncodingTable locale_encoding = { - locale_has_property_wrapper, - locale_at_boundary, - locale_at_word_start, - locale_at_word_end, - locale_at_boundary, /* No special "default word boundary" for locale. */ - locale_at_word_start, /* No special "default start of a word" for locale. */ - locale_at_word_end, /* No special "default end of a word" for locale. */ - at_boundary_always, /* No special "grapheme boundary" for locale. */ - ascii_is_line_sep, /* Assume locale line separators are same as ASCII. */ - ascii_at_line_start, /* Assume locale line separators are same as ASCII. */ - ascii_at_line_end, /* Assume locale line separators are same as ASCII. */ - locale_possible_turkic, - locale_all_cases, - locale_simple_case_fold, - locale_full_case_fold, - locale_all_turkic_i, -}; - -/* Unicode-specific. */ - -/* Checks whether a Unicode character has a property. */ -Py_LOCAL_INLINE(BOOL) unicode_has_property(RE_CODE property, Py_UCS4 ch) { - RE_UINT32 prop; - RE_UINT32 value; - RE_UINT32 v; - - prop = property >> 16; - if (prop >= sizeof(re_get_property) / sizeof(re_get_property[0])) - return FALSE; - - value = property & 0xFFFF; - v = re_get_property[prop](ch); - - if (v == value) - return TRUE; - - if (prop == RE_PROP_GC) { - switch (value) { - case RE_PROP_ASSIGNED: - return v != RE_PROP_CN; - case RE_PROP_C: - return (RE_PROP_C_MASK & (1 << v)) != 0; - case RE_PROP_CASEDLETTER: - return v == RE_PROP_LU || v == RE_PROP_LL || v == RE_PROP_LT; - case RE_PROP_L: - return (RE_PROP_L_MASK & (1 << v)) != 0; - case RE_PROP_M: - return (RE_PROP_M_MASK & (1 << v)) != 0; - case RE_PROP_N: - return (RE_PROP_N_MASK & (1 << v)) != 0; - case RE_PROP_P: - return (RE_PROP_P_MASK & (1 << v)) != 0; - case RE_PROP_S: - return (RE_PROP_S_MASK & (1 << v)) != 0; - case RE_PROP_Z: - return (RE_PROP_Z_MASK & (1 << v)) != 0; - } - } - - return FALSE; -} - -/* Wrapper for calling 'unicode_has_property' via a pointer. */ -static BOOL unicode_has_property_wrapper(RE_CODE property, Py_UCS4 ch) { - return unicode_has_property(property, ch); -} - -/* Checks whether there's a word character to the left. */ -Py_LOCAL_INLINE(BOOL) unicode_word_left(RE_State* state, Py_ssize_t text_pos) { - return text_pos > 0 && unicode_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos - 1)); -} - -/* Checks whether there's a word character to the right. */ -Py_LOCAL_INLINE(BOOL) unicode_word_right(RE_State* state, Py_ssize_t text_pos) - { - return text_pos < state->text_length && unicode_has_property(RE_PROP_WORD, - state->char_at(state->text, text_pos)); -} - -/* Checks whether a position is on a word boundary. */ -static BOOL unicode_at_boundary(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = unicode_word_left(state, text_pos); - right = unicode_word_right(state, text_pos); - - return left != right; -} - -/* Checks whether a position is at the start of a word. */ -static BOOL unicode_at_word_start(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = unicode_word_left(state, text_pos); - right = unicode_word_right(state, text_pos); - - return !left && right; -} - -/* Checks whether a position is at the end of a word. */ -static BOOL unicode_at_word_end(RE_State* state, Py_ssize_t text_pos) { - BOOL left; - BOOL right; - - left = unicode_word_left(state, text_pos); - right = unicode_word_right(state, text_pos); - - return left && !right; -} - -/* Checks whether a character is a Unicode vowel. - * - * Only a limited number are treated as vowels. - */ -Py_LOCAL_INLINE(BOOL) is_unicode_vowel(Py_UCS4 ch) { - switch (Py_UNICODE_TOLOWER((Py_UNICODE)ch)) { - case 'a': case 0xE0: case 0xE1: case 0xE2: - case 'e': case 0xE8: case 0xE9: case 0xEA: - case 'i': case 0xEC: case 0xED: case 0xEE: - case 'o': case 0xF2: case 0xF3: case 0xF4: - case 'u': case 0xF9: case 0xFA: case 0xFB: - return TRUE; - default: - return FALSE; - } -} - -/* Checks whether a position is on a default word boundary. - * - * The rules are defined here: - * http://www.unicode.org/reports/tr29/#Default_Word_Boundaries - */ -static BOOL unicode_at_default_boundary(RE_State* state, Py_ssize_t text_pos) { - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - int prop; - int prop_m1; - Py_ssize_t pos_m1; - Py_ssize_t pos_m2; - int prop_m2; - Py_ssize_t pos_p0; - int prop_p0; - Py_ssize_t pos_p1; - int prop_p1; - - /* Break at the start and end of the text. */ - if (text_pos <= 0) - return TRUE; - - if (text_pos >= state->text_length) - return TRUE; - - char_at = state->char_at; - - prop = (int)re_get_word_break(char_at(state->text, text_pos)); - prop_m1 = (int)re_get_word_break(char_at(state->text, text_pos - 1)); - - /* Don't break within CRLF. */ - if (prop_m1 == RE_BREAK_CR && prop == RE_BREAK_LF) - return FALSE; - - /* Otherwise break before and after Newlines (including CR and LF). */ - if (prop_m1 == RE_BREAK_NEWLINE || prop_m1 == RE_BREAK_CR || prop_m1 == - RE_BREAK_LF || prop == RE_BREAK_NEWLINE || prop == RE_BREAK_CR || prop == - RE_BREAK_LF) - return TRUE; - - /* Get the property of the previous character. */ - pos_m1 = text_pos - 1; - prop_m1 = RE_BREAK_OTHER; - while (pos_m1 >= 0) { - prop_m1 = (int)re_get_word_break(char_at(state->text, pos_m1)); - if (prop_m1 != RE_BREAK_EXTEND && prop_m1 != RE_BREAK_FORMAT) - break; - - --pos_m1; - } - - /* Get the property of the preceding character. */ - pos_m2 = pos_m1 - 1; - prop_m2 = RE_BREAK_OTHER; - while (pos_m2 >= 0) { - prop_m2 = (int)re_get_word_break(char_at(state->text, pos_m2)); - if (prop_m2 != RE_BREAK_EXTEND && prop_m2 != RE_BREAK_FORMAT) - break; - - --pos_m2; - } - - /* Get the property of the next character. */ - pos_p0 = text_pos; - prop_p0 = prop; - while (pos_p0 < state->text_length) { - prop_p0 = (int)re_get_word_break(char_at(state->text, pos_p0)); - if (prop_p0 != RE_BREAK_EXTEND && prop_p0 != RE_BREAK_FORMAT) - break; - - ++pos_p0; - } - - /* Get the property of the following character. */ - pos_p1 = pos_p0 + 1; - prop_p1 = RE_BREAK_OTHER; - while (pos_p1 < state->text_length) { - prop_p1 = (int)re_get_word_break(char_at(state->text, pos_p1)); - if (prop_p1 != RE_BREAK_EXTEND && prop_p1 != RE_BREAK_FORMAT) - break; - - ++pos_p1; - } - - /* Don't break between most letters. */ - if ((prop_m1 == RE_BREAK_ALETTER || prop_m1 == RE_BREAK_HEBREWLETTER) && - (prop_p0 == RE_BREAK_ALETTER || prop_p0 == RE_BREAK_HEBREWLETTER)) - return FALSE; - - /* Break between apostrophe and vowels (French, Italian). */ - if (pos_m1 >= 0 && char_at(state->text, pos_m1) == '\'' && - is_unicode_vowel(char_at(state->text, text_pos))) - return TRUE; - - /* Don't break letters across certain punctuation. */ - if ((prop_m1 == RE_BREAK_ALETTER || prop_m1 == RE_BREAK_HEBREWLETTER) && - (prop_p0 == RE_BREAK_MIDLETTER || prop_p0 == RE_BREAK_MIDNUMLET || - prop_p0 == RE_BREAK_SINGLEQUOTE) && (prop_p1 == RE_BREAK_ALETTER || - prop_p1 == RE_BREAK_HEBREWLETTER)) - return FALSE; - if ((prop_m2 == RE_BREAK_ALETTER || prop_m2 == RE_BREAK_HEBREWLETTER) && - (prop_m1 == RE_BREAK_MIDLETTER || prop_m1 == RE_BREAK_MIDNUMLET || - prop_m1 == RE_BREAK_SINGLEQUOTE) && (prop_p0 == RE_BREAK_ALETTER || - prop_p0 == RE_BREAK_HEBREWLETTER)) - return FALSE; - if (prop_m1 == RE_BREAK_HEBREWLETTER && prop_p0 == RE_BREAK_SINGLEQUOTE) - return FALSE; - if (prop_m1 == RE_BREAK_HEBREWLETTER && prop_p0 == RE_BREAK_DOUBLEQUOTE && - prop_p1 == RE_BREAK_HEBREWLETTER) - return FALSE; - if (prop_m2 == RE_BREAK_HEBREWLETTER && prop_m1 == RE_BREAK_DOUBLEQUOTE && - prop_p0 == RE_BREAK_HEBREWLETTER) - return FALSE; - - /* Don't break within sequences of digits, or digits adjacent to letters - * ("3a", or "A3"). - */ - if (prop_m1 == RE_BREAK_NUMERIC && prop_p0 == RE_BREAK_NUMERIC) - return FALSE; - if ((prop_m1 == RE_BREAK_ALETTER || prop_m1 == RE_BREAK_HEBREWLETTER) && - prop_p0 == RE_BREAK_NUMERIC) - return FALSE; - if (prop_m1 == RE_BREAK_NUMERIC && (prop_p0 == RE_BREAK_ALETTER || prop_p0 - == RE_BREAK_HEBREWLETTER)) - return FALSE; - - /* Don't break within sequences, such as "3.2" or "3,456.789". */ - if (prop_m2 == RE_BREAK_NUMERIC && (prop_m1 == RE_BREAK_MIDNUM || prop_m1 - == RE_BREAK_MIDNUMLET || prop_m1 == RE_BREAK_SINGLEQUOTE) && prop_p0 == - RE_BREAK_NUMERIC) - return FALSE; - if (prop_m1 == RE_BREAK_NUMERIC && (prop_p0 == RE_BREAK_MIDNUM || prop_p0 - == RE_BREAK_MIDNUMLET || prop_p0 == RE_BREAK_SINGLEQUOTE) && prop_p1 == - RE_BREAK_NUMERIC) - return FALSE; - - /* Don't break between Katakana. */ - if (prop_m1 == RE_BREAK_KATAKANA && prop_p0 == RE_BREAK_KATAKANA) - return FALSE; - - /* Don't break from extenders. */ - if ((prop_m1 == RE_BREAK_ALETTER || prop_m1 == RE_BREAK_HEBREWLETTER || - prop_m1 == RE_BREAK_NUMERIC || prop_m1 == RE_BREAK_KATAKANA || prop_m1 == - RE_BREAK_EXTENDNUMLET) && prop_p0 == RE_BREAK_EXTENDNUMLET) - return FALSE; - if (prop_m1 == RE_BREAK_EXTENDNUMLET && (prop_p0 == RE_BREAK_ALETTER || - prop_p0 == RE_BREAK_HEBREWLETTER || prop_p0 == RE_BREAK_NUMERIC || - prop_p0 == RE_BREAK_KATAKANA)) - return FALSE; - - /* Don't break between regional indicator symbols. */ - if (prop_m1 == RE_BREAK_REGIONALINDICATOR && prop_p0 == - RE_BREAK_REGIONALINDICATOR) - return FALSE; - - /* Otherwise, break everywhere (including around ideographs). */ - return TRUE; -} - -/* Checks whether a position is at the start/end of a word. */ -Py_LOCAL_INLINE(BOOL) unicode_at_default_word_start_or_end(RE_State* state, - Py_ssize_t text_pos, BOOL at_start) { - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - BOOL before; - BOOL after; - Py_UCS4 char_0; - Py_UCS4 char_m1; - int prop; - int prop_m1; - Py_ssize_t pos_m1; - Py_UCS4 char_p1; - Py_ssize_t pos_p1; - int prop_p1; - Py_ssize_t pos_m2; - Py_UCS4 char_m2; - int prop_m2; - - char_at = state->char_at; - - /* At the start or end of the text. */ - if (text_pos <= 0 || text_pos >= state->text_length) { - before = unicode_word_left(state, text_pos); - after = unicode_word_right(state, text_pos); - - return before != at_start && after == at_start; - } - - char_0 = char_at(state->text, text_pos); - char_m1 = char_at(state->text, text_pos - 1); - prop = (int)re_get_word_break(char_0); - prop_m1 = (int)re_get_word_break(char_m1); - - /* No break within CRLF. */ - if (prop_m1 == RE_BREAK_CR && prop == RE_BREAK_LF) - return FALSE; - - /* Break before and after Newlines (including CR and LF). */ - if (prop_m1 == RE_BREAK_NEWLINE || prop_m1 == RE_BREAK_CR || prop_m1 == - RE_BREAK_LF || prop == RE_BREAK_NEWLINE || prop == RE_BREAK_CR || prop == - RE_BREAK_LF) { - before = unicode_has_property(RE_PROP_WORD, char_m1); - after = unicode_has_property(RE_PROP_WORD, char_0); - - return before != at_start && after == at_start; - } - - /* No break just before Format or Extend characters. */ - if (prop == RE_BREAK_EXTEND || prop == RE_BREAK_FORMAT) - return FALSE; - - /* Get the property of the previous character. */ - pos_m1 = text_pos - 1; - prop_m1 = RE_BREAK_OTHER; - while (pos_m1 >= 0) { - char_m1 = char_at(state->text, pos_m1); - prop_m1 = (int)re_get_word_break(char_m1); - if (prop_m1 != RE_BREAK_EXTEND && prop_m1 != RE_BREAK_FORMAT) - break; - - --pos_m1; - } - - /* No break between most letters. */ - if (prop_m1 == RE_BREAK_ALETTER && prop == RE_BREAK_ALETTER) - return FALSE; - - if (pos_m1 >= 0 && char_m1 == '\'' && is_unicode_vowel(char_0)) - return TRUE; - - pos_p1 = text_pos + 1; - prop_p1 = RE_BREAK_OTHER; - while (pos_p1 < state->text_length) { - char_p1 = char_at(state->text, pos_p1); - prop_p1 = (int)re_get_word_break(char_p1); - if (prop_p1 != RE_BREAK_EXTEND && prop_p1 != RE_BREAK_FORMAT) - break; - - ++pos_p1; - } - - /* No break letters across certain punctuation. */ - if (prop_m1 == RE_BREAK_ALETTER && (prop == RE_BREAK_MIDLETTER || prop == - RE_BREAK_MIDNUMLET) && prop_p1 == RE_BREAK_ALETTER) - return FALSE; - - pos_m2 = pos_m1 - 1; - prop_m2 = RE_BREAK_OTHER; - while (pos_m2 >= 0) { - char_m2 = char_at(state->text, pos_m2); - prop_m2 = (int)re_get_word_break(char_m2); - if (prop_m2 != RE_BREAK_EXTEND && prop_m1 != RE_BREAK_FORMAT) - break; - - --pos_m2; - } - - if (prop_m2 == RE_BREAK_ALETTER && (prop_m1 == RE_BREAK_MIDLETTER || - prop_m1 == RE_BREAK_MIDNUMLET) && prop == RE_BREAK_ALETTER) - return FALSE; - - /* No break within sequences of digits, or digits adjacent to letters - * ("3a", or "A3"). - */ - if ((prop_m1 == RE_BREAK_NUMERIC || prop_m1 == RE_BREAK_ALETTER) && prop == - RE_BREAK_NUMERIC) - return FALSE; - - if (prop_m1 == RE_BREAK_NUMERIC && prop == RE_BREAK_ALETTER) - return FALSE; - - /* No break within sequences, such as "3.2" or "3,456.789". */ - if (prop_m2 == RE_BREAK_NUMERIC && (prop_m1 == RE_BREAK_MIDNUM || prop_m1 - == RE_BREAK_MIDNUMLET) && prop == RE_BREAK_NUMERIC) - return FALSE; - - if (prop_m1 == RE_BREAK_NUMERIC && (prop == RE_BREAK_MIDNUM || prop == - RE_BREAK_MIDNUMLET) && prop_p1 == RE_BREAK_NUMERIC) - return FALSE; - - /* No break between Katakana. */ - if (prop_m1 == RE_BREAK_KATAKANA && prop == RE_BREAK_KATAKANA) - return FALSE; - - /* No break from extenders. */ - if ((prop_m1 == RE_BREAK_ALETTER || prop_m1 == RE_BREAK_NUMERIC || prop_m1 - == RE_BREAK_KATAKANA || prop_m1 == RE_BREAK_EXTENDNUMLET) && prop == - RE_BREAK_EXTENDNUMLET) - return FALSE; - - if (prop_m1 == RE_BREAK_EXTENDNUMLET && (prop == RE_BREAK_ALETTER || prop - == RE_BREAK_NUMERIC || prop == RE_BREAK_KATAKANA)) - return FALSE; - - /* Otherwise, break everywhere (including around ideographs). */ - before = unicode_has_property(RE_PROP_WORD, char_m1); - after = unicode_has_property(RE_PROP_WORD, char_0); - - return before != at_start && after == at_start; -} - -/* Checks whether a position is at the start of a word. */ -static BOOL unicode_at_default_word_start(RE_State* state, Py_ssize_t text_pos) - { - return unicode_at_default_word_start_or_end(state, text_pos, TRUE); -} - -/* Checks whether a position is at the end of a word. */ -static BOOL unicode_at_default_word_end(RE_State* state, Py_ssize_t text_pos) { - return unicode_at_default_word_start_or_end(state, text_pos, FALSE); -} - -/* Checks whether a position is on a grapheme boundary. - * - * The rules are defined here: - * http://www.unicode.org/reports/tr29/#Grapheme_Cluster_Boundaries - */ -static BOOL unicode_at_grapheme_boundary(RE_State* state, Py_ssize_t text_pos) - { - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - int prop; - int prop_m1; - - /* Break at the start and end of the text. */ - if (text_pos <= 0) - return TRUE; - - if (text_pos >= state->text_length) - return TRUE; - - char_at = state->char_at; - - prop = (int)re_get_grapheme_cluster_break(char_at(state->text, text_pos)); - prop_m1 = (int)re_get_grapheme_cluster_break(char_at(state->text, text_pos - - 1)); - - /* Don't break within CRLF. */ - if (prop_m1 == RE_GBREAK_CR && prop == RE_GBREAK_LF) - return FALSE; - - /* Otherwise break before and after controls (including CR and LF). */ - if (prop_m1 == RE_GBREAK_CONTROL || prop_m1 == RE_GBREAK_CR || prop_m1 == - RE_GBREAK_LF || prop == RE_GBREAK_CONTROL || prop == RE_GBREAK_CR || prop - == RE_GBREAK_LF) - return TRUE; - - /* Don't break Hangul syllable sequences. */ - if (prop_m1 == RE_GBREAK_L && (prop == RE_GBREAK_L || prop == RE_GBREAK_V - || prop == RE_GBREAK_LV || prop == RE_GBREAK_LVT)) - return FALSE; - if ((prop_m1 == RE_GBREAK_LV || prop_m1 == RE_GBREAK_V) && (prop == - RE_GBREAK_V || prop == RE_GBREAK_T)) - return FALSE; - if ((prop_m1 == RE_GBREAK_LVT || prop_m1 == RE_GBREAK_T) && (prop == - RE_GBREAK_T)) - return FALSE; - - /* Don't break between regional indicator symbols. */ - if (prop_m1 == RE_GBREAK_REGIONALINDICATOR && prop == - RE_GBREAK_REGIONALINDICATOR) - return FALSE; - - /* Don't break just before Extend characters. */ - if (prop == RE_GBREAK_EXTEND) - return FALSE; - - /* Don't break before SpacingMarks, or after Prepend characters. */ - if (prop == RE_GBREAK_SPACINGMARK) - return FALSE; - - if (prop_m1 == RE_GBREAK_PREPEND) - return FALSE; - - /* Otherwise, break everywhere. */ - return TRUE; -} - -/* Checks whether a character is a line separator. */ -static BOOL unicode_is_line_sep(Py_UCS4 ch) { - return (0x0A <= ch && ch <= 0x0D) || ch == 0x85 || ch == 0x2028 || ch == - 0x2029; -} - -/* Checks whether a position is at the start of a line. */ -static BOOL unicode_at_line_start(RE_State* state, Py_ssize_t text_pos) { - Py_UCS4 ch; - - if (text_pos <= 0) - return TRUE; - - ch = state->char_at(state->text, text_pos - 1); - - if (ch == 0x0D) { - if (text_pos >= state->text_length) - return TRUE; - - /* No line break inside CRLF. */ - return state->char_at(state->text, text_pos) != 0x0A; - } - - return (0x0A <= ch && ch <= 0x0D) || ch == 0x85 || ch == 0x2028 || ch == - 0x2029; -} - -/* Checks whether a position is at the end of a line. */ -static BOOL unicode_at_line_end(RE_State* state, Py_ssize_t text_pos) { - Py_UCS4 ch; - - if (text_pos >= state->text_length) - return TRUE; - - ch = state->char_at(state->text, text_pos); - - if (ch == 0x0A) { - if (text_pos <= 0) - return TRUE; - - /* No line break inside CRLF. */ - return state->char_at(state->text, text_pos - 1) != 0x0D; - } - - return (0x0A <= ch && ch <= 0x0D) || ch == 0x85 || ch == 0x2028 || ch == - 0x2029; -} - -/* Checks whether a character could be Turkic (variants of I/i). */ -static BOOL unicode_possible_turkic(Py_UCS4 ch) { - return ch == 'I' || ch == 'i' || ch == 0x0130 || ch == 0x0131; -} - -/* Gets all the cases of a character. */ -static int unicode_all_cases(Py_UCS4 ch, Py_UCS4* codepoints) { - return re_get_all_cases(ch, codepoints); -} - -/* Returns a character with its case folded, unless it could be Turkic - * (variants of I/i). - */ -static Py_UCS4 unicode_simple_case_fold(Py_UCS4 ch) { - /* Is it a possible Turkic character? If so, pass it through unchanged. */ - if (ch == 'I' || ch == 'i' || ch == 0x0130 || ch == 0x0131) - return ch; - - return (Py_UCS4)re_get_simple_case_folding(ch); -} - -/* Returns a character with its case folded, unless it could be Turkic - * (variants of I/i). - */ -static int unicode_full_case_fold(Py_UCS4 ch, Py_UCS4* folded) { - /* Is it a possible Turkic character? If so, pass it through unchanged. */ - if (ch == 'I' || ch == 'i' || ch == 0x0130 || ch == 0x0131) { - folded[0] = ch; - return 1; - } - - return re_get_full_case_folding(ch, folded); -} - -/* Gets all the case variants of Turkic 'I'. */ -static int unicode_all_turkic_i(Py_UCS4 ch, Py_UCS4* cases) { - int count; - - count = 0; - - cases[count++] = ch; - - if (ch != 'I') - cases[count++] = 'I'; - - if (ch != 'i') - cases[count++] = 'i'; - - if (ch != 0x130) - cases[count++] = 0x130; - - if (ch != 0x131) - cases[count++] = 0x131; - - return count; - -} - -/* The handlers for Unicode characters. */ -static RE_EncodingTable unicode_encoding = { - unicode_has_property_wrapper, - unicode_at_boundary, - unicode_at_word_start, - unicode_at_word_end, - unicode_at_default_boundary, - unicode_at_default_word_start, - unicode_at_default_word_end, - unicode_at_grapheme_boundary, - unicode_is_line_sep, - unicode_at_line_start, - unicode_at_line_end, - unicode_possible_turkic, - unicode_all_cases, - unicode_simple_case_fold, - unicode_full_case_fold, - unicode_all_turkic_i, -}; - -Py_LOCAL_INLINE(PyObject*) get_object(char* module_name, char* object_name); - -/* Sets the error message. */ -Py_LOCAL_INLINE(void) set_error(int status, PyObject* object) { - TRACE(("<>\n")) - - if (!error_exception) - error_exception = get_object("_" RE_MODULE "_core", "error"); - - switch (status) { - case RE_ERROR_BACKTRACKING: - PyErr_SetString(error_exception, "too much backtracking"); - break; - case RE_ERROR_CONCURRENT: - PyErr_SetString(PyExc_ValueError, "concurrent not int or None"); - break; - case RE_ERROR_GROUP_INDEX_TYPE: - if (object) - PyErr_Format(PyExc_TypeError, - "group indices must be integers or strings, not %.200s", - object->ob_type->tp_name); - else - PyErr_Format(PyExc_TypeError, - "group indices must be integers or strings"); - break; - case RE_ERROR_ILLEGAL: - PyErr_SetString(PyExc_RuntimeError, "invalid RE code"); - break; - case RE_ERROR_INDEX: - PyErr_SetString(PyExc_TypeError, "string indices must be integers"); - break; - case RE_ERROR_INTERRUPTED: - /* An exception has already been raised, so let it fly. */ - break; - case RE_ERROR_INVALID_GROUP_REF: - PyErr_SetString(error_exception, "invalid group reference"); - break; - case RE_ERROR_MEMORY: - PyErr_NoMemory(); - break; - case RE_ERROR_NOT_STRING: - PyErr_Format(PyExc_TypeError, "expected string instance, %.200s found", - object->ob_type->tp_name); - break; - case RE_ERROR_NOT_UNICODE: - PyErr_Format(PyExc_TypeError, - "expected unicode instance, %.200s found", object->ob_type->tp_name); - break; - case RE_ERROR_NO_SUCH_GROUP: - PyErr_SetString(PyExc_IndexError, "no such group"); - break; - case RE_ERROR_REPLACEMENT: - PyErr_SetString(error_exception, "invalid replacement"); - break; - default: - /* Other error codes indicate compiler/engine bugs. */ - PyErr_SetString(PyExc_RuntimeError, - "internal error in regular expression engine"); - break; - } -} - -/* Allocates memory. - * - * Sets the Python error handler and returns NULL if the allocation fails. - */ -Py_LOCAL_INLINE(void*) re_alloc(size_t size) { - void* new_ptr; - - new_ptr = PyMem_Malloc(size); - if (!new_ptr) - set_error(RE_ERROR_MEMORY, NULL); - - return new_ptr; -} - -/* Reallocates memory. - * - * Sets the Python error handler and returns NULL if the reallocation fails. - */ -Py_LOCAL_INLINE(void*) re_realloc(void* ptr, size_t size) { - void* new_ptr; - - new_ptr = PyMem_Realloc(ptr, size); - if (!new_ptr) - set_error(RE_ERROR_MEMORY, NULL); - - return new_ptr; -} - -/* Deallocates memory. */ -Py_LOCAL_INLINE(void) re_dealloc(void* ptr) { - PyMem_Free(ptr); -} - -/* Releases the GIL if multithreading is enabled. */ -Py_LOCAL_INLINE(void) release_GIL(RE_SafeState* safe_state) { - if (safe_state->re_state->is_multithreaded) - safe_state->thread_state = PyEval_SaveThread(); -} - -/* Acquires the GIL if multithreading is enabled. */ -Py_LOCAL_INLINE(void) acquire_GIL(RE_SafeState* safe_state) { - if (safe_state->re_state->is_multithreaded) - PyEval_RestoreThread(safe_state->thread_state); -} - -/* Allocates memory, holding the GIL during the allocation. - * - * Sets the Python error handler and returns NULL if the allocation fails. - */ -Py_LOCAL_INLINE(void*) safe_alloc(RE_SafeState* safe_state, size_t size) { - void* new_ptr; - - acquire_GIL(safe_state); - - new_ptr = re_alloc(size); - - release_GIL(safe_state); - - return new_ptr; -} - -/* Reallocates memory, holding the GIL during the reallocation. - * - * Sets the Python error handler and returns NULL if the reallocation fails. - */ -Py_LOCAL_INLINE(void*) safe_realloc(RE_SafeState* safe_state, void* ptr, size_t - size) { - void* new_ptr; - - acquire_GIL(safe_state); - - new_ptr = re_realloc(ptr, size); - - release_GIL(safe_state); - - return new_ptr; -} - -/* Deallocates memory, holding the GIL during the deallocation. */ -Py_LOCAL_INLINE(void) safe_dealloc(RE_SafeState* safe_state, void* ptr) { - acquire_GIL(safe_state); - - re_dealloc(ptr); - - release_GIL(safe_state); -} - -/* Checks for KeyboardInterrupt, holding the GIL during the check. */ -Py_LOCAL_INLINE(BOOL) safe_check_signals(RE_SafeState* safe_state) { - BOOL result; - - acquire_GIL(safe_state); - - result = (BOOL)PyErr_CheckSignals(); - - release_GIL(safe_state); - - return result; -} - -/* Checks whether a character is in a range. */ -Py_LOCAL_INLINE(BOOL) in_range(RE_EncodingTable* encoding, Py_UCS4 lower, - Py_UCS4 upper, Py_UCS4 ch) { - return lower <= ch && ch <= upper; -} - -/* Checks whether a character is in a range, ignoring case. */ -Py_LOCAL_INLINE(BOOL) in_range_ign(RE_EncodingTable* encoding, Py_UCS4 lower, - Py_UCS4 upper, Py_UCS4 ch) { - Py_UCS4 cases[RE_MAX_CASES]; - int count; - int i; - - count = encoding->all_cases(ch, cases); - - for (i = 0; i < count; i++) { - if (in_range(encoding, lower, upper, cases[i])) - return TRUE; - } - - return FALSE; -} - -/* Checks whether 2 characters are the same. */ -Py_LOCAL_INLINE(BOOL) same_char(RE_EncodingTable* encoding, Py_UCS4 ch1, - Py_UCS4 ch2) { - return ch1 == ch2; -} - -/* Wrapper for calling 'same_char' via a pointer. */ -static BOOL same_char_wrapper(RE_EncodingTable* encoding, Py_UCS4 ch1, Py_UCS4 - ch2) { - return same_char(encoding, ch1, ch2); -} - -/* Checks whether 2 characters are the same, ignoring case. */ -Py_LOCAL_INLINE(BOOL) same_char_ign(RE_EncodingTable* encoding, Py_UCS4 ch1, - Py_UCS4 ch2) { - Py_UCS4 cases[RE_MAX_CASES]; - int count; - int i; - - if (ch1 == ch2) - return TRUE; - - count = encoding->all_cases(ch1, cases); - - for (i = 1; i < count; i++) { - if (cases[i] == ch2) - return TRUE; - } - - return FALSE; -} - -/* Wrapper for calling 'same_char' via a pointer. */ -static BOOL same_char_ign_wrapper(RE_EncodingTable* encoding, Py_UCS4 ch1, - Py_UCS4 ch2) { - return same_char_ign(encoding, ch1, ch2); -} - -/* Checks whether a character is anything except a newline. */ -Py_LOCAL_INLINE(BOOL) matches_ANY(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - return ch != '\n'; -} - -/* Checks whether a character is anything except a line separator. */ -Py_LOCAL_INLINE(BOOL) matches_ANY_U(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - return !encoding->is_line_sep(ch); -} - -/* Checks whether 2 characters are the same. */ -Py_LOCAL_INLINE(BOOL) matches_CHARACTER(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - return same_char(encoding, node->values[0], ch); -} - -/* Checks whether 2 characters are the same, ignoring case. */ -Py_LOCAL_INLINE(BOOL) matches_CHARACTER_IGN(RE_EncodingTable* encoding, - RE_Node* node, Py_UCS4 ch) { - return same_char_ign(encoding, node->values[0], ch); -} - -/* Checks whether a character has a property. */ -Py_LOCAL_INLINE(BOOL) matches_PROPERTY(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - return encoding->has_property(node->values[0], ch); -} - -/* Checks whether a character has a property, ignoring case. */ -Py_LOCAL_INLINE(BOOL) matches_PROPERTY_IGN(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - RE_UINT32 property; - RE_UINT32 prop; - - property = node->values[0]; - prop = property >> 16; - - /* We need to do special handling of case-sensitive properties according to - * the 'encoding'. - */ - if (encoding == &unicode_encoding) { - /* We are working with Unicode. */ - if (property == RE_PROP_GC_LU || property == RE_PROP_GC_LL || property - == RE_PROP_GC_LT) { - RE_UINT32 value; - - value = re_get_general_category(ch); - - return value == RE_PROP_LU || value == RE_PROP_LL || value == - RE_PROP_LT; - } else if (prop == RE_PROP_UPPERCASE || prop == RE_PROP_LOWERCASE) - return (BOOL)re_get_cased(ch); - - /* The property is case-insensitive. */ - return unicode_has_property(property, ch); - } else if (encoding == &ascii_encoding) { - /* We are working with ASCII. */ - if (property == RE_PROP_GC_LU || property == RE_PROP_GC_LL || property - == RE_PROP_GC_LT) { - RE_UINT32 value; - - value = re_get_general_category(ch); - - return value == RE_PROP_LU || value == RE_PROP_LL || value == - RE_PROP_LT; - } else if (prop == RE_PROP_UPPERCASE || prop == RE_PROP_LOWERCASE) - return (BOOL)re_get_cased(ch); - - /* The property is case-insensitive. */ - return ascii_has_property(property, ch); - } else { - /* We are working with Locale. */ - if (property == RE_PROP_GC_LU || property == RE_PROP_GC_LL || property - == RE_PROP_GC_LT) - return ch <= RE_LOCALE_MAX && (isupper((int)ch) || - islower((int)ch)) != 0; - else if (prop == RE_PROP_UPPERCASE || prop == RE_PROP_LOWERCASE) - return ch <= RE_LOCALE_MAX && (isupper((int)ch) || - islower((int)ch)) != 0; - - /* The property is case-insensitive. */ - return locale_has_property(property, ch); - } -} - -/* Checks whether a character is in a range. */ -Py_LOCAL_INLINE(BOOL) matches_RANGE(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - return in_range(encoding, node->values[0], node->values[1], ch); -} - -/* Checks whether a character is in a range, ignoring case. */ -Py_LOCAL_INLINE(BOOL) matches_RANGE_IGN(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - return in_range_ign(encoding, node->values[0], node->values[1], ch); -} - -Py_LOCAL_INLINE(BOOL) in_set_diff(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch); -Py_LOCAL_INLINE(BOOL) in_set_inter(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch); -Py_LOCAL_INLINE(BOOL) in_set_sym_diff(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch); -Py_LOCAL_INLINE(BOOL) in_set_union(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch); - -/* Checks whether a character matches a set member. */ -Py_LOCAL_INLINE(BOOL) matches_member(RE_EncodingTable* encoding, RE_Node* - member, Py_UCS4 ch) { - switch (member->op) { - case RE_OP_CHARACTER: - /* values are: char_code */ - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->values[0])) - return ch == member->values[0]; - case RE_OP_PROPERTY: - /* values are: property */ - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->values[0])) - return encoding->has_property(member->values[0], ch); - case RE_OP_RANGE: - /* values are: lower, upper */ - TRACE(("%s %d %d %d\n", re_op_text[member->op], member->match, - member->values[0], member->values[1])) - return in_range(encoding, member->values[0], member->values[1], ch); - case RE_OP_SET_DIFF: - TRACE(("%s\n", re_op_text[member->op])) - return in_set_diff(encoding, member, ch); - case RE_OP_SET_INTER: - TRACE(("%s\n", re_op_text[member->op])) - return in_set_inter(encoding, member, ch); - case RE_OP_SET_SYM_DIFF: - TRACE(("%s\n", re_op_text[member->op])) - return in_set_sym_diff(encoding, member, ch); - case RE_OP_SET_UNION: - TRACE(("%s\n", re_op_text[member->op])) - return in_set_union(encoding, member, ch); - case RE_OP_STRING: - { - /* values are: char_code, char_code, ... */ - size_t i; - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->value_count)) - - for (i = 0; i < member->value_count; i++) { - if (ch == member->values[i]) - return TRUE; - } - return FALSE; - } - default: - return FALSE; - } -} - -/* Checks whether a character matches a set member, ignoring case. */ -Py_LOCAL_INLINE(BOOL) matches_member_ign(RE_EncodingTable* encoding, RE_Node* - member, int case_count, Py_UCS4* cases) { - int i; - - for (i = 0; i < case_count; i++) { - switch (member->op) { - case RE_OP_CHARACTER: - /* values are: char_code */ - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->values[0])) - if (cases[i] == member->values[0]) - return TRUE; - break; - case RE_OP_PROPERTY: - /* values are: property */ - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->values[0])) - if (encoding->has_property(member->values[0], cases[i])) - return TRUE; - break; - case RE_OP_RANGE: - /* values are: lower, upper */ - TRACE(("%s %d %d %d\n", re_op_text[member->op], member->match, - member->values[0], member->values[1])) - if (in_range(encoding, member->values[0], member->values[1], - cases[i])) - return TRUE; - break; - case RE_OP_SET_DIFF: - TRACE(("%s\n", re_op_text[member->op])) - if (in_set_diff(encoding, member, cases[i])) - return TRUE; - break; - case RE_OP_SET_INTER: - TRACE(("%s\n", re_op_text[member->op])) - if (in_set_inter(encoding, member, cases[i])) - return TRUE; - break; - case RE_OP_SET_SYM_DIFF: - TRACE(("%s\n", re_op_text[member->op])) - if (in_set_sym_diff(encoding, member, cases[i])) - return TRUE; - break; - case RE_OP_SET_UNION: - TRACE(("%s\n", re_op_text[member->op])) - if (in_set_union(encoding, member, cases[i])) - return TRUE; - break; - case RE_OP_STRING: - { - size_t j; - TRACE(("%s %d %d\n", re_op_text[member->op], member->match, - member->value_count)) - - for (j = 0; j < member->value_count; j++) { - if (cases[i] == member->values[j]) - return TRUE; - } - break; - } - default: - return TRUE; - } - } - - return FALSE; -} - -/* Checks whether a character is in a set difference. */ -Py_LOCAL_INLINE(BOOL) in_set_diff(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - if (matches_member(encoding, member, ch) != member->match) - return FALSE; - - member = member->next_1.node; - - while (member) { - if (matches_member(encoding, member, ch) == member->match) - return FALSE; - - member = member->next_1.node; - } - - return TRUE; -} - -/* Checks whether a character is in a set difference, ignoring case. */ -Py_LOCAL_INLINE(BOOL) in_set_diff_ign(RE_EncodingTable* encoding, RE_Node* - node, int case_count, Py_UCS4* cases) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - if (matches_member_ign(encoding, member, case_count, cases) != - member->match) - return FALSE; - - member = member->next_1.node; - - while (member) { - if (matches_member_ign(encoding, member, case_count, cases) == - member->match) - return FALSE; - - member = member->next_1.node; - } - - return TRUE; -} - -/* Checks whether a character is in a set intersection. */ -Py_LOCAL_INLINE(BOOL) in_set_inter(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - while (member) { - if (matches_member(encoding, member, ch) != member->match) - return FALSE; - - member = member->next_1.node; - } - - return TRUE; -} - -/* Checks whether a character is in a set intersection, ignoring case. */ -Py_LOCAL_INLINE(BOOL) in_set_inter_ign(RE_EncodingTable* encoding, RE_Node* - node, int case_count, Py_UCS4* cases) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - while (member) { - if (matches_member_ign(encoding, member, case_count, cases) != - member->match) - return FALSE; - - member = member->next_1.node; - } - - return TRUE; -} - -/* Checks whether a character is in a set symmetric difference. */ -Py_LOCAL_INLINE(BOOL) in_set_sym_diff(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - RE_Node* member; - BOOL result; - - member = node->nonstring.next_2.node; - - result = FALSE; - - while (member) { - if (matches_member(encoding, member, ch) == member->match) - result = !result; - - member = member->next_1.node; - } - - return result; -} - -/* Checks whether a character is in a set symmetric difference, ignoring case. - */ -Py_LOCAL_INLINE(BOOL) in_set_sym_diff_ign(RE_EncodingTable* encoding, RE_Node* - node, int case_count, Py_UCS4* cases) { - RE_Node* member; - BOOL result; - - member = node->nonstring.next_2.node; - - result = FALSE; - - while (member) { - if (matches_member_ign(encoding, member, case_count, cases) == - member->match) - result = !result; - - member = member->next_1.node; - } - - return result; -} - -/* Checks whether a character is in a set union. */ -Py_LOCAL_INLINE(BOOL) in_set_union(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - while (member) { - if (matches_member(encoding, member, ch) == member->match) - return TRUE; - - member = member->next_1.node; - } - - return FALSE; -} - -/* Checks whether a character is in a set union, ignoring case. */ -Py_LOCAL_INLINE(BOOL) in_set_union_ign(RE_EncodingTable* encoding, RE_Node* - node, int case_count, Py_UCS4* cases) { - RE_Node* member; - - member = node->nonstring.next_2.node; - - while (member) { - if (matches_member_ign(encoding, member, case_count, cases) == - member->match) - return TRUE; - - member = member->next_1.node; - } - - return FALSE; -} - -/* Checks whether a character is in a set. */ -Py_LOCAL_INLINE(BOOL) matches_SET(RE_EncodingTable* encoding, RE_Node* node, - Py_UCS4 ch) { - switch (node->op) { - case RE_OP_SET_DIFF: - case RE_OP_SET_DIFF_REV: - return in_set_diff(encoding, node, ch); - case RE_OP_SET_INTER: - case RE_OP_SET_INTER_REV: - return in_set_inter(encoding, node, ch); - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_SYM_DIFF_REV: - return in_set_sym_diff(encoding, node, ch); - case RE_OP_SET_UNION: - case RE_OP_SET_UNION_REV: - return in_set_union(encoding, node, ch); - } - - return FALSE; -} - -/* Checks whether a character is in a set, ignoring case. */ -Py_LOCAL_INLINE(BOOL) matches_SET_IGN(RE_EncodingTable* encoding, RE_Node* - node, Py_UCS4 ch) { - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - case_count = encoding->all_cases(ch, cases); - - switch (node->op) { - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_DIFF_IGN_REV: - return in_set_diff_ign(encoding, node, case_count, cases); - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_INTER_IGN_REV: - return in_set_inter_ign(encoding, node, case_count, cases); - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_SYM_DIFF_IGN_REV: - return in_set_sym_diff_ign(encoding, node, case_count, cases); - case RE_OP_SET_UNION_IGN: - case RE_OP_SET_UNION_IGN_REV: - return in_set_union_ign(encoding, node, case_count, cases); - } - - return FALSE; -} - -/* Resets a guard list. */ -Py_LOCAL_INLINE(void) reset_guard_list(RE_GuardList* guard_list) { - guard_list->count = 0; - guard_list->last_text_pos = -1; -} - -/* Initialises the state for a match. */ -Py_LOCAL_INLINE(void) init_match(RE_State* state) { - size_t i; - - /* Reset the backtrack. */ - state->current_backtrack_block = &state->backtrack_block; - state->current_backtrack_block->count = 0; - state->current_saved_groups = state->first_saved_groups; - state->backtrack = NULL; - state->search_anchor = state->text_pos; - state->match_pos = state->text_pos; - - /* Reset the guards for the repeats. */ - for (i = 0; i < state->pattern->repeat_count; i++) { - reset_guard_list(&state->repeats[i].body_guard_list); - reset_guard_list(&state->repeats[i].tail_guard_list); - } - - /* Reset the guards for the fuzzy sections. */ - for (i = 0; i < state->pattern->fuzzy_count; i++) { - reset_guard_list(&state->fuzzy_guards[i].body_guard_list); - reset_guard_list(&state->fuzzy_guards[i].tail_guard_list); - } - - for (i = 0; i < state->pattern->true_group_count; i++) { - RE_GroupData* group; - - group = &state->groups[i]; - group->span.start = -1; - group->span.end = -1; - group->capture_count = 0; - group->current_capture = -1; - } - - /* Reset the guards for the group calls. */ - for (i = 0; i < state->pattern->call_ref_info_count; i++) - reset_guard_list(&state->group_call_guard_list[i]); - - /* Clear the counts and cost for matching. */ - memset(state->fuzzy_info.counts, 0, sizeof(state->fuzzy_info.counts)); - state->fuzzy_info.total_cost = 0; - memset(state->total_fuzzy_counts, 0, sizeof(state->total_fuzzy_counts)); - state->total_errors = 0; - state->total_cost = 0; - state->too_few_errors = FALSE; - state->capture_change = 0; - state->iterations = 0; -} - -/* Adds a new backtrack entry. */ -Py_LOCAL_INLINE(BOOL) add_backtrack(RE_SafeState* safe_state, RE_UINT8 op) { - RE_State* state; - RE_BacktrackBlock* current; - - state = safe_state->re_state; - - current = state->current_backtrack_block; - if (current->count >= current->capacity) { - if (!current->next) { - RE_BacktrackBlock* next; - - /* Is there too much backtracking? */ - if (state->backtrack_allocated >= RE_MAX_BACKTRACK_ALLOC) - return FALSE; - - next = (RE_BacktrackBlock*)safe_alloc(safe_state, - sizeof(RE_BacktrackBlock)); - if (!next) - return FALSE; - - next->previous = current; - next->next = NULL; - next->capacity = RE_BACKTRACK_BLOCK_SIZE; - current->next = next; - - state->backtrack_allocated += RE_BACKTRACK_BLOCK_SIZE; - } - - current = current->next; - current->count = 0; - state->current_backtrack_block = current; - } - - state->backtrack = ¤t->items[current->count++]; - state->backtrack->op = op; - - return TRUE; -} - -/* Gets the last backtrack entry. - * - * It'll never be called when there are _no_ entries. - */ -Py_LOCAL_INLINE(RE_BacktrackData*) last_backtrack(RE_State* state) { - RE_BacktrackBlock* current; - - current = state->current_backtrack_block; - state->backtrack = ¤t->items[current->count - 1]; - - return state->backtrack; -} - -/* Discards the last backtrack entry. - * - * It'll never be called to discard the _only_ entry. - */ -Py_LOCAL_INLINE(void) discard_backtrack(RE_State* state) { - RE_BacktrackBlock* current; - - current = state->current_backtrack_block; - --current->count; - if (current->count == 0 && current->previous) - state->current_backtrack_block = current->previous; -} - -/* Copies a repeat guard list. */ -Py_LOCAL_INLINE(BOOL) copy_guard_data(RE_SafeState* safe_state, RE_GuardList* - dst, RE_GuardList* src) { - if (dst->capacity < src->count) { - RE_GuardSpan* new_spans; - - if (!safe_state) - return FALSE; - - dst->capacity = src->count; - new_spans = (RE_GuardSpan*)safe_realloc(safe_state, dst->spans, - dst->capacity * sizeof(RE_GuardSpan)); - if (!new_spans) - return FALSE; - - dst->spans = new_spans; - } - - dst->count = src->count; - memmove(dst->spans, src->spans, dst->count * sizeof(RE_GuardSpan)); - - dst->last_text_pos = -1; - - return TRUE; -} - -/* Copies a repeat. */ -Py_LOCAL_INLINE(BOOL) copy_repeat_data(RE_SafeState* safe_state, RE_RepeatData* - dst, RE_RepeatData* src) { - if (!copy_guard_data(safe_state, &dst->body_guard_list, - &src->body_guard_list) || !copy_guard_data(safe_state, - &dst->tail_guard_list, &src->tail_guard_list)) { - safe_dealloc(safe_state, dst->body_guard_list.spans); - safe_dealloc(safe_state, dst->tail_guard_list.spans); - - return FALSE; - } - - dst->count = src->count; - dst->start = src->start; - dst->capture_change = src->capture_change; - - return TRUE; -} - -/* Pushes a return node onto the group call stack. */ -Py_LOCAL_INLINE(BOOL) push_group_return(RE_SafeState* safe_state, RE_Node* - return_node) { - RE_State* state; - PatternObject* pattern; - RE_GroupCallFrame* frame; - - state = safe_state->re_state; - pattern = state->pattern; - - if (state->current_group_call_frame && - state->current_group_call_frame->next) - /* Advance to the next allocated frame. */ - frame = state->current_group_call_frame->next; - else if (!state->current_group_call_frame && state->first_group_call_frame) - /* Advance to the first allocated frame. */ - frame = state->first_group_call_frame; - else { - /* Create a new frame. */ - frame = (RE_GroupCallFrame*)safe_alloc(safe_state, - sizeof(RE_GroupCallFrame)); - if (!frame) - return FALSE; - - frame->groups = (RE_GroupData*)safe_alloc(safe_state, - pattern->true_group_count * sizeof(RE_GroupData)); - frame->repeats = (RE_RepeatData*)safe_alloc(safe_state, - pattern->repeat_count * sizeof(RE_RepeatData)); - if (!frame->groups || !frame->repeats) { - safe_dealloc(safe_state, frame->groups); - safe_dealloc(safe_state, frame->repeats); - safe_dealloc(safe_state, frame); - - return FALSE; - } - - memset(frame->groups, 0, pattern->true_group_count * - sizeof(RE_GroupData)); - memset(frame->repeats, 0, pattern->repeat_count * - sizeof(RE_RepeatData)); - - frame->previous = state->current_group_call_frame; - frame->next = NULL; - - if (frame->previous) - frame->previous->next = frame; - else - state->first_group_call_frame = frame; - } - - frame->node = return_node; - - /* Push the groups and guards. */ - if (return_node) { - size_t g; - size_t r; - - for (g = 0; g < pattern->true_group_count; g++) { - frame->groups[g].span = state->groups[g].span; - frame->groups[g].current_capture = - state->groups[g].current_capture; - } - - for (r = 0; r < pattern->repeat_count; r++) { - if (!copy_repeat_data(safe_state, &frame->repeats[r], - &state->repeats[r])) - return FALSE; - } - } - - state->current_group_call_frame = frame; - - return TRUE; -} - -/* Pops a return node from the group call stack. */ -Py_LOCAL_INLINE(RE_Node*) pop_group_return(RE_State* state) { - RE_GroupCallFrame* frame; - - frame = state->current_group_call_frame; - - /* Pop the groups and repeats. */ - if (frame->node) { - PatternObject* pattern; - size_t g; - size_t r; - - pattern = state->pattern; - - for (g = 0; g < pattern->true_group_count; g++) { - state->groups[g].span = frame->groups[g].span; - state->groups[g].current_capture = - frame->groups[g].current_capture; - } - - for (r = 0; r < pattern->repeat_count; r++) - copy_repeat_data(NULL, &state->repeats[r], &frame->repeats[r]); - } - - /* Withdraw to previous frame. */ - state->current_group_call_frame = frame->previous; - - return frame->node; -} - -/* Returns the return node from the top of the group call stack. */ -Py_LOCAL_INLINE(RE_Node*) top_group_return(RE_State* state) { - RE_GroupCallFrame* frame; - - frame = state->current_group_call_frame; - - return frame->node; -} - -/* Checks whether a node matches only 1 character. */ -Py_LOCAL_INLINE(BOOL) node_matches_one_character(RE_Node* node) { - switch (node->op) { - case RE_OP_ANY: - case RE_OP_ANY_ALL: - case RE_OP_ANY_ALL_REV: - case RE_OP_ANY_REV: - case RE_OP_ANY_U: - case RE_OP_ANY_U_REV: - case RE_OP_CHARACTER: - case RE_OP_CHARACTER_IGN: - case RE_OP_CHARACTER_IGN_REV: - case RE_OP_CHARACTER_REV: - case RE_OP_PROPERTY: - case RE_OP_PROPERTY_IGN: - case RE_OP_PROPERTY_IGN_REV: - case RE_OP_PROPERTY_REV: - case RE_OP_RANGE: - case RE_OP_RANGE_IGN: - case RE_OP_RANGE_IGN_REV: - case RE_OP_RANGE_REV: - case RE_OP_SET_DIFF: - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION: - case RE_OP_SET_UNION_IGN: - case RE_OP_SET_UNION_IGN_REV: - case RE_OP_SET_UNION_REV: - return TRUE; - default: - return FALSE; - } -} - -/* Checks whether the node is a firstset. */ -Py_LOCAL_INLINE(BOOL) is_firstset(RE_Node* node) { - if (node->step != 0) - return FALSE; - - return node_matches_one_character(node); -} - -/* Locates the start node for testing ahead. */ -Py_LOCAL_INLINE(RE_Node*) locate_test_start(RE_Node* node) { - for (;;) { - switch (node->op) { - case RE_OP_BOUNDARY: - switch (node->next_1.node->op) { - case RE_OP_STRING: - case RE_OP_STRING_FLD: - case RE_OP_STRING_FLD_REV: - case RE_OP_STRING_IGN: - case RE_OP_STRING_IGN_REV: - case RE_OP_STRING_REV: - return node->next_1.node; - default: - return node; - } - case RE_OP_CALL_REF: - case RE_OP_END_GROUP: - case RE_OP_START_GROUP: - node = node->next_1.node; - break; - case RE_OP_GREEDY_REPEAT: - case RE_OP_LAZY_REPEAT: - if (node->values[1] == 0) - return node; - node = node->next_1.node; - break; - case RE_OP_GREEDY_REPEAT_ONE: - case RE_OP_LAZY_REPEAT_ONE: - if (node->values[1] == 0) - return node; - return node->nonstring.next_2.node; - case RE_OP_LOOKAROUND: - node = node->next_1.node; - break; - default: - if (is_firstset(node)) { - switch (node->next_1.node->op) { - case RE_OP_END_OF_STRING: - case RE_OP_START_OF_STRING: - return node->next_1.node; - } - } - - return node; - } - } -} - -/* Checks whether a character matches any of a set of case characters. */ -Py_LOCAL_INLINE(BOOL) any_case(Py_UCS4 ch, int case_count, Py_UCS4* cases) { - int i; - - for (i = 0; i < case_count; i++) { - if (ch == cases[i]) - return TRUE; - } - - return FALSE; -} - -/* Matches many ANYs, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_ANY(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many ANYs, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_ANY_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many ANY_Us, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_ANY_U(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY_U(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY_U(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_ANY_U(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many ANY_Us, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_ANY_U_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY_U(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY_U(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_ANY_U(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many CHARACTERs, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_CHARACTER(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - Py_UCS4 ch; - - text = state->text; - match = node->match == match; - ch = node->values[0]; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && (text_ptr[0] == ch) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && (text_ptr[0] == ch) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && (text_ptr[0] == ch) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many CHARACTERs, up to a limit, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_CHARACTER_IGN(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - text = state->text; - match = node->match == match; - case_count = state->encoding->all_cases(node->values[0], cases); - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && any_case(text_ptr[0], case_count, cases) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && any_case(text_ptr[0], case_count, cases) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && any_case(text_ptr[0], case_count, cases) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many CHARACTERs, up to a limit, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_CHARACTER_IGN_REV(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - text = state->text; - match = node->match == match; - case_count = state->encoding->all_cases(node->values[0], cases); - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && any_case(text_ptr[-1], case_count, - cases) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && any_case(text_ptr[-1], case_count, - cases) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && any_case(text_ptr[-1], case_count, - cases) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many CHARACTERs, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_CHARACTER_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - Py_UCS4 ch; - - text = state->text; - match = node->match == match; - ch = node->values[0]; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && (text_ptr[-1] == ch) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && (text_ptr[-1] == ch) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && (text_ptr[-1] == ch) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many PROPERTYs, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_PROPERTY(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many PROPERTYs, up to a limit, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_PROPERTY_IGN(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many PROPERTYs, up to a limit, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_PROPERTY_IGN_REV(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many PROPERTYs, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_PROPERTY_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_PROPERTY(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many RANGEs, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_RANGE(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many RANGEs, up to a limit, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_RANGE_IGN(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many RANGEs, up to a limit, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_RANGE_IGN_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many RANGEs, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_RANGE_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_RANGE(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many SETs, up to a limit. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_SET(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_SET(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_SET(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_SET(encoding, node, text_ptr[0]) - == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many SETs, up to a limit, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_SET_IGN(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr < limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr < limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr < limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[0]) == match) - ++text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many SETs, up to a limit, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_SET_IGN_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_SET_IGN(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Matches many SETs, up to a limit, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) match_many_SET_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit, BOOL match) { - void* text; - RE_EncodingTable* encoding; - - text = state->text; - match = node->match == match; - encoding = state->encoding; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr > limit_ptr && matches_SET(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS1*)text; - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr > limit_ptr && matches_SET(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS2*)text; - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr > limit_ptr && matches_SET(encoding, node, - text_ptr[-1]) == match) - --text_ptr; - - text_pos = text_ptr - (Py_UCS4*)text; - break; - } - } - - return text_pos; -} - -/* Counts a repeated character pattern. */ -Py_LOCAL_INLINE(size_t) count_one(RE_State* state, RE_Node* node, Py_ssize_t - text_pos, size_t max_count, BOOL* is_partial) { - size_t count; - - *is_partial = FALSE; - - if (max_count < 1) - return 0; - - switch (node->op) { - case RE_OP_ANY: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_ANY(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_ANY_ALL: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_ANY_ALL_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_ANY_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_ANY_REV(state, node, text_pos, - text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_ANY_U: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_ANY_U(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_ANY_U_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_ANY_U_REV(state, node, text_pos, - text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_CHARACTER: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_CHARACTER(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_CHARACTER_IGN: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_CHARACTER_IGN(state, node, text_pos, - text_pos + (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_CHARACTER_IGN_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_CHARACTER_IGN_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_CHARACTER_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_CHARACTER_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_PROPERTY: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_PROPERTY(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_PROPERTY_IGN: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_PROPERTY_IGN(state, node, text_pos, - text_pos + (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_PROPERTY_IGN_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_PROPERTY_IGN_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_PROPERTY_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_PROPERTY_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_RANGE: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_RANGE(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_RANGE_IGN: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_RANGE_IGN(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_RANGE_IGN_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_RANGE_IGN_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_RANGE_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_RANGE_REV(state, node, text_pos, - text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_SET_DIFF: - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_SET(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION_IGN: - count = min_size_t((size_t)(state->slice_end - text_pos), max_count); - - count = (size_t)(match_many_SET_IGN(state, node, text_pos, text_pos + - (Py_ssize_t)count, TRUE) - text_pos); - - *is_partial = count == (size_t)(state->text_length - text_pos) && count - < max_count && state->partial_side == RE_PARTIAL_RIGHT; - - return count; - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_UNION_IGN_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_SET_IGN_REV(state, node, - text_pos, text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_REV: - count = min_size_t((size_t)(text_pos - state->slice_start), max_count); - - count = (size_t)(text_pos - match_many_SET_REV(state, node, text_pos, - text_pos - (Py_ssize_t)count, TRUE)); - - *is_partial = count == (size_t)(text_pos) && count < max_count && - state->partial_side == RE_PARTIAL_LEFT; - - return count; - } - - return 0; -} - -/* Performs a simple string search. */ -Py_LOCAL_INLINE(Py_ssize_t) simple_string_search(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - Py_ssize_t length; - RE_CODE* values; - RE_EncodingTable* encoding; - Py_UCS4 check_char; - - length = (Py_ssize_t)node->value_count; - values = node->values; - encoding = state->encoding; - check_char = values[0]; - - *is_partial = FALSE; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text = (Py_UCS1*)state->text; - Py_UCS1* text_ptr = text + text_pos; - Py_UCS1* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (text_ptr[0] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[s_pos], values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 2: - { - Py_UCS2* text = (Py_UCS2*)state->text; - Py_UCS2* text_ptr = text + text_pos; - Py_UCS2* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (text_ptr[0] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[s_pos], values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 4: - { - Py_UCS4* text = (Py_UCS4*)state->text; - Py_UCS4* text_ptr = text + text_pos; - Py_UCS4* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (text_ptr[0] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[s_pos], values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - } - - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_pos; - } - - return -1; -} - -/* Performs a simple string search, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) simple_string_search_ign(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - Py_ssize_t length; - RE_CODE* values; - RE_EncodingTable* encoding; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - length = (Py_ssize_t)node->value_count; - values = node->values; - encoding = state->encoding; - case_count = encoding->all_cases(values[0], cases); - - *is_partial = FALSE; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text = (Py_UCS1*)state->text; - Py_UCS1* text_ptr = text + text_pos; - Py_UCS1* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (any_case(text_ptr[0], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[s_pos], - values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 2: - { - Py_UCS2* text = (Py_UCS2*)state->text; - Py_UCS2* text_ptr = text + text_pos; - Py_UCS2* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (any_case(text_ptr[0], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[s_pos], - values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 4: - { - Py_UCS4* text = (Py_UCS4*)state->text; - Py_UCS4* text_ptr = text + text_pos; - Py_UCS4* limit_ptr = text + limit; - - while (text_ptr < limit_ptr) { - if (any_case(text_ptr[0], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr + s_pos >= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[s_pos], - values[s_pos])) - break; - - ++s_pos; - } - } - - ++text_ptr; - } - text_pos = text_ptr - text; - break; - } - } - - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_RIGHT) { - /* Partial match. */ - *is_partial = TRUE; - return text_pos; - } - - return -1; -} - -/* Performs a simple string search, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) simple_string_search_ign_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - Py_ssize_t length; - RE_CODE* values; - RE_EncodingTable* encoding; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - length = (Py_ssize_t)node->value_count; - values = node->values; - encoding = state->encoding; - case_count = encoding->all_cases(values[length - 1], cases); - - *is_partial = FALSE; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text = (Py_UCS1*)state->text; - Py_UCS1* text_ptr = text + text_pos; - Py_UCS1* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (any_case(text_ptr[-1], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 2: - { - Py_UCS2* text = (Py_UCS2*)state->text; - Py_UCS2* text_ptr = text + text_pos; - Py_UCS2* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (any_case(text_ptr[-1], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 4: - { - Py_UCS4* text = (Py_UCS4*)state->text; - Py_UCS4* text_ptr = text + text_pos; - Py_UCS4* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (any_case(text_ptr[-1], case_count, cases)) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char_ign(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - } - - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_pos; - } - - return -1; -} - -/* Performs a simple string search, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) simple_string_search_rev(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - Py_ssize_t length; - RE_CODE* values; - RE_EncodingTable* encoding; - Py_UCS4 check_char; - - length = (Py_ssize_t)node->value_count; - values = node->values; - encoding = state->encoding; - check_char = values[length - 1]; - - *is_partial = FALSE; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text = (Py_UCS1*)state->text; - Py_UCS1* text_ptr = text + text_pos; - Py_UCS1* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (text_ptr[-1] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 2: - { - Py_UCS2* text = (Py_UCS2*)state->text; - Py_UCS2* text_ptr = text + text_pos; - Py_UCS2* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (text_ptr[-1] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - case 4: - { - Py_UCS4* text = (Py_UCS4*)state->text; - Py_UCS4* text_ptr = text + text_pos; - Py_UCS4* limit_ptr = text + limit; - - while (text_ptr > limit_ptr) { - if (text_ptr[-1] == check_char) { - Py_ssize_t s_pos; - - s_pos = 1; - - for (;;) { - if (s_pos >= length) - /* End of search string. */ - return text_ptr - text; - - if (text_ptr - s_pos <= limit_ptr) { - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_ptr - text; - } - - return -1; - - } - - if (!same_char(encoding, text_ptr[- s_pos - 1], - values[length - s_pos - 1])) - break; - - ++s_pos; - } - } - - --text_ptr; - } - text_pos = text_ptr - text; - break; - } - } - - /* Off the end of the text. */ - if (state->partial_side == RE_PARTIAL_LEFT) { - /* Partial match. */ - *is_partial = TRUE; - return text_pos; - } - - return -1; -} - -/* Performs a Boyer-Moore fast string search. */ -Py_LOCAL_INLINE(Py_ssize_t) fast_string_search(RE_State* state, RE_Node* node, - Py_ssize_t text_pos, Py_ssize_t limit) { - RE_EncodingTable* encoding; - void* text; - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad_character_offset; - Py_ssize_t* good_suffix_offset; - Py_ssize_t last_pos; - Py_UCS4 check_char; - - encoding = state->encoding; - text = state->text; - length = (Py_ssize_t)node->value_count; - values = node->values; - good_suffix_offset = node->string.good_suffix_offset; - bad_character_offset = node->string.bad_character_offset; - last_pos = length - 1; - check_char = values[last_pos]; - limit -= length; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS1*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS2*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS4*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - } - - return -1; -} - -/* Performs a Boyer-Moore fast string search, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) fast_string_search_ign(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit) { - RE_EncodingTable* encoding; - void* text; - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad_character_offset; - Py_ssize_t* good_suffix_offset; - Py_ssize_t last_pos; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - encoding = state->encoding; - text = state->text; - length = (Py_ssize_t)node->value_count; - values = node->values; - good_suffix_offset = node->string.good_suffix_offset; - bad_character_offset = node->string.bad_character_offset; - last_pos = length - 1; - case_count = encoding->all_cases(values[last_pos], cases); - limit -= length; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char_ign(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS1*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char_ign(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS2*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr <= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[last_pos]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = last_pos - 1; - while (pos >= 0 && same_char_ign(encoding, - text_ptr[pos], values[pos])) - --pos; - - if (pos < 0) - return text_ptr - (Py_UCS4*)text; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - } - - return -1; -} - -/* Performs a Boyer-Moore fast string search, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) fast_string_search_ign_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit) { - RE_EncodingTable* encoding; - void* text; - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad_character_offset; - Py_ssize_t* good_suffix_offset; - Py_UCS4 cases[RE_MAX_CASES]; - int case_count; - - encoding = state->encoding; - text = state->text; - length = (Py_ssize_t)node->value_count; - values = node->values; - good_suffix_offset = node->string.good_suffix_offset; - bad_character_offset = node->string.bad_character_offset; - case_count = encoding->all_cases(values[0], cases); - text_pos -= length; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char_ign(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS1*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char_ign(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS2*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (any_case(ch, case_count, cases)) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char_ign(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS4*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - } - - return -1; -} - -/* Performs a Boyer-Moore fast string search, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) fast_string_search_rev(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit) { - RE_EncodingTable* encoding; - void* text; - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad_character_offset; - Py_ssize_t* good_suffix_offset; - Py_UCS4 check_char; - - encoding = state->encoding; - text = state->text; - length = (Py_ssize_t)node->value_count; - values = node->values; - good_suffix_offset = node->string.good_suffix_offset; - bad_character_offset = node->string.bad_character_offset; - check_char = values[0]; - text_pos -= length; - - switch (state->charsize) { - case 1: - { - Py_UCS1* text_ptr; - Py_UCS1* limit_ptr; - - text_ptr = (Py_UCS1*)text + text_pos; - limit_ptr = (Py_UCS1*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS1*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 2: - { - Py_UCS2* text_ptr; - Py_UCS2* limit_ptr; - - text_ptr = (Py_UCS2*)text + text_pos; - limit_ptr = (Py_UCS2*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS2*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - case 4: - { - Py_UCS4* text_ptr; - Py_UCS4* limit_ptr; - - text_ptr = (Py_UCS4*)text + text_pos; - limit_ptr = (Py_UCS4*)text + limit; - - while (text_ptr >= limit_ptr) { - Py_UCS4 ch; - - ch = text_ptr[0]; - if (ch == check_char) { - Py_ssize_t pos; - - pos = 1; - while (pos < length && same_char(encoding, - text_ptr[pos], values[pos])) - ++pos; - - if (pos >= length) - return text_ptr - (Py_UCS4*)text + length; - - text_ptr += good_suffix_offset[pos]; - } else - text_ptr += bad_character_offset[ch & 0xFF]; - } - break; - } - } - - return -1; -} - -/* Builds the tables for a Boyer-Moore fast string search. */ -Py_LOCAL_INLINE(BOOL) build_fast_tables(RE_EncodingTable* encoding, RE_Node* - node, BOOL ignore) { - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad; - Py_ssize_t* good; - Py_UCS4 ch; - Py_ssize_t last_pos; - Py_ssize_t pos; - BOOL (*is_same_char)(RE_EncodingTable* encoding, Py_UCS4 ch1, Py_UCS4 ch2); - Py_ssize_t suffix_len; - BOOL saved_start; - Py_ssize_t s; - Py_ssize_t i; - Py_ssize_t s_start; - Py_UCS4 codepoints[RE_MAX_CASES]; - - length = (Py_ssize_t)node->value_count; - - if (length < RE_MIN_FAST_LENGTH) - return TRUE; - - values = node->values; - bad = (Py_ssize_t*)re_alloc(256 * sizeof(bad[0])); - good = (Py_ssize_t*)re_alloc((size_t)length * sizeof(good[0])); - - if (!bad || !good) { - re_dealloc(bad); - re_dealloc(good); - - return FALSE; - } - - for (ch = 0; ch < 0x100; ch++) - bad[ch] = length; - - last_pos = length - 1; - - for (pos = 0; pos < last_pos; pos++) { - Py_ssize_t offset; - - offset = last_pos - pos; - ch = values[pos]; - if (ignore) { - int count; - int i; - - count = encoding->all_cases(ch, codepoints); - - for (i = 0; i < count; i++) - bad[codepoints[i] & 0xFF] = offset; - } else - bad[ch & 0xFF] = offset; - } - - is_same_char = ignore ? same_char_ign_wrapper : same_char_wrapper; - - suffix_len = 2; - pos = length - suffix_len; - saved_start = FALSE; - s = pos - 1; - i = suffix_len - 1; - s_start = s; - - while (pos >= 0) { - /* Look for another occurrence of the suffix. */ - while (i > 0) { - /* Have we dropped off the end of the string? */ - if (s + i < 0) - break; - - if (is_same_char(encoding, values[s + i], values[pos + i])) - /* It still matches. */ - --i; - else { - /* Start again further along. */ - --s; - i = suffix_len - 1; - } - } - - if (s >= 0 && is_same_char(encoding, values[s], values[pos])) { - /* We haven't dropped off the end of the string, and the suffix has - * matched this far, so this is a good starting point for the next - * iteration. - */ - --s; - if (!saved_start) { - s_start = s; - saved_start = TRUE; - } - } else { - /* Calculate the suffix offset. */ - good[pos] = pos - s; - - /* Extend the suffix and start searching for _this_ one. */ - --pos; - ++suffix_len; - - /* Where's a good place to start searching? */ - if (saved_start) { - s = s_start; - saved_start = FALSE; - } else - --s; - - /* Can we short-circuit the searching? */ - if (s < 0) - break; - } - - i = suffix_len - 1; - } - - /* Fill-in any remaining entries. */ - while (pos >= 0) { - good[pos] = pos - s; - --pos; - --s; - } - - node->string.bad_character_offset = bad; - node->string.good_suffix_offset = good; - - return TRUE; -} - -/* Builds the tables for a Boyer-Moore fast string search, backwards. */ -Py_LOCAL_INLINE(BOOL) build_fast_tables_rev(RE_EncodingTable* encoding, - RE_Node* node, BOOL ignore) { - Py_ssize_t length; - RE_CODE* values; - Py_ssize_t* bad; - Py_ssize_t* good; - Py_UCS4 ch; - Py_ssize_t last_pos; - Py_ssize_t pos; - BOOL (*is_same_char)(RE_EncodingTable* encoding, Py_UCS4 ch1, Py_UCS4 ch2); - Py_ssize_t suffix_len; - BOOL saved_start; - Py_ssize_t s; - Py_ssize_t i; - Py_ssize_t s_start; - Py_UCS4 codepoints[RE_MAX_CASES]; - - length = (Py_ssize_t)node->value_count; - - if (length < RE_MIN_FAST_LENGTH) - return TRUE; - - values = node->values; - bad = (Py_ssize_t*)re_alloc(256 * sizeof(bad[0])); - good = (Py_ssize_t*)re_alloc((size_t)length * sizeof(good[0])); - - if (!bad || !good) { - re_dealloc(bad); - re_dealloc(good); - - return FALSE; - } - - for (ch = 0; ch < 0x100; ch++) - bad[ch] = -length; - - last_pos = length - 1; - - for (pos = last_pos; pos > 0; pos--) { - Py_ssize_t offset; - - offset = -pos; - ch = values[pos]; - if (ignore) { - int count; - int i; - - count = encoding->all_cases(ch, codepoints); - - for (i = 0; i < count; i++) - bad[codepoints[i] & 0xFF] = offset; - } else - bad[ch & 0xFF] = offset; - } - - is_same_char = ignore ? same_char_ign_wrapper : same_char_wrapper; - - suffix_len = 2; - pos = suffix_len - 1; - saved_start = FALSE; - s = pos + 1; - i = suffix_len - 1; - s_start = s; - - while (pos < length) { - /* Look for another occurrence of the suffix. */ - while (i > 0) { - /* Have we dropped off the end of the string? */ - if (s - i >= length) - break; - - if (is_same_char(encoding, values[s - i], values[pos - i])) - /* It still matches. */ - --i; - else { - /* Start again further along. */ - ++s; - i = suffix_len - 1; - } - } - - if (s < length && is_same_char(encoding, values[s], values[pos])) { - /* We haven't dropped off the end of the string, and the suffix has - * matched this far, so this is a good starting point for the next - * iteration. - */ - ++s; - if (!saved_start) { - s_start = s; - saved_start = TRUE; - } - } else { - /* Calculate the suffix offset. */ - good[pos] = pos - s; - - /* Extend the suffix and start searching for _this_ one. */ - ++pos; - ++suffix_len; - - /* Where's a good place to start searching? */ - if (saved_start) { - s = s_start; - saved_start = FALSE; - } else - ++s; - - /* Can we short-circuit the searching? */ - if (s >= length) - break; - } - - i = suffix_len - 1; - } - - /* Fill-in any remaining entries. */ - while (pos < length) { - good[pos] = pos - s; - ++pos; - ++s; - } - - node->string.bad_character_offset = bad; - node->string.good_suffix_offset = good; - - return TRUE; -} - -/* Performs a string search. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search(RE_SafeState* safe_state, RE_Node* - node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - RE_State* state; - Py_ssize_t found_pos; - - state = safe_state->re_state; - - *is_partial = FALSE; - - /* Has the node been initialised for fast searching, if necessary? */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - /* Ideally the pattern should immutable and shareable across threads. - * Internally, however, it isn't. For safety we need to hold the GIL. - */ - acquire_GIL(safe_state); - - /* Double-check because of multithreading. */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - build_fast_tables(state->encoding, node, FALSE); - node->status |= RE_STATUS_FAST_INIT; - } - - release_GIL(safe_state); - } - - if (node->string.bad_character_offset) { - /* Start with a fast search. This will find the string if it's complete - * (i.e. not truncated). - */ - found_pos = fast_string_search(state, node, text_pos, limit); - if (found_pos < 0 && state->partial_side == RE_PARTIAL_RIGHT) - /* We didn't find the string, but it could've been truncated, so - * try again, starting close to the end. - */ - found_pos = simple_string_search(state, node, limit - - (Py_ssize_t)(node->value_count - 1), limit, is_partial); - } else - found_pos = simple_string_search(state, node, text_pos, limit, - is_partial); - - return found_pos; -} - -/* Performs a string search, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search_fld(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, Py_ssize_t* new_pos, - BOOL* is_partial) { - RE_State* state; - RE_EncodingTable* encoding; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - void* text; - RE_CODE* values; - Py_ssize_t start_pos; - int f_pos; - int folded_len; - Py_ssize_t length; - Py_ssize_t s_pos; - Py_UCS4 folded[RE_MAX_FOLDED]; - - state = safe_state->re_state; - encoding = state->encoding; - full_case_fold = encoding->full_case_fold; - char_at = state->char_at; - text = state->text; - - values = node->values; - start_pos = text_pos; - f_pos = 0; - folded_len = 0; - length = (Py_ssize_t)node->value_count; - s_pos = 0; - - *is_partial = FALSE; - - while (s_pos < length || f_pos < folded_len) { - if (f_pos >= folded_len) { - /* Fetch and casefold another character. */ - if (text_pos >= limit) { - if (text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) { - *is_partial = TRUE; - return start_pos; - } - - return -1; - } - - folded_len = full_case_fold(char_at(text, text_pos), folded); - f_pos = 0; - } - - if (same_char_ign(encoding, values[s_pos], folded[f_pos])) { - ++s_pos; - ++f_pos; - - if (f_pos >= folded_len) - ++text_pos; - } else { - ++start_pos; - text_pos = start_pos; - f_pos = 0; - folded_len = 0; - s_pos = 0; - } - } - - /* We found the string. */ - if (new_pos) - *new_pos = text_pos; - - return start_pos; -} - -/* Performs a string search, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search_fld_rev(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, Py_ssize_t* new_pos, - BOOL* is_partial) { - RE_State* state; - RE_EncodingTable* encoding; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - void* text; - RE_CODE* values; - Py_ssize_t start_pos; - int f_pos; - int folded_len; - Py_ssize_t length; - Py_ssize_t s_pos; - Py_UCS4 folded[RE_MAX_FOLDED]; - - state = safe_state->re_state; - encoding = state->encoding; - full_case_fold = encoding->full_case_fold; - char_at = state->char_at; - text = state->text; - - values = node->values; - start_pos = text_pos; - f_pos = 0; - folded_len = 0; - length = (Py_ssize_t)node->value_count; - s_pos = 0; - - *is_partial = FALSE; - - while (s_pos < length || f_pos < folded_len) { - if (f_pos >= folded_len) { - /* Fetch and casefold another character. */ - if (text_pos <= limit) { - if (text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) { - *is_partial = TRUE; - return start_pos; - } - - return -1; - } - - folded_len = full_case_fold(char_at(text, text_pos - 1), folded); - f_pos = 0; - } - - if (same_char_ign(encoding, values[length - s_pos - 1], - folded[folded_len - f_pos - 1])) { - ++s_pos; - ++f_pos; - - if (f_pos >= folded_len) - --text_pos; - } else { - --start_pos; - text_pos = start_pos; - f_pos = 0; - folded_len = 0; - s_pos = 0; - } - } - - /* We found the string. */ - if (new_pos) - *new_pos = text_pos; - - return start_pos; -} - -/* Performs a string search, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search_ign(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - RE_State* state; - Py_ssize_t found_pos; - - state = safe_state->re_state; - - *is_partial = FALSE; - - /* Has the node been initialised for fast searching, if necessary? */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - /* Ideally the pattern should immutable and shareable across threads. - * Internally, however, it isn't. For safety we need to hold the GIL. - */ - acquire_GIL(safe_state); - - /* Double-check because of multithreading. */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - build_fast_tables(state->encoding, node, TRUE); - node->status |= RE_STATUS_FAST_INIT; - } - - release_GIL(safe_state); - } - - if (node->string.bad_character_offset) { - /* Start with a fast search. This will find the string if it's complete - * (i.e. not truncated). - */ - found_pos = fast_string_search_ign(state, node, text_pos, limit); - if (found_pos < 0 && state->partial_side == RE_PARTIAL_RIGHT) - /* We didn't find the string, but it could've been truncated, so - * try again, starting close to the end. - */ - found_pos = simple_string_search_ign(state, node, limit - - (Py_ssize_t)(node->value_count - 1), limit, is_partial); - } else - found_pos = simple_string_search_ign(state, node, text_pos, limit, - is_partial); - - return found_pos; -} - -/* Performs a string search, backwards, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search_ign_rev(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - RE_State* state; - Py_ssize_t found_pos; - - state = safe_state->re_state; - - *is_partial = FALSE; - - /* Has the node been initialised for fast searching, if necessary? */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - /* Ideally the pattern should immutable and shareable across threads. - * Internally, however, it isn't. For safety we need to hold the GIL. - */ - acquire_GIL(safe_state); - - /* Double-check because of multithreading. */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - build_fast_tables_rev(state->encoding, node, TRUE); - node->status |= RE_STATUS_FAST_INIT; - } - - release_GIL(safe_state); - } - - if (node->string.bad_character_offset) { - /* Start with a fast search. This will find the string if it's complete - * (i.e. not truncated). - */ - found_pos = fast_string_search_ign_rev(state, node, text_pos, limit); - if (found_pos < 0 && state->partial_side == RE_PARTIAL_LEFT) - /* We didn't find the string, but it could've been truncated, so - * try again, starting close to the end. - */ - found_pos = simple_string_search_ign_rev(state, node, limit + - (Py_ssize_t)(node->value_count - 1), limit, is_partial); - } else - found_pos = simple_string_search_ign_rev(state, node, text_pos, limit, - is_partial); - - return found_pos; -} - -/* Performs a string search, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) string_search_rev(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t limit, BOOL* is_partial) { - RE_State* state; - Py_ssize_t found_pos; - - state = safe_state->re_state; - - *is_partial = FALSE; - - /* Has the node been initialised for fast searching, if necessary? */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - /* Ideally the pattern should immutable and shareable across threads. - * Internally, however, it isn't. For safety we need to hold the GIL. - */ - acquire_GIL(safe_state); - - /* Double-check because of multithreading. */ - if (!(node->status & RE_STATUS_FAST_INIT)) { - build_fast_tables_rev(state->encoding, node, FALSE); - node->status |= RE_STATUS_FAST_INIT; - } - - release_GIL(safe_state); - } - - if (node->string.bad_character_offset) { - /* Start with a fast search. This will find the string if it's complete - * (i.e. not truncated). - */ - found_pos = fast_string_search_rev(state, node, text_pos, limit); - if (found_pos < 0 && state->partial_side == RE_PARTIAL_LEFT) - /* We didn't find the string, but it could've been truncated, so - * try again, starting close to the end. - */ - found_pos = simple_string_search_rev(state, node, limit + - (Py_ssize_t)(node->value_count - 1), limit, is_partial); - } else - found_pos = simple_string_search_rev(state, node, text_pos, limit, - is_partial); - - return found_pos; -} - -/* Returns how many characters there could be before full case-folding. */ -Py_LOCAL_INLINE(Py_ssize_t) possible_unfolded_length(Py_ssize_t length) { - if (length == 0) - return 0; - - if (length < RE_MAX_FOLDED) - return 1; - - return length / RE_MAX_FOLDED; -} - -/* Checks whether there's any character except a newline at a position. */ -Py_LOCAL_INLINE(int) try_match_ANY(RE_State* state, RE_Node* node, Py_ssize_t - text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_ANY(state->encoding, node, state->char_at(state->text, - text_pos))); -} - -/* Checks whether there's any character at all at a position. */ -Py_LOCAL_INLINE(int) try_match_ANY_ALL(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end); -} - -/* Checks whether there's any character at all at a position, backwards. */ -Py_LOCAL_INLINE(int) try_match_ANY_ALL_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start); -} - -/* Checks whether there's any character except a newline at a position, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_ANY_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_ANY(state->encoding, node, state->char_at(state->text, text_pos - - 1))); -} - -/* Checks whether there's any character except a line separator at a position. - */ -Py_LOCAL_INLINE(int) try_match_ANY_U(RE_State* state, RE_Node* node, Py_ssize_t - text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_ANY_U(state->encoding, node, state->char_at(state->text, - text_pos))); -} - -/* Checks whether there's any character except a line separator at a position, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_ANY_U_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_ANY_U(state->encoding, node, state->char_at(state->text, text_pos - - 1))); -} - -/* Checks whether a position is on a word boundary. */ -Py_LOCAL_INLINE(int) try_match_BOUNDARY(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_boundary(state, text_pos) == - node->match); -} - -/* Checks whether there's a character at a position. */ -Py_LOCAL_INLINE(int) try_match_CHARACTER(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_CHARACTER(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character at a position, ignoring case. */ -Py_LOCAL_INLINE(int) try_match_CHARACTER_IGN(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_CHARACTER_IGN(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character at a position, ignoring case, backwards. - */ -Py_LOCAL_INLINE(int) try_match_CHARACTER_IGN_REV(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_CHARACTER_IGN(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether there's a character at a position, backwards. */ -Py_LOCAL_INLINE(int) try_match_CHARACTER_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_CHARACTER(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether a position is on a default word boundary. */ -Py_LOCAL_INLINE(int) try_match_DEFAULT_BOUNDARY(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_default_boundary(state, text_pos) - == node->match); -} - -/* Checks whether a position is at the default end of a word. */ -Py_LOCAL_INLINE(int) try_match_DEFAULT_END_OF_WORD(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_default_word_end(state, - text_pos)); -} - -/* Checks whether a position is at the default start of a word. */ -Py_LOCAL_INLINE(int) try_match_DEFAULT_START_OF_WORD(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_default_word_start(state, - text_pos)); -} - -/* Checks whether a position is at the end of a line. */ -Py_LOCAL_INLINE(int) try_match_END_OF_LINE(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(text_pos >= state->slice_end || - state->char_at(state->text, text_pos) == '\n'); -} - -/* Checks whether a position is at the end of a line. */ -Py_LOCAL_INLINE(int) try_match_END_OF_LINE_U(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_line_end(state, text_pos)); -} - -/* Checks whether a position is at the end of the string. */ -Py_LOCAL_INLINE(int) try_match_END_OF_STRING(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(text_pos >= state->text_length); -} - -/* Checks whether a position is at the end of a line or the string. */ -Py_LOCAL_INLINE(int) try_match_END_OF_STRING_LINE(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - return bool_as_status(text_pos >= state->text_length || text_pos == - state->final_newline); -} - -/* Checks whether a position is at the end of the string. */ -Py_LOCAL_INLINE(int) try_match_END_OF_STRING_LINE_U(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - return bool_as_status(text_pos >= state->text_length || text_pos == - state->final_line_sep); -} - -/* Checks whether a position is at the end of a word. */ -Py_LOCAL_INLINE(int) try_match_END_OF_WORD(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_word_end(state, text_pos)); -} - -/* Checks whether a position is on a grapheme boundary. */ -Py_LOCAL_INLINE(int) try_match_GRAPHEME_BOUNDARY(RE_State* state, RE_Node* - node, Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_grapheme_boundary(state, - text_pos)); -} - -/* Checks whether there's a character with a certain property at a position. */ -Py_LOCAL_INLINE(int) try_match_PROPERTY(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_PROPERTY(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character with a certain property at a position, - * ignoring case. - */ -Py_LOCAL_INLINE(int) try_match_PROPERTY_IGN(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_PROPERTY_IGN(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character with a certain property at a position, - * ignoring case, backwards. - */ -Py_LOCAL_INLINE(int) try_match_PROPERTY_IGN_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_PROPERTY_IGN(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether there's a character with a certain property at a position, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_PROPERTY_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_PROPERTY(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether there's a character in a certain range at a position. */ -Py_LOCAL_INLINE(int) try_match_RANGE(RE_State* state, RE_Node* node, Py_ssize_t - text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_RANGE(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character in a certain range at a position, - * ignoring case. - */ -Py_LOCAL_INLINE(int) try_match_RANGE_IGN(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_RANGE_IGN(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character in a certain range at a position, - * ignoring case, backwards. - */ -Py_LOCAL_INLINE(int) try_match_RANGE_IGN_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_RANGE_IGN(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether there's a character in a certain range at a position, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_RANGE_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_RANGE(state->encoding, node, state->char_at(state->text, text_pos - - 1)) == node->match); -} - -/* Checks whether a position is at the search anchor. */ -Py_LOCAL_INLINE(int) try_match_SEARCH_ANCHOR(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(text_pos == state->search_anchor); -} - -/* Checks whether there's a character in a certain set at a position. */ -Py_LOCAL_INLINE(int) try_match_SET(RE_State* state, RE_Node* node, Py_ssize_t - text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_SET(state->encoding, node, state->char_at(state->text, text_pos)) - == node->match); -} - -/* Checks whether there's a character in a certain set at a position, ignoring - * case. - */ -Py_LOCAL_INLINE(int) try_match_SET_IGN(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos < state->slice_end && - matches_SET_IGN(state->encoding, node, state->char_at(state->text, - text_pos)) == node->match); -} - -/* Checks whether there's a character in a certain set at a position, ignoring - * case, backwards. - */ -Py_LOCAL_INLINE(int) try_match_SET_IGN_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_SET_IGN(state->encoding, node, state->char_at(state->text, - text_pos - 1)) == node->match); -} - -/* Checks whether there's a character in a certain set at a position, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_SET_REV(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - if (text_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - return bool_as_status(text_pos > state->slice_start && - matches_SET(state->encoding, node, state->char_at(state->text, text_pos - - 1)) == node->match); -} - -/* Checks whether a position is at the start of a line. */ -Py_LOCAL_INLINE(int) try_match_START_OF_LINE(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(text_pos <= 0 || state->char_at(state->text, text_pos - - 1) == '\n'); -} - -/* Checks whether a position is at the start of a line. */ -Py_LOCAL_INLINE(int) try_match_START_OF_LINE_U(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_line_start(state, text_pos)); -} - -/* Checks whether a position is at the start of the string. */ -Py_LOCAL_INLINE(int) try_match_START_OF_STRING(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(text_pos <= 0); -} - -/* Checks whether a position is at the start of a word. */ -Py_LOCAL_INLINE(int) try_match_START_OF_WORD(RE_State* state, RE_Node* node, - Py_ssize_t text_pos) { - return bool_as_status(state->encoding->at_word_start(state, text_pos)); -} - -/* Checks whether there's a certain string at a position. */ -Py_LOCAL_INLINE(int) try_match_STRING(RE_State* state, RE_NextNode* next, - RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - RE_CODE* values; - Py_ssize_t s_pos; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - values = node->values; - - for (s_pos = 0; s_pos < length; s_pos++) { - if (text_pos + s_pos >= state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - if (!same_char(encoding, char_at(state->text, text_pos + s_pos), - values[s_pos])) - return RE_ERROR_FAILURE; - } - - next_position->node = next->match_next; - next_position->text_pos = text_pos + next->match_step; - - return RE_ERROR_SUCCESS; -} - -/* Checks whether there's a certain string at a position, ignoring case. */ -Py_LOCAL_INLINE(int) try_match_STRING_FLD(RE_State* state, RE_NextNode* next, - RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_ssize_t s_pos; - RE_CODE* values; - int folded_len; - int f_pos; - Py_ssize_t start_pos; - Py_UCS4 folded[RE_MAX_FOLDED]; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - full_case_fold = encoding->full_case_fold; - - s_pos = 0; - values = node->values; - folded_len = 0; - f_pos = 0; - start_pos = text_pos; - - while (s_pos < length) { - if (f_pos >= folded_len) { - /* Fetch and casefold another character. */ - if (text_pos >= state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - folded_len = full_case_fold(char_at(state->text, text_pos), - folded); - f_pos = 0; - } - - if (!same_char_ign(encoding, folded[f_pos], values[s_pos])) - return RE_ERROR_FAILURE; - - ++s_pos; - ++f_pos; - - if (f_pos >= folded_len) - ++text_pos; - } - - if (f_pos < folded_len) - return RE_ERROR_FAILURE; - - next_position->node = next->match_next; - if (next->match_step == 0) - next_position->text_pos = start_pos; - else - next_position->text_pos = text_pos; - - return RE_ERROR_SUCCESS; -} - -/* Checks whether there's a certain string at a position, ignoring case, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_STRING_FLD_REV(RE_State* state, RE_NextNode* - next, RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_ssize_t s_pos; - RE_CODE* values; - int folded_len; - int f_pos; - Py_ssize_t start_pos; - Py_UCS4 folded[RE_MAX_FOLDED]; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - full_case_fold = encoding->full_case_fold; - - s_pos = 0; - values = node->values; - folded_len = 0; - f_pos = 0; - start_pos = text_pos; - - while (s_pos < length) { - if (f_pos >= folded_len) { - /* Fetch and casefold another character. */ - if (text_pos <= state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - folded_len = full_case_fold(char_at(state->text, text_pos - 1), - folded); - f_pos = 0; - } - - if (!same_char_ign(encoding, folded[folded_len - f_pos - 1], - values[length - s_pos - 1])) - return RE_ERROR_FAILURE; - - ++s_pos; - ++f_pos; - - if (f_pos >= folded_len) - --text_pos; - } - - if (f_pos < folded_len) - return RE_ERROR_FAILURE; - - next_position->node = next->match_next; - if (next->match_step == 0) - next_position->text_pos = start_pos; - else - next_position->text_pos = text_pos; - - return RE_ERROR_SUCCESS; -} - -/* Checks whether there's a certain string at a position, ignoring case. */ -Py_LOCAL_INLINE(int) try_match_STRING_IGN(RE_State* state, RE_NextNode* next, - RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - RE_CODE* values; - Py_ssize_t s_pos; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - values = node->values; - - for (s_pos = 0; s_pos < length; s_pos++) { - if (text_pos + s_pos >= state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - if (!same_char_ign(encoding, char_at(state->text, text_pos + s_pos), - values[s_pos])) - return RE_ERROR_FAILURE; - } - - next_position->node = next->match_next; - next_position->text_pos = text_pos + next->match_step; - - return RE_ERROR_SUCCESS; -} - -/* Checks whether there's a certain string at a position, ignoring case, - * backwards. - */ -Py_LOCAL_INLINE(int) try_match_STRING_IGN_REV(RE_State* state, RE_NextNode* - next, RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - RE_CODE* values; - Py_ssize_t s_pos; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - values = node->values; - - for (s_pos = 0; s_pos < length; s_pos++) { - if (text_pos - s_pos <= state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - if (!same_char_ign(encoding, char_at(state->text, text_pos - s_pos - - 1), values[length - s_pos - 1])) - return RE_ERROR_FAILURE; - } - - next_position->node = next->match_next; - next_position->text_pos = text_pos + next->match_step; - - return RE_ERROR_SUCCESS; -} - -/* Checks whether there's a certain string at a position, backwards. */ -Py_LOCAL_INLINE(int) try_match_STRING_REV(RE_State* state, RE_NextNode* next, - RE_Node* node, Py_ssize_t text_pos, RE_Position* next_position) { - Py_ssize_t length; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - RE_EncodingTable* encoding; - RE_CODE* values; - Py_ssize_t s_pos; - - length = (Py_ssize_t)node->value_count; - char_at = state->char_at; - encoding = state->encoding; - values = node->values; - - for (s_pos = 0; s_pos < length; s_pos++) { - if (text_pos - s_pos <= state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - - if (!same_char(encoding, char_at(state->text, text_pos - s_pos - 1), - values[length - s_pos - 1])) - return RE_ERROR_FAILURE; - } - - next_position->node = next->match_next; - next_position->text_pos = text_pos + next->match_step; - - return RE_ERROR_SUCCESS; -} - -/* Tries a match at the current text position. - * - * Returns the next node and text position if the match succeeds. - */ -Py_LOCAL_INLINE(int) try_match(RE_State* state, RE_NextNode* next, Py_ssize_t - text_pos, RE_Position* next_position) { - RE_Node* test; - int status; - - test = next->test; - - if (test->status & RE_STATUS_FUZZY) { - next_position->node = next->node; - next_position->text_pos = text_pos; - return RE_ERROR_SUCCESS; - } - - switch (test->op) { - case RE_OP_ANY: - status = try_match_ANY(state, test, text_pos); - break; - case RE_OP_ANY_ALL: - status = try_match_ANY_ALL(state, test, text_pos); - break; - case RE_OP_ANY_ALL_REV: - status = try_match_ANY_ALL_REV(state, test, text_pos); - break; - case RE_OP_ANY_REV: - status = try_match_ANY_REV(state, test, text_pos); - break; - case RE_OP_ANY_U: - status = try_match_ANY_U(state, test, text_pos); - break; - case RE_OP_ANY_U_REV: - status = try_match_ANY_U_REV(state, test, text_pos); - break; - case RE_OP_BOUNDARY: - status = try_match_BOUNDARY(state, test, text_pos); - break; - case RE_OP_BRANCH: - status = try_match(state, &test->next_1, text_pos, next_position); - if (status == RE_ERROR_FAILURE) - status = try_match(state, &test->nonstring.next_2, text_pos, - next_position); - break; - case RE_OP_CHARACTER: - status = try_match_CHARACTER(state, test, text_pos); - break; - case RE_OP_CHARACTER_IGN: - status = try_match_CHARACTER_IGN(state, test, text_pos); - break; - case RE_OP_CHARACTER_IGN_REV: - status = try_match_CHARACTER_IGN_REV(state, test, text_pos); - break; - case RE_OP_CHARACTER_REV: - status = try_match_CHARACTER_REV(state, test, text_pos); - break; - case RE_OP_DEFAULT_BOUNDARY: - status = try_match_DEFAULT_BOUNDARY(state, test, text_pos); - break; - case RE_OP_DEFAULT_END_OF_WORD: - status = try_match_DEFAULT_END_OF_WORD(state, test, text_pos); - break; - case RE_OP_DEFAULT_START_OF_WORD: - status = try_match_DEFAULT_START_OF_WORD(state, test, text_pos); - break; - case RE_OP_END_OF_LINE: - status = try_match_END_OF_LINE(state, test, text_pos); - break; - case RE_OP_END_OF_LINE_U: - status = try_match_END_OF_LINE_U(state, test, text_pos); - break; - case RE_OP_END_OF_STRING: - status = try_match_END_OF_STRING(state, test, text_pos); - break; - case RE_OP_END_OF_STRING_LINE: - status = try_match_END_OF_STRING_LINE(state, test, text_pos); - break; - case RE_OP_END_OF_STRING_LINE_U: - status = try_match_END_OF_STRING_LINE_U(state, test, text_pos); - break; - case RE_OP_END_OF_WORD: - status = try_match_END_OF_WORD(state, test, text_pos); - break; - case RE_OP_GRAPHEME_BOUNDARY: - status = try_match_GRAPHEME_BOUNDARY(state, test, text_pos); - break; - case RE_OP_PROPERTY: - status = try_match_PROPERTY(state, test, text_pos); - break; - case RE_OP_PROPERTY_IGN: - status = try_match_PROPERTY_IGN(state, test, text_pos); - break; - case RE_OP_PROPERTY_IGN_REV: - status = try_match_PROPERTY_IGN_REV(state, test, text_pos); - break; - case RE_OP_PROPERTY_REV: - status = try_match_PROPERTY_REV(state, test, text_pos); - break; - case RE_OP_RANGE: - status = try_match_RANGE(state, test, text_pos); - break; - case RE_OP_RANGE_IGN: - status = try_match_RANGE_IGN(state, test, text_pos); - break; - case RE_OP_RANGE_IGN_REV: - status = try_match_RANGE_IGN_REV(state, test, text_pos); - break; - case RE_OP_RANGE_REV: - status = try_match_RANGE_REV(state, test, text_pos); - break; - case RE_OP_SEARCH_ANCHOR: - status = try_match_SEARCH_ANCHOR(state, test, text_pos); - break; - case RE_OP_SET_DIFF: - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - status = try_match_SET(state, test, text_pos); - break; - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION_IGN: - status = try_match_SET_IGN(state, test, text_pos); - break; - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_UNION_IGN_REV: - status = try_match_SET_IGN_REV(state, test, text_pos); - break; - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_REV: - status = try_match_SET_REV(state, test, text_pos); - break; - case RE_OP_START_OF_LINE: - status = try_match_START_OF_LINE(state, test, text_pos); - break; - case RE_OP_START_OF_LINE_U: - status = try_match_START_OF_LINE_U(state, test, text_pos); - break; - case RE_OP_START_OF_STRING: - status = try_match_START_OF_STRING(state, test, text_pos); - break; - case RE_OP_START_OF_WORD: - status = try_match_START_OF_WORD(state, test, text_pos); - break; - case RE_OP_STRING: - return try_match_STRING(state, next, test, text_pos, next_position); - case RE_OP_STRING_FLD: - return try_match_STRING_FLD(state, next, test, text_pos, - next_position); - case RE_OP_STRING_FLD_REV: - return try_match_STRING_FLD_REV(state, next, test, text_pos, - next_position); - case RE_OP_STRING_IGN: - return try_match_STRING_IGN(state, next, test, text_pos, - next_position); - case RE_OP_STRING_IGN_REV: - return try_match_STRING_IGN_REV(state, next, test, text_pos, - next_position); - case RE_OP_STRING_REV: - return try_match_STRING_REV(state, next, test, text_pos, - next_position); - default: - next_position->node = next->node; - next_position->text_pos = text_pos; - return RE_ERROR_SUCCESS; - } - - if (status != RE_ERROR_SUCCESS) - return status; - - next_position->node = next->match_next; - next_position->text_pos = text_pos + next->match_step; - - return RE_ERROR_SUCCESS; -} - -/* Searches for a word boundary. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_BOUNDARY(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_boundary = state->encoding->at_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for a word boundary, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_BOUNDARY_rev(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_boundary = state->encoding->at_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for a default word boundary. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_BOUNDARY(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_default_boundary = state->encoding->at_default_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_default_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for a default word boundary, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_BOUNDARY_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_default_boundary = state->encoding->at_default_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_default_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the default end of a word. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_END_OF_WORD(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_word_end)(RE_State* state, Py_ssize_t text_pos); - - at_default_word_end = state->encoding->at_default_word_end; - - *is_partial = FALSE; - - for (;;) { - if (at_default_word_end(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the default end of a word, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_END_OF_WORD_rev(RE_State* - state, RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_word_end)(RE_State* state, Py_ssize_t text_pos); - - at_default_word_end = state->encoding->at_default_word_end; - - *is_partial = FALSE; - - for (;;) { - if (at_default_word_end(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the default start of a word. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_START_OF_WORD(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_word_start)(RE_State* state, Py_ssize_t text_pos); - - at_default_word_start = state->encoding->at_default_word_start; - - *is_partial = FALSE; - - for (;;) { - if (at_default_word_start(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the default start of a word, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_DEFAULT_START_OF_WORD_rev(RE_State* - state, RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_default_word_start)(RE_State* state, Py_ssize_t text_pos); - - at_default_word_start = state->encoding->at_default_word_start; - - *is_partial = FALSE; - - for (;;) { - if (at_default_word_start(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the end of line. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_LINE(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - for (;;) { - if (text_pos >= state->text_length || state->char_at(state->text, - text_pos) == '\n') - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the end of line, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_LINE_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - for (;;) { - if (text_pos >= state->text_length || state->char_at(state->text, - text_pos) == '\n') - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the end of the string. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_STRING(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (state->slice_end >= state->text_length) - return state->text_length; - - return -1; -} - -/* Searches for the end of the string, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_STRING_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (text_pos >= state->text_length) - return text_pos; - - return -1; -} - -/* Searches for the end of the string or line. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_STRING_LINE(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (text_pos <= state->final_newline) - text_pos = state->final_newline; - else if (text_pos <= state->text_length) - text_pos = state->text_length; - - if (text_pos > state->slice_end) - return -1; - - if (text_pos >= state->text_length) - return text_pos; - - return text_pos; -} - -/* Searches for the end of the string or line, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_STRING_LINE_rev(RE_State* - state, RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (text_pos >= state->text_length) - text_pos = state->text_length; - else if (text_pos >= state->final_newline) - text_pos = state->final_newline; - else - return -1; - - if (text_pos < state->slice_start) - return -1; - - if (text_pos <= 0) - return text_pos; - - return text_pos; -} - -/* Searches for the end of a word. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_WORD(RE_State* state, RE_Node* - node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_word_end)(RE_State* state, Py_ssize_t text_pos); - - at_word_end = state->encoding->at_word_end; - - *is_partial = FALSE; - - for (;;) { - if (at_word_end(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the end of a word, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_END_OF_WORD_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_word_end)(RE_State* state, Py_ssize_t text_pos); - - at_word_end = state->encoding->at_word_end; - - *is_partial = FALSE; - - for (;;) { - if (at_word_end(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for a grapheme boundary. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_GRAPHEME_BOUNDARY(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_grapheme_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_grapheme_boundary = state->encoding->at_grapheme_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_grapheme_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for a grapheme boundary, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_GRAPHEME_BOUNDARY_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_grapheme_boundary)(RE_State* state, Py_ssize_t text_pos); - - at_grapheme_boundary = state->encoding->at_grapheme_boundary; - - *is_partial = FALSE; - - for (;;) { - if (at_grapheme_boundary(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the start of line. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_LINE(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - for (;;) { - if (text_pos <= 0 || state->char_at(state->text, text_pos - 1) == '\n') - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the start of line, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_LINE_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - for (;;) { - if (text_pos <= 0 || state->char_at(state->text, text_pos - 1) == '\n') - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for the start of the string. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_STRING(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (text_pos <= 0) - return text_pos; - - return -1; -} - -/* Searches for the start of the string, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_STRING_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - *is_partial = FALSE; - - if (state->slice_start <= 0) - return 0; - - return -1; -} - -/* Searches for the start of a word. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_WORD(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_word_start)(RE_State* state, Py_ssize_t text_pos); - - at_word_start = state->encoding->at_word_start; - - *is_partial = FALSE; - - for (;;) { - if (at_word_start(state, text_pos) == node->match) - return text_pos; - - if (text_pos >= state->slice_end) - return -1; - - ++text_pos; - } -} - -/* Searches for the start of a word, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_START_OF_WORD_rev(RE_State* state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - BOOL (*at_word_start)(RE_State* state, Py_ssize_t text_pos); - - at_word_start = state->encoding->at_word_start; - - *is_partial = FALSE; - - for (;;) { - if (at_word_start(state, text_pos) == node->match) - return text_pos; - - if (text_pos <= state->slice_start) - return -1; - - --text_pos; - } -} - -/* Searches for a string. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) - return text_pos; - - return string_search(safe_state, node, text_pos, state->slice_end, - is_partial); -} - -/* Searches for a string, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING_FLD(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, Py_ssize_t* new_pos, BOOL* is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) { - *new_pos = state->req_end; - return text_pos; - } - - return string_search_fld(safe_state, node, text_pos, state->slice_end, - new_pos, is_partial); -} - -/* Searches for a string, ignoring case, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING_FLD_REV(RE_SafeState* - safe_state, RE_Node* node, Py_ssize_t text_pos, Py_ssize_t* new_pos, BOOL* - is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) { - *new_pos = state->req_end; - return text_pos; - } - - return string_search_fld_rev(safe_state, node, text_pos, - state->slice_start, new_pos, is_partial); -} - -/* Searches for a string, ignoring case. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING_IGN(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) - return text_pos; - - return string_search_ign(safe_state, node, text_pos, state->slice_end, - is_partial); -} - -/* Searches for a string, ignoring case, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING_IGN_REV(RE_SafeState* - safe_state, RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) - return text_pos; - - return string_search_ign_rev(safe_state, node, text_pos, - state->slice_start, is_partial); -} - -/* Searches for a string, backwards. */ -Py_LOCAL_INLINE(Py_ssize_t) search_start_STRING_REV(RE_SafeState* safe_state, - RE_Node* node, Py_ssize_t text_pos, BOOL* is_partial) { - RE_State* state; - - state = safe_state->re_state; - - *is_partial = FALSE; - - if ((node->status & RE_STATUS_REQUIRED) && text_pos == state->req_pos) - return text_pos; - - return string_search_rev(safe_state, node, text_pos, state->slice_start, - is_partial); -} - -/* Searches for the start of a match. */ -Py_LOCAL_INLINE(int) search_start(RE_SafeState* safe_state, RE_NextNode* next, - RE_Position* new_position, int search_index) { - RE_State* state; - Py_ssize_t text_pos; - RE_Node* test; - RE_Node* node; - Py_ssize_t start_pos; - RE_SearchPosition* info; - - state = safe_state->re_state; - - start_pos = state->text_pos; - TRACE(("<> at %d\n", start_pos)) - - test = next->test; - node = next->node; - - if (state->reverse) { - if (start_pos < state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = state->slice_start; - return RE_ERROR_PARTIAL; - } - - return RE_ERROR_FAILURE; - } - } else { - if (start_pos > state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = state->slice_end; - return RE_ERROR_PARTIAL; - } - } - } - - if (test->status & RE_STATUS_FUZZY) { - /* Don't call 'search_start' again. */ - state->pattern->do_search_start = FALSE; - - state->match_pos = start_pos; - new_position->node = node; - new_position->text_pos = start_pos; - - return RE_ERROR_SUCCESS; - } - -again: - if (!state->pattern->is_fuzzy && state->partial_side == RE_PARTIAL_NONE) { - if (state->reverse) { - if (start_pos - state->min_width < state->slice_start) - return RE_ERROR_FAILURE; - } else { - if (start_pos + state->min_width > state->slice_end) - return RE_ERROR_FAILURE; - } - } - - if (search_index < MAX_SEARCH_POSITIONS) { - info = &state->search_positions[search_index]; - if (state->reverse) { - if (info->start_pos >= 0 && info->start_pos >= start_pos && - start_pos >= info->match_pos) { - state->match_pos = info->match_pos; - - new_position->text_pos = state->match_pos; - new_position->node = node; - - return RE_ERROR_SUCCESS; - } - } else { - if (info->start_pos >= 0 && info->start_pos <= start_pos && - start_pos <= info->match_pos) { - state->match_pos = info->match_pos; - - new_position->text_pos = state->match_pos; - new_position->node = node; - - return RE_ERROR_SUCCESS; - } - } - } else - info = NULL; - - switch (test->op) { - case RE_OP_ANY: - start_pos = match_many_ANY(state, test, start_pos, state->slice_end, - FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_ANY_ALL: - break; - case RE_OP_ANY_ALL_REV: - break; - case RE_OP_ANY_REV: - start_pos = match_many_ANY_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_ANY_U: - start_pos = match_many_ANY_U(state, test, start_pos, state->slice_end, - FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_ANY_U_REV: - start_pos = match_many_ANY_U_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_BOUNDARY: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_BOUNDARY_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_BOUNDARY(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_CHARACTER: - start_pos = match_many_CHARACTER(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_CHARACTER_IGN: - start_pos = match_many_CHARACTER_IGN(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_CHARACTER_IGN_REV: - start_pos = match_many_CHARACTER_IGN_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_CHARACTER_REV: - start_pos = match_many_CHARACTER_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_DEFAULT_BOUNDARY: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_DEFAULT_BOUNDARY_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_DEFAULT_BOUNDARY(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_DEFAULT_END_OF_WORD: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_DEFAULT_END_OF_WORD_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_DEFAULT_END_OF_WORD(state, test, - start_pos, &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_DEFAULT_START_OF_WORD: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_DEFAULT_START_OF_WORD_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_DEFAULT_START_OF_WORD(state, test, - start_pos, &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_END_OF_LINE: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_END_OF_LINE_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_END_OF_LINE(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_END_OF_STRING: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_END_OF_STRING_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_END_OF_STRING(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_END_OF_STRING_LINE: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_END_OF_STRING_LINE_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_END_OF_STRING_LINE(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_END_OF_WORD: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_END_OF_WORD_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_END_OF_WORD(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_GRAPHEME_BOUNDARY: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_GRAPHEME_BOUNDARY_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_GRAPHEME_BOUNDARY(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_PROPERTY: - start_pos = match_many_PROPERTY(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_PROPERTY_IGN: - start_pos = match_many_PROPERTY_IGN(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_PROPERTY_IGN_REV: - start_pos = match_many_PROPERTY_IGN_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_PROPERTY_REV: - start_pos = match_many_PROPERTY_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_RANGE: - start_pos = match_many_RANGE(state, test, start_pos, state->slice_end, - FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_RANGE_IGN: - start_pos = match_many_RANGE_IGN(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return RE_ERROR_FAILURE; - break; - case RE_OP_RANGE_IGN_REV: - start_pos = match_many_RANGE_IGN_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_RANGE_REV: - start_pos = match_many_RANGE_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return RE_ERROR_FAILURE; - break; - case RE_OP_SEARCH_ANCHOR: - if (state->reverse) { - if (start_pos < state->search_anchor) - return RE_ERROR_FAILURE; - } else { - if (start_pos > state->search_anchor) - return RE_ERROR_FAILURE; - } - - start_pos = state->search_anchor; - break; - case RE_OP_SET_DIFF: - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - start_pos = match_many_SET(state, test, start_pos, state->slice_end, - FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return FALSE; - break; - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION_IGN: - start_pos = match_many_SET_IGN(state, test, start_pos, - state->slice_end, FALSE); - - if (start_pos >= state->text_length) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos >= state->slice_end) - return FALSE; - break; - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_UNION_IGN_REV: - start_pos = match_many_SET_IGN_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return FALSE; - break; - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_REV: - start_pos = match_many_SET_REV(state, test, start_pos, - state->slice_start, FALSE); - - if (start_pos <= 0) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - } - - if (start_pos <= state->slice_start) - return FALSE; - break; - case RE_OP_START_OF_LINE: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_START_OF_LINE_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_START_OF_LINE(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_START_OF_STRING: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_START_OF_STRING_rev(state, test, - start_pos, &is_partial); - else - start_pos = search_start_START_OF_STRING(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_START_OF_WORD: - { - BOOL is_partial; - - if (state->reverse) - start_pos = search_start_START_OF_WORD_rev(state, test, start_pos, - &is_partial); - else - start_pos = search_start_START_OF_WORD(state, test, start_pos, - &is_partial); - - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_STRING: - { - BOOL is_partial; - - start_pos = search_start_STRING(safe_state, test, start_pos, - &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_STRING_FLD: - { - Py_ssize_t new_pos; - BOOL is_partial; - - start_pos = search_start_STRING_FLD(safe_state, test, start_pos, - &new_pos, &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - - /* Can we look further ahead? */ - if (test == node) { - if (test->next_1.node) { - int status; - - status = try_match(state, &test->next_1, new_pos, - new_position); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) { - ++start_pos; - - if (start_pos >= state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = state->slice_start; - return RE_ERROR_PARTIAL; - } - - return RE_ERROR_FAILURE; - } - - goto again; - } - } - - /* It's a possible match. */ - state->match_pos = start_pos; - - if (info) { - info->start_pos = state->text_pos; - info->match_pos = state->match_pos; - } - - return RE_ERROR_SUCCESS; - } - break; - } - case RE_OP_STRING_FLD_REV: - { - Py_ssize_t new_pos; - BOOL is_partial; - - start_pos = search_start_STRING_FLD_REV(safe_state, test, start_pos, - &new_pos, &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - - /* Can we look further ahead? */ - if (test == node) { - if (test->next_1.node) { - int status; - - status = try_match(state, &test->next_1, new_pos, - new_position); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) { - --start_pos; - - if (start_pos <= state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = state->slice_start; - return RE_ERROR_PARTIAL; - } - - return RE_ERROR_FAILURE; - } - - goto again; - } - } - - /* It's a possible match. */ - state->match_pos = start_pos; - - if (info) { - info->start_pos = state->text_pos; - info->match_pos = state->match_pos; - } - - return RE_ERROR_SUCCESS; - } - break; - } - case RE_OP_STRING_IGN: - { - BOOL is_partial; - - start_pos = search_start_STRING_IGN(safe_state, test, start_pos, - &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_STRING_IGN_REV: - { - BOOL is_partial; - - start_pos = search_start_STRING_IGN_REV(safe_state, test, start_pos, - &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - case RE_OP_STRING_REV: - { - BOOL is_partial; - - start_pos = search_start_STRING_REV(safe_state, test, start_pos, - &is_partial); - if (start_pos < 0) - return RE_ERROR_FAILURE; - - if (is_partial) { - new_position->text_pos = start_pos; - return RE_ERROR_PARTIAL; - } - break; - } - default: - /* Don't call 'search_start' again. */ - state->pattern->do_search_start = FALSE; - - state->match_pos = start_pos; - new_position->node = node; - new_position->text_pos = start_pos; - return RE_ERROR_SUCCESS; - } - - /* Can we look further ahead? */ - if (test == node) { - text_pos = start_pos + test->step; - - if (test->next_1.node) { - int status; - - status = try_match(state, &test->next_1, text_pos, new_position); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) { - if (state->reverse) { - --start_pos; - - if (start_pos < state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) { - new_position->text_pos = state->slice_start; - return RE_ERROR_PARTIAL; - } - - return RE_ERROR_FAILURE; - } - } else { - ++start_pos; - - if (start_pos > state->slice_end) { - if (state->partial_side == RE_PARTIAL_RIGHT) { - new_position->text_pos = state->slice_end; - return RE_ERROR_PARTIAL; - } - - return RE_ERROR_FAILURE; - } - } - - goto again; - } - } - } else { - new_position->node = node; - new_position->text_pos = start_pos; - } - - /* It's a possible match. */ - state->match_pos = start_pos; - - if (info) { - info->start_pos = state->text_pos; - info->match_pos = state->match_pos; - } - - return RE_ERROR_SUCCESS; -} - -/* Saves a capture group. */ -Py_LOCAL_INLINE(BOOL) save_capture(RE_SafeState* safe_state, size_t - private_index, size_t public_index) { - RE_State* state; - RE_GroupData* private_group; - RE_GroupData* public_group; - - state = safe_state->re_state; - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - private_group = &state->groups[private_index - 1]; - public_group = &state->groups[public_index - 1]; - - /* Will the repeated captures ever be visible? */ - if (!state->visible_captures) { - public_group->captures[0] = private_group->span; - public_group->capture_count = 1; - - return TRUE; - } - - if (public_group->capture_count >= public_group->capture_capacity) { - size_t new_capacity; - RE_GroupSpan* new_captures; - - new_capacity = public_group->capture_capacity * 2; - new_capacity = max_size_t(new_capacity, RE_INIT_CAPTURE_SIZE); - new_captures = (RE_GroupSpan*)safe_realloc(safe_state, - public_group->captures, new_capacity * sizeof(RE_GroupSpan)); - if (!new_captures) - return FALSE; - - public_group->captures = new_captures; - public_group->capture_capacity = new_capacity; - } - - public_group->captures[public_group->capture_count++] = - private_group->span; - - return TRUE; -} - -/* Unsaves a capture group. */ -Py_LOCAL_INLINE(void) unsave_capture(RE_State* state, size_t private_index, - size_t public_index) { - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - if (state->groups[public_index - 1].capture_count > 0) - --state->groups[public_index - 1].capture_count; -} - -/* Pushes the groups for backtracking. */ -Py_LOCAL_INLINE(BOOL) push_groups(RE_SafeState* safe_state) { - RE_State* state; - size_t group_count; - RE_SavedGroups* current; - size_t g; - - state = safe_state->re_state; - - group_count = state->pattern->true_group_count; - if (group_count == 0) - return TRUE; - - current = state->current_saved_groups; - - if (current && current->next) - current = current->next; - else if (!current && state->first_saved_groups) - current = state->first_saved_groups; - else { - RE_SavedGroups* new_block; - - new_block = (RE_SavedGroups*)safe_alloc(safe_state, - sizeof(RE_SavedGroups)); - if (!new_block) - return FALSE; - - new_block->spans = (RE_GroupSpan*)safe_alloc(safe_state, group_count * - sizeof(RE_GroupSpan)); - new_block->counts = (size_t*)safe_alloc(safe_state, group_count * - sizeof(Py_ssize_t)); - if (!new_block->spans || !new_block->counts) { - safe_dealloc(safe_state, new_block->spans); - safe_dealloc(safe_state, new_block->counts); - safe_dealloc(safe_state, new_block); - return FALSE; - } - - new_block->previous = current; - new_block->next = NULL; - - if (new_block->previous) - new_block->previous->next = new_block; - else - state->first_saved_groups = new_block; - - current = new_block; - } - - for (g = 0; g < group_count; g++) { - current->spans[g] = state->groups[g].span; - current->counts[g] = state->groups[g].capture_count; - } - - state->current_saved_groups = current; - - return TRUE; -} - -/* Pops the groups for backtracking. */ -Py_LOCAL_INLINE(void) pop_groups(RE_State* state) { - size_t group_count; - RE_SavedGroups* current; - size_t g; - - group_count = state->pattern->true_group_count; - if (group_count == 0) - return; - - current = state->current_saved_groups; - - for (g = 0; g < group_count; g++) { - state->groups[g].span = current->spans[g]; - state->groups[g].capture_count = current->counts[g]; - } - - state->current_saved_groups = current->previous; -} - -/* Drops the groups for backtracking. */ -Py_LOCAL_INLINE(void) drop_groups(RE_State* state) { - if (state->pattern->true_group_count != 0) - state->current_saved_groups = state->current_saved_groups->previous; -} - -/* Pushes the repeats for backtracking. */ -Py_LOCAL_INLINE(BOOL) push_repeats(RE_SafeState* safe_state) { - RE_State* state; - PatternObject* pattern; - size_t repeat_count; - RE_SavedRepeats* current; - size_t r; - - state = safe_state->re_state; - pattern = state->pattern; - - repeat_count = pattern->repeat_count; - if (repeat_count == 0) - return TRUE; - - current = state->current_saved_repeats; - - if (current && current->next) - current = current->next; - else if (!current && state->first_saved_repeats) - current = state->first_saved_repeats; - else { - RE_SavedRepeats* new_block; - - new_block = (RE_SavedRepeats*)safe_alloc(safe_state, - sizeof(RE_SavedRepeats)); - if (!new_block) - return FALSE; - - memset(new_block, 0, sizeof(RE_SavedRepeats)); - - new_block->repeats = (RE_RepeatData*)safe_alloc(safe_state, - repeat_count * sizeof(RE_RepeatData)); - if (!new_block->repeats) { - safe_dealloc(safe_state, new_block); - return FALSE; - } - - memset(new_block->repeats, 0, repeat_count * sizeof(RE_RepeatData)); - - new_block->previous = current; - new_block->next = NULL; - - if (new_block->previous) - new_block->previous->next = new_block; - else - state->first_saved_repeats = new_block; - - current = new_block; - } - - for (r = 0; r < repeat_count; r++) { - if (!copy_repeat_data(safe_state, ¤t->repeats[r], - &state->repeats[r])) - return FALSE; - } - - state->current_saved_repeats = current; - - return TRUE; -} - -/* Pops the repeats for backtracking. */ -Py_LOCAL_INLINE(void) pop_repeats(RE_State* state) { - PatternObject* pattern; - size_t repeat_count; - RE_SavedRepeats* current; - size_t r; - - pattern = state->pattern; - - repeat_count = pattern->repeat_count; - if (repeat_count == 0) - return; - - current = state->current_saved_repeats; - - for (r = 0; r < repeat_count; r++) - copy_repeat_data(NULL, &state->repeats[r], ¤t->repeats[r]); - - state->current_saved_repeats = current->previous; -} - -/* Saves state info before a recusive call by 'basic_match'. */ -Py_LOCAL_INLINE(void) save_info(RE_State* state, RE_Info* info) { - info->backtrack_count = state->current_backtrack_block->count; - info->current_backtrack_block = state->current_backtrack_block; - info->current_saved_groups = state->current_saved_groups; - info->must_advance = state->must_advance; - info->current_group_call_frame = state->current_group_call_frame; -} - -/* Restores state info after a recusive call by 'basic_match'. */ -Py_LOCAL_INLINE(void) restore_info(RE_State* state, RE_Info* info) { - state->current_group_call_frame = info->current_group_call_frame; - state->must_advance = info->must_advance; - state->current_saved_groups = info->current_saved_groups; - state->current_backtrack_block = info->current_backtrack_block; - state->current_backtrack_block->count = info->backtrack_count; -} - -/* Inserts a new span in a guard list. */ -Py_LOCAL_INLINE(BOOL) insert_guard_span(RE_SafeState* safe_state, RE_GuardList* - guard_list, size_t index) { - size_t n; - - if (guard_list->count >= guard_list->capacity) { - size_t new_capacity; - RE_GuardSpan* new_spans; - - new_capacity = guard_list->capacity * 2; - if (new_capacity == 0) - new_capacity = RE_INIT_GUARDS_BLOCK_SIZE; - new_spans = (RE_GuardSpan*)safe_realloc(safe_state, guard_list->spans, - new_capacity * sizeof(RE_GuardSpan)); - if (!new_spans) - return FALSE; - - guard_list->capacity = new_capacity; - guard_list->spans = new_spans; - } - - n = guard_list->count - index; - if (n > 0) - memmove(guard_list->spans + index + 1, guard_list->spans + index, n * - sizeof(RE_GuardSpan)); - ++guard_list->count; - - return TRUE; -} - -/* Deletes a span in a guard list. */ -Py_LOCAL_INLINE(void) delete_guard_span(RE_GuardList* guard_list, size_t index) - { - size_t n; - - n = guard_list->count - index - 1; - if (n > 0) - memmove(guard_list->spans + index, guard_list->spans + index + 1, n * - sizeof(RE_GuardSpan)); - --guard_list->count; -} - -/* Checks whether a position is guarded against further matching. */ -Py_LOCAL_INLINE(BOOL) is_guarded(RE_GuardList* guard_list, Py_ssize_t text_pos) - { - size_t low; - size_t high; - - /* Is this position in the guard list? */ - low = 0; - high = guard_list->count; - while (low < high) { - size_t mid; - RE_GuardSpan* span; - - mid = (low + high) / 2; - span = &guard_list->spans[mid]; - if (text_pos < span->low) - high = mid; - else if (text_pos > span->high) - low = mid + 1; - else - return span->protect; - } - - guard_list->last_text_pos = text_pos; - guard_list->last_low = low; - - return FALSE; -} - -/* Guards a position against further matching. */ -Py_LOCAL_INLINE(BOOL) guard(RE_SafeState* safe_state, RE_GuardList* guard_list, - Py_ssize_t text_pos, BOOL protect) { - size_t low; - size_t high; - - /* Where should be new position be added? */ - if (text_pos == guard_list->last_text_pos) - low = guard_list->last_low; - else { - low = 0; - high = guard_list->count; - while (low < high) { - size_t mid; - RE_GuardSpan* span; - - mid = (low + high) / 2; - span = &guard_list->spans[mid]; - if (text_pos < span->low) - high = mid; - else if (text_pos > span->high) - low = mid + 1; - else - return TRUE; - } - } - - /* Add the position to the guard list. */ - if (low > 0 && guard_list->spans[low - 1].high + 1 == text_pos && - guard_list->spans[low - 1].protect == protect) { - /* The new position is just above this span. */ - if (low < guard_list->count && guard_list->spans[low].low - 1 == - text_pos && guard_list->spans[low].protect == protect) { - /* The new position joins 2 spans */ - guard_list->spans[low - 1].high = guard_list->spans[low].high; - delete_guard_span(guard_list, low); - } else - /* Extend the span. */ - guard_list->spans[low - 1].high = text_pos; - } else if (low < guard_list->count && guard_list->spans[low].low - 1 == - text_pos && guard_list->spans[low].protect == protect) - /* The new position is just below this span. */ - /* Extend the span. */ - guard_list->spans[low].low = text_pos; - else { - /* Insert a new span. */ - if (!insert_guard_span(safe_state, guard_list, low)) - return FALSE; - guard_list->spans[low].low = text_pos; - guard_list->spans[low].high = text_pos; - guard_list->spans[low].protect = protect; - } - - guard_list->last_text_pos = -1; - - return TRUE; -} - -/* Guards a position against further matching for a repeat. */ -Py_LOCAL_INLINE(BOOL) guard_repeat(RE_SafeState* safe_state, size_t index, - Py_ssize_t text_pos, RE_STATUS_T guard_type, BOOL protect) { - RE_State* state; - RE_GuardList* guard_list; - - state = safe_state->re_state; - - /* Is a guard active here? */ - if (!(state->pattern->repeat_info[index].status & guard_type)) - return TRUE; - - /* Which guard list? */ - if (guard_type & RE_STATUS_BODY) - guard_list = &state->repeats[index].body_guard_list; - else - guard_list = &state->repeats[index].tail_guard_list; - - return guard(safe_state, guard_list, text_pos, protect); -} - -/* Checks whether a position is guarded against further matching for a repeat. - */ -Py_LOCAL_INLINE(BOOL) is_repeat_guarded(RE_SafeState* safe_state, size_t index, - Py_ssize_t text_pos, RE_STATUS_T guard_type) { - RE_State* state; - RE_GuardList* guard_list; - - state = safe_state->re_state; - - /* Is a guard active here? */ - if (!(state->pattern->repeat_info[index].status & guard_type)) - return FALSE; - - /* Which guard list? */ - if (guard_type == RE_STATUS_BODY) - guard_list = &state->repeats[index].body_guard_list; - else - guard_list = &state->repeats[index].tail_guard_list; - - return is_guarded(guard_list, text_pos); -} - -/* Resets the guards inside atomic subpatterns and lookarounds. */ -Py_LOCAL_INLINE(void) reset_guards(RE_State* state, RE_CODE* values) { - PatternObject* pattern; - size_t repeat_count; - - pattern = state->pattern; - repeat_count = pattern->repeat_count; - - if (values) { - size_t i; - - for (i = 1; i <= values[0]; i++) { - size_t index; - - index = values[i]; - - if (index < repeat_count) { - reset_guard_list(&state->repeats[index].body_guard_list); - reset_guard_list(&state->repeats[index].tail_guard_list); - } else { - index -= repeat_count; - - reset_guard_list(&state->fuzzy_guards[index].body_guard_list); - reset_guard_list(&state->fuzzy_guards[index].tail_guard_list); - } - } - } else { - size_t index; - size_t fuzzy_count; - - for (index = 0; index < repeat_count; index++) { - reset_guard_list(&state->repeats[index].body_guard_list); - reset_guard_list(&state->repeats[index].tail_guard_list); - } - - fuzzy_count = pattern->fuzzy_count; - - for (index = 0; index < fuzzy_count; index++) { - reset_guard_list(&state->fuzzy_guards[index].body_guard_list); - reset_guard_list(&state->fuzzy_guards[index].tail_guard_list); - } - } -} - -/* Builds a Unicode string. */ -Py_LOCAL_INLINE(PyObject*) build_unicode_value(void* buffer, Py_ssize_t len, - Py_ssize_t buffer_charsize) { - return PyUnicode_FromUnicode(buffer, len); -} - -/* Builds a bytestring. Returns NULL if any member is too wide. */ -Py_LOCAL_INLINE(PyObject*) build_bytes_value(void* buffer, Py_ssize_t len, - Py_ssize_t buffer_charsize) -{ - Py_UCS1* byte_buffer; - Py_ssize_t i; - PyObject* result; - - if (buffer_charsize == 1) - return Py_BuildValue("s#", buffer, len); - - byte_buffer = re_alloc((size_t)len); - if (!byte_buffer) - return NULL; - - for (i = 0; i < len; i++) { - Py_UCS2 c = ((Py_UCS2*)buffer)[i]; - if (c > 0xFF) - goto too_wide; - - byte_buffer[i] = (Py_UCS1)c; - } - - result = Py_BuildValue("s#", byte_buffer, len); - - re_dealloc(byte_buffer); - - return result; - -too_wide: - re_dealloc(byte_buffer); - - return NULL; -} - -/* Looks for a string in a string set. */ -Py_LOCAL_INLINE(int) string_set_contains(RE_State* state, PyObject* string_set, - Py_ssize_t first, Py_ssize_t last) { - PyObject* string; - int status; - - if (state->is_unicode) - string = build_unicode_value(state->point_to(state->text, first), last - - first, state->charsize); - else - string = build_bytes_value(state->point_to(state->text, first), last - - first, state->charsize); - if (!string) - return RE_ERROR_INTERNAL; - - status = PySet_Contains(string_set, string); - Py_DECREF(string); - - return status; -} - -/* Looks for a string in a string set, ignoring case. */ -Py_LOCAL_INLINE(int) string_set_contains_ign(RE_State* state, PyObject* - string_set, void* buffer, Py_ssize_t index, Py_ssize_t len, Py_ssize_t - buffer_charsize) { - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - void (*set_char_at)(void* text, Py_ssize_t pos, Py_UCS4 ch); - RE_EncodingTable* encoding; - BOOL (*possible_turkic)(Py_UCS4 ch); - Py_UCS4 codepoints[4]; - - switch (buffer_charsize) { - case 1: - char_at = bytes1_char_at; - set_char_at = bytes1_set_char_at; - break; - case 2: - char_at = bytes2_char_at; - set_char_at = bytes2_set_char_at; - break; - case 4: - char_at = bytes4_char_at; - set_char_at = bytes4_set_char_at; - break; - default: - char_at = bytes1_char_at; - set_char_at = bytes1_set_char_at; - break; - } - - encoding = state->encoding; - possible_turkic = encoding->possible_turkic; - - /* Look for a possible Turkic 'I'. */ - while (index < len && !possible_turkic(char_at(buffer, index))) - ++index; - - if (index < len) { - /* Possible Turkic 'I'. */ - int count; - int i; - - /* Try all the alternatives to the 'I'. */ - count = encoding->all_turkic_i(char_at(buffer, index), codepoints); - - for (i = 0; i < count; i++) { - int status; - - set_char_at(buffer, index, codepoints[i]); - - /* Recurse for the remainder of the string. */ - status = string_set_contains_ign(state, string_set, buffer, index + - 1, len, buffer_charsize); - if (status != 0) - return status; - } - - return 0; - } else { - /* No Turkic 'I'. */ - PyObject* string; - int status; - - if (state->is_unicode) - string = build_unicode_value(buffer, len, buffer_charsize); - else - string = build_bytes_value(buffer, len, buffer_charsize); - if (!string) - return RE_ERROR_MEMORY; - - status = PySet_Contains(string_set, string); - Py_DECREF(string); - - return status; - } -} - -/* Creates a partial string set for truncation at the left or right side. */ -Py_LOCAL_INLINE(int) make_partial_string_set(RE_State* state, RE_Node* node) { - PatternObject* pattern; - int partial_side; - PyObject* string_set; - PyObject* partial_set; - PyObject* iter = NULL; - PyObject* item = NULL; - PyObject* slice = NULL; - - pattern = state->pattern; - partial_side = state->partial_side; - if (partial_side != RE_PARTIAL_LEFT && partial_side != RE_PARTIAL_RIGHT) - return RE_ERROR_INTERNAL; - - /* Fetch the full string set. PyList_GET_ITEM borrows a reference. */ - string_set = PyList_GET_ITEM(pattern->named_list_indexes, node->values[0]); - if (!string_set) - return RE_ERROR_INTERNAL; - - /* Gets the list of partial string sets. */ - if (!pattern->partial_named_lists[partial_side]) { - size_t size; - - size = pattern->named_lists_count * sizeof(PyObject*); - pattern->partial_named_lists[partial_side] = re_alloc(size); - if (!pattern->partial_named_lists[partial_side]) - return RE_ERROR_INTERNAL; - - memset(pattern->partial_named_lists[partial_side], 0, size); - } - - /* Get the partial string set. */ - partial_set = pattern->partial_named_lists[partial_side][node->values[0]]; - if (partial_set) - return 1; - - /* Build the partial string set. */ - partial_set = PySet_New(NULL); - if (!partial_set) - return RE_ERROR_INTERNAL; - - iter = PyObject_GetIter(string_set); - if (!iter) - goto error; - - item = PyIter_Next(iter); - - while (item) { - Py_ssize_t len; - Py_ssize_t first; - Py_ssize_t last; - - len = PySequence_Length(item); - if (len == -1) - goto error; - - first = 0; - last = len; - - while (last - first > 1) { - int status; - - /* Shorten the entry. */ - if (partial_side == RE_PARTIAL_LEFT) - ++first; - else - --last; - - slice = PySequence_GetSlice(item, first, last); - if (!slice) - goto error; - - status = PySet_Add(partial_set, slice); - Py_DECREF(slice); - if (status < 0) - goto error; - } - - Py_DECREF(item); - item = PyIter_Next(iter); - } - - if (PyErr_Occurred()) - goto error; - - Py_DECREF(iter); - - pattern->partial_named_lists[partial_side][node->values[0]] = partial_set; - - return 1; - -error: - Py_XDECREF(item); - Py_XDECREF(iter); - Py_DECREF(partial_set); - - return RE_ERROR_INTERNAL; -} - -/* Tries to match a string at the current position with a member of a string - * set, forwards or backwards. - */ -Py_LOCAL_INLINE(int) string_set_match_fwdrev(RE_SafeState* safe_state, RE_Node* - node, BOOL reverse) { - RE_State* state; - Py_ssize_t min_len; - Py_ssize_t max_len; - Py_ssize_t text_available; - Py_ssize_t slice_available; - int partial_side; - Py_ssize_t len; - Py_ssize_t first; - Py_ssize_t last; - int status; - PyObject* string_set; - - state = safe_state->re_state; - - min_len = (Py_ssize_t)node->values[1]; - max_len = (Py_ssize_t)node->values[2]; - - acquire_GIL(safe_state); - - if (reverse) { - text_available = state->text_pos; - slice_available = state->text_pos - state->slice_start; - partial_side = RE_PARTIAL_LEFT; - } else { - text_available = state->text_length - state->text_pos; - slice_available = state->slice_end - state->text_pos; - partial_side = RE_PARTIAL_RIGHT; - } - - /* Get as many characters as we need for the longest possible match. */ - len = min_ssize_t(max_len, slice_available); - - if (reverse) { - first = state->text_pos - len; - last = state->text_pos; - } else { - first = state->text_pos; - last = state->text_pos + len; - } - - /* If we didn't get all of the characters we need, is a partial match - * allowed? - */ - if (len < max_len && len == text_available && state->partial_side == - partial_side) { - if (len == 0) { - /* An empty string is always a possible partial match. */ - status = RE_ERROR_PARTIAL; - goto finished; - } - - /* Make a set of the possible partial matches. */ - status = make_partial_string_set(state, node); - if (status < 0) - goto finished; - - /* Fetch the partial string set. */ - string_set = - state->pattern->partial_named_lists[partial_side][node->values[0]]; - - /* Is the text we have a partial match? */ - status = string_set_contains(state, string_set, first, last); - if (status < 0) - goto finished; - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= len; - else - state->text_pos += len; - - status = RE_ERROR_PARTIAL; - goto finished; - } - } - - /* Fetch the string set. PyList_GET_ITEM borrows a reference. */ - string_set = PyList_GET_ITEM(state->pattern->named_list_indexes, - node->values[0]); - if (!string_set) { - status = RE_ERROR_INTERNAL; - goto finished; - } - - /* We've already looked for a partial match (if allowed), but what about a - * complete match? - */ - while (len >= min_len) { - status = string_set_contains(state, string_set, first, last); - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= len; - else - state->text_pos += len; - - status = 1; - goto finished; - } - - /* Look for a shorter match. */ - --len; - if (reverse) - ++first; - else - --last; - } - - /* No match. */ - status = 0; - -finished: - release_GIL(safe_state); - - return status; -} - -/* Tries to match a string at the current position with a member of a string - * set, ignoring case, forwards or backwards. - */ -Py_LOCAL_INLINE(int) string_set_match_fld_fwdrev(RE_SafeState* safe_state, - RE_Node* node, BOOL reverse) { - RE_State* state; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - Py_ssize_t folded_charsize; - void (*set_char_at)(void* text, Py_ssize_t pos, Py_UCS4 ch); - Py_ssize_t min_len; - Py_ssize_t max_len; - Py_ssize_t buf_len; - void* folded; - int status; - BOOL* end_of_fold = NULL; - Py_ssize_t text_available; - Py_ssize_t slice_available; - Py_ssize_t t_pos; - Py_ssize_t f_pos; - int step; - int partial_side; - Py_ssize_t len; - Py_ssize_t consumed; - Py_UCS4 codepoints[RE_MAX_FOLDED]; - PyObject* string_set; - Py_ssize_t first; - Py_ssize_t last; - - state = safe_state->re_state; - full_case_fold = state->encoding->full_case_fold; - char_at = state->char_at; - - /* The folded string will have the same width as the original string. */ - folded_charsize = state->charsize; - - switch (folded_charsize) { - case 1: - set_char_at = bytes1_set_char_at; - break; - case 2: - set_char_at = bytes2_set_char_at; - break; - case 4: - set_char_at = bytes4_set_char_at; - break; - default: - return RE_ERROR_INTERNAL; - } - - min_len = (Py_ssize_t)node->values[1]; - max_len = (Py_ssize_t)node->values[2]; - - acquire_GIL(safe_state); - - /* Allocate a buffer for the folded string. */ - buf_len = max_len + RE_MAX_FOLDED; - folded = re_alloc((size_t)(buf_len * folded_charsize)); - if (!folded) { - status = RE_ERROR_MEMORY; - goto finished; - } - - end_of_fold = re_alloc((size_t)buf_len * sizeof(BOOL)); - if (!end_of_fold) { - status = RE_ERROR_MEMORY; - goto finished; - } - - memset(end_of_fold, 0, (size_t)buf_len * sizeof(BOOL)); - - if (reverse) { - text_available = state->text_pos; - slice_available = state->text_pos - state->slice_start; - t_pos = state->text_pos - 1; - f_pos = buf_len; - step = -1; - partial_side = RE_PARTIAL_LEFT; - } else { - text_available = state->text_length - state->text_pos; - slice_available = state->slice_end - state->text_pos; - t_pos = state->text_pos; - f_pos = 0; - step = 1; - partial_side = RE_PARTIAL_RIGHT; - } - - /* We can stop getting characters as soon as the case-folded string is long - * enough (each codepoint from the text can expand to more than one folded - * codepoint). - */ - len = 0; - end_of_fold[len] = TRUE; - - consumed = 0; - while (len < max_len && consumed < slice_available) { - int count; - int j; - - count = full_case_fold(char_at(state->text, t_pos), codepoints); - - if (reverse) - f_pos -= count; - - for (j = 0; j < count; j++) - set_char_at(folded, f_pos + j, codepoints[j]); - - if (!reverse) - f_pos += count; - - len += count; - end_of_fold[len] = TRUE; - ++consumed; - t_pos += step; - } - - if (reverse) { - first = f_pos; - last = buf_len; - } else { - first = 0; - last = f_pos; - } - - /* If we didn't get all of the characters we need, is a partial match - * allowed? - */ - if (len < max_len && len == text_available && state->partial_side == - partial_side) { - if (len == 0) { - /* An empty string is always a possible partial match. */ - status = RE_ERROR_PARTIAL; - goto finished; - } - - /* Make a set of the possible partial matches. */ - status = make_partial_string_set(state, node); - if (status < 0) - goto finished; - - /* Fetch the partial string set. */ - string_set = - state->pattern->partial_named_lists[partial_side][node->values[0]]; - - /* Is the text we have a partial match? */ - status = string_set_contains_ign(state, string_set, folded, first, - last, folded_charsize); - if (status < 0) - goto finished; - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= consumed; - else - state->text_pos += consumed; - - status = RE_ERROR_PARTIAL; - goto finished; - } - } - - /* Fetch the string set. PyList_GET_ITEM borrows a reference. */ - string_set = PyList_GET_ITEM(state->pattern->named_list_indexes, - node->values[0]); - if (!string_set) { - status = RE_ERROR_INTERNAL; - goto finished; - } - - /* We've already looked for a partial match (if allowed), but what about a - * complete match? - */ - while (len >= min_len) { - if (end_of_fold[len]) { - status = string_set_contains_ign(state, string_set, folded, first, - last, folded_charsize); - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= consumed; - else - state->text_pos += consumed; - - status = 1; - goto finished; - } - - --consumed; - } - - /* Look for a shorter match. */ - --len; - if (reverse) - ++first; - else - --last; - } - - /* No match. */ - status = 0; - -finished: - re_dealloc(end_of_fold); - re_dealloc(folded); - - release_GIL(safe_state); - - return status; -} - -/* Tries to match a string at the current position with a member of a string - * set, ignoring case, forwards or backwards. - */ -Py_LOCAL_INLINE(int) string_set_match_ign_fwdrev(RE_SafeState* safe_state, - RE_Node* node, BOOL reverse) { - RE_State* state; - Py_UCS4 (*simple_case_fold)(Py_UCS4 ch); - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - Py_ssize_t folded_charsize; - void (*set_char_at)(void* text, Py_ssize_t pos, Py_UCS4 ch); - Py_ssize_t min_len; - Py_ssize_t max_len; - void* folded; - int status; - Py_ssize_t text_available; - Py_ssize_t slice_available; - Py_ssize_t t_pos; - Py_ssize_t f_pos; - int step; - int partial_side; - Py_ssize_t len; - Py_ssize_t i; - Py_ssize_t first; - Py_ssize_t last; - PyObject* string_set; - - state = safe_state->re_state; - simple_case_fold = state->encoding->simple_case_fold; - char_at = state->char_at; - - /* The folded string will have the same width as the original string. */ - folded_charsize = state->charsize; - - switch (folded_charsize) { - case 1: - set_char_at = bytes1_set_char_at; - break; - case 2: - set_char_at = bytes2_set_char_at; - break; - case 4: - set_char_at = bytes4_set_char_at; - break; - default: - return RE_ERROR_INTERNAL; - } - - min_len = (Py_ssize_t)node->values[1]; - max_len = (Py_ssize_t)node->values[2]; - - acquire_GIL(safe_state); - - /* Allocate a buffer for the folded string. */ - folded = re_alloc((size_t)(max_len * folded_charsize)); - if (!folded) { - status = RE_ERROR_MEMORY; - goto finished; - } - - if (reverse) { - text_available = state->text_pos; - slice_available = state->text_pos - state->slice_start; - t_pos = state->text_pos - 1; - f_pos = max_len - 1; - step = -1; - partial_side = RE_PARTIAL_LEFT; - } else { - text_available = state->text_length - state->text_pos; - slice_available = state->slice_end - state->text_pos; - t_pos = state->text_pos; - f_pos = 0; - step = 1; - partial_side = RE_PARTIAL_RIGHT; - } - - /* Get as many characters as we need for the longest possible match. */ - len = min_ssize_t(max_len, slice_available); - - for (i = 0; i < len; i ++) { - Py_UCS4 ch; - - ch = simple_case_fold(char_at(state->text, t_pos)); - set_char_at(folded, f_pos, ch); - t_pos += step; - f_pos += step; - } - - if (reverse) { - first = f_pos; - last = max_len; - } else { - first = 0; - last = f_pos; - } - - /* If we didn't get all of the characters we need, is a partial match - * allowed? - */ - if (len < max_len && len == text_available && state->partial_side == - partial_side) { - if (len == 0) { - /* An empty string is always a possible partial match. */ - status = RE_ERROR_PARTIAL; - goto finished; - } - - /* Make a set of the possible partial matches. */ - status = make_partial_string_set(state, node); - if (status < 0) - goto finished; - - /* Fetch the partial string set. */ - string_set = - state->pattern->partial_named_lists[partial_side][node->values[0]]; - - /* Is the text we have a partial match? */ - status = string_set_contains_ign(state, string_set, folded, first, - last, folded_charsize); - if (status < 0) - goto finished; - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= len; - else - state->text_pos += len; - - status = RE_ERROR_PARTIAL; - goto finished; - } - } - - /* Fetch the string set. PyList_GET_ITEM borrows a reference. */ - string_set = PyList_GET_ITEM(state->pattern->named_list_indexes, - node->values[0]); - if (!string_set) { - status = RE_ERROR_INTERNAL; - goto finished; - } - - /* We've already looked for a partial match (if allowed), but what about a - * complete match? - */ - while (len >= min_len) { - status = string_set_contains_ign(state, string_set, folded, first, - last, folded_charsize); - - if (status == 1) { - /* Advance past the match. */ - if (reverse) - state->text_pos -= len; - else - state->text_pos += len; - - status = 1; - goto finished; - } - - /* Look for a shorter match. */ - --len; - if (reverse) - ++first; - else - --last; - } - - /* No match. */ - status = 0; - -finished: - re_dealloc(folded); - - release_GIL(safe_state); - - return status; -} - -/* Checks whether any additional fuzzy error is permitted. */ -Py_LOCAL_INLINE(BOOL) any_error_permitted(RE_State* state) { - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - return fuzzy_info->total_cost <= values[RE_FUZZY_VAL_MAX_COST] && - fuzzy_info->counts[RE_FUZZY_ERR] < values[RE_FUZZY_VAL_MAX_ERR] && - state->total_cost <= state->max_cost; -} - -/* Checks whether this additional fuzzy error is permitted. */ -Py_LOCAL_INLINE(BOOL) this_error_permitted(RE_State* state, int fuzzy_type) { - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - return fuzzy_info->total_cost + values[RE_FUZZY_VAL_COST_BASE + fuzzy_type] - <= values[RE_FUZZY_VAL_MAX_COST] && fuzzy_info->counts[fuzzy_type] < - values[RE_FUZZY_VAL_MAX_BASE + fuzzy_type] && state->total_cost + - values[RE_FUZZY_VAL_COST_BASE + fuzzy_type] <= state->max_cost; -} - -/* Checks whether we've reachsd the end of the text during a fuzzy partial - * match. - */ -Py_LOCAL_INLINE(int) check_fuzzy_partial(RE_State* state, Py_ssize_t text_pos) - { - switch (state->partial_side) { - case RE_PARTIAL_LEFT: - if (text_pos < 0) - return RE_ERROR_PARTIAL; - break; - case RE_PARTIAL_RIGHT: - if (text_pos > state->text_length) - return RE_ERROR_PARTIAL; - break; - } - - return RE_ERROR_FAILURE; -} - -/* Checks a fuzzy match of an item. */ -Py_LOCAL_INLINE(int) next_fuzzy_match_item(RE_State* state, RE_FuzzyData* data, - BOOL is_string, int step) { - Py_ssize_t new_pos; - - if (this_error_permitted(state, data->fuzzy_type)) { - switch (data->fuzzy_type) { - case RE_FUZZY_DEL: - /* Could a character at text_pos have been deleted? */ - if (is_string) - data->new_string_pos += step; - else - data->new_node = data->new_node->next_1.node; - return RE_ERROR_SUCCESS; - case RE_FUZZY_INS: - /* Could the character at text_pos have been inserted? */ - if (!data->permit_insertion) - return RE_ERROR_FAILURE; - - new_pos = data->new_text_pos + step; - if (state->slice_start <= new_pos && new_pos <= state->slice_end) { - data->new_text_pos = new_pos; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - case RE_FUZZY_SUB: - /* Could the character at text_pos have been substituted? */ - new_pos = data->new_text_pos + step; - if (state->slice_start <= new_pos && new_pos <= state->slice_end) { - data->new_text_pos = new_pos; - if (is_string) - data->new_string_pos += step; - else - data->new_node = data->new_node->next_1.node; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - } - } - - return RE_ERROR_FAILURE; -} - -/* Tries a fuzzy match of an item of width 0 or 1. */ -Py_LOCAL_INLINE(int) fuzzy_match_item(RE_SafeState* safe_state, BOOL search, - Py_ssize_t* text_pos, RE_Node** node, int step) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - - state = safe_state->re_state; - - if (!any_error_permitted(state)) { - *node = NULL; - return RE_ERROR_SUCCESS; - } - - data.new_text_pos = *text_pos; - data.new_node = *node; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - if (step == 0) { - if (data.new_node->status & RE_STATUS_REVERSE) { - data.step = -1; - data.limit = state->slice_start; - } else { - data.step = 1; - data.limit = state->slice_end; - } - } else - data.step = step; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || data.new_text_pos != - state->search_anchor; - - for (data.fuzzy_type = 0; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_item(state, &data, FALSE, step); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - *node = NULL; - return RE_ERROR_SUCCESS; - -found: - if (!add_backtrack(safe_state, (*node)->op)) - return RE_ERROR_FAILURE; - bt_data = state->backtrack; - bt_data->fuzzy_item.position.text_pos = *text_pos; - bt_data->fuzzy_item.position.node = *node; - bt_data->fuzzy_item.fuzzy_type = (RE_INT8)data.fuzzy_type; - bt_data->fuzzy_item.step = (RE_INT8)step; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = data.new_text_pos; - *node = data.new_node; - - return RE_ERROR_SUCCESS; -} - -/* Retries a fuzzy match of a item of width 0 or 1. */ -Py_LOCAL_INLINE(int) retry_fuzzy_match_item(RE_SafeState* safe_state, BOOL - search, Py_ssize_t* text_pos, RE_Node** node, BOOL advance) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - int step; - - state = safe_state->re_state; - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - bt_data = state->backtrack; - data.new_text_pos = bt_data->fuzzy_item.position.text_pos; - data.new_node = bt_data->fuzzy_item.position.node; - data.fuzzy_type = bt_data->fuzzy_item.fuzzy_type; - data.step = bt_data->fuzzy_item.step; - - if (data.fuzzy_type >= 0) { - --fuzzy_info->counts[data.fuzzy_type]; - --fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost -= values[RE_FUZZY_VAL_COST_BASE + - data.fuzzy_type]; - --state->total_errors; - state->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - } - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || data.new_text_pos != - state->search_anchor; - - step = advance ? data.step : 0; - - for (++data.fuzzy_type; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_item(state, &data, FALSE, step); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - discard_backtrack(state); - *node = NULL; - return RE_ERROR_SUCCESS; - -found: - bt_data->fuzzy_item.fuzzy_type = (RE_INT8)data.fuzzy_type; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = data.new_text_pos; - *node = data.new_node; - - return RE_ERROR_SUCCESS; -} - -/* Tries a fuzzy insertion. */ -Py_LOCAL_INLINE(int) fuzzy_insert(RE_SafeState* safe_state, Py_ssize_t - text_pos, RE_Node* node) { - RE_State* state; - RE_BacktrackData* bt_data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - - state = safe_state->re_state; - - /* No insertion or deletion. */ - if (!add_backtrack(safe_state, node->op)) - return RE_ERROR_FAILURE; - bt_data = state->backtrack; - bt_data->fuzzy_insert.position.text_pos = text_pos; - bt_data->fuzzy_insert.position.node = node; - bt_data->fuzzy_insert.count = 0; - bt_data->fuzzy_insert.too_few_errors = state->too_few_errors; - bt_data->fuzzy_insert.fuzzy_node = node; /* END_FUZZY node. */ - - /* Check whether there are too few errors. */ - fuzzy_info = &state->fuzzy_info; - - /* The node in this case is the END_FUZZY node. */ - values = node->values; - - if (fuzzy_info->counts[RE_FUZZY_DEL] < values[RE_FUZZY_VAL_MIN_DEL] || - fuzzy_info->counts[RE_FUZZY_INS] < values[RE_FUZZY_VAL_MIN_INS] || - fuzzy_info->counts[RE_FUZZY_SUB] < values[RE_FUZZY_VAL_MIN_SUB] || - fuzzy_info->counts[RE_FUZZY_ERR] < values[RE_FUZZY_VAL_MIN_ERR]) - state->too_few_errors = RE_ERROR_SUCCESS; - - return RE_ERROR_SUCCESS; -} - -/* Retries a fuzzy insertion. */ -Py_LOCAL_INLINE(int) retry_fuzzy_insert(RE_SafeState* safe_state, Py_ssize_t* - text_pos, RE_Node** node) { - RE_State* state; - RE_FuzzyInfo* fuzzy_info; - RE_BacktrackData* bt_data; - Py_ssize_t new_text_pos; - RE_Node* new_node; - int step; - Py_ssize_t limit; - RE_Node* fuzzy_node; - RE_CODE* values; - - state = safe_state->re_state; - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - bt_data = state->backtrack; - new_text_pos = bt_data->fuzzy_insert.position.text_pos; - new_node = bt_data->fuzzy_insert.position.node; - - if (new_node->status & RE_STATUS_REVERSE) { - step = -1; - limit = state->slice_start; - } else { - step = 1; - limit = state->slice_end; - } - - /* Could the character at text_pos have been inserted? */ - if (!this_error_permitted(state, RE_FUZZY_INS) || new_text_pos == limit) { - size_t count; - - count = bt_data->fuzzy_insert.count; - - fuzzy_info->counts[RE_FUZZY_INS] -= count; - fuzzy_info->counts[RE_FUZZY_ERR] -= count; - fuzzy_info->total_cost -= values[RE_FUZZY_VAL_INS_COST] * count; - state->total_errors -= count; - state->total_cost -= values[RE_FUZZY_VAL_INS_COST] * count; - state->too_few_errors = bt_data->fuzzy_insert.too_few_errors; - - discard_backtrack(state); - *node = NULL; - return RE_ERROR_SUCCESS; - } - - ++bt_data->fuzzy_insert.count; - - ++fuzzy_info->counts[RE_FUZZY_INS]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_INS_COST]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_INS_COST]; - - /* Check whether there are too few errors. */ - state->too_few_errors = bt_data->fuzzy_insert.too_few_errors; - fuzzy_node = bt_data->fuzzy_insert.fuzzy_node; /* END_FUZZY node. */ - values = fuzzy_node->values; - if (fuzzy_info->counts[RE_FUZZY_DEL] < values[RE_FUZZY_VAL_MIN_DEL] || - fuzzy_info->counts[RE_FUZZY_INS] < values[RE_FUZZY_VAL_MIN_INS] || - fuzzy_info->counts[RE_FUZZY_SUB] < values[RE_FUZZY_VAL_MIN_SUB] || - fuzzy_info->counts[RE_FUZZY_ERR] < values[RE_FUZZY_VAL_MIN_ERR]) - state->too_few_errors = RE_ERROR_SUCCESS; - - *text_pos = new_text_pos + step * (Py_ssize_t)bt_data->fuzzy_insert.count; - *node = new_node; - - return RE_ERROR_SUCCESS; -} - -/* Tries a fuzzy match of a string. */ -Py_LOCAL_INLINE(int) fuzzy_match_string(RE_SafeState* safe_state, BOOL search, - Py_ssize_t* text_pos, RE_Node* node, Py_ssize_t* string_pos, BOOL* matched, - int step) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - - state = safe_state->re_state; - - if (!any_error_permitted(state)) { - *matched = FALSE; - return RE_ERROR_SUCCESS; - } - - data.new_text_pos = *text_pos; - data.new_string_pos = *string_pos; - data.step = step; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || data.new_text_pos != - state->search_anchor; - - for (data.fuzzy_type = 0; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_item(state, &data, TRUE, data.step); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - if (!add_backtrack(safe_state, node->op)) - return RE_ERROR_FAILURE; - bt_data = state->backtrack; - bt_data->fuzzy_string.position.text_pos = *text_pos; - bt_data->fuzzy_string.position.node = node; - bt_data->fuzzy_string.string_pos = *string_pos; - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - bt_data->fuzzy_string.step = (RE_INT8)step; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = data.new_text_pos; - *string_pos = data.new_string_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Retries a fuzzy match of a string. */ -Py_LOCAL_INLINE(int) retry_fuzzy_match_string(RE_SafeState* safe_state, BOOL - search, Py_ssize_t* text_pos, RE_Node** node, Py_ssize_t* string_pos, BOOL* - matched) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - RE_Node* new_node; - - state = safe_state->re_state; - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - bt_data = state->backtrack; - data.new_text_pos = bt_data->fuzzy_string.position.text_pos; - new_node = bt_data->fuzzy_string.position.node; - data.new_string_pos = bt_data->fuzzy_string.string_pos; - data.fuzzy_type = bt_data->fuzzy_string.fuzzy_type; - data.step = bt_data->fuzzy_string.step; - - --fuzzy_info->counts[data.fuzzy_type]; - --fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - --state->total_errors; - state->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || data.new_text_pos != - state->search_anchor; - - for (++data.fuzzy_type; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_item(state, &data, TRUE, data.step); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - discard_backtrack(state); - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = data.new_text_pos; - *node = new_node; - *string_pos = data.new_string_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Checks a fuzzy match of a atring. */ -Py_LOCAL_INLINE(int) next_fuzzy_match_string_fld(RE_State* state, RE_FuzzyData* - data) { - int new_pos; - - if (this_error_permitted(state, data->fuzzy_type)) { - switch (data->fuzzy_type) { - case RE_FUZZY_DEL: - /* Could a character at text_pos have been deleted? */ - data->new_string_pos += data->step; - return RE_ERROR_SUCCESS; - case RE_FUZZY_INS: - /* Could the character at text_pos have been inserted? */ - if (!data->permit_insertion) - return RE_ERROR_FAILURE; - - new_pos = data->new_folded_pos + data->step; - if (0 <= new_pos && new_pos <= data->folded_len) { - data->new_folded_pos = new_pos; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - case RE_FUZZY_SUB: - /* Could the character at text_pos have been substituted? */ - new_pos = data->new_folded_pos + data->step; - if (0 <= new_pos && new_pos <= data->folded_len) { - data->new_folded_pos = new_pos; - data->new_string_pos += data->step; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - } - } - - return RE_ERROR_FAILURE; -} - -/* Tries a fuzzy match of a string, ignoring case. */ -Py_LOCAL_INLINE(int) fuzzy_match_string_fld(RE_SafeState* safe_state, BOOL - search, Py_ssize_t* text_pos, RE_Node* node, Py_ssize_t* string_pos, int* - folded_pos, int folded_len, BOOL* matched, int step) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - Py_ssize_t new_text_pos; - RE_BacktrackData* bt_data; - - state = safe_state->re_state; - - if (!any_error_permitted(state)) { - *matched = FALSE; - return RE_ERROR_SUCCESS; - } - - new_text_pos = *text_pos; - data.new_string_pos = *string_pos; - data.new_folded_pos = *folded_pos; - data.folded_len = folded_len; - data.step = step; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || new_text_pos != state->search_anchor; - if (step > 0) { - if (data.new_folded_pos != 0) - data.permit_insertion = RE_ERROR_SUCCESS; - } else { - if (data.new_folded_pos != folded_len) - data.permit_insertion = RE_ERROR_SUCCESS; - } - - for (data.fuzzy_type = 0; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_string_fld(state, &data); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - if (!add_backtrack(safe_state, node->op)) - return RE_ERROR_FAILURE; - bt_data = state->backtrack; - bt_data->fuzzy_string.position.text_pos = *text_pos; - bt_data->fuzzy_string.position.node = node; - bt_data->fuzzy_string.string_pos = *string_pos; - bt_data->fuzzy_string.folded_pos = (RE_INT8)(*folded_pos); - bt_data->fuzzy_string.folded_len = (RE_INT8)folded_len; - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - bt_data->fuzzy_string.step = (RE_INT8)step; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = new_text_pos; - *string_pos = data.new_string_pos; - *folded_pos = data.new_folded_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Retries a fuzzy match of a string, ignoring case. */ -Py_LOCAL_INLINE(int) retry_fuzzy_match_string_fld(RE_SafeState* safe_state, - BOOL search, Py_ssize_t* text_pos, RE_Node** node, Py_ssize_t* string_pos, - int* folded_pos, BOOL* matched) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - Py_ssize_t new_text_pos; - RE_Node* new_node; - - state = safe_state->re_state; - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - bt_data = state->backtrack; - new_text_pos = bt_data->fuzzy_string.position.text_pos; - new_node = bt_data->fuzzy_string.position.node; - data.new_string_pos = bt_data->fuzzy_string.string_pos; - data.new_folded_pos = bt_data->fuzzy_string.folded_pos; - data.folded_len = bt_data->fuzzy_string.folded_len; - data.fuzzy_type = bt_data->fuzzy_string.fuzzy_type; - data.step = bt_data->fuzzy_string.step; - - --fuzzy_info->counts[data.fuzzy_type]; - --fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - --state->total_errors; - state->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || new_text_pos != state->search_anchor; - if (data.step > 0) { - if (data.new_folded_pos != 0) - data.permit_insertion = RE_ERROR_SUCCESS; - } else { - if (data.new_folded_pos != bt_data->fuzzy_string.folded_len) - data.permit_insertion = RE_ERROR_SUCCESS; - } - - for (++data.fuzzy_type; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_string_fld(state, &data); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - discard_backtrack(state); - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = new_text_pos; - *node = new_node; - *string_pos = data.new_string_pos; - *folded_pos = data.new_folded_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Checks a fuzzy match of a atring. */ -Py_LOCAL_INLINE(int) next_fuzzy_match_group_fld(RE_State* state, RE_FuzzyData* - data) { - int new_pos; - - if (this_error_permitted(state, data->fuzzy_type)) { - switch (data->fuzzy_type) { - case RE_FUZZY_DEL: - /* Could a character at text_pos have been deleted? */ - data->new_gfolded_pos += data->step; - return RE_ERROR_SUCCESS; - case RE_FUZZY_INS: - /* Could the character at text_pos have been inserted? */ - if (!data->permit_insertion) - return RE_ERROR_FAILURE; - - new_pos = data->new_folded_pos + data->step; - if (0 <= new_pos && new_pos <= data->folded_len) { - data->new_folded_pos = new_pos; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - case RE_FUZZY_SUB: - /* Could the character at text_pos have been substituted? */ - new_pos = data->new_folded_pos + data->step; - if (0 <= new_pos && new_pos <= data->folded_len) { - data->new_folded_pos = new_pos; - data->new_gfolded_pos += data->step; - return RE_ERROR_SUCCESS; - } - - return check_fuzzy_partial(state, new_pos); - } - } - - return RE_ERROR_FAILURE; -} - -/* Tries a fuzzy match of a group reference, ignoring case. */ -Py_LOCAL_INLINE(int) fuzzy_match_group_fld(RE_SafeState* safe_state, BOOL - search, Py_ssize_t* text_pos, RE_Node* node, int* folded_pos, int folded_len, - Py_ssize_t* group_pos, int* gfolded_pos, int gfolded_len, BOOL* matched, int - step) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - Py_ssize_t new_text_pos; - Py_ssize_t new_group_pos; - RE_BacktrackData* bt_data; - - state = safe_state->re_state; - - if (!any_error_permitted(state)) { - *matched = FALSE; - return RE_ERROR_SUCCESS; - } - - new_text_pos = *text_pos; - data.new_folded_pos = *folded_pos; - data.folded_len = folded_len; - new_group_pos = *group_pos; - data.new_gfolded_pos = *gfolded_pos; - data.step = step; - - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || new_text_pos != state->search_anchor; - if (data.step > 0) { - if (data.new_folded_pos != 0) - data.permit_insertion = RE_ERROR_SUCCESS; - } else { - if (data.new_folded_pos != folded_len) - data.permit_insertion = RE_ERROR_SUCCESS; - } - - for (data.fuzzy_type = 0; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_group_fld(state, &data); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - if (!add_backtrack(safe_state, node->op)) - return RE_ERROR_FAILURE; - bt_data = state->backtrack; - bt_data->fuzzy_string.position.text_pos = *text_pos; - bt_data->fuzzy_string.position.node = node; - bt_data->fuzzy_string.string_pos = *group_pos; - bt_data->fuzzy_string.folded_pos = (RE_INT8)(*folded_pos); - bt_data->fuzzy_string.folded_len = (RE_INT8)folded_len; - bt_data->fuzzy_string.gfolded_pos = (RE_INT8)(*gfolded_pos); - bt_data->fuzzy_string.gfolded_len = (RE_INT8)gfolded_len; - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - bt_data->fuzzy_string.step = (RE_INT8)step; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = new_text_pos; - *group_pos = new_group_pos; - *folded_pos = data.new_folded_pos; - *gfolded_pos = data.new_gfolded_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Retries a fuzzy match of a group reference, ignoring case. */ -Py_LOCAL_INLINE(int) retry_fuzzy_match_group_fld(RE_SafeState* safe_state, BOOL - search, Py_ssize_t* text_pos, RE_Node** node, int* folded_pos, Py_ssize_t* - group_pos, int* gfolded_pos, BOOL* matched) { - RE_State* state; - RE_FuzzyData data; - RE_FuzzyInfo* fuzzy_info; - RE_CODE* values; - RE_BacktrackData* bt_data; - Py_ssize_t new_text_pos; - Py_ssize_t new_group_pos; - RE_Node* new_node; - - state = safe_state->re_state; - fuzzy_info = &state->fuzzy_info; - values = fuzzy_info->node->values; - - bt_data = state->backtrack; - new_text_pos = bt_data->fuzzy_string.position.text_pos; - new_node = bt_data->fuzzy_string.position.node; - new_group_pos = bt_data->fuzzy_string.string_pos; - data.new_folded_pos = bt_data->fuzzy_string.folded_pos; - data.folded_len = bt_data->fuzzy_string.folded_len; - data.new_gfolded_pos = bt_data->fuzzy_string.gfolded_pos; - data.fuzzy_type = bt_data->fuzzy_string.fuzzy_type; - data.step = bt_data->fuzzy_string.step; - - --fuzzy_info->counts[data.fuzzy_type]; - --fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - --state->total_errors; - state->total_cost -= values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - /* Permit insertion except initially when searching (it's better just to - * start searching one character later). - */ - data.permit_insertion = !search || new_text_pos != state->search_anchor || - data.new_folded_pos != bt_data->fuzzy_string.folded_len; - - for (++data.fuzzy_type; data.fuzzy_type < RE_FUZZY_COUNT; - data.fuzzy_type++) { - int status; - - status = next_fuzzy_match_group_fld(state, &data); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - goto found; - } - - discard_backtrack(state); - *matched = FALSE; - return RE_ERROR_SUCCESS; - -found: - bt_data->fuzzy_string.fuzzy_type = (RE_INT8)data.fuzzy_type; - - ++fuzzy_info->counts[data.fuzzy_type]; - ++fuzzy_info->counts[RE_FUZZY_ERR]; - fuzzy_info->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - ++state->total_errors; - state->total_cost += values[RE_FUZZY_VAL_COST_BASE + data.fuzzy_type]; - - *text_pos = new_text_pos; - *node = new_node; - *group_pos = new_group_pos; - *folded_pos = data.new_folded_pos; - *gfolded_pos = data.new_gfolded_pos; - *matched = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Locates the required string, if there's one. */ -Py_LOCAL_INLINE(Py_ssize_t) locate_required_string(RE_SafeState* safe_state) { - RE_State* state; - PatternObject* pattern; - Py_ssize_t found_pos; - Py_ssize_t end_pos; - - state = safe_state->re_state; - pattern = state->pattern; - - /* We haven't matched the required string yet. */ - state->req_pos = -1; - - if (!pattern->req_string) - /* There isn't a required string, so start matching from the current - * position. - */ - return state->text_pos; - - /* Search for the required string and calculate where to start matching. */ - switch (pattern->req_string->op) { - case RE_OP_STRING: - { - BOOL is_partial; - - found_pos = string_search(safe_state, pattern->req_string, - state->text_pos, state->slice_end, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = found_pos + - (Py_ssize_t)pattern->req_string->value_count; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos -= pattern->req_offset; - if (found_pos >= state->text_pos) - return found_pos; - } - break; - } - case RE_OP_STRING_FLD: - { - BOOL is_partial; - - found_pos = string_search_fld(safe_state, pattern->req_string, - state->text_pos, state->slice_end, &end_pos, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = end_pos; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos -= pattern->req_offset; - if (found_pos >= state->text_pos) - return found_pos; - } - break; - } - case RE_OP_STRING_FLD_REV: - { - BOOL is_partial; - - found_pos = string_search_fld_rev(safe_state, pattern->req_string, - state->text_pos, state->slice_start, &end_pos, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = end_pos; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos += pattern->req_offset; - if (found_pos <= state->text_pos) - return found_pos; - } - break; - } - case RE_OP_STRING_IGN: - { - BOOL is_partial; - - found_pos = string_search_ign(safe_state, pattern->req_string, - state->text_pos, state->slice_end, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = found_pos + - (Py_ssize_t)pattern->req_string->value_count; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos -= pattern->req_offset; - if (found_pos >= state->text_pos) - return found_pos; - } - break; - } - case RE_OP_STRING_IGN_REV: - { - BOOL is_partial; - - found_pos = string_search_ign_rev(safe_state, pattern->req_string, - state->text_pos, state->slice_start, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = found_pos - - (Py_ssize_t)pattern->req_string->value_count; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos += pattern->req_offset; - if (found_pos <= state->text_pos) - return found_pos; - } - break; - } - case RE_OP_STRING_REV: - { - BOOL is_partial; - - found_pos = string_search_rev(safe_state, pattern->req_string, - state->text_pos, state->slice_start, &is_partial); - if (found_pos < 0) - /* The required string wasn't found. */ - return -1; - - if (is_partial) - /* We found a partial match, so start matching from there. */ - return found_pos; - - /* Record where the required string matched. */ - state->req_pos = found_pos; - state->req_end = found_pos - - (Py_ssize_t)pattern->req_string->value_count; - - if (pattern->req_offset >= 0) { - /* Step back from the required string to where we should start - * matching. - */ - found_pos += pattern->req_offset; - if (found_pos <= state->text_pos) - return found_pos; - } - break; - } - } - - /* Start matching from the current position. */ - return state->text_pos; -} - -/* Tries to match a character pattern. */ -Py_LOCAL_INLINE(int) match_one(RE_State* state, RE_Node* node, Py_ssize_t - text_pos) { - switch (node->op) { - case RE_OP_ANY: - return try_match_ANY(state, node, text_pos); - case RE_OP_ANY_ALL: - return try_match_ANY_ALL(state, node, text_pos); - case RE_OP_ANY_ALL_REV: - return try_match_ANY_ALL_REV(state, node, text_pos); - case RE_OP_ANY_REV: - return try_match_ANY_REV(state, node, text_pos); - case RE_OP_ANY_U: - return try_match_ANY_U(state, node, text_pos); - case RE_OP_ANY_U_REV: - return try_match_ANY_U_REV(state, node, text_pos); - case RE_OP_CHARACTER: - return try_match_CHARACTER(state, node, text_pos); - case RE_OP_CHARACTER_IGN: - return try_match_CHARACTER_IGN(state, node, text_pos); - case RE_OP_CHARACTER_IGN_REV: - return try_match_CHARACTER_IGN_REV(state, node, text_pos); - case RE_OP_CHARACTER_REV: - return try_match_CHARACTER_REV(state, node, text_pos); - case RE_OP_PROPERTY: - return try_match_PROPERTY(state, node, text_pos); - case RE_OP_PROPERTY_IGN: - return try_match_PROPERTY_IGN(state, node, text_pos); - case RE_OP_PROPERTY_IGN_REV: - return try_match_PROPERTY_IGN_REV(state, node, text_pos); - case RE_OP_PROPERTY_REV: - return try_match_PROPERTY_REV(state, node, text_pos); - case RE_OP_RANGE: - return try_match_RANGE(state, node, text_pos); - case RE_OP_RANGE_IGN: - return try_match_RANGE_IGN(state, node, text_pos); - case RE_OP_RANGE_IGN_REV: - return try_match_RANGE_IGN_REV(state, node, text_pos); - case RE_OP_RANGE_REV: - return try_match_RANGE_REV(state, node, text_pos); - case RE_OP_SET_DIFF: - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - return try_match_SET(state, node, text_pos); - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION_IGN: - return try_match_SET_IGN(state, node, text_pos); - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_UNION_IGN_REV: - return try_match_SET_IGN_REV(state, node, text_pos); - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_REV: - return try_match_SET_REV(state, node, text_pos); - } - - return FALSE; -} - -/* Performs a depth-first match or search from the context. */ -Py_LOCAL_INLINE(int) basic_match(RE_SafeState* safe_state, RE_Node* start_node, - BOOL search, BOOL recursive_call) { - RE_State* state; - RE_EncodingTable* encoding; - PatternObject* pattern; - RE_NextNode start_pair; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - Py_ssize_t pattern_step; /* The overall step of the pattern (forwards or backwards). */ - Py_ssize_t string_pos; - BOOL do_search_start; - Py_ssize_t found_pos; - int folded_pos; - int gfolded_pos; - RE_Node* node; - int status; - TRACE(("<>\n")) - - state = safe_state->re_state; - encoding = state->encoding; - pattern = state->pattern; - - /* Look beyond any initial group node. */ - start_pair.node = start_node; - if (recursive_call) - start_pair.test = locate_test_start(start_node); - else - start_pair.test = pattern->start_test; - - /* Is the pattern anchored to the start or end of the string? */ - switch (start_pair.test->op) { - case RE_OP_END_OF_STRING: - if (state->reverse) { - /* Searching backwards. */ - if (state->text_pos != state->text_length) - return RE_ERROR_FAILURE; - - /* Don't bother to search further because it's anchored. */ - search = FALSE; - } - break; - case RE_OP_START_OF_STRING: - if (!state->reverse) { - /* Searching forwards. */ - if (state->text_pos != 0) - return RE_ERROR_FAILURE; - - /* Don't bother to search further because it's anchored. */ - search = FALSE; - } - break; - } - - char_at = state->char_at; - pattern_step = state->reverse ? -1 : 1; - string_pos = -1; - do_search_start = pattern->do_search_start; - - /* Add a backtrack entry for failure. */ - if (!add_backtrack(safe_state, RE_OP_FAILURE)) - return RE_ERROR_BACKTRACKING; - -start_match: - /* If we're searching, advance along the string until there could be a - * match. - */ - if (pattern->pattern_call_ref >= 0) { - RE_GuardList* guard_list; - - guard_list = &state->group_call_guard_list[pattern->pattern_call_ref]; - guard_list->count = 0; - guard_list->last_text_pos = -1; - } - - /* Locate the required string, if there's one, unless this is a recursive - * call of 'basic_match'. - */ - if (!pattern->req_string || recursive_call) - found_pos = state->text_pos; - else { - found_pos = locate_required_string(safe_state); - if (found_pos < 0) - return RE_ERROR_FAILURE; - } - - if (search) { - state->text_pos = found_pos; - - if (do_search_start) { - RE_Position new_position; - -next_match_1: - /* 'search_start' will clear 'do_search_start' if it can't perform - * a fast search for the next possible match. This enables us to - * avoid the overhead of the call subsequently. - */ - status = search_start(safe_state, &start_pair, &new_position, 0); - if (status != RE_ERROR_SUCCESS) - return status; - - node = new_position.node; - state->text_pos = new_position.text_pos; - - if (node->op == RE_OP_SUCCESS) { - /* Must the match advance past its start? */ - if (state->text_pos != state->search_anchor || - !state->must_advance) - return RE_ERROR_SUCCESS; - - state->text_pos = state->match_pos + pattern_step; - goto next_match_1; - } - - /* 'do_search_start' may have been cleared. */ - do_search_start = pattern->do_search_start; - } else { - /* Avoiding 'search_start', which we've found can't perform a fast - * search for the next possible match. - */ - node = start_node; - -next_match_2: - if (state->reverse) { - if (state->text_pos < state->slice_start) { - if (state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - } else { - if (state->text_pos > state->slice_end) { - if (state-> partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - return RE_ERROR_FAILURE; - } - } - - state->match_pos = state->text_pos; - - if (node->op == RE_OP_SUCCESS) { - /* Must the match advance past its start? */ - if (state->text_pos != state->search_anchor || - !state->must_advance) { - BOOL success; - - if (state->match_all && !recursive_call) { - /* We want to match all of the slice. */ - if (state->reverse) - success = state->text_pos == state->slice_start; - else - success = state->text_pos == state->slice_end; - } else - success = TRUE; - - if (success) - return RE_ERROR_SUCCESS; - } - - state->text_pos = state->match_pos + pattern_step; - goto next_match_2; - } - } - } else { - /* The start position is anchored to the current position. */ - if (found_pos != state->text_pos) - return RE_ERROR_FAILURE; - - node = start_node; - } - -advance: - /* The main matching loop. */ - for (;;) { - TRACE(("%d|", state->text_pos)) - - /* Should we abort the matching? */ - ++state->iterations; - - if (state->iterations == 0 && safe_check_signals(safe_state)) - return RE_ERROR_INTERRUPTED; - - switch (node->op) { - case RE_OP_ANY: /* Any character except a newline. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - ++state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ANY_ALL: /* Any character at all. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY_ALL(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - ++state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ANY_ALL_REV: /* Any character at all, backwards. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY_ALL_REV(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - --state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ANY_REV: /* Any character except a newline, backwards. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY_REV(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - --state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ANY_U: /* Any character except a line separator. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY_U(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - ++state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ANY_U_REV: /* Any character except a line separator, backwards. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_ANY_U_REV(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - --state->text_pos; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_ATOMIC: /* Atomic subpattern. */ - { - RE_Info info; - int status; - TRACE(("%s\n", re_op_text[node->op])) - - if (!add_backtrack(safe_state, RE_OP_ATOMIC)) - return RE_ERROR_BACKTRACKING; - state->backtrack->atomic.too_few_errors = state->too_few_errors; - state->backtrack->atomic.capture_change = state->capture_change; - - /* Save the groups. */ - if (!push_groups(safe_state)) - return RE_ERROR_MEMORY; - - save_info(state, &info); - - state->must_advance = FALSE; - - status = basic_match(safe_state, node->nonstring.next_2.node, - FALSE, TRUE); - if (status < 0) - return status; - - reset_guards(state, node->values); - - restore_info(state, &info); - - if (status != RE_ERROR_SUCCESS) - goto backtrack; - - node = node->next_1.node; - break; - } - case RE_OP_BOUNDARY: /* On a word boundary. */ - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - status = try_match_BOUNDARY(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_BRANCH: /* 2-way branch. */ - { - RE_Position next_position; - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match(state, &node->next_1, state->text_pos, - &next_position); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) { - if (!add_backtrack(safe_state, RE_OP_BRANCH)) - return RE_ERROR_BACKTRACKING; - state->backtrack->branch.position.node = - node->nonstring.next_2.node; - state->backtrack->branch.position.text_pos = state->text_pos; - - node = next_position.node; - state->text_pos = next_position.text_pos; - } else - node = node->nonstring.next_2.node; - break; - } - case RE_OP_CALL_REF: /* A group call reference. */ - { - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - if (!push_group_return(safe_state, NULL)) - return RE_ERROR_MEMORY; - - if (!add_backtrack(safe_state, RE_OP_CALL_REF)) - return RE_ERROR_BACKTRACKING; - - node = node->next_1.node; - break; - } - case RE_OP_CHARACTER: /* A character. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - matches_CHARACTER(encoding, node, char_at(state->text, - state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_CHARACTER_IGN: /* A character, ignoring case. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - matches_CHARACTER_IGN(encoding, node, char_at(state->text, - state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_CHARACTER_IGN_REV: /* A character, backwards, ignoring case. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_CHARACTER_IGN(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_CHARACTER_REV: /* A character, backwards. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_CHARACTER(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_DEFAULT_BOUNDARY: /* On a default word boundary. */ - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - status = try_match_DEFAULT_BOUNDARY(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_DEFAULT_END_OF_WORD: /* At the default end of a word. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_DEFAULT_END_OF_WORD(state, node, - state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_DEFAULT_START_OF_WORD: /* At the default start of a word. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_DEFAULT_START_OF_WORD(state, node, - state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_FUZZY: /* End of fuzzy matching. */ - TRACE(("%s\n", re_op_text[node->op])) - - if (!fuzzy_insert(safe_state, state->text_pos, node)) - return RE_ERROR_BACKTRACKING; - - /* If there were too few errors, in the fuzzy section, try again. - */ - if (state->too_few_errors) { - state->too_few_errors = FALSE; - goto backtrack; - } - - state->total_fuzzy_counts[RE_FUZZY_SUB] += - state->fuzzy_info.counts[RE_FUZZY_SUB]; - state->total_fuzzy_counts[RE_FUZZY_INS] += - state->fuzzy_info.counts[RE_FUZZY_INS]; - state->total_fuzzy_counts[RE_FUZZY_DEL] += - state->fuzzy_info.counts[RE_FUZZY_DEL]; - - node = node->next_1.node; - break; - case RE_OP_END_GREEDY_REPEAT: /* End of a greedy repeat. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - BOOL changed; - BOOL try_body; - int body_status; - RE_Position next_body_position; - BOOL try_tail; - int tail_status; - RE_Position next_tail_position; - RE_BacktrackData* bt_data; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - /* The body has matched successfully at this position. */ - if (!guard_repeat(safe_state, index, rp_data->start, - RE_STATUS_BODY, FALSE)) - return RE_ERROR_MEMORY; - - ++rp_data->count; - - /* Have we advanced through the text or has a capture group change? - */ - changed = rp_data->capture_change != state->capture_change || - state->text_pos != rp_data->start; - - /* The counts are of type size_t, so the format needs to specify - * that. - */ - TRACE(("min is %" PY_FORMAT_SIZE_T "u, max is %" PY_FORMAT_SIZE_T - "u, count is %" PY_FORMAT_SIZE_T "u\n", node->values[1], - node->values[2], rp_data->count)) - - /* Could the body or tail match? */ - try_body = changed && (rp_data->count < node->values[2] || - ~node->values[2] == 0) && !is_repeat_guarded(safe_state, index, - state->text_pos, RE_STATUS_BODY); - if (try_body) { - body_status = try_match(state, &node->next_1, state->text_pos, - &next_body_position); - - if (body_status == RE_ERROR_FAILURE) - try_body = FALSE; - } else - body_status = RE_ERROR_FAILURE; - - try_tail = (!changed || rp_data->count >= node->values[1]) && - !is_repeat_guarded(safe_state, index, state->text_pos, - RE_STATUS_TAIL); - if(try_tail) { - tail_status = try_match(state, &node->nonstring.next_2, - state->text_pos, &next_tail_position); - - if (tail_status == RE_ERROR_FAILURE) - try_tail = FALSE; - } else - tail_status = RE_ERROR_FAILURE; - - if (!try_body && !try_tail) { - /* Neither the body nor the tail could match. */ - --rp_data->count; - goto backtrack; - } - - if (body_status < 0 || (body_status == 0 && tail_status < 0)) - return RE_ERROR_PARTIAL; - - /* Record info in case we backtrack into the body. */ - if (!add_backtrack(safe_state, RE_OP_BODY_END)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count - 1; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - - if (try_body) { - /* Both the body and the tail could match. */ - if (try_tail) { - /* The body takes precedence. If the body fails to match - * then we want to try the tail before backtracking - * further. - */ - - /* Record backtracking info for matching the tail. */ - if (!add_backtrack(safe_state, RE_OP_MATCH_TAIL)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position = next_tail_position; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - } - - /* Record backtracking info in case the body fails to match. */ - if (!add_backtrack(safe_state, RE_OP_BODY_START)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.text_pos = state->text_pos; - - rp_data->capture_change = state->capture_change; - rp_data->start = state->text_pos; - - /* Advance into the body. */ - node = next_body_position.node; - state->text_pos = next_body_position.text_pos; - } else { - /* Only the tail could match. */ - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } - break; - } - case RE_OP_END_GROUP: /* End of a capture group. */ - { - RE_CODE private_index; - RE_CODE public_index; - RE_GroupData* group; - RE_BacktrackData* bt_data; - TRACE(("%s %d\n", re_op_text[node->op], node->values[1])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - */ - private_index = node->values[0]; - public_index = node->values[1]; - group = &state->groups[private_index - 1]; - - if (!add_backtrack(safe_state, RE_OP_END_GROUP)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->group.private_index = private_index; - bt_data->group.public_index = public_index; - bt_data->group.text_pos = group->span.end; - bt_data->group.capture = (BOOL)node->values[2]; - bt_data->group.current_capture = group->current_capture; - - if (pattern->group_info[private_index - 1].referenced && - group->span.end != state->text_pos) - ++state->capture_change; - group->span.end = state->text_pos; - - /* Save the capture? */ - if (node->values[2]) { - group->current_capture = (Py_ssize_t)group->capture_count; - if (!save_capture(safe_state, private_index, public_index)) - return RE_ERROR_MEMORY; - } - - node = node->next_1.node; - break; - } - case RE_OP_END_LAZY_REPEAT: /* End of a lazy repeat. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - BOOL changed; - BOOL try_body; - int body_status; - RE_Position next_body_position; - BOOL try_tail; - int tail_status; - RE_Position next_tail_position; - RE_BacktrackData* bt_data; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - /* The body has matched successfully at this position. */ - if (!guard_repeat(safe_state, index, rp_data->start, - RE_STATUS_BODY, FALSE)) - return RE_ERROR_MEMORY; - - ++rp_data->count; - - /* Have we advanced through the text or has a capture group change? - */ - changed = rp_data->capture_change != state->capture_change || - state->text_pos != rp_data->start; - - /* The counts are of type size_t, so the format needs to specify - * that. - */ - TRACE(("min is %" PY_FORMAT_SIZE_T "u, max is %" PY_FORMAT_SIZE_T - "u, count is %" PY_FORMAT_SIZE_T "u\n", node->values[1], - node->values[2], rp_data->count)) - - /* Could the body or tail match? */ - try_body = changed && (rp_data->count < node->values[2] || - ~node->values[2] == 0) && !is_repeat_guarded(safe_state, index, - state->text_pos, RE_STATUS_BODY); - if (try_body) { - body_status = try_match(state, &node->next_1, state->text_pos, - &next_body_position); - - if (body_status == RE_ERROR_FAILURE) - try_body = FALSE; - } else - body_status = RE_ERROR_FAILURE; - - try_tail = (!changed || rp_data->count >= node->values[1]); - if (try_tail) { - tail_status = try_match(state, &node->nonstring.next_2, - state->text_pos, &next_tail_position); - - if (tail_status == RE_ERROR_FAILURE) - try_tail = FALSE; - } else - tail_status = RE_ERROR_FAILURE; - - if (!try_body && !try_tail) { - /* Neither the body nor the tail could match. */ - --rp_data->count; - goto backtrack; - } - - if (body_status < 0 || (body_status == 0 && tail_status < 0)) - return RE_ERROR_PARTIAL; - - /* Record info in case we backtrack into the body. */ - if (!add_backtrack(safe_state, RE_OP_BODY_END)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count - 1; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - - if (try_body) { - /* Both the body and the tail could match. */ - if (try_tail) { - /* The tail takes precedence. If the tail fails to match - * then we want to try the body before backtracking - * further. - */ - - /* Record backtracking info for matching the body. */ - if (!add_backtrack(safe_state, RE_OP_MATCH_BODY)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position = next_body_position; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } else { - /* Only the body could match. */ - - /* Record backtracking info in case the body fails to - * match. - */ - if (!add_backtrack(safe_state, RE_OP_BODY_START)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.text_pos = state->text_pos; - - rp_data->capture_change = state->capture_change; - rp_data->start = state->text_pos; - - /* Advance into the body. */ - node = next_body_position.node; - state->text_pos = next_body_position.text_pos; - } - } else { - /* Only the tail could match. */ - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } - break; - } - case RE_OP_END_OF_LINE: /* At the end of a line. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_LINE(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_OF_LINE_U: /* At the end of a line. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_LINE_U(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_OF_STRING: /* At the end of the string. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_STRING(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_OF_STRING_LINE: /* At end of string or final newline. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_STRING_LINE(state, node, - state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_OF_STRING_LINE_U: /* At end of string or final newline. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_STRING_LINE_U(state, node, - state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_END_OF_WORD: /* At the end of a word. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_END_OF_WORD(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_FUZZY: /* Fuzzy matching. */ - { - RE_FuzzyInfo* fuzzy_info; - RE_BacktrackData* bt_data; - TRACE(("%s\n", re_op_text[node->op])) - - fuzzy_info = &state->fuzzy_info; - - /* Save the current fuzzy info. */ - if (!add_backtrack(safe_state, RE_OP_FUZZY)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - memmove(&bt_data->fuzzy.fuzzy_info, fuzzy_info, - sizeof(RE_FuzzyInfo)); - bt_data->fuzzy.index = node->values[0]; - bt_data->fuzzy.text_pos = state->text_pos; - - /* Initialise the new fuzzy info. */ - memset(fuzzy_info->counts, 0, 4 * sizeof(fuzzy_info->counts[0])); - fuzzy_info->total_cost = 0; - fuzzy_info->node = node; - - node = node->next_1.node; - break; - } - case RE_OP_GRAPHEME_BOUNDARY: /* On a grapheme boundary. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_GRAPHEME_BOUNDARY(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_GREEDY_REPEAT: /* Greedy repeat. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - RE_BacktrackData* bt_data; - BOOL try_body; - int body_status; - RE_Position next_body_position; - BOOL try_tail; - int tail_status; - RE_Position next_tail_position; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - /* We might need to backtrack into the head, so save the current - * repeat. - */ - if (!add_backtrack(safe_state, RE_OP_GREEDY_REPEAT)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - - /* Initialise the new repeat. */ - rp_data->count = 0; - rp_data->start = state->text_pos; - rp_data->capture_change = state->capture_change; - - /* Could the body or tail match? */ - try_body = node->values[2] > 0 && !is_repeat_guarded(safe_state, - index, state->text_pos, RE_STATUS_BODY); - if (try_body) { - body_status = try_match(state, &node->next_1, state->text_pos, - &next_body_position); - - if (body_status == RE_ERROR_FAILURE) - try_body = FALSE; - } else - body_status = RE_ERROR_FAILURE; - - try_tail = node->values[1] == 0; - if (try_tail) { - tail_status = try_match(state, &node->nonstring.next_2, - state->text_pos, &next_tail_position); - - if (tail_status == RE_ERROR_FAILURE) - try_tail = FALSE; - } else - tail_status = RE_ERROR_FAILURE; - if (!try_body && !try_tail) - /* Neither the body nor the tail could match. */ - goto backtrack; - - if (body_status < 0 || (body_status == 0 && tail_status < 0)) - return RE_ERROR_PARTIAL; - - if (try_body) { - if (try_tail) { - /* Both the body and the tail could match, but the body - * takes precedence. If the body fails to match then we - * want to try the tail before backtracking further. - */ - - /* Record backtracking info for matching the tail. */ - if (!add_backtrack(safe_state, RE_OP_MATCH_TAIL)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position = next_tail_position; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - } - - /* Advance into the body. */ - node = next_body_position.node; - state->text_pos = next_body_position.text_pos; - } else { - /* Only the tail could match. */ - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } - break; - } - case RE_OP_GREEDY_REPEAT_ONE: /* Greedy repeat for one character. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - size_t count; - BOOL is_partial; - BOOL match; - RE_BacktrackData* bt_data; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - if (is_repeat_guarded(safe_state, index, state->text_pos, - RE_STATUS_BODY)) - goto backtrack; - - /* Count how many times the character repeats, up to the maximum. - */ - count = count_one(state, node->nonstring.next_2.node, - state->text_pos, node->values[2], &is_partial); - if (is_partial) { - state->text_pos += (Py_ssize_t)count * node->step; - return RE_ERROR_PARTIAL; - } - - /* Unmatch until it's not guarded. */ - match = FALSE; - for (;;) { - if (count < node->values[1]) - /* The number of repeats is below the minimum. */ - break; - - if (!is_repeat_guarded(safe_state, index, state->text_pos + - (Py_ssize_t)count * node->step, RE_STATUS_TAIL)) { - /* It's not guarded at this position. */ - match = TRUE; - break; - } - - if (count == 0) - break; - - --count; - } - - if (!match) { - /* The repeat has failed to match at this position. */ - if (!guard_repeat(safe_state, index, state->text_pos, - RE_STATUS_BODY, TRUE)) - return RE_ERROR_MEMORY; - goto backtrack; - } - - /* Record the backtracking info. */ - if (!add_backtrack(safe_state, RE_OP_GREEDY_REPEAT_ONE)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position.node = node; - bt_data->repeat.index = index; - bt_data->repeat.text_pos = rp_data->start; - bt_data->repeat.count = rp_data->count; - - rp_data->start = state->text_pos; - rp_data->count = count; - - /* Advance into the tail. */ - state->text_pos += (Py_ssize_t)count * node->step; - node = node->next_1.node; - break; - } - case RE_OP_GROUP_CALL: /* Group call. */ - { - size_t index; - size_t g; - size_t r; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - index = node->values[0]; - - /* Save the capture groups and repeat guards. */ - if (!push_group_return(safe_state, node->next_1.node)) - return RE_ERROR_MEMORY; - - /* Clear the capture groups for the group call. They'll be restored - * on return. - */ - for (g = 0; g < state->pattern->true_group_count; g++) { - RE_GroupData* group; - - group = &state->groups[g]; - group->span.start = -1; - group->span.end = -1; - group->current_capture = -1; - } - - /* Clear the repeat guards for the group call. They'll be restored - * on return. - */ - for (r = 0; r < state->pattern->repeat_count; r++) { - RE_RepeatData* repeat; - - repeat = &state->repeats[r]; - repeat->body_guard_list.count = 0; - repeat->body_guard_list.last_text_pos = -1; - repeat->tail_guard_list.count = 0; - repeat->tail_guard_list.last_text_pos = -1; - } - - /* Call a group, skipping its CALL_REF node. */ - node = pattern->call_ref_info[index].node->next_1.node; - - if (!add_backtrack(safe_state, RE_OP_GROUP_CALL)) - return RE_ERROR_BACKTRACKING; - break; - } - case RE_OP_GROUP_EXISTS: /* Capture group exists. */ - { - RE_GroupData* group; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture >= 0) - node = node->next_1.node; - else - node = node->nonstring.next_2.node; - break; - } - case RE_OP_GROUP_RETURN: /* Group return. */ - { - RE_Node* return_node; - RE_BacktrackData* bt_data; - TRACE(("%s\n", re_op_text[node->op])) - - return_node = top_group_return(state); - - if (!add_backtrack(safe_state, RE_OP_GROUP_RETURN)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->group_call.node = return_node; - bt_data->group_call.capture_change = state->capture_change; - - if (return_node) { - /* The group was called. */ - node = return_node; - - /* Save the groups. */ - if (!push_groups(safe_state)) - return RE_ERROR_MEMORY; - - /* Save the repeats. */ - if (!push_repeats(safe_state)) - return RE_ERROR_MEMORY; - } else - /* The group was not called. */ - node = node->next_1.node; - - pop_group_return(state); - break; - } - case RE_OP_LAZY_REPEAT: /* Lazy repeat. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - RE_BacktrackData* bt_data; - BOOL try_body; - int body_status; - RE_Position next_body_position; - BOOL try_tail; - int tail_status; - RE_Position next_tail_position; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - /* We might need to backtrack into the head, so save the current - * repeat. - */ - if (!add_backtrack(safe_state, RE_OP_LAZY_REPEAT)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - - /* Initialise the new repeat. */ - rp_data->count = 0; - rp_data->start = state->text_pos; - rp_data->capture_change = state->capture_change; - - /* Could the body or tail match? */ - try_body = node->values[2] > 0 && !is_repeat_guarded(safe_state, - index, state->text_pos, RE_STATUS_BODY); - if (try_body) { - body_status = try_match(state, &node->next_1, state->text_pos, - &next_body_position); - - if (body_status == RE_ERROR_FAILURE) - try_body = FALSE; - } else - body_status = RE_ERROR_FAILURE; - - try_tail = node->values[1] == 0; - if(try_tail) { - tail_status = try_match(state, &node->nonstring.next_2, - state->text_pos, &next_tail_position); - - if (tail_status == RE_ERROR_FAILURE) - try_tail = FALSE; - } else - tail_status = RE_ERROR_FAILURE; - - if (!try_body && !try_tail) - /* Neither the body nor the tail could match. */ - goto backtrack; - - if (body_status < 0 || (body_status == 0 && tail_status < 0)) - return RE_ERROR_PARTIAL; - - if (try_body) { - if (try_tail) { - /* Both the body and the tail could match, but the tail - * takes precedence. If the tail fails to match then we - * want to try the body before backtracking further. - */ - - /* Record backtracking info for matching the tail. */ - if (!add_backtrack(safe_state, RE_OP_MATCH_BODY)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position = next_body_position; - bt_data->repeat.index = index; - bt_data->repeat.count = rp_data->count; - bt_data->repeat.start = rp_data->start; - bt_data->repeat.capture_change = rp_data->capture_change; - bt_data->repeat.text_pos = state->text_pos; - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } else { - /* Advance into the body. */ - node = next_body_position.node; - state->text_pos = next_body_position.text_pos; - } - } else { - /* Only the tail could match. */ - - /* Advance into the tail. */ - node = next_tail_position.node; - state->text_pos = next_tail_position.text_pos; - } - break; - } - case RE_OP_LAZY_REPEAT_ONE: /* Lazy repeat for one character. */ - { - RE_CODE index; - RE_RepeatData* rp_data; - size_t count; - BOOL is_partial; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Repeat indexes are 0-based. */ - index = node->values[0]; - rp_data = &state->repeats[index]; - - if (is_repeat_guarded(safe_state, index, state->text_pos, - RE_STATUS_BODY)) - goto backtrack; - - /* Count how many times the character repeats, up to the minimum. - */ - count = count_one(state, node->nonstring.next_2.node, - state->text_pos, node->values[1], &is_partial); - if (is_partial) { - state->text_pos += (Py_ssize_t)count * node->step; - return RE_ERROR_PARTIAL; - } - - /* Have we matched at least the minimum? */ - if (count < node->values[1]) { - /* The repeat has failed to match at this position. */ - if (!guard_repeat(safe_state, index, state->text_pos, - RE_STATUS_BODY, TRUE)) - return RE_ERROR_MEMORY; - goto backtrack; - } - - if (count < node->values[2]) { - /* The match is shorter than the maximum, so we might need to - * backtrack the repeat to consume more. - */ - RE_BacktrackData* bt_data; - - /* Get the offset to the repeat values in the context. */ - rp_data = &state->repeats[index]; - if (!add_backtrack(safe_state, RE_OP_LAZY_REPEAT_ONE)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->repeat.position.node = node; - bt_data->repeat.index = index; - bt_data->repeat.text_pos = rp_data->start; - bt_data->repeat.count = rp_data->count; - - rp_data->start = state->text_pos; - rp_data->count = count; - } - - /* Advance into the tail. */ - state->text_pos += (Py_ssize_t)count * node->step; - node = node->next_1.node; - break; - } - case RE_OP_LOOKAROUND: /* Lookaround. */ - { - RE_Info info; - size_t capture_change; - Py_ssize_t saved_slice_start; - Py_ssize_t saved_slice_end; - Py_ssize_t saved_text_pos; - BOOL too_few_errors; - int status; - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - /* Save the groups. */ - if (!push_groups(safe_state)) - return RE_ERROR_MEMORY; - - capture_change = state->capture_change; - - /* Save the other info. */ - save_info(state, &info); - - saved_slice_start = state->slice_start; - saved_slice_end = state->slice_end; - saved_text_pos = state->text_pos; - state->slice_start = 0; - state->slice_end = state->text_length; - state->must_advance = FALSE; - - too_few_errors = state->too_few_errors; - - status = basic_match(safe_state, node->nonstring.next_2.node, - FALSE, TRUE); - if (status < 0) - return status; - - reset_guards(state, node->values + 1); - - state->text_pos = saved_text_pos; - state->slice_end = saved_slice_end; - state->slice_start = saved_slice_start; - - /* Restore the other info. */ - restore_info(state, &info); - - if (node->match) { - /* It's a positive lookaround. */ - if (status == RE_ERROR_SUCCESS) { - /* It succeeded, so the groups and certain flags may have - * changed. - */ - if (!add_backtrack(safe_state, RE_OP_LOOKAROUND)) - return RE_ERROR_BACKTRACKING; - - /* We'll restore the groups and flags on backtracking. */ - state->backtrack->lookaround.too_few_errors = - too_few_errors; - state->backtrack->lookaround.capture_change = - capture_change; - } else { - /* It failed, so the groups and certain flags haven't - * changed. - */ - drop_groups(state); - goto backtrack; - } - } else { - /* It's a negative lookaround. */ - if (status == RE_ERROR_SUCCESS) { - /* It succeeded, so the groups and certain flags may have - * changed. We need to restore them. - */ - pop_groups(state); - state->too_few_errors = too_few_errors; - state->capture_change = capture_change; - goto backtrack; - } else - /* It failed, so the groups and certain flags haven't - * changed. - */ - drop_groups(state); - } - - node = node->next_1.node; - break; - } - case RE_OP_PROPERTY: /* A property. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - matches_PROPERTY(encoding, node, char_at(state->text, - state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_PROPERTY_IGN: /* A property, ignoring case. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - matches_PROPERTY_IGN(encoding, node, char_at(state->text, - state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_PROPERTY_IGN_REV: /* A property, backwards, ignoring case. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_PROPERTY_IGN(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_PROPERTY_REV: /* A property, backwards. */ - TRACE(("%s %d %d\n", re_op_text[node->op], node->match, - node->values[0])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_PROPERTY(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_RANGE: /* A range. */ - TRACE(("%s %d %d %d\n", re_op_text[node->op], node->match, - node->values[0], node->values[1])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && matches_RANGE(encoding, - node, char_at(state->text, state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_RANGE_IGN: /* A range, ignoring case. */ - TRACE(("%s %d %d %d\n", re_op_text[node->op], node->match, - node->values[0], node->values[1])) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - matches_RANGE_IGN(encoding, node, char_at(state->text, - state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_RANGE_IGN_REV: /* A range, backwards, ignoring case. */ - TRACE(("%s %d %d %d\n", re_op_text[node->op], node->match, - node->values[0], node->values[1])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_RANGE_IGN(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_RANGE_REV: /* A range, backwards. */ - TRACE(("%s %d %d %d\n", re_op_text[node->op], node->match, - node->values[0], node->values[1])) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && matches_RANGE(encoding, - node, char_at(state->text, state->text_pos - 1)) == node->match) - { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_REF_GROUP: /* Reference to a capture group. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - if (string_pos < 0) - string_pos = span->start; - - /* Try comparing. */ - while (string_pos < span->end) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && same_char(encoding, - char_at(state->text, state->text_pos), char_at(state->text, - string_pos))) { - ++string_pos; - ++state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_REF_GROUP_FLD: /* Reference to a capture group, ignoring case. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - int folded_len; - int gfolded_len; - Py_UCS4 folded[RE_MAX_FOLDED]; - Py_UCS4 gfolded[RE_MAX_FOLDED]; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - full_case_fold = encoding->full_case_fold; - - if (string_pos < 0) { - string_pos = span->start; - folded_pos = 0; - folded_len = 0; - gfolded_pos = 0; - gfolded_len = 0; - } else { - folded_len = full_case_fold(char_at(state->text, - state->text_pos), folded); - gfolded_len = full_case_fold(char_at(state->text, string_pos), - gfolded); - } - - /* Try comparing. */ - while (string_pos < span->end) { - /* Case-fold at current position in text. */ - if (folded_pos >= folded_len) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end) - folded_len = full_case_fold(char_at(state->text, - state->text_pos), folded); - else - folded_len = 0; - - folded_pos = 0; - } - - /* Case-fold at current position in group. */ - if (gfolded_pos >= gfolded_len) { - gfolded_len = full_case_fold(char_at(state->text, - string_pos), gfolded); - gfolded_pos = 0; - } - - if (folded_pos < folded_len && folded[folded_pos] == - gfolded[gfolded_pos]) { - ++folded_pos; - ++gfolded_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_group_fld(safe_state, search, - &state->text_pos, node, &folded_pos, folded_len, - &string_pos, &gfolded_pos, gfolded_len, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - - if (folded_pos >= folded_len && folded_len > 0) - ++state->text_pos; - - if (gfolded_pos >= gfolded_len) - ++string_pos; - } - - string_pos = -1; - - if (folded_pos < folded_len || gfolded_pos < gfolded_len) - goto backtrack; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_REF_GROUP_FLD_REV: /* Reference to a capture group, ignoring case. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - int folded_len; - int gfolded_len; - Py_UCS4 folded[RE_MAX_FOLDED]; - Py_UCS4 gfolded[RE_MAX_FOLDED]; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - full_case_fold = encoding->full_case_fold; - - if (string_pos < 0) { - string_pos = span->end; - folded_pos = 0; - folded_len = 0; - gfolded_pos = 0; - gfolded_len = 0; - } else { - folded_len = full_case_fold(char_at(state->text, - state->text_pos - 1), folded); - gfolded_len = full_case_fold(char_at(state->text, string_pos - - 1), gfolded); - } - - /* Try comparing. */ - while (string_pos > span->start) { - /* Case-fold at current position in text. */ - if (folded_pos <= 0) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start) - folded_len = full_case_fold(char_at(state->text, - state->text_pos - 1), folded); - else - folded_len = 0; - - folded_pos = folded_len; - } - - /* Case-fold at current position in group. */ - if (gfolded_pos <= 0) { - gfolded_len = full_case_fold(char_at(state->text, - string_pos - 1), gfolded); - gfolded_pos = gfolded_len; - } - - if (folded_pos > 0 && folded[folded_pos - 1] == - gfolded[gfolded_pos - 1]) { - --folded_pos; - --gfolded_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_group_fld(safe_state, search, - &state->text_pos, node, &folded_pos, folded_len, - &string_pos, &gfolded_pos, gfolded_len, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - - if (folded_pos <= 0 && folded_len > 0) - --state->text_pos; - - if (gfolded_pos <= 0) - --string_pos; - } - - string_pos = -1; - - if (folded_pos > 0 || gfolded_pos > 0) - goto backtrack; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_REF_GROUP_IGN: /* Reference to a capture group, ignoring case. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - if (string_pos < 0) - string_pos = span->start; - - /* Try comparing. */ - while (string_pos < span->end) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - same_char_ign(encoding, char_at(state->text, - state->text_pos), char_at(state->text, string_pos))) { - ++string_pos; - ++state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_REF_GROUP_IGN_REV: /* Reference to a capture group, ignoring case. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - if (string_pos < 0) - string_pos = span->end; - - /* Try comparing. */ - while (string_pos > span->start) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - same_char_ign(encoding, char_at(state->text, state->text_pos - - 1), char_at(state->text, string_pos - 1))) { - --string_pos; - --state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_REF_GROUP_REV: /* Reference to a capture group. */ - { - RE_GroupData* group; - RE_GroupSpan* span; - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - * - * Check whether the captured text, if any, exists at this position - * in the string. - */ - - /* Did the group capture anything? */ - group = &state->groups[node->values[0] - 1]; - if (group->current_capture < 0) - goto backtrack; - - span = &group->captures[group->current_capture]; - - if (string_pos < 0) - string_pos = span->end; - - /* Try comparing. */ - while (string_pos > span->start) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && same_char(encoding, - char_at(state->text, state->text_pos - 1), - char_at(state->text, string_pos - 1))) { - --string_pos; - --state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_SEARCH_ANCHOR: /* At the start of the search. */ - TRACE(("%s %d\n", re_op_text[node->op], node->values[0])) - - if (state->text_pos == state->search_anchor) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_SET_DIFF: /* Character set. */ - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && matches_SET(encoding, - node, char_at(state->text, state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_SET_DIFF_IGN: /* Character set, ignoring case. */ - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION_IGN: - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - if (state->text_pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && matches_SET_IGN(encoding, - node, char_at(state->text, state->text_pos)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_SET_DIFF_IGN_REV: /* Character set, ignoring case. */ - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_UNION_IGN_REV: - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - matches_SET_IGN(encoding, node, char_at(state->text, - state->text_pos - 1)) == node->match) { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_SET_DIFF_REV: /* Character set. */ - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_REV: - TRACE(("%s %d\n", re_op_text[node->op], node->match)) - - if (state->text_pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && matches_SET(encoding, - node, char_at(state->text, state->text_pos - 1)) == node->match) - { - state->text_pos += node->step; - node = node->next_1.node; - } else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_START_GROUP: /* Start of a capture group. */ - { - RE_CODE private_index; - RE_CODE public_index; - RE_GroupData* group; - RE_BacktrackData* bt_data; - TRACE(("%s %d\n", re_op_text[node->op], node->values[1])) - - /* Capture group indexes are 1-based (excluding group 0, which is - * the entire matched string). - */ - private_index = node->values[0]; - public_index = node->values[1]; - group = &state->groups[private_index - 1]; - - if (!add_backtrack(safe_state, RE_OP_START_GROUP)) - return RE_ERROR_BACKTRACKING; - bt_data = state->backtrack; - bt_data->group.private_index = private_index; - bt_data->group.public_index = public_index; - bt_data->group.text_pos = group->span.start; - bt_data->group.capture = (BOOL)node->values[2]; - bt_data->group.current_capture = group->current_capture; - - if (pattern->group_info[private_index - 1].referenced && - group->span.start != state->text_pos) - ++state->capture_change; - group->span.start = state->text_pos; - - /* Save the capture? */ - if (node->values[2]) { - group->current_capture = (Py_ssize_t)group->capture_count; - if (!save_capture(safe_state, private_index, public_index)) - return RE_ERROR_MEMORY; - } - - node = node->next_1.node; - break; - } - case RE_OP_START_OF_LINE: /* At the start of a line. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_START_OF_LINE(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_START_OF_LINE_U: /* At the start of a line. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_START_OF_LINE_U(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_START_OF_STRING: /* At the start of the string. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_START_OF_STRING(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_START_OF_WORD: /* At the start of a word. */ - TRACE(("%s\n", re_op_text[node->op])) - - status = try_match_START_OF_WORD(state, node, state->text_pos); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS) - node = node->next_1.node; - else if (node->status & RE_STATUS_FUZZY) { - status = fuzzy_match_item(safe_state, search, &state->text_pos, - &node, 0); - if (status < 0) - return status; - - if (!node) - goto backtrack; - } else - goto backtrack; - break; - case RE_OP_STRING: /* A string. */ - { - Py_ssize_t length; - RE_CODE* values; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - if (string_pos < 0) - string_pos = 0; - - values = node->values; - - /* Try comparing. */ - while (string_pos < length) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - same_char(encoding, char_at(state->text, - state->text_pos), values[string_pos])) { - ++string_pos; - ++state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_FLD: /* A string, ignoring case. */ - { - Py_ssize_t length; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - RE_CODE* values; - int folded_len; - Py_UCS4 folded[RE_MAX_FOLDED]; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - full_case_fold = encoding->full_case_fold; - - if (string_pos < 0) { - string_pos = 0; - folded_pos = 0; - folded_len = 0; - } else { - folded_len = full_case_fold(char_at(state->text, - state->text_pos), folded); - if (folded_pos >= folded_len) { - if (state->text_pos >= state->slice_end) - goto backtrack; - - ++state->text_pos; - folded_pos = 0; - folded_len = 0; - } - } - - values = node->values; - - /* Try comparing. */ - while (string_pos < length) { - if (folded_pos >= folded_len) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - folded_len = full_case_fold(char_at(state->text, - state->text_pos), folded); - folded_pos = 0; - } - - if (same_char_ign(encoding, folded[folded_pos], - values[string_pos])) { - ++string_pos; - ++folded_pos; - - if (folded_pos >= folded_len) - ++state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string_fld(safe_state, search, - &state->text_pos, node, &string_pos, &folded_pos, - folded_len, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - - if (folded_pos >= folded_len) - ++state->text_pos; - } else { - string_pos = -1; - goto backtrack; - } - } - - if (node->status & RE_STATUS_FUZZY) { - while (folded_pos < folded_len) { - BOOL matched; - - if (!fuzzy_match_string_fld(safe_state, search, - &state->text_pos, node, &string_pos, &folded_pos, - folded_len, &matched, 1)) - return RE_ERROR_BACKTRACKING; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - - if (folded_pos >= folded_len) - ++state->text_pos; - } - } - - string_pos = -1; - - if (folded_pos < folded_len) - goto backtrack; - } - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_FLD_REV: /* A string, ignoring case. */ - { - Py_ssize_t length; - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - RE_CODE* values; - int folded_len; - Py_UCS4 folded[RE_MAX_FOLDED]; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - full_case_fold = encoding->full_case_fold; - - if (string_pos < 0) { - string_pos = length; - folded_pos = 0; - folded_len = 0; - } else { - folded_len = full_case_fold(char_at(state->text, - state->text_pos - 1), folded); - if (folded_pos <= 0) { - if (state->text_pos <= state->slice_start) - goto backtrack; - - --state->text_pos; - folded_pos = 0; - folded_len = 0; - } - } - - values = node->values; - - /* Try comparing. */ - while (string_pos > 0) { - if (folded_pos <= 0) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - folded_len = full_case_fold(char_at(state->text, - state->text_pos - 1), folded); - folded_pos = folded_len; - } - - if (same_char_ign(encoding, folded[folded_pos - 1], - values[string_pos - 1])) { - --string_pos; - --folded_pos; - - if (folded_pos <= 0) - --state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string_fld(safe_state, search, - &state->text_pos, node, &string_pos, &folded_pos, - folded_len, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - - if (folded_pos <= 0) - --state->text_pos; - } else { - string_pos = -1; - goto backtrack; - } - } - - if (node->status & RE_STATUS_FUZZY) { - while (folded_pos > 0) { - BOOL matched; - - if (!fuzzy_match_string_fld(safe_state, search, - &state->text_pos, node, &string_pos, &folded_pos, - folded_len, &matched, -1)) - return RE_ERROR_BACKTRACKING; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - - if (folded_pos <= 0) - --state->text_pos; - } - } - - string_pos = -1; - - if (folded_pos > 0) - goto backtrack; - } - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_IGN: /* A string, ignoring case. */ - { - Py_ssize_t length; - RE_CODE* values; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - if (string_pos < 0) - string_pos = 0; - - values = node->values; - - /* Try comparing. */ - while (string_pos < length) { - if (state->text_pos >= state->text_length && - state->partial_side == RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (state->text_pos < state->slice_end && - same_char_ign(encoding, char_at(state->text, - state->text_pos), values[string_pos])) { - ++string_pos; - ++state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, 1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_IGN_REV: /* A string, ignoring case. */ - { - Py_ssize_t length; - RE_CODE* values; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - if (string_pos < 0) - string_pos = length; - - values = node->values; - - /* Try comparing. */ - while (string_pos > 0) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - same_char_ign(encoding, char_at(state->text, - state->text_pos - 1), values[string_pos - 1])) { - --string_pos; - --state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_REV: /* A string. */ - { - Py_ssize_t length; - RE_CODE* values; - TRACE(("%s %d\n", re_op_text[node->op], node->value_count)) - - if ((node->status & RE_STATUS_REQUIRED) && state->text_pos == - state->req_pos && string_pos < 0) - state->text_pos = state->req_end; - else { - length = (Py_ssize_t)node->value_count; - - if (string_pos < 0) - string_pos = length; - - values = node->values; - - /* Try comparing. */ - while (string_pos > 0) { - if (state->text_pos <= 0 && state->partial_side == - RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (state->text_pos > state->slice_start && - same_char(encoding, char_at(state->text, state->text_pos - - 1), values[string_pos - 1])) { - --string_pos; - --state->text_pos; - } else if (node->status & RE_STATUS_FUZZY) { - BOOL matched; - - status = fuzzy_match_string(safe_state, search, - &state->text_pos, node, &string_pos, &matched, -1); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (!matched) { - string_pos = -1; - goto backtrack; - } - } else { - string_pos = -1; - goto backtrack; - } - } - } - - string_pos = -1; - - /* Successful match. */ - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET: /* Member of a string set. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_fwdrev(safe_state, node, FALSE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET_FLD: /* Member of a string set, ignoring case. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_fld_fwdrev(safe_state, node, FALSE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET_FLD_REV: /* Member of a string set, ignoring case. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_fld_fwdrev(safe_state, node, TRUE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET_IGN: /* Member of a string set, ignoring case. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_ign_fwdrev(safe_state, node, FALSE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET_IGN_REV: /* Member of a string set, ignoring case. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_ign_fwdrev(safe_state, node, TRUE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_STRING_SET_REV: /* Member of a string set. */ - { - int status; - TRACE(("%s\n", re_op_text[node->op])) - - status = string_set_match_fwdrev(safe_state, node, TRUE); - if (status < 0) - return status; - if (status == 0) - goto backtrack; - node = node->next_1.node; - break; - } - case RE_OP_SUCCESS: /* Success. */ - /* Must the match advance past its start? */ - TRACE(("%s\n", re_op_text[node->op])) - - if (state->text_pos == state->search_anchor && state->must_advance) - goto backtrack; - - if (state->match_all && !recursive_call) { - /* We want to match all of the slice. */ - if (state->reverse) { - if (state->text_pos != state->slice_start) - goto backtrack; - } else { - if (state->text_pos != state->slice_end) - goto backtrack; - } - } - - return RE_ERROR_SUCCESS; - default: /* Illegal opcode! */ - TRACE(("UNKNOWN OP %d\n", node->op)) - return RE_ERROR_ILLEGAL; - } - } - -backtrack: - for (;;) { - RE_BacktrackData* bt_data; - TRACE(("BACKTRACK ")) - - /* Should we abort the matching? */ - ++state->iterations; - - if (state->iterations == 0 && safe_check_signals(safe_state)) - return RE_ERROR_INTERRUPTED; - - bt_data = last_backtrack(state); - - switch (bt_data->op) { - case RE_OP_ANY: /* Any character except a newline. */ - case RE_OP_ANY_ALL: /* Any character at all. */ - case RE_OP_ANY_ALL_REV: /* Any character at all, backwards. */ - case RE_OP_ANY_REV: /* Any character except a newline, backwards. */ - case RE_OP_ANY_U: /* Any character except a line separator. */ - case RE_OP_ANY_U_REV: /* Any character except a line separator, backwards. */ - case RE_OP_CHARACTER: /* A character. */ - case RE_OP_CHARACTER_IGN: /* A character, ignoring case. */ - case RE_OP_CHARACTER_IGN_REV: /* A character, ignoring case, backwards. */ - case RE_OP_CHARACTER_REV: /* A character, backwards. */ - case RE_OP_PROPERTY: /* A property. */ - case RE_OP_PROPERTY_IGN: /* A property, ignoring case. */ - case RE_OP_PROPERTY_IGN_REV: /* A property, ignoring case, backwards. */ - case RE_OP_PROPERTY_REV: /* A property, backwards. */ - case RE_OP_RANGE: /* A range. */ - case RE_OP_RANGE_IGN: /* A range, ignoring case. */ - case RE_OP_RANGE_IGN_REV: /* A range, ignoring case, backwards. */ - case RE_OP_RANGE_REV: /* A range, backwards. */ - case RE_OP_SET_DIFF: /* Set difference. */ - case RE_OP_SET_DIFF_IGN: /* Set difference, ignoring case. */ - case RE_OP_SET_DIFF_IGN_REV: /* Set difference, ignoring case, backwards. */ - case RE_OP_SET_DIFF_REV: /* Set difference, backwards. */ - case RE_OP_SET_INTER: /* Set intersection. */ - case RE_OP_SET_INTER_IGN: /* Set intersection, ignoring case. */ - case RE_OP_SET_INTER_IGN_REV: /* Set intersection, ignoring case, backwards. */ - case RE_OP_SET_INTER_REV: /* Set intersection, backwards. */ - case RE_OP_SET_SYM_DIFF: /* Set symmetric difference. */ - case RE_OP_SET_SYM_DIFF_IGN: /* Set symmetric difference, ignoring case. */ - case RE_OP_SET_SYM_DIFF_IGN_REV: /* Set symmetric difference, ignoring case, backwards. */ - case RE_OP_SET_SYM_DIFF_REV: /* Set symmetric difference, backwards. */ - case RE_OP_SET_UNION: /* Set union. */ - case RE_OP_SET_UNION_IGN: /* Set union, ignoring case. */ - case RE_OP_SET_UNION_IGN_REV: /* Set union, ignoring case, backwards. */ - case RE_OP_SET_UNION_REV: /* Set union, backwards. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - status = retry_fuzzy_match_item(safe_state, search, - &state->text_pos, &node, TRUE); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (node) - goto advance; - break; - case RE_OP_ATOMIC: /* Atomic subpattern. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - /* Restore the groups and certain flags and then backtrack. */ - pop_groups(state); - state->too_few_errors = bt_data->atomic.too_few_errors; - state->capture_change = bt_data->atomic.capture_change; - discard_backtrack(state); - break; - case RE_OP_BODY_END: - { - RE_RepeatData* rp_data; - TRACE(("%s %d\n", re_op_text[bt_data->op], bt_data->repeat.index)) - - /* We're backtracking into the body. */ - rp_data = &state->repeats[bt_data->repeat.index]; - - /* Restore the repeat info. */ - rp_data->count = bt_data->repeat.count; - rp_data->start = bt_data->repeat.start; - rp_data->capture_change = bt_data->repeat.capture_change; - - discard_backtrack(state); - break; - } - case RE_OP_BODY_START: - { - TRACE(("%s %d\n", re_op_text[bt_data->op], bt_data->repeat.index)) - - /* The body may have failed to match at this position. */ - if (!guard_repeat(safe_state, bt_data->repeat.index, - bt_data->repeat.text_pos, RE_STATUS_BODY, TRUE)) - return RE_ERROR_MEMORY; - - discard_backtrack(state); - break; - } - case RE_OP_BOUNDARY: /* On a word boundary. */ - case RE_OP_DEFAULT_BOUNDARY: /* On a default word boundary. */ - case RE_OP_DEFAULT_END_OF_WORD: /* At a default end of a word. */ - case RE_OP_DEFAULT_START_OF_WORD: /* At a default start of a word. */ - case RE_OP_END_OF_LINE: /* At the end of a line. */ - case RE_OP_END_OF_LINE_U: /* At the end of a line. */ - case RE_OP_END_OF_STRING: /* At the end of the string. */ - case RE_OP_END_OF_STRING_LINE: /* At end of string or final newline. */ - case RE_OP_END_OF_STRING_LINE_U: /* At end of string or final newline. */ - case RE_OP_END_OF_WORD: /* At end of a word. */ - case RE_OP_GRAPHEME_BOUNDARY: /* On a grapheme boundary. */ - case RE_OP_SEARCH_ANCHOR: /* At the start of the search. */ - case RE_OP_START_OF_LINE: /* At the start of a line. */ - case RE_OP_START_OF_LINE_U: /* At the start of a line. */ - case RE_OP_START_OF_STRING: /* At the start of the string. */ - case RE_OP_START_OF_WORD: /* At start of a word. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - status = retry_fuzzy_match_item(safe_state, search, - &state->text_pos, &node, FALSE); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (node) - goto advance; - break; - case RE_OP_BRANCH: /* 2-way branch. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - node = bt_data->branch.position.node; - state->text_pos = bt_data->branch.position.text_pos; - discard_backtrack(state); - goto advance; - case RE_OP_CALL_REF: /* A group call ref. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - pop_group_return(state); - discard_backtrack(state); - break; - case RE_OP_END_FUZZY: /* End of fuzzy matching. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - state->total_fuzzy_counts[RE_FUZZY_SUB] -= - state->fuzzy_info.counts[RE_FUZZY_SUB]; - state->total_fuzzy_counts[RE_FUZZY_INS] -= - state->fuzzy_info.counts[RE_FUZZY_INS]; - state->total_fuzzy_counts[RE_FUZZY_DEL] -= - state->fuzzy_info.counts[RE_FUZZY_DEL]; - - /* We need to retry the fuzzy match. */ - status = retry_fuzzy_insert(safe_state, &state->text_pos, &node); - if (status < 0) - return RE_ERROR_PARTIAL; - - /* If there were too few errors, in the fuzzy section, try again. - */ - if (state->too_few_errors) { - state->too_few_errors = FALSE; - goto backtrack; - } - - if (node) { - state->total_fuzzy_counts[RE_FUZZY_SUB] += - state->fuzzy_info.counts[RE_FUZZY_SUB]; - state->total_fuzzy_counts[RE_FUZZY_INS] += - state->fuzzy_info.counts[RE_FUZZY_INS]; - state->total_fuzzy_counts[RE_FUZZY_DEL] += - state->fuzzy_info.counts[RE_FUZZY_DEL]; - - node = node->next_1.node; - goto advance; - } - break; - case RE_OP_END_GROUP: /* End of a capture group. */ - { - RE_CODE private_index; - RE_GroupData* group; - TRACE(("%s %d\n", re_op_text[bt_data->op], - bt_data->group.public_index)) - - private_index = bt_data->group.private_index; - group = &state->groups[private_index - 1]; - - /* Unsave the capture? */ - if (bt_data->group.capture) - unsave_capture(state, bt_data->group.private_index, - bt_data->group.public_index); - - if (pattern->group_info[private_index - 1].referenced && - group->span.end != bt_data->group.text_pos) - --state->capture_change; - group->span.end = bt_data->group.text_pos; - group->current_capture = bt_data->group.current_capture; - - discard_backtrack(state); - break; - } - case RE_OP_FAILURE: - { - Py_ssize_t end_pos; - TRACE(("%s\n", re_op_text[bt_data->op])) - - /* Do we have to advance? */ - if (!search) - return RE_ERROR_FAILURE; - - /* Can we advance? */ - state->text_pos = state->match_pos; - end_pos = state->reverse ? state->slice_start : state->slice_end; - if (state->text_pos == end_pos) - return RE_ERROR_FAILURE; - - /* Skip over any repeated leading characters. */ - switch (start_node->op) { - case RE_OP_GREEDY_REPEAT_ONE: - case RE_OP_LAZY_REPEAT_ONE: - { - size_t count; - BOOL is_partial; - - /* How many characters did the repeat actually match? */ - count = count_one(state, start_node->nonstring.next_2.node, - state->text_pos, start_node->values[2], &is_partial); - - /* If it's fewer than the maximum then skip over those - * characters. - */ - if (count < start_node->values[2]) - state->text_pos += (Py_ssize_t)count * pattern_step; - break; - } - } - - /* Advance and try to match again. */ - state->text_pos += pattern_step; - - goto start_match; - } - case RE_OP_FUZZY: /* Fuzzy matching. */ - { - RE_FuzzyInfo* fuzzy_info; - TRACE(("%s\n", re_op_text[bt_data->op])) - - /* Restore the previous fuzzy info. */ - fuzzy_info = &state->fuzzy_info; - memmove(fuzzy_info, &bt_data->fuzzy.fuzzy_info, - sizeof(RE_FuzzyInfo)); - - discard_backtrack(state); - break; - } - case RE_OP_GREEDY_REPEAT: /* Greedy repeat. */ - case RE_OP_LAZY_REPEAT: /* Lazy repeat. */ - { - RE_RepeatData* rp_data; - TRACE(("%s\n", re_op_text[bt_data->op])) - - /* The repeat failed to match. */ - rp_data = &state->repeats[bt_data->repeat.index]; - - /* The body may have failed to match at this position. */ - if (!guard_repeat(safe_state, bt_data->repeat.index, - bt_data->repeat.text_pos, RE_STATUS_BODY, TRUE)) - return RE_ERROR_MEMORY; - - /* Restore the previous repeat. */ - rp_data->count = bt_data->repeat.count; - rp_data->start = bt_data->repeat.start; - rp_data->capture_change = bt_data->repeat.capture_change; - - discard_backtrack(state); - break; - } - case RE_OP_GREEDY_REPEAT_ONE: /* Greedy repeat for one character. */ - { - RE_RepeatData* rp_data; - size_t count; - Py_ssize_t step; - Py_ssize_t pos; - Py_ssize_t limit; - RE_Node* test; - BOOL match; - BOOL m; - size_t index; - TRACE(("%s\n", re_op_text[bt_data->op])) - - node = bt_data->repeat.position.node; - - rp_data = &state->repeats[bt_data->repeat.index]; - - /* Unmatch one character at a time until the tail could match or we - * have reached the minimum. - */ - state->text_pos = rp_data->start; - - count = rp_data->count; - step = node->step; - pos = state->text_pos + (Py_ssize_t)count * step; - limit = state->text_pos + (Py_ssize_t)node->values[1] * step; - - /* The tail failed to match at this position. */ - if (!guard_repeat(safe_state, bt_data->repeat.index, pos, - RE_STATUS_TAIL, TRUE)) - return RE_ERROR_MEMORY; - - if (count == node->values[1]) { - /* We've backtracked the repeat as far as we can. */ - rp_data->start = bt_data->repeat.text_pos; - rp_data->count = bt_data->repeat.count; - discard_backtrack(state); - break; - } - - test = node->next_1.test; - - m = test->match; - index = node->values[0]; - - match = FALSE; - - if (test->status & RE_STATUS_FUZZY) { - for (;;) { - RE_Position next_position; - - pos -= step; - - if (try_match(state, &node->next_1, pos, &next_position) && - !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - } - } else { - /* A repeated single-character match is often followed by a - * literal, so checking specially for it can be a good - * optimisation when working with long strings. - */ - switch (test->op) { - case RE_OP_CHARACTER: - { - Py_UCS4 ch; - - ch = test->values[0]; - - for (;;) { - --pos; - - if (same_char(encoding, char_at(state->text, pos), ch) - == m && !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - - } - break; - } - case RE_OP_CHARACTER_IGN: - { - Py_UCS4 ch; - - ch = test->values[0]; - - for (;;) { - --pos; - - if (same_char_ign(encoding, char_at(state->text, pos), - ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - - } - break; - } - case RE_OP_CHARACTER_IGN_REV: - { - Py_UCS4 ch; - - ch = test->values[0]; - - for (;;) { - ++pos; - - if (same_char_ign(encoding, char_at(state->text, pos - - 1), ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - - } - break; - } - case RE_OP_CHARACTER_REV: - { - Py_UCS4 ch; - - ch = test->values[0]; - - for (;;) { - ++pos; - - if (same_char(encoding, char_at(state->text, pos - 1), - ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - - } - break; - } - case RE_OP_STRING: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = min_ssize_t(pos, state->slice_end - length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos < limit) - break; - - found = string_search_rev(safe_state, test, pos + - length, limit, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found - length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - --pos; - } - break; - } - case RE_OP_STRING_FLD: - { - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_ssize_t folded_length; - size_t i; - Py_UCS4 folded[RE_MAX_FOLDED]; - - full_case_fold = encoding->full_case_fold; - - folded_length = 0; - for (i = 0; i < test->value_count; i++) - folded_length += full_case_fold(test->values[i], - folded); - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = min_ssize_t(pos, state->slice_end - folded_length); - - for (;;) { - Py_ssize_t found; - Py_ssize_t new_pos; - BOOL is_partial; - - if (pos < limit) - break; - - found = string_search_fld_rev(safe_state, test, pos + - folded_length, limit, &new_pos, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found - folded_length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - --pos; - } - break; - } - case RE_OP_STRING_FLD_REV: - { - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_ssize_t folded_length; - size_t i; - Py_UCS4 folded[RE_MAX_FOLDED]; - - full_case_fold = encoding->full_case_fold; - - folded_length = 0; - for (i = 0; i < test->value_count; i++) - folded_length += full_case_fold(test->values[i], - folded); - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = max_ssize_t(pos, state->slice_start + folded_length); - - for (;;) { - Py_ssize_t found; - Py_ssize_t new_pos; - BOOL is_partial; - - if (pos > limit) - break; - - found = string_search_fld(safe_state, test, pos - - folded_length, limit, &new_pos, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found + folded_length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - ++pos; - } - break; - } - case RE_OP_STRING_IGN: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = min_ssize_t(pos, state->slice_end - length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos < limit) - break; - - found = string_search_ign_rev(safe_state, test, pos + - length, limit, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found - length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - --pos; - } - break; - } - case RE_OP_STRING_IGN_REV: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = max_ssize_t(pos, state->slice_start + length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos > limit) - break; - - found = string_search_ign(safe_state, test, pos - - length, limit, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found + length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - ++pos; - } - break; - } - case RE_OP_STRING_REV: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - pos = max_ssize_t(pos, state->slice_start + length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos > limit) - break; - - found = string_search(safe_state, test, pos - length, - limit, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - pos = found + length; - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - ++pos; - } - break; - } - default: - for (;;) { - RE_Position next_position; - - pos -= step; - - status = try_match(state, &node->next_1, pos, - &next_position); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS && - !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - } - break; - } - } - - if (match) { - count = (size_t)abs_ssize_t(pos - state->text_pos); - - /* The tail could match. */ - if (count > node->values[1]) - /* The match is longer than the minimum, so we might need - * to backtrack the repeat again to consume less. - */ - rp_data->count = count; - else { - /* We've reached or passed the minimum, so we won't need to - * backtrack the repeat again. - */ - rp_data->start = bt_data->repeat.text_pos; - rp_data->count = bt_data->repeat.count; - discard_backtrack(state); - - /* Have we passed the minimum? */ - if (count < node->values[1]) - goto backtrack; - } - - node = node->next_1.node; - state->text_pos = pos; - goto advance; - } else { - /* We've backtracked the repeat as far as we can. */ - rp_data->start = bt_data->repeat.text_pos; - rp_data->count = bt_data->repeat.count; - discard_backtrack(state); - } - break; - } - case RE_OP_GROUP_CALL: /* Group call. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - pop_group_return(state); - discard_backtrack(state); - break; - case RE_OP_GROUP_RETURN: /* Group return. */ - { - RE_Node* return_node; - TRACE(("%s\n", re_op_text[bt_data->op])) - - return_node = bt_data->group_call.node; - - push_group_return(safe_state, return_node); - - if (return_node) { - /* Restore the groups. */ - pop_groups(state); - state->capture_change = bt_data->group_call.capture_change; - - /* Restore the repeats. */ - pop_repeats(state); - } - - discard_backtrack(state); - break; - } - case RE_OP_LAZY_REPEAT_ONE: /* Lazy repeat for one character. */ - { - RE_RepeatData* rp_data; - size_t count; - Py_ssize_t step; - Py_ssize_t pos; - Py_ssize_t available; - size_t max_count; - Py_ssize_t limit; - RE_Node* repeated; - RE_Node* test; - BOOL match; - BOOL m; - size_t index; - TRACE(("%s\n", re_op_text[bt_data->op])) - - node = bt_data->repeat.position.node; - - rp_data = &state->repeats[bt_data->repeat.index]; - - /* Match one character at a time until the tail could match or we - * have reached the maximum. - */ - state->text_pos = rp_data->start; - count = rp_data->count; - - step = node->step; - pos = state->text_pos + (Py_ssize_t)count * step; - available = step > 0 ? state->slice_end - state->text_pos : - state->text_pos - state->slice_start; - max_count = min_size_t((size_t)available, node->values[2]); - limit = state->text_pos + (Py_ssize_t)max_count * step; - - repeated = node->nonstring.next_2.node; - - test = node->next_1.test; - - m = test->match; - index = node->values[0]; - - match = FALSE; - - if (test->status & RE_STATUS_FUZZY) { - for (;;) { - RE_Position next_position; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - pos += step; - - status = try_match(state, &node->next_1, pos, - &next_position); - if (status < 0) - return status; - - if (status == RE_ERROR_SUCCESS && - !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - } - } else { - /* A repeated single-character match is often followed by a - * literal, so checking specially for it can be a good - * optimisation when working with long strings. - */ - switch (test->op) { - case RE_OP_CHARACTER: - { - Py_UCS4 ch; - - ch = test->values[0]; - - /* The tail is a character. We don't want to go off the end - * of the slice. - */ - limit = min_ssize_t(limit, state->slice_end - 1); - - for (;;) { - if (pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (pos >= limit) - break; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - ++pos; - - if (same_char(encoding, char_at(state->text, pos), ch) - == m && !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_CHARACTER_IGN: - { - Py_UCS4 ch; - - ch = test->values[0]; - - /* The tail is a character. We don't want to go off the end - * of the slice. - */ - limit = min_ssize_t(limit, state->slice_end - 1); - - for (;;) { - if (pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (pos >= limit) - break; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - ++pos; - - if (same_char_ign(encoding, char_at(state->text, pos), - ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_CHARACTER_IGN_REV: - { - Py_UCS4 ch; - - ch = test->values[0]; - - /* The tail is a character. We don't want to go off the end - * of the slice. - */ - limit = max_ssize_t(limit, state->slice_start + 1); - - for (;;) { - if (pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (pos <= limit) - break; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - --pos; - - if (same_char_ign(encoding, char_at(state->text, pos - - 1), ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_CHARACTER_REV: - { - Py_UCS4 ch; - - ch = test->values[0]; - - /* The tail is a character. We don't want to go off the end - * of the slice. - */ - limit = max_ssize_t(limit, state->slice_start + 1); - - for (;;) { - if (pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (pos <= limit) - break; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - --pos; - - if (same_char(encoding, char_at(state->text, pos - 1), - ch) == m && !is_repeat_guarded(safe_state, index, - pos, RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = min_ssize_t(limit, state->slice_end - length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (pos >= limit) - break; - - /* Look for the tail string. */ - found = string_search(safe_state, test, pos + 1, limit - + length, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - ++pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING_FLD: - { - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = min_ssize_t(limit, state->slice_end); - - for (;;) { - Py_ssize_t found; - Py_ssize_t new_pos; - BOOL is_partial; - - if (pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (pos >= limit) - break; - - /* Look for the tail string. */ - found = string_search_fld(safe_state, test, pos + 1, - limit, &new_pos, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - ++pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING_FLD_REV: - { - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = max_ssize_t(limit, state->slice_start); - - for (;;) { - Py_ssize_t found; - Py_ssize_t new_pos; - BOOL is_partial; - - if (pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (pos <= limit) - break; - - /* Look for the tail string. */ - found = string_search_fld_rev(safe_state, test, pos - - 1, limit, &new_pos, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - --pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING_IGN: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = min_ssize_t(limit, state->slice_end - length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos >= state->text_length && state->partial_side == - RE_PARTIAL_RIGHT) - return RE_ERROR_PARTIAL; - - if (pos >= limit) - break; - - /* Look for the tail string. */ - found = string_search_ign(safe_state, test, pos + 1, - limit + length, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - ++pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING_IGN_REV: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = max_ssize_t(limit, state->slice_start + length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (pos <= limit) - break; - - /* Look for the tail string. */ - found = string_search_ign_rev(safe_state, test, pos - - 1, limit - length, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - --pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - case RE_OP_STRING_REV: - { - Py_ssize_t length; - - length = (Py_ssize_t)test->value_count; - - /* The tail is a string. We don't want to go off the end of - * the slice. - */ - limit = max_ssize_t(limit, state->slice_start + length); - - for (;;) { - Py_ssize_t found; - BOOL is_partial; - - if (pos <= 0 && state->partial_side == RE_PARTIAL_LEFT) - return RE_ERROR_PARTIAL; - - if (pos <= limit) - break; - - /* Look for the tail string. */ - found = string_search_rev(safe_state, test, pos - 1, - limit - length, &is_partial); - if (is_partial) - return RE_ERROR_PARTIAL; - - if (found < 0) - break; - - if (repeated->op == RE_OP_ANY_ALL) - /* Anything can precede the tail. */ - pos = found; - else { - /* Check that what precedes the tail will match. */ - while (pos != found) { - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - --pos; - } - - if (pos != found) - /* Something preceding the tail didn't match. - */ - break; - } - - if (!is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - } - break; - } - default: - for (;;) { - RE_Position next_position; - - status = match_one(state, repeated, pos); - if (status < 0) - return status; - - if (status == RE_ERROR_FAILURE) - break; - - pos += step; - - status = try_match(state, &node->next_1, pos, - &next_position); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (status == RE_ERROR_SUCCESS && - !is_repeat_guarded(safe_state, index, pos, - RE_STATUS_TAIL)) { - match = TRUE; - break; - } - - if (pos == limit) - break; - } - break; - } - } - - if (match) { - /* The tail could match. */ - count = (size_t)abs_ssize_t(pos - state->text_pos); - state->text_pos = pos; - - if (count < max_count) { - /* The match is shorter than the maximum, so we might need - * to backtrack the repeat again to consume more. - */ - rp_data->count = count; - } else { - /* We've reached or passed the maximum, so we won't need to - * backtrack the repeat again. - */ - rp_data->start = bt_data->repeat.text_pos; - rp_data->count = bt_data->repeat.count; - discard_backtrack(state); - - /* Have we passed the maximum? */ - if (count > max_count) - goto backtrack; - } - - node = node->next_1.node; - goto advance; - } else { - /* The tail couldn't match. */ - rp_data->start = bt_data->repeat.text_pos; - rp_data->count = bt_data->repeat.count; - discard_backtrack(state); - } - break; - } - case RE_OP_LOOKAROUND: /* Lookaround. */ - TRACE(("%s\n", re_op_text[bt_data->op])) - - /* Restore the groups and certain flags and then backtrack. */ - pop_groups(state); - state->too_few_errors = bt_data->lookaround.too_few_errors; - state->capture_change = bt_data->lookaround.capture_change; - discard_backtrack(state); - break; - case RE_OP_MATCH_BODY: - { - RE_RepeatData* rp_data; - TRACE(("%s %d\n", re_op_text[bt_data->op], bt_data->repeat.index)) - - /* We want to match the body. */ - rp_data = &state->repeats[bt_data->repeat.index]; - - /* Restore the repeat info. */ - rp_data->count = bt_data->repeat.count; - rp_data->start = bt_data->repeat.start; - rp_data->capture_change = bt_data->repeat.capture_change; - - /* Record backtracking info in case the body fails to match. */ - bt_data->op = RE_OP_BODY_START; - - /* Advance into the body. */ - node = bt_data->repeat.position.node; - state->text_pos = bt_data->repeat.position.text_pos; - goto advance; - } - case RE_OP_MATCH_TAIL: - { - RE_RepeatData* rp_data; - TRACE(("%s %d\n", re_op_text[bt_data->op], bt_data->repeat.index)) - - /* We want to match the tail. */ - rp_data = &state->repeats[bt_data->repeat.index]; - - /* Restore the repeat info. */ - rp_data->count = bt_data->repeat.count; - rp_data->start = bt_data->repeat.start; - rp_data->capture_change = bt_data->repeat.capture_change; - - /* Advance into the tail. */ - node = bt_data->repeat.position.node; - state->text_pos = bt_data->repeat.position.text_pos; - - discard_backtrack(state); - goto advance; - } - case RE_OP_REF_GROUP: /* Reference to a capture group. */ - case RE_OP_REF_GROUP_IGN: /* Reference to a capture group, ignoring case. */ - case RE_OP_REF_GROUP_IGN_REV: /* Reference to a capture group, backwards, ignoring case. */ - case RE_OP_REF_GROUP_REV: /* Reference to a capture group, backwards. */ - case RE_OP_STRING: /* A string. */ - case RE_OP_STRING_IGN: /* A string, ignoring case. */ - case RE_OP_STRING_IGN_REV: /* A string, backwards, ignoring case. */ - case RE_OP_STRING_REV: /* A string, backwards. */ - { - BOOL matched; - TRACE(("%s\n", re_op_text[bt_data->op])) - - status = retry_fuzzy_match_string(safe_state, search, - &state->text_pos, &node, &string_pos, &matched); - if (status < 0) - return RE_ERROR_PARTIAL; - - - if (matched) - goto advance; - - string_pos = -1; - break; - } - case RE_OP_REF_GROUP_FLD: /* Reference to a capture group, ignoring case. */ - case RE_OP_REF_GROUP_FLD_REV: /* Reference to a capture group, backwards, ignoring case. */ - { - BOOL matched; - TRACE(("%s\n", re_op_text[bt_data->op])) - - status = retry_fuzzy_match_group_fld(safe_state, search, - &state->text_pos, &node, &folded_pos, &string_pos, &gfolded_pos, - &matched); - if (status < 0) - return RE_ERROR_PARTIAL; - - - if (matched) - goto advance; - - string_pos = -1; - break; - } - case RE_OP_START_GROUP: /* Start of a capture group. */ - { - RE_CODE private_index; - RE_GroupData* group; - TRACE(("%s %d\n", re_op_text[bt_data->op], - bt_data->group.public_index)) - - private_index = bt_data->group.private_index; - group = &state->groups[private_index - 1]; - - /* Unsave the capture? */ - if (bt_data->group.capture) - unsave_capture(state, bt_data->group.private_index, - bt_data->group.public_index); - - if (pattern->group_info[private_index - 1].referenced && - group->span.start != bt_data->group.text_pos) - --state->capture_change; - group->span.start = bt_data->group.text_pos; - group->current_capture = bt_data->group.current_capture; - - discard_backtrack(state); - break; - } - case RE_OP_STRING_FLD: /* A string, ignoring case. */ - case RE_OP_STRING_FLD_REV: /* A string, backwards, ignoring case. */ - { - BOOL matched; - TRACE(("%s\n", re_op_text[bt_data->op])) - - status = retry_fuzzy_match_string_fld(safe_state, search, - &state->text_pos, &node, &string_pos, &folded_pos, &matched); - if (status < 0) - return RE_ERROR_PARTIAL; - - if (matched) - goto advance; - - string_pos = -1; - break; - } - default: - TRACE(("UNKNOWN OP %d\n", bt_data->op)) - return RE_ERROR_ILLEGAL; - } - } -} - -/* Saves group data for fuzzy matching. */ -Py_LOCAL_INLINE(RE_GroupData*) save_groups(RE_SafeState* safe_state, - RE_GroupData* saved_groups) { - RE_State* state; - PatternObject* pattern; - size_t g; - - /* Re-acquire the GIL. */ - acquire_GIL(safe_state); - - state = safe_state->re_state; - pattern = state->pattern; - - if (!saved_groups) { - saved_groups = (RE_GroupData*)re_alloc(pattern->true_group_count * - sizeof(RE_GroupData)); - if (!saved_groups) - goto error; - - memset(saved_groups, 0, pattern->true_group_count * - sizeof(RE_GroupData)); - } - - for (g = 0; g < pattern->true_group_count; g++) { - RE_GroupData* orig; - RE_GroupData* copy; - - orig = &state->groups[g]; - copy = &saved_groups[g]; - - copy->span = orig->span; - - if (orig->capture_count > copy->capture_capacity) { - RE_GroupSpan* cap_copy; - - cap_copy = (RE_GroupSpan*)re_realloc(copy->captures, - orig->capture_count * sizeof(RE_GroupSpan)); - if (!cap_copy) - goto error; - - copy->capture_capacity = orig->capture_count; - copy->captures = cap_copy; - } - - copy->capture_count = orig->capture_count; - Py_MEMCPY(copy->captures, orig->captures, orig->capture_count * - sizeof(RE_GroupSpan)); - } - - /* Release the GIL. */ - release_GIL(safe_state); - - return saved_groups; - -error: - if (saved_groups) { - for (g = 0; g < pattern->true_group_count; g++) - re_dealloc(saved_groups[g].captures); - - re_dealloc(saved_groups); - } - - /* Release the GIL. */ - release_GIL(safe_state); - - return NULL; -} - -/* Restores group data for fuzzy matching. */ -Py_LOCAL_INLINE(void) restore_groups(RE_SafeState* safe_state, RE_GroupData* - saved_groups) { - RE_State* state; - PatternObject* pattern; - size_t g; - - /* Re-acquire the GIL. */ - acquire_GIL(safe_state); - - state = safe_state->re_state; - pattern = state->pattern; - - for (g = 0; g < pattern->true_group_count; g++) - re_dealloc(state->groups[g].captures); - - Py_MEMCPY(state->groups, saved_groups, pattern->true_group_count * - sizeof(RE_GroupData)); - - re_dealloc(saved_groups); - - /* Release the GIL. */ - release_GIL(safe_state); -} - -/* Discards group data for fuzzy matching. */ -Py_LOCAL_INLINE(void) discard_groups(RE_SafeState* safe_state, RE_GroupData* - saved_groups) { - RE_State* state; - PatternObject* pattern; - size_t g; - - /* Re-acquire the GIL. */ - acquire_GIL(safe_state); - - state = safe_state->re_state; - pattern = state->pattern; - - for (g = 0; g < pattern->true_group_count; g++) - re_dealloc(saved_groups[g].captures); - - re_dealloc(saved_groups); - - /* Release the GIL. */ - release_GIL(safe_state); -} - -/* Saves the fuzzy info. */ -Py_LOCAL_INLINE(void) save_fuzzy_counts(RE_State* state, size_t* fuzzy_counts) - { - Py_MEMCPY(fuzzy_counts, state->total_fuzzy_counts, - sizeof(state->total_fuzzy_counts)); -} - -/* Restores the fuzzy info. */ -Py_LOCAL_INLINE(void) restore_fuzzy_counts(RE_State* state, size_t* - fuzzy_counts) { - Py_MEMCPY(state->total_fuzzy_counts, fuzzy_counts, - sizeof(state->total_fuzzy_counts)); -} - -/* Performs a match or search from the current text position. - * - * The state can sometimes be shared across threads. In such instances there's - * a lock (mutex) on it. The lock is held for the duration of matching. - */ -Py_LOCAL_INLINE(int) do_match(RE_SafeState* safe_state, BOOL search) { - RE_State* state; - PatternObject* pattern; - Py_ssize_t available; - BOOL get_best; - BOOL enhance_match; - BOOL must_advance; - RE_GroupData* best_groups; - Py_ssize_t best_match_pos; - Py_ssize_t best_text_pos = 0; /* Initialise to stop compiler warning. */ - int status; - Py_ssize_t slice_start; - Py_ssize_t slice_end; - size_t best_fuzzy_counts[RE_FUZZY_COUNT]; - TRACE(("<>\n")) - - state = safe_state->re_state; - pattern = state->pattern; - - /* Release the GIL. */ - release_GIL(safe_state); - - /* Is there enough to search? */ - if (state->reverse) { - if (state->text_pos < state->slice_start) { - acquire_GIL(safe_state); - return FALSE; - } - - available = state->text_pos - state->slice_start; - } else { - if (state->text_pos > state->slice_end) { - acquire_GIL(safe_state); - return FALSE; - } - - available = state->slice_end - state->text_pos; - } - - get_best = (pattern->flags & RE_FLAG_BESTMATCH) != 0; - enhance_match = (pattern->flags & RE_FLAG_ENHANCEMATCH) != 0 && !get_best; - - /* The maximum permitted cost. */ - state->max_cost = pattern->is_fuzzy ? PY_SSIZE_T_MAX : 0; - - best_groups = NULL; - - best_match_pos = state->text_pos; - must_advance = state->must_advance; - - slice_start = state->slice_start; - slice_end = state->slice_end; - - for (;;) { - /* If there's a better match, it won't start earlier in the string than - * the current best match, so there's no need to start earlier than - * that match. - */ - state->text_pos = best_match_pos; - state->must_advance = must_advance; - - /* Initialise the state. */ - init_match(state); - - status = RE_ERROR_SUCCESS; - if (state->max_cost == 0 && state->partial_side == RE_PARTIAL_NONE) { - /* An exact match, and partial matches not permitted. */ - if (available < state->min_width || (available == 0 && - state->must_advance)) - status = RE_ERROR_FAILURE; - } - - if (status == RE_ERROR_SUCCESS) - status = basic_match(safe_state, pattern->start_node, search, - FALSE); - - /* Has an error occurred, or is it a partial match? */ - if (status < 0) - break; - - if (status == RE_ERROR_FAILURE || (status == RE_ERROR_SUCCESS && - state->total_cost == 0)) - break; - - if (!get_best && !enhance_match) - break; - - save_fuzzy_counts(state, best_fuzzy_counts); - - if (!get_best && state->text_pos == state->match_pos) - /* We want the first match. The match is already zero-width, so the - * cost can't get any lower (because the fit can't get any better). - */ - break; - - if (best_groups) { - BOOL same; - size_t g; - - /* Did we get the same match as the best so far? */ - same = state->match_pos == best_match_pos && state->text_pos == - best_text_pos; - for (g = 0; same && g < pattern->public_group_count; g++) { - same = state->groups[g].span.start == best_groups[g].span.start - && state->groups[g].span.end == best_groups[g].span.end; - } - - if (same) - break; - } - - /* Save the best result so far. */ - best_groups = save_groups(safe_state, best_groups); - if (!best_groups) { - status = RE_ERROR_MEMORY; - break; - } - - best_match_pos = state->match_pos; - best_text_pos = state->text_pos; - - if (state->max_cost == 0) - break; - - /* Reduce the maximum permitted cost and try again. */ - state->max_cost = state->total_cost - 1; - - if (enhance_match) { - if (state->reverse) { - state->slice_start = state->text_pos; - state->slice_end = state->match_pos; - } else { - state->slice_start = state->match_pos; - state->slice_end = state->text_pos; - } - } - } - - state->slice_start = slice_start; - state->slice_end = slice_end; - - if (best_groups) { - if (status == RE_ERROR_SUCCESS && state->total_cost == 0) - /* We have a perfect match, so the previous best match. */ - discard_groups(safe_state, best_groups); - else { - /* Restore the previous best match. */ - status = RE_ERROR_SUCCESS; - - state->match_pos = best_match_pos; - state->text_pos = best_text_pos; - - restore_groups(safe_state, best_groups); - restore_fuzzy_counts(state, best_fuzzy_counts); - } - } - - if (status == RE_ERROR_SUCCESS || status == RE_ERROR_PARTIAL) { - Py_ssize_t max_end_index; - RE_GroupInfo* group_info; - size_t g; - - /* Store the results. */ - state->lastindex = -1; - state->lastgroup = -1; - max_end_index = -1; - - /* Store the capture groups. */ - group_info = pattern->group_info; - - for (g = 0; g < pattern->public_group_count; g++) { - RE_GroupSpan* span; - - span = &state->groups[g].span; - /* The string positions are of type Py_ssize_t, so the format needs - * to specify that. - */ - TRACE(("group %d from %" PY_FORMAT_SIZE_T "d to %" PY_FORMAT_SIZE_T - "d\n", g + 1, span->start, span->end)) - - if (span->start >= 0 && span->end >= 0 && group_info[g].end_index > - max_end_index) { - max_end_index = group_info[g].end_index; - state->lastindex = (Py_ssize_t)g + 1; - if (group_info[g].has_name) - state->lastgroup = (Py_ssize_t)g + 1; - } - } - } - - /* Re-acquire the GIL. */ - acquire_GIL(safe_state); - - if (status < 0 && status != RE_ERROR_PARTIAL && !PyErr_Occurred()) - set_error(status, NULL); - - return status; -} - -/* Gets a string from a Python object. - * - * If the function returns true and str_info->should_release is true then it's - * the responsibility of the caller to release the buffer when it's no longer - * needed. - */ -Py_LOCAL_INLINE(BOOL) get_string(PyObject* string, RE_StringInfo* str_info) { - /* Given a Python object, return a data pointer, a length (in characters), - * and a character size. Return FALSE if the object is not a string (or not - * compatible). - */ - PyBufferProcs* buffer; - Py_ssize_t bytes; - Py_ssize_t size; - - /* Unicode objects do not support the buffer API. So, get the data directly - * instead. - */ - if (PyUnicode_Check(string)) { - /* Unicode strings doesn't always support the buffer interface. */ - str_info->characters = (void*)PyUnicode_AS_DATA(string); - str_info->length = PyUnicode_GET_SIZE(string); - str_info->charsize = sizeof(Py_UNICODE); - str_info->is_unicode = TRUE; - str_info->should_release = FALSE; - return TRUE; - } - - /* Get pointer to string buffer. */ -#if PY_VERSION_HEX >= 0x02060000 - buffer = Py_TYPE(string)->tp_as_buffer; - str_info->view.len = -1; -#else - buffer = string->ob_type->tp_as_buffer; -#endif - - if (!buffer) { - PyErr_SetString(PyExc_TypeError, "expected string or buffer"); - return FALSE; - } - -#if PY_VERSION_HEX >= 0x02060000 - if (buffer->bf_getbuffer && (*buffer->bf_getbuffer)(string, - &str_info->view, PyBUF_SIMPLE) >= 0) - /* It's a new-style buffer. */ - str_info->should_release = TRUE; - else -#endif - if (buffer->bf_getreadbuffer && buffer->bf_getsegcount && - buffer->bf_getsegcount(string, NULL) == 1) - /* It's an old-style buffer. */ - str_info->should_release = FALSE; - else { - PyErr_SetString(PyExc_TypeError, "expected string or buffer"); - return FALSE; - } - - /* Determine buffer size. */ -#if PY_VERSION_HEX >= 0x02060000 - if (str_info->should_release) { - /* It's a new-style buffer. */ - bytes = str_info->view.len; - str_info->characters = str_info->view.buf; - - if (str_info->characters == NULL) { - PyBuffer_Release(&str_info->view); - PyErr_SetString(PyExc_ValueError, "buffer is NULL"); - return FALSE; - } - } else -#endif - /* It's an old-style buffer. */ - bytes = buffer->bf_getreadbuffer(string, 0, &str_info->characters); - - if (bytes < 0) { -#if PY_VERSION_HEX >= 0x02060000 - if (str_info->should_release) - PyBuffer_Release(&str_info->view); -#endif - PyErr_SetString(PyExc_TypeError, "buffer has negative size"); - return FALSE; - } - - /* Determine character size. */ - size = PyObject_Size(string); - - if (PyString_Check(string) || bytes == size) - str_info->charsize = 1; - else { -#if PY_VERSION_HEX >= 0x02060000 - if (str_info->should_release) - PyBuffer_Release(&str_info->view); -#endif - PyErr_SetString(PyExc_TypeError, "buffer size mismatch"); - return FALSE; - } - - str_info->length = size; - str_info->is_unicode = FALSE; - - return TRUE; -} - -/* Deallocates the groups storage. */ -Py_LOCAL_INLINE(void) dealloc_groups(RE_GroupData* groups, size_t group_count) - { - size_t g; - - if (!groups) - return; - - for (g = 0; g < group_count; g++) - re_dealloc(groups[g].captures); - - re_dealloc(groups); -} - -/* Initialises a state object. */ -Py_LOCAL_INLINE(BOOL) state_init_2(RE_State* state, PatternObject* pattern, - PyObject* string, RE_StringInfo* str_info, Py_ssize_t start, Py_ssize_t end, - BOOL overlapped, int concurrent, BOOL partial, BOOL use_lock, BOOL - visible_captures, BOOL match_all) { - Py_ssize_t final_pos; - int i; - - state->groups = NULL; - state->repeats = NULL; - state->visible_captures = visible_captures; - state->match_all = match_all; - state->backtrack_block.previous = NULL; - state->backtrack_block.next = NULL; - state->backtrack_block.capacity = RE_BACKTRACK_BLOCK_SIZE; - state->backtrack_allocated = RE_BACKTRACK_BLOCK_SIZE; - state->first_saved_groups = NULL; - state->current_saved_groups = NULL; - state->first_saved_repeats = NULL; - state->current_saved_repeats = NULL; - state->lock = NULL; - state->fuzzy_guards = NULL; - state->first_group_call_frame = NULL; - state->current_group_call_frame = NULL; - state->group_call_guard_list = NULL; - state->req_pos = -1; - - /* The call guards used by recursive patterns. */ - if (pattern->call_ref_info_count > 0) { - state->group_call_guard_list = - (RE_GuardList*)re_alloc(pattern->call_ref_info_count * - sizeof(RE_GuardList)); - if (!state->group_call_guard_list) - goto error; - memset(state->group_call_guard_list, 0, pattern->call_ref_info_count * - sizeof(RE_GuardList)); - } - - /* The capture groups. */ - if (pattern->true_group_count) { - size_t g; - - if (pattern->groups_storage) { - state->groups = pattern->groups_storage; - pattern->groups_storage = NULL; - } else { - state->groups = (RE_GroupData*)re_alloc(pattern->true_group_count * - sizeof(RE_GroupData)); - if (!state->groups) - goto error; - memset(state->groups, 0, pattern->true_group_count * - sizeof(RE_GroupData)); - - for (g = 0; g < pattern->true_group_count; g++) { - RE_GroupSpan* captures; - - captures = (RE_GroupSpan*)re_alloc(sizeof(RE_GroupSpan)); - if (!captures) { - size_t i; - - for (i = 0; i < g; i++) - re_dealloc(state->groups[i].captures); - - goto error; - } - - state->groups[g].captures = captures; - state->groups[g].capture_capacity = 1; - } - } - } - - /* Adjust boundaries. */ - if (start < 0) - start += str_info->length; - if (start < 0) - start = 0; - else if (start > str_info->length) - start = str_info->length; - - if (end < 0) - end += str_info->length; - if (end < 0) - end = 0; - else if (end > str_info->length) - end = str_info->length; - - state->overlapped = overlapped; - state->min_width = pattern->min_width; - - /* Initialise the getters and setters for the character size. */ - state->charsize = str_info->charsize; - state->is_unicode = str_info->is_unicode; - -#if PY_VERSION_HEX >= 0x02060000 - /* Are we using a buffer object? If so, we need to copy the info. */ - state->should_release = str_info->should_release; - if (state->should_release) - state->view = str_info->view; - -#endif - switch (state->charsize) { - case 1: - state->char_at = bytes1_char_at; - state->set_char_at = bytes1_set_char_at; - state->point_to = bytes1_point_to; - break; - case 2: - state->char_at = bytes2_char_at; - state->set_char_at = bytes2_set_char_at; - state->point_to = bytes2_point_to; - break; - case 4: - state->char_at = bytes4_char_at; - state->set_char_at = bytes4_set_char_at; - state->point_to = bytes4_point_to; - break; - default: - goto error; - } - - state->encoding = pattern->encoding; - - /* The state object contains a reference to the string and also a pointer - * to its contents. - * - * The documentation says that the end of the slice behaves like the end of - * the string. - */ - state->text = str_info->characters; - state->text_length = end; - - state->reverse = (pattern->flags & RE_FLAG_REVERSE) != 0; - if (partial) - state->partial_side = state->reverse ? RE_PARTIAL_LEFT : - RE_PARTIAL_RIGHT; - else - state->partial_side = RE_PARTIAL_NONE; - - state->slice_start = start; - state->slice_end = state->text_length; - state->text_pos = state->reverse ? state->slice_end : state->slice_start; - - /* Point to the final newline and line separator if it's at the end of the - * string, otherwise just -1. - */ - state->final_newline = -1; - state->final_line_sep = -1; - final_pos = state->text_length - 1; - if (final_pos >= 0) { - Py_UCS4 ch; - - ch = state->char_at(state->text, final_pos); - if (ch == 0x0A) { - /* The string ends with LF. */ - state->final_newline = final_pos; - state->final_line_sep = final_pos; - - /* Does the string end with CR/LF? */ - --final_pos; - if (final_pos >= 0 && state->char_at(state->text, final_pos) == - 0x0D) - state->final_line_sep = final_pos; - } else { - /* The string doesn't end with LF, but it could be another kind of - * line separator. - */ - if (state->encoding->is_line_sep(ch)) - state->final_line_sep = final_pos; - } - } - - /* If the 'new' behaviour is enabled then split correctly on zero-width - * matches. - */ - state->version_0 = (pattern->flags & RE_FLAG_VERSION1) == 0; - state->must_advance = FALSE; - - state->pattern = pattern; - state->string = string; - - if (pattern->repeat_count) { - if (pattern->repeats_storage) { - state->repeats = pattern->repeats_storage; - pattern->repeats_storage = NULL; - } else { - state->repeats = (RE_RepeatData*)re_alloc(pattern->repeat_count * - sizeof(RE_RepeatData)); - if (!state->repeats) - goto error; - memset(state->repeats, 0, pattern->repeat_count * - sizeof(RE_RepeatData)); - } - } - - if (pattern->fuzzy_count) { - state->fuzzy_guards = (RE_FuzzyGuards*)re_alloc(pattern->fuzzy_count * - sizeof(RE_FuzzyGuards)); - if (!state->fuzzy_guards) - goto error; - memset(state->fuzzy_guards, 0, pattern->fuzzy_count * - sizeof(RE_FuzzyGuards)); - } - - Py_INCREF(state->pattern); - Py_INCREF(state->string); - - /* Multithreading is allowed during matching when explicitly enabled or on - * immutable strings. - */ - switch (concurrent) { - case RE_CONC_NO: - state->is_multithreaded = FALSE; - break; - case RE_CONC_YES: - state->is_multithreaded = TRUE; - break; - default: - state->is_multithreaded = PyUnicode_Check(string) || - PyString_Check(string); - break; - } - - /* A state struct can sometimes be shared across threads. In such - * instances, if multithreading is enabled we need to protect the state - * with a lock (mutex) during matching. - */ - if (state->is_multithreaded && use_lock) - state->lock = PyThread_allocate_lock(); - - for (i = 0; i < MAX_SEARCH_POSITIONS; i++) - state->search_positions[i].start_pos = -1; - - return TRUE; - -error: - re_dealloc(state->group_call_guard_list); - re_dealloc(state->repeats); - dealloc_groups(state->groups, pattern->true_group_count); - re_dealloc(state->fuzzy_guards); - state->repeats = NULL; - state->groups = NULL; - state->fuzzy_guards = NULL; - return FALSE; -} - -#if PY_VERSION_HEX >= 0x02060000 -/* Releases the string's buffer, if necessary. */ -Py_LOCAL_INLINE(void) release_buffer(RE_StringInfo* str_info) { - if (str_info->should_release) - PyBuffer_Release(&str_info->view); -} - -#endif -/* Initialises a state object. */ -Py_LOCAL_INLINE(BOOL) state_init(RE_State* state, PatternObject* pattern, - PyObject* string, Py_ssize_t start, Py_ssize_t end, BOOL overlapped, int - concurrent, BOOL partial, BOOL use_lock, BOOL visible_captures, BOOL - match_all) { - RE_StringInfo str_info; - - /* Get the string to search or match. */ - if (!get_string(string, &str_info)) - return FALSE; - - /* If we fail to initialise the state then we need to release the buffer if - * the string is a buffer object. - */ - if (!state_init_2(state, pattern, string, &str_info, start, end, - overlapped, concurrent, partial, use_lock, visible_captures, match_all)) - { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return FALSE; - } - - /* The state has been initialised successfully, so now the state has the - * responsibility of releasing the buffer if the string is a buffer object. - */ - return TRUE; -} - -/* Deallocates repeat data. */ -Py_LOCAL_INLINE(void) dealloc_repeats(RE_RepeatData* repeats, size_t - repeat_count) { - size_t i; - - if (!repeats) - return; - - for (i = 0; i < repeat_count; i++) { - re_dealloc(repeats[i].body_guard_list.spans); - re_dealloc(repeats[i].tail_guard_list.spans); - } - - re_dealloc(repeats); -} - -/* Deallocates fuzzy guards. */ -Py_LOCAL_INLINE(void) dealloc_fuzzy_guards(RE_FuzzyGuards* guards, size_t - fuzzy_count) { - size_t i; - - if (!guards) - return; - - for (i = 0; i < fuzzy_count; i++) { - re_dealloc(guards[i].body_guard_list.spans); - re_dealloc(guards[i].tail_guard_list.spans); - } - - re_dealloc(guards); -} - -/* Finalises a state object, discarding its contents. */ -Py_LOCAL_INLINE(void) state_fini(RE_State* state) { - RE_BacktrackBlock* current; - PatternObject* pattern; - RE_SavedGroups* saved_groups; - RE_SavedRepeats* saved_repeats; - RE_GroupCallFrame* frame; - size_t i; - - /* Discard the lock (mutex) if there's one. */ - if (state->lock) - PyThread_free_lock(state->lock); - - /* Deallocate the backtrack blocks. */ - current = state->backtrack_block.next; - while (current) { - RE_BacktrackBlock* next; - - next = current->next; - re_dealloc(current); - state->backtrack_allocated -= RE_BACKTRACK_BLOCK_SIZE; - current = next; - } - - pattern = state->pattern; - - saved_groups = state->first_saved_groups; - while (saved_groups) { - RE_SavedGroups* next; - - next = saved_groups->next; - re_dealloc(saved_groups->spans); - re_dealloc(saved_groups->counts); - re_dealloc(saved_groups); - saved_groups = next; - } - - saved_repeats = state->first_saved_repeats; - while (saved_repeats) { - RE_SavedRepeats* next; - - next = saved_repeats->next; - - dealloc_repeats(saved_repeats->repeats, pattern->repeat_count); - - re_dealloc(saved_repeats); - saved_repeats = next; - } - - if (pattern->groups_storage) - dealloc_groups(state->groups, pattern->true_group_count); - else - pattern->groups_storage = state->groups; - - if (pattern->repeats_storage) - dealloc_repeats(state->repeats, pattern->repeat_count); - else - pattern->repeats_storage = state->repeats; - - frame = state->first_group_call_frame; - while (frame) { - RE_GroupCallFrame* next; - - next = frame->next; - - dealloc_groups(frame->groups, pattern->true_group_count); - dealloc_repeats(frame->repeats, pattern->repeat_count); - - re_dealloc(frame); - frame = next; - } - - for (i = 0; i < pattern->call_ref_info_count; i++) - re_dealloc(state->group_call_guard_list[i].spans); - - if (state->group_call_guard_list) - re_dealloc(state->group_call_guard_list); - - if (state->fuzzy_guards) - dealloc_fuzzy_guards(state->fuzzy_guards, pattern->fuzzy_count); - - Py_DECREF(state->pattern); - Py_DECREF(state->string); -#if PY_VERSION_HEX >= 0x02060000 - - if (state->should_release) - PyBuffer_Release(&state->view); -#endif -} - -/* Converts a string index to an integer. - * - * If the index is None then the default will be returned. - */ -Py_LOCAL_INLINE(Py_ssize_t) as_string_index(PyObject* obj, Py_ssize_t def) { - Py_ssize_t value; - - if (obj == Py_None) - return def; - - value = PyInt_AsSsize_t(obj); - if (value != -1 || !PyErr_Occurred()) - return value; - - PyErr_Clear(); - - value = PyLong_AsLong(obj); - if (value != -1 || !PyErr_Occurred()) - return value; - - set_error(RE_ERROR_INDEX, NULL); - return 0; -} - -/* Deallocates a MatchObject. */ -static void match_dealloc(PyObject* self_) { - MatchObject* self; - - self = (MatchObject*)self_; - - Py_XDECREF(self->string); - Py_XDECREF(self->substring); - Py_DECREF(self->pattern); - if (self->groups) - re_dealloc(self->groups); - Py_XDECREF(self->regs); - PyObject_DEL(self); -} - -/* Restricts a value to a range. */ -Py_LOCAL_INLINE(Py_ssize_t) limited_range(Py_ssize_t value, Py_ssize_t lower, - Py_ssize_t upper) { - if (value < lower) - return lower; - - if (value > upper) - return upper; - - return value; -} - -/* Gets a slice from a Unicode string. */ -Py_LOCAL_INLINE(PyObject*) unicode_slice(PyObject* string, Py_ssize_t start, - Py_ssize_t end) { - Py_ssize_t length; - Py_UNICODE* buffer; - - length = PyUnicode_GET_SIZE(string); - start = limited_range(start, 0, length); - end = limited_range(end, 0, length); - - buffer = PyUnicode_AsUnicode(string); - - return PyUnicode_FromUnicode(buffer + start, end - start); -} - -/* Gets a slice from a bytestring. */ -Py_LOCAL_INLINE(PyObject*) bytes_slice(PyObject* string, Py_ssize_t start, - Py_ssize_t end) { - Py_ssize_t length; - char* buffer; - - length = PyString_GET_SIZE(string); - start = limited_range(start, 0, length); - end = limited_range(end, 0, length); - - buffer = PyString_AsString(string); - - return PyString_FromStringAndSize(buffer + start, end - start); -} - -/* Gets a slice from a string, returning either a Unicode string or a - * bytestring. - */ -Py_LOCAL_INLINE(PyObject*) get_slice(PyObject* string, Py_ssize_t start, - Py_ssize_t end) { - if (PyUnicode_Check(string)) - return unicode_slice(string, start, end); - - if (PyString_Check(string)) - return bytes_slice(string, start, end); - - return PySequence_GetSlice(string, start, end); -} - -/* Gets a MatchObject's group by integer index. */ -static PyObject* match_get_group_by_index(MatchObject* self, Py_ssize_t index, - PyObject* def) { - RE_GroupSpan* span; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) - return get_slice(self->substring, self->match_start - - self->substring_offset, self->match_end - self->substring_offset); - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - span = &self->groups[index - 1].span; - - if (span->start < 0 || span->end < 0) { - /* Return default value if the string or group is undefined. */ - Py_INCREF(def); - return def; - } - - return get_slice(self->substring, span->start - self->substring_offset, - span->end - self->substring_offset); -} - -/* Gets a MatchObject's start by integer index. */ -static PyObject* match_get_start_by_index(MatchObject* self, Py_ssize_t index) - { - RE_GroupSpan* span; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) - return Py_BuildValue("n", self->match_start); - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - span = &self->groups[index - 1].span; - return Py_BuildValue("n", span->start); -} - -/* Gets a MatchObject's starts by integer index. */ -static PyObject* match_get_starts_by_index(MatchObject* self, Py_ssize_t index) - { - RE_GroupData* group; - PyObject* result; - PyObject* item; - size_t i; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) { - result = PyList_New(1); - if (!result) - return NULL; - - item = Py_BuildValue("n", self->match_start); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, 0, item); - - return result; - } - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - group = &self->groups[index - 1]; - - result = PyList_New((Py_ssize_t)group->capture_count); - if (!result) - return NULL; - - for (i = 0; i < group->capture_count; i++) { - item = Py_BuildValue("n", group->captures[i].start); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, i, item); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* Gets a MatchObject's end by integer index. */ -static PyObject* match_get_end_by_index(MatchObject* self, Py_ssize_t index) { - RE_GroupSpan* span; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) - return Py_BuildValue("n", self->match_end); - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - span = &self->groups[index - 1].span; - return Py_BuildValue("n", span->end); -} - -/* Gets a MatchObject's ends by integer index. */ -static PyObject* match_get_ends_by_index(MatchObject* self, Py_ssize_t index) { - RE_GroupData* group; - PyObject* result; - PyObject* item; - size_t i; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) { - result = PyList_New(1); - if (!result) - return NULL; - - item = Py_BuildValue("n", self->match_end); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, 0, item); - - return result; - } - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - group = &self->groups[index - 1]; - - result = PyList_New((Py_ssize_t)group->capture_count); - if (!result) - return NULL; - - for (i = 0; i < group->capture_count; i++) { - item = Py_BuildValue("n", group->captures[i].end); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, i, item); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* Gets a MatchObject's span by integer index. */ -static PyObject* match_get_span_by_index(MatchObject* self, Py_ssize_t index) { - RE_GroupSpan* span; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) - return Py_BuildValue("nn", self->match_start, self->match_end); - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - span = &self->groups[index - 1].span; - return Py_BuildValue("nn", span->start, span->end); -} - -/* Gets a MatchObject's spans by integer index. */ -static PyObject* match_get_spans_by_index(MatchObject* self, Py_ssize_t index) - { - RE_GroupData* group; - PyObject* result; - PyObject* item; - size_t i; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) { - result = PyList_New(1); - if (!result) - return NULL; - - item = Py_BuildValue("nn", self->match_start, self->match_end); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, 0, item); - - return result; - } - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - group = &self->groups[index - 1]; - - result = PyList_New((Py_ssize_t)group->capture_count); - if (!result) - return NULL; - - for (i = 0; i < group->capture_count; i++) { - item = Py_BuildValue("nn", group->captures[i].start, - group->captures[i].end); - if (!item) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, i, item); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* Gets a MatchObject's captures by integer index. */ -static PyObject* match_get_captures_by_index(MatchObject* self, Py_ssize_t - index) { - RE_GroupData* group; - PyObject* result; - PyObject* slice; - size_t i; - - if (index < 0 || (size_t)index > self->group_count) { - /* Raise error if we were given a bad group number. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } - - if (index == 0) { - result = PyList_New(1); - if (!result) - return NULL; - - slice = get_slice(self->substring, self->match_start - - self->substring_offset, self->match_end - self->substring_offset); - if (!slice) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, 0, slice); - - return result; - } - - /* Capture group indexes are 1-based (excluding group 0, which is the - * entire matched string). - */ - group = &self->groups[index - 1]; - - result = PyList_New((Py_ssize_t)group->capture_count); - if (!result) - return NULL; - - for (i = 0; i < group->capture_count; i++) { - slice = get_slice(self->substring, group->captures[i].start - - self->substring_offset, group->captures[i].end - - self->substring_offset); - if (!slice) - goto error; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(result, i, slice); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* Converts a group index to an integer. */ -Py_LOCAL_INLINE(Py_ssize_t) as_group_index(PyObject* obj) { - Py_ssize_t value; - - value = PyInt_AsSsize_t(obj); - if (value != -1 || !PyErr_Occurred()) - return value; - - PyErr_Clear(); - - value = PyLong_AsLong(obj); - if (value != -1 || !PyErr_Occurred()) - return value; - - set_error(RE_ERROR_INDEX, NULL); - return -1; -} - -/* Gets a MatchObject's group index. - * - * The supplied index can be an integer or a string (group name) object. - */ -Py_LOCAL_INLINE(Py_ssize_t) match_get_group_index(MatchObject* self, PyObject* - index, BOOL allow_neg) { - Py_ssize_t group; - - /* Is the index an integer? */ - group = as_group_index(index); - if (group != -1 || !PyErr_Occurred()) { - Py_ssize_t min_group = 0; - - /* Adjust negative indices where valid and allowed. */ - if (group < 0 && allow_neg) { - group += (Py_ssize_t)self->group_count + 1; - min_group = 1; - } - - if (min_group <= group && (size_t)group <= self->group_count) - return group; - - return -1; - } - - /* The index might be a group name. */ - if (self->pattern->groupindex) { - /* Look up the name. */ - PyErr_Clear(); - - index = PyObject_GetItem(self->pattern->groupindex, index); - if (index) { - /* Check that we have an integer. */ - group = as_group_index(index); - Py_DECREF(index); - if (group != -1 || !PyErr_Occurred()) - return group; - } - } - - PyErr_Clear(); - return -1; -} - -/* Gets a MatchObject's group by object index. */ -Py_LOCAL_INLINE(PyObject*) match_get_group(MatchObject* self, PyObject* index, - PyObject* def, BOOL allow_neg) { - /* Check that the index is an integer or a string. */ - if (PyInt_Check(index) || PyLong_Check(index) || PyUnicode_Check(index) || - PyString_Check(index)) - return match_get_group_by_index(self, match_get_group_index(self, - index, allow_neg), def); - - set_error(RE_ERROR_GROUP_INDEX_TYPE, index); - return NULL; -} - -/* Gets info from a MatchObject by object index. */ -Py_LOCAL_INLINE(PyObject*) get_by_arg(MatchObject* self, PyObject* index, - RE_GetByIndexFunc get_by_index) { - /* Check that the index is an integer or a string. */ - if (PyInt_Check(index) || PyLong_Check(index) || PyUnicode_Check(index) || - PyString_Check(index)) - return get_by_index(self, match_get_group_index(self, index, FALSE)); - - set_error(RE_ERROR_GROUP_INDEX_TYPE, index); - return NULL; -} - -/* MatchObject's 'group' method. */ -static PyObject* match_group(MatchObject* self, PyObject* args) { - Py_ssize_t size; - PyObject* result; - Py_ssize_t i; - - size = PyTuple_GET_SIZE(args); - - switch (size) { - case 0: - /* group() */ - result = match_get_group_by_index(self, 0, Py_None); - break; - case 1: - /* group(x). PyTuple_GET_ITEM borrows the reference. */ - result = match_get_group(self, PyTuple_GET_ITEM(args, 0), Py_None, - FALSE); - break; - default: - /* group(x, y, z, ...) */ - /* Fetch multiple items. */ - result = PyTuple_New(size); - if (!result) - return NULL; - - for (i = 0; i < size; i++) { - PyObject* item; - - /* PyTuple_GET_ITEM borrows the reference. */ - item = match_get_group(self, PyTuple_GET_ITEM(args, i), Py_None, - FALSE); - if (!item) { - Py_DECREF(result); - return NULL; - } - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(result, i, item); - } - break; - } - - return result; -} - -/* Generic method for getting info from a MatchObject. */ -Py_LOCAL_INLINE(PyObject*) get_from_match(MatchObject* self, PyObject* args, - RE_GetByIndexFunc get_by_index) { - Py_ssize_t size; - PyObject* result; - Py_ssize_t i; - - size = PyTuple_GET_SIZE(args); - - switch (size) { - case 0: - /* get() */ - result = get_by_index(self, 0); - break; - case 1: - /* get(x). PyTuple_GET_ITEM borrows the reference. */ - result = get_by_arg(self, PyTuple_GET_ITEM(args, 0), get_by_index); - break; - default: - /* get(x, y, z, ...) */ - /* Fetch multiple items. */ - result = PyTuple_New(size); - if (!result) - return NULL; - - for (i = 0; i < size; i++) { - PyObject* item; - - /* PyTuple_GET_ITEM borrows the reference. */ - item = get_by_arg(self, PyTuple_GET_ITEM(args, i), get_by_index); - if (!item) { - Py_DECREF(result); - return NULL; - } - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(result, i, item); - } - break; - } - - return result; -} - -/* MatchObject's 'start' method. */ -static PyObject* match_start(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_start_by_index); -} - -/* MatchObject's 'starts' method. */ -static PyObject* match_starts(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_starts_by_index); -} - -/* MatchObject's 'end' method. */ -static PyObject* match_end(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_end_by_index); -} - -/* MatchObject's 'ends' method. */ -static PyObject* match_ends(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_ends_by_index); -} - -/* MatchObject's 'span' method. */ -static PyObject* match_span(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_span_by_index); -} - -/* MatchObject's 'spans' method. */ -static PyObject* match_spans(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_spans_by_index); -} - -/* MatchObject's 'captures' method. */ -static PyObject* match_captures(MatchObject* self, PyObject* args) { - return get_from_match(self, args, match_get_captures_by_index); -} - -/* MatchObject's 'groups' method. */ -static PyObject* match_groups(MatchObject* self, PyObject* args, PyObject* - kwargs) { - PyObject* result; - size_t g; - - PyObject* def = Py_None; - static char* kwlist[] = { "default", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O:groups", kwlist, &def)) - return NULL; - - result = PyTuple_New((Py_ssize_t)self->group_count); - if (!result) - return NULL; - - /* Group 0 is the entire matched portion of the string. */ - for (g = 0; g < self->group_count; g++) { - PyObject* item; - - item = match_get_group_by_index(self, (Py_ssize_t)g + 1, def); - if (!item) - goto error; - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(result, g, item); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* MatchObject's 'groupdict' method. */ -static PyObject* match_groupdict(MatchObject* self, PyObject* args, PyObject* - kwargs) { - PyObject* result; - PyObject* keys; - Py_ssize_t g; - - PyObject* def = Py_None; - static char* kwlist[] = { "default", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O:groupdict", kwlist, - &def)) - return NULL; - - result = PyDict_New(); - if (!result || !self->pattern->groupindex) - return result; - - keys = PyMapping_Keys(self->pattern->groupindex); - if (!keys) - goto failed; - - for (g = 0; g < PyList_GET_SIZE(keys); g++) { - PyObject* key; - PyObject* value; - int status; - - /* PyList_GET_ITEM borrows a reference. */ - key = PyList_GET_ITEM(keys, g); - if (!key) - goto failed; - - value = match_get_group(self, key, def, FALSE); - if (!value) - goto failed; - - status = PyDict_SetItem(result, key, value); - Py_DECREF(value); - if (status < 0) - goto failed; - } - - Py_DECREF(keys); - - return result; - -failed: - Py_XDECREF(keys); - Py_DECREF(result); - return NULL; -} - -/* MatchObject's 'capturesdict' method. */ -static PyObject* match_capturesdict(MatchObject* self) { - PyObject* result; - PyObject* keys; - Py_ssize_t g; - - result = PyDict_New(); - if (!result || !self->pattern->groupindex) - return result; - - keys = PyMapping_Keys(self->pattern->groupindex); - if (!keys) - goto failed; - - for (g = 0; g < PyList_GET_SIZE(keys); g++) { - PyObject* key; - Py_ssize_t group; - PyObject* captures; - int status; - - /* PyList_GET_ITEM borrows a reference. */ - key = PyList_GET_ITEM(keys, g); - if (!key) - goto failed; - - group = match_get_group_index(self, key, FALSE); - if (group < 0) - goto failed; - - captures = match_get_captures_by_index(self, group); - if (!captures) - goto failed; - - status = PyDict_SetItem(result, key, captures); - Py_DECREF(captures); - if (status < 0) - goto failed; - } - - Py_DECREF(keys); - - return result; - -failed: - Py_XDECREF(keys); - Py_DECREF(result); - return NULL; -} - -/* Gets a Python object by name from a named module. */ -Py_LOCAL_INLINE(PyObject*) get_object(char* module_name, char* object_name) { - PyObject* module; - PyObject* object; - - module = PyImport_ImportModule(module_name); - if (!module) - return NULL; - - object = PyObject_GetAttrString(module, object_name); - Py_DECREF(module); - - return object; -} - -/* Calls a function in a module. */ -Py_LOCAL_INLINE(PyObject*) call(char* module_name, char* function_name, - PyObject* args) { - PyObject* function; - PyObject* result; - - if (!args) - return NULL; - - function = get_object(module_name, function_name); - if (!function) - return NULL; - - result = PyObject_CallObject(function, args); - Py_DECREF(function); - Py_DECREF(args); - - return result; -} - -/* Gets a replacement item from the replacement list. - * - * The replacement item could be a string literal or a group. - */ -Py_LOCAL_INLINE(PyObject*) get_match_replacement(MatchObject* self, PyObject* - item, size_t group_count) { - Py_ssize_t index; - - if (PyUnicode_Check(item) || PyString_Check(item)) { - /* It's a literal, which can be added directly to the list. */ - Py_INCREF(item); - return item; - } - - /* Is it a group reference? */ - index = as_group_index(item); - if (index == -1 && PyErr_Occurred()) { - /* Not a group either! */ - set_error(RE_ERROR_REPLACEMENT, NULL); - return NULL; - } - - if (index == 0) { - /* The entire matched portion of the string. */ - return get_slice(self->substring, self->match_start - - self->substring_offset, self->match_end - self->substring_offset); - } else if (index >= 1 && (size_t)index <= group_count) { - /* A group. If it didn't match then return None instead. */ - RE_GroupData* group; - - group = &self->groups[index - 1]; - - if (group->capture_count > 0) - return get_slice(self->substring, group->span.start - - self->substring_offset, group->span.end - - self->substring_offset); - else { - Py_INCREF(Py_None); - return Py_None; - } - } else { - /* No such group. */ - set_error(RE_ERROR_NO_SUCH_GROUP, NULL); - return NULL; - } -} - -/* Initialises the join list. */ -Py_LOCAL_INLINE(void) init_join_list(JoinInfo* join_info, BOOL reversed, BOOL - is_unicode) { - join_info->list = NULL; - join_info->item = NULL; - join_info->reversed = reversed; - join_info->is_unicode = is_unicode; -} - -/* Adds an item to the join list. */ -Py_LOCAL_INLINE(int) add_to_join_list(JoinInfo* join_info, PyObject* item) { - PyObject* new_item; - int status; - - if (join_info->is_unicode) { - if (PyUnicode_Check(item)) { - new_item = item; - Py_INCREF(new_item); - } else { - new_item = PyUnicode_FromObject(item); - if (!new_item) { - set_error(RE_ERROR_NOT_UNICODE, item); - return RE_ERROR_NOT_UNICODE; - } - } - } else { - if (PyString_Check(item)) { - new_item = item; - Py_INCREF(new_item); - } else { - new_item = PyUnicode_FromObject(item); - if (!new_item) { - set_error(RE_ERROR_NOT_STRING, item); - return RE_ERROR_NOT_STRING; - } - } - } - - /* If the list already exists then just add the item to it. */ - if (join_info->list) { - status = PyList_Append(join_info->list, new_item); - if (status < 0) - goto error; - - Py_DECREF(new_item); - return status; - } - - /* If we already have an item then we now have 2(!) and we need to put them - * into a list. - */ - if (join_info->item) { - join_info->list = PyList_New(2); - if (!join_info->list) { - status = RE_ERROR_MEMORY; - goto error; - } - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(join_info->list, 0, join_info->item); - join_info->item = NULL; - - /* PyList_SET_ITEM borrows the reference. */ - PyList_SET_ITEM(join_info->list, 1, new_item); - return 0; - } - - /* This is the first item. */ - join_info->item = new_item; - - return 0; - -error: - Py_DECREF(new_item); - set_error(status, NULL); - return status; -} - -/* Clears the join list. */ -Py_LOCAL_INLINE(void) clear_join_list(JoinInfo* join_info) { - Py_XDECREF(join_info->list); - Py_XDECREF(join_info->item); -} - -/* Joins together a list of strings for pattern_subx. */ -Py_LOCAL_INLINE(PyObject*) join_list_info(JoinInfo* join_info) { - /* If the list already exists then just do the join. */ - if (join_info->list) { - PyObject* joiner; - PyObject* result; - - if (join_info->reversed) - /* The list needs to be reversed before being joined. */ - PyList_Reverse(join_info->list); - - if (join_info->is_unicode) { - /* Concatenate the Unicode strings. */ - joiner = PyUnicode_FromUnicode(NULL, 0); - if (!joiner) { - clear_join_list(join_info); - return NULL; - } - - result = PyUnicode_Join(joiner, join_info->list); - } else { - joiner = PyString_FromString(""); - if (!joiner) { - clear_join_list(join_info); - return NULL; - } - - /* Concatenate the bytestrings. */ - result = _PyString_Join(joiner, join_info->list); - } - - Py_DECREF(joiner); - clear_join_list(join_info); - - return result; - } - - /* If we have only 1 item, so we'll just return it. */ - if (join_info->item) - return join_info->item; - - /* There are no items, so return an empty string. */ - if (join_info->is_unicode) - return PyUnicode_FromUnicode(NULL, 0); - else - return PyString_FromString(""); -} - -/* Checks whether a string replacement is a literal. - * - * To keep it simple we'll say that a literal is a string which can be used - * as-is. - * - * Returns its length if it is a literal, otherwise -1. - */ -Py_LOCAL_INLINE(Py_ssize_t) check_replacement_string(PyObject* str_replacement, - unsigned char special_char) { - RE_StringInfo str_info; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - Py_ssize_t pos; - - if (!get_string(str_replacement, &str_info)) - return -1; - - switch (str_info.charsize) { - case 1: - char_at = bytes1_char_at; - break; - case 2: - char_at = bytes2_char_at; - break; - case 4: - char_at = bytes4_char_at; - break; - default: -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); -#endif - return -1; - } - - for (pos = 0; pos < str_info.length; pos++) { - if (char_at(str_info.characters, pos) == special_char) { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return -1; - } - } - -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return str_info.length; -} - -/* MatchObject's 'expand' method. */ -static PyObject* match_expand(MatchObject* self, PyObject* str_template) { - Py_ssize_t literal_length; - PyObject* replacement; - JoinInfo join_info; - Py_ssize_t size; - Py_ssize_t i; - - /* Is the template just a literal? */ - literal_length = check_replacement_string(str_template, '\\'); - if (literal_length >= 0) { - /* It's a literal. */ - Py_INCREF(str_template); - return str_template; - } - - /* Hand the template to the template compiler. */ - replacement = call(RE_MODULE, "_compile_replacement_helper", - PyTuple_Pack(2, self->pattern, str_template)); - if (!replacement) - return NULL; - - init_join_list(&join_info, FALSE, PyUnicode_Check(self->string)); - - /* Add each part of the template to the list. */ - size = PyList_GET_SIZE(replacement); - for (i = 0; i < size; i++) { - PyObject* item; - PyObject* str_item; - - /* PyList_GET_ITEM borrows a reference. */ - item = PyList_GET_ITEM(replacement, i); - str_item = get_match_replacement(self, item, self->group_count); - if (!str_item) - goto error; - - /* Add to the list. */ - if (str_item == Py_None) - Py_DECREF(str_item); - else { - int status; - - status = add_to_join_list(&join_info, str_item); - Py_DECREF(str_item); - if (status < 0) - goto error; - } - } - - Py_DECREF(replacement); - - /* Convert the list to a single string (also cleans up join_info). */ - return join_list_info(&join_info); - -error: - clear_join_list(&join_info); - Py_DECREF(replacement); - return NULL; -} - -#if PY_VERSION_HEX >= 0x02060000 -/* Gets a MatchObject's group dictionary. */ -Py_LOCAL_INLINE(PyObject*) match_get_group_dict(MatchObject* self) { - PyObject* result; - PyObject* keys; - Py_ssize_t g; - - result = PyDict_New(); - if (!result || !self->pattern->groupindex) - return result; - - keys = PyMapping_Keys(self->pattern->groupindex); - if (!keys) - goto failed; - - for (g = 0; g < PyList_GET_SIZE(keys); g++) { - int status; - PyObject* key; - PyObject* value; - - /* PyList_GET_ITEM borrows a reference. */ - key = PyList_GET_ITEM(keys, g); - if (!key) - goto failed; - - value = match_get_group(self, key, Py_None, FALSE); - if (!value) - goto failed; - - status = PyDict_SetItem(result, key, value); - Py_DECREF(value); - if (status < 0) - goto failed; - } - - Py_DECREF(keys); - - return result; - -failed: - Py_XDECREF(keys); - Py_DECREF(result); - return NULL; -} - -/* MatchObject's 'expandf' method. */ -static PyObject* match_expandf(MatchObject* self, PyObject* str_template) { - PyObject* format_func; - PyObject* args = NULL; - size_t g; - PyObject* kwargs = NULL; - PyObject* result; - - format_func = PyObject_GetAttrString(str_template, "format"); - if (!format_func) - return NULL; - - args = PyTuple_New((Py_ssize_t)self->group_count + 1); - if (!args) - goto error; - - for (g = 0; g < self->group_count + 1; g++) - /* PyTuple_SetItem borrows the reference. */ - PyTuple_SetItem(args, (Py_ssize_t)g, match_get_group_by_index(self, - (Py_ssize_t)g, Py_None)); - - kwargs = match_get_group_dict(self); - if (!kwargs) - goto error; - - result = PyObject_Call(format_func, args, kwargs); - Py_DECREF(kwargs); - Py_DECREF(args); - Py_DECREF(format_func); - - return result; - -error: - Py_XDECREF(args); - Py_DECREF(format_func); - return NULL; -} - -#endif -Py_LOCAL_INLINE(PyObject*) make_match_copy(MatchObject* self); - -/* MatchObject's '__copy__' method. */ -static PyObject* match_copy(MatchObject* self, PyObject *unused) { - return make_match_copy(self); -} - -/* MatchObject's '__deepcopy__' method. */ -static PyObject* match_deepcopy(MatchObject* self, PyObject* memo) { - return make_match_copy(self); -} - -/* MatchObject's 'regs' attribute. */ -static PyObject* match_regs(MatchObject* self) { - PyObject* regs; - PyObject* item; - size_t g; - - regs = PyTuple_New((Py_ssize_t)self->group_count + 1); - if (!regs) - return NULL; - - item = Py_BuildValue("nn", self->match_start, self->match_end); - if (!item) - goto error; - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(regs, 0, item); - - for (g = 0; g < self->group_count; g++) { - RE_GroupSpan* span; - - span = &self->groups[g].span; - item = Py_BuildValue("nn", span->start, span->end); - if (!item) - goto error; - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(regs, g + 1, item); - } - - Py_INCREF(regs); - self->regs = regs; - - return regs; - -error: - Py_DECREF(regs); - return NULL; -} - -/* MatchObject's slice method. */ -Py_LOCAL_INLINE(PyObject*) match_get_group_slice(MatchObject* self, PyObject* - slice) { - Py_ssize_t start; - Py_ssize_t end; - Py_ssize_t step; - Py_ssize_t slice_length; - - if (PySlice_GetIndicesEx((PySliceObject*)slice, - (Py_ssize_t)self->group_count + 1, &start, &end, &step, &slice_length) < - 0) - return NULL; - - if (slice_length <= 0) - return PyTuple_New(0); - else { - PyObject* result; - Py_ssize_t cur; - Py_ssize_t i; - - result = PyTuple_New(slice_length); - if (!result) - return NULL; - - cur = start; - for (i = 0; i < slice_length; i++) { - /* PyTuple_SetItem borrows the reference. */ - PyTuple_SetItem(result, i, match_get_group_by_index(self, cur, - Py_None)); - cur += step; - } - - return result; - } -} - -/* MatchObject's length method. */ -Py_LOCAL_INLINE(Py_ssize_t) match_length(MatchObject* self) { - return (Py_ssize_t)self->group_count + 1; -} - -/* MatchObject's '__getitem__' method. */ -static PyObject* match_getitem(MatchObject* self, PyObject* item) { - if (PySlice_Check(item)) - return match_get_group_slice(self, item); - - return match_get_group(self, item, Py_None, TRUE); -} - -/* Determines the portion of the target string which is covered by the group - * captures. - */ -Py_LOCAL_INLINE(void) determine_target_substring(MatchObject* match, - Py_ssize_t* slice_start, Py_ssize_t* slice_end) { - Py_ssize_t start; - Py_ssize_t end; - size_t g; - - start = match->pos; - end = match->endpos; - - for (g = 0; g < match->group_count; g++) { - RE_GroupSpan* span; - size_t c; - - span = &match->groups[g].span; - if (span->start >= 0 && span->start < start) - start = span->start; - if (span->end >= 0 && span->end > end) - end = span->end; - - for (c = 0; c < match->groups[g].capture_count; c++) { - RE_GroupSpan* span; - - span = match->groups[g].captures; - if (span->start >= 0 && span->start < start) - start = span->start; - if (span->end >= 0 && span->end > end) - end = span->end; - } - } - - *slice_start = start; - *slice_end = end; -} - -/* MatchObject's 'detach_string' method. */ -static PyObject* match_detach_string(MatchObject* self, PyObject* unused) { - if (self->string) { - Py_ssize_t start; - Py_ssize_t end; - PyObject* substring; - - determine_target_substring(self, &start, &end); - - substring = get_slice(self->string, start, end); - if (substring) { - Py_XDECREF(self->substring); - self->substring = substring; - self->substring_offset = start; - - Py_DECREF(self->string); - self->string = NULL; - } - } - - Py_INCREF(Py_None); - return Py_None; -} - -/* The documentation of a MatchObject. */ -PyDoc_STRVAR(match_group_doc, - "group([group1, ...]) --> string or tuple of strings.\n\ - Return one or more subgroups of the match. If there is a single argument,\n\ - the result is a single string, or None if the group did not contribute to\n\ - the match; if there are multiple arguments, the result is a tuple with one\n\ - item per argument; if there are no arguments, the whole match is returned.\n\ - Group 0 is the whole match."); - -PyDoc_STRVAR(match_start_doc, - "start([group1, ...]) --> int or tuple of ints.\n\ - Return the index of the start of one or more subgroups of the match. If\n\ - there is a single argument, the result is an index, or -1 if the group did\n\ - not contribute to the match; if there are multiple arguments, the result is\n\ - a tuple with one item per argument; if there are no arguments, the index of\n\ - the start of the whole match is returned. Group 0 is the whole match."); - -PyDoc_STRVAR(match_end_doc, - "end([group1, ...]) --> int or tuple of ints.\n\ - Return the index of the end of one or more subgroups of the match. If there\n\ - is a single argument, the result is an index, or -1 if the group did not\n\ - contribute to the match; if there are multiple arguments, the result is a\n\ - tuple with one item per argument; if there are no arguments, the index of\n\ - the end of the whole match is returned. Group 0 is the whole match."); - -PyDoc_STRVAR(match_span_doc, - "span([group1, ...]) --> 2-tuple of int or tuple of 2-tuple of ints.\n\ - Return the span (a 2-tuple of the indices of the start and end) of one or\n\ - more subgroups of the match. If there is a single argument, the result is a\n\ - span, or (-1, -1) if the group did not contribute to the match; if there are\n\ - multiple arguments, the result is a tuple with one item per argument; if\n\ - there are no arguments, the span of the whole match is returned. Group 0 is\n\ - the whole match."); - -PyDoc_STRVAR(match_groups_doc, - "groups(default=None) --> tuple of strings.\n\ - Return a tuple containing all the subgroups of the match. The argument is\n\ - the default for groups that did not participate in the match."); - -PyDoc_STRVAR(match_groupdict_doc, - "groupdict(default=None) --> dict.\n\ - Return a dictionary containing all the named subgroups of the match, keyed\n\ - by the subgroup name. The argument is the value to be given for groups that\n\ - did not participate in the match."); - -PyDoc_STRVAR(match_capturesdict_doc, - "capturesdict() --> dict.\n\ - Return a dictionary containing the captures of all the named subgroups of the\n\ - match, keyed by the subgroup name."); - -PyDoc_STRVAR(match_expand_doc, - "expand(template) --> string.\n\ - Return the string obtained by doing backslash substitution on the template,\n\ - as done by the sub() method."); - -#if PY_VERSION_HEX >= 0x02060000 -PyDoc_STRVAR(match_expandf_doc, - "expandf(format) --> string.\n\ - Return the string obtained by using the format, as done by the subf()\n\ - method."); - -#endif -PyDoc_STRVAR(match_captures_doc, - "captures([group1, ...]) --> list of strings or tuple of list of strings.\n\ - Return the captures of one or more subgroups of the match. If there is a\n\ - single argument, the result is a list of strings; if there are multiple\n\ - arguments, the result is a tuple of lists with one item per argument; if\n\ - there are no arguments, the captures of the whole match is returned. Group\n\ - 0 is the whole match."); - -PyDoc_STRVAR(match_starts_doc, - "starts([group1, ...]) --> list of ints or tuple of list of ints.\n\ - Return the indices of the starts of the captures of one or more subgroups of\n\ - the match. If there is a single argument, the result is a list of indices;\n\ - if there are multiple arguments, the result is a tuple of lists with one\n\ - item per argument; if there are no arguments, the indices of the starts of\n\ - the captures of the whole match is returned. Group 0 is the whole match."); - -PyDoc_STRVAR(match_ends_doc, - "ends([group1, ...]) --> list of ints or tuple of list of ints.\n\ - Return the indices of the ends of the captures of one or more subgroups of\n\ - the match. If there is a single argument, the result is a list of indices;\n\ - if there are multiple arguments, the result is a tuple of lists with one\n\ - item per argument; if there are no arguments, the indices of the ends of the\n\ - captures of the whole match is returned. Group 0 is the whole match."); - -PyDoc_STRVAR(match_spans_doc, - "spans([group1, ...]) --> list of 2-tuple of ints or tuple of list of 2-tuple of ints.\n\ - Return the spans (a 2-tuple of the indices of the start and end) of the\n\ - captures of one or more subgroups of the match. If there is a single\n\ - argument, the result is a list of spans; if there are multiple arguments,\n\ - the result is a tuple of lists with one item per argument; if there are no\n\ - arguments, the spans of the captures of the whole match is returned. Group\n\ - 0 is the whole match."); - -PyDoc_STRVAR(match_detach_string_doc, - "detach_string()\n\ - Detaches the target string from the match object. The 'string' attribute\n\ - will become None."); - -/* MatchObject's methods. */ -static PyMethodDef match_methods[] = { - {"group", (PyCFunction)match_group, METH_VARARGS, match_group_doc}, - {"start", (PyCFunction)match_start, METH_VARARGS, match_start_doc}, - {"end", (PyCFunction)match_end, METH_VARARGS, match_end_doc}, - {"span", (PyCFunction)match_span, METH_VARARGS, match_span_doc}, - {"groups", (PyCFunction)match_groups, METH_VARARGS|METH_KEYWORDS, - match_groups_doc}, - {"groupdict", (PyCFunction)match_groupdict, METH_VARARGS|METH_KEYWORDS, - match_groupdict_doc}, - {"capturesdict", (PyCFunction)match_capturesdict, METH_NOARGS, - match_capturesdict_doc}, - {"expand", (PyCFunction)match_expand, METH_O, match_expand_doc}, -#if PY_VERSION_HEX >= 0x02060000 - {"expandf", (PyCFunction)match_expandf, METH_O, match_expandf_doc}, -#endif - {"captures", (PyCFunction)match_captures, METH_VARARGS, - match_captures_doc}, - {"starts", (PyCFunction)match_starts, METH_VARARGS, match_starts_doc}, - {"ends", (PyCFunction)match_ends, METH_VARARGS, match_ends_doc}, - {"spans", (PyCFunction)match_spans, METH_VARARGS, match_spans_doc}, - {"detach_string", (PyCFunction)match_detach_string, METH_NOARGS, - match_detach_string_doc}, - {"__copy__", (PyCFunction)match_copy, METH_NOARGS}, - {"__deepcopy__", (PyCFunction)match_deepcopy, METH_O}, - {"__getitem__", (PyCFunction)match_getitem, METH_O|METH_COEXIST}, - {NULL, NULL} -}; - -PyDoc_STRVAR(match_doc, "Match object"); - -/* MatchObject's 'lastindex' attribute. */ -static PyObject* match_lastindex(PyObject* self_) { - MatchObject* self; - - self = (MatchObject*)self_; - - if (self->lastindex >= 0) - return Py_BuildValue("n", self->lastindex); - - Py_INCREF(Py_None); - return Py_None; -} - -/* MatchObject's 'lastgroup' attribute. */ -static PyObject* match_lastgroup(PyObject* self_) { - MatchObject* self; - - self = (MatchObject*)self_; - - if (self->pattern->indexgroup && self->lastgroup >= 0) { - PyObject* index; - PyObject* result; - - index = Py_BuildValue("n", self->lastgroup); - - /* PyDict_GetItem returns borrows a reference. */ - result = PyDict_GetItem(self->pattern->indexgroup, index); - Py_DECREF(index); - if (result) { - Py_INCREF(result); - return result; - } - PyErr_Clear(); - } - - Py_INCREF(Py_None); - return Py_None; -} - -/* MatchObject's 'string' attribute. */ -static PyObject* match_string(PyObject* self_) { - MatchObject* self; - - self = (MatchObject*)self_; - - if (self->string) { - Py_INCREF(self->string); - return self->string; - } else { - Py_INCREF(Py_None); - return Py_None; - } -} -#if PY_VERSION_HEX < 0x02060000 - -/* MatchObject's 'partial' attribute. */ -static PyObject* match_partial(PyObject* self_) { - MatchObject* self; - PyObject* result; - - self = (MatchObject*)self_; - - result = self->partial ? Py_True : Py_False; - Py_INCREF(result); - - return result; -} -#endif - -/* MatchObject's 'fuzzy_counts' attribute. */ -static PyObject* match_fuzzy_counts(PyObject* self_) { - MatchObject* self; - - self = (MatchObject*)self_; - - return Py_BuildValue("nnn", self->fuzzy_counts[RE_FUZZY_SUB], - self->fuzzy_counts[RE_FUZZY_INS], self->fuzzy_counts[RE_FUZZY_DEL]); -} - -static PyGetSetDef match_getset[] = { - {"lastindex", (getter)match_lastindex, (setter)NULL, - "The group number of the last matched capturing group, or None."}, - {"lastgroup", (getter)match_lastgroup, (setter)NULL, - "The name of the last matched capturing group, or None."}, - {"regs", (getter)match_regs, (setter)NULL, - "A tuple of the spans of the capturing groups."}, - {"string", (getter)match_string, (setter)NULL, - "The string that was searched, or None if it has been detached."}, -#if PY_VERSION_HEX < 0x02060000 - {"partial", (getter)match_partial, (setter)NULL, - "Whether it's a partial match."}, -#endif - {"fuzzy_counts", (getter)match_fuzzy_counts, (setter)NULL, - "A tuple of the number of substitutions, insertions and deletions."}, - {NULL} /* Sentinel */ -}; - -static PyMemberDef match_members[] = { - {"re", T_OBJECT, offsetof(MatchObject, pattern), READONLY, - "The regex object that produced this match object."}, - {"pos", T_PYSSIZET, offsetof(MatchObject, pos), READONLY, - "The position at which the regex engine starting searching."}, - {"endpos", T_PYSSIZET, offsetof(MatchObject, endpos), READONLY, - "The final position beyond which the regex engine won't search."}, -#if PY_VERSION_HEX >= 0x02060000 - {"partial", T_BOOL, offsetof(MatchObject, partial), READONLY, - "Whether it's a partial match."}, -#endif - {NULL} /* Sentinel */ -}; - -static PyMappingMethods match_as_mapping = { - (lenfunc)match_length, /* mp_length */ - (binaryfunc)match_getitem, /* mp_subscript */ - 0, /* mp_ass_subscript */ -}; - -static PyTypeObject Match_Type = { - PyObject_HEAD_INIT(NULL) - 0, - "_" RE_MODULE "." "Match", - sizeof(MatchObject) -}; - -/* Copies the groups. */ -Py_LOCAL_INLINE(RE_GroupData*) copy_groups(RE_GroupData* groups, size_t - group_count) { - size_t span_count; - size_t g; - RE_GroupData* groups_copy; - RE_GroupSpan* spans_copy; - size_t offset; - - /* Calculate the total size of the group info. */ - span_count = 0; - for (g = 0; g < group_count; g++) - span_count += groups[g].capture_count; - - /* Allocate the storage for the group info in a single block. */ - groups_copy = (RE_GroupData*)re_alloc(group_count * sizeof(RE_GroupData) + - span_count * sizeof(RE_GroupSpan)); - if (!groups_copy) - return NULL; - - /* The storage for the spans comes after the other group info. */ - spans_copy = (RE_GroupSpan*)&groups_copy[group_count]; - - /* There's no need to initialise the spans info. */ - memset(groups_copy, 0, group_count * sizeof(RE_GroupData)); - - offset = 0; - for (g = 0; g < group_count; g++) { - RE_GroupData* orig; - RE_GroupData* copy; - - orig = &groups[g]; - copy = &groups_copy[g]; - copy->span = orig->span; - - copy->captures = &spans_copy[offset]; - offset += orig->capture_count; - - if (orig->capture_count > 0) { - Py_MEMCPY(copy->captures, orig->captures, orig->capture_count * - sizeof(RE_GroupSpan)); - copy->capture_capacity = orig->capture_count; - copy->capture_count = orig->capture_count; - } - } - - return groups_copy; -} - -/* Makes a copy of a MatchObject. */ -Py_LOCAL_INLINE(PyObject*) make_match_copy(MatchObject* self) { - MatchObject* match; - - if (!self->string) { - /* The target string has been detached, so the MatchObject is now - * immutable. - */ - Py_INCREF(self); - return (PyObject*)self; - } - - /* Create a MatchObject. */ - match = PyObject_NEW(MatchObject, &Match_Type); - if (!match) - return NULL; - - Py_MEMCPY(match, self, sizeof(MatchObject)); - - Py_INCREF(match->string); - Py_INCREF(match->substring); - Py_INCREF(match->pattern); - - /* Copy the groups to the MatchObject. */ - if (self->group_count > 0) { - match->groups = copy_groups(self->groups, self->group_count); - if (!match->groups) { - Py_DECREF(match); - return NULL; - } - } - - return (PyObject*)match; -} - -/* Creates a new MatchObject. */ -Py_LOCAL_INLINE(PyObject*) pattern_new_match(PatternObject* pattern, RE_State* - state, int status) { - /* Create MatchObject (from state object). */ - if (status > 0 || status == RE_ERROR_PARTIAL) { - MatchObject* match; - - /* Create a MatchObject. */ - match = PyObject_NEW(MatchObject, &Match_Type); - if (!match) - return NULL; - - match->string = state->string; - match->substring = state->string; - match->substring_offset = 0; - match->pattern = pattern; - match->regs = NULL; - match->fuzzy_counts[RE_FUZZY_SUB] = - state->total_fuzzy_counts[RE_FUZZY_SUB]; - match->fuzzy_counts[RE_FUZZY_INS] = - state->total_fuzzy_counts[RE_FUZZY_INS]; - match->fuzzy_counts[RE_FUZZY_DEL] = - state->total_fuzzy_counts[RE_FUZZY_DEL]; - match->partial = status == RE_ERROR_PARTIAL; - Py_INCREF(match->string); - Py_INCREF(match->substring); - Py_INCREF(match->pattern); - - /* Copy the groups to the MatchObject. */ - if (pattern->public_group_count > 0) { - match->groups = copy_groups(state->groups, - pattern->public_group_count); - if (!match->groups) { - Py_DECREF(match); - return NULL; - } - } else - match->groups = NULL; - - match->group_count = pattern->public_group_count; - - match->pos = state->slice_start; - match->endpos = state->slice_end; - - if (state->reverse) { - match->match_start = state->text_pos; - match->match_end = state->match_pos; - } else { - match->match_start = state->match_pos; - match->match_end = state->text_pos; - } - - match->lastindex = state->lastindex; - match->lastgroup = state->lastgroup; - - return (PyObject*)match; - } else if (status == 0) { - /* No match. */ - Py_INCREF(Py_None); - return Py_None; - } else { - /* Internal error. */ - set_error(status, NULL); - return NULL; - } -} - -/* Gets the text of a capture group from a state. */ -Py_LOCAL_INLINE(PyObject*) state_get_group(RE_State* state, Py_ssize_t index, - PyObject* string, BOOL empty) { - RE_GroupData* group; - Py_ssize_t start; - Py_ssize_t end; - - group = &state->groups[index - 1]; - - if (string != Py_None && index >= 1 && (size_t)index <= - state->pattern->public_group_count && group->capture_count > 0) { - start = group->span.start; - end = group->span.end; - } else { - if (empty) - /* Want an empty string. */ - start = end = 0; - else { - Py_INCREF(Py_None); - return Py_None; - } - } - - return get_slice(string, start, end); -} - -/* Acquires the lock (mutex) on the state if there's one. - * - * It also increments the owner's refcount just to ensure that it won't be - * destroyed by another thread. - */ -Py_LOCAL_INLINE(void) acquire_state_lock(PyObject* owner, RE_SafeState* - safe_state) { - RE_State* state; - - state = safe_state->re_state; - - if (state->lock) { - /* In order to avoid deadlock we need to release the GIL while trying - * to acquire the lock. - */ - Py_INCREF(owner); - if (!PyThread_acquire_lock(state->lock, 0)) { - release_GIL(safe_state); - PyThread_acquire_lock(state->lock, 1); - acquire_GIL(safe_state); - } - } -} - -/* Releases the lock (mutex) on the state if there's one. - * - * It also decrements the owner's refcount, which was incremented when the lock - * was acquired. - */ -Py_LOCAL_INLINE(void) release_state_lock(PyObject* owner, RE_SafeState* - safe_state) { - RE_State* state; - - state = safe_state->re_state; - - if (state->lock) { - PyThread_release_lock(state->lock); - Py_DECREF(owner); - } -} - -/* Implements the functionality of ScanObject's search and match methods. */ -Py_LOCAL_INLINE(PyObject*) scanner_search_or_match(ScannerObject* self, BOOL - search) { - RE_State* state; - RE_SafeState safe_state; - PyObject* match; - - state = &self->state; - - /* Initialise the "safe state" structure. */ - safe_state.re_state = state; - safe_state.thread_state = NULL; - - /* Acquire the state lock in case we're sharing the scanner object across - * threads. - */ - acquire_state_lock((PyObject*)self, &safe_state); - - if (self->status == RE_ERROR_FAILURE || self->status == RE_ERROR_PARTIAL) { - /* No or partial match. */ - release_state_lock((PyObject*)self, &safe_state); - Py_INCREF(Py_None); - return Py_None; - } else if (self->status < 0) { - /* Internal error. */ - release_state_lock((PyObject*)self, &safe_state); - set_error(self->status, NULL); - return NULL; - } - - /* Look for another match. */ - self->status = do_match(&safe_state, search); - if (self->status >= 0 || self->status == RE_ERROR_PARTIAL) { - /* Create the match object. */ - match = pattern_new_match(self->pattern, state, self->status); - - if (search && state->overlapped) { - /* Advance one character. */ - Py_ssize_t step; - - step = state->reverse ? -1 : 1; - state->text_pos = state->match_pos + step; - state->must_advance = FALSE; - } else - /* Continue from where we left off, but don't allow 2 contiguous - * zero-width matches. - */ - state->must_advance = state->text_pos == state->match_pos; - } else - /* Internal error. */ - match = NULL; - - /* Release the state lock. */ - release_state_lock((PyObject*)self, &safe_state); - - return match; -} - -/* ScannerObject's 'match' method. */ -static PyObject* scanner_match(ScannerObject* self, PyObject* unused) { - return scanner_search_or_match(self, FALSE); -} - -/* ScannerObject's 'search' method. */ -static PyObject* scanner_search(ScannerObject* self, PyObject *unused) { - return scanner_search_or_match(self, TRUE); -} - -/* ScannerObject's 'next' method. */ -static PyObject* scanner_next(PyObject* self) { - PyObject* match; - - match = scanner_search((ScannerObject*)self, NULL); - - if (match == Py_None) { - /* No match. */ - Py_DECREF(Py_None); - PyErr_SetNone(PyExc_StopIteration); - return NULL; - } - - return match; -} - -/* Returns an iterator for a ScannerObject. - * - * The iterator is actually the ScannerObject itself. - */ -static PyObject* scanner_iter(PyObject* self) { - Py_INCREF(self); - return self; -} - -/* Gets the next result from a scanner iterator. */ -static PyObject* scanner_iternext(PyObject* self) { - PyObject* match; - - match = scanner_search((ScannerObject*)self, NULL); - - if (match == Py_None) { - /* No match. */ - Py_DECREF(match); - return NULL; - } - - return match; -} - -/* Makes a copy of a ScannerObject. - * - * It actually doesn't make a copy, just returns the original object. - */ -Py_LOCAL_INLINE(PyObject*) make_scanner_copy(ScannerObject* self) { - Py_INCREF(self); - return (PyObject*)self; -} - -/* ScannerObject's '__copy__' method. */ -static PyObject* scanner_copy(ScannerObject* self, PyObject *unused) { - return make_scanner_copy(self); -} - -/* ScannerObject's '__deepcopy__' method. */ -static PyObject* scanner_deepcopy(ScannerObject* self, PyObject* memo) { - return make_scanner_copy(self); -} - -/* The documentation of a ScannerObject. */ -PyDoc_STRVAR(scanner_match_doc, - "match() --> MatchObject or None.\n\ - Match at the current position in the string."); - -PyDoc_STRVAR(scanner_search_doc, - "search() --> MatchObject or None.\n\ - Search from the current position in the string."); - -/* ScannerObject's methods. */ -static PyMethodDef scanner_methods[] = { - {"next", (PyCFunction)scanner_next, METH_NOARGS}, - {"match", (PyCFunction)scanner_match, METH_NOARGS, scanner_match_doc}, - {"search", (PyCFunction)scanner_search, METH_NOARGS, scanner_search_doc}, - {"__copy__", (PyCFunction)scanner_copy, METH_NOARGS}, - {"__deepcopy__", (PyCFunction)scanner_deepcopy, METH_O}, - {NULL, NULL} -}; - -PyDoc_STRVAR(scanner_doc, "Scanner object"); - -/* Deallocates a ScannerObject. */ -static void scanner_dealloc(PyObject* self_) { - ScannerObject* self; - - self = (ScannerObject*)self_; - - state_fini(&self->state); - Py_DECREF(self->pattern); - PyObject_DEL(self); -} - -static PyMemberDef scanner_members[] = { - {"pattern", T_OBJECT, offsetof(ScannerObject, pattern), READONLY, - "The regex object that produced this scanner object."}, - {NULL} /* Sentinel */ -}; - -static PyTypeObject Scanner_Type = { - PyObject_HEAD_INIT(NULL) - 0, - "_" RE_MODULE "." "Scanner", - sizeof(ScannerObject) -}; - -/* Decodes a 'concurrent' argument. */ -Py_LOCAL_INLINE(int) decode_concurrent(PyObject* concurrent) { - Py_ssize_t value; - - if (concurrent == Py_None) - return RE_CONC_DEFAULT; - - value = PyLong_AsLong(concurrent); - if (value == -1 && PyErr_Occurred()) { - set_error(RE_ERROR_CONCURRENT, NULL); - return -1; - } - - return value ? RE_CONC_YES : RE_CONC_NO; -} - -/* Decodes a 'partial' argument. */ -Py_LOCAL_INLINE(BOOL) decode_partial(PyObject* partial) { - Py_ssize_t value; - - if (partial == Py_False) - return FALSE; - - if (partial == Py_True) - return TRUE; - - value = PyLong_AsLong(partial); - if (value == -1 && PyErr_Occurred()) { - PyErr_Clear(); - return TRUE; - } - - return value != 0; -} - -/* Creates a new ScannerObject. */ -static PyObject* pattern_scanner(PatternObject* pattern, PyObject* args, - PyObject* kwargs) { - /* Create search state object. */ - ScannerObject* self; - Py_ssize_t start; - Py_ssize_t end; - int conc; - BOOL part; - - PyObject* string; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - Py_ssize_t overlapped = FALSE; - PyObject* concurrent = Py_None; - PyObject* partial = Py_False; - static char* kwlist[] = { "string", "pos", "endpos", "overlapped", - "concurrent", "partial", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|OOnOO:scanner", kwlist, - &string, &pos, &endpos, &overlapped, &concurrent, &partial)) - return NULL; - - start = as_string_index(pos, 0); - if (start == -1 && PyErr_Occurred()) - return NULL; - - end = as_string_index(endpos, PY_SSIZE_T_MAX); - if (end == -1 && PyErr_Occurred()) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - part = decode_partial(partial); - - /* Create a scanner object. */ - self = PyObject_NEW(ScannerObject, &Scanner_Type); - if (!self) - return NULL; - - self->pattern = pattern; - Py_INCREF(self->pattern); - - /* The MatchObject, and therefore repeated captures, will be visible. */ - if (!state_init(&self->state, pattern, string, start, end, overlapped != 0, - conc, part, TRUE, TRUE, FALSE)) { - PyObject_DEL(self); - return NULL; - } - - self->status = RE_ERROR_SUCCESS; - - return (PyObject*) self; -} - -/* Performs the split for the SplitterObject. */ -Py_LOCAL_INLINE(PyObject*) next_split_part(SplitterObject* self) { - RE_State* state; - RE_SafeState safe_state; - PyObject* result = NULL; /* Initialise to stop compiler warning. */ - - state = &self->state; - - /* Initialise the "safe state" structure. */ - safe_state.re_state = state; - safe_state.thread_state = NULL; - - /* Acquire the state lock in case we're sharing the splitter object across - * threads. - */ - acquire_state_lock((PyObject*)self, &safe_state); - - if (self->status == RE_ERROR_FAILURE || self->status == RE_ERROR_PARTIAL) { - /* Finished. */ - release_state_lock((PyObject*)self, &safe_state); - result = Py_False; - Py_INCREF(result); - return result; - } else if (self->status < 0) { - /* Internal error. */ - release_state_lock((PyObject*)self, &safe_state); - set_error(self->status, NULL); - return NULL; - } - - if (self->index == 0) { - if (self->split_count < self->maxsplit) { - Py_ssize_t step; - Py_ssize_t end_pos; - - if (state->reverse) { - step = -1; - end_pos = state->slice_start; - } else { - step = 1; - end_pos = state->slice_end; - } - -retry: - self->status = do_match(&safe_state, TRUE); - if (self->status < 0) - goto error; - - if (self->status == RE_ERROR_SUCCESS) { - if (state->version_0) { - /* Version 0 behaviour is to advance one character if the - * split was zero-width. Unfortunately, this can give an - * incorrect result. GvR wants this behaviour to be - * retained so as not to break any existing software which - * might rely on it. - */ - if (state->text_pos == state->match_pos) { - if (self->last_pos == end_pos) - goto no_match; - - /* Advance one character. */ - state->text_pos += step; - state->must_advance = FALSE; - goto retry; - } - } - - ++self->split_count; - - /* Get segment before this match. */ - if (state->reverse) - result = get_slice(state->string, state->match_pos, - self->last_pos); - else - result = get_slice(state->string, self->last_pos, - state->match_pos); - if (!result) - goto error; - - self->last_pos = state->text_pos; - - /* Version 0 behaviour is to advance one character if the match - * was zero-width. Unfortunately, this can give an incorrect - * result. GvR wants this behaviour to be retained so as not to - * break any existing software which might rely on it. - */ - if (state->version_0) { - if (state->text_pos == state->match_pos) - /* Advance one character. */ - state->text_pos += step; - - state->must_advance = FALSE; - } else - /* Continue from where we left off, but don't allow a - * contiguous zero-width match. - */ - state->must_advance = TRUE; - } - } else - goto no_match; - - if (self->status == RE_ERROR_FAILURE || self->status == - RE_ERROR_PARTIAL) { -no_match: - /* Get segment following last match (even if empty). */ - if (state->reverse) - result = get_slice(state->string, 0, self->last_pos); - else - result = get_slice(state->string, self->last_pos, - state->text_length); - if (!result) - goto error; - } - } else { - /* Add group. */ - result = state_get_group(state, self->index, state->string, FALSE); - if (!result) - goto error; - } - - ++self->index; - if ((size_t)self->index > state->pattern->public_group_count) - self->index = 0; - - /* Release the state lock. */ - release_state_lock((PyObject*)self, &safe_state); - - return result; - -error: - /* Release the state lock. */ - release_state_lock((PyObject*)self, &safe_state); - - return NULL; -} - -/* SplitterObject's 'split' method. */ -static PyObject* splitter_split(SplitterObject* self, PyObject *unused) { - PyObject* result; - - result = next_split_part(self); - - if (result == Py_False) { - /* The sentinel. */ - Py_DECREF(Py_False); - Py_INCREF(Py_None); - return Py_None; - } - - return result; -} - -/* SplitterObject's 'next' method. */ -static PyObject* splitter_next(PyObject* self) { - PyObject* result; - - result = next_split_part((SplitterObject*)self); - - if (result == Py_False) { - /* No match. */ - Py_DECREF(Py_False); - PyErr_SetNone(PyExc_StopIteration); - return NULL; - } - - return result; -} - -/* Returns an iterator for a SplitterObject. - * - * The iterator is actually the SplitterObject itself. - */ -static PyObject* splitter_iter(PyObject* self) { - Py_INCREF(self); - return self; -} - -/* Gets the next result from a splitter iterator. */ -static PyObject* splitter_iternext(PyObject* self) { - PyObject* result; - - result = next_split_part((SplitterObject*)self); - - if (result == Py_False) { - /* No match. */ - Py_DECREF(result); - return NULL; - } - - return result; -} - -/* Makes a copy of a SplitterObject. - * - * It actually doesn't make a copy, just returns the original object. - */ -Py_LOCAL_INLINE(PyObject*) make_splitter_copy(SplitterObject* self) { - Py_INCREF(self); - return (PyObject*)self; -} - -/* SplitterObject's '__copy__' method. */ -static PyObject* splitter_copy(SplitterObject* self, PyObject *unused) { - return make_splitter_copy(self); -} - -/* SplitterObject's '__deepcopy__' method. */ -static PyObject* splitter_deepcopy(SplitterObject* self, PyObject* memo) { - return make_splitter_copy(self); -} - -/* The documentation of a SplitterObject. */ -PyDoc_STRVAR(splitter_split_doc, - "split() --> string or None.\n\ - Return the next part of the split string."); - -/* SplitterObject's methods. */ -static PyMethodDef splitter_methods[] = { - {"next", (PyCFunction)splitter_next, METH_NOARGS}, - {"split", (PyCFunction)splitter_split, METH_NOARGS, splitter_split_doc}, - {"__copy__", (PyCFunction)splitter_copy, METH_NOARGS}, - {"__deepcopy__", (PyCFunction)splitter_deepcopy, METH_O}, - {NULL, NULL} -}; - -PyDoc_STRVAR(splitter_doc, "Splitter object"); - -/* Deallocates a SplitterObject. */ -static void splitter_dealloc(PyObject* self_) { - SplitterObject* self; - - self = (SplitterObject*)self_; - - state_fini(&self->state); - Py_DECREF(self->pattern); - PyObject_DEL(self); -} - -static PyMemberDef splitter_members[] = { - {"pattern", T_OBJECT, offsetof(SplitterObject, pattern), READONLY, - "The regex object that produced this splitter object."}, - {NULL} /* Sentinel */ -}; - -static PyTypeObject Splitter_Type = { - PyObject_HEAD_INIT(NULL) - 0, - "_" RE_MODULE "." "Splitter", - sizeof(SplitterObject) -}; - -/* Creates a new SplitterObject. */ -Py_LOCAL_INLINE(PyObject*) pattern_splitter(PatternObject* pattern, PyObject* - args, PyObject* kwargs) { - /* Create split state object. */ - int conc; - SplitterObject* self; - RE_State* state; - - PyObject* string; - Py_ssize_t maxsplit = 0; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "string", "maxsplit", "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|nO:splitter", kwlist, - &string, &maxsplit, &concurrent)) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - /* Create a splitter object. */ - self = PyObject_NEW(SplitterObject, &Splitter_Type); - if (!self) - return NULL; - - self->pattern = pattern; - Py_INCREF(self->pattern); - - if (maxsplit == 0) - maxsplit = PY_SSIZE_T_MAX; - - state = &self->state; - - /* The MatchObject, and therefore repeated captures, will not be visible. - */ - if (!state_init(state, pattern, string, 0, PY_SSIZE_T_MAX, FALSE, conc, - FALSE, TRUE, FALSE, FALSE)) { - PyObject_DEL(self); - return NULL; - } - - self->maxsplit = maxsplit; - self->last_pos = state->reverse ? state->text_length : 0; - self->split_count = 0; - self->index = 0; - self->status = 1; - - return (PyObject*) self; -} - -/* Implements the functionality of PatternObject's search and match methods. */ -Py_LOCAL_INLINE(PyObject*) pattern_search_or_match(PatternObject* self, - PyObject* args, PyObject* kwargs, char* args_desc, BOOL search, BOOL - match_all) { - Py_ssize_t start; - Py_ssize_t end; - int conc; - BOOL part; - RE_State state; - RE_SafeState safe_state; - int status; - PyObject* match; - - PyObject* string; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - PyObject* concurrent = Py_None; - PyObject* partial = Py_False; - static char* kwlist[] = { "string", "pos", "endpos", "concurrent", - "partial", NULL }; - /* When working with a short string, such as a line from a file, the - * relative cost of PyArg_ParseTupleAndKeywords can be significant, and - * it's worth not using it when there are only positional arguments. - */ - Py_ssize_t arg_count; - if (args && !kwargs && PyTuple_CheckExact(args)) - arg_count = PyTuple_GET_SIZE(args); - else - arg_count = -1; - - if (1 <= arg_count && arg_count <= 5) { - /* PyTuple_GET_ITEM borrows the reference. */ - string = PyTuple_GET_ITEM(args, 0); - if (arg_count >= 2) - pos = PyTuple_GET_ITEM(args, 1); - if (arg_count >= 3) - endpos = PyTuple_GET_ITEM(args, 2); - if (arg_count >= 4) - concurrent = PyTuple_GET_ITEM(args, 3); - if (arg_count >= 5) - partial = PyTuple_GET_ITEM(args, 4); - } else if (!PyArg_ParseTupleAndKeywords(args, kwargs, args_desc, kwlist, - &string, &pos, &endpos, &concurrent, &partial)) - return NULL; - - start = as_string_index(pos, 0); - if (start == -1 && PyErr_Occurred()) - return NULL; - - end = as_string_index(endpos, PY_SSIZE_T_MAX); - if (end == -1 && PyErr_Occurred()) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - part = decode_partial(partial); - - /* The MatchObject, and therefore repeated captures, will be visible. */ - if (!state_init(&state, self, string, start, end, FALSE, conc, part, FALSE, - TRUE, match_all)) - return NULL; - - /* Initialise the "safe state" structure. */ - safe_state.re_state = &state; - safe_state.thread_state = NULL; - - status = do_match(&safe_state, search); - - if (status >= 0 || status == RE_ERROR_PARTIAL) - /* Create the match object. */ - match = pattern_new_match(self, &state, status); - else - match = NULL; - - state_fini(&state); - - return match; -} - -/* PatternObject's 'match' method. */ -static PyObject* pattern_match(PatternObject* self, PyObject* args, PyObject* - kwargs) { - return pattern_search_or_match(self, args, kwargs, "O|OOOO:match", FALSE, - FALSE); -} - -/* PatternObject's 'fullmatch' method. */ -static PyObject* pattern_fullmatch(PatternObject* self, PyObject* args, - PyObject* kwargs) { - return pattern_search_or_match(self, args, kwargs, "O|OOOO:fullmatch", - FALSE, TRUE); -} - -/* PatternObject's 'search' method. */ -static PyObject* pattern_search(PatternObject* self, PyObject* args, PyObject* - kwargs) { - return pattern_search_or_match(self, args, kwargs, "O|OOOO:search", TRUE, - FALSE); -} - -/* Gets the limits of the matching. */ -Py_LOCAL_INLINE(BOOL) get_limits(PyObject* pos, PyObject* endpos, Py_ssize_t - length, Py_ssize_t* start, Py_ssize_t* end) { - Py_ssize_t s; - Py_ssize_t e; - - s = as_string_index(pos, 0); - if (s == -1 && PyErr_Occurred()) - return FALSE; - - e = as_string_index(endpos, PY_SSIZE_T_MAX); - if (e == -1 && PyErr_Occurred()) - return FALSE; - - /* Adjust boundaries. */ - if (s < 0) - s += length; - if (s < 0) - s = 0; - else if (s > length) - s = length; - - if (e < 0) - e += length; - if (e < 0) - e = 0; - else if (e > length) - e = length; - - *start = s; - *end = e; - - return TRUE; -} - -/* Gets a replacement item from the replacement list. - * - * The replacement item could be a string literal or a group. - * - * It can return None to represent an empty string. - */ -Py_LOCAL_INLINE(PyObject*) get_sub_replacement(PyObject* item, PyObject* - string, RE_State* state, size_t group_count) { - Py_ssize_t index; - - if (PyUnicode_CheckExact(item) || PyString_CheckExact(item)) { - /* It's a literal, which can be added directly to the list. */ - Py_INCREF(item); - return item; - } - - /* Is it a group reference? */ - index = as_group_index(item); - if (index == -1 && PyErr_Occurred()) { - /* Not a group either! */ - set_error(RE_ERROR_REPLACEMENT, NULL); - return NULL; - } - - if (index == 0) { - /* The entire matched portion of the string. */ - if (state->match_pos == state->text_pos) { - /* Return None for "". */ - Py_INCREF(Py_None); - return Py_None; - } - - if (state->reverse) - return get_slice(string, state->text_pos, state->match_pos); - else - return get_slice(string, state->match_pos, state->text_pos); - } else if (1 <= index && (size_t)index <= group_count) { - /* A group. */ - RE_GroupData* group; - - group = &state->groups[index - 1]; - - if (group->capture_count == 0 && group->span.start != group->span.end) - { - /* The group didn't match or is "", so return None for "". */ - Py_INCREF(Py_None); - return Py_None; - } - - return get_slice(string, group->span.start, group->span.end); - } else { - /* No such group. */ - set_error(RE_ERROR_INVALID_GROUP_REF, NULL); - return NULL; - } -} - -/* PatternObject's 'subx' method. */ -Py_LOCAL_INLINE(PyObject*) pattern_subx(PatternObject* self, PyObject* - str_template, PyObject* string, Py_ssize_t maxsub, int sub_type, PyObject* - pos, PyObject* endpos, int concurrent) { - RE_StringInfo str_info; - Py_ssize_t start; - Py_ssize_t end; - BOOL is_callable = FALSE; - BOOL is_literal = FALSE; - BOOL is_template = FALSE; - PyObject* replacement = NULL; -#if PY_VERSION_HEX >= 0x02060000 - BOOL is_format = FALSE; -#endif - RE_State state; - RE_SafeState safe_state; - JoinInfo join_info; - Py_ssize_t sub_count; - Py_ssize_t last_pos; - PyObject* item; - Py_ssize_t end_pos; - Py_ssize_t step; - - /* Get the string. */ - if (!get_string(string, &str_info)) - return NULL; - - /* Get the limits of the search. */ - if (!get_limits(pos, endpos, str_info.length, &start, &end)) { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return NULL; - } - - /* If the pattern is too long for the string, then take a shortcut, unless - * it's a fuzzy pattern. - */ - if (!self->is_fuzzy && self->min_width > end - start) { - PyObject* result; - - Py_INCREF(string); - - if (sub_type & RE_SUBN) - result = Py_BuildValue("Nn", string, 0); - else - result = string; - -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return result; - } - - if (maxsub == 0) - maxsub = PY_SSIZE_T_MAX; - - /* sub/subn takes either a function or a string template. */ - if (PyCallable_Check(str_template)) { - /* It's callable. */ - is_callable = TRUE; - - replacement = str_template; - Py_INCREF(replacement); -#if PY_VERSION_HEX >= 0x02060000 - } else if (sub_type & RE_SUBF) { - /* Is it a literal format? - * - * To keep it simple we'll say that a literal is a string which can be - * used as-is, so no placeholders. - */ - Py_ssize_t literal_length; - - literal_length = check_replacement_string(str_template, '{'); - if (literal_length > 0) { - /* It's a literal. */ - is_literal = TRUE; - - replacement = str_template; - Py_INCREF(replacement); - } else if (literal_length < 0) { - /* It isn't a literal, so get the 'format' method. */ - is_format = TRUE; - - replacement = PyObject_GetAttrString(str_template, "format"); - if (!replacement) { - release_buffer(&str_info); - return NULL; - } - } -#endif - } else { - /* Is it a literal template? - * - * To keep it simple we'll say that a literal is a string which can be - * used as-is, so no backslashes. - */ - Py_ssize_t literal_length; - - literal_length = check_replacement_string(str_template, '\\'); - if (literal_length > 0) { - /* It's a literal. */ - is_literal = TRUE; - - replacement = str_template; - Py_INCREF(replacement); - } else if (literal_length < 0 ) { - /* It isn't a literal, so hand it over to the template compiler. */ - is_template = TRUE; - - replacement = call(RE_MODULE, "_compile_replacement_helper", - PyTuple_Pack(2, self, str_template)); - if (!replacement) { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return NULL; - } - } - } - - /* The MatchObject, and therefore repeated captures, will be visible only - * if the replacement is callable. - */ - if (!state_init_2(&state, self, string, &str_info, start, end, FALSE, - concurrent, FALSE, FALSE, is_callable, FALSE)) { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - Py_XDECREF(replacement); - return NULL; - } - - /* Initialise the "safe state" structure. */ - safe_state.re_state = &state; - safe_state.thread_state = NULL; - - init_join_list(&join_info, state.reverse, PyUnicode_Check(string)); - - sub_count = 0; - last_pos = state.reverse ? state.text_length : 0; - step = state.reverse ? -1 : 1; - while (sub_count < maxsub) { - int status; - - status = do_match(&safe_state, TRUE); - if (status < 0) - goto error; - - if (status == 0) - break; - - /* Append the segment before this match. */ - if (state.match_pos != last_pos) { - if (state.reverse) - item = get_slice(string, state.match_pos, last_pos); - else - item = get_slice(string, last_pos, state.match_pos); - if (!item) - goto error; - - /* Add to the list. */ - status = add_to_join_list(&join_info, item); - Py_DECREF(item); - if (status < 0) - goto error; - } - - /* Add this match. */ - if (is_literal) { - /* The replacement is a literal string. */ - status = add_to_join_list(&join_info, replacement); - if (status < 0) - goto error; -#if PY_VERSION_HEX >= 0x02060000 - } else if (is_format) { - /* The replacement is a format string. */ - MatchObject* match; - PyObject* args; - size_t g; - PyObject* kwargs; - - /* We need to create the arguments for the 'format' method. We'll - * start by creating a MatchObject. - */ - match = (MatchObject*)pattern_new_match(self, &state, 1); - if (!match) - goto error; - - /* The args are a tuple of the capture group matches. */ - args = PyTuple_New((Py_ssize_t)state.pattern->public_group_count + - 1); - if (!args) { - Py_DECREF(match); - goto error; - } - - for (g = 0; g < state.pattern->public_group_count + 1; g++) - /* PyTuple_SetItem borrows the reference. */ - PyTuple_SetItem(args, (Py_ssize_t)g, - match_get_group_by_index(match, (Py_ssize_t)g, Py_None)); - - /* The kwargs are a dict of the named capture group matches. */ - kwargs = match_get_group_dict(match); - if (!kwargs) { - Py_DECREF(args); - Py_DECREF(match); - goto error; - } - - /* Call the 'format' method. */ - item = PyObject_Call(replacement, args, kwargs); - Py_DECREF(kwargs); - Py_DECREF(args); - Py_DECREF(match); - if (!item) - goto error; - - /* Add the result to the list. */ - status = add_to_join_list(&join_info, item); - Py_DECREF(item); - if (status < 0) - goto error; -#endif - } else if (is_template) { - /* The replacement is a list template. */ - Py_ssize_t size; - Py_ssize_t i; - - /* Add each part of the template to the list. */ - size = PyList_GET_SIZE(replacement); - for (i = 0; i < size; i++) { - PyObject* item; - PyObject* str_item; - - /* PyList_GET_ITEM borrows a reference. */ - item = PyList_GET_ITEM(replacement, i); - str_item = get_sub_replacement(item, string, &state, - self->public_group_count); - if (!str_item) - goto error; - - /* Add the result to the list. */ - if (str_item == Py_None) - /* None for "". */ - Py_DECREF(str_item); - else { - status = add_to_join_list(&join_info, str_item); - Py_DECREF(str_item); - if (status < 0) - goto error; - } - } - } else if (is_callable) { - /* Pass a MatchObject to the replacement function. */ - PyObject* match; - PyObject* args; - - /* We need to create a MatchObject to pass to the replacement - * function. - */ - match = pattern_new_match(self, &state, 1); - if (!match) - goto error; - - /* The args for the replacement function. */ - args = PyTuple_Pack(1, match); - if (!args) { - Py_DECREF(match); - goto error; - } - - /* Call the replacement function. */ - item = PyObject_CallObject(replacement, args); - Py_DECREF(args); - Py_DECREF(match); - if (!item) - goto error; - - /* Add the result to the list. */ - status = add_to_join_list(&join_info, item); - Py_DECREF(item); - if (status < 0) - goto error; - } - - ++sub_count; - - last_pos = state.text_pos; - - if (state.version_0) { - /* Always advance after a zero-width match. */ - if (state.match_pos == state.text_pos) { - state.text_pos += step; - state.must_advance = FALSE; - } else - state.must_advance = TRUE; - } else - /* Continue from where we left off, but don't allow a contiguous - * zero-width match. - */ - state.must_advance = state.match_pos == state.text_pos; - } - - /* Get the segment following the last match. We use 'length' instead of - * 'text_length' because the latter is truncated to 'slice_end', a - * documented idiosyncracy of the 're' module. - */ - end_pos = state.reverse ? 0 : str_info.length; - if (last_pos != end_pos) { - int status; - - /* The segment is part of the original string. */ - if (state.reverse) - item = get_slice(string, 0, last_pos); - else - item = get_slice(string, last_pos, str_info.length); - if (!item) - goto error; - - status = add_to_join_list(&join_info, item); - Py_DECREF(item); - if (status < 0) - goto error; - } - - Py_XDECREF(replacement); - - /* Convert the list to a single string (also cleans up join_info). */ - item = join_list_info(&join_info); - - state_fini(&state); - - if (!item) - return NULL; - - if (sub_type & RE_SUBN) - return Py_BuildValue("Nn", item, sub_count); - - return item; - -error: - clear_join_list(&join_info); - state_fini(&state); - Py_XDECREF(replacement); - return NULL; -} - -/* PatternObject's 'sub' method. */ -static PyObject* pattern_sub(PatternObject* self, PyObject* args, PyObject* - kwargs) { - int conc; - - PyObject* replacement; - PyObject* string; - Py_ssize_t count = 0; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "repl", "string", "count", "pos", "endpos", - "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|nOOO:sub", kwlist, - &replacement, &string, &count, &pos, &endpos, &concurrent)) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - return pattern_subx(self, replacement, string, count, RE_SUB, pos, endpos, - conc); -} - -#if PY_VERSION_HEX >= 0x02060000 -/* PatternObject's 'subf' method. */ -static PyObject* pattern_subf(PatternObject* self, PyObject* args, PyObject* - kwargs) { - int conc; - - PyObject* format; - PyObject* string; - Py_ssize_t count = 0; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "format", "string", "count", "pos", "endpos", - "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|nOOO:sub", kwlist, - &format, &string, &count, &pos, &endpos, &concurrent)) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - return pattern_subx(self, format, string, count, RE_SUBF, pos, endpos, - conc); -} - -#endif -/* PatternObject's 'subn' method. */ -static PyObject* pattern_subn(PatternObject* self, PyObject* args, PyObject* - kwargs) { - int conc; - - PyObject* replacement; - PyObject* string; - Py_ssize_t count = 0; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "repl", "string", "count", "pos", "endpos", - "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|nOOO:subn", kwlist, - &replacement, &string, &count, &pos, &endpos, &concurrent)) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - return pattern_subx(self, replacement, string, count, RE_SUBN, pos, endpos, - conc); -} - -#if PY_VERSION_HEX >= 0x02060000 -/* PatternObject's 'subfn' method. */ -static PyObject* pattern_subfn(PatternObject* self, PyObject* args, PyObject* - kwargs) { - int conc; - - PyObject* format; - PyObject* string; - Py_ssize_t count = 0; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "format", "string", "count", "pos", "endpos", - "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|nOOO:subn", kwlist, - &format, &string, &count, &pos, &endpos, &concurrent)) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - return pattern_subx(self, format, string, count, RE_SUBF | RE_SUBN, pos, - endpos, conc); -} - -#endif -/* PatternObject's 'split' method. */ -static PyObject* pattern_split(PatternObject* self, PyObject* args, PyObject* - kwargs) { - int conc; - - RE_State state; - RE_SafeState safe_state; - PyObject* list; - PyObject* item; - int status; - Py_ssize_t split_count; - size_t g; - Py_ssize_t start_pos; - Py_ssize_t end_pos; - Py_ssize_t step; - Py_ssize_t last_pos; - - PyObject* string; - Py_ssize_t maxsplit = 0; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "string", "maxsplit", "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|nO:split", kwlist, - &string, &maxsplit, &concurrent)) - return NULL; - - if (maxsplit == 0) - maxsplit = PY_SSIZE_T_MAX; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - /* The MatchObject, and therefore repeated captures, will not be visible. - */ - if (!state_init(&state, self, string, 0, PY_SSIZE_T_MAX, FALSE, conc, - FALSE, FALSE, FALSE, FALSE)) - return NULL; - - /* Initialise the "safe state" structure. */ - safe_state.re_state = &state; - safe_state.thread_state = NULL; - - list = PyList_New(0); - if (!list) { - state_fini(&state); - return NULL; - } - - split_count = 0; - if (state.reverse) { - start_pos = state.text_length; - end_pos = 0; - step = -1; - } else { - start_pos = 0; - end_pos = state.text_length; - step = 1; - } - - last_pos = start_pos; - while (split_count < maxsplit) { - status = do_match(&safe_state, TRUE); - if (status < 0) - goto error; - - if (status == 0) - /* No more matches. */ - break; - - if (state.version_0) { - /* Version 0 behaviour is to advance one character if the split was - * zero-width. Unfortunately, this can give an incorrect result. - * GvR wants this behaviour to be retained so as not to break any - * existing software which might rely on it. - */ - if (state.text_pos == state.match_pos) { - if (last_pos == end_pos) - break; - - /* Advance one character. */ - state.text_pos += step; - state.must_advance = FALSE; - continue; - } - } - - /* Get segment before this match. */ - if (state.reverse) - item = get_slice(string, state.match_pos, last_pos); - else - item = get_slice(string, last_pos, state.match_pos); - if (!item) - goto error; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - - /* Add groups (if any). */ - for (g = 1; g <= self->public_group_count; g++) { - item = state_get_group(&state, (Py_ssize_t)g, string, FALSE); - if (!item) - goto error; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - } - - ++split_count; - last_pos = state.text_pos; - - /* Version 0 behaviour is to advance one character if the match was - * zero-width. Unfortunately, this can give an incorrect result. GvR - * wants this behaviour to be retained so as not to break any existing - * software which might rely on it. - */ - if (state.version_0) { - if (state.text_pos == state.match_pos) - /* Advance one character. */ - state.text_pos += step; - - state.must_advance = FALSE; - } else - /* Continue from where we left off, but don't allow a contiguous - * zero-width match. - */ - state.must_advance = TRUE; - } - - /* Get segment following last match (even if empty). */ - if (state.reverse) - item = get_slice(string, 0, last_pos); - else - item = get_slice(string, last_pos, state.text_length); - if (!item) - goto error; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - - state_fini(&state); - - return list; - -error: - Py_DECREF(list); - state_fini(&state); - return NULL; -} - -/* PatternObject's 'splititer' method. */ -static PyObject* pattern_splititer(PatternObject* pattern, PyObject* args, - PyObject* kwargs) { - return pattern_splitter(pattern, args, kwargs); -} - -/* PatternObject's 'findall' method. */ -static PyObject* pattern_findall(PatternObject* self, PyObject* args, PyObject* - kwargs) { - Py_ssize_t start; - Py_ssize_t end; - RE_State state; - int conc; - RE_SafeState safe_state; - PyObject* list; - Py_ssize_t step; - int status; - size_t g; - Py_ssize_t b; - Py_ssize_t e; - - PyObject* string; - PyObject* pos = Py_None; - PyObject* endpos = Py_None; - Py_ssize_t overlapped = FALSE; - PyObject* concurrent = Py_None; - static char* kwlist[] = { "string", "pos", "endpos", "overlapped", - "concurrent", NULL }; - if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|OOnO:findall", kwlist, - &string, &pos, &endpos, &overlapped, &concurrent)) - return NULL; - - start = as_string_index(pos, 0); - if (start == -1 && PyErr_Occurred()) - return NULL; - - end = as_string_index(endpos, PY_SSIZE_T_MAX); - if (end == -1 && PyErr_Occurred()) - return NULL; - - conc = decode_concurrent(concurrent); - if (conc < 0) - return NULL; - - /* The MatchObject, and therefore repeated captures, will not be visible. - */ - if (!state_init(&state, self, string, start, end, overlapped != 0, conc, - FALSE, FALSE, FALSE, FALSE)) - return NULL; - - /* Initialise the "safe state" structure. */ - safe_state.re_state = &state; - safe_state.thread_state = NULL; - - list = PyList_New(0); - if (!list) { - state_fini(&state); - return NULL; - } - - step = state.reverse ? -1 : 1; - while (state.slice_start <= state.text_pos && state.text_pos <= - state.slice_end) { - PyObject* item; - - status = do_match(&safe_state, TRUE); - if (status < 0) - goto error; - - if (status == 0) - break; - - /* Don't bother to build a MatchObject. */ - switch (self->public_group_count) { - case 0: - if (state.reverse) { - b = state.text_pos; - e = state.match_pos; - } else { - b = state.match_pos; - e = state.text_pos; - } - item = get_slice(string, b, e); - if (!item) - goto error; - break; - case 1: - item = state_get_group(&state, 1, string, TRUE); - if (!item) - goto error; - break; - default: - item = PyTuple_New((Py_ssize_t)self->public_group_count); - if (!item) - goto error; - - for (g = 0; g < self->public_group_count; g++) { - PyObject* o; - - o = state_get_group(&state, (Py_ssize_t)g + 1, string, TRUE); - if (!o) { - Py_DECREF(item); - goto error; - } - - /* PyTuple_SET_ITEM borrows the reference. */ - PyTuple_SET_ITEM(item, g, o); - } - break; - } - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - - if (state.overlapped) { - /* Advance one character. */ - state.text_pos = state.match_pos + step; - state.must_advance = FALSE; - } else - /* Continue from where we left off, but don't allow 2 contiguous - * zero-width matches. - */ - state.must_advance = state.text_pos == state.match_pos; - } - - state_fini(&state); - - return list; - -error: - Py_DECREF(list); - state_fini(&state); - return NULL; -} - -/* PatternObject's 'finditer' method. */ -static PyObject* pattern_finditer(PatternObject* pattern, PyObject* args, - PyObject* kwargs) { - return pattern_scanner(pattern, args, kwargs); -} - -/* Makes a copy of a PatternObject. */ -Py_LOCAL_INLINE(PyObject*) make_pattern_copy(PatternObject* self) { - Py_INCREF(self); - return (PyObject*)self; -} - -/* PatternObject's '__copy__' method. */ -static PyObject* pattern_copy(PatternObject* self, PyObject *unused) { - return make_pattern_copy(self); -} - -/* PatternObject's '__deepcopy__' method. */ -static PyObject* pattern_deepcopy(PatternObject* self, PyObject* memo) { - return make_pattern_copy(self); -} - -/* The documentation of a PatternObject. */ -PyDoc_STRVAR(pattern_match_doc, - "match(string, pos=None, endpos=None, concurrent=None) --> MatchObject or None.\n\ - Match zero or more characters at the beginning of the string."); - -PyDoc_STRVAR(pattern_fullmatch_doc, - "fullmatch(string, pos=None, endpos=None, concurrent=None) --> MatchObject or None.\n\ - Match zero or more characters against all of the string."); - -PyDoc_STRVAR(pattern_search_doc, - "search(string, pos=None, endpos=None, concurrent=None) --> MatchObject or None.\n\ - Search through string looking for a match, and return a corresponding\n\ - match object instance. Return None if no match is found."); - -PyDoc_STRVAR(pattern_sub_doc, - "sub(repl, string, count=0, flags=0, pos=None, endpos=None, concurrent=None) --> newstring\n\ - Return the string obtained by replacing the leftmost (or rightmost with a\n\ - reverse pattern) non-overlapping occurrences of pattern in string by the\n\ - replacement repl."); - -#if PY_VERSION_HEX >= 0x02060000 -PyDoc_STRVAR(pattern_subf_doc, - "subf(format, string, count=0, flags=0, pos=None, endpos=None, concurrent=None) --> newstring\n\ - Return the string obtained by replacing the leftmost (or rightmost with a\n\ - reverse pattern) non-overlapping occurrences of pattern in string by the\n\ - replacement format."); - -#endif -PyDoc_STRVAR(pattern_subn_doc, - "subn(repl, string, count=0, flags=0, pos=None, endpos=None, concurrent=None) --> (newstring, number of subs)\n\ - Return the tuple (new_string, number_of_subs_made) found by replacing the\n\ - leftmost (or rightmost with a reverse pattern) non-overlapping occurrences\n\ - of pattern with the replacement repl."); - -#if PY_VERSION_HEX >= 0x02060000 -PyDoc_STRVAR(pattern_subfn_doc, - "subfn(format, string, count=0, flags=0, pos=None, endpos=None, concurrent=None) --> (newstring, number of subs)\n\ - Return the tuple (new_string, number_of_subs_made) found by replacing the\n\ - leftmost (or rightmost with a reverse pattern) non-overlapping occurrences\n\ - of pattern with the replacement format."); - -#endif -PyDoc_STRVAR(pattern_split_doc, - "split(string, string, maxsplit=0, concurrent=None) --> list.\n\ - Split string by the occurrences of pattern."); - -PyDoc_STRVAR(pattern_splititer_doc, - "splititer(string, maxsplit=0, concurrent=None) --> iterator.\n\ - Return an iterator yielding the parts of a split string."); - -PyDoc_STRVAR(pattern_findall_doc, - "findall(string, pos=None, endpos=None, overlapped=False, concurrent=None) --> list.\n\ - Return a list of all matches of pattern in string. The matches may be\n\ - overlapped if overlapped is True."); - -PyDoc_STRVAR(pattern_finditer_doc, - "finditer(string, pos=None, endpos=None, overlapped=False, concurrent=None) --> iterator.\n\ - Return an iterator over all matches for the RE pattern in string. The\n\ - matches may be overlapped if overlapped is True. For each match, the\n\ - iterator returns a MatchObject."); - -PyDoc_STRVAR(pattern_scanner_doc, - "scanner(string, pos=None, endpos=None, overlapped=False, concurrent=None) --> scanner.\n\ - Return an scanner for the RE pattern in string. The matches may be overlapped\n\ - if overlapped is True."); - -/* The methods of a PatternObject. */ -static PyMethodDef pattern_methods[] = { - {"match", (PyCFunction)pattern_match, METH_VARARGS|METH_KEYWORDS, - pattern_match_doc}, - {"fullmatch", (PyCFunction)pattern_fullmatch, METH_VARARGS|METH_KEYWORDS, - pattern_fullmatch_doc}, - {"search", (PyCFunction)pattern_search, METH_VARARGS|METH_KEYWORDS, - pattern_search_doc}, - {"sub", (PyCFunction)pattern_sub, METH_VARARGS|METH_KEYWORDS, - pattern_sub_doc}, -#if PY_VERSION_HEX >= 0x02060000 - {"subf", (PyCFunction)pattern_subf, METH_VARARGS|METH_KEYWORDS, - pattern_subf_doc}, -#endif - {"subn", (PyCFunction)pattern_subn, METH_VARARGS|METH_KEYWORDS, - pattern_subn_doc}, -#if PY_VERSION_HEX >= 0x02060000 - {"subfn", (PyCFunction)pattern_subfn, METH_VARARGS|METH_KEYWORDS, - pattern_subfn_doc}, -#endif - {"split", (PyCFunction)pattern_split, METH_VARARGS|METH_KEYWORDS, - pattern_split_doc}, - {"splititer", (PyCFunction)pattern_splititer, METH_VARARGS|METH_KEYWORDS, - pattern_splititer_doc}, - {"findall", (PyCFunction)pattern_findall, METH_VARARGS|METH_KEYWORDS, - pattern_findall_doc}, - {"finditer", (PyCFunction)pattern_finditer, METH_VARARGS|METH_KEYWORDS, - pattern_finditer_doc}, - {"scanner", (PyCFunction)pattern_scanner, METH_VARARGS|METH_KEYWORDS, - pattern_scanner_doc}, - {"__copy__", (PyCFunction)pattern_copy, METH_NOARGS}, - {"__deepcopy__", (PyCFunction)pattern_deepcopy, METH_O}, - {NULL, NULL} -}; - -PyDoc_STRVAR(pattern_doc, "Compiled regex object"); - -/* Deallocates a PatternObject. */ -static void pattern_dealloc(PyObject* self_) { - PatternObject* self; - int partial_side; - size_t i; - - self = (PatternObject*)self_; - - /* Discard the nodes. */ - for (i = 0; i < self->node_count; i++) { - RE_Node* node; - - node = self->node_list[i]; - re_dealloc(node->values); - if (node->status & RE_STATUS_STRING) { - re_dealloc(node->string.bad_character_offset); - re_dealloc(node->string.good_suffix_offset); - } - re_dealloc(node); - } - re_dealloc(self->node_list); - - /* Discard the group info. */ - re_dealloc(self->group_info); - - /* Discard the call_ref info. */ - re_dealloc(self->call_ref_info); - - /* Discard the repeat info. */ - re_dealloc(self->repeat_info); - - dealloc_groups(self->groups_storage, self->true_group_count); - - dealloc_repeats(self->repeats_storage, self->repeat_count); - - if (self->weakreflist) - PyObject_ClearWeakRefs((PyObject*)self); - Py_XDECREF(self->pattern); - Py_XDECREF(self->groupindex); - Py_XDECREF(self->indexgroup); - - for (partial_side = 0; partial_side < 2; partial_side++) { - if (self->partial_named_lists[partial_side]) { - for (i = 0; i < self->named_lists_count; i++) - Py_XDECREF(self->partial_named_lists[partial_side][i]); - - re_dealloc(self->partial_named_lists[partial_side]); - } - } - - Py_DECREF(self->named_lists); - Py_DECREF(self->named_list_indexes); - PyObject_DEL(self); -} - -/* Info about the various flags that can be passed in. */ -typedef struct RE_FlagName { - char* name; - int value; -} RE_FlagName; - -/* We won't bother about the A flag in Python 2. */ -static RE_FlagName flag_names[] = { - {"B", RE_FLAG_BESTMATCH}, - {"D", RE_FLAG_DEBUG}, - {"S", RE_FLAG_DOTALL}, - {"F", RE_FLAG_FULLCASE}, - {"I", RE_FLAG_IGNORECASE}, - {"L", RE_FLAG_LOCALE}, - {"M", RE_FLAG_MULTILINE}, - {"R", RE_FLAG_REVERSE}, - {"T", RE_FLAG_TEMPLATE}, - {"U", RE_FLAG_UNICODE}, - {"X", RE_FLAG_VERBOSE}, - {"V0", RE_FLAG_VERSION0}, - {"V1", RE_FLAG_VERSION1}, - {"W", RE_FLAG_WORD}, -}; - -/* Appends a string to a list. */ -Py_LOCAL_INLINE(BOOL) append_string(PyObject* list, char* string) { - PyObject* item; - int status; - - item = Py_BuildValue("s", string); - if (!item) - return FALSE; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - return FALSE; - - return TRUE; -} - -/* Appends a (decimal) integer to a list. */ -Py_LOCAL_INLINE(BOOL) append_integer(PyObject* list, Py_ssize_t value) { - PyObject* int_obj; - PyObject* repr_obj; - int status; - - int_obj = Py_BuildValue("n", value); - if (!int_obj) - return FALSE; - - repr_obj = PyObject_Repr(int_obj); - Py_DECREF(int_obj); - if (!repr_obj) - return FALSE; - - status = PyList_Append(list, repr_obj); - Py_DECREF(repr_obj); - if (status < 0) - return FALSE; - - return TRUE; -} - -/* MatchObject's '__repr__' method. */ -static PyObject* match_repr(PyObject* self_) { - MatchObject* self; - PyObject* list; - PyObject* matched_substring; - PyObject* matched_repr; - int status; - PyObject* separator; - PyObject* result; - - self = (MatchObject*)self_; - - list = PyList_New(0); - if (!list) - return NULL; - - if (!append_string(list, "match_start)) - goto error; - - if (! append_string(list, ", ")) - goto error; - - if (!append_integer(list, self->match_end)) - goto error; - - if (!append_string(list, "), match=")) - goto error; - - matched_substring = get_slice(self->substring, self->match_start - - self->substring_offset, self->match_end - self->substring_offset); - if (!matched_substring) - goto error; - - matched_repr = PyObject_Repr(matched_substring); - Py_DECREF(matched_substring); - if (!matched_repr) - goto error; - - status = PyList_Append(list, matched_repr); - Py_DECREF(matched_repr); - if (status < 0) - goto error; - - if (self->fuzzy_counts[RE_FUZZY_SUB] != 0 || - self->fuzzy_counts[RE_FUZZY_INS] != 0 || self->fuzzy_counts[RE_FUZZY_DEL] - != 0) { - if (! append_string(list, ", fuzzy_counts=(")) - goto error; - - if (!append_integer(list, - (Py_ssize_t)self->fuzzy_counts[RE_FUZZY_SUB])) - goto error; - - if (! append_string(list, ", ")) - goto error; - - if (!append_integer(list, - (Py_ssize_t)self->fuzzy_counts[RE_FUZZY_INS])) - goto error; - - if (! append_string(list, ", ")) - goto error; - if (!append_integer(list, - (Py_ssize_t)self->fuzzy_counts[RE_FUZZY_DEL])) - goto error; - - if (! append_string(list, ")")) - goto error; - } - - if (self->partial) { - if (!append_string(list, ", partial=True")) - goto error; - } - - if (! append_string(list, ">")) - goto error; - - separator = Py_BuildValue("s", ""); - if (!separator) - goto error; - - result = PyUnicode_Join(separator, list); - Py_DECREF(separator); - Py_DECREF(list); - - return result; - -error: - Py_DECREF(list); - return NULL; -} - -/* PatternObject's '__repr__' method. */ -static PyObject* pattern_repr(PyObject* self_) { - PatternObject* self; - PyObject* list; - PyObject* item; - int status; - int flag_count; - unsigned int i; - Py_ssize_t pos; - PyObject *key; - PyObject *value; - PyObject* separator; - PyObject* result; - - self = (PatternObject*)self_; - - list = PyList_New(0); - if (!list) - return NULL; - - if (!append_string(list, "regex.Regex(")) - goto error; - - item = PyObject_Repr(self->pattern); - if (!item) - goto error; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - - flag_count = 0; - for (i = 0; i < sizeof(flag_names) / sizeof(flag_names[0]); i++) { - if (self->flags & flag_names[i].value) { - if (flag_count == 0) { - if (!append_string(list, ", flags=")) - goto error; - } else { - if (!append_string(list, " | ")) - goto error; - } - - if (!append_string(list, "regex.")) - goto error; - - if (!append_string(list, flag_names[i].name)) - goto error; - - ++flag_count; - } - } - - pos = 0; - /* PyDict_Next borrows references. */ - while (PyDict_Next(self->named_lists, &pos, &key, &value)) { - if (!append_string(list, ", ")) - goto error; - - status = PyList_Append(list, key); - if (status < 0) - goto error; - - if (!append_string(list, "=")) - goto error; - - item = PyObject_Repr(value); - if (!item) - goto error; - - status = PyList_Append(list, item); - Py_DECREF(item); - if (status < 0) - goto error; - } - - if (!append_string(list, ")")) - goto error; - - separator = Py_BuildValue("s", ""); - if (!separator) - goto error; - - result = PyUnicode_Join(separator, list); - Py_DECREF(separator); - Py_DECREF(list); - - return result; - -error: - Py_DECREF(list); - return NULL; -} - -/* PatternObject's 'groupindex' method. */ -static PyObject* pattern_groupindex(PyObject* self_) { - PatternObject* self; - - self = (PatternObject*)self_; - - return PyDict_Copy(self->groupindex); -} - -static PyGetSetDef pattern_getset[] = { - {"groupindex", (getter)pattern_groupindex, (setter)NULL, - "A dictionary mapping group names to group numbers."}, - {NULL} /* Sentinel */ -}; - -static PyMemberDef pattern_members[] = { - {"pattern", T_OBJECT, offsetof(PatternObject, pattern), READONLY, - "The pattern string from which the regex object was compiled."}, - {"flags", T_PYSSIZET, offsetof(PatternObject, flags), READONLY, - "The regex matching flags."}, - {"groups", T_PYSSIZET, offsetof(PatternObject, public_group_count), - READONLY, "The number of capturing groups in the pattern."}, - {"named_lists", T_OBJECT, offsetof(PatternObject, named_lists), READONLY, - "The named lists used by the regex."}, - {NULL} /* Sentinel */ -}; - -static PyTypeObject Pattern_Type = { - PyObject_HEAD_INIT(NULL) - 0, - "_" RE_MODULE "." "Pattern", - sizeof(PatternObject) -}; - -/* Building the nodes is made simpler by allowing branches to have a single - * exit. These need to be removed. - */ -Py_LOCAL_INLINE(void) skip_one_way_branches(PatternObject* pattern) { - BOOL modified; - - /* If a node refers to a 1-way branch then make the former refer to the - * latter's destination. Repeat until they're all done. - */ - do { - size_t i; - - modified = FALSE; - - for (i = 0; i < pattern->node_count; i++) { - RE_Node* node; - RE_Node* next; - - node = pattern->node_list[i]; - - /* Check the first destination. */ - next = node->next_1.node; - if (next && next->op == RE_OP_BRANCH && - !next->nonstring.next_2.node) { - node->next_1.node = next->next_1.node; - modified = TRUE; - } - - /* Check the second destination. */ - next = node->nonstring.next_2.node; - if (next && next->op == RE_OP_BRANCH && - !next->nonstring.next_2.node) { - node->nonstring.next_2.node = next->next_1.node; - modified = TRUE; - } - } - } while (modified); - - /* The start node might be a 1-way branch. Skip over it because it'll be - * removed. It might even be the first in a chain. - */ - while (pattern->start_node->op == RE_OP_BRANCH && - !pattern->start_node->nonstring.next_2.node) - pattern->start_node = pattern->start_node->next_1.node; -} - -/* Adds guards to repeats which are followed by a reference to a group. - * - * Returns whether a guard was added for a node at or after the given node. - */ -Py_LOCAL_INLINE(RE_STATUS_T) add_repeat_guards(PatternObject* pattern, RE_Node* - node) { - RE_STATUS_T result; - - result = RE_STATUS_NEITHER; - - for (;;) { - if (node->status & RE_STATUS_VISITED_AG) - return node->status & (RE_STATUS_REPEAT | RE_STATUS_REF); - - switch (node->op) { - case RE_OP_ATOMIC: - case RE_OP_LOOKAROUND: - { - RE_STATUS_T body_result; - RE_STATUS_T tail_result; - RE_STATUS_T status; - - body_result = add_repeat_guards(pattern, - node->nonstring.next_2.node); - tail_result = add_repeat_guards(pattern, node->next_1.node); - status = max_status_3(result, body_result, tail_result); - node->status = RE_STATUS_VISITED_AG | status; - return status; - } - case RE_OP_BRANCH: - { - RE_STATUS_T branch_1_result; - RE_STATUS_T branch_2_result; - RE_STATUS_T status; - - branch_1_result = add_repeat_guards(pattern, node->next_1.node); - branch_2_result = add_repeat_guards(pattern, - node->nonstring.next_2.node); - status = max_status_3(result, branch_1_result, branch_2_result); - node->status = RE_STATUS_VISITED_AG | status; - return status; - } - case RE_OP_END_GREEDY_REPEAT: - case RE_OP_END_LAZY_REPEAT: - node->status |= RE_STATUS_VISITED_AG; - return result; - case RE_OP_GREEDY_REPEAT: - case RE_OP_LAZY_REPEAT: - { - BOOL limited; - RE_STATUS_T body_result; - RE_STATUS_T tail_result; - RE_RepeatInfo* repeat_info; - RE_STATUS_T status; - - limited = ~node->values[2] != 0; - if (limited) - body_result = RE_STATUS_LIMITED; - else - body_result = add_repeat_guards(pattern, node->next_1.node); - tail_result = add_repeat_guards(pattern, - node->nonstring.next_2.node); - - repeat_info = &pattern->repeat_info[node->values[0]]; - if (body_result != RE_STATUS_REF) - repeat_info->status |= RE_STATUS_BODY; - if (tail_result != RE_STATUS_REF) - repeat_info->status |= RE_STATUS_TAIL; - if (limited) - result = max_status_2(result, RE_STATUS_LIMITED); - else - result = max_status_2(result, RE_STATUS_REPEAT); - status = max_status_3(result, body_result, tail_result); - node->status |= RE_STATUS_VISITED_AG | status; - return status; - } - case RE_OP_GREEDY_REPEAT_ONE: - case RE_OP_LAZY_REPEAT_ONE: - { - BOOL limited; - RE_STATUS_T tail_result; - RE_RepeatInfo* repeat_info; - RE_STATUS_T status; - - limited = ~node->values[2] != 0; - tail_result = add_repeat_guards(pattern, node->next_1.node); - - repeat_info = &pattern->repeat_info[node->values[0]]; - repeat_info->status |= RE_STATUS_BODY; - if (tail_result != RE_STATUS_REF) - repeat_info->status |= RE_STATUS_TAIL; - if (limited) - result = max_status_2(result, RE_STATUS_LIMITED); - else - result = max_status_2(result, RE_STATUS_REPEAT); - status = max_status_3(result, RE_STATUS_REPEAT, tail_result); - node->status = RE_STATUS_VISITED_AG | status; - return status; - } - case RE_OP_GROUP_EXISTS: - { - RE_STATUS_T branch_1_result; - RE_STATUS_T branch_2_result; - RE_STATUS_T status; - - branch_1_result = add_repeat_guards(pattern, node->next_1.node); - branch_2_result = add_repeat_guards(pattern, - node->nonstring.next_2.node); - status = max_status_4(result, branch_1_result, branch_2_result, - RE_STATUS_REF); - node->status = RE_STATUS_VISITED_AG | status; - return status; - } - case RE_OP_GROUP_CALL: - case RE_OP_REF_GROUP: - case RE_OP_REF_GROUP_FLD: - case RE_OP_REF_GROUP_FLD_REV: - case RE_OP_REF_GROUP_IGN: - case RE_OP_REF_GROUP_IGN_REV: - case RE_OP_REF_GROUP_REV: - result = RE_STATUS_REF; - node = node->next_1.node; - break; - case RE_OP_SUCCESS: - node->status = RE_STATUS_VISITED_AG | result; - return result; - default: - node = node->next_1.node; - break; - } - } -} - -/* Adds an index to a node's values unless it's already present. - * - * 'offset' is the offset of the index count within the values. - */ -Py_LOCAL_INLINE(BOOL) add_index(RE_Node* node, size_t offset, size_t index) { - size_t index_count; - size_t first_index; - size_t i; - RE_CODE* new_values; - - if (!node) - return TRUE; - - index_count = node->values[offset]; - first_index = offset + 1; - - /* Is the index already present? */ - for (i = 0; i < index_count; i++) { - if (node->values[first_index + i] == index) - return TRUE; - } - - /* Allocate more space for the new index. */ - new_values = re_realloc(node->values, (node->value_count + 1) * - sizeof(RE_CODE)); - if (!new_values) - return FALSE; - - ++node->value_count; - node->values = new_values; - - node->values[first_index + node->values[offset]++] = (RE_CODE)index; - - return TRUE; -} - -/* Records the index of every repeat and fuzzy section within atomic - * subpatterns and lookarounds. - */ -Py_LOCAL_INLINE(BOOL) record_subpattern_repeats_and_fuzzy_sections(RE_Node* - parent_node, size_t offset, size_t repeat_count, RE_Node* node) { - while (node) { - if (node->status & RE_STATUS_VISITED_REP) - return TRUE; - - node->status |= RE_STATUS_VISITED_REP; - - switch (node->op) { - case RE_OP_ATOMIC: - if (!record_subpattern_repeats_and_fuzzy_sections(node, 0, - repeat_count, node->nonstring.next_2.node)) - return FALSE; - node = node->next_1.node; - break; - case RE_OP_BRANCH: - if (!record_subpattern_repeats_and_fuzzy_sections(parent_node, - offset, repeat_count, node->next_1.node)) - return FALSE; - node = node->nonstring.next_2.node; - break; - case RE_OP_END_FUZZY: - node = node->next_1.node; - break; - case RE_OP_END_GREEDY_REPEAT: - case RE_OP_END_LAZY_REPEAT: - return TRUE; - case RE_OP_FUZZY: - /* Record the fuzzy index. */ - if (!add_index(parent_node, offset, repeat_count + - node->values[0])) - return FALSE; - node = node->next_1.node; - break; - case RE_OP_GREEDY_REPEAT: - case RE_OP_LAZY_REPEAT: - /* Record the repeat index. */ - if (!add_index(parent_node, offset, node->values[0])) - return FALSE; - if (!record_subpattern_repeats_and_fuzzy_sections(parent_node, - offset, repeat_count, node->next_1.node)) - return FALSE; - node = node->nonstring.next_2.node; - break; - case RE_OP_GREEDY_REPEAT_ONE: - case RE_OP_LAZY_REPEAT_ONE: - /* Record the repeat index. */ - if (!add_index(parent_node, offset, node->values[0])) - return FALSE; - node = node->next_1.node; - break; - case RE_OP_GROUP_EXISTS: - if (!record_subpattern_repeats_and_fuzzy_sections(parent_node, - offset, repeat_count, node->next_1.node)) - return FALSE; - node = node->nonstring.next_2.node; - break; - case RE_OP_LOOKAROUND: - if (!record_subpattern_repeats_and_fuzzy_sections(node, 1, - repeat_count, node->nonstring.next_2.node)) - return FALSE; - node = node->next_1.node; - break; - default: - node = node->next_1.node; - break; - } - } - - return TRUE; -} - -/* Marks nodes which are being used as used. */ -Py_LOCAL_INLINE(void) use_nodes(RE_Node* node) { - while (node && !(node->status & RE_STATUS_USED)) { - node->status |= RE_STATUS_USED; - if (!(node->status & RE_STATUS_STRING)) { - if (node->nonstring.next_2.node) - use_nodes(node->nonstring.next_2.node); - } - node = node->next_1.node; - } -} - -/* Discards any unused nodes. - * - * Optimising the nodes might result in some nodes no longer being used. - */ -Py_LOCAL_INLINE(void) discard_unused_nodes(PatternObject* pattern) { - size_t new_count; - size_t i; - - /* Mark the nodes which are being used. */ - use_nodes(pattern->start_node); - - for (i = 0; i < pattern->call_ref_info_capacity; i++) - use_nodes(pattern->call_ref_info[i].node); - - new_count = 0; - for (i = 0; i < pattern->node_count; i++) { - RE_Node* node; - - node = pattern->node_list[i]; - if (node->status & RE_STATUS_USED) - pattern->node_list[new_count++] = node; - else { - re_dealloc(node->values); - if (node->status & RE_STATUS_STRING) { - re_dealloc(node->string.bad_character_offset); - re_dealloc(node->string.good_suffix_offset); - } - re_dealloc(node); - } - } - - pattern->node_count = new_count; -} - -/* Marks all the group which are named. Returns FALSE if there's an error. */ -Py_LOCAL_INLINE(BOOL) mark_named_groups(PatternObject* pattern) { - size_t i; - - for (i = 0; i < pattern->public_group_count; i++) { - RE_GroupInfo* group_info; - PyObject* index; - int status; - - group_info = &pattern->group_info[i]; - index = Py_BuildValue("n", i + 1); - if (!index) - return FALSE; - - status = PyDict_Contains(pattern->indexgroup, index); - Py_DECREF(index); - if (status < 0) - return FALSE; - - group_info->has_name = status == 1; - } - - return TRUE; -} - -/* Gets the test node. - * - * The test node lets the matcher look ahead in the pattern, allowing it to - * avoid the cost of housekeeping, only to find that what follows doesn't match - * anyway. - */ -Py_LOCAL_INLINE(void) set_test_node(RE_NextNode* next) { - RE_Node* node = next->node; - RE_Node* test; - - next->test = node; - next->match_next = node; - next->match_step = 0; - - if (!node) - return; - - test = node; - while (test->op == RE_OP_END_GROUP || test->op == RE_OP_START_GROUP) - test = test->next_1.node; - - next->test = test; - - if (test != node) - return; - - switch (test->op) { - case RE_OP_ANY: - case RE_OP_ANY_ALL: - case RE_OP_ANY_ALL_REV: - case RE_OP_ANY_REV: - case RE_OP_ANY_U: - case RE_OP_ANY_U_REV: - case RE_OP_BOUNDARY: - case RE_OP_CHARACTER: - case RE_OP_CHARACTER_IGN: - case RE_OP_CHARACTER_IGN_REV: - case RE_OP_CHARACTER_REV: - case RE_OP_DEFAULT_BOUNDARY: - case RE_OP_DEFAULT_END_OF_WORD: - case RE_OP_DEFAULT_START_OF_WORD: - case RE_OP_END_OF_LINE: - case RE_OP_END_OF_LINE_U: - case RE_OP_END_OF_STRING: - case RE_OP_END_OF_STRING_LINE: - case RE_OP_END_OF_STRING_LINE_U: - case RE_OP_END_OF_WORD: - case RE_OP_GRAPHEME_BOUNDARY: - case RE_OP_PROPERTY: - case RE_OP_PROPERTY_IGN: - case RE_OP_PROPERTY_IGN_REV: - case RE_OP_PROPERTY_REV: - case RE_OP_RANGE: - case RE_OP_RANGE_IGN: - case RE_OP_RANGE_IGN_REV: - case RE_OP_RANGE_REV: - case RE_OP_SEARCH_ANCHOR: - case RE_OP_SET_DIFF: - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION: - case RE_OP_SET_UNION_IGN: - case RE_OP_SET_UNION_IGN_REV: - case RE_OP_SET_UNION_REV: - case RE_OP_START_OF_LINE: - case RE_OP_START_OF_LINE_U: - case RE_OP_START_OF_STRING: - case RE_OP_START_OF_WORD: - case RE_OP_STRING: - case RE_OP_STRING_FLD: - case RE_OP_STRING_FLD_REV: - case RE_OP_STRING_IGN: - case RE_OP_STRING_IGN_REV: - case RE_OP_STRING_REV: - next->match_next = test->next_1.node; - next->match_step = test->step; - break; - case RE_OP_GREEDY_REPEAT_ONE: - case RE_OP_LAZY_REPEAT_ONE: - if (test->values[1] > 0) - next->test = test; - break; - } -} - -/* Sets the test nodes. */ -Py_LOCAL_INLINE(void) set_test_nodes(PatternObject* pattern) { - RE_Node** node_list; - size_t i; - - node_list = pattern->node_list; - for (i = 0; i < pattern->node_count; i++) { - RE_Node* node; - - node = node_list[i]; - set_test_node(&node->next_1); - if (!(node->status & RE_STATUS_STRING)) - set_test_node(&node->nonstring.next_2); - } -} - -/* Optimises the pattern. */ -Py_LOCAL_INLINE(BOOL) optimise_pattern(PatternObject* pattern) { - size_t i; - - /* Building the nodes is made simpler by allowing branches to have a single - * exit. These need to be removed. - */ - skip_one_way_branches(pattern); - - /* Add position guards for repeat bodies containing a reference to a group - * or repeat tails followed at some point by a reference to a group. - */ - add_repeat_guards(pattern, pattern->start_node); - - /* Record the index of repeats and fuzzy sections within the body of atomic - * and lookaround nodes. - */ - if (!record_subpattern_repeats_and_fuzzy_sections(NULL, 0, - pattern->repeat_count, pattern->start_node)) - return FALSE; - - for (i = 0; i < pattern->call_ref_info_count; i++) { - RE_Node* node; - - node = pattern->call_ref_info[i].node; - if (!record_subpattern_repeats_and_fuzzy_sections(NULL, 0, - pattern->repeat_count, node)) - return FALSE; - } - - /* Discard any unused nodes. */ - discard_unused_nodes(pattern); - - /* Set the test nodes. */ - set_test_nodes(pattern); - - /* Mark all the group that are named. */ - if (!mark_named_groups(pattern)) - return FALSE; - - return TRUE; -} - -/* Creates a new pattern node. */ -Py_LOCAL_INLINE(RE_Node*) create_node(PatternObject* pattern, RE_UINT8 op, - RE_CODE flags, Py_ssize_t step, size_t value_count) { - RE_Node* node; - - node = (RE_Node*)re_alloc(sizeof(*node)); - if (!node) - return NULL; - memset(node, 0, sizeof(RE_Node)); - - node->value_count = value_count; - if (node->value_count > 0) { - node->values = (RE_CODE*)re_alloc(node->value_count * sizeof(RE_CODE)); - if (!node->values) - goto error; - } else - node->values = NULL; - - node->op = op; - node->match = (flags & RE_POSITIVE_OP) != 0; - node->status = (RE_STATUS_T)(flags << RE_STATUS_SHIFT); - node->step = step; - - /* Ensure that there's enough storage to record the new node. */ - if (pattern->node_count >= pattern->node_capacity) { - RE_Node** new_node_list; - - pattern->node_capacity *= 2; - if (pattern->node_capacity == 0) - pattern->node_capacity = RE_INIT_NODE_LIST_SIZE; - new_node_list = (RE_Node**)re_realloc(pattern->node_list, - pattern->node_capacity * sizeof(RE_Node*)); - if (!new_node_list) - goto error; - pattern->node_list = new_node_list; - } - - /* Record the new node. */ - pattern->node_list[pattern->node_count++] = node; - - return node; - -error: - re_dealloc(node->values); - re_dealloc(node); - return NULL; -} - -/* Adds a node as a next node for another node. */ -Py_LOCAL_INLINE(void) add_node(RE_Node* node_1, RE_Node* node_2) { - if (!node_1->next_1.node) - node_1->next_1.node = node_2; - else - node_1->nonstring.next_2.node = node_2; -} - -/* Ensures that the entry for a group's details actually exists. */ -Py_LOCAL_INLINE(BOOL) ensure_group(PatternObject* pattern, size_t group) { - size_t old_capacity; - size_t new_capacity; - RE_GroupInfo* new_group_info; - - if (group <= pattern->true_group_count) - /* We already have an entry for the group. */ - return TRUE; - - /* Increase the storage capacity to include the new entry if it's - * insufficient. - */ - old_capacity = pattern->group_info_capacity; - new_capacity = pattern->group_info_capacity; - while (group > new_capacity) - new_capacity += RE_LIST_SIZE_INC; - - if (new_capacity > old_capacity) { - new_group_info = (RE_GroupInfo*)re_realloc(pattern->group_info, - new_capacity * sizeof(RE_GroupInfo)); - if (!new_group_info) - return FALSE; - memset(new_group_info + old_capacity, 0, (new_capacity - old_capacity) - * sizeof(RE_GroupInfo)); - - pattern->group_info = new_group_info; - pattern->group_info_capacity = new_capacity; - } - - pattern->true_group_count = group; - - return TRUE; -} - -/* Records that there's a reference to a group. */ -Py_LOCAL_INLINE(BOOL) record_ref_group(PatternObject* pattern, size_t group) { - if (!ensure_group(pattern, group)) - return FALSE; - - pattern->group_info[group - 1].referenced = TRUE; - - return TRUE; -} - -/* Records that there's a new group. */ -Py_LOCAL_INLINE(BOOL) record_group(PatternObject* pattern, size_t group, - RE_Node* node) { - if (!ensure_group(pattern, group)) - return FALSE; - - if (group >= 1) { - RE_GroupInfo* info; - - info = &pattern->group_info[group - 1]; - info->end_index = (Py_ssize_t)pattern->true_group_count; - info->node = node; - } - - return TRUE; -} - -/* Records that a group has closed. */ -Py_LOCAL_INLINE(void) record_group_end(PatternObject* pattern, size_t group) { - if (group >= 1) - pattern->group_info[group - 1].end_index = ++pattern->group_end_index; -} - -/* Ensures that the entry for a call_ref's details actually exists. */ -Py_LOCAL_INLINE(BOOL) ensure_call_ref(PatternObject* pattern, size_t call_ref) - { - size_t old_capacity; - size_t new_capacity; - RE_CallRefInfo* new_call_ref_info; - - if (call_ref < pattern->call_ref_info_count) - /* We already have an entry for the call_ref. */ - return TRUE; - - /* Increase the storage capacity to include the new entry if it's - * insufficient. - */ - old_capacity = pattern->call_ref_info_capacity; - new_capacity = pattern->call_ref_info_capacity; - while (call_ref >= new_capacity) - new_capacity += RE_LIST_SIZE_INC; - - if (new_capacity > old_capacity) { - new_call_ref_info = (RE_CallRefInfo*)re_realloc(pattern->call_ref_info, - new_capacity * sizeof(RE_CallRefInfo)); - if (!new_call_ref_info) - return FALSE; - memset(new_call_ref_info + old_capacity, 0, (new_capacity - - old_capacity) * sizeof(RE_CallRefInfo)); - - pattern->call_ref_info = new_call_ref_info; - pattern->call_ref_info_capacity = new_capacity; - } - - pattern->call_ref_info_count = 1 + call_ref; - - return TRUE; -} - -/* Records that a call_ref is defined. */ -Py_LOCAL_INLINE(BOOL) record_call_ref_defined(PatternObject* pattern, size_t - call_ref, RE_Node* node) { - if (!ensure_call_ref(pattern, call_ref)) - return FALSE; - - pattern->call_ref_info[call_ref].defined = TRUE; - pattern->call_ref_info[call_ref].node = node; - - return TRUE; -} - -/* Records that a call_ref is used. */ -Py_LOCAL_INLINE(BOOL) record_call_ref_used(PatternObject* pattern, size_t - call_ref) { - if (!ensure_call_ref(pattern, call_ref)) - return FALSE; - - pattern->call_ref_info[call_ref].used = TRUE; - - return TRUE; -} - -/* Checks whether a node matches one and only one character. */ -Py_LOCAL_INLINE(BOOL) sequence_matches_one(RE_Node* node) { - while (node->op == RE_OP_BRANCH && !node->nonstring.next_2.node) - node = node->next_1.node; - - if (node->next_1.node || (node->status & RE_STATUS_FUZZY)) - return FALSE; - - return node_matches_one_character(node); -} - -/* Records a repeat. */ -Py_LOCAL_INLINE(BOOL) record_repeat(PatternObject* pattern, size_t index, - size_t repeat_depth) { - size_t old_capacity; - size_t new_capacity; - - /* Increase the storage capacity to include the new entry if it's - * insufficient. - */ - old_capacity = pattern->repeat_info_capacity; - new_capacity = pattern->repeat_info_capacity; - while (index >= new_capacity) - new_capacity += RE_LIST_SIZE_INC; - - if (new_capacity > old_capacity) { - RE_RepeatInfo* new_repeat_info; - - new_repeat_info = (RE_RepeatInfo*)re_realloc(pattern->repeat_info, - new_capacity * sizeof(RE_RepeatInfo)); - if (!new_repeat_info) - return FALSE; - memset(new_repeat_info + old_capacity, 0, (new_capacity - old_capacity) - * sizeof(RE_RepeatInfo)); - - pattern->repeat_info = new_repeat_info; - pattern->repeat_info_capacity = new_capacity; - } - - if (index >= pattern->repeat_count) - pattern->repeat_count = index + 1; - - if (repeat_depth > 0) - pattern->repeat_info[index].status |= RE_STATUS_INNER; - - return TRUE; -} - -Py_LOCAL_INLINE(Py_ssize_t) get_step(RE_CODE op) { - switch (op) { - case RE_OP_ANY: - case RE_OP_ANY_ALL: - case RE_OP_ANY_U: - case RE_OP_CHARACTER: - case RE_OP_CHARACTER_IGN: - case RE_OP_PROPERTY: - case RE_OP_PROPERTY_IGN: - case RE_OP_RANGE: - case RE_OP_RANGE_IGN: - case RE_OP_SET_DIFF: - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_INTER: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_UNION: - case RE_OP_SET_UNION_IGN: - case RE_OP_STRING: - case RE_OP_STRING_FLD: - case RE_OP_STRING_IGN: - return 1; - case RE_OP_ANY_ALL_REV: - case RE_OP_ANY_REV: - case RE_OP_ANY_U_REV: - case RE_OP_CHARACTER_IGN_REV: - case RE_OP_CHARACTER_REV: - case RE_OP_PROPERTY_IGN_REV: - case RE_OP_PROPERTY_REV: - case RE_OP_RANGE_IGN_REV: - case RE_OP_RANGE_REV: - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION_IGN_REV: - case RE_OP_SET_UNION_REV: - case RE_OP_STRING_FLD_REV: - case RE_OP_STRING_IGN_REV: - case RE_OP_STRING_REV: - return -1; - } - - return 0; -} - -Py_LOCAL_INLINE(int) build_sequence(RE_CompileArgs* args); - -/* Builds an ANY node. */ -Py_LOCAL_INLINE(int) build_ANY(RE_CompileArgs* args) { - RE_UINT8 op; - RE_CODE flags; - Py_ssize_t step; - RE_Node* node; - - /* codes: opcode, flags. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - op = (RE_UINT8)args->code[0]; - flags = args->code[1]; - - step = get_step(op); - - /* Create the node. */ - node = create_node(args->pattern, op, flags, step, 0); - if (!node) - return RE_ERROR_MEMORY; - - args->code += 2; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - ++args->min_width; - - return RE_ERROR_SUCCESS; -} - -/* Builds a FUZZY node. */ -Py_LOCAL_INLINE(int) build_FUZZY(RE_CompileArgs* args) { - RE_CODE flags; - RE_Node* start_node; - RE_Node* end_node; - RE_CODE index; - RE_CompileArgs subargs; - int status; - - /* codes: opcode, flags, constraints, sequence, end. */ - if (args->code + 13 > args->end_code) - return RE_ERROR_ILLEGAL; - - flags = args->code[1]; - - /* Create nodes for the start and end of the fuzzy sequence. */ - start_node = create_node(args->pattern, RE_OP_FUZZY, flags, 0, 9); - end_node = create_node(args->pattern, RE_OP_END_FUZZY, flags, 0, 5); - if (!start_node || !end_node) - return RE_ERROR_MEMORY; - - index = (RE_CODE)args->pattern->fuzzy_count++; - start_node->values[0] = index; - end_node->values[0] = index; - - /* The constraints consist of 4 pairs of limits and the cost equation. */ - end_node->values[RE_FUZZY_VAL_MIN_DEL] = args->code[2]; /* Deletion minimum. */ - end_node->values[RE_FUZZY_VAL_MIN_INS] = args->code[4]; /* Insertion minimum. */ - end_node->values[RE_FUZZY_VAL_MIN_SUB] = args->code[6]; /* Substitution minimum. */ - end_node->values[RE_FUZZY_VAL_MIN_ERR] = args->code[8]; /* Error minimum. */ - - start_node->values[RE_FUZZY_VAL_MAX_DEL] = args->code[3]; /* Deletion maximum. */ - start_node->values[RE_FUZZY_VAL_MAX_INS] = args->code[5]; /* Insertion maximum. */ - start_node->values[RE_FUZZY_VAL_MAX_SUB] = args->code[7]; /* Substitution maximum. */ - start_node->values[RE_FUZZY_VAL_MAX_ERR] = args->code[9]; /* Error maximum. */ - - start_node->values[RE_FUZZY_VAL_DEL_COST] = args->code[10]; /* Deletion cost. */ - start_node->values[RE_FUZZY_VAL_INS_COST] = args->code[11]; /* Insertion cost. */ - start_node->values[RE_FUZZY_VAL_SUB_COST] = args->code[12]; /* Substitution cost. */ - start_node->values[RE_FUZZY_VAL_MAX_COST] = args->code[13]; /* Total cost. */ - - args->code += 14; - - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = TRUE; - subargs.within_fuzzy = TRUE; - - /* Compile the sequence and check that we've reached the end of the - * subpattern. - */ - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->min_width = subargs.min_width; - args->has_captures |= subargs.has_captures; - - ++args->code; - - /* Append the fuzzy sequence. */ - add_node(args->end, start_node); - add_node(start_node, subargs.start); - add_node(subargs.end, end_node); - args->end = end_node; - - args->is_fuzzy = TRUE; - - return RE_ERROR_SUCCESS; -} - -/* Builds an ATOMIC node. */ -Py_LOCAL_INLINE(int) build_ATOMIC(RE_CompileArgs* args) { - RE_Node* atomic_node; - RE_CompileArgs subargs; - RE_Node* success_node; - int status; - - /* codes: opcode, sequence, end. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - atomic_node = create_node(args->pattern, RE_OP_ATOMIC, 0, 0, 1); - if (!atomic_node) - return RE_ERROR_MEMORY; - - /* The number of repeat indexes. */ - atomic_node->values[0] = 0; - - ++args->code; - - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - - /* Compile the sequence and check that we've reached the end of the - * subpattern. - */ - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - /* Create the success node to terminate the subpattern. */ - success_node = create_node(subargs.pattern, RE_OP_SUCCESS, 0, 0, 0); - if (!success_node) - return RE_ERROR_MEMORY; - - /* Append the SUCCESS node. */ - add_node(subargs.end, success_node); - - /* Insert the subpattern. */ - atomic_node->nonstring.next_2.node = subargs.start; - - args->code = subargs.code; - args->min_width = subargs.min_width; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - /* Append the node. */ - add_node(args->end, atomic_node); - args->end = atomic_node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a BOUNDARY node. */ -Py_LOCAL_INLINE(int) build_BOUNDARY(RE_CompileArgs* args) { - RE_UINT8 op; - RE_CODE flags; - RE_Node* node; - - /* codes: opcode, flags. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - op = (RE_UINT8)args->code[0]; - flags = args->code[1]; - - args->code += 2; - - /* Create the node. */ - node = create_node(args->pattern, op, flags, 0, 0); - if (!node) - return RE_ERROR_MEMORY; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a BRANCH node. */ -Py_LOCAL_INLINE(int) build_BRANCH(RE_CompileArgs* args) { - RE_Node* branch_node; - RE_Node* join_node; - Py_ssize_t smallest_min_width; - RE_CompileArgs subargs; - int status; - - /* codes: opcode, branch, next, branch, end. */ - if (args->code + 2 > args->end_code) - return RE_ERROR_ILLEGAL; - - /* Create nodes for the start and end of the branch sequence. */ - branch_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - join_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - if (!branch_node || !join_node) - return RE_ERROR_MEMORY; - - /* Append the node. */ - add_node(args->end, branch_node); - args->end = join_node; - - smallest_min_width = PY_SSIZE_T_MAX; - - subargs = *args; - - /* A branch in the regular expression is compiled into a series of 2-way - * branches. - */ - do { - RE_Node* next_branch_node; - - /* Skip over the 'BRANCH' or 'NEXT' opcode. */ - ++subargs.code; - - /* Compile the sequence until the next 'BRANCH' or 'NEXT' opcode. */ - subargs.min_width = 0; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - smallest_min_width = min_ssize_t(smallest_min_width, - subargs.min_width); - - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - /* Append the sequence. */ - add_node(branch_node, subargs.start); - add_node(subargs.end, join_node); - - /* Create a start node for the next sequence and append it. */ - next_branch_node = create_node(subargs.pattern, RE_OP_BRANCH, 0, 0, 0); - if (!next_branch_node) - return RE_ERROR_MEMORY; - - add_node(branch_node, next_branch_node); - branch_node = next_branch_node; - } while (subargs.code < subargs.end_code && subargs.code[0] == RE_OP_NEXT); - - /* We should have reached the end of the branch. */ - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - - ++args->code; - args->min_width += smallest_min_width; - - return RE_ERROR_SUCCESS; -} - -/* Builds a CALL_REF node. */ -Py_LOCAL_INLINE(int) build_CALL_REF(RE_CompileArgs* args) { - RE_CODE call_ref; - RE_Node* start_node; - RE_Node* end_node; - RE_CompileArgs subargs; - int status; - - /* codes: opcode, call_ref. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - call_ref = args->code[1]; - - args->code += 2; - - /* Create nodes for the start and end of the subpattern. */ - start_node = create_node(args->pattern, RE_OP_CALL_REF, 0, 0, 1); - end_node = create_node(args->pattern, RE_OP_GROUP_RETURN, 0, 0, 0); - if (!start_node || !end_node) - return RE_ERROR_MEMORY; - - start_node->values[0] = call_ref; - - /* Compile the sequence and check that we've reached the end of the - * subpattern. - */ - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->min_width = subargs.min_width; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - /* Record that we defined a call_ref. */ - if (!record_call_ref_defined(args->pattern, call_ref, start_node)) - return RE_ERROR_MEMORY; - - /* Append the node. */ - add_node(args->end, start_node); - add_node(start_node, subargs.start); - add_node(subargs.end, end_node); - args->end = end_node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a CHARACTER or PROPERTY node. */ -Py_LOCAL_INLINE(int) build_CHARACTER_or_PROPERTY(RE_CompileArgs* args) { - RE_UINT8 op; - RE_CODE flags; - Py_ssize_t step; - RE_Node* node; - - /* codes: opcode, flags, value. */ - if (args->code + 2 > args->end_code) - return RE_ERROR_ILLEGAL; - - op = (RE_UINT8)args->code[0]; - flags = args->code[1]; - - step = get_step(op); - - if (flags & RE_ZEROWIDTH_OP) - step = 0; - - /* Create the node. */ - node = create_node(args->pattern, op, flags, step, 1); - if (!node) - return RE_ERROR_MEMORY; - - node->values[0] = args->code[2]; - - args->code += 3; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - if (step != 0) - ++args->min_width; - - return RE_ERROR_SUCCESS; -} - -/* Builds a GROUP node. */ -Py_LOCAL_INLINE(int) build_GROUP(RE_CompileArgs* args) { - RE_CODE private_group; - RE_CODE public_group; - RE_Node* start_node; - RE_Node* end_node; - RE_CompileArgs subargs; - int status; - - /* codes: opcode, private_group, public_group. */ - if (args->code + 2 > args->end_code) - return RE_ERROR_ILLEGAL; - - private_group = args->code[1]; - public_group = args->code[2]; - - args->code += 3; - - /* Create nodes for the start and end of the capture group. */ - start_node = create_node(args->pattern, args->forward ? RE_OP_START_GROUP : - RE_OP_END_GROUP, 0, 0, 3); - end_node = create_node(args->pattern, args->forward ? RE_OP_END_GROUP : - RE_OP_START_GROUP, 0, 0, 3); - if (!start_node || !end_node) - return RE_ERROR_MEMORY; - - start_node->values[0] = private_group; - end_node->values[0] = private_group; - start_node->values[1] = public_group; - end_node->values[1] = public_group; - - /* Signal that the capture should be saved when it's complete. */ - start_node->values[2] = 0; - end_node->values[2] = 1; - - /* Record that we have a new capture group. */ - if (!record_group(args->pattern, private_group, start_node)) - return RE_ERROR_MEMORY; - - /* Compile the sequence and check that we've reached the end of the capture - * group. - */ - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->min_width = subargs.min_width; - if (subargs.has_captures || subargs.visible_captures) - args->has_captures = TRUE; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - /* Record that the capture group has closed. */ - record_group_end(args->pattern, private_group); - - /* Append the capture group. */ - add_node(args->end, start_node); - add_node(start_node, subargs.start); - add_node(subargs.end, end_node); - args->end = end_node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a GROUP_CALL node. */ -Py_LOCAL_INLINE(int) build_GROUP_CALL(RE_CompileArgs* args) { - RE_CODE call_ref; - RE_Node* node; - - /* codes: opcode, call_ref. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - call_ref = args->code[1]; - - /* Create the node. */ - node = create_node(args->pattern, RE_OP_GROUP_CALL, 0, 0, 1); - if (!node) - return RE_ERROR_MEMORY; - - node->values[0] = call_ref; - - args->code += 2; - - /* Record that we used a call_ref. */ - if (!record_call_ref_used(args->pattern, call_ref)) - return RE_ERROR_MEMORY; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a GROUP_EXISTS node. */ -Py_LOCAL_INLINE(int) build_GROUP_EXISTS(RE_CompileArgs* args) { - RE_CODE group; - RE_Node* start_node; - RE_Node* end_node; - RE_CompileArgs subargs; - Py_ssize_t min_width; - int status; - - /* codes: opcode, sequence, next, sequence, end. */ - if (args->code + 2 > args->end_code) - return RE_ERROR_ILLEGAL; - - group = args->code[1]; - - args->code += 2; - - /* Create nodes for the start and end of the structure. */ - start_node = create_node(args->pattern, RE_OP_GROUP_EXISTS, 0, 0, 1); - end_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - if (!start_node || !end_node) - return RE_ERROR_MEMORY; - - start_node->values[0] = group; - - subargs = *args; - subargs.min_width = 0; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - args->code = subargs.code; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - min_width = subargs.min_width; - - /* Append the start node. */ - add_node(args->end, start_node); - add_node(start_node, subargs.start); - add_node(subargs.end, end_node); - - if (args->code[0] == RE_OP_NEXT) { - ++args->code; - - subargs.code = args->code; - subargs.min_width = 0; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - args->code = subargs.code; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - min_width = min_ssize_t(min_width, subargs.min_width); - - add_node(start_node, subargs.start); - add_node(subargs.end, end_node); - } else { - add_node(start_node, end_node); - - min_width = 0; - } - - args->min_width += min_width; - - if (args->code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - ++args->code; - - args->end = end_node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a LOOKAROUND node. */ -Py_LOCAL_INLINE(int) build_LOOKAROUND(RE_CompileArgs* args) { - RE_CODE flags; - BOOL forward; - RE_Node* lookaround_node; - RE_Node* success_node; - RE_CompileArgs subargs; - int status; - - /* codes: opcode, flags, forward, sequence, end. */ - if (args->code + 3 > args->end_code) - return RE_ERROR_ILLEGAL; - - flags = args->code[1]; - forward = (BOOL)args->code[2]; - - /* Create a node for the lookaround. */ - lookaround_node = create_node(args->pattern, RE_OP_LOOKAROUND, flags, 0, - 2); - if (!lookaround_node) - return RE_ERROR_MEMORY; - - /* The number of repeat indexes. */ - lookaround_node->values[1] = 0; - - args->code += 3; - - /* Compile the sequence and check that we've reached the end of the - * subpattern. - */ - subargs = *args; - subargs.forward = forward; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - lookaround_node->values[0] = subargs.has_captures; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - ++args->code; - - /* Create the 'SUCCESS' node and append it to the subpattern. */ - success_node = create_node(args->pattern, RE_OP_SUCCESS, 0, 0, 0); - if (!success_node) - return RE_ERROR_MEMORY; - - /* Append the SUCCESS node. */ - add_node(subargs.end, success_node); - - /* Insert the subpattern into the node. */ - lookaround_node->nonstring.next_2.node = subargs.start; - - /* Append the lookaround. */ - add_node(args->end, lookaround_node); - args->end = lookaround_node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a RANGE node. */ -Py_LOCAL_INLINE(int) build_RANGE(RE_CompileArgs* args) { - RE_UINT8 op; - RE_CODE flags; - Py_ssize_t step; - RE_Node* node; - - /* codes: opcode, flags, lower, upper. */ - if (args->code + 3 > args->end_code) - return RE_ERROR_ILLEGAL; - - op = (RE_UINT8)args->code[0]; - flags = args->code[1]; - - step = get_step(op); - - if (flags & RE_ZEROWIDTH_OP) - step = 0; - - /* Create the node. */ - node = create_node(args->pattern, op, flags, step, 2); - if (!node) - return RE_ERROR_MEMORY; - - node->values[0] = args->code[2]; - node->values[1] = args->code[3]; - - args->code += 4; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - if (step != 0) - ++args->min_width; - - return RE_ERROR_SUCCESS; -} - -/* Builds a REF_GROUP node. */ -Py_LOCAL_INLINE(int) build_REF_GROUP(RE_CompileArgs* args) { - RE_CODE flags; - RE_CODE group; - RE_Node* node; - - /* codes: opcode, flags, group. */ - if (args->code + 2 > args->end_code) - return RE_ERROR_ILLEGAL; - - flags = args->code[1]; - group = args->code[2]; - node = create_node(args->pattern, (RE_UINT8)args->code[0], flags, 0, 1); - if (!node) - return RE_ERROR_MEMORY; - - node->values[0] = group; - - args->code += 3; - - /* Record that we have a reference to a group. */ - if (!record_ref_group(args->pattern, group)) - return RE_ERROR_MEMORY; - - /* Append the reference. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a REPEAT node. */ -Py_LOCAL_INLINE(int) build_REPEAT(RE_CompileArgs* args) { - BOOL greedy; - RE_CODE min_count; - RE_CODE max_count; - int status; - - /* codes: opcode, min_count, max_count, sequence, end. */ - if (args->code + 3 > args->end_code) - return RE_ERROR_ILLEGAL; - - /* This includes special cases such as optional items, which we'll check - * for and treat specially. They don't need repeat counts, which helps us - * avoid unnecessary work when matching. - */ - greedy = args->code[0] == RE_OP_GREEDY_REPEAT; - min_count = args->code[1]; - max_count = args->code[2]; - if (args->code[1] > args->code[2]) - return RE_ERROR_ILLEGAL; - - args->code += 3; - - if (min_count == 0 && max_count == 1) { - /* Optional sequence. */ - RE_Node* branch_node; - RE_Node* join_node; - RE_CompileArgs subargs; - - /* Create the start and end nodes. */ - branch_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - join_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - if (!branch_node || !join_node) - return RE_ERROR_MEMORY; - - /* Compile the sequence and check that we've reached the end of it. */ - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - if (greedy) { - /* It's a greedy option. */ - add_node(branch_node, subargs.start); - add_node(branch_node, join_node); - } else { - /* It's a lazy option. */ - add_node(branch_node, join_node); - add_node(branch_node, subargs.start); - } - add_node(subargs.end, join_node); - - /* Append the optional sequence. */ - add_node(args->end, branch_node); - args->end = join_node; - } else if (min_count == 1 && max_count == 1) { - /* Singly-repeated sequence. */ - RE_CompileArgs subargs; - - subargs = *args; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->min_width = subargs.min_width; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - /* Append the sequence. */ - add_node(args->end, subargs.start); - args->end = subargs.end; - } else { - size_t index; - RE_Node* repeat_node; - RE_CompileArgs subargs; - - index = args->pattern->repeat_count; - - /* Create the nodes for the repeat. */ - repeat_node = create_node(args->pattern, greedy ? RE_OP_GREEDY_REPEAT : - RE_OP_LAZY_REPEAT, 0, args->forward ? 1 : -1, 4); - if (!repeat_node || !record_repeat(args->pattern, index, - args->repeat_depth)) - return RE_ERROR_MEMORY; - - repeat_node->values[0] = (RE_CODE)index; - repeat_node->values[1] = min_count; - repeat_node->values[2] = max_count; - repeat_node->values[3] = args->forward; - - if (args->within_fuzzy) - args->pattern->repeat_info[index].status |= RE_STATUS_BODY; - - /* Compile the 'body' and check that we've reached the end of it. */ - subargs = *args; - subargs.min_width = 0; - subargs.visible_captures = TRUE; - subargs.has_captures = FALSE; - subargs.is_fuzzy = FALSE; - ++subargs.repeat_depth; - status = build_sequence(&subargs); - if (status != RE_ERROR_SUCCESS) - return status; - - if (subargs.code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - args->code = subargs.code; - args->min_width += (Py_ssize_t)min_count * subargs.min_width; - args->has_captures |= subargs.has_captures; - args->is_fuzzy |= subargs.is_fuzzy; - - ++args->code; - - /* Is it a repeat of something which will match a single character? - * - * If it's in a fuzzy section then it won't be optimised as a - * single-character repeat. - */ - if (sequence_matches_one(subargs.start)) { - repeat_node->op = greedy ? RE_OP_GREEDY_REPEAT_ONE : - RE_OP_LAZY_REPEAT_ONE; - - /* Append the new sequence. */ - add_node(args->end, repeat_node); - repeat_node->nonstring.next_2.node = subargs.start; - args->end = repeat_node; - } else { - RE_Node* end_repeat_node; - RE_Node* end_node; - - end_repeat_node = create_node(args->pattern, greedy ? - RE_OP_END_GREEDY_REPEAT : RE_OP_END_LAZY_REPEAT, 0, args->forward - ? 1 : -1, 4); - if (!end_repeat_node) - return RE_ERROR_MEMORY; - - end_repeat_node->values[0] = repeat_node->values[0]; - end_repeat_node->values[1] = repeat_node->values[1]; - end_repeat_node->values[2] = repeat_node->values[2]; - end_repeat_node->values[3] = args->forward; - - end_node = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - if (!end_node) - return RE_ERROR_MEMORY; - - /* Append the new sequence. */ - add_node(args->end, repeat_node); - add_node(repeat_node, subargs.start); - add_node(repeat_node, end_node); - add_node(subargs.end, end_repeat_node); - add_node(end_repeat_node, subargs.start); - add_node(end_repeat_node, end_node); - args->end = end_node; - } - } - - return RE_ERROR_SUCCESS; -} - -/* Builds a STRING node. */ -Py_LOCAL_INLINE(int) build_STRING(RE_CompileArgs* args, BOOL is_charset) { - RE_CODE flags; - RE_CODE length; - RE_UINT8 op; - Py_ssize_t step; - RE_Node* node; - size_t i; - - /* codes: opcode, flags, length, characters. */ - flags = args->code[1]; - length = args->code[2]; - if (args->code + 3 + length > args->end_code) - return RE_ERROR_ILLEGAL; - - op = (RE_UINT8)args->code[0]; - - step = get_step(op); - - /* Create the node. */ - node = create_node(args->pattern, op, flags, step * (Py_ssize_t)length, - length); - if (!node) - return RE_ERROR_MEMORY; - if (!is_charset) - node->status |= RE_STATUS_STRING; - - for (i = 0; i < length; i++) - node->values[i] = args->code[3 + i]; - - args->code += 3 + length; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - /* Because of full case-folding, one character in the text could match - * multiple characters in the pattern. - */ - if (op == RE_OP_STRING_FLD || op == RE_OP_STRING_FLD_REV) - args->min_width += possible_unfolded_length((Py_ssize_t)length); - else - args->min_width += (Py_ssize_t)length; - - return RE_ERROR_SUCCESS; -} - -/* Builds a SET node. */ -Py_LOCAL_INLINE(int) build_SET(RE_CompileArgs* args) { - RE_UINT8 op; - RE_CODE flags; - Py_ssize_t step; - RE_Node* node; - Py_ssize_t saved_min_width; - int status; - - /* codes: opcode, flags, members. */ - op = (RE_UINT8)args->code[0]; - flags = args->code[1]; - - step = get_step(op); - - if (flags & RE_ZEROWIDTH_OP) - step = 0; - - node = create_node(args->pattern, op, flags, step, 0); - if (!node) - return RE_ERROR_MEMORY; - - args->code += 2; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - saved_min_width = args->min_width; - - /* Compile the character set. */ - do { - switch (args->code[0]) { - case RE_OP_CHARACTER: - case RE_OP_PROPERTY: - status = build_CHARACTER_or_PROPERTY(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_RANGE: - status = build_RANGE(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_SET_DIFF: - case RE_OP_SET_INTER: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_UNION: - status = build_SET(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_STRING: - /* A set of characters. */ - if (!build_STRING(args, TRUE)) - return FALSE; - break; - default: - /* Illegal opcode for a character set. */ - return RE_ERROR_ILLEGAL; - } - } while (args->code < args->end_code && args->code[0] != RE_OP_END); - - /* Check that we've reached the end correctly. (The last opcode should be - * 'END'.) - */ - if (args->code >= args->end_code || args->code[0] != RE_OP_END) - return RE_ERROR_ILLEGAL; - - ++args->code; - - /* At this point the set's members are in the main sequence. They need to - * be moved out-of-line. - */ - node->nonstring.next_2.node = node->next_1.node; - node->next_1.node = NULL; - args->end = node; - - args->min_width = saved_min_width; - - if (step != 0) - ++args->min_width; - - return RE_ERROR_SUCCESS; -} - -/* Builds a STRING_SET node. */ -Py_LOCAL_INLINE(int) build_STRING_SET(RE_CompileArgs* args) { - RE_CODE index; - RE_CODE min_len; - RE_CODE max_len; - RE_Node* node; - - /* codes: opcode, index, min_len, max_len. */ - if (args->code + 3 > args->end_code) - return RE_ERROR_ILLEGAL; - - index = args->code[1]; - min_len = args->code[2]; - max_len = args->code[3]; - node = create_node(args->pattern, (RE_UINT8)args->code[0], 0, 0, 3); - if (!node) - return RE_ERROR_MEMORY; - - node->values[0] = index; - node->values[1] = min_len; - node->values[2] = max_len; - - args->code += 4; - - /* Append the reference. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a SUCCESS node . */ -Py_LOCAL_INLINE(int) build_SUCCESS(RE_CompileArgs* args) { - RE_Node* node; - /* code: opcode. */ - - /* Create the node. */ - node = create_node(args->pattern, RE_OP_SUCCESS, 0, 0, 0); - if (!node) - return RE_ERROR_MEMORY; - - ++args->code; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a zero-width node. */ -Py_LOCAL_INLINE(int) build_zerowidth(RE_CompileArgs* args) { - RE_CODE flags; - RE_Node* node; - - /* codes: opcode, flags. */ - if (args->code + 1 > args->end_code) - return RE_ERROR_ILLEGAL; - - flags = args->code[1]; - - /* Create the node. */ - node = create_node(args->pattern, (RE_UINT8)args->code[0], flags, 0, 0); - if (!node) - return RE_ERROR_MEMORY; - - args->code += 2; - - /* Append the node. */ - add_node(args->end, node); - args->end = node; - - return RE_ERROR_SUCCESS; -} - -/* Builds a sequence of nodes from regular expression code. */ -Py_LOCAL_INLINE(int) build_sequence(RE_CompileArgs* args) { - int status; - - /* Guarantee that there's something to attach to. */ - args->start = create_node(args->pattern, RE_OP_BRANCH, 0, 0, 0); - args->end = args->start; - - /* The sequence should end with an opcode we don't understand. If it - * doesn't then the code is illegal. - */ - while (args->code < args->end_code) { - /* The following code groups opcodes by format, not function. */ - switch (args->code[0]) { - case RE_OP_ANY: - case RE_OP_ANY_ALL: - case RE_OP_ANY_ALL_REV: - case RE_OP_ANY_REV: - case RE_OP_ANY_U: - case RE_OP_ANY_U_REV: - /* A simple opcode with no trailing codewords and width of 1. */ - status = build_ANY(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_ATOMIC: - /* An atomic sequence. */ - status = build_ATOMIC(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_BOUNDARY: - case RE_OP_DEFAULT_BOUNDARY: - case RE_OP_DEFAULT_END_OF_WORD: - case RE_OP_DEFAULT_START_OF_WORD: - case RE_OP_END_OF_WORD: - case RE_OP_GRAPHEME_BOUNDARY: - case RE_OP_START_OF_WORD: - /* A word or grapheme boundary. */ - status = build_BOUNDARY(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_BRANCH: - /* A 2-way branch. */ - status = build_BRANCH(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_CALL_REF: - /* A group call ref. */ - status = build_CALL_REF(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_CHARACTER: - case RE_OP_CHARACTER_IGN: - case RE_OP_CHARACTER_IGN_REV: - case RE_OP_CHARACTER_REV: - case RE_OP_PROPERTY: - case RE_OP_PROPERTY_IGN: - case RE_OP_PROPERTY_IGN_REV: - case RE_OP_PROPERTY_REV: - /* A character literal or a property. */ - status = build_CHARACTER_or_PROPERTY(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_END_OF_LINE: - case RE_OP_END_OF_LINE_U: - case RE_OP_END_OF_STRING: - case RE_OP_END_OF_STRING_LINE: - case RE_OP_END_OF_STRING_LINE_U: - case RE_OP_SEARCH_ANCHOR: - case RE_OP_START_OF_LINE: - case RE_OP_START_OF_LINE_U: - case RE_OP_START_OF_STRING: - /* A simple opcode with no trailing codewords and width of 0. */ - status = build_zerowidth(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_FUZZY: - /* A fuzzy sequence. */ - status = build_FUZZY(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_GREEDY_REPEAT: - case RE_OP_LAZY_REPEAT: - /* A repeated sequence. */ - status = build_REPEAT(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_GROUP: - /* A capture group. */ - status = build_GROUP(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_GROUP_CALL: - /* A group call. */ - status = build_GROUP_CALL(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_GROUP_EXISTS: - /* A conditional sequence. */ - status = build_GROUP_EXISTS(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_LOOKAROUND: - /* A lookaround. */ - status = build_LOOKAROUND(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_RANGE: - case RE_OP_RANGE_IGN: - case RE_OP_RANGE_IGN_REV: - case RE_OP_RANGE_REV: - /* A range. */ - status = build_RANGE(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_REF_GROUP: - case RE_OP_REF_GROUP_FLD: - case RE_OP_REF_GROUP_FLD_REV: - case RE_OP_REF_GROUP_IGN: - case RE_OP_REF_GROUP_IGN_REV: - case RE_OP_REF_GROUP_REV: - /* A reference to a group. */ - status = build_REF_GROUP(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_SET_DIFF: - case RE_OP_SET_DIFF_IGN: - case RE_OP_SET_DIFF_IGN_REV: - case RE_OP_SET_DIFF_REV: - case RE_OP_SET_INTER: - case RE_OP_SET_INTER_IGN: - case RE_OP_SET_INTER_IGN_REV: - case RE_OP_SET_INTER_REV: - case RE_OP_SET_SYM_DIFF: - case RE_OP_SET_SYM_DIFF_IGN: - case RE_OP_SET_SYM_DIFF_IGN_REV: - case RE_OP_SET_SYM_DIFF_REV: - case RE_OP_SET_UNION: - case RE_OP_SET_UNION_IGN: - case RE_OP_SET_UNION_IGN_REV: - case RE_OP_SET_UNION_REV: - /* A set. */ - status = build_SET(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_STRING: - case RE_OP_STRING_FLD: - case RE_OP_STRING_FLD_REV: - case RE_OP_STRING_IGN: - case RE_OP_STRING_IGN_REV: - case RE_OP_STRING_REV: - /* A string literal. */ - if (!build_STRING(args, FALSE)) - return FALSE; - break; - case RE_OP_STRING_SET: - case RE_OP_STRING_SET_FLD: - case RE_OP_STRING_SET_FLD_REV: - case RE_OP_STRING_SET_IGN: - case RE_OP_STRING_SET_IGN_REV: - case RE_OP_STRING_SET_REV: - /* A reference to a list. */ - status = build_STRING_SET(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - case RE_OP_SUCCESS: - /* Success. */ - status = build_SUCCESS(args); - if (status != RE_ERROR_SUCCESS) - return status; - break; - default: - /* We've found an opcode which we don't recognise. We'll leave it - * for the caller. - */ - return RE_ERROR_SUCCESS; - } - } - - /* If we're here then we should be at the end of the code, otherwise we - * have an error. - */ - return args->code == args->end_code; -} - -/* Compiles the regular expression code to 'nodes'. - * - * Various details about the regular expression are discovered during - * compilation and stored in the PatternObject. - */ -Py_LOCAL_INLINE(BOOL) compile_to_nodes(RE_CODE* code, RE_CODE* end_code, - PatternObject* pattern) { - RE_CompileArgs args; - int status; - - /* Compile a regex sequence and then check that we've reached the end - * correctly. (The last opcode should be 'SUCCESS'.) - * - * If successful, 'start' and 'end' will point to the start and end nodes - * of the compiled sequence. - */ - args.code = code; - args.end_code = end_code; - args.pattern = pattern; - args.forward = (pattern->flags & RE_FLAG_REVERSE) == 0; - args.min_width = 0; - args.visible_captures = FALSE; - args.has_captures = FALSE; - args.repeat_depth = 0; - args.is_fuzzy = FALSE; - args.within_fuzzy = FALSE; - status = build_sequence(&args); - if (status == RE_ERROR_ILLEGAL) - set_error(RE_ERROR_ILLEGAL, NULL); - - if (status != RE_ERROR_SUCCESS) - return FALSE; - - pattern->min_width = args.min_width; - pattern->is_fuzzy = args.is_fuzzy; - pattern->do_search_start = TRUE; - pattern->start_node = args.start; - - /* Optimise the pattern. */ - if (!optimise_pattern(pattern)) - return FALSE; - - pattern->start_test = locate_test_start(pattern->start_node); - - /* Get the call_ref for the entire pattern, if any. */ - if (pattern->start_node->op == RE_OP_CALL_REF) - pattern->pattern_call_ref = (Py_ssize_t)pattern->start_node->values[0]; - else - pattern->pattern_call_ref = -1; - - return TRUE; -} - -/* Gets the required characters for a regex. - * - * In the event of an error, it just pretends that there are no required - * characters. - */ -Py_LOCAL_INLINE(void) get_required_chars(PyObject* required_chars, RE_CODE** - req_chars, size_t* req_length) { - Py_ssize_t len; - RE_CODE* chars; - Py_ssize_t i; - - *req_chars = NULL; - *req_length = 0; - - len = PyTuple_GET_SIZE(required_chars); - if (len < 1 || PyErr_Occurred()) { - PyErr_Clear(); - return; - } - - chars = (RE_CODE*)re_alloc((size_t)len * sizeof(RE_CODE)); - if (!chars) - goto error; - - for (i = 0; i < len; i++) { - PyObject* o; - size_t value; - - /* PyTuple_SET_ITEM borrows the reference. */ - o = PyTuple_GET_ITEM(required_chars, i); - - value = PyLong_AsUnsignedLong(o); - if ((Py_ssize_t)value == -1 && PyErr_Occurred()) - goto error; - - chars[i] = (RE_CODE)value; - if (chars[i] != value) - goto error; - } - - *req_chars = chars; - *req_length = (size_t)len; - - return; - -error: - PyErr_Clear(); - re_dealloc(chars); -} - -/* Makes a STRING node. */ -Py_LOCAL_INLINE(RE_Node*) make_STRING_node(PatternObject* pattern, RE_UINT8 op, - size_t length, RE_CODE* chars) { - Py_ssize_t step; - RE_Node* node; - size_t i; - - step = get_step(op); - - /* Create the node. */ - node = create_node(pattern, op, 0, step * (Py_ssize_t)length, length); - if (!node) - return NULL; - - node->status |= RE_STATUS_STRING; - - for (i = 0; i < length; i++) - node->values[i] = chars[i]; - - return node; -} - -/* Compiles regular expression code to a PatternObject. - * - * The regular expression code is provided as a list and is then compiled to - * 'nodes'. Various details about the regular expression are discovered during - * compilation and stored in the PatternObject. - */ -static PyObject* re_compile(PyObject* self_, PyObject* args) { - PyObject* pattern; - Py_ssize_t flags = 0; - PyObject* code_list; - PyObject* groupindex; - PyObject* indexgroup; - PyObject* named_lists; - PyObject* named_list_indexes; - Py_ssize_t req_offset; - PyObject* required_chars; - size_t req_length; - RE_CODE* req_chars; - Py_ssize_t req_flags; - size_t public_group_count; - Py_ssize_t code_len; - RE_CODE* code; - Py_ssize_t i; - PatternObject* self; - BOOL ascii; - BOOL locale; - BOOL unicode; - BOOL ok; - - if (!PyArg_ParseTuple(args, "OnOOOOOnOnn:re_compile", &pattern, &flags, - &code_list, &groupindex, &indexgroup, &named_lists, &named_list_indexes, - &req_offset, &required_chars, &req_flags, &public_group_count)) - return NULL; - - /* Read the regex code. */ - code_len = PyList_GET_SIZE(code_list); - code = (RE_CODE*)re_alloc((size_t)code_len * sizeof(RE_CODE)); - if (!code) - return NULL; - - for (i = 0; i < code_len; i++) { - PyObject* o; - size_t value; - - /* PyList_GET_ITEM borrows a reference. */ - o = PyList_GET_ITEM(code_list, i); - - value = PyLong_AsUnsignedLong(o); - if ((Py_ssize_t)value == -1 && PyErr_Occurred()) - goto error; - - code[i] = (RE_CODE)value; - if (code[i] != value) - goto error; - } - - /* Get the required characters. */ - get_required_chars(required_chars, &req_chars, &req_length); - - /* Create the PatternObject. */ - self = PyObject_NEW(PatternObject, &Pattern_Type); - if (!self) { - set_error(RE_ERROR_MEMORY, NULL); - re_dealloc(req_chars); - re_dealloc(code); - return NULL; - } - - /* Initialise the PatternObject. */ - self->pattern = pattern; - self->flags = flags; - self->weakreflist = NULL; - self->start_node = NULL; - self->repeat_count = 0; - self->true_group_count = 0; - self->public_group_count = public_group_count; - self->group_end_index = 0; - self->groupindex = groupindex; - self->indexgroup = indexgroup; - self->named_lists = named_lists; - self->named_lists_count = (size_t)PyDict_Size(named_lists); - self->partial_named_lists[0] = NULL; - self->partial_named_lists[1] = NULL; - self->named_list_indexes = named_list_indexes; - self->node_capacity = 0; - self->node_count = 0; - self->node_list = NULL; - self->group_info_capacity = 0; - self->group_info = NULL; - self->call_ref_info_capacity = 0; - self->call_ref_info_count = 0; - self->call_ref_info = NULL; - self->repeat_info_capacity = 0; - self->repeat_info = NULL; - self->groups_storage = NULL; - self->repeats_storage = NULL; - self->fuzzy_count = 0; - self->recursive = FALSE; - self->req_offset = req_offset; - self->req_string = NULL; - Py_INCREF(self->pattern); - Py_INCREF(self->groupindex); - Py_INCREF(self->indexgroup); - Py_INCREF(self->named_lists); - Py_INCREF(self->named_list_indexes); - - /* Initialise the character encoding. */ - unicode = (flags & RE_FLAG_UNICODE) != 0; - locale = (flags & RE_FLAG_LOCALE) != 0; - ascii = (flags & RE_FLAG_ASCII) != 0; - if (!unicode && !locale && !ascii) { - if (PyString_Check(self->pattern)) - ascii = RE_FLAG_ASCII; - else - unicode = RE_FLAG_UNICODE; - } - if (unicode) - self->encoding = &unicode_encoding; - else if (locale) - self->encoding = &locale_encoding; - else if (ascii) - self->encoding = &ascii_encoding; - - /* Compile the regular expression code to nodes. */ - ok = compile_to_nodes(code, code + code_len, self); - - /* We no longer need the regular expression code. */ - re_dealloc(code); - - if (!ok) { - Py_DECREF(self); - re_dealloc(req_chars); - return NULL; - } - - /* Make a node for the required string, if there's one. */ - if (req_chars) { - /* Remove the FULLCASE flag if it's not a Unicode pattern. */ - if (!(self->flags & RE_FLAG_UNICODE)) - req_flags &= ~RE_FLAG_FULLCASE; - - if (self->flags & RE_FLAG_REVERSE) { - switch (req_flags) { - case 0: - self->req_string = make_STRING_node(self, RE_OP_STRING_REV, - req_length, req_chars); - break; - case RE_FLAG_IGNORECASE | RE_FLAG_FULLCASE: - self->req_string = make_STRING_node(self, RE_OP_STRING_FLD_REV, - req_length, req_chars); - break; - case RE_FLAG_IGNORECASE: - self->req_string = make_STRING_node(self, RE_OP_STRING_IGN_REV, - req_length, req_chars); - break; - } - } else { - switch (req_flags) { - case 0: - self->req_string = make_STRING_node(self, RE_OP_STRING, - req_length, req_chars); - break; - case RE_FLAG_IGNORECASE | RE_FLAG_FULLCASE: - self->req_string = make_STRING_node(self, RE_OP_STRING_FLD, - req_length, req_chars); - break; - case RE_FLAG_IGNORECASE: - self->req_string = make_STRING_node(self, RE_OP_STRING_IGN, - req_length, req_chars); - break; - } - } - - re_dealloc(req_chars); - } - - return (PyObject*)self; - -error: - re_dealloc(code); - set_error(RE_ERROR_ILLEGAL, NULL); - return NULL; -} - -/* Gets the size of the codewords. */ -static PyObject* get_code_size(PyObject* self, PyObject* unused) { - return Py_BuildValue("n", sizeof(RE_CODE)); -} - -/* Gets the property dict. */ -static PyObject* get_properties(PyObject* self_, PyObject* args) { - Py_INCREF(property_dict); - - return property_dict; -} - -/* Folds the case of a string. */ -static PyObject* fold_case(PyObject* self_, PyObject* args) { - RE_StringInfo str_info; - Py_UCS4 (*char_at)(void* text, Py_ssize_t pos); - Py_ssize_t folded_charsize; - void (*set_char_at)(void* text, Py_ssize_t pos, Py_UCS4 ch); - RE_EncodingTable* encoding; - Py_ssize_t buf_size; - void* folded; - Py_ssize_t folded_len; - PyObject* result; - - Py_ssize_t flags; - PyObject* string; - if (!PyArg_ParseTuple(args, "nO:fold_case", &flags, &string)) - return NULL; - - if (!(flags & RE_FLAG_IGNORECASE)) { - Py_INCREF(string); - return string; - } - - /* Get the string. */ - if (!get_string(string, &str_info)) - return NULL; - - /* Get the function for reading from the original string. */ - switch (str_info.charsize) { - case 1: - char_at = bytes1_char_at; - break; - case 2: - char_at = bytes2_char_at; - break; - case 4: - char_at = bytes4_char_at; - break; - default: -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return NULL; - } - - /* What's the encoding? */ - if (flags & RE_FLAG_UNICODE) - encoding = &unicode_encoding; - else if (flags & RE_FLAG_LOCALE) - encoding = &locale_encoding; - else if (flags & RE_FLAG_ASCII) - encoding = &ascii_encoding; - else - encoding = &unicode_encoding; - - /* The folded string will have the same width as the original string. */ - folded_charsize = str_info.charsize; - - /* Get the function for writing to the folded string. */ - switch (folded_charsize) { - case 1: - set_char_at = bytes1_set_char_at; - break; - case 2: - set_char_at = bytes2_set_char_at; - break; - case 4: - set_char_at = bytes4_set_char_at; - break; - default: -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return NULL; - } - - /* Allocate a buffer for the folded string. */ - if (flags & RE_FLAG_FULLCASE) - /* When using full case-folding with Unicode, some single codepoints - * are mapped to multiple codepoints. - */ - buf_size = str_info.length * RE_MAX_FOLDED; - else - buf_size = str_info.length; - - folded = re_alloc((size_t)(buf_size * folded_charsize)); - if (!folded) { -#if PY_VERSION_HEX >= 0x02060000 - release_buffer(&str_info); - -#endif - return NULL; - } - - /* Fold the case of the string. */ - folded_len = 0; - - if (flags & RE_FLAG_FULLCASE) { - /* Full case-folding. */ - int (*full_case_fold)(Py_UCS4 ch, Py_UCS4* folded); - Py_ssize_t i; - Py_UCS4 codepoints[RE_MAX_FOLDED]; - - full_case_fold = encoding->full_case_fold; - - for (i = 0; i < str_info.length; i++) { - int count; - int j; - - count = full_case_fold(char_at(str_info.characters, i), - codepoints); - for (j = 0; j < count; j++) - set_char_at(folded, folded_len + j, codepoints[j]); - - folded_len += count; - } - } else { - /* Simple case-folding. */ - Py_UCS4 (*simple_case_fold)(Py_UCS4 ch); - Py_ssize_t i; - - simple_case_fold = encoding->simple_case_fold; - - for (i = 0; i < str_info.length; i++) { - Py_UCS4 ch; - - ch = simple_case_fold(char_at(str_info.characters, i)); - set_char_at(folded, i, ch); - } - - folded_len = str_info.length; - } - - /* Build the result string. */ - if (str_info.is_unicode) - result = build_unicode_value(folded, folded_len, folded_charsize); - else - result = build_bytes_value(folded, folded_len, folded_charsize); - - re_dealloc(folded); - -#if PY_VERSION_HEX >= 0x02060000 - /* Release the original string's buffer. */ - release_buffer(&str_info); - -#endif - return result; -} - -/* Returns a tuple of the Unicode characters that expand on full case-folding. - */ -static PyObject* get_expand_on_folding(PyObject* self, PyObject* unused) { - int count; - int i; - PyObject* result; - - /* How many characters are there? */ - count = sizeof(re_expand_on_folding) / sizeof(re_expand_on_folding[0]); - - /* Put all the characters in a tuple. */ - result = PyTuple_New(count); - if (!result) - return NULL; - - for (i = 0; i < count; i++) { - Py_UNICODE codepoint; - PyObject* item; - - codepoint = re_expand_on_folding[i]; - - item = build_unicode_value(&codepoint, 1, sizeof(codepoint)); - if (!item) - goto error; - - /* PyTuple_SetItem borrows the reference. */ - PyTuple_SetItem(result, i, item); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* Returns whether a character has a given value for a Unicode property. */ -static PyObject* has_property_value(PyObject* self_, PyObject* args) { - BOOL v; - - Py_ssize_t property_value; - Py_ssize_t character; - if (!PyArg_ParseTuple(args, "nn:has_property_value", &property_value, - &character)) - return NULL; - - v = unicode_has_property((RE_CODE)property_value, (Py_UCS4)character) ? 1 : - 0; - - return Py_BuildValue("n", v); -} - -/* Returns a list of all the simple cases of a character. - * - * If full case-folding is turned on and the character also expands on full - * case-folding, a None is appended to the list. - */ -static PyObject* get_all_cases(PyObject* self_, PyObject* args) { - RE_EncodingTable* encoding; - int count; - Py_UCS4 cases[RE_MAX_CASES]; - Py_UCS4 folded[RE_MAX_FOLDED]; - PyObject* result; - int i; - - Py_ssize_t flags; - Py_ssize_t character; - if (!PyArg_ParseTuple(args, "nn:get_all_cases", &flags, &character)) - return NULL; - - /* What's the encoding? */ - if (flags & RE_FLAG_UNICODE) - encoding = &unicode_encoding; - else if (flags & RE_FLAG_LOCALE) - encoding = &locale_encoding; - else if (flags & RE_FLAG_ASCII) - encoding = &ascii_encoding; - else - encoding = &ascii_encoding; - - /* Get all the simple cases. */ - count = encoding->all_cases((Py_UCS4)character, cases); - - result = PyList_New(count); - if (!result) - return NULL; - - for (i = 0; i < count; i++) { - PyObject* item; - - item = Py_BuildValue("n", cases[i]); - if (!item) - goto error; - - /* PyList_SetItem borrows the reference. */ - PyList_SetItem(result, i, item); - } - - /* If the character also expands on full case-folding, append a None. */ - if ((flags & RE_FULL_CASE_FOLDING) == RE_FULL_CASE_FOLDING) { - count = encoding->full_case_fold((Py_UCS4)character, folded); - if (count > 1) - PyList_Append(result, Py_None); - } - - return result; - -error: - Py_DECREF(result); - return NULL; -} - -/* The table of the module's functions. */ -static PyMethodDef _functions[] = { - {"compile", (PyCFunction)re_compile, METH_VARARGS}, - {"get_code_size", (PyCFunction)get_code_size, METH_NOARGS}, - {"get_properties", (PyCFunction)get_properties, METH_VARARGS}, - {"fold_case", (PyCFunction)fold_case, METH_VARARGS}, - {"get_expand_on_folding", (PyCFunction)get_expand_on_folding, METH_NOARGS}, - {"has_property_value", (PyCFunction)has_property_value, METH_VARARGS}, - {"get_all_cases", (PyCFunction)get_all_cases, METH_VARARGS}, - {NULL, NULL} -}; - -/* Initialises the property dictionary. */ -Py_LOCAL_INLINE(BOOL) init_property_dict(void) { - size_t value_set_count; - size_t i; - PyObject** value_dicts; - - property_dict = NULL; - - /* How many value sets are there? */ - value_set_count = 0; - - for (i = 0; i < sizeof(re_property_values) / sizeof(re_property_values[0]); - i++) { - RE_PropertyValue* value; - - value = &re_property_values[i]; - if (value->value_set >= value_set_count) - value_set_count = (size_t)value->value_set + 1; - } - - /* Quick references for the value sets. */ - value_dicts = (PyObject**)re_alloc(value_set_count * - sizeof(value_dicts[0])); - if (!value_dicts) - return FALSE; - - memset(value_dicts, 0, value_set_count * sizeof(value_dicts[0])); - - /* Build the property values dictionaries. */ - for (i = 0; i < sizeof(re_property_values) / sizeof(re_property_values[0]); - i++) { - RE_PropertyValue* value; - PyObject* v; - int status; - - value = &re_property_values[i]; - if (!value_dicts[value->value_set]) { - value_dicts[value->value_set] = PyDict_New(); - if (!value_dicts[value->value_set]) - goto error; - } - - v = Py_BuildValue("i", value->id); - if (!v) - goto error; - - status = PyDict_SetItemString(value_dicts[value->value_set], - re_strings[value->name], v); - Py_DECREF(v); - if (status < 0) - goto error; - } - - /* Build the property dictionary. */ - property_dict = PyDict_New(); - if (!property_dict) - goto error; - - for (i = 0; i < sizeof(re_properties) / sizeof(re_properties[0]); i++) { - RE_Property* property; - PyObject* v; - int status; - - property = &re_properties[i]; - v = Py_BuildValue("iO", property->id, - value_dicts[property->value_set]); - if (!v) - goto error; - - status = PyDict_SetItemString(property_dict, - re_strings[property->name], v); - Py_DECREF(v); - if (status < 0) - goto error; - } - - /* DECREF the value sets. Any unused ones will be deallocated. */ - for (i = 0; i < value_set_count; i++) - Py_XDECREF(value_dicts[i]); - - re_dealloc(value_dicts); - - return TRUE; - -error: - Py_XDECREF(property_dict); - - /* DECREF the value sets. */ - for (i = 0; i < value_set_count; i++) - Py_XDECREF(value_dicts[i]); - - re_dealloc(value_dicts); - - return FALSE; -} - -/* Initialises the module. */ -PyMODINIT_FUNC init_regex(void) { - PyObject* m; - PyObject* d; - PyObject* x; - -#if defined(VERBOSE) - /* Unbuffered in case it crashes! */ - setvbuf(stdout, NULL, _IONBF, 0); - -#endif - /* Initialise Pattern_Type. */ - Pattern_Type.tp_dealloc = pattern_dealloc; - Pattern_Type.tp_repr = pattern_repr; - Pattern_Type.tp_flags = Py_TPFLAGS_HAVE_WEAKREFS; - Pattern_Type.tp_doc = pattern_doc; - Pattern_Type.tp_weaklistoffset = offsetof(PatternObject, weakreflist); - Pattern_Type.tp_methods = pattern_methods; - Pattern_Type.tp_members = pattern_members; - Pattern_Type.tp_getset = pattern_getset; - - /* Initialise Match_Type. */ - Match_Type.tp_dealloc = match_dealloc; - Match_Type.tp_repr = match_repr; - Match_Type.tp_as_mapping = &match_as_mapping; - Match_Type.tp_flags = Py_TPFLAGS_DEFAULT; - Match_Type.tp_doc = match_doc; - Match_Type.tp_methods = match_methods; - Match_Type.tp_members = match_members; - Match_Type.tp_getset = match_getset; - - /* Initialise Scanner_Type. */ - Scanner_Type.tp_dealloc = scanner_dealloc; - Scanner_Type.tp_flags = Py_TPFLAGS_DEFAULT; - Scanner_Type.tp_doc = scanner_doc; - Scanner_Type.tp_iter = scanner_iter; - Scanner_Type.tp_iternext = scanner_iternext; - Scanner_Type.tp_methods = scanner_methods; - Scanner_Type.tp_members = scanner_members; - - /* Initialise Splitter_Type. */ - Splitter_Type.tp_dealloc = splitter_dealloc; - Splitter_Type.tp_flags = Py_TPFLAGS_DEFAULT; - Splitter_Type.tp_doc = splitter_doc; - Splitter_Type.tp_iter = splitter_iter; - Splitter_Type.tp_iternext = splitter_iternext; - Splitter_Type.tp_methods = splitter_methods; - Splitter_Type.tp_members = splitter_members; - - /* Initialize object types */ - if (PyType_Ready(&Pattern_Type) < 0) - return; - if (PyType_Ready(&Match_Type) < 0) - return; - if (PyType_Ready(&Scanner_Type) < 0) - return; - if (PyType_Ready(&Splitter_Type) < 0) - return; - - error_exception = NULL; - - m = Py_InitModule("_" RE_MODULE, _functions); - if (!m) - return; - - d = PyModule_GetDict(m); - - x = PyInt_FromLong(RE_MAGIC); - if (x) { - PyDict_SetItemString(d, "MAGIC", x); - Py_DECREF(x); - } - - x = PyInt_FromLong(sizeof(RE_CODE)); - if (x) { - PyDict_SetItemString(d, "CODE_SIZE", x); - Py_DECREF(x); - } - - x = PyString_FromString(copyright); - if (x) { - PyDict_SetItemString(d, "copyright", x); - Py_DECREF(x); - } - - /* Initialise the property dictionary. */ - if (!init_property_dict()) - return; -} - -/* vim:ts=4:sw=4:et */ diff --git a/lib/regex/_regex.h b/lib/regex/_regex.h deleted file mode 100644 index 33dc1540..00000000 --- a/lib/regex/_regex.h +++ /dev/null @@ -1,228 +0,0 @@ -/* - * Secret Labs' Regular Expression Engine - * - * regular expression matching engine - * - * Copyright (c) 1997-2001 by Secret Labs AB. All rights reserved. - * - * NOTE: This file is generated by regex.py. If you need - * to change anything in here, edit regex.py and run it. - * - * 2010-01-16 mrab Re-written - */ - -/* Supports Unicode version 6.3.0. */ - -#define RE_MAGIC 20100116 - -#include "_regex_unicode.h" - -/* Operators. */ -#define RE_OP_FAILURE 0 -#define RE_OP_SUCCESS 1 -#define RE_OP_ANY 2 -#define RE_OP_ANY_ALL 3 -#define RE_OP_ANY_ALL_REV 4 -#define RE_OP_ANY_REV 5 -#define RE_OP_ANY_U 6 -#define RE_OP_ANY_U_REV 7 -#define RE_OP_ATOMIC 8 -#define RE_OP_BOUNDARY 9 -#define RE_OP_BRANCH 10 -#define RE_OP_CALL_REF 11 -#define RE_OP_CHARACTER 12 -#define RE_OP_CHARACTER_IGN 13 -#define RE_OP_CHARACTER_IGN_REV 14 -#define RE_OP_CHARACTER_REV 15 -#define RE_OP_DEFAULT_BOUNDARY 16 -#define RE_OP_DEFAULT_END_OF_WORD 17 -#define RE_OP_DEFAULT_START_OF_WORD 18 -#define RE_OP_END 19 -#define RE_OP_END_OF_LINE 20 -#define RE_OP_END_OF_LINE_U 21 -#define RE_OP_END_OF_STRING 22 -#define RE_OP_END_OF_STRING_LINE 23 -#define RE_OP_END_OF_STRING_LINE_U 24 -#define RE_OP_END_OF_WORD 25 -#define RE_OP_FUZZY 26 -#define RE_OP_GRAPHEME_BOUNDARY 27 -#define RE_OP_GREEDY_REPEAT 28 -#define RE_OP_GROUP 29 -#define RE_OP_GROUP_CALL 30 -#define RE_OP_GROUP_EXISTS 31 -#define RE_OP_LAZY_REPEAT 32 -#define RE_OP_LOOKAROUND 33 -#define RE_OP_NEXT 34 -#define RE_OP_PROPERTY 35 -#define RE_OP_PROPERTY_IGN 36 -#define RE_OP_PROPERTY_IGN_REV 37 -#define RE_OP_PROPERTY_REV 38 -#define RE_OP_RANGE 39 -#define RE_OP_RANGE_IGN 40 -#define RE_OP_RANGE_IGN_REV 41 -#define RE_OP_RANGE_REV 42 -#define RE_OP_REF_GROUP 43 -#define RE_OP_REF_GROUP_FLD 44 -#define RE_OP_REF_GROUP_FLD_REV 45 -#define RE_OP_REF_GROUP_IGN 46 -#define RE_OP_REF_GROUP_IGN_REV 47 -#define RE_OP_REF_GROUP_REV 48 -#define RE_OP_SEARCH_ANCHOR 49 -#define RE_OP_SET_DIFF 50 -#define RE_OP_SET_DIFF_IGN 51 -#define RE_OP_SET_DIFF_IGN_REV 52 -#define RE_OP_SET_DIFF_REV 53 -#define RE_OP_SET_INTER 54 -#define RE_OP_SET_INTER_IGN 55 -#define RE_OP_SET_INTER_IGN_REV 56 -#define RE_OP_SET_INTER_REV 57 -#define RE_OP_SET_SYM_DIFF 58 -#define RE_OP_SET_SYM_DIFF_IGN 59 -#define RE_OP_SET_SYM_DIFF_IGN_REV 60 -#define RE_OP_SET_SYM_DIFF_REV 61 -#define RE_OP_SET_UNION 62 -#define RE_OP_SET_UNION_IGN 63 -#define RE_OP_SET_UNION_IGN_REV 64 -#define RE_OP_SET_UNION_REV 65 -#define RE_OP_START_OF_LINE 66 -#define RE_OP_START_OF_LINE_U 67 -#define RE_OP_START_OF_STRING 68 -#define RE_OP_START_OF_WORD 69 -#define RE_OP_STRING 70 -#define RE_OP_STRING_FLD 71 -#define RE_OP_STRING_FLD_REV 72 -#define RE_OP_STRING_IGN 73 -#define RE_OP_STRING_IGN_REV 74 -#define RE_OP_STRING_REV 75 -#define RE_OP_STRING_SET 76 -#define RE_OP_STRING_SET_FLD 77 -#define RE_OP_STRING_SET_FLD_REV 78 -#define RE_OP_STRING_SET_IGN 79 -#define RE_OP_STRING_SET_IGN_REV 80 -#define RE_OP_STRING_SET_REV 81 -#define RE_OP_BODY_END 82 -#define RE_OP_BODY_START 83 -#define RE_OP_END_FUZZY 84 -#define RE_OP_END_GREEDY_REPEAT 85 -#define RE_OP_END_GROUP 86 -#define RE_OP_END_LAZY_REPEAT 87 -#define RE_OP_GREEDY_REPEAT_ONE 88 -#define RE_OP_GROUP_RETURN 89 -#define RE_OP_LAZY_REPEAT_ONE 90 -#define RE_OP_MATCH_BODY 91 -#define RE_OP_MATCH_TAIL 92 -#define RE_OP_START_GROUP 93 - -char* re_op_text[] = { - "RE_OP_FAILURE", - "RE_OP_SUCCESS", - "RE_OP_ANY", - "RE_OP_ANY_ALL", - "RE_OP_ANY_ALL_REV", - "RE_OP_ANY_REV", - "RE_OP_ANY_U", - "RE_OP_ANY_U_REV", - "RE_OP_ATOMIC", - "RE_OP_BOUNDARY", - "RE_OP_BRANCH", - "RE_OP_CALL_REF", - "RE_OP_CHARACTER", - "RE_OP_CHARACTER_IGN", - "RE_OP_CHARACTER_IGN_REV", - "RE_OP_CHARACTER_REV", - "RE_OP_DEFAULT_BOUNDARY", - "RE_OP_DEFAULT_END_OF_WORD", - "RE_OP_DEFAULT_START_OF_WORD", - "RE_OP_END", - "RE_OP_END_OF_LINE", - "RE_OP_END_OF_LINE_U", - "RE_OP_END_OF_STRING", - "RE_OP_END_OF_STRING_LINE", - "RE_OP_END_OF_STRING_LINE_U", - "RE_OP_END_OF_WORD", - "RE_OP_FUZZY", - "RE_OP_GRAPHEME_BOUNDARY", - "RE_OP_GREEDY_REPEAT", - "RE_OP_GROUP", - "RE_OP_GROUP_CALL", - "RE_OP_GROUP_EXISTS", - "RE_OP_LAZY_REPEAT", - "RE_OP_LOOKAROUND", - "RE_OP_NEXT", - "RE_OP_PROPERTY", - "RE_OP_PROPERTY_IGN", - "RE_OP_PROPERTY_IGN_REV", - "RE_OP_PROPERTY_REV", - "RE_OP_RANGE", - "RE_OP_RANGE_IGN", - "RE_OP_RANGE_IGN_REV", - "RE_OP_RANGE_REV", - "RE_OP_REF_GROUP", - "RE_OP_REF_GROUP_FLD", - "RE_OP_REF_GROUP_FLD_REV", - "RE_OP_REF_GROUP_IGN", - "RE_OP_REF_GROUP_IGN_REV", - "RE_OP_REF_GROUP_REV", - "RE_OP_SEARCH_ANCHOR", - "RE_OP_SET_DIFF", - "RE_OP_SET_DIFF_IGN", - "RE_OP_SET_DIFF_IGN_REV", - "RE_OP_SET_DIFF_REV", - "RE_OP_SET_INTER", - "RE_OP_SET_INTER_IGN", - "RE_OP_SET_INTER_IGN_REV", - "RE_OP_SET_INTER_REV", - "RE_OP_SET_SYM_DIFF", - "RE_OP_SET_SYM_DIFF_IGN", - "RE_OP_SET_SYM_DIFF_IGN_REV", - "RE_OP_SET_SYM_DIFF_REV", - "RE_OP_SET_UNION", - "RE_OP_SET_UNION_IGN", - "RE_OP_SET_UNION_IGN_REV", - "RE_OP_SET_UNION_REV", - "RE_OP_START_OF_LINE", - "RE_OP_START_OF_LINE_U", - "RE_OP_START_OF_STRING", - "RE_OP_START_OF_WORD", - "RE_OP_STRING", - "RE_OP_STRING_FLD", - "RE_OP_STRING_FLD_REV", - "RE_OP_STRING_IGN", - "RE_OP_STRING_IGN_REV", - "RE_OP_STRING_REV", - "RE_OP_STRING_SET", - "RE_OP_STRING_SET_FLD", - "RE_OP_STRING_SET_FLD_REV", - "RE_OP_STRING_SET_IGN", - "RE_OP_STRING_SET_IGN_REV", - "RE_OP_STRING_SET_REV", - "RE_OP_BODY_END", - "RE_OP_BODY_START", - "RE_OP_END_FUZZY", - "RE_OP_END_GREEDY_REPEAT", - "RE_OP_END_GROUP", - "RE_OP_END_LAZY_REPEAT", - "RE_OP_GREEDY_REPEAT_ONE", - "RE_OP_GROUP_RETURN", - "RE_OP_LAZY_REPEAT_ONE", - "RE_OP_MATCH_BODY", - "RE_OP_MATCH_TAIL", - "RE_OP_START_GROUP", -}; - -#define RE_FLAG_ASCII 0x80 -#define RE_FLAG_BESTMATCH 0x1000 -#define RE_FLAG_DEBUG 0x200 -#define RE_FLAG_DOTALL 0x10 -#define RE_FLAG_ENHANCEMATCH 0x8000 -#define RE_FLAG_FULLCASE 0x4000 -#define RE_FLAG_IGNORECASE 0x2 -#define RE_FLAG_LOCALE 0x4 -#define RE_FLAG_MULTILINE 0x8 -#define RE_FLAG_REVERSE 0x400 -#define RE_FLAG_TEMPLATE 0x1 -#define RE_FLAG_UNICODE 0x20 -#define RE_FLAG_VERBOSE 0x40 -#define RE_FLAG_VERSION0 0x2000 -#define RE_FLAG_VERSION1 0x100 -#define RE_FLAG_WORD 0x800 diff --git a/lib/regex/_regex_core.py b/lib/regex/_regex_core.py deleted file mode 100644 index 5adbb524..00000000 --- a/lib/regex/_regex_core.py +++ /dev/null @@ -1,4086 +0,0 @@ -# -# Secret Labs' Regular Expression Engine core module -# -# Copyright (c) 1998-2001 by Secret Labs AB. All rights reserved. -# -# This version of the SRE library can be redistributed under CNRI's -# Python 1.6 license. For any other use, please contact Secret Labs -# AB (info@pythonware.com). -# -# Portions of this engine have been developed in cooperation with -# CNRI. Hewlett-Packard provided funding for 1.6 integration and -# other compatibility work. -# -# 2010-01-16 mrab Python front-end re-written and extended - -import string -import sys -import unicodedata -from collections import defaultdict - -if sys.version_info < (2, 6): - from Python25 import _regex -elif sys.version_info < (2, 7): - from Python26 import _regex -else: - from Python27 import _regex - - -__all__ = ["A", "ASCII", "B", "BESTMATCH", "D", "DEBUG", "E", "ENHANCEMATCH", - "F", "FULLCASE", "I", "IGNORECASE", "L", "LOCALE", "M", "MULTILINE", "R", - "REVERSE", "S", "DOTALL", "T", "TEMPLATE", "U", "UNICODE", "V0", "VERSION0", - "V1", "VERSION1", "W", "WORD", "X", "VERBOSE", "error", - "Scanner"] - -# The regex exception. -class error(Exception): - def __init__(self, message, set_error=False): - Exception.__init__(self, message) - self.set_error = set_error - -# The exception for when a positional flag has been turned on in the old -# behaviour. -class _UnscopedFlagSet(Exception): - pass - -# The exception for when parsing fails and we want to try something else. -class ParseError(Exception): - pass - -# The exception for when there isn't a valid first set. -class _FirstSetError(Exception): - pass - -# Flags. -A = ASCII = 0x80 # Assume ASCII locale. -B = BESTMATCH = 0x1000 # Best fuzzy match. -D = DEBUG = 0x200 # Print parsed pattern. -E = ENHANCEMATCH = 0x8000 # Attempt to improve the fit after finding the first - # fuzzy match. -F = FULLCASE = 0x4000 # Unicode full case-folding. -I = IGNORECASE = 0x2 # Ignore case. -L = LOCALE = 0x4 # Assume current 8-bit locale. -M = MULTILINE = 0x8 # Make anchors look for newline. -R = REVERSE = 0x400 # Search backwards. -S = DOTALL = 0x10 # Make dot match newline. -U = UNICODE = 0x20 # Assume Unicode locale. -V0 = VERSION0 = 0x2000 # Old legacy behaviour. -V1 = VERSION1 = 0x100 # New enhanced behaviour. -W = WORD = 0x800 # Default Unicode word breaks. -X = VERBOSE = 0x40 # Ignore whitespace and comments. -T = TEMPLATE = 0x1 # Template (present because re module has it). - -DEFAULT_VERSION = VERSION1 - -_ALL_VERSIONS = VERSION0 | VERSION1 -_ALL_ENCODINGS = ASCII | LOCALE | UNICODE - -# The default flags for the various versions. -DEFAULT_FLAGS = {VERSION0: 0, VERSION1: FULLCASE} - -# The mask for the flags. -GLOBAL_FLAGS = (_ALL_ENCODINGS | _ALL_VERSIONS | BESTMATCH | DEBUG | - ENHANCEMATCH | REVERSE) -SCOPED_FLAGS = FULLCASE | IGNORECASE | MULTILINE | DOTALL | WORD | VERBOSE - -ALPHA = frozenset(string.ascii_letters) -DIGITS = frozenset(string.digits) -ALNUM = ALPHA | DIGITS -OCT_DIGITS = frozenset(string.octdigits) -HEX_DIGITS = frozenset(string.hexdigits) -SPECIAL_CHARS = frozenset("()|?*+{^$.[\\#") | frozenset([""]) -NAMED_CHAR_PART = ALNUM | frozenset(" -") -PROPERTY_NAME_PART = ALNUM | frozenset(" &_-.") -SET_OPS = ("||", "~~", "&&", "--") - -# The width of the code words inside the regex engine. -BYTES_PER_CODE = _regex.get_code_size() -BITS_PER_CODE = BYTES_PER_CODE * 8 - -# The repeat count which represents infinity. -UNLIMITED = (1 << BITS_PER_CODE) - 1 - -# The regular expression flags. -REGEX_FLAGS = {"a": ASCII, "b": BESTMATCH, "e": ENHANCEMATCH, "f": FULLCASE, - "i": IGNORECASE, "L": LOCALE, "m": MULTILINE, "r": REVERSE, "s": DOTALL, "u": - UNICODE, "V0": VERSION0, "V1": VERSION1, "w": WORD, "x": VERBOSE} - -# The case flags. -CASE_FLAGS = FULLCASE | IGNORECASE -NOCASE = 0 -FULLIGNORECASE = FULLCASE | IGNORECASE - -FULL_CASE_FOLDING = UNICODE | FULLIGNORECASE - -# The number of digits in hexadecimal escapes. -HEX_ESCAPES = {"x": 2, "u": 4, "U": 8} - -# A singleton which indicates a comment within a pattern. -COMMENT = object() -FLAGS = object() - -# The names of the opcodes. -OPCODES = """ -FAILURE -SUCCESS -ANY -ANY_ALL -ANY_ALL_REV -ANY_REV -ANY_U -ANY_U_REV -ATOMIC -BOUNDARY -BRANCH -CALL_REF -CHARACTER -CHARACTER_IGN -CHARACTER_IGN_REV -CHARACTER_REV -DEFAULT_BOUNDARY -DEFAULT_END_OF_WORD -DEFAULT_START_OF_WORD -END -END_OF_LINE -END_OF_LINE_U -END_OF_STRING -END_OF_STRING_LINE -END_OF_STRING_LINE_U -END_OF_WORD -FUZZY -GRAPHEME_BOUNDARY -GREEDY_REPEAT -GROUP -GROUP_CALL -GROUP_EXISTS -LAZY_REPEAT -LOOKAROUND -NEXT -PROPERTY -PROPERTY_IGN -PROPERTY_IGN_REV -PROPERTY_REV -RANGE -RANGE_IGN -RANGE_IGN_REV -RANGE_REV -REF_GROUP -REF_GROUP_FLD -REF_GROUP_FLD_REV -REF_GROUP_IGN -REF_GROUP_IGN_REV -REF_GROUP_REV -SEARCH_ANCHOR -SET_DIFF -SET_DIFF_IGN -SET_DIFF_IGN_REV -SET_DIFF_REV -SET_INTER -SET_INTER_IGN -SET_INTER_IGN_REV -SET_INTER_REV -SET_SYM_DIFF -SET_SYM_DIFF_IGN -SET_SYM_DIFF_IGN_REV -SET_SYM_DIFF_REV -SET_UNION -SET_UNION_IGN -SET_UNION_IGN_REV -SET_UNION_REV -START_OF_LINE -START_OF_LINE_U -START_OF_STRING -START_OF_WORD -STRING -STRING_FLD -STRING_FLD_REV -STRING_IGN -STRING_IGN_REV -STRING_REV -STRING_SET -STRING_SET_FLD -STRING_SET_FLD_REV -STRING_SET_IGN -STRING_SET_IGN_REV -STRING_SET_REV -""" - -# Define the opcodes in a namespace. -class Namespace(object): - pass - -OP = Namespace() -for i, op in enumerate(OPCODES.split()): - setattr(OP, op, i) - -def _shrink_cache(cache_dict, args_dict, max_length, divisor=5): - """Make room in the given cache. - - Args: - cache_dict: The cache dictionary to modify. - args_dict: The dictionary of named list args used by patterns. - max_length: Maximum # of entries in cache_dict before it is shrunk. - divisor: Cache will shrink to max_length - 1/divisor*max_length items. - """ - # Toss out a fraction of the entries at random to make room for new ones. - # A random algorithm was chosen as opposed to simply cache_dict.popitem() - # as popitem could penalize the same regular expression repeatedly based - # on its internal hash value. Being random should spread the cache miss - # love around. - cache_keys = tuple(cache_dict.keys()) - overage = len(cache_keys) - max_length - if overage < 0: - # Cache is already within limits. Normally this should not happen - # but it could due to multithreading. - return - - number_to_toss = max_length // divisor + overage - - # The import is done here to avoid a circular dependency. - import random - if not hasattr(random, 'sample'): - # Do nothing while resolving the circular dependency: - # re->random->warnings->tokenize->string->re - return - - for doomed_key in random.sample(cache_keys, number_to_toss): - try: - del cache_dict[doomed_key] - except KeyError: - # Ignore problems if the cache changed from another thread. - pass - - # Rebuild the arguments dictionary. - args_dict.clear() - for pattern, pattern_type, flags, args, default_version in cache_dict: - args_dict[pattern, pattern_type, flags, default_version] = args - -def _fold_case(info, string): - "Folds the case of a string." - flags = info.flags - if (flags & _ALL_ENCODINGS) == 0: - flags |= info.guess_encoding - - return _regex.fold_case(flags, string) - -def is_cased(info, char): - "Checks whether a character is cased." - return len(_regex.get_all_cases(info.flags, char)) > 1 - -def _compile_firstset(info, fs): - "Compiles the firstset for the pattern." - if not fs or None in fs: - return [] - - # If we ignore the case, for simplicity we won't build a firstset. - members = set() - for i in fs: - if i.case_flags: - if isinstance(i, Character): - if is_cased(info, i.value): - return [] - elif isinstance(i, SetBase): - return [] - - members.add(i.with_flags(case_flags=NOCASE)) - - # Build the firstset. - fs = SetUnion(info, list(members), zerowidth=True) - fs = fs.optimise(info, in_set=True) - - # Compile the firstset. - return fs.compile(bool(info.flags & REVERSE)) - -def _flatten_code(code): - "Flattens the code from a list of tuples." - flat_code = [] - for c in code: - flat_code.extend(c) - - return flat_code - -def make_character(info, value, in_set=False): - "Makes a character literal." - if in_set: - # A character set is built case-sensitively. - return Character(value) - - return Character(value, case_flags=info.flags & CASE_FLAGS) - -def make_ref_group(info, name, position): - "Makes a group reference." - return RefGroup(info, name, position, case_flags=info.flags & CASE_FLAGS) - -def make_string_set(info, name): - "Makes a string set." - return StringSet(info, name, case_flags=info.flags & CASE_FLAGS) - -def make_property(info, prop, in_set): - "Makes a property." - if in_set: - return prop - - return prop.with_flags(case_flags=info.flags & CASE_FLAGS) - -def _parse_pattern(source, info): - "Parses a pattern, eg. 'a|b|c'." - branches = [parse_sequence(source, info)] - while source.match("|"): - branches.append(parse_sequence(source, info)) - - if len(branches) == 1: - return branches[0] - return Branch(branches) - -def parse_sequence(source, info): - "Parses a sequence, eg. 'abc'." - sequence = [] - applied = False - while True: - # Get literal characters followed by an element. - characters, case_flags, element = parse_literal_and_element(source, - info) - if not element: - # No element, just a literal. We've also reached the end of the - # sequence. - append_literal(characters, case_flags, sequence) - break - - if element is COMMENT or element is FLAGS: - append_literal(characters, case_flags, sequence) - elif type(element) is tuple: - # It looks like we've found a quantifier. - ch, saved_pos = element - - counts = parse_quantifier(source, info, ch) - if counts: - # It _is_ a quantifier. - apply_quantifier(source, info, counts, characters, case_flags, - ch, saved_pos, applied, sequence) - applied = True - else: - # It's not a quantifier. Maybe it's a fuzzy constraint. - constraints = parse_fuzzy(source, ch) - if constraints: - # It _is_ a fuzzy constraint. - apply_constraint(source, info, constraints, characters, - case_flags, saved_pos, applied, sequence) - applied = True - else: - # The element was just a literal. - characters.append(ord(ch)) - append_literal(characters, case_flags, sequence) - applied = False - else: - # We have a literal followed by something else. - append_literal(characters, case_flags, sequence) - sequence.append(element) - applied = False - - return make_sequence(sequence) - -def apply_quantifier(source, info, counts, characters, case_flags, ch, - saved_pos, applied, sequence): - if characters: - # The quantifier applies to the last character. - append_literal(characters[ : -1], case_flags, sequence) - element = Character(characters[-1], case_flags=case_flags) - else: - # The quantifier applies to the last item in the sequence. - if applied or not sequence: - raise error("nothing to repeat at position %d" % saved_pos) - - element = sequence.pop() - - min_count, max_count = counts - saved_pos = source.pos - ch = source.get() - if ch == "?": - # The "?" suffix that means it's a lazy repeat. - repeated = LazyRepeat - elif ch == "+": - # The "+" suffix that means it's a possessive repeat. - repeated = PossessiveRepeat - else: - # No suffix means that it's a greedy repeat. - source.pos = saved_pos - repeated = GreedyRepeat - - # Ignore the quantifier if it applies to a zero-width item or the number of - # repeats is fixed at 1. - if not element.is_empty() and (min_count != 1 or max_count != 1): - element = repeated(element, min_count, max_count) - - sequence.append(element) - -def apply_constraint(source, info, constraints, characters, case_flags, - saved_pos, applied, sequence): - if characters: - # The constraint applies to the last character. - append_literal(characters[ : -1], case_flags, sequence) - element = Character(characters[-1], case_flags=case_flags) - sequence.append(Fuzzy(element, constraints)) - else: - # The constraint applies to the last item in the sequence. - if applied or not sequence: - raise error("nothing for fuzzy constraint at position %d" % saved_pos) - - element = sequence.pop() - - # If a group is marked as fuzzy then put all of the fuzzy part in the - # group. - if isinstance(element, Group): - element.subpattern = Fuzzy(element.subpattern, constraints) - sequence.append(element) - else: - sequence.append(Fuzzy(element, constraints)) - -def append_literal(characters, case_flags, sequence): - if characters: - sequence.append(Literal(characters, case_flags=case_flags)) - -def PossessiveRepeat(element, min_count, max_count): - "Builds a possessive repeat." - return Atomic(GreedyRepeat(element, min_count, max_count)) - -_QUANTIFIERS = {"?": (0, 1), "*": (0, None), "+": (1, None)} - -def parse_quantifier(source, info, ch): - "Parses a quantifier." - q = _QUANTIFIERS.get(ch) - if q: - # It's a quantifier. - return q - - if ch == "{": - # Looks like a limited repeated element, eg. 'a{2,3}'. - counts = parse_limited_quantifier(source) - if counts: - return counts - - return None - -def is_above_limit(count): - "Checks whether a count is above the maximum." - return count is not None and count >= UNLIMITED - -def parse_limited_quantifier(source): - "Parses a limited quantifier." - saved_pos = source.pos - min_count = parse_count(source) - if source.match(","): - max_count = parse_count(source) - - # No minimum means 0 and no maximum means unlimited. - min_count = int(min_count or 0) - max_count = int(max_count) if max_count else None - - if max_count is not None and min_count > max_count: - raise error("min repeat greater than max repeat at position %d" % saved_pos) - else: - if not min_count: - source.pos = saved_pos - return None - - min_count = max_count = int(min_count) - - if is_above_limit(min_count) or is_above_limit(max_count): - raise error("repeat count too big at position %d" % saved_pos) - - if not source.match ("}"): - source.pos = saved_pos - return None - - return min_count, max_count - -def parse_fuzzy(source, ch): - "Parses a fuzzy setting, if present." - if ch != "{": - return None - - saved_pos = source.pos - - constraints = {} - try: - parse_fuzzy_item(source, constraints) - while source.match(","): - parse_fuzzy_item(source, constraints) - except ParseError: - source.pos = saved_pos - return None - - if not source.match("}"): - raise error("expected } at position %d" % source.pos) - - return constraints - -def parse_fuzzy_item(source, constraints): - "Parses a fuzzy setting item." - saved_pos = source.pos - try: - parse_cost_constraint(source, constraints) - except ParseError: - source.pos = saved_pos - - parse_cost_equation(source, constraints) - -def parse_cost_constraint(source, constraints): - "Parses a cost constraint." - saved_pos = source.pos - ch = source.get() - if ch in ALPHA: - # Syntax: constraint [("<=" | "<") cost] - constraint = parse_constraint(source, constraints, ch) - - max_inc = parse_fuzzy_compare(source) - - if max_inc is None: - # No maximum cost. - constraints[constraint] = 0, None - else: - # There's a maximum cost. - cost_pos = source.pos - max_cost = int(parse_count(source)) - - # Inclusive or exclusive limit? - if not max_inc: - max_cost -= 1 - - if max_cost < 0: - raise error("bad fuzzy cost limit at position %d" % cost_pos) - - constraints[constraint] = 0, max_cost - elif ch in DIGITS: - # Syntax: cost ("<=" | "<") constraint ("<=" | "<") cost - source.pos = saved_pos - try: - # Minimum cost. - min_cost = int(parse_count(source)) - - min_inc = parse_fuzzy_compare(source) - if min_inc is None: - raise ParseError() - - constraint = parse_constraint(source, constraints, source.get()) - - max_inc = parse_fuzzy_compare(source) - if max_inc is None: - raise ParseError() - - # Maximum cost. - cost_pos = source.pos - max_cost = int(parse_count(source)) - - # Inclusive or exclusive limits? - if not min_inc: - min_cost += 1 - if not max_inc: - max_cost -= 1 - - if not 0 <= min_cost <= max_cost: - raise error("bad fuzzy cost limit at position %d" % cost_pos) - - constraints[constraint] = min_cost, max_cost - except ValueError: - raise ParseError() - else: - raise ParseError() - -def parse_constraint(source, constraints, ch): - "Parses a constraint." - if ch not in "deis": - raise error("bad fuzzy constraint at position %d" % source.pos) - - if ch in constraints: - raise error("repeated fuzzy constraint at position %d" % source.pos) - - return ch - -def parse_fuzzy_compare(source): - "Parses a cost comparator." - if source.match("<="): - return True - elif source.match("<"): - return False - else: - return None - -def parse_cost_equation(source, constraints): - "Parses a cost equation." - if "cost" in constraints: - raise error("more than one cost equation at position %d" % source.pos) - - cost = {} - - parse_cost_term(source, cost) - while source.match("+"): - parse_cost_term(source, cost) - - max_inc = parse_fuzzy_compare(source) - if max_inc is None: - raise error("missing fuzzy cost limit at position %d" % source.pos) - - max_cost = int(parse_count(source)) - - if not max_inc: - max_cost -= 1 - - if max_cost < 0: - raise error("bad fuzzy cost limit at position %d" % source.pos) - - cost["max"] = max_cost - - constraints["cost"] = cost - -def parse_cost_term(source, cost): - "Parses a cost equation term." - coeff = parse_count(source) - ch = source.get() - if ch not in "dis": - raise ParseError() - - if ch in cost: - raise error("repeated fuzzy cost at position %d" % source.pos) - - cost[ch] = int(coeff or 1) - -def parse_count(source): - "Parses a quantifier's count, which can be empty." - return source.get_while(DIGITS) - -def parse_literal_and_element(source, info): - """Parses a literal followed by an element. The element is FLAGS if it's an - inline flag or None if it has reached the end of a sequence. - """ - characters = [] - case_flags = info.flags & CASE_FLAGS - while True: - saved_pos = source.pos - ch = source.get() - if ch in SPECIAL_CHARS: - if ch in ")|": - # The end of a sequence. At the end of the pattern ch is "". - source.pos = saved_pos - return characters, case_flags, None - elif ch == "\\": - # An escape sequence outside a set. - element = parse_escape(source, info, False) - return characters, case_flags, element - elif ch == "(": - # A parenthesised subpattern or a flag. - element = parse_paren(source, info) - if element and element is not COMMENT: - return characters, case_flags, element - elif ch == ".": - # Any character. - if info.flags & DOTALL: - element = AnyAll() - elif info.flags & WORD: - element = AnyU() - else: - element = Any() - - return characters, case_flags, element - elif ch == "[": - # A character set. - element = parse_set(source, info) - return characters, case_flags, element - elif ch == "^": - # The start of a line or the string. - if info.flags & MULTILINE: - if info.flags & WORD: - element = StartOfLineU() - else: - element = StartOfLine() - else: - element = StartOfString() - - return characters, case_flags, element - elif ch == "$": - # The end of a line or the string. - if info.flags & MULTILINE: - if info.flags & WORD: - element = EndOfLineU() - else: - element = EndOfLine() - else: - if info.flags & WORD: - element = EndOfStringLineU() - else: - element = EndOfStringLine() - - return characters, case_flags, element - elif ch in "?*+{": - # Looks like a quantifier. - return characters, case_flags, (ch, saved_pos) - else: - # A literal. - characters.append(ord(ch)) - else: - # A literal. - characters.append(ord(ch)) - -def parse_paren(source, info): - """Parses a parenthesised subpattern or a flag. Returns FLAGS if it's an - inline flag. - """ - saved_pos = source.pos - ch = source.get() - if ch == "?": - # (?... - saved_pos_2 = source.pos - ch = source.get() - if ch == "<": - # (?<... - saved_pos_3 = source.pos - ch = source.get() - if ch in ("=", "!"): - # (?<=... or (?") - saved_flags = info.flags - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - info.close_group() - return Group(info, group, subpattern) - if ch in ("=", "!"): - # (?=... or (?!...: lookahead. - return parse_lookaround(source, info, False, ch == "=") - if ch == "P": - # (?P...: a Python extension. - return parse_extension(source, info) - if ch == "#": - # (?#...: a comment. - return parse_comment(source) - if ch == "(": - # (?(...: a conditional subpattern. - return parse_conditional(source, info) - if ch == ">": - # (?>...: an atomic subpattern. - return parse_atomic(source, info) - if ch == "|": - # (?|...: a common/reset groups branch. - return parse_common(source, info) - if ch == "R" or "0" <= ch <= "9": - # (?R...: probably a call to a group. - return parse_call_group(source, info, ch, saved_pos_2) - if ch == "&": - # (?&...: a call to a named group. - return parse_call_named_group(source, info, saved_pos_2) - - # (?...: probably a flags subpattern. - source.pos = saved_pos_2 - return parse_flags_subpattern(source, info) - - # (...: an unnamed capture group. - source.pos = saved_pos - group = info.open_group() - saved_flags = info.flags - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - info.close_group() - - return Group(info, group, subpattern) - -def parse_extension(source, info): - "Parses a Python extension." - saved_pos = source.pos - ch = source.get() - if ch == "<": - # (?P<...: a named capture group. - name = parse_name(source) - group = info.open_group(name) - source.expect(">") - saved_flags = info.flags - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - info.close_group() - - return Group(info, group, subpattern) - if ch == "=": - # (?P=...: a named group reference. - name = parse_name(source) - source.expect(")") - if info.is_open_group(name): - raise error("can't refer to an open group at position %d" % saved_pos) - - return make_ref_group(info, name, saved_pos) - if ch == ">" or ch == "&": - # (?P>...: a call to a group. - return parse_call_named_group(source, info, saved_pos) - - source.pos = saved_pos - raise error("unknown extension at position %d" % saved_pos) - -def parse_comment(source): - "Parses a comment." - source.skip_while(set(")"), include=False) - source.expect(")") - - return COMMENT - -def parse_lookaround(source, info, behind, positive): - "Parses a lookaround." - saved_flags = info.flags - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - return LookAround(behind, positive, subpattern) - -def parse_conditional(source, info): - "Parses a conditional subpattern." - saved_flags = info.flags - saved_pos = source.pos - try: - group = parse_name(source, True) - source.expect(")") - yes_branch = parse_sequence(source, info) - if source.match("|"): - no_branch = parse_sequence(source, info) - else: - no_branch = Sequence() - - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - if yes_branch.is_empty() and no_branch.is_empty(): - return Sequence() - - return Conditional(info, group, yes_branch, no_branch, saved_pos) - -def parse_atomic(source, info): - "Parses an atomic subpattern." - saved_flags = info.flags - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - return Atomic(subpattern) - -def parse_common(source, info): - "Parses a common groups branch." - # Capture group numbers in different branches can reuse the group numbers. - initial_group_count = info.group_count - branches = [parse_sequence(source, info)] - final_group_count = info.group_count - while source.match("|"): - info.group_count = initial_group_count - branches.append(parse_sequence(source, info)) - final_group_count = max(final_group_count, info.group_count) - - info.group_count = final_group_count - source.expect(")") - - if len(branches) == 1: - return branches[0] - return Branch(branches) - -def parse_call_group(source, info, ch, pos): - "Parses a call to a group." - if ch == "R": - group = "0" - else: - group = ch + source.get_while(DIGITS) - - source.expect(")") - - return CallGroup(info, group, pos) - -def parse_call_named_group(source, info, pos): - "Parses a call to a named group." - group = parse_name(source) - source.expect(")") - - return CallGroup(info, group, pos) - -def parse_flag_set(source): - "Parses a set of inline flags." - flags = 0 - - try: - while True: - saved_pos = source.pos - ch = source.get() - if ch == "V": - ch += source.get() - flags |= REGEX_FLAGS[ch] - except KeyError: - source.pos = saved_pos - - return flags - -def parse_flags(source, info): - "Parses flags being turned on/off." - flags_on = parse_flag_set(source) - if source.match("-"): - flags_off = parse_flag_set(source) - if not flags_off: - raise error("bad inline flags: no flags after '-' at position %d" % source.pos) - else: - flags_off = 0 - - return flags_on, flags_off - -def parse_subpattern(source, info, flags_on, flags_off): - "Parses a subpattern with scoped flags." - saved_flags = info.flags - info.flags = (info.flags | flags_on) & ~flags_off - source.ignore_space = bool(info.flags & VERBOSE) - try: - subpattern = _parse_pattern(source, info) - source.expect(")") - finally: - info.flags = saved_flags - source.ignore_space = bool(info.flags & VERBOSE) - - return subpattern - -def parse_flags_subpattern(source, info): - """Parses a flags subpattern. It could be inline flags or a subpattern - possibly with local flags. If it's a subpattern, then that's returned; - if it's a inline flags, then FLAGS is returned. - """ - flags_on, flags_off = parse_flags(source, info) - - if flags_off & GLOBAL_FLAGS: - raise error("bad inline flags: can't turn off global flag at position %d" % source.pos) - - if flags_on & flags_off: - raise error("bad inline flags: flag turned on and off at position %d" % source.pos) - - # Handle flags which are global in all regex behaviours. - new_global_flags = (flags_on & ~info.global_flags) & GLOBAL_FLAGS - if new_global_flags: - info.global_flags |= new_global_flags - - # A global has been turned on, so reparse the pattern. - raise _UnscopedFlagSet(info.global_flags) - - # Ensure that from now on we have only scoped flags. - flags_on &= ~GLOBAL_FLAGS - - if source.match(":"): - return parse_subpattern(source, info, flags_on, flags_off) - - if source.match(")"): - parse_positional_flags(source, info, flags_on, flags_off) - return FLAGS - - raise error("unknown extension at position %d" % source.pos) - -def parse_positional_flags(source, info, flags_on, flags_off): - "Parses positional flags." - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - if version == VERSION0: - # Positional flags are global and can only be turned on. - if flags_off: - raise error("bad inline flags: can't turn flags off at position %d" % source.pos) - - new_global_flags = flags_on & ~info.global_flags - if new_global_flags: - info.global_flags |= new_global_flags - - # A global has been turned on, so reparse the pattern. - raise _UnscopedFlagSet(info.global_flags) - else: - info.flags = (info.flags | flags_on) & ~flags_off - - source.ignore_space = bool(info.flags & VERBOSE) - -def parse_name(source, allow_numeric=False): - "Parses a name." - name = source.get_while(set(")>"), include=False) - - if not name: - raise error("bad group name at position %d" % source.pos) - - if name.isdigit(): - if not allow_numeric: - raise error("bad group name at position %d" % source.pos) - else: - if not is_identifier(name): - raise error("bad group name at position %d" % source.pos) - - return name - -def is_identifier(name): - if not name: - return False - - if name[0] not in ALPHA and name[0] != "_": - return False - - name = name.replace("_", "") - - return not name or all(c in ALNUM for c in name) - -def is_octal(string): - "Checks whether a string is octal." - return all(ch in OCT_DIGITS for ch in string) - -def is_decimal(string): - "Checks whether a string is decimal." - return all(ch in DIGITS for ch in string) - -def is_hexadecimal(string): - "Checks whether a string is hexadecimal." - return all(ch in HEX_DIGITS for ch in string) - -def parse_escape(source, info, in_set): - "Parses an escape sequence." - saved_ignore = source.ignore_space - source.ignore_space = False - ch = source.get() - source.ignore_space = saved_ignore - if not ch: - # A backslash at the end of the pattern. - raise error("bad escape at position %d" % source.pos) - if ch in HEX_ESCAPES: - # A hexadecimal escape sequence. - return parse_hex_escape(source, info, HEX_ESCAPES[ch], in_set) - elif ch == "g" and not in_set: - # A group reference. - saved_pos = source.pos - try: - return parse_group_ref(source, info) - except error: - # Invalid as a group reference, so assume it's a literal. - source.pos = saved_pos - - return make_character(info, ord(ch), in_set) - elif ch == "G" and not in_set: - # A search anchor. - return SearchAnchor() - elif ch == "L" and not in_set: - # A string set. - return parse_string_set(source, info) - elif ch == "N": - # A named codepoint. - return parse_named_char(source, info, in_set) - elif ch in "pP": - # A Unicode property, positive or negative. - return parse_property(source, info, ch == "p", in_set) - elif ch == "X" and not in_set: - # A grapheme cluster. - return Grapheme() - elif ch in ALPHA: - # An alphabetic escape sequence. - # Positional escapes aren't allowed inside a character set. - if not in_set: - if info.flags & WORD: - value = WORD_POSITION_ESCAPES.get(ch) - else: - value = POSITION_ESCAPES.get(ch) - - if value: - return value - - value = CHARSET_ESCAPES.get(ch) - if value: - return value - - value = CHARACTER_ESCAPES.get(ch) - if value: - return Character(ord(value)) - - return make_character(info, ord(ch), in_set) - elif ch in DIGITS: - # A numeric escape sequence. - return parse_numeric_escape(source, info, ch, in_set) - else: - # A literal. - return make_character(info, ord(ch), in_set) - -def parse_numeric_escape(source, info, ch, in_set): - "Parses a numeric escape sequence." - if in_set or ch == "0": - # Octal escape sequence, max 3 digits. - return parse_octal_escape(source, info, [ch], in_set) - - # At least 1 digit, so either octal escape or group. - digits = ch - saved_pos = source.pos - ch = source.get() - if ch in DIGITS: - # At least 2 digits, so either octal escape or group. - digits += ch - saved_pos = source.pos - ch = source.get() - if is_octal(digits) and ch in OCT_DIGITS: - # 3 octal digits, so octal escape sequence. - encoding = info.flags & _ALL_ENCODINGS - if encoding == ASCII or encoding == LOCALE: - octal_mask = 0xFF - else: - octal_mask = 0x1FF - - value = int(digits + ch, 8) & octal_mask - return make_character(info, value) - - # Group reference. - source.pos = saved_pos - if info.is_open_group(digits): - raise error("can't refer to an open group at position %d" % source.pos) - - return make_ref_group(info, digits, source.pos) - -def parse_octal_escape(source, info, digits, in_set): - "Parses an octal escape sequence." - saved_pos = source.pos - ch = source.get() - while len(digits) < 3 and ch in OCT_DIGITS: - digits.append(ch) - saved_pos = source.pos - ch = source.get() - - source.pos = saved_pos - try: - value = int("".join(digits), 8) - return make_character(info, value, in_set) - except ValueError: - raise error("bad octal escape at position %d" % source.pos) - -def parse_hex_escape(source, info, expected_len, in_set): - "Parses a hex escape sequence." - digits = [] - for i in range(expected_len): - ch = source.get() - if ch not in HEX_DIGITS: - raise error("bad hex escape at position %d" % source.pos) - digits.append(ch) - - value = int("".join(digits), 16) - return make_character(info, value, in_set) - -def parse_group_ref(source, info): - "Parses a group reference." - source.expect("<") - saved_pos = source.pos - name = parse_name(source, True) - source.expect(">") - if info.is_open_group(name): - raise error("can't refer to an open group at position %d" % source.pos) - - return make_ref_group(info, name, saved_pos) - -def parse_string_set(source, info): - "Parses a string set reference." - source.expect("<") - name = parse_name(source, True) - source.expect(">") - if name is None or name not in info.kwargs: - raise error("undefined named list at position %d" % source.pos) - - return make_string_set(info, name) - -def parse_named_char(source, info, in_set): - "Parses a named character." - saved_pos = source.pos - if source.match("{"): - name = source.get_while(NAMED_CHAR_PART) - if source.match("}"): - try: - value = unicodedata.lookup(name) - return make_character(info, ord(value), in_set) - except KeyError: - raise error("undefined character name at position %d" % source.pos) - - source.pos = saved_pos - return make_character(info, ord("N"), in_set) - -def parse_property(source, info, positive, in_set): - "Parses a Unicode property." - saved_pos = source.pos - ch = source.get() - if ch == "{": - negate = source.match("^") - prop_name, name = parse_property_name(source) - if source.match("}"): - # It's correctly delimited. - prop = lookup_property(prop_name, name, positive != negate, source_pos=source.pos) - return make_property(info, prop, in_set) - elif ch and ch in "CLMNPSZ": - # An abbreviated property, eg \pL. - prop = lookup_property(None, ch, positive) - return make_property(info, prop, in_set, source_pos=source.pos) - - # Not a property, so treat as a literal "p" or "P". - source.pos = saved_pos - ch = "p" if positive else "P" - return make_character(info, ord(ch), in_set) - -def parse_property_name(source): - "Parses a property name, which may be qualified." - name = source.get_while(PROPERTY_NAME_PART) - saved_pos = source.pos - - ch = source.get() - if ch and ch in ":=": - prop_name = name - name = source.get_while(ALNUM | set(" &_-./")).strip() - - if name: - # Name after the ":" or "=", so it's a qualified name. - saved_pos = source.pos - else: - # No name after the ":" or "=", so assume it's an unqualified name. - prop_name, name = None, prop_name - else: - prop_name = None - - source.pos = saved_pos - return prop_name, name - -def parse_set(source, info): - "Parses a character set." - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - - saved_ignore = source.ignore_space - source.ignore_space = False - # Negative set? - negate = source.match("^") - try: - if version == VERSION0: - item = parse_set_imp_union(source, info) - else: - item = parse_set_union(source, info) - - if not source.match("]"): - raise error("missing ] at position %d" % source.pos) - finally: - source.ignore_space = saved_ignore - - if negate: - item = item.with_flags(positive=not item.positive) - - item = item.with_flags(case_flags=info.flags & CASE_FLAGS) - - return item - -def parse_set_union(source, info): - "Parses a set union ([x||y])." - items = [parse_set_symm_diff(source, info)] - while source.match("||"): - items.append(parse_set_symm_diff(source, info)) - - if len(items) == 1: - return items[0] - return SetUnion(info, items) - -def parse_set_symm_diff(source, info): - "Parses a set symmetric difference ([x~~y])." - items = [parse_set_inter(source, info)] - while source.match("~~"): - items.append(parse_set_inter(source, info)) - - if len(items) == 1: - return items[0] - return SetSymDiff(info, items) - -def parse_set_inter(source, info): - "Parses a set intersection ([x&&y])." - items = [parse_set_diff(source, info)] - while source.match("&&"): - items.append(parse_set_diff(source, info)) - - if len(items) == 1: - return items[0] - return SetInter(info, items) - -def parse_set_diff(source, info): - "Parses a set difference ([x--y])." - items = [parse_set_imp_union(source, info)] - while source.match("--"): - items.append(parse_set_imp_union(source, info)) - - if len(items) == 1: - return items[0] - return SetDiff(info, items) - -def parse_set_imp_union(source, info): - "Parses a set implicit union ([xy])." - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - - items = [parse_set_member(source, info)] - while True: - saved_pos = source.pos - if source.match("]"): - # End of the set. - source.pos = saved_pos - break - - if version == VERSION1 and any(source.match(op) for op in SET_OPS): - # The new behaviour has set operators. - source.pos = saved_pos - break - - items.append(parse_set_member(source, info)) - - if len(items) == 1: - return items[0] - return SetUnion(info, items) - -def parse_set_member(source, info): - "Parses a member in a character set." - # Parse a set item. - start = parse_set_item(source, info) - if (not isinstance(start, Character) or not start.positive or not - source.match("-")): - # It's not the start of a range. - return start - - # It looks like the start of a range of characters. - saved_pos = source.pos - if source.match("]"): - # We've reached the end of the set, so return both the character and - # hyphen. - source.pos = saved_pos - return SetUnion(info, [start, Character(ord("-"))]) - - # Parse a set item. - end = parse_set_item(source, info) - if not isinstance(end, Character) or not end.positive: - # It's not a range, so return the character, hyphen and property. - return SetUnion(info, [start, Character(ord("-")), end]) - - # It _is_ a range. - if start.value > end.value: - raise error("bad character range at position %d" % source.pos) - - if start.value == end.value: - return start - - return Range(start.value, end.value) - -def parse_set_item(source, info): - "Parses an item in a character set." - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - - if source.match("\\"): - # An escape sequence in a set. - return parse_escape(source, info, True) - - saved_pos = source.pos - if source.match("[:"): - # Looks like a POSIX character class. - try: - return parse_posix_class(source, info) - except ParseError: - # Not a POSIX character class. - source.pos = saved_pos - - if version == VERSION1 and source.match("["): - # It's the start of a nested set. - - # Negative set? - negate = source.match("^") - item = parse_set_union(source, info) - - if not source.match("]"): - raise error("missing ] at position %d" % source.pos) - - if negate: - item = item.with_flags(positive=not item.positive) - - return item - - ch = source.get() - if not ch: - raise error("bad set at position %d" % source.pos, True) - - return Character(ord(ch)) - -def parse_posix_class(source, info): - "Parses a POSIX character class." - negate = source.match("^") - prop_name, name = parse_property_name(source) - if not source.match(":]"): - raise ParseError() - - return lookup_property(prop_name, name, positive=not negate, source_pos=source.pos) - -def float_to_rational(flt): - "Converts a float to a rational pair." - int_part = int(flt) - error = flt - int_part - if abs(error) < 0.0001: - return int_part, 1 - - den, num = float_to_rational(1.0 / error) - - return int_part * den + num, den - -def numeric_to_rational(numeric): - "Converts a numeric string to a rational string, if possible." - if numeric[0] == "-": - sign, numeric = numeric[0], numeric[1 : ] - else: - sign = "" - - parts = numeric.split("/") - if len(parts) == 2: - num, den = float_to_rational(float(parts[0]) / float(parts[1])) - elif len(parts) == 1: - num, den = float_to_rational(float(parts[0])) - else: - raise ValueError() - - result = "%s%s/%s" % (sign, num, den) - if result.endswith("/1"): - return result[ : -2] - - return result - -def standardise_name(name): - "Standardises a property or value name." - try: - return numeric_to_rational("".join(name)) - except (ValueError, ZeroDivisionError): - return "".join(ch for ch in name if ch not in "_- ").upper() - -def lookup_property(property, value, positive, source_pos=None): - "Looks up a property." - # Normalise the names (which may still be lists). - property = standardise_name(property) if property else None - value = standardise_name(value) - - if (property, value) == ("GENERALCATEGORY", "ASSIGNED"): - property, value, positive = "GENERALCATEGORY", "UNASSIGNED", not positive - - if property: - # Both the property and the value are provided. - prop = PROPERTIES.get(property) - if not prop: - raise error("unknown property at position %d" % source_pos) - - prop_id, value_dict = prop - val_id = value_dict.get(value) - if val_id is None: - raise error("unknown property value at position %d" % source_pos) - - if "YES" in value_dict and val_id == 0: - positive, val_id = not positive, 1 - - return Property((prop_id << 16) | val_id, positive) - - # Only the value is provided. - # It might be the name of a GC, script or block value. - for property in ("GC", "SCRIPT", "BLOCK"): - prop_id, value_dict = PROPERTIES.get(property) - val_id = value_dict.get(value) - if val_id is not None: - return Property((prop_id << 16) | val_id, positive) - - # It might be the name of a binary property. - prop = PROPERTIES.get(value) - if prop: - prop_id, value_dict = prop - - if "YES" in value_dict: - return Property((prop_id << 16) | 1, positive) - - # It might be the name of a binary property starting with a prefix. - if value.startswith("IS"): - prop = PROPERTIES.get(value[2 : ]) - if prop: - prop_id, value_dict = prop - if "YES" in value_dict: - return Property((prop_id << 16) | 1, positive) - - # It might be the name of a script or block starting with a prefix. - for prefix, property in (("IS", "SCRIPT"), ("IN", "BLOCK")): - if value.startswith(prefix): - prop_id, value_dict = PROPERTIES.get(property) - val_id = value_dict.get(value[2 : ]) - if val_id is not None: - return Property((prop_id << 16) | val_id, positive) - - # Unknown property. - raise error("unknown property at position %d" % source_pos) - -def _compile_replacement(source, pattern, is_unicode): - "Compiles a replacement template escape sequence." - ch = source.get() - if ch in ALPHA: - # An alphabetic escape sequence. - value = CHARACTER_ESCAPES.get(ch) - if value: - return False, [ord(value)] - - if ch in HEX_ESCAPES and (ch == "x" or is_unicode): - # A hexadecimal escape sequence. - return False, [parse_repl_hex_escape(source, HEX_ESCAPES[ch])] - - if ch == "g": - # A group preference. - return True, [compile_repl_group(source, pattern)] - - if ch == "N" and is_unicode: - # A named character. - value = parse_repl_named_char(source) - if value is not None: - return False, [value] - - return False, [ord("\\"), ord(ch)] - - if isinstance(source.sep, str): - octal_mask = 0xFF - else: - octal_mask = 0x1FF - - if ch == "0": - # An octal escape sequence. - digits = ch - while len(digits) < 3: - saved_pos = source.pos - ch = source.get() - if ch not in OCT_DIGITS: - source.pos = saved_pos - break - digits += ch - - return False, [int(digits, 8) & octal_mask] - - if ch in DIGITS: - # Either an octal escape sequence (3 digits) or a group reference (max - # 2 digits). - digits = ch - saved_pos = source.pos - ch = source.get() - if ch in DIGITS: - digits += ch - saved_pos = source.pos - ch = source.get() - if ch and is_octal(digits + ch): - # An octal escape sequence. - return False, [int(digits + ch, 8) & octal_mask] - - # A group reference. - source.pos = saved_pos - return True, [int(digits)] - - if ch == "\\": - # An escaped backslash is a backslash. - return False, [ord("\\")] - - if not ch: - # A trailing backslash. - raise error("bad escape at position %d" % source.pos) - - # An escaped non-backslash is a backslash followed by the literal. - return False, [ord("\\"), ord(ch)] - -def parse_repl_hex_escape(source, expected_len): - "Parses a hex escape sequence in a replacement string." - digits = [] - for i in range(expected_len): - ch = source.get() - if ch not in HEX_DIGITS: - raise error("bad hex escape at position %d" % source.pos) - digits.append(ch) - - return int("".join(digits), 16) - -def parse_repl_named_char(source): - "Parses a named character in a replacement string." - saved_pos = source.pos - if source.match("{"): - name = source.get_while(ALPHA | set(" ")) - - if source.match("}"): - try: - value = unicodedata.lookup(name) - return ord(value) - except KeyError: - raise error("undefined character name at position %d" % source.pos) - - source.pos = saved_pos - return None - -def compile_repl_group(source, pattern): - "Compiles a replacement template group reference." - source.expect("<") - name = parse_name(source, True) - - source.expect(">") - if name.isdigit(): - index = int(name) - if not 0 <= index <= pattern.groups: - raise error("invalid group at position %d" % source.pos) - - return index - - try: - return pattern.groupindex[name] - except KeyError: - raise IndexError("unknown group") - -# The regular expression is parsed into a syntax tree. The different types of -# node are defined below. - -INDENT = " " -POSITIVE_OP = 0x1 -ZEROWIDTH_OP = 0x2 -FUZZY_OP = 0x4 -REVERSE_OP = 0x8 -REQUIRED_OP = 0x10 - -POS_TEXT = {False: "NON-MATCH", True: "MATCH"} -CASE_TEXT = {NOCASE: "", IGNORECASE: " SIMPLE_IGNORE_CASE", FULLCASE: "", - FULLIGNORECASE: " FULL_IGNORE_CASE"} - -def make_sequence(items): - if len(items) == 1: - return items[0] - return Sequence(items) - -# Common base class for all nodes. -class RegexBase(object): - def __init__(self): - self._key = self.__class__ - - def with_flags(self, positive=None, case_flags=None, zerowidth=None): - if positive is None: - positive = self.positive - else: - positive = bool(positive) - if case_flags is None: - case_flags = self.case_flags - else: - case_flags = case_flags & CASE_FLAGS - if zerowidth is None: - zerowidth = self.zerowidth - else: - zerowidth = bool(zerowidth) - - if (positive == self.positive and case_flags == self.case_flags and - zerowidth == self.zerowidth): - return self - - return self.rebuild(positive, case_flags, zerowidth) - - def fix_groups(self, reverse, fuzzy): - pass - - def optimise(self, info): - return self - - def pack_characters(self, info): - return self - - def remove_captures(self): - return self - - def is_atomic(self): - return True - - def can_be_affix(self): - return True - - def contains_group(self): - return False - - def get_firstset(self, reverse): - raise _FirstSetError() - - def has_simple_start(self): - return False - - def compile(self, reverse=False, fuzzy=False): - return self._compile(reverse, fuzzy) - - def dump(self, indent, reverse): - self._dump(indent, reverse) - - def is_empty(self): - return False - - def __hash__(self): - return hash(self._key) - - def __eq__(self, other): - return type(self) is type(other) and self._key == other._key - - def __ne__(self, other): - return not self.__eq__(other) - - def get_required_string(self, reverse): - return self.max_width(), None - -# Base class for zero-width nodes. -class ZeroWidthBase(RegexBase): - def __init__(self, positive=True): - RegexBase.__init__(self) - self.positive = bool(positive) - - self._key = self.__class__, self.positive - - def get_firstset(self, reverse): - return set([None]) - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if fuzzy: - flags |= FUZZY_OP - if reverse: - flags |= REVERSE_OP - return [(self._opcode, flags)] - - def _dump(self, indent, reverse): - print "%s%s %s" % (INDENT * indent, self._op_name, - POS_TEXT[self.positive]) - - def max_width(self): - return 0 - -class Any(RegexBase): - _opcode = {False: OP.ANY, True: OP.ANY_REV} - _op_name = "ANY" - - def has_simple_start(self): - return True - - def _compile(self, reverse, fuzzy): - flags = 0 - if fuzzy: - flags |= FUZZY_OP - return [(self._opcode[reverse], flags)] - - def _dump(self, indent, reverse): - print "%s%s" % (INDENT * indent, self._op_name) - - def max_width(self): - return 1 - -class AnyAll(Any): - _opcode = {False: OP.ANY_ALL, True: OP.ANY_ALL_REV} - _op_name = "ANY_ALL" - -class AnyU(Any): - _opcode = {False: OP.ANY_U, True: OP.ANY_U_REV} - _op_name = "ANY_U" - -class Atomic(RegexBase): - def __init__(self, subpattern): - RegexBase.__init__(self) - self.subpattern = subpattern - - def fix_groups(self, reverse, fuzzy): - self.subpattern.fix_groups(reverse, fuzzy) - - def optimise(self, info): - self.subpattern = self.subpattern.optimise(info) - - if self.subpattern.is_empty(): - return self.subpattern - return self - - def pack_characters(self, info): - self.subpattern = self.subpattern.pack_characters(info) - return self - - def remove_captures(self): - self.subpattern = self.subpattern.remove_captures() - return self - - def can_be_affix(self): - return self.subpattern.can_be_affix() - - def contains_group(self): - return self.subpattern.contains_group() - - def get_firstset(self, reverse): - return self.subpattern.get_firstset(reverse) - - def has_simple_start(self): - return self.subpattern.has_simple_start() - - def _compile(self, reverse, fuzzy): - return ([(OP.ATOMIC, )] + self.subpattern.compile(reverse, fuzzy) + - [(OP.END, )]) - - def _dump(self, indent, reverse): - print "%sATOMIC" % (INDENT * indent) - self.subpattern.dump(indent + 1, reverse) - - def is_empty(self): - return self.subpattern.is_empty() - - def __eq__(self, other): - return (type(self) is type(other) and self.subpattern == - other.subpattern) - - def max_width(self): - return self.subpattern.max_width() - - def get_required_string(self, reverse): - return self.subpattern.get_required_string(reverse) - -class Boundary(ZeroWidthBase): - _opcode = OP.BOUNDARY - _op_name = "BOUNDARY" - -class Branch(RegexBase): - def __init__(self, branches): - RegexBase.__init__(self) - self.branches = branches - - def fix_groups(self, reverse, fuzzy): - for b in self.branches: - b.fix_groups(reverse, fuzzy) - - def optimise(self, info): - # Flatten branches within branches. - branches = Branch._flatten_branches(info, self.branches) - - # Move any common prefix or suffix out of the branches. - prefix, branches = Branch._split_common_prefix(info, branches) - suffix, branches = Branch._split_common_suffix(info, branches) - - # Merge branches starting with the same character. (If a character - # prefix doesn't match in one branch, it won't match in any of the - # others starting with that same character.) - branches = Branch._merge_common_prefixes(info, branches) - - # Try to reduce adjacent single-character branches to sets. - branches = Branch._reduce_to_set(info, branches) - - if len(branches) > 1: - sequence = prefix + [Branch(branches)] + suffix - else: - sequence = prefix + branches + suffix - - return make_sequence(sequence) - - def optimise(self, info): - # Flatten branches within branches. - branches = Branch._flatten_branches(info, self.branches) - - # Try to reduce adjacent single-character branches to sets. - branches = Branch._reduce_to_set(info, branches) - - if len(branches) > 1: - sequence = [Branch(branches)] - else: - sequence = branches - - return make_sequence(sequence) - - def pack_characters(self, info): - self.branches = [b.pack_characters(info) for b in self.branches] - return self - - def remove_captures(self): - self.branches = [b.remove_captures() for b in self.branches] - return self - - def is_atomic(self): - return all(b.is_atomic() for b in self.branches) - - def can_be_affix(self): - return all(b.can_be_affix() for b in self.branches) - - def contains_group(self): - return any(b.contains_group() for b in self.branches) - - def get_firstset(self, reverse): - fs = set() - for b in self.branches: - fs |= b.get_firstset(reverse) - - return fs or set([None]) - - def _compile(self, reverse, fuzzy): - code = [(OP.BRANCH, )] - for b in self.branches: - code.extend(b.compile(reverse, fuzzy)) - code.append((OP.NEXT, )) - - code[-1] = (OP.END, ) - - return code - - def _dump(self, indent, reverse): - print "%sBRANCH" % (INDENT * indent) - self.branches[0].dump(indent + 1, reverse) - for b in self.branches[1 : ]: - print "%sOR" % (INDENT * indent) - b.dump(indent + 1, reverse) - - @staticmethod - def _flatten_branches(info, branches): - # Flatten the branches so that there aren't branches of branches. - new_branches = [] - for b in branches: - b = b.optimise(info) - if isinstance(b, Branch): - new_branches.extend(b.branches) - else: - new_branches.append(b) - - return new_branches - - @staticmethod - def _split_common_prefix(info, branches): - # Common leading items can be moved out of the branches. - # Get the items in the branches. - alternatives = [] - for b in branches: - if isinstance(b, Sequence): - alternatives.append(b.items) - else: - alternatives.append([b]) - - # What is the maximum possible length of the prefix? - max_count = min(len(a) for a in alternatives) - - # What is the longest common prefix? - prefix = alternatives[0] - pos = 0 - end_pos = max_count - while pos < end_pos and prefix[pos].can_be_affix() and all(a[pos] == - prefix[pos] for a in alternatives): - pos += 1 - count = pos - - if info.flags & UNICODE: - # We need to check that we're not splitting a sequence of - # characters which could form part of full case-folding. - count = pos - while count > 0 and not all(Branch._can_split(a, count) for a in - alternatives): - count -= 1 - - # No common prefix is possible. - if count == 0: - return [], branches - - # Rebuild the branches. - new_branches = [] - for a in alternatives: - new_branches.append(make_sequence(a[count : ])) - - return prefix[ : count], new_branches - - @staticmethod - def _split_common_suffix(info, branches): - # Common trailing items can be moved out of the branches. - # Get the items in the branches. - alternatives = [] - for b in branches: - if isinstance(b, Sequence): - alternatives.append(b.items) - else: - alternatives.append([b]) - - # What is the maximum possible length of the suffix? - max_count = min(len(a) for a in alternatives) - - # What is the longest common suffix? - suffix = alternatives[0] - pos = -1 - end_pos = -1 - max_count - while pos > end_pos and suffix[pos].can_be_affix() and all(a[pos] == - suffix[pos] for a in alternatives): - pos -= 1 - count = -1 - pos - - if info.flags & UNICODE: - # We need to check that we're not splitting a sequence of - # characters which could form part of full case-folding. - while count > 0 and not all(Branch._can_split_rev(a, count) for a - in alternatives): - count -= 1 - - # No common suffix is possible. - if count == 0: - return [], branches - - # Rebuild the branches. - new_branches = [] - for a in alternatives: - new_branches.append(make_sequence(a[ : -count])) - - return suffix[-count : ], new_branches - - @staticmethod - def _can_split(items, count): - # Check the characters either side of the proposed split. - if not Branch._is_full_case(items, count - 1): - return True - - if not Branch._is_full_case(items, count): - return True - - # Check whether a 1-1 split would be OK. - if Branch._is_folded(items[count - 1 : count + 1]): - return False - - # Check whether a 1-2 split would be OK. - if (Branch._is_full_case(items, count + 2) and - Branch._is_folded(items[count - 1 : count + 2])): - return False - - # Check whether a 2-1 split would be OK. - if (Branch._is_full_case(items, count - 2) and - Branch._is_folded(items[count - 2 : count + 1])): - return False - - return True - - @staticmethod - def _can_split_rev(items, count): - end = len(items) - - # Check the characters either side of the proposed split. - if not Branch._is_full_case(items, end - count): - return True - - if not Branch._is_full_case(items, end - count - 1): - return True - - # Check whether a 1-1 split would be OK. - if Branch._is_folded(items[end - count - 1 : end - count + 1]): - return False - - # Check whether a 1-2 split would be OK. - if (Branch._is_full_case(items, end - count + 2) and - Branch._is_folded(items[end - count - 1 : end - count + 2])): - return False - - # Check whether a 2-1 split would be OK. - if (Branch._is_full_case(items, end - count - 2) and - Branch._is_folded(items[end - count - 2 : end - count + 1])): - return False - - return True - - @staticmethod - def _merge_common_prefixes(info, branches): - # Branches with the same case-sensitive character prefix can be grouped - # together if they are separated only by other branches with a - # character prefix. - prefixed = defaultdict(list) - order = {} - new_branches = [] - for b in branches: - if Branch._is_simple_character(b): - # Branch starts with a simple character. - prefixed[b.value].append([b]) - order.setdefault(b.value, len(order)) - elif (isinstance(b, Sequence) and b.items and - Branch._is_simple_character(b.items[0])): - # Branch starts with a simple character. - prefixed[b.items[0].value].append(b.items) - order.setdefault(b.items[0].value, len(order)) - else: - Branch._flush_char_prefix(info, prefixed, order, new_branches) - - new_branches.append(b) - - Branch._flush_char_prefix(info, prefixed, order, new_branches) - - return new_branches - - @staticmethod - def _is_simple_character(c): - return isinstance(c, Character) and c.positive and not c.case_flags - - @staticmethod - def _reduce_to_set(info, branches): - # Can the branches be reduced to a set? - new_branches = [] - items = set() - case_flags = NOCASE - for b in branches: - if isinstance(b, (Character, Property, SetBase)): - # Branch starts with a single character. - if b.case_flags != case_flags: - # Different case sensitivity, so flush. - Branch._flush_set_members(info, items, case_flags, - new_branches) - - case_flags = b.case_flags - - items.add(b.with_flags(case_flags=NOCASE)) - else: - Branch._flush_set_members(info, items, case_flags, - new_branches) - - new_branches.append(b) - - Branch._flush_set_members(info, items, case_flags, new_branches) - - return new_branches - - @staticmethod - def _flush_char_prefix(info, prefixed, order, new_branches): - # Flush the prefixed branches. - if not prefixed: - return - - for value, branches in sorted(prefixed.items(), key=lambda pair: - order[pair[0]]): - if len(branches) == 1: - new_branches.append(make_sequence(branches[0])) - else: - subbranches = [] - optional = False - for b in branches: - if len(b) > 1: - subbranches.append(make_sequence(b[1 : ])) - elif not optional: - subbranches.append(Sequence()) - optional = True - - sequence = Sequence([Character(value), Branch(subbranches)]) - new_branches.append(sequence.optimise(info)) - - prefixed.clear() - order.clear() - - @staticmethod - def _flush_set_members(info, items, case_flags, new_branches): - # Flush the set members. - if not items: - return - - if len(items) == 1: - item = list(items)[0] - else: - item = SetUnion(info, list(items)).optimise(info) - - new_branches.append(item.with_flags(case_flags=case_flags)) - - items.clear() - - @staticmethod - def _is_full_case(items, i): - if not 0 <= i < len(items): - return False - - item = items[i] - return (isinstance(item, Character) and item.positive and - (item.case_flags & FULLIGNORECASE) == FULLIGNORECASE) - - @staticmethod - def _is_folded(items): - if len(items) < 2: - return False - - for i in items: - if (not isinstance(i, Character) or not i.positive or not - i.case_flags): - return False - - folded = u"".join(unichr(i.value) for i in items) - folded = _regex.fold_case(FULL_CASE_FOLDING, folded) - - # Get the characters which expand to multiple codepoints on folding. - expanding_chars = _regex.get_expand_on_folding() - - for c in expanding_chars: - if folded == _regex.fold_case(FULL_CASE_FOLDING, c): - return True - - return False - - def is_empty(self): - return all(b.is_empty() for b in self.branches) - - def __eq__(self, other): - return type(self) is type(other) and self.branches == other.branches - - def max_width(self): - return max(b.max_width() for b in self.branches) - -class CallGroup(RegexBase): - def __init__(self, info, group, position): - RegexBase.__init__(self) - self.info = info - self.group = group - self.position = position - - self._key = self.__class__, self.group - - def fix_groups(self, reverse, fuzzy): - try: - self.group = int(self.group) - except ValueError: - try: - self.group = self.info.group_index[self.group] - except KeyError: - raise error("unknown group at position %d" % self.position) - - if not 0 <= self.group <= self.info.group_count: - raise error("unknown group at position %d" % self.position) - - if self.group > 0 and self.info.open_group_count[self.group] > 1: - raise error("ambiguous group reference at position %d" % self.position) - - self.info.group_calls.append((self, reverse, fuzzy)) - - self._key = self.__class__, self.group - - def remove_captures(self): - raise error("group reference not allowed at position %d" % self.position) - - def _compile(self, reverse, fuzzy): - return [(OP.GROUP_CALL, self.call_ref)] - - def _dump(self, indent, reverse): - print "%sGROUP_CALL %s" % (INDENT * indent, self.group) - - def __eq__(self, other): - return type(self) is type(other) and self.group == other.group - - def max_width(self): - return UNLIMITED - -class Character(RegexBase): - _opcode = {(NOCASE, False): OP.CHARACTER, (IGNORECASE, False): - OP.CHARACTER_IGN, (FULLCASE, False): OP.CHARACTER, (FULLIGNORECASE, - False): OP.CHARACTER_IGN, (NOCASE, True): OP.CHARACTER_REV, (IGNORECASE, - True): OP.CHARACTER_IGN_REV, (FULLCASE, True): OP.CHARACTER_REV, - (FULLIGNORECASE, True): OP.CHARACTER_IGN_REV} - - def __init__(self, value, positive=True, case_flags=NOCASE, - zerowidth=False): - RegexBase.__init__(self) - self.value = value - self.positive = bool(positive) - self.case_flags = case_flags - self.zerowidth = bool(zerowidth) - - if (self.positive and (self.case_flags & FULLIGNORECASE) == - FULLIGNORECASE): - self.folded = _regex.fold_case(FULL_CASE_FOLDING, unichr(self.value)) - else: - self.folded = unichr(self.value) - - self._key = (self.__class__, self.value, self.positive, - self.case_flags, self.zerowidth) - - def rebuild(self, positive, case_flags, zerowidth): - return Character(self.value, positive, case_flags, zerowidth) - - def optimise(self, info, in_set=False): - return self - - def get_firstset(self, reverse): - return set([self]) - - def has_simple_start(self): - return True - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if self.zerowidth: - flags |= ZEROWIDTH_OP - if fuzzy: - flags |= FUZZY_OP - - code = PrecompiledCode([self._opcode[self.case_flags, reverse], flags, - self.value]) - - if len(self.folded) > 1: - # The character expands on full case-folding. - code = Branch([code, String([ord(c) for c in self.folded], - case_flags=self.case_flags)]) - - return code.compile(reverse, fuzzy) - - def _dump(self, indent, reverse): - display = repr(unichr(self.value)).lstrip("bu") - print "%sCHARACTER %s %s%s" % (INDENT * indent, - POS_TEXT[self.positive], display, CASE_TEXT[self.case_flags]) - - def matches(self, ch): - return (ch == self.value) == self.positive - - def max_width(self): - return len(self.folded) - - def get_required_string(self, reverse): - if not self.positive: - return 1, None - - self.folded_characters = tuple(ord(c) for c in self.folded) - - return 0, self - -class Conditional(RegexBase): - def __init__(self, info, group, yes_item, no_item, position): - RegexBase.__init__(self) - self.info = info - self.group = group - self.yes_item = yes_item - self.no_item = no_item - self.position = position - - def fix_groups(self, reverse, fuzzy): - try: - self.group = int(self.group) - except ValueError: - try: - self.group = self.info.group_index[self.group] - except KeyError: - raise error("unknown group at position %d" % self.position) - - if not 1 <= self.group <= self.info.group_count: - raise error("unknown group at position %d" % self.position) - - self.yes_item.fix_groups(reverse, fuzzy) - self.no_item.fix_groups(reverse, fuzzy) - - def optimise(self, info): - yes_item = self.yes_item.optimise(info) - no_item = self.no_item.optimise(info) - - return Conditional(info, self.group, yes_item, no_item, self.position) - - def pack_characters(self, info): - self.yes_item = self.yes_item.pack_characters(info) - self.no_item = self.no_item.pack_characters(info) - return self - - def remove_captures(self): - self.yes_item = self.yes_item.remove_captures() - self.no_item = self.no_item.remove_captures() - - def is_atomic(self): - return self.yes_item.is_atomic() and self.no_item.is_atomic() - - def can_be_affix(self): - return self.yes_item.can_be_affix() and self.no_item.can_be_affix() - - def contains_group(self): - return self.yes_item.contains_group() or self.no_item.contains_group() - - def get_firstset(self, reverse): - return (self.yes_item.get_firstset(reverse) | - self.no_item.get_firstset(reverse)) - - def _compile(self, reverse, fuzzy): - code = [(OP.GROUP_EXISTS, self.group)] - code.extend(self.yes_item.compile(reverse, fuzzy)) - add_code = self.no_item.compile(reverse, fuzzy) - if add_code: - code.append((OP.NEXT, )) - code.extend(add_code) - - code.append((OP.END, )) - - return code - - def _dump(self, indent, reverse): - print "%sGROUP_EXISTS %s" % (INDENT * indent, self.group) - self.yes_item.dump(indent + 1, reverse) - if self.no_item: - print "%sOR" % (INDENT * indent) - self.no_item.dump(indent + 1, reverse) - - def is_empty(self): - return self.yes_item.is_empty() and self.no_item.is_empty() - - def __eq__(self, other): - return type(self) is type(other) and (self.group, self.yes_item, - self.no_item) == (other.group, other.yes_item, other.no_item) - - def max_width(self): - return max(self.yes_item.max_width(), self.no_item.max_width()) - -class DefaultBoundary(ZeroWidthBase): - _opcode = OP.DEFAULT_BOUNDARY - _op_name = "DEFAULT_BOUNDARY" - -class DefaultEndOfWord(ZeroWidthBase): - _opcode = OP.DEFAULT_END_OF_WORD - _op_name = "DEFAULT_END_OF_WORD" - -class DefaultStartOfWord(ZeroWidthBase): - _opcode = OP.DEFAULT_START_OF_WORD - _op_name = "DEFAULT_START_OF_WORD" - -class EndOfLine(ZeroWidthBase): - _opcode = OP.END_OF_LINE - _op_name = "END_OF_LINE" - -class EndOfLineU(EndOfLine): - _opcode = OP.END_OF_LINE_U - _op_name = "END_OF_LINE_U" - -class EndOfString(ZeroWidthBase): - _opcode = OP.END_OF_STRING - _op_name = "END_OF_STRING" - -class EndOfStringLine(ZeroWidthBase): - _opcode = OP.END_OF_STRING_LINE - _op_name = "END_OF_STRING_LINE" - -class EndOfStringLineU(EndOfStringLine): - _opcode = OP.END_OF_STRING_LINE_U - _op_name = "END_OF_STRING_LINE_U" - -class EndOfWord(ZeroWidthBase): - _opcode = OP.END_OF_WORD - _op_name = "END_OF_WORD" - -class Fuzzy(RegexBase): - def __init__(self, subpattern, constraints=None): - RegexBase.__init__(self) - if constraints is None: - constraints = {} - self.subpattern = subpattern - self.constraints = constraints - - # If an error type is mentioned in the cost equation, then its maximum - # defaults to unlimited. - if "cost" in constraints: - for e in "dis": - if e in constraints["cost"]: - constraints.setdefault(e, (0, None)) - - # If any error type is mentioned, then all the error maxima default to - # 0, otherwise they default to unlimited. - if set(constraints) & set("dis"): - for e in "dis": - constraints.setdefault(e, (0, 0)) - else: - for e in "dis": - constraints.setdefault(e, (0, None)) - - # The maximum of the generic error type defaults to unlimited. - constraints.setdefault("e", (0, None)) - - # The cost equation defaults to equal costs. Also, the cost of any - # error type not mentioned in the cost equation defaults to 0. - if "cost" in constraints: - for e in "dis": - constraints["cost"].setdefault(e, 0) - else: - constraints["cost"] = {"d": 1, "i": 1, "s": 1, "max": - constraints["e"][1]} - - def fix_groups(self, reverse, fuzzy): - self.subpattern.fix_groups(reverse, True) - - def pack_characters(self, info): - self.subpattern = self.subpattern.pack_characters(info) - return self - - def remove_captures(self): - self.subpattern = self.subpattern.remove_captures() - return self - - def is_atomic(self): - return self.subpattern.is_atomic() - - def contains_group(self): - return self.subpattern.contains_group() - - def _compile(self, reverse, fuzzy): - # The individual limits. - arguments = [] - for e in "dise": - v = self.constraints[e] - arguments.append(v[0]) - arguments.append(UNLIMITED if v[1] is None else v[1]) - - # The coeffs of the cost equation. - for e in "dis": - arguments.append(self.constraints["cost"][e]) - - # The maximum of the cost equation. - v = self.constraints["cost"]["max"] - arguments.append(UNLIMITED if v is None else v) - - flags = 0 - if reverse: - flags |= REVERSE_OP - - return ([(OP.FUZZY, flags) + tuple(arguments)] + - self.subpattern.compile(reverse, True) + [(OP.END,)]) - - def _dump(self, indent, reverse): - constraints = self._constraints_to_string() - if constraints: - constraints = " " + constraints - print "%sFUZZY%s" % (INDENT * indent, constraints) - self.subpattern.dump(indent + 1, reverse) - - def is_empty(self): - return self.subpattern.is_empty() - - def __eq__(self, other): - return (type(self) is type(other) and self.subpattern == - other.subpattern) - - def max_width(self): - return UNLIMITED - - def _constraints_to_string(self): - constraints = [] - - for name in "ids": - min, max = self.constraints[name] - if max == 0: - continue - - con = "" - - if min > 0: - con = "%s<=" % min - - con += name - - if max is not None: - con += "<=%s" % max - - constraints.append(con) - - cost = [] - for name in "ids": - coeff = self.constraints["cost"][name] - if coeff > 0: - cost.append("%s%s" % (coeff, name)) - - limit = self.constraints["cost"]["max"] - if limit is not None and limit > 0: - cost = "%s<=%s" % ("+".join(cost), limit) - constraints.append(cost) - - return ",".join(constraints) - -class Grapheme(RegexBase): - def _compile(self, reverse, fuzzy): - # Match at least 1 character until a grapheme boundary is reached. Note - # that this is the same whether matching forwards or backwards. - character_matcher = LazyRepeat(AnyAll(), 1, None).compile(reverse, - fuzzy) - boundary_matcher = [(OP.GRAPHEME_BOUNDARY, 1)] - - return character_matcher + boundary_matcher - - def _dump(self, indent, reverse): - print "%sGRAPHEME" % (INDENT * indent) - - def max_width(self): - return UNLIMITED - -class GreedyRepeat(RegexBase): - _opcode = OP.GREEDY_REPEAT - _op_name = "GREEDY_REPEAT" - - def __init__(self, subpattern, min_count, max_count): - RegexBase.__init__(self) - self.subpattern = subpattern - self.min_count = min_count - self.max_count = max_count - - def fix_groups(self, reverse, fuzzy): - self.subpattern.fix_groups(reverse, fuzzy) - - def optimise(self, info): - subpattern = self.subpattern.optimise(info) - - return type(self)(subpattern, self.min_count, self.max_count) - - def pack_characters(self, info): - self.subpattern = self.subpattern.pack_characters(info) - return self - - def remove_captures(self): - self.subpattern = self.subpattern.remove_captures() - return self - - def is_atomic(self): - return self.min_count == self.max_count and self.subpattern.is_atomic() - - def contains_group(self): - return self.subpattern.contains_group() - - def get_firstset(self, reverse): - fs = self.subpattern.get_firstset(reverse) - if self.min_count == 0: - fs.add(None) - - return fs - - def _compile(self, reverse, fuzzy): - repeat = [self._opcode, self.min_count] - if self.max_count is None: - repeat.append(UNLIMITED) - else: - repeat.append(self.max_count) - - subpattern = self.subpattern.compile(reverse, fuzzy) - if not subpattern: - return [] - - return ([tuple(repeat)] + subpattern + [(OP.END, )]) - - def _dump(self, indent, reverse): - if self.max_count is None: - limit = "INF" - else: - limit = self.max_count - print "%s%s %s %s" % (INDENT * indent, self._op_name, self.min_count, - limit) - - self.subpattern.dump(indent + 1, reverse) - - def is_empty(self): - return self.subpattern.is_empty() - - def __eq__(self, other): - return type(self) is type(other) and (self.subpattern, self.min_count, - self.max_count) == (other.subpattern, other.min_count, - other.max_count) - - def max_width(self): - if self.max_count is None: - return UNLIMITED - - return self.subpattern.max_width() * self.max_count - - def get_required_string(self, reverse): - max_count = UNLIMITED if self.max_count is None else self.max_count - if self.min_count == 0: - w = self.subpattern.max_width() * max_count - return min(w, UNLIMITED), None - - ofs, req = self.subpattern.get_required_string(reverse) - if req: - return ofs, req - - w = self.subpattern.max_width() * max_count - return min(w, UNLIMITED), None - -class Group(RegexBase): - def __init__(self, info, group, subpattern): - RegexBase.__init__(self) - self.info = info - self.group = group - self.subpattern = subpattern - - self.call_ref = None - - def fix_groups(self, reverse, fuzzy): - self.info.defined_groups[self.group] = (self, reverse, fuzzy) - self.subpattern.fix_groups(reverse, fuzzy) - - def optimise(self, info): - subpattern = self.subpattern.optimise(info) - - return Group(self.info, self.group, subpattern) - - def pack_characters(self, info): - self.subpattern = self.subpattern.pack_characters(info) - return self - - def remove_captures(self): - return self.subpattern.remove_captures() - - def is_atomic(self): - return self.subpattern.is_atomic() - - def can_be_affix(self): - return False - - def contains_group(self): - return True - - def get_firstset(self, reverse): - return self.subpattern.get_firstset(reverse) - - def has_simple_start(self): - return self.subpattern.has_simple_start() - - def _compile(self, reverse, fuzzy): - code = [] - - key = self.group, reverse, fuzzy - ref = self.info.call_refs.get(key) - if ref is not None: - code += [(OP.CALL_REF, ref)] - - public_group = private_group = self.group - if private_group < 0: - public_group = self.info.private_groups[private_group] - private_group = self.info.group_count - private_group - - code += ([(OP.GROUP, private_group, public_group)] + - self.subpattern.compile(reverse, fuzzy) + [(OP.END, )]) - - if ref is not None: - code += [(OP.END, )] - - return code - - def _dump(self, indent, reverse): - group = self.group - if group < 0: - group = private_groups[group] - print "%sGROUP %s" % (INDENT * indent, group) - self.subpattern.dump(indent + 1, reverse) - - def __eq__(self, other): - return (type(self) is type(other) and (self.group, self.subpattern) == - (other.group, other.subpattern)) - - def max_width(self): - return self.subpattern.max_width() - - def get_required_string(self, reverse): - return self.subpattern.get_required_string(reverse) - -class LazyRepeat(GreedyRepeat): - _opcode = OP.LAZY_REPEAT - _op_name = "LAZY_REPEAT" - -class LookAround(RegexBase): - _dir_text = {False: "AHEAD", True: "BEHIND"} - - def __new__(cls, behind, positive, subpattern): - if positive and subpattern.is_empty(): - return subpattern - - return RegexBase.__new__(cls) - - def __init__(self, behind, positive, subpattern): - RegexBase.__init__(self) - self.behind = bool(behind) - self.positive = bool(positive) - self.subpattern = subpattern - - def fix_groups(self, reverse, fuzzy): - self.subpattern.fix_groups(self.behind, fuzzy) - - def optimise(self, info): - subpattern = self.subpattern.optimise(info) - - return LookAround(self.behind, self.positive, subpattern) - - def pack_characters(self, info): - self.subpattern = self.subpattern.pack_characters(info) - return self - - def remove_captures(self): - return self.subpattern.remove_captures() - - def is_atomic(self): - return self.subpattern.is_atomic() - - def can_be_affix(self): - return self.subpattern.can_be_affix() - - def contains_group(self): - return self.subpattern.contains_group() - - def _compile(self, reverse, fuzzy): - return ([(OP.LOOKAROUND, int(self.positive), int(not self.behind))] + - self.subpattern.compile(self.behind) + [(OP.END, )]) - - def _dump(self, indent, reverse): - print "%sLOOK%s %s" % (INDENT * indent, self._dir_text[self.behind], - POS_TEXT[self.positive]) - self.subpattern.dump(indent + 1, self.behind) - - def is_empty(self): - return self.subpattern.is_empty() - - def __eq__(self, other): - return type(self) is type(other) and (self.behind, self.positive, - self.subpattern) == (other.behind, other.positive, other.subpattern) - - def max_width(self): - return 0 - -class PrecompiledCode(RegexBase): - def __init__(self, code): - self.code = code - - def _compile(self, reverse, fuzzy): - return [tuple(self.code)] - -class Property(RegexBase): - _opcode = {(NOCASE, False): OP.PROPERTY, (IGNORECASE, False): - OP.PROPERTY_IGN, (FULLCASE, False): OP.PROPERTY, (FULLIGNORECASE, False): - OP.PROPERTY_IGN, (NOCASE, True): OP.PROPERTY_REV, (IGNORECASE, True): - OP.PROPERTY_IGN_REV, (FULLCASE, True): OP.PROPERTY_REV, (FULLIGNORECASE, - True): OP.PROPERTY_IGN_REV} - - def __init__(self, value, positive=True, case_flags=NOCASE, - zerowidth=False): - RegexBase.__init__(self) - self.value = value - self.positive = bool(positive) - self.case_flags = case_flags - self.zerowidth = bool(zerowidth) - - self._key = (self.__class__, self.value, self.positive, - self.case_flags, self.zerowidth) - - def rebuild(self, positive, case_flags, zerowidth): - return Property(self.value, positive, case_flags, zerowidth) - - def optimise(self, info, in_set=False): - return self - - def get_firstset(self, reverse): - return set([self]) - - def has_simple_start(self): - return True - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if self.zerowidth: - flags |= ZEROWIDTH_OP - if fuzzy: - flags |= FUZZY_OP - return [(self._opcode[self.case_flags, reverse], flags, self.value)] - - def _dump(self, indent, reverse): - prop = PROPERTY_NAMES[self.value >> 16] - name, value = prop[0], prop[1][self.value & 0xFFFF] - print "%sPROPERTY %s %s:%s%s" % (INDENT * indent, - POS_TEXT[self.positive], name, value, CASE_TEXT[self.case_flags]) - - def matches(self, ch): - return _regex.has_property_value(self.value, ch) == self.positive - - def max_width(self): - return 1 - -class Range(RegexBase): - _opcode = {(NOCASE, False): OP.RANGE, (IGNORECASE, False): OP.RANGE_IGN, - (FULLCASE, False): OP.RANGE, (FULLIGNORECASE, False): OP.RANGE_IGN, - (NOCASE, True): OP.RANGE_REV, (IGNORECASE, True): OP.RANGE_IGN_REV, - (FULLCASE, True): OP.RANGE_REV, (FULLIGNORECASE, True): OP.RANGE_IGN_REV} - _op_name = "RANGE" - - def __init__(self, lower, upper, positive=True, case_flags=NOCASE, - zerowidth=False): - RegexBase.__init__(self) - self.lower = lower - self.upper = upper - self.positive = bool(positive) - self.case_flags = case_flags - self.zerowidth = bool(zerowidth) - - self._key = (self.__class__, self.lower, self.upper, self.positive, - self.case_flags, self.zerowidth) - - def rebuild(self, positive, case_flags, zerowidth): - return Range(self.lower, self.upper, positive, case_flags, zerowidth) - - def optimise(self, info, in_set=False): - # Is the range case-sensitive? - if not self.positive or not (self.case_flags & IGNORECASE) or in_set: - return self - - # Is full case-folding possible? - if (not (info.flags & UNICODE) or (self.case_flags & FULLIGNORECASE) != - FULLIGNORECASE): - return self - - # Get the characters which expand to multiple codepoints on folding. - expanding_chars = _regex.get_expand_on_folding() - - # Get the folded characters in the range. - items = [] - for ch in expanding_chars: - if self.lower <= ord(ch) <= self.upper: - folded = _regex.fold_case(FULL_CASE_FOLDING, ch) - items.append(String([ord(c) for c in folded], - case_flags=self.case_flags)) - - if not items: - # We can fall back to simple case-folding. - return self - - if len(items) < self.upper - self.lower + 1: - # Not all the characters are covered by the full case-folding. - items.insert(0, self) - - return Branch(items) - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if self.zerowidth: - flags |= ZEROWIDTH_OP - if fuzzy: - flags |= FUZZY_OP - return [(self._opcode[self.case_flags, reverse], flags, self.lower, - self.upper)] - - def _dump(self, indent, reverse): - display_lower = repr(unichr(self.lower)).lstrip("bu") - display_upper = repr(unichr(self.upper)).lstrip("bu") - print "%sRANGE %s %s %s%s" % (INDENT * indent, POS_TEXT[self.positive], - display_lower, display_upper, CASE_TEXT[self.case_flags]) - - def matches(self, ch): - return (self.lower <= ch <= self.upper) == self.positive - - def max_width(self): - return 1 - -class RefGroup(RegexBase): - _opcode = {(NOCASE, False): OP.REF_GROUP, (IGNORECASE, False): - OP.REF_GROUP_IGN, (FULLCASE, False): OP.REF_GROUP, (FULLIGNORECASE, - False): OP.REF_GROUP_FLD, (NOCASE, True): OP.REF_GROUP_REV, (IGNORECASE, - True): OP.REF_GROUP_IGN_REV, (FULLCASE, True): OP.REF_GROUP_REV, - (FULLIGNORECASE, True): OP.REF_GROUP_FLD_REV} - - def __init__(self, info, group, position, case_flags=NOCASE): - RegexBase.__init__(self) - self.info = info - self.group = group - self.position = position - self.case_flags = case_flags - - self._key = self.__class__, self.group, self.case_flags - - def fix_groups(self, reverse, fuzzy): - try: - self.group = int(self.group) - except ValueError: - try: - self.group = self.info.group_index[self.group] - except KeyError: - raise error("unknown group at position %d" % self.position) - - if not 1 <= self.group <= self.info.group_count: - raise error("unknown group at position %d" % self.position) - - self._key = self.__class__, self.group, self.case_flags - - def remove_captures(self): - raise error("group reference not allowed at position %d" % self.position) - - def _compile(self, reverse, fuzzy): - flags = 0 - if fuzzy: - flags |= FUZZY_OP - return [(self._opcode[self.case_flags, reverse], flags, self.group)] - - def _dump(self, indent, reverse): - print "%sREF_GROUP %s%s" % (INDENT * indent, self.group, - CASE_TEXT[self.case_flags]) - - def max_width(self): - return UNLIMITED - -class SearchAnchor(ZeroWidthBase): - _opcode = OP.SEARCH_ANCHOR - _op_name = "SEARCH_ANCHOR" - -class Sequence(RegexBase): - def __init__(self, items=None): - RegexBase.__init__(self) - if items is None: - items = [] - - self.items = items - - def fix_groups(self, reverse, fuzzy): - for s in self.items: - s.fix_groups(reverse, fuzzy) - - def optimise(self, info): - # Flatten the sequences. - items = [] - for s in self.items: - s = s.optimise(info) - if isinstance(s, Sequence): - items.extend(s.items) - else: - items.append(s) - - return make_sequence(items) - - def pack_characters(self, info): - "Packs sequences of characters into strings." - items = [] - characters = [] - case_flags = NOCASE - for s in self.items: - if type(s) is Character and s.positive: - if s.case_flags != case_flags: - # Different case sensitivity, so flush, unless neither the - # previous nor the new character are cased. - if s.case_flags or is_cased(info, s.value): - Sequence._flush_characters(info, characters, - case_flags, items) - - case_flags = s.case_flags - - characters.append(s.value) - elif type(s) is String or type(s) is Literal: - if s.case_flags != case_flags: - # Different case sensitivity, so flush, unless the neither - # the previous nor the new string are cased. - if s.case_flags or any(is_cased(info, c) for c in - characters): - Sequence._flush_characters(info, characters, - case_flags, items) - - case_flags = s.case_flags - - characters.extend(s.characters) - else: - Sequence._flush_characters(info, characters, case_flags, items) - - items.append(s.pack_characters(info)) - - Sequence._flush_characters(info, characters, case_flags, items) - - return make_sequence(items) - - def remove_captures(self): - self.items = [s.remove_captures() for s in self.items] - return self - - def is_atomic(self): - return all(s.is_atomic() for s in self.items) - - def can_be_affix(self): - return False - - def contains_group(self): - return any(s.contains_group() for s in self.items) - - def get_firstset(self, reverse): - fs = set() - items = self.items - if reverse: - items.reverse() - for s in items: - fs |= s.get_firstset(reverse) - if None not in fs: - return fs - fs.discard(None) - - return fs | set([None]) - - def has_simple_start(self): - return self.items and self.items[0].has_simple_start() - - def _compile(self, reverse, fuzzy): - seq = self.items - if reverse: - seq = seq[::-1] - - code = [] - for s in seq: - code.extend(s.compile(reverse, fuzzy)) - - return code - - def _dump(self, indent, reverse): - for s in self.items: - s.dump(indent, reverse) - - @staticmethod - def _flush_characters(info, characters, case_flags, items): - if not characters: - return - - # Disregard case_flags if all of the characters are case-less. - if case_flags & IGNORECASE: - if not any(is_cased(info, c) for c in characters): - case_flags = NOCASE - - if len(characters) == 1: - items.append(Character(characters[0], case_flags=case_flags)) - else: - items.append(String(characters, case_flags=case_flags)) - - characters[:] = [] - - def is_empty(self): - return all(i.is_empty() for i in self.items) - - def __eq__(self, other): - return type(self) is type(other) and self.items == other.items - - def max_width(self): - return sum(s.max_width() for s in self.items) - - def get_required_string(self, reverse): - seq = self.items - if reverse: - seq = seq[::-1] - - offset = 0 - - for s in seq: - ofs, req = s.get_required_string(reverse) - offset += ofs - if req: - return offset, req - - return offset, None - -class SetBase(RegexBase): - def __init__(self, info, items, positive=True, case_flags=NOCASE, - zerowidth=False): - RegexBase.__init__(self) - self.info = info - self.items = tuple(items) - self.positive = bool(positive) - self.case_flags = case_flags - self.zerowidth = bool(zerowidth) - - self.char_width = 1 - - self._key = (self.__class__, self.items, self.positive, - self.case_flags, self.zerowidth) - - def rebuild(self, positive, case_flags, zerowidth): - return type(self)(self.info, self.items, positive, case_flags, - zerowidth).optimise(self.info) - - def get_firstset(self, reverse): - return set([self]) - - def has_simple_start(self): - return True - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if self.zerowidth: - flags |= ZEROWIDTH_OP - if fuzzy: - flags |= FUZZY_OP - code = [(self._opcode[self.case_flags, reverse], flags)] - for m in self.items: - code.extend(m.compile()) - - code.append((OP.END, )) - - return code - - def _dump(self, indent, reverse): - print "%s%s %s%s" % (INDENT * indent, self._op_name, - POS_TEXT[self.positive], CASE_TEXT[self.case_flags]) - for i in self.items: - i.dump(indent + 1) - - def _handle_case_folding(self, info, in_set): - # Is the set case-sensitive? - if not self.positive or not (self.case_flags & IGNORECASE) or in_set: - return self - - # Is full case-folding possible? - if (not (self.info.flags & UNICODE) or (self.case_flags & - FULLIGNORECASE) != - FULLIGNORECASE): - return self - - # Get the characters which expand to multiple codepoints on folding. - expanding_chars = _regex.get_expand_on_folding() - - # Get the folded characters in the set. - items = [] - seen = set() - for ch in expanding_chars: - if self.matches(ord(ch)): - folded = _regex.fold_case(FULL_CASE_FOLDING, ch) - if folded not in seen: - items.append(String([ord(c) for c in folded], - case_flags=self.case_flags)) - seen.add(folded) - - if not items: - # We can fall back to simple case-folding. - return self - - return Branch([self] + items) - - def max_width(self): - # Is the set case-sensitive? - if not self.positive or not (self.case_flags & IGNORECASE): - return 1 - - # Is full case-folding possible? - if (not (self.info.flags & UNICODE) or (self.case_flags & - FULLIGNORECASE) != FULLIGNORECASE): - return 1 - - # Get the characters which expand to multiple codepoints on folding. - expanding_chars = _regex.get_expand_on_folding() - - # Get the folded characters in the set. - seen = set() - for ch in expanding_chars: - if self.matches(ord(ch)): - folded = _regex.fold_case(FULL_CASE_FOLDING, ch) - seen.add(folded) - - if not seen: - return 1 - - return max(len(folded) for folded in seen) - -class SetDiff(SetBase): - _opcode = {(NOCASE, False): OP.SET_DIFF, (IGNORECASE, False): - OP.SET_DIFF_IGN, (FULLCASE, False): OP.SET_DIFF, (FULLIGNORECASE, False): - OP.SET_DIFF_IGN, (NOCASE, True): OP.SET_DIFF_REV, (IGNORECASE, True): - OP.SET_DIFF_IGN_REV, (FULLCASE, True): OP.SET_DIFF_REV, (FULLIGNORECASE, - True): OP.SET_DIFF_IGN_REV} - _op_name = "SET_DIFF" - - def optimise(self, info, in_set=False): - items = self.items - if len(items) > 2: - items = [items[0], SetUnion(info, items[1 : ])] - - if len(items) == 1: - return items[0].with_flags(case_flags=self.case_flags, - zerowidth=self.zerowidth).optimise(info, in_set) - - self.items = tuple(m.optimise(info, in_set=True) for m in items) - - return self._handle_case_folding(info, in_set) - - def matches(self, ch): - m = self.items[0].matches(ch) and not self.items[1].matches(ch) - return m == self.positive - -class SetInter(SetBase): - _opcode = {(NOCASE, False): OP.SET_INTER, (IGNORECASE, False): - OP.SET_INTER_IGN, (FULLCASE, False): OP.SET_INTER, (FULLIGNORECASE, - False): OP.SET_INTER_IGN, (NOCASE, True): OP.SET_INTER_REV, (IGNORECASE, - True): OP.SET_INTER_IGN_REV, (FULLCASE, True): OP.SET_INTER_REV, - (FULLIGNORECASE, True): OP.SET_INTER_IGN_REV} - _op_name = "SET_INTER" - - def optimise(self, info, in_set=False): - items = [] - for m in self.items: - m = m.optimise(info, in_set=True) - if isinstance(m, SetInter) and m.positive: - # Intersection in intersection. - items.extend(m.items) - else: - items.append(m) - - if len(items) == 1: - return items[0].with_flags(case_flags=self.case_flags, - zerowidth=self.zerowidth).optimise(info, in_set) - - self.items = tuple(items) - - return self._handle_case_folding(info, in_set) - - def matches(self, ch): - m = all(i.matches(ch) for i in self.items) - return m == self.positive - -class SetSymDiff(SetBase): - _opcode = {(NOCASE, False): OP.SET_SYM_DIFF, (IGNORECASE, False): - OP.SET_SYM_DIFF_IGN, (FULLCASE, False): OP.SET_SYM_DIFF, (FULLIGNORECASE, - False): OP.SET_SYM_DIFF_IGN, (NOCASE, True): OP.SET_SYM_DIFF_REV, - (IGNORECASE, True): OP.SET_SYM_DIFF_IGN_REV, (FULLCASE, True): - OP.SET_SYM_DIFF_REV, (FULLIGNORECASE, True): OP.SET_SYM_DIFF_IGN_REV} - _op_name = "SET_SYM_DIFF" - - def optimise(self, info, in_set=False): - items = [] - for m in self.items: - m = m.optimise(info, in_set=True) - if isinstance(m, SetSymDiff) and m.positive: - # Symmetric difference in symmetric difference. - items.extend(m.items) - else: - items.append(m) - - if len(items) == 1: - return items[0].with_flags(case_flags=self.case_flags, - zerowidth=self.zerowidth).optimise(info, in_set) - - self.items = tuple(items) - - return self._handle_case_folding(info, in_set) - - def matches(self, ch): - m = False - for i in self.items: - m = m != i.matches(ch) - - return m == self.positive - -class SetUnion(SetBase): - _opcode = {(NOCASE, False): OP.SET_UNION, (IGNORECASE, False): - OP.SET_UNION_IGN, (FULLCASE, False): OP.SET_UNION, (FULLIGNORECASE, - False): OP.SET_UNION_IGN, (NOCASE, True): OP.SET_UNION_REV, (IGNORECASE, - True): OP.SET_UNION_IGN_REV, (FULLCASE, True): OP.SET_UNION_REV, - (FULLIGNORECASE, True): OP.SET_UNION_IGN_REV} - _op_name = "SET_UNION" - - def optimise(self, info, in_set=False): - items = [] - for m in self.items: - m = m.optimise(info, in_set=True) - if isinstance(m, SetUnion) and m.positive: - # Union in union. - items.extend(m.items) - else: - items.append(m) - - if len(items) == 1: - i = items[0] - return i.with_flags(positive=i.positive == self.positive, - case_flags=self.case_flags, - zerowidth=self.zerowidth).optimise(info, in_set) - - self.items = tuple(items) - - return self._handle_case_folding(info, in_set) - - def _compile(self, reverse, fuzzy): - flags = 0 - if self.positive: - flags |= POSITIVE_OP - if self.zerowidth: - flags |= ZEROWIDTH_OP - if fuzzy: - flags |= FUZZY_OP - - characters, others = defaultdict(list), [] - for m in self.items: - if isinstance(m, Character): - characters[m.positive].append(m.value) - else: - others.append(m) - - code = [(self._opcode[self.case_flags, reverse], flags)] - - for positive, values in characters.items(): - flags = 0 - if positive: - flags |= POSITIVE_OP - if len(values) == 1: - code.append((OP.CHARACTER, flags, values[0])) - else: - code.append((OP.STRING, flags, len(values)) + tuple(values)) - - for m in others: - code.extend(m.compile()) - - code.append((OP.END, )) - - return code - - def matches(self, ch): - m = any(i.matches(ch) for i in self.items) - return m == self.positive - -class StartOfLine(ZeroWidthBase): - _opcode = OP.START_OF_LINE - _op_name = "START_OF_LINE" - -class StartOfLineU(StartOfLine): - _opcode = OP.START_OF_LINE_U - _op_name = "START_OF_LINE_U" - -class StartOfString(ZeroWidthBase): - _opcode = OP.START_OF_STRING - _op_name = "START_OF_STRING" - -class StartOfWord(ZeroWidthBase): - _opcode = OP.START_OF_WORD - _op_name = "START_OF_WORD" - -class String(RegexBase): - _opcode = {(NOCASE, False): OP.STRING, (IGNORECASE, False): OP.STRING_IGN, - (FULLCASE, False): OP.STRING, (FULLIGNORECASE, False): OP.STRING_FLD, - (NOCASE, True): OP.STRING_REV, (IGNORECASE, True): OP.STRING_IGN_REV, - (FULLCASE, True): OP.STRING_REV, (FULLIGNORECASE, True): - OP.STRING_FLD_REV} - - def __init__(self, characters, case_flags=NOCASE): - self.characters = tuple(characters) - self.case_flags = case_flags - - if (self.case_flags & FULLIGNORECASE) == FULLIGNORECASE: - folded_characters = [] - for char in self.characters: - folded = _regex.fold_case(FULL_CASE_FOLDING, unichr(char)) - folded_characters.extend(ord(c) for c in folded) - else: - folded_characters = self.characters - - self.folded_characters = tuple(folded_characters) - self.required = False - - self._key = self.__class__, self.characters, self.case_flags - - def get_firstset(self, reverse): - if reverse: - pos = -1 - else: - pos = 0 - return set([Character(self.characters[pos], - case_flags=self.case_flags)]) - - def has_simple_start(self): - return True - - def _compile(self, reverse, fuzzy): - flags = 0 - if fuzzy: - flags |= FUZZY_OP - if self.required: - flags |= REQUIRED_OP - return [(self._opcode[self.case_flags, reverse], flags, - len(self.folded_characters)) + self.folded_characters] - - def _dump(self, indent, reverse): - display = repr("".join(unichr(c) for c in self.characters)).lstrip("bu") - print "%sSTRING %s%s" % (INDENT * indent, display, - CASE_TEXT[self.case_flags]) - - def max_width(self): - return len(self.folded_characters) - - def get_required_string(self, reverse): - return 0, self - -class Literal(String): - def _dump(self, indent, reverse): - for c in self.characters: - display = ascii("".join(chr(c))).lstrip("bu") - print("{}CHARACTER MATCH {}{}".format(INDENT * indent, - display, CASE_TEXT[self.case_flags])) - -class StringSet(RegexBase): - _opcode = {(NOCASE, False): OP.STRING_SET, (IGNORECASE, False): - OP.STRING_SET_IGN, (FULLCASE, False): OP.STRING_SET, (FULLIGNORECASE, - False): OP.STRING_SET_FLD, (NOCASE, True): OP.STRING_SET_REV, - (IGNORECASE, True): OP.STRING_SET_IGN_REV, (FULLCASE, True): - OP.STRING_SET_REV, (FULLIGNORECASE, True): OP.STRING_SET_FLD_REV} - - def __init__(self, info, name, case_flags=NOCASE): - self.info = info - self.name = name - self.case_flags = case_flags - - self._key = self.__class__, self.name, self.case_flags - - self.set_key = (name, self.case_flags) - if self.set_key not in info.named_lists_used: - info.named_lists_used[self.set_key] = len(info.named_lists_used) - - def _compile(self, reverse, fuzzy): - index = self.info.named_lists_used[self.set_key] - items = self.info.kwargs[self.name] - - case_flags = self.case_flags - - if not items: - return [] - - encoding = self.info.flags & _ALL_ENCODINGS - fold_flags = encoding | case_flags - - if fuzzy: - choices = [self._folded(fold_flags, i) for i in items] - - # Sort from longest to shortest. - choices.sort(key=lambda s: (-len(s), s)) - - branches = [] - for string in choices: - branches.append(Sequence([Character(c, case_flags=case_flags) - for c in string])) - - if len(branches) > 1: - branch = Branch(branches) - else: - branch = branches[0] - branch = branch.optimise(self.info).pack_characters(self.info) - - return branch.compile(reverse, fuzzy) - else: - min_len = min(len(i) for i in items) - max_len = max(len(self._folded(fold_flags, i)) for i in items) - return [(self._opcode[case_flags, reverse], index, min_len, - max_len)] - - def _dump(self, indent, reverse): - print "%sSTRING_SET %s%s" % (INDENT * indent, self.name, - CASE_TEXT[self.case_flags]) - - def _folded(self, fold_flags, item): - if isinstance(item, unicode): - return [ord(c) for c in _regex.fold_case(fold_flags, item)] - else: - return [ord(c) for c in item] - - def _flatten(self, s): - # Flattens the branches. - if isinstance(s, Branch): - for b in s.branches: - self._flatten(b) - elif isinstance(s, Sequence) and s.items: - seq = s.items - - while isinstance(seq[-1], Sequence): - seq[-1 : ] = seq[-1].items - - n = 0 - while n < len(seq) and isinstance(seq[n], Character): - n += 1 - - if n > 1: - seq[ : n] = [String([c.value for c in seq[ : n]], - case_flags=self.case_flags)] - - self._flatten(seq[-1]) - - def max_width(self): - if not self.info.kwargs[self.name]: - return 0 - - if self.case_flags & IGNORECASE: - fold_flags = (self.info.flags & _ALL_ENCODINGS) | self.case_flags - return max(len(_regex.fold_case(fold_flags, i)) for i in - self.info.kwargs[self.name]) - else: - return max(len(i) for i in self.info.kwargs[self.name]) - -class Source(object): - "Scanner for the regular expression source string." - def __init__(self, string): - if isinstance(string, unicode): - self.string = string - self.char_type = unichr - else: - self.string = string - self.char_type = chr - - self.pos = 0 - self.ignore_space = False - self.sep = string[ : 0] - - def get(self): - string = self.string - pos = self.pos - - try: - if self.ignore_space: - while True: - if string[pos].isspace(): - # Skip over the whitespace. - pos += 1 - elif string[pos] == "#": - # Skip over the comment to the end of the line. - pos = string.index("\n", pos) - else: - break - - ch = string[pos] - self.pos = pos + 1 - return ch - except IndexError: - # We've reached the end of the string. - self.pos = pos - return string[ : 0] - except ValueError: - # The comment extended to the end of the string. - self.pos = len(string) - return string[ : 0] - - def get_many(self, count=1): - string = self.string - pos = self.pos - - try: - if self.ignore_space: - substring = [] - - while len(substring) < count: - while True: - if string[pos].isspace(): - # Skip over the whitespace. - pos += 1 - elif string[pos] == "#": - # Skip over the comment to the end of the line. - pos = string.index("\n", pos) - else: - break - - substring.append(string[pos]) - pos += 1 - - substring = "".join(substring) - else: - substring = string[pos : pos + count] - pos += len(substring) - - self.pos = pos - return substring - except IndexError: - # We've reached the end of the string. - self.pos = len(string) - return "".join(substring) - except ValueError: - # The comment extended to the end of the string. - self.pos = len(string) - return "".join(substring) - - def get_while(self, test_set, include=True): - string = self.string - pos = self.pos - - if self.ignore_space: - try: - substring = [] - - while True: - if string[pos].isspace(): - # Skip over the whitespace. - pos += 1 - elif string[pos] == "#": - # Skip over the comment to the end of the line. - pos = string.index("\n", pos) - elif (string[pos] in test_set) == include: - substring.append(string[pos]) - pos += 1 - else: - break - - self.pos = pos - except IndexError: - # We've reached the end of the string. - self.pos = len(string) - except ValueError: - # The comment extended to the end of the string. - self.pos = len(string) - - return "".join(substring) - else: - try: - while (string[pos] in test_set) == include: - pos += 1 - - substring = string[self.pos : pos] - - self.pos = pos - - return substring - except IndexError: - # We've reached the end of the string. - substring = string[self.pos : pos] - - self.pos = pos - - return substring - - def skip_while(self, test_set, include=True): - string = self.string - pos = self.pos - - try: - if self.ignore_space: - while True: - if string[pos].isspace(): - # Skip over the whitespace. - pos += 1 - elif string[pos] == "#": - # Skip over the comment to the end of the line. - pos = string.index("\n", pos) - elif (string[pos] in test_set) == include: - pos += 1 - else: - break - else: - while (string[pos] in test_set) == include: - pos += 1 - - self.pos = pos - except IndexError: - # We've reached the end of the string. - self.pos = len(string) - except ValueError: - # The comment extended to the end of the string. - self.pos = len(string) - - def match(self, substring): - string = self.string - pos = self.pos - - if self.ignore_space: - try: - for c in substring: - while True: - if string[pos].isspace(): - # Skip over the whitespace. - pos += 1 - elif string[pos] == "#": - # Skip over the comment to the end of the line. - pos = string.index("\n", pos) - else: - break - - if string[pos] != c: - return False - - pos += 1 - - self.pos = pos - - return True - except IndexError: - # We've reached the end of the string. - return False - except ValueError: - # The comment extended to the end of the string. - return False - else: - if not string.startswith(substring, pos): - return False - - self.pos = pos + len(substring) - - return True - - def expect(self, substring): - if not self.match(substring): - raise error("missing %s at position %d" % (substring, self.pos)) - - def at_end(self): - string = self.string - pos = self.pos - - try: - if self.ignore_space: - while True: - if string[pos].isspace(): - pos += 1 - elif string[pos] == "#": - pos = string.index("\n", pos) - else: - break - - return pos >= len(string) - except IndexError: - # We've reached the end of the string. - return True - except ValueError: - # The comment extended to the end of the string. - return True - -class Info(object): - "Info about the regular expression." - - def __init__(self, flags=0, char_type=None, kwargs={}): - flags |= DEFAULT_FLAGS[(flags & _ALL_VERSIONS) or DEFAULT_VERSION] - self.flags = flags - self.global_flags = flags - - self.kwargs = kwargs - - self.group_count = 0 - self.group_index = {} - self.group_name = {} - self.char_type = char_type - self.named_lists_used = {} - self.open_groups = [] - self.open_group_count = {} - self.defined_groups = {} - self.group_calls = [] - self.private_groups = {} - - def open_group(self, name=None): - group = self.group_index.get(name) - if group is None: - while True: - self.group_count += 1 - if name is None or self.group_count not in self.group_name: - break - - group = self.group_count - if name: - self.group_index[name] = group - self.group_name[group] = name - - if group in self.open_groups: - # We have a nested named group. We'll assign it a private group - # number, initially negative until we can assign a proper - # (positive) number. - group_alias = -(len(self.private_groups) + 1) - self.private_groups[group_alias] = group - group = group_alias - - self.open_groups.append(group) - self.open_group_count[group] = self.open_group_count.get(group, 0) + 1 - - return group - - def close_group(self): - self.open_groups.pop() - - def is_open_group(self, name): - # In version 1, a group reference can refer to an open group. We'll - # just pretend the group isn't open. - version = (self.flags & _ALL_VERSIONS) or DEFAULT_VERSION - if version == VERSION1: - return False - - if name.isdigit(): - group = int(name) - else: - group = self.group_index.get(name) - - return group in self.open_groups - -def _check_group_features(info, parsed): - """Checks whether the reverse and fuzzy features of the group calls match - the groups which they call. - """ - call_refs = {} - additional_groups = [] - for call, reverse, fuzzy in info.group_calls: - # Look up the reference of this group call. - key = (call.group, reverse, fuzzy) - ref = call_refs.get(key) - if ref is None: - # This group doesn't have a reference yet, so look up its features. - if call.group == 0: - # Calling the pattern as a whole. - rev = bool(info.flags & REVERSE) - fuz = isinstance(parsed, Fuzzy) - if (rev, fuz) != (reverse, fuzzy): - # The pattern as a whole doesn't have the features we want, - # so we'll need to make a copy of it with the desired - # features. - additional_groups.append((parsed, reverse, fuzzy)) - else: - # Calling a capture group. - def_info = info.defined_groups[call.group] - group = def_info[0] - if def_info[1 : ] != (reverse, fuzzy): - # The group doesn't have the features we want, so we'll - # need to make a copy of it with the desired features. - additional_groups.append((group, reverse, fuzzy)) - - ref = len(call_refs) - call_refs[key] = ref - - call.call_ref = ref - - info.call_refs = call_refs - info.additional_groups = additional_groups - -def _get_required_string(parsed, flags): - "Gets the required string and related info of a parsed pattern." - - req_offset, required = parsed.get_required_string(bool(flags & REVERSE)) - if required: - required.required = True - if req_offset >= UNLIMITED: - req_offset = -1 - - req_flags = required.case_flags - if not (flags & UNICODE): - req_flags &= ~UNICODE - - req_chars = required.folded_characters - else: - req_offset = 0 - req_chars = () - req_flags = 0 - - return req_offset, req_chars, req_flags - -class Scanner: - def __init__(self, lexicon, flags=0): - self.lexicon = lexicon - - # Combine phrases into a compound pattern. - patterns = [] - for phrase, action in lexicon: - # Parse the regular expression. - source = Source(phrase) - info = Info(flags, source.char_type) - source.ignore_space = bool(info.flags & VERBOSE) - parsed = _parse_pattern(source, info) - if not source.at_end(): - raise error("trailing characters at position %d" % source.pos) - - # We want to forbid capture groups within each phrase. - patterns.append(parsed.remove_captures()) - - # Combine all the subpatterns into one pattern. - info = Info(flags) - patterns = [Group(info, g + 1, p) for g, p in enumerate(patterns)] - parsed = Branch(patterns) - - # Optimise the compound pattern. - parsed = parsed.optimise(info) - parsed = parsed.pack_characters(info) - - # Get the required string. - req_offset, req_chars, req_flags = _get_required_string(parsed, - info.flags) - - # Check the features of the groups. - _check_group_features(info, parsed) - - # Complain if there are any group calls. They are not supported by the - # Scanner class. - if info.call_refs: - raise error("recursive regex not supported by Scanner") - - reverse = bool(info.flags & REVERSE) - - # Compile the compound pattern. The result is a list of tuples. - code = parsed.compile(reverse) + [(OP.SUCCESS, )] - - # Flatten the code into a list of ints. - code = _flatten_code(code) - - if not parsed.has_simple_start(): - # Get the first set, if possible. - try: - fs_code = _compile_firstset(info, parsed.get_firstset(reverse)) - fs_code = _flatten_code(fs_code) - code = fs_code + code - except _FirstSetError: - pass - - # Check the global flags for conflicts. - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - if version not in (0, VERSION0, VERSION1): - raise ValueError("VERSION0 and VERSION1 flags are mutually incompatible") - - # Create the PatternObject. - # - # Local flags like IGNORECASE affect the code generation, but aren't - # needed by the PatternObject itself. Conversely, global flags like - # LOCALE _don't_ affect the code generation but _are_ needed by the - # PatternObject. - self.scanner = _regex.compile(None, (flags & GLOBAL_FLAGS) | version, - code, {}, {}, {}, [], req_offset, req_chars, req_flags, - len(patterns)) - - def scan(self, string): - result = [] - append = result.append - match = self.scanner.scanner(string).match - i = 0 - while True: - m = match() - if not m: - break - j = m.end() - if i == j: - break - action = self.lexicon[m.lastindex - 1][1] - if hasattr(action, '__call__'): - self.match = m - action = action(self, m.group()) - if action is not None: - append(action) - i = j - - return result, string[i : ] - -# Get the known properties dict. -PROPERTIES = _regex.get_properties() - -# Build the inverse of the properties dict. -PROPERTY_NAMES = {} -for prop_name, (prop_id, values) in PROPERTIES.items(): - name, prop_values = PROPERTY_NAMES.get(prop_id, ("", {})) - name = max(name, prop_name, key=len) - PROPERTY_NAMES[prop_id] = name, prop_values - - for val_name, val_id in values.items(): - prop_values[val_id] = max(prop_values.get(val_id, ""), val_name, - key=len) - -# Character escape sequences. -CHARACTER_ESCAPES = { - "a": "\a", - "b": "\b", - "f": "\f", - "n": "\n", - "r": "\r", - "t": "\t", - "v": "\v", -} - -# Predefined character set escape sequences. -CHARSET_ESCAPES = { - "d": lookup_property(None, "Digit", True), - "D": lookup_property(None, "Digit", False), - "s": lookup_property(None, "Space", True), - "S": lookup_property(None, "Space", False), - "w": lookup_property(None, "Word", True), - "W": lookup_property(None, "Word", False), -} - -# Positional escape sequences. -POSITION_ESCAPES = { - "A": StartOfString(), - "b": Boundary(), - "B": Boundary(False), - "m": StartOfWord(), - "M": EndOfWord(), - "Z": EndOfString(), -} - -# Positional escape sequences when WORD flag set. -WORD_POSITION_ESCAPES = dict(POSITION_ESCAPES) -WORD_POSITION_ESCAPES.update({ - "b": DefaultBoundary(), - "B": DefaultBoundary(False), - "m": DefaultStartOfWord(), - "M": DefaultEndOfWord(), -}) diff --git a/lib/regex/_regex_unicode.c b/lib/regex/_regex_unicode.c deleted file mode 100644 index 663a6bed..00000000 --- a/lib/regex/_regex_unicode.c +++ /dev/null @@ -1,12748 +0,0 @@ -/* For Unicode version 6.3.0 */ - -#include "_regex_unicode.h" - -#define RE_BLANK_MASK ((1 << RE_PROP_ZL) | (1 << RE_PROP_ZP)) -#define RE_GRAPH_MASK ((1 << RE_PROP_CC) | (1 << RE_PROP_CS) | (1 << RE_PROP_CN)) -#define RE_WORD_MASK (RE_PROP_M_MASK | (1 << RE_PROP_ND) | (1 << RE_PROP_PC)) - -typedef struct RE_AllCases { - RE_INT32 diffs[RE_MAX_CASES - 1]; -} RE_AllCases; - -typedef struct RE_FullCaseFolding { - RE_INT32 diff; - RE_UINT16 codepoints[RE_MAX_FOLDED - 1]; -} RE_FullCaseFolding; - -/* strings. */ - -char* re_strings[] = { - "-1/2", - "0", - "1", - "1/10", - "1/16", - "1/2", - "1/3", - "1/4", - "1/5", - "1/6", - "1/7", - "1/8", - "1/9", - "10", - "100", - "1000", - "10000", - "100000", - "100000000", - "1000000000000", - "103", - "107", - "11", - "11/2", - "118", - "12", - "122", - "129", - "13", - "13/2", - "130", - "132", - "133", - "14", - "15", - "15/2", - "16", - "17", - "17/2", - "18", - "19", - "2", - "2/3", - "2/5", - "20", - "200", - "2000", - "20000", - "202", - "21", - "214", - "216", - "216000", - "218", - "22", - "220", - "222", - "224", - "226", - "228", - "23", - "230", - "232", - "233", - "234", - "24", - "240", - "25", - "26", - "27", - "28", - "29", - "3", - "3/16", - "3/2", - "3/4", - "3/5", - "3/8", - "30", - "300", - "3000", - "30000", - "31", - "32", - "33", - "34", - "35", - "36", - "37", - "38", - "39", - "4", - "4/5", - "40", - "400", - "4000", - "40000", - "41", - "42", - "43", - "432000", - "44", - "45", - "46", - "47", - "48", - "49", - "5", - "5/2", - "5/6", - "5/8", - "50", - "500", - "5000", - "50000", - "6", - "60", - "600", - "6000", - "60000", - "7", - "7/2", - "7/8", - "70", - "700", - "7000", - "70000", - "8", - "80", - "800", - "8000", - "80000", - "84", - "9", - "9/2", - "90", - "900", - "9000", - "90000", - "91", - "A", - "ABOVE", - "ABOVELEFT", - "ABOVERIGHT", - "AEGEANNUMBERS", - "AHEX", - "AI", - "AIN", - "AL", - "ALAPH", - "ALCHEMICAL", - "ALCHEMICALSYMBOLS", - "ALEF", - "ALETTER", - "ALNUM", - "ALPHA", - "ALPHABETIC", - "ALPHABETICPF", - "ALPHABETICPRESENTATIONFORMS", - "ALPHANUMERIC", - "AMBIGUOUS", - "AN", - "ANCIENTGREEKMUSIC", - "ANCIENTGREEKMUSICALNOTATION", - "ANCIENTGREEKNUMBERS", - "ANCIENTSYMBOLS", - "ANY", - "AR", - "ARAB", - "ARABIC", - "ARABICEXTA", - "ARABICEXTENDEDA", - "ARABICLETTER", - "ARABICMATH", - "ARABICMATHEMATICALALPHABETICSYMBOLS", - "ARABICNUMBER", - "ARABICPFA", - "ARABICPFB", - "ARABICPRESENTATIONFORMSA", - "ARABICPRESENTATIONFORMSB", - "ARABICSUP", - "ARABICSUPPLEMENT", - "ARMENIAN", - "ARMI", - "ARMN", - "ARROWS", - "ASCII", - "ASCIIHEXDIGIT", - "ASSIGNED", - "AT", - "ATA", - "ATAR", - "ATB", - "ATBL", - "ATERM", - "ATTACHEDABOVE", - "ATTACHEDABOVERIGHT", - "ATTACHEDBELOW", - "ATTACHEDBELOWLEFT", - "AVAGRAHA", - "AVESTAN", - "AVST", - "B", - "B2", - "BA", - "BALI", - "BALINESE", - "BAMU", - "BAMUM", - "BAMUMSUP", - "BAMUMSUPPLEMENT", - "BASICLATIN", - "BATAK", - "BATK", - "BB", - "BC", - "BEH", - "BELOW", - "BELOWLEFT", - "BELOWRIGHT", - "BENG", - "BENGALI", - "BETH", - "BIDIC", - "BIDICLASS", - "BIDICONTROL", - "BIDIM", - "BIDIMIRRORED", - "BINDU", - "BK", - "BL", - "BLANK", - "BLK", - "BLOCK", - "BLOCKELEMENTS", - "BN", - "BOPO", - "BOPOMOFO", - "BOPOMOFOEXT", - "BOPOMOFOEXTENDED", - "BOTTOM", - "BOTTOMANDRIGHT", - "BOUNDARYNEUTRAL", - "BOXDRAWING", - "BR", - "BRAH", - "BRAHMI", - "BRAI", - "BRAILLE", - "BRAILLEPATTERNS", - "BREAKAFTER", - "BREAKBEFORE", - "BREAKBOTH", - "BREAKSYMBOLS", - "BUGI", - "BUGINESE", - "BUHD", - "BUHID", - "BURUSHASKIYEHBARREE", - "BYZANTINEMUSIC", - "BYZANTINEMUSICALSYMBOLS", - "C", - "C&", - "CAKM", - "CAN", - "CANADIANABORIGINAL", - "CANADIANSYLLABICS", - "CANONICAL", - "CANONICALCOMBININGCLASS", - "CANS", - "CARI", - "CARIAN", - "CARRIAGERETURN", - "CASED", - "CASEDLETTER", - "CASEIGNORABLE", - "CB", - "CC", - "CCC", - "CCC10", - "CCC103", - "CCC107", - "CCC11", - "CCC118", - "CCC12", - "CCC122", - "CCC129", - "CCC13", - "CCC130", - "CCC132", - "CCC133", - "CCC14", - "CCC15", - "CCC16", - "CCC17", - "CCC18", - "CCC19", - "CCC20", - "CCC21", - "CCC22", - "CCC23", - "CCC24", - "CCC25", - "CCC26", - "CCC27", - "CCC28", - "CCC29", - "CCC30", - "CCC31", - "CCC32", - "CCC33", - "CCC34", - "CCC35", - "CCC36", - "CCC84", - "CCC91", - "CF", - "CHAKMA", - "CHAM", - "CHANGESWHENCASEFOLDED", - "CHANGESWHENCASEMAPPED", - "CHANGESWHENLOWERCASED", - "CHANGESWHENTITLECASED", - "CHANGESWHENUPPERCASED", - "CHER", - "CHEROKEE", - "CI", - "CIRCLE", - "CJ", - "CJK", - "CJKCOMPAT", - "CJKCOMPATFORMS", - "CJKCOMPATIBILITY", - "CJKCOMPATIBILITYFORMS", - "CJKCOMPATIBILITYIDEOGRAPHS", - "CJKCOMPATIBILITYIDEOGRAPHSSUPPLEMENT", - "CJKCOMPATIDEOGRAPHS", - "CJKCOMPATIDEOGRAPHSSUP", - "CJKEXTA", - "CJKEXTB", - "CJKEXTC", - "CJKEXTD", - "CJKRADICALSSUP", - "CJKRADICALSSUPPLEMENT", - "CJKSTROKES", - "CJKSYMBOLS", - "CJKSYMBOLSANDPUNCTUATION", - "CJKUNIFIEDIDEOGRAPHS", - "CJKUNIFIEDIDEOGRAPHSEXTENSIONA", - "CJKUNIFIEDIDEOGRAPHSEXTENSIONB", - "CJKUNIFIEDIDEOGRAPHSEXTENSIONC", - "CJKUNIFIEDIDEOGRAPHSEXTENSIOND", - "CL", - "CLOSE", - "CLOSEPARENTHESIS", - "CLOSEPUNCTUATION", - "CM", - "CN", - "CNTRL", - "CO", - "COM", - "COMBININGDIACRITICALMARKS", - "COMBININGDIACRITICALMARKSFORSYMBOLS", - "COMBININGDIACRITICALMARKSSUPPLEMENT", - "COMBININGHALFMARKS", - "COMBININGMARK", - "COMBININGMARKSFORSYMBOLS", - "COMMON", - "COMMONINDICNUMBERFORMS", - "COMMONSEPARATOR", - "COMPAT", - "COMPATJAMO", - "COMPLEXCONTEXT", - "CONDITIONALJAPANESESTARTER", - "CONNECTORPUNCTUATION", - "CONSONANT", - "CONSONANTDEAD", - "CONSONANTFINAL", - "CONSONANTHEADLETTER", - "CONSONANTMEDIAL", - "CONSONANTPLACEHOLDER", - "CONSONANTREPHA", - "CONSONANTSUBJOINED", - "CONTINGENTBREAK", - "CONTROL", - "CONTROLPICTURES", - "COPT", - "COPTIC", - "COUNTINGROD", - "COUNTINGRODNUMERALS", - "CP", - "CPRT", - "CR", - "CS", - "CUNEIFORM", - "CUNEIFORMNUMBERS", - "CUNEIFORMNUMBERSANDPUNCTUATION", - "CURRENCYSYMBOL", - "CURRENCYSYMBOLS", - "CWCF", - "CWCM", - "CWL", - "CWT", - "CWU", - "CYPRIOT", - "CYPRIOTSYLLABARY", - "CYRILLIC", - "CYRILLICEXTA", - "CYRILLICEXTB", - "CYRILLICEXTENDEDA", - "CYRILLICEXTENDEDB", - "CYRILLICSUP", - "CYRILLICSUPPLEMENT", - "CYRILLICSUPPLEMENTARY", - "CYRL", - "D", - "DA", - "DAL", - "DALATHRISH", - "DASH", - "DASHPUNCTUATION", - "DB", - "DE", - "DECIMAL", - "DECIMALNUMBER", - "DECOMPOSITIONTYPE", - "DEFAULTIGNORABLECODEPOINT", - "DEP", - "DEPRECATED", - "DESERET", - "DEVA", - "DEVANAGARI", - "DEVANAGARIEXT", - "DEVANAGARIEXTENDED", - "DI", - "DIA", - "DIACRITIC", - "DIACRITICALS", - "DIACRITICALSFORSYMBOLS", - "DIACRITICALSSUP", - "DIGIT", - "DINGBATS", - "DOMINO", - "DOMINOTILES", - "DOUBLEABOVE", - "DOUBLEBELOW", - "DOUBLEQUOTE", - "DQ", - "DSRT", - "DT", - "DUALJOINING", - "E", - "EA", - "EASTASIANWIDTH", - "EGYP", - "EGYPTIANHIEROGLYPHS", - "EMOTICONS", - "EN", - "ENC", - "ENCLOSEDALPHANUM", - "ENCLOSEDALPHANUMERICS", - "ENCLOSEDALPHANUMERICSUPPLEMENT", - "ENCLOSEDALPHANUMSUP", - "ENCLOSEDCJK", - "ENCLOSEDCJKLETTERSANDMONTHS", - "ENCLOSEDIDEOGRAPHICSUP", - "ENCLOSEDIDEOGRAPHICSUPPLEMENT", - "ENCLOSINGMARK", - "ES", - "ET", - "ETHI", - "ETHIOPIC", - "ETHIOPICEXT", - "ETHIOPICEXTA", - "ETHIOPICEXTENDED", - "ETHIOPICEXTENDEDA", - "ETHIOPICSUP", - "ETHIOPICSUPPLEMENT", - "EUROPEANNUMBER", - "EUROPEANSEPARATOR", - "EUROPEANTERMINATOR", - "EX", - "EXCLAMATION", - "EXT", - "EXTEND", - "EXTENDER", - "EXTENDNUMLET", - "F", - "FALSE", - "FARSIYEH", - "FE", - "FEH", - "FIN", - "FINAL", - "FINALPUNCTUATION", - "FINALSEMKATH", - "FIRSTSTRONGISOLATE", - "FO", - "FONT", - "FORMAT", - "FRA", - "FRACTION", - "FSI", - "FULLWIDTH", - "GAF", - "GAMAL", - "GC", - "GCB", - "GENERALCATEGORY", - "GENERALPUNCTUATION", - "GEOMETRICSHAPES", - "GEOR", - "GEORGIAN", - "GEORGIANSUP", - "GEORGIANSUPPLEMENT", - "GL", - "GLAG", - "GLAGOLITIC", - "GLUE", - "GOTH", - "GOTHIC", - "GRAPH", - "GRAPHEMEBASE", - "GRAPHEMECLUSTERBREAK", - "GRAPHEMEEXTEND", - "GRAPHEMELINK", - "GRBASE", - "GREEK", - "GREEKANDCOPTIC", - "GREEKEXT", - "GREEKEXTENDED", - "GREK", - "GREXT", - "GRLINK", - "GUJARATI", - "GUJR", - "GURMUKHI", - "GURU", - "H", - "H2", - "H3", - "HAH", - "HALFANDFULLFORMS", - "HALFMARKS", - "HALFWIDTH", - "HALFWIDTHANDFULLWIDTHFORMS", - "HAMZAONHEHGOAL", - "HAN", - "HANG", - "HANGUL", - "HANGULCOMPATIBILITYJAMO", - "HANGULJAMO", - "HANGULJAMOEXTENDEDA", - "HANGULJAMOEXTENDEDB", - "HANGULSYLLABLES", - "HANGULSYLLABLETYPE", - "HANI", - "HANO", - "HANUNOO", - "HE", - "HEBR", - "HEBREW", - "HEBREWLETTER", - "HEH", - "HEHGOAL", - "HETH", - "HEX", - "HEXDIGIT", - "HIGHPRIVATEUSESURROGATES", - "HIGHPUSURROGATES", - "HIGHSURROGATES", - "HIRA", - "HIRAGANA", - "HL", - "HRKT", - "HST", - "HY", - "HYPHEN", - "ID", - "IDC", - "IDCONTINUE", - "IDEO", - "IDEOGRAPHIC", - "IDEOGRAPHICDESCRIPTIONCHARACTERS", - "IDS", - "IDSB", - "IDSBINARYOPERATOR", - "IDST", - "IDSTART", - "IDSTRINARYOPERATOR", - "IMPERIALARAMAIC", - "IN", - "INDICMATRACATEGORY", - "INDICNUMBERFORMS", - "INDICSYLLABICCATEGORY", - "INFIXNUMERIC", - "INHERITED", - "INIT", - "INITIAL", - "INITIALPUNCTUATION", - "INMC", - "INSC", - "INSCRIPTIONALPAHLAVI", - "INSCRIPTIONALPARTHIAN", - "INSEPARABLE", - "INSEPERABLE", - "INVISIBLE", - "IOTASUBSCRIPT", - "IPAEXT", - "IPAEXTENSIONS", - "IS", - "ISO", - "ISOLATED", - "ITAL", - "JAMO", - "JAMOEXTA", - "JAMOEXTB", - "JAVA", - "JAVANESE", - "JG", - "JL", - "JOINC", - "JOINCAUSING", - "JOINCONTROL", - "JOININGGROUP", - "JOININGTYPE", - "JT", - "JV", - "KA", - "KAF", - "KAITHI", - "KALI", - "KANA", - "KANASUP", - "KANASUPPLEMENT", - "KANAVOICING", - "KANBUN", - "KANGXI", - "KANGXIRADICALS", - "KANNADA", - "KAPH", - "KATAKANA", - "KATAKANAEXT", - "KATAKANAORHIRAGANA", - "KATAKANAPHONETICEXTENSIONS", - "KAYAHLI", - "KHAPH", - "KHAR", - "KHAROSHTHI", - "KHMER", - "KHMERSYMBOLS", - "KHMR", - "KNDA", - "KNOTTEDHEH", - "KTHI", - "KV", - "L", - "L&", - "LAM", - "LAMADH", - "LANA", - "LAO", - "LAOO", - "LATIN", - "LATIN1", - "LATIN1SUP", - "LATIN1SUPPLEMENT", - "LATINEXTA", - "LATINEXTADDITIONAL", - "LATINEXTB", - "LATINEXTC", - "LATINEXTD", - "LATINEXTENDEDA", - "LATINEXTENDEDADDITIONAL", - "LATINEXTENDEDB", - "LATINEXTENDEDC", - "LATINEXTENDEDD", - "LATN", - "LB", - "LC", - "LE", - "LEADINGJAMO", - "LEFT", - "LEFTANDRIGHT", - "LEFTJOINING", - "LEFTTORIGHT", - "LEFTTORIGHTEMBEDDING", - "LEFTTORIGHTISOLATE", - "LEFTTORIGHTOVERRIDE", - "LEPC", - "LEPCHA", - "LETTER", - "LETTERLIKESYMBOLS", - "LETTERNUMBER", - "LF", - "LIMB", - "LIMBU", - "LINB", - "LINEARB", - "LINEARBIDEOGRAMS", - "LINEARBSYLLABARY", - "LINEBREAK", - "LINEFEED", - "LINESEPARATOR", - "LISU", - "LL", - "LM", - "LO", - "LOE", - "LOGICALORDEREXCEPTION", - "LOWER", - "LOWERCASE", - "LOWERCASELETTER", - "LOWSURROGATES", - "LRE", - "LRI", - "LRO", - "LT", - "LU", - "LV", - "LVSYLLABLE", - "LVT", - "LVTSYLLABLE", - "LYCI", - "LYCIAN", - "LYDI", - "LYDIAN", - "M", - "M&", - "MAHJONG", - "MAHJONGTILES", - "MALAYALAM", - "MAND", - "MANDAIC", - "MANDATORYBREAK", - "MARK", - "MATH", - "MATHALPHANUM", - "MATHEMATICALALPHANUMERICSYMBOLS", - "MATHEMATICALOPERATORS", - "MATHOPERATORS", - "MATHSYMBOL", - "MB", - "MC", - "ME", - "MED", - "MEDIAL", - "MEEM", - "MEETEIMAYEK", - "MEETEIMAYEKEXT", - "MEETEIMAYEKEXTENSIONS", - "MERC", - "MERO", - "MEROITICCURSIVE", - "MEROITICHIEROGLYPHS", - "MIAO", - "MIDLETTER", - "MIDNUM", - "MIDNUMLET", - "MIM", - "MISCARROWS", - "MISCELLANEOUSMATHEMATICALSYMBOLSA", - "MISCELLANEOUSMATHEMATICALSYMBOLSB", - "MISCELLANEOUSSYMBOLS", - "MISCELLANEOUSSYMBOLSANDARROWS", - "MISCELLANEOUSSYMBOLSANDPICTOGRAPHS", - "MISCELLANEOUSTECHNICAL", - "MISCMATHSYMBOLSA", - "MISCMATHSYMBOLSB", - "MISCPICTOGRAPHS", - "MISCSYMBOLS", - "MISCTECHNICAL", - "ML", - "MLYM", - "MN", - "MODIFIERLETTER", - "MODIFIERLETTERS", - "MODIFIERSYMBOL", - "MODIFIERTONELETTERS", - "MODIFYINGLETTER", - "MONG", - "MONGOLIAN", - "MTEI", - "MUSIC", - "MUSICALSYMBOLS", - "MYANMAR", - "MYANMAREXTA", - "MYANMAREXTENDEDA", - "MYMR", - "N", - "N&", - "NA", - "NAN", - "NAR", - "NARROW", - "NB", - "NCHAR", - "ND", - "NEUTRAL", - "NEWLINE", - "NEWTAILUE", - "NEXTLINE", - "NK", - "NKO", - "NKOO", - "NL", - "NO", - "NOBLOCK", - "NOBREAK", - "NOJOININGGROUP", - "NONCHARACTERCODEPOINT", - "NONE", - "NONJOINING", - "NONSPACINGMARK", - "NONSTARTER", - "NOON", - "NOTAPPLICABLE", - "NOTREORDERED", - "NR", - "NS", - "NSM", - "NT", - "NU", - "NUKTA", - "NUMBER", - "NUMBERFORMS", - "NUMERIC", - "NUMERICTYPE", - "NUMERICVALUE", - "NUN", - "NV", - "NYA", - "OALPHA", - "OCR", - "ODI", - "OGAM", - "OGHAM", - "OGREXT", - "OIDC", - "OIDS", - "OLCHIKI", - "OLCK", - "OLDITALIC", - "OLDPERSIAN", - "OLDSOUTHARABIAN", - "OLDTURKIC", - "OLETTER", - "OLOWER", - "OMATH", - "ON", - "OP", - "OPENPUNCTUATION", - "OPTICALCHARACTERRECOGNITION", - "ORIYA", - "ORKH", - "ORYA", - "OSMA", - "OSMANYA", - "OTHER", - "OTHERALPHABETIC", - "OTHERDEFAULTIGNORABLECODEPOINT", - "OTHERGRAPHEMEEXTEND", - "OTHERIDCONTINUE", - "OTHERIDSTART", - "OTHERLETTER", - "OTHERLOWERCASE", - "OTHERMATH", - "OTHERNEUTRAL", - "OTHERNUMBER", - "OTHERPUNCTUATION", - "OTHERSYMBOL", - "OTHERUPPERCASE", - "OUPPER", - "OV", - "OVERLAY", - "OVERSTRUCK", - "P", - "P&", - "PARAGRAPHSEPARATOR", - "PATSYN", - "PATTERNSYNTAX", - "PATTERNWHITESPACE", - "PATWS", - "PC", - "PD", - "PDF", - "PDI", - "PE", - "PF", - "PHAG", - "PHAGSPA", - "PHAISTOS", - "PHAISTOSDISC", - "PHLI", - "PHNX", - "PHOENICIAN", - "PHONETICEXT", - "PHONETICEXTENSIONS", - "PHONETICEXTENSIONSSUPPLEMENT", - "PHONETICEXTSUP", - "PI", - "PLAYINGCARDS", - "PLRD", - "PO", - "POPDIRECTIONALFORMAT", - "POPDIRECTIONALISOLATE", - "POSTFIXNUMERIC", - "PP", - "PR", - "PREFIXNUMERIC", - "PREPEND", - "PRINT", - "PRIVATEUSE", - "PRIVATEUSEAREA", - "PRTI", - "PS", - "PUA", - "PUNCT", - "PUNCTUATION", - "QAAC", - "QAAI", - "QAF", - "QAPH", - "QMARK", - "QU", - "QUOTATION", - "QUOTATIONMARK", - "R", - "RADICAL", - "REGIONALINDICATOR", - "REGISTERSHIFTER", - "REH", - "REJANG", - "REVERSEDPE", - "RI", - "RIGHT", - "RIGHTJOINING", - "RIGHTTOLEFT", - "RIGHTTOLEFTEMBEDDING", - "RIGHTTOLEFTISOLATE", - "RIGHTTOLEFTOVERRIDE", - "RJNG", - "RLE", - "RLI", - "RLO", - "ROHINGYAYEH", - "RUMI", - "RUMINUMERALSYMBOLS", - "RUNIC", - "RUNR", - "S", - "S&", - "SA", - "SAD", - "SADHE", - "SAMARITAN", - "SAMR", - "SARB", - "SAUR", - "SAURASHTRA", - "SB", - "SC", - "SCONTINUE", - "SCRIPT", - "SD", - "SE", - "SEEN", - "SEGMENTSEPARATOR", - "SEMKATH", - "SENTENCEBREAK", - "SEP", - "SEPARATOR", - "SG", - "SHARADA", - "SHAVIAN", - "SHAW", - "SHIN", - "SHRD", - "SINGLEQUOTE", - "SINH", - "SINHALA", - "SK", - "SM", - "SMALL", - "SMALLFORMS", - "SMALLFORMVARIANTS", - "SML", - "SO", - "SOFTDOTTED", - "SORA", - "SORASOMPENG", - "SP", - "SPACE", - "SPACESEPARATOR", - "SPACINGMARK", - "SPACINGMODIFIERLETTERS", - "SPECIALS", - "SQ", - "SQR", - "SQUARE", - "ST", - "STERM", - "SUB", - "SUND", - "SUNDANESE", - "SUNDANESESUP", - "SUNDANESESUPPLEMENT", - "SUP", - "SUPARROWSA", - "SUPARROWSB", - "SUPER", - "SUPERANDSUB", - "SUPERSCRIPTSANDSUBSCRIPTS", - "SUPMATHOPERATORS", - "SUPPLEMENTALARROWSA", - "SUPPLEMENTALARROWSB", - "SUPPLEMENTALMATHEMATICALOPERATORS", - "SUPPLEMENTALPUNCTUATION", - "SUPPLEMENTARYPRIVATEUSEAREAA", - "SUPPLEMENTARYPRIVATEUSEAREAB", - "SUPPUAA", - "SUPPUAB", - "SUPPUNCTUATION", - "SURROGATE", - "SWASHKAF", - "SY", - "SYLO", - "SYLOTINAGRI", - "SYMBOL", - "SYRC", - "SYRIAC", - "SYRIACWAW", - "T", - "TAGALOG", - "TAGB", - "TAGBANWA", - "TAGS", - "TAH", - "TAILE", - "TAITHAM", - "TAIVIET", - "TAIXUANJING", - "TAIXUANJINGSYMBOLS", - "TAKR", - "TAKRI", - "TALE", - "TALU", - "TAMIL", - "TAML", - "TAVT", - "TAW", - "TEHMARBUTA", - "TEHMARBUTAGOAL", - "TELU", - "TELUGU", - "TERM", - "TERMINALPUNCTUATION", - "TETH", - "TFNG", - "TGLG", - "THAA", - "THAANA", - "THAI", - "TIBETAN", - "TIBT", - "TIFINAGH", - "TITLECASELETTER", - "TONELETTER", - "TONEMARK", - "TOP", - "TOPANDBOTTOM", - "TOPANDBOTTOMANDRIGHT", - "TOPANDLEFT", - "TOPANDLEFTANDRIGHT", - "TOPANDRIGHT", - "TRAILINGJAMO", - "TRANSPARENT", - "TRANSPORTANDMAP", - "TRANSPORTANDMAPSYMBOLS", - "TRUE", - "U", - "UCAS", - "UCASEXT", - "UGAR", - "UGARITIC", - "UIDEO", - "UNASSIGNED", - "UNIFIEDCANADIANABORIGINALSYLLABICS", - "UNIFIEDCANADIANABORIGINALSYLLABICSEXTENDED", - "UNIFIEDIDEOGRAPH", - "UNKNOWN", - "UP", - "UPPER", - "UPPERCASE", - "UPPERCASELETTER", - "V", - "VAI", - "VAII", - "VARIATIONSELECTOR", - "VARIATIONSELECTORS", - "VARIATIONSELECTORSSUPPLEMENT", - "VEDICEXT", - "VEDICEXTENSIONS", - "VERT", - "VERTICAL", - "VERTICALFORMS", - "VIRAMA", - "VISARGA", - "VISUALORDERLEFT", - "VOWEL", - "VOWELDEPENDENT", - "VOWELINDEPENDENT", - "VOWELJAMO", - "VR", - "VS", - "VSSUP", - "W", - "WAW", - "WB", - "WHITESPACE", - "WIDE", - "WJ", - "WORD", - "WORDBREAK", - "WORDJOINER", - "WS", - "WSPACE", - "XDIGIT", - "XIDC", - "XIDCONTINUE", - "XIDS", - "XIDSTART", - "XPEO", - "XSUX", - "XX", - "Y", - "YEH", - "YEHBARREE", - "YEHWITHTAIL", - "YES", - "YI", - "YIII", - "YIJING", - "YIJINGHEXAGRAMSYMBOLS", - "YIRADICALS", - "YISYLLABLES", - "YUDH", - "YUDHHE", - "Z", - "Z&", - "ZAIN", - "ZHAIN", - "ZINH", - "ZL", - "ZP", - "ZS", - "ZW", - "ZWSPACE", - "ZYYY", - "ZZZZ", -}; - -/* strings: 10595 bytes. */ - -/* properties. */ - -RE_Property re_properties[] = { - { 508, 0, 0}, - { 506, 0, 0}, - { 233, 1, 1}, - { 232, 1, 1}, - { 963, 2, 2}, - { 961, 2, 2}, - {1123, 3, 3}, - {1118, 3, 3}, - { 523, 4, 4}, - { 507, 4, 4}, - { 969, 5, 5}, - { 960, 5, 5}, - { 736, 6, 6}, - { 156, 7, 6}, - { 155, 7, 6}, - { 711, 8, 6}, - { 710, 8, 6}, - {1093, 9, 6}, - {1092, 9, 6}, - { 273, 10, 6}, - { 275, 11, 6}, - { 326, 11, 6}, - { 321, 12, 6}, - { 401, 12, 6}, - { 323, 13, 6}, - { 403, 13, 6}, - { 322, 14, 6}, - { 402, 14, 6}, - { 319, 15, 6}, - { 399, 15, 6}, - { 320, 16, 6}, - { 400, 16, 6}, - { 588, 17, 6}, - { 584, 17, 6}, - { 580, 18, 6}, - { 579, 18, 6}, - {1131, 19, 6}, - {1130, 19, 6}, - {1129, 20, 6}, - {1128, 20, 6}, - { 426, 21, 6}, - { 434, 21, 6}, - { 524, 22, 6}, - { 532, 22, 6}, - { 522, 23, 6}, - { 526, 23, 6}, - { 525, 24, 6}, - { 533, 24, 6}, - {1119, 25, 6}, - {1126, 25, 6}, - { 992, 25, 6}, - { 225, 26, 6}, - { 223, 26, 6}, - { 623, 27, 6}, - { 621, 27, 6}, - { 419, 28, 6}, - { 577, 29, 6}, - { 926, 30, 6}, - { 923, 30, 6}, - {1056, 31, 6}, - {1055, 31, 6}, - { 866, 32, 6}, - { 848, 32, 6}, - { 567, 33, 6}, - { 566, 33, 6}, - { 187, 34, 6}, - { 145, 34, 6}, - { 859, 35, 6}, - { 832, 35, 6}, - { 582, 36, 6}, - { 581, 36, 6}, - { 436, 37, 6}, - { 435, 37, 6}, - { 485, 38, 6}, - { 483, 38, 6}, - { 865, 39, 6}, - { 847, 39, 6}, - { 871, 40, 6}, - { 872, 40, 6}, - { 810, 41, 6}, - { 796, 41, 6}, - { 861, 42, 6}, - { 837, 42, 6}, - { 586, 43, 6}, - { 585, 43, 6}, - { 589, 44, 6}, - { 587, 44, 6}, - { 928, 45, 6}, - {1089, 46, 6}, - {1085, 46, 6}, - { 860, 47, 6}, - { 834, 47, 6}, - { 428, 48, 6}, - { 427, 48, 6}, - { 988, 49, 6}, - { 964, 49, 6}, - { 709, 50, 6}, - { 708, 50, 6}, - { 863, 51, 6}, - { 839, 51, 6}, - { 862, 52, 6}, - { 838, 52, 6}, - {1001, 53, 6}, - {1098, 54, 6}, - {1114, 54, 6}, - { 881, 55, 6}, - { 882, 55, 6}, - { 880, 56, 6}, - { 879, 56, 6}, - { 555, 57, 7}, - { 575, 57, 7}, - { 224, 58, 8}, - { 215, 58, 8}, - { 268, 59, 9}, - { 278, 59, 9}, - { 425, 60, 10}, - { 449, 60, 10}, - { 453, 61, 11}, - { 452, 61, 11}, - { 624, 62, 12}, - { 619, 62, 12}, - { 625, 63, 13}, - { 626, 63, 13}, - { 701, 64, 14}, - { 678, 64, 14}, - { 827, 65, 15}, - { 821, 65, 15}, - { 828, 66, 16}, - { 830, 66, 16}, - { 227, 67, 6}, - { 226, 67, 6}, - { 592, 68, 17}, - { 600, 68, 17}, - { 594, 69, 18}, - { 601, 69, 18}, - { 159, 70, 6}, - { 154, 70, 6}, - { 166, 71, 6}, - { 231, 72, 6}, - { 521, 73, 6}, - { 911, 74, 6}, - {1122, 75, 6}, - {1127, 76, 6}, -}; - -/* properties: 572 bytes. */ - -/* property values. */ - -RE_PropertyValue re_property_values[] = { - {1086, 0, 0}, - { 357, 0, 0}, - {1094, 0, 1}, - { 718, 0, 1}, - { 712, 0, 2}, - { 705, 0, 2}, - {1066, 0, 3}, - { 717, 0, 3}, - { 775, 0, 4}, - { 706, 0, 4}, - { 864, 0, 5}, - { 707, 0, 5}, - { 813, 0, 6}, - { 774, 0, 6}, - { 467, 0, 7}, - { 744, 0, 7}, - { 994, 0, 8}, - { 743, 0, 8}, - { 424, 0, 9}, - { 797, 0, 9}, - { 440, 0, 9}, - { 693, 0, 10}, - { 805, 0, 10}, - { 868, 0, 11}, - { 806, 0, 11}, - { 993, 0, 12}, - {1155, 0, 12}, - { 703, 0, 13}, - {1153, 0, 13}, - { 878, 0, 14}, - {1154, 0, 14}, - { 384, 0, 15}, - { 277, 0, 15}, - { 358, 0, 15}, - { 499, 0, 16}, - { 316, 0, 16}, - { 912, 0, 17}, - { 359, 0, 17}, - {1023, 0, 18}, - { 393, 0, 18}, - { 420, 0, 19}, - { 884, 0, 19}, - { 851, 0, 20}, - { 915, 0, 20}, - { 355, 0, 21}, - { 887, 0, 21}, - { 374, 0, 22}, - { 883, 0, 22}, - { 869, 0, 23}, - { 903, 0, 23}, - { 741, 0, 24}, - { 982, 0, 24}, - { 397, 0, 25}, - { 961, 0, 25}, - { 777, 0, 26}, - { 981, 0, 26}, - { 870, 0, 27}, - { 987, 0, 27}, - { 599, 0, 28}, - { 900, 0, 28}, - { 494, 0, 29}, - { 888, 0, 29}, - { 858, 0, 30}, - { 261, 0, 30}, - { 262, 0, 30}, - { 691, 0, 31}, - { 656, 0, 31}, - { 657, 0, 31}, - { 735, 0, 32}, - { 727, 0, 32}, - { 365, 0, 32}, - { 728, 0, 32}, - { 824, 0, 33}, - { 789, 0, 33}, - { 790, 0, 33}, - { 918, 0, 34}, - { 876, 0, 34}, - { 917, 0, 34}, - { 877, 0, 34}, - {1028, 0, 35}, - { 950, 0, 35}, - { 951, 0, 35}, - { 971, 0, 36}, - {1148, 0, 36}, - {1149, 0, 36}, - { 274, 0, 37}, - { 679, 0, 37}, - { 188, 0, 38}, - { 807, 1, 0}, - { 795, 1, 0}, - { 211, 1, 1}, - { 186, 1, 1}, - { 666, 1, 2}, - { 665, 1, 2}, - { 664, 1, 2}, - { 672, 1, 3}, - { 667, 1, 3}, - { 674, 1, 4}, - { 669, 1, 4}, - { 609, 1, 5}, - { 608, 1, 5}, - { 995, 1, 6}, - { 776, 1, 6}, - { 361, 1, 7}, - { 437, 1, 7}, - { 528, 1, 8}, - { 527, 1, 8}, - { 406, 1, 9}, - { 412, 1, 10}, - { 411, 1, 10}, - { 413, 1, 10}, - { 182, 1, 11}, - { 561, 1, 12}, - { 169, 1, 13}, - {1030, 1, 14}, - { 181, 1, 15}, - { 180, 1, 15}, - {1061, 1, 16}, - { 803, 1, 17}, - { 955, 1, 18}, - { 733, 1, 19}, - { 171, 1, 20}, - { 170, 1, 20}, - { 431, 1, 21}, - { 221, 1, 22}, - { 536, 1, 23}, - { 534, 1, 24}, - { 853, 1, 25}, - {1047, 1, 26}, - {1054, 1, 27}, - { 639, 1, 28}, - { 731, 1, 29}, - { 980, 1, 30}, - {1062, 1, 31}, - { 661, 1, 32}, - {1063, 1, 33}, - { 785, 1, 34}, - { 512, 1, 35}, - { 551, 1, 36}, - { 614, 1, 36}, - { 471, 1, 37}, - { 477, 1, 38}, - { 476, 1, 38}, - { 325, 1, 39}, - {1087, 1, 40}, - {1081, 1, 40}, - { 266, 1, 40}, - { 836, 1, 41}, - { 948, 1, 42}, - {1033, 1, 43}, - { 558, 1, 44}, - { 257, 1, 45}, - {1035, 1, 46}, - { 649, 1, 47}, - { 781, 1, 48}, - {1088, 1, 49}, - {1082, 1, 49}, - { 696, 1, 50}, - {1038, 1, 51}, - { 800, 1, 52}, - { 650, 1, 53}, - { 255, 1, 54}, - {1039, 1, 55}, - { 206, 1, 56}, - {1004, 1, 57}, - { 212, 1, 58}, - { 690, 1, 59}, - { 840, 1, 60}, - {1006, 1, 61}, - {1005, 1, 61}, - {1102, 1, 62}, - {1101, 1, 62}, - { 897, 1, 63}, - { 896, 1, 63}, - { 898, 1, 64}, - { 899, 1, 64}, - { 363, 1, 65}, - { 439, 1, 65}, - { 673, 1, 66}, - { 668, 1, 66}, - { 530, 1, 67}, - { 529, 1, 67}, - { 509, 1, 68}, - { 918, 1, 68}, - {1012, 1, 69}, - {1011, 1, 69}, - { 398, 1, 70}, - { 362, 1, 71}, - { 438, 1, 71}, - { 366, 1, 71}, - { 692, 1, 72}, - { 825, 1, 73}, - { 185, 1, 74}, - { 739, 1, 75}, - { 740, 1, 75}, - { 766, 1, 76}, - { 771, 1, 76}, - { 385, 1, 77}, - { 852, 1, 78}, - { 833, 1, 78}, - { 460, 1, 79}, - { 459, 1, 79}, - { 243, 1, 80}, - { 234, 1, 81}, - { 510, 1, 82}, - { 763, 1, 83}, - { 770, 1, 83}, - { 441, 1, 84}, - { 761, 1, 85}, - { 767, 1, 85}, - {1014, 1, 86}, - {1008, 1, 86}, - { 249, 1, 87}, - { 248, 1, 87}, - {1015, 1, 88}, - {1009, 1, 88}, - { 762, 1, 89}, - { 768, 1, 89}, - {1016, 1, 90}, - {1013, 1, 90}, - { 764, 1, 91}, - { 760, 1, 91}, - { 517, 1, 92}, - { 675, 1, 93}, - { 670, 1, 93}, - { 387, 1, 94}, - { 514, 1, 95}, - { 513, 1, 95}, - {1065, 1, 96}, - { 474, 1, 97}, - { 472, 1, 97}, - { 409, 1, 98}, - { 407, 1, 98}, - {1017, 1, 99}, - {1022, 1, 99}, - { 343, 1, 100}, - { 342, 1, 100}, - { 638, 1, 101}, - { 637, 1, 101}, - { 583, 1, 102}, - { 579, 1, 102}, - { 346, 1, 103}, - { 345, 1, 103}, - { 572, 1, 104}, - { 641, 1, 105}, - { 237, 1, 106}, - { 550, 1, 107}, - { 371, 1, 107}, - { 636, 1, 108}, - { 239, 1, 109}, - { 238, 1, 109}, - { 344, 1, 110}, - { 644, 1, 111}, - { 642, 1, 111}, - { 464, 1, 112}, - { 463, 1, 112}, - { 332, 1, 113}, - { 330, 1, 113}, - { 348, 1, 114}, - { 338, 1, 114}, - {1143, 1, 115}, - {1142, 1, 115}, - { 347, 1, 116}, - { 329, 1, 116}, - {1145, 1, 117}, - {1144, 1, 118}, - { 704, 1, 119}, - {1096, 1, 120}, - { 410, 1, 121}, - { 408, 1, 121}, - { 208, 1, 122}, - { 778, 1, 123}, - { 676, 1, 124}, - { 671, 1, 124}, - {1027, 1, 125}, - { 368, 1, 126}, - { 593, 1, 126}, - { 890, 1, 127}, - { 959, 1, 128}, - { 433, 1, 129}, - { 432, 1, 129}, - { 645, 1, 130}, - { 932, 1, 131}, - { 552, 1, 132}, - { 615, 1, 132}, - { 618, 1, 133}, - { 318, 1, 134}, - { 787, 1, 135}, - { 786, 1, 135}, - {1040, 1, 136}, - { 750, 1, 137}, - { 749, 1, 137}, - { 475, 1, 138}, - { 473, 1, 138}, - { 748, 1, 139}, - { 554, 1, 140}, - { 549, 1, 140}, - { 553, 1, 141}, - { 616, 1, 141}, - { 570, 1, 142}, - { 568, 1, 143}, - { 569, 1, 143}, - { 713, 1, 144}, - { 913, 1, 145}, - { 916, 1, 145}, - { 912, 1, 145}, - { 334, 1, 146}, - { 336, 1, 146}, - { 158, 1, 147}, - { 157, 1, 147}, - { 178, 1, 148}, - { 176, 1, 148}, - {1099, 1, 149}, - {1114, 1, 149}, - {1105, 1, 150}, - { 364, 1, 151}, - { 543, 1, 151}, - { 333, 1, 152}, - { 331, 1, 152}, - { 985, 1, 153}, - { 984, 1, 153}, - { 179, 1, 154}, - { 177, 1, 154}, - { 545, 1, 155}, - { 542, 1, 155}, - { 996, 1, 156}, - { 700, 1, 157}, - { 699, 1, 158}, - { 144, 1, 159}, - { 164, 1, 160}, - { 165, 1, 161}, - { 892, 1, 162}, - { 891, 1, 162}, - { 724, 1, 163}, - { 271, 1, 164}, - { 842, 1, 165}, - { 520, 1, 166}, - {1084, 1, 167}, - { 843, 1, 168}, - { 429, 1, 169}, - { 974, 1, 170}, - { 857, 1, 171}, - { 405, 1, 172}, - { 590, 1, 173}, - { 895, 1, 174}, - { 726, 1, 175}, - { 754, 1, 176}, - { 753, 1, 177}, - { 648, 1, 178}, - { 844, 1, 179}, - { 200, 1, 180}, - { 603, 1, 181}, - { 602, 1, 182}, - { 845, 1, 183}, - { 947, 1, 184}, - { 946, 1, 184}, - { 246, 1, 185}, - { 630, 1, 186}, - { 990, 1, 187}, - { 317, 1, 188}, - { 973, 1, 189}, - {1044, 1, 190}, - { 394, 1, 191}, - { 396, 1, 192}, - { 395, 1, 192}, - { 455, 1, 193}, - { 210, 1, 194}, - { 209, 1, 194}, - { 755, 1, 195}, - { 634, 1, 196}, - { 633, 1, 196}, - { 260, 1, 197}, - { 259, 1, 197}, - { 784, 1, 198}, - { 783, 1, 198}, - { 163, 1, 199}, - { 162, 1, 199}, - {1042, 1, 200}, - {1041, 1, 200}, - { 389, 1, 201}, - { 388, 1, 201}, - { 738, 1, 202}, - { 737, 1, 202}, - { 174, 1, 203}, - { 173, 1, 203}, - { 730, 1, 204}, - { 729, 1, 204}, - { 443, 1, 205}, - { 442, 1, 205}, - { 901, 1, 206}, - { 461, 1, 207}, - { 462, 1, 207}, - { 466, 1, 208}, - { 465, 1, 208}, - { 765, 1, 209}, - { 769, 1, 209}, - { 456, 1, 210}, - {1078, 1, 211}, - {1077, 1, 211}, - { 151, 1, 212}, - { 150, 1, 212}, - { 349, 1, 213}, - { 339, 1, 213}, - { 350, 1, 214}, - { 340, 1, 214}, - { 351, 1, 215}, - { 341, 1, 215}, - { 335, 1, 216}, - { 337, 1, 216}, - {1036, 1, 217}, - {1100, 1, 218}, - {1115, 1, 218}, - {1018, 1, 219}, - {1020, 1, 219}, - {1019, 1, 220}, - {1021, 1, 220}, - {1090, 2, 0}, - {1159, 2, 0}, - { 367, 2, 1}, - {1158, 2, 1}, - { 663, 2, 2}, - { 677, 2, 2}, - { 527, 2, 3}, - { 531, 2, 3}, - { 406, 2, 4}, - { 414, 2, 4}, - { 182, 2, 5}, - { 184, 2, 5}, - { 561, 2, 6}, - { 560, 2, 6}, - { 169, 2, 7}, - { 168, 2, 7}, - {1030, 2, 8}, - {1029, 2, 8}, - {1061, 2, 9}, - {1060, 2, 9}, - { 431, 2, 10}, - { 430, 2, 10}, - { 221, 2, 11}, - { 220, 2, 11}, - { 536, 2, 12}, - { 537, 2, 12}, - { 534, 2, 13}, - { 535, 2, 13}, - { 853, 2, 14}, - { 855, 2, 14}, - {1047, 2, 15}, - {1048, 2, 15}, - {1054, 2, 16}, - {1053, 2, 16}, - { 639, 2, 17}, - { 652, 2, 17}, - { 731, 2, 18}, - { 773, 2, 18}, - { 980, 2, 19}, - { 979, 2, 19}, - {1062, 2, 20}, - { 661, 2, 21}, - { 662, 2, 21}, - {1063, 2, 22}, - {1064, 2, 22}, - { 785, 2, 23}, - { 788, 2, 23}, - { 512, 2, 24}, - { 511, 2, 24}, - { 549, 2, 25}, - { 548, 2, 25}, - { 471, 2, 26}, - { 470, 2, 26}, - { 325, 2, 27}, - { 324, 2, 27}, - { 265, 2, 28}, - { 269, 2, 28}, - { 836, 2, 29}, - { 835, 2, 29}, - { 948, 2, 30}, - { 949, 2, 30}, - { 649, 2, 31}, - { 651, 2, 31}, - { 781, 2, 32}, - { 780, 2, 32}, - { 572, 2, 33}, - { 571, 2, 33}, - { 641, 2, 34}, - { 632, 2, 34}, - { 237, 2, 35}, - { 236, 2, 35}, - { 547, 2, 36}, - { 556, 2, 36}, - {1140, 2, 37}, - {1141, 2, 37}, - { 842, 2, 38}, - { 613, 2, 38}, - { 520, 2, 39}, - { 519, 2, 39}, - { 429, 2, 40}, - { 448, 2, 40}, - { 596, 2, 41}, - {1152, 2, 41}, - { 920, 2, 41}, - {1033, 2, 42}, - {1059, 2, 42}, - { 558, 2, 43}, - { 557, 2, 43}, - { 257, 2, 44}, - { 256, 2, 44}, - {1035, 2, 45}, - {1034, 2, 45}, - { 696, 2, 46}, - { 695, 2, 46}, - {1038, 2, 47}, - {1045, 2, 47}, - { 698, 2, 48}, - { 697, 2, 48}, - {1084, 2, 49}, - {1083, 2, 49}, - { 974, 2, 50}, - { 975, 2, 50}, - { 857, 2, 51}, - { 856, 2, 51}, - { 404, 2, 52}, - { 391, 2, 52}, - { 248, 2, 53}, - { 247, 2, 53}, - { 255, 2, 54}, - { 254, 2, 54}, - { 387, 2, 55}, - { 386, 2, 55}, - { 919, 2, 55}, - { 800, 2, 56}, - {1046, 2, 56}, - { 517, 2, 57}, - { 516, 2, 57}, - {1065, 2, 58}, - {1058, 2, 58}, - {1027, 2, 59}, - {1026, 2, 59}, - { 843, 2, 60}, - {1132, 2, 60}, - { 648, 2, 61}, - { 647, 2, 61}, - { 206, 2, 62}, - { 205, 2, 62}, - { 394, 2, 63}, - {1133, 2, 63}, - { 895, 2, 64}, - { 894, 2, 64}, - { 890, 2, 65}, - { 889, 2, 65}, - { 803, 2, 66}, - { 804, 2, 66}, - {1004, 2, 67}, - {1003, 2, 67}, - { 690, 2, 68}, - { 689, 2, 68}, - { 840, 2, 69}, - { 841, 2, 69}, - {1096, 2, 70}, - {1097, 2, 70}, - { 959, 2, 71}, - { 958, 2, 71}, - { 645, 2, 72}, - { 631, 2, 72}, - { 932, 2, 73}, - { 941, 2, 73}, - { 724, 2, 74}, - { 723, 2, 74}, - { 271, 2, 75}, - { 270, 2, 75}, - { 726, 2, 76}, - { 725, 2, 76}, - { 318, 2, 77}, - {1039, 2, 78}, - { 660, 2, 78}, - {1040, 2, 79}, - {1049, 2, 79}, - { 200, 2, 80}, - { 201, 2, 80}, - { 455, 2, 81}, - { 454, 2, 81}, - { 955, 2, 82}, - { 956, 2, 82}, - { 704, 2, 83}, - { 208, 2, 84}, - { 207, 2, 84}, - { 618, 2, 85}, - { 617, 2, 85}, - { 748, 2, 86}, - { 782, 2, 86}, - { 590, 2, 87}, - { 183, 2, 87}, - { 844, 2, 88}, - { 957, 2, 88}, - { 603, 2, 89}, - { 914, 2, 89}, - { 602, 2, 90}, - { 893, 2, 90}, - { 845, 2, 91}, - { 854, 2, 91}, - { 630, 2, 92}, - { 654, 2, 92}, - { 212, 2, 93}, - { 213, 2, 93}, - { 246, 2, 94}, - { 245, 2, 94}, - { 733, 2, 95}, - { 732, 2, 95}, - { 317, 2, 96}, - { 263, 2, 96}, - { 753, 2, 97}, - { 751, 2, 97}, - { 754, 2, 98}, - { 752, 2, 98}, - { 755, 2, 99}, - { 902, 2, 99}, - { 973, 2, 100}, - { 977, 2, 100}, - { 990, 2, 101}, - { 989, 2, 101}, - {1044, 2, 102}, - {1043, 2, 102}, - { 643, 2, 103}, - { 574, 2, 103}, - { 858, 3, 0}, - {1134, 3, 0}, - { 446, 3, 1}, - { 447, 3, 1}, - { 978, 3, 2}, - { 997, 3, 2}, - { 562, 3, 3}, - { 573, 3, 3}, - { 392, 3, 4}, - { 694, 3, 5}, - { 799, 3, 6}, - { 805, 3, 6}, - { 484, 3, 7}, - { 929, 3, 8}, - { 934, 3, 8}, - { 499, 3, 9}, - { 497, 3, 9}, - { 641, 3, 10}, - { 628, 3, 10}, - { 153, 3, 11}, - { 680, 3, 11}, - { 756, 3, 12}, - { 772, 3, 12}, - { 757, 3, 13}, - { 774, 3, 13}, - { 758, 3, 14}, - { 742, 3, 14}, - { 826, 3, 15}, - { 822, 3, 15}, - { 486, 3, 16}, - { 481, 3, 16}, - { 858, 4, 0}, - {1134, 4, 0}, - { 392, 4, 1}, - { 694, 4, 2}, - { 384, 4, 3}, - { 357, 4, 3}, - { 484, 4, 4}, - { 481, 4, 4}, - { 929, 4, 5}, - { 934, 4, 5}, - { 994, 4, 6}, - { 982, 4, 6}, - { 656, 4, 7}, - {1095, 4, 8}, - {1032, 4, 9}, - { 719, 4, 10}, - { 721, 4, 11}, - { 910, 4, 12}, - { 907, 4, 12}, - { 858, 5, 0}, - {1134, 5, 0}, - { 392, 5, 1}, - { 694, 5, 2}, - { 484, 5, 3}, - { 481, 5, 3}, - { 970, 5, 4}, - { 965, 5, 4}, - { 499, 5, 5}, - { 497, 5, 5}, - { 991, 5, 6}, - { 710, 5, 7}, - { 707, 5, 7}, - {1092, 5, 8}, - {1091, 5, 8}, - { 846, 5, 9}, - { 680, 5, 9}, - { 826, 5, 10}, - { 822, 5, 10}, - { 194, 5, 11}, - { 189, 5, 11}, - {1001, 5, 12}, - {1000, 5, 12}, - { 353, 5, 13}, - { 352, 5, 13}, - { 962, 5, 14}, - { 961, 5, 14}, - { 806, 6, 0}, - { 789, 6, 0}, - { 487, 6, 0}, - { 488, 6, 0}, - {1139, 6, 1}, - {1135, 6, 1}, - {1032, 6, 1}, - {1079, 6, 1}, - { 816, 7, 0}, - { 791, 7, 0}, - { 681, 7, 1}, - { 656, 7, 1}, - {1112, 7, 2}, - {1095, 7, 2}, - {1075, 7, 3}, - {1032, 7, 3}, - { 720, 7, 4}, - { 719, 7, 4}, - { 722, 7, 5}, - { 721, 7, 5}, - { 685, 8, 0}, - { 656, 8, 0}, - { 937, 8, 1}, - { 927, 8, 1}, - { 478, 8, 2}, - { 457, 8, 2}, - { 479, 8, 3}, - { 468, 8, 3}, - { 480, 8, 4}, - { 469, 8, 4}, - { 175, 8, 5}, - { 161, 8, 5}, - { 369, 8, 6}, - { 393, 8, 6}, - { 878, 8, 7}, - { 202, 8, 7}, - { 967, 8, 8}, - { 950, 8, 8}, - {1119, 8, 9}, - {1125, 8, 9}, - { 867, 8, 10}, - { 849, 8, 10}, - { 242, 8, 11}, - { 235, 8, 11}, - { 813, 8, 12}, - { 820, 8, 12}, - { 172, 8, 13}, - { 148, 8, 13}, - { 688, 8, 14}, - { 716, 8, 14}, - { 940, 8, 15}, - { 944, 8, 15}, - { 686, 8, 16}, - { 714, 8, 16}, - { 938, 8, 17}, - { 942, 8, 17}, - { 904, 8, 18}, - { 885, 8, 18}, - { 687, 8, 19}, - { 715, 8, 19}, - { 939, 8, 20}, - { 943, 8, 20}, - { 496, 8, 21}, - { 502, 8, 21}, - { 905, 8, 22}, - { 886, 8, 22}, - { 817, 9, 0}, - { 1, 9, 0}, - { 818, 9, 0}, - { 874, 9, 1}, - { 2, 9, 1}, - { 873, 9, 1}, - { 823, 9, 2}, - { 120, 9, 2}, - { 802, 9, 2}, - { 635, 9, 3}, - { 127, 9, 3}, - { 655, 9, 3}, - {1106, 9, 4}, - { 133, 9, 4}, - {1113, 9, 4}, - { 279, 9, 5}, - { 13, 9, 5}, - { 282, 9, 6}, - { 22, 9, 6}, - { 284, 9, 7}, - { 25, 9, 7}, - { 287, 9, 8}, - { 28, 9, 8}, - { 291, 9, 9}, - { 33, 9, 9}, - { 292, 9, 10}, - { 34, 9, 10}, - { 293, 9, 11}, - { 36, 9, 11}, - { 294, 9, 12}, - { 37, 9, 12}, - { 295, 9, 13}, - { 39, 9, 13}, - { 296, 9, 14}, - { 40, 9, 14}, - { 297, 9, 15}, - { 44, 9, 15}, - { 298, 9, 16}, - { 49, 9, 16}, - { 299, 9, 17}, - { 54, 9, 17}, - { 300, 9, 18}, - { 60, 9, 18}, - { 301, 9, 19}, - { 65, 9, 19}, - { 302, 9, 20}, - { 67, 9, 20}, - { 303, 9, 21}, - { 68, 9, 21}, - { 304, 9, 22}, - { 69, 9, 22}, - { 305, 9, 23}, - { 70, 9, 23}, - { 306, 9, 24}, - { 71, 9, 24}, - { 307, 9, 25}, - { 78, 9, 25}, - { 308, 9, 26}, - { 82, 9, 26}, - { 309, 9, 27}, - { 83, 9, 27}, - { 310, 9, 28}, - { 84, 9, 28}, - { 311, 9, 29}, - { 85, 9, 29}, - { 312, 9, 30}, - { 86, 9, 30}, - { 313, 9, 31}, - { 87, 9, 31}, - { 314, 9, 32}, - { 132, 9, 32}, - { 315, 9, 33}, - { 139, 9, 33}, - { 280, 9, 34}, - { 20, 9, 34}, - { 281, 9, 35}, - { 21, 9, 35}, - { 283, 9, 36}, - { 24, 9, 36}, - { 285, 9, 37}, - { 26, 9, 37}, - { 286, 9, 38}, - { 27, 9, 38}, - { 288, 9, 39}, - { 30, 9, 39}, - { 289, 9, 40}, - { 31, 9, 40}, - { 197, 9, 41}, - { 48, 9, 41}, - { 192, 9, 41}, - { 195, 9, 42}, - { 50, 9, 42}, - { 190, 9, 42}, - { 196, 9, 43}, - { 51, 9, 43}, - { 191, 9, 43}, - { 218, 9, 44}, - { 53, 9, 44}, - { 230, 9, 44}, - { 217, 9, 45}, - { 55, 9, 45}, - { 202, 9, 45}, - { 219, 9, 46}, - { 56, 9, 46}, - { 244, 9, 46}, - { 682, 9, 47}, - { 57, 9, 47}, - { 656, 9, 47}, - { 935, 9, 48}, - { 58, 9, 48}, - { 927, 9, 48}, - { 142, 9, 49}, - { 59, 9, 49}, - { 148, 9, 49}, - { 141, 9, 50}, - { 61, 9, 50}, - { 140, 9, 50}, - { 143, 9, 51}, - { 62, 9, 51}, - { 167, 9, 51}, - { 445, 9, 52}, - { 63, 9, 52}, - { 421, 9, 52}, - { 444, 9, 53}, - { 64, 9, 53}, - { 416, 9, 53}, - { 607, 9, 54}, - { 66, 9, 54}, - { 610, 9, 54}, - { 290, 9, 55}, - { 32, 9, 55}, - { 198, 9, 56}, - { 45, 9, 56}, - { 193, 9, 56}, - { 811, 10, 0}, - { 267, 10, 1}, - { 264, 10, 1}, - { 370, 10, 2}, - { 360, 10, 2}, - { 498, 10, 3}, - { 808, 10, 4}, - { 795, 10, 4}, - { 598, 10, 5}, - { 597, 10, 5}, - { 746, 10, 6}, - { 745, 10, 6}, - { 493, 10, 7}, - { 492, 10, 7}, - { 612, 10, 8}, - { 611, 10, 8}, - { 327, 10, 9}, - { 458, 10, 9}, - {1010, 10, 10}, - {1007, 10, 10}, - {1002, 10, 11}, - {1104, 10, 12}, - {1103, 10, 12}, - {1120, 10, 13}, - { 794, 10, 14}, - { 793, 10, 14}, - { 983, 10, 15}, - { 986, 10, 15}, - { 999, 10, 16}, - { 998, 10, 16}, - { 501, 10, 17}, - { 500, 10, 17}, - { 798, 11, 0}, - { 789, 11, 0}, - { 160, 11, 1}, - { 140, 11, 1}, - { 544, 11, 2}, - { 538, 11, 2}, - {1120, 11, 3}, - {1116, 11, 3}, - { 503, 11, 4}, - { 487, 11, 4}, - { 794, 11, 5}, - { 791, 11, 5}, - { 809, 12, 0}, - { 147, 12, 1}, - { 149, 12, 2}, - { 152, 12, 3}, - { 216, 12, 4}, - { 222, 12, 5}, - { 417, 12, 6}, - { 418, 12, 7}, - { 451, 12, 8}, - { 491, 12, 9}, - { 495, 12, 10}, - { 504, 12, 11}, - { 505, 12, 12}, - { 541, 12, 13}, - { 546, 12, 14}, - {1052, 12, 14}, - { 559, 12, 15}, - { 563, 12, 16}, - { 564, 12, 17}, - { 565, 12, 18}, - { 629, 12, 19}, - { 640, 12, 20}, - { 653, 12, 21}, - { 658, 12, 22}, - { 659, 12, 23}, - { 747, 12, 24}, - { 759, 12, 25}, - { 815, 12, 26}, - { 829, 12, 27}, - { 887, 12, 28}, - { 921, 12, 29}, - { 922, 12, 30}, - { 931, 12, 31}, - { 933, 12, 32}, - { 953, 12, 33}, - { 954, 12, 34}, - { 966, 12, 35}, - { 968, 12, 36}, - { 976, 12, 37}, - {1024, 12, 38}, - {1037, 12, 39}, - {1050, 12, 40}, - {1051, 12, 41}, - {1057, 12, 42}, - {1117, 12, 43}, - {1031, 12, 44}, - {1136, 12, 45}, - {1137, 12, 46}, - {1138, 12, 47}, - {1146, 12, 48}, - {1147, 12, 49}, - {1150, 12, 50}, - {1151, 12, 51}, - { 646, 12, 52}, - { 490, 12, 53}, - { 258, 12, 54}, - { 489, 12, 55}, - { 831, 12, 56}, - { 945, 12, 57}, - { 812, 13, 0}, - {1080, 13, 0}, - { 622, 13, 1}, - { 261, 13, 1}, - { 450, 13, 2}, - { 415, 13, 2}, - { 936, 13, 3}, - { 927, 13, 3}, - { 684, 13, 4}, - { 656, 13, 4}, - {1076, 13, 5}, - {1032, 13, 5}, - {1090, 14, 0}, - {1134, 14, 0}, - { 851, 14, 1}, - { 850, 14, 1}, - { 355, 14, 2}, - { 352, 14, 2}, - { 925, 14, 3}, - { 924, 14, 3}, - { 518, 14, 4}, - { 515, 14, 4}, - { 814, 14, 5}, - { 819, 14, 5}, - { 482, 14, 6}, - { 481, 14, 6}, - { 253, 14, 7}, - {1025, 14, 7}, - { 595, 14, 8}, - { 610, 14, 8}, - { 909, 14, 9}, - { 908, 14, 9}, - { 906, 14, 10}, - { 903, 14, 10}, - { 826, 14, 11}, - { 822, 14, 11}, - { 156, 14, 12}, - { 148, 14, 12}, - { 582, 14, 13}, - { 578, 14, 13}, - { 604, 14, 14}, - { 591, 14, 14}, - { 605, 14, 14}, - { 577, 14, 15}, - { 576, 14, 15}, - { 365, 14, 16}, - { 356, 14, 16}, - { 251, 14, 17}, - { 214, 14, 17}, - { 250, 14, 18}, - { 204, 14, 18}, - { 992, 14, 19}, - { 991, 14, 19}, - { 734, 14, 20}, - { 229, 14, 20}, - { 272, 14, 21}, - { 392, 14, 21}, - { 702, 14, 22}, - { 694, 14, 22}, - { 383, 14, 23}, - { 276, 14, 23}, - { 372, 14, 24}, - { 952, 14, 24}, - { 160, 14, 25}, - { 146, 14, 25}, - { 252, 14, 26}, - { 203, 14, 26}, - {1023, 14, 27}, - { 972, 14, 27}, - {1157, 14, 28}, - {1156, 14, 28}, - { 801, 14, 29}, - { 805, 14, 29}, - {1124, 14, 30}, - {1121, 14, 30}, - { 620, 14, 31}, - { 627, 14, 32}, - { 626, 14, 33}, - { 539, 14, 34}, - { 540, 14, 35}, - { 354, 14, 36}, - { 390, 14, 36}, - { 562, 14, 37}, - { 573, 14, 37}, - { 373, 14, 38}, - { 328, 14, 38}, - { 929, 14, 39}, - { 934, 14, 39}, - { 811, 15, 0}, - { 826, 15, 1}, - { 822, 15, 1}, - { 440, 15, 2}, - { 434, 15, 2}, - { 423, 15, 3}, - { 422, 15, 3}, - { 792, 16, 0}, - { 0, 16, 1}, - { 1, 16, 2}, - { 4, 16, 3}, - { 3, 16, 4}, - { 12, 16, 5}, - { 11, 16, 6}, - { 10, 16, 7}, - { 9, 16, 8}, - { 73, 16, 9}, - { 8, 16, 10}, - { 7, 16, 11}, - { 6, 16, 12}, - { 77, 16, 13}, - { 43, 16, 14}, - { 5, 16, 15}, - { 76, 16, 16}, - { 110, 16, 17}, - { 42, 16, 18}, - { 75, 16, 19}, - { 92, 16, 20}, - { 109, 16, 21}, - { 122, 16, 22}, - { 2, 16, 23}, - { 74, 16, 24}, - { 41, 16, 25}, - { 108, 16, 26}, - { 72, 16, 27}, - { 121, 16, 28}, - { 91, 16, 29}, - { 134, 16, 30}, - { 107, 16, 31}, - { 23, 16, 32}, - { 115, 16, 33}, - { 29, 16, 34}, - { 120, 16, 35}, - { 35, 16, 36}, - { 127, 16, 37}, - { 38, 16, 38}, - { 133, 16, 39}, - { 13, 16, 40}, - { 22, 16, 41}, - { 25, 16, 42}, - { 28, 16, 43}, - { 33, 16, 44}, - { 34, 16, 45}, - { 36, 16, 46}, - { 37, 16, 47}, - { 39, 16, 48}, - { 40, 16, 49}, - { 44, 16, 50}, - { 49, 16, 51}, - { 54, 16, 52}, - { 60, 16, 53}, - { 65, 16, 54}, - { 67, 16, 55}, - { 68, 16, 56}, - { 69, 16, 57}, - { 70, 16, 58}, - { 71, 16, 59}, - { 78, 16, 60}, - { 82, 16, 61}, - { 83, 16, 62}, - { 84, 16, 63}, - { 85, 16, 64}, - { 86, 16, 65}, - { 87, 16, 66}, - { 88, 16, 67}, - { 89, 16, 68}, - { 90, 16, 69}, - { 93, 16, 70}, - { 97, 16, 71}, - { 98, 16, 72}, - { 99, 16, 73}, - { 101, 16, 74}, - { 102, 16, 75}, - { 103, 16, 76}, - { 104, 16, 77}, - { 105, 16, 78}, - { 106, 16, 79}, - { 111, 16, 80}, - { 116, 16, 81}, - { 123, 16, 82}, - { 128, 16, 83}, - { 135, 16, 84}, - { 14, 16, 85}, - { 45, 16, 86}, - { 79, 16, 87}, - { 94, 16, 88}, - { 112, 16, 89}, - { 117, 16, 90}, - { 124, 16, 91}, - { 129, 16, 92}, - { 136, 16, 93}, - { 15, 16, 94}, - { 46, 16, 95}, - { 80, 16, 96}, - { 95, 16, 97}, - { 113, 16, 98}, - { 118, 16, 99}, - { 125, 16, 100}, - { 130, 16, 101}, - { 137, 16, 102}, - { 16, 16, 103}, - { 47, 16, 104}, - { 81, 16, 105}, - { 96, 16, 106}, - { 114, 16, 107}, - { 119, 16, 108}, - { 126, 16, 109}, - { 131, 16, 110}, - { 138, 16, 111}, - { 17, 16, 112}, - { 52, 16, 113}, - { 100, 16, 114}, - { 18, 16, 115}, - { 19, 16, 116}, - { 791, 17, 0}, - { 935, 17, 1}, - { 682, 17, 2}, - {1108, 17, 3}, - { 683, 17, 4}, - {1069, 17, 5}, - { 240, 17, 6}, - {1070, 17, 7}, - {1074, 17, 8}, - {1072, 17, 9}, - {1073, 17, 10}, - { 241, 17, 11}, - {1071, 17, 12}, - { 875, 17, 13}, - { 606, 17, 14}, - { 858, 18, 0}, - { 228, 18, 1}, - {1107, 18, 2}, - { 199, 18, 3}, - { 823, 18, 4}, - {1106, 18, 5}, - {1111, 18, 6}, - {1110, 18, 7}, - {1109, 18, 8}, - { 380, 18, 9}, - { 375, 18, 10}, - { 376, 18, 11}, - { 381, 18, 12}, - { 382, 18, 13}, - { 379, 18, 14}, - { 377, 18, 15}, - { 378, 18, 16}, - { 779, 18, 17}, - {1067, 18, 18}, - {1068, 18, 19}, - { 930, 18, 20}, -}; - -/* property values: 5004 bytes. */ - -/* Codepoints which expand on full case-folding. */ - -RE_UINT16 re_expand_on_folding[] = { - 223, 304, 329, 496, 912, 944, 1415, 7830, - 7831, 7832, 7833, 7834, 7838, 8016, 8018, 8020, - 8022, 8064, 8065, 8066, 8067, 8068, 8069, 8070, - 8071, 8072, 8073, 8074, 8075, 8076, 8077, 8078, - 8079, 8080, 8081, 8082, 8083, 8084, 8085, 8086, - 8087, 8088, 8089, 8090, 8091, 8092, 8093, 8094, - 8095, 8096, 8097, 8098, 8099, 8100, 8101, 8102, - 8103, 8104, 8105, 8106, 8107, 8108, 8109, 8110, - 8111, 8114, 8115, 8116, 8118, 8119, 8124, 8130, - 8131, 8132, 8134, 8135, 8140, 8146, 8147, 8150, - 8151, 8162, 8163, 8164, 8166, 8167, 8178, 8179, - 8180, 8182, 8183, 8188, 64256, 64257, 64258, 64259, - 64260, 64261, 64262, 64275, 64276, 64277, 64278, 64279, -}; - -/* expand_on_folding: 208 bytes. */ - -/* General_Category. */ - -static RE_UINT8 re_general_category_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 14, 14, 14, 15, - 16, 17, 18, 19, 20, 19, 21, 19, 19, 19, 19, 19, 19, 22, 19, 19, - 19, 19, 19, 19, 19, 19, 23, 19, 19, 19, 24, 19, 19, 25, 26, 19, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 27, 7, 28, 29, 19, 19, 19, 19, 19, 19, 19, 30, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 31, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 32, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 32, -}; - -static RE_UINT8 re_general_category_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, - 32, 33, 34, 34, 35, 36, 37, 38, 39, 34, 34, 34, 40, 41, 42, 43, - 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, - 60, 61, 62, 63, 64, 64, 65, 66, 67, 68, 69, 70, 71, 69, 72, 73, - 69, 69, 64, 74, 64, 64, 75, 76, 77, 78, 79, 80, 81, 82, 69, 83, - 84, 85, 86, 87, 88, 89, 69, 69, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 90, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 91, - 92, 34, 34, 34, 34, 34, 34, 34, 34, 93, 34, 34, 94, 95, 96, 97, - 98, 99, 100, 101, 102, 103, 104, 105, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 106, - 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, - 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, - 108, 108, 34, 34, 109, 110, 111, 112, 34, 34, 113, 114, 115, 116, 117, 118, - 119, 120, 121, 122, 76, 123, 124, 125, 126, 127, 76, 76, 76, 76, 76, 76, - 128, 76, 129, 130, 131, 76, 132, 76, 133, 76, 76, 76, 134, 76, 76, 76, - 135, 136, 137, 138, 76, 76, 76, 76, 76, 76, 76, 76, 76, 139, 76, 76, - 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, - 34, 34, 34, 34, 34, 34, 140, 76, 141, 76, 76, 76, 76, 76, 76, 76, - 34, 34, 34, 34, 34, 34, 34, 34, 142, 76, 76, 76, 76, 76, 76, 76, - 34, 34, 34, 34, 143, 76, 76, 76, 76, 76, 76, 76, 76, 76, 144, 145, - 146, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, - 69, 147, 148, 149, 150, 76, 151, 76, 152, 153, 154, 155, 156, 157, 158, 159, - 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 160, 161, 76, 76, - 162, 163, 164, 165, 166, 76, 167, 168, 169, 170, 171, 172, 173, 174, 175, 76, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 176, 34, 34, - 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 34, 177, 34, - 178, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, - 34, 34, 34, 34, 178, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, - 179, 76, 180, 181, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, 76, - 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 108, 182, -}; - -static RE_UINT16 re_general_category_stage_3[] = { - 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 7, 8, 9, 10, 11, 12, - 13, 13, 13, 14, 15, 13, 13, 16, 17, 18, 19, 20, 21, 22, 13, 23, - 13, 13, 13, 24, 25, 11, 11, 11, 11, 26, 11, 27, 28, 29, 30, 31, - 32, 32, 32, 32, 32, 32, 32, 33, 34, 35, 36, 11, 37, 38, 13, 39, - 9, 9, 9, 11, 11, 11, 13, 13, 40, 13, 13, 13, 41, 13, 13, 13, - 13, 13, 42, 43, 9, 44, 45, 11, 46, 47, 32, 48, 49, 50, 51, 52, - 53, 54, 50, 50, 55, 32, 56, 57, 50, 50, 50, 50, 50, 58, 59, 60, - 61, 62, 50, 32, 63, 50, 50, 50, 50, 50, 64, 65, 66, 50, 67, 68, - 50, 69, 70, 71, 50, 72, 73, 73, 73, 73, 74, 73, 73, 73, 75, 76, - 77, 50, 50, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, - 91, 84, 85, 92, 93, 94, 95, 96, 97, 98, 85, 99, 100, 101, 89, 102, - 83, 84, 85, 103, 104, 105, 89, 106, 107, 108, 109, 110, 111, 112, 95, 113, - 114, 115, 85, 116, 117, 118, 89, 119, 120, 115, 85, 121, 122, 123, 89, 124, - 120, 115, 50, 125, 126, 127, 89, 128, 129, 130, 50, 131, 132, 133, 73, 134, - 135, 50, 50, 136, 137, 138, 73, 73, 139, 140, 141, 142, 143, 144, 73, 73, - 145, 146, 147, 148, 149, 50, 150, 151, 152, 153, 32, 154, 155, 156, 73, 73, - 50, 50, 157, 158, 159, 160, 161, 162, 163, 164, 9, 9, 165, 50, 50, 166, - 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 167, 168, 50, 50, - 167, 50, 50, 169, 170, 171, 50, 50, 50, 170, 50, 50, 50, 172, 173, 174, - 50, 175, 50, 50, 50, 50, 50, 176, 177, 50, 50, 50, 50, 50, 50, 50, - 50, 50, 50, 50, 50, 50, 178, 50, 179, 180, 50, 50, 50, 50, 181, 182, - 183, 184, 50, 185, 50, 186, 183, 187, 50, 50, 50, 188, 189, 190, 191, 192, - 193, 191, 50, 50, 194, 50, 50, 195, 50, 50, 196, 50, 50, 50, 50, 197, - 50, 150, 198, 199, 200, 50, 201, 176, 50, 50, 202, 203, 204, 205, 206, 206, - 50, 207, 50, 50, 50, 208, 209, 210, 191, 191, 211, 73, 73, 73, 73, 73, - 212, 50, 50, 213, 214, 159, 215, 216, 217, 50, 218, 66, 50, 50, 219, 220, - 50, 50, 221, 222, 223, 66, 50, 224, 73, 73, 73, 73, 225, 226, 227, 228, - 11, 11, 229, 27, 27, 27, 230, 231, 11, 232, 27, 27, 32, 32, 233, 234, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 235, 13, 13, 13, 13, 13, 13, - 236, 237, 236, 236, 237, 238, 236, 239, 240, 240, 240, 241, 242, 243, 244, 245, - 246, 247, 248, 249, 250, 251, 252, 253, 254, 255, 256, 257, 73, 258, 259, 260, - 261, 262, 263, 264, 265, 266, 267, 267, 268, 269, 270, 206, 271, 272, 206, 273, - 274, 274, 274, 274, 274, 274, 274, 274, 275, 206, 276, 206, 206, 206, 206, 277, - 206, 278, 274, 279, 206, 280, 281, 282, 206, 206, 283, 73, 284, 73, 266, 266, - 266, 285, 206, 206, 206, 206, 286, 266, 206, 206, 206, 206, 206, 206, 206, 206, - 206, 206, 206, 287, 288, 206, 206, 289, 206, 206, 206, 206, 206, 206, 290, 206, - 291, 206, 206, 206, 206, 206, 292, 293, 266, 294, 206, 206, 295, 274, 296, 274, - 297, 298, 274, 274, 274, 299, 274, 300, 206, 206, 206, 274, 301, 175, 73, 73, - 73, 73, 73, 73, 73, 73, 73, 73, 9, 9, 302, 11, 11, 303, 304, 305, - 13, 13, 13, 13, 13, 13, 306, 307, 11, 11, 308, 50, 50, 50, 309, 310, - 50, 311, 312, 312, 312, 312, 32, 32, 313, 314, 315, 316, 73, 73, 73, 73, - 206, 317, 206, 206, 206, 206, 206, 282, 206, 206, 206, 206, 206, 318, 73, 319, - 320, 321, 322, 323, 135, 50, 50, 50, 50, 324, 177, 50, 50, 50, 50, 325, - 326, 50, 201, 135, 50, 50, 50, 50, 327, 328, 50, 51, 206, 206, 282, 50, - 206, 329, 330, 206, 331, 332, 206, 206, 330, 206, 206, 332, 206, 206, 206, 329, - 50, 50, 50, 197, 206, 206, 206, 206, 50, 50, 50, 50, 150, 73, 73, 73, - 50, 333, 50, 50, 50, 50, 50, 50, 150, 206, 206, 206, 283, 50, 50, 224, - 334, 50, 335, 73, 13, 13, 336, 337, 13, 338, 50, 50, 50, 50, 339, 340, - 31, 341, 342, 343, 13, 13, 13, 344, 345, 346, 347, 73, 73, 73, 73, 348, - 349, 50, 350, 351, 50, 50, 50, 352, 353, 50, 50, 354, 355, 191, 32, 356, - 66, 50, 357, 50, 358, 359, 50, 150, 77, 50, 50, 360, 361, 362, 73, 73, - 50, 50, 363, 364, 365, 366, 50, 367, 50, 50, 50, 368, 369, 370, 371, 372, - 373, 374, 312, 73, 73, 73, 73, 73, 73, 73, 73, 73, 50, 50, 375, 191, - 50, 50, 376, 50, 377, 50, 50, 202, 378, 378, 378, 378, 378, 378, 378, 378, - 379, 379, 379, 379, 379, 379, 379, 379, 50, 50, 50, 50, 50, 50, 201, 50, - 50, 50, 50, 50, 50, 380, 73, 73, 381, 382, 383, 384, 385, 50, 50, 50, - 50, 50, 50, 386, 387, 388, 50, 50, 50, 50, 50, 389, 73, 50, 50, 50, - 50, 390, 50, 50, 195, 73, 73, 391, 32, 392, 233, 393, 394, 395, 396, 397, - 50, 50, 50, 50, 50, 50, 50, 398, 399, 2, 3, 4, 5, 400, 401, 402, - 50, 403, 50, 327, 404, 405, 406, 407, 408, 50, 171, 409, 201, 201, 73, 73, - 50, 50, 50, 50, 50, 50, 50, 51, 410, 266, 266, 411, 267, 267, 267, 412, - 413, 319, 73, 73, 73, 206, 206, 414, 50, 150, 50, 50, 50, 101, 73, 73, - 50, 327, 415, 50, 416, 73, 73, 73, 50, 417, 50, 50, 418, 419, 73, 73, - 9, 9, 420, 11, 11, 50, 50, 50, 50, 201, 191, 73, 73, 73, 73, 73, - 421, 50, 50, 422, 50, 423, 73, 73, 50, 424, 50, 425, 73, 73, 73, 73, - 50, 50, 50, 426, 73, 73, 73, 73, 427, 428, 50, 429, 430, 431, 50, 432, - 50, 50, 50, 433, 50, 434, 50, 435, 50, 50, 50, 50, 436, 73, 73, 73, - 73, 73, 73, 73, 73, 73, 266, 437, 438, 50, 50, 439, 440, 441, 442, 73, - 217, 50, 50, 443, 444, 50, 436, 191, 445, 50, 446, 447, 448, 73, 73, 73, - 217, 50, 50, 449, 450, 191, 73, 73, 50, 50, 451, 452, 191, 73, 73, 73, - 50, 50, 50, 50, 50, 50, 327, 73, 267, 267, 267, 267, 267, 267, 453, 448, - 50, 50, 327, 73, 73, 73, 73, 73, 50, 50, 50, 436, 73, 73, 73, 73, - 50, 50, 50, 50, 176, 454, 203, 455, 456, 457, 73, 73, 73, 73, 73, 73, - 458, 73, 73, 73, 73, 73, 73, 73, 206, 206, 206, 206, 206, 206, 206, 318, - 206, 206, 459, 206, 206, 206, 460, 461, 462, 206, 463, 206, 206, 464, 73, 73, - 206, 206, 206, 206, 465, 73, 73, 73, 206, 206, 206, 206, 206, 283, 266, 466, - 9, 467, 11, 468, 469, 470, 236, 9, 471, 472, 473, 474, 475, 9, 467, 11, - 476, 477, 11, 478, 479, 480, 481, 9, 482, 11, 9, 467, 11, 468, 469, 11, - 236, 9, 471, 481, 9, 482, 11, 9, 467, 11, 483, 9, 484, 485, 486, 487, - 11, 488, 9, 489, 490, 491, 492, 11, 493, 9, 494, 11, 495, 496, 496, 496, - 497, 50, 498, 499, 500, 501, 502, 503, 504, 202, 505, 202, 73, 73, 73, 506, - 206, 206, 319, 206, 206, 206, 206, 206, 206, 282, 329, 507, 291, 291, 73, 73, - 508, 206, 329, 206, 206, 206, 319, 206, 206, 284, 73, 73, 73, 73, 509, 206, - 510, 206, 206, 284, 511, 512, 73, 73, 206, 206, 513, 514, 206, 206, 206, 515, - 206, 282, 206, 206, 516, 73, 206, 513, 206, 206, 206, 329, 517, 206, 206, 206, - 206, 206, 206, 206, 206, 206, 206, 518, 206, 206, 206, 464, 282, 206, 519, 73, - 73, 73, 73, 73, 73, 73, 73, 520, 206, 206, 206, 206, 521, 73, 73, 73, - 206, 206, 206, 206, 318, 73, 73, 73, 206, 206, 206, 206, 206, 206, 206, 282, - 50, 50, 50, 50, 50, 311, 73, 73, 50, 50, 50, 176, 50, 50, 50, 50, - 50, 201, 73, 73, 73, 73, 73, 73, 522, 73, 523, 523, 523, 523, 523, 523, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 73, - 379, 379, 379, 379, 379, 379, 379, 524, -}; - -static RE_UINT8 re_general_category_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 2, 4, 5, 6, 2, - 7, 7, 7, 7, 7, 2, 8, 9, 10, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 12, 13, 14, 15, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 17, 18, 19, 1, 20, 20, 21, 22, 23, 24, 25, - 26, 27, 15, 2, 28, 29, 27, 30, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 31, 11, 11, 11, 32, 16, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 33, 16, 16, 16, 16, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 34, 34, 34, 34, 34, 34, 34, 34, 16, 32, 32, 32, - 32, 32, 32, 32, 11, 34, 34, 16, 34, 32, 32, 11, 34, 11, 16, 11, - 11, 34, 32, 11, 32, 16, 11, 34, 32, 32, 32, 11, 34, 16, 32, 11, - 34, 11, 34, 34, 32, 35, 32, 16, 36, 36, 37, 34, 38, 37, 34, 34, - 34, 34, 34, 34, 34, 34, 16, 32, 34, 38, 32, 11, 32, 32, 32, 32, - 32, 32, 16, 16, 16, 11, 34, 32, 34, 34, 11, 32, 32, 32, 32, 32, - 16, 16, 39, 16, 16, 16, 16, 16, 40, 40, 40, 40, 40, 40, 40, 40, - 40, 41, 41, 40, 40, 40, 40, 40, 40, 41, 41, 41, 41, 41, 41, 41, - 40, 40, 42, 41, 41, 41, 42, 42, 41, 41, 41, 41, 41, 41, 41, 41, - 43, 43, 43, 43, 43, 43, 43, 43, 32, 32, 42, 32, 44, 45, 16, 46, - 44, 44, 41, 47, 11, 48, 48, 11, 34, 11, 11, 11, 11, 11, 11, 11, - 11, 49, 11, 11, 11, 11, 16, 16, 16, 16, 16, 16, 16, 16, 16, 34, - 16, 11, 32, 16, 32, 32, 32, 32, 16, 16, 32, 50, 34, 32, 34, 11, - 32, 51, 43, 43, 52, 32, 32, 32, 11, 34, 34, 34, 34, 34, 34, 16, - 32, 32, 32, 32, 44, 44, 44, 44, 49, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 48, 53, 2, 2, 2, 54, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 55, 56, 44, 57, 58, 43, 43, 43, 43, 43, 43, 43, - 43, 43, 43, 43, 43, 43, 43, 59, 60, 61, 43, 60, 44, 44, 44, 44, - 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 62, 44, 44, - 36, 63, 46, 44, 44, 44, 44, 44, 64, 64, 65, 8, 9, 66, 2, 67, - 43, 43, 43, 43, 43, 61, 65, 2, 68, 36, 36, 36, 36, 69, 43, 43, - 7, 7, 7, 7, 7, 2, 2, 36, 70, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 71, 43, 43, 43, 72, 51, 43, 43, 73, 74, 75, 43, 43, 36, - 7, 7, 7, 7, 7, 36, 76, 77, 2, 2, 2, 2, 2, 2, 2, 78, - 69, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, 43, 79, 80, 36, - 36, 36, 36, 43, 43, 43, 43, 43, 70, 44, 44, 44, 44, 44, 44, 44, - 7, 7, 7, 7, 7, 36, 36, 36, 36, 36, 36, 36, 36, 69, 43, 43, - 43, 43, 40, 21, 2, 81, 44, 44, 36, 36, 36, 43, 43, 74, 43, 43, - 43, 43, 74, 43, 74, 43, 43, 44, 2, 2, 2, 2, 2, 2, 2, 46, - 36, 36, 36, 36, 69, 43, 44, 46, 44, 44, 44, 44, 44, 44, 44, 44, - 62, 36, 36, 36, 36, 36, 62, 44, 44, 44, 43, 43, 43, 43, 43, 43, - 43, 43, 43, 43, 43, 43, 43, 79, 43, 82, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 82, 70, 83, 84, 43, 43, 43, 82, 83, 84, 83, - 69, 43, 43, 43, 36, 36, 36, 36, 36, 43, 2, 7, 7, 7, 7, 7, - 85, 36, 36, 36, 80, 36, 36, 36, 58, 83, 80, 36, 36, 36, 62, 80, - 62, 80, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 62, 36, 36, 36, - 62, 62, 44, 36, 36, 44, 70, 83, 84, 43, 79, 86, 87, 86, 84, 62, - 44, 44, 44, 86, 44, 44, 36, 80, 36, 43, 44, 7, 7, 7, 7, 7, - 36, 20, 27, 27, 27, 88, 44, 44, 58, 82, 80, 36, 36, 62, 44, 80, - 62, 36, 80, 62, 36, 44, 79, 83, 84, 79, 44, 58, 79, 58, 43, 44, - 58, 44, 44, 44, 80, 36, 62, 62, 44, 44, 44, 7, 7, 7, 7, 7, - 43, 36, 69, 44, 44, 44, 44, 44, 58, 82, 80, 36, 36, 36, 36, 80, - 36, 80, 36, 36, 36, 36, 36, 36, 62, 36, 80, 36, 36, 44, 70, 83, - 84, 43, 43, 58, 82, 86, 84, 44, 62, 44, 44, 44, 44, 44, 44, 44, - 66, 44, 44, 44, 44, 44, 44, 44, 62, 36, 80, 36, 36, 44, 70, 84, - 84, 43, 79, 86, 87, 86, 84, 44, 44, 44, 44, 82, 44, 44, 36, 80, - 77, 27, 27, 27, 44, 44, 44, 44, 44, 70, 80, 36, 36, 62, 44, 36, - 62, 36, 36, 44, 80, 62, 62, 36, 44, 80, 62, 44, 36, 62, 44, 36, - 36, 36, 36, 36, 36, 44, 44, 83, 82, 87, 44, 83, 87, 83, 84, 44, - 62, 44, 44, 86, 44, 44, 44, 44, 27, 89, 67, 67, 88, 90, 44, 44, - 86, 83, 80, 36, 36, 36, 62, 36, 62, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 80, 36, 36, 44, 80, 43, 82, 83, 87, 43, 79, 43, 43, 44, - 44, 44, 58, 79, 36, 44, 44, 44, 44, 44, 44, 44, 27, 27, 27, 89, - 44, 83, 80, 36, 36, 36, 62, 36, 36, 36, 80, 36, 36, 44, 70, 84, - 83, 83, 87, 82, 87, 83, 43, 44, 44, 44, 86, 87, 44, 44, 44, 62, - 80, 62, 44, 44, 44, 44, 44, 44, 36, 36, 36, 36, 36, 62, 80, 83, - 84, 43, 79, 83, 87, 83, 84, 62, 44, 44, 44, 86, 44, 44, 44, 44, - 27, 27, 27, 44, 91, 36, 36, 36, 44, 83, 80, 36, 36, 36, 36, 36, - 36, 36, 36, 62, 44, 36, 36, 36, 36, 80, 36, 36, 36, 36, 80, 44, - 36, 36, 36, 62, 44, 79, 44, 86, 83, 43, 79, 79, 83, 83, 83, 83, - 44, 83, 46, 44, 44, 44, 44, 44, 80, 36, 36, 36, 36, 36, 36, 36, - 69, 36, 43, 43, 43, 79, 44, 57, 36, 36, 36, 74, 43, 43, 43, 61, - 7, 7, 7, 7, 7, 2, 44, 44, 80, 62, 62, 80, 62, 62, 80, 44, - 44, 44, 36, 36, 80, 36, 36, 36, 80, 36, 80, 80, 44, 36, 80, 36, - 69, 36, 43, 43, 43, 58, 70, 44, 36, 36, 62, 81, 43, 43, 43, 44, - 7, 7, 7, 7, 7, 44, 36, 36, 76, 67, 2, 2, 2, 2, 2, 2, - 2, 92, 92, 67, 43, 67, 67, 67, 7, 7, 7, 7, 7, 27, 27, 27, - 27, 27, 51, 51, 51, 4, 4, 83, 36, 36, 36, 36, 80, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 62, 44, 58, 43, 43, 43, 43, 43, 43, 82, - 43, 43, 61, 43, 36, 36, 69, 43, 43, 43, 43, 43, 58, 43, 43, 43, - 43, 43, 43, 43, 43, 43, 79, 67, 67, 67, 67, 75, 67, 67, 90, 67, - 2, 2, 92, 67, 21, 46, 44, 44, 36, 36, 36, 36, 36, 93, 84, 43, - 82, 43, 43, 43, 84, 82, 84, 70, 7, 7, 7, 7, 7, 2, 2, 2, - 36, 36, 36, 83, 43, 36, 36, 43, 70, 83, 94, 93, 83, 83, 83, 36, - 69, 43, 70, 36, 36, 36, 36, 36, 36, 82, 84, 82, 83, 83, 84, 93, - 7, 7, 7, 7, 7, 83, 84, 67, 11, 11, 11, 49, 44, 44, 49, 44, - 36, 36, 36, 36, 36, 63, 68, 36, 36, 36, 36, 36, 62, 36, 36, 44, - 36, 36, 36, 62, 62, 36, 36, 44, 62, 36, 36, 44, 36, 36, 36, 62, - 62, 36, 36, 44, 36, 36, 36, 36, 36, 36, 36, 62, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 62, 58, 43, 2, 2, 2, 2, 95, 27, 27, 27, - 27, 27, 27, 27, 27, 27, 96, 44, 67, 67, 67, 67, 67, 44, 44, 44, - 36, 36, 62, 44, 44, 44, 44, 44, 97, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 63, 71, 98, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 99, 100, 44, 36, 36, 36, 36, 36, 63, 2, 101, - 102, 44, 44, 44, 44, 44, 44, 44, 36, 36, 36, 36, 36, 36, 62, 36, - 36, 43, 79, 44, 44, 44, 44, 44, 36, 43, 61, 46, 44, 44, 44, 44, - 36, 43, 44, 44, 44, 44, 44, 44, 62, 43, 44, 44, 44, 44, 44, 44, - 36, 36, 43, 84, 43, 43, 43, 83, 83, 83, 83, 82, 84, 43, 43, 43, - 43, 43, 2, 85, 2, 66, 69, 44, 7, 7, 7, 7, 7, 44, 44, 44, - 27, 27, 27, 27, 27, 44, 44, 44, 2, 2, 2, 103, 2, 60, 43, 65, - 36, 104, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 44, 44, 44, 44, - 36, 36, 36, 36, 69, 62, 44, 44, 36, 36, 36, 44, 44, 44, 44, 44, - 43, 82, 83, 84, 82, 83, 44, 44, 83, 82, 83, 83, 84, 43, 44, 44, - 90, 44, 2, 7, 7, 7, 7, 7, 36, 36, 36, 36, 36, 36, 36, 44, - 36, 36, 36, 36, 36, 36, 44, 44, 83, 83, 83, 83, 83, 83, 83, 83, - 94, 36, 36, 36, 83, 44, 44, 44, 7, 7, 7, 7, 7, 96, 44, 67, - 67, 67, 67, 67, 67, 67, 67, 67, 36, 36, 36, 69, 82, 84, 44, 2, - 36, 36, 93, 82, 43, 43, 43, 79, 82, 82, 84, 43, 43, 43, 82, 83, - 83, 84, 43, 43, 43, 43, 79, 58, 2, 2, 2, 85, 2, 2, 2, 44, - 43, 43, 94, 36, 36, 36, 36, 36, 36, 36, 82, 43, 43, 82, 82, 83, - 83, 82, 94, 36, 36, 36, 44, 44, 92, 67, 67, 67, 67, 51, 43, 43, - 43, 43, 67, 67, 67, 67, 90, 44, 43, 94, 36, 36, 36, 36, 36, 36, - 93, 43, 43, 83, 43, 84, 83, 36, 36, 36, 36, 82, 43, 83, 84, 84, - 43, 83, 44, 44, 44, 44, 2, 2, 36, 36, 83, 83, 83, 83, 43, 43, - 43, 43, 83, 43, 44, 55, 2, 2, 7, 7, 7, 7, 7, 44, 80, 36, - 36, 36, 36, 36, 40, 40, 40, 2, 2, 2, 2, 2, 44, 44, 44, 44, - 43, 61, 43, 43, 43, 43, 43, 43, 82, 43, 43, 43, 70, 36, 69, 36, - 36, 83, 70, 62, 44, 44, 44, 44, 16, 16, 16, 16, 16, 16, 40, 40, - 40, 40, 40, 40, 40, 45, 16, 16, 16, 16, 16, 16, 45, 16, 16, 16, - 16, 16, 16, 16, 16, 105, 40, 40, 43, 43, 43, 79, 44, 44, 44, 44, - 44, 44, 44, 44, 44, 44, 43, 43, 32, 32, 32, 16, 16, 16, 16, 32, - 16, 16, 16, 16, 11, 11, 11, 11, 16, 16, 16, 44, 11, 11, 11, 44, - 16, 16, 16, 16, 49, 49, 49, 49, 16, 16, 16, 16, 16, 16, 16, 44, - 16, 16, 16, 16, 106, 106, 106, 106, 16, 16, 107, 16, 11, 11, 108, 109, - 41, 16, 107, 16, 11, 11, 108, 41, 16, 16, 44, 16, 11, 11, 110, 41, - 16, 16, 16, 16, 11, 11, 111, 41, 44, 16, 107, 16, 11, 11, 108, 112, - 113, 113, 113, 113, 113, 114, 64, 64, 115, 115, 115, 2, 116, 117, 116, 117, - 2, 2, 2, 2, 118, 64, 64, 119, 2, 2, 2, 2, 120, 121, 2, 122, - 123, 2, 124, 125, 2, 2, 2, 2, 2, 9, 123, 2, 2, 2, 2, 126, - 64, 64, 65, 64, 64, 64, 64, 64, 127, 44, 27, 27, 27, 8, 124, 128, - 27, 27, 27, 27, 27, 8, 124, 100, 40, 40, 40, 40, 40, 40, 81, 44, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 129, 44, 44, - 43, 43, 43, 43, 43, 43, 130, 52, 131, 52, 131, 43, 43, 43, 43, 43, - 79, 44, 44, 44, 44, 44, 44, 44, 67, 132, 67, 133, 67, 34, 11, 16, - 11, 32, 133, 67, 50, 11, 11, 67, 67, 67, 132, 132, 132, 11, 11, 134, - 11, 11, 35, 36, 39, 67, 16, 11, 8, 8, 50, 16, 16, 26, 67, 135, - 27, 27, 27, 27, 27, 27, 27, 27, 101, 101, 101, 101, 101, 101, 101, 101, - 101, 136, 137, 101, 138, 44, 44, 44, 8, 8, 139, 67, 67, 8, 67, 67, - 139, 26, 67, 139, 67, 67, 67, 139, 67, 67, 67, 67, 67, 67, 67, 8, - 67, 139, 139, 67, 67, 67, 67, 67, 67, 67, 8, 8, 8, 8, 8, 8, - 8, 8, 8, 8, 8, 8, 8, 8, 67, 67, 67, 67, 4, 4, 67, 67, - 8, 67, 67, 67, 140, 141, 67, 67, 67, 67, 67, 67, 67, 67, 139, 67, - 67, 67, 67, 67, 67, 26, 8, 8, 8, 8, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 8, 8, 8, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 44, 44, 44, 44, 44, 44, 67, 67, 67, 90, 44, 44, 44, 44, - 67, 67, 67, 67, 67, 90, 44, 44, 27, 27, 27, 27, 27, 27, 67, 67, - 67, 67, 67, 67, 67, 27, 27, 27, 67, 67, 67, 26, 67, 67, 67, 67, - 26, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 8, 8, 8, 8, - 67, 67, 67, 67, 67, 67, 67, 26, 91, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 4, 4, 4, 4, 4, 4, 4, 27, 27, 27, 27, 27, - 27, 27, 67, 67, 67, 67, 67, 67, 8, 8, 124, 142, 8, 8, 8, 8, - 8, 8, 8, 4, 4, 4, 4, 4, 8, 124, 143, 143, 143, 143, 143, 143, - 143, 143, 143, 143, 142, 8, 8, 8, 8, 8, 8, 8, 4, 4, 8, 8, - 8, 8, 8, 8, 8, 8, 4, 8, 8, 8, 139, 26, 8, 8, 144, 44, - 11, 11, 11, 11, 11, 11, 11, 48, 16, 16, 16, 16, 16, 16, 16, 107, - 32, 11, 32, 34, 34, 34, 34, 11, 32, 32, 34, 16, 16, 16, 40, 11, - 32, 32, 135, 67, 67, 133, 34, 145, 43, 32, 44, 44, 55, 2, 95, 2, - 16, 16, 16, 54, 44, 44, 54, 44, 36, 36, 36, 36, 44, 44, 44, 53, - 46, 44, 44, 44, 44, 44, 44, 58, 36, 36, 36, 62, 44, 44, 44, 44, - 36, 36, 36, 62, 36, 36, 36, 62, 2, 116, 116, 2, 120, 121, 116, 2, - 2, 2, 2, 6, 2, 103, 116, 2, 116, 4, 4, 4, 4, 2, 2, 85, - 2, 2, 2, 2, 2, 115, 44, 44, 67, 67, 67, 67, 67, 91, 67, 67, - 67, 67, 67, 44, 44, 44, 44, 44, 67, 67, 67, 67, 67, 67, 44, 44, - 1, 2, 146, 147, 4, 4, 4, 4, 4, 67, 4, 4, 4, 4, 148, 149, - 150, 101, 101, 101, 101, 43, 43, 83, 151, 40, 40, 67, 101, 152, 63, 67, - 36, 36, 36, 62, 58, 153, 154, 68, 36, 36, 36, 36, 36, 63, 40, 68, - 44, 44, 80, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 62, - 67, 27, 27, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 90, - 27, 27, 27, 27, 27, 67, 67, 67, 67, 67, 67, 67, 27, 27, 27, 27, - 155, 27, 27, 27, 27, 27, 27, 27, 36, 36, 104, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 156, 2, 7, 7, 7, 7, 7, 36, 44, 44, - 32, 32, 32, 32, 32, 32, 32, 69, 52, 157, 43, 43, 43, 43, 43, 85, - 32, 32, 32, 32, 44, 44, 44, 58, 36, 36, 36, 101, 101, 101, 101, 101, - 43, 2, 2, 2, 44, 44, 44, 44, 41, 41, 41, 154, 40, 40, 40, 40, - 41, 32, 32, 32, 32, 32, 32, 32, 16, 32, 32, 32, 32, 32, 32, 32, - 45, 16, 16, 16, 34, 34, 34, 32, 32, 32, 32, 32, 42, 158, 34, 107, - 32, 32, 44, 44, 44, 44, 44, 44, 32, 32, 32, 32, 32, 48, 44, 44, - 44, 44, 44, 44, 40, 35, 36, 36, 36, 70, 36, 70, 36, 69, 36, 36, - 36, 93, 84, 82, 67, 67, 44, 44, 27, 27, 27, 67, 159, 44, 44, 44, - 36, 36, 2, 2, 44, 44, 44, 44, 83, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 83, 83, 83, 83, 83, 83, 83, 83, 79, 44, 44, 44, 44, 2, - 43, 36, 36, 36, 2, 71, 44, 44, 36, 36, 36, 43, 43, 43, 43, 2, - 36, 36, 36, 69, 43, 43, 43, 43, 43, 83, 44, 44, 44, 44, 44, 55, - 36, 69, 83, 43, 43, 83, 82, 83, 160, 2, 2, 2, 2, 2, 2, 53, - 7, 7, 7, 7, 7, 44, 44, 2, 36, 36, 36, 36, 69, 43, 43, 82, - 84, 82, 84, 79, 44, 44, 44, 44, 36, 69, 36, 36, 36, 36, 82, 44, - 7, 7, 7, 7, 7, 44, 2, 2, 68, 36, 36, 76, 67, 93, 44, 44, - 70, 43, 70, 69, 70, 36, 36, 43, 69, 62, 44, 44, 44, 44, 44, 44, - 44, 44, 44, 44, 44, 80, 104, 2, 36, 36, 36, 36, 36, 93, 43, 83, - 2, 104, 161, 79, 44, 44, 44, 44, 80, 36, 36, 62, 80, 36, 36, 62, - 80, 36, 36, 62, 44, 44, 44, 44, 36, 93, 84, 83, 82, 160, 84, 44, - 36, 36, 44, 44, 44, 44, 44, 44, 36, 36, 36, 62, 44, 80, 36, 36, - 162, 162, 162, 162, 162, 162, 162, 162, 163, 163, 163, 163, 163, 163, 163, 163, - 36, 36, 36, 36, 36, 44, 44, 44, 16, 16, 16, 107, 44, 44, 44, 44, - 44, 54, 16, 16, 44, 44, 80, 70, 36, 36, 36, 36, 164, 36, 36, 36, - 36, 36, 36, 62, 36, 36, 62, 62, 36, 80, 62, 36, 36, 36, 36, 36, - 36, 41, 41, 41, 41, 41, 41, 41, 41, 44, 44, 44, 44, 44, 44, 44, - 44, 80, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 4, - 44, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 159, 44, - 2, 2, 2, 165, 125, 44, 44, 44, 6, 166, 167, 143, 143, 143, 143, 143, - 143, 143, 125, 165, 125, 2, 122, 168, 2, 46, 2, 2, 148, 143, 143, 125, - 2, 169, 8, 144, 66, 2, 44, 44, 36, 36, 62, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 62, 78, 55, 2, 3, 2, 4, 5, 6, 2, - 16, 16, 16, 16, 16, 17, 18, 124, 125, 4, 2, 36, 36, 36, 36, 36, - 68, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 40, - 44, 36, 36, 36, 44, 36, 36, 36, 44, 36, 36, 36, 44, 36, 62, 44, - 20, 170, 88, 129, 26, 8, 139, 90, 44, 44, 44, 44, 78, 64, 67, 44, - 36, 36, 36, 36, 36, 36, 80, 36, 36, 36, 36, 36, 36, 62, 36, 80, - 2, 46, 44, 171, 27, 27, 27, 27, 27, 27, 44, 91, 67, 67, 67, 67, - 101, 101, 138, 27, 89, 67, 67, 67, 67, 67, 67, 67, 67, 96, 44, 44, - 67, 67, 67, 67, 67, 67, 51, 44, 27, 27, 44, 44, 44, 44, 44, 44, - 147, 36, 36, 36, 36, 102, 44, 44, 36, 36, 36, 36, 36, 36, 36, 55, - 36, 36, 44, 44, 36, 36, 36, 36, 172, 101, 101, 44, 44, 44, 44, 44, - 11, 11, 11, 11, 16, 16, 16, 16, 36, 36, 36, 44, 62, 36, 36, 36, - 36, 36, 36, 80, 62, 44, 62, 80, 36, 36, 36, 55, 27, 27, 27, 27, - 36, 36, 36, 27, 27, 27, 44, 55, 36, 36, 36, 36, 36, 44, 44, 55, - 36, 36, 36, 36, 44, 44, 44, 36, 69, 43, 58, 79, 44, 44, 43, 43, - 36, 36, 80, 36, 80, 36, 36, 36, 36, 36, 44, 44, 43, 79, 44, 58, - 27, 27, 27, 27, 44, 44, 44, 44, 2, 2, 2, 2, 46, 44, 44, 44, - 36, 36, 36, 36, 36, 36, 173, 30, 36, 36, 36, 44, 55, 2, 2, 2, - 36, 36, 36, 44, 27, 27, 27, 27, 36, 62, 44, 44, 27, 27, 27, 27, - 36, 36, 36, 36, 62, 44, 44, 44, 27, 27, 27, 27, 27, 27, 27, 96, - 84, 94, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 43, 43, 43, 43, - 43, 43, 43, 61, 2, 2, 2, 44, 44, 27, 27, 27, 27, 27, 27, 27, - 27, 27, 27, 7, 7, 7, 7, 7, 83, 84, 43, 82, 84, 61, 174, 2, - 2, 44, 44, 44, 44, 44, 44, 44, 43, 70, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 69, 43, 43, 84, 43, 43, 43, 79, 7, 7, 7, 7, 7, - 2, 2, 44, 44, 44, 44, 44, 44, 36, 93, 83, 43, 43, 43, 43, 82, - 94, 36, 63, 2, 46, 44, 44, 44, 36, 36, 36, 36, 36, 69, 84, 83, - 43, 43, 43, 84, 44, 44, 44, 44, 101, 102, 44, 44, 44, 44, 44, 44, - 93, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 87, - 44, 44, 44, 44, 44, 44, 44, 58, 43, 73, 40, 40, 40, 40, 40, 40, - 36, 44, 44, 44, 44, 44, 44, 44, 67, 67, 67, 90, 91, 67, 67, 67, - 67, 67, 175, 84, 43, 67, 175, 83, 83, 176, 64, 64, 64, 177, 43, 43, - 43, 75, 51, 43, 43, 43, 67, 67, 67, 67, 67, 67, 67, 43, 43, 67, - 67, 67, 67, 67, 67, 67, 67, 44, 67, 43, 75, 44, 44, 44, 44, 44, - 27, 44, 44, 44, 44, 44, 44, 44, 11, 11, 11, 11, 11, 16, 16, 16, - 16, 16, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 16, - 16, 16, 107, 16, 16, 16, 16, 16, 11, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 16, 48, 11, 44, 48, 49, 48, 49, 11, 48, 11, - 11, 11, 11, 16, 16, 54, 54, 16, 16, 16, 54, 16, 16, 16, 16, 16, - 16, 16, 11, 49, 11, 48, 49, 11, 11, 11, 48, 11, 11, 11, 48, 16, - 16, 16, 16, 16, 11, 49, 11, 48, 11, 11, 48, 48, 44, 11, 11, 11, - 48, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 11, 11, - 11, 11, 11, 16, 16, 16, 16, 16, 16, 16, 16, 44, 11, 11, 11, 11, - 31, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 33, 16, 16, - 16, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 31, 16, 16, - 16, 16, 33, 16, 16, 16, 11, 11, 11, 11, 31, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 16, 16, 33, 16, 16, 16, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 31, 16, 16, 16, 16, 33, 16, 16, 16, - 11, 11, 11, 11, 31, 16, 16, 16, 16, 33, 16, 16, 16, 32, 44, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 36, 36, 80, 36, 36, 36, 36, 36, - 80, 62, 62, 80, 80, 36, 36, 36, 36, 62, 36, 36, 80, 80, 44, 44, - 44, 62, 44, 80, 80, 80, 80, 36, 80, 62, 62, 80, 80, 80, 80, 80, - 80, 62, 62, 80, 36, 62, 36, 36, 36, 62, 36, 36, 80, 36, 62, 62, - 36, 36, 36, 36, 36, 80, 36, 36, 80, 36, 80, 36, 36, 80, 36, 36, - 8, 44, 44, 44, 44, 44, 44, 44, 91, 67, 67, 67, 67, 67, 67, 90, - 27, 27, 27, 27, 27, 96, 44, 44, 44, 44, 44, 67, 67, 67, 67, 67, - 67, 90, 44, 44, 44, 44, 44, 44, 67, 67, 67, 67, 90, 44, 44, 44, - 67, 44, 44, 44, 44, 44, 44, 44, 90, 44, 44, 44, 44, 44, 44, 44, - 67, 67, 67, 91, 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, 90, 44, - 67, 67, 90, 67, 67, 90, 44, 44, 90, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 91, 67, 90, 44, 67, 67, 67, 67, 44, 44, 44, 44, - 44, 44, 44, 44, 44, 91, 67, 67, 90, 44, 91, 67, 67, 67, 67, 67, - 78, 44, 44, 44, 44, 44, 44, 44, 64, 64, 64, 64, 64, 64, 64, 64, - 163, 163, 163, 163, 163, 163, 163, 44, -}; - -static RE_UINT8 re_general_category_stage_5[] = { - 15, 15, 12, 23, 23, 23, 25, 23, 20, 21, 23, 24, 23, 19, 9, 9, - 24, 24, 24, 23, 23, 1, 1, 1, 1, 20, 23, 21, 26, 22, 26, 2, - 2, 2, 2, 20, 24, 21, 24, 15, 25, 25, 27, 23, 26, 27, 5, 28, - 24, 16, 27, 26, 27, 24, 11, 11, 26, 11, 5, 29, 11, 23, 1, 24, - 1, 2, 2, 24, 2, 1, 2, 5, 5, 5, 1, 3, 3, 2, 5, 2, - 4, 4, 26, 26, 4, 26, 6, 6, 0, 0, 4, 2, 23, 0, 1, 23, - 1, 0, 0, 1, 24, 1, 27, 6, 7, 7, 0, 4, 0, 2, 0, 23, - 19, 0, 0, 25, 0, 6, 19, 6, 23, 6, 6, 23, 5, 0, 5, 23, - 16, 16, 16, 0, 23, 25, 27, 27, 4, 5, 5, 6, 6, 5, 23, 5, - 6, 16, 6, 4, 4, 6, 6, 27, 5, 27, 27, 5, 0, 16, 6, 0, - 0, 5, 4, 0, 6, 8, 8, 8, 8, 6, 23, 4, 0, 8, 8, 0, - 27, 25, 11, 27, 27, 0, 0, 27, 23, 27, 5, 8, 8, 5, 23, 11, - 11, 0, 19, 5, 12, 5, 5, 20, 21, 0, 10, 10, 10, 0, 19, 23, - 5, 4, 2, 4, 3, 3, 2, 0, 3, 26, 2, 26, 0, 26, 1, 26, - 26, 0, 12, 12, 12, 16, 19, 19, 28, 29, 20, 28, 13, 14, 16, 12, - 23, 28, 29, 23, 23, 22, 22, 23, 24, 20, 21, 23, 23, 12, 11, 4, - 21, 4, 25, 0, 6, 7, 7, 6, 1, 27, 27, 1, 27, 2, 2, 27, - 10, 1, 2, 10, 10, 11, 24, 27, 27, 20, 21, 27, 21, 24, 21, 20, - 24, 0, 2, 6, 27, 4, 5, 10, 19, 20, 21, 21, 27, 10, 19, 4, - 10, 4, 6, 26, 26, 4, 27, 11, 4, 23, 7, 23, 26, 1, 25, 27, - 8, 23, 4, 8, 18, 18, 17, 17, 5, 24, 23, 20, 19, 22, 22, 20, - 22, 22, 24, 19, 24, 26, 0, 11, 23, 10, 5, 11, 23, 16, 27, 8, - 8, 16, 16, 6, -}; - -/* General_Category: 8556 bytes. */ - -RE_UINT32 re_get_general_category(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 11; - code = ch ^ (f << 11); - pos = (RE_UINT32)re_general_category_stage_1[f] << 4; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_general_category_stage_2[pos + f] << 3; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_general_category_stage_3[pos + f] << 3; - f = code >> 1; - code ^= f << 1; - pos = (RE_UINT32)re_general_category_stage_4[pos + f] << 1; - value = re_general_category_stage_5[pos + code]; - - return value; -} - -/* Block. */ - -static RE_UINT8 re_block_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 10, 11, 12, 12, 12, 12, 13, 14, 15, 15, 15, 16, - 17, 18, 19, 20, 21, 20, 22, 20, 20, 20, 20, 20, 20, 23, 20, 20, - 20, 20, 20, 20, 20, 20, 24, 20, 20, 20, 25, 20, 20, 26, 27, 20, - 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, - 28, 28, 28, 28, 29, 30, 31, 32, 20, 20, 20, 20, 20, 20, 20, 33, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 34, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, - 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, - 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, -}; - -static RE_UINT8 re_block_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9, 10, 11, 11, 12, 13, - 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 28, - 29, 30, 31, 31, 32, 32, 32, 33, 34, 34, 34, 34, 34, 35, 36, 37, - 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 50, 51, 51, - 52, 53, 54, 55, 56, 56, 57, 57, 58, 59, 60, 61, 62, 62, 63, 64, - 65, 65, 66, 67, 68, 68, 69, 69, 70, 71, 72, 73, 74, 75, 76, 77, - 78, 79, 80, 81, 82, 82, 83, 83, 84, 84, 84, 84, 84, 84, 84, 84, - 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, - 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 84, 85, 86, 86, 86, 86, - 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, - 87, 87, 87, 87, 87, 87, 87, 87, 87, 88, 89, 89, 90, 91, 92, 93, - 94, 95, 96, 97, 98, 99, 100, 101, 102, 102, 102, 102, 102, 102, 102, 102, - 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, - 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 103, - 104, 104, 104, 104, 104, 104, 104, 105, 106, 106, 106, 106, 106, 106, 106, 106, - 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, 107, - 107, 107, 108, 108, 108, 108, 109, 110, 110, 110, 110, 110, 111, 112, 113, 114, - 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 119, 119, 119, 119, 119, 119, - 125, 119, 126, 127, 128, 119, 129, 119, 130, 119, 119, 119, 131, 119, 119, 119, - 132, 133, 134, 135, 119, 119, 119, 119, 119, 119, 119, 119, 119, 136, 119, 119, - 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, - 137, 137, 137, 137, 137, 137, 137, 137, 138, 119, 119, 119, 119, 119, 119, 119, - 139, 139, 139, 139, 139, 139, 139, 139, 140, 119, 119, 119, 119, 119, 119, 119, - 141, 141, 141, 141, 142, 119, 119, 119, 119, 119, 119, 119, 119, 119, 143, 144, - 145, 145, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, - 146, 146, 147, 147, 148, 119, 149, 119, 150, 150, 150, 150, 150, 150, 150, 150, - 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 151, 151, 119, 119, - 152, 153, 154, 154, 155, 155, 156, 156, 156, 156, 156, 156, 157, 158, 159, 119, - 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, - 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 161, 162, 162, - 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, - 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 162, 163, 164, - 165, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, - 166, 166, 166, 166, 167, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, - 168, 119, 169, 170, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, - 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, - 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, 172, -}; - -static RE_UINT8 re_block_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 5, 5, 5, 5, 5, - 6, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 8, 8, 8, 8, 8, 8, 8, 8, 9, 9, 9, 10, 10, 10, 10, 10, - 10, 11, 11, 11, 11, 11, 11, 11, 12, 12, 12, 12, 12, 12, 12, 12, - 13, 13, 13, 13, 13, 14, 14, 14, 15, 15, 15, 15, 16, 16, 16, 16, - 17, 17, 17, 17, 18, 18, 19, 19, 19, 19, 20, 20, 20, 20, 20, 20, - 21, 21, 21, 21, 21, 21, 21, 21, 22, 22, 22, 22, 22, 22, 22, 22, - 23, 23, 23, 23, 23, 23, 23, 23, 24, 24, 24, 24, 24, 24, 24, 24, - 25, 25, 25, 25, 25, 25, 25, 25, 26, 26, 26, 26, 26, 26, 26, 26, - 27, 27, 27, 27, 27, 27, 27, 27, 28, 28, 28, 28, 28, 28, 28, 28, - 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 30, 30, 30, 30, 30, 30, - 31, 31, 31, 31, 31, 31, 31, 31, 32, 32, 32, 32, 32, 32, 32, 32, - 33, 33, 33, 33, 33, 33, 33, 33, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 35, 35, 35, 35, 35, 35, 36, 36, 36, 36, 36, 36, 36, 36, - 37, 37, 37, 37, 37, 37, 37, 37, 38, 38, 39, 39, 39, 39, 39, 39, - 40, 40, 40, 40, 40, 40, 40, 40, 41, 41, 42, 42, 42, 42, 42, 42, - 43, 43, 44, 44, 45, 45, 46, 46, 47, 47, 47, 47, 47, 47, 47, 47, - 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 49, 49, 49, 49, 49, - 50, 50, 50, 50, 50, 51, 51, 51, 52, 52, 52, 52, 52, 52, 53, 53, - 54, 54, 55, 55, 55, 55, 55, 55, 55, 55, 55, 19, 19, 19, 19, 19, - 56, 56, 56, 56, 56, 56, 56, 56, 57, 57, 57, 57, 58, 58, 58, 58, - 59, 59, 59, 59, 59, 60, 60, 60, 19, 19, 19, 19, 61, 62, 62, 62, - 63, 63, 63, 63, 63, 63, 63, 63, 64, 64, 64, 64, 65, 65, 65, 65, - 66, 66, 66, 66, 66, 66, 66, 66, 67, 67, 67, 67, 67, 67, 67, 67, - 68, 68, 68, 68, 68, 68, 68, 69, 69, 69, 70, 70, 70, 71, 71, 71, - 72, 72, 72, 72, 72, 73, 73, 73, 73, 74, 74, 74, 74, 74, 74, 74, - 75, 75, 75, 75, 75, 75, 75, 75, 76, 76, 76, 76, 76, 76, 76, 76, - 77, 77, 77, 77, 78, 78, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 80, 80, 80, 80, 80, 80, 80, 80, 81, 81, 82, 82, 82, 82, 82, 82, - 83, 83, 83, 83, 83, 83, 83, 83, 84, 84, 84, 84, 84, 84, 84, 84, - 84, 84, 84, 84, 85, 85, 85, 86, 87, 87, 87, 87, 87, 87, 87, 87, - 88, 88, 88, 88, 88, 88, 88, 88, 89, 89, 89, 89, 89, 89, 89, 89, - 90, 90, 90, 90, 90, 90, 90, 90, 91, 91, 91, 91, 91, 91, 91, 91, - 92, 92, 92, 92, 92, 92, 93, 93, 94, 94, 94, 94, 94, 94, 94, 94, - 95, 95, 95, 96, 96, 96, 96, 96, 97, 97, 97, 97, 97, 97, 98, 98, - 99, 99, 99, 99, 99, 99, 99, 99, 100, 100, 100, 100, 100, 100, 100, 100, - 101, 101, 101, 101, 101, 101, 101, 101, 101, 101, 101, 101, 101, 101, 19, 102, - 103, 103, 103, 103, 104, 104, 104, 104, 104, 104, 105, 105, 105, 105, 105, 105, - 106, 106, 106, 107, 107, 107, 107, 107, 107, 108, 109, 109, 110, 110, 110, 111, - 112, 112, 112, 112, 112, 112, 112, 112, 113, 113, 113, 113, 113, 113, 113, 113, - 114, 114, 114, 114, 114, 114, 114, 114, 114, 114, 114, 114, 115, 115, 115, 115, - 116, 116, 116, 116, 116, 116, 116, 116, 117, 117, 117, 117, 117, 117, 117, 117, - 117, 118, 118, 118, 118, 119, 119, 119, 120, 120, 120, 120, 120, 120, 120, 120, - 120, 120, 120, 120, 121, 121, 121, 121, 121, 121, 122, 122, 122, 122, 122, 122, - 123, 123, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, 124, - 125, 125, 125, 126, 127, 127, 127, 127, 128, 128, 128, 128, 128, 128, 129, 129, - 130, 130, 130, 131, 131, 131, 132, 132, 133, 133, 133, 133, 133, 133, 19, 19, - 134, 134, 134, 134, 134, 134, 135, 135, 136, 136, 136, 136, 136, 136, 137, 137, - 138, 138, 138, 19, 19, 19, 19, 19, 19, 19, 19, 19, 139, 139, 139, 139, - 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 140, 141, 141, 141, 141, 141, - 142, 142, 142, 142, 142, 142, 142, 142, 143, 143, 143, 143, 143, 143, 143, 143, - 144, 144, 144, 144, 144, 144, 144, 144, 145, 145, 145, 145, 145, 145, 145, 145, - 146, 146, 146, 146, 146, 146, 146, 146, 147, 147, 147, 147, 147, 148, 148, 148, - 148, 148, 148, 148, 148, 148, 148, 148, 149, 150, 151, 152, 152, 153, 153, 154, - 154, 154, 154, 154, 154, 154, 154, 154, 155, 155, 155, 155, 155, 155, 155, 155, - 155, 155, 155, 155, 155, 155, 155, 156, 157, 157, 157, 157, 157, 157, 157, 157, - 158, 158, 158, 158, 158, 158, 158, 158, 159, 159, 159, 159, 160, 160, 160, 160, - 160, 161, 161, 161, 161, 162, 162, 162, 19, 19, 19, 19, 19, 19, 19, 19, - 163, 163, 164, 164, 164, 164, 19, 19, 165, 165, 165, 166, 166, 19, 19, 19, - 167, 167, 168, 168, 168, 168, 19, 19, 169, 169, 169, 169, 169, 170, 170, 170, - 171, 171, 171, 19, 19, 19, 19, 19, 172, 172, 172, 172, 173, 173, 19, 19, - 174, 174, 175, 175, 19, 19, 19, 19, 176, 176, 177, 177, 177, 177, 177, 177, - 178, 178, 178, 178, 178, 178, 179, 179, 180, 180, 180, 180, 181, 181, 182, 182, - 183, 183, 183, 183, 183, 19, 19, 19, 19, 19, 19, 19, 19, 19, 184, 184, - 185, 185, 185, 185, 185, 185, 185, 185, 186, 186, 186, 186, 186, 187, 187, 187, - 188, 188, 188, 188, 188, 19, 19, 19, 189, 189, 189, 189, 189, 189, 19, 19, - 190, 190, 190, 190, 190, 19, 19, 19, 191, 191, 191, 191, 191, 191, 191, 191, - 192, 192, 192, 192, 192, 192, 192, 192, 193, 193, 193, 193, 193, 193, 193, 193, - 193, 193, 193, 19, 19, 19, 19, 19, 194, 194, 194, 194, 194, 194, 194, 194, - 194, 194, 194, 194, 19, 19, 19, 19, 195, 195, 195, 195, 195, 195, 195, 195, - 195, 195, 19, 19, 19, 19, 19, 19, 196, 196, 196, 196, 196, 196, 196, 196, - 197, 197, 197, 197, 197, 197, 197, 197, 198, 198, 198, 198, 198, 198, 198, 198, - 199, 199, 199, 199, 199, 19, 19, 19, 200, 200, 200, 200, 200, 200, 201, 201, - 202, 202, 202, 202, 202, 202, 202, 202, 203, 203, 203, 203, 203, 203, 203, 203, - 204, 204, 204, 205, 205, 205, 205, 205, 205, 205, 206, 206, 206, 206, 206, 206, - 207, 207, 207, 207, 207, 207, 207, 207, 208, 208, 208, 208, 208, 208, 208, 208, - 209, 209, 209, 209, 209, 209, 209, 209, 210, 210, 210, 210, 210, 19, 19, 19, - 211, 211, 211, 211, 211, 211, 211, 211, 212, 212, 212, 212, 212, 212, 212, 212, - 213, 213, 213, 213, 213, 213, 213, 213, 213, 213, 213, 213, 213, 213, 19, 19, - 214, 214, 214, 214, 214, 214, 214, 214, 214, 214, 214, 214, 215, 215, 215, 215, - 215, 215, 215, 215, 215, 215, 215, 215, 215, 215, 19, 19, 19, 19, 19, 19, - 216, 216, 216, 216, 216, 216, 216, 216, 216, 216, 19, 19, 19, 19, 19, 19, - 217, 217, 217, 217, 217, 217, 217, 217, 218, 218, 218, 218, 218, 218, 218, 218, - 218, 218, 218, 218, 218, 218, 218, 19, 219, 219, 219, 219, 219, 219, 219, 219, - 220, 220, 220, 220, 220, 220, 220, 220, -}; - -static RE_UINT8 re_block_stage_4[] = { - 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, - 4, 4, 4, 4, 5, 5, 5, 5, 6, 6, 6, 6, 7, 7, 7, 7, - 8, 8, 8, 8, 9, 9, 9, 9, 10, 10, 10, 10, 11, 11, 11, 11, - 12, 12, 12, 12, 13, 13, 13, 13, 14, 14, 14, 14, 15, 15, 15, 15, - 16, 16, 16, 16, 17, 17, 17, 17, 18, 18, 18, 18, 19, 19, 19, 19, - 20, 20, 20, 20, 21, 21, 21, 21, 22, 22, 22, 22, 23, 23, 23, 23, - 24, 24, 24, 24, 25, 25, 25, 25, 26, 26, 26, 26, 27, 27, 27, 27, - 28, 28, 28, 28, 29, 29, 29, 29, 30, 30, 30, 30, 31, 31, 31, 31, - 32, 32, 32, 32, 33, 33, 33, 33, 34, 34, 34, 34, 35, 35, 35, 35, - 36, 36, 36, 36, 37, 37, 37, 37, 38, 38, 38, 38, 39, 39, 39, 39, - 40, 40, 40, 40, 41, 41, 41, 41, 42, 42, 42, 42, 43, 43, 43, 43, - 44, 44, 44, 44, 45, 45, 45, 45, 46, 46, 46, 46, 47, 47, 47, 47, - 48, 48, 48, 48, 49, 49, 49, 49, 50, 50, 50, 50, 51, 51, 51, 51, - 52, 52, 52, 52, 53, 53, 53, 53, 54, 54, 54, 54, 55, 55, 55, 55, - 56, 56, 56, 56, 57, 57, 57, 57, 58, 58, 58, 58, 59, 59, 59, 59, - 60, 60, 60, 60, 61, 61, 61, 61, 62, 62, 62, 62, 63, 63, 63, 63, - 64, 64, 64, 64, 65, 65, 65, 65, 66, 66, 66, 66, 67, 67, 67, 67, - 68, 68, 68, 68, 69, 69, 69, 69, 70, 70, 70, 70, 71, 71, 71, 71, - 72, 72, 72, 72, 73, 73, 73, 73, 74, 74, 74, 74, 75, 75, 75, 75, - 76, 76, 76, 76, 77, 77, 77, 77, 78, 78, 78, 78, 79, 79, 79, 79, - 80, 80, 80, 80, 81, 81, 81, 81, 82, 82, 82, 82, 83, 83, 83, 83, - 84, 84, 84, 84, 85, 85, 85, 85, 86, 86, 86, 86, 87, 87, 87, 87, - 88, 88, 88, 88, 89, 89, 89, 89, 90, 90, 90, 90, 91, 91, 91, 91, - 92, 92, 92, 92, 93, 93, 93, 93, 94, 94, 94, 94, 95, 95, 95, 95, - 96, 96, 96, 96, 97, 97, 97, 97, 98, 98, 98, 98, 99, 99, 99, 99, - 100, 100, 100, 100, 101, 101, 101, 101, 102, 102, 102, 102, 103, 103, 103, 103, - 104, 104, 104, 104, 105, 105, 105, 105, 106, 106, 106, 106, 107, 107, 107, 107, - 108, 108, 108, 108, 109, 109, 109, 109, 110, 110, 110, 110, 111, 111, 111, 111, - 112, 112, 112, 112, 113, 113, 113, 113, 114, 114, 114, 114, 115, 115, 115, 115, - 116, 116, 116, 116, 117, 117, 117, 117, 118, 118, 118, 118, 119, 119, 119, 119, - 120, 120, 120, 120, 121, 121, 121, 121, 122, 122, 122, 122, 123, 123, 123, 123, - 124, 124, 124, 124, 125, 125, 125, 125, 126, 126, 126, 126, 127, 127, 127, 127, - 128, 128, 128, 128, 129, 129, 129, 129, 130, 130, 130, 130, 131, 131, 131, 131, - 132, 132, 132, 132, 133, 133, 133, 133, 134, 134, 134, 134, 135, 135, 135, 135, - 136, 136, 136, 136, 137, 137, 137, 137, 138, 138, 138, 138, 139, 139, 139, 139, - 140, 140, 140, 140, 141, 141, 141, 141, 142, 142, 142, 142, 143, 143, 143, 143, - 144, 144, 144, 144, 145, 145, 145, 145, 146, 146, 146, 146, 147, 147, 147, 147, - 148, 148, 148, 148, 149, 149, 149, 149, 150, 150, 150, 150, 151, 151, 151, 151, - 152, 152, 152, 152, 153, 153, 153, 153, 154, 154, 154, 154, 155, 155, 155, 155, - 156, 156, 156, 156, 157, 157, 157, 157, 158, 158, 158, 158, 159, 159, 159, 159, - 160, 160, 160, 160, 161, 161, 161, 161, 162, 162, 162, 162, 163, 163, 163, 163, - 164, 164, 164, 164, 165, 165, 165, 165, 166, 166, 166, 166, 167, 167, 167, 167, - 168, 168, 168, 168, 169, 169, 169, 169, 170, 170, 170, 170, 171, 171, 171, 171, - 172, 172, 172, 172, 173, 173, 173, 173, 174, 174, 174, 174, 175, 175, 175, 175, - 176, 176, 176, 176, 177, 177, 177, 177, 178, 178, 178, 178, 179, 179, 179, 179, - 180, 180, 180, 180, 181, 181, 181, 181, 182, 182, 182, 182, 183, 183, 183, 183, - 184, 184, 184, 184, 185, 185, 185, 185, 186, 186, 186, 186, 187, 187, 187, 187, - 188, 188, 188, 188, 189, 189, 189, 189, 190, 190, 190, 190, 191, 191, 191, 191, - 192, 192, 192, 192, 193, 193, 193, 193, 194, 194, 194, 194, 195, 195, 195, 195, - 196, 196, 196, 196, 197, 197, 197, 197, 198, 198, 198, 198, 199, 199, 199, 199, - 200, 200, 200, 200, 201, 201, 201, 201, 202, 202, 202, 202, 203, 203, 203, 203, - 204, 204, 204, 204, 205, 205, 205, 205, 206, 206, 206, 206, 207, 207, 207, 207, - 208, 208, 208, 208, 209, 209, 209, 209, 210, 210, 210, 210, 211, 211, 211, 211, - 212, 212, 212, 212, 213, 213, 213, 213, 214, 214, 214, 214, 215, 215, 215, 215, - 216, 216, 216, 216, 217, 217, 217, 217, 218, 218, 218, 218, 219, 219, 219, 219, - 220, 220, 220, 220, -}; - -static RE_UINT8 re_block_stage_5[] = { - 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, - 5, 5, 5, 5, 6, 6, 6, 6, 7, 7, 7, 7, 8, 8, 8, 8, - 9, 9, 9, 9, 10, 10, 10, 10, 11, 11, 11, 11, 12, 12, 12, 12, - 13, 13, 13, 13, 14, 14, 14, 14, 15, 15, 15, 15, 16, 16, 16, 16, - 17, 17, 17, 17, 18, 18, 18, 18, 19, 19, 19, 19, 0, 0, 0, 0, - 20, 20, 20, 20, 21, 21, 21, 21, 22, 22, 22, 22, 23, 23, 23, 23, - 24, 24, 24, 24, 25, 25, 25, 25, 26, 26, 26, 26, 27, 27, 27, 27, - 28, 28, 28, 28, 29, 29, 29, 29, 30, 30, 30, 30, 31, 31, 31, 31, - 32, 32, 32, 32, 33, 33, 33, 33, 34, 34, 34, 34, 35, 35, 35, 35, - 36, 36, 36, 36, 37, 37, 37, 37, 38, 38, 38, 38, 39, 39, 39, 39, - 40, 40, 40, 40, 41, 41, 41, 41, 42, 42, 42, 42, 43, 43, 43, 43, - 44, 44, 44, 44, 45, 45, 45, 45, 46, 46, 46, 46, 47, 47, 47, 47, - 48, 48, 48, 48, 49, 49, 49, 49, 50, 50, 50, 50, 51, 51, 51, 51, - 52, 52, 52, 52, 53, 53, 53, 53, 54, 54, 54, 54, 55, 55, 55, 55, - 56, 56, 56, 56, 57, 57, 57, 57, 58, 58, 58, 58, 59, 59, 59, 59, - 60, 60, 60, 60, 61, 61, 61, 61, 62, 62, 62, 62, 63, 63, 63, 63, - 64, 64, 64, 64, 65, 65, 65, 65, 66, 66, 66, 66, 67, 67, 67, 67, - 68, 68, 68, 68, 69, 69, 69, 69, 70, 70, 70, 70, 71, 71, 71, 71, - 72, 72, 72, 72, 73, 73, 73, 73, 74, 74, 74, 74, 75, 75, 75, 75, - 76, 76, 76, 76, 77, 77, 77, 77, 78, 78, 78, 78, 79, 79, 79, 79, - 80, 80, 80, 80, 81, 81, 81, 81, 82, 82, 82, 82, 83, 83, 83, 83, - 84, 84, 84, 84, 85, 85, 85, 85, 86, 86, 86, 86, 87, 87, 87, 87, - 88, 88, 88, 88, 89, 89, 89, 89, 90, 90, 90, 90, 91, 91, 91, 91, - 92, 92, 92, 92, 93, 93, 93, 93, 94, 94, 94, 94, 95, 95, 95, 95, - 96, 96, 96, 96, 97, 97, 97, 97, 98, 98, 98, 98, 99, 99, 99, 99, - 100, 100, 100, 100, 101, 101, 101, 101, 102, 102, 102, 102, 103, 103, 103, 103, - 104, 104, 104, 104, 105, 105, 105, 105, 106, 106, 106, 106, 107, 107, 107, 107, - 108, 108, 108, 108, 109, 109, 109, 109, 110, 110, 110, 110, 111, 111, 111, 111, - 112, 112, 112, 112, 113, 113, 113, 113, 114, 114, 114, 114, 115, 115, 115, 115, - 116, 116, 116, 116, 117, 117, 117, 117, 118, 118, 118, 118, 119, 119, 119, 119, - 120, 120, 120, 120, 121, 121, 121, 121, 122, 122, 122, 122, 123, 123, 123, 123, - 124, 124, 124, 124, 125, 125, 125, 125, 126, 126, 126, 126, 127, 127, 127, 127, - 128, 128, 128, 128, 129, 129, 129, 129, 130, 130, 130, 130, 131, 131, 131, 131, - 132, 132, 132, 132, 133, 133, 133, 133, 134, 134, 134, 134, 135, 135, 135, 135, - 136, 136, 136, 136, 137, 137, 137, 137, 138, 138, 138, 138, 139, 139, 139, 139, - 140, 140, 140, 140, 141, 141, 141, 141, 142, 142, 142, 142, 143, 143, 143, 143, - 144, 144, 144, 144, 145, 145, 145, 145, 146, 146, 146, 146, 147, 147, 147, 147, - 148, 148, 148, 148, 149, 149, 149, 149, 150, 150, 150, 150, 151, 151, 151, 151, - 152, 152, 152, 152, 153, 153, 153, 153, 154, 154, 154, 154, 155, 155, 155, 155, - 156, 156, 156, 156, 157, 157, 157, 157, 158, 158, 158, 158, 159, 159, 159, 159, - 160, 160, 160, 160, 161, 161, 161, 161, 162, 162, 162, 162, 163, 163, 163, 163, - 164, 164, 164, 164, 165, 165, 165, 165, 166, 166, 166, 166, 167, 167, 167, 167, - 168, 168, 168, 168, 169, 169, 169, 169, 170, 170, 170, 170, 171, 171, 171, 171, - 172, 172, 172, 172, 173, 173, 173, 173, 174, 174, 174, 174, 175, 175, 175, 175, - 176, 176, 176, 176, 177, 177, 177, 177, 178, 178, 178, 178, 179, 179, 179, 179, - 180, 180, 180, 180, 181, 181, 181, 181, 182, 182, 182, 182, 183, 183, 183, 183, - 184, 184, 184, 184, 185, 185, 185, 185, 186, 186, 186, 186, 187, 187, 187, 187, - 188, 188, 188, 188, 189, 189, 189, 189, 190, 190, 190, 190, 191, 191, 191, 191, - 192, 192, 192, 192, 193, 193, 193, 193, 194, 194, 194, 194, 195, 195, 195, 195, - 196, 196, 196, 196, 197, 197, 197, 197, 198, 198, 198, 198, 199, 199, 199, 199, - 200, 200, 200, 200, 201, 201, 201, 201, 202, 202, 202, 202, 203, 203, 203, 203, - 204, 204, 204, 204, 205, 205, 205, 205, 206, 206, 206, 206, 207, 207, 207, 207, - 208, 208, 208, 208, 209, 209, 209, 209, 210, 210, 210, 210, 211, 211, 211, 211, - 212, 212, 212, 212, 213, 213, 213, 213, 214, 214, 214, 214, 215, 215, 215, 215, - 216, 216, 216, 216, 217, 217, 217, 217, 218, 218, 218, 218, 219, 219, 219, 219, - 220, 220, 220, 220, -}; - -/* Block: 4288 bytes. */ - -RE_UINT32 re_get_block(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 11; - code = ch ^ (f << 11); - pos = (RE_UINT32)re_block_stage_1[f] << 4; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_block_stage_2[pos + f] << 3; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_block_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_block_stage_4[pos + f] << 2; - value = re_block_stage_5[pos + code]; - - return value; -} - -/* Script. */ - -static RE_UINT8 re_script_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 12, 12, 12, 12, 13, 14, 14, 14, 14, 15, - 16, 17, 18, 14, 19, 14, 20, 14, 14, 14, 14, 14, 14, 21, 14, 14, - 14, 14, 14, 14, 14, 14, 22, 14, 14, 14, 23, 14, 14, 24, 25, 14, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 26, 7, 27, 28, 14, 14, 14, 14, 14, 14, 14, 29, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 30, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, -}; - -static RE_UINT8 re_script_stage_2[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, - 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, - 30, 31, 32, 32, 33, 34, 35, 36, 37, 37, 37, 37, 37, 38, 39, 40, - 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 2, 2, 53, 54, - 55, 56, 57, 58, 59, 59, 59, 60, 61, 59, 59, 59, 59, 59, 62, 59, - 63, 63, 59, 59, 59, 59, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, - 74, 75, 76, 77, 78, 79, 80, 59, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 81, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 82, - 83, 83, 83, 83, 83, 83, 83, 83, 83, 84, 85, 85, 86, 87, 88, 89, - 90, 91, 92, 93, 94, 95, 96, 97, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 98, - 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, - 65, 65, 72, 72, 99, 100, 101, 102, 103, 103, 104, 105, 106, 107, 108, 109, - 110, 111, 112, 113, 65, 114, 115, 116, 117, 118, 65, 65, 65, 65, 65, 65, - 119, 65, 120, 121, 122, 65, 123, 65, 124, 65, 65, 65, 125, 65, 65, 65, - 126, 127, 128, 129, 65, 65, 65, 65, 65, 65, 65, 65, 65, 130, 65, 65, - 131, 131, 131, 131, 131, 131, 132, 65, 133, 65, 65, 65, 65, 65, 65, 65, - 134, 134, 134, 134, 134, 134, 134, 134, 135, 65, 65, 65, 65, 65, 65, 65, - 136, 136, 136, 136, 137, 65, 65, 65, 65, 65, 65, 65, 65, 65, 138, 139, - 140, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, - 59, 141, 142, 143, 144, 65, 145, 65, 146, 147, 148, 59, 59, 149, 59, 150, - 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 151, 152, 65, 65, - 153, 154, 155, 156, 157, 65, 158, 159, 160, 161, 162, 163, 164, 165, 60, 65, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 166, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 167, 72, - 168, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, - 72, 72, 72, 72, 168, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, - 169, 65, 170, 171, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, -}; - -static RE_UINT16 re_script_stage_3[] = { - 0, 0, 0, 0, 1, 2, 1, 2, 0, 0, 3, 3, 4, 5, 4, 5, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 0, 0, 7, 0, - 8, 8, 8, 8, 8, 8, 8, 9, 10, 11, 12, 11, 11, 11, 13, 11, - 14, 14, 14, 14, 14, 14, 14, 14, 15, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 16, 17, 18, 19, 17, 18, 20, 21, 22, 22, 23, 22, 24, 25, - 26, 27, 28, 28, 29, 30, 31, 32, 28, 28, 28, 28, 28, 33, 28, 28, - 34, 35, 35, 35, 36, 28, 28, 28, 37, 37, 37, 38, 39, 39, 39, 40, - 41, 41, 42, 43, 44, 45, 46, 46, 46, 46, 47, 46, 46, 46, 48, 49, - 50, 50, 50, 50, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, - 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, - 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, - 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, - 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 46, 124, - 125, 126, 126, 127, 126, 128, 46, 46, 129, 130, 131, 132, 133, 134, 46, 46, - 135, 135, 135, 135, 136, 135, 137, 138, 135, 136, 135, 139, 139, 140, 46, 46, - 141, 141, 141, 141, 141, 141, 141, 141, 141, 141, 142, 142, 143, 142, 142, 144, - 145, 145, 145, 145, 145, 145, 145, 145, 146, 146, 146, 146, 147, 148, 146, 146, - 147, 146, 146, 149, 150, 151, 146, 146, 146, 150, 146, 146, 146, 152, 146, 153, - 146, 154, 155, 155, 155, 155, 155, 156, 157, 157, 157, 157, 157, 157, 157, 157, - 158, 159, 160, 160, 160, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, - 171, 171, 171, 171, 171, 172, 173, 173, 174, 175, 176, 176, 176, 176, 176, 177, - 176, 176, 178, 157, 157, 157, 157, 179, 180, 181, 182, 182, 183, 184, 185, 186, - 187, 187, 188, 187, 189, 190, 171, 171, 191, 192, 193, 193, 193, 194, 193, 195, - 196, 196, 197, 46, 46, 46, 46, 46, 198, 198, 198, 198, 199, 198, 198, 200, - 201, 201, 201, 201, 202, 202, 202, 203, 204, 204, 204, 205, 206, 207, 207, 207, - 46, 46, 46, 46, 208, 209, 210, 211, 4, 4, 212, 4, 4, 213, 214, 215, - 4, 4, 4, 216, 8, 8, 217, 218, 11, 219, 11, 11, 219, 220, 11, 221, - 11, 11, 11, 222, 222, 223, 11, 224, 225, 0, 0, 0, 0, 0, 226, 227, - 228, 229, 0, 230, 46, 8, 8, 231, 0, 0, 232, 233, 234, 0, 4, 4, - 235, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 236, 0, 0, 237, 46, 230, 46, 0, 0, - 238, 0, 0, 0, 0, 0, 0, 0, 239, 239, 239, 239, 239, 239, 239, 239, - 0, 0, 0, 0, 240, 241, 46, 46, 46, 46, 46, 46, 46, 46, 46, 46, - 242, 242, 243, 242, 242, 243, 4, 4, 244, 244, 244, 244, 244, 244, 244, 245, - 142, 142, 143, 246, 246, 246, 247, 248, 146, 249, 250, 250, 250, 250, 14, 14, - 0, 0, 0, 251, 46, 46, 46, 46, 252, 253, 252, 252, 252, 252, 252, 254, - 252, 252, 252, 252, 252, 252, 252, 252, 252, 252, 252, 252, 252, 255, 46, 251, - 256, 0, 257, 258, 259, 260, 260, 260, 260, 261, 262, 263, 263, 263, 263, 264, - 265, 266, 267, 268, 145, 145, 145, 145, 269, 0, 266, 270, 0, 0, 236, 263, - 145, 269, 0, 0, 0, 0, 145, 271, 0, 0, 0, 0, 0, 263, 263, 272, - 263, 263, 263, 263, 263, 273, 0, 0, 252, 252, 252, 255, 0, 0, 0, 0, - 252, 252, 252, 252, 274, 46, 46, 46, 275, 275, 275, 275, 275, 275, 275, 275, - 276, 275, 275, 275, 277, 278, 278, 278, 279, 279, 279, 279, 279, 279, 279, 279, - 279, 279, 280, 46, 14, 14, 14, 14, 14, 281, 282, 282, 282, 282, 282, 283, - 0, 0, 284, 4, 4, 4, 4, 4, 285, 286, 287, 46, 46, 46, 46, 288, - 289, 289, 290, 241, 291, 291, 291, 292, 293, 293, 293, 293, 294, 295, 50, 296, - 297, 297, 297, 298, 298, 299, 145, 300, 301, 301, 301, 301, 302, 303, 46, 46, - 304, 304, 304, 305, 306, 307, 141, 308, 309, 309, 309, 309, 310, 311, 312, 313, - 314, 315, 250, 46, 46, 46, 46, 46, 46, 46, 46, 46, 312, 312, 316, 317, - 145, 145, 318, 145, 319, 145, 145, 320, 252, 252, 252, 252, 252, 252, 321, 252, - 252, 252, 252, 252, 252, 322, 46, 46, 323, 324, 22, 325, 326, 28, 28, 28, - 28, 28, 28, 28, 327, 328, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, - 28, 28, 28, 329, 46, 28, 28, 28, 28, 330, 28, 28, 331, 46, 46, 332, - 8, 241, 217, 0, 0, 333, 334, 335, 28, 28, 28, 28, 28, 28, 28, 336, - 238, 0, 1, 2, 1, 2, 337, 262, 263, 338, 145, 269, 339, 340, 341, 342, - 343, 344, 345, 346, 347, 347, 46, 46, 344, 344, 344, 344, 344, 344, 344, 348, - 349, 0, 0, 350, 11, 11, 11, 11, 351, 251, 46, 46, 46, 0, 0, 352, - 353, 354, 355, 355, 355, 356, 46, 46, 357, 358, 359, 360, 361, 46, 46, 46, - 362, 363, 364, 364, 365, 366, 46, 46, 367, 367, 367, 367, 367, 368, 368, 368, - 369, 370, 371, 46, 46, 46, 46, 46, 372, 373, 373, 374, 375, 376, 46, 46, - 377, 378, 379, 380, 46, 46, 46, 46, 381, 381, 382, 383, 46, 46, 46, 46, - 384, 385, 386, 387, 388, 389, 390, 390, 391, 391, 391, 392, 393, 394, 395, 396, - 397, 397, 397, 397, 398, 46, 46, 46, 46, 46, 46, 46, 46, 46, 28, 49, - 399, 399, 399, 399, 400, 401, 399, 46, 402, 402, 402, 402, 403, 404, 405, 406, - 407, 407, 407, 408, 409, 46, 46, 46, 410, 410, 410, 410, 411, 412, 46, 46, - 413, 413, 413, 414, 415, 46, 46, 46, 416, 416, 416, 416, 416, 416, 416, 416, - 416, 416, 416, 416, 416, 416, 417, 46, 416, 416, 416, 416, 416, 416, 418, 419, - 420, 420, 420, 420, 420, 420, 420, 420, 420, 420, 421, 46, 46, 46, 46, 46, - 282, 282, 282, 282, 282, 282, 282, 282, 282, 282, 282, 422, 46, 46, 46, 46, - 423, 423, 423, 423, 424, 423, 423, 425, 426, 423, 46, 46, 46, 46, 46, 46, - 427, 46, 46, 46, 46, 46, 46, 46, 0, 0, 0, 0, 0, 0, 0, 428, - 0, 0, 429, 0, 0, 0, 430, 431, 432, 0, 433, 0, 0, 434, 46, 46, - 11, 11, 11, 11, 435, 46, 46, 46, 0, 0, 0, 0, 0, 237, 0, 436, - 0, 0, 0, 0, 0, 226, 0, 0, 0, 437, 438, 439, 440, 0, 0, 0, - 441, 442, 0, 443, 444, 445, 0, 0, 0, 0, 446, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 447, 0, 0, 0, 448, 28, 449, 450, 451, 452, 453, 454, - 455, 456, 457, 456, 46, 46, 46, 327, 0, 0, 251, 0, 0, 0, 0, 0, - 0, 236, 228, 458, 238, 238, 46, 46, 230, 0, 228, 0, 0, 0, 251, 0, - 0, 230, 46, 46, 46, 46, 459, 0, 460, 0, 0, 230, 461, 436, 46, 46, - 0, 0, 462, 463, 0, 0, 0, 240, 0, 236, 0, 0, 464, 46, 0, 462, - 0, 0, 0, 228, 445, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 465, - 0, 0, 0, 434, 236, 0, 466, 46, 46, 46, 46, 46, 46, 46, 46, 467, - 0, 0, 0, 0, 468, 46, 46, 46, 0, 0, 0, 0, 428, 46, 46, 46, - 252, 252, 252, 252, 252, 469, 46, 46, 252, 252, 252, 470, 252, 252, 252, 252, - 252, 321, 46, 46, 46, 46, 46, 46, 471, 46, 0, 0, 0, 0, 0, 0, - 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 46, -}; - -static RE_UINT8 re_script_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 3, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, - 2, 2, 2, 2, 3, 0, 0, 0, 2, 2, 3, 0, 0, 4, 0, 0, - 5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 7, 6, 8, 6, 6, 9, - 8, 8, 10, 10, 6, 11, 11, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 12, 6, 6, 6, 6, 6, 6, 6, 13, 13, 13, 13, 13, 13, 13, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 15, 16, 14, 14, 14, 14, - 14, 14, 14, 14, 8, 8, 8, 8, 17, 18, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 19, 17, 18, 18, 18, - 18, 18, 18, 18, 20, 19, 8, 17, 21, 22, 22, 22, 22, 22, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 8, 8, 8, 8, - 22, 22, 22, 22, 22, 23, 8, 8, 22, 22, 23, 8, 8, 8, 8, 8, - 24, 24, 25, 24, 24, 24, 26, 24, 24, 24, 24, 24, 24, 27, 25, 27, - 24, 24, 24, 24, 24, 24, 24, 24, 26, 24, 24, 24, 24, 28, 5, 5, - 5, 5, 5, 24, 24, 24, 24, 24, 0, 0, 0, 0, 0, 24, 24, 24, - 29, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 27, 24, - 30, 30, 30, 30, 30, 30, 30, 31, 30, 30, 30, 30, 30, 30, 30, 30, - 30, 30, 30, 30, 30, 32, 31, 30, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 8, 8, 8, 8, 8, 8, 8, 34, 34, 34, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 35, 8, 8, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 36, 8, 36, 36, 36, 36, 36, 36, 36, 37, - 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 38, 8, 39, - 8, 8, 8, 8, 8, 8, 8, 8, 25, 24, 24, 24, 24, 24, 25, 8, - 8, 8, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 25, - 40, 40, 40, 40, 40, 40, 40, 40, 41, 42, 40, 40, 40, 40, 40, 40, - 40, 40, 0, 40, 40, 40, 40, 40, 40, 40, 40, 40, 43, 40, 40, 40, - 44, 45, 44, 45, 45, 45, 46, 44, 46, 44, 45, 45, 45, 45, 45, 45, - 45, 45, 45, 45, 46, 45, 45, 45, 46, 46, 8, 45, 45, 8, 45, 45, - 45, 45, 46, 44, 46, 44, 45, 46, 8, 8, 8, 44, 8, 8, 45, 44, - 45, 45, 8, 45, 45, 45, 45, 45, 45, 45, 45, 45, 45, 45, 8, 8, - 47, 48, 47, 48, 48, 49, 8, 47, 49, 47, 48, 48, 48, 48, 48, 48, - 48, 48, 48, 48, 49, 48, 48, 48, 49, 48, 47, 49, 48, 8, 49, 48, - 48, 49, 8, 47, 49, 47, 48, 8, 47, 8, 8, 8, 47, 48, 49, 49, - 8, 8, 8, 48, 48, 48, 48, 48, 48, 48, 48, 8, 8, 8, 8, 8, - 50, 51, 50, 51, 51, 51, 51, 50, 51, 50, 51, 51, 51, 51, 51, 51, - 51, 51, 51, 51, 52, 51, 51, 51, 52, 51, 50, 51, 51, 8, 51, 51, - 51, 51, 51, 50, 51, 50, 51, 8, 52, 8, 8, 8, 8, 8, 8, 8, - 51, 51, 8, 51, 51, 51, 51, 51, 51, 8, 8, 8, 8, 8, 8, 8, - 53, 54, 53, 54, 54, 54, 55, 53, 55, 53, 54, 54, 54, 54, 54, 54, - 54, 54, 54, 54, 55, 54, 54, 54, 55, 54, 53, 54, 54, 8, 54, 54, - 54, 54, 55, 53, 55, 53, 54, 8, 8, 8, 8, 54, 8, 8, 54, 53, - 54, 54, 8, 54, 54, 54, 54, 54, 54, 54, 54, 54, 8, 8, 8, 8, - 8, 56, 57, 56, 56, 58, 8, 56, 58, 56, 56, 8, 57, 58, 58, 56, - 8, 57, 58, 8, 56, 58, 8, 56, 56, 56, 56, 56, 56, 8, 8, 56, - 56, 58, 8, 56, 58, 56, 56, 8, 58, 8, 8, 57, 8, 8, 8, 8, - 8, 8, 8, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 58, 8, 8, - 59, 60, 59, 60, 60, 60, 61, 60, 61, 60, 60, 60, 60, 60, 60, 60, - 60, 60, 60, 60, 61, 60, 60, 60, 60, 60, 59, 60, 60, 8, 59, 60, - 60, 60, 61, 60, 61, 60, 60, 8, 8, 8, 59, 61, 60, 8, 8, 8, - 60, 60, 8, 60, 60, 60, 60, 60, 8, 8, 8, 8, 60, 60, 60, 60, - 8, 62, 63, 62, 62, 62, 64, 62, 64, 62, 62, 62, 62, 62, 62, 62, - 62, 62, 62, 62, 64, 62, 62, 62, 62, 62, 63, 62, 62, 8, 62, 62, - 62, 62, 64, 62, 64, 62, 62, 8, 8, 8, 63, 64, 8, 8, 8, 64, - 62, 62, 8, 62, 62, 62, 62, 62, 63, 64, 8, 8, 8, 8, 8, 8, - 8, 65, 66, 65, 65, 65, 67, 65, 67, 65, 65, 65, 65, 65, 65, 65, - 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 67, 66, 65, - 65, 65, 67, 65, 67, 65, 65, 67, 8, 8, 8, 66, 8, 8, 8, 8, - 65, 65, 8, 65, 65, 65, 65, 65, 65, 65, 65, 8, 66, 65, 65, 65, - 8, 68, 69, 68, 68, 68, 68, 68, 68, 68, 68, 70, 8, 68, 68, 68, - 68, 68, 68, 68, 68, 68, 68, 68, 68, 69, 68, 68, 68, 68, 69, 8, - 68, 68, 68, 70, 8, 70, 8, 69, 68, 68, 70, 70, 68, 68, 68, 68, - 8, 68, 70, 8, 8, 8, 8, 8, 71, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 73, 8, 20, - 72, 72, 72, 72, 72, 72, 8, 8, 74, 75, 75, 74, 75, 75, 74, 8, - 8, 8, 76, 76, 74, 76, 76, 76, 74, 76, 74, 74, 8, 76, 74, 76, - 76, 76, 76, 76, 76, 74, 76, 8, 76, 76, 75, 75, 76, 76, 76, 8, - 76, 76, 76, 76, 76, 8, 76, 76, 77, 77, 77, 77, 77, 77, 77, 77, - 77, 77, 77, 77, 78, 77, 77, 77, 77, 77, 77, 77, 77, 77, 79, 8, - 78, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 77, 79, 77, - 77, 77, 80, 0, 81, 79, 8, 8, 82, 82, 82, 82, 82, 82, 82, 82, - 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 83, 84, 8, 8, 84, 8, - 83, 83, 83, 83, 83, 85, 83, 83, 86, 86, 86, 86, 86, 86, 86, 86, - 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 87, 88, 87, 87, 8, - 87, 87, 87, 88, 88, 87, 87, 8, 88, 87, 87, 8, 87, 87, 87, 88, - 88, 87, 87, 8, 87, 87, 87, 87, 87, 87, 87, 88, 87, 87, 87, 87, - 87, 87, 87, 87, 87, 88, 89, 87, 87, 87, 87, 87, 87, 87, 88, 8, - 87, 87, 87, 87, 87, 8, 8, 8, 90, 90, 90, 90, 90, 90, 90, 90, - 90, 90, 91, 8, 8, 8, 8, 8, 92, 92, 92, 92, 92, 92, 92, 92, - 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 93, 94, 8, - 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, 95, 96, 0, 95, - 97, 8, 8, 8, 8, 8, 8, 8, 98, 98, 98, 98, 98, 98, 99, 98, - 98, 98, 99, 8, 8, 8, 8, 8, 100, 100, 100, 100, 100, 100, 100, 100, - 100, 100, 101, 9, 8, 8, 8, 8, 102, 102, 102, 102, 102, 102, 102, 102, - 102, 102, 8, 8, 8, 8, 8, 8, 103, 103, 103, 103, 103, 103, 104, 103, - 104, 103, 8, 8, 8, 8, 8, 8, 105, 105, 105, 105, 105, 105, 105, 105, - 105, 105, 105, 105, 105, 105, 105, 8, 105, 105, 105, 105, 105, 8, 8, 8, - 106, 0, 107, 106, 106, 106, 106, 108, 106, 106, 106, 106, 106, 8, 8, 8, - 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 106, 8, 8, 8, 8, - 106, 106, 106, 106, 106, 108, 8, 8, 92, 92, 92, 8, 8, 8, 8, 8, - 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 110, 8, - 109, 109, 109, 109, 109, 109, 8, 8, 110, 8, 109, 109, 109, 109, 109, 109, - 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 111, 8, - 111, 111, 112, 8, 8, 8, 8, 8, 113, 113, 113, 113, 113, 113, 113, 113, - 113, 113, 113, 113, 113, 113, 8, 8, 113, 113, 113, 113, 113, 8, 8, 8, - 113, 113, 113, 113, 113, 114, 8, 113, 115, 115, 115, 115, 115, 115, 115, 115, - 115, 115, 115, 115, 115, 115, 8, 115, 116, 116, 116, 116, 116, 116, 116, 116, - 116, 116, 116, 116, 116, 116, 116, 117, 116, 116, 116, 116, 116, 116, 117, 118, - 116, 116, 116, 116, 116, 8, 8, 8, 116, 116, 116, 116, 116, 116, 116, 8, - 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 119, 8, 8, - 119, 119, 119, 119, 119, 119, 120, 8, 121, 121, 121, 121, 121, 121, 121, 121, - 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 8, 8, 8, 8, 122, 122, - 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 123, 8, 124, 123, 123, - 123, 123, 123, 123, 123, 8, 124, 123, 125, 125, 125, 125, 125, 125, 125, 125, - 121, 121, 121, 121, 8, 8, 8, 8, 5, 126, 5, 5, 5, 5, 5, 5, - 126, 5, 5, 5, 126, 0, 127, 0, 0, 0, 126, 9, 8, 8, 8, 8, - 2, 2, 2, 6, 6, 128, 2, 2, 2, 2, 2, 2, 2, 2, 129, 6, - 6, 2, 2, 6, 6, 130, 2, 2, 2, 2, 2, 2, 131, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 129, 5, 5, 5, 132, 8, 8, 8, 8, - 8, 8, 8, 8, 8, 8, 5, 5, 6, 6, 6, 8, 6, 6, 6, 8, - 6, 6, 6, 6, 12, 12, 12, 12, 6, 6, 6, 6, 6, 6, 6, 8, - 6, 6, 11, 6, 6, 6, 6, 6, 6, 6, 8, 6, 6, 6, 12, 6, - 8, 6, 11, 6, 6, 6, 6, 11, 0, 0, 0, 0, 0, 0, 5, 0, - 0, 0, 9, 0, 0, 0, 0, 0, 1, 8, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, 0, 9, 2, 2, 2, 2, 2, 2, 133, 8, - 0, 0, 0, 0, 0, 9, 8, 8, 132, 8, 8, 8, 8, 8, 8, 8, - 0, 0, 0, 10, 0, 2, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 3, 2, 2, 2, 2, 3, 8, 8, 8, - 0, 0, 8, 8, 8, 8, 8, 8, 0, 0, 0, 9, 8, 8, 8, 8, - 20, 0, 0, 0, 0, 0, 0, 0, 134, 134, 134, 134, 134, 134, 134, 134, - 0, 0, 0, 0, 0, 0, 9, 8, 0, 0, 0, 0, 0, 8, 8, 8, - 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, 136, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 8, 8, 137, 13, 13, 13, - 138, 138, 138, 138, 138, 138, 138, 138, 138, 138, 138, 138, 8, 8, 8, 139, - 140, 8, 8, 8, 8, 8, 8, 139, 87, 87, 87, 88, 8, 8, 8, 8, - 87, 87, 87, 88, 87, 87, 87, 88, 0, 0, 0, 0, 0, 0, 8, 8, - 141, 141, 141, 141, 141, 141, 141, 141, 141, 141, 141, 141, 141, 142, 141, 141, - 141, 141, 8, 8, 8, 8, 8, 8, 141, 141, 141, 8, 8, 8, 8, 8, - 0, 0, 143, 143, 0, 0, 0, 0, 143, 141, 141, 141, 141, 5, 5, 86, - 0, 0, 0, 0, 141, 141, 0, 0, 144, 145, 145, 145, 145, 145, 145, 145, - 145, 145, 145, 145, 145, 145, 145, 145, 145, 145, 145, 146, 147, 126, 148, 145, - 149, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, 150, - 150, 150, 150, 150, 150, 151, 149, 150, 8, 8, 152, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 8, - 153, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 86, 154, - 4, 4, 4, 4, 4, 155, 8, 8, 86, 86, 86, 86, 86, 86, 86, 156, - 150, 150, 150, 150, 150, 150, 150, 157, 150, 150, 150, 150, 0, 0, 0, 0, - 141, 141, 141, 141, 141, 141, 158, 8, 159, 159, 159, 159, 159, 159, 159, 159, - 159, 159, 159, 159, 159, 159, 160, 8, 159, 159, 159, 160, 8, 8, 8, 8, - 161, 161, 161, 161, 161, 161, 161, 161, 162, 162, 162, 162, 162, 162, 162, 162, - 162, 162, 162, 162, 162, 162, 8, 8, 14, 14, 14, 14, 8, 8, 8, 163, - 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 8, 8, 8, 8, - 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 1, 2, 133, - 2, 2, 8, 8, 8, 8, 8, 8, 2, 2, 2, 2, 2, 133, 8, 8, - 8, 8, 8, 8, 2, 2, 2, 2, 165, 165, 165, 165, 165, 165, 165, 165, - 165, 165, 165, 165, 165, 165, 8, 8, 166, 166, 166, 166, 166, 166, 166, 166, - 166, 166, 166, 166, 8, 8, 8, 8, 167, 167, 167, 167, 167, 167, 167, 167, - 167, 167, 168, 8, 8, 8, 8, 167, 167, 167, 167, 167, 167, 8, 8, 8, - 40, 40, 40, 40, 40, 40, 8, 8, 169, 169, 169, 169, 169, 169, 169, 169, - 170, 170, 170, 170, 170, 170, 170, 170, 170, 170, 8, 8, 8, 8, 8, 171, - 86, 86, 86, 86, 86, 86, 154, 8, 172, 172, 172, 172, 172, 172, 172, 172, - 172, 172, 172, 172, 172, 172, 172, 20, 172, 172, 172, 172, 172, 8, 8, 172, - 173, 173, 173, 173, 173, 173, 173, 173, 173, 173, 173, 174, 8, 8, 8, 8, - 173, 173, 173, 173, 173, 173, 173, 8, 173, 173, 173, 173, 173, 8, 173, 173, - 82, 82, 82, 82, 82, 82, 8, 8, 175, 175, 175, 175, 175, 175, 175, 175, - 175, 176, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 177, 175, 175, - 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 178, 179, 8, 8, 8, 8, - 89, 87, 87, 88, 89, 87, 87, 88, 89, 87, 87, 88, 8, 8, 8, 8, - 178, 178, 178, 178, 178, 178, 178, 8, 178, 178, 178, 178, 178, 8, 8, 8, - 86, 86, 8, 8, 8, 8, 8, 8, 86, 86, 86, 154, 8, 153, 86, 86, - 86, 86, 86, 86, 86, 86, 8, 8, 141, 141, 141, 141, 141, 141, 141, 8, - 141, 141, 141, 141, 141, 8, 8, 8, 2, 2, 2, 133, 8, 8, 8, 8, - 8, 17, 18, 18, 8, 8, 21, 22, 22, 22, 22, 23, 22, 22, 23, 23, - 22, 21, 23, 22, 22, 22, 22, 22, 24, 8, 8, 8, 8, 8, 8, 8, - 8, 180, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 0, - 8, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 8, 8, 8, 8, - 24, 24, 24, 24, 24, 24, 27, 8, 0, 9, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 9, 0, 0, 8, 8, 24, 24, 25, 24, 24, 24, 24, 24, - 24, 24, 24, 24, 24, 24, 25, 20, 0, 0, 0, 150, 150, 150, 150, 150, - 150, 150, 150, 150, 150, 150, 150, 0, 8, 86, 86, 86, 8, 86, 86, 86, - 8, 86, 86, 86, 8, 86, 154, 8, 0, 0, 0, 9, 0, 0, 0, 9, - 8, 8, 8, 8, 20, 0, 0, 8, 181, 181, 181, 181, 181, 181, 182, 181, - 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 181, 183, 181, 181, 181, 181, - 181, 181, 181, 181, 181, 183, 181, 182, 181, 181, 181, 181, 181, 181, 181, 8, - 181, 181, 181, 181, 181, 183, 8, 8, 0, 9, 8, 20, 0, 0, 0, 0, - 0, 0, 8, 20, 0, 0, 0, 0, 6, 6, 6, 6, 6, 11, 8, 8, - 0, 0, 0, 0, 0, 0, 127, 8, 184, 184, 184, 184, 184, 184, 184, 184, - 184, 184, 184, 184, 184, 184, 185, 8, 186, 186, 186, 186, 186, 186, 186, 186, - 187, 8, 8, 8, 8, 8, 8, 8, 188, 188, 188, 188, 188, 188, 188, 188, - 188, 188, 188, 188, 188, 188, 188, 189, 188, 188, 8, 8, 8, 8, 8, 8, - 190, 190, 190, 190, 190, 190, 190, 190, 190, 190, 190, 190, 190, 191, 8, 8, - 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 193, - 194, 194, 194, 194, 194, 194, 194, 194, 194, 194, 8, 8, 194, 194, 194, 194, - 194, 194, 194, 8, 8, 8, 8, 8, 195, 195, 195, 195, 195, 195, 195, 195, - 196, 196, 196, 196, 196, 196, 196, 196, 197, 197, 197, 197, 197, 197, 197, 197, - 197, 197, 197, 197, 197, 197, 197, 8, 197, 197, 197, 197, 197, 8, 8, 8, - 198, 198, 198, 8, 199, 198, 198, 198, 198, 198, 198, 198, 198, 198, 198, 198, - 198, 198, 198, 200, 199, 8, 199, 200, 201, 201, 201, 201, 201, 201, 201, 201, - 201, 201, 201, 202, 201, 201, 201, 201, 203, 203, 203, 203, 203, 203, 203, 203, - 203, 203, 203, 203, 203, 203, 8, 204, 205, 205, 205, 205, 205, 205, 205, 205, - 205, 205, 205, 205, 205, 8, 8, 206, 207, 207, 207, 207, 207, 207, 207, 207, - 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 8, 8, 8, 208, - 209, 209, 210, 211, 8, 8, 209, 209, 209, 209, 210, 209, 210, 209, 209, 209, - 209, 209, 209, 209, 209, 209, 209, 209, 209, 209, 8, 8, 209, 211, 8, 210, - 209, 209, 209, 209, 8, 8, 8, 8, 209, 209, 209, 209, 211, 8, 8, 8, - 212, 212, 212, 212, 212, 212, 212, 212, 213, 213, 213, 213, 213, 213, 213, 213, - 213, 213, 213, 8, 214, 213, 213, 213, 215, 215, 215, 215, 215, 215, 215, 215, - 215, 215, 215, 8, 215, 215, 215, 215, 216, 216, 216, 216, 216, 216, 216, 216, - 216, 217, 8, 8, 216, 216, 216, 216, 218, 218, 218, 218, 218, 218, 218, 218, - 218, 218, 218, 218, 219, 8, 8, 8, 220, 220, 220, 220, 220, 220, 220, 220, - 220, 220, 220, 220, 220, 220, 220, 8, 8, 220, 220, 220, 220, 220, 220, 220, - 221, 221, 221, 221, 221, 221, 221, 221, 221, 8, 8, 8, 8, 8, 8, 8, - 222, 222, 222, 222, 222, 222, 222, 222, 222, 222, 222, 222, 223, 8, 8, 8, - 222, 222, 222, 222, 222, 8, 8, 8, 224, 224, 224, 224, 224, 224, 224, 224, - 224, 224, 225, 224, 224, 224, 224, 224, 224, 224, 8, 8, 8, 8, 8, 8, - 226, 226, 226, 226, 226, 226, 226, 226, 226, 226, 226, 226, 227, 8, 8, 8, - 226, 226, 226, 226, 226, 8, 8, 8, 228, 228, 228, 228, 228, 228, 228, 228, - 228, 228, 228, 228, 8, 8, 8, 8, 228, 228, 228, 228, 228, 8, 8, 8, - 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 229, 230, - 229, 230, 8, 8, 8, 8, 8, 8, 229, 229, 8, 8, 8, 8, 8, 8, - 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 231, 232, - 164, 164, 164, 164, 233, 8, 8, 8, 234, 234, 234, 234, 234, 234, 234, 234, - 234, 234, 235, 8, 8, 8, 8, 8, 234, 234, 234, 234, 234, 234, 234, 235, - 8, 8, 8, 8, 8, 8, 8, 236, 237, 8, 8, 8, 8, 8, 8, 8, - 0, 0, 0, 8, 8, 8, 8, 8, 0, 0, 0, 9, 20, 0, 0, 0, - 0, 0, 0, 127, 5, 0, 0, 0, 0, 0, 0, 0, 0, 127, 5, 5, - 5, 126, 127, 5, 5, 5, 0, 0, 0, 0, 0, 0, 0, 5, 5, 0, - 0, 0, 0, 0, 0, 0, 0, 8, 6, 6, 6, 8, 8, 8, 8, 8, - 0, 8, 8, 8, 8, 8, 8, 8, 0, 0, 0, 0, 0, 0, 9, 0, - 8, 9, 20, 9, 20, 0, 9, 0, 0, 0, 0, 0, 0, 20, 20, 0, - 0, 0, 20, 0, 0, 0, 0, 0, 0, 0, 0, 20, 0, 9, 20, 0, - 0, 0, 9, 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 20, 0, 9, - 0, 0, 9, 9, 8, 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 0, - 24, 24, 180, 24, 24, 24, 24, 24, 180, 25, 25, 180, 180, 24, 24, 24, - 24, 25, 24, 24, 180, 180, 8, 8, 8, 25, 8, 180, 180, 180, 180, 24, - 180, 25, 25, 180, 180, 180, 180, 180, 180, 25, 25, 180, 24, 25, 24, 24, - 24, 25, 24, 24, 180, 24, 25, 25, 24, 24, 24, 24, 24, 180, 24, 24, - 24, 24, 24, 24, 24, 24, 8, 8, 180, 24, 180, 24, 24, 180, 24, 24, - 20, 0, 0, 0, 0, 0, 0, 9, 8, 8, 8, 0, 0, 0, 0, 0, - 238, 9, 8, 8, 8, 8, 8, 8, 0, 0, 0, 0, 9, 8, 8, 8, - 9, 8, 8, 8, 8, 8, 8, 8, 0, 0, 0, 20, 0, 0, 0, 0, - 0, 0, 9, 0, 0, 9, 8, 8, 0, 0, 0, 0, 20, 0, 9, 8, - 0, 0, 0, 0, 8, 8, 8, 8, 8, 8, 8, 8, 8, 20, 0, 0, - 9, 8, 20, 0, 0, 0, 0, 0, 141, 141, 141, 158, 8, 8, 8, 8, - 141, 141, 158, 8, 8, 8, 8, 8, 20, 8, 8, 8, 8, 8, 8, 8, -}; - -static RE_UINT8 re_script_stage_5[] = { - 1, 1, 1, 2, 2, 2, 2, 1, 35, 35, 41, 41, 3, 3, 1, 3, - 0, 0, 1, 0, 3, 1, 3, 0, 0, 3, 55, 55, 4, 4, 4, 41, - 41, 4, 0, 5, 5, 5, 5, 0, 0, 1, 0, 6, 6, 6, 6, 0, - 7, 7, 7, 0, 1, 7, 7, 1, 7, 41, 41, 7, 8, 8, 0, 8, - 8, 0, 9, 9, 66, 66, 66, 0, 82, 82, 82, 0, 95, 95, 95, 0, - 10, 10, 10, 41, 41, 10, 0, 10, 0, 11, 11, 11, 11, 0, 0, 12, - 12, 12, 12, 0, 0, 13, 13, 13, 13, 0, 0, 14, 14, 14, 14, 0, - 15, 15, 0, 15, 15, 0, 0, 16, 16, 16, 16, 0, 17, 17, 0, 17, - 17, 0, 18, 18, 0, 18, 18, 0, 19, 19, 0, 19, 19, 0, 0, 20, - 20, 20, 20, 0, 0, 21, 21, 0, 21, 21, 22, 22, 0, 22, 22, 0, - 22, 1, 1, 22, 23, 23, 24, 24, 0, 24, 24, 1, 25, 25, 26, 26, - 26, 0, 0, 26, 27, 27, 27, 0, 28, 28, 29, 29, 29, 0, 30, 30, - 30, 1, 30, 0, 42, 42, 42, 0, 43, 43, 43, 1, 44, 44, 45, 45, - 45, 0, 31, 31, 32, 32, 32, 1, 32, 0, 46, 46, 46, 0, 47, 47, - 47, 0, 56, 56, 56, 0, 54, 54, 78, 78, 78, 0, 0, 78, 62, 62, - 62, 0, 67, 67, 93, 93, 68, 68, 0, 68, 69, 69, 41, 1, 1, 41, - 3, 4, 2, 3, 3, 2, 4, 2, 41, 0, 2, 0, 53, 53, 57, 57, - 57, 0, 0, 55, 58, 58, 0, 58, 58, 0, 36, 36, 0, 36, 1, 36, - 0, 33, 33, 33, 33, 0, 0, 41, 1, 33, 1, 34, 34, 34, 34, 1, - 0, 35, 0, 25, 25, 0, 35, 0, 25, 1, 34, 0, 36, 0, 37, 37, - 37, 0, 83, 83, 70, 70, 0, 4, 84, 84, 59, 59, 65, 65, 71, 71, - 71, 0, 72, 72, 73, 73, 0, 73, 85, 85, 77, 77, 77, 0, 79, 79, - 79, 0, 0, 79, 86, 86, 86, 0, 0, 7, 48, 48, 0, 48, 48, 0, - 74, 74, 74, 0, 75, 75, 75, 0, 38, 38, 38, 0, 39, 39, 39, 0, - 49, 49, 0, 49, 60, 60, 40, 40, 50, 50, 51, 51, 52, 52, 52, 0, - 0, 52, 87, 87, 0, 87, 64, 64, 0, 64, 76, 76, 0, 76, 98, 98, - 97, 97, 61, 61, 0, 61, 61, 0, 88, 88, 80, 80, 0, 80, 89, 89, - 90, 90, 90, 0, 91, 91, 91, 0, 94, 94, 92, 92, 101, 101, 101, 0, - 96, 96, 96, 0, 100, 100, 100, 0, 102, 102, 63, 63, 63, 0, 81, 81, - 81, 0, 84, 0, 99, 99, 99, 0, 0, 99, 34, 33, 33, 1, -}; - -/* Script: 8046 bytes. */ - -RE_UINT32 re_get_script(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 11; - code = ch ^ (f << 11); - pos = (RE_UINT32)re_script_stage_1[f] << 4; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_script_stage_2[pos + f] << 3; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_script_stage_3[pos + f] << 3; - f = code >> 1; - code ^= f << 1; - pos = (RE_UINT32)re_script_stage_4[pos + f] << 1; - value = re_script_stage_5[pos + code]; - - return value; -} - -/* Word_Break. */ - -static RE_UINT8 re_word_break_stage_1[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 5, 6, 6, 7, 4, 8, - 9, 10, 11, 12, 4, 4, 13, 4, 4, 4, 4, 14, 4, 15, 16, 17, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 18, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_word_break_stage_2[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 2, 6, 7, 8, 9, 10, 11, 12, - 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, - 29, 30, 2, 2, 31, 32, 33, 34, 35, 2, 2, 2, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 2, 50, 2, 2, 51, 52, - 53, 54, 55, 56, 57, 57, 57, 57, 57, 58, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 59, 60, 61, 62, 63, 57, 57, 57, - 64, 65, 66, 67, 57, 68, 69, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 70, 2, 2, 71, 72, 73, 74, - 75, 76, 77, 78, 79, 80, 81, 82, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 83, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 84, 85, 2, 2, 86, 87, 88, 89, 90, 91, - 92, 93, 94, 95, 57, 96, 97, 98, 2, 99, 57, 57, 57, 57, 57, 57, - 100, 57, 101, 102, 103, 57, 104, 57, 105, 57, 57, 57, 57, 57, 57, 57, - 106, 107, 108, 109, 57, 57, 57, 57, 57, 57, 57, 57, 57, 110, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 2, 2, 2, 2, 2, 2, 111, 57, 112, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 2, 2, 2, 2, 2, 2, 2, 2, 113, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 2, 2, 2, 2, 114, 57, 57, 57, 57, 57, 57, 57, 57, 57, 115, 116, - 117, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 118, 119, 120, 57, 57, 57, 121, 122, 123, 2, 2, 124, 125, 126, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 127, 128, 57, 57, - 57, 57, 57, 129, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 130, 57, 131, 132, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, -}; - -static RE_UINT8 re_word_break_stage_3[] = { - 0, 1, 0, 0, 2, 3, 4, 5, 6, 7, 7, 8, 6, 7, 7, 9, - 10, 0, 0, 0, 0, 11, 12, 13, 7, 7, 14, 7, 7, 7, 14, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 15, 7, 16, 0, 17, 18, 0, 0, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 20, 21, - 22, 23, 7, 7, 24, 7, 7, 7, 7, 7, 7, 7, 7, 7, 25, 7, - 26, 27, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 0, 6, 7, 7, 7, 14, 28, 6, 7, 7, 7, - 7, 29, 30, 19, 19, 19, 19, 31, 32, 0, 33, 33, 33, 34, 35, 0, - 36, 37, 19, 38, 7, 7, 7, 7, 7, 39, 19, 19, 4, 40, 41, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 42, 43, 44, 45, 4, 46, - 0, 47, 48, 7, 7, 7, 19, 19, 19, 49, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 50, 19, 51, 0, 4, 52, 7, 7, 7, 39, 53, 54, - 7, 7, 50, 55, 56, 57, 0, 0, 7, 7, 7, 58, 0, 0, 0, 0, - 0, 0, 0, 0, 59, 17, 0, 0, 0, 0, 0, 0, 60, 19, 19, 61, - 62, 7, 7, 7, 7, 7, 7, 63, 19, 19, 64, 7, 65, 4, 6, 6, - 66, 67, 68, 7, 7, 59, 69, 70, 71, 72, 73, 74, 65, 4, 75, 0, - 66, 76, 68, 7, 7, 59, 77, 78, 79, 80, 81, 82, 83, 4, 84, 0, - 66, 25, 24, 7, 7, 59, 85, 70, 31, 86, 87, 0, 65, 4, 0, 0, - 66, 67, 68, 7, 7, 59, 85, 70, 71, 80, 88, 74, 65, 4, 28, 0, - 89, 90, 91, 92, 93, 90, 7, 94, 95, 96, 97, 0, 83, 4, 0, 0, - 66, 20, 59, 7, 7, 59, 98, 99, 100, 96, 101, 75, 65, 4, 0, 0, - 102, 20, 59, 7, 7, 59, 98, 70, 100, 96, 101, 103, 65, 4, 104, 0, - 102, 20, 59, 7, 7, 7, 7, 105, 100, 106, 73, 0, 65, 4, 0, 107, - 102, 7, 14, 107, 7, 7, 24, 108, 14, 109, 110, 19, 0, 0, 111, 0, - 0, 0, 0, 0, 0, 0, 112, 113, 73, 61, 4, 114, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 112, 115, 0, 116, 4, 114, 0, 0, 0, 0, - 87, 0, 0, 117, 4, 114, 118, 119, 7, 6, 7, 7, 7, 17, 30, 19, - 100, 120, 19, 30, 19, 19, 19, 121, 122, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 123, 19, 61, 4, 114, 88, 124, 125, 116, 126, 0, - 127, 31, 4, 128, 7, 7, 7, 7, 25, 129, 7, 7, 7, 7, 7, 130, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 91, 14, 91, 7, 7, 7, 7, - 7, 91, 7, 7, 7, 7, 91, 14, 91, 7, 14, 7, 7, 7, 7, 7, - 7, 7, 91, 7, 7, 7, 7, 7, 7, 7, 7, 131, 0, 0, 0, 0, - 7, 7, 0, 0, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 17, 0, - 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 67, 7, 7, - 6, 7, 7, 9, 7, 7, 7, 7, 7, 7, 7, 7, 7, 90, 87, 0, - 7, 20, 132, 0, 7, 7, 132, 0, 7, 7, 133, 0, 7, 20, 134, 0, - 0, 0, 0, 0, 0, 0, 60, 19, 19, 19, 135, 136, 4, 114, 0, 0, - 0, 137, 4, 114, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 0, - 7, 7, 7, 7, 7, 138, 7, 7, 7, 7, 7, 7, 7, 7, 139, 0, - 7, 7, 7, 17, 19, 135, 19, 135, 83, 4, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 19, 19, 140, 117, 4, 114, 0, 0, 0, 0, - 7, 7, 141, 135, 0, 0, 0, 0, 0, 0, 142, 61, 19, 19, 19, 71, - 4, 114, 4, 114, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 143, 7, 7, 7, 7, 7, 144, 19, 143, 145, 4, 114, 0, 123, 135, 0, - 146, 7, 7, 7, 64, 147, 4, 52, 7, 7, 7, 7, 50, 19, 135, 0, - 7, 7, 7, 7, 144, 19, 19, 0, 4, 148, 4, 52, 7, 7, 7, 139, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 149, 19, 19, 150, 151, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 19, 19, 19, 19, 61, 0, 0, 60, - 7, 7, 139, 139, 7, 7, 7, 7, 139, 139, 7, 152, 7, 7, 7, 139, - 7, 7, 7, 7, 7, 7, 20, 153, 154, 17, 155, 145, 7, 17, 154, 17, - 0, 156, 0, 157, 158, 159, 0, 160, 161, 0, 162, 0, 163, 164, 28, 165, - 0, 0, 7, 17, 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 140, 0, - 166, 107, 108, 167, 18, 168, 7, 169, 170, 171, 0, 0, 7, 7, 7, 7, - 7, 87, 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, 172, 7, 7, 7, 7, 7, 7, 75, 0, 0, - 7, 7, 7, 7, 7, 14, 7, 7, 7, 7, 7, 14, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 17, 173, 174, 0, - 7, 7, 7, 7, 25, 129, 7, 7, 7, 7, 7, 7, 7, 165, 0, 73, - 7, 7, 14, 0, 14, 14, 14, 14, 14, 14, 14, 14, 19, 19, 19, 19, - 0, 0, 0, 0, 0, 165, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 129, 0, 0, 0, 0, 127, 175, 93, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 176, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 178, - 170, 7, 7, 7, 7, 139, 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 14, 0, 0, 7, 7, 7, 9, 0, 0, 0, 0, 0, 0, 177, 177, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 177, 177, 177, 177, 177, 179, - 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 177, 0, 0, 0, 0, 0, - 7, 17, 0, 0, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, 7, 139, - 7, 17, 7, 7, 4, 180, 0, 0, 7, 7, 7, 7, 7, 141, 149, 181, - 7, 7, 7, 73, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 117, 0, - 0, 0, 165, 7, 107, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 182, 145, 0, 7, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, - 183, 184, 7, 7, 39, 0, 0, 0, 7, 7, 7, 7, 7, 7, 145, 0, - 27, 7, 7, 7, 7, 7, 144, 19, 121, 0, 4, 114, 19, 19, 27, 185, - 4, 52, 7, 7, 50, 116, 7, 7, 141, 19, 135, 0, 7, 7, 7, 17, - 62, 7, 7, 7, 7, 7, 39, 19, 140, 165, 4, 114, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 64, 61, 0, 184, 186, 4, 114, 0, 0, 0, 187, - 0, 0, 0, 0, 0, 0, 125, 188, 81, 0, 0, 0, 7, 39, 189, 0, - 190, 190, 190, 0, 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, 39, 191, 4, 114, - 7, 7, 7, 7, 145, 0, 7, 7, 14, 192, 7, 7, 7, 7, 7, 145, - 14, 0, 192, 193, 33, 194, 195, 196, 197, 33, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 75, 0, 0, 0, 192, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 139, 0, 0, 7, 7, 7, 7, 7, 7, - 7, 7, 107, 7, 7, 7, 7, 7, 7, 0, 0, 0, 0, 0, 7, 145, - 19, 19, 198, 0, 61, 0, 199, 0, 0, 200, 201, 0, 0, 0, 20, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 202, - 203, 3, 0, 204, 6, 7, 7, 8, 6, 7, 7, 9, 205, 177, 177, 177, - 177, 177, 177, 206, 7, 7, 7, 14, 107, 107, 107, 207, 0, 0, 0, 208, - 7, 98, 7, 7, 14, 7, 7, 209, 7, 139, 7, 139, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 9, - 0, 0, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, 7, 7, 17, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 136, - 7, 7, 7, 17, 7, 7, 7, 7, 7, 7, 87, 0, 0, 0, 0, 0, - 7, 7, 7, 14, 0, 0, 7, 7, 7, 9, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 139, 7, 7, 7, 7, 145, 7, 167, 0, 0, 0, 0, 0, - 7, 7, 7, 139, 4, 114, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 139, 59, 7, 7, 7, 7, 25, 210, 7, 7, 139, 0, 0, 0, 0, 0, - 7, 7, 139, 0, 7, 7, 7, 75, 0, 0, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 172, 0, 0, 0, 0, 0, 0, 0, 0, - 211, 60, 98, 6, 7, 7, 145, 79, 0, 0, 0, 0, 7, 7, 7, 17, - 7, 7, 7, 7, 7, 7, 139, 0, 7, 7, 139, 0, 7, 7, 9, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 87, 0, 0, 0, 0, 0, 0, - 146, 7, 7, 7, 7, 7, 7, 19, 61, 0, 0, 0, 83, 4, 0, 0, - 146, 7, 7, 7, 7, 7, 19, 212, 0, 0, 7, 7, 7, 87, 4, 114, - 146, 7, 7, 7, 141, 19, 213, 4, 0, 0, 0, 0, 0, 0, 0, 0, - 146, 7, 7, 7, 7, 7, 39, 19, 214, 0, 4, 114, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 39, 19, 0, 4, 114, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 14, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 9, 0, 0, 0, - 7, 7, 7, 7, 7, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 87, 0, 0, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 17, 0, 64, 19, 19, 19, 19, 61, - 0, 73, 146, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 215, 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, 142, 216, 217, 218, - 219, 135, 0, 0, 0, 220, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 221, 0, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 20, 7, 7, 7, 7, 7, - 7, 7, 7, 20, 222, 223, 7, 224, 98, 7, 7, 7, 7, 7, 7, 7, - 25, 225, 20, 20, 7, 7, 7, 226, 153, 107, 59, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 139, 7, 7, 7, 59, 7, 7, 130, 7, 7, 7, 130, - 7, 7, 20, 7, 7, 7, 20, 7, 7, 14, 7, 7, 7, 14, 7, 7, - 7, 59, 7, 7, 7, 59, 7, 7, 130, 227, 4, 4, 4, 4, 4, 4, - 98, 7, 7, 7, 228, 6, 130, 229, 166, 230, 228, 152, 228, 130, 130, 82, - 7, 24, 7, 145, 231, 24, 7, 145, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 232, 233, 233, 233, - 234, 0, 0, 0, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, 164, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, 0, -}; - -static RE_UINT8 re_word_break_stage_4[] = { - 0, 0, 1, 2, 3, 4, 0, 5, 6, 6, 7, 0, 8, 9, 9, 9, - 10, 11, 10, 0, 0, 12, 13, 14, 0, 15, 13, 0, 9, 10, 16, 17, - 16, 18, 9, 19, 0, 20, 21, 21, 9, 22, 17, 23, 0, 24, 10, 22, - 25, 9, 9, 25, 26, 21, 27, 9, 28, 0, 29, 0, 30, 21, 21, 31, - 32, 31, 33, 33, 34, 0, 35, 36, 37, 38, 0, 39, 40, 38, 41, 21, - 42, 43, 44, 9, 9, 45, 21, 46, 21, 47, 48, 27, 49, 50, 0, 51, - 52, 9, 40, 8, 9, 53, 54, 0, 49, 9, 21, 16, 55, 0, 56, 21, - 21, 57, 57, 58, 57, 0, 22, 9, 0, 21, 21, 40, 21, 9, 53, 59, - 57, 21, 53, 60, 30, 8, 9, 50, 50, 9, 20, 17, 16, 59, 21, 61, - 61, 62, 0, 63, 0, 25, 16, 0, 10, 64, 22, 65, 16, 48, 40, 63, - 61, 58, 66, 0, 8, 20, 0, 60, 27, 67, 22, 8, 31, 58, 19, 0, - 0, 68, 69, 8, 10, 17, 22, 16, 65, 22, 64, 19, 16, 68, 40, 68, - 48, 58, 19, 63, 9, 8, 16, 45, 21, 48, 0, 32, 68, 8, 0, 13, - 65, 0, 10, 45, 48, 62, 17, 9, 9, 28, 70, 63, 21, 71, 68, 0, - 66, 21, 40, 0, 72, 0, 31, 73, 21, 58, 58, 0, 0, 74, 66, 68, - 9, 57, 21, 73, 0, 70, 63, 21, 58, 68, 48, 61, 30, 73, 68, 21, - 75, 58, 0, 28, 10, 9, 10, 30, 53, 73, 53, 0, 76, 0, 21, 0, - 0, 66, 63, 77, 78, 0, 9, 16, 73, 0, 9, 41, 0, 30, 21, 44, - 9, 21, 9, 0, 79, 9, 21, 27, 72, 8, 40, 21, 44, 52, 53, 80, - 81, 81, 9, 20, 17, 22, 9, 17, 0, 82, 83, 0, 0, 84, 85, 86, - 0, 11, 87, 88, 0, 87, 37, 89, 37, 37, 0, 64, 13, 64, 8, 16, - 22, 25, 16, 9, 0, 8, 16, 13, 0, 17, 64, 41, 27, 0, 90, 91, - 92, 93, 94, 94, 95, 94, 94, 95, 49, 0, 21, 96, 50, 10, 97, 97, - 41, 9, 64, 0, 9, 58, 63, 0, 73, 68, 17, 98, 8, 10, 40, 58, - 64, 9, 0, 99, 100, 33, 33, 34, 33, 101, 102, 100, 103, 88, 11, 87, - 0, 104, 5, 105, 9, 106, 0, 107, 108, 0, 0, 109, 94, 110, 17, 19, - 111, 0, 10, 25, 19, 50, 57, 32, 40, 14, 21, 112, 44, 19, 93, 0, - 58, 30, 113, 37, 114, 21, 40, 30, 68, 58, 68, 73, 13, 65, 8, 22, - 25, 8, 10, 8, 25, 10, 9, 60, 65, 50, 81, 0, 81, 8, 8, 8, - 0, 115, 116, 116, 14, 0, -}; - -static RE_UINT8 re_word_break_stage_5[] = { - 0, 0, 0, 0, 0, 0, 5, 6, 6, 4, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 2, 13, 0, 14, 0, 15, 15, 15, 15, 15, 15, 12, 13, - 0, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 0, 0, 0, 0, 16, - 0, 6, 0, 0, 0, 0, 11, 0, 0, 9, 0, 0, 0, 11, 0, 12, - 11, 11, 0, 0, 0, 0, 11, 11, 0, 0, 0, 12, 11, 0, 0, 0, - 11, 0, 11, 0, 7, 7, 7, 7, 11, 0, 11, 11, 11, 11, 13, 0, - 0, 0, 11, 12, 11, 11, 0, 11, 11, 11, 0, 7, 7, 7, 11, 11, - 0, 11, 0, 0, 0, 13, 0, 0, 0, 7, 7, 7, 7, 7, 0, 7, - 0, 7, 7, 0, 3, 3, 3, 3, 3, 3, 3, 0, 3, 3, 3, 11, - 12, 0, 0, 0, 9, 9, 9, 9, 9, 0, 0, 0, 13, 13, 0, 0, - 7, 7, 7, 0, 11, 11, 11, 7, 15, 15, 0, 15, 13, 0, 11, 11, - 7, 11, 11, 11, 0, 11, 7, 7, 7, 9, 0, 7, 7, 11, 11, 7, - 7, 0, 7, 7, 15, 15, 11, 11, 11, 0, 0, 11, 0, 0, 0, 9, - 11, 7, 11, 11, 11, 11, 7, 7, 7, 11, 0, 0, 13, 0, 11, 0, - 7, 7, 11, 7, 11, 7, 7, 7, 7, 7, 0, 0, 7, 11, 7, 7, - 0, 0, 15, 15, 7, 0, 0, 7, 7, 7, 11, 0, 0, 0, 0, 7, - 0, 0, 0, 11, 0, 11, 11, 0, 0, 7, 0, 0, 11, 7, 0, 0, - 0, 0, 7, 7, 0, 0, 7, 11, 0, 0, 7, 0, 7, 0, 7, 0, - 15, 15, 0, 0, 7, 0, 0, 0, 0, 7, 0, 7, 15, 15, 7, 7, - 11, 0, 7, 7, 7, 7, 9, 0, 11, 7, 11, 0, 7, 7, 7, 11, - 7, 11, 11, 0, 0, 11, 0, 11, 7, 7, 9, 9, 14, 14, 0, 0, - 14, 0, 0, 12, 6, 6, 9, 9, 9, 9, 9, 0, 16, 0, 0, 0, - 13, 0, 0, 0, 9, 0, 9, 9, 0, 10, 10, 10, 10, 10, 0, 0, - 0, 7, 7, 10, 10, 0, 0, 0, 10, 10, 10, 10, 10, 10, 10, 0, - 7, 7, 0, 11, 11, 11, 7, 11, 11, 7, 7, 0, 0, 3, 7, 3, - 3, 0, 3, 3, 3, 0, 3, 0, 3, 3, 0, 3, 13, 0, 0, 12, - 0, 16, 16, 16, 13, 12, 0, 0, 11, 0, 0, 9, 0, 0, 0, 14, - 0, 0, 12, 13, 0, 0, 10, 10, 10, 10, 7, 7, 0, 9, 9, 9, - 7, 0, 15, 15, 7, 7, 7, 9, 9, 9, 9, 7, 0, 0, 8, 8, - 8, 8, 8, 8, -}; - -/* Word_Break: 3946 bytes. */ - -RE_UINT32 re_get_word_break(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_word_break_stage_1[f] << 5; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_word_break_stage_2[pos + f] << 4; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_word_break_stage_3[pos + f] << 1; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_word_break_stage_4[pos + f] << 2; - value = re_word_break_stage_5[pos + code]; - - return value; -} - -/* Grapheme_Cluster_Break. */ - -static RE_UINT8 re_grapheme_cluster_break_stage_1[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 6, 2, 2, 7, 2, 2, 8, 9, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 10, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_grapheme_cluster_break_stage_2[] = { - 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, - 15, 16, 1, 17, 1, 1, 1, 18, 19, 20, 21, 22, 23, 24, 1, 1, - 25, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 26, 27, 1, 1, - 28, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 29, 1, 30, 31, 32, 33, 34, 35, 36, 37, - 38, 39, 40, 34, 35, 36, 37, 38, 39, 40, 34, 35, 36, 37, 38, 39, - 40, 34, 35, 36, 37, 38, 39, 40, 34, 35, 36, 37, 38, 39, 40, 34, - 35, 36, 37, 38, 39, 40, 34, 41, 42, 42, 42, 42, 42, 42, 42, 42, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 43, 1, 1, 44, 45, - 1, 46, 1, 1, 1, 1, 1, 1, 1, 1, 47, 1, 1, 1, 1, 1, - 48, 49, 1, 1, 1, 1, 50, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 51, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 52, 53, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 54, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 42, 55, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_grapheme_cluster_break_stage_3[] = { - 0, 1, 2, 2, 2, 2, 2, 3, 1, 1, 4, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 5, 5, 5, 5, 5, 5, 5, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 6, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 7, 5, 8, 9, 2, 2, 2, - 10, 11, 2, 2, 12, 5, 2, 13, 2, 2, 2, 2, 2, 14, 15, 2, - 3, 16, 2, 5, 17, 2, 2, 2, 2, 2, 18, 13, 2, 2, 12, 19, - 2, 20, 21, 2, 2, 22, 2, 2, 2, 2, 2, 2, 2, 2, 23, 24, - 25, 2, 2, 26, 27, 28, 29, 2, 30, 2, 2, 31, 32, 33, 29, 2, - 34, 2, 2, 35, 36, 16, 2, 37, 34, 2, 2, 35, 38, 2, 29, 2, - 30, 2, 2, 39, 32, 40, 29, 2, 41, 2, 2, 42, 43, 33, 2, 2, - 44, 2, 2, 45, 46, 47, 29, 2, 48, 2, 2, 49, 50, 47, 29, 2, - 48, 2, 2, 42, 51, 33, 29, 2, 48, 2, 2, 2, 52, 53, 2, 48, - 2, 2, 2, 54, 55, 2, 2, 2, 2, 2, 2, 56, 57, 2, 2, 2, - 2, 58, 2, 59, 2, 2, 2, 60, 61, 62, 5, 63, 64, 2, 2, 2, - 2, 2, 65, 66, 2, 67, 13, 68, 69, 70, 2, 2, 2, 2, 2, 2, - 71, 71, 71, 71, 71, 71, 72, 72, 72, 72, 73, 74, 74, 74, 74, 74, - 2, 2, 2, 2, 2, 65, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 75, 2, 75, 2, 29, 2, 29, 2, 2, 2, 76, 77, 78, 2, 2, - 79, 2, 2, 2, 2, 2, 2, 2, 2, 2, 80, 2, 2, 2, 2, 2, - 2, 2, 81, 82, 2, 2, 2, 2, 2, 2, 2, 83, 2, 2, 2, 2, - 2, 84, 2, 2, 2, 85, 86, 87, 2, 2, 2, 2, 2, 2, 2, 2, - 88, 2, 2, 89, 90, 2, 12, 19, 91, 2, 92, 2, 2, 2, 93, 94, - 2, 2, 95, 96, 2, 2, 2, 2, 2, 2, 2, 2, 2, 97, 98, 99, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 5, 5, 100, 101, - 102, 2, 103, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 5, 5, 13, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 104, 105, - 2, 2, 2, 2, 2, 2, 2, 104, 2, 2, 2, 2, 2, 2, 5, 5, - 2, 2, 106, 2, 2, 2, 2, 2, 2, 107, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 104, 108, 2, 104, 2, 2, 2, 2, 2, 105, - 109, 2, 110, 2, 2, 2, 2, 2, 111, 2, 2, 112, 113, 2, 5, 105, - 2, 2, 114, 2, 115, 94, 71, 116, 25, 2, 2, 117, 118, 2, 2, 2, - 2, 2, 119, 120, 121, 2, 2, 2, 2, 2, 2, 122, 16, 2, 123, 124, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 125, 2, - 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, - 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, - 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, - 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, - 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, - 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, - 130, 128, 126, 127, 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 130, 128, - 128, 129, 128, 130, 128, 126, 127, 128, 129, 128, 131, 72, 132, 74, 74, 133, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 134, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 5, 2, 100, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 45, 2, 2, 2, 2, 2, 135, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 70, - 136, 2, 2, 137, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 138, 2, 2, 139, 100, 2, 2, 2, 91, 2, 2, 140, 2, 2, 2, 2, - 141, 2, 142, 143, 2, 2, 2, 2, 91, 2, 2, 144, 118, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 145, 146, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 147, 148, 149, 104, 141, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 150, 151, 152, 2, 153, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 75, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 154, 155, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 1, -}; - -static RE_UINT8 re_grapheme_cluster_break_stage_4[] = { - 0, 0, 1, 2, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 4, - 3, 3, 3, 5, 6, 6, 6, 6, 7, 6, 8, 3, 9, 6, 6, 6, - 6, 6, 6, 10, 11, 10, 3, 3, 0, 12, 3, 3, 6, 6, 13, 12, - 3, 3, 7, 6, 14, 3, 3, 3, 3, 15, 6, 16, 6, 17, 18, 8, - 19, 3, 3, 3, 6, 6, 13, 3, 3, 15, 6, 6, 6, 3, 3, 3, - 3, 15, 10, 6, 6, 9, 9, 8, 3, 3, 9, 3, 3, 6, 6, 6, - 6, 6, 6, 13, 20, 3, 3, 3, 3, 3, 21, 22, 23, 6, 24, 25, - 9, 6, 3, 3, 15, 3, 3, 3, 26, 3, 3, 3, 3, 3, 3, 27, - 23, 28, 29, 30, 3, 7, 3, 3, 31, 3, 3, 3, 3, 3, 3, 22, - 32, 7, 17, 8, 8, 19, 3, 3, 23, 10, 33, 30, 3, 3, 3, 18, - 3, 15, 3, 3, 34, 3, 3, 3, 3, 3, 3, 21, 35, 36, 37, 30, - 38, 3, 3, 3, 3, 3, 3, 15, 24, 39, 18, 8, 3, 11, 3, 3, - 36, 3, 3, 3, 3, 3, 3, 40, 41, 42, 37, 8, 23, 22, 37, 30, - 3, 3, 34, 7, 43, 44, 45, 46, 47, 6, 13, 3, 3, 7, 6, 13, - 47, 6, 10, 14, 3, 3, 6, 8, 3, 3, 8, 3, 3, 48, 19, 36, - 9, 6, 6, 20, 6, 18, 3, 9, 6, 6, 9, 6, 6, 6, 6, 14, - 3, 34, 3, 3, 3, 3, 3, 9, 49, 6, 31, 32, 3, 36, 8, 15, - 9, 14, 3, 3, 34, 32, 3, 19, 3, 3, 3, 19, 50, 50, 50, 50, - 51, 51, 51, 51, 51, 51, 52, 52, 52, 52, 52, 52, 15, 14, 3, 3, - 3, 53, 6, 54, 45, 41, 23, 6, 6, 3, 3, 19, 3, 3, 7, 55, - 3, 3, 19, 3, 20, 46, 24, 3, 41, 45, 23, 3, 3, 38, 56, 3, - 3, 7, 57, 3, 3, 58, 6, 13, 44, 9, 6, 24, 46, 6, 6, 17, - 6, 59, 3, 3, 3, 49, 20, 24, 41, 59, 3, 3, 60, 3, 3, 3, - 61, 54, 53, 62, 3, 21, 54, 63, 54, 3, 3, 3, 3, 45, 45, 6, - 6, 43, 3, 3, 13, 6, 6, 6, 49, 6, 14, 19, 36, 14, 3, 3, - 6, 13, 3, 3, 3, 3, 3, 6, 3, 3, 4, 64, 3, 3, 0, 65, - 3, 3, 3, 7, 8, 3, 3, 3, 3, 3, 15, 6, 3, 3, 11, 3, - 13, 6, 6, 8, 34, 34, 7, 3, 66, 67, 3, 3, 62, 3, 3, 3, - 3, 45, 45, 45, 45, 14, 3, 3, 3, 15, 6, 8, 3, 7, 6, 6, - 50, 50, 50, 68, 7, 43, 54, 24, 59, 3, 3, 3, 3, 3, 9, 20, - 67, 32, 3, 3, 7, 3, 3, 69, 18, 17, 14, 15, 3, 3, 66, 54, - 3, 70, 3, 3, 66, 25, 35, 30, 71, 72, 72, 72, 72, 72, 72, 71, - 72, 72, 72, 72, 72, 72, 71, 72, 72, 71, 72, 72, 72, 3, 3, 3, - 51, 73, 74, 52, 52, 52, 52, 3, 3, 3, 3, 34, 0, 0, 0, 3, - 9, 11, 3, 6, 3, 3, 13, 7, 75, 3, 3, 3, 3, 3, 6, 6, - 46, 20, 32, 5, 13, 3, 3, 3, 3, 7, 6, 23, 6, 14, 3, 3, - 66, 43, 6, 20, 3, 3, 7, 25, 6, 53, 3, 3, 38, 45, 45, 45, - 45, 45, 45, 45, 45, 45, 45, 76, 3, 77, 8, 61, 78, 0, 79, 6, - 13, 9, 6, 3, 3, 3, 15, 8, 3, 80, 81, 81, 81, 81, 81, 81, -}; - -static RE_UINT8 re_grapheme_cluster_break_stage_5[] = { - 3, 3, 3, 3, 3, 3, 2, 3, 3, 1, 3, 3, 0, 0, 0, 0, - 0, 0, 0, 3, 0, 3, 0, 0, 4, 4, 4, 4, 0, 0, 0, 4, - 4, 4, 0, 0, 0, 4, 4, 4, 4, 4, 0, 4, 0, 4, 4, 0, - 3, 0, 0, 0, 4, 4, 4, 0, 4, 0, 0, 0, 0, 0, 4, 4, - 4, 3, 0, 4, 4, 0, 0, 4, 4, 0, 4, 4, 0, 4, 0, 0, - 4, 4, 4, 6, 0, 0, 4, 6, 4, 0, 6, 6, 6, 4, 4, 4, - 4, 6, 6, 6, 6, 4, 6, 6, 0, 4, 6, 6, 4, 0, 4, 6, - 4, 0, 0, 6, 6, 0, 0, 6, 6, 4, 0, 0, 0, 4, 4, 6, - 6, 4, 4, 0, 4, 6, 0, 6, 0, 0, 4, 0, 4, 6, 6, 0, - 0, 0, 6, 6, 6, 0, 6, 6, 0, 6, 6, 6, 6, 0, 4, 4, - 4, 0, 6, 4, 6, 6, 4, 6, 6, 0, 4, 6, 6, 6, 4, 4, - 4, 0, 4, 0, 6, 6, 6, 6, 6, 6, 6, 4, 0, 4, 0, 6, - 0, 4, 0, 4, 4, 6, 4, 4, 7, 7, 7, 7, 8, 8, 8, 8, - 9, 9, 9, 9, 4, 4, 6, 4, 4, 4, 6, 6, 4, 4, 3, 0, - 0, 0, 6, 0, 4, 6, 6, 4, 0, 6, 4, 6, 6, 0, 0, 0, - 4, 4, 6, 0, 0, 6, 4, 4, 6, 6, 0, 0, 6, 4, 6, 4, - 4, 4, 3, 3, 3, 3, 3, 0, 0, 0, 0, 6, 6, 4, 4, 6, - 7, 0, 0, 0, 4, 6, 0, 0, 0, 6, 4, 0, 10, 11, 11, 11, - 11, 11, 11, 11, 8, 8, 8, 0, 0, 0, 0, 9, 6, 4, 6, 0, - 6, 6, 6, 0, 0, 4, 6, 4, 4, 4, 4, 3, 3, 3, 3, 4, - 0, 0, 5, 5, 5, 5, 5, 5, -}; - -/* Grapheme_Cluster_Break: 2336 bytes. */ - -RE_UINT32 re_get_grapheme_cluster_break(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_grapheme_cluster_break_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_grapheme_cluster_break_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_grapheme_cluster_break_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_grapheme_cluster_break_stage_4[pos + f] << 2; - value = re_grapheme_cluster_break_stage_5[pos + code]; - - return value; -} - -/* Sentence_Break. */ - -static RE_UINT8 re_sentence_break_stage_1[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 6, 7, 5, 5, 8, 9, 10, - 11, 12, 13, 14, 9, 9, 15, 9, 9, 9, 9, 16, 9, 17, 18, 9, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 19, 20, 9, 9, 9, 21, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 22, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, -}; - -static RE_UINT8 re_sentence_break_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 17, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, - 31, 32, 33, 34, 35, 33, 33, 36, 33, 37, 33, 33, 38, 39, 40, 33, - 41, 42, 33, 33, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 43, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 44, - 17, 17, 17, 17, 45, 17, 46, 47, 48, 49, 50, 51, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 52, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 33, 33, 33, 33, 33, 33, 33, 33, 17, 53, 54, 17, 55, 56, 57, - 58, 59, 60, 61, 62, 33, 33, 33, 63, 64, 65, 66, 67, 33, 33, 33, - 68, 69, 33, 33, 33, 33, 70, 33, 33, 33, 33, 33, 33, 33, 33, 33, - 17, 17, 17, 71, 72, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, - 17, 17, 17, 17, 73, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 33, 33, 33, 33, 33, 33, 33, 17, 17, 74, 33, 33, 33, 33, 75, - 76, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 77, 78, 33, 79, 80, 81, 82, 33, 33, 33, 33, 33, 33, 33, 33, - 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 83, 33, - 17, 17, 17, 17, 17, 17, 84, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 85, 86, 33, 33, 33, 33, 33, 33, 33, - 33, 33, 33, 33, 33, 33, 33, 33, 17, 17, 86, 33, 33, 33, 33, 33, - 87, 88, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, 33, -}; - -static RE_UINT16 re_sentence_break_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 8, 16, 17, 18, 19, 20, 21, 22, 23, 23, 23, 24, 25, 26, 27, 28, - 29, 30, 18, 8, 31, 8, 32, 8, 8, 33, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 41, 41, 44, 45, 46, 47, 48, 41, 41, 49, 50, 51, - 52, 53, 54, 55, 55, 56, 55, 57, 58, 59, 60, 61, 62, 63, 64, 65, - 66, 67, 68, 69, 70, 71, 72, 73, 62, 71, 74, 75, 76, 77, 78, 79, - 80, 81, 82, 73, 83, 84, 85, 86, 83, 87, 88, 89, 90, 91, 92, 93, - 94, 95, 96, 55, 97, 98, 99, 55, 100, 101, 102, 103, 104, 105, 106, 55, - 41, 107, 108, 109, 110, 29, 111, 112, 41, 41, 41, 41, 41, 41, 41, 41, - 41, 41, 113, 41, 114, 115, 116, 41, 117, 41, 118, 119, 120, 41, 41, 121, - 94, 41, 41, 41, 41, 41, 41, 41, 41, 41, 41, 122, 123, 41, 41, 124, - 125, 126, 127, 128, 41, 129, 130, 131, 132, 41, 41, 133, 41, 134, 41, 135, - 136, 137, 138, 139, 41, 140, 141, 55, 142, 41, 143, 144, 145, 146, 55, 55, - 147, 129, 148, 149, 150, 151, 41, 152, 41, 153, 154, 155, 55, 55, 156, 157, - 18, 18, 18, 18, 18, 18, 23, 158, 8, 8, 8, 8, 159, 8, 8, 8, - 160, 161, 162, 163, 161, 164, 165, 166, 167, 168, 169, 170, 171, 55, 172, 173, - 174, 175, 176, 30, 177, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, - 178, 179, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 180, 30, 181, - 55, 55, 182, 183, 55, 55, 184, 185, 55, 55, 55, 55, 186, 55, 187, 188, - 29, 189, 190, 191, 8, 8, 8, 192, 18, 193, 41, 194, 195, 196, 196, 23, - 197, 198, 55, 55, 55, 55, 55, 55, 199, 200, 94, 41, 201, 94, 41, 112, - 202, 203, 41, 41, 204, 205, 55, 206, 41, 41, 41, 41, 41, 135, 55, 55, - 41, 41, 41, 41, 41, 41, 207, 55, 41, 41, 41, 41, 207, 55, 206, 208, - 209, 210, 8, 211, 212, 41, 41, 213, 214, 215, 8, 216, 217, 218, 55, 219, - 220, 221, 41, 222, 223, 129, 224, 225, 50, 226, 227, 136, 58, 228, 229, 55, - 41, 230, 231, 232, 41, 233, 234, 235, 236, 237, 55, 55, 55, 55, 41, 238, - 41, 41, 41, 41, 41, 239, 240, 241, 41, 41, 41, 242, 41, 41, 243, 55, - 244, 245, 246, 41, 41, 247, 248, 41, 41, 249, 206, 41, 250, 41, 251, 252, - 253, 254, 255, 256, 41, 41, 41, 257, 258, 2, 259, 260, 261, 262, 263, 264, - 265, 266, 267, 55, 41, 41, 41, 205, 55, 55, 41, 121, 55, 55, 55, 268, - 55, 55, 55, 55, 136, 41, 269, 55, 262, 206, 270, 55, 271, 41, 272, 55, - 29, 273, 274, 41, 271, 131, 55, 55, 275, 276, 135, 55, 55, 55, 55, 55, - 135, 243, 55, 55, 41, 277, 55, 55, 278, 279, 280, 136, 55, 55, 55, 55, - 41, 135, 135, 281, 55, 55, 55, 55, 41, 41, 282, 55, 55, 55, 55, 55, - 150, 283, 284, 79, 150, 285, 286, 287, 150, 288, 289, 55, 150, 228, 290, 55, - 55, 55, 55, 55, 41, 291, 131, 55, 41, 41, 41, 204, 55, 55, 55, 55, - 41, 41, 41, 292, 55, 55, 55, 55, 41, 204, 55, 55, 55, 55, 55, 55, - 41, 293, 55, 55, 55, 55, 55, 55, 41, 41, 294, 295, 296, 55, 55, 55, - 297, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 298, 299, 300, 55, 55, - 55, 55, 301, 55, 55, 55, 55, 55, 302, 303, 304, 305, 306, 307, 308, 309, - 310, 311, 312, 313, 314, 302, 303, 315, 305, 316, 317, 318, 309, 319, 320, 321, - 322, 323, 324, 189, 325, 326, 327, 328, 329, 330, 331, 332, 333, 334, 55, 55, - 41, 41, 41, 41, 41, 41, 195, 55, 41, 121, 41, 41, 41, 41, 41, 41, - 271, 55, 55, 55, 55, 55, 55, 55, 335, 336, 336, 336, 55, 55, 55, 55, - 23, 23, 23, 23, 23, 23, 23, 337, -}; - -static RE_UINT8 re_sentence_break_stage_4[] = { - 0, 0, 1, 2, 0, 0, 0, 0, 3, 4, 5, 6, 7, 7, 8, 9, - 10, 11, 11, 11, 11, 11, 12, 13, 14, 15, 15, 15, 15, 15, 16, 13, - 0, 17, 0, 0, 0, 0, 0, 0, 18, 0, 19, 20, 0, 21, 19, 0, - 11, 11, 11, 11, 11, 22, 11, 23, 15, 15, 15, 15, 15, 24, 15, 15, - 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 26, 26, - 26, 26, 27, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 28, 29, - 30, 31, 32, 33, 28, 31, 34, 28, 25, 31, 29, 31, 32, 26, 35, 34, - 36, 28, 31, 26, 26, 26, 26, 27, 25, 25, 25, 25, 30, 31, 25, 25, - 25, 25, 25, 25, 25, 15, 33, 30, 26, 23, 25, 25, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 37, 15, 15, - 15, 15, 15, 15, 15, 15, 38, 36, 39, 40, 36, 36, 41, 0, 0, 0, - 15, 42, 0, 43, 0, 0, 0, 0, 44, 44, 44, 44, 44, 44, 44, 44, - 44, 44, 44, 44, 25, 45, 46, 39, 0, 47, 22, 48, 32, 11, 11, 11, - 49, 11, 11, 15, 15, 15, 15, 15, 15, 15, 15, 50, 33, 34, 25, 25, - 25, 25, 25, 25, 15, 51, 30, 32, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 15, 15, 15, 15, 52, 44, 53, 25, 25, 25, 25, 25, - 28, 26, 26, 29, 25, 25, 25, 25, 25, 25, 0, 0, 10, 11, 11, 11, - 11, 11, 11, 11, 11, 22, 54, 55, 14, 15, 15, 15, 15, 15, 15, 15, - 15, 15, 56, 0, 57, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 58, - 59, 58, 0, 0, 36, 36, 36, 36, 36, 36, 60, 0, 36, 0, 0, 0, - 61, 62, 0, 63, 44, 44, 64, 65, 36, 36, 36, 36, 36, 36, 36, 36, - 36, 36, 66, 44, 44, 44, 44, 44, 7, 7, 67, 68, 69, 36, 36, 36, - 36, 36, 36, 36, 36, 70, 44, 71, 44, 72, 73, 74, 7, 7, 75, 76, - 77, 0, 0, 78, 79, 36, 36, 36, 36, 36, 36, 36, 44, 44, 44, 44, - 44, 44, 64, 80, 36, 36, 36, 36, 36, 81, 44, 44, 82, 0, 0, 0, - 7, 7, 75, 36, 36, 36, 36, 36, 36, 36, 66, 44, 44, 41, 83, 0, - 36, 36, 36, 36, 36, 81, 84, 44, 44, 85, 85, 86, 0, 0, 0, 0, - 36, 36, 36, 36, 36, 36, 85, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 87, 36, 36, 88, 0, 0, 0, 0, 0, 44, 44, 44, 44, 44, 44, 64, - 44, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 81, 89, - 44, 44, 44, 44, 85, 44, 36, 36, 81, 90, 7, 7, 80, 36, 80, 36, - 57, 80, 36, 76, 76, 36, 36, 36, 36, 36, 87, 36, 43, 40, 41, 89, - 44, 91, 91, 92, 0, 93, 0, 94, 81, 95, 7, 7, 41, 0, 0, 0, - 57, 80, 60, 96, 76, 36, 36, 36, 36, 36, 87, 36, 87, 97, 41, 73, - 64, 93, 91, 86, 98, 0, 80, 43, 0, 95, 7, 7, 74, 99, 0, 0, - 57, 80, 36, 94, 94, 36, 36, 36, 36, 36, 87, 36, 87, 80, 41, 89, - 44, 58, 58, 86, 88, 0, 0, 0, 81, 95, 7, 7, 0, 0, 0, 0, - 44, 91, 91, 86, 0, 100, 0, 94, 81, 95, 7, 7, 54, 0, 0, 0, - 101, 80, 60, 40, 87, 41, 97, 87, 96, 88, 60, 40, 36, 36, 41, 100, - 64, 100, 73, 86, 88, 93, 0, 0, 0, 95, 7, 7, 0, 0, 0, 0, - 57, 80, 36, 87, 87, 36, 36, 36, 36, 36, 87, 36, 36, 80, 41, 102, - 44, 73, 73, 86, 0, 59, 41, 0, 100, 80, 36, 87, 87, 36, 36, 36, - 36, 36, 87, 36, 36, 80, 41, 89, 44, 73, 73, 86, 0, 59, 0, 103, - 81, 95, 7, 7, 97, 0, 0, 0, 36, 36, 36, 36, 36, 36, 60, 102, - 44, 73, 73, 92, 0, 93, 0, 0, 81, 95, 7, 7, 0, 0, 40, 36, - 100, 80, 36, 36, 36, 60, 40, 36, 36, 36, 36, 36, 94, 36, 36, 54, - 36, 60, 104, 93, 44, 105, 44, 44, 0, 0, 0, 0, 100, 0, 0, 0, - 80, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 79, 44, 64, 0, - 36, 66, 44, 64, 7, 7, 106, 0, 97, 76, 43, 54, 0, 36, 80, 36, - 80, 107, 40, 80, 79, 44, 58, 82, 36, 43, 44, 86, 7, 7, 106, 36, - 88, 0, 0, 0, 0, 0, 86, 0, 7, 7, 106, 0, 0, 108, 109, 110, - 36, 36, 80, 36, 36, 36, 36, 36, 36, 36, 36, 88, 57, 44, 44, 44, - 44, 73, 36, 85, 44, 44, 57, 44, 44, 44, 44, 44, 44, 44, 44, 111, - 0, 104, 0, 0, 0, 0, 0, 0, 36, 36, 66, 44, 44, 44, 44, 112, - 7, 7, 113, 0, 36, 81, 74, 81, 89, 72, 44, 74, 85, 69, 36, 36, - 81, 44, 44, 84, 7, 7, 114, 86, 11, 49, 0, 115, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 36, 60, 36, 36, 36, 87, 41, 36, 60, 87, 41, - 36, 36, 87, 41, 36, 36, 36, 36, 36, 36, 36, 36, 87, 41, 36, 60, - 87, 41, 36, 36, 36, 60, 36, 36, 36, 36, 36, 36, 87, 41, 36, 36, - 36, 36, 36, 36, 36, 36, 60, 57, 116, 9, 117, 0, 0, 0, 0, 0, - 36, 36, 36, 36, 0, 0, 0, 0, 36, 36, 36, 36, 36, 88, 0, 0, - 36, 36, 36, 118, 36, 36, 36, 36, 119, 36, 36, 36, 36, 36, 120, 121, - 36, 36, 60, 40, 88, 0, 0, 0, 36, 36, 36, 87, 81, 111, 0, 0, - 36, 36, 36, 36, 81, 122, 0, 0, 36, 36, 36, 36, 81, 0, 0, 0, - 36, 36, 36, 87, 123, 0, 0, 0, 36, 36, 36, 36, 36, 44, 44, 44, - 44, 44, 44, 44, 44, 96, 0, 99, 7, 7, 106, 0, 0, 0, 0, 0, - 124, 0, 125, 126, 7, 7, 106, 0, 36, 36, 36, 36, 36, 36, 0, 0, - 36, 36, 127, 0, 36, 36, 36, 36, 36, 36, 36, 36, 36, 41, 0, 0, - 36, 36, 36, 36, 36, 36, 36, 88, 44, 44, 44, 0, 44, 44, 44, 0, - 0, 90, 7, 7, 36, 36, 36, 36, 36, 36, 36, 41, 36, 88, 0, 0, - 36, 36, 36, 0, 44, 44, 44, 44, 69, 36, 86, 0, 7, 7, 106, 0, - 36, 36, 36, 36, 36, 66, 44, 0, 36, 36, 36, 36, 36, 85, 44, 64, - 44, 44, 44, 44, 44, 44, 44, 91, 7, 7, 106, 0, 7, 7, 106, 0, - 0, 96, 128, 0, 0, 0, 0, 0, 44, 69, 36, 36, 36, 36, 36, 36, - 44, 69, 36, 0, 7, 7, 113, 129, 0, 0, 93, 44, 44, 0, 0, 0, - 112, 36, 36, 36, 36, 36, 36, 36, 85, 44, 44, 74, 7, 7, 75, 36, - 36, 81, 44, 44, 44, 0, 0, 0, 36, 44, 44, 44, 44, 44, 9, 117, - 7, 7, 106, 80, 7, 7, 75, 36, 36, 36, 36, 36, 36, 36, 36, 130, - 0, 0, 0, 0, 64, 44, 44, 44, 44, 44, 69, 79, 81, 131, 0, 0, - 44, 64, 0, 0, 0, 0, 0, 44, 25, 25, 25, 25, 25, 34, 15, 27, - 15, 15, 11, 11, 15, 39, 11, 132, 15, 15, 11, 11, 15, 15, 11, 11, - 15, 39, 11, 132, 15, 15, 133, 133, 15, 15, 11, 11, 15, 15, 15, 39, - 15, 15, 11, 11, 15, 134, 11, 135, 46, 134, 11, 136, 15, 46, 11, 0, - 15, 15, 11, 136, 46, 134, 11, 136, 137, 137, 138, 139, 140, 141, 142, 142, - 0, 143, 144, 145, 0, 0, 146, 147, 0, 148, 147, 0, 0, 0, 0, 149, - 61, 150, 61, 61, 21, 0, 0, 151, 0, 0, 0, 146, 15, 15, 15, 42, - 0, 0, 0, 0, 44, 44, 44, 44, 44, 44, 44, 44, 111, 0, 0, 0, - 47, 152, 153, 154, 23, 115, 10, 132, 0, 155, 48, 156, 11, 38, 157, 33, - 0, 158, 39, 159, 0, 0, 0, 0, 160, 38, 88, 0, 0, 0, 0, 0, - 0, 0, 142, 0, 0, 0, 0, 0, 0, 0, 146, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 161, 11, 11, 15, 15, 39, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 4, 162, 0, 0, 142, 142, 142, 5, 0, 0, - 0, 146, 0, 0, 0, 0, 0, 0, 0, 163, 142, 142, 0, 0, 0, 0, - 4, 142, 142, 142, 142, 142, 121, 0, 0, 0, 0, 0, 0, 0, 142, 0, - 0, 0, 0, 0, 0, 0, 0, 5, 11, 11, 11, 22, 15, 15, 15, 15, - 15, 15, 15, 15, 15, 15, 15, 24, 31, 164, 26, 32, 25, 29, 15, 33, - 25, 42, 152, 165, 53, 0, 0, 0, 15, 166, 0, 21, 36, 36, 36, 36, - 36, 36, 0, 96, 0, 0, 0, 93, 36, 36, 36, 36, 36, 60, 0, 0, - 36, 60, 36, 60, 36, 60, 36, 60, 142, 142, 142, 5, 0, 0, 0, 5, - 142, 142, 5, 167, 0, 0, 0, 0, 168, 80, 142, 142, 5, 142, 142, 169, - 80, 36, 81, 44, 80, 41, 36, 88, 36, 36, 36, 36, 36, 60, 59, 80, - 0, 80, 36, 36, 36, 36, 36, 36, 36, 36, 36, 41, 80, 36, 36, 36, - 36, 36, 36, 60, 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 60, 0, - 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 36, 88, 0, 0, 0, 0, - 36, 36, 36, 36, 36, 36, 36, 170, 36, 36, 36, 171, 36, 36, 36, 36, - 7, 7, 75, 0, 0, 0, 0, 0, 25, 25, 25, 172, 64, 44, 44, 173, - 25, 25, 25, 25, 25, 25, 0, 93, 36, 36, 36, 36, 174, 9, 0, 0, - 0, 0, 0, 0, 0, 96, 36, 36, 175, 25, 25, 25, 27, 25, 25, 25, - 25, 25, 25, 25, 15, 15, 26, 30, 25, 25, 176, 177, 25, 0, 0, 0, - 25, 25, 178, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 179, 36, - 180, 180, 66, 36, 36, 36, 36, 36, 66, 44, 0, 0, 0, 0, 0, 0, - 36, 36, 36, 36, 36, 129, 0, 0, 74, 36, 36, 36, 36, 36, 36, 36, - 44, 111, 0, 129, 7, 7, 106, 0, 44, 44, 44, 44, 74, 36, 96, 0, - 36, 81, 44, 174, 36, 36, 36, 36, 36, 66, 44, 44, 44, 0, 0, 0, - 36, 36, 36, 36, 66, 44, 44, 44, 111, 0, 147, 96, 7, 7, 106, 0, - 36, 36, 85, 44, 44, 64, 0, 0, 66, 36, 36, 86, 7, 7, 106, 181, - 36, 36, 36, 36, 36, 60, 182, 0, 36, 36, 36, 36, 89, 72, 69, 81, - 127, 0, 0, 0, 0, 0, 96, 41, 36, 36, 66, 44, 183, 184, 0, 0, - 80, 60, 80, 60, 80, 60, 0, 0, 36, 60, 36, 60, 0, 0, 0, 0, - 66, 44, 185, 86, 7, 7, 106, 0, 36, 0, 0, 0, 36, 36, 36, 36, - 36, 60, 96, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 0, - 36, 36, 36, 41, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 41, 0, - 15, 24, 0, 0, 186, 15, 0, 187, 36, 36, 87, 36, 36, 60, 36, 43, - 94, 87, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 41, 0, 0, 0, - 0, 0, 0, 0, 96, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 188, - 36, 36, 36, 36, 40, 36, 36, 36, 36, 36, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 36, 36, 36, 0, 44, 44, 44, 44, 189, 4, 121, 0, - 44, 64, 0, 0, 190, 169, 142, 142, 142, 191, 121, 0, 6, 192, 193, 162, - 140, 0, 0, 0, 36, 87, 36, 36, 36, 36, 36, 36, 36, 36, 36, 194, - 56, 0, 5, 6, 0, 0, 195, 9, 14, 15, 15, 15, 15, 15, 16, 196, - 197, 198, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 81, - 36, 36, 36, 36, 36, 36, 36, 60, 40, 36, 40, 36, 40, 36, 40, 88, - 0, 0, 0, 0, 0, 0, 199, 0, 36, 36, 36, 80, 36, 36, 36, 36, - 36, 60, 36, 36, 36, 36, 60, 94, 36, 36, 36, 41, 36, 36, 36, 41, - 0, 0, 0, 0, 0, 0, 0, 98, 36, 36, 36, 36, 88, 0, 0, 0, - 36, 36, 60, 0, 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 36, 41, - 36, 0, 36, 36, 80, 41, 0, 0, 11, 11, 15, 15, 15, 15, 15, 15, - 15, 15, 15, 15, 36, 36, 36, 36, 36, 41, 87, 36, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 94, 88, 76, 36, 36, 36, 36, 36, 36, 0, 40, - 85, 59, 0, 44, 36, 80, 80, 36, 36, 36, 36, 36, 36, 0, 64, 93, - 0, 0, 0, 0, 0, 129, 0, 0, 36, 36, 36, 36, 60, 0, 0, 0, - 36, 36, 88, 0, 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 44, 44, - 44, 185, 117, 0, 0, 0, 0, 0, 36, 36, 36, 36, 44, 44, 64, 200, - 147, 0, 0, 0, 36, 36, 36, 36, 36, 36, 88, 0, 7, 7, 106, 0, - 36, 66, 44, 44, 44, 201, 7, 7, 181, 0, 0, 0, 0, 0, 0, 0, - 69, 202, 0, 0, 7, 7, 106, 0, 36, 36, 66, 44, 44, 44, 0, 0, - 60, 0, 0, 0, 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 88, 0, - 36, 88, 0, 0, 85, 44, 44, 44, 44, 44, 44, 44, 44, 44, 44, 64, - 0, 0, 0, 93, 112, 36, 36, 36, 41, 0, 0, 0, 0, 0, 0, 0, - 0, 57, 86, 57, 203, 61, 204, 44, 64, 57, 44, 0, 0, 0, 0, 0, - 0, 0, 100, 86, 0, 0, 0, 0, 100, 111, 0, 0, 0, 0, 0, 0, - 11, 11, 11, 11, 11, 11, 154, 15, 15, 15, 15, 15, 15, 11, 11, 11, - 11, 11, 11, 154, 15, 134, 15, 15, 15, 15, 11, 11, 11, 11, 11, 11, - 154, 15, 15, 15, 15, 15, 15, 48, 47, 205, 10, 48, 11, 154, 166, 14, - 15, 14, 15, 15, 11, 11, 11, 11, 11, 11, 154, 15, 15, 15, 15, 15, - 15, 49, 22, 10, 11, 48, 11, 206, 15, 15, 15, 15, 15, 15, 49, 22, - 11, 155, 161, 11, 206, 15, 15, 15, 15, 15, 15, 11, 11, 11, 11, 11, - 11, 154, 15, 15, 15, 15, 15, 15, 11, 11, 11, 154, 15, 15, 15, 15, - 154, 15, 15, 15, 15, 15, 15, 11, 11, 11, 11, 11, 11, 154, 15, 15, - 15, 15, 15, 15, 11, 11, 11, 11, 15, 39, 11, 11, 11, 11, 11, 11, - 206, 15, 15, 15, 15, 15, 24, 15, 33, 11, 11, 11, 11, 11, 22, 15, - 15, 15, 15, 15, 15, 134, 15, 11, 11, 11, 11, 11, 11, 206, 15, 15, - 15, 15, 15, 24, 15, 33, 11, 11, 15, 15, 134, 15, 11, 11, 11, 11, - 11, 11, 206, 15, 15, 15, 15, 15, 24, 15, 27, 95, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 36, 80, 36, 36, 36, 36, 36, 36, - 97, 76, 80, 36, 60, 36, 107, 0, 103, 96, 107, 80, 97, 76, 107, 107, - 97, 76, 60, 36, 60, 36, 80, 43, 36, 36, 94, 36, 36, 36, 36, 0, - 80, 80, 94, 36, 36, 36, 36, 0, 20, 0, 0, 0, 0, 0, 0, 0, - 61, 61, 61, 61, 61, 61, 61, 61, 44, 44, 44, 44, 0, 0, 0, 0, -}; - -static RE_UINT8 re_sentence_break_stage_5[] = { - 0, 0, 0, 0, 0, 6, 2, 6, 6, 1, 0, 0, 6, 12, 13, 0, - 0, 0, 0, 13, 13, 13, 0, 0, 14, 14, 11, 0, 10, 10, 10, 10, - 10, 10, 14, 0, 0, 0, 0, 12, 0, 8, 8, 8, 8, 8, 8, 8, - 8, 8, 8, 13, 0, 13, 0, 0, 0, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 13, 0, 4, 0, 0, 6, 0, 0, 0, 0, 0, 7, 13, - 0, 5, 0, 0, 0, 7, 0, 0, 8, 8, 8, 0, 8, 8, 8, 7, - 7, 7, 7, 0, 8, 7, 8, 7, 7, 8, 7, 8, 7, 7, 8, 7, - 8, 8, 7, 8, 7, 8, 7, 7, 7, 8, 8, 7, 8, 7, 8, 8, - 7, 8, 8, 8, 7, 7, 8, 8, 8, 7, 7, 7, 8, 7, 7, 9, - 9, 9, 9, 9, 9, 7, 7, 7, 7, 9, 9, 9, 7, 7, 0, 0, - 0, 0, 9, 9, 9, 9, 0, 0, 7, 0, 0, 0, 9, 0, 9, 0, - 3, 3, 3, 3, 9, 0, 8, 7, 0, 0, 7, 7, 0, 0, 8, 0, - 8, 0, 8, 8, 8, 8, 0, 8, 7, 7, 7, 8, 8, 7, 0, 8, - 8, 7, 0, 3, 3, 3, 8, 7, 0, 9, 0, 0, 12, 14, 12, 0, - 0, 12, 0, 0, 0, 3, 3, 3, 3, 3, 0, 3, 0, 3, 3, 0, - 9, 9, 9, 0, 5, 5, 5, 5, 5, 0, 0, 0, 14, 14, 0, 0, - 3, 3, 3, 0, 5, 0, 0, 12, 9, 9, 9, 3, 10, 10, 0, 10, - 10, 0, 9, 9, 3, 9, 9, 9, 12, 9, 3, 3, 3, 5, 0, 3, - 3, 9, 9, 3, 3, 0, 3, 3, 3, 3, 9, 9, 10, 10, 9, 9, - 9, 0, 0, 9, 12, 12, 12, 0, 0, 0, 0, 5, 9, 3, 9, 9, - 0, 9, 9, 9, 9, 9, 3, 3, 3, 9, 0, 0, 14, 12, 9, 0, - 3, 3, 9, 3, 9, 3, 3, 3, 3, 3, 0, 0, 9, 0, 9, 9, - 9, 0, 0, 0, 3, 9, 3, 3, 12, 12, 10, 10, 3, 0, 0, 3, - 3, 3, 9, 0, 0, 0, 0, 3, 9, 9, 0, 9, 0, 0, 10, 10, - 0, 0, 0, 9, 0, 9, 9, 0, 0, 3, 0, 0, 9, 3, 0, 0, - 0, 0, 3, 3, 0, 0, 3, 9, 0, 9, 3, 3, 0, 0, 9, 0, - 0, 0, 3, 0, 3, 0, 3, 0, 10, 10, 0, 0, 0, 9, 0, 9, - 0, 3, 0, 3, 0, 3, 13, 13, 13, 13, 3, 3, 3, 0, 0, 0, - 3, 3, 3, 9, 10, 10, 12, 12, 10, 10, 3, 3, 0, 8, 0, 0, - 0, 0, 12, 0, 12, 0, 0, 0, 9, 0, 12, 9, 6, 9, 9, 9, - 9, 9, 9, 13, 13, 0, 0, 0, 3, 12, 12, 0, 9, 0, 3, 3, - 0, 0, 14, 12, 14, 12, 0, 3, 3, 3, 5, 0, 9, 3, 9, 0, - 12, 12, 12, 12, 0, 0, 12, 12, 9, 9, 12, 12, 3, 9, 9, 0, - 8, 8, 0, 0, 0, 8, 0, 8, 7, 0, 7, 7, 8, 0, 7, 0, - 8, 0, 0, 0, 6, 6, 6, 6, 6, 6, 6, 5, 3, 3, 5, 5, - 0, 0, 0, 14, 14, 0, 0, 0, 13, 13, 13, 13, 11, 0, 0, 0, - 4, 4, 5, 5, 5, 5, 5, 6, 0, 13, 13, 0, 12, 12, 0, 0, - 0, 13, 13, 12, 0, 0, 0, 6, 5, 0, 5, 5, 0, 13, 13, 7, - 0, 0, 0, 8, 0, 0, 7, 8, 8, 8, 7, 7, 8, 0, 8, 0, - 8, 8, 0, 7, 9, 7, 0, 0, 0, 8, 7, 7, 0, 0, 7, 0, - 9, 9, 9, 8, 0, 0, 8, 8, 13, 13, 13, 0, 0, 0, 13, 13, - 8, 7, 7, 8, 7, 8, 7, 3, 7, 7, 0, 7, 0, 0, 12, 9, - 6, 14, 12, 0, 0, 13, 13, 13, 9, 9, 0, 12, 9, 0, 12, 12, - 8, 7, 9, 3, 3, 3, 0, 9, 3, 3, 0, 12, 0, 0, 8, 7, - 9, 0, 0, 8, 7, 8, 7, 0, 8, 7, 8, 0, 7, 7, 7, 9, - 9, 9, 3, 9, 0, 12, 12, 12, 0, 0, 9, 3, 12, 12, 9, 9, - 9, 3, 3, 0, 3, 3, 3, 12, 0, 0, 0, 7, 0, 9, 3, 9, - 9, 9, 13, 13, 14, 14, 0, 14, 0, 14, 14, 0, 13, 0, 0, 13, - 0, 14, 12, 12, 14, 13, 13, 13, 9, 0, 0, 5, 0, 0, 14, 0, - 0, 13, 0, 13, 13, 12, 13, 13, 14, 0, 9, 9, 0, 5, 5, 5, - 0, 5, 12, 12, 3, 0, 10, 10, 9, 12, 12, 0, 3, 3, 3, 5, - 5, 5, 5, 3, 0, 8, 8, 0, 8, 0, 7, 7, -}; - -/* Sentence_Break: 5596 bytes. */ - -RE_UINT32 re_get_sentence_break(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_sentence_break_stage_1[f] << 4; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_sentence_break_stage_2[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_sentence_break_stage_3[pos + f] << 3; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_sentence_break_stage_4[pos + f] << 2; - value = re_sentence_break_stage_5[pos + code]; - - return value; -} - -/* Math. */ - -static RE_UINT8 re_math_stage_1[] = { - 0, 1, 2, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, -}; - -static RE_UINT8 re_math_stage_2[] = { - 0, 1, 1, 1, 2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, 1, 1, 6, 1, 1, -}; - -static RE_UINT8 re_math_stage_3[] = { - 0, 1, 1, 2, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 4, 5, 6, 7, 1, 8, 9, 10, 1, 6, 6, 11, 1, 1, 1, 1, - 1, 1, 1, 12, 1, 1, 13, 14, 1, 1, 1, 1, 15, 16, 17, 18, - 1, 1, 1, 1, 1, 1, 19, 1, -}; - -static RE_UINT8 re_math_stage_4[] = { - 0, 1, 2, 3, 0, 4, 5, 5, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 6, 7, 8, 0, 0, 0, 0, 0, 0, 0, - 9, 10, 11, 12, 13, 0, 14, 15, 16, 17, 18, 0, 19, 20, 21, 22, - 23, 23, 23, 23, 23, 23, 23, 23, 24, 25, 0, 26, 27, 28, 29, 30, - 0, 0, 0, 0, 0, 31, 32, 33, 34, 0, 35, 36, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 23, 23, 0, 19, 37, 0, 0, 0, 0, 0, - 0, 38, 0, 0, 0, 0, 0, 0, 0, 0, 0, 39, 0, 0, 0, 0, - 1, 3, 3, 0, 0, 0, 0, 40, 23, 23, 41, 23, 42, 43, 44, 23, - 45, 46, 47, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 48, 23, 23, - 23, 23, 23, 23, 23, 23, 49, 23, 44, 50, 51, 52, 53, 54, 0, 55, -}; - -static RE_UINT8 re_math_stage_5[] = { - 0, 0, 0, 0, 0, 8, 0, 112, 0, 0, 0, 64, 0, 0, 0, 80, - 0, 16, 2, 0, 0, 0, 128, 0, 0, 0, 39, 0, 0, 0, 115, 0, - 192, 1, 0, 0, 0, 0, 64, 0, 0, 0, 28, 0, 17, 0, 4, 0, - 30, 0, 0, 124, 0, 124, 0, 0, 0, 0, 255, 31, 98, 248, 0, 0, - 132, 252, 47, 63, 16, 179, 251, 241, 255, 11, 0, 0, 0, 0, 255, 255, - 255, 126, 195, 240, 255, 255, 255, 47, 48, 0, 240, 255, 255, 255, 255, 255, - 0, 15, 0, 0, 3, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, 248, - 255, 255, 191, 0, 0, 0, 1, 240, 7, 0, 0, 0, 3, 192, 255, 240, - 195, 140, 15, 0, 148, 31, 0, 255, 96, 0, 0, 0, 5, 0, 0, 0, - 15, 224, 0, 0, 159, 31, 0, 0, 0, 2, 0, 0, 126, 1, 0, 0, - 4, 30, 0, 0, 255, 255, 223, 255, 255, 255, 255, 223, 100, 222, 255, 235, - 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, 95, 252, 253, 255, - 63, 255, 255, 255, 255, 207, 255, 255, 150, 254, 247, 10, 132, 234, 150, 170, - 150, 247, 247, 94, 255, 251, 255, 15, 238, 251, 255, 15, 0, 0, 3, 0, -}; - -/* Math: 538 bytes. */ - -RE_UINT32 re_get_math(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_math_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_math_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_math_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_math_stage_4[pos + f] << 5; - pos += code; - value = (re_math_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Alphabetic. */ - -static RE_UINT8 re_alphabetic_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, -}; - -static RE_UINT8 re_alphabetic_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_alphabetic_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 33, 34, 35, 31, - 36, 37, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 38, 1, 1, 1, 1, 1, 1, 1, 1, 1, 39, - 1, 1, 1, 1, 40, 1, 41, 42, 43, 44, 45, 46, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 47, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 48, 49, 1, 50, 51, 52, 53, 54, 55, 56, 57, 31, 31, 31, - 58, 59, 60, 61, 62, 31, 31, 31, 63, 64, 31, 31, 31, 31, 65, 31, - 1, 1, 1, 66, 67, 31, 31, 31, 1, 1, 1, 1, 68, 31, 31, 31, - 1, 1, 69, 31, 31, 31, 31, 70, 71, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 72, 73, 74, 75, 31, 31, 31, 31, 31, 31, 76, 31, - 1, 1, 1, 1, 1, 1, 77, 1, 1, 1, 1, 1, 1, 1, 1, 78, - 79, 31, 31, 31, 31, 31, 31, 31, 1, 1, 79, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_alphabetic_stage_4[] = { - 0, 0, 1, 1, 0, 2, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 5, 6, 0, 0, 7, 8, 9, 10, 4, 11, - 4, 4, 4, 4, 12, 4, 4, 4, 4, 13, 14, 15, 16, 17, 18, 19, - 20, 4, 21, 22, 4, 4, 23, 24, 25, 4, 26, 4, 4, 27, 28, 29, - 30, 31, 32, 0, 0, 33, 0, 34, 4, 35, 36, 37, 38, 39, 40, 41, - 42, 43, 44, 45, 46, 47, 48, 49, 38, 47, 50, 51, 52, 53, 54, 0, - 55, 56, 57, 49, 58, 56, 59, 60, 58, 61, 62, 63, 64, 65, 66, 67, - 15, 68, 69, 0, 70, 71, 72, 0, 73, 0, 74, 75, 76, 77, 0, 0, - 4, 78, 25, 79, 80, 4, 81, 82, 4, 4, 83, 4, 84, 85, 86, 4, - 87, 4, 88, 0, 89, 4, 4, 90, 15, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 91, 1, 4, 4, 92, 93, 94, 94, 95, 4, 96, 97, 0, - 0, 4, 4, 98, 4, 99, 4, 100, 77, 101, 25, 102, 4, 103, 104, 0, - 105, 4, 106, 107, 0, 108, 0, 0, 4, 109, 110, 0, 4, 111, 4, 112, - 4, 100, 113, 114, 0, 0, 0, 115, 4, 4, 4, 4, 4, 4, 0, 0, - 116, 4, 117, 114, 4, 118, 119, 120, 0, 0, 0, 121, 122, 0, 0, 0, - 123, 124, 125, 4, 126, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 127, 4, 104, 4, 128, 106, 4, 4, 4, 4, 129, - 4, 81, 4, 130, 131, 132, 132, 4, 0, 133, 0, 0, 0, 0, 0, 0, - 134, 135, 15, 4, 136, 15, 4, 82, 137, 138, 4, 4, 139, 68, 0, 25, - 4, 4, 4, 4, 4, 100, 0, 0, 4, 4, 4, 4, 4, 4, 31, 0, - 4, 4, 4, 4, 31, 0, 25, 114, 140, 141, 4, 142, 143, 4, 4, 89, - 144, 145, 4, 4, 146, 147, 0, 148, 149, 16, 4, 94, 4, 4, 49, 150, - 28, 99, 151, 77, 4, 152, 133, 0, 4, 131, 153, 154, 4, 106, 155, 156, - 157, 158, 0, 0, 0, 0, 4, 147, 4, 4, 4, 4, 4, 159, 160, 105, - 4, 4, 4, 161, 4, 4, 162, 0, 163, 164, 165, 4, 4, 27, 166, 4, - 4, 114, 25, 4, 167, 4, 16, 168, 0, 0, 0, 169, 4, 4, 4, 77, - 0, 1, 1, 170, 4, 106, 171, 0, 172, 173, 174, 0, 4, 4, 4, 68, - 0, 0, 4, 90, 0, 0, 0, 0, 0, 0, 0, 0, 77, 4, 175, 0, - 106, 25, 147, 0, 114, 4, 176, 0, 4, 4, 4, 4, 114, 0, 0, 0, - 177, 178, 100, 0, 0, 0, 0, 0, 100, 162, 0, 0, 4, 179, 0, 0, - 180, 94, 0, 77, 0, 0, 0, 0, 4, 100, 100, 151, 0, 0, 0, 0, - 4, 4, 126, 0, 0, 0, 0, 0, 4, 4, 181, 0, 145, 32, 25, 126, - 4, 151, 0, 0, 4, 4, 182, 0, 0, 0, 0, 0, 4, 100, 0, 0, - 4, 4, 4, 139, 0, 0, 0, 0, 4, 4, 4, 183, 0, 0, 0, 0, - 4, 139, 0, 0, 0, 0, 0, 0, 4, 32, 0, 0, 0, 0, 0, 0, - 4, 4, 184, 106, 166, 0, 0, 0, 185, 0, 0, 0, 0, 0, 0, 0, - 4, 4, 186, 4, 187, 188, 189, 4, 190, 191, 192, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 193, 194, 82, 186, 186, 128, 128, 195, 195, 196, 0, - 189, 197, 198, 199, 200, 201, 0, 0, 4, 4, 4, 4, 4, 4, 131, 0, - 4, 90, 4, 4, 4, 4, 4, 4, 114, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_alphabetic_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 4, 32, 4, 255, 255, 127, 255, - 255, 255, 255, 255, 195, 255, 3, 0, 31, 80, 0, 0, 32, 0, 0, 0, - 0, 0, 223, 60, 64, 215, 255, 255, 251, 255, 255, 255, 255, 255, 191, 255, - 3, 252, 255, 255, 255, 0, 254, 255, 255, 255, 127, 2, 254, 255, 255, 255, - 255, 0, 0, 0, 0, 0, 255, 191, 182, 0, 255, 255, 255, 7, 7, 0, - 0, 0, 255, 7, 255, 255, 255, 254, 0, 192, 255, 255, 255, 255, 239, 31, - 254, 225, 0, 156, 0, 0, 255, 255, 0, 224, 255, 255, 255, 255, 3, 0, - 0, 252, 255, 255, 255, 7, 48, 4, 255, 255, 255, 252, 255, 31, 0, 0, - 255, 255, 255, 1, 253, 31, 0, 0, 240, 3, 255, 127, 255, 255, 255, 239, - 255, 223, 225, 255, 15, 0, 254, 254, 238, 159, 249, 255, 255, 253, 197, 227, - 159, 89, 128, 176, 15, 0, 3, 0, 238, 135, 249, 255, 255, 253, 109, 195, - 135, 25, 2, 94, 0, 0, 63, 0, 238, 191, 251, 255, 255, 253, 237, 227, - 191, 27, 1, 0, 15, 0, 0, 0, 159, 25, 192, 176, 15, 0, 2, 0, - 236, 199, 61, 214, 24, 199, 255, 195, 199, 29, 129, 0, 238, 223, 253, 255, - 255, 253, 239, 227, 223, 29, 96, 3, 236, 223, 253, 255, 223, 29, 96, 64, - 15, 0, 6, 0, 255, 255, 255, 231, 223, 93, 128, 0, 15, 0, 0, 252, - 236, 255, 127, 252, 255, 255, 251, 47, 127, 128, 95, 255, 0, 0, 12, 0, - 255, 255, 255, 7, 127, 32, 0, 0, 150, 37, 240, 254, 174, 236, 255, 59, - 95, 32, 0, 240, 1, 0, 0, 0, 255, 254, 255, 255, 255, 31, 254, 255, - 3, 255, 255, 254, 255, 255, 255, 31, 255, 255, 127, 249, 231, 193, 255, 255, - 127, 64, 0, 48, 191, 32, 255, 255, 255, 255, 255, 247, 255, 61, 127, 61, - 255, 61, 255, 255, 255, 255, 61, 127, 61, 255, 127, 255, 255, 255, 61, 255, - 255, 255, 255, 135, 255, 255, 0, 0, 255, 255, 31, 0, 255, 159, 255, 255, - 255, 199, 1, 0, 255, 223, 15, 0, 255, 255, 15, 0, 255, 223, 13, 0, - 255, 255, 207, 255, 255, 1, 128, 16, 255, 255, 255, 0, 255, 7, 255, 255, - 255, 255, 63, 0, 255, 15, 255, 1, 255, 63, 31, 0, 255, 15, 255, 255, - 255, 3, 0, 0, 255, 255, 255, 15, 255, 255, 255, 127, 254, 255, 31, 0, - 128, 0, 0, 0, 255, 255, 239, 255, 239, 15, 0, 0, 255, 243, 0, 252, - 191, 255, 3, 0, 0, 224, 0, 252, 255, 255, 255, 63, 0, 222, 111, 0, - 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 95, 220, 31, 207, 15, - 255, 31, 220, 31, 0, 0, 2, 128, 0, 0, 255, 31, 132, 252, 47, 62, - 80, 189, 255, 243, 224, 67, 0, 0, 255, 1, 0, 0, 0, 0, 192, 255, - 255, 127, 255, 255, 31, 120, 12, 0, 255, 128, 0, 0, 255, 255, 127, 0, - 127, 127, 127, 127, 0, 128, 0, 0, 224, 0, 0, 0, 254, 3, 62, 31, - 255, 255, 127, 224, 224, 255, 255, 255, 255, 63, 254, 255, 255, 127, 0, 0, - 255, 31, 255, 255, 0, 12, 0, 0, 255, 127, 240, 143, 255, 255, 255, 128, - 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 255, 187, 247, 255, 255, 0, 0, 252, 8, 255, 255, 7, 0, - 255, 255, 247, 255, 255, 63, 0, 0, 255, 255, 127, 4, 5, 0, 0, 56, - 255, 255, 60, 0, 126, 126, 126, 0, 127, 127, 0, 0, 15, 0, 255, 255, - 127, 248, 255, 255, 255, 63, 255, 255, 255, 255, 255, 3, 127, 0, 248, 224, - 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, 255, 255, 252, 255, - 0, 0, 255, 15, 0, 0, 223, 255, 192, 255, 255, 255, 252, 252, 252, 28, - 255, 239, 255, 255, 127, 255, 255, 183, 255, 63, 255, 63, 255, 255, 1, 0, - 15, 255, 62, 0, 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 255, 192, - 111, 240, 239, 254, 63, 0, 0, 0, 30, 0, 0, 0, 7, 0, 0, 0, - 31, 0, 255, 255, 3, 0, 0, 0, 255, 255, 223, 255, 255, 255, 255, 223, - 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, - 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, 255, 253, 255, 255, - 247, 15, 0, 0, 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, - 255, 251, 255, 15, 238, 251, 255, 15, -}; - -/* Alphabetic: 1817 bytes. */ - -RE_UINT32 re_get_alphabetic(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_alphabetic_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_alphabetic_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_alphabetic_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_alphabetic_stage_4[pos + f] << 5; - pos += code; - value = (re_alphabetic_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Lowercase. */ - -static RE_UINT8 re_lowercase_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_lowercase_stage_2[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 5, - 6, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 7, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_lowercase_stage_3[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 5, - 6, 3, 7, 3, 3, 3, 8, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 9, 3, 3, 3, 3, 3, 3, 3, 3, 3, 10, 3, 11, - 3, 3, 12, 3, 3, 3, 3, 3, 3, 3, 13, 14, 3, 3, 3, 3, -}; - -static RE_UINT8 re_lowercase_stage_4[] = { - 0, 0, 0, 1, 0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, - 5, 13, 14, 15, 16, 17, 18, 19, 0, 0, 20, 21, 22, 23, 24, 25, - 0, 26, 15, 5, 27, 5, 28, 5, 5, 29, 0, 30, 31, 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, 15, 15, 15, 15, 15, 15, 0, 0, - 5, 5, 5, 5, 32, 5, 5, 5, 33, 34, 35, 36, 34, 37, 38, 39, - 0, 0, 0, 40, 41, 0, 0, 0, 42, 43, 44, 26, 45, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 26, 46, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 26, 47, 48, 5, 5, 5, 49, 15, 50, 0, 0, 0, 0, 0, 0, - 0, 0, 5, 51, 52, 0, 0, 0, 0, 53, 5, 54, 55, 56, 0, 57, - 0, 0, 0, 0, 0, 0, 0, 0, 58, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 59, 60, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 61, 62, 63, 31, 64, 65, 66, 67, 68, 69, 70, 71, 72, 61, 62, 73, - 31, 64, 74, 60, 67, 75, 76, 77, 78, 74, 79, 26, 80, 67, 81, 0, -}; - -static RE_UINT8 re_lowercase_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 4, 32, 4, 0, 0, 0, 128, - 255, 255, 127, 255, 170, 170, 170, 170, 170, 170, 170, 85, 85, 171, 170, 170, - 170, 170, 170, 212, 41, 49, 36, 78, 42, 45, 81, 230, 64, 82, 85, 181, - 170, 170, 41, 170, 170, 170, 250, 147, 133, 170, 255, 255, 255, 255, 255, 255, - 255, 255, 239, 255, 255, 255, 255, 1, 3, 0, 0, 0, 31, 0, 0, 0, - 32, 0, 0, 0, 0, 0, 138, 60, 0, 0, 1, 0, 0, 240, 255, 255, - 255, 127, 227, 170, 170, 170, 47, 25, 0, 0, 255, 255, 2, 168, 170, 170, - 84, 213, 170, 170, 170, 0, 0, 0, 254, 255, 255, 255, 255, 0, 0, 0, - 170, 170, 234, 191, 255, 0, 63, 0, 255, 0, 255, 0, 63, 0, 255, 0, - 255, 0, 255, 63, 255, 0, 223, 64, 220, 0, 207, 0, 255, 0, 220, 0, - 0, 0, 2, 128, 0, 0, 255, 31, 0, 196, 8, 0, 0, 128, 16, 50, - 192, 67, 0, 0, 16, 0, 0, 0, 255, 3, 0, 0, 255, 255, 255, 127, - 98, 21, 218, 63, 26, 80, 8, 0, 191, 32, 0, 0, 170, 42, 0, 0, - 170, 170, 170, 0, 168, 170, 171, 170, 170, 170, 255, 149, 170, 80, 10, 0, - 170, 2, 0, 0, 0, 0, 0, 7, 127, 0, 248, 0, 0, 255, 255, 255, - 255, 255, 0, 0, 0, 0, 0, 252, 255, 255, 15, 0, 0, 192, 223, 255, - 252, 255, 255, 15, 0, 0, 192, 235, 239, 255, 0, 0, 0, 252, 255, 255, - 15, 0, 0, 192, 255, 255, 255, 0, 0, 0, 252, 255, 255, 15, 0, 0, - 192, 255, 255, 255, 0, 192, 255, 255, 0, 0, 192, 255, 63, 0, 0, 0, - 252, 255, 255, 247, 3, 0, 0, 240, 255, 255, 223, 15, 255, 127, 63, 0, - 255, 253, 0, 0, 247, 11, 0, 0, -}; - -/* Lowercase: 697 bytes. */ - -RE_UINT32 re_get_lowercase(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_lowercase_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_lowercase_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_lowercase_stage_3[pos + f] << 4; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_lowercase_stage_4[pos + f] << 5; - pos += code; - value = (re_lowercase_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Uppercase. */ - -static RE_UINT8 re_uppercase_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_uppercase_stage_2[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 5, - 6, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 7, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_uppercase_stage_3[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 3, 3, 5, - 6, 3, 7, 3, 3, 3, 8, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 9, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 10, - 3, 3, 11, 3, 3, 3, 3, 3, 3, 3, 12, 13, 3, 3, 3, 3, -}; - -static RE_UINT8 re_uppercase_stage_4[] = { - 0, 0, 1, 0, 0, 0, 2, 0, 3, 4, 5, 6, 7, 8, 9, 10, - 3, 11, 12, 0, 0, 0, 0, 0, 0, 0, 0, 13, 14, 15, 16, 17, - 18, 19, 0, 3, 20, 3, 21, 3, 3, 22, 23, 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, 18, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 3, 3, 3, 3, 25, 3, 3, 3, 26, 27, 28, 29, 0, 30, 31, 32, - 0, 0, 0, 0, 0, 0, 0, 0, 33, 34, 35, 19, 36, 0, 0, 0, - 0, 0, 0, 0, 0, 37, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 18, 38, 0, 39, 3, 3, 3, 40, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 41, 42, 0, 0, 0, 0, 43, 3, 44, 45, 46, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, - 18, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 48, 49, 50, - 51, 61, 62, 54, 55, 51, 63, 64, 65, 66, 37, 38, 54, 67, 68, 0, -}; - -static RE_UINT8 re_uppercase_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 255, 255, 127, 127, 85, 85, 85, 85, - 85, 85, 85, 170, 170, 84, 85, 85, 85, 85, 85, 43, 214, 206, 219, 177, - 213, 210, 174, 17, 144, 164, 170, 74, 85, 85, 210, 85, 85, 85, 5, 108, - 122, 85, 0, 0, 0, 0, 69, 0, 64, 215, 254, 255, 251, 15, 0, 0, - 0, 128, 28, 85, 85, 85, 144, 230, 255, 255, 255, 255, 255, 255, 0, 0, - 1, 84, 85, 85, 171, 42, 85, 85, 85, 0, 254, 255, 255, 255, 127, 0, - 191, 32, 0, 0, 85, 85, 21, 64, 0, 255, 0, 63, 0, 255, 0, 255, - 0, 63, 0, 170, 0, 255, 0, 0, 0, 0, 0, 15, 0, 15, 0, 15, - 0, 31, 0, 15, 132, 56, 39, 62, 80, 61, 15, 192, 32, 0, 0, 0, - 8, 0, 0, 0, 0, 0, 192, 255, 255, 127, 0, 0, 157, 234, 37, 192, - 5, 40, 4, 0, 85, 21, 0, 0, 85, 85, 85, 0, 84, 85, 84, 85, - 85, 85, 0, 106, 85, 40, 5, 0, 85, 5, 0, 0, 255, 0, 0, 0, - 255, 255, 255, 3, 0, 0, 240, 255, 255, 63, 0, 0, 0, 255, 255, 255, - 3, 0, 0, 208, 100, 222, 63, 0, 0, 0, 255, 255, 255, 3, 0, 0, - 176, 231, 223, 31, 0, 0, 0, 123, 95, 252, 1, 0, 0, 240, 255, 255, - 63, 0, 0, 0, 3, 0, 0, 240, 255, 255, 63, 0, 1, 0, 0, 0, - 252, 255, 255, 7, 0, 0, 0, 240, 255, 255, 31, 0, 255, 1, 0, 0, - 0, 4, 0, 0, -}; - -/* Uppercase: 629 bytes. */ - -RE_UINT32 re_get_uppercase(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_uppercase_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_uppercase_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_uppercase_stage_3[pos + f] << 4; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_uppercase_stage_4[pos + f] << 5; - pos += code; - value = (re_uppercase_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Cased. */ - -static RE_UINT8 re_cased_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_cased_stage_2[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 5, - 6, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 7, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_cased_stage_3[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 3, 5, 6, - 7, 3, 8, 3, 3, 3, 9, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 10, 3, 3, 3, 3, 3, 3, 3, 3, 3, 11, 3, 12, - 3, 3, 13, 3, 3, 3, 3, 3, 3, 3, 14, 15, 3, 3, 3, 3, -}; - -static RE_UINT8 re_cased_stage_4[] = { - 0, 0, 1, 1, 0, 2, 3, 3, 4, 4, 4, 4, 4, 5, 6, 4, - 4, 4, 4, 4, 7, 8, 9, 10, 0, 0, 11, 12, 13, 14, 4, 15, - 4, 4, 4, 4, 16, 4, 4, 4, 4, 17, 18, 19, 20, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 4, 4, 4, 4, 4, 4, 0, 0, - 4, 4, 4, 4, 4, 4, 4, 4, 22, 4, 23, 24, 4, 25, 26, 27, - 0, 0, 0, 28, 29, 0, 0, 0, 30, 31, 32, 4, 33, 0, 0, 0, - 0, 0, 0, 0, 0, 34, 4, 35, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 36, 37, 4, 4, 4, 4, 38, 4, 21, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 39, 40, 0, 0, 0, 0, 41, 4, 4, 42, 43, 0, 44, - 0, 0, 0, 0, 0, 0, 0, 0, 45, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, - 4, 4, 46, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 4, 47, 4, 48, 49, 50, 4, 51, 52, 53, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 54, 55, 5, 47, 47, 36, 36, 56, 56, 57, 0, -}; - -static RE_UINT8 re_cased_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 4, 32, 4, 255, 255, 127, 255, - 255, 255, 255, 255, 255, 255, 255, 247, 240, 255, 255, 255, 255, 255, 239, 255, - 255, 255, 255, 1, 3, 0, 0, 0, 31, 0, 0, 0, 32, 0, 0, 0, - 0, 0, 207, 60, 64, 215, 255, 255, 251, 255, 255, 255, 255, 255, 191, 255, - 3, 252, 255, 255, 255, 0, 254, 255, 255, 255, 127, 0, 254, 255, 255, 255, - 255, 0, 0, 0, 191, 32, 0, 0, 255, 255, 63, 63, 63, 63, 255, 170, - 255, 255, 255, 63, 255, 255, 223, 95, 220, 31, 207, 15, 255, 31, 220, 31, - 0, 0, 2, 128, 0, 0, 255, 31, 132, 252, 47, 62, 80, 189, 31, 242, - 224, 67, 0, 0, 24, 0, 0, 0, 0, 0, 192, 255, 255, 3, 0, 0, - 255, 127, 255, 255, 255, 255, 255, 127, 31, 120, 12, 0, 255, 63, 0, 0, - 255, 255, 255, 0, 252, 255, 255, 255, 255, 120, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 7, 127, 0, 248, 0, 255, 255, 0, 0, 255, 255, 223, 255, - 255, 255, 255, 223, 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, - 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, - 255, 253, 255, 255, 247, 15, 0, 0, -}; - -/* Cased: 617 bytes. */ - -RE_UINT32 re_get_cased(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_cased_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_cased_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_cased_stage_3[pos + f] << 4; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_cased_stage_4[pos + f] << 5; - pos += code; - value = (re_cased_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Case_Ignorable. */ - -static RE_UINT8 re_case_ignorable_stage_1[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, 4, 4, 4, - 4, 4, -}; - -static RE_UINT8 re_case_ignorable_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 8, 9, 7, 7, 7, 7, 7, 7, 7, 7, 7, 10, - 11, 12, 13, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 14, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 15, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 16, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, -}; - -static RE_UINT8 re_case_ignorable_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 1, 17, 1, 1, 1, 18, 19, 20, 21, 22, 23, 24, 1, 25, - 26, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 27, 28, 29, 1, - 30, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 31, 1, 1, 1, 32, 1, 33, 34, 35, 36, 37, 38, 1, 1, 1, 1, - 1, 1, 1, 39, 1, 1, 40, 41, 1, 42, 1, 1, 1, 1, 1, 1, - 1, 1, 43, 1, 1, 1, 1, 1, 44, 45, 1, 1, 1, 1, 46, 1, - 1, 1, 1, 1, 1, 1, 1, 47, 1, 48, 49, 1, 1, 1, 1, 1, - 50, 51, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_case_ignorable_stage_4[] = { - 0, 1, 2, 3, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 5, 6, 6, 6, 6, 6, 7, 8, 0, 0, 0, - 0, 0, 0, 0, 9, 0, 0, 0, 0, 0, 10, 0, 11, 12, 13, 14, - 15, 0, 16, 17, 0, 0, 18, 19, 20, 5, 21, 0, 0, 22, 0, 23, - 24, 25, 26, 0, 0, 0, 0, 27, 28, 29, 30, 31, 32, 33, 34, 35, - 36, 33, 37, 38, 36, 33, 39, 35, 32, 40, 41, 35, 42, 0, 43, 0, - 0, 44, 45, 35, 0, 40, 46, 35, 0, 0, 34, 35, 0, 0, 47, 0, - 0, 48, 49, 0, 0, 50, 51, 0, 52, 53, 0, 54, 55, 56, 57, 0, - 0, 58, 59, 60, 61, 0, 0, 33, 0, 0, 62, 0, 0, 0, 0, 0, - 63, 63, 64, 64, 0, 65, 66, 0, 67, 0, 68, 0, 0, 69, 0, 0, - 0, 70, 0, 0, 0, 0, 0, 0, 71, 0, 72, 73, 0, 74, 0, 0, - 75, 76, 42, 77, 78, 79, 0, 80, 0, 81, 0, 82, 0, 0, 83, 84, - 0, 85, 6, 86, 87, 6, 6, 88, 0, 0, 0, 0, 0, 89, 90, 91, - 92, 93, 0, 94, 95, 0, 5, 96, 0, 0, 0, 97, 0, 0, 0, 98, - 0, 0, 0, 99, 0, 0, 0, 6, 0, 100, 0, 0, 0, 0, 0, 0, - 101, 102, 0, 0, 103, 0, 0, 104, 105, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 82, 106, 0, 0, 107, 108, 0, 0, 109, - 6, 78, 0, 17, 110, 0, 0, 52, 111, 112, 0, 0, 0, 0, 113, 114, - 0, 115, 116, 0, 28, 117, 100, 0, 0, 118, 119, 17, 0, 120, 121, 122, - 0, 0, 0, 0, 0, 0, 0, 123, 2, 0, 0, 0, 0, 124, 78, 0, - 125, 126, 127, 0, 0, 0, 0, 108, 1, 2, 3, 17, 44, 0, 0, 128, - 0, 0, 0, 0, 0, 0, 0, 129, 130, 131, 0, 0, 0, 0, 0, 0, - 32, 132, 126, 0, 78, 133, 0, 0, 28, 134, 0, 0, 78, 135, 0, 0, - 0, 0, 0, 0, 0, 136, 0, 0, 0, 0, 0, 0, 137, 0, 0, 0, - 0, 0, 0, 138, 139, 140, 0, 0, 0, 0, 141, 0, 0, 0, 0, 0, - 32, 6, 6, 6, 0, 0, 0, 0, 6, 6, 6, 6, 6, 6, 6, 142, -}; - -static RE_UINT8 re_case_ignorable_stage_5[] = { - 0, 0, 0, 0, 128, 64, 0, 4, 0, 0, 0, 64, 1, 0, 0, 0, - 0, 161, 144, 1, 0, 0, 255, 255, 255, 255, 255, 255, 255, 255, 48, 4, - 176, 0, 0, 0, 248, 3, 0, 0, 0, 0, 0, 2, 0, 0, 254, 255, - 255, 255, 255, 191, 182, 0, 0, 0, 0, 0, 16, 0, 31, 0, 255, 23, - 1, 248, 255, 255, 0, 0, 1, 0, 0, 0, 192, 191, 255, 61, 0, 0, - 0, 128, 2, 0, 255, 7, 0, 0, 192, 255, 1, 0, 0, 248, 63, 4, - 0, 0, 192, 255, 255, 63, 0, 0, 0, 0, 0, 14, 240, 255, 255, 127, - 7, 0, 0, 0, 0, 0, 0, 20, 254, 33, 254, 0, 12, 0, 2, 0, - 2, 0, 0, 0, 0, 0, 0, 16, 30, 32, 0, 0, 12, 0, 0, 0, - 6, 0, 0, 0, 134, 57, 2, 0, 0, 0, 35, 0, 190, 33, 0, 0, - 0, 0, 0, 144, 30, 32, 64, 0, 4, 0, 0, 0, 1, 32, 0, 0, - 0, 0, 0, 192, 193, 61, 96, 0, 64, 48, 0, 0, 0, 4, 92, 0, - 0, 0, 242, 7, 192, 127, 0, 0, 0, 0, 242, 27, 64, 63, 0, 0, - 0, 0, 0, 3, 0, 0, 160, 2, 0, 0, 254, 127, 223, 224, 255, 254, - 255, 255, 255, 31, 64, 0, 0, 0, 0, 224, 253, 102, 0, 0, 0, 195, - 1, 0, 30, 0, 100, 32, 0, 32, 0, 0, 0, 224, 0, 0, 28, 0, - 0, 0, 12, 0, 0, 0, 176, 63, 64, 254, 143, 32, 0, 120, 0, 0, - 8, 0, 0, 0, 0, 2, 0, 0, 135, 1, 4, 14, 0, 0, 128, 9, - 0, 0, 64, 127, 229, 31, 248, 159, 128, 0, 0, 0, 15, 0, 0, 0, - 0, 0, 208, 23, 0, 248, 15, 0, 3, 0, 0, 0, 60, 11, 0, 0, - 64, 163, 3, 0, 0, 240, 207, 0, 0, 0, 0, 63, 0, 0, 247, 255, - 253, 33, 16, 0, 0, 240, 255, 255, 255, 7, 0, 1, 0, 0, 0, 248, - 127, 0, 0, 240, 0, 0, 0, 160, 3, 224, 0, 224, 0, 224, 0, 96, - 0, 248, 0, 3, 144, 124, 0, 0, 223, 255, 2, 128, 0, 0, 255, 31, - 255, 255, 1, 0, 0, 0, 0, 48, 0, 128, 3, 0, 0, 128, 0, 128, - 0, 128, 0, 0, 32, 0, 0, 0, 0, 60, 62, 8, 0, 0, 0, 126, - 0, 0, 0, 112, 0, 0, 32, 0, 0, 16, 0, 0, 0, 128, 247, 191, - 0, 0, 0, 128, 0, 0, 3, 0, 0, 7, 0, 0, 68, 8, 0, 0, - 96, 0, 0, 0, 16, 0, 0, 0, 255, 255, 3, 0, 192, 63, 0, 0, - 128, 255, 3, 0, 0, 0, 200, 19, 0, 126, 102, 0, 8, 16, 0, 0, - 0, 0, 157, 193, 2, 0, 0, 32, 0, 48, 88, 0, 32, 33, 0, 0, - 0, 0, 252, 255, 255, 255, 8, 0, 127, 0, 0, 0, 0, 0, 36, 0, - 8, 0, 0, 14, 0, 0, 0, 32, 110, 240, 0, 0, 0, 0, 0, 135, - 0, 0, 0, 255, 0, 0, 120, 38, 128, 239, 31, 0, 0, 0, 192, 127, - 0, 40, 191, 0, 0, 128, 255, 255, 128, 3, 248, 255, 231, 15, 0, 0, - 0, 60, 0, 0, 28, 0, 0, 0, 255, 255, 0, 0, -}; - -/* Case_Ignorable: 1254 bytes. */ - -RE_UINT32 re_get_case_ignorable(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_case_ignorable_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_case_ignorable_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_case_ignorable_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_case_ignorable_stage_4[pos + f] << 5; - pos += code; - value = (re_case_ignorable_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Changes_When_Lowercased. */ - -static RE_UINT8 re_changes_when_lowercased_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_changes_when_lowercased_stage_2[] = { - 0, 1, 2, 3, 4, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 6, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, - 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_changes_when_lowercased_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, - 6, 10, 6, 6, 11, 6, 6, 6, 6, 6, 6, 6, 12, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, 6, 6, 6, 6, 6, 15, - 6, 6, 6, 6, 16, 6, 6, 6, -}; - -static RE_UINT8 re_changes_when_lowercased_stage_4[] = { - 0, 0, 1, 0, 0, 0, 2, 0, 3, 4, 5, 6, 7, 8, 9, 10, - 3, 11, 12, 0, 0, 0, 0, 0, 0, 0, 0, 13, 14, 15, 16, 17, - 18, 19, 0, 3, 20, 3, 21, 3, 3, 22, 23, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 24, 0, - 3, 3, 3, 3, 25, 3, 3, 3, 26, 27, 28, 29, 27, 30, 31, 32, - 0, 33, 0, 19, 34, 0, 0, 0, 0, 0, 0, 0, 0, 35, 19, 0, - 18, 36, 0, 37, 3, 3, 3, 38, 0, 0, 3, 39, 40, 0, 0, 0, - 0, 41, 3, 42, 43, 44, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, - 18, 45, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_changes_when_lowercased_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 255, 255, 127, 127, 85, 85, 85, 85, - 85, 85, 85, 170, 170, 84, 85, 85, 85, 85, 85, 43, 214, 206, 219, 177, - 213, 210, 174, 17, 176, 173, 170, 74, 85, 85, 214, 85, 85, 85, 5, 108, - 122, 85, 0, 0, 0, 0, 69, 0, 64, 215, 254, 255, 251, 15, 0, 0, - 0, 128, 0, 85, 85, 85, 144, 230, 255, 255, 255, 255, 255, 255, 0, 0, - 1, 84, 85, 85, 171, 42, 85, 85, 85, 0, 254, 255, 255, 255, 127, 0, - 191, 32, 0, 0, 85, 85, 21, 64, 0, 255, 0, 63, 0, 255, 0, 255, - 0, 63, 0, 170, 0, 255, 0, 0, 0, 255, 0, 31, 0, 31, 0, 15, - 0, 31, 0, 31, 64, 12, 4, 0, 8, 0, 0, 0, 0, 0, 192, 255, - 255, 127, 0, 0, 157, 234, 37, 192, 5, 40, 4, 0, 85, 21, 0, 0, - 85, 85, 85, 0, 84, 85, 84, 85, 85, 85, 0, 106, 85, 40, 5, 0, - 85, 5, 0, 0, 255, 0, 0, 0, -}; - -/* Changes_When_Lowercased: 490 bytes. */ - -RE_UINT32 re_get_changes_when_lowercased(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_changes_when_lowercased_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_changes_when_lowercased_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_changes_when_lowercased_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_changes_when_lowercased_stage_4[pos + f] << 5; - pos += code; - value = (re_changes_when_lowercased_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Changes_When_Uppercased. */ - -static RE_UINT8 re_changes_when_uppercased_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_changes_when_uppercased_stage_2[] = { - 0, 1, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 6, - 7, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_changes_when_uppercased_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 7, 8, 9, 6, 10, 6, 6, 11, 6, 6, 6, - 6, 6, 6, 6, 12, 13, 6, 6, 6, 6, 6, 6, 6, 6, 14, 15, - 6, 6, 6, 16, 6, 6, 6, 17, 6, 6, 6, 6, 18, 6, 6, 6, -}; - -static RE_UINT8 re_changes_when_uppercased_stage_4[] = { - 0, 0, 0, 1, 0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, - 5, 13, 14, 15, 16, 0, 0, 0, 0, 0, 17, 18, 19, 20, 21, 22, - 0, 23, 24, 5, 25, 5, 26, 5, 5, 27, 0, 28, 29, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 30, 0, 0, 0, 0, - 5, 5, 5, 5, 31, 5, 5, 5, 32, 33, 34, 35, 24, 36, 37, 38, - 0, 0, 39, 23, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 41, - 0, 23, 42, 43, 5, 5, 5, 44, 24, 45, 0, 0, 0, 0, 0, 0, - 0, 0, 5, 46, 47, 0, 0, 0, 0, 48, 5, 49, 50, 51, 0, 0, - 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 53, 54, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_changes_when_uppercased_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 0, 32, 0, 0, 0, 0, 128, - 255, 255, 127, 255, 170, 170, 170, 170, 170, 170, 170, 84, 85, 171, 170, 170, - 170, 170, 170, 212, 41, 17, 36, 70, 42, 33, 81, 162, 96, 91, 85, 181, - 170, 170, 45, 170, 168, 170, 10, 144, 133, 170, 223, 10, 105, 139, 38, 32, - 9, 31, 4, 0, 32, 0, 0, 0, 0, 0, 138, 56, 0, 0, 1, 0, - 0, 240, 255, 255, 255, 127, 227, 170, 170, 170, 39, 9, 0, 0, 255, 255, - 255, 255, 255, 255, 2, 168, 170, 170, 84, 213, 170, 170, 170, 0, 0, 0, - 254, 255, 255, 255, 255, 0, 0, 0, 0, 0, 0, 34, 170, 170, 234, 15, - 255, 0, 63, 0, 255, 0, 255, 0, 63, 0, 255, 0, 255, 0, 255, 63, - 255, 255, 223, 80, 220, 16, 207, 0, 255, 0, 220, 16, 0, 64, 0, 0, - 16, 0, 0, 0, 255, 3, 0, 0, 255, 255, 255, 127, 98, 21, 72, 0, - 10, 80, 8, 0, 191, 32, 0, 0, 170, 42, 0, 0, 170, 170, 170, 0, - 168, 170, 168, 170, 170, 170, 0, 148, 170, 16, 10, 0, 170, 2, 0, 0, - 127, 0, 248, 0, 0, 255, 255, 255, 255, 255, 0, 0, -}; - -/* Changes_When_Uppercased: 534 bytes. */ - -RE_UINT32 re_get_changes_when_uppercased(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_changes_when_uppercased_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_changes_when_uppercased_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_changes_when_uppercased_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_changes_when_uppercased_stage_4[pos + f] << 5; - pos += code; - value = (re_changes_when_uppercased_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Changes_When_Titlecased. */ - -static RE_UINT8 re_changes_when_titlecased_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_changes_when_titlecased_stage_2[] = { - 0, 1, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 6, - 7, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_changes_when_titlecased_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 7, 8, 9, 6, 10, 6, 6, 11, 6, 6, 6, - 6, 6, 6, 6, 12, 13, 6, 6, 6, 6, 6, 6, 6, 6, 14, 15, - 6, 6, 6, 16, 6, 6, 6, 17, 6, 6, 6, 6, 18, 6, 6, 6, -}; - -static RE_UINT8 re_changes_when_titlecased_stage_4[] = { - 0, 0, 0, 1, 0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, - 5, 13, 14, 15, 16, 0, 0, 0, 0, 0, 17, 18, 19, 20, 21, 22, - 0, 23, 24, 5, 25, 5, 26, 5, 5, 27, 0, 28, 29, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 30, 0, 0, 0, 0, - 5, 5, 5, 5, 31, 5, 5, 5, 32, 33, 34, 35, 33, 36, 37, 38, - 0, 0, 39, 23, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 41, - 0, 23, 42, 43, 5, 5, 5, 44, 24, 45, 0, 0, 0, 0, 0, 0, - 0, 0, 5, 46, 47, 0, 0, 0, 0, 48, 5, 49, 50, 51, 0, 0, - 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 53, 54, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_changes_when_titlecased_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 0, 32, 0, 0, 0, 0, 128, - 255, 255, 127, 255, 170, 170, 170, 170, 170, 170, 170, 84, 85, 171, 170, 170, - 170, 170, 170, 212, 41, 17, 36, 70, 42, 33, 81, 162, 208, 86, 85, 181, - 170, 170, 43, 170, 168, 170, 10, 144, 133, 170, 223, 10, 105, 139, 38, 32, - 9, 31, 4, 0, 32, 0, 0, 0, 0, 0, 138, 56, 0, 0, 1, 0, - 0, 240, 255, 255, 255, 127, 227, 170, 170, 170, 39, 9, 0, 0, 255, 255, - 255, 255, 255, 255, 2, 168, 170, 170, 84, 213, 170, 170, 170, 0, 0, 0, - 254, 255, 255, 255, 255, 0, 0, 0, 0, 0, 0, 34, 170, 170, 234, 15, - 255, 0, 63, 0, 255, 0, 255, 0, 63, 0, 255, 0, 255, 0, 255, 63, - 255, 0, 223, 64, 220, 0, 207, 0, 255, 0, 220, 0, 0, 64, 0, 0, - 16, 0, 0, 0, 255, 3, 0, 0, 255, 255, 255, 127, 98, 21, 72, 0, - 10, 80, 8, 0, 191, 32, 0, 0, 170, 42, 0, 0, 170, 170, 170, 0, - 168, 170, 168, 170, 170, 170, 0, 148, 170, 16, 10, 0, 170, 2, 0, 0, - 127, 0, 248, 0, 0, 255, 255, 255, 255, 255, 0, 0, -}; - -/* Changes_When_Titlecased: 534 bytes. */ - -RE_UINT32 re_get_changes_when_titlecased(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_changes_when_titlecased_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_changes_when_titlecased_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_changes_when_titlecased_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_changes_when_titlecased_stage_4[pos + f] << 5; - pos += code; - value = (re_changes_when_titlecased_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Changes_When_Casefolded. */ - -static RE_UINT8 re_changes_when_casefolded_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_changes_when_casefolded_stage_2[] = { - 0, 1, 2, 3, 4, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 6, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, - 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_changes_when_casefolded_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, - 6, 10, 6, 6, 11, 6, 6, 6, 6, 6, 6, 6, 12, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, 6, 15, 6, 6, 6, 16, - 6, 6, 6, 6, 17, 6, 6, 6, -}; - -static RE_UINT8 re_changes_when_casefolded_stage_4[] = { - 0, 0, 1, 0, 0, 2, 3, 0, 4, 5, 6, 7, 8, 9, 10, 11, - 4, 12, 13, 0, 0, 0, 0, 0, 0, 0, 14, 15, 16, 17, 18, 19, - 20, 21, 0, 4, 22, 4, 23, 4, 4, 24, 25, 0, 26, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 27, 0, - 4, 4, 4, 4, 28, 4, 4, 4, 29, 30, 31, 32, 20, 33, 34, 35, - 0, 36, 0, 21, 37, 0, 0, 0, 0, 0, 0, 0, 0, 38, 21, 0, - 20, 39, 0, 40, 4, 4, 4, 41, 0, 0, 4, 42, 43, 0, 0, 0, - 0, 44, 4, 45, 46, 47, 0, 0, 48, 0, 0, 0, 0, 0, 0, 0, - 0, 1, 0, 0, 0, 0, 0, 0, 20, 49, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_changes_when_casefolded_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 0, 32, 0, 255, 255, 127, 255, - 85, 85, 85, 85, 85, 85, 85, 170, 170, 86, 85, 85, 85, 85, 85, 171, - 214, 206, 219, 177, 213, 210, 174, 17, 176, 173, 170, 74, 85, 85, 214, 85, - 85, 85, 5, 108, 122, 85, 0, 0, 32, 0, 0, 0, 0, 0, 69, 0, - 64, 215, 254, 255, 251, 15, 0, 0, 4, 128, 99, 85, 85, 85, 179, 230, - 255, 255, 255, 255, 255, 255, 0, 0, 1, 84, 85, 85, 171, 42, 85, 85, - 85, 0, 254, 255, 255, 255, 127, 0, 128, 0, 0, 0, 191, 32, 0, 0, - 85, 85, 21, 76, 0, 255, 0, 63, 0, 255, 0, 255, 0, 63, 0, 170, - 0, 255, 0, 0, 255, 255, 156, 31, 156, 31, 0, 15, 0, 31, 156, 31, - 64, 12, 4, 0, 8, 0, 0, 0, 0, 0, 192, 255, 255, 127, 0, 0, - 157, 234, 37, 192, 5, 40, 4, 0, 85, 21, 0, 0, 85, 85, 85, 0, - 84, 85, 84, 85, 85, 85, 0, 106, 85, 40, 5, 0, 85, 5, 0, 0, - 127, 0, 248, 0, 255, 0, 0, 0, -}; - -/* Changes_When_Casefolded: 514 bytes. */ - -RE_UINT32 re_get_changes_when_casefolded(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_changes_when_casefolded_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_changes_when_casefolded_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_changes_when_casefolded_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_changes_when_casefolded_stage_4[pos + f] << 5; - pos += code; - value = (re_changes_when_casefolded_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Changes_When_Casemapped. */ - -static RE_UINT8 re_changes_when_casemapped_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_changes_when_casemapped_stage_2[] = { - 0, 1, 2, 3, 4, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 6, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, - 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_changes_when_casemapped_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, 10, - 6, 11, 6, 6, 12, 6, 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, - 6, 6, 6, 6, 6, 6, 15, 16, 6, 6, 6, 17, 6, 6, 6, 18, - 6, 6, 6, 6, 19, 6, 6, 6, -}; - -static RE_UINT8 re_changes_when_casemapped_stage_4[] = { - 0, 0, 1, 1, 0, 2, 3, 3, 4, 5, 4, 4, 6, 7, 8, 4, - 4, 9, 10, 11, 12, 0, 0, 0, 0, 0, 13, 14, 15, 16, 17, 18, - 4, 4, 4, 4, 19, 4, 4, 4, 4, 20, 21, 22, 23, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 24, 0, - 0, 0, 0, 25, 0, 0, 0, 0, 4, 4, 4, 4, 26, 4, 4, 4, - 27, 4, 28, 29, 4, 30, 31, 32, 0, 33, 34, 4, 35, 0, 0, 0, - 0, 0, 0, 0, 0, 36, 4, 37, 4, 38, 39, 40, 4, 4, 4, 41, - 4, 24, 0, 0, 0, 0, 0, 0, 0, 0, 4, 42, 43, 0, 0, 0, - 0, 44, 4, 45, 46, 47, 0, 0, 48, 0, 0, 0, 0, 0, 0, 0, - 0, 1, 1, 0, 0, 0, 0, 0, 4, 4, 49, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_changes_when_casemapped_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 0, 32, 0, 255, 255, 127, 255, - 255, 255, 255, 255, 255, 255, 255, 254, 255, 223, 255, 247, 255, 243, 255, 179, - 240, 255, 255, 255, 253, 255, 15, 252, 255, 255, 223, 10, 105, 139, 38, 32, - 9, 31, 4, 0, 32, 0, 0, 0, 0, 0, 207, 56, 64, 215, 255, 255, - 251, 255, 255, 255, 255, 255, 227, 255, 255, 255, 183, 239, 3, 252, 255, 255, - 255, 0, 254, 255, 255, 255, 127, 0, 254, 255, 255, 255, 255, 0, 0, 0, - 191, 32, 0, 0, 0, 0, 0, 34, 255, 255, 255, 79, 255, 255, 63, 63, - 63, 63, 255, 170, 255, 255, 255, 63, 255, 255, 223, 95, 220, 31, 207, 15, - 255, 31, 220, 31, 64, 12, 4, 0, 0, 64, 0, 0, 24, 0, 0, 0, - 0, 0, 192, 255, 255, 3, 0, 0, 255, 127, 255, 255, 255, 255, 255, 127, - 255, 255, 109, 192, 15, 120, 12, 0, 255, 63, 0, 0, 255, 255, 255, 0, - 252, 255, 252, 255, 255, 255, 0, 254, 255, 56, 15, 0, 255, 7, 0, 0, - 127, 0, 248, 0, 255, 255, 0, 0, -}; - -/* Changes_When_Casemapped: 530 bytes. */ - -RE_UINT32 re_get_changes_when_casemapped(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_changes_when_casemapped_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_changes_when_casemapped_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_changes_when_casemapped_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_changes_when_casemapped_stage_4[pos + f] << 5; - pos += code; - value = (re_changes_when_casemapped_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* ID_Start. */ - -static RE_UINT8 re_id_start_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, -}; - -static RE_UINT8 re_id_start_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_id_start_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 33, 31, 31, - 34, 35, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 36, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, - 1, 1, 1, 1, 38, 1, 39, 40, 41, 42, 43, 44, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 45, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 46, 47, 1, 48, 49, 50, 51, 52, 53, 54, 55, 31, 31, 31, - 56, 57, 58, 59, 60, 31, 31, 31, 61, 62, 31, 31, 31, 31, 63, 31, - 1, 1, 1, 64, 65, 31, 31, 31, 1, 1, 1, 1, 66, 31, 31, 31, - 1, 1, 67, 31, 31, 31, 31, 68, 69, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 70, 71, 72, 73, 31, 31, 31, 31, 31, 31, 74, 31, - 1, 1, 1, 1, 1, 1, 75, 1, 1, 1, 1, 1, 1, 1, 1, 76, - 77, 31, 31, 31, 31, 31, 31, 31, 1, 1, 77, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_id_start_stage_4[] = { - 0, 0, 1, 1, 0, 2, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 5, 6, 0, 0, 0, 7, 8, 9, 4, 10, - 4, 4, 4, 4, 11, 4, 4, 4, 4, 12, 13, 14, 15, 0, 16, 17, - 0, 4, 18, 19, 4, 4, 20, 21, 22, 23, 24, 4, 4, 25, 26, 27, - 28, 29, 30, 0, 0, 31, 0, 0, 32, 33, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 36, 45, 48, 49, 50, 51, 46, 0, - 52, 53, 54, 47, 52, 53, 55, 56, 52, 57, 58, 59, 60, 61, 62, 0, - 14, 63, 62, 0, 64, 65, 66, 0, 67, 0, 68, 69, 70, 0, 0, 0, - 4, 71, 72, 73, 74, 4, 75, 76, 4, 4, 77, 4, 78, 79, 80, 4, - 81, 4, 82, 0, 23, 4, 4, 83, 14, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 84, 1, 4, 4, 85, 86, 87, 87, 88, 4, 89, 90, 0, - 0, 4, 4, 91, 4, 92, 4, 93, 94, 0, 16, 95, 4, 96, 97, 0, - 98, 4, 83, 0, 0, 99, 0, 0, 100, 89, 101, 0, 102, 103, 4, 104, - 4, 105, 106, 107, 0, 0, 0, 108, 4, 4, 4, 4, 4, 4, 0, 0, - 109, 4, 110, 107, 4, 111, 112, 113, 0, 0, 0, 114, 115, 0, 0, 0, - 116, 117, 118, 4, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 120, 121, 4, 4, 4, 4, 122, 4, 75, 4, 123, 98, 124, 124, 0, - 125, 126, 14, 4, 127, 14, 4, 76, 100, 128, 4, 4, 129, 82, 0, 16, - 4, 4, 4, 4, 4, 93, 0, 0, 4, 4, 4, 4, 4, 4, 69, 0, - 4, 4, 4, 4, 69, 0, 16, 107, 130, 131, 4, 132, 91, 4, 4, 23, - 133, 134, 4, 4, 135, 18, 0, 136, 137, 138, 4, 89, 134, 89, 0, 139, - 26, 140, 62, 94, 32, 141, 142, 0, 4, 119, 143, 144, 4, 145, 146, 147, - 148, 149, 0, 0, 0, 0, 4, 138, 4, 4, 4, 4, 4, 150, 151, 152, - 4, 4, 4, 153, 4, 4, 154, 0, 155, 156, 157, 4, 4, 87, 158, 4, - 4, 107, 16, 4, 159, 4, 15, 160, 0, 0, 0, 161, 4, 4, 4, 94, - 0, 1, 1, 162, 4, 121, 163, 0, 164, 165, 166, 0, 4, 4, 4, 82, - 0, 0, 4, 83, 0, 0, 0, 0, 0, 0, 0, 0, 94, 4, 167, 0, - 121, 16, 18, 0, 107, 4, 168, 0, 4, 4, 4, 4, 107, 0, 0, 0, - 169, 170, 93, 0, 0, 0, 0, 0, 93, 154, 0, 0, 4, 171, 0, 0, - 172, 89, 0, 94, 0, 0, 0, 0, 4, 93, 93, 141, 0, 0, 0, 0, - 4, 4, 119, 0, 0, 0, 0, 0, 102, 91, 0, 0, 102, 23, 16, 119, - 102, 62, 0, 0, 102, 141, 173, 0, 0, 0, 0, 0, 4, 18, 0, 0, - 4, 4, 4, 129, 0, 0, 0, 0, 4, 4, 4, 138, 0, 0, 0, 0, - 4, 129, 0, 0, 0, 0, 0, 0, 4, 30, 0, 0, 0, 0, 0, 0, - 4, 4, 174, 0, 158, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 0, - 4, 4, 175, 4, 176, 177, 178, 4, 179, 180, 181, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 182, 183, 76, 175, 175, 120, 120, 184, 184, 143, 0, - 178, 185, 186, 187, 188, 189, 0, 0, 4, 4, 4, 4, 4, 4, 98, 0, - 4, 83, 4, 4, 4, 4, 4, 4, 107, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_id_start_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 4, 32, 4, 255, 255, 127, 255, - 255, 255, 255, 255, 195, 255, 3, 0, 31, 80, 0, 0, 0, 0, 223, 60, - 64, 215, 255, 255, 251, 255, 255, 255, 255, 255, 191, 255, 3, 252, 255, 255, - 255, 0, 254, 255, 255, 255, 127, 2, 254, 255, 255, 255, 255, 0, 0, 0, - 0, 0, 255, 255, 255, 7, 7, 0, 255, 7, 0, 0, 0, 192, 254, 255, - 255, 255, 47, 0, 96, 192, 0, 156, 0, 0, 253, 255, 255, 255, 0, 0, - 0, 224, 255, 255, 63, 0, 2, 0, 0, 252, 255, 255, 255, 7, 48, 4, - 255, 255, 63, 4, 16, 1, 0, 0, 255, 255, 255, 1, 253, 31, 0, 0, - 240, 255, 255, 255, 255, 255, 255, 35, 0, 0, 1, 255, 3, 0, 254, 254, - 224, 159, 249, 255, 255, 253, 197, 35, 0, 64, 0, 176, 3, 0, 3, 0, - 224, 135, 249, 255, 255, 253, 109, 3, 0, 0, 0, 94, 0, 0, 28, 0, - 224, 191, 251, 255, 255, 253, 237, 35, 0, 0, 1, 0, 3, 0, 0, 0, - 0, 0, 0, 176, 3, 0, 2, 0, 232, 199, 61, 214, 24, 199, 255, 3, - 224, 223, 253, 255, 255, 253, 239, 35, 0, 0, 0, 3, 0, 0, 0, 64, - 3, 0, 6, 0, 255, 255, 255, 39, 0, 64, 0, 0, 3, 0, 0, 252, - 224, 255, 127, 252, 255, 255, 251, 47, 127, 0, 0, 0, 255, 255, 13, 0, - 150, 37, 240, 254, 174, 236, 13, 32, 95, 0, 0, 240, 1, 0, 0, 0, - 255, 254, 255, 255, 255, 31, 0, 0, 0, 31, 0, 0, 255, 7, 0, 128, - 0, 0, 63, 60, 98, 192, 225, 255, 3, 64, 0, 0, 191, 32, 255, 255, - 255, 255, 255, 247, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 255, 255, 255, 7, 255, 255, 31, 0, - 255, 159, 255, 255, 255, 199, 1, 0, 255, 223, 3, 0, 255, 255, 3, 0, - 255, 223, 1, 0, 255, 255, 15, 0, 0, 0, 128, 16, 255, 255, 255, 0, - 255, 5, 255, 255, 255, 255, 63, 0, 255, 255, 255, 31, 255, 63, 31, 0, - 255, 15, 0, 0, 254, 0, 0, 0, 255, 255, 127, 0, 128, 0, 0, 0, - 224, 255, 255, 255, 224, 15, 0, 0, 248, 255, 255, 255, 1, 192, 0, 252, - 63, 0, 0, 0, 15, 0, 0, 0, 0, 224, 0, 252, 255, 255, 255, 63, - 0, 222, 99, 0, 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 95, - 220, 31, 207, 15, 255, 31, 220, 31, 0, 0, 2, 128, 0, 0, 255, 31, - 132, 252, 47, 63, 80, 253, 255, 243, 224, 67, 0, 0, 255, 1, 0, 0, - 255, 127, 255, 255, 255, 255, 255, 127, 31, 120, 12, 0, 255, 128, 0, 0, - 127, 127, 127, 127, 224, 0, 0, 0, 254, 3, 62, 31, 255, 255, 127, 248, - 255, 63, 254, 255, 255, 127, 0, 0, 255, 31, 255, 255, 0, 12, 0, 0, - 255, 127, 0, 128, 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, - 0, 0, 0, 255, 187, 247, 255, 255, 7, 0, 0, 0, 0, 0, 252, 8, - 63, 0, 255, 255, 255, 255, 7, 0, 0, 128, 0, 0, 247, 15, 0, 0, - 255, 255, 127, 4, 255, 255, 98, 62, 5, 0, 0, 56, 255, 7, 28, 0, - 126, 126, 126, 0, 127, 127, 0, 0, 15, 0, 255, 255, 127, 248, 255, 255, - 255, 255, 255, 15, 255, 63, 255, 255, 255, 255, 255, 3, 127, 0, 248, 160, - 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, 255, 255, 252, 255, - 0, 0, 255, 15, 0, 0, 223, 255, 192, 255, 255, 255, 252, 252, 252, 28, - 255, 239, 255, 255, 127, 255, 255, 183, 255, 63, 255, 63, 255, 255, 1, 0, - 15, 255, 62, 0, 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 255, 192, - 1, 0, 239, 254, 30, 0, 0, 0, 31, 0, 1, 0, 255, 255, 223, 255, - 255, 255, 255, 223, 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, - 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, - 255, 253, 255, 255, 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, - 255, 251, 255, 15, 238, 251, 255, 15, -}; - -/* ID_Start: 1753 bytes. */ - -RE_UINT32 re_get_id_start(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_id_start_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_id_start_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_id_start_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_id_start_stage_4[pos + f] << 5; - pos += code; - value = (re_id_start_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* ID_Continue. */ - -static RE_UINT8 re_id_continue_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 6, 6, 6, - 6, 6, -}; - -static RE_UINT8 re_id_continue_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 28, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_id_continue_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 33, 31, 31, - 34, 35, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 36, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, - 1, 1, 1, 1, 38, 1, 39, 40, 41, 42, 43, 44, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 45, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 46, 47, 1, 48, 49, 50, 51, 52, 53, 54, 55, 31, 31, 31, - 56, 57, 58, 59, 60, 31, 31, 31, 61, 62, 31, 31, 31, 31, 63, 31, - 1, 1, 1, 64, 65, 31, 31, 31, 1, 1, 1, 1, 66, 31, 31, 31, - 1, 1, 67, 31, 31, 31, 31, 68, 69, 31, 31, 31, 31, 31, 31, 31, - 31, 70, 71, 31, 72, 73, 74, 75, 31, 31, 31, 31, 31, 31, 76, 31, - 1, 1, 1, 1, 1, 1, 77, 1, 1, 1, 1, 1, 1, 1, 1, 78, - 79, 31, 31, 31, 31, 31, 31, 31, 1, 1, 79, 31, 31, 31, 31, 31, - 31, 80, 31, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_id_continue_stage_4[] = { - 0, 1, 2, 3, 0, 4, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 7, 8, 6, 6, 6, 9, 10, 11, 6, 12, - 6, 6, 6, 6, 13, 6, 6, 6, 6, 14, 15, 16, 14, 17, 18, 19, - 20, 6, 6, 21, 6, 6, 22, 23, 24, 6, 25, 6, 6, 26, 6, 27, - 6, 28, 29, 0, 0, 30, 0, 31, 6, 6, 6, 32, 33, 34, 35, 36, - 37, 38, 39, 40, 41, 42, 43, 44, 33, 42, 45, 46, 47, 48, 49, 50, - 51, 52, 53, 44, 54, 55, 56, 57, 54, 58, 59, 60, 61, 62, 63, 64, - 16, 65, 66, 0, 67, 68, 69, 0, 70, 71, 72, 73, 74, 75, 76, 0, - 6, 6, 77, 6, 78, 6, 79, 80, 6, 6, 81, 6, 82, 83, 84, 6, - 85, 6, 58, 86, 87, 6, 6, 88, 16, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 89, 3, 6, 6, 90, 91, 88, 92, 93, 6, 6, 94, 95, - 96, 6, 6, 97, 6, 98, 6, 99, 75, 100, 101, 102, 6, 103, 104, 0, - 29, 6, 105, 106, 107, 108, 0, 0, 6, 6, 109, 110, 6, 6, 6, 92, - 6, 97, 111, 78, 0, 0, 112, 113, 6, 6, 6, 6, 6, 6, 6, 114, - 115, 6, 116, 78, 6, 117, 118, 119, 0, 120, 121, 122, 123, 0, 123, 124, - 125, 126, 127, 6, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 6, 129, 105, 6, 6, 6, 6, 130, 6, 79, 6, 131, 113, 132, 132, 6, - 133, 134, 16, 6, 135, 16, 6, 80, 136, 137, 6, 6, 138, 65, 0, 24, - 6, 6, 6, 6, 6, 99, 0, 0, 6, 6, 6, 6, 6, 6, 139, 0, - 6, 6, 6, 6, 139, 0, 24, 78, 140, 141, 6, 142, 143, 6, 6, 26, - 144, 145, 6, 6, 146, 147, 0, 148, 6, 149, 6, 92, 6, 6, 150, 151, - 6, 152, 92, 75, 6, 6, 153, 0, 6, 113, 154, 155, 6, 6, 156, 157, - 158, 159, 0, 0, 0, 0, 6, 160, 6, 6, 6, 6, 6, 161, 162, 29, - 6, 6, 6, 152, 6, 6, 163, 0, 164, 165, 166, 6, 6, 26, 167, 6, - 6, 78, 24, 6, 168, 6, 149, 169, 87, 170, 171, 172, 6, 6, 6, 75, - 1, 2, 3, 101, 6, 105, 173, 0, 174, 175, 176, 0, 6, 6, 6, 65, - 0, 0, 6, 88, 0, 0, 0, 177, 0, 0, 0, 0, 75, 6, 178, 0, - 105, 24, 147, 0, 78, 6, 179, 0, 6, 6, 6, 6, 78, 95, 0, 0, - 180, 181, 99, 0, 0, 0, 0, 0, 99, 163, 0, 0, 6, 182, 0, 0, - 183, 184, 0, 75, 0, 0, 0, 0, 6, 99, 99, 185, 0, 0, 0, 0, - 6, 6, 128, 0, 0, 0, 0, 0, 6, 6, 186, 50, 6, 65, 24, 187, - 6, 188, 0, 0, 6, 6, 150, 0, 0, 0, 0, 0, 6, 97, 95, 0, - 6, 6, 6, 138, 0, 0, 0, 0, 6, 6, 6, 189, 0, 0, 0, 0, - 6, 138, 0, 0, 0, 0, 0, 0, 6, 190, 0, 0, 0, 0, 0, 0, - 6, 6, 191, 105, 192, 0, 0, 0, 193, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 194, 195, 196, 0, 0, 0, 0, 197, 0, 0, 0, 0, 0, - 6, 6, 188, 6, 198, 199, 200, 6, 201, 202, 203, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 204, 205, 80, 188, 188, 129, 129, 206, 206, 207, 6, - 200, 208, 209, 210, 211, 212, 0, 0, 6, 6, 6, 6, 6, 6, 113, 0, - 6, 88, 6, 6, 6, 6, 6, 6, 78, 0, 0, 0, 0, 0, 0, 0, - 6, 6, 6, 6, 6, 6, 6, 87, -}; - -static RE_UINT8 re_id_continue_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 254, 255, 255, 135, 254, 255, 255, 7, - 0, 4, 160, 4, 255, 255, 127, 255, 255, 255, 255, 255, 195, 255, 3, 0, - 31, 80, 0, 0, 255, 255, 223, 60, 192, 215, 255, 255, 251, 255, 255, 255, - 255, 255, 191, 255, 251, 252, 255, 255, 255, 0, 254, 255, 255, 255, 127, 2, - 254, 255, 255, 255, 255, 255, 255, 191, 182, 0, 255, 255, 255, 7, 7, 0, - 0, 0, 255, 7, 255, 195, 255, 255, 255, 255, 239, 159, 255, 253, 255, 159, - 0, 0, 255, 255, 255, 231, 255, 255, 255, 255, 3, 0, 255, 255, 63, 4, - 255, 63, 0, 0, 255, 255, 255, 15, 253, 31, 0, 0, 240, 255, 255, 127, - 207, 255, 254, 254, 238, 159, 249, 255, 255, 253, 197, 243, 159, 121, 128, 176, - 207, 255, 3, 0, 238, 135, 249, 255, 255, 253, 109, 211, 135, 57, 2, 94, - 192, 255, 63, 0, 238, 191, 251, 255, 255, 253, 237, 243, 191, 59, 1, 0, - 207, 255, 0, 0, 159, 57, 192, 176, 207, 255, 2, 0, 236, 199, 61, 214, - 24, 199, 255, 195, 199, 61, 129, 0, 192, 255, 0, 0, 238, 223, 253, 255, - 255, 253, 239, 227, 223, 61, 96, 3, 236, 223, 253, 255, 255, 253, 239, 243, - 223, 61, 96, 64, 207, 255, 6, 0, 255, 255, 255, 231, 223, 125, 128, 0, - 207, 255, 0, 252, 236, 255, 127, 252, 255, 255, 251, 47, 127, 132, 95, 255, - 0, 0, 12, 0, 255, 255, 255, 7, 255, 127, 255, 3, 150, 37, 240, 254, - 174, 236, 255, 59, 95, 63, 255, 243, 1, 0, 0, 3, 255, 3, 160, 194, - 255, 254, 255, 255, 255, 31, 254, 255, 223, 255, 255, 254, 255, 255, 255, 31, - 64, 0, 0, 0, 255, 3, 255, 255, 255, 255, 255, 63, 191, 32, 255, 255, - 255, 255, 255, 247, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 0, 254, 3, 0, 255, 255, 0, 0, - 255, 255, 31, 0, 255, 159, 255, 255, 255, 199, 1, 0, 255, 223, 31, 0, - 255, 255, 15, 0, 255, 223, 13, 0, 255, 255, 143, 48, 255, 3, 0, 0, - 0, 56, 255, 3, 255, 255, 255, 0, 255, 7, 255, 255, 255, 255, 63, 0, - 255, 15, 255, 15, 192, 255, 255, 255, 255, 63, 31, 0, 255, 15, 255, 255, - 255, 3, 255, 7, 255, 255, 255, 127, 255, 255, 255, 159, 255, 3, 255, 3, - 128, 0, 0, 0, 255, 15, 255, 3, 0, 248, 15, 0, 255, 227, 255, 255, - 0, 0, 247, 255, 255, 255, 127, 0, 127, 0, 0, 240, 255, 255, 63, 63, - 63, 63, 255, 170, 255, 255, 223, 95, 220, 31, 207, 15, 255, 31, 220, 31, - 0, 0, 0, 128, 1, 0, 16, 0, 0, 0, 2, 128, 0, 0, 255, 31, - 226, 255, 1, 0, 132, 252, 47, 63, 80, 253, 255, 243, 224, 67, 0, 0, - 255, 1, 0, 0, 255, 127, 255, 255, 31, 248, 15, 0, 255, 128, 0, 128, - 127, 127, 127, 127, 224, 0, 0, 0, 254, 255, 62, 31, 255, 255, 127, 254, - 224, 255, 255, 255, 255, 63, 254, 255, 255, 127, 0, 0, 255, 31, 0, 0, - 255, 31, 255, 255, 255, 15, 0, 0, 255, 255, 240, 191, 255, 255, 255, 128, - 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 255, 255, 0, 0, 0, 31, 0, 255, 3, 255, 255, 255, 8, - 255, 63, 255, 255, 1, 128, 255, 3, 255, 63, 255, 3, 255, 255, 127, 12, - 7, 0, 0, 56, 255, 255, 124, 0, 126, 126, 126, 0, 127, 127, 0, 0, - 255, 55, 255, 3, 15, 0, 255, 255, 127, 248, 255, 255, 255, 255, 255, 3, - 127, 0, 248, 224, 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, - 255, 255, 252, 255, 0, 0, 255, 15, 127, 0, 24, 0, 0, 224, 0, 0, - 0, 0, 223, 255, 252, 252, 252, 28, 255, 239, 255, 255, 127, 255, 255, 183, - 255, 63, 255, 63, 0, 0, 0, 32, 255, 255, 1, 0, 15, 255, 62, 0, - 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 255, 192, 111, 240, 239, 254, - 255, 255, 15, 135, 255, 255, 7, 0, 127, 0, 0, 0, 255, 1, 255, 3, - 255, 255, 223, 255, 7, 0, 0, 0, 255, 255, 255, 1, 31, 0, 255, 255, - 0, 128, 255, 255, 3, 0, 0, 0, 224, 227, 7, 248, 231, 15, 0, 0, - 0, 60, 0, 0, 28, 0, 0, 0, 255, 255, 255, 223, 100, 222, 255, 235, - 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, 95, 252, 253, 255, - 63, 255, 255, 255, 253, 255, 255, 247, 255, 253, 255, 255, 247, 207, 255, 255, - 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, - 238, 251, 255, 15, -}; - -/* ID_Continue: 1894 bytes. */ - -RE_UINT32 re_get_id_continue(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_id_continue_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_id_continue_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_id_continue_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_id_continue_stage_4[pos + f] << 5; - pos += code; - value = (re_id_continue_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* XID_Start. */ - -static RE_UINT8 re_xid_start_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, -}; - -static RE_UINT8 re_xid_start_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_xid_start_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 33, 31, 31, - 34, 35, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 36, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, - 1, 1, 1, 1, 38, 1, 39, 40, 41, 42, 43, 44, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 45, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 31, 31, 31, - 57, 58, 59, 60, 61, 31, 31, 31, 62, 63, 31, 31, 31, 31, 64, 31, - 1, 1, 1, 65, 66, 31, 31, 31, 1, 1, 1, 1, 67, 31, 31, 31, - 1, 1, 68, 31, 31, 31, 31, 69, 70, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 71, 72, 73, 74, 31, 31, 31, 31, 31, 31, 75, 31, - 1, 1, 1, 1, 1, 1, 76, 1, 1, 1, 1, 1, 1, 1, 1, 77, - 78, 31, 31, 31, 31, 31, 31, 31, 1, 1, 78, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_xid_start_stage_4[] = { - 0, 0, 1, 1, 0, 2, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 5, 6, 0, 0, 0, 7, 8, 9, 4, 10, - 4, 4, 4, 4, 11, 4, 4, 4, 4, 12, 13, 14, 15, 0, 16, 17, - 0, 4, 18, 19, 4, 4, 20, 21, 22, 23, 24, 4, 4, 25, 26, 27, - 28, 29, 30, 0, 0, 31, 0, 0, 32, 33, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 36, 45, 48, 49, 50, 51, 46, 0, - 52, 53, 54, 47, 52, 53, 55, 56, 52, 57, 58, 59, 60, 61, 62, 0, - 14, 63, 62, 0, 64, 65, 66, 0, 67, 0, 68, 69, 70, 0, 0, 0, - 4, 71, 72, 73, 74, 4, 75, 76, 4, 4, 77, 4, 78, 79, 80, 4, - 81, 4, 82, 0, 23, 4, 4, 83, 14, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 84, 1, 4, 4, 85, 86, 87, 87, 88, 4, 89, 90, 0, - 0, 4, 4, 91, 4, 92, 4, 93, 94, 0, 16, 95, 4, 96, 97, 0, - 98, 4, 83, 0, 0, 99, 0, 0, 100, 89, 101, 0, 102, 103, 4, 104, - 4, 105, 106, 107, 0, 0, 0, 108, 4, 4, 4, 4, 4, 4, 0, 0, - 109, 4, 110, 107, 4, 111, 112, 113, 0, 0, 0, 114, 115, 0, 0, 0, - 116, 117, 118, 4, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 120, 121, 4, 4, 4, 4, 122, 4, 75, 4, 123, 98, 124, 124, 0, - 125, 126, 14, 4, 127, 14, 4, 76, 100, 128, 4, 4, 129, 82, 0, 16, - 4, 4, 4, 4, 4, 93, 0, 0, 4, 4, 4, 4, 4, 4, 69, 0, - 4, 4, 4, 4, 69, 0, 16, 107, 130, 131, 4, 132, 91, 4, 4, 23, - 133, 134, 4, 4, 135, 18, 0, 136, 137, 138, 4, 89, 134, 89, 0, 139, - 26, 140, 62, 94, 32, 141, 142, 0, 4, 119, 143, 144, 4, 145, 146, 147, - 148, 149, 0, 0, 0, 0, 4, 138, 4, 4, 4, 4, 4, 150, 151, 152, - 4, 4, 4, 153, 4, 4, 154, 0, 155, 156, 157, 4, 4, 87, 158, 4, - 4, 4, 107, 32, 4, 4, 4, 4, 4, 107, 16, 4, 159, 4, 15, 160, - 0, 0, 0, 161, 4, 4, 4, 94, 0, 1, 1, 162, 107, 121, 163, 0, - 164, 165, 166, 0, 4, 4, 4, 82, 0, 0, 4, 83, 0, 0, 0, 0, - 0, 0, 0, 0, 94, 4, 167, 0, 121, 16, 18, 0, 107, 4, 168, 0, - 4, 4, 4, 4, 107, 0, 0, 0, 169, 170, 93, 0, 0, 0, 0, 0, - 93, 154, 0, 0, 4, 171, 0, 0, 172, 89, 0, 94, 0, 0, 0, 0, - 4, 93, 93, 141, 0, 0, 0, 0, 4, 4, 119, 0, 0, 0, 0, 0, - 102, 91, 0, 0, 102, 23, 16, 119, 102, 62, 0, 0, 102, 141, 173, 0, - 0, 0, 0, 0, 4, 18, 0, 0, 4, 4, 4, 129, 0, 0, 0, 0, - 4, 4, 4, 138, 0, 0, 0, 0, 4, 129, 0, 0, 0, 0, 0, 0, - 4, 30, 0, 0, 0, 0, 0, 0, 4, 4, 174, 0, 158, 0, 0, 0, - 47, 0, 0, 0, 0, 0, 0, 0, 4, 4, 175, 4, 176, 177, 178, 4, - 179, 180, 181, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 182, 183, 76, - 175, 175, 120, 120, 184, 184, 143, 0, 178, 185, 186, 187, 188, 189, 0, 0, - 4, 4, 4, 4, 4, 4, 98, 0, 4, 83, 4, 4, 4, 4, 4, 4, - 107, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_xid_start_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 7, 0, 4, 32, 4, 255, 255, 127, 255, - 255, 255, 255, 255, 195, 255, 3, 0, 31, 80, 0, 0, 0, 0, 223, 56, - 64, 215, 255, 255, 251, 255, 255, 255, 255, 255, 191, 255, 3, 252, 255, 255, - 255, 0, 254, 255, 255, 255, 127, 2, 254, 255, 255, 255, 255, 0, 0, 0, - 0, 0, 255, 255, 255, 7, 7, 0, 255, 7, 0, 0, 0, 192, 254, 255, - 255, 255, 47, 0, 96, 192, 0, 156, 0, 0, 253, 255, 255, 255, 0, 0, - 0, 224, 255, 255, 63, 0, 2, 0, 0, 252, 255, 255, 255, 7, 48, 4, - 255, 255, 63, 4, 16, 1, 0, 0, 255, 255, 255, 1, 253, 31, 0, 0, - 240, 255, 255, 255, 255, 255, 255, 35, 0, 0, 1, 255, 3, 0, 254, 254, - 224, 159, 249, 255, 255, 253, 197, 35, 0, 64, 0, 176, 3, 0, 3, 0, - 224, 135, 249, 255, 255, 253, 109, 3, 0, 0, 0, 94, 0, 0, 28, 0, - 224, 191, 251, 255, 255, 253, 237, 35, 0, 0, 1, 0, 3, 0, 0, 0, - 0, 0, 0, 176, 3, 0, 2, 0, 232, 199, 61, 214, 24, 199, 255, 3, - 224, 223, 253, 255, 255, 253, 239, 35, 0, 0, 0, 3, 0, 0, 0, 64, - 3, 0, 6, 0, 255, 255, 255, 39, 0, 64, 0, 0, 3, 0, 0, 252, - 224, 255, 127, 252, 255, 255, 251, 47, 127, 0, 0, 0, 255, 255, 5, 0, - 150, 37, 240, 254, 174, 236, 5, 32, 95, 0, 0, 240, 1, 0, 0, 0, - 255, 254, 255, 255, 255, 31, 0, 0, 0, 31, 0, 0, 255, 7, 0, 128, - 0, 0, 63, 60, 98, 192, 225, 255, 3, 64, 0, 0, 191, 32, 255, 255, - 255, 255, 255, 247, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 255, 255, 255, 7, 255, 255, 31, 0, - 255, 159, 255, 255, 255, 199, 1, 0, 255, 223, 3, 0, 255, 255, 3, 0, - 255, 223, 1, 0, 255, 255, 15, 0, 0, 0, 128, 16, 255, 255, 255, 0, - 255, 5, 255, 255, 255, 255, 63, 0, 255, 255, 255, 31, 255, 63, 31, 0, - 255, 15, 0, 0, 254, 0, 0, 0, 255, 255, 127, 0, 128, 0, 0, 0, - 224, 255, 255, 255, 224, 15, 0, 0, 248, 255, 255, 255, 1, 192, 0, 252, - 63, 0, 0, 0, 15, 0, 0, 0, 0, 224, 0, 252, 255, 255, 255, 63, - 0, 222, 99, 0, 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 95, - 220, 31, 207, 15, 255, 31, 220, 31, 0, 0, 2, 128, 0, 0, 255, 31, - 132, 252, 47, 63, 80, 253, 255, 243, 224, 67, 0, 0, 255, 1, 0, 0, - 255, 127, 255, 255, 255, 255, 255, 127, 31, 120, 12, 0, 255, 128, 0, 0, - 127, 127, 127, 127, 224, 0, 0, 0, 254, 3, 62, 31, 255, 255, 127, 224, - 255, 63, 254, 255, 255, 127, 0, 0, 255, 31, 255, 255, 0, 12, 0, 0, - 255, 127, 0, 128, 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, - 0, 0, 0, 255, 187, 247, 255, 255, 7, 0, 0, 0, 0, 0, 252, 8, - 63, 0, 255, 255, 255, 255, 7, 0, 0, 128, 0, 0, 247, 15, 0, 0, - 255, 255, 127, 4, 255, 255, 98, 62, 5, 0, 0, 56, 255, 7, 28, 0, - 126, 126, 126, 0, 127, 127, 0, 0, 15, 0, 255, 255, 127, 248, 255, 255, - 255, 255, 255, 15, 255, 63, 255, 255, 255, 255, 255, 3, 127, 0, 248, 160, - 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, 255, 255, 252, 255, - 0, 0, 255, 3, 0, 0, 138, 170, 192, 255, 255, 255, 252, 252, 252, 28, - 255, 239, 255, 255, 127, 255, 255, 183, 255, 63, 255, 63, 255, 255, 1, 0, - 15, 255, 62, 0, 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 255, 192, - 1, 0, 239, 254, 30, 0, 0, 0, 31, 0, 1, 0, 255, 255, 223, 255, - 255, 255, 255, 223, 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, - 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, - 255, 253, 255, 255, 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, - 255, 251, 255, 15, 238, 251, 255, 15, -}; - -/* XID_Start: 1761 bytes. */ - -RE_UINT32 re_get_xid_start(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_xid_start_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_xid_start_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_xid_start_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_xid_start_stage_4[pos + f] << 5; - pos += code; - value = (re_xid_start_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* XID_Continue. */ - -static RE_UINT8 re_xid_continue_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 6, 6, 6, - 6, 6, -}; - -static RE_UINT8 re_xid_continue_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 28, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_xid_continue_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 31, 31, 31, 31, 31, 31, 31, 31, 32, 33, 31, 31, - 34, 35, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 36, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, - 1, 1, 1, 1, 38, 1, 39, 40, 41, 42, 43, 44, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 45, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 31, 31, 31, - 57, 58, 59, 60, 61, 31, 31, 31, 62, 63, 31, 31, 31, 31, 64, 31, - 1, 1, 1, 65, 66, 31, 31, 31, 1, 1, 1, 1, 67, 31, 31, 31, - 1, 1, 68, 31, 31, 31, 31, 69, 70, 31, 31, 31, 31, 31, 31, 31, - 31, 71, 72, 31, 73, 74, 75, 76, 31, 31, 31, 31, 31, 31, 77, 31, - 1, 1, 1, 1, 1, 1, 78, 1, 1, 1, 1, 1, 1, 1, 1, 79, - 80, 31, 31, 31, 31, 31, 31, 31, 1, 1, 80, 31, 31, 31, 31, 31, - 31, 81, 31, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_xid_continue_stage_4[] = { - 0, 1, 2, 3, 0, 4, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 7, 8, 6, 6, 6, 9, 10, 11, 6, 12, - 6, 6, 6, 6, 13, 6, 6, 6, 6, 14, 15, 16, 14, 17, 18, 19, - 20, 6, 6, 21, 6, 6, 22, 23, 24, 6, 25, 6, 6, 26, 6, 27, - 6, 28, 29, 0, 0, 30, 0, 31, 6, 6, 6, 32, 33, 34, 35, 36, - 37, 38, 39, 40, 41, 42, 43, 44, 33, 42, 45, 46, 47, 48, 49, 50, - 51, 52, 53, 44, 54, 55, 56, 57, 54, 58, 59, 60, 61, 62, 63, 64, - 16, 65, 66, 0, 67, 68, 69, 0, 70, 71, 72, 73, 74, 75, 76, 0, - 6, 6, 77, 6, 78, 6, 79, 80, 6, 6, 81, 6, 82, 83, 84, 6, - 85, 6, 58, 86, 87, 6, 6, 88, 16, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 89, 3, 6, 6, 90, 91, 88, 92, 93, 6, 6, 94, 95, - 96, 6, 6, 97, 6, 98, 6, 99, 75, 100, 101, 102, 6, 103, 104, 0, - 29, 6, 105, 106, 107, 108, 0, 0, 6, 6, 109, 110, 6, 6, 6, 92, - 6, 97, 111, 78, 0, 0, 112, 113, 6, 6, 6, 6, 6, 6, 6, 114, - 115, 6, 116, 78, 6, 117, 118, 119, 0, 120, 121, 122, 123, 0, 123, 124, - 125, 126, 127, 6, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 6, 129, 105, 6, 6, 6, 6, 130, 6, 79, 6, 131, 113, 132, 132, 6, - 133, 134, 16, 6, 135, 16, 6, 80, 136, 137, 6, 6, 138, 65, 0, 24, - 6, 6, 6, 6, 6, 99, 0, 0, 6, 6, 6, 6, 6, 6, 139, 0, - 6, 6, 6, 6, 139, 0, 24, 78, 140, 141, 6, 142, 143, 6, 6, 26, - 144, 145, 6, 6, 146, 147, 0, 148, 6, 149, 6, 92, 6, 6, 150, 151, - 6, 152, 92, 75, 6, 6, 153, 0, 6, 113, 154, 155, 6, 6, 156, 157, - 158, 159, 0, 0, 0, 0, 6, 160, 6, 6, 6, 6, 6, 161, 162, 29, - 6, 6, 6, 152, 6, 6, 163, 0, 164, 165, 166, 6, 6, 26, 167, 6, - 6, 6, 78, 168, 6, 6, 6, 6, 6, 78, 24, 6, 169, 6, 149, 1, - 87, 170, 171, 172, 6, 6, 6, 75, 1, 2, 3, 101, 6, 105, 173, 0, - 174, 175, 176, 0, 6, 6, 6, 65, 0, 0, 6, 88, 0, 0, 0, 177, - 0, 0, 0, 0, 75, 6, 178, 0, 105, 24, 147, 0, 78, 6, 179, 0, - 6, 6, 6, 6, 78, 95, 0, 0, 180, 181, 99, 0, 0, 0, 0, 0, - 99, 163, 0, 0, 6, 182, 0, 0, 183, 184, 0, 75, 0, 0, 0, 0, - 6, 99, 99, 185, 0, 0, 0, 0, 6, 6, 128, 0, 0, 0, 0, 0, - 6, 6, 186, 50, 6, 65, 24, 187, 6, 188, 0, 0, 6, 6, 150, 0, - 0, 0, 0, 0, 6, 97, 95, 0, 6, 6, 6, 138, 0, 0, 0, 0, - 6, 6, 6, 189, 0, 0, 0, 0, 6, 138, 0, 0, 0, 0, 0, 0, - 6, 190, 0, 0, 0, 0, 0, 0, 6, 6, 191, 105, 192, 0, 0, 0, - 193, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 194, 195, 196, 0, 0, - 0, 0, 197, 0, 0, 0, 0, 0, 6, 6, 188, 6, 198, 199, 200, 6, - 201, 202, 203, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 204, 205, 80, - 188, 188, 129, 129, 206, 206, 207, 6, 200, 208, 209, 210, 211, 212, 0, 0, - 6, 6, 6, 6, 6, 6, 113, 0, 6, 88, 6, 6, 6, 6, 6, 6, - 78, 0, 0, 0, 0, 0, 0, 0, 6, 6, 6, 6, 6, 6, 6, 87, -}; - -static RE_UINT8 re_xid_continue_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 254, 255, 255, 135, 254, 255, 255, 7, - 0, 4, 160, 4, 255, 255, 127, 255, 255, 255, 255, 255, 195, 255, 3, 0, - 31, 80, 0, 0, 255, 255, 223, 56, 192, 215, 255, 255, 251, 255, 255, 255, - 255, 255, 191, 255, 251, 252, 255, 255, 255, 0, 254, 255, 255, 255, 127, 2, - 254, 255, 255, 255, 255, 255, 255, 191, 182, 0, 255, 255, 255, 7, 7, 0, - 0, 0, 255, 7, 255, 195, 255, 255, 255, 255, 239, 159, 255, 253, 255, 159, - 0, 0, 255, 255, 255, 231, 255, 255, 255, 255, 3, 0, 255, 255, 63, 4, - 255, 63, 0, 0, 255, 255, 255, 15, 253, 31, 0, 0, 240, 255, 255, 127, - 207, 255, 254, 254, 238, 159, 249, 255, 255, 253, 197, 243, 159, 121, 128, 176, - 207, 255, 3, 0, 238, 135, 249, 255, 255, 253, 109, 211, 135, 57, 2, 94, - 192, 255, 63, 0, 238, 191, 251, 255, 255, 253, 237, 243, 191, 59, 1, 0, - 207, 255, 0, 0, 159, 57, 192, 176, 207, 255, 2, 0, 236, 199, 61, 214, - 24, 199, 255, 195, 199, 61, 129, 0, 192, 255, 0, 0, 238, 223, 253, 255, - 255, 253, 239, 227, 223, 61, 96, 3, 236, 223, 253, 255, 255, 253, 239, 243, - 223, 61, 96, 64, 207, 255, 6, 0, 255, 255, 255, 231, 223, 125, 128, 0, - 207, 255, 0, 252, 236, 255, 127, 252, 255, 255, 251, 47, 127, 132, 95, 255, - 0, 0, 12, 0, 255, 255, 255, 7, 255, 127, 255, 3, 150, 37, 240, 254, - 174, 236, 255, 59, 95, 63, 255, 243, 1, 0, 0, 3, 255, 3, 160, 194, - 255, 254, 255, 255, 255, 31, 254, 255, 223, 255, 255, 254, 255, 255, 255, 31, - 64, 0, 0, 0, 255, 3, 255, 255, 255, 255, 255, 63, 191, 32, 255, 255, - 255, 255, 255, 247, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 0, 254, 3, 0, 255, 255, 0, 0, - 255, 255, 31, 0, 255, 159, 255, 255, 255, 199, 1, 0, 255, 223, 31, 0, - 255, 255, 15, 0, 255, 223, 13, 0, 255, 255, 143, 48, 255, 3, 0, 0, - 0, 56, 255, 3, 255, 255, 255, 0, 255, 7, 255, 255, 255, 255, 63, 0, - 255, 15, 255, 15, 192, 255, 255, 255, 255, 63, 31, 0, 255, 15, 255, 255, - 255, 3, 255, 7, 255, 255, 255, 127, 255, 255, 255, 159, 255, 3, 255, 3, - 128, 0, 0, 0, 255, 15, 255, 3, 0, 248, 15, 0, 255, 227, 255, 255, - 0, 0, 247, 255, 255, 255, 127, 0, 127, 0, 0, 240, 255, 255, 63, 63, - 63, 63, 255, 170, 255, 255, 223, 95, 220, 31, 207, 15, 255, 31, 220, 31, - 0, 0, 0, 128, 1, 0, 16, 0, 0, 0, 2, 128, 0, 0, 255, 31, - 226, 255, 1, 0, 132, 252, 47, 63, 80, 253, 255, 243, 224, 67, 0, 0, - 255, 1, 0, 0, 255, 127, 255, 255, 31, 248, 15, 0, 255, 128, 0, 128, - 127, 127, 127, 127, 224, 0, 0, 0, 254, 255, 62, 31, 255, 255, 127, 230, - 224, 255, 255, 255, 255, 63, 254, 255, 255, 127, 0, 0, 255, 31, 0, 0, - 255, 31, 255, 255, 255, 15, 0, 0, 255, 255, 240, 191, 255, 255, 255, 128, - 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 255, 255, 0, 0, 0, 31, 0, 255, 3, 255, 255, 255, 8, - 255, 63, 255, 255, 1, 128, 255, 3, 255, 63, 255, 3, 255, 255, 127, 12, - 7, 0, 0, 56, 255, 255, 124, 0, 126, 126, 126, 0, 127, 127, 0, 0, - 255, 55, 255, 3, 15, 0, 255, 255, 127, 248, 255, 255, 255, 255, 255, 3, - 127, 0, 248, 224, 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, - 240, 255, 255, 255, 255, 255, 252, 255, 127, 0, 24, 0, 0, 224, 0, 0, - 0, 0, 138, 170, 252, 252, 252, 28, 255, 239, 255, 255, 127, 255, 255, 183, - 255, 63, 255, 63, 0, 0, 0, 32, 255, 255, 1, 0, 15, 255, 62, 0, - 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 255, 192, 111, 240, 239, 254, - 255, 255, 15, 135, 255, 255, 7, 0, 127, 0, 0, 0, 255, 1, 255, 3, - 255, 255, 223, 255, 7, 0, 0, 0, 255, 255, 255, 1, 31, 0, 255, 255, - 0, 128, 255, 255, 3, 0, 0, 0, 224, 227, 7, 248, 231, 15, 0, 0, - 0, 60, 0, 0, 28, 0, 0, 0, 255, 255, 255, 223, 100, 222, 255, 235, - 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, 95, 252, 253, 255, - 63, 255, 255, 255, 253, 255, 255, 247, 255, 253, 255, 255, 247, 207, 255, 255, - 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, - 238, 251, 255, 15, -}; - -/* XID_Continue: 1902 bytes. */ - -RE_UINT32 re_get_xid_continue(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_xid_continue_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_xid_continue_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_xid_continue_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_xid_continue_stage_4[pos + f] << 5; - pos += code; - value = (re_xid_continue_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Default_Ignorable_Code_Point. */ - -static RE_UINT8 re_default_ignorable_code_point_stage_1[] = { - 0, 1, 1, 2, 1, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, -}; - -static RE_UINT8 re_default_ignorable_code_point_stage_2[] = { - 0, 1, 2, 3, 4, 1, 5, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 6, 1, 1, 7, 1, 1, 1, 1, 1, - 8, 8, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_default_ignorable_code_point_stage_3[] = { - 0, 1, 1, 2, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 4, 1, 1, 1, 1, 1, 5, 6, 1, 1, 1, 1, 1, 1, 1, - 7, 1, 1, 1, 1, 1, 1, 1, 1, 8, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 9, 10, 1, 11, 1, 1, 1, 1, 1, 1, - 12, 12, 12, 12, 12, 12, 12, 12, -}; - -static RE_UINT8 re_default_ignorable_code_point_stage_4[] = { - 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 2, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 0, 0, - 7, 0, 0, 0, 0, 0, 0, 0, 8, 9, 0, 10, 0, 0, 0, 0, - 0, 0, 0, 11, 0, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 4, - 0, 0, 0, 0, 0, 5, 0, 12, 0, 0, 0, 13, 0, 0, 0, 0, - 14, 14, 14, 14, 14, 14, 14, 14, -}; - -static RE_UINT8 re_default_ignorable_code_point_stage_5[] = { - 0, 0, 0, 0, 0, 32, 0, 0, 0, 128, 0, 0, 0, 0, 0, 16, - 0, 0, 0, 128, 1, 0, 0, 0, 0, 0, 48, 0, 0, 120, 0, 0, - 0, 248, 0, 0, 0, 124, 0, 0, 255, 255, 0, 0, 16, 0, 0, 0, - 0, 0, 255, 1, 0, 0, 248, 7, 255, 255, 255, 255, -}; - -/* Default_Ignorable_Code_Point: 344 bytes. */ - -RE_UINT32 re_get_default_ignorable_code_point(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 14; - code = ch ^ (f << 14); - pos = (RE_UINT32)re_default_ignorable_code_point_stage_1[f] << 3; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_default_ignorable_code_point_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_default_ignorable_code_point_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_default_ignorable_code_point_stage_4[pos + f] << 5; - pos += code; - value = (re_default_ignorable_code_point_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Grapheme_Extend. */ - -static RE_UINT8 re_grapheme_extend_stage_1[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, 4, 4, 4, - 4, 4, -}; - -static RE_UINT8 re_grapheme_extend_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 8, 9, 7, 7, 7, 7, 7, 7, 7, 7, 7, 10, - 11, 12, 13, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 14, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 15, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 16, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, -}; - -static RE_UINT8 re_grapheme_extend_stage_3[] = { - 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, - 14, 0, 0, 15, 0, 0, 0, 16, 17, 18, 19, 20, 21, 22, 0, 0, - 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 25, 0, 0, - 26, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 27, 0, 28, 29, 30, 31, 0, 0, 0, 0, - 0, 0, 0, 32, 0, 0, 33, 34, 0, 35, 0, 0, 0, 0, 0, 0, - 0, 0, 36, 0, 0, 0, 0, 0, 37, 38, 0, 0, 0, 0, 39, 0, - 0, 0, 0, 0, 0, 0, 0, 40, 0, 41, 42, 0, 0, 0, 0, 0, - 0, 43, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_grapheme_extend_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 2, 0, 0, 0, 0, - 0, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 4, 5, 6, 0, - 7, 0, 8, 9, 0, 0, 10, 11, 12, 13, 14, 0, 0, 15, 0, 16, - 17, 18, 19, 0, 0, 0, 0, 20, 21, 22, 23, 24, 25, 26, 27, 24, - 28, 29, 30, 31, 28, 29, 32, 24, 25, 33, 34, 24, 35, 36, 37, 0, - 0, 38, 39, 24, 0, 40, 41, 24, 0, 36, 27, 24, 0, 0, 42, 0, - 0, 43, 44, 0, 0, 45, 46, 0, 47, 48, 0, 49, 50, 51, 52, 0, - 0, 53, 54, 55, 56, 0, 0, 0, 0, 0, 57, 0, 0, 0, 0, 0, - 58, 58, 59, 59, 0, 60, 61, 0, 62, 0, 0, 0, 0, 63, 0, 0, - 0, 64, 0, 0, 0, 0, 0, 0, 65, 0, 66, 67, 0, 0, 0, 0, - 68, 69, 35, 16, 70, 71, 0, 72, 0, 73, 0, 0, 0, 0, 74, 75, - 0, 0, 0, 0, 0, 0, 1, 76, 77, 0, 0, 0, 0, 0, 13, 78, - 0, 0, 0, 0, 0, 0, 0, 79, 0, 0, 0, 80, 0, 0, 0, 1, - 0, 81, 0, 0, 82, 0, 0, 0, 0, 0, 0, 83, 80, 0, 0, 84, - 85, 86, 0, 0, 0, 0, 87, 88, 0, 89, 90, 0, 21, 91, 0, 0, - 0, 92, 93, 0, 0, 94, 25, 95, 0, 0, 0, 0, 0, 0, 0, 96, - 36, 0, 0, 0, 0, 0, 0, 0, 2, 97, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 38, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 98, - 99, 100, 0, 0, 0, 0, 0, 0, 25, 101, 97, 0, 70, 102, 0, 0, - 21, 103, 0, 0, 70, 104, 0, 0, 0, 0, 0, 0, 0, 105, 0, 0, - 0, 0, 0, 0, 106, 0, 0, 0, 0, 0, 0, 107, 108, 109, 0, 0, - 0, 0, 110, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 2, -}; - -static RE_UINT8 re_grapheme_extend_stage_5[] = { - 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 0, 0, 248, 3, 0, 0, - 0, 0, 254, 255, 255, 255, 255, 191, 182, 0, 0, 0, 0, 0, 255, 7, - 0, 248, 255, 255, 0, 0, 1, 0, 0, 0, 192, 159, 159, 61, 0, 0, - 0, 0, 2, 0, 0, 0, 255, 255, 255, 7, 0, 0, 192, 255, 1, 0, - 0, 248, 15, 0, 0, 0, 192, 251, 239, 62, 0, 0, 0, 0, 0, 14, - 240, 255, 255, 127, 7, 0, 0, 0, 0, 0, 0, 20, 254, 33, 254, 0, - 12, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 80, 30, 32, 128, 0, - 6, 0, 0, 0, 0, 0, 0, 16, 134, 57, 2, 0, 0, 0, 35, 0, - 190, 33, 0, 0, 0, 0, 0, 208, 30, 32, 192, 0, 4, 0, 0, 0, - 0, 0, 0, 64, 1, 32, 128, 0, 0, 0, 0, 192, 193, 61, 96, 0, - 0, 0, 0, 144, 68, 48, 96, 0, 0, 132, 92, 128, 0, 0, 242, 7, - 128, 127, 0, 0, 0, 0, 242, 27, 0, 63, 0, 0, 0, 0, 0, 3, - 0, 0, 160, 2, 0, 0, 254, 127, 223, 224, 255, 254, 255, 255, 255, 31, - 64, 0, 0, 0, 0, 224, 253, 102, 0, 0, 0, 195, 1, 0, 30, 0, - 100, 32, 0, 32, 0, 0, 0, 224, 0, 0, 28, 0, 0, 0, 12, 0, - 0, 0, 176, 63, 64, 254, 15, 32, 0, 56, 0, 0, 0, 2, 0, 0, - 135, 1, 4, 14, 0, 0, 128, 9, 0, 0, 64, 127, 229, 31, 248, 159, - 15, 0, 0, 0, 0, 0, 208, 23, 3, 0, 0, 0, 60, 11, 0, 0, - 64, 163, 3, 0, 0, 240, 207, 0, 0, 0, 247, 255, 253, 33, 16, 0, - 127, 0, 0, 240, 0, 48, 0, 0, 255, 255, 1, 0, 0, 128, 3, 0, - 0, 0, 0, 128, 0, 252, 0, 0, 0, 0, 0, 6, 0, 128, 247, 63, - 0, 0, 3, 0, 68, 8, 0, 0, 96, 0, 0, 0, 16, 0, 0, 0, - 255, 255, 3, 0, 192, 63, 0, 0, 128, 255, 3, 0, 0, 0, 200, 19, - 0, 126, 102, 0, 8, 16, 0, 0, 0, 0, 157, 193, 0, 48, 64, 0, - 32, 33, 0, 0, 127, 0, 0, 0, 0, 0, 0, 32, 110, 240, 0, 0, - 0, 0, 0, 135, 0, 0, 0, 255, 0, 0, 120, 6, 128, 239, 31, 0, - 0, 0, 192, 127, 0, 40, 191, 0, 0, 128, 7, 0, 160, 195, 7, 248, - 231, 15, 0, 0, 0, 60, 0, 0, 28, 0, 0, 0, -}; - -/* Grapheme_Extend: 1062 bytes. */ - -RE_UINT32 re_get_grapheme_extend(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_grapheme_extend_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_grapheme_extend_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_grapheme_extend_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_grapheme_extend_stage_4[pos + f] << 5; - pos += code; - value = (re_grapheme_extend_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Grapheme_Base. */ - -static RE_UINT8 re_grapheme_base_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, -}; - -static RE_UINT8 re_grapheme_base_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 24, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 25, 7, 26, 27, 13, 13, 13, 13, 13, 13, 13, 28, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_grapheme_base_stage_3[] = { - 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, - 15, 1, 16, 17, 1, 1, 18, 19, 20, 21, 22, 23, 24, 25, 1, 26, - 27, 28, 1, 29, 30, 1, 1, 31, 1, 1, 1, 32, 33, 34, 35, 36, - 37, 38, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 40, 1, 1, 1, 1, 1, 1, 1, 1, 1, 41, - 1, 1, 1, 1, 42, 1, 43, 44, 45, 46, 47, 48, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 49, 50, 50, 50, 50, 50, 50, 50, 50, - 50, 1, 51, 52, 1, 53, 54, 55, 56, 57, 58, 59, 60, 50, 50, 50, - 61, 62, 63, 64, 65, 50, 66, 50, 67, 68, 50, 50, 50, 50, 69, 50, - 1, 1, 1, 70, 71, 50, 50, 50, 1, 1, 1, 1, 72, 50, 50, 50, - 1, 1, 73, 50, 50, 50, 50, 74, 75, 50, 50, 50, 50, 50, 50, 50, - 76, 77, 78, 79, 80, 81, 82, 83, 50, 50, 50, 50, 50, 50, 84, 50, - 85, 86, 87, 88, 89, 90, 91, 92, 1, 1, 1, 1, 1, 1, 93, 1, - 1, 1, 1, 1, 1, 1, 1, 94, 95, 50, 50, 50, 50, 50, 50, 50, - 1, 1, 95, 50, 50, 50, 50, 50, -}; - -static RE_UINT8 re_grapheme_base_stage_4[] = { - 0, 1, 1, 2, 0, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 0, 0, 0, 4, 5, 6, 1, 1, 1, 1, 1, 1, 7, 1, 1, 1, - 1, 8, 9, 10, 11, 12, 13, 14, 15, 1, 16, 17, 1, 1, 18, 19, - 20, 21, 22, 1, 1, 23, 1, 24, 25, 26, 27, 0, 0, 28, 0, 0, - 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, - 33, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, - 56, 60, 61, 62, 63, 64, 65, 66, 10, 67, 68, 0, 69, 70, 71, 0, - 72, 73, 74, 75, 76, 77, 78, 0, 1, 79, 80, 81, 82, 1, 83, 1, - 1, 1, 84, 1, 85, 86, 87, 1, 88, 1, 89, 90, 91, 1, 1, 92, - 1, 1, 1, 1, 90, 1, 1, 93, 94, 95, 96, 97, 1, 98, 99, 100, - 101, 1, 1, 102, 1, 103, 1, 104, 90, 105, 106, 107, 1, 108, 109, 1, - 110, 1, 111, 112, 100, 113, 0, 0, 114, 115, 116, 117, 118, 119, 1, 120, - 1, 121, 122, 1, 0, 0, 123, 124, 1, 1, 1, 1, 1, 1, 0, 0, - 125, 1, 126, 127, 1, 128, 129, 130, 131, 132, 1, 133, 134, 89, 0, 0, - 1, 1, 1, 1, 135, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 136, - 1, 137, 16, 1, 1, 1, 1, 1, 10, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 138, 0, 0, 0, 0, 0, 1, 139, 2, 1, 1, 1, 1, 140, - 1, 83, 1, 141, 142, 143, 143, 0, 1, 144, 0, 0, 145, 1, 1, 136, - 1, 1, 1, 1, 1, 1, 104, 146, 1, 135, 10, 1, 147, 1, 1, 1, - 148, 149, 1, 1, 139, 89, 1, 150, 2, 1, 1, 1, 1, 1, 1, 2, - 1, 1, 1, 1, 1, 104, 1, 1, 1, 1, 1, 1, 1, 1, 151, 0, - 1, 1, 1, 1, 152, 1, 153, 1, 1, 154, 1, 155, 102, 1, 1, 156, - 1, 1, 1, 1, 157, 16, 0, 158, 159, 160, 1, 102, 1, 1, 161, 162, - 1, 163, 164, 90, 29, 165, 166, 0, 1, 167, 168, 144, 1, 169, 170, 171, - 172, 173, 0, 0, 0, 0, 1, 174, 1, 1, 1, 1, 1, 150, 175, 144, - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 176, 1, 1, 91, 0, - 177, 178, 179, 1, 1, 1, 180, 1, 1, 1, 181, 1, 182, 1, 183, 184, - 185, 181, 186, 187, 1, 1, 1, 90, 10, 1, 1, 1, 127, 2, 188, 189, - 190, 191, 192, 0, 1, 1, 1, 89, 193, 194, 1, 1, 195, 0, 181, 90, - 0, 0, 0, 0, 90, 1, 93, 0, 2, 150, 16, 0, 196, 1, 197, 0, - 1, 1, 1, 1, 127, 198, 0, 0, 199, 200, 201, 0, 0, 0, 0, 0, - 202, 203, 0, 0, 1, 204, 0, 0, 205, 136, 206, 1, 0, 0, 0, 0, - 1, 207, 208, 209, 0, 0, 0, 0, 1, 1, 210, 0, 0, 0, 0, 0, - 0, 0, 0, 2, 0, 0, 0, 0, 211, 102, 212, 21, 118, 213, 214, 215, - 29, 216, 217, 0, 118, 218, 215, 0, 0, 0, 0, 0, 1, 219, 198, 0, - 1, 1, 1, 220, 0, 0, 0, 0, 1, 1, 1, 221, 0, 0, 0, 0, - 1, 220, 0, 0, 0, 0, 0, 0, 1, 222, 0, 0, 0, 0, 0, 0, - 1, 1, 223, 2, 224, 0, 0, 0, 225, 0, 0, 0, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 1, 1, 104, 1, 226, 1, 227, 228, 229, 127, 0, - 1, 1, 230, 0, 0, 0, 0, 0, 1, 1, 142, 96, 0, 0, 0, 0, - 1, 1, 128, 1, 231, 232, 233, 1, 234, 235, 236, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 237, 1, 1, 1, 1, 1, 1, 1, 1, 238, 1, - 233, 239, 240, 241, 242, 243, 0, 244, 1, 108, 1, 1, 136, 245, 246, 0, - 131, 139, 1, 108, 89, 0, 0, 247, 248, 89, 249, 0, 0, 0, 0, 0, - 1, 250, 1, 90, 136, 1, 251, 93, 1, 2, 211, 1, 1, 1, 1, 252, - 1, 127, 150, 183, 0, 0, 0, 253, 1, 1, 254, 0, 1, 1, 255, 0, - 1, 1, 1, 136, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 142, 0, - 1, 92, 1, 1, 1, 1, 1, 1, 127, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_grapheme_base_stage_5[] = { - 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 127, 255, 223, 255, 255, - 0, 0, 255, 124, 240, 215, 255, 255, 251, 255, 255, 255, 7, 252, 255, 255, - 255, 0, 254, 255, 255, 255, 127, 254, 254, 255, 255, 255, 255, 134, 0, 0, - 0, 0, 0, 64, 73, 0, 255, 255, 255, 7, 31, 0, 192, 255, 0, 200, - 255, 7, 0, 0, 255, 255, 254, 255, 255, 255, 63, 64, 96, 194, 255, 255, - 255, 63, 253, 255, 255, 255, 0, 0, 0, 224, 255, 255, 63, 0, 2, 0, - 255, 7, 240, 7, 255, 255, 63, 4, 16, 1, 255, 127, 255, 255, 255, 65, - 253, 31, 0, 0, 248, 255, 255, 255, 255, 255, 255, 235, 1, 222, 1, 255, - 243, 255, 255, 254, 236, 159, 249, 255, 255, 253, 197, 163, 129, 89, 0, 176, - 195, 255, 255, 15, 232, 135, 249, 255, 255, 253, 109, 195, 1, 0, 0, 94, - 192, 255, 28, 0, 232, 191, 251, 255, 255, 253, 237, 227, 1, 26, 1, 0, - 195, 255, 3, 0, 255, 253, 237, 35, 129, 25, 0, 176, 195, 255, 255, 0, - 232, 199, 61, 214, 24, 199, 255, 131, 198, 29, 1, 0, 192, 255, 255, 7, - 238, 223, 253, 255, 255, 253, 239, 35, 30, 0, 0, 3, 195, 255, 0, 255, - 236, 223, 253, 255, 255, 253, 239, 99, 155, 13, 0, 64, 195, 255, 6, 0, - 255, 255, 255, 167, 193, 93, 0, 0, 195, 255, 63, 254, 236, 255, 127, 252, - 255, 255, 251, 47, 127, 0, 3, 127, 0, 0, 28, 0, 255, 255, 13, 128, - 127, 128, 255, 15, 150, 37, 240, 254, 174, 236, 13, 32, 95, 0, 255, 243, - 255, 255, 255, 252, 255, 255, 95, 253, 255, 254, 255, 255, 255, 31, 0, 128, - 32, 31, 0, 0, 0, 0, 0, 192, 191, 223, 255, 7, 255, 31, 2, 153, - 255, 255, 255, 60, 254, 255, 225, 255, 155, 223, 255, 223, 191, 32, 255, 255, - 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, 61, 255, 127, 255, - 255, 255, 61, 255, 255, 255, 255, 7, 255, 255, 255, 31, 255, 255, 255, 3, - 255, 255, 31, 0, 255, 255, 1, 0, 255, 223, 3, 0, 255, 255, 99, 0, - 255, 255, 3, 0, 255, 223, 1, 0, 255, 255, 79, 192, 191, 1, 240, 31, - 255, 3, 255, 3, 255, 7, 255, 3, 255, 255, 255, 0, 255, 5, 255, 255, - 255, 255, 63, 0, 120, 14, 251, 1, 241, 255, 255, 255, 255, 63, 31, 0, - 255, 15, 255, 255, 255, 3, 255, 199, 255, 255, 127, 198, 255, 255, 191, 0, - 26, 224, 7, 0, 255, 63, 0, 0, 240, 255, 255, 255, 255, 255, 47, 232, - 251, 15, 255, 255, 255, 7, 240, 31, 252, 255, 255, 255, 195, 244, 255, 255, - 191, 92, 12, 240, 255, 15, 48, 248, 255, 227, 255, 255, 255, 0, 8, 0, - 2, 222, 111, 0, 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 255, 63, - 255, 255, 223, 255, 223, 255, 207, 239, 255, 255, 220, 127, 255, 7, 255, 255, - 255, 128, 255, 255, 0, 0, 243, 255, 255, 127, 255, 31, 255, 3, 255, 255, - 255, 255, 15, 0, 127, 0, 0, 0, 255, 31, 255, 3, 255, 127, 255, 255, - 255, 127, 12, 254, 255, 128, 1, 0, 255, 255, 127, 0, 127, 127, 127, 127, - 255, 255, 255, 15, 255, 255, 255, 251, 0, 0, 255, 15, 255, 255, 127, 248, - 224, 255, 255, 255, 255, 63, 254, 255, 15, 0, 255, 255, 255, 31, 0, 0, - 255, 31, 255, 255, 127, 0, 255, 255, 255, 15, 0, 0, 255, 127, 8, 192, - 255, 255, 252, 0, 255, 127, 15, 0, 0, 0, 0, 255, 187, 247, 255, 255, - 159, 15, 255, 3, 15, 192, 255, 3, 0, 0, 252, 15, 63, 192, 255, 255, - 127, 0, 12, 128, 255, 255, 55, 236, 255, 191, 255, 195, 255, 129, 25, 0, - 247, 47, 255, 243, 255, 255, 98, 62, 5, 0, 0, 248, 255, 207, 63, 0, - 126, 126, 126, 0, 127, 127, 0, 0, 223, 30, 255, 3, 127, 248, 255, 255, - 255, 63, 255, 255, 127, 0, 248, 160, 255, 255, 127, 95, 219, 255, 255, 255, - 3, 0, 248, 255, 0, 0, 255, 255, 255, 255, 252, 255, 255, 0, 0, 0, - 0, 0, 255, 63, 0, 0, 255, 3, 255, 255, 247, 255, 127, 15, 223, 255, - 252, 252, 252, 28, 127, 127, 0, 48, 255, 239, 255, 255, 127, 255, 255, 183, - 255, 63, 255, 63, 135, 255, 255, 255, 255, 255, 143, 255, 255, 7, 255, 15, - 255, 255, 255, 191, 15, 255, 63, 0, 255, 3, 0, 0, 63, 253, 255, 255, - 255, 255, 191, 145, 255, 255, 191, 255, 255, 255, 255, 143, 255, 255, 255, 131, - 255, 255, 255, 192, 1, 0, 239, 254, 255, 0, 255, 1, 255, 255, 63, 254, - 255, 255, 63, 255, 255, 255, 7, 255, 255, 1, 0, 0, 253, 255, 255, 255, - 128, 63, 252, 255, 255, 255, 135, 217, 3, 0, 255, 255, 255, 1, 255, 3, - 127, 16, 192, 255, 15, 0, 0, 0, 255, 255, 63, 128, 255, 215, 64, 0, - 255, 127, 0, 0, 7, 0, 15, 0, 255, 255, 255, 1, 31, 0, 255, 255, - 0, 0, 248, 255, 3, 0, 0, 0, 127, 254, 255, 255, 95, 60, 0, 0, - 24, 240, 255, 255, 255, 195, 255, 255, 35, 0, 0, 0, 255, 255, 255, 223, - 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, - 95, 252, 253, 255, 63, 255, 255, 255, 255, 207, 255, 255, 150, 254, 247, 10, - 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, 238, 251, 255, 15, - 0, 0, 3, 0, 255, 127, 254, 127, 254, 255, 254, 255, 192, 255, 255, 255, - 7, 0, 255, 255, 255, 1, 3, 0, 1, 0, 191, 255, 223, 7, 0, 0, - 255, 255, 255, 30, 0, 0, 0, 248, 225, 255, 0, 0, 63, 0, 0, 0, -}; - -/* Grapheme_Base: 2169 bytes. */ - -RE_UINT32 re_get_grapheme_base(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_grapheme_base_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_grapheme_base_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_grapheme_base_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_grapheme_base_stage_4[pos + f] << 5; - pos += code; - value = (re_grapheme_base_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Grapheme_Link. */ - -static RE_UINT8 re_grapheme_link_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_grapheme_link_stage_2[] = { - 0, 1, 2, 3, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 6, 7, 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, -}; - -static RE_UINT8 re_grapheme_link_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 3, 4, - 5, 0, 0, 0, 0, 0, 0, 6, 0, 0, 7, 8, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 9, 0, 0, 10, 11, 12, 13, 0, 0, 0, 0, - 0, 0, 14, 0, 0, 0, 0, 0, 15, 16, 0, 0, 0, 0, 17, 0, -}; - -static RE_UINT8 re_grapheme_link_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, - 0, 0, 1, 0, 0, 0, 2, 0, 0, 3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 4, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, - 6, 6, 0, 0, 0, 0, 7, 0, 0, 0, 0, 8, 0, 0, 0, 0, - 0, 0, 4, 0, 0, 9, 0, 10, 0, 0, 0, 11, 0, 0, 0, 0, - 12, 0, 0, 0, 0, 0, 4, 0, 0, 0, 13, 0, 0, 0, 8, 0, - 0, 0, 0, 0, 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 0, 1, - 0, 11, 0, 0, 0, 0, 0, 0, 0, 0, 12, 0, 0, 15, 0, 0, - 0, 16, 0, 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 14, 0, 0, -}; - -static RE_UINT8 re_grapheme_link_stage_5[] = { - 0, 0, 0, 0, 0, 32, 0, 0, 0, 4, 0, 0, 0, 0, 0, 4, - 16, 0, 0, 0, 0, 0, 0, 6, 0, 0, 16, 0, 0, 0, 4, 0, - 1, 0, 0, 0, 0, 12, 0, 0, 0, 0, 12, 0, 0, 0, 0, 128, - 64, 0, 0, 0, 0, 0, 8, 0, 0, 0, 64, 0, 0, 0, 0, 2, - 0, 0, 24, 0, -}; - -/* Grapheme_Link: 374 bytes. */ - -RE_UINT32 re_get_grapheme_link(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_grapheme_link_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_grapheme_link_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_grapheme_link_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_grapheme_link_stage_4[pos + f] << 5; - pos += code; - value = (re_grapheme_link_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* White_Space. */ - -static RE_UINT8 re_white_space_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_white_space_stage_2[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_white_space_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_white_space_stage_4[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 3, 1, 1, 1, 1, 1, 4, 5, 1, 1, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_white_space_stage_5[] = { - 0, 62, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 32, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 255, 7, 0, 0, 0, 131, 0, 0, 0, 0, 0, 128, 0, 0, 0, 0, -}; - -/* White_Space: 169 bytes. */ - -RE_UINT32 re_get_white_space(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_white_space_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_white_space_stage_2[pos + f] << 4; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_white_space_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_white_space_stage_4[pos + f] << 6; - pos += code; - value = (re_white_space_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Bidi_Control. */ - -static RE_UINT8 re_bidi_control_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_bidi_control_stage_2[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_bidi_control_stage_3[] = { - 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_bidi_control_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 2, 3, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_bidi_control_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, - 0, 192, 0, 0, 0, 124, 0, 0, 0, 0, 0, 0, 192, 3, 0, 0, -}; - -/* Bidi_Control: 129 bytes. */ - -RE_UINT32 re_get_bidi_control(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_bidi_control_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_bidi_control_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_bidi_control_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_bidi_control_stage_4[pos + f] << 6; - pos += code; - value = (re_bidi_control_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Join_Control. */ - -static RE_UINT8 re_join_control_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_join_control_stage_2[] = { - 0, 0, 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, -}; - -static RE_UINT8 re_join_control_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_join_control_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_join_control_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 48, 0, 0, 0, 0, 0, 0, -}; - -/* Join_Control: 97 bytes. */ - -RE_UINT32 re_get_join_control(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_join_control_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_join_control_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_join_control_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_join_control_stage_4[pos + f] << 6; - pos += code; - value = (re_join_control_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Dash. */ - -static RE_UINT8 re_dash_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_dash_stage_2[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_dash_stage_3[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 3, 1, 4, 1, 1, 1, - 5, 6, 1, 1, 1, 1, 1, 7, 8, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 9, -}; - -static RE_UINT8 re_dash_stage_4[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 2, 1, 3, 1, 1, 1, 1, 1, 1, 1, - 4, 1, 1, 1, 1, 1, 1, 1, 5, 6, 7, 1, 1, 1, 1, 1, - 8, 1, 1, 1, 1, 1, 1, 1, 9, 1, 1, 1, 1, 1, 1, 1, - 10, 1, 11, 1, 1, 1, 1, 1, 12, 13, 1, 1, 14, 1, 1, 1, -}; - -static RE_UINT8 re_dash_stage_5[] = { - 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 4, 0, 0, 0, 0, 0, 64, 1, 0, 0, 0, 0, 0, 0, 0, - 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 63, 0, 0, 0, 0, 0, - 0, 0, 8, 0, 0, 0, 0, 8, 0, 8, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 128, 4, 0, 0, 0, 12, - 0, 0, 0, 16, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 6, 0, 0, 0, 0, 1, 8, 0, 0, 0, - 0, 32, 0, 0, 0, 0, 0, 0, -}; - -/* Dash: 297 bytes. */ - -RE_UINT32 re_get_dash(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_dash_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_dash_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_dash_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_dash_stage_4[pos + f] << 6; - pos += code; - value = (re_dash_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Hyphen. */ - -static RE_UINT8 re_hyphen_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_hyphen_stage_2[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_hyphen_stage_3[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 1, 1, 1, - 4, 1, 1, 1, 1, 1, 1, 5, 6, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, -}; - -static RE_UINT8 re_hyphen_stage_4[] = { - 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 2, 1, 3, 1, 1, 1, 1, 1, 1, 1, - 4, 1, 1, 1, 1, 1, 1, 1, 5, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 6, 1, 1, 1, 1, 1, 7, 1, 1, 8, 9, 1, 1, -}; - -static RE_UINT8 re_hyphen_stage_5[] = { - 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 4, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 128, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 8, 0, 0, 0, 0, 8, 0, 0, 0, - 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 0, 0, 0, -}; - -/* Hyphen: 241 bytes. */ - -RE_UINT32 re_get_hyphen(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_hyphen_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_hyphen_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_hyphen_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_hyphen_stage_4[pos + f] << 6; - pos += code; - value = (re_hyphen_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Quotation_Mark. */ - -static RE_UINT8 re_quotation_mark_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_quotation_mark_stage_2[] = { - 0, 1, 2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_quotation_mark_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 1, 1, 1, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 4, -}; - -static RE_UINT8 re_quotation_mark_stage_4[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, - 1, 5, 1, 1, 6, 7, 1, 1, -}; - -static RE_UINT8 re_quotation_mark_stage_5[] = { - 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 8, 0, 8, 0, 0, 0, 255, 0, 0, 0, 6, - 0, 240, 0, 224, 0, 0, 0, 0, 30, 0, 0, 0, 0, 0, 0, 0, - 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 0, 0, 0, -}; - -/* Quotation_Mark: 193 bytes. */ - -RE_UINT32 re_get_quotation_mark(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_quotation_mark_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_quotation_mark_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_quotation_mark_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_quotation_mark_stage_4[pos + f] << 6; - pos += code; - value = (re_quotation_mark_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Terminal_Punctuation. */ - -static RE_UINT8 re_terminal_punctuation_stage_1[] = { - 0, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, -}; - -static RE_UINT8 re_terminal_punctuation_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 9, 10, 11, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 12, 13, 9, 9, 9, 9, 9, - 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 14, - 15, 9, 16, 9, 17, 9, 9, 9, 9, 18, 9, 9, 9, 9, 9, 9, -}; - -static RE_UINT8 re_terminal_punctuation_stage_3[] = { - 0, 1, 1, 1, 1, 1, 2, 3, 1, 1, 1, 4, 5, 6, 7, 8, - 9, 1, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 11, 1, 12, 1, - 13, 1, 1, 1, 1, 1, 14, 1, 1, 1, 1, 1, 15, 16, 1, 17, - 18, 1, 19, 1, 1, 20, 21, 1, 22, 1, 1, 1, 1, 1, 1, 1, - 23, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 24, 1, 1, 1, 25, 1, 1, 1, 1, 1, 1, 1, - 1, 26, 1, 1, 27, 28, 1, 1, 29, 30, 31, 32, 33, 34, 1, 35, - 1, 1, 1, 1, 36, 1, 37, 1, 1, 1, 1, 1, 1, 1, 1, 38, - 39, 1, 40, 1, 1, 1, 41, 1, 42, 43, 44, 45, 1, 1, 1, 1, - 46, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_terminal_punctuation_stage_4[] = { - 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 3, 0, 0, 0, - 4, 0, 5, 0, 6, 0, 0, 0, 0, 0, 7, 0, 8, 0, 0, 0, - 0, 0, 0, 9, 0, 10, 2, 0, 0, 0, 0, 11, 0, 0, 12, 0, - 13, 0, 0, 0, 0, 0, 14, 0, 0, 0, 0, 15, 0, 0, 0, 16, - 0, 0, 0, 17, 0, 0, 18, 0, 19, 0, 0, 0, 0, 0, 11, 0, - 0, 20, 0, 0, 0, 0, 21, 0, 0, 22, 0, 23, 0, 24, 25, 0, - 0, 26, 0, 0, 27, 0, 0, 0, 0, 0, 0, 23, 28, 0, 0, 0, - 0, 0, 0, 29, 0, 0, 0, 30, 0, 0, 31, 0, 0, 32, 0, 0, - 0, 0, 25, 0, 0, 0, 33, 0, 0, 0, 34, 35, 0, 0, 0, 36, - 0, 0, 37, 0, 1, 0, 0, 38, 34, 0, 39, 0, 0, 0, 40, 0, - 34, 0, 0, 0, 0, 41, 0, 0, 0, 0, 42, 0, 0, 23, 43, 0, - 0, 0, 44, 0, 0, 0, 45, 0, 0, 0, 0, 46, -}; - -static RE_UINT8 re_terminal_punctuation_stage_5[] = { - 0, 0, 0, 0, 2, 80, 0, 140, 0, 0, 0, 64, 128, 0, 0, 0, - 0, 2, 0, 0, 8, 0, 0, 0, 0, 16, 0, 136, 0, 0, 16, 0, - 255, 23, 0, 0, 0, 0, 0, 3, 0, 0, 255, 127, 48, 0, 0, 0, - 0, 0, 0, 12, 0, 225, 7, 0, 0, 12, 0, 0, 254, 1, 0, 0, - 0, 96, 0, 0, 0, 56, 0, 0, 0, 0, 112, 4, 60, 3, 0, 0, - 0, 15, 0, 0, 0, 0, 0, 236, 0, 0, 0, 248, 0, 0, 0, 192, - 0, 0, 0, 48, 128, 3, 0, 0, 0, 64, 0, 0, 6, 0, 0, 0, - 0, 224, 0, 0, 0, 0, 248, 0, 0, 0, 192, 0, 0, 192, 0, 0, - 0, 128, 0, 0, 0, 0, 0, 224, 0, 0, 0, 128, 0, 0, 3, 0, - 0, 8, 0, 0, 0, 0, 247, 0, 18, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 128, 0, 0, 0, 0, 252, 128, 63, 0, 0, 3, 0, 0, 0, - 14, 0, 0, 0, 96, 0, 0, 0, 0, 0, 15, 0, -}; - -/* Terminal_Punctuation: 676 bytes. */ - -RE_UINT32 re_get_terminal_punctuation(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 14; - code = ch ^ (f << 14); - pos = (RE_UINT32)re_terminal_punctuation_stage_1[f] << 4; - f = code >> 10; - code ^= f << 10; - pos = (RE_UINT32)re_terminal_punctuation_stage_2[pos + f] << 3; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_terminal_punctuation_stage_3[pos + f] << 2; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_terminal_punctuation_stage_4[pos + f] << 5; - pos += code; - value = (re_terminal_punctuation_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Math. */ - -static RE_UINT8 re_other_math_stage_1[] = { - 0, 1, 2, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, -}; - -static RE_UINT8 re_other_math_stage_2[] = { - 0, 1, 1, 1, 2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, 1, 1, 6, 1, 1, -}; - -static RE_UINT8 re_other_math_stage_3[] = { - 0, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 3, 4, 1, 5, 1, 6, 7, 8, 1, 9, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 10, 11, 1, 1, 1, 1, 12, 13, 14, 15, - 1, 1, 1, 1, 1, 1, 16, 1, -}; - -static RE_UINT8 re_other_math_stage_4[] = { - 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 2, 3, 4, 5, 6, 7, 8, 0, 9, 10, - 11, 12, 13, 0, 14, 15, 16, 17, 18, 0, 0, 0, 0, 19, 20, 21, - 0, 0, 0, 0, 0, 22, 23, 24, 25, 0, 26, 27, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 25, 28, 0, 0, 0, 0, 29, 0, 30, 31, - 0, 0, 0, 32, 0, 0, 0, 0, 0, 33, 0, 0, 0, 0, 0, 0, - 34, 34, 35, 34, 36, 37, 38, 34, 39, 40, 41, 34, 34, 34, 34, 34, - 34, 34, 34, 34, 34, 42, 43, 44, 35, 35, 45, 45, 46, 46, 47, 34, - 38, 48, 49, 50, 51, 52, 0, 0, -}; - -static RE_UINT8 re_other_math_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 39, 0, 0, 0, 51, 0, - 0, 0, 64, 0, 0, 0, 28, 0, 1, 0, 0, 0, 30, 0, 0, 96, - 0, 96, 0, 0, 0, 0, 255, 31, 98, 248, 0, 0, 132, 252, 47, 62, - 16, 179, 251, 241, 224, 3, 0, 0, 0, 0, 224, 243, 182, 62, 195, 240, - 255, 63, 235, 47, 48, 0, 0, 0, 0, 15, 0, 0, 0, 0, 176, 0, - 0, 0, 1, 0, 4, 0, 0, 0, 3, 192, 127, 240, 193, 140, 15, 0, - 148, 31, 0, 0, 96, 0, 0, 0, 5, 0, 0, 0, 15, 96, 0, 0, - 192, 255, 0, 0, 248, 255, 255, 1, 0, 0, 0, 15, 0, 0, 0, 48, - 10, 1, 0, 0, 0, 0, 0, 80, 255, 255, 255, 255, 255, 255, 223, 255, - 255, 255, 255, 223, 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, - 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, - 255, 255, 255, 247, 255, 127, 255, 255, 255, 253, 255, 255, 247, 207, 255, 255, - 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, - 238, 251, 255, 15, -}; - -/* Other_Math: 502 bytes. */ - -RE_UINT32 re_get_other_math(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_other_math_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_other_math_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_other_math_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_other_math_stage_4[pos + f] << 5; - pos += code; - value = (re_other_math_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Hex_Digit. */ - -static RE_UINT8 re_hex_digit_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_hex_digit_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_hex_digit_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 2, -}; - -static RE_UINT8 re_hex_digit_stage_4[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 2, 1, -}; - -static RE_UINT8 re_hex_digit_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 126, 0, 0, 0, 126, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 255, 3, 126, 0, 0, 0, 126, 0, 0, 0, 0, 0, 0, 0, -}; - -/* Hex_Digit: 129 bytes. */ - -RE_UINT32 re_get_hex_digit(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_hex_digit_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_hex_digit_stage_2[pos + f] << 3; - f = code >> 10; - code ^= f << 10; - pos = (RE_UINT32)re_hex_digit_stage_3[pos + f] << 3; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_hex_digit_stage_4[pos + f] << 7; - pos += code; - value = (re_hex_digit_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* ASCII_Hex_Digit. */ - -static RE_UINT8 re_ascii_hex_digit_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_ascii_hex_digit_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_ascii_hex_digit_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_ascii_hex_digit_stage_4[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_ascii_hex_digit_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 126, 0, 0, 0, 126, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -/* ASCII_Hex_Digit: 97 bytes. */ - -RE_UINT32 re_get_ascii_hex_digit(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_ascii_hex_digit_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_ascii_hex_digit_stage_2[pos + f] << 3; - f = code >> 10; - code ^= f << 10; - pos = (RE_UINT32)re_ascii_hex_digit_stage_3[pos + f] << 3; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_ascii_hex_digit_stage_4[pos + f] << 7; - pos += code; - value = (re_ascii_hex_digit_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Alphabetic. */ - -static RE_UINT8 re_other_alphabetic_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, -}; - -static RE_UINT8 re_other_alphabetic_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 7, 8, 6, 6, 6, 6, 6, 6, 6, 6, 6, 9, - 6, 10, 11, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 12, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, -}; - -static RE_UINT8 re_other_alphabetic_stage_3[] = { - 0, 0, 0, 1, 0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, - 13, 0, 0, 14, 0, 0, 0, 15, 16, 17, 18, 19, 20, 0, 0, 0, - 0, 0, 0, 0, 21, 0, 0, 0, 0, 0, 0, 0, 0, 22, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 0, - 24, 25, 26, 27, 0, 0, 0, 0, 0, 0, 0, 28, 0, 0, 0, 0, - 0, 0, 29, 0, 0, 0, 0, 0, 30, 31, 0, 0, 0, 0, 32, 0, - 0, 0, 0, 0, 0, 0, 0, 33, -}; - -static RE_UINT8 re_other_alphabetic_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 3, 0, 4, 0, 5, 6, 0, 0, 7, 8, - 9, 10, 0, 0, 0, 11, 0, 0, 12, 13, 0, 0, 0, 0, 0, 14, - 15, 16, 17, 18, 19, 20, 21, 18, 19, 20, 22, 23, 19, 20, 24, 18, - 19, 20, 25, 18, 26, 20, 27, 0, 19, 20, 28, 18, 18, 20, 28, 18, - 18, 20, 29, 18, 18, 0, 30, 31, 0, 32, 33, 0, 0, 34, 33, 0, - 0, 0, 0, 35, 36, 37, 0, 0, 0, 38, 39, 40, 41, 0, 0, 0, - 0, 0, 42, 0, 0, 0, 0, 0, 31, 31, 31, 31, 0, 43, 44, 0, - 0, 0, 0, 0, 0, 45, 0, 0, 0, 46, 0, 0, 0, 10, 47, 0, - 48, 0, 49, 50, 0, 0, 0, 0, 51, 52, 15, 0, 53, 54, 0, 55, - 0, 56, 0, 0, 0, 0, 0, 31, 0, 0, 0, 0, 0, 43, 57, 58, - 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, 0, 59, 42, 0, 0, 0, - 0, 60, 0, 0, 61, 62, 15, 0, 0, 63, 64, 0, 15, 62, 0, 0, - 0, 65, 66, 0, 0, 67, 0, 68, 0, 0, 0, 0, 0, 0, 0, 69, - 70, 0, 0, 0, 0, 0, 0, 0, 71, 0, 0, 0, 0, 0, 0, 0, - 53, 72, 73, 0, 26, 74, 0, 0, 53, 64, 0, 0, 53, 75, 0, 0, - 0, 0, 0, 0, 0, 76, 0, 0, 0, 0, 35, 77, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_alphabetic_stage_5[] = { - 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 255, 191, 182, 0, 0, 0, - 0, 0, 255, 7, 0, 248, 255, 254, 0, 0, 1, 0, 0, 0, 192, 31, - 158, 33, 0, 0, 0, 0, 2, 0, 0, 0, 255, 255, 192, 255, 1, 0, - 0, 0, 192, 248, 239, 30, 0, 0, 240, 3, 255, 127, 15, 0, 0, 0, - 0, 0, 0, 204, 255, 223, 224, 0, 12, 0, 0, 0, 14, 0, 0, 0, - 0, 0, 0, 192, 159, 25, 128, 0, 135, 25, 2, 0, 0, 0, 35, 0, - 191, 27, 0, 0, 159, 25, 192, 0, 4, 0, 0, 0, 199, 29, 128, 0, - 223, 29, 96, 0, 223, 29, 128, 0, 0, 128, 95, 255, 0, 0, 12, 0, - 0, 0, 242, 7, 0, 32, 0, 0, 0, 0, 242, 27, 0, 0, 254, 255, - 3, 224, 255, 254, 255, 255, 255, 31, 0, 248, 127, 121, 0, 0, 192, 195, - 133, 1, 30, 0, 124, 0, 0, 48, 0, 0, 0, 128, 0, 0, 192, 255, - 255, 1, 0, 0, 0, 2, 0, 0, 255, 15, 255, 1, 1, 3, 0, 0, - 0, 0, 128, 15, 0, 0, 224, 127, 254, 255, 31, 0, 31, 0, 0, 0, - 0, 0, 224, 255, 7, 0, 0, 0, 254, 51, 0, 0, 128, 255, 3, 0, - 240, 255, 63, 0, 255, 255, 255, 255, 255, 3, 0, 0, 0, 0, 240, 15, - 248, 0, 0, 0, 3, 0, 0, 0, 0, 0, 240, 255, 192, 7, 0, 0, - 128, 255, 7, 0, 0, 254, 127, 0, 8, 48, 0, 0, 0, 0, 157, 65, - 0, 248, 32, 0, 248, 7, 0, 0, 0, 0, 0, 64, 110, 240, 0, 0, - 0, 0, 0, 255, 63, 0, 0, 0, 0, 0, 255, 1, 0, 0, 248, 255, - 0, 248, 63, 0, 255, 255, 255, 127, -}; - -/* Other_Alphabetic: 786 bytes. */ - -RE_UINT32 re_get_other_alphabetic(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_other_alphabetic_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_other_alphabetic_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_other_alphabetic_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_other_alphabetic_stage_4[pos + f] << 5; - pos += code; - value = (re_other_alphabetic_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Ideographic. */ - -static RE_UINT8 re_ideographic_stage_1[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_ideographic_stage_2[] = { - 0, 0, 0, 1, 2, 3, 3, 3, 3, 4, 0, 0, 0, 0, 0, 5, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 6, 7, 0, 0, 0, 8, -}; - -static RE_UINT8 re_ideographic_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 4, 0, 0, 0, 0, 5, 6, 0, 0, - 2, 2, 2, 7, 2, 2, 2, 2, 2, 2, 2, 8, 9, 0, 0, 0, - 0, 0, 0, 0, 2, 9, 0, 0, -}; - -static RE_UINT8 re_ideographic_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 0, - 2, 2, 2, 2, 2, 2, 2, 4, 0, 0, 0, 0, 2, 2, 2, 2, - 2, 5, 2, 6, 0, 0, 0, 0, 2, 2, 2, 7, 2, 2, 2, 2, - 2, 2, 2, 2, 8, 2, 2, 2, 9, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_ideographic_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 192, 0, 0, 0, 254, 3, 0, 7, - 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 63, 0, - 255, 31, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255, 255, 63, 255, 255, - 255, 255, 255, 3, 0, 0, 0, 0, 255, 255, 127, 0, 0, 0, 0, 0, - 255, 255, 255, 255, 255, 255, 31, 0, 255, 255, 255, 63, 0, 0, 0, 0, -}; - -/* Ideographic: 297 bytes. */ - -RE_UINT32 re_get_ideographic(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_ideographic_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_ideographic_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_ideographic_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_ideographic_stage_4[pos + f] << 6; - pos += code; - value = (re_ideographic_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Diacritic. */ - -static RE_UINT8 re_diacritic_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_diacritic_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 7, 8, 4, 4, 4, 4, 4, 4, 4, 4, 4, 9, - 4, 4, 10, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 11, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 12, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_diacritic_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 1, 1, 1, 1, 1, 17, 1, 18, 19, 20, 21, 22, 1, 23, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 24, 1, 25, 1, - 26, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 27, 28, - 29, 30, 31, 32, 1, 1, 1, 1, 1, 1, 1, 33, 1, 1, 34, 35, - 36, 37, 1, 1, 1, 1, 38, 1, 1, 1, 1, 1, 1, 1, 1, 39, - 1, 40, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_diacritic_stage_4[] = { - 0, 0, 1, 2, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, 5, 5, 5, 5, 6, 7, 8, 0, 0, 0, - 0, 0, 0, 0, 9, 0, 0, 0, 0, 0, 10, 0, 11, 12, 13, 0, - 0, 0, 14, 0, 0, 0, 15, 16, 0, 4, 17, 0, 0, 18, 0, 19, - 20, 0, 0, 0, 0, 0, 0, 21, 0, 22, 23, 24, 0, 22, 25, 0, - 0, 22, 25, 0, 0, 22, 25, 0, 0, 22, 25, 0, 0, 0, 25, 0, - 0, 0, 25, 0, 0, 22, 25, 0, 0, 0, 25, 0, 0, 0, 26, 0, - 0, 0, 27, 0, 0, 0, 28, 0, 20, 29, 0, 0, 30, 0, 31, 0, - 0, 32, 0, 0, 33, 0, 0, 0, 0, 0, 0, 0, 0, 0, 34, 0, - 0, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 36, 0, 0, 0, 0, - 0, 37, 38, 39, 0, 40, 0, 0, 0, 41, 0, 42, 0, 0, 4, 43, - 0, 44, 5, 17, 0, 0, 45, 46, 0, 0, 0, 0, 0, 47, 48, 49, - 0, 0, 0, 0, 0, 0, 0, 50, 0, 51, 0, 0, 0, 0, 0, 0, - 0, 52, 0, 0, 53, 0, 0, 22, 0, 0, 0, 54, 0, 0, 0, 55, - 56, 57, 0, 0, 58, 0, 0, 20, 0, 0, 0, 0, 0, 0, 38, 59, - 0, 60, 61, 0, 0, 61, 2, 0, 0, 0, 0, 62, 0, 15, 63, 64, - 0, 0, 0, 0, 0, 0, 0, 65, 1, 0, 0, 0, 0, 0, 0, 0, - 0, 66, 0, 0, 0, 0, 0, 0, 0, 1, 2, 67, 68, 0, 0, 69, - 0, 0, 0, 0, 0, 70, 0, 0, 0, 71, 0, 0, 0, 0, 2, 0, - 0, 0, 0, 0, 0, 41, 0, 0, 0, 0, 0, 0, 72, 0, 0, 0, - 0, 0, 0, 73, 74, 75, 0, 0, -}; - -static RE_UINT8 re_diacritic_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 64, 1, 0, 0, 0, 0, 129, 144, 1, - 0, 0, 255, 255, 255, 255, 255, 255, 255, 127, 255, 224, 7, 0, 48, 4, - 48, 0, 0, 0, 248, 0, 0, 0, 0, 0, 0, 2, 0, 0, 254, 255, - 251, 255, 255, 191, 22, 0, 0, 0, 0, 248, 135, 1, 0, 0, 0, 128, - 97, 28, 0, 0, 255, 7, 0, 0, 192, 255, 1, 0, 0, 248, 63, 0, - 0, 0, 0, 3, 240, 255, 255, 127, 0, 0, 0, 16, 0, 32, 30, 0, - 0, 0, 2, 0, 0, 32, 0, 0, 0, 4, 0, 0, 128, 95, 0, 0, - 0, 31, 0, 0, 0, 0, 160, 194, 220, 0, 0, 0, 64, 0, 0, 0, - 0, 0, 128, 6, 128, 191, 0, 12, 0, 254, 15, 32, 0, 0, 0, 14, - 0, 0, 224, 159, 0, 0, 16, 0, 16, 0, 0, 0, 0, 248, 15, 0, - 0, 12, 0, 0, 0, 0, 192, 0, 0, 0, 0, 63, 255, 33, 16, 0, - 0, 240, 255, 255, 240, 255, 0, 0, 0, 0, 0, 224, 0, 0, 0, 160, - 3, 224, 0, 224, 0, 224, 0, 96, 0, 128, 3, 0, 0, 128, 0, 0, - 0, 252, 0, 0, 0, 0, 0, 30, 0, 128, 0, 176, 0, 0, 3, 0, - 0, 0, 128, 255, 3, 0, 0, 0, 0, 1, 0, 0, 255, 255, 3, 0, - 0, 120, 0, 0, 0, 0, 8, 0, 0, 0, 0, 8, 7, 0, 0, 0, - 0, 0, 64, 0, 0, 48, 0, 0, 127, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 192, 8, 0, 0, 0, 0, 0, 0, 6, 0, 0, 24, 0, - 0, 128, 255, 255, 128, 227, 7, 248, 231, 15, 0, 0, 0, 60, 0, 0, -}; - -/* Diacritic: 849 bytes. */ - -RE_UINT32 re_get_diacritic(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_diacritic_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_diacritic_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_diacritic_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_diacritic_stage_4[pos + f] << 5; - pos += code; - value = (re_diacritic_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Extender. */ - -static RE_UINT8 re_extender_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_extender_stage_2[] = { - 0, 1, 2, 3, 2, 2, 4, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 5, 6, 2, 2, 2, 2, 2, 2, 2, 2, 2, 7, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_extender_stage_3[] = { - 0, 1, 2, 1, 1, 1, 3, 4, 1, 1, 1, 1, 1, 1, 5, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 6, 1, 7, 1, 8, 1, 1, 1, - 9, 1, 1, 1, 1, 1, 1, 1, 10, 1, 1, 1, 1, 1, 11, 1, - 1, 12, 13, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 14, -}; - -static RE_UINT8 re_extender_stage_4[] = { - 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, 5, 0, 0, 0, 5, 0, - 6, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 0, 0, - 0, 9, 0, 10, 0, 0, 0, 0, 11, 12, 0, 0, 13, 0, 0, 14, - 15, 0, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 17, 0, 0, 0, 0, 18, 0, 0, 19, 20, - 0, 0, 0, 18, 0, 0, 0, 0, -}; - -static RE_UINT8 re_extender_stage_5[] = { - 0, 0, 0, 0, 0, 0, 128, 0, 0, 0, 3, 0, 1, 0, 0, 0, - 0, 0, 0, 4, 64, 0, 0, 0, 0, 4, 0, 0, 8, 0, 0, 0, - 128, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 8, 32, 0, 0, 0, - 0, 0, 62, 0, 0, 0, 0, 96, 0, 0, 0, 112, 0, 0, 32, 0, - 0, 16, 0, 0, 0, 128, 0, 0, 0, 0, 1, 0, 0, 0, 0, 32, - 0, 0, 24, 0, -}; - -/* Extender: 349 bytes. */ - -RE_UINT32 re_get_extender(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_extender_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_extender_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_extender_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_extender_stage_4[pos + f] << 5; - pos += code; - value = (re_extender_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Lowercase. */ - -static RE_UINT8 re_other_lowercase_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_other_lowercase_stage_2[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 4, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_other_lowercase_stage_3[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 2, - 4, 2, 5, 2, 2, 2, 6, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 7, 2, 2, 2, 2, -}; - -static RE_UINT8 re_other_lowercase_stage_4[] = { - 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 2, 3, 0, 4, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 6, 7, 0, - 0, 8, 9, 0, 0, 10, 0, 0, 0, 0, 0, 11, 0, 0, 0, 0, - 0, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 0, 14, -}; - -static RE_UINT8 re_other_lowercase_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 4, - 0, 0, 0, 0, 0, 0, 255, 1, 3, 0, 0, 0, 31, 0, 0, 0, - 32, 0, 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 240, 255, 255, - 255, 255, 255, 255, 255, 7, 0, 1, 0, 0, 0, 248, 255, 255, 255, 255, - 0, 0, 0, 0, 0, 0, 2, 128, 0, 0, 255, 31, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 255, 255, 0, 0, 255, 255, 255, 3, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 48, 0, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 0, 0, 0, 0, 3, -}; - -/* Other_Lowercase: 273 bytes. */ - -RE_UINT32 re_get_other_lowercase(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_lowercase_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_other_lowercase_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_other_lowercase_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_other_lowercase_stage_4[pos + f] << 6; - pos += code; - value = (re_other_lowercase_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Uppercase. */ - -static RE_UINT8 re_other_uppercase_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_other_uppercase_stage_2[] = { - 0, 0, 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, -}; - -static RE_UINT8 re_other_uppercase_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 1, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_uppercase_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 1, 0, -}; - -static RE_UINT8 re_other_uppercase_stage_5[] = { - 0, 0, 0, 0, 255, 255, 0, 0, 0, 0, 192, 255, -}; - -/* Other_Uppercase: 117 bytes. */ - -RE_UINT32 re_get_other_uppercase(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_uppercase_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_other_uppercase_stage_2[pos + f] << 4; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_other_uppercase_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_other_uppercase_stage_4[pos + f] << 5; - pos += code; - value = (re_other_uppercase_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Noncharacter_Code_Point. */ - -static RE_UINT8 re_noncharacter_code_point_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_noncharacter_code_point_stage_2[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, -}; - -static RE_UINT8 re_noncharacter_code_point_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, - 0, 0, 0, 0, 0, 0, 0, 2, -}; - -static RE_UINT8 re_noncharacter_code_point_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, 0, 2, -}; - -static RE_UINT8 re_noncharacter_code_point_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 192, -}; - -/* Noncharacter_Code_Point: 121 bytes. */ - -RE_UINT32 re_get_noncharacter_code_point(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_noncharacter_code_point_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_noncharacter_code_point_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_noncharacter_code_point_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_noncharacter_code_point_stage_4[pos + f] << 6; - pos += code; - value = (re_noncharacter_code_point_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Grapheme_Extend. */ - -static RE_UINT8 re_other_grapheme_extend_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_other_grapheme_extend_stage_2[] = { - 0, 1, 2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_other_grapheme_extend_stage_3[] = { - 0, 0, 0, 0, 1, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 6, 7, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_grapheme_extend_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, - 0, 0, 0, 0, 1, 2, 1, 2, 0, 0, 0, 3, 1, 2, 0, 4, - 5, 0, 0, 0, 0, 0, 0, 0, 6, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 8, 0, 0, -}; - -static RE_UINT8 re_other_grapheme_extend_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, - 0, 0, 128, 0, 0, 0, 0, 0, 4, 0, 96, 0, 0, 0, 0, 0, - 0, 128, 0, 128, 0, 0, 0, 0, 0, 48, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 192, 0, 0, 0, 0, 0, 192, 0, 0, 0, 0, - 0, 0, 0, 0, 32, 192, 7, 0, -}; - -/* Other_Grapheme_Extend: 249 bytes. */ - -RE_UINT32 re_get_other_grapheme_extend(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_grapheme_extend_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_other_grapheme_extend_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_other_grapheme_extend_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_other_grapheme_extend_stage_4[pos + f] << 6; - pos += code; - value = (re_other_grapheme_extend_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* IDS_Binary_Operator. */ - -static RE_UINT8 re_ids_binary_operator_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_ids_binary_operator_stage_2[] = { - 0, 0, 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, -}; - -static RE_UINT8 re_ids_binary_operator_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, -}; - -static RE_UINT8 re_ids_binary_operator_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, -}; - -static RE_UINT8 re_ids_binary_operator_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 243, 15, -}; - -/* IDS_Binary_Operator: 97 bytes. */ - -RE_UINT32 re_get_ids_binary_operator(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_ids_binary_operator_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_ids_binary_operator_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_ids_binary_operator_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_ids_binary_operator_stage_4[pos + f] << 6; - pos += code; - value = (re_ids_binary_operator_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* IDS_Trinary_Operator. */ - -static RE_UINT8 re_ids_trinary_operator_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_ids_trinary_operator_stage_2[] = { - 0, 0, 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, -}; - -static RE_UINT8 re_ids_trinary_operator_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, -}; - -static RE_UINT8 re_ids_trinary_operator_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, -}; - -static RE_UINT8 re_ids_trinary_operator_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 0, -}; - -/* IDS_Trinary_Operator: 97 bytes. */ - -RE_UINT32 re_get_ids_trinary_operator(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_ids_trinary_operator_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_ids_trinary_operator_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_ids_trinary_operator_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_ids_trinary_operator_stage_4[pos + f] << 6; - pos += code; - value = (re_ids_trinary_operator_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Radical. */ - -static RE_UINT8 re_radical_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_radical_stage_2[] = { - 0, 0, 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, -}; - -static RE_UINT8 re_radical_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, -}; - -static RE_UINT8 re_radical_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 2, 2, 3, 2, 2, 2, 2, 2, 2, 4, 0, -}; - -static RE_UINT8 re_radical_stage_5[] = { - 0, 0, 0, 0, 255, 255, 255, 251, 255, 255, 255, 255, 255, 255, 15, 0, - 255, 255, 63, 0, -}; - -/* Radical: 117 bytes. */ - -RE_UINT32 re_get_radical(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_radical_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_radical_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_radical_stage_3[pos + f] << 4; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_radical_stage_4[pos + f] << 5; - pos += code; - value = (re_radical_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Unified_Ideograph. */ - -static RE_UINT8 re_unified_ideograph_stage_1[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_unified_ideograph_stage_2[] = { - 0, 0, 0, 1, 2, 3, 3, 3, 3, 4, 0, 0, 0, 0, 0, 5, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 6, 7, 0, 0, 0, 0, -}; - -static RE_UINT8 re_unified_ideograph_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 3, 0, 0, 0, 0, 0, 4, 0, 0, - 1, 1, 1, 5, 1, 1, 1, 1, 1, 1, 1, 6, 7, 0, 0, 0, -}; - -static RE_UINT8 re_unified_ideograph_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 2, 0, 1, 1, 1, 1, 1, 1, 1, 3, - 4, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 5, 1, 1, 1, 1, - 1, 1, 1, 1, 6, 1, 1, 1, 7, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_unified_ideograph_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 255, - 255, 255, 255, 255, 255, 255, 63, 0, 255, 31, 0, 0, 0, 0, 0, 0, - 0, 192, 26, 128, 154, 3, 0, 0, 255, 255, 127, 0, 0, 0, 0, 0, - 255, 255, 255, 255, 255, 255, 31, 0, 255, 255, 255, 63, 0, 0, 0, 0, -}; - -/* Unified_Ideograph: 257 bytes. */ - -RE_UINT32 re_get_unified_ideograph(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_unified_ideograph_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_unified_ideograph_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_unified_ideograph_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_unified_ideograph_stage_4[pos + f] << 6; - pos += code; - value = (re_unified_ideograph_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_Default_Ignorable_Code_Point. */ - -static RE_UINT8 re_other_default_ignorable_code_point_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, - 1, -}; - -static RE_UINT8 re_other_default_ignorable_code_point_stage_2[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 6, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_other_default_ignorable_code_point_stage_3[] = { - 0, 1, 0, 0, 0, 0, 0, 0, 2, 0, 0, 3, 0, 0, 0, 0, - 4, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, - 7, 8, 8, 8, 8, 8, 8, 8, -}; - -static RE_UINT8 re_other_default_ignorable_code_point_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, - 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, - 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, - 0, 0, 0, 0, 0, 0, 6, 7, 8, 0, 9, 9, 0, 0, 0, 10, - 9, 9, 9, 9, 9, 9, 9, 9, -}; - -static RE_UINT8 re_other_default_ignorable_code_point_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 128, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 48, 0, - 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, - 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 1, - 253, 255, 255, 255, 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 255, - 0, 0, 0, 0, 0, 0, 255, 255, -}; - -/* Other_Default_Ignorable_Code_Point: 281 bytes. */ - -RE_UINT32 re_get_other_default_ignorable_code_point(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_default_ignorable_code_point_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_other_default_ignorable_code_point_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_other_default_ignorable_code_point_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_other_default_ignorable_code_point_stage_4[pos + f] << 6; - pos += code; - value = (re_other_default_ignorable_code_point_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Deprecated. */ - -static RE_UINT8 re_deprecated_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, - 1, 1, -}; - -static RE_UINT8 re_deprecated_stage_2[] = { - 0, 1, 2, 3, 4, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 5, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_deprecated_stage_3[] = { - 0, 1, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 3, - 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, - 5, 0, 0, 6, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_deprecated_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, - 0, 6, 0, 0, 0, 0, 0, 0, 7, 8, 8, 8, 0, 0, 0, 0, -}; - -static RE_UINT8 re_deprecated_stage_5[] = { - 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 8, 0, 0, 0, 128, 2, - 24, 0, 0, 0, 0, 252, 0, 0, 0, 6, 0, 0, 2, 0, 0, 0, - 255, 255, 255, 255, -}; - -/* Deprecated: 230 bytes. */ - -RE_UINT32 re_get_deprecated(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_deprecated_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_deprecated_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_deprecated_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_deprecated_stage_4[pos + f] << 5; - pos += code; - value = (re_deprecated_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Soft_Dotted. */ - -static RE_UINT8 re_soft_dotted_stage_1[] = { - 0, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, -}; - -static RE_UINT8 re_soft_dotted_stage_2[] = { - 0, 1, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_soft_dotted_stage_3[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 5, 6, 7, 5, 8, 9, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 10, 5, 5, 5, 5, 5, 5, 5, 11, 12, 13, 5, -}; - -static RE_UINT8 re_soft_dotted_stage_4[] = { - 0, 0, 0, 1, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 4, 5, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, - 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 9, 10, 11, 0, 0, 0, 12, 0, 0, 0, 0, 13, 0, - 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 15, 0, 0, 0, 0, 0, - 0, 0, 0, 16, 0, 0, 0, 0, 0, 17, 18, 0, 19, 20, 0, 21, - 0, 22, 23, 0, 24, 0, 17, 18, 0, 19, 20, 0, 21, 0, 0, 0, -}; - -static RE_UINT8 re_soft_dotted_stage_5[] = { - 0, 0, 0, 0, 0, 6, 0, 0, 0, 128, 0, 0, 0, 2, 0, 0, - 0, 1, 0, 0, 0, 0, 0, 32, 0, 0, 4, 0, 0, 0, 8, 0, - 0, 0, 64, 1, 4, 0, 0, 0, 0, 0, 64, 0, 16, 1, 0, 0, - 0, 32, 0, 0, 0, 8, 0, 0, 0, 0, 2, 0, 0, 3, 0, 0, - 0, 0, 0, 16, 12, 0, 0, 0, 0, 0, 192, 0, 0, 12, 0, 0, - 0, 0, 0, 192, 0, 0, 12, 0, 192, 0, 0, 0, 0, 0, 0, 12, - 0, 192, 0, 0, -}; - -/* Soft_Dotted: 342 bytes. */ - -RE_UINT32 re_get_soft_dotted(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_soft_dotted_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_soft_dotted_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_soft_dotted_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_soft_dotted_stage_4[pos + f] << 5; - pos += code; - value = (re_soft_dotted_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Logical_Order_Exception. */ - -static RE_UINT8 re_logical_order_exception_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_logical_order_exception_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_logical_order_exception_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 0, 0, -}; - -static RE_UINT8 re_logical_order_exception_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, - 0, 0, 2, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_logical_order_exception_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 31, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 96, 26, -}; - -/* Logical_Order_Exception: 121 bytes. */ - -RE_UINT32 re_get_logical_order_exception(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_logical_order_exception_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_logical_order_exception_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_logical_order_exception_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_logical_order_exception_stage_4[pos + f] << 6; - pos += code; - value = (re_logical_order_exception_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_ID_Start. */ - -static RE_UINT8 re_other_id_start_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_other_id_start_stage_2[] = { - 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_id_start_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_id_start_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, - 0, 0, 2, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_other_id_start_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 64, 0, 0, - 0, 0, 0, 24, 0, 0, 0, 0, -}; - -/* Other_ID_Start: 113 bytes. */ - -RE_UINT32 re_get_other_id_start(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_id_start_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_other_id_start_stage_2[pos + f] << 4; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_other_id_start_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_other_id_start_stage_4[pos + f] << 6; - pos += code; - value = (re_other_id_start_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Other_ID_Continue. */ - -static RE_UINT8 re_other_id_continue_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_other_id_continue_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_other_id_continue_stage_3[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 3, 2, 2, 4, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_other_id_continue_stage_4[] = { - 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 4, -}; - -static RE_UINT8 re_other_id_continue_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 0, - 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 254, 3, 0, - 0, 0, 0, 4, 0, 0, 0, 0, -}; - -/* Other_ID_Continue: 145 bytes. */ - -RE_UINT32 re_get_other_id_continue(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_other_id_continue_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_other_id_continue_stage_2[pos + f] << 4; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_other_id_continue_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_other_id_continue_stage_4[pos + f] << 6; - pos += code; - value = (re_other_id_continue_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* STerm. */ - -static RE_UINT8 re_sterm_stage_1[] = { - 0, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, -}; - -static RE_UINT8 re_sterm_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 3, 3, 9, 10, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 11, 12, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 13, - 3, 3, 14, 3, 15, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -}; - -static RE_UINT8 re_sterm_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, 7, - 1, 1, 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 9, 1, 1, 1, 1, 1, 10, 1, 1, 1, 1, 1, 11, 1, 12, 1, - 13, 1, 14, 1, 1, 15, 16, 1, 17, 1, 1, 1, 1, 1, 1, 1, - 18, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 19, 1, 1, 1, - 20, 1, 1, 1, 1, 1, 1, 1, 1, 21, 1, 1, 22, 23, 1, 1, - 24, 25, 26, 27, 28, 29, 1, 30, 1, 1, 1, 1, 31, 1, 32, 1, - 1, 1, 1, 1, 33, 1, 1, 1, 34, 35, 36, 37, 1, 1, 1, 1, -}; - -static RE_UINT8 re_sterm_stage_4[] = { - 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 3, 0, 0, 0, - 4, 0, 0, 0, 0, 0, 5, 0, 6, 0, 0, 0, 0, 0, 0, 7, - 0, 0, 0, 8, 0, 0, 9, 0, 0, 0, 0, 10, 0, 0, 0, 11, - 0, 12, 0, 0, 13, 0, 0, 0, 0, 0, 8, 0, 0, 14, 0, 0, - 0, 0, 15, 0, 0, 16, 0, 17, 0, 18, 19, 0, 0, 11, 0, 0, - 20, 0, 0, 0, 0, 0, 0, 4, 21, 0, 0, 0, 0, 0, 0, 22, - 0, 0, 0, 23, 0, 0, 21, 0, 0, 24, 0, 0, 0, 0, 25, 0, - 0, 0, 26, 0, 0, 0, 0, 27, 0, 0, 0, 28, 0, 0, 29, 0, - 1, 0, 0, 30, 0, 0, 23, 0, 0, 0, 31, 0, 0, 17, 32, 0, - 0, 0, 33, 0, 0, 0, 34, 0, -}; - -static RE_UINT8 re_sterm_stage_5[] = { - 0, 0, 0, 0, 2, 64, 0, 128, 0, 0, 0, 80, 0, 2, 0, 0, - 0, 0, 0, 128, 0, 0, 16, 0, 7, 0, 0, 0, 0, 0, 0, 2, - 48, 0, 0, 0, 0, 12, 0, 0, 132, 1, 0, 0, 0, 64, 0, 0, - 0, 0, 96, 0, 8, 2, 0, 0, 0, 15, 0, 0, 0, 0, 0, 204, - 0, 0, 0, 24, 0, 0, 0, 192, 0, 0, 0, 48, 128, 3, 0, 0, - 4, 0, 0, 0, 0, 192, 0, 0, 0, 0, 136, 0, 0, 0, 192, 0, - 0, 128, 0, 0, 0, 3, 0, 0, 0, 0, 0, 224, 0, 0, 3, 0, - 0, 8, 0, 0, 0, 0, 196, 0, 2, 0, 0, 0, 128, 1, 0, 0, - 3, 0, 0, 0, 14, 0, 0, 0, 96, 0, 0, 0, -}; - -/* STerm: 568 bytes. */ - -RE_UINT32 re_get_sterm(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 14; - code = ch ^ (f << 14); - pos = (RE_UINT32)re_sterm_stage_1[f] << 4; - f = code >> 10; - code ^= f << 10; - pos = (RE_UINT32)re_sterm_stage_2[pos + f] << 3; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_sterm_stage_3[pos + f] << 2; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_sterm_stage_4[pos + f] << 5; - pos += code; - value = (re_sterm_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Variation_Selector. */ - -static RE_UINT8 re_variation_selector_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, - 1, -}; - -static RE_UINT8 re_variation_selector_stage_2[] = { - 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_variation_selector_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 2, 3, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_variation_selector_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 3, 4, -}; - -static RE_UINT8 re_variation_selector_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 56, 0, 0, 0, 0, 0, 0, - 255, 255, 0, 0, 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 255, - 255, 255, 255, 255, 255, 255, 0, 0, -}; - -/* Variation_Selector: 169 bytes. */ - -RE_UINT32 re_get_variation_selector(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_variation_selector_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_variation_selector_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_variation_selector_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_variation_selector_stage_4[pos + f] << 6; - pos += code; - value = (re_variation_selector_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Pattern_White_Space. */ - -static RE_UINT8 re_pattern_white_space_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_pattern_white_space_stage_2[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_pattern_white_space_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_pattern_white_space_stage_4[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_pattern_white_space_stage_5[] = { - 0, 62, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 32, 0, 0, 0, 0, 0, 0, 0, 0, 192, 0, 0, 0, 3, 0, 0, -}; - -/* Pattern_White_Space: 129 bytes. */ - -RE_UINT32 re_get_pattern_white_space(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_pattern_white_space_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_pattern_white_space_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_pattern_white_space_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_pattern_white_space_stage_4[pos + f] << 6; - pos += code; - value = (re_pattern_white_space_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Pattern_Syntax. */ - -static RE_UINT8 re_pattern_syntax_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_pattern_syntax_stage_2[] = { - 0, 1, 1, 1, 2, 3, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_pattern_syntax_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 3, 4, 4, 5, 4, 4, 6, 4, 4, 4, 4, 1, 1, 7, 1, - 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 9, 10, 1, -}; - -static RE_UINT8 re_pattern_syntax_stage_4[] = { - 0, 1, 2, 2, 0, 3, 4, 4, 0, 0, 0, 0, 0, 0, 0, 0, - 5, 6, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 8, 8, 8, - 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 0, 0, 0, 0, 0, - 8, 8, 8, 9, 10, 8, 8, 8, 8, 8, 8, 8, 0, 0, 0, 0, - 11, 12, 0, 0, 0, 0, 0, 0, 0, 13, 0, 0, 0, 0, 0, 0, - 0, 0, 14, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_pattern_syntax_stage_5[] = { - 0, 0, 0, 0, 254, 255, 0, 252, 1, 0, 0, 120, 254, 90, 67, 136, - 0, 0, 128, 0, 0, 0, 255, 255, 255, 0, 255, 127, 254, 255, 239, 127, - 255, 255, 255, 255, 255, 255, 63, 0, 0, 0, 240, 255, 14, 255, 255, 255, - 1, 0, 1, 0, 0, 0, 0, 192, 96, 0, 0, 0, -}; - -/* Pattern_Syntax: 277 bytes. */ - -RE_UINT32 re_get_pattern_syntax(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_pattern_syntax_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_pattern_syntax_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_pattern_syntax_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_pattern_syntax_stage_4[pos + f] << 5; - pos += code; - value = (re_pattern_syntax_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Hangul_Syllable_Type. */ - -static RE_UINT8 re_hangul_syllable_type_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_hangul_syllable_type_stage_2[] = { - 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 3, 4, 5, 6, 7, 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, -}; - -static RE_UINT8 re_hangul_syllable_type_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 1, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 0, 0, 0, 0, 0, 4, 5, 6, 7, 8, 9, 10, 4, - 5, 6, 7, 8, 9, 10, 4, 5, 6, 7, 8, 9, 10, 4, 5, 6, - 7, 8, 9, 10, 4, 5, 6, 7, 8, 9, 10, 4, 5, 6, 7, 8, - 9, 10, 4, 5, 6, 7, 8, 9, 10, 4, 5, 6, 7, 8, 9, 10, - 4, 5, 6, 7, 8, 9, 10, 4, 5, 6, 7, 8, 9, 10, 4, 5, - 6, 7, 8, 9, 10, 4, 5, 6, 7, 8, 9, 10, 4, 5, 6, 11, -}; - -static RE_UINT8 re_hangul_syllable_type_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 4, - 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, - 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, - 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, - 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, - 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, - 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, - 6, 6, 5, 6, 6, 7, 6, 6, 6, 5, 6, 6, 7, 6, 6, 6, - 6, 5, 6, 6, 8, 0, 2, 2, 9, 10, 3, 3, 3, 3, 3, 11, -}; - -static RE_UINT8 re_hangul_syllable_type_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, - 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, - 1, 1, 1, 1, 1, 0, 0, 0, 4, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 4, 5, 5, 5, - 5, 5, 5, 5, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, 0, - 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, -}; - -/* Hangul_Syllable_Type: 497 bytes. */ - -RE_UINT32 re_get_hangul_syllable_type(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_hangul_syllable_type_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_hangul_syllable_type_stage_2[pos + f] << 4; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_hangul_syllable_type_stage_3[pos + f] << 4; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_hangul_syllable_type_stage_4[pos + f] << 3; - value = re_hangul_syllable_type_stage_5[pos + code]; - - return value; -} - -/* Bidi_Class. */ - -static RE_UINT8 re_bidi_class_stage_1[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 5, 6, 5, 5, 5, 5, 7, - 8, 9, 5, 5, 5, 5, 10, 5, 5, 5, 5, 5, 5, 11, 12, 13, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 15, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 14, -}; - -static RE_UINT8 re_bidi_class_stage_2[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 2, 6, 2, 7, 8, 9, 10, 11, - 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, - 28, 29, 2, 2, 2, 2, 30, 31, 32, 2, 2, 2, 2, 33, 34, 35, - 36, 37, 38, 39, 40, 2, 41, 42, 43, 44, 2, 45, 2, 2, 2, 46, - 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 52, 52, 52, 57, 58, 52, - 2, 2, 52, 52, 52, 52, 59, 2, 2, 60, 61, 62, 63, 64, 52, 65, - 66, 67, 2, 68, 69, 70, 71, 72, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 73, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 74, 2, 2, 75, 76, 77, 78, - 79, 80, 81, 82, 83, 84, 2, 85, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 86, 87, 87, 87, 88, 89, 90, 91, 92, 93, - 2, 2, 94, 95, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 96, 96, 97, 96, 98, 96, 99, 96, 96, 96, 96, 96, 100, 96, 96, 96, - 101, 102, 103, 104, 2, 2, 2, 2, 2, 2, 2, 2, 2, 105, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 106, - 2, 2, 107, 108, 109, 2, 110, 2, 2, 2, 2, 2, 2, 111, 112, 113, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 96, 87, 114, 96, 96, - 115, 116, 117, 2, 2, 2, 118, 119, 120, 121, 122, 123, 124, 125, 126, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 127, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 127, - 128, 128, 129, 130, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, - 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, -}; - -static RE_UINT8 re_bidi_class_stage_3[] = { - 0, 1, 2, 3, 4, 5, 4, 6, 7, 8, 9, 10, 11, 12, 11, 12, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 13, 14, 14, 15, 16, - 17, 17, 17, 17, 17, 17, 17, 18, 19, 11, 11, 11, 11, 11, 11, 20, - 21, 11, 11, 11, 11, 11, 11, 11, 22, 23, 17, 24, 25, 26, 26, 26, - 27, 28, 29, 29, 30, 17, 31, 32, 29, 29, 29, 29, 29, 33, 34, 35, - 29, 36, 29, 17, 28, 29, 29, 29, 29, 29, 37, 32, 26, 26, 38, 39, - 26, 40, 41, 26, 26, 42, 26, 26, 26, 26, 29, 29, 29, 29, 43, 44, - 45, 11, 11, 46, 47, 48, 49, 11, 50, 11, 11, 51, 52, 11, 49, 53, - 54, 11, 11, 51, 55, 50, 11, 56, 54, 11, 11, 51, 57, 11, 49, 58, - 50, 11, 11, 59, 52, 60, 49, 11, 61, 11, 11, 11, 62, 11, 11, 63, - 11, 11, 11, 64, 65, 66, 49, 67, 11, 11, 11, 51, 68, 11, 49, 11, - 11, 11, 11, 11, 52, 11, 49, 11, 11, 11, 11, 11, 69, 70, 11, 11, - 11, 11, 11, 71, 72, 11, 11, 11, 11, 11, 11, 73, 74, 11, 11, 11, - 11, 75, 11, 76, 11, 11, 11, 77, 78, 79, 17, 80, 60, 11, 11, 11, - 11, 11, 81, 82, 11, 83, 84, 85, 86, 87, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 81, 11, 11, 11, 88, 11, 11, 11, 11, 11, 11, - 4, 11, 11, 11, 11, 11, 11, 11, 89, 90, 11, 11, 11, 11, 11, 11, - 11, 91, 11, 91, 11, 49, 11, 49, 11, 11, 11, 92, 93, 94, 11, 88, - 95, 11, 11, 11, 11, 11, 11, 11, 11, 11, 96, 11, 11, 11, 11, 11, - 11, 11, 97, 98, 99, 11, 11, 11, 11, 11, 11, 11, 11, 100, 16, 16, - 11, 101, 11, 11, 11, 102, 103, 104, 105, 11, 11, 106, 61, 11, 107, 105, - 108, 11, 109, 11, 11, 11, 110, 108, 11, 11, 111, 112, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 113, 114, 115, 11, 11, 11, 11, 17, 17, 116, 111, - 11, 11, 11, 117, 118, 119, 119, 120, 121, 16, 122, 123, 124, 125, 126, 127, - 128, 11, 129, 129, 129, 17, 17, 84, 130, 131, 132, 133, 134, 16, 11, 11, - 135, 16, 16, 16, 16, 16, 16, 16, 16, 136, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 137, 11, 11, 11, 5, - 16, 138, 16, 16, 16, 16, 16, 139, 16, 16, 140, 11, 141, 11, 16, 16, - 142, 143, 11, 11, 11, 11, 144, 16, 16, 16, 145, 16, 16, 16, 16, 16, - 146, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 147, 88, 11, 11, - 11, 11, 11, 11, 11, 11, 148, 149, 11, 11, 11, 11, 11, 11, 11, 150, - 11, 11, 11, 11, 11, 11, 17, 17, 16, 16, 16, 151, 11, 11, 11, 11, - 16, 152, 16, 16, 16, 16, 16, 139, 16, 16, 16, 16, 16, 137, 11, 151, - 153, 16, 154, 155, 11, 11, 11, 11, 11, 156, 4, 11, 11, 11, 11, 157, - 11, 11, 11, 11, 16, 16, 139, 11, 11, 120, 11, 11, 11, 16, 11, 158, - 11, 11, 11, 146, 159, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 160, - 11, 11, 11, 11, 11, 100, 11, 161, 11, 11, 11, 11, 16, 16, 16, 16, - 11, 16, 16, 16, 140, 11, 11, 11, 119, 11, 11, 11, 11, 11, 150, 162, - 11, 150, 11, 11, 11, 11, 11, 108, 16, 16, 163, 11, 11, 11, 11, 11, - 164, 11, 11, 11, 11, 11, 11, 11, 165, 11, 166, 167, 11, 11, 11, 168, - 11, 11, 11, 11, 115, 11, 17, 108, 11, 11, 169, 11, 170, 108, 11, 11, - 45, 11, 11, 171, 11, 11, 11, 11, 11, 11, 172, 173, 174, 11, 11, 11, - 11, 11, 11, 175, 50, 11, 68, 60, 11, 11, 11, 11, 11, 11, 176, 11, - 11, 177, 178, 26, 26, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, - 29, 29, 29, 179, 29, 29, 29, 29, 29, 29, 29, 29, 29, 8, 8, 180, - 17, 88, 116, 16, 16, 181, 182, 29, 29, 29, 29, 29, 29, 29, 29, 183, - 184, 3, 4, 5, 4, 5, 137, 11, 11, 11, 11, 11, 11, 11, 185, 186, - 187, 11, 11, 11, 16, 16, 16, 16, 141, 151, 11, 11, 11, 11, 11, 87, - 26, 26, 26, 26, 26, 26, 26, 26, 26, 188, 26, 26, 26, 26, 26, 26, - 189, 26, 26, 190, 26, 26, 26, 26, 26, 26, 26, 191, 26, 26, 26, 26, - 26, 26, 26, 26, 26, 26, 192, 193, 50, 11, 11, 194, 116, 14, 137, 11, - 108, 11, 11, 195, 11, 11, 11, 11, 45, 11, 196, 197, 11, 11, 11, 11, - 108, 11, 11, 198, 11, 11, 11, 11, 11, 11, 199, 200, 11, 11, 11, 11, - 150, 45, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 201, 202, - 203, 11, 204, 11, 11, 11, 11, 11, 16, 16, 16, 16, 205, 11, 11, 11, - 16, 16, 16, 16, 16, 140, 11, 11, 11, 11, 11, 11, 11, 157, 11, 11, - 11, 206, 11, 11, 161, 11, 11, 11, 135, 11, 11, 11, 207, 208, 208, 208, - 29, 29, 29, 29, 29, 29, 29, 209, 16, 16, 151, 16, 16, 16, 16, 16, - 16, 139, 210, 211, 146, 146, 11, 11, 212, 11, 11, 11, 11, 11, 133, 11, - 16, 16, 4, 213, 16, 16, 16, 147, 16, 139, 16, 16, 214, 11, 16, 4, - 16, 16, 16, 210, 215, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 216, - 16, 16, 16, 217, 139, 16, 218, 11, 11, 11, 11, 11, 11, 11, 11, 5, - 16, 16, 16, 16, 219, 11, 11, 11, 16, 16, 16, 16, 137, 11, 11, 11, - 16, 16, 16, 16, 16, 16, 16, 139, 11, 11, 11, 11, 11, 11, 11, 220, - 8, 8, 8, 8, 8, 8, 8, 8, 17, 17, 17, 17, 17, 17, 17, 17, - 17, 17, 17, 17, 17, 17, 17, 8, -}; - -static RE_UINT8 re_bidi_class_stage_4[] = { - 0, 0, 1, 2, 0, 0, 0, 3, 4, 5, 6, 7, 8, 8, 9, 10, - 11, 12, 12, 12, 12, 12, 13, 10, 12, 12, 13, 14, 0, 15, 0, 0, - 0, 0, 0, 0, 16, 5, 17, 18, 19, 20, 21, 10, 12, 12, 12, 12, - 12, 13, 12, 12, 12, 12, 22, 12, 23, 10, 10, 10, 12, 24, 10, 17, - 10, 10, 10, 10, 25, 25, 25, 25, 12, 26, 12, 27, 12, 17, 12, 12, - 12, 27, 12, 12, 28, 25, 29, 12, 12, 12, 27, 30, 31, 25, 25, 25, - 25, 25, 25, 32, 33, 32, 34, 34, 34, 34, 34, 34, 35, 36, 37, 38, - 25, 25, 39, 40, 40, 40, 40, 40, 40, 40, 41, 25, 35, 35, 42, 43, - 44, 40, 40, 40, 40, 45, 25, 46, 25, 47, 48, 49, 8, 8, 50, 40, - 51, 40, 40, 40, 40, 45, 25, 25, 34, 34, 52, 25, 25, 53, 54, 34, - 34, 55, 32, 25, 25, 31, 31, 56, 34, 34, 31, 34, 40, 25, 25, 25, - 25, 25, 25, 39, 57, 12, 12, 12, 12, 12, 58, 59, 60, 25, 59, 61, - 60, 25, 12, 12, 62, 12, 12, 12, 61, 12, 12, 12, 12, 12, 12, 59, - 60, 59, 12, 61, 63, 12, 30, 12, 64, 12, 12, 12, 64, 28, 65, 29, - 29, 61, 12, 12, 60, 66, 59, 61, 67, 12, 12, 12, 12, 12, 12, 65, - 12, 58, 12, 12, 58, 12, 12, 12, 59, 12, 12, 61, 13, 10, 68, 12, - 12, 12, 12, 62, 59, 62, 69, 29, 12, 64, 12, 12, 12, 12, 10, 70, - 12, 12, 12, 29, 12, 12, 58, 12, 62, 71, 12, 12, 61, 25, 57, 30, - 12, 28, 25, 57, 61, 25, 66, 59, 12, 12, 25, 29, 12, 12, 29, 12, - 12, 72, 73, 26, 60, 25, 25, 57, 25, 69, 12, 60, 25, 25, 60, 25, - 25, 25, 25, 59, 12, 12, 12, 60, 69, 25, 64, 64, 12, 12, 29, 62, - 59, 12, 12, 12, 60, 59, 12, 12, 58, 64, 12, 61, 12, 12, 12, 61, - 10, 10, 26, 12, 74, 12, 12, 12, 12, 12, 13, 11, 62, 59, 12, 12, - 12, 66, 25, 29, 12, 58, 60, 25, 25, 12, 30, 61, 10, 10, 75, 76, - 12, 12, 61, 12, 57, 28, 59, 12, 58, 12, 60, 12, 11, 26, 12, 12, - 12, 12, 12, 23, 12, 28, 65, 12, 12, 58, 25, 57, 71, 60, 25, 59, - 28, 25, 25, 65, 25, 12, 12, 12, 12, 69, 57, 59, 12, 12, 28, 25, - 29, 12, 12, 12, 62, 29, 66, 12, 12, 58, 29, 72, 12, 12, 12, 25, - 25, 62, 12, 12, 57, 25, 25, 25, 69, 25, 59, 61, 12, 59, 12, 12, - 25, 57, 12, 12, 12, 12, 12, 77, 26, 12, 12, 24, 12, 12, 12, 24, - 12, 12, 12, 22, 78, 78, 79, 80, 10, 10, 81, 82, 83, 84, 10, 10, - 10, 85, 10, 10, 10, 10, 10, 86, 0, 87, 88, 0, 89, 8, 90, 70, - 8, 8, 90, 70, 83, 83, 83, 83, 17, 70, 26, 12, 12, 20, 11, 23, - 10, 77, 91, 92, 12, 12, 23, 12, 10, 11, 23, 26, 12, 12, 91, 12, - 93, 10, 10, 10, 10, 26, 12, 12, 10, 20, 10, 10, 10, 12, 12, 12, - 10, 70, 12, 12, 10, 10, 70, 12, 10, 10, 8, 8, 8, 8, 8, 12, - 12, 12, 23, 10, 10, 10, 10, 24, 24, 10, 10, 10, 10, 10, 10, 11, - 12, 24, 70, 28, 29, 12, 24, 10, 12, 12, 12, 28, 10, 10, 10, 12, - 10, 10, 17, 10, 94, 11, 10, 10, 11, 12, 62, 29, 11, 23, 12, 24, - 12, 12, 95, 11, 12, 12, 13, 12, 12, 12, 12, 70, 12, 12, 12, 10, - 12, 13, 70, 12, 12, 12, 12, 13, 96, 25, 25, 97, 26, 12, 12, 12, - 12, 12, 11, 12, 58, 58, 28, 12, 12, 64, 10, 12, 12, 12, 98, 12, - 12, 10, 12, 12, 12, 62, 25, 29, 12, 28, 25, 25, 28, 62, 29, 59, - 12, 12, 60, 57, 64, 64, 12, 12, 28, 12, 12, 59, 69, 65, 59, 62, - 12, 61, 59, 61, 12, 12, 12, 99, 34, 34, 100, 34, 40, 40, 40, 101, - 40, 40, 40, 102, 103, 104, 10, 105, 106, 70, 107, 12, 40, 40, 40, 108, - 109, 5, 6, 7, 5, 110, 10, 70, 0, 0, 111, 112, 91, 12, 12, 12, - 34, 34, 34, 113, 31, 33, 34, 25, 34, 34, 114, 52, 34, 34, 115, 10, - 35, 35, 35, 35, 35, 35, 35, 116, 12, 12, 25, 25, 28, 57, 64, 12, - 12, 28, 25, 60, 25, 59, 12, 12, 12, 62, 25, 57, 12, 12, 28, 61, - 25, 66, 12, 12, 12, 28, 29, 12, 117, 0, 118, 25, 57, 60, 25, 12, - 12, 12, 62, 29, 119, 120, 12, 12, 12, 91, 12, 12, 13, 12, 12, 121, - 8, 8, 8, 8, 122, 40, 40, 40, 10, 10, 10, 70, 24, 10, 10, 70, - 8, 8, 123, 12, 10, 17, 10, 10, 10, 20, 70, 12, 20, 10, 10, 10, - 10, 10, 24, 11, 10, 10, 10, 26, 10, 10, 12, 12, 11, 24, 10, 10, - 12, 12, 12, 124, -}; - -static RE_UINT8 re_bidi_class_stage_5[] = { - 11, 11, 11, 11, 11, 8, 7, 8, 9, 7, 11, 11, 7, 7, 7, 8, - 9, 10, 10, 4, 4, 4, 10, 10, 10, 10, 10, 3, 6, 3, 6, 6, - 2, 2, 2, 2, 2, 2, 6, 10, 10, 10, 10, 10, 10, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 10, 10, 10, 10, 11, 11, 7, 11, 11, - 6, 10, 4, 4, 10, 10, 0, 10, 10, 11, 10, 10, 4, 4, 2, 2, - 10, 0, 10, 10, 10, 2, 0, 10, 0, 10, 10, 0, 0, 0, 10, 10, - 0, 10, 10, 10, 12, 12, 12, 12, 10, 10, 0, 0, 0, 0, 10, 0, - 0, 0, 0, 12, 12, 12, 0, 0, 0, 0, 0, 4, 1, 12, 12, 12, - 12, 12, 1, 12, 1, 12, 12, 1, 1, 1, 1, 1, 5, 5, 5, 5, - 5, 13, 10, 10, 13, 4, 4, 13, 6, 13, 10, 10, 12, 12, 12, 13, - 13, 13, 13, 13, 13, 13, 13, 12, 5, 5, 4, 5, 5, 13, 13, 13, - 12, 13, 13, 13, 13, 13, 12, 12, 12, 5, 10, 12, 12, 13, 13, 12, - 12, 10, 12, 12, 12, 12, 13, 13, 2, 2, 13, 13, 13, 12, 13, 13, - 1, 1, 1, 12, 1, 1, 10, 10, 10, 10, 1, 1, 1, 1, 12, 12, - 12, 12, 1, 1, 12, 12, 12, 0, 0, 0, 12, 0, 12, 0, 0, 0, - 0, 12, 12, 12, 0, 12, 0, 0, 0, 0, 12, 12, 0, 0, 4, 4, - 0, 12, 12, 0, 12, 0, 0, 12, 12, 12, 0, 12, 0, 4, 0, 0, - 10, 4, 10, 0, 12, 0, 12, 12, 10, 10, 10, 0, 12, 0, 12, 0, - 0, 12, 0, 12, 0, 12, 10, 10, 9, 0, 0, 0, 10, 10, 10, 12, - 12, 12, 11, 0, 0, 10, 0, 10, 9, 9, 9, 9, 9, 9, 9, 11, - 11, 11, 0, 1, 9, 7, 16, 17, 18, 14, 15, 6, 4, 4, 4, 4, - 4, 10, 10, 10, 6, 10, 10, 10, 10, 10, 10, 9, 11, 11, 19, 20, - 21, 22, 11, 11, 2, 0, 0, 0, 2, 2, 3, 3, 0, 10, 0, 0, - 0, 0, 4, 0, 10, 10, 3, 4, 9, 10, 10, 10, 0, 12, 12, 10, - 12, 12, 12, 10, 12, 12, 10, 10, 4, 4, 0, 0, 0, 1, 12, 1, - 1, 3, 1, 1, 13, 13, 10, 10, 13, 10, 13, 13, 6, 10, 6, 0, - 10, 6, 10, 10, 10, 10, 10, 4, 10, 10, 3, 3, 10, 4, 4, 10, - 13, 13, 13, 11, 0, 10, 10, 4, 10, 4, 4, 0, 11, 10, 10, 10, - 10, 10, 11, 11, 1, 1, 1, 10, 12, 12, 12, 1, 1, 10, 10, 10, - 5, 5, 5, 1, 0, 0, 0, 11, 11, 11, 11, 12, 10, 10, 12, 12, - 12, 10, 0, 0, 0, 0, 2, 2, 10, 10, 13, 13, 2, 2, 2, 0, - 0, 0, 11, 11, -}; - -/* Bidi_Class: 3216 bytes. */ - -RE_UINT32 re_get_bidi_class(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_bidi_class_stage_1[f] << 5; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_bidi_class_stage_2[pos + f] << 3; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_bidi_class_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_bidi_class_stage_4[pos + f] << 2; - value = re_bidi_class_stage_5[pos + code]; - - return value; -} - -/* Canonical_Combining_Class. */ - -static RE_UINT8 re_canonical_combining_class_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 4, 5, 2, 2, 2, 2, 2, 6, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_canonical_combining_class_stage_2[] = { - 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, - 14, 0, 0, 15, 0, 0, 0, 16, 17, 18, 19, 20, 21, 22, 0, 0, - 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 25, 0, 0, - 26, 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, 27, 0, 28, 29, 30, 31, 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, 32, 0, 0, 33, 0, - 0, 34, 0, 0, 0, 0, 0, 0, 0, 0, 35, 0, 0, 0, 0, 0, - 36, 37, 0, 0, 0, 0, 38, 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, 39, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_canonical_combining_class_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 0, 0, 0, 0, - 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, 6, 7, 8, 0, - 9, 0, 10, 11, 0, 0, 12, 13, 14, 15, 16, 0, 0, 0, 0, 17, - 18, 19, 20, 0, 0, 0, 0, 21, 0, 22, 23, 0, 0, 22, 24, 0, - 0, 22, 24, 0, 0, 22, 24, 0, 0, 22, 24, 0, 0, 0, 24, 0, - 0, 0, 25, 0, 0, 22, 24, 0, 0, 0, 24, 0, 0, 0, 26, 0, - 0, 27, 28, 0, 0, 29, 30, 0, 31, 32, 0, 33, 34, 0, 35, 0, - 0, 36, 0, 0, 37, 0, 0, 0, 0, 0, 38, 0, 0, 0, 0, 0, - 39, 39, 0, 0, 0, 0, 40, 0, 0, 0, 0, 0, 0, 41, 0, 0, - 0, 42, 0, 0, 0, 0, 0, 0, 43, 0, 0, 44, 0, 0, 0, 0, - 0, 45, 46, 47, 0, 48, 0, 49, 0, 50, 0, 0, 0, 0, 51, 52, - 0, 0, 0, 0, 0, 0, 53, 54, 0, 0, 0, 0, 0, 0, 55, 56, - 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, 0, 58, 0, 0, 0, 59, - 0, 60, 0, 0, 61, 0, 0, 0, 0, 0, 0, 62, 63, 0, 0, 64, - 65, 0, 0, 0, 0, 0, 46, 66, 0, 67, 68, 0, 0, 69, 70, 0, - 0, 0, 0, 0, 0, 71, 72, 73, 0, 0, 0, 0, 0, 0, 0, 24, - 74, 0, 0, 0, 0, 0, 0, 0, 0, 75, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 76, 77, 78, 0, 0, 0, 0, 0, 0, - 0, 0, 65, 0, 0, 79, 0, 0, 80, 81, 0, 0, 0, 0, 70, 0, - 0, 0, 0, 0, 0, 82, 0, 0, 0, 0, 0, 83, 84, 85, 0, 0, - 0, 0, 86, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_canonical_combining_class_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 3, 4, - 5, 6, 7, 4, 4, 8, 9, 10, 1, 11, 12, 13, 14, 15, 16, 17, - 18, 1, 1, 1, 0, 0, 0, 0, 19, 1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 20, 21, 22, 1, 23, 4, 21, 24, 25, 26, 27, 28, - 29, 30, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 31, 0, - 0, 0, 32, 33, 34, 35, 1, 36, 0, 0, 0, 0, 37, 0, 0, 0, - 0, 0, 0, 0, 0, 38, 1, 39, 14, 39, 40, 41, 0, 0, 0, 0, - 0, 0, 0, 0, 42, 0, 0, 0, 0, 0, 0, 0, 43, 36, 44, 45, - 21, 45, 46, 0, 0, 0, 0, 0, 0, 0, 19, 1, 21, 0, 0, 0, - 0, 0, 0, 0, 0, 38, 47, 1, 1, 48, 48, 49, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 50, 0, 0, 21, 43, 51, 52, 21, 35, 53, - 0, 0, 0, 0, 0, 0, 0, 54, 0, 0, 0, 55, 56, 57, 0, 0, - 0, 0, 0, 55, 0, 0, 0, 0, 0, 0, 0, 55, 0, 58, 0, 0, - 0, 0, 59, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 60, 0, - 0, 0, 61, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 62, 0, - 0, 0, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, - 0, 0, 0, 0, 0, 65, 66, 0, 0, 0, 0, 0, 67, 68, 69, 70, - 71, 72, 0, 0, 0, 0, 0, 0, 0, 73, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 74, 75, 0, 0, 0, 0, 76, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 48, 0, 0, 0, 0, 0, 77, 0, 0, - 0, 0, 0, 0, 59, 0, 0, 78, 0, 0, 79, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 80, 0, 0, 0, 0, 0, 0, 19, 81, 0, - 77, 0, 0, 0, 0, 48, 1, 82, 0, 0, 0, 0, 0, 54, 0, 0, - 0, 77, 0, 0, 0, 0, 0, 0, 0, 0, 19, 10, 1, 0, 0, 0, - 0, 0, 83, 0, 0, 0, 0, 0, 0, 84, 0, 0, 83, 0, 0, 0, - 0, 0, 0, 0, 0, 74, 0, 0, 0, 0, 0, 0, 53, 9, 12, 4, - 85, 8, 86, 76, 0, 57, 0, 0, 21, 1, 21, 87, 88, 1, 1, 1, - 1, 53, 0, 0, 0, 0, 0, 89, 0, 0, 0, 0, 90, 1, 91, 57, - 78, 92, 93, 4, 57, 0, 0, 0, 0, 0, 0, 19, 49, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 94, 1, 1, 1, 1, 1, 1, 1, 1, - 0, 0, 95, 96, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 97, 0, - 0, 0, 0, 19, 0, 1, 1, 49, 0, 0, 0, 0, 0, 0, 0, 19, - 0, 0, 0, 0, 49, 0, 0, 0, 0, 59, 0, 0, 0, 0, 0, 0, - 1, 1, 1, 1, 49, 0, 0, 0, 0, 0, 98, 64, 0, 0, 0, 0, - 0, 0, 0, 0, 94, 0, 0, 0, 0, 0, 0, 0, 74, 0, 0, 0, - 77, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 99, 100, 57, 38, - 78, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 101, 1, 53, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 76, 0, 0, 0, 102, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 103, 94, 0, 0, 0, 0, 0, 0, 104, 0, - 53, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 94, 77, 0, 0, - 0, 0, 0, 0, 0, 105, 0, 0, 0, 106, 107, 108, 109, 0, 98, 4, - 110, 48, 23, 0, 0, 0, 0, 0, 0, 0, 38, 49, 0, 0, 0, 0, - 38, 57, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_canonical_combining_class_stage_5[] = { - 0, 0, 0, 0, 50, 50, 50, 50, 50, 51, 45, 45, 45, 45, 51, 43, - 45, 45, 45, 45, 45, 41, 41, 45, 45, 45, 45, 41, 41, 45, 45, 45, - 1, 1, 1, 1, 1, 45, 45, 45, 45, 50, 50, 50, 50, 54, 50, 45, - 45, 45, 50, 50, 50, 45, 45, 0, 50, 50, 50, 45, 45, 45, 45, 50, - 51, 45, 45, 50, 52, 53, 53, 52, 53, 53, 52, 50, 0, 0, 0, 50, - 0, 45, 50, 50, 50, 50, 45, 50, 50, 50, 46, 45, 50, 50, 45, 45, - 50, 46, 49, 50, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 14, 15, - 16, 17, 0, 18, 0, 19, 20, 0, 50, 45, 0, 13, 25, 26, 27, 0, - 0, 0, 0, 22, 23, 24, 25, 26, 27, 28, 29, 50, 50, 45, 45, 50, - 45, 50, 50, 45, 30, 0, 0, 0, 0, 0, 50, 50, 50, 0, 0, 50, - 50, 0, 45, 50, 50, 45, 0, 0, 0, 31, 0, 0, 50, 45, 50, 50, - 45, 45, 50, 45, 45, 50, 45, 50, 45, 50, 50, 0, 50, 50, 0, 50, - 0, 50, 50, 50, 50, 50, 0, 0, 0, 45, 45, 45, 50, 45, 45, 45, - 22, 23, 24, 50, 50, 50, 50, 0, 2, 0, 0, 0, 0, 4, 0, 0, - 0, 50, 45, 50, 50, 0, 0, 0, 0, 32, 33, 0, 0, 0, 4, 0, - 34, 34, 4, 0, 35, 35, 35, 35, 36, 36, 0, 0, 37, 37, 37, 37, - 45, 45, 0, 0, 0, 45, 0, 45, 0, 43, 0, 0, 0, 38, 39, 0, - 40, 0, 0, 0, 0, 0, 39, 39, 39, 39, 0, 0, 39, 0, 50, 50, - 4, 0, 50, 50, 0, 0, 45, 0, 0, 0, 0, 2, 0, 4, 4, 0, - 0, 45, 0, 0, 4, 0, 0, 0, 0, 50, 0, 0, 0, 49, 0, 0, - 0, 46, 50, 45, 45, 0, 0, 0, 50, 0, 0, 45, 0, 0, 4, 4, - 0, 0, 2, 0, 50, 0, 1, 1, 1, 0, 0, 0, 50, 53, 42, 45, - 41, 50, 50, 50, 52, 45, 50, 45, 50, 50, 1, 1, 1, 1, 1, 50, - 0, 1, 1, 50, 45, 50, 1, 1, 0, 0, 0, 4, 0, 0, 44, 49, - 51, 46, 47, 47, 0, 3, 3, 0, 0, 0, 0, 45, 50, 0, 50, 50, - 45, 0, 0, 50, 0, 0, 21, 0, 0, 45, 0, 50, 50, 1, 45, 0, - 0, 4, 2, 0, 0, 0, 4, 2, 0, 43, 43, 1, 1, 1, 0, 0, - 0, 48, 43, 43, 43, 43, 43, 0, 45, 45, 45, 0, -}; - -/* Canonical_Combining_Class: 1828 bytes. */ - -RE_UINT32 re_get_canonical_combining_class(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_canonical_combining_class_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_canonical_combining_class_stage_2[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_canonical_combining_class_stage_3[pos + f] << 3; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_canonical_combining_class_stage_4[pos + f] << 2; - value = re_canonical_combining_class_stage_5[pos + code]; - - return value; -} - -/* Decomposition_Type. */ - -static RE_UINT8 re_decomposition_type_stage_1[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 6, 2, 2, 2, 2, 2, 7, 8, - 2, 2, 2, 2, 2, 2, 2, 9, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_decomposition_type_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 9, 10, 11, 12, 13, 14, - 15, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 16, 7, 17, 18, 19, - 20, 21, 22, 23, 24, 7, 7, 7, 7, 7, 25, 7, 26, 27, 28, 29, - 30, 31, 32, 33, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 34, 7, 7, 7, 7, 35, 35, 35, 35, - 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, - 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, 35, - 35, 35, 35, 35, 35, 35, 35, 36, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 35, 37, 38, 39, 40, 41, 42, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 43, 44, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 45, 7, 7, 46, 47, 48, 49, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 50, 7, - 7, 51, 52, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 7, 7, 7, 35, 35, 53, 7, 7, 7, 7, 7, -}; - -static RE_UINT8 re_decomposition_type_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 3, 5, - 6, 7, 8, 9, 10, 11, 8, 12, 0, 0, 13, 14, 15, 16, 17, 18, - 6, 19, 20, 21, 0, 0, 0, 0, 0, 0, 0, 22, 0, 23, 24, 0, - 0, 0, 0, 0, 25, 0, 0, 26, 27, 14, 28, 14, 29, 30, 0, 31, - 32, 33, 0, 33, 0, 32, 0, 34, 0, 0, 0, 0, 35, 36, 37, 38, - 0, 0, 0, 0, 0, 0, 0, 0, 39, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 40, 0, 0, 0, 0, 41, 0, 0, 0, 0, 42, 43, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 33, 44, 0, 45, 0, 0, 0, 0, 0, 0, 46, 47, 0, 0, - 0, 0, 0, 48, 0, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 50, 51, 0, 0, 0, 52, 0, 0, 53, 0, 0, 0, - 0, 0, 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, 55, 0, 0, 0, - 0, 0, 0, 0, 53, 0, 0, 0, 0, 0, 0, 0, 0, 56, 0, 0, - 0, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 57, 0, 58, 0, 0, - 59, 0, 0, 0, 60, 61, 33, 62, 63, 60, 61, 33, 0, 0, 0, 0, - 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 65, - 66, 67, 0, 68, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 70, 71, 72, 73, 74, 75, 0, 76, 73, 73, 0, 0, 0, 0, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 77, 6, 6, 6, 6, 6, 78, - 6, 79, 6, 6, 79, 80, 6, 81, 6, 6, 6, 82, 83, 84, 6, 85, - 86, 87, 88, 89, 90, 91, 0, 92, 93, 94, 95, 0, 0, 0, 0, 0, - 96, 97, 98, 99, 100, 101, 102, 102, 103, 104, 105, 0, 106, 0, 0, 0, - 107, 0, 108, 109, 110, 0, 111, 112, 112, 0, 113, 0, 0, 0, 114, 0, - 0, 0, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 116, 117, 102, 102, 102, 118, 116, 116, 119, 0, - 120, 0, 0, 0, 0, 0, 0, 121, 0, 0, 0, 0, 0, 122, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 123, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 124, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 125, 0, 0, 0, 0, 0, 57, - 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 102, 126, 0, 0, - 127, 0, 0, 128, 129, 130, 131, 132, 0, 133, 129, 130, 131, 132, 0, 134, - 0, 0, 0, 135, 102, 102, 102, 102, 136, 137, 0, 0, 0, 0, 0, 0, - 102, 136, 102, 102, 138, 139, 116, 140, 116, 116, 116, 116, 141, 116, 116, 140, - 142, 142, 142, 142, 142, 143, 102, 144, 142, 142, 142, 142, 142, 142, 102, 145, - 0, 0, 0, 0, 0, 0, 0, 146, 0, 0, 0, 0, 0, 0, 0, 147, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 21, 0, 0, 0, 0, 0, - 81, 148, 149, 6, 6, 6, 81, 6, 6, 6, 6, 6, 6, 78, 0, 0, - 150, 151, 152, 153, 154, 155, 156, 156, 157, 156, 158, 159, 0, 160, 161, 162, - 163, 163, 163, 163, 163, 163, 164, 165, 165, 166, 167, 167, 167, 168, 169, 170, - 163, 171, 172, 173, 0, 174, 175, 176, 177, 178, 165, 179, 180, 0, 0, 181, - 0, 182, 0, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 192, 193, 194, - 195, 196, 196, 196, 196, 196, 197, 198, 198, 198, 198, 199, 200, 201, 202, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 203, 204, 0, 0, 0, 0, 0, - 0, 0, 205, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 205, 206, 0, 0, 0, 0, 207, 14, 0, 0, 0, - 208, 208, 208, 208, 208, 209, 208, 208, 208, 210, 211, 212, 213, 208, 208, 208, - 214, 215, 208, 216, 217, 218, 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, - 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 219, 208, 208, 208, 208, 208, - 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 208, 220, 208, 208, 208, - 213, 208, 221, 222, 223, 224, 225, 226, 227, 228, 229, 228, 0, 0, 0, 0, - 230, 102, 231, 142, 142, 0, 232, 0, 0, 233, 0, 0, 0, 0, 0, 0, - 234, 142, 142, 235, 236, 237, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 6, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_decomposition_type_stage_4[] = { - 0, 0, 0, 0, 1, 0, 2, 3, 4, 5, 6, 7, 8, 9, 8, 8, - 10, 11, 10, 12, 10, 11, 10, 9, 8, 8, 8, 8, 13, 8, 8, 8, - 8, 12, 8, 8, 14, 8, 10, 15, 16, 8, 17, 8, 12, 8, 8, 8, - 8, 8, 8, 15, 12, 0, 0, 18, 19, 0, 0, 0, 0, 20, 20, 21, - 8, 8, 8, 22, 8, 13, 8, 8, 23, 12, 8, 8, 8, 8, 8, 13, - 0, 13, 8, 8, 8, 0, 0, 0, 24, 24, 25, 0, 0, 0, 20, 5, - 24, 25, 0, 0, 9, 19, 0, 0, 0, 19, 26, 27, 0, 21, 11, 22, - 0, 0, 13, 8, 0, 0, 13, 11, 28, 29, 0, 0, 30, 5, 31, 0, - 9, 18, 0, 11, 0, 0, 32, 0, 0, 13, 0, 0, 33, 0, 0, 0, - 8, 13, 13, 8, 13, 8, 13, 8, 8, 12, 12, 0, 0, 3, 0, 0, - 13, 11, 0, 0, 0, 34, 35, 0, 36, 0, 0, 0, 18, 0, 0, 0, - 32, 19, 0, 0, 0, 0, 8, 8, 0, 0, 18, 19, 0, 0, 0, 9, - 18, 27, 0, 0, 0, 0, 10, 27, 0, 0, 37, 19, 0, 0, 0, 12, - 0, 19, 0, 0, 0, 0, 13, 19, 0, 0, 19, 0, 19, 18, 22, 0, - 0, 0, 27, 11, 3, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 1, - 18, 0, 0, 32, 27, 18, 0, 19, 18, 38, 17, 0, 32, 0, 0, 0, - 0, 27, 0, 0, 0, 0, 0, 25, 0, 27, 36, 36, 27, 0, 0, 0, - 0, 0, 18, 32, 9, 0, 0, 0, 0, 0, 0, 39, 24, 24, 39, 24, - 24, 24, 24, 40, 24, 24, 24, 24, 41, 42, 43, 0, 0, 0, 25, 0, - 0, 0, 44, 24, 8, 8, 45, 0, 8, 8, 12, 0, 8, 12, 8, 12, - 8, 8, 46, 46, 8, 8, 8, 12, 8, 22, 8, 47, 21, 22, 8, 8, - 8, 13, 8, 10, 13, 22, 8, 48, 49, 50, 30, 0, 51, 3, 0, 0, - 0, 30, 0, 52, 3, 53, 0, 54, 0, 3, 5, 0, 0, 3, 0, 3, - 55, 24, 24, 24, 42, 42, 42, 43, 42, 42, 42, 56, 0, 0, 35, 0, - 57, 34, 58, 59, 59, 60, 61, 62, 63, 64, 65, 66, 66, 67, 68, 59, - 69, 61, 62, 0, 70, 70, 70, 70, 20, 20, 20, 20, 0, 0, 71, 0, - 0, 0, 13, 0, 0, 0, 0, 27, 0, 0, 0, 10, 0, 19, 32, 19, - 0, 36, 0, 72, 35, 0, 0, 0, 32, 37, 32, 0, 36, 0, 0, 10, - 12, 12, 12, 0, 0, 0, 0, 8, 8, 0, 13, 12, 0, 0, 33, 0, - 73, 73, 73, 73, 73, 20, 20, 20, 20, 74, 73, 73, 73, 73, 75, 0, - 0, 0, 0, 35, 0, 30, 0, 0, 0, 0, 0, 19, 0, 0, 0, 76, - 0, 0, 0, 44, 0, 0, 0, 3, 20, 5, 0, 0, 77, 0, 0, 0, - 0, 26, 30, 0, 0, 0, 0, 36, 36, 36, 36, 36, 36, 46, 32, 0, - 9, 22, 33, 12, 0, 19, 3, 78, 0, 37, 11, 79, 34, 20, 20, 20, - 20, 20, 20, 30, 4, 24, 24, 24, 20, 73, 0, 0, 80, 73, 73, 73, - 73, 73, 73, 75, 20, 20, 20, 81, 81, 81, 81, 81, 81, 81, 20, 20, - 82, 81, 81, 81, 20, 20, 20, 83, 25, 0, 0, 0, 0, 0, 55, 0, - 36, 10, 8, 11, 36, 33, 13, 8, 20, 30, 0, 0, 3, 20, 0, 46, - 59, 59, 84, 8, 8, 11, 8, 36, 9, 22, 8, 15, 85, 86, 86, 86, - 86, 86, 86, 86, 86, 85, 85, 85, 87, 85, 86, 86, 88, 0, 0, 0, - 89, 90, 91, 92, 85, 87, 86, 85, 85, 85, 93, 87, 94, 94, 94, 94, - 94, 95, 95, 95, 95, 95, 95, 95, 95, 96, 97, 97, 97, 97, 97, 97, - 97, 97, 97, 98, 99, 99, 99, 99, 99, 100, 94, 94, 101, 95, 95, 95, - 95, 95, 95, 102, 97, 99, 99, 103, 104, 97, 105, 106, 107, 105, 108, 105, - 104, 96, 95, 105, 96, 109, 110, 97, 111, 106, 112, 105, 95, 106, 113, 95, - 96, 106, 0, 0, 94, 94, 94, 114, 115, 115, 116, 0, 115, 115, 115, 115, - 115, 117, 118, 20, 119, 120, 120, 120, 120, 119, 120, 0, 121, 122, 123, 123, - 124, 91, 125, 126, 90, 125, 127, 127, 127, 127, 126, 91, 125, 127, 127, 127, - 127, 127, 127, 127, 127, 127, 127, 126, 125, 126, 91, 128, 129, 130, 130, 130, - 130, 130, 130, 130, 131, 132, 132, 132, 132, 132, 132, 132, 132, 132, 132, 133, - 134, 132, 134, 132, 134, 132, 134, 135, 130, 136, 132, 133, 0, 0, 27, 19, - 0, 0, 18, 0, 0, 0, 0, 13, 8, 19, 0, 0, 0, 0, 18, 8, - 59, 59, 59, 59, 59, 137, 59, 59, 59, 59, 59, 137, 138, 139, 61, 137, - 59, 59, 66, 61, 59, 61, 59, 59, 59, 66, 140, 61, 59, 137, 59, 137, - 59, 59, 66, 140, 59, 141, 142, 59, 137, 59, 59, 59, 59, 62, 59, 59, - 59, 59, 59, 142, 139, 143, 61, 59, 140, 59, 144, 0, 138, 145, 144, 61, - 139, 143, 144, 144, 139, 143, 140, 59, 140, 59, 61, 141, 59, 59, 66, 59, - 59, 59, 59, 0, 61, 61, 66, 59, 20, 20, 30, 0, 20, 20, 146, 75, - 0, 0, 4, 0, 147, 0, 0, 0, 148, 0, 0, 0, 81, 81, 148, 0, - 20, 20, 35, 0, 149, 0, 0, 0, -}; - -static RE_UINT8 re_decomposition_type_stage_5[] = { - 0, 0, 0, 0, 4, 0, 0, 0, 2, 0, 10, 0, 0, 0, 0, 2, - 0, 0, 10, 10, 2, 2, 0, 0, 2, 10, 10, 0, 17, 17, 17, 0, - 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 1, 0, - 1, 1, 0, 0, 0, 0, 1, 1, 1, 0, 2, 2, 1, 1, 1, 2, - 2, 0, 0, 1, 1, 2, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, - 2, 2, 2, 2, 2, 1, 1, 1, 1, 0, 1, 1, 1, 2, 2, 2, - 10, 10, 10, 10, 10, 0, 0, 0, 0, 0, 2, 0, 0, 0, 1, 0, - 2, 2, 2, 1, 1, 2, 2, 0, 2, 2, 2, 0, 0, 2, 0, 0, - 0, 1, 0, 0, 0, 1, 1, 0, 0, 2, 2, 2, 2, 0, 0, 0, - 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 1, 2, 10, 10, 10, 0, - 10, 10, 0, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 0, - 0, 0, 0, 10, 1, 1, 2, 1, 0, 1, 0, 1, 1, 2, 1, 2, - 1, 1, 2, 0, 1, 1, 2, 2, 2, 2, 2, 4, 0, 4, 0, 0, - 0, 0, 0, 4, 2, 0, 2, 2, 2, 0, 2, 0, 10, 10, 0, 0, - 11, 0, 0, 0, 2, 2, 3, 2, 0, 2, 3, 3, 3, 3, 3, 3, - 0, 3, 2, 0, 0, 3, 3, 3, 3, 3, 0, 0, 10, 2, 10, 0, - 3, 0, 1, 0, 3, 0, 1, 1, 3, 3, 0, 3, 3, 2, 2, 2, - 2, 3, 0, 2, 3, 0, 0, 0, 17, 17, 17, 17, 0, 17, 0, 0, - 2, 2, 0, 2, 9, 9, 9, 9, 2, 2, 9, 9, 9, 9, 9, 0, - 11, 10, 0, 0, 13, 0, 0, 0, 2, 0, 1, 12, 0, 0, 1, 12, - 16, 9, 9, 9, 16, 16, 16, 16, 2, 16, 16, 16, 2, 2, 2, 16, - 3, 3, 1, 1, 8, 7, 8, 7, 5, 6, 8, 7, 8, 7, 5, 6, - 8, 7, 0, 0, 0, 0, 0, 8, 7, 5, 6, 8, 7, 8, 7, 8, - 7, 8, 8, 7, 5, 8, 7, 5, 8, 8, 8, 8, 7, 7, 7, 7, - 7, 7, 7, 5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, - 6, 8, 8, 8, 8, 7, 7, 7, 7, 5, 5, 5, 7, 8, 0, 0, - 5, 7, 5, 5, 7, 5, 7, 7, 5, 5, 7, 7, 5, 5, 7, 5, - 5, 7, 7, 5, 7, 7, 5, 7, 5, 5, 5, 7, 0, 0, 5, 5, - 5, 7, 7, 7, 5, 7, 5, 7, 8, 0, 0, 0, 12, 12, 12, 12, - 12, 12, 0, 0, 12, 0, 0, 12, 12, 2, 2, 2, 15, 15, 15, 0, - 15, 15, 15, 15, 8, 6, 8, 0, 8, 0, 8, 6, 8, 6, 8, 6, - 8, 8, 7, 8, 7, 8, 7, 5, 6, 8, 7, 8, 6, 8, 7, 5, - 7, 0, 0, 0, 0, 13, 13, 13, 13, 13, 13, 13, 13, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 0, 0, 0, 14, 14, 14, 0, 0, 0, - 13, 13, 13, 0, 3, 0, 3, 3, 0, 0, 3, 0, 0, 3, 3, 0, - 3, 3, 3, 0, 3, 0, 3, 0, 0, 0, 3, 3, 3, 0, 0, 3, - 0, 3, 0, 3, 0, 0, 0, 3, 2, 2, 2, 9, 16, 0, 0, 0, - 16, 16, 16, 0, 9, 9, 0, 0, -}; - -/* Decomposition_Type: 2872 bytes. */ - -RE_UINT32 re_get_decomposition_type(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_decomposition_type_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_decomposition_type_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_decomposition_type_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_decomposition_type_stage_4[pos + f] << 2; - value = re_decomposition_type_stage_5[pos + code]; - - return value; -} - -/* East_Asian_Width. */ - -static RE_UINT8 re_east_asian_width_stage_1[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 5, 6, 5, 5, 7, 8, 9, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 10, 10, 10, 12, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 13, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 13, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 14, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 15, - 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 15, -}; - -static RE_UINT8 re_east_asian_width_stage_2[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 6, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 7, 8, 9, 10, 11, 12, 13, 14, 5, 15, 5, 16, 5, 5, 17, 18, - 19, 20, 21, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 23, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, - 22, 22, 22, 22, 24, 5, 5, 5, 5, 25, 5, 5, 22, 22, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 26, 5, 5, 5, 5, 5, 5, 5, 5, - 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, - 27, 27, 27, 27, 27, 27, 27, 27, 27, 22, 22, 5, 5, 5, 28, 29, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 30, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 31, 32, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 33, - 5, 34, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 35, -}; - -static RE_UINT8 re_east_asian_width_stage_3[] = { - 0, 0, 1, 1, 1, 1, 1, 2, 0, 0, 3, 4, 5, 6, 7, 8, - 9, 10, 11, 12, 13, 14, 11, 0, 0, 0, 0, 0, 15, 16, 0, 0, - 0, 0, 0, 0, 0, 9, 9, 0, 0, 0, 0, 0, 17, 18, 0, 0, - 19, 19, 19, 19, 19, 19, 19, 0, 0, 20, 21, 20, 21, 0, 0, 0, - 9, 19, 19, 19, 19, 9, 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, - 22, 22, 22, 22, 22, 22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 23, 24, 25, 0, 0, 0, 26, 27, 0, 28, 0, 0, 0, 0, 0, - 29, 30, 31, 0, 0, 32, 33, 34, 35, 34, 0, 36, 0, 37, 38, 0, - 39, 40, 41, 42, 43, 44, 45, 0, 46, 47, 48, 49, 0, 0, 0, 0, - 0, 44, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, 19, 19, 51, 19, - 19, 19, 19, 19, 33, 19, 19, 52, 19, 53, 21, 54, 55, 56, 57, 0, - 58, 59, 0, 0, 60, 0, 61, 0, 0, 62, 0, 62, 63, 19, 64, 19, - 0, 0, 0, 65, 0, 38, 0, 66, 0, 0, 0, 0, 0, 0, 67, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 68, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 22, 70, 22, 22, 22, 22, 22, 71, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 72, 0, 73, - 74, 22, 22, 75, 76, 22, 22, 22, 22, 77, 22, 22, 22, 22, 22, 22, - 78, 22, 79, 76, 22, 22, 22, 22, 75, 22, 22, 80, 22, 22, 71, 22, - 22, 75, 22, 22, 81, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 75, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 0, 0, 0, 0, - 22, 22, 22, 22, 22, 22, 22, 22, 82, 22, 22, 22, 83, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 22, 82, 0, 0, 0, 0, 0, 0, 0, 0, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 71, 0, 0, 0, 0, 0, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, - 19, 84, 0, 22, 22, 85, 86, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 87, 88, 88, 88, 88, 88, 89, 90, 90, 90, 90, 91, 92, 93, 94, 65, - 95, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 96, 19, 97, 19, 19, 19, 34, 19, 19, 96, 0, 0, 0, 0, 0, 0, - 98, 22, 22, 80, 99, 95, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 79, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 0, - 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 97, -}; - -static RE_UINT8 re_east_asian_width_stage_4[] = { - 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, - 7, 8, 9, 7, 0, 10, 0, 0, 11, 12, 11, 13, 14, 10, 9, 14, - 8, 12, 9, 5, 15, 0, 0, 0, 16, 0, 12, 0, 0, 13, 12, 0, - 17, 0, 11, 12, 9, 11, 7, 15, 13, 0, 0, 0, 0, 0, 0, 10, - 5, 5, 5, 11, 0, 18, 17, 15, 11, 0, 7, 16, 7, 7, 7, 7, - 17, 7, 7, 7, 19, 7, 14, 0, 20, 20, 20, 20, 18, 9, 14, 14, - 9, 7, 0, 0, 8, 15, 12, 10, 0, 11, 0, 12, 17, 11, 0, 0, - 0, 0, 21, 11, 12, 15, 15, 0, 12, 10, 0, 0, 22, 10, 12, 0, - 12, 11, 12, 9, 7, 7, 7, 0, 7, 7, 14, 0, 0, 0, 15, 0, - 0, 0, 14, 0, 10, 11, 0, 0, 0, 12, 0, 0, 8, 12, 18, 12, - 15, 15, 10, 17, 18, 16, 7, 5, 0, 7, 0, 14, 0, 0, 11, 11, - 10, 0, 0, 0, 14, 7, 13, 13, 13, 13, 0, 0, 0, 15, 15, 0, - 0, 15, 0, 0, 0, 0, 0, 12, 0, 0, 23, 0, 7, 7, 19, 7, - 7, 0, 0, 0, 13, 14, 0, 0, 13, 13, 0, 14, 14, 13, 18, 13, - 14, 0, 0, 0, 13, 14, 0, 12, 0, 22, 15, 13, 0, 14, 0, 5, - 5, 0, 0, 0, 19, 19, 9, 19, 0, 0, 0, 13, 0, 7, 7, 19, - 19, 0, 7, 7, 0, 0, 0, 15, 0, 13, 7, 7, 0, 24, 1, 25, - 0, 26, 0, 0, 0, 17, 14, 0, 20, 20, 27, 20, 20, 0, 0, 0, - 20, 28, 0, 0, 20, 20, 20, 0, 29, 20, 20, 20, 20, 20, 20, 30, - 31, 20, 20, 20, 20, 30, 31, 20, 0, 31, 20, 20, 20, 20, 20, 28, - 20, 20, 30, 0, 20, 20, 7, 7, 20, 20, 20, 32, 20, 30, 0, 0, - 20, 20, 28, 0, 30, 20, 20, 20, 20, 30, 20, 0, 33, 34, 34, 34, - 34, 34, 34, 34, 35, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 37, - 38, 36, 38, 36, 38, 36, 38, 39, 34, 40, 36, 37, 28, 0, 0, 0, - 7, 7, 9, 0, 7, 7, 7, 14, 30, 0, 0, 0, 20, 20, 32, 0, -}; - -static RE_UINT8 re_east_asian_width_stage_5[] = { - 0, 0, 0, 0, 5, 5, 5, 5, 5, 5, 5, 0, 0, 1, 5, 5, - 1, 5, 5, 1, 1, 0, 1, 0, 5, 1, 1, 5, 1, 1, 1, 1, - 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, - 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, - 0, 1, 0, 1, 0, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0, 1, - 3, 3, 3, 3, 0, 2, 0, 0, 0, 1, 1, 0, 0, 3, 3, 0, - 0, 0, 5, 5, 5, 5, 0, 0, 0, 5, 5, 0, 3, 3, 0, 3, - 3, 3, 0, 0, 4, 3, 3, 3, 3, 3, 3, 0, 0, 3, 3, 3, - 3, 0, 0, 0, 0, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 2, 2, 2, 0, 0, 0, - 4, 4, 4, 0, -}; - -/* East_Asian_Width: 1668 bytes. */ - -RE_UINT32 re_get_east_asian_width(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_east_asian_width_stage_1[f] << 4; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_east_asian_width_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_east_asian_width_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_east_asian_width_stage_4[pos + f] << 2; - value = re_east_asian_width_stage_5[pos + code]; - - return value; -} - -/* Joining_Group. */ - -static RE_UINT8 re_joining_group_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_joining_group_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_joining_group_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 0, - 0, 4, 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, -}; - -static RE_UINT8 re_joining_group_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 0, 7, 8, 9, - 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 0, 0, 21, 0, 22, - 0, 0, 23, 24, 25, 26, 0, 0, 0, 27, 28, 29, 30, 31, 32, 33, - 0, 0, 0, 0, 34, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_joining_group_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 45, 0, 3, 3, 43, 3, 45, 3, - 4, 41, 4, 4, 13, 13, 13, 6, 6, 31, 31, 35, 35, 33, 33, 39, - 39, 1, 1, 11, 11, 55, 55, 55, 0, 9, 29, 19, 22, 24, 26, 16, - 43, 45, 45, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 29, - 0, 3, 3, 3, 0, 3, 43, 43, 45, 4, 4, 4, 4, 4, 4, 4, - 4, 13, 13, 13, 13, 13, 13, 13, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 31, 31, 31, 31, 31, 31, 31, 31, 31, 35, 35, 35, 33, 33, 39, - 1, 9, 9, 9, 9, 9, 9, 29, 29, 11, 38, 11, 19, 19, 19, 11, - 11, 11, 11, 11, 11, 22, 22, 22, 22, 26, 26, 26, 26, 56, 21, 13, - 41, 17, 17, 14, 43, 43, 43, 43, 43, 43, 43, 43, 55, 47, 55, 43, - 45, 45, 46, 46, 0, 41, 0, 0, 0, 0, 0, 0, 0, 0, 6, 31, - 0, 0, 35, 33, 1, 0, 0, 21, 2, 0, 5, 12, 12, 7, 7, 15, - 44, 50, 18, 42, 42, 48, 49, 20, 23, 25, 27, 36, 10, 8, 28, 32, - 34, 30, 7, 37, 40, 5, 12, 7, 0, 0, 0, 0, 0, 51, 52, 53, - 4, 4, 4, 4, 4, 4, 4, 13, 13, 6, 6, 31, 35, 1, 1, 1, - 9, 9, 11, 11, 11, 24, 24, 26, 26, 26, 22, 31, 31, 35, 13, 13, - 35, 31, 13, 3, 3, 55, 55, 45, 43, 43, 54, 54, 13, 35, 35, 19, - 4, 0, 13, 39, 9, 29, 22, 24, 45, 45, 31, 43, 57, 0, 0, 0, -}; - -/* Joining_Group: 481 bytes. */ - -RE_UINT32 re_get_joining_group(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_joining_group_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_joining_group_stage_2[pos + f] << 5; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_joining_group_stage_3[pos + f] << 4; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_joining_group_stage_4[pos + f] << 3; - value = re_joining_group_stage_5[pos + code]; - - return value; -} - -/* Joining_Type. */ - -static RE_UINT8 re_joining_type_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 4, 5, 2, 2, 6, 2, 2, 7, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 8, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_joining_type_stage_2[] = { - 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, - 15, 1, 1, 16, 1, 1, 1, 17, 18, 19, 20, 21, 22, 23, 1, 1, - 24, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 25, 26, 1, 1, - 27, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 28, 1, 29, 30, 31, 32, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 33, 1, 1, 34, 35, - 1, 36, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 1, 1, 1, - 38, 39, 1, 1, 1, 1, 40, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 41, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 42, 43, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 44, 45, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_joining_type_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 2, 5, 6, 0, 0, 0, - 0, 7, 8, 9, 10, 2, 11, 12, 13, 14, 15, 15, 16, 17, 18, 19, - 20, 21, 22, 2, 23, 24, 25, 26, 0, 0, 27, 28, 29, 15, 30, 31, - 0, 32, 33, 0, 34, 35, 0, 0, 0, 0, 36, 0, 0, 0, 37, 38, - 39, 0, 0, 40, 41, 42, 43, 0, 44, 0, 0, 45, 46, 0, 43, 0, - 47, 0, 0, 45, 48, 44, 0, 49, 47, 0, 0, 45, 50, 0, 43, 0, - 44, 0, 0, 51, 46, 52, 43, 0, 53, 0, 0, 0, 54, 0, 0, 0, - 0, 0, 0, 55, 56, 57, 43, 0, 0, 0, 0, 51, 58, 0, 43, 0, - 0, 0, 0, 0, 46, 0, 43, 0, 0, 0, 0, 0, 59, 60, 0, 0, - 0, 0, 0, 61, 62, 0, 0, 0, 0, 0, 0, 63, 64, 0, 0, 0, - 0, 65, 0, 66, 0, 0, 0, 67, 68, 69, 2, 70, 52, 0, 0, 0, - 0, 0, 71, 72, 0, 73, 28, 74, 75, 1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 71, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 76, 0, 76, 0, 43, 0, 43, 0, 0, 0, 77, 78, 79, 0, 0, - 80, 0, 15, 15, 15, 15, 15, 81, 82, 15, 83, 0, 0, 0, 0, 0, - 0, 0, 84, 85, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 86, 0, 0, 0, 87, 88, 89, 0, 0, 0, 0, 0, 0, 0, 0, - 90, 0, 0, 91, 53, 0, 92, 90, 93, 0, 94, 0, 0, 0, 95, 93, - 0, 0, 96, 97, 0, 0, 0, 0, 0, 0, 0, 0, 0, 98, 99, 100, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 2, 101, 96, - 102, 0, 103, 0, 0, 0, 104, 0, 0, 0, 0, 0, 0, 2, 2, 28, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 93, - 0, 0, 0, 0, 0, 0, 0, 20, 0, 0, 0, 0, 0, 0, 2, 2, - 0, 0, 105, 0, 0, 0, 0, 0, 0, 106, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 20, 107, 0, 20, 0, 0, 0, 0, 0, 93, - 108, 0, 57, 0, 15, 15, 15, 109, 0, 0, 0, 0, 100, 0, 2, 93, - 0, 0, 110, 0, 111, 93, 0, 0, 39, 0, 0, 112, 0, 0, 0, 0, - 0, 0, 113, 114, 115, 0, 0, 0, 0, 0, 0, 116, 44, 0, 117, 52, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 118, 0, - 0, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 0, 101, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 120, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, - 121, 0, 0, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 44, 0, 0, 123, 101, 0, 0, 0, 93, 0, 0, 124, 0, 0, 0, 0, - 39, 0, 125, 126, 0, 0, 0, 0, 93, 0, 0, 127, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 129, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 20, 39, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 130, 131, 132, 0, 105, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 44, 0, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, -}; - -static RE_UINT8 re_joining_type_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 2, 2, 3, 2, 4, 0, - 5, 2, 2, 2, 2, 2, 2, 6, 7, 6, 0, 0, 2, 2, 8, 9, - 10, 11, 12, 13, 14, 15, 15, 15, 16, 15, 17, 2, 0, 0, 0, 18, - 19, 20, 15, 15, 15, 15, 21, 21, 21, 21, 22, 15, 15, 15, 15, 15, - 23, 21, 21, 24, 25, 26, 2, 27, 2, 27, 28, 29, 0, 0, 18, 30, - 0, 0, 0, 3, 31, 32, 22, 33, 15, 15, 34, 23, 2, 2, 8, 35, - 15, 15, 32, 15, 15, 15, 13, 36, 24, 36, 22, 15, 0, 37, 2, 2, - 9, 0, 0, 0, 0, 0, 18, 15, 15, 15, 38, 2, 2, 0, 39, 0, - 0, 37, 6, 2, 2, 5, 5, 4, 36, 33, 12, 13, 15, 40, 5, 0, - 41, 15, 25, 42, 0, 2, 2, 2, 2, 2, 2, 8, 8, 0, 0, 0, - 0, 0, 43, 9, 5, 2, 9, 1, 5, 2, 0, 0, 37, 0, 0, 0, - 1, 0, 0, 0, 0, 0, 0, 9, 5, 9, 0, 1, 7, 0, 0, 0, - 7, 3, 27, 4, 4, 1, 0, 0, 5, 6, 9, 1, 0, 0, 0, 27, - 0, 43, 0, 0, 43, 0, 0, 0, 9, 0, 0, 1, 0, 0, 0, 37, - 9, 37, 28, 4, 0, 7, 0, 0, 0, 43, 0, 4, 0, 0, 43, 0, - 37, 44, 0, 0, 1, 2, 8, 0, 0, 3, 2, 8, 1, 2, 6, 9, - 0, 0, 2, 4, 0, 0, 4, 0, 0, 45, 1, 0, 5, 2, 2, 8, - 2, 28, 0, 5, 2, 2, 5, 2, 2, 2, 2, 9, 0, 0, 0, 5, - 28, 2, 7, 7, 0, 0, 4, 37, 5, 9, 0, 0, 43, 7, 0, 1, - 37, 9, 0, 0, 0, 6, 2, 4, 0, 43, 5, 2, 2, 0, 0, 1, - 0, 46, 47, 4, 15, 15, 0, 0, 0, 46, 15, 15, 15, 15, 48, 0, - 8, 3, 9, 0, 43, 0, 5, 0, 0, 3, 27, 0, 0, 43, 2, 8, - 44, 5, 2, 9, 3, 2, 2, 27, 2, 0, 0, 0, 0, 28, 8, 9, - 0, 0, 3, 2, 4, 0, 0, 0, 37, 4, 6, 0, 0, 43, 4, 45, - 0, 0, 0, 2, 2, 37, 0, 0, 8, 2, 2, 2, 28, 2, 9, 1, - 0, 9, 0, 0, 2, 8, 0, 0, 0, 0, 3, 49, 0, 0, 37, 8, - 2, 9, 37, 2, 0, 0, 37, 4, 0, 0, 7, 0, 8, 2, 2, 4, - 43, 43, 3, 0, 50, 0, 0, 0, 0, 37, 2, 4, 0, 3, 2, 2, - 3, 37, 4, 9, 0, 0, 5, 8, 7, 7, 0, 0, 3, 0, 0, 9, - 28, 27, 9, 37, 0, 0, 0, 4, 0, 1, 9, 1, 0, 0, 0, 43, - 0, 0, 5, 0, 5, 7, 0, 2, 0, 0, 8, 3, 0, 0, 2, 2, - 3, 8, 7, 1, 0, 3, 2, 5, 2, 9, 0, 0, 0, 37, 2, 8, - 0, 0, 3, 1, 2, 6, 0, 0, 0, 3, 4, 0, 3, 2, 2, 2, - 8, 5, 2, 0, -}; - -static RE_UINT8 re_joining_type_stage_5[] = { - 0, 0, 0, 0, 0, 5, 0, 0, 5, 5, 5, 5, 0, 0, 0, 5, - 5, 5, 0, 0, 0, 5, 5, 5, 5, 5, 0, 5, 0, 5, 5, 0, - 5, 5, 5, 0, 5, 0, 0, 0, 2, 0, 3, 3, 3, 3, 2, 3, - 2, 3, 2, 2, 2, 2, 2, 3, 3, 3, 3, 2, 2, 2, 2, 2, - 1, 2, 2, 2, 3, 2, 2, 5, 0, 0, 2, 2, 5, 3, 3, 3, - 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 2, 3, 2, 2, 3, - 2, 3, 2, 3, 2, 2, 3, 3, 0, 3, 5, 5, 5, 0, 0, 5, - 5, 0, 5, 5, 5, 5, 3, 3, 2, 0, 0, 2, 3, 5, 2, 2, - 2, 3, 3, 3, 2, 2, 3, 2, 3, 2, 3, 2, 0, 3, 2, 2, - 3, 2, 2, 2, 0, 0, 5, 5, 2, 2, 2, 5, 0, 0, 1, 0, - 3, 2, 0, 0, 2, 0, 2, 2, 3, 0, 0, 0, 0, 0, 5, 0, - 5, 0, 5, 0, 0, 5, 0, 5, 0, 0, 0, 2, 0, 0, 1, 5, - 2, 5, 2, 0, 0, 1, 5, 5, 2, 2, 4, 0, -}; - -/* Joining_Type: 1896 bytes. */ - -RE_UINT32 re_get_joining_type(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_joining_type_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_joining_type_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_joining_type_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_joining_type_stage_4[pos + f] << 2; - value = re_joining_type_stage_5[pos + code]; - - return value; -} - -/* Line_Break. */ - -static RE_UINT8 re_line_break_stage_1[] = { - 0, 1, 2, 3, 4, 5, 5, 5, 5, 5, 6, 7, 8, 9, 10, 11, - 12, 13, 14, 15, 10, 10, 16, 10, 10, 10, 10, 17, 10, 18, 19, 20, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 21, - 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 21, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 22, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, - 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, -}; - -static RE_UINT8 re_line_break_stage_2[] = { - 0, 1, 2, 2, 2, 3, 4, 5, 2, 6, 7, 8, 9, 10, 11, 12, - 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, - 29, 30, 31, 32, 33, 34, 35, 36, 37, 2, 2, 2, 2, 38, 39, 40, - 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 2, 51, 2, 2, 52, 53, - 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, - 2, 2, 2, 70, 2, 2, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, - 81, 82, 83, 84, 85, 86, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 87, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 88, 79, 79, 79, 79, 79, 79, 79, 79, 89, 2, 2, 90, 91, 2, 92, - 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 101, - 102, 103, 104, 105, 106, 107, 101, 102, 103, 104, 105, 106, 107, 101, 102, 103, - 104, 105, 106, 107, 101, 102, 103, 104, 105, 106, 107, 101, 102, 103, 104, 105, - 106, 107, 101, 102, 103, 104, 105, 106, 107, 101, 102, 103, 104, 105, 106, 107, - 101, 102, 103, 104, 105, 106, 107, 101, 102, 103, 104, 105, 106, 107, 101, 102, - 103, 104, 105, 106, 107, 101, 102, 103, 104, 105, 106, 107, 101, 102, 103, 108, - 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, 109, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 79, 79, 79, 79, 110, 111, 2, 2, 112, 113, 114, 115, 116, 117, - 118, 119, 120, 121, 72, 122, 123, 124, 2, 125, 72, 72, 72, 72, 72, 72, - 126, 72, 127, 128, 129, 72, 130, 72, 131, 72, 72, 72, 132, 72, 72, 72, - 133, 134, 135, 136, 72, 72, 72, 72, 72, 72, 72, 72, 72, 137, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 2, 2, 2, 2, 2, 2, 138, 72, 139, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 2, 2, 2, 2, 140, 141, 142, 2, 143, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 2, 2, 2, 2, 144, 72, 72, 72, 72, 72, 72, 72, 72, 72, 145, 146, - 147, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 2, 148, 149, 150, 151, 72, 152, 72, 153, 154, 155, 2, 2, 156, 2, 157, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 158, 159, 72, 72, - 160, 161, 162, 163, 164, 72, 165, 166, 167, 168, 169, 170, 171, 172, 173, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, - 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 79, 174, - 175, 72, 176, 177, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, - 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, 72, -}; - -static RE_UINT16 re_line_break_stage_3[] = { - 0, 1, 2, 3, 4, 5, 4, 6, 7, 1, 8, 9, 4, 10, 4, 10, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 11, 12, 4, 4, - 1, 1, 1, 1, 13, 14, 15, 16, 17, 4, 18, 4, 4, 4, 4, 4, - 19, 4, 4, 4, 4, 4, 4, 4, 4, 4, 20, 21, 4, 22, 21, 4, - 23, 24, 1, 25, 26, 27, 28, 29, 30, 31, 4, 4, 32, 1, 33, 34, - 4, 4, 4, 4, 4, 35, 36, 37, 38, 39, 4, 1, 40, 4, 4, 4, - 4, 4, 41, 42, 37, 4, 32, 43, 4, 44, 45, 46, 4, 47, 48, 48, - 48, 48, 49, 48, 48, 48, 50, 51, 52, 4, 4, 53, 1, 54, 55, 56, - 57, 58, 59, 60, 61, 62, 63, 64, 65, 58, 59, 66, 67, 68, 69, 70, - 71, 18, 59, 72, 73, 74, 63, 75, 57, 58, 59, 72, 76, 77, 63, 20, - 78, 79, 80, 81, 82, 83, 69, 84, 85, 86, 59, 87, 88, 89, 63, 90, - 91, 86, 59, 92, 88, 93, 63, 94, 91, 86, 4, 95, 96, 97, 63, 98, - 99, 100, 4, 101, 102, 103, 48, 104, 105, 106, 106, 107, 108, 109, 48, 48, - 110, 111, 112, 113, 114, 115, 48, 48, 116, 117, 37, 118, 56, 4, 119, 120, - 121, 122, 1, 123, 124, 125, 48, 48, 106, 106, 106, 106, 126, 106, 106, 106, - 106, 127, 4, 4, 128, 4, 4, 4, 129, 129, 129, 129, 129, 129, 130, 130, - 130, 130, 131, 132, 132, 132, 132, 132, 4, 4, 4, 4, 133, 134, 4, 4, - 133, 4, 4, 135, 136, 137, 4, 4, 4, 136, 4, 4, 4, 138, 139, 119, - 4, 140, 4, 4, 4, 4, 4, 141, 142, 4, 4, 4, 4, 4, 4, 4, - 142, 143, 4, 4, 4, 4, 144, 74, 145, 146, 4, 147, 4, 148, 145, 149, - 106, 106, 106, 106, 106, 150, 151, 140, 152, 151, 4, 4, 4, 4, 4, 20, - 4, 4, 153, 4, 4, 4, 4, 154, 4, 119, 155, 155, 156, 106, 157, 158, - 106, 106, 159, 106, 160, 161, 4, 4, 4, 162, 106, 106, 106, 163, 106, 164, - 151, 151, 157, 48, 48, 48, 48, 48, 165, 4, 4, 166, 167, 168, 169, 170, - 171, 4, 172, 37, 4, 4, 41, 173, 4, 4, 166, 174, 175, 37, 4, 176, - 48, 48, 48, 48, 20, 177, 178, 179, 4, 4, 4, 4, 1, 1, 180, 181, - 4, 182, 4, 4, 182, 183, 4, 184, 4, 4, 4, 185, 185, 186, 4, 187, - 188, 189, 190, 191, 192, 193, 194, 195, 196, 119, 197, 198, 199, 1, 1, 200, - 201, 202, 203, 4, 4, 204, 205, 206, 207, 206, 4, 4, 4, 208, 4, 4, - 209, 210, 211, 212, 213, 214, 215, 4, 216, 217, 218, 219, 4, 4, 4, 4, - 4, 220, 221, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 222, - 4, 4, 223, 48, 224, 48, 225, 225, 225, 225, 225, 225, 225, 225, 225, 226, - 225, 225, 225, 225, 205, 225, 225, 227, 225, 228, 229, 230, 231, 232, 233, 4, - 234, 235, 4, 236, 237, 4, 238, 239, 4, 240, 4, 241, 242, 243, 244, 245, - 246, 4, 4, 4, 4, 247, 248, 249, 225, 250, 4, 4, 251, 4, 252, 4, - 253, 254, 4, 4, 4, 255, 4, 256, 4, 4, 4, 4, 119, 257, 48, 48, - 48, 48, 48, 48, 48, 48, 48, 48, 4, 4, 46, 4, 4, 46, 4, 4, - 4, 4, 4, 4, 4, 4, 258, 259, 4, 4, 128, 4, 4, 4, 260, 261, - 4, 223, 262, 262, 262, 262, 1, 1, 263, 264, 265, 266, 48, 48, 48, 48, - 267, 268, 267, 267, 267, 267, 267, 222, 267, 267, 267, 267, 267, 267, 267, 267, - 267, 267, 267, 267, 267, 269, 48, 270, 271, 272, 273, 274, 275, 267, 276, 267, - 277, 278, 279, 267, 276, 267, 277, 280, 281, 267, 282, 283, 267, 267, 267, 267, - 284, 267, 267, 285, 267, 267, 222, 286, 267, 284, 267, 267, 287, 267, 267, 267, - 267, 267, 267, 267, 267, 267, 267, 284, 267, 267, 267, 267, 4, 4, 4, 4, - 267, 288, 267, 267, 267, 267, 267, 267, 289, 267, 267, 267, 290, 4, 4, 176, - 291, 4, 292, 48, 4, 4, 258, 293, 4, 294, 4, 4, 4, 4, 4, 295, - 46, 296, 224, 48, 48, 48, 48, 90, 297, 4, 298, 299, 4, 4, 4, 300, - 301, 4, 4, 166, 302, 151, 1, 303, 37, 4, 304, 4, 305, 306, 129, 307, - 52, 4, 4, 308, 309, 310, 48, 48, 4, 4, 311, 180, 312, 313, 106, 159, - 106, 106, 106, 106, 314, 315, 32, 316, 317, 318, 262, 48, 48, 48, 48, 48, - 48, 48, 48, 48, 4, 4, 319, 151, 320, 321, 322, 323, 322, 324, 322, 320, - 321, 322, 323, 322, 324, 322, 320, 321, 322, 323, 322, 324, 322, 320, 321, 322, - 323, 322, 324, 322, 320, 321, 322, 323, 322, 324, 322, 320, 321, 322, 323, 322, - 324, 322, 320, 321, 322, 323, 322, 324, 322, 320, 321, 322, 323, 322, 324, 322, - 323, 322, 325, 130, 326, 132, 132, 327, 328, 328, 328, 328, 328, 328, 328, 328, - 223, 329, 330, 331, 332, 4, 4, 4, 4, 4, 4, 4, 333, 334, 4, 4, - 4, 4, 4, 335, 48, 4, 4, 4, 4, 336, 4, 4, 20, 48, 48, 337, - 1, 338, 180, 339, 340, 341, 342, 185, 4, 4, 4, 4, 4, 4, 4, 343, - 344, 345, 267, 346, 267, 347, 348, 349, 4, 350, 4, 46, 351, 352, 353, 354, - 355, 4, 137, 356, 184, 184, 48, 48, 4, 4, 4, 4, 4, 4, 4, 224, - 357, 4, 4, 358, 4, 4, 4, 4, 224, 359, 48, 48, 48, 4, 4, 360, - 4, 119, 4, 4, 4, 74, 48, 48, 4, 46, 296, 4, 224, 48, 48, 48, - 4, 361, 4, 4, 362, 363, 48, 48, 4, 184, 151, 48, 48, 48, 48, 48, - 364, 4, 4, 365, 4, 366, 48, 48, 4, 367, 4, 368, 48, 48, 48, 48, - 4, 4, 4, 369, 48, 48, 48, 48, 370, 371, 4, 372, 20, 373, 4, 4, - 4, 4, 4, 374, 4, 375, 4, 376, 4, 4, 4, 4, 377, 48, 48, 48, - 48, 48, 48, 48, 48, 48, 4, 46, 171, 4, 4, 378, 379, 336, 380, 48, - 171, 4, 4, 381, 382, 4, 377, 151, 171, 4, 305, 383, 384, 48, 48, 48, - 171, 4, 4, 308, 385, 151, 48, 48, 4, 4, 32, 386, 151, 48, 48, 48, - 4, 4, 4, 4, 4, 4, 46, 48, 4, 4, 4, 4, 4, 4, 387, 384, - 4, 4, 4, 4, 4, 388, 4, 4, 389, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 390, 4, 4, 46, 48, 48, 48, 48, 48, - 4, 4, 4, 377, 48, 48, 48, 48, 4, 4, 4, 4, 141, 391, 1, 51, - 392, 171, 48, 48, 48, 48, 48, 48, 393, 48, 48, 48, 48, 48, 48, 48, - 4, 4, 4, 4, 4, 4, 4, 154, 4, 4, 22, 4, 4, 4, 394, 1, - 395, 4, 396, 4, 4, 184, 48, 48, 4, 4, 4, 4, 397, 48, 48, 48, - 4, 4, 4, 4, 4, 223, 4, 333, 4, 4, 4, 4, 4, 185, 4, 4, - 4, 145, 398, 399, 400, 4, 4, 4, 401, 402, 4, 403, 404, 86, 4, 4, - 4, 4, 375, 4, 4, 4, 4, 4, 4, 4, 4, 4, 405, 406, 406, 406, - 400, 4, 407, 408, 409, 410, 411, 412, 413, 359, 414, 359, 48, 48, 48, 333, - 267, 267, 270, 267, 267, 267, 267, 267, 267, 222, 284, 415, 283, 283, 48, 48, - 416, 225, 417, 225, 225, 225, 418, 225, 225, 416, 48, 48, 48, 48, 419, 420, - 421, 267, 267, 285, 422, 393, 48, 48, 267, 267, 423, 424, 267, 267, 267, 289, - 267, 222, 267, 425, 426, 48, 267, 423, 267, 267, 267, 284, 427, 267, 267, 267, - 267, 267, 428, 429, 267, 267, 267, 430, 431, 432, 433, 434, 296, 267, 435, 48, - 48, 48, 48, 48, 48, 48, 48, 436, 267, 267, 267, 267, 437, 48, 48, 48, - 267, 267, 267, 267, 269, 48, 48, 48, 4, 4, 4, 4, 4, 4, 4, 296, - 267, 267, 267, 267, 267, 267, 267, 282, 438, 48, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 48, -}; - -static RE_UINT8 re_line_break_stage_4[] = { - 0, 0, 0, 0, 1, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 4, 5, 6, 7, 8, 9, 10, 11, 12, 12, 12, 12, 12, 13, 14, 15, - 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 16, 17, 14, - 14, 14, 14, 14, 14, 16, 18, 19, 0, 0, 20, 0, 0, 0, 0, 0, - 21, 22, 23, 24, 25, 26, 27, 14, 22, 28, 29, 28, 28, 26, 28, 30, - 14, 14, 14, 24, 14, 14, 14, 14, 14, 14, 14, 24, 31, 28, 31, 14, - 25, 14, 14, 14, 28, 28, 24, 32, 0, 0, 0, 0, 0, 0, 0, 33, - 0, 0, 0, 0, 0, 0, 34, 34, 34, 35, 0, 0, 0, 0, 0, 0, - 14, 14, 14, 14, 36, 14, 14, 37, 36, 36, 14, 14, 14, 38, 38, 14, - 14, 39, 14, 14, 14, 14, 14, 14, 14, 19, 0, 0, 0, 14, 14, 14, - 14, 14, 14, 14, 36, 36, 36, 36, 39, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 38, 39, 14, 14, 14, 14, 14, 14, 14, 40, 41, 36, 42, - 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 44, - 19, 45, 0, 46, 36, 36, 36, 36, 47, 47, 47, 47, 47, 47, 47, 47, - 47, 47, 47, 47, 47, 48, 36, 36, 47, 49, 38, 36, 36, 36, 36, 36, - 14, 14, 38, 14, 50, 51, 13, 14, 0, 0, 0, 0, 0, 52, 53, 54, - 14, 14, 14, 14, 14, 19, 0, 0, 12, 12, 12, 12, 12, 55, 56, 14, - 45, 14, 14, 14, 14, 14, 14, 14, 14, 14, 57, 0, 0, 0, 45, 19, - 0, 0, 45, 19, 45, 0, 0, 14, 12, 12, 12, 12, 12, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 39, 19, 14, 14, 14, 14, 14, 14, 14, - 0, 0, 0, 0, 0, 53, 39, 14, 14, 14, 14, 0, 0, 0, 0, 0, - 45, 36, 36, 36, 36, 36, 36, 36, 0, 0, 14, 14, 58, 38, 36, 36, - 14, 14, 14, 0, 0, 19, 0, 0, 0, 0, 19, 0, 19, 0, 0, 36, - 14, 14, 14, 14, 14, 14, 14, 38, 14, 14, 14, 14, 19, 0, 36, 38, - 36, 36, 36, 36, 36, 36, 36, 36, 38, 14, 14, 14, 14, 14, 38, 36, - 36, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 53, - 0, 0, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 0, 45, 0, - 19, 0, 0, 0, 14, 14, 14, 14, 14, 0, 59, 12, 12, 12, 12, 12, - 14, 14, 14, 14, 39, 14, 14, 14, 43, 0, 39, 14, 14, 14, 38, 39, - 38, 39, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 38, 14, 14, 14, - 38, 38, 36, 14, 14, 36, 45, 0, 0, 0, 53, 43, 53, 43, 0, 38, - 36, 36, 36, 43, 36, 36, 14, 39, 14, 0, 36, 12, 12, 12, 12, 12, - 14, 51, 14, 14, 50, 9, 36, 36, 43, 0, 39, 14, 14, 38, 36, 39, - 38, 14, 39, 38, 14, 36, 53, 0, 0, 53, 36, 43, 53, 43, 0, 36, - 43, 36, 36, 36, 39, 14, 38, 38, 36, 36, 36, 12, 12, 12, 12, 12, - 0, 14, 19, 36, 36, 36, 36, 36, 43, 0, 39, 14, 14, 14, 14, 39, - 38, 14, 39, 14, 14, 36, 45, 0, 0, 0, 0, 43, 0, 43, 0, 36, - 38, 36, 36, 36, 36, 36, 36, 36, 9, 36, 36, 36, 36, 36, 36, 36, - 0, 0, 53, 43, 53, 43, 0, 36, 36, 36, 36, 0, 36, 36, 14, 39, - 36, 45, 39, 14, 14, 38, 36, 14, 38, 14, 14, 36, 39, 38, 38, 14, - 36, 39, 38, 36, 14, 38, 36, 14, 14, 14, 14, 14, 14, 36, 36, 0, - 0, 53, 36, 0, 53, 0, 0, 36, 38, 36, 36, 43, 36, 36, 36, 36, - 14, 14, 14, 14, 9, 38, 36, 36, 43, 0, 39, 14, 14, 14, 38, 14, - 38, 14, 14, 14, 14, 14, 14, 14, 14, 14, 39, 14, 14, 36, 39, 0, - 0, 0, 53, 0, 53, 0, 0, 36, 36, 36, 43, 53, 14, 36, 36, 36, - 36, 36, 36, 36, 14, 14, 14, 14, 36, 0, 39, 14, 14, 14, 38, 14, - 14, 14, 39, 14, 14, 36, 45, 0, 36, 36, 43, 53, 36, 36, 36, 38, - 39, 38, 36, 36, 36, 36, 36, 36, 14, 14, 14, 14, 14, 38, 39, 0, - 0, 0, 53, 0, 53, 0, 0, 38, 36, 36, 36, 43, 36, 36, 36, 36, - 14, 14, 14, 36, 60, 14, 14, 14, 36, 0, 39, 14, 14, 14, 14, 14, - 14, 14, 14, 38, 36, 14, 14, 14, 14, 39, 14, 14, 14, 14, 39, 36, - 14, 14, 14, 38, 36, 53, 36, 43, 0, 0, 53, 53, 0, 0, 0, 0, - 36, 0, 38, 36, 36, 36, 36, 36, 61, 62, 62, 62, 62, 62, 62, 62, - 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 63, 36, 42, - 62, 62, 62, 62, 62, 62, 62, 64, 12, 12, 12, 12, 12, 59, 36, 36, - 61, 63, 63, 61, 63, 63, 61, 36, 36, 36, 62, 62, 61, 62, 62, 62, - 61, 62, 61, 61, 36, 62, 61, 62, 62, 62, 62, 62, 62, 61, 62, 36, - 62, 62, 63, 63, 62, 62, 62, 36, 12, 12, 12, 12, 12, 36, 62, 62, - 32, 65, 29, 65, 66, 67, 68, 54, 54, 69, 57, 14, 0, 14, 14, 14, - 14, 14, 44, 19, 19, 70, 70, 0, 14, 14, 14, 14, 14, 14, 38, 36, - 43, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 14, 14, 19, 0, - 0, 0, 0, 0, 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 53, 59, - 14, 14, 14, 45, 14, 14, 38, 14, 65, 71, 14, 14, 72, 73, 36, 36, - 12, 12, 12, 12, 12, 59, 14, 14, 12, 12, 12, 12, 12, 62, 62, 62, - 14, 14, 14, 39, 36, 36, 39, 36, 74, 74, 74, 74, 74, 74, 74, 74, - 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 75, 76, 76, 76, 76, - 76, 76, 76, 76, 76, 76, 76, 76, 14, 14, 14, 14, 38, 14, 14, 36, - 14, 14, 14, 38, 38, 14, 14, 36, 38, 14, 14, 36, 14, 14, 14, 38, - 38, 14, 14, 36, 14, 14, 14, 14, 14, 14, 14, 38, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 38, 43, 0, 27, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 36, 36, 36, 14, 14, 38, 36, 36, 36, 36, 36, - 77, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 16, 78, 36, - 14, 14, 14, 14, 14, 27, 59, 14, 14, 14, 14, 14, 14, 14, 38, 14, - 14, 0, 53, 36, 36, 36, 36, 36, 14, 0, 1, 41, 36, 36, 36, 36, - 14, 0, 36, 36, 36, 36, 36, 36, 38, 0, 36, 36, 36, 36, 36, 36, - 62, 62, 59, 79, 77, 80, 62, 36, 12, 12, 12, 12, 12, 36, 36, 36, - 14, 54, 59, 29, 54, 19, 0, 73, 14, 14, 14, 14, 19, 38, 36, 36, - 14, 14, 14, 36, 36, 36, 36, 36, 0, 0, 0, 0, 0, 0, 36, 36, - 38, 36, 54, 12, 12, 12, 12, 12, 62, 62, 62, 62, 62, 62, 62, 36, - 62, 62, 63, 36, 36, 36, 36, 36, 62, 62, 62, 62, 62, 62, 36, 36, - 62, 62, 62, 62, 62, 36, 36, 36, 12, 12, 12, 12, 12, 63, 36, 62, - 14, 14, 14, 19, 0, 0, 36, 14, 62, 62, 62, 62, 62, 62, 62, 63, - 62, 62, 62, 62, 62, 62, 63, 43, 0, 0, 45, 14, 14, 14, 14, 14, - 14, 14, 0, 0, 0, 0, 0, 0, 0, 0, 45, 14, 14, 14, 36, 36, - 12, 12, 12, 12, 12, 59, 27, 59, 77, 14, 14, 14, 14, 19, 0, 0, - 0, 0, 14, 14, 14, 14, 38, 36, 0, 45, 14, 14, 14, 14, 14, 14, - 19, 0, 0, 0, 0, 0, 0, 14, 0, 0, 36, 36, 36, 36, 14, 14, - 0, 0, 0, 0, 36, 81, 59, 59, 12, 12, 12, 12, 12, 36, 39, 14, - 14, 14, 14, 14, 14, 14, 14, 59, 0, 45, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 45, 14, 19, 14, 14, 0, 45, 38, 36, 36, 36, 36, - 0, 0, 0, 53, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 0, 0, - 14, 14, 14, 36, 14, 14, 14, 36, 14, 14, 14, 14, 39, 39, 39, 39, - 14, 14, 14, 14, 14, 14, 14, 36, 14, 14, 38, 14, 14, 14, 14, 14, - 14, 14, 36, 14, 14, 14, 39, 14, 36, 14, 38, 14, 14, 14, 32, 38, - 59, 59, 59, 82, 59, 83, 0, 0, 82, 59, 84, 25, 85, 86, 85, 86, - 28, 14, 87, 88, 89, 0, 0, 33, 51, 51, 51, 51, 7, 90, 91, 14, - 14, 14, 92, 93, 91, 14, 14, 14, 14, 14, 14, 77, 59, 59, 27, 59, - 94, 14, 38, 0, 0, 0, 0, 0, 14, 36, 25, 14, 14, 14, 16, 95, - 24, 28, 25, 14, 14, 14, 16, 78, 23, 23, 23, 6, 23, 23, 23, 23, - 23, 23, 23, 22, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, - 53, 36, 36, 36, 36, 36, 36, 36, 14, 50, 24, 14, 50, 14, 14, 14, - 14, 24, 14, 96, 14, 14, 14, 14, 24, 25, 14, 14, 14, 24, 14, 14, - 14, 14, 28, 14, 14, 24, 14, 25, 28, 28, 28, 28, 28, 28, 14, 14, - 28, 28, 28, 28, 28, 14, 14, 14, 14, 14, 14, 14, 24, 36, 36, 36, - 14, 25, 25, 14, 14, 14, 14, 14, 25, 28, 14, 24, 25, 24, 14, 24, - 24, 23, 24, 14, 14, 25, 24, 28, 25, 24, 24, 24, 28, 28, 25, 25, - 14, 14, 28, 28, 14, 14, 28, 14, 14, 14, 14, 14, 25, 14, 25, 14, - 14, 25, 14, 14, 14, 14, 14, 14, 28, 14, 28, 28, 14, 28, 14, 28, - 14, 28, 14, 28, 14, 14, 14, 14, 14, 14, 24, 14, 24, 14, 14, 14, - 14, 14, 24, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 24, - 14, 25, 14, 14, 14, 97, 14, 14, 14, 14, 14, 14, 16, 98, 14, 14, - 97, 97, 36, 36, 36, 36, 36, 36, 14, 14, 14, 38, 36, 36, 36, 36, - 14, 14, 14, 14, 14, 38, 36, 36, 28, 28, 28, 28, 28, 28, 28, 28, - 28, 28, 28, 28, 28, 28, 28, 25, 28, 28, 25, 14, 14, 14, 14, 14, - 14, 28, 28, 14, 14, 14, 14, 14, 28, 24, 28, 28, 28, 14, 14, 14, - 14, 28, 14, 28, 14, 14, 28, 14, 28, 14, 14, 28, 25, 24, 14, 28, - 28, 14, 14, 14, 14, 14, 14, 14, 14, 28, 28, 14, 14, 14, 14, 24, - 97, 97, 24, 25, 24, 14, 14, 28, 14, 14, 97, 28, 99, 97, 97, 97, - 14, 14, 14, 14, 100, 97, 14, 14, 25, 25, 14, 14, 14, 14, 14, 14, - 28, 24, 28, 24, 101, 25, 28, 24, 14, 14, 14, 14, 14, 14, 14, 100, - 14, 14, 14, 14, 14, 14, 14, 28, 14, 14, 14, 14, 14, 14, 100, 97, - 97, 97, 97, 97, 101, 28, 102, 100, 97, 102, 101, 28, 97, 28, 101, 102, - 97, 24, 14, 14, 28, 101, 28, 28, 102, 97, 97, 102, 97, 101, 102, 97, - 103, 97, 99, 14, 97, 97, 97, 14, 14, 14, 14, 24, 14, 7, 85, 5, - 14, 54, 14, 14, 70, 70, 70, 70, 70, 70, 70, 28, 28, 28, 28, 28, - 28, 28, 14, 14, 14, 14, 14, 14, 14, 14, 16, 98, 14, 14, 14, 14, - 14, 14, 14, 70, 70, 70, 70, 70, 14, 16, 104, 104, 104, 104, 104, 104, - 104, 104, 104, 104, 98, 14, 14, 14, 14, 14, 14, 14, 70, 70, 14, 14, - 14, 14, 14, 14, 14, 14, 70, 14, 14, 14, 24, 28, 28, 36, 36, 36, - 14, 14, 14, 14, 14, 14, 14, 19, 0, 14, 36, 36, 105, 59, 77, 106, - 14, 14, 14, 14, 36, 36, 36, 39, 41, 36, 36, 36, 36, 36, 36, 43, - 14, 14, 14, 38, 14, 14, 14, 38, 85, 85, 85, 85, 85, 85, 85, 59, - 59, 59, 59, 27, 107, 14, 85, 14, 85, 70, 70, 70, 70, 59, 59, 57, - 59, 27, 77, 14, 14, 108, 36, 36, 97, 97, 97, 97, 97, 97, 97, 97, - 97, 97, 97, 97, 97, 103, 97, 97, 97, 97, 97, 36, 36, 36, 36, 36, - 97, 97, 97, 97, 97, 97, 36, 36, 18, 109, 110, 97, 70, 70, 70, 70, - 70, 97, 70, 70, 70, 70, 111, 112, 97, 97, 97, 97, 97, 0, 0, 0, - 97, 97, 113, 97, 97, 110, 114, 97, 115, 116, 116, 116, 116, 97, 97, 97, - 97, 116, 97, 97, 97, 97, 97, 97, 97, 116, 116, 116, 97, 97, 97, 117, - 97, 97, 116, 118, 43, 119, 91, 114, 120, 116, 116, 116, 116, 97, 97, 97, - 97, 97, 116, 117, 97, 110, 121, 114, 36, 36, 103, 97, 97, 97, 97, 97, - 97, 97, 97, 97, 97, 97, 97, 36, 103, 97, 97, 97, 97, 97, 97, 97, - 97, 97, 97, 97, 97, 97, 97, 122, 97, 97, 97, 97, 97, 122, 36, 36, - 123, 123, 123, 123, 123, 123, 123, 123, 97, 97, 97, 97, 28, 28, 28, 28, - 97, 97, 110, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 97, 122, 36, - 97, 97, 97, 122, 36, 36, 36, 36, 14, 14, 14, 14, 14, 14, 27, 106, - 12, 12, 12, 12, 12, 14, 36, 36, 0, 45, 0, 0, 0, 0, 0, 14, - 14, 14, 14, 14, 36, 36, 36, 43, 0, 27, 59, 59, 36, 36, 36, 36, - 14, 14, 36, 36, 36, 36, 36, 36, 14, 45, 14, 45, 14, 19, 14, 14, - 14, 19, 0, 0, 14, 14, 36, 36, 14, 14, 14, 14, 124, 36, 36, 36, - 14, 14, 65, 54, 36, 36, 36, 36, 0, 14, 14, 14, 14, 14, 14, 14, - 0, 0, 53, 36, 36, 36, 36, 59, 0, 14, 14, 14, 14, 14, 36, 36, - 14, 14, 14, 0, 0, 0, 0, 59, 14, 14, 14, 19, 0, 0, 0, 0, - 0, 0, 36, 36, 36, 36, 36, 39, 74, 74, 74, 74, 74, 74, 125, 36, - 14, 19, 0, 0, 0, 0, 0, 0, 45, 14, 14, 27, 59, 14, 14, 39, - 12, 12, 12, 12, 12, 36, 36, 14, 14, 14, 14, 14, 19, 0, 0, 0, - 14, 19, 14, 14, 14, 14, 0, 36, 12, 12, 12, 12, 12, 36, 27, 59, - 62, 63, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 36, 61, 62, 62, - 59, 14, 19, 53, 36, 36, 36, 36, 39, 14, 14, 38, 39, 14, 14, 38, - 39, 14, 14, 38, 36, 36, 36, 36, 14, 19, 0, 0, 0, 1, 0, 36, - 126, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 126, 127, - 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 126, 127, 127, 127, - 127, 127, 126, 127, 127, 127, 127, 127, 127, 127, 36, 36, 36, 36, 36, 36, - 75, 75, 75, 128, 36, 129, 76, 76, 76, 76, 76, 76, 76, 76, 36, 36, - 130, 130, 130, 130, 130, 130, 130, 130, 36, 39, 14, 14, 36, 36, 131, 132, - 47, 47, 47, 47, 49, 47, 47, 47, 47, 47, 47, 48, 47, 47, 48, 48, - 47, 131, 48, 47, 47, 47, 47, 47, 14, 36, 36, 36, 36, 36, 36, 36, - 36, 39, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 70, - 36, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 124, 36, - 133, 134, 58, 135, 136, 36, 36, 36, 97, 97, 137, 104, 104, 104, 104, 104, - 104, 104, 109, 137, 109, 97, 97, 97, 109, 78, 91, 54, 137, 104, 104, 109, - 97, 97, 97, 122, 138, 139, 36, 36, 14, 14, 14, 14, 14, 14, 38, 140, - 105, 97, 6, 97, 70, 97, 109, 109, 97, 97, 97, 97, 97, 91, 97, 141, - 97, 97, 97, 97, 97, 137, 142, 97, 97, 97, 97, 97, 97, 137, 142, 137, - 112, 70, 93, 143, 123, 123, 123, 123, 144, 14, 14, 14, 14, 14, 14, 14, - 14, 14, 14, 14, 14, 14, 14, 91, 36, 14, 14, 14, 36, 14, 14, 14, - 36, 14, 14, 14, 36, 14, 38, 36, 22, 97, 138, 145, 14, 14, 14, 38, - 36, 36, 36, 36, 43, 0, 146, 36, 14, 14, 14, 14, 14, 14, 39, 14, - 14, 14, 14, 14, 14, 38, 14, 39, 59, 41, 36, 39, 14, 14, 14, 14, - 14, 14, 36, 39, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 36, 36, - 14, 14, 14, 14, 14, 14, 19, 36, 14, 14, 14, 14, 14, 14, 14, 81, - 14, 14, 36, 36, 14, 14, 14, 14, 77, 14, 14, 36, 36, 36, 36, 36, - 14, 14, 14, 36, 38, 14, 14, 14, 14, 14, 14, 39, 38, 36, 38, 39, - 14, 14, 14, 81, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 36, 81, - 14, 14, 14, 14, 14, 36, 36, 39, 14, 14, 14, 14, 36, 36, 36, 14, - 19, 0, 43, 53, 36, 36, 0, 0, 14, 14, 39, 14, 39, 14, 14, 14, - 14, 14, 36, 36, 0, 53, 36, 43, 59, 59, 59, 59, 38, 36, 36, 36, - 14, 14, 14, 36, 81, 59, 59, 59, 14, 14, 14, 36, 14, 14, 14, 14, - 14, 38, 36, 36, 14, 14, 14, 14, 14, 14, 14, 14, 38, 36, 36, 36, - 14, 14, 14, 14, 0, 0, 0, 0, 0, 0, 0, 1, 77, 14, 14, 36, - 14, 14, 14, 12, 12, 12, 12, 12, 0, 0, 0, 0, 0, 45, 14, 59, - 59, 36, 36, 36, 36, 36, 36, 36, 0, 0, 53, 12, 12, 12, 12, 12, - 59, 59, 36, 36, 36, 36, 36, 36, 45, 14, 27, 77, 41, 36, 36, 36, - 0, 0, 0, 0, 36, 36, 36, 36, 14, 38, 36, 36, 36, 36, 36, 36, - 14, 14, 14, 14, 147, 70, 112, 14, 14, 98, 14, 70, 70, 14, 14, 14, - 14, 14, 14, 14, 16, 112, 14, 14, 19, 0, 0, 0, 0, 0, 0, 0, - 36, 36, 36, 36, 36, 36, 36, 43, 97, 36, 36, 36, 36, 36, 36, 36, - 14, 14, 19, 0, 0, 14, 19, 0, 0, 45, 19, 0, 0, 0, 14, 14, - 14, 14, 14, 14, 14, 0, 0, 14, 14, 0, 45, 36, 36, 36, 36, 36, - 36, 38, 39, 38, 39, 14, 38, 14, 14, 14, 14, 14, 14, 39, 39, 14, - 14, 14, 39, 14, 14, 14, 14, 14, 14, 14, 14, 39, 14, 38, 39, 14, - 14, 14, 38, 14, 14, 14, 38, 14, 14, 14, 14, 14, 14, 39, 14, 38, - 14, 14, 38, 38, 36, 14, 14, 14, 14, 14, 14, 14, 14, 14, 36, 12, - 12, 12, 12, 12, 12, 12, 12, 12, 39, 38, 38, 39, 39, 14, 14, 14, - 14, 38, 14, 14, 39, 39, 36, 36, 36, 38, 36, 39, 39, 39, 39, 14, - 39, 38, 38, 39, 39, 39, 39, 39, 39, 38, 38, 39, 14, 38, 14, 14, - 14, 38, 14, 14, 39, 14, 38, 38, 14, 14, 14, 14, 14, 39, 14, 14, - 39, 14, 39, 14, 14, 39, 14, 14, 103, 97, 97, 97, 97, 97, 97, 122, - 28, 28, 28, 28, 28, 148, 36, 36, 28, 28, 28, 28, 28, 28, 28, 38, - 28, 28, 28, 28, 28, 14, 36, 36, 36, 36, 36, 149, 149, 149, 149, 149, - 149, 149, 149, 149, 149, 149, 149, 149, 97, 122, 36, 36, 36, 36, 36, 36, - 97, 97, 97, 97, 122, 36, 36, 36, 122, 36, 36, 36, 36, 36, 36, 36, - 97, 97, 97, 103, 97, 97, 97, 97, 97, 97, 99, 100, 97, 97, 100, 97, - 97, 97, 122, 97, 97, 122, 36, 36, 122, 97, 97, 97, 97, 97, 97, 97, - 100, 100, 100, 97, 97, 97, 97, 99, 99, 100, 97, 97, 97, 97, 97, 97, - 97, 97, 97, 97, 103, 97, 122, 36, 14, 14, 14, 100, 97, 97, 97, 97, - 97, 97, 97, 99, 14, 14, 14, 14, 14, 14, 100, 97, 97, 97, 97, 97, - 97, 14, 14, 14, 14, 14, 14, 36, 97, 97, 97, 97, 36, 36, 36, 36, - 36, 36, 36, 36, 36, 103, 97, 97, 122, 36, 103, 97, 97, 97, 97, 97, - 43, 36, 36, 36, 36, 36, 36, 36, -}; - -static RE_UINT8 re_line_break_stage_5[] = { - 16, 16, 16, 18, 22, 20, 20, 21, 19, 6, 3, 12, 9, 10, 12, 3, - 1, 36, 12, 9, 8, 15, 8, 7, 11, 11, 8, 8, 12, 12, 12, 6, - 12, 1, 9, 36, 18, 2, 12, 16, 16, 29, 4, 1, 10, 9, 9, 9, - 12, 25, 25, 12, 25, 3, 12, 18, 25, 25, 17, 12, 25, 1, 17, 25, - 12, 17, 16, 4, 4, 4, 4, 16, 0, 0, 8, 0, 12, 0, 0, 12, - 0, 8, 18, 0, 0, 9, 0, 16, 18, 16, 16, 12, 6, 16, 37, 37, - 37, 0, 37, 12, 12, 10, 10, 10, 16, 6, 16, 0, 6, 6, 10, 11, - 11, 12, 6, 12, 8, 6, 18, 18, 0, 10, 0, 24, 24, 24, 24, 0, - 24, 12, 17, 17, 4, 17, 17, 18, 4, 6, 4, 12, 1, 2, 18, 17, - 12, 4, 4, 0, 31, 31, 32, 32, 33, 33, 18, 12, 2, 0, 5, 24, - 18, 9, 0, 18, 18, 4, 18, 28, 26, 25, 3, 3, 1, 3, 14, 14, - 14, 18, 20, 20, 3, 25, 5, 5, 8, 1, 2, 5, 30, 12, 2, 25, - 9, 12, 13, 13, 2, 12, 13, 12, 12, 13, 13, 25, 25, 13, 0, 13, - 2, 1, 0, 6, 6, 18, 1, 18, 26, 26, 2, 13, 13, 5, 5, 1, - 2, 2, 13, 16, 5, 13, 0, 38, 13, 38, 38, 13, 38, 0, 16, 5, - 5, 38, 38, 5, 13, 0, 38, 38, 10, 12, 31, 0, 34, 35, 35, 35, - 32, 0, 0, 33, 27, 27, 0, 37, 16, 37, 8, 2, 2, 8, 6, 1, - 2, 14, 13, 1, 13, 9, 10, 13, 0, 30, 13, 6, 13, 2, 12, 38, - 38, 12, 9, 0, 23, 25, 1, 1, 25, 0, 39, 39, -}; - -/* Line_Break: 7668 bytes. */ - -RE_UINT32 re_get_line_break(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_line_break_stage_1[f] << 5; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_line_break_stage_2[pos + f] << 3; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_line_break_stage_3[pos + f] << 3; - f = code >> 1; - code ^= f << 1; - pos = (RE_UINT32)re_line_break_stage_4[pos + f] << 1; - value = re_line_break_stage_5[pos + code]; - - return value; -} - -/* Numeric_Type. */ - -static RE_UINT8 re_numeric_type_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 11, 11, 11, 12, - 13, 14, 15, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 16, 11, 17, - 18, 11, 19, 20, 11, 11, 21, 11, 11, 11, 11, 11, 11, 11, 11, 22, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, -}; - -static RE_UINT8 re_numeric_type_stage_2[] = { - 0, 1, 1, 1, 1, 1, 2, 3, 1, 4, 5, 6, 7, 8, 9, 10, - 11, 1, 1, 12, 1, 1, 13, 14, 15, 16, 17, 18, 19, 1, 1, 1, - 20, 21, 1, 1, 22, 1, 1, 23, 1, 1, 1, 1, 24, 1, 1, 1, - 25, 26, 27, 1, 28, 1, 1, 1, 29, 1, 1, 30, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 31, 32, - 1, 33, 1, 34, 1, 1, 35, 1, 36, 1, 1, 1, 1, 1, 37, 38, - 1, 1, 39, 40, 1, 1, 1, 41, 1, 1, 1, 1, 1, 1, 1, 42, - 1, 1, 1, 43, 1, 1, 44, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 45, 1, 1, 1, 46, 1, 1, 1, 1, 1, 1, 1, 47, 48, 1, 1, - 1, 1, 1, 1, 1, 1, 49, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 50, 1, 51, 52, 53, 54, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 55, 1, 1, 1, 1, 1, 15, - 1, 56, 1, 57, 58, 1, 1, 1, 59, 60, 61, 62, 1, 1, 63, 1, - 64, 65, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 66, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 67, 1, 1, 1, 68, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 69, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 70, 71, 1, 1, 1, 1, 1, 1, 1, 72, 73, 74, 1, 1, 1, 1, - 1, 1, 1, 75, 1, 1, 1, 1, 1, 76, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 77, 1, 1, 1, 1, - 1, 1, 78, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 75, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_numeric_type_stage_3[] = { - 0, 1, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 3, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 3, 0, - 0, 0, 0, 4, 0, 0, 0, 5, 0, 0, 0, 4, 0, 0, 0, 4, - 0, 0, 0, 6, 0, 0, 0, 7, 0, 0, 0, 8, 0, 0, 0, 4, - 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, - 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 1, 0, 0, 0, - 0, 0, 0, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, - 0, 0, 0, 0, 0, 0, 0, 13, 1, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 0, 0, 0, 14, 0, 0, 0, 0, 0, 15, 0, 0, 0, - 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 15, 0, 0, 0, 0, 0, - 0, 0, 0, 16, 17, 0, 0, 0, 0, 0, 18, 19, 20, 0, 0, 0, - 0, 0, 0, 21, 22, 0, 0, 23, 0, 0, 0, 24, 25, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 26, 27, 28, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 29, 0, 0, 0, 0, 30, 31, 0, 30, 32, 0, 0, - 33, 0, 0, 0, 34, 0, 0, 0, 0, 35, 0, 0, 0, 0, 0, 0, - 0, 0, 36, 0, 0, 0, 0, 0, 37, 0, 26, 0, 38, 39, 40, 41, - 36, 0, 0, 42, 0, 0, 0, 0, 43, 0, 44, 45, 0, 0, 0, 0, - 0, 0, 46, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 0, 48, 0, - 0, 0, 0, 0, 0, 0, 0, 49, 0, 0, 0, 50, 0, 0, 0, 51, - 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 53, - 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 55, 0, - 44, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 56, 0, 0, 0, - 0, 0, 0, 53, 0, 0, 0, 0, 0, 0, 0, 0, 44, 0, 0, 0, - 0, 54, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, - 0, 42, 0, 0, 0, 0, 0, 0, 0, 58, 59, 60, 0, 0, 0, 56, - 0, 3, 0, 0, 0, 0, 0, 61, 0, 62, 0, 0, 0, 0, 1, 0, - 3, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 63, 0, 55, 64, 26, - 65, 66, 19, 67, 35, 0, 0, 0, 0, 68, 69, 0, 0, 0, 70, 0, - 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, 71, 0, 0, 0, 0, 0, - 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 73, 74, 0, 0, 0, 0, - 0, 0, 71, 71, 0, 0, 0, 0, 0, 0, 0, 75, 0, 0, 0, 0, - 0, 0, 76, 77, 0, 0, 0, 1, 0, 78, 0, 0, 0, 0, 1, 0, - 19, 19, 19, 79, 0, 0, 0, 0, 0, 0, 0, 80, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 81, 82, 83, 0, 0, 0, 0, 0, 0, 0, - 58, 0, 0, 43, 0, 0, 0, 84, 0, 58, 0, 0, 0, 0, 0, 0, - 0, 35, 0, 0, 85, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 86, - 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 42, 0, 0, 0, - 0, 0, 0, 0, 60, 0, 0, 0, 48, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 36, 0, 0, 0, 0, -}; - -static RE_UINT8 re_numeric_type_stage_4[] = { - 0, 0, 0, 0, 0, 0, 1, 2, 0, 0, 3, 4, 1, 2, 0, 0, - 5, 1, 0, 0, 5, 1, 6, 7, 5, 1, 8, 0, 5, 1, 9, 0, - 5, 1, 0, 10, 5, 1, 11, 0, 1, 12, 13, 0, 0, 14, 15, 16, - 0, 17, 18, 0, 1, 2, 19, 7, 0, 0, 1, 20, 1, 2, 1, 2, - 0, 0, 21, 22, 23, 22, 0, 0, 0, 0, 19, 19, 19, 19, 19, 19, - 24, 7, 0, 0, 23, 25, 26, 27, 19, 23, 25, 13, 0, 28, 29, 30, - 0, 0, 31, 32, 23, 33, 34, 0, 0, 0, 0, 35, 36, 0, 0, 0, - 37, 7, 0, 9, 0, 0, 38, 0, 19, 7, 0, 0, 0, 19, 37, 19, - 0, 0, 37, 19, 35, 0, 0, 0, 39, 0, 0, 0, 0, 40, 0, 0, - 0, 35, 0, 0, 41, 42, 0, 0, 0, 43, 44, 0, 0, 0, 0, 36, - 18, 0, 0, 36, 0, 18, 0, 0, 0, 0, 18, 0, 43, 0, 0, 0, - 45, 0, 0, 0, 0, 46, 0, 0, 47, 43, 0, 0, 48, 0, 0, 0, - 0, 0, 0, 39, 0, 0, 42, 42, 0, 0, 0, 40, 0, 0, 0, 17, - 0, 49, 18, 0, 0, 0, 0, 45, 0, 43, 0, 0, 0, 0, 40, 0, - 0, 0, 45, 0, 0, 45, 39, 0, 42, 0, 0, 0, 45, 43, 0, 0, - 0, 0, 0, 18, 17, 19, 0, 0, 0, 0, 11, 0, 0, 39, 39, 18, - 0, 0, 50, 0, 36, 19, 19, 19, 19, 19, 13, 0, 19, 19, 19, 18, - 13, 0, 0, 0, 42, 40, 0, 0, 0, 0, 51, 0, 0, 0, 0, 19, - 0, 0, 17, 13, 52, 0, 0, 0, 0, 0, 0, 53, 23, 25, 19, 10, - 0, 0, 54, 55, 56, 1, 0, 0, 0, 0, 5, 1, 9, 0, 0, 0, - 19, 19, 7, 0, 0, 5, 1, 1, 1, 1, 1, 1, 23, 57, 0, 0, - 40, 0, 0, 0, 39, 43, 0, 43, 0, 40, 0, 35, 0, 0, 0, 42, -}; - -static RE_UINT8 re_numeric_type_stage_5[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 0, 0, 0, 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, - 0, 2, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 3, 3, - 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, - 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, - 3, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, - 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, - 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, - 3, 3, 2, 0, 0, 0, 0, 0, 2, 0, 0, 0, 2, 2, 2, 2, - 2, 2, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, 2, - 1, 1, 1, 0, 0, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, - 0, 0, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 1, 2, 0, 0, 0, 0, 0, 0, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 1, 2, 1, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, - 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, - 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 1, - 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, - 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, - 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, - 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, - 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, - 2, 2, 2, 2, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, - 0, 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 3, 3, 2, 2, 2, 0, 0, 0, 0, 0, -}; - -/* Numeric_Type: 2088 bytes. */ - -RE_UINT32 re_get_numeric_type(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_numeric_type_stage_1[f] << 4; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_numeric_type_stage_2[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_numeric_type_stage_3[pos + f] << 2; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_numeric_type_stage_4[pos + f] << 3; - value = re_numeric_type_stage_5[pos + code]; - - return value; -} - -/* Numeric_Value. */ - -static RE_UINT8 re_numeric_value_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 11, 11, 11, 12, - 13, 14, 15, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 16, 11, 17, - 18, 11, 19, 20, 11, 11, 21, 11, 11, 11, 11, 11, 11, 11, 11, 22, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, - 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, -}; - -static RE_UINT8 re_numeric_value_stage_2[] = { - 0, 1, 1, 1, 1, 1, 2, 3, 1, 4, 5, 6, 7, 8, 9, 10, - 11, 1, 1, 12, 1, 1, 13, 14, 15, 16, 17, 18, 19, 1, 1, 1, - 20, 21, 1, 1, 22, 1, 1, 23, 1, 1, 1, 1, 24, 1, 1, 1, - 25, 26, 27, 1, 28, 1, 1, 1, 29, 1, 1, 30, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 31, 32, - 1, 33, 1, 34, 1, 1, 35, 1, 36, 1, 1, 1, 1, 1, 37, 38, - 1, 1, 39, 40, 1, 1, 1, 41, 1, 1, 1, 1, 1, 1, 1, 42, - 1, 1, 1, 43, 1, 1, 44, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 45, 1, 1, 1, 46, 1, 1, 1, 1, 1, 1, 1, 47, 48, 1, 1, - 1, 1, 1, 1, 1, 1, 49, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 50, 1, 51, 52, 53, 54, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 55, 1, 1, 1, 1, 1, 15, - 1, 56, 1, 57, 58, 1, 1, 1, 59, 60, 61, 62, 1, 1, 63, 1, - 64, 65, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 66, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 67, 1, 1, 1, 68, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 69, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 70, 71, 1, 1, 1, 1, 1, 1, 1, 72, 73, 74, 1, 1, 1, 1, - 1, 1, 1, 75, 1, 1, 1, 1, 1, 76, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 77, 1, 1, 1, 1, - 1, 1, 78, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 79, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_numeric_value_stage_3[] = { - 0, 1, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 3, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 3, 0, - 0, 0, 0, 4, 0, 0, 0, 5, 0, 0, 0, 4, 0, 0, 0, 4, - 0, 0, 0, 6, 0, 0, 0, 7, 0, 0, 0, 8, 0, 0, 0, 4, - 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, - 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 1, 0, 0, 0, - 0, 0, 0, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, - 0, 0, 0, 0, 0, 0, 0, 13, 1, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 0, 0, 0, 14, 0, 0, 0, 0, 0, 13, 0, 0, 0, - 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 13, 0, 0, 0, 0, 0, - 0, 0, 0, 15, 3, 0, 0, 0, 0, 0, 16, 17, 18, 0, 0, 0, - 0, 0, 0, 19, 20, 0, 0, 21, 0, 0, 0, 22, 23, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 24, 25, 26, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 27, 0, 0, 0, 0, 28, 29, 0, 28, 30, 0, 0, - 31, 0, 0, 0, 32, 0, 0, 0, 0, 33, 0, 0, 0, 0, 0, 0, - 0, 0, 34, 0, 0, 0, 0, 0, 35, 0, 36, 0, 37, 38, 39, 40, - 41, 0, 0, 42, 0, 0, 0, 0, 43, 0, 44, 45, 0, 0, 0, 0, - 0, 0, 46, 0, 0, 0, 47, 0, 0, 0, 0, 0, 0, 0, 48, 0, - 0, 0, 0, 0, 0, 0, 0, 49, 0, 0, 0, 50, 0, 0, 0, 51, - 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 53, - 0, 0, 54, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 55, 0, - 56, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 57, 0, 0, 0, - 0, 0, 0, 58, 0, 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, 0, - 0, 60, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 61, 0, 0, - 0, 62, 0, 0, 0, 0, 0, 0, 0, 63, 64, 65, 0, 0, 0, 66, - 0, 3, 0, 0, 0, 0, 0, 67, 0, 68, 0, 0, 0, 0, 1, 0, - 3, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 69, 0, 70, 71, 72, - 73, 74, 75, 76, 77, 0, 0, 0, 0, 78, 79, 0, 0, 0, 80, 0, - 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, 81, 0, 0, 0, 0, 0, - 82, 0, 0, 0, 0, 0, 0, 0, 0, 0, 83, 84, 0, 0, 0, 0, - 0, 0, 85, 85, 0, 0, 0, 0, 0, 0, 0, 86, 0, 0, 0, 0, - 0, 0, 87, 88, 0, 0, 0, 1, 0, 89, 0, 0, 0, 0, 1, 0, - 90, 91, 92, 93, 0, 0, 0, 0, 0, 0, 0, 94, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 95, 96, 97, 0, 0, 0, 0, 0, 0, 0, - 98, 0, 0, 99, 0, 0, 0, 100, 0, 101, 0, 0, 0, 0, 0, 0, - 0, 102, 0, 0, 103, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 104, - 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 62, 0, 0, 0, - 0, 0, 0, 0, 106, 0, 0, 0, 107, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 108, 0, 0, 0, 0, 0, 0, 0, 0, 109, 0, 0, 0, -}; - -static RE_UINT8 re_numeric_value_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 0, - 0, 0, 0, 0, 4, 0, 5, 6, 1, 2, 3, 0, 0, 0, 0, 0, - 0, 7, 8, 9, 0, 0, 0, 0, 0, 7, 8, 9, 0, 10, 11, 0, - 0, 7, 8, 9, 12, 13, 0, 0, 0, 7, 8, 9, 14, 0, 0, 0, - 0, 7, 8, 9, 0, 0, 1, 15, 0, 7, 8, 9, 16, 17, 0, 0, - 1, 2, 18, 19, 20, 0, 0, 0, 0, 0, 21, 2, 22, 23, 24, 25, - 0, 0, 0, 26, 27, 0, 0, 0, 1, 2, 3, 0, 1, 2, 3, 0, - 0, 0, 0, 0, 1, 2, 28, 0, 0, 0, 0, 0, 29, 2, 3, 0, - 0, 0, 0, 0, 30, 31, 32, 33, 34, 35, 36, 37, 34, 35, 36, 37, - 38, 39, 40, 0, 0, 0, 0, 0, 34, 35, 36, 41, 42, 34, 35, 36, - 41, 42, 34, 35, 36, 41, 42, 0, 0, 0, 43, 44, 45, 46, 2, 47, - 0, 0, 0, 0, 0, 48, 49, 50, 34, 35, 51, 49, 50, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 52, 0, 53, 0, 0, 0, 0, 0, 0, - 21, 2, 3, 0, 0, 0, 54, 0, 0, 0, 0, 0, 48, 55, 0, 0, - 34, 35, 56, 0, 0, 0, 0, 0, 0, 0, 57, 58, 59, 60, 61, 62, - 0, 0, 0, 0, 63, 64, 65, 66, 0, 67, 0, 0, 0, 0, 0, 0, - 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, 69, 0, 0, 0, 0, 0, - 0, 0, 0, 70, 0, 0, 0, 0, 71, 72, 73, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 74, 0, 0, 0, 75, 0, 76, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 77, 78, 0, 0, 0, 0, 0, 0, 79, - 0, 0, 80, 0, 0, 0, 0, 0, 0, 0, 0, 67, 0, 0, 0, 0, - 0, 0, 0, 0, 81, 0, 0, 0, 0, 82, 0, 0, 0, 0, 0, 0, - 0, 83, 0, 0, 0, 0, 0, 0, 0, 0, 84, 85, 0, 0, 0, 0, - 86, 87, 0, 88, 0, 0, 0, 0, 89, 80, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 90, 0, 0, 0, 0, 0, 5, 0, 5, 0, - 0, 0, 0, 0, 0, 0, 91, 0, 0, 0, 0, 0, 0, 0, 0, 92, - 0, 0, 0, 15, 75, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 93, - 0, 0, 0, 94, 0, 0, 0, 0, 0, 0, 0, 0, 95, 0, 0, 0, - 0, 95, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 96, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 97, 0, 98, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 25, 0, 0, 0, 0, 0, 0, 0, 99, 68, 0, 0, 0, - 0, 0, 0, 0, 75, 0, 0, 0, 100, 0, 0, 0, 0, 0, 0, 0, - 0, 101, 0, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 102, 0, - 0, 0, 0, 0, 0, 103, 0, 0, 0, 48, 49, 104, 0, 0, 0, 0, - 0, 0, 0, 0, 105, 106, 0, 0, 0, 0, 107, 0, 108, 0, 75, 0, - 0, 0, 0, 0, 103, 0, 0, 0, 0, 0, 0, 0, 109, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 110, 0, 111, 8, 9, 57, 58, 112, 113, - 114, 115, 116, 117, 118, 0, 0, 0, 119, 120, 121, 122, 123, 124, 125, 126, - 127, 128, 129, 130, 122, 131, 132, 0, 0, 0, 103, 0, 0, 0, 0, 0, - 133, 0, 0, 0, 0, 0, 0, 0, 134, 0, 135, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 136, 137, 0, 0, 0, 0, 0, 0, 0, 0, 138, 139, - 0, 0, 0, 0, 0, 140, 141, 0, 34, 142, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 143, 0, 0, 0, 0, 0, 0, 34, 142, - 34, 35, 144, 145, 146, 147, 148, 149, 0, 0, 0, 0, 48, 49, 50, 150, - 151, 152, 8, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 8, 9, - 8, 9, 49, 153, 35, 154, 2, 155, 156, 157, 9, 158, 159, 158, 160, 161, - 162, 163, 164, 165, 166, 167, 168, 169, 170, 0, 0, 0, 0, 0, 0, 0, - 34, 35, 144, 145, 171, 0, 0, 0, 0, 0, 0, 7, 8, 9, 1, 2, - 172, 8, 9, 1, 2, 172, 8, 9, 173, 49, 174, 0, 0, 0, 0, 0, - 70, 0, 0, 0, 0, 0, 0, 0, 0, 175, 0, 0, 0, 0, 0, 0, - 98, 0, 0, 0, 0, 0, 0, 0, 67, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 91, 0, 0, 0, 0, 0, 176, 0, 0, 88, 0, 0, 0, 88, - 0, 0, 101, 0, 0, 0, 0, 73, 0, 0, 0, 0, 0, 0, 73, 0, - 0, 0, 0, 0, 0, 0, 80, 0, 0, 0, 0, 0, 0, 0, 107, 0, - 0, 0, 0, 177, 0, 0, 0, 0, 0, 0, 0, 0, 178, 0, 0, 0, -}; - -static RE_UINT8 re_numeric_value_stage_5[] = { - 0, 0, 0, 0, 2, 23, 25, 27, 29, 31, 33, 35, 37, 39, 0, 0, - 0, 0, 25, 27, 0, 23, 0, 0, 11, 15, 19, 0, 0, 0, 2, 23, - 25, 27, 29, 31, 33, 35, 37, 39, 3, 6, 9, 11, 19, 46, 0, 0, - 0, 0, 11, 15, 19, 3, 6, 9, 40, 85, 94, 0, 23, 25, 27, 0, - 40, 85, 94, 11, 15, 19, 0, 0, 37, 39, 15, 24, 26, 28, 30, 32, - 34, 36, 38, 1, 0, 23, 25, 27, 37, 39, 40, 50, 60, 70, 80, 81, - 82, 83, 84, 85, 103, 0, 0, 0, 0, 0, 47, 48, 49, 0, 0, 0, - 37, 39, 23, 0, 2, 0, 0, 0, 7, 5, 4, 12, 18, 10, 14, 16, - 20, 8, 21, 6, 13, 17, 22, 23, 23, 25, 27, 29, 31, 33, 35, 37, - 39, 40, 41, 42, 80, 85, 89, 94, 94, 98, 103, 0, 0, 33, 80, 107, - 112, 2, 0, 0, 43, 44, 45, 46, 47, 48, 49, 50, 0, 0, 2, 41, - 42, 43, 44, 45, 46, 47, 48, 49, 50, 23, 25, 27, 37, 39, 40, 2, - 0, 0, 23, 25, 27, 29, 31, 33, 35, 37, 39, 40, 39, 40, 23, 25, - 0, 15, 0, 0, 0, 0, 0, 2, 40, 50, 60, 0, 27, 29, 0, 0, - 39, 40, 0, 0, 40, 50, 60, 70, 80, 81, 82, 83, 0, 51, 52, 53, - 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 0, 66, 67, 68, - 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 0, 31, 0, 0, - 0, 0, 0, 25, 0, 0, 31, 0, 0, 35, 0, 0, 23, 0, 0, 35, - 0, 0, 0, 103, 0, 27, 0, 0, 0, 39, 0, 0, 25, 0, 0, 0, - 31, 0, 29, 0, 0, 0, 0, 115, 40, 0, 0, 0, 0, 0, 0, 94, - 27, 0, 0, 0, 85, 0, 0, 0, 115, 0, 0, 0, 0, 0, 116, 0, - 0, 25, 0, 37, 0, 33, 0, 0, 0, 40, 0, 94, 50, 60, 0, 0, - 70, 0, 0, 0, 0, 27, 27, 27, 0, 0, 0, 29, 0, 0, 23, 0, - 0, 0, 39, 50, 0, 0, 40, 0, 37, 0, 0, 0, 0, 0, 35, 0, - 0, 0, 39, 0, 0, 0, 85, 0, 0, 0, 29, 0, 0, 0, 25, 0, - 0, 94, 0, 0, 0, 0, 33, 0, 33, 0, 0, 0, 0, 0, 2, 0, - 35, 37, 39, 2, 11, 15, 19, 3, 6, 9, 0, 0, 0, 0, 0, 27, - 0, 0, 0, 40, 0, 33, 0, 33, 0, 40, 0, 0, 0, 0, 0, 23, - 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, - 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 11, 15, 23, 31, - 80, 89, 98, 107, 31, 40, 80, 85, 89, 94, 98, 31, 40, 80, 85, 89, - 94, 103, 107, 40, 23, 23, 23, 25, 25, 25, 25, 31, 40, 40, 40, 40, - 40, 60, 80, 80, 80, 80, 85, 87, 89, 89, 89, 89, 80, 15, 15, 18, - 19, 0, 0, 0, 23, 31, 40, 80, 0, 84, 0, 0, 0, 0, 93, 0, - 0, 23, 25, 40, 50, 85, 0, 0, 23, 25, 27, 40, 50, 85, 94, 103, - 0, 0, 23, 40, 50, 85, 25, 27, 40, 50, 85, 94, 0, 23, 80, 0, - 39, 40, 50, 60, 70, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, - 91, 92, 93, 15, 11, 12, 18, 0, 50, 60, 70, 80, 81, 82, 83, 84, - 85, 94, 2, 23, 35, 37, 39, 29, 39, 23, 25, 27, 37, 39, 23, 25, - 27, 29, 31, 25, 27, 27, 29, 31, 23, 25, 27, 27, 29, 31, 113, 114, - 29, 31, 27, 27, 29, 29, 29, 29, 33, 35, 35, 35, 37, 37, 39, 39, - 39, 39, 25, 27, 29, 31, 33, 23, 25, 27, 29, 29, 31, 31, 25, 27, - 23, 25, 12, 18, 21, 12, 18, 6, 11, 8, 11, 0, 83, 84, 0, 0, - 37, 39, 2, 23, 2, 2, 23, 25, 35, 37, 39, 0, 29, 0, 0, 0, - 0, 0, 0, 60, 0, 29, 0, 0, 39, 0, 0, 0, -}; - -/* Numeric_Value: 2876 bytes. */ - -RE_UINT32 re_get_numeric_value(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 12; - code = ch ^ (f << 12); - pos = (RE_UINT32)re_numeric_value_stage_1[f] << 4; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_numeric_value_stage_2[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_numeric_value_stage_3[pos + f] << 3; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_numeric_value_stage_4[pos + f] << 2; - value = re_numeric_value_stage_5[pos + code]; - - return value; -} - -/* Bidi_Mirrored. */ - -static RE_UINT8 re_bidi_mirrored_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_bidi_mirrored_stage_2[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_bidi_mirrored_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 3, 1, 1, 1, 1, - 4, 5, 1, 6, 7, 8, 1, 9, 10, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 11, - 1, 1, 1, 12, 1, 1, 1, 1, -}; - -static RE_UINT8 re_bidi_mirrored_stage_4[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 3, 3, 4, 3, 3, 3, 3, 3, 5, 3, 3, 3, 3, 3, - 6, 7, 8, 3, 3, 9, 3, 3, 10, 11, 12, 13, 14, 3, 3, 3, - 3, 3, 3, 3, 3, 15, 3, 16, 3, 3, 3, 3, 3, 3, 17, 18, - 19, 20, 21, 22, 3, 3, 3, 3, 23, 3, 3, 3, 3, 3, 3, 3, - 24, 3, 3, 3, 3, 3, 3, 3, 3, 25, 3, 3, 26, 27, 3, 3, - 3, 3, 3, 28, 29, 30, 31, 32, -}; - -static RE_UINT8 re_bidi_mirrored_stage_5[] = { - 0, 0, 0, 0, 0, 3, 0, 80, 0, 0, 0, 40, 0, 0, 0, 40, - 0, 0, 0, 0, 0, 8, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 60, 0, 0, 0, 24, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 6, 96, 0, 0, 0, 0, 0, 0, 96, - 0, 96, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 30, 63, 98, 188, 87, 248, 15, 250, 255, 31, 60, 128, 245, 207, 255, 255, - 255, 159, 7, 1, 204, 255, 255, 193, 0, 62, 195, 255, 255, 63, 255, 255, - 0, 15, 0, 0, 3, 6, 0, 0, 0, 0, 0, 0, 0, 255, 63, 0, - 121, 59, 120, 112, 252, 255, 0, 0, 248, 255, 255, 249, 255, 255, 0, 1, - 63, 194, 55, 31, 58, 3, 240, 51, 0, 252, 255, 223, 83, 122, 48, 112, - 0, 0, 128, 1, 48, 188, 25, 254, 255, 255, 255, 255, 207, 191, 255, 255, - 255, 255, 127, 80, 124, 112, 136, 47, 60, 54, 0, 48, 255, 3, 0, 0, - 0, 255, 243, 15, 0, 0, 0, 0, 0, 0, 0, 126, 48, 0, 0, 0, - 0, 3, 0, 80, 0, 0, 0, 40, 0, 0, 0, 168, 13, 0, 0, 0, - 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, - 0, 128, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, - 8, 0, 0, 0, 0, 0, 0, 0, -}; - -/* Bidi_Mirrored: 489 bytes. */ - -RE_UINT32 re_get_bidi_mirrored(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_bidi_mirrored_stage_1[f] << 4; - f = code >> 12; - code ^= f << 12; - pos = (RE_UINT32)re_bidi_mirrored_stage_2[pos + f] << 3; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_bidi_mirrored_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_bidi_mirrored_stage_4[pos + f] << 6; - pos += code; - value = (re_bidi_mirrored_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Indic_Matra_Category. */ - -static RE_UINT8 re_indic_matra_category_stage_1[] = { - 0, 1, 1, 1, 1, 2, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_indic_matra_category_stage_2[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, - 8, 0, 0, 0, 0, 0, 0, 9, 0, 10, 11, 12, 13, 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, 14, 15, 16, 17, 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, 18, 0, 0, 0, 0, 0, - 19, 20, 0, 0, 0, 0, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_indic_matra_category_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 1, 2, 3, 4, 0, 0, 0, 0, 5, 6, 7, 4, 0, - 0, 0, 0, 5, 8, 0, 0, 0, 0, 0, 0, 5, 9, 0, 4, 0, - 0, 0, 0, 10, 11, 12, 4, 0, 0, 0, 0, 13, 14, 7, 0, 0, - 0, 0, 0, 15, 16, 17, 4, 0, 0, 0, 0, 10, 18, 19, 4, 0, - 0, 0, 0, 13, 20, 7, 4, 0, 0, 0, 0, 0, 21, 22, 0, 23, - 0, 0, 0, 24, 25, 0, 0, 0, 0, 0, 0, 26, 27, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 28, 29, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 30, 31, 0, 32, 33, 34, 35, 36, 0, 0, 0, 0, 0, 0, - 0, 37, 0, 37, 0, 38, 0, 38, 0, 0, 0, 39, 40, 41, 0, 0, - 0, 0, 42, 0, 0, 0, 0, 0, 0, 0, 0, 43, 44, 0, 0, 0, - 0, 45, 0, 0, 0, 0, 46, 47, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 48, 49, 0, 0, 0, 0, 0, 50, 0, 0, 0, 0, 23, - 0, 0, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 52, 0, 53, 0, 0, 0, 0, 0, 0, 0, 0, 54, 55, 0, 0, 0, - 0, 0, 0, 0, 56, 57, 0, 0, 0, 0, 0, 58, 59, 0, 0, 0, - 0, 0, 60, 61, 0, 0, 0, 0, 0, 0, 0, 62, 0, 0, 63, 64, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 65, 0, - 66, 0, 0, 67, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 68, 69, 0, 0, 0, 0, 0, 0, 70, 0, 0, 0, 0, - 0, 0, 71, 72, 0, 0, 0, 0, 0, 0, 0, 73, 44, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 74, 69, 0, 0, 0, 0, -}; - -static RE_UINT8 re_indic_matra_category_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 2, - 3, 4, 5, 6, 1, 7, 3, 8, 0, 0, 9, 4, 0, 0, 0, 0, - 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, - 3, 4, 10, 11, 12, 13, 14, 0, 0, 0, 0, 15, 0, 0, 0, 0, - 3, 10, 0, 9, 16, 9, 17, 0, 3, 4, 5, 9, 18, 15, 3, 0, - 0, 0, 0, 0, 0, 0, 0, 19, 3, 4, 10, 11, 20, 13, 21, 0, - 0, 0, 0, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, - 17, 10, 0, 22, 12, 23, 24, 0, 0, 0, 0, 0, 0, 0, 0, 6, - 1, 7, 25, 6, 26, 6, 6, 0, 0, 0, 9, 10, 0, 0, 0, 0, - 27, 7, 25, 18, 28, 29, 6, 0, 0, 0, 15, 25, 0, 0, 0, 0, - 7, 3, 10, 22, 12, 23, 24, 0, 0, 0, 0, 0, 0, 16, 0, 15, - 7, 6, 10, 10, 2, 30, 23, 31, 0, 7, 0, 0, 0, 0, 0, 0, - 19, 7, 6, 6, 4, 10, 0, 0, 32, 32, 33, 9, 0, 0, 0, 16, - 19, 7, 6, 6, 4, 9, 0, 0, 32, 32, 34, 0, 0, 0, 0, 0, - 35, 36, 4, 37, 37, 6, 6, 0, 36, 0, 10, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 15, 19, 17, 38, 6, 6, 0, 39, 16, 0, 0, - 0, 0, 0, 7, 4, 0, 0, 0, 0, 25, 0, 15, 25, 0, 0, 0, - 9, 6, 16, 0, 0, 0, 0, 0, 0, 15, 40, 16, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 19, 0, 0, 17, 10, 0, 0, 0, 0, 0, - 0, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 6, 17, 4, 41, - 42, 22, 23, 0, 25, 0, 0, 0, 9, 43, 0, 0, 0, 0, 0, 0, - 6, 44, 45, 46, 16, 0, 0, 0, 7, 7, 2, 22, 7, 8, 7, 7, - 25, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 38, 2, 0, 0, - 47, 1, 19, 6, 17, 5, 44, 22, 22, 40, 16, 0, 0, 0, 0, 0, - 0, 0, 15, 6, 4, 48, 49, 22, 23, 18, 25, 0, 0, 0, 0, 0, - 0, 0, 17, 8, 6, 25, 0, 0, 0, 0, 0, 2, 50, 7, 10, 0, - 0, 0, 0, 16, 0, 0, 0, 0, 0, 15, 3, 1, 0, 0, 0, 0, - 0, 0, 15, 7, 7, 7, 7, 7, 7, 7, 10, 0, 0, 0, 0, 0, - 0, 0, 0, 35, 4, 17, 4, 10, 0, 15, 0, 0, 0, 0, 0, 0, - 0, 0, 7, 6, 4, 22, 16, 0, 51, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 9, 6, 17, 52, 40, 10, 0, 0, 0, 0, 0, 0, - 1, 6, 53, 54, 55, 56, 33, 16, 0, 0, 0, 0, 0, 11, 5, 8, - 0, 0, 0, 43, 0, 0, 0, 0, 0, 15, 19, 7, 44, 25, 35, 0, - 57, 4, 9, 58, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 39, - 0, 0, 0, 0, 6, 6, 4, 4, 4, 6, 6, 16, 0, 0, 0, 0, - 2, 3, 5, 1, 3, 0, 0, 0, 0, 0, 0, 9, 6, 4, 40, 37, - 17, 59, 16, 0, 0, 0, 0, 0, 0, 15, 8, 4, 4, 4, 6, 18, - 0, 0, 0, 0, 0, 0, 9, 8, -}; - -static RE_UINT8 re_indic_matra_category_stage_5[] = { - 0, 0, 5, 1, 1, 2, 1, 6, 6, 6, 6, 5, 5, 5, 1, 1, - 2, 1, 0, 5, 6, 0, 0, 2, 2, 0, 0, 4, 4, 6, 0, 1, - 5, 0, 5, 6, 5, 8, 1, 5, 9, 0, 10, 6, 2, 2, 4, 4, - 4, 5, 1, 0, 7, 0, 8, 1, 8, 0, 8, 8, 9, 2, 4, 1, - 3, 3, 3, 1, 3, 0, 0, 6, 5, 7, 7, 7, 6, 2, 0, 14, - 2, 5, 9, 10, 4, 2, 14, 0, 6, 1, 1, 8, 8, 5, 14, 1, - 6, 11, 7, 12, 2, 9, 11, 0, 5, 2, 6, 3, 3, 5, 5, 3, - 1, 3, 0, 13, 13, 0, 6, 14, -}; - -/* Indic_Matra_Category: 1336 bytes. */ - -RE_UINT32 re_get_indic_matra_category(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_indic_matra_category_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_indic_matra_category_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_indic_matra_category_stage_3[pos + f] << 3; - f = code >> 1; - code ^= f << 1; - pos = (RE_UINT32)re_indic_matra_category_stage_4[pos + f] << 1; - value = re_indic_matra_category_stage_5[pos + code]; - - return value; -} - -/* Indic_Syllabic_Category. */ - -static RE_UINT8 re_indic_syllabic_category_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 2, 4, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_indic_syllabic_category_stage_2[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 4, 5, 6, 7, 8, - 9, 1, 1, 1, 1, 1, 1, 10, 1, 11, 12, 13, 14, 1, 1, 1, - 1, 1, 1, 1, 1, 15, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 16, 17, 18, 19, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, - 21, 22, 1, 1, 1, 1, 23, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_indic_syllabic_category_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 8, 16, - 17, 11, 12, 18, 19, 20, 0, 21, 22, 23, 12, 24, 25, 0, 8, 0, - 10, 11, 12, 24, 26, 27, 8, 28, 29, 30, 31, 32, 33, 34, 0, 0, - 35, 36, 12, 37, 38, 39, 8, 0, 40, 36, 12, 41, 38, 42, 8, 0, - 40, 36, 4, 43, 44, 34, 8, 45, 46, 47, 4, 48, 49, 50, 0, 51, - 52, 4, 53, 54, 55, 0, 0, 0, 56, 57, 58, 59, 60, 61, 0, 0, - 0, 0, 0, 0, 62, 4, 63, 64, 65, 66, 67, 68, 0, 0, 0, 0, - 4, 4, 69, 70, 0, 71, 72, 73, 74, 75, 0, 0, 0, 0, 0, 0, - 76, 77, 78, 77, 78, 79, 76, 80, 4, 4, 81, 82, 83, 84, 0, 0, - 85, 63, 86, 87, 0, 4, 88, 89, 4, 4, 90, 91, 92, 0, 0, 0, - 4, 93, 4, 4, 94, 95, 96, 97, 0, 0, 0, 0, 0, 0, 0, 0, - 98, 78, 4, 99, 100, 0, 0, 0, 101, 4, 102, 103, 4, 4, 104, 105, - 4, 4, 106, 107, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 109, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 110, 0, 0, 0, - 111, 4, 112, 0, 4, 113, 114, 115, 116, 117, 4, 118, 119, 0, 0, 0, - 120, 4, 121, 4, 122, 123, 0, 0, 124, 4, 4, 125, 126, 0, 0, 0, - 127, 4, 128, 129, 130, 0, 4, 131, 4, 4, 4, 132, 133, 0, 134, 135, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 136, 137, 138, 0, - 139, 140, 4, 141, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 142, 78, 4, 143, 144, 0, 0, 0, 145, 4, 4, 146, 0, 0, 0, 0, - 147, 4, 148, 149, 0, 0, 0, 0, 150, 151, 4, 152, 153, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 154, 4, 155, 156, 0, 0, 0, 0, -}; - -static RE_UINT8 re_indic_syllabic_category_stage_4[] = { - 0, 0, 0, 0, 1, 0, 0, 0, 2, 3, 3, 3, 3, 4, 5, 5, - 5, 5, 5, 5, 5, 5, 6, 7, 8, 8, 8, 9, 0, 10, 5, 5, - 11, 0, 0, 0, 12, 3, 13, 5, 14, 15, 3, 16, 16, 4, 5, 5, - 5, 5, 17, 5, 18, 19, 20, 7, 8, 21, 21, 22, 0, 23, 0, 24, - 20, 0, 0, 0, 14, 15, 25, 26, 17, 27, 20, 28, 29, 23, 21, 30, - 0, 0, 13, 18, 31, 32, 0, 0, 14, 15, 3, 33, 33, 4, 5, 5, - 17, 13, 20, 7, 8, 34, 34, 30, 8, 21, 21, 30, 0, 35, 0, 24, - 36, 0, 0, 0, 37, 15, 25, 12, 38, 39, 27, 17, 40, 41, 42, 19, - 5, 5, 20, 35, 29, 35, 43, 30, 0, 23, 0, 0, 14, 15, 3, 38, - 38, 4, 5, 5, 5, 13, 20, 44, 8, 43, 43, 30, 0, 45, 20, 0, - 46, 15, 3, 38, 5, 13, 20, 7, 0, 45, 0, 47, 5, 5, 42, 44, - 8, 43, 43, 48, 0, 0, 49, 50, 46, 15, 3, 3, 3, 25, 19, 5, - 24, 5, 5, 36, 5, 42, 51, 23, 8, 52, 8, 8, 35, 0, 0, 0, - 13, 5, 5, 5, 5, 5, 5, 42, 8, 8, 53, 0, 8, 34, 54, 55, - 27, 56, 18, 36, 0, 5, 13, 5, 13, 57, 19, 27, 8, 8, 34, 58, - 8, 59, 54, 60, 0, 0, 0, 20, 5, 5, 13, 5, 5, 5, 5, 41, - 10, 8, 8, 61, 62, 63, 64, 65, 66, 66, 67, 66, 66, 66, 66, 66, - 66, 66, 66, 68, 69, 3, 70, 8, 8, 71, 72, 73, 74, 11, 75, 76, - 77, 78, 79, 80, 81, 82, 5, 5, 83, 84, 54, 85, 0, 0, 86, 87, - 88, 5, 5, 17, 6, 89, 0, 0, 88, 5, 5, 5, 6, 0, 0, 0, - 90, 0, 0, 0, 91, 3, 3, 3, 3, 35, 8, 8, 8, 61, 92, 93, - 94, 0, 0, 95, 96, 5, 5, 5, 8, 8, 97, 0, 98, 99, 100, 0, - 101, 102, 102, 103, 104, 105, 0, 0, 5, 5, 5, 0, 8, 8, 8, 8, - 106, 99, 107, 0, 5, 108, 8, 0, 5, 5, 5, 69, 88, 109, 99, 110, - 111, 8, 8, 8, 8, 79, 107, 0, 112, 113, 3, 3, 5, 114, 8, 8, - 8, 115, 5, 0, 116, 3, 117, 5, 118, 8, 119, 120, 0, 0, 121, 122, - 5, 123, 8, 8, 124, 0, 0, 0, 5, 125, 8, 106, 99, 126, 0, 0, - 0, 0, 0, 13, 127, 0, 0, 0, 0, 0, 0, 1, 33, 128, 129, 5, - 108, 8, 0, 0, 5, 5, 5, 130, 131, 132, 133, 5, 134, 0, 0, 0, - 135, 3, 3, 3, 117, 5, 5, 5, 5, 136, 8, 8, 8, 89, 0, 0, - 0, 0, 19, 5, 130, 102, 137, 107, 5, 108, 8, 138, 139, 0, 0, 0, - 140, 3, 4, 88, 141, 8, 8, 142, 89, 0, 0, 0, 3, 117, 5, 5, - 5, 5, 81, 8, 143, 144, 0, 0, 99, 99, 99, 145, 13, 0, 146, 0, - 8, 8, 8, 84, 147, 0, 0, 0, 117, 5, 108, 8, 0, 148, 0, 0, - 5, 5, 5, 74, 149, 5, 150, 99, 151, 8, 29, 152, 81, 45, 0, 153, - 5, 13, 13, 5, 5, 0, 0, 154, 155, 15, 3, 3, 5, 5, 8, 8, - 8, 53, 0, 0, 156, 3, 3, 4, 8, 8, 157, 0, 156, 88, 5, 5, - 5, 108, 8, 8, 158, 89, 0, 0, 156, 3, 3, 3, 4, 5, 5, 5, - 108, 8, 8, 8, 63, 0, 0, 0, 3, 3, 117, 5, 5, 5, 129, 159, - 8, 160, 0, 0, -}; - -static RE_UINT8 re_indic_syllabic_category_stage_5[] = { - 0, 0, 0, 0, 9, 0, 0, 0, 1, 1, 1, 2, 6, 6, 6, 6, - 6, 10, 10, 10, 10, 10, 10, 10, 10, 10, 7, 7, 4, 3, 7, 7, - 7, 7, 7, 7, 7, 5, 7, 7, 0, 7, 7, 7, 6, 6, 7, 7, - 0, 0, 6, 6, 0, 10, 10, 10, 0, 1, 1, 2, 0, 6, 6, 6, - 6, 0, 0, 6, 10, 0, 10, 10, 10, 0, 10, 0, 0, 0, 10, 10, - 10, 10, 0, 0, 7, 0, 0, 7, 7, 5, 11, 0, 0, 0, 0, 7, - 10, 10, 0, 10, 6, 6, 6, 0, 0, 0, 0, 6, 0, 10, 10, 0, - 4, 0, 7, 7, 7, 7, 7, 0, 7, 5, 0, 0, 1, 0, 9, 9, - 0, 14, 0, 0, 6, 6, 0, 6, 7, 7, 0, 7, 0, 0, 7, 7, - 0, 10, 0, 0, 0, 0, 1, 17, 6, 0, 6, 6, 6, 10, 0, 0, - 0, 0, 0, 10, 10, 0, 0, 0, 10, 10, 10, 0, 7, 0, 7, 7, - 0, 3, 7, 7, 0, 7, 7, 0, 0, 0, 1, 2, 0, 0, 10, 0, - 7, 5, 12, 0, 0, 0, 11, 11, 11, 11, 11, 11, 0, 0, 5, 0, - 7, 0, 7, 0, 7, 7, 5, 0, 19, 19, 19, 19, 0, 1, 5, 0, - 10, 0, 0, 10, 0, 10, 0, 10, 14, 14, 0, 0, 7, 0, 0, 0, - 0, 1, 0, 0, 7, 7, 1, 2, 7, 7, 1, 1, 5, 3, 0, 0, - 16, 16, 16, 16, 16, 13, 13, 13, 13, 13, 13, 13, 0, 13, 13, 13, - 13, 0, 0, 0, 10, 6, 6, 6, 6, 6, 6, 7, 7, 7, 1, 19, - 2, 5, 5, 14, 14, 14, 14, 10, 10, 10, 6, 6, 7, 7, 10, 10, - 10, 10, 14, 14, 14, 10, 7, 19, 19, 10, 10, 7, 7, 19, 19, 19, - 19, 19, 10, 10, 10, 7, 7, 7, 7, 10, 10, 10, 10, 10, 14, 7, - 7, 7, 7, 19, 19, 19, 10, 19, 0, 0, 19, 19, 7, 7, 0, 0, - 6, 6, 6, 10, 5, 0, 0, 0, 10, 0, 7, 7, 10, 10, 10, 6, - 7, 20, 20, 0, 12, 0, 0, 0, 0, 5, 5, 0, 3, 0, 0, 0, - 9, 10, 10, 10, 7, 13, 13, 13, 15, 15, 1, 15, 15, 15, 15, 15, - 15, 0, 0, 0, 10, 10, 10, 8, 8, 8, 8, 8, 8, 8, 0, 0, - 18, 18, 18, 18, 18, 0, 0, 0, 7, 15, 15, 15, 19, 19, 0, 0, - 10, 10, 10, 7, 10, 14, 14, 15, 15, 15, 15, 0, 5, 7, 7, 7, - 1, 1, 1, 12, 2, 6, 6, 6, 4, 7, 7, 7, 5, 10, 10, 10, - 1, 12, 2, 6, 6, 6, 10, 10, 10, 13, 13, 13, 7, 7, 5, 5, - 13, 13, 10, 10, 0, 0, 3, 10, 10, 10, 15, 15, 6, 6, 4, 7, - 15, 15, 5, 5, 13, 13, 7, 7, 1, 1, 0, 4, 0, 0, 2, 2, - 6, 6, 5, 10, 10, 10, 10, 1, 10, 10, 8, 8, 8, 8, 10, 10, - 10, 10, 8, 13, 13, 10, 10, 10, 10, 13, 10, 1, 1, 2, 6, 6, - 15, 7, 7, 7, 8, 8, 8, 19, 7, 7, 7, 15, 15, 15, 15, 5, - 1, 1, 12, 2, 10, 10, 10, 4, 7, 13, 14, 14, 7, 7, 7, 14, - 14, 14, 14, 0, 15, 15, 0, 0, 0, 0, 10, 19, 18, 19, 18, 0, - 0, 2, 5, 0, 10, 6, 10, 10, 10, 10, 10, 15, 15, 15, 15, 7, - 19, 5, 0, 0, 7, 0, 1, 2, 0, 0, 0, 5, 1, 1, 2, 0, - 1, 1, 2, 6, 7, 5, 4, 0, 7, 7, 7, 5, 2, 7, 7, 7, - 7, 7, 5, 4, -}; - -/* Indic_Syllabic_Category: 1952 bytes. */ - -RE_UINT32 re_get_indic_syllabic_category(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_indic_syllabic_category_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_indic_syllabic_category_stage_2[pos + f] << 4; - f = code >> 4; - code ^= f << 4; - pos = (RE_UINT32)re_indic_syllabic_category_stage_3[pos + f] << 2; - f = code >> 2; - code ^= f << 2; - pos = (RE_UINT32)re_indic_syllabic_category_stage_4[pos + f] << 2; - value = re_indic_syllabic_category_stage_5[pos + code]; - - return value; -} - -/* Alphanumeric. */ - -static RE_UINT8 re_alphanumeric_stage_1[] = { - 0, 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, -}; - -static RE_UINT8 re_alphanumeric_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_alphanumeric_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 33, 34, 35, 31, - 36, 37, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 38, 1, 1, 1, 1, 1, 1, 1, 1, 1, 39, - 1, 1, 1, 1, 40, 1, 41, 42, 43, 44, 45, 46, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 47, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 48, 49, 1, 50, 51, 52, 53, 54, 55, 56, 57, 31, 31, 31, - 58, 59, 60, 61, 62, 31, 31, 31, 63, 64, 31, 31, 31, 31, 65, 31, - 1, 1, 1, 66, 67, 31, 31, 31, 1, 1, 1, 1, 68, 31, 31, 31, - 1, 1, 69, 31, 31, 31, 31, 70, 71, 31, 31, 31, 31, 31, 31, 31, - 31, 31, 31, 31, 72, 73, 74, 75, 31, 31, 31, 31, 31, 31, 76, 31, - 1, 1, 1, 1, 1, 1, 77, 1, 1, 1, 1, 1, 1, 1, 1, 78, - 79, 31, 31, 31, 31, 31, 31, 31, 1, 1, 79, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_alphanumeric_stage_4[] = { - 0, 1, 2, 2, 0, 3, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 5, 5, 6, 7, 0, 0, 8, 9, 10, 11, 5, 12, - 5, 5, 5, 5, 13, 5, 5, 5, 5, 14, 15, 16, 17, 18, 19, 20, - 21, 5, 22, 23, 5, 5, 24, 25, 26, 5, 27, 5, 5, 28, 5, 29, - 30, 31, 32, 0, 0, 33, 0, 34, 5, 35, 36, 37, 38, 39, 40, 41, - 42, 43, 44, 45, 46, 47, 48, 49, 38, 47, 50, 51, 52, 53, 54, 55, - 56, 57, 58, 49, 59, 57, 60, 61, 59, 62, 63, 64, 65, 66, 67, 68, - 16, 69, 70, 0, 71, 72, 73, 0, 74, 75, 76, 77, 78, 79, 0, 0, - 5, 80, 81, 82, 83, 5, 84, 85, 5, 5, 86, 5, 87, 88, 89, 5, - 90, 5, 91, 0, 92, 5, 5, 93, 16, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 94, 2, 5, 5, 95, 96, 97, 97, 98, 5, 99, 100, 75, - 1, 5, 5, 101, 5, 102, 5, 103, 79, 104, 105, 106, 5, 107, 108, 0, - 109, 5, 110, 111, 108, 112, 0, 0, 5, 113, 114, 0, 5, 115, 5, 116, - 5, 103, 117, 118, 0, 0, 0, 119, 5, 5, 5, 5, 5, 5, 0, 0, - 120, 5, 121, 118, 5, 122, 123, 124, 0, 0, 0, 125, 126, 0, 0, 0, - 127, 128, 129, 5, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 131, 5, 75, 5, 132, 110, 5, 5, 5, 5, 133, - 5, 84, 5, 134, 135, 136, 136, 5, 0, 137, 0, 0, 0, 0, 0, 0, - 138, 139, 16, 5, 140, 16, 5, 85, 141, 142, 5, 5, 143, 69, 0, 26, - 5, 5, 5, 5, 5, 103, 0, 0, 5, 5, 5, 5, 5, 5, 31, 0, - 5, 5, 5, 5, 31, 0, 26, 118, 144, 145, 5, 146, 147, 5, 5, 92, - 148, 149, 5, 5, 150, 151, 0, 152, 153, 17, 5, 97, 5, 5, 154, 155, - 5, 102, 156, 79, 5, 157, 158, 0, 5, 135, 159, 160, 5, 110, 161, 162, - 163, 164, 0, 0, 0, 0, 5, 165, 5, 5, 5, 5, 5, 166, 167, 109, - 5, 5, 5, 168, 5, 5, 169, 0, 170, 171, 172, 5, 5, 28, 173, 5, - 5, 118, 26, 5, 174, 5, 17, 175, 0, 0, 0, 176, 5, 5, 5, 79, - 1, 2, 2, 105, 5, 110, 177, 0, 178, 179, 180, 0, 5, 5, 5, 69, - 0, 0, 5, 93, 0, 0, 0, 0, 0, 0, 0, 0, 79, 5, 181, 0, - 110, 26, 151, 0, 118, 5, 182, 0, 5, 5, 5, 5, 118, 75, 0, 0, - 183, 184, 103, 0, 0, 0, 0, 0, 103, 169, 0, 0, 5, 185, 0, 0, - 186, 97, 0, 79, 0, 0, 0, 0, 5, 103, 103, 156, 0, 0, 0, 0, - 5, 5, 130, 0, 0, 0, 0, 0, 5, 5, 187, 55, 149, 32, 26, 188, - 5, 189, 0, 0, 5, 5, 190, 0, 0, 0, 0, 0, 5, 103, 75, 0, - 5, 5, 5, 143, 0, 0, 0, 0, 5, 5, 5, 191, 0, 0, 0, 0, - 5, 143, 0, 0, 0, 0, 0, 0, 5, 32, 0, 0, 0, 0, 0, 0, - 5, 5, 192, 110, 173, 0, 0, 0, 193, 0, 0, 0, 0, 0, 0, 0, - 5, 5, 194, 5, 195, 196, 197, 5, 198, 199, 200, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 5, 201, 202, 85, 194, 194, 132, 132, 203, 203, 204, 5, - 197, 205, 206, 207, 208, 209, 0, 0, 5, 5, 5, 5, 5, 5, 135, 0, - 5, 93, 5, 5, 5, 5, 5, 5, 118, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_alphanumeric_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 254, 255, 255, 7, 0, 4, 32, 4, - 255, 255, 127, 255, 255, 255, 255, 255, 195, 255, 3, 0, 31, 80, 0, 0, - 32, 0, 0, 0, 0, 0, 223, 60, 64, 215, 255, 255, 251, 255, 255, 255, - 255, 255, 191, 255, 3, 252, 255, 255, 255, 0, 254, 255, 255, 255, 127, 2, - 254, 255, 255, 255, 255, 0, 0, 0, 0, 0, 255, 191, 182, 0, 255, 255, - 255, 7, 7, 0, 0, 0, 255, 7, 255, 255, 255, 254, 255, 195, 255, 255, - 255, 255, 239, 31, 254, 225, 255, 159, 0, 0, 255, 255, 0, 224, 255, 255, - 255, 255, 3, 0, 255, 7, 48, 4, 255, 255, 255, 252, 255, 31, 0, 0, - 255, 255, 255, 1, 253, 31, 0, 0, 240, 3, 255, 127, 255, 255, 255, 239, - 255, 223, 225, 255, 207, 255, 254, 254, 238, 159, 249, 255, 255, 253, 197, 227, - 159, 89, 128, 176, 207, 255, 3, 0, 238, 135, 249, 255, 255, 253, 109, 195, - 135, 25, 2, 94, 192, 255, 63, 0, 238, 191, 251, 255, 255, 253, 237, 227, - 191, 27, 1, 0, 207, 255, 0, 0, 159, 25, 192, 176, 207, 255, 2, 0, - 236, 199, 61, 214, 24, 199, 255, 195, 199, 29, 129, 0, 192, 255, 0, 0, - 238, 223, 253, 255, 255, 253, 239, 227, 223, 29, 96, 3, 236, 223, 253, 255, - 223, 29, 96, 64, 207, 255, 6, 0, 255, 255, 255, 231, 223, 93, 128, 0, - 207, 255, 0, 252, 236, 255, 127, 252, 255, 255, 251, 47, 127, 128, 95, 255, - 0, 0, 12, 0, 255, 255, 255, 7, 127, 32, 255, 3, 150, 37, 240, 254, - 174, 236, 255, 59, 95, 32, 255, 243, 1, 0, 0, 0, 255, 3, 0, 0, - 255, 254, 255, 255, 255, 31, 254, 255, 3, 255, 255, 254, 255, 255, 255, 31, - 255, 255, 127, 249, 255, 3, 255, 255, 231, 193, 255, 255, 127, 64, 255, 51, - 191, 32, 255, 255, 255, 255, 255, 247, 255, 61, 127, 61, 255, 61, 255, 255, - 255, 255, 61, 127, 61, 255, 127, 255, 255, 255, 61, 255, 255, 255, 255, 135, - 255, 255, 0, 0, 255, 255, 31, 0, 255, 159, 255, 255, 255, 199, 1, 0, - 255, 223, 15, 0, 255, 255, 15, 0, 255, 223, 13, 0, 255, 255, 207, 255, - 255, 1, 128, 16, 255, 255, 255, 0, 255, 7, 255, 255, 255, 255, 63, 0, - 255, 15, 255, 1, 192, 255, 255, 255, 255, 63, 31, 0, 255, 15, 255, 255, - 255, 3, 255, 3, 255, 255, 255, 15, 255, 255, 255, 127, 254, 255, 31, 0, - 128, 0, 0, 0, 255, 255, 239, 255, 239, 15, 255, 3, 255, 243, 255, 255, - 191, 255, 3, 0, 255, 227, 255, 255, 255, 255, 255, 63, 0, 222, 111, 0, - 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 95, 220, 31, 207, 15, - 255, 31, 220, 31, 0, 0, 2, 128, 0, 0, 255, 31, 132, 252, 47, 62, - 80, 189, 255, 243, 224, 67, 0, 0, 255, 1, 0, 0, 0, 0, 192, 255, - 255, 127, 255, 255, 31, 120, 12, 0, 255, 128, 0, 0, 255, 255, 127, 0, - 127, 127, 127, 127, 0, 128, 0, 0, 224, 0, 0, 0, 254, 3, 62, 31, - 255, 255, 127, 224, 224, 255, 255, 255, 255, 63, 254, 255, 255, 127, 0, 0, - 255, 31, 255, 255, 255, 15, 0, 0, 255, 127, 240, 143, 255, 255, 255, 128, - 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 255, 187, 247, 255, 255, 15, 0, 255, 3, 0, 0, 252, 8, - 255, 255, 7, 0, 255, 255, 247, 255, 0, 128, 255, 3, 255, 63, 255, 3, - 255, 255, 127, 4, 5, 0, 0, 56, 255, 255, 60, 0, 126, 126, 126, 0, - 127, 127, 0, 0, 255, 7, 255, 3, 15, 0, 255, 255, 127, 248, 255, 255, - 255, 63, 255, 255, 255, 255, 255, 3, 127, 0, 248, 224, 255, 253, 127, 95, - 219, 255, 255, 255, 0, 0, 248, 255, 255, 255, 252, 255, 0, 0, 255, 15, - 0, 0, 223, 255, 252, 252, 252, 28, 255, 239, 255, 255, 127, 255, 255, 183, - 255, 63, 255, 63, 255, 255, 1, 0, 15, 255, 62, 0, 63, 253, 255, 255, - 255, 255, 191, 145, 255, 255, 255, 192, 111, 240, 239, 254, 63, 0, 0, 0, - 255, 1, 255, 3, 255, 255, 199, 255, 30, 0, 255, 3, 7, 0, 0, 0, - 31, 0, 255, 255, 3, 0, 0, 0, 255, 255, 223, 255, 255, 255, 255, 223, - 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, - 95, 252, 253, 255, 63, 255, 255, 255, 253, 255, 255, 247, 255, 253, 255, 255, - 247, 207, 255, 255, 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, - 255, 251, 255, 15, 238, 251, 255, 15, -}; - -/* Alphanumeric: 1849 bytes. */ - -RE_UINT32 re_get_alphanumeric(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_alphanumeric_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_alphanumeric_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_alphanumeric_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_alphanumeric_stage_4[pos + f] << 5; - pos += code; - value = (re_alphanumeric_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Any. */ - -RE_UINT32 re_get_any(RE_UINT32 ch) { - return 1; -} - -/* Blank. */ - -static RE_UINT8 re_blank_stage_1[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, -}; - -static RE_UINT8 re_blank_stage_2[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_blank_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_blank_stage_4[] = { - 0, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 3, 1, 1, 1, 1, 1, 4, 5, 1, 1, 1, 1, 1, 1, - 3, 1, 1, 1, 1, 1, 1, 1, -}; - -static RE_UINT8 re_blank_stage_5[] = { - 0, 2, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, - 255, 7, 0, 0, 0, 128, 0, 0, 0, 0, 0, 128, 0, 0, 0, 0, -}; - -/* Blank: 169 bytes. */ - -RE_UINT32 re_get_blank(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_blank_stage_1[f] << 3; - f = code >> 13; - code ^= f << 13; - pos = (RE_UINT32)re_blank_stage_2[pos + f] << 4; - f = code >> 9; - code ^= f << 9; - pos = (RE_UINT32)re_blank_stage_3[pos + f] << 3; - f = code >> 6; - code ^= f << 6; - pos = (RE_UINT32)re_blank_stage_4[pos + f] << 6; - pos += code; - value = (re_blank_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Graph. */ - -static RE_UINT8 re_graph_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 6, 4, 8, - 4, 8, -}; - -static RE_UINT8 re_graph_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 7, 7, 7, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 24, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 25, 7, 26, 27, 13, 13, 13, 13, 13, 13, 13, 28, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 29, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 30, -}; - -static RE_UINT8 re_graph_stage_3[] = { - 0, 1, 1, 2, 1, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, - 14, 1, 15, 16, 1, 1, 17, 18, 19, 20, 21, 22, 23, 24, 1, 25, - 26, 27, 1, 28, 29, 1, 1, 30, 1, 1, 1, 31, 32, 33, 34, 35, - 36, 37, 38, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 40, - 1, 1, 1, 1, 41, 1, 42, 43, 44, 45, 46, 47, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 48, 49, 49, 49, 49, 49, 49, 49, 49, - 1, 1, 50, 51, 1, 52, 53, 54, 55, 56, 57, 58, 59, 49, 49, 49, - 60, 61, 62, 63, 64, 49, 65, 49, 66, 67, 49, 49, 49, 49, 68, 49, - 1, 1, 1, 69, 70, 49, 49, 49, 1, 1, 1, 1, 71, 49, 49, 49, - 1, 1, 72, 49, 49, 49, 49, 73, 74, 49, 49, 49, 49, 49, 49, 49, - 75, 76, 77, 78, 79, 80, 81, 82, 49, 49, 49, 49, 49, 49, 83, 49, - 84, 85, 86, 87, 88, 89, 90, 91, 1, 1, 1, 1, 1, 1, 92, 1, - 1, 1, 1, 1, 1, 1, 1, 93, 94, 49, 49, 49, 49, 49, 49, 49, - 1, 1, 94, 49, 49, 49, 49, 49, 95, 96, 49, 49, 49, 49, 49, 49, - 1, 1, 1, 1, 1, 1, 1, 97, -}; - -static RE_UINT8 re_graph_stage_4[] = { - 0, 1, 2, 3, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 4, 5, 6, 2, 2, 2, 7, 8, 1, 9, 2, 10, 11, - 12, 2, 2, 2, 2, 2, 2, 2, 13, 2, 14, 2, 2, 15, 2, 16, - 2, 17, 18, 0, 0, 19, 0, 20, 2, 2, 2, 21, 22, 23, 24, 25, - 26, 27, 28, 29, 30, 31, 32, 33, 22, 31, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 44, 48, 49, 50, 51, 52, 53, 54, - 1, 55, 56, 0, 57, 58, 59, 0, 2, 2, 60, 61, 21, 62, 63, 0, - 2, 2, 2, 2, 2, 2, 64, 2, 2, 2, 65, 2, 66, 67, 68, 2, - 69, 2, 48, 70, 71, 2, 2, 72, 2, 2, 2, 2, 73, 2, 2, 74, - 75, 76, 77, 78, 2, 2, 79, 80, 81, 2, 2, 82, 2, 83, 2, 84, - 70, 85, 86, 87, 2, 88, 89, 2, 90, 2, 3, 91, 80, 92, 0, 0, - 2, 2, 88, 70, 2, 2, 2, 93, 2, 94, 95, 2, 0, 0, 10, 76, - 2, 2, 2, 2, 2, 2, 2, 96, 97, 2, 98, 79, 2, 99, 100, 101, - 102, 103, 3, 104, 105, 16, 106, 74, 2, 2, 2, 2, 107, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 77, 2, 108, 109, 2, 2, 2, 2, 2, - 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 110, 0, 0, 0, 0, 0, - 2, 111, 3, 2, 2, 2, 2, 112, 2, 64, 2, 113, 76, 114, 114, 2, - 2, 56, 0, 0, 115, 2, 2, 77, 2, 2, 2, 2, 2, 2, 84, 116, - 1, 2, 1, 2, 8, 2, 2, 2, 117, 118, 2, 2, 111, 16, 2, 119, - 3, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 2, 84, 2, 2, - 2, 2, 2, 2, 2, 2, 120, 0, 2, 2, 2, 2, 121, 2, 122, 2, - 2, 123, 2, 2, 124, 2, 2, 82, 2, 2, 2, 2, 125, 109, 0, 126, - 2, 127, 2, 82, 2, 2, 128, 56, 2, 2, 129, 70, 2, 2, 130, 0, - 2, 76, 131, 56, 2, 2, 132, 76, 133, 134, 0, 0, 0, 0, 2, 135, - 2, 2, 2, 2, 2, 119, 136, 56, 0, 0, 0, 0, 0, 0, 0, 0, - 2, 2, 2, 137, 2, 2, 71, 0, 138, 139, 140, 2, 2, 2, 141, 2, - 2, 2, 106, 2, 142, 2, 143, 144, 71, 122, 145, 146, 2, 2, 2, 91, - 1, 2, 2, 2, 2, 3, 147, 148, 149, 150, 151, 0, 2, 2, 2, 16, - 152, 153, 2, 2, 154, 0, 106, 79, 0, 0, 0, 0, 70, 2, 74, 0, - 3, 119, 109, 0, 155, 2, 156, 0, 2, 2, 2, 2, 79, 157, 0, 0, - 158, 159, 160, 0, 0, 0, 0, 0, 161, 162, 0, 0, 2, 163, 0, 0, - 164, 165, 166, 2, 0, 0, 0, 0, 2, 167, 168, 169, 0, 0, 0, 0, - 2, 2, 170, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0, - 2, 2, 171, 172, 2, 2, 173, 174, 2, 99, 175, 0, 2, 2, 174, 0, - 0, 0, 0, 0, 2, 82, 157, 0, 2, 2, 2, 176, 0, 0, 0, 0, - 2, 2, 2, 177, 0, 0, 0, 0, 2, 176, 0, 0, 0, 0, 0, 0, - 2, 178, 0, 0, 0, 0, 0, 0, 2, 2, 179, 3, 180, 0, 0, 0, - 181, 0, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, 84, - 2, 182, 2, 2, 2, 2, 79, 0, 2, 2, 183, 0, 0, 0, 0, 0, - 2, 2, 76, 15, 0, 0, 0, 0, 2, 2, 99, 2, 62, 184, 185, 2, - 186, 187, 188, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 189, 2, 2, - 2, 2, 2, 2, 2, 2, 190, 2, 185, 191, 192, 193, 194, 195, 0, 196, - 2, 88, 2, 2, 77, 197, 198, 0, 83, 111, 2, 88, 16, 0, 0, 199, - 200, 16, 201, 0, 0, 0, 0, 0, 2, 202, 2, 70, 77, 2, 203, 74, - 2, 3, 204, 2, 2, 2, 2, 205, 2, 79, 119, 143, 0, 0, 0, 206, - 2, 2, 207, 0, 2, 2, 183, 0, 2, 2, 2, 77, 0, 0, 0, 0, - 2, 2, 2, 2, 2, 2, 76, 0, 2, 72, 2, 2, 2, 2, 2, 2, - 79, 0, 0, 0, 0, 0, 0, 0, 208, 2, 2, 2, 0, 0, 0, 0, - 2, 2, 2, 2, 2, 2, 2, 172, 2, 2, 2, 2, 2, 2, 2, 79, -}; - -static RE_UINT8 re_graph_stage_5[] = { - 0, 0, 0, 0, 254, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 127, - 255, 255, 255, 124, 240, 215, 255, 255, 251, 255, 255, 255, 255, 0, 254, 255, - 255, 255, 127, 254, 255, 134, 254, 255, 255, 0, 255, 255, 255, 7, 31, 0, - 223, 255, 255, 223, 255, 191, 255, 255, 255, 231, 255, 255, 255, 255, 3, 0, - 255, 255, 255, 7, 255, 63, 255, 127, 255, 255, 255, 79, 253, 31, 0, 0, - 240, 255, 255, 127, 255, 255, 255, 254, 238, 159, 249, 255, 255, 253, 197, 243, - 159, 121, 128, 176, 207, 255, 255, 15, 238, 135, 249, 255, 255, 253, 109, 211, - 135, 57, 2, 94, 192, 255, 63, 0, 238, 191, 251, 255, 255, 253, 237, 243, - 191, 59, 1, 0, 207, 255, 3, 0, 159, 57, 192, 176, 207, 255, 255, 0, - 236, 199, 61, 214, 24, 199, 255, 195, 199, 61, 129, 0, 192, 255, 255, 7, - 238, 223, 253, 255, 255, 253, 239, 227, 223, 61, 96, 3, 207, 255, 0, 255, - 236, 223, 253, 255, 255, 253, 239, 243, 223, 61, 96, 64, 207, 255, 6, 0, - 255, 255, 255, 231, 223, 125, 128, 0, 207, 255, 63, 254, 236, 255, 127, 252, - 255, 255, 251, 47, 127, 132, 95, 255, 0, 0, 28, 0, 255, 255, 255, 135, - 255, 255, 255, 15, 150, 37, 240, 254, 174, 236, 255, 59, 95, 63, 255, 243, - 255, 254, 255, 255, 255, 31, 254, 255, 255, 255, 255, 223, 255, 223, 255, 7, - 191, 32, 255, 255, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 255, 255, 255, 31, 255, 255, 255, 3, - 255, 255, 31, 0, 254, 255, 255, 31, 255, 255, 1, 0, 255, 223, 31, 0, - 255, 255, 127, 0, 255, 255, 15, 0, 255, 223, 13, 0, 255, 255, 255, 63, - 255, 3, 255, 3, 255, 127, 255, 3, 255, 255, 255, 0, 255, 7, 255, 255, - 255, 255, 63, 0, 255, 15, 255, 15, 241, 255, 255, 255, 255, 63, 31, 0, - 255, 15, 255, 255, 255, 3, 255, 199, 255, 255, 255, 207, 255, 255, 255, 159, - 255, 63, 0, 0, 255, 255, 15, 240, 255, 255, 255, 248, 255, 227, 255, 255, - 127, 0, 0, 240, 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 255, - 223, 255, 207, 239, 255, 255, 220, 127, 0, 248, 255, 255, 255, 124, 255, 255, - 223, 255, 243, 255, 255, 127, 255, 31, 0, 0, 255, 255, 255, 3, 255, 255, - 127, 0, 0, 0, 255, 7, 0, 0, 255, 31, 255, 3, 255, 127, 255, 255, - 255, 255, 15, 254, 255, 128, 1, 128, 127, 127, 127, 127, 255, 255, 255, 251, - 0, 0, 255, 15, 224, 255, 255, 255, 255, 63, 254, 255, 15, 0, 255, 255, - 255, 31, 0, 0, 255, 31, 255, 255, 127, 0, 255, 255, 255, 15, 0, 0, - 255, 255, 255, 128, 255, 127, 15, 0, 0, 0, 0, 255, 255, 15, 255, 3, - 31, 192, 255, 3, 255, 255, 15, 128, 255, 191, 255, 195, 255, 63, 255, 243, - 7, 0, 0, 248, 126, 126, 126, 0, 127, 127, 0, 0, 255, 63, 255, 3, - 127, 248, 255, 255, 255, 63, 255, 255, 127, 0, 248, 224, 255, 255, 127, 95, - 219, 255, 255, 255, 3, 0, 248, 255, 255, 255, 252, 255, 255, 0, 0, 0, - 0, 0, 255, 63, 255, 255, 247, 255, 127, 15, 223, 255, 252, 252, 252, 28, - 127, 127, 0, 62, 255, 239, 255, 255, 127, 255, 255, 183, 255, 63, 255, 63, - 135, 255, 255, 255, 255, 255, 143, 255, 255, 7, 255, 15, 255, 255, 255, 191, - 15, 255, 63, 0, 255, 3, 0, 0, 63, 253, 255, 255, 255, 255, 191, 145, - 255, 255, 191, 255, 255, 255, 255, 143, 255, 255, 255, 131, 255, 255, 255, 192, - 111, 240, 239, 254, 255, 255, 15, 135, 255, 0, 255, 1, 255, 255, 63, 254, - 255, 255, 63, 255, 255, 255, 7, 255, 255, 1, 0, 0, 255, 63, 252, 255, - 255, 255, 0, 0, 3, 0, 255, 255, 255, 1, 255, 3, 15, 0, 0, 0, - 255, 127, 0, 0, 7, 0, 15, 0, 255, 255, 255, 1, 31, 0, 255, 255, - 0, 128, 255, 255, 3, 0, 0, 0, 127, 254, 255, 255, 63, 0, 0, 0, - 100, 222, 255, 235, 239, 255, 255, 255, 191, 231, 223, 223, 255, 255, 255, 123, - 95, 252, 253, 255, 63, 255, 255, 255, 255, 207, 255, 255, 150, 254, 247, 10, - 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, 238, 251, 255, 15, - 0, 0, 3, 0, 255, 127, 254, 127, 254, 255, 254, 255, 192, 255, 255, 255, - 7, 0, 255, 255, 255, 1, 3, 0, 1, 0, 191, 255, 223, 7, 0, 0, - 253, 255, 255, 255, 255, 255, 255, 30, 0, 0, 0, 248, 225, 255, 0, 0, - 2, 0, 0, 0, -}; - -/* Graph: 2046 bytes. */ - -RE_UINT32 re_get_graph(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_graph_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_graph_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_graph_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_graph_stage_4[pos + f] << 5; - pos += code; - value = (re_graph_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Print. */ - -static RE_UINT8 re_print_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 6, 4, 8, - 4, 8, -}; - -static RE_UINT8 re_print_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 7, 7, 7, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 24, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 25, 7, 26, 27, 13, 13, 13, 13, 13, 13, 13, 28, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 29, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 30, -}; - -static RE_UINT8 re_print_stage_3[] = { - 0, 1, 1, 2, 1, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, - 14, 1, 15, 16, 1, 1, 17, 18, 19, 20, 21, 22, 23, 24, 1, 25, - 26, 27, 1, 28, 29, 1, 1, 30, 1, 1, 1, 31, 32, 33, 34, 35, - 36, 37, 38, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 40, - 1, 1, 1, 1, 41, 1, 42, 43, 44, 45, 46, 47, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 48, 49, 49, 49, 49, 49, 49, 49, 49, - 1, 1, 50, 51, 1, 52, 53, 54, 55, 56, 57, 58, 59, 49, 49, 49, - 60, 61, 62, 63, 64, 49, 65, 49, 66, 67, 49, 49, 49, 49, 68, 49, - 1, 1, 1, 69, 70, 49, 49, 49, 1, 1, 1, 1, 71, 49, 49, 49, - 1, 1, 72, 49, 49, 49, 49, 73, 74, 49, 49, 49, 49, 49, 49, 49, - 75, 76, 77, 78, 79, 80, 81, 82, 49, 49, 49, 49, 49, 49, 83, 49, - 84, 85, 86, 87, 88, 89, 90, 91, 1, 1, 1, 1, 1, 1, 92, 1, - 1, 1, 1, 1, 1, 1, 1, 93, 94, 49, 49, 49, 49, 49, 49, 49, - 1, 1, 94, 49, 49, 49, 49, 49, 95, 96, 49, 49, 49, 49, 49, 49, - 1, 1, 1, 1, 1, 1, 1, 97, -}; - -static RE_UINT8 re_print_stage_4[] = { - 0, 1, 1, 2, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 3, 4, 5, 1, 1, 1, 6, 7, 8, 9, 1, 10, 11, - 12, 1, 1, 1, 1, 1, 1, 1, 13, 1, 14, 1, 1, 15, 1, 16, - 1, 17, 18, 0, 0, 19, 0, 20, 1, 1, 1, 21, 22, 23, 24, 25, - 26, 27, 28, 29, 30, 31, 32, 33, 22, 31, 34, 35, 36, 37, 38, 39, - 40, 41, 42, 43, 44, 45, 46, 47, 44, 48, 49, 50, 51, 52, 53, 54, - 8, 55, 56, 0, 57, 58, 59, 0, 1, 1, 60, 61, 21, 62, 63, 0, - 1, 1, 1, 1, 1, 1, 64, 1, 1, 1, 65, 1, 66, 67, 68, 1, - 69, 1, 48, 70, 71, 1, 1, 72, 1, 1, 1, 1, 70, 1, 1, 73, - 74, 75, 76, 77, 1, 1, 78, 79, 80, 1, 1, 81, 1, 82, 1, 83, - 70, 84, 85, 86, 1, 87, 88, 1, 89, 1, 2, 90, 79, 91, 0, 0, - 1, 1, 87, 70, 1, 1, 1, 92, 1, 93, 94, 1, 0, 0, 10, 75, - 1, 1, 1, 1, 1, 1, 1, 95, 96, 1, 97, 78, 1, 98, 99, 100, - 1, 101, 1, 102, 103, 16, 104, 73, 1, 1, 1, 1, 105, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 76, 1, 106, 107, 1, 1, 1, 1, 1, - 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 108, 0, 0, 0, 0, 0, - 1, 109, 2, 1, 1, 1, 1, 110, 1, 64, 1, 111, 75, 112, 112, 1, - 1, 56, 0, 0, 113, 1, 1, 76, 1, 1, 1, 1, 1, 1, 83, 114, - 1, 1, 8, 1, 7, 1, 1, 1, 115, 116, 1, 1, 109, 16, 1, 117, - 2, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 83, 1, 1, - 1, 1, 1, 1, 1, 1, 118, 0, 1, 1, 1, 1, 119, 1, 120, 1, - 1, 121, 1, 1, 122, 1, 1, 81, 1, 1, 1, 1, 123, 107, 0, 124, - 1, 125, 1, 81, 1, 1, 126, 56, 1, 1, 127, 70, 1, 1, 128, 0, - 1, 75, 129, 56, 1, 1, 130, 75, 131, 132, 0, 0, 0, 0, 1, 133, - 1, 1, 1, 1, 1, 117, 134, 56, 0, 0, 0, 0, 0, 0, 0, 0, - 1, 1, 1, 135, 1, 1, 71, 0, 136, 137, 138, 1, 1, 1, 139, 1, - 1, 1, 104, 1, 140, 1, 141, 142, 71, 120, 143, 144, 1, 1, 1, 90, - 8, 1, 1, 1, 1, 2, 145, 146, 147, 148, 149, 0, 1, 1, 1, 16, - 150, 151, 1, 1, 152, 0, 104, 78, 0, 0, 0, 0, 70, 1, 73, 0, - 2, 117, 107, 0, 153, 1, 154, 0, 1, 1, 1, 1, 78, 155, 0, 0, - 156, 157, 158, 0, 0, 0, 0, 0, 159, 160, 0, 0, 1, 161, 0, 0, - 162, 163, 164, 1, 0, 0, 0, 0, 1, 165, 166, 167, 0, 0, 0, 0, - 1, 1, 168, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, - 1, 1, 169, 170, 1, 1, 171, 172, 1, 98, 173, 0, 1, 1, 172, 0, - 0, 0, 0, 0, 1, 81, 155, 0, 1, 1, 1, 174, 0, 0, 0, 0, - 1, 1, 1, 175, 0, 0, 0, 0, 1, 174, 0, 0, 0, 0, 0, 0, - 1, 176, 0, 0, 0, 0, 0, 0, 1, 1, 177, 2, 178, 0, 0, 0, - 179, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 83, - 1, 180, 1, 1, 1, 1, 78, 0, 1, 1, 181, 0, 0, 0, 0, 0, - 1, 1, 75, 15, 0, 0, 0, 0, 1, 1, 98, 1, 62, 182, 183, 1, - 184, 185, 186, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 187, 1, 1, - 1, 1, 1, 1, 1, 1, 188, 1, 183, 189, 190, 191, 192, 193, 0, 194, - 1, 87, 1, 1, 76, 195, 196, 0, 82, 109, 1, 87, 16, 0, 0, 197, - 198, 16, 199, 0, 0, 0, 0, 0, 1, 200, 1, 70, 76, 1, 201, 73, - 1, 2, 202, 1, 1, 1, 1, 203, 1, 78, 117, 141, 0, 0, 0, 204, - 1, 1, 205, 0, 1, 1, 181, 0, 1, 1, 1, 76, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 1, 75, 0, 1, 72, 1, 1, 1, 1, 1, 1, - 78, 0, 0, 0, 0, 0, 0, 0, 206, 1, 1, 1, 0, 0, 0, 0, - 1, 1, 1, 1, 1, 1, 1, 170, 1, 1, 1, 1, 1, 1, 1, 78, -}; - -static RE_UINT8 re_print_stage_5[] = { - 0, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 127, 255, 255, 255, 124, - 240, 215, 255, 255, 251, 255, 255, 255, 255, 0, 254, 255, 255, 255, 127, 254, - 254, 255, 255, 255, 255, 134, 254, 255, 255, 0, 255, 255, 255, 7, 31, 0, - 223, 255, 255, 223, 255, 191, 255, 255, 255, 231, 255, 255, 255, 255, 3, 0, - 255, 255, 255, 7, 255, 63, 255, 127, 255, 255, 255, 79, 253, 31, 0, 0, - 240, 255, 255, 127, 255, 255, 255, 254, 238, 159, 249, 255, 255, 253, 197, 243, - 159, 121, 128, 176, 207, 255, 255, 15, 238, 135, 249, 255, 255, 253, 109, 211, - 135, 57, 2, 94, 192, 255, 63, 0, 238, 191, 251, 255, 255, 253, 237, 243, - 191, 59, 1, 0, 207, 255, 3, 0, 159, 57, 192, 176, 207, 255, 255, 0, - 236, 199, 61, 214, 24, 199, 255, 195, 199, 61, 129, 0, 192, 255, 255, 7, - 238, 223, 253, 255, 255, 253, 239, 227, 223, 61, 96, 3, 207, 255, 0, 255, - 236, 223, 253, 255, 255, 253, 239, 243, 223, 61, 96, 64, 207, 255, 6, 0, - 255, 255, 255, 231, 223, 125, 128, 0, 207, 255, 63, 254, 236, 255, 127, 252, - 255, 255, 251, 47, 127, 132, 95, 255, 0, 0, 28, 0, 255, 255, 255, 135, - 255, 255, 255, 15, 150, 37, 240, 254, 174, 236, 255, 59, 95, 63, 255, 243, - 255, 254, 255, 255, 255, 31, 254, 255, 255, 255, 255, 223, 255, 223, 255, 7, - 191, 32, 255, 255, 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, - 61, 255, 127, 255, 255, 255, 61, 255, 255, 255, 255, 31, 255, 255, 255, 3, - 255, 255, 31, 0, 255, 255, 1, 0, 255, 223, 31, 0, 255, 255, 127, 0, - 255, 255, 15, 0, 255, 223, 13, 0, 255, 255, 255, 63, 255, 3, 255, 3, - 255, 127, 255, 3, 255, 255, 255, 0, 255, 7, 255, 255, 255, 255, 63, 0, - 255, 15, 255, 15, 241, 255, 255, 255, 255, 63, 31, 0, 255, 15, 255, 255, - 255, 3, 255, 199, 255, 255, 255, 207, 255, 255, 255, 159, 255, 63, 0, 0, - 255, 255, 15, 240, 255, 255, 255, 248, 255, 227, 255, 255, 127, 0, 0, 240, - 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 255, 223, 255, 207, 239, - 255, 255, 220, 127, 255, 252, 255, 255, 223, 255, 243, 255, 255, 127, 255, 31, - 0, 0, 255, 255, 255, 3, 255, 255, 127, 0, 0, 0, 255, 7, 0, 0, - 255, 31, 255, 3, 255, 127, 255, 255, 255, 255, 15, 254, 255, 128, 1, 128, - 127, 127, 127, 127, 255, 255, 255, 251, 0, 0, 255, 15, 224, 255, 255, 255, - 255, 63, 254, 255, 15, 0, 255, 255, 255, 31, 0, 0, 255, 31, 255, 255, - 127, 0, 255, 255, 255, 15, 0, 0, 255, 255, 255, 128, 255, 127, 15, 0, - 0, 0, 0, 255, 255, 15, 255, 3, 31, 192, 255, 3, 255, 255, 15, 128, - 255, 191, 255, 195, 255, 63, 255, 243, 7, 0, 0, 248, 126, 126, 126, 0, - 127, 127, 0, 0, 255, 63, 255, 3, 127, 248, 255, 255, 255, 63, 255, 255, - 127, 0, 248, 224, 255, 255, 127, 95, 219, 255, 255, 255, 3, 0, 248, 255, - 255, 255, 252, 255, 255, 0, 0, 0, 0, 0, 255, 63, 255, 255, 247, 255, - 127, 15, 223, 255, 252, 252, 252, 28, 127, 127, 0, 62, 255, 239, 255, 255, - 127, 255, 255, 183, 255, 63, 255, 63, 135, 255, 255, 255, 255, 255, 143, 255, - 255, 7, 255, 15, 255, 255, 255, 191, 15, 255, 63, 0, 255, 3, 0, 0, - 63, 253, 255, 255, 255, 255, 191, 145, 255, 255, 191, 255, 255, 255, 255, 143, - 255, 255, 255, 131, 255, 255, 255, 192, 111, 240, 239, 254, 255, 255, 15, 135, - 255, 0, 255, 1, 255, 255, 63, 254, 255, 255, 63, 255, 255, 255, 7, 255, - 255, 1, 0, 0, 255, 63, 252, 255, 255, 255, 0, 0, 3, 0, 255, 255, - 255, 1, 255, 3, 15, 0, 0, 0, 255, 127, 0, 0, 7, 0, 15, 0, - 255, 255, 255, 1, 31, 0, 255, 255, 0, 128, 255, 255, 3, 0, 0, 0, - 127, 254, 255, 255, 63, 0, 0, 0, 100, 222, 255, 235, 239, 255, 255, 255, - 191, 231, 223, 223, 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, - 255, 207, 255, 255, 150, 254, 247, 10, 132, 234, 150, 170, 150, 247, 247, 94, - 255, 251, 255, 15, 238, 251, 255, 15, 0, 0, 3, 0, 255, 127, 254, 127, - 254, 255, 254, 255, 192, 255, 255, 255, 7, 0, 255, 255, 255, 1, 3, 0, - 1, 0, 191, 255, 223, 7, 0, 0, 253, 255, 255, 255, 255, 255, 255, 30, - 0, 0, 0, 248, 225, 255, 0, 0, 2, 0, 0, 0, -}; - -/* Print: 2038 bytes. */ - -RE_UINT32 re_get_print(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_print_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_print_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_print_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_print_stage_4[pos + f] << 5; - pos += code; - value = (re_print_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* Word. */ - -static RE_UINT8 re_word_stage_1[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 6, 6, 6, - 6, 6, -}; - -static RE_UINT8 re_word_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 9, 10, 11, 7, 7, 7, 7, 12, 13, 13, 13, 13, 14, - 15, 16, 17, 13, 18, 13, 19, 13, 13, 13, 13, 13, 13, 20, 13, 13, - 13, 13, 13, 13, 13, 13, 21, 13, 13, 13, 22, 13, 13, 23, 13, 13, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 13, 13, 13, 13, 13, 13, 13, 27, - 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, - 28, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -}; - -static RE_UINT8 re_word_stage_3[] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 1, 17, 18, 19, 1, 20, 21, 22, 23, 24, 25, 26, 27, 1, 28, - 29, 30, 31, 31, 32, 31, 31, 31, 31, 31, 31, 31, 33, 34, 35, 31, - 36, 37, 31, 31, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 38, 1, 1, 1, 1, 1, 1, 1, 1, 1, 39, - 1, 1, 1, 1, 40, 1, 41, 42, 43, 44, 45, 46, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 47, 31, 31, 31, 31, 31, 31, 31, 31, - 31, 1, 48, 49, 1, 50, 51, 52, 53, 54, 55, 56, 57, 31, 31, 31, - 58, 59, 60, 61, 62, 31, 31, 31, 63, 64, 31, 31, 31, 31, 65, 31, - 1, 1, 1, 66, 67, 31, 31, 31, 1, 1, 1, 1, 68, 31, 31, 31, - 1, 1, 69, 31, 31, 31, 31, 70, 71, 31, 31, 31, 31, 31, 31, 31, - 31, 72, 73, 31, 74, 75, 76, 77, 31, 31, 31, 31, 31, 31, 78, 31, - 1, 1, 1, 1, 1, 1, 79, 1, 1, 1, 1, 1, 1, 1, 1, 80, - 81, 31, 31, 31, 31, 31, 31, 31, 1, 1, 81, 31, 31, 31, 31, 31, - 31, 82, 31, 31, 31, 31, 31, 31, -}; - -static RE_UINT8 re_word_stage_4[] = { - 0, 1, 2, 3, 0, 4, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 7, 8, 6, 6, 6, 9, 10, 11, 6, 12, - 6, 6, 6, 6, 11, 6, 6, 6, 6, 13, 14, 15, 13, 16, 17, 18, - 19, 6, 6, 20, 6, 6, 21, 22, 23, 6, 24, 6, 6, 25, 6, 26, - 6, 27, 28, 0, 0, 29, 0, 30, 6, 6, 6, 31, 32, 33, 34, 35, - 36, 37, 38, 39, 40, 41, 42, 43, 32, 41, 44, 45, 46, 47, 48, 49, - 50, 51, 52, 43, 53, 54, 55, 56, 53, 57, 58, 59, 60, 61, 62, 63, - 15, 64, 65, 0, 66, 67, 68, 0, 69, 70, 71, 72, 73, 74, 75, 0, - 6, 6, 76, 6, 77, 6, 78, 79, 6, 6, 80, 6, 81, 82, 83, 6, - 84, 6, 57, 0, 85, 6, 6, 86, 15, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 87, 3, 6, 6, 88, 89, 86, 90, 91, 6, 6, 92, 93, - 94, 6, 6, 95, 6, 96, 6, 97, 74, 98, 99, 100, 6, 101, 102, 0, - 28, 6, 103, 104, 102, 105, 0, 0, 6, 6, 106, 107, 6, 6, 6, 90, - 6, 95, 108, 77, 0, 0, 109, 110, 6, 6, 6, 6, 6, 6, 6, 111, - 112, 6, 113, 77, 6, 114, 115, 116, 117, 118, 119, 120, 121, 0, 23, 122, - 123, 124, 125, 6, 126, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 127, 6, 93, 6, 128, 103, 6, 6, 6, 6, 129, - 6, 78, 6, 130, 110, 131, 131, 6, 0, 132, 0, 0, 0, 0, 0, 0, - 133, 134, 15, 6, 135, 15, 6, 79, 136, 137, 6, 6, 138, 64, 0, 23, - 6, 6, 6, 6, 6, 97, 0, 0, 6, 6, 6, 6, 6, 6, 139, 0, - 6, 6, 6, 6, 139, 0, 23, 77, 140, 141, 6, 142, 143, 6, 6, 25, - 144, 145, 6, 6, 146, 147, 0, 148, 6, 149, 6, 90, 6, 6, 150, 151, - 6, 152, 90, 74, 6, 6, 153, 0, 6, 110, 154, 155, 6, 6, 156, 157, - 158, 159, 0, 0, 0, 0, 6, 160, 6, 6, 6, 6, 6, 161, 162, 28, - 6, 6, 6, 152, 6, 6, 163, 0, 164, 165, 166, 6, 6, 25, 167, 6, - 6, 77, 23, 6, 168, 6, 149, 169, 85, 170, 171, 172, 6, 6, 6, 74, - 1, 2, 3, 99, 6, 103, 173, 0, 174, 175, 176, 0, 6, 6, 6, 64, - 0, 0, 6, 86, 0, 0, 0, 177, 0, 0, 0, 0, 74, 6, 122, 0, - 103, 23, 147, 0, 77, 6, 178, 0, 6, 6, 6, 6, 77, 93, 0, 0, - 179, 180, 97, 0, 0, 0, 0, 0, 97, 163, 0, 0, 6, 181, 0, 0, - 182, 183, 0, 74, 0, 0, 0, 0, 6, 97, 97, 184, 0, 0, 0, 0, - 6, 6, 126, 0, 0, 0, 0, 0, 6, 6, 185, 49, 6, 64, 23, 186, - 6, 187, 0, 0, 6, 6, 150, 0, 0, 0, 0, 0, 6, 95, 93, 0, - 6, 6, 6, 138, 0, 0, 0, 0, 6, 6, 6, 188, 0, 0, 0, 0, - 6, 138, 0, 0, 0, 0, 0, 0, 6, 189, 0, 0, 0, 0, 0, 0, - 6, 6, 190, 103, 191, 0, 0, 0, 192, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 193, 194, 195, 0, 0, 0, 0, 196, 0, 0, 0, 0, 0, - 6, 6, 187, 6, 197, 198, 199, 6, 200, 201, 202, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 203, 204, 79, 187, 187, 128, 128, 205, 205, 206, 6, - 199, 207, 208, 209, 210, 211, 0, 0, 6, 6, 6, 6, 6, 6, 110, 0, - 6, 86, 6, 6, 6, 6, 6, 6, 77, 0, 0, 0, 0, 0, 0, 0, - 6, 6, 6, 6, 6, 6, 6, 85, -}; - -static RE_UINT8 re_word_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 254, 255, 255, 135, 254, 255, 255, 7, - 0, 4, 32, 4, 255, 255, 127, 255, 255, 255, 255, 255, 195, 255, 3, 0, - 31, 80, 0, 0, 255, 255, 223, 60, 64, 215, 255, 255, 251, 255, 255, 255, - 255, 255, 191, 255, 255, 0, 254, 255, 255, 255, 127, 2, 254, 255, 255, 255, - 255, 255, 255, 191, 182, 0, 255, 255, 255, 7, 7, 0, 0, 0, 255, 7, - 255, 195, 255, 255, 255, 255, 239, 159, 255, 253, 255, 159, 0, 0, 255, 255, - 255, 231, 255, 255, 255, 255, 3, 0, 255, 255, 63, 4, 255, 63, 0, 0, - 255, 255, 255, 15, 253, 31, 0, 0, 240, 255, 255, 127, 207, 255, 254, 254, - 238, 159, 249, 255, 255, 253, 197, 243, 159, 121, 128, 176, 207, 255, 3, 0, - 238, 135, 249, 255, 255, 253, 109, 211, 135, 57, 2, 94, 192, 255, 63, 0, - 238, 191, 251, 255, 255, 253, 237, 243, 191, 59, 1, 0, 207, 255, 0, 0, - 159, 57, 192, 176, 207, 255, 2, 0, 236, 199, 61, 214, 24, 199, 255, 195, - 199, 61, 129, 0, 192, 255, 0, 0, 238, 223, 253, 255, 255, 253, 239, 227, - 223, 61, 96, 3, 236, 223, 253, 255, 255, 253, 239, 243, 223, 61, 96, 64, - 207, 255, 6, 0, 255, 255, 255, 231, 223, 125, 128, 0, 207, 255, 0, 252, - 236, 255, 127, 252, 255, 255, 251, 47, 127, 132, 95, 255, 0, 0, 12, 0, - 255, 255, 255, 7, 255, 127, 255, 3, 150, 37, 240, 254, 174, 236, 255, 59, - 95, 63, 255, 243, 1, 0, 0, 3, 255, 3, 160, 194, 255, 254, 255, 255, - 255, 31, 254, 255, 223, 255, 255, 254, 255, 255, 255, 31, 64, 0, 0, 0, - 255, 3, 255, 255, 255, 255, 255, 63, 191, 32, 255, 255, 255, 255, 255, 247, - 255, 61, 127, 61, 255, 61, 255, 255, 255, 255, 61, 127, 61, 255, 127, 255, - 255, 255, 61, 255, 255, 255, 0, 0, 255, 255, 31, 0, 255, 159, 255, 255, - 255, 199, 1, 0, 255, 223, 31, 0, 255, 255, 15, 0, 255, 223, 13, 0, - 255, 255, 143, 48, 255, 3, 0, 0, 0, 56, 255, 3, 255, 255, 255, 0, - 255, 7, 255, 255, 255, 255, 63, 0, 255, 15, 255, 15, 192, 255, 255, 255, - 255, 63, 31, 0, 255, 15, 255, 255, 255, 3, 255, 3, 255, 255, 255, 127, - 255, 255, 255, 159, 128, 0, 0, 0, 255, 15, 255, 3, 0, 248, 15, 0, - 255, 227, 255, 255, 0, 0, 247, 255, 255, 255, 127, 0, 127, 0, 0, 240, - 255, 255, 63, 63, 63, 63, 255, 170, 255, 255, 223, 95, 220, 31, 207, 15, - 255, 31, 220, 31, 0, 48, 0, 0, 0, 0, 0, 128, 1, 0, 16, 0, - 0, 0, 2, 128, 0, 0, 255, 31, 255, 255, 1, 0, 132, 252, 47, 62, - 80, 189, 255, 243, 224, 67, 0, 0, 255, 1, 0, 0, 0, 0, 192, 255, - 255, 127, 255, 255, 31, 248, 15, 0, 255, 128, 0, 128, 127, 127, 127, 127, - 0, 128, 0, 0, 224, 0, 0, 0, 254, 255, 62, 31, 255, 255, 127, 230, - 224, 255, 255, 255, 255, 63, 254, 255, 255, 127, 0, 0, 255, 31, 0, 0, - 255, 31, 255, 255, 255, 15, 0, 0, 255, 255, 247, 191, 255, 255, 255, 128, - 0, 0, 128, 255, 252, 255, 255, 255, 255, 121, 15, 0, 255, 7, 0, 0, - 0, 0, 0, 255, 255, 0, 0, 0, 31, 0, 255, 3, 255, 255, 255, 8, - 255, 63, 255, 255, 1, 128, 255, 3, 255, 63, 255, 3, 255, 255, 127, 12, - 7, 0, 0, 56, 255, 255, 124, 0, 126, 126, 126, 0, 127, 127, 0, 0, - 255, 55, 255, 3, 15, 0, 255, 255, 127, 248, 255, 255, 255, 255, 255, 3, - 127, 0, 248, 224, 255, 253, 127, 95, 219, 255, 255, 255, 0, 0, 248, 255, - 255, 255, 252, 255, 0, 0, 255, 15, 127, 0, 24, 0, 0, 224, 0, 0, - 0, 0, 223, 255, 252, 252, 252, 28, 255, 239, 255, 255, 127, 255, 255, 183, - 255, 63, 255, 63, 0, 0, 0, 32, 15, 255, 62, 0, 63, 253, 255, 255, - 255, 255, 191, 145, 255, 255, 255, 192, 111, 240, 239, 254, 255, 255, 15, 135, - 255, 255, 7, 0, 127, 0, 0, 0, 255, 1, 255, 3, 255, 255, 223, 255, - 7, 0, 0, 0, 255, 255, 255, 1, 31, 0, 255, 255, 0, 128, 255, 255, - 3, 0, 0, 0, 224, 227, 7, 248, 231, 15, 0, 0, 0, 60, 0, 0, - 28, 0, 0, 0, 255, 255, 255, 223, 100, 222, 255, 235, 239, 255, 255, 255, - 191, 231, 223, 223, 255, 255, 255, 123, 95, 252, 253, 255, 63, 255, 255, 255, - 253, 255, 255, 247, 255, 253, 255, 255, 247, 207, 255, 255, 150, 254, 247, 10, - 132, 234, 150, 170, 150, 247, 247, 94, 255, 251, 255, 15, 238, 251, 255, 15, -}; - -/* Word: 1906 bytes. */ - -RE_UINT32 re_get_word(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 15; - code = ch ^ (f << 15); - pos = (RE_UINT32)re_word_stage_1[f] << 4; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_word_stage_2[pos + f] << 3; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_word_stage_3[pos + f] << 3; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_word_stage_4[pos + f] << 5; - pos += code; - value = (re_word_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* XDigit. */ - -static RE_UINT8 re_xdigit_stage_1[] = { - 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, -}; - -static RE_UINT8 re_xdigit_stage_2[] = { - 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 5, 6, 4, 4, 4, 4, 4, 4, 4, 4, 4, 7, - 8, 4, 9, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 10, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, - 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, -}; - -static RE_UINT8 re_xdigit_stage_3[] = { - 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 1, 4, - 1, 1, 5, 5, 5, 5, 5, 5, 5, 5, 5, 1, 6, 6, 7, 1, - 4, 8, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, - 8, 1, 9, 6, 1, 10, 6, 11, 12, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, 1, 1, 1, - 1, 6, 13, 6, 6, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 14, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 7, 1, 1, 1, 1, 1, 1, - 5, 3, 15, 6, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 16, -}; - -static RE_UINT8 re_xdigit_stage_4[] = { - 0, 1, 2, 2, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 1, - 0, 0, 3, 0, 0, 0, 0, 4, 0, 0, 1, 0, 0, 3, 0, 0, - 1, 0, 0, 0, 0, 0, 4, 0, 5, 0, 0, 0, 0, 1, 0, 0, - 0, 0, 5, 0, 3, 0, 0, 0, 1, 2, 2, 0, 0, 6, 0, 0, - 0, 0, 7, 8, -}; - -static RE_UINT8 re_xdigit_stage_5[] = { - 0, 0, 0, 0, 0, 0, 255, 3, 126, 0, 0, 0, 255, 3, 0, 0, - 192, 255, 0, 0, 255, 3, 255, 3, 0, 0, 192, 255, 0, 192, 255, 255, - 255, 255, 255, 255, -}; - -/* XDigit: 393 bytes. */ - -RE_UINT32 re_get_xdigit(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - - f = ch >> 16; - code = ch ^ (f << 16); - pos = (RE_UINT32)re_xdigit_stage_1[f] << 5; - f = code >> 11; - code ^= f << 11; - pos = (RE_UINT32)re_xdigit_stage_2[pos + f] << 4; - f = code >> 7; - code ^= f << 7; - pos = (RE_UINT32)re_xdigit_stage_3[pos + f] << 2; - f = code >> 5; - code ^= f << 5; - pos = (RE_UINT32)re_xdigit_stage_4[pos + f] << 5; - pos += code; - value = (re_xdigit_stage_5[pos >> 3] >> (pos & 0x7)) & 0x1; - - return value; -} - -/* All_Cases. */ - -static RE_UINT8 re_all_cases_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 4, 5, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_all_cases_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, 10, - 6, 11, 6, 6, 12, 6, 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 15, 16, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 17, 6, 6, 6, 18, - 6, 6, 6, 6, 19, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, -}; - -static RE_UINT8 re_all_cases_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, - 0, 0, 0, 0, 0, 0, 9, 0, 10, 11, 12, 13, 14, 15, 16, 17, - 18, 18, 18, 18, 18, 18, 19, 20, 21, 22, 18, 18, 18, 18, 18, 23, - 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 21, 34, 18, 18, 35, 18, - 18, 18, 18, 18, 36, 18, 37, 38, 39, 18, 40, 41, 42, 43, 44, 45, - 46, 47, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 49, 0, 0, 0, 0, 0, 50, 51, - 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 18, 18, 18, 63, 64, - 65, 65, 11, 11, 11, 11, 15, 15, 15, 15, 66, 66, 18, 18, 18, 18, - 67, 68, 18, 18, 18, 18, 18, 18, 69, 70, 18, 18, 18, 18, 18, 18, - 18, 18, 18, 18, 18, 0, 71, 72, 72, 72, 73, 0, 74, 75, 75, 75, - 76, 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, 0, 0, 0, 77, 77, 77, 77, 78, 79, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 80, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 81, 18, 18, 18, - 18, 18, 82, 83, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, - 84, 85, 86, 87, 84, 85, 84, 85, 86, 87, 88, 89, 84, 85, 90, 91, - 84, 85, 84, 85, 84, 85, 92, 93, 94, 95, 96, 97, 98, 99, 94, 100, - 0, 0, 0, 0, 101, 102, 103, 0, 0, 104, 0, 0, 105, 105, 106, 106, - 107, 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, 108, 109, 109, 109, 110, 110, 110, 111, 0, 0, - 72, 72, 72, 72, 72, 73, 75, 75, 75, 75, 75, 76, 112, 113, 114, 115, - 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 37, 116, 117, 0, - 118, 118, 118, 118, 119, 120, 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, 18, 18, 18, 18, 18, 82, 0, 0, - 18, 18, 18, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 68, 18, 68, 18, 18, 18, 18, 18, 18, 18, 0, 121, - 18, 122, 37, 0, 18, 123, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 124, 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, 1, 11, 11, 4, 5, 15, 15, 8, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 125, 125, 125, 125, 125, 126, 126, 126, 126, 126, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -}; - -static RE_UINT8 re_all_cases_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, - 1, 2, 1, 3, 1, 1, 1, 1, 1, 1, 1, 4, 1, 1, 1, 1, - 1, 1, 1, 0, 0, 0, 0, 0, 0, 5, 5, 5, 5, 5, 5, 5, - 5, 6, 5, 7, 5, 5, 5, 5, 5, 5, 5, 8, 5, 5, 5, 5, - 5, 5, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 0, 0, - 1, 1, 1, 1, 1, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 11, - 5, 5, 5, 5, 5, 12, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, - 5, 5, 5, 5, 5, 5, 5, 0, 5, 5, 5, 5, 5, 5, 5, 13, - 14, 15, 14, 15, 14, 15, 14, 15, 16, 17, 14, 15, 14, 15, 14, 15, - 0, 14, 15, 14, 15, 14, 15, 14, 15, 14, 15, 14, 15, 14, 15, 14, - 15, 0, 14, 15, 14, 15, 14, 15, 18, 14, 15, 14, 15, 14, 15, 19, - 20, 21, 14, 15, 14, 15, 22, 14, 15, 23, 23, 14, 15, 0, 24, 25, - 26, 14, 15, 23, 27, 28, 29, 30, 14, 15, 31, 0, 29, 32, 33, 34, - 14, 15, 14, 15, 14, 15, 35, 14, 15, 35, 0, 0, 14, 15, 35, 14, - 15, 36, 36, 14, 15, 14, 15, 37, 14, 15, 0, 0, 14, 15, 0, 38, - 0, 0, 0, 0, 39, 40, 41, 39, 40, 41, 39, 40, 41, 14, 15, 14, - 15, 14, 15, 14, 15, 42, 14, 15, 0, 39, 40, 41, 14, 15, 43, 44, - 45, 0, 14, 15, 14, 15, 14, 15, 14, 15, 14, 15, 0, 0, 0, 0, - 0, 0, 46, 14, 15, 47, 48, 49, 49, 14, 15, 50, 51, 52, 14, 15, - 53, 54, 55, 56, 57, 0, 58, 58, 0, 59, 0, 60, 0, 0, 0, 0, - 58, 0, 0, 61, 0, 62, 63, 0, 64, 65, 0, 66, 0, 0, 0, 65, - 0, 67, 68, 0, 0, 69, 0, 0, 0, 0, 0, 0, 0, 70, 0, 0, - 71, 0, 0, 71, 0, 0, 0, 0, 71, 72, 73, 73, 74, 0, 0, 0, - 0, 0, 75, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 76, 0, 0, - 14, 15, 14, 15, 0, 0, 14, 15, 0, 0, 0, 33, 33, 33, 0, 0, - 0, 0, 0, 0, 0, 0, 77, 0, 78, 78, 78, 0, 79, 0, 80, 80, - 81, 1, 82, 1, 1, 83, 1, 1, 84, 85, 86, 1, 87, 1, 1, 1, - 88, 89, 0, 90, 1, 1, 91, 1, 1, 92, 1, 1, 93, 94, 94, 94, - 95, 5, 96, 5, 5, 97, 5, 5, 98, 99, 100, 5, 101, 5, 5, 5, - 102, 103, 104, 105, 5, 5, 106, 5, 5, 107, 5, 5, 108, 109, 109, 110, - 111, 112, 0, 0, 0, 113, 114, 115, 116, 117, 118, 0, 119, 120, 0, 14, - 15, 121, 14, 15, 0, 45, 45, 45, 122, 122, 122, 122, 122, 122, 122, 122, - 123, 123, 123, 123, 123, 123, 123, 123, 14, 15, 0, 0, 0, 0, 0, 0, - 0, 0, 14, 15, 14, 15, 14, 15, 124, 14, 15, 14, 15, 14, 15, 14, - 15, 14, 15, 14, 15, 14, 15, 125, 0, 126, 126, 126, 126, 126, 126, 126, - 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 126, 0, - 0, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, - 127, 127, 127, 127, 127, 127, 127, 0, 128, 128, 128, 128, 128, 128, 128, 128, - 128, 128, 128, 128, 128, 128, 0, 128, 0, 0, 0, 0, 0, 128, 0, 0, - 0, 129, 0, 0, 0, 130, 0, 0, 131, 132, 14, 15, 14, 15, 14, 15, - 14, 15, 14, 15, 14, 15, 0, 0, 0, 0, 0, 133, 0, 0, 134, 0, - 110, 110, 110, 110, 110, 110, 110, 110, 115, 115, 115, 115, 115, 115, 115, 115, - 110, 110, 110, 110, 110, 110, 0, 0, 115, 115, 115, 115, 115, 115, 0, 0, - 0, 110, 0, 110, 0, 110, 0, 110, 0, 115, 0, 115, 0, 115, 0, 115, - 135, 135, 136, 136, 136, 136, 137, 137, 138, 138, 139, 139, 140, 140, 0, 0, - 110, 110, 0, 141, 0, 0, 0, 0, 115, 115, 142, 142, 143, 0, 144, 0, - 0, 0, 0, 141, 0, 0, 0, 0, 145, 145, 145, 145, 143, 0, 0, 0, - 110, 110, 0, 146, 0, 0, 0, 0, 115, 115, 147, 147, 0, 0, 0, 0, - 110, 110, 0, 148, 0, 118, 0, 0, 115, 115, 149, 149, 121, 0, 0, 0, - 150, 150, 151, 151, 143, 0, 0, 0, 0, 0, 0, 0, 0, 0, 152, 0, - 0, 0, 153, 154, 0, 0, 0, 0, 0, 0, 155, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 156, 0, 157, 157, 157, 157, 157, 157, 157, 157, - 158, 158, 158, 158, 158, 158, 158, 158, 0, 0, 0, 14, 15, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 159, 159, 159, 159, 159, 159, 159, 159, 159, 159, - 160, 160, 160, 160, 160, 160, 160, 160, 160, 160, 0, 0, 0, 0, 0, 0, - 14, 15, 161, 162, 163, 164, 165, 14, 15, 14, 15, 14, 15, 166, 167, 168, - 169, 0, 14, 15, 0, 14, 15, 0, 0, 0, 0, 0, 0, 0, 170, 170, - 0, 0, 0, 14, 15, 14, 15, 0, 0, 0, 14, 15, 0, 0, 0, 0, - 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 171, 0, 171, - 0, 0, 0, 0, 0, 171, 0, 0, 0, 14, 15, 14, 15, 172, 14, 15, - 0, 0, 0, 14, 15, 173, 0, 0, 14, 15, 174, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 14, 15, 0, 175, 175, 175, 175, 175, 175, 175, 175, - 176, 176, 176, 176, 176, 176, 176, 176, -}; - -/* All_Cases: 1984 bytes. */ - -static RE_AllCases re_all_cases_table[] = { - {{ 0, 0, 0}}, - {{ 32, 0, 0}}, - {{ 32, 232, 0}}, - {{ 32, 8415, 0}}, - {{ 32, 300, 0}}, - {{ -32, 0, 0}}, - {{ -32, 199, 0}}, - {{ -32, 8383, 0}}, - {{ -32, 268, 0}}, - {{ 743, 775, 0}}, - {{ 32, 8294, 0}}, - {{ 7615, 0, 0}}, - {{ -32, 8262, 0}}, - {{ 121, 0, 0}}, - {{ 1, 0, 0}}, - {{ -1, 0, 0}}, - {{ -199, 0, 0}}, - {{ -232, 0, 0}}, - {{ -121, 0, 0}}, - {{ -300, -268, 0}}, - {{ 195, 0, 0}}, - {{ 210, 0, 0}}, - {{ 206, 0, 0}}, - {{ 205, 0, 0}}, - {{ 79, 0, 0}}, - {{ 202, 0, 0}}, - {{ 203, 0, 0}}, - {{ 207, 0, 0}}, - {{ 97, 0, 0}}, - {{ 211, 0, 0}}, - {{ 209, 0, 0}}, - {{ 163, 0, 0}}, - {{ 213, 0, 0}}, - {{ 130, 0, 0}}, - {{ 214, 0, 0}}, - {{ 218, 0, 0}}, - {{ 217, 0, 0}}, - {{ 219, 0, 0}}, - {{ 56, 0, 0}}, - {{ 1, 2, 0}}, - {{ -1, 1, 0}}, - {{ -2, -1, 0}}, - {{ -79, 0, 0}}, - {{ -97, 0, 0}}, - {{ -56, 0, 0}}, - {{ -130, 0, 0}}, - {{ 10795, 0, 0}}, - {{ -163, 0, 0}}, - {{ 10792, 0, 0}}, - {{ 10815, 0, 0}}, - {{ -195, 0, 0}}, - {{ 69, 0, 0}}, - {{ 71, 0, 0}}, - {{ 10783, 0, 0}}, - {{ 10780, 0, 0}}, - {{ 10782, 0, 0}}, - {{ -210, 0, 0}}, - {{ -206, 0, 0}}, - {{ -205, 0, 0}}, - {{ -202, 0, 0}}, - {{ -203, 0, 0}}, - {{ -207, 0, 0}}, - {{ 42280, 0, 0}}, - {{ 42308, 0, 0}}, - {{ -209, 0, 0}}, - {{ -211, 0, 0}}, - {{ 10743, 0, 0}}, - {{ 10749, 0, 0}}, - {{ -213, 0, 0}}, - {{ -214, 0, 0}}, - {{ 10727, 0, 0}}, - {{ -218, 0, 0}}, - {{ -69, 0, 0}}, - {{ -217, 0, 0}}, - {{ -71, 0, 0}}, - {{ -219, 0, 0}}, - {{ 84, 116, 7289}}, - {{ 38, 0, 0}}, - {{ 37, 0, 0}}, - {{ 64, 0, 0}}, - {{ 63, 0, 0}}, - {{ 7235, 0, 0}}, - {{ 32, 62, 0}}, - {{ 32, 96, 0}}, - {{ 32, 57, 92}}, - {{ -84, 32, 7205}}, - {{ 32, 86, 0}}, - {{ -743, 32, 0}}, - {{ 32, 54, 0}}, - {{ 32, 80, 0}}, - {{ 31, 32, 0}}, - {{ 32, 47, 0}}, - {{ 32, 7549, 0}}, - {{ -38, 0, 0}}, - {{ -37, 0, 0}}, - {{ 7219, 0, 0}}, - {{ -32, 30, 0}}, - {{ -32, 64, 0}}, - {{ -32, 25, 60}}, - {{ -116, -32, 7173}}, - {{ -32, 54, 0}}, - {{ -775, -32, 0}}, - {{ -32, 22, 0}}, - {{ -32, 48, 0}}, - {{ -31, 1, 0}}, - {{ -32, -1, 0}}, - {{ -32, 15, 0}}, - {{ -32, 7517, 0}}, - {{ -64, 0, 0}}, - {{ -63, 0, 0}}, - {{ 8, 0, 0}}, - {{ -62, -30, 0}}, - {{ -57, -25, 35}}, - {{ -47, -15, 0}}, - {{ -54, -22, 0}}, - {{ -8, 0, 0}}, - {{ -86, -54, 0}}, - {{ -80, -48, 0}}, - {{ 7, 0, 0}}, - {{ -92, -60, -35}}, - {{ -96, -64, 0}}, - {{ -7, 0, 0}}, - {{ 80, 0, 0}}, - {{ -80, 0, 0}}, - {{ 15, 0, 0}}, - {{ -15, 0, 0}}, - {{ 48, 0, 0}}, - {{ -48, 0, 0}}, - {{ 7264, 0, 0}}, - {{ 35332, 0, 0}}, - {{ 3814, 0, 0}}, - {{ 1, 59, 0}}, - {{ -1, 58, 0}}, - {{ -59, -58, 0}}, - {{ -7615, 0, 0}}, - {{ 74, 0, 0}}, - {{ 86, 0, 0}}, - {{ 100, 0, 0}}, - {{ 128, 0, 0}}, - {{ 112, 0, 0}}, - {{ 126, 0, 0}}, - {{ 9, 0, 0}}, - {{ -74, 0, 0}}, - {{ -9, 0, 0}}, - {{ -7289, -7205, -7173}}, - {{ -86, 0, 0}}, - {{ -7235, 0, 0}}, - {{ -100, 0, 0}}, - {{ -7219, 0, 0}}, - {{ -112, 0, 0}}, - {{ -128, 0, 0}}, - {{ -126, 0, 0}}, - {{ -7549, -7517, 0}}, - {{ -8415, -8383, 0}}, - {{ -8294, -8262, 0}}, - {{ 28, 0, 0}}, - {{ -28, 0, 0}}, - {{ 16, 0, 0}}, - {{ -16, 0, 0}}, - {{ 26, 0, 0}}, - {{ -26, 0, 0}}, - {{-10743, 0, 0}}, - {{ -3814, 0, 0}}, - {{-10727, 0, 0}}, - {{-10795, 0, 0}}, - {{-10792, 0, 0}}, - {{-10780, 0, 0}}, - {{-10749, 0, 0}}, - {{-10783, 0, 0}}, - {{-10782, 0, 0}}, - {{-10815, 0, 0}}, - {{ -7264, 0, 0}}, - {{-35332, 0, 0}}, - {{-42280, 0, 0}}, - {{-42308, 0, 0}}, - {{ 40, 0, 0}}, - {{ -40, 0, 0}}, -}; - -/* All_Cases: 2124 bytes. */ - -int re_get_all_cases(RE_UINT32 ch, RE_UINT32* codepoints) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - RE_AllCases* all_cases; - int count; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_all_cases_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_all_cases_stage_2[pos + f] << 5; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_all_cases_stage_3[pos + f] << 3; - value = re_all_cases_stage_4[pos + code]; - - all_cases = &re_all_cases_table[value]; - - codepoints[0] = ch; - count = 1; - - while (count < RE_MAX_CASES && all_cases->diffs[count - 1] != 0) { - codepoints[count] = (RE_UINT32)((RE_INT32)ch + all_cases->diffs[count - - 1]); - ++count; - } - - return count; -} - -/* Simple_Case_Folding. */ - -static RE_UINT8 re_simple_case_folding_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 4, 5, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_simple_case_folding_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, - 6, 10, 6, 6, 11, 6, 6, 6, 6, 6, 6, 6, 12, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 15, - 6, 6, 6, 6, 16, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, -}; - -static RE_UINT8 re_simple_case_folding_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 3, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 4, 0, 2, 2, 5, 5, 0, 0, 0, 0, - 6, 6, 6, 6, 6, 6, 7, 8, 8, 7, 6, 6, 6, 6, 6, 9, - 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 8, 20, 6, 6, 21, 6, - 6, 6, 6, 6, 22, 6, 23, 24, 25, 6, 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, 26, 0, 0, 0, 0, 0, 27, 0, - 28, 29, 1, 2, 30, 31, 0, 0, 32, 33, 34, 6, 6, 6, 35, 36, - 37, 37, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, 6, 6, 6, 6, - 38, 7, 6, 6, 6, 6, 6, 6, 39, 40, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 0, 41, 42, 42, 42, 43, 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, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 44, 44, 44, 44, 45, 46, 0, 0, 0, 0, 0, 0, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 47, 48, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 0, 49, 0, 50, 0, 49, 0, 49, 0, 50, 0, 51, 0, 49, 0, 0, - 0, 49, 0, 49, 0, 49, 0, 52, 0, 53, 0, 54, 0, 55, 0, 56, - 0, 0, 0, 0, 57, 58, 59, 0, 0, 0, 0, 0, 60, 60, 0, 0, - 61, 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, 62, 63, 63, 63, 0, 0, 0, 0, 0, 0, - 42, 42, 42, 42, 42, 43, 0, 0, 0, 0, 0, 0, 64, 65, 66, 67, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 23, 68, 32, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 6, 6, 6, 6, 6, 47, 0, 0, - 6, 6, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 7, 6, 7, 6, 6, 6, 6, 6, 6, 6, 0, 69, - 6, 70, 23, 0, 6, 71, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 1, 2, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 72, 72, 72, 72, 72, 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, -}; - -static RE_UINT8 re_simple_case_folding_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, - 3, 0, 3, 0, 3, 0, 3, 0, 0, 0, 3, 0, 3, 0, 3, 0, - 0, 3, 0, 3, 0, 3, 0, 3, 4, 3, 0, 3, 0, 3, 0, 5, - 0, 6, 3, 0, 3, 0, 7, 3, 0, 8, 8, 3, 0, 0, 9, 10, - 11, 3, 0, 8, 12, 0, 13, 14, 3, 0, 0, 0, 13, 15, 0, 16, - 3, 0, 3, 0, 3, 0, 17, 3, 0, 17, 0, 0, 3, 0, 17, 3, - 0, 18, 18, 3, 0, 3, 0, 19, 3, 0, 0, 0, 3, 0, 0, 0, - 0, 0, 0, 0, 20, 3, 0, 20, 3, 0, 20, 3, 0, 3, 0, 3, - 0, 3, 0, 3, 0, 0, 3, 0, 0, 20, 3, 0, 3, 0, 21, 22, - 23, 0, 3, 0, 3, 0, 3, 0, 3, 0, 3, 0, 0, 0, 0, 0, - 0, 0, 24, 3, 0, 25, 26, 0, 0, 3, 0, 27, 28, 29, 3, 0, - 0, 0, 0, 0, 0, 30, 0, 0, 3, 0, 3, 0, 0, 0, 3, 0, - 0, 0, 0, 0, 0, 0, 31, 0, 32, 32, 32, 0, 33, 0, 34, 34, - 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, - 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 35, - 36, 37, 0, 0, 0, 38, 39, 0, 40, 41, 0, 0, 42, 43, 0, 3, - 0, 44, 3, 0, 0, 23, 23, 23, 45, 45, 45, 45, 45, 45, 45, 45, - 3, 0, 0, 0, 0, 0, 0, 0, 46, 3, 0, 3, 0, 3, 0, 3, - 0, 3, 0, 3, 0, 3, 0, 0, 0, 47, 47, 47, 47, 47, 47, 47, - 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 47, 0, - 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 0, 48, - 0, 0, 0, 0, 0, 48, 0, 0, 3, 0, 3, 0, 3, 0, 0, 0, - 0, 0, 0, 49, 0, 0, 50, 0, 51, 51, 51, 51, 51, 51, 51, 51, - 51, 51, 51, 51, 51, 51, 0, 0, 0, 51, 0, 51, 0, 51, 0, 51, - 51, 51, 52, 52, 53, 0, 54, 0, 55, 55, 55, 55, 53, 0, 0, 0, - 51, 51, 56, 56, 0, 0, 0, 0, 51, 51, 57, 57, 44, 0, 0, 0, - 58, 58, 59, 59, 53, 0, 0, 0, 0, 0, 0, 0, 0, 0, 60, 0, - 0, 0, 61, 62, 0, 0, 0, 0, 0, 0, 63, 0, 0, 0, 0, 0, - 64, 64, 64, 64, 64, 64, 64, 64, 0, 0, 0, 3, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, - 3, 0, 66, 67, 68, 0, 0, 3, 0, 3, 0, 3, 0, 69, 70, 71, - 72, 0, 3, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 73, 73, - 0, 0, 0, 3, 0, 3, 0, 0, 0, 3, 0, 3, 0, 74, 3, 0, - 0, 0, 0, 3, 0, 75, 0, 0, 3, 0, 76, 0, 0, 0, 0, 0, - 77, 77, 77, 77, 77, 77, 77, 77, -}; - -/* Simple_Case_Folding: 1456 bytes. */ - -static RE_INT32 re_simple_case_folding_table[] = { - 0, - 32, - 775, - 1, - -121, - -268, - 210, - 206, - 205, - 79, - 202, - 203, - 207, - 211, - 209, - 213, - 214, - 218, - 217, - 219, - 2, - -97, - -56, - -130, - 10795, - -163, - 10792, - -195, - 69, - 71, - 116, - 38, - 37, - 64, - 63, - 8, - -30, - -25, - -15, - -22, - -54, - -48, - -60, - -64, - -7, - 80, - 15, - 48, - 7264, - -58, - -7615, - -8, - -74, - -9, - -7173, - -86, - -100, - -112, - -128, - -126, - -7517, - -8383, - -8262, - 28, - 16, - 26, - -10743, - -3814, - -10727, - -10780, - -10749, - -10783, - -10782, - -10815, - -35332, - -42280, - -42308, - 40, -}; - -/* Simple_Case_Folding: 312 bytes. */ - -RE_UINT32 re_get_simple_case_folding(RE_UINT32 ch) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - RE_INT32 diff; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_simple_case_folding_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_simple_case_folding_stage_2[pos + f] << 5; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_simple_case_folding_stage_3[pos + f] << 3; - value = re_simple_case_folding_stage_4[pos + code]; - - diff = re_simple_case_folding_table[value]; - - return (RE_UINT32)((RE_INT32)ch + diff); -} - -/* Full_Case_Folding. */ - -static RE_UINT8 re_full_case_folding_stage_1[] = { - 0, 1, 2, 2, 2, 3, 2, 4, 5, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, -}; - -static RE_UINT8 re_full_case_folding_stage_2[] = { - 0, 1, 2, 3, 4, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 7, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 8, 9, - 6, 10, 6, 6, 11, 6, 6, 6, 6, 6, 6, 6, 12, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 13, 14, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 15, 6, 6, 6, 16, - 6, 6, 6, 6, 17, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, - 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, -}; - -static RE_UINT8 re_full_case_folding_stage_3[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 2, 3, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 4, 0, 2, 2, 5, 6, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 8, 9, 9, 10, 7, 7, 7, 7, 7, 11, - 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 9, 22, 7, 7, 23, 7, - 7, 7, 7, 7, 24, 7, 25, 26, 27, 7, 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, 28, 0, 0, 0, 0, 0, 29, 0, - 30, 31, 32, 2, 33, 34, 35, 0, 36, 37, 38, 7, 7, 7, 39, 40, - 41, 41, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, - 42, 43, 7, 7, 7, 7, 7, 7, 44, 45, 7, 7, 7, 7, 7, 7, - 7, 7, 7, 7, 7, 0, 46, 47, 47, 47, 48, 0, 0, 0, 0, 0, - 49, 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, 0, 0, 0, 50, 50, 50, 50, 51, 52, 0, 0, 0, 0, 0, 0, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 7, 7, 53, 54, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, - 0, 55, 0, 56, 0, 55, 0, 55, 0, 56, 57, 58, 0, 55, 0, 0, - 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, - 0, 0, 0, 0, 75, 76, 77, 0, 0, 0, 0, 0, 78, 78, 0, 0, - 79, 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, 80, 81, 81, 81, 0, 0, 0, 0, 0, 0, - 47, 47, 47, 47, 47, 48, 0, 0, 0, 0, 0, 0, 82, 83, 84, 85, - 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 25, 86, 36, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 7, 7, 7, 7, 7, 87, 0, 0, - 7, 7, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 43, 7, 43, 7, 7, 7, 7, 7, 7, 7, 0, 88, - 7, 89, 25, 0, 7, 90, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 91, 0, 92, 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, 1, 2, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 93, 93, 93, 93, 93, 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, -}; - -static RE_UINT8 re_full_case_folding_stage_4[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, - 1, 1, 1, 1, 1, 1, 1, 3, 4, 0, 4, 0, 4, 0, 4, 0, - 5, 0, 4, 0, 4, 0, 4, 0, 0, 4, 0, 4, 0, 4, 0, 4, - 0, 6, 4, 0, 4, 0, 4, 0, 7, 4, 0, 4, 0, 4, 0, 8, - 0, 9, 4, 0, 4, 0, 10, 4, 0, 11, 11, 4, 0, 0, 12, 13, - 14, 4, 0, 11, 15, 0, 16, 17, 4, 0, 0, 0, 16, 18, 0, 19, - 4, 0, 4, 0, 4, 0, 20, 4, 0, 20, 0, 0, 4, 0, 20, 4, - 0, 21, 21, 4, 0, 4, 0, 22, 4, 0, 0, 0, 4, 0, 0, 0, - 0, 0, 0, 0, 23, 4, 0, 23, 4, 0, 23, 4, 0, 4, 0, 4, - 0, 4, 0, 4, 0, 0, 4, 0, 24, 23, 4, 0, 4, 0, 25, 26, - 27, 0, 4, 0, 4, 0, 4, 0, 4, 0, 4, 0, 0, 0, 0, 0, - 0, 0, 28, 4, 0, 29, 30, 0, 0, 4, 0, 31, 32, 33, 4, 0, - 0, 0, 0, 0, 0, 34, 0, 0, 4, 0, 4, 0, 0, 0, 4, 0, - 0, 0, 0, 0, 0, 0, 35, 0, 36, 36, 36, 0, 37, 0, 38, 38, - 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 0, 0, 0, 0, 40, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 41, - 42, 43, 0, 0, 0, 44, 45, 0, 46, 47, 0, 0, 48, 49, 0, 4, - 0, 50, 4, 0, 0, 27, 27, 27, 51, 51, 51, 51, 51, 51, 51, 51, - 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 4, 0, 4, 0, - 52, 4, 0, 4, 0, 4, 0, 4, 0, 4, 0, 4, 0, 4, 0, 0, - 0, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, - 53, 53, 53, 53, 53, 53, 53, 0, 0, 0, 0, 0, 0, 0, 0, 54, - 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 55, 0, 55, - 0, 0, 0, 0, 0, 55, 0, 0, 4, 0, 4, 0, 4, 0, 56, 57, - 58, 59, 60, 61, 0, 0, 62, 0, 63, 63, 63, 63, 63, 63, 63, 63, - 63, 63, 63, 63, 63, 63, 0, 0, 64, 0, 65, 0, 66, 0, 67, 0, - 0, 63, 0, 63, 0, 63, 0, 63, 68, 68, 68, 68, 68, 68, 68, 68, - 69, 69, 69, 69, 69, 69, 69, 69, 70, 70, 70, 70, 70, 70, 70, 70, - 71, 71, 71, 71, 71, 71, 71, 71, 72, 72, 72, 72, 72, 72, 72, 72, - 73, 73, 73, 73, 73, 73, 73, 73, 0, 0, 74, 75, 76, 0, 77, 78, - 63, 63, 79, 79, 80, 0, 81, 0, 0, 0, 82, 83, 84, 0, 85, 86, - 87, 87, 87, 87, 88, 0, 0, 0, 0, 0, 89, 90, 0, 0, 91, 92, - 63, 63, 93, 93, 0, 0, 0, 0, 0, 0, 94, 95, 96, 0, 97, 98, - 63, 63, 99, 99, 50, 0, 0, 0, 0, 0, 100, 101, 102, 0, 103, 104, - 105, 105, 106, 106, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 108, 0, - 0, 0, 109, 110, 0, 0, 0, 0, 0, 0, 111, 0, 0, 0, 0, 0, - 112, 112, 112, 112, 112, 112, 112, 112, 0, 0, 0, 4, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, - 4, 0, 114, 115, 116, 0, 0, 4, 0, 4, 0, 4, 0, 117, 118, 119, - 120, 0, 4, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 121, 121, - 0, 0, 0, 4, 0, 4, 0, 0, 4, 0, 4, 0, 4, 0, 0, 0, - 0, 4, 0, 4, 0, 122, 4, 0, 0, 0, 0, 4, 0, 123, 0, 0, - 4, 0, 124, 0, 0, 0, 0, 0, 125, 126, 127, 128, 129, 130, 131, 0, - 0, 0, 0, 132, 133, 134, 135, 136, 137, 137, 137, 137, 137, 137, 137, 137, -}; - -/* Full_Case_Folding: 1656 bytes. */ - -static RE_FullCaseFolding re_full_case_folding_table[] = { - { 0, { 0, 0}}, - { 32, { 0, 0}}, - { 775, { 0, 0}}, - { -108, { 115, 0}}, - { 1, { 0, 0}}, - { -199, { 775, 0}}, - { 371, { 110, 0}}, - { -121, { 0, 0}}, - { -268, { 0, 0}}, - { 210, { 0, 0}}, - { 206, { 0, 0}}, - { 205, { 0, 0}}, - { 79, { 0, 0}}, - { 202, { 0, 0}}, - { 203, { 0, 0}}, - { 207, { 0, 0}}, - { 211, { 0, 0}}, - { 209, { 0, 0}}, - { 213, { 0, 0}}, - { 214, { 0, 0}}, - { 218, { 0, 0}}, - { 217, { 0, 0}}, - { 219, { 0, 0}}, - { 2, { 0, 0}}, - { -390, { 780, 0}}, - { -97, { 0, 0}}, - { -56, { 0, 0}}, - { -130, { 0, 0}}, - { 10795, { 0, 0}}, - { -163, { 0, 0}}, - { 10792, { 0, 0}}, - { -195, { 0, 0}}, - { 69, { 0, 0}}, - { 71, { 0, 0}}, - { 116, { 0, 0}}, - { 38, { 0, 0}}, - { 37, { 0, 0}}, - { 64, { 0, 0}}, - { 63, { 0, 0}}, - { 41, { 776, 769}}, - { 21, { 776, 769}}, - { 8, { 0, 0}}, - { -30, { 0, 0}}, - { -25, { 0, 0}}, - { -15, { 0, 0}}, - { -22, { 0, 0}}, - { -54, { 0, 0}}, - { -48, { 0, 0}}, - { -60, { 0, 0}}, - { -64, { 0, 0}}, - { -7, { 0, 0}}, - { 80, { 0, 0}}, - { 15, { 0, 0}}, - { 48, { 0, 0}}, - { -34, {1410, 0}}, - { 7264, { 0, 0}}, - { -7726, { 817, 0}}, - { -7715, { 776, 0}}, - { -7713, { 778, 0}}, - { -7712, { 778, 0}}, - { -7737, { 702, 0}}, - { -58, { 0, 0}}, - { -7723, { 115, 0}}, - { -8, { 0, 0}}, - { -7051, { 787, 0}}, - { -7053, { 787, 768}}, - { -7055, { 787, 769}}, - { -7057, { 787, 834}}, - { -128, { 953, 0}}, - { -136, { 953, 0}}, - { -112, { 953, 0}}, - { -120, { 953, 0}}, - { -64, { 953, 0}}, - { -72, { 953, 0}}, - { -66, { 953, 0}}, - { -7170, { 953, 0}}, - { -7176, { 953, 0}}, - { -7173, { 834, 0}}, - { -7174, { 834, 953}}, - { -74, { 0, 0}}, - { -7179, { 953, 0}}, - { -7173, { 0, 0}}, - { -78, { 953, 0}}, - { -7180, { 953, 0}}, - { -7190, { 953, 0}}, - { -7183, { 834, 0}}, - { -7184, { 834, 953}}, - { -86, { 0, 0}}, - { -7189, { 953, 0}}, - { -7193, { 776, 768}}, - { -7194, { 776, 769}}, - { -7197, { 834, 0}}, - { -7198, { 776, 834}}, - { -100, { 0, 0}}, - { -7197, { 776, 768}}, - { -7198, { 776, 769}}, - { -7203, { 787, 0}}, - { -7201, { 834, 0}}, - { -7202, { 776, 834}}, - { -112, { 0, 0}}, - { -118, { 953, 0}}, - { -7210, { 953, 0}}, - { -7206, { 953, 0}}, - { -7213, { 834, 0}}, - { -7214, { 834, 953}}, - { -128, { 0, 0}}, - { -126, { 0, 0}}, - { -7219, { 953, 0}}, - { -7517, { 0, 0}}, - { -8383, { 0, 0}}, - { -8262, { 0, 0}}, - { 28, { 0, 0}}, - { 16, { 0, 0}}, - { 26, { 0, 0}}, - {-10743, { 0, 0}}, - { -3814, { 0, 0}}, - {-10727, { 0, 0}}, - {-10780, { 0, 0}}, - {-10749, { 0, 0}}, - {-10783, { 0, 0}}, - {-10782, { 0, 0}}, - {-10815, { 0, 0}}, - {-35332, { 0, 0}}, - {-42280, { 0, 0}}, - {-42308, { 0, 0}}, - {-64154, { 102, 0}}, - {-64155, { 105, 0}}, - {-64156, { 108, 0}}, - {-64157, { 102, 105}}, - {-64158, { 102, 108}}, - {-64146, { 116, 0}}, - {-64147, { 116, 0}}, - {-62879, {1398, 0}}, - {-62880, {1381, 0}}, - {-62881, {1387, 0}}, - {-62872, {1398, 0}}, - {-62883, {1389, 0}}, - { 40, { 0, 0}}, -}; - -/* Full_Case_Folding: 1104 bytes. */ - -int re_get_full_case_folding(RE_UINT32 ch, RE_UINT32* codepoints) { - RE_UINT32 code; - RE_UINT32 f; - RE_UINT32 pos; - RE_UINT32 value; - RE_FullCaseFolding* case_folding; - int count; - - f = ch >> 13; - code = ch ^ (f << 13); - pos = (RE_UINT32)re_full_case_folding_stage_1[f] << 5; - f = code >> 8; - code ^= f << 8; - pos = (RE_UINT32)re_full_case_folding_stage_2[pos + f] << 5; - f = code >> 3; - code ^= f << 3; - pos = (RE_UINT32)re_full_case_folding_stage_3[pos + f] << 3; - value = re_full_case_folding_stage_4[pos + code]; - - case_folding = &re_full_case_folding_table[value]; - - codepoints[0] = (RE_UINT32)((RE_INT32)ch + case_folding->diff); - count = 1; - - while (count < RE_MAX_FOLDED && case_folding->codepoints[count - 1] != 0) { - codepoints[count] = case_folding->codepoints[count - 1]; - ++count; - } - - return count; -} - -/* Property function table. */ - -RE_GetPropertyFunc re_get_property[] = { - re_get_general_category, - re_get_block, - re_get_script, - re_get_word_break, - re_get_grapheme_cluster_break, - re_get_sentence_break, - re_get_math, - re_get_alphabetic, - re_get_lowercase, - re_get_uppercase, - re_get_cased, - re_get_case_ignorable, - re_get_changes_when_lowercased, - re_get_changes_when_uppercased, - re_get_changes_when_titlecased, - re_get_changes_when_casefolded, - re_get_changes_when_casemapped, - re_get_id_start, - re_get_id_continue, - re_get_xid_start, - re_get_xid_continue, - re_get_default_ignorable_code_point, - re_get_grapheme_extend, - re_get_grapheme_base, - re_get_grapheme_link, - re_get_white_space, - re_get_bidi_control, - re_get_join_control, - re_get_dash, - re_get_hyphen, - re_get_quotation_mark, - re_get_terminal_punctuation, - re_get_other_math, - re_get_hex_digit, - re_get_ascii_hex_digit, - re_get_other_alphabetic, - re_get_ideographic, - re_get_diacritic, - re_get_extender, - re_get_other_lowercase, - re_get_other_uppercase, - re_get_noncharacter_code_point, - re_get_other_grapheme_extend, - re_get_ids_binary_operator, - re_get_ids_trinary_operator, - re_get_radical, - re_get_unified_ideograph, - re_get_other_default_ignorable_code_point, - re_get_deprecated, - re_get_soft_dotted, - re_get_logical_order_exception, - re_get_other_id_start, - re_get_other_id_continue, - re_get_sterm, - re_get_variation_selector, - re_get_pattern_white_space, - re_get_pattern_syntax, - re_get_hangul_syllable_type, - re_get_bidi_class, - re_get_canonical_combining_class, - re_get_decomposition_type, - re_get_east_asian_width, - re_get_joining_group, - re_get_joining_type, - re_get_line_break, - re_get_numeric_type, - re_get_numeric_value, - re_get_bidi_mirrored, - re_get_indic_matra_category, - re_get_indic_syllabic_category, - re_get_alphanumeric, - re_get_any, - re_get_blank, - re_get_graph, - re_get_print, - re_get_word, - re_get_xdigit, -}; diff --git a/lib/regex/_regex_unicode.h b/lib/regex/_regex_unicode.h deleted file mode 100644 index fa8114be..00000000 --- a/lib/regex/_regex_unicode.h +++ /dev/null @@ -1,218 +0,0 @@ -typedef unsigned char RE_UINT8; -typedef signed char RE_INT8; -typedef unsigned short RE_UINT16; -typedef signed short RE_INT16; -typedef unsigned int RE_UINT32; -typedef signed int RE_INT32; - -typedef unsigned char BOOL; -enum {FALSE, TRUE}; - -#define RE_ASCII_MAX 0x7F -#define RE_LOCALE_MAX 0xFF -#define RE_UNICODE_MAX 0x10FFFF - -#define RE_MAX_CASES 4 -#define RE_MAX_FOLDED 3 - -typedef struct RE_Property { - RE_UINT16 name; - RE_UINT8 id; - RE_UINT8 value_set; -} RE_Property; - -typedef struct RE_PropertyValue { - RE_UINT16 name; - RE_UINT8 value_set; - RE_UINT8 id; -} RE_PropertyValue; - -typedef RE_UINT32 (*RE_GetPropertyFunc)(RE_UINT32 ch); - -#define RE_PROP_GC 0x0 -#define RE_PROP_CASED 0xA -#define RE_PROP_UPPERCASE 0x9 -#define RE_PROP_LOWERCASE 0x8 - -#define RE_PROP_C 30 -#define RE_PROP_L 31 -#define RE_PROP_M 32 -#define RE_PROP_N 33 -#define RE_PROP_P 34 -#define RE_PROP_S 35 -#define RE_PROP_Z 36 -#define RE_PROP_ASSIGNED 38 -#define RE_PROP_CASEDLETTER 37 - -#define RE_PROP_CN 0 -#define RE_PROP_LU 1 -#define RE_PROP_LL 2 -#define RE_PROP_LT 3 -#define RE_PROP_LM 4 -#define RE_PROP_LO 5 -#define RE_PROP_MN 6 -#define RE_PROP_ME 7 -#define RE_PROP_MC 8 -#define RE_PROP_ND 9 -#define RE_PROP_NL 10 -#define RE_PROP_NO 11 -#define RE_PROP_ZS 12 -#define RE_PROP_ZL 13 -#define RE_PROP_ZP 14 -#define RE_PROP_CC 15 -#define RE_PROP_CF 16 -#define RE_PROP_CO 17 -#define RE_PROP_CS 18 -#define RE_PROP_PD 19 -#define RE_PROP_PS 20 -#define RE_PROP_PE 21 -#define RE_PROP_PC 22 -#define RE_PROP_PO 23 -#define RE_PROP_SM 24 -#define RE_PROP_SC 25 -#define RE_PROP_SK 26 -#define RE_PROP_SO 27 -#define RE_PROP_PI 28 -#define RE_PROP_PF 29 - -#define RE_PROP_C_MASK 0x00078001 -#define RE_PROP_L_MASK 0x0000003E -#define RE_PROP_M_MASK 0x000001C0 -#define RE_PROP_N_MASK 0x00000E00 -#define RE_PROP_P_MASK 0x30F80000 -#define RE_PROP_S_MASK 0x0F000000 -#define RE_PROP_Z_MASK 0x00007000 - -#define RE_PROP_ALNUM 0x460001 -#define RE_PROP_ALPHA 0x070001 -#define RE_PROP_ANY 0x470001 -#define RE_PROP_ASCII 0x010001 -#define RE_PROP_BLANK 0x480001 -#define RE_PROP_CNTRL 0x00000F -#define RE_PROP_DIGIT 0x000009 -#define RE_PROP_GRAPH 0x490001 -#define RE_PROP_LOWER 0x080001 -#define RE_PROP_PRINT 0x4A0001 -#define RE_PROP_SPACE 0x190001 -#define RE_PROP_UPPER 0x090001 -#define RE_PROP_WORD 0x4B0001 -#define RE_PROP_XDIGIT 0x4C0001 - -#define RE_BREAK_OTHER 0 -#define RE_BREAK_DOUBLEQUOTE 1 -#define RE_BREAK_SINGLEQUOTE 2 -#define RE_BREAK_HEBREWLETTER 3 -#define RE_BREAK_CR 4 -#define RE_BREAK_LF 5 -#define RE_BREAK_NEWLINE 6 -#define RE_BREAK_EXTEND 7 -#define RE_BREAK_REGIONALINDICATOR 8 -#define RE_BREAK_FORMAT 9 -#define RE_BREAK_KATAKANA 10 -#define RE_BREAK_ALETTER 11 -#define RE_BREAK_MIDLETTER 12 -#define RE_BREAK_MIDNUM 13 -#define RE_BREAK_MIDNUMLET 14 -#define RE_BREAK_NUMERIC 15 -#define RE_BREAK_EXTENDNUMLET 16 - -#define RE_GBREAK_OTHER 0 -#define RE_GBREAK_CR 1 -#define RE_GBREAK_LF 2 -#define RE_GBREAK_CONTROL 3 -#define RE_GBREAK_EXTEND 4 -#define RE_GBREAK_REGIONALINDICATOR 5 -#define RE_GBREAK_SPACINGMARK 6 -#define RE_GBREAK_L 7 -#define RE_GBREAK_V 8 -#define RE_GBREAK_T 9 -#define RE_GBREAK_LV 10 -#define RE_GBREAK_LVT 11 -#define RE_GBREAK_PREPEND 12 - -extern char* re_strings[1160]; -extern RE_Property re_properties[143]; -extern RE_PropertyValue re_property_values[1251]; -extern RE_UINT16 re_expand_on_folding[104]; -extern RE_GetPropertyFunc re_get_property[77]; - -RE_UINT32 re_get_general_category(RE_UINT32 ch); -RE_UINT32 re_get_block(RE_UINT32 ch); -RE_UINT32 re_get_script(RE_UINT32 ch); -RE_UINT32 re_get_word_break(RE_UINT32 ch); -RE_UINT32 re_get_grapheme_cluster_break(RE_UINT32 ch); -RE_UINT32 re_get_sentence_break(RE_UINT32 ch); -RE_UINT32 re_get_math(RE_UINT32 ch); -RE_UINT32 re_get_alphabetic(RE_UINT32 ch); -RE_UINT32 re_get_lowercase(RE_UINT32 ch); -RE_UINT32 re_get_uppercase(RE_UINT32 ch); -RE_UINT32 re_get_cased(RE_UINT32 ch); -RE_UINT32 re_get_case_ignorable(RE_UINT32 ch); -RE_UINT32 re_get_changes_when_lowercased(RE_UINT32 ch); -RE_UINT32 re_get_changes_when_uppercased(RE_UINT32 ch); -RE_UINT32 re_get_changes_when_titlecased(RE_UINT32 ch); -RE_UINT32 re_get_changes_when_casefolded(RE_UINT32 ch); -RE_UINT32 re_get_changes_when_casemapped(RE_UINT32 ch); -RE_UINT32 re_get_id_start(RE_UINT32 ch); -RE_UINT32 re_get_id_continue(RE_UINT32 ch); -RE_UINT32 re_get_xid_start(RE_UINT32 ch); -RE_UINT32 re_get_xid_continue(RE_UINT32 ch); -RE_UINT32 re_get_default_ignorable_code_point(RE_UINT32 ch); -RE_UINT32 re_get_grapheme_extend(RE_UINT32 ch); -RE_UINT32 re_get_grapheme_base(RE_UINT32 ch); -RE_UINT32 re_get_grapheme_link(RE_UINT32 ch); -RE_UINT32 re_get_white_space(RE_UINT32 ch); -RE_UINT32 re_get_bidi_control(RE_UINT32 ch); -RE_UINT32 re_get_join_control(RE_UINT32 ch); -RE_UINT32 re_get_dash(RE_UINT32 ch); -RE_UINT32 re_get_hyphen(RE_UINT32 ch); -RE_UINT32 re_get_quotation_mark(RE_UINT32 ch); -RE_UINT32 re_get_terminal_punctuation(RE_UINT32 ch); -RE_UINT32 re_get_other_math(RE_UINT32 ch); -RE_UINT32 re_get_hex_digit(RE_UINT32 ch); -RE_UINT32 re_get_ascii_hex_digit(RE_UINT32 ch); -RE_UINT32 re_get_other_alphabetic(RE_UINT32 ch); -RE_UINT32 re_get_ideographic(RE_UINT32 ch); -RE_UINT32 re_get_diacritic(RE_UINT32 ch); -RE_UINT32 re_get_extender(RE_UINT32 ch); -RE_UINT32 re_get_other_lowercase(RE_UINT32 ch); -RE_UINT32 re_get_other_uppercase(RE_UINT32 ch); -RE_UINT32 re_get_noncharacter_code_point(RE_UINT32 ch); -RE_UINT32 re_get_other_grapheme_extend(RE_UINT32 ch); -RE_UINT32 re_get_ids_binary_operator(RE_UINT32 ch); -RE_UINT32 re_get_ids_trinary_operator(RE_UINT32 ch); -RE_UINT32 re_get_radical(RE_UINT32 ch); -RE_UINT32 re_get_unified_ideograph(RE_UINT32 ch); -RE_UINT32 re_get_other_default_ignorable_code_point(RE_UINT32 ch); -RE_UINT32 re_get_deprecated(RE_UINT32 ch); -RE_UINT32 re_get_soft_dotted(RE_UINT32 ch); -RE_UINT32 re_get_logical_order_exception(RE_UINT32 ch); -RE_UINT32 re_get_other_id_start(RE_UINT32 ch); -RE_UINT32 re_get_other_id_continue(RE_UINT32 ch); -RE_UINT32 re_get_sterm(RE_UINT32 ch); -RE_UINT32 re_get_variation_selector(RE_UINT32 ch); -RE_UINT32 re_get_pattern_white_space(RE_UINT32 ch); -RE_UINT32 re_get_pattern_syntax(RE_UINT32 ch); -RE_UINT32 re_get_hangul_syllable_type(RE_UINT32 ch); -RE_UINT32 re_get_bidi_class(RE_UINT32 ch); -RE_UINT32 re_get_canonical_combining_class(RE_UINT32 ch); -RE_UINT32 re_get_decomposition_type(RE_UINT32 ch); -RE_UINT32 re_get_east_asian_width(RE_UINT32 ch); -RE_UINT32 re_get_joining_group(RE_UINT32 ch); -RE_UINT32 re_get_joining_type(RE_UINT32 ch); -RE_UINT32 re_get_line_break(RE_UINT32 ch); -RE_UINT32 re_get_numeric_type(RE_UINT32 ch); -RE_UINT32 re_get_numeric_value(RE_UINT32 ch); -RE_UINT32 re_get_bidi_mirrored(RE_UINT32 ch); -RE_UINT32 re_get_indic_matra_category(RE_UINT32 ch); -RE_UINT32 re_get_indic_syllabic_category(RE_UINT32 ch); -RE_UINT32 re_get_alphanumeric(RE_UINT32 ch); -RE_UINT32 re_get_any(RE_UINT32 ch); -RE_UINT32 re_get_blank(RE_UINT32 ch); -RE_UINT32 re_get_graph(RE_UINT32 ch); -RE_UINT32 re_get_print(RE_UINT32 ch); -RE_UINT32 re_get_word(RE_UINT32 ch); -RE_UINT32 re_get_xdigit(RE_UINT32 ch); -int re_get_all_cases(RE_UINT32 ch, RE_UINT32* codepoints); -RE_UINT32 re_get_simple_case_folding(RE_UINT32 ch); -int re_get_full_case_folding(RE_UINT32 ch, RE_UINT32* codepoints); diff --git a/lib/regex/regex.py b/lib/regex/regex.py deleted file mode 100644 index e5e40d1f..00000000 --- a/lib/regex/regex.py +++ /dev/null @@ -1,684 +0,0 @@ -# -# Secret Labs' Regular Expression Engine -# -# Copyright (c) 1998-2001 by Secret Labs AB. All rights reserved. -# -# This version of the SRE library can be redistributed under CNRI's -# Python 1.6 license. For any other use, please contact Secret Labs -# AB (info@pythonware.com). -# -# Portions of this engine have been developed in cooperation with -# CNRI. Hewlett-Packard provided funding for 1.6 integration and -# other compatibility work. -# -# 2010-01-16 mrab Python front-end re-written and extended - -r"""Support for regular expressions (RE). - -This module provides regular expression matching operations similar to those -found in Perl. It supports both 8-bit and Unicode strings; both the pattern and -the strings being processed can contain null bytes and characters outside the -US ASCII range. - -Regular expressions can contain both special and ordinary characters. Most -ordinary characters, like "A", "a", or "0", are the simplest regular -expressions; they simply match themselves. You can concatenate ordinary -characters, so last matches the string 'last'. - -There are a few differences between the old (legacy) behaviour and the new -(enhanced) behaviour, which are indicated by VERSION0 or VERSION1. - -The special characters are: - "." Matches any character except a newline. - "^" Matches the start of the string. - "$" Matches the end of the string or just before the - newline at the end of the string. - "*" Matches 0 or more (greedy) repetitions of the preceding - RE. Greedy means that it will match as many repetitions - as possible. - "+" Matches 1 or more (greedy) repetitions of the preceding - RE. - "?" Matches 0 or 1 (greedy) of the preceding RE. - *?,+?,?? Non-greedy versions of the previous three special - characters. - *+,++,?+ Possessive versions of the previous three special - characters. - {m,n} Matches from m to n repetitions of the preceding RE. - {m,n}? Non-greedy version of the above. - {m,n}+ Possessive version of the above. - {...} Fuzzy matching constraints. - "\\" Either escapes special characters or signals a special - sequence. - [...] Indicates a set of characters. A "^" as the first - character indicates a complementing set. - "|" A|B, creates an RE that will match either A or B. - (...) Matches the RE inside the parentheses. The contents are - captured and can be retrieved or matched later in the - string. - (?flags-flags) VERSION1: Sets/clears the flags for the remainder of - the group or pattern; VERSION0: Sets the flags for the - entire pattern. - (?:...) Non-capturing version of regular parentheses. - (?>...) Atomic non-capturing version of regular parentheses. - (?flags-flags:...) Non-capturing version of regular parentheses with local - flags. - (?P...) The substring matched by the group is accessible by - name. - (?...) The substring matched by the group is accessible by - name. - (?P=name) Matches the text matched earlier by the group named - name. - (?#...) A comment; ignored. - (?=...) Matches if ... matches next, but doesn't consume the - string. - (?!...) Matches if ... doesn't match next. - (?<=...) Matches if preceded by .... - (? Matches the text matched by the group named name. - \G Matches the empty string, but only at the position where - the search started. - \L Named list. The list is provided as a keyword argument. - \m Matches the empty string, but only at the start of a word. - \M Matches the empty string, but only at the end of a word. - \n Matches the newline character. - \N{name} Matches the named character. - \p{name=value} Matches the character if its property has the specified - value. - \P{name=value} Matches the character if its property hasn't the specified - value. - \r Matches the carriage-return character. - \s Matches any whitespace character; equivalent to - [ \t\n\r\f\v]. - \S Matches any non-whitespace character; equivalent to [^\s]. - \t Matches the tab character. - \uXXXX Matches the Unicode codepoint with 4-digit hex code XXXX. - \UXXXXXXXX Matches the Unicode codepoint with 8-digit hex code - XXXXXXXX. - \v Matches the vertical tab character. - \w Matches any alphanumeric character; equivalent to - [a-zA-Z0-9_] when matching a bytestring or a Unicode string - with the ASCII flag, or the whole range of Unicode - alphanumeric characters (letters plus digits plus - underscore) when matching a Unicode string. With LOCALE, it - will match the set [0-9_] plus characters defined as - letters for the current locale. - \W Matches the complement of \w; equivalent to [^\w]. - \xXX Matches the character with 2-digit hex code XX. - \X Matches a grapheme. - \Z Matches only at the end of the string. - \\ Matches a literal backslash. - -This module exports the following functions: - match Match a regular expression pattern at the beginning of a string. - fullmatch Match a regular expression pattern against all of a string. - search Search a string for the presence of a pattern. - sub Substitute occurrences of a pattern found in a string using a - template string. - subf Substitute occurrences of a pattern found in a string using a - format string. - subn Same as sub, but also return the number of substitutions made. - subfn Same as subf, but also return the number of substitutions made. - split Split a string by the occurrences of a pattern. VERSION1: will - split at zero-width match; VERSION0: won't split at zero-width - match. - splititer Return an iterator yielding the parts of a split string. - findall Find all occurrences of a pattern in a string. - finditer Return an iterator yielding a match object for each match. - compile Compile a pattern into a Pattern object. - purge Clear the regular expression cache. - escape Backslash all non-alphanumerics or special characters in a - string. - -Most of the functions support a concurrent parameter: if True, the GIL will be -released during matching, allowing other Python threads to run concurrently. If -the string changes during matching, the behaviour is undefined. This parameter -is not needed when working on the builtin (immutable) string classes. - -Some of the functions in this module take flags as optional parameters. Most of -these flags can also be set within an RE: - A a ASCII Make \w, \W, \b, \B, \d, and \D match the - corresponding ASCII character categories. Default - when matching a bytestring. - B b BESTMATCH Find the best fuzzy match (default is first). - D DEBUG Print the parsed pattern. - F f FULLCASE Use full case-folding when performing - case-insensitive matching in Unicode. - I i IGNORECASE Perform case-insensitive matching. - L L LOCALE Make \w, \W, \b, \B, \d, and \D dependent on the - current locale. (One byte per character only.) - M m MULTILINE "^" matches the beginning of lines (after a newline) - as well as the string. "$" matches the end of lines - (before a newline) as well as the end of the string. - E e ENHANCEMATCH Attempt to improve the fit after finding the first - fuzzy match. - R r REVERSE Searches backwards. - S s DOTALL "." matches any character at all, including the - newline. - U u UNICODE Make \w, \W, \b, \B, \d, and \D dependent on the - Unicode locale. Default when matching a Unicode - string. - V0 V0 VERSION0 Turn on the old legacy behaviour. - V1 V1 VERSION1 Turn on the new enhanced behaviour. This flag - includes the FULLCASE flag. - W w WORD Make \b and \B work with default Unicode word breaks - and make ".", "^" and "$" work with Unicode line - breaks. - X x VERBOSE Ignore whitespace and comments for nicer looking REs. - -This module also defines an exception 'error'. - -""" - -# Public symbols. -__all__ = ["compile", "escape", "findall", "finditer", "fullmatch", "match", - "purge", "search", "split", "splititer", "sub", "subf", "subfn", "subn", - "template", "Scanner", "A", "ASCII", "B", "BESTMATCH", "D", "DEBUG", "E", - "ENHANCEMATCH", "S", "DOTALL", "F", "FULLCASE", "I", "IGNORECASE", "L", - "LOCALE", "M", "MULTILINE", "R", "REVERSE", "T", "TEMPLATE", "U", "UNICODE", - "V0", "VERSION0", "V1", "VERSION1", "X", "VERBOSE", "W", "WORD", "error", - "Regex"] - -__version__ = "2.4.45" - -# -------------------------------------------------------------------- -# Public interface. - -def match(pattern, string, flags=0, pos=None, endpos=None, partial=False, - concurrent=None, **kwargs): - """Try to apply the pattern at the start of the string, returning a match - object, or None if no match was found.""" - return _compile(pattern, flags, kwargs).match(string, pos, endpos, - concurrent, partial) - -def fullmatch(pattern, string, flags=0, pos=None, endpos=None, partial=False, - concurrent=None, **kwargs): - """Try to apply the pattern against all of the string, returning a match - object, or None if no match was found.""" - return _compile(pattern, flags, kwargs).fullmatch(string, pos, endpos, - concurrent, partial) - -def search(pattern, string, flags=0, pos=None, endpos=None, partial=False, - concurrent=None, **kwargs): - """Search through string looking for a match to the pattern, returning a - match object, or None if no match was found.""" - return _compile(pattern, flags, kwargs).search(string, pos, endpos, - concurrent, partial) - -def sub(pattern, repl, string, count=0, flags=0, pos=None, endpos=None, - concurrent=None, **kwargs): - """Return the string obtained by replacing the leftmost (or rightmost with a - reverse pattern) non-overlapping occurrences of the pattern in string by the - replacement repl. repl can be either a string or a callable; if a string, - backslash escapes in it are processed; if a callable, it's passed the match - object and must return a replacement string to be used.""" - return _compile(pattern, flags, kwargs).sub(repl, string, count, pos, - endpos, concurrent) - -def subf(pattern, format, string, count=0, flags=0, pos=None, endpos=None, - concurrent=None, **kwargs): - """Return the string obtained by replacing the leftmost (or rightmost with a - reverse pattern) non-overlapping occurrences of the pattern in string by the - replacement format. format can be either a string or a callable; if a string, - it's treated as a format string; if a callable, it's passed the match object - and must return a replacement string to be used.""" - return _compile(pattern, flags, kwargs).subf(format, string, count, pos, - endpos, concurrent) - -def subn(pattern, repl, string, count=0, flags=0, pos=None, endpos=None, - concurrent=None, **kwargs): - """Return a 2-tuple containing (new_string, number). new_string is the string - obtained by replacing the leftmost (or rightmost with a reverse pattern) - non-overlapping occurrences of the pattern in the source string by the - replacement repl. number is the number of substitutions that were made. repl - can be either a string or a callable; if a string, backslash escapes in it - are processed; if a callable, it's passed the match object and must return a - replacement string to be used.""" - return _compile(pattern, flags, kwargs).subn(repl, string, count, pos, - endpos, concurrent) - -def subfn(pattern, format, string, count=0, flags=0, pos=None, endpos=None, - concurrent=None, **kwargs): - """Return a 2-tuple containing (new_string, number). new_string is the string - obtained by replacing the leftmost (or rightmost with a reverse pattern) - non-overlapping occurrences of the pattern in the source string by the - replacement format. number is the number of substitutions that were made. format - can be either a string or a callable; if a string, it's treated as a format - string; if a callable, it's passed the match object and must return a - replacement string to be used.""" - return _compile(pattern, flags, kwargs).subfn(format, string, count, pos, - endpos, concurrent) - -def split(pattern, string, maxsplit=0, flags=0, concurrent=None, **kwargs): - """Split the source string by the occurrences of the pattern, returning a - list containing the resulting substrings. If capturing parentheses are used - in pattern, then the text of all groups in the pattern are also returned as - part of the resulting list. If maxsplit is nonzero, at most maxsplit splits - occur, and the remainder of the string is returned as the final element of - the list.""" - return _compile(pattern, flags, kwargs).split(string, maxsplit, concurrent) - -def splititer(pattern, string, maxsplit=0, flags=0, concurrent=None, **kwargs): - "Return an iterator yielding the parts of a split string." - return _compile(pattern, flags, kwargs).splititer(string, maxsplit, - concurrent) - -def findall(pattern, string, flags=0, pos=None, endpos=None, overlapped=False, - concurrent=None, **kwargs): - """Return a list of all matches in the string. The matches may be overlapped - if overlapped is True. If one or more groups are present in the pattern, - return a list of groups; this will be a list of tuples if the pattern has - more than one group. Empty matches are included in the result.""" - return _compile(pattern, flags, kwargs).findall(string, pos, endpos, - overlapped, concurrent) - -def finditer(pattern, string, flags=0, pos=None, endpos=None, overlapped=False, - partial=False, concurrent=None, **kwargs): - """Return an iterator over all matches in the string. The matches may be - overlapped if overlapped is True. For each match, the iterator returns a - match object. Empty matches are included in the result.""" - return _compile(pattern, flags, kwargs).finditer(string, pos, endpos, - overlapped, concurrent, partial) - -def compile(pattern, flags=0, **kwargs): - "Compile a regular expression pattern, returning a pattern object." - return _compile(pattern, flags, kwargs) - -def purge(): - "Clear the regular expression cache" - _cache.clear() - -def template(pattern, flags=0): - "Compile a template pattern, returning a pattern object." - return _compile(pattern, flags | TEMPLATE) - -def escape(pattern, special_only=False): - "Escape all non-alphanumeric characters or special characters in pattern." - if isinstance(pattern, unicode): - s = [] - if special_only: - for c in pattern: - if c in _METACHARS: - s.append(u"\\") - s.append(c) - elif c == u"\x00": - s.append(u"\\000") - else: - s.append(c) - else: - for c in pattern: - if c in _ALNUM: - s.append(c) - elif c == u"\x00": - s.append(u"\\000") - else: - s.append(u"\\") - s.append(c) - - return u"".join(s) - else: - s = [] - if special_only: - for c in pattern: - if c in _METACHARS: - s.append("\\") - s.append(c) - elif c == "\x00": - s.append("\\000") - else: - s.append(c) - else: - for c in pattern: - if c in _ALNUM: - s.append(c) - elif c == "\x00": - s.append("\\000") - else: - s.append("\\") - s.append(c) - - return "".join(s) - -# -------------------------------------------------------------------- -# Internals. - -import _regex_core -import sys -if sys.version_info < (2, 6): - from Python25 import _regex -elif sys.version_info < (2, 7): - from Python26 import _regex -else: - from Python27 import _regex -from threading import RLock as _RLock -from _regex_core import * -from _regex_core import (_ALL_VERSIONS, _ALL_ENCODINGS, _FirstSetError, - _UnscopedFlagSet, _check_group_features, _compile_firstset, - _compile_replacement, _flatten_code, _fold_case, _get_required_string, - _parse_pattern, _shrink_cache) -from _regex_core import (ALNUM as _ALNUM, Info as _Info, OP as _OP, Source as - _Source, Fuzzy as _Fuzzy) - -# Version 0 is the old behaviour, compatible with the original 're' module. -# Version 1 is the new behaviour, which differs slightly. - -DEFAULT_VERSION = VERSION0 - -_METACHARS = frozenset("()[]{}?*+|^$\\.") - -_regex_core.DEFAULT_VERSION = DEFAULT_VERSION - -# Caches for the patterns and replacements. -_cache = {} -_cache_lock = _RLock() -_named_args = {} -_replacement_cache = {} - -# Maximum size of the cache. -_MAXCACHE = 500 -_MAXREPCACHE = 500 - -def _compile(pattern, flags=0, kwargs={}): - "Compiles a regular expression to a PatternObject." - try: - # Do we know what keyword arguments are needed? - args_key = pattern, type(pattern), flags - args_needed = _named_args[args_key] - - # Are we being provided with its required keyword arguments? - args_supplied = set() - if args_needed: - for k, v in args_needed: - try: - args_supplied.add((k, frozenset(kwargs[k]))) - except KeyError: - raise error("missing named list") - - args_supplied = frozenset(args_supplied) - - # Have we already seen this regular expression and named list? - pattern_key = (pattern, type(pattern), flags, args_supplied, - DEFAULT_VERSION) - return _cache[pattern_key] - except KeyError: - # It's a new pattern, or new named list for a known pattern. - pass - - # Guess the encoding from the class of the pattern string. - if isinstance(pattern, unicode): - guess_encoding = UNICODE - elif isinstance(pattern, str): - guess_encoding = ASCII - elif isinstance(pattern, _pattern_type): - if flags: - raise ValueError("can't process flags argument with a compiled pattern") - - return pattern - else: - raise TypeError("first argument must be a string or compiled pattern") - - # Set the default version in the core code in case it has been changed. - _regex_core.DEFAULT_VERSION = DEFAULT_VERSION - - caught_exception = None - global_flags = flags - - while True: - try: - source = _Source(pattern) - info = _Info(global_flags, source.char_type, kwargs) - info.guess_encoding = guess_encoding - source.ignore_space = bool(info.flags & VERBOSE) - parsed = _parse_pattern(source, info) - break - except _UnscopedFlagSet: - # Remember the global flags for the next attempt. - global_flags = info.global_flags - except error, e: - caught_exception = e - - if caught_exception: - raise error(str(caught_exception)) - - if not source.at_end(): - raise error("trailing characters in pattern at position %d" % source.pos) - - # Check the global flags for conflicts. - version = (info.flags & _ALL_VERSIONS) or DEFAULT_VERSION - if version not in (0, VERSION0, VERSION1): - raise ValueError("VERSION0 and VERSION1 flags are mutually incompatible") - - if (info.flags & _ALL_ENCODINGS) not in (0, ASCII, LOCALE, UNICODE): - raise ValueError("ASCII, LOCALE and UNICODE flags are mutually incompatible") - - if not (info.flags & _ALL_ENCODINGS): - if isinstance(pattern, unicode): - info.flags |= UNICODE - else: - info.flags |= ASCII - - reverse = bool(info.flags & REVERSE) - fuzzy = isinstance(parsed, _Fuzzy) - - # Should we print the parsed pattern? - if flags & DEBUG: - parsed.dump(indent=0, reverse=reverse) - - # Fix the group references. - parsed.fix_groups(reverse, False) - - # Optimise the parsed pattern. - parsed = parsed.optimise(info) - parsed = parsed.pack_characters(info) - - # Get the required string. - req_offset, req_chars, req_flags = _get_required_string(parsed, info.flags) - - # Build the named lists. - named_lists = {} - named_list_indexes = [None] * len(info.named_lists_used) - args_needed = set() - for key, index in info.named_lists_used.items(): - name, case_flags = key - values = frozenset(kwargs[name]) - if case_flags: - items = frozenset(_fold_case(info, v) for v in values) - else: - items = values - named_lists[name] = values - named_list_indexes[index] = items - args_needed.add((name, values)) - - # Check the features of the groups. - _check_group_features(info, parsed) - - # Compile the parsed pattern. The result is a list of tuples. - code = parsed.compile(reverse) - - # Is there a group call to the pattern as a whole? - key = (0, reverse, fuzzy) - ref = info.call_refs.get(key) - if ref is not None: - code = [(_OP.CALL_REF, ref)] + code + [(_OP.END, )] - - # Add the final 'success' opcode. - code += [(_OP.SUCCESS, )] - - # Compile the additional copies of the groups that we need. - for group, rev, fuz in info.additional_groups: - code += group.compile(rev, fuz) - - # Flatten the code into a list of ints. - code = _flatten_code(code) - - if not parsed.has_simple_start(): - # Get the first set, if possible. - try: - fs_code = _compile_firstset(info, parsed.get_firstset(reverse)) - fs_code = _flatten_code(fs_code) - code = fs_code + code - except _FirstSetError: - pass - - # The named capture groups. - index_group = dict((v, n) for n, v in info.group_index.items()) - - # Create the PatternObject. - # - # Local flags like IGNORECASE affect the code generation, but aren't needed - # by the PatternObject itself. Conversely, global flags like LOCALE _don't_ - # affect the code generation but _are_ needed by the PatternObject. - compiled_pattern = _regex.compile(pattern, info.flags | version, code, - info.group_index, index_group, named_lists, named_list_indexes, - req_offset, req_chars, req_flags, info.group_count) - - # Do we need to reduce the size of the cache? - if len(_cache) >= _MAXCACHE: - _cache_lock.acquire() - try: - _shrink_cache(_cache, _named_args, _MAXCACHE) - finally: - _cache_lock.release() - - args_needed = frozenset(args_needed) - - # Store this regular expression and named list. - pattern_key = (pattern, type(pattern), flags, args_needed, DEFAULT_VERSION) - _cache[pattern_key] = compiled_pattern - - # Store what keyword arguments are needed. - _named_args[args_key] = args_needed - - return compiled_pattern - -def _compile_replacement_helper(pattern, template): - "Compiles a replacement template." - # This function is called by the _regex module. - - # Have we seen this before? - key = pattern.pattern, pattern.flags, template - compiled = _replacement_cache.get(key) - if compiled is not None: - return compiled - - if len(_replacement_cache) >= _MAXREPCACHE: - _replacement_cache.clear() - - is_unicode = isinstance(template, unicode) - source = _Source(template) - if is_unicode: - def make_string(char_codes): - return u"".join(unichr(c) for c in char_codes) - else: - def make_string(char_codes): - return "".join(chr(c) for c in char_codes) - - compiled = [] - literal = [] - while True: - ch = source.get() - if not ch: - break - if ch == "\\": - # '_compile_replacement' will return either an int group reference - # or a string literal. It returns items (plural) in order to handle - # a 2-character literal (an invalid escape sequence). - is_group, items = _compile_replacement(source, pattern, is_unicode) - if is_group: - # It's a group, so first flush the literal. - if literal: - compiled.append(make_string(literal)) - literal = [] - compiled.extend(items) - else: - literal.extend(items) - else: - literal.append(ord(ch)) - - # Flush the literal. - if literal: - compiled.append(make_string(literal)) - - _replacement_cache[key] = compiled - - return compiled - -# We define _pattern_type here after all the support objects have been defined. -_pattern_type = type(_compile("", 0, {})) - -# We'll define an alias for the 'compile' function so that the repr of a -# pattern object is eval-able. -Regex = compile - -# Register myself for pickling. -import copy_reg as _copy_reg - -def _pickle(p): - return _compile, (p.pattern, p.flags) - -_copy_reg.pickle(_pattern_type, _pickle, _compile) - -if not hasattr(str, "format"): - # Strings don't have the .format method (below Python 2.6). - while True: - _start = __doc__.find(" subf") - if _start < 0: - break - - _end = __doc__.find("\n", _start) + 1 - while __doc__.startswith(" ", _end): - _end = __doc__.find("\n", _end) + 1 - - __doc__ = __doc__[ : _start] + __doc__[_end : ] - - __all__ = [_name for _name in __all__ if not _name.startswith("subf")] - - del _start, _end - - del subf, subfn diff --git a/lib/regex/test_regex.py b/lib/regex/test_regex.py deleted file mode 100644 index 55b14c4d..00000000 --- a/lib/regex/test_regex.py +++ /dev/null @@ -1,3230 +0,0 @@ -from __future__ import with_statement -import regex -import string -from weakref import proxy -import unittest -import copy -from test.test_support import run_unittest -import re - -# _AssertRaisesContext is defined here because the class doesn't exist before -# Python 2.7. -class _AssertRaisesContext(object): - """A context manager used to implement TestCase.assertRaises* methods.""" - - def __init__(self, expected, test_case, expected_regexp=None): - self.expected = expected - self.failureException = test_case.failureException - self.expected_regexp = expected_regexp - - def __enter__(self): - return self - - def __exit__(self, exc_type, exc_value, tb): - if exc_type is None: - try: - exc_name = self.expected.__name__ - except AttributeError: - exc_name = str(self.expected) - raise self.failureException( - "{0} not raised".format(exc_name)) - if not issubclass(exc_type, self.expected): - # let unexpected exceptions pass through - return False - self.exception = exc_value # store for later retrieval - if self.expected_regexp is None: - return True - - expected_regexp = self.expected_regexp - if isinstance(expected_regexp, basestring): - expected_regexp = re.compile(expected_regexp) - if not expected_regexp.search(str(exc_value)): - raise self.failureException('"%s" does not match "%s"' % - (expected_regexp.pattern, str(exc_value))) - return True - -class RegexTests(unittest.TestCase): - PATTERN_CLASS = "" - FLAGS_WITH_COMPILED_PAT = "can't process flags argument with a compiled pattern" - INVALID_GROUP_REF = "invalid group reference" - MISSING_GT = "missing >" - BAD_GROUP_NAME = "bad group name" - MISSING_LT = "missing <" - UNKNOWN_GROUP_I = "unknown group" - UNKNOWN_GROUP = "unknown group" - BAD_ESCAPE = "bad escape" - BAD_OCTAL_ESCAPE = "bad octal escape" - BAD_SET = "bad set" - STR_PAT_ON_BYTES = "can't use a string pattern on a bytes-like object" - BYTES_PAT_ON_STR = "can't use a bytes pattern on a string-like object" - STR_PAT_BYTES_TEMPL = "expected str instance, bytes found" - BYTES_PAT_STR_TEMPL = "expected bytes instance, str found" - BYTES_PAT_UNI_FLAG = "can't use UNICODE flag with a bytes pattern" - MIXED_FLAGS = "ASCII, LOCALE and UNICODE flags are mutually incompatible" - MISSING_RPAREN = "missing \\)" # Need to escape parenthesis for unittest. - TRAILING_CHARS = "trailing characters in pattern" - BAD_CHAR_RANGE = "bad character range" - NOTHING_TO_REPEAT = "nothing to repeat" - OPEN_GROUP = "can't refer to an open group" - DUPLICATE_GROUP = "duplicate group" - CANT_TURN_OFF = "bad inline flags: can't turn flags off" - UNDEF_CHAR_NAME = "undefined character name" - - # assertRaisesRegex is defined here because the method isn't in the - # superclass before Python 2.7. - def assertRaisesRegex(self, expected_exception, expected_regexp, - callable_obj=None, *args, **kwargs): - """Asserts that the message in a raised exception matches a regexp. - - Args: - expected_exception: Exception class expected to be raised. - expected_regexp: Regexp (re pattern object or string) expected - to be found in error message. - callable_obj: Function to be called. - args: Extra args. - kwargs: Extra kwargs. - """ - context = _AssertRaisesContext(expected_exception, self, expected_regexp) - if callable_obj is None: - return context - with context: - callable_obj(*args, **kwargs) - - def assertTypedEqual(self, actual, expect, msg=None): - self.assertEqual(actual, expect, msg) - - def recurse(actual, expect): - if isinstance(expect, (tuple, list)): - for x, y in zip(actual, expect): - recurse(x, y) - else: - self.assertIs(type(actual), type(expect), msg) - - recurse(actual, expect) - - def test_weakref(self): - s = 'QabbbcR' - x = regex.compile('ab+c') - y = proxy(x) - if x.findall('QabbbcR') != y.findall('QabbbcR'): - self.fail() - - def test_search_star_plus(self): - self.assertEqual(regex.search('a*', 'xxx').span(0), (0, 0)) - self.assertEqual(regex.search('x*', 'axx').span(), (0, 0)) - self.assertEqual(regex.search('x+', 'axx').span(0), (1, 3)) - self.assertEqual(regex.search('x+', 'axx').span(), (1, 3)) - self.assertEqual(regex.search('x', 'aaa'), None) - self.assertEqual(regex.match('a*', 'xxx').span(0), (0, 0)) - self.assertEqual(regex.match('a*', 'xxx').span(), (0, 0)) - self.assertEqual(regex.match('x*', 'xxxa').span(0), (0, 3)) - self.assertEqual(regex.match('x*', 'xxxa').span(), (0, 3)) - self.assertEqual(regex.match('a+', 'xxx'), None) - - def bump_num(self, matchobj): - int_value = int(matchobj[0]) - return str(int_value + 1) - - def test_basic_regex_sub(self): - self.assertEqual(regex.sub("(?i)b+", "x", "bbbb BBBB"), 'x x') - self.assertEqual(regex.sub(r'\d+', self.bump_num, '08.2 -2 23x99y'), - '9.3 -3 24x100y') - self.assertEqual(regex.sub(r'\d+', self.bump_num, '08.2 -2 23x99y', 3), - '9.3 -3 23x99y') - - self.assertEqual(regex.sub('.', lambda m: r"\n", 'x'), "\\n") - self.assertEqual(regex.sub('.', r"\n", 'x'), "\n") - - self.assertEqual(regex.sub('(?Px)', r'\g\g', 'xx'), 'xxxx') - self.assertEqual(regex.sub('(?Px)', r'\g\g<1>', 'xx'), 'xxxx') - self.assertEqual(regex.sub('(?Px)', r'\g\g', 'xx'), - 'xxxx') - self.assertEqual(regex.sub('(?Px)', r'\g<1>\g<1>', 'xx'), 'xxxx') - - self.assertEqual(regex.sub('a', r'\t\n\v\r\f\a\b\B\Z\a\A\w\W\s\S\d\D', - 'a'), "\t\n\v\r\f\a\b\\B\\Z\a\\A\\w\\W\\s\\S\\d\\D") - self.assertEqual(regex.sub('a', '\t\n\v\r\f\a', 'a'), "\t\n\v\r\f\a") - self.assertEqual(regex.sub('a', '\t\n\v\r\f\a', 'a'), chr(9) + chr(10) - + chr(11) + chr(13) + chr(12) + chr(7)) - - self.assertEqual(regex.sub(r'^\s*', 'X', 'test'), 'Xtest') - - self.assertEqual(regex.sub(ur"x", ur"\x0A", u"x"), u"\n") - self.assertEqual(regex.sub(ur"x", ur"\u000A", u"x"), u"\n") - self.assertEqual(regex.sub(ur"x", ur"\U0000000A", u"x"), u"\n") - self.assertEqual(regex.sub(ur"x", ur"\N{LATIN CAPITAL LETTER A}", - u"x"), u"A") - - self.assertEqual(regex.sub(r"x", r"\x0A", "x"), "\n") - self.assertEqual(regex.sub(r"x", r"\u000A", "x"), "\\u000A") - self.assertEqual(regex.sub(r"x", r"\U0000000A", "x"), "\\U0000000A") - self.assertEqual(regex.sub(r"x", r"\N{LATIN CAPITAL LETTER A}", "x"), - "\\N{LATIN CAPITAL LETTER A}") - - def test_bug_449964(self): - # Fails for group followed by other escape. - self.assertEqual(regex.sub(r'(?Px)', r'\g<1>\g<1>\b', 'xx'), - "xx\bxx\b") - - def test_bug_449000(self): - # Test for sub() on escaped characters. - self.assertEqual(regex.sub(r'\r\n', r'\n', 'abc\r\ndef\r\n'), - "abc\ndef\n") - self.assertEqual(regex.sub('\r\n', r'\n', 'abc\r\ndef\r\n'), - "abc\ndef\n") - self.assertEqual(regex.sub(r'\r\n', '\n', 'abc\r\ndef\r\n'), - "abc\ndef\n") - self.assertEqual(regex.sub('\r\n', '\n', 'abc\r\ndef\r\n'), - "abc\ndef\n") - - def test_bug_1140(self): - # regex.sub(x, y, u'') should return u'', not '', and - # regex.sub(x, y, '') should return '', not u''. - # Also: - # regex.sub(x, y, unicode(x)) should return unicode(y), and - # regex.sub(x, y, str(x)) should return - # str(y) if isinstance(y, str) else unicode(y). - for x in 'x', u'x': - for y in 'y', u'y': - z = regex.sub(x, y, u'') - self.assertEqual((type(z), z), (unicode, u'')) - z = regex.sub(x, y, '') - self.assertEqual((type(z), z), (str, '')) - z = regex.sub(x, y, unicode(x)) - self.assertEqual((type(z), z), (unicode, unicode(y))) - z = regex.sub(x, y, str(x)) - self.assertEqual((type(z), z), (type(y), y)) - - def test_bug_1661(self): - # Verify that flags do not get silently ignored with compiled patterns - pattern = regex.compile('.') - self.assertRaisesRegex(ValueError, self.FLAGS_WITH_COMPILED_PAT, - lambda: regex.match(pattern, 'A', regex.I)) - self.assertRaisesRegex(ValueError, self.FLAGS_WITH_COMPILED_PAT, - lambda: regex.search(pattern, 'A', regex.I)) - self.assertRaisesRegex(ValueError, self.FLAGS_WITH_COMPILED_PAT, - lambda: regex.findall(pattern, 'A', regex.I)) - self.assertRaisesRegex(ValueError, self.FLAGS_WITH_COMPILED_PAT, - lambda: regex.compile(pattern, regex.I)) - - def test_bug_3629(self): - # A regex that triggered a bug in the sre-code validator - self.assertEqual(repr(type(regex.compile("(?P)(?(quote))"))), - self.PATTERN_CLASS) - - def test_sub_template_numeric_escape(self): - # Bug 776311 and friends. - self.assertEqual(regex.sub('x', r'\0', 'x'), "\0") - self.assertEqual(regex.sub('x', r'\000', 'x'), "\000") - self.assertEqual(regex.sub('x', r'\001', 'x'), "\001") - self.assertEqual(regex.sub('x', r'\008', 'x'), "\0" + "8") - self.assertEqual(regex.sub('x', r'\009', 'x'), "\0" + "9") - self.assertEqual(regex.sub('x', r'\111', 'x'), "\111") - self.assertEqual(regex.sub('x', r'\117', 'x'), "\117") - - self.assertEqual(regex.sub('x', r'\1111', 'x'), "\1111") - self.assertEqual(regex.sub('x', r'\1111', 'x'), "\111" + "1") - - self.assertEqual(regex.sub('x', r'\00', 'x'), '\x00') - self.assertEqual(regex.sub('x', r'\07', 'x'), '\x07') - self.assertEqual(regex.sub('x', r'\08', 'x'), "\0" + "8") - self.assertEqual(regex.sub('x', r'\09', 'x'), "\0" + "9") - self.assertEqual(regex.sub('x', r'\0a', 'x'), "\0" + "a") - - self.assertEqual(regex.sub(u'x', ur'\400', u'x'), u"\u0100") - self.assertEqual(regex.sub(u'x', ur'\777', u'x'), u"\u01FF") - self.assertEqual(regex.sub('x', r'\400', 'x'), "\x00") - self.assertEqual(regex.sub('x', r'\777', 'x'), "\xFF") - - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\1', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\8', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\9', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\11', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\18', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\1a', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\90', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\99', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\118', 'x')) # r'\11' + '8' - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\11a', 'x')) - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\181', 'x')) # r'\18' + '1' - self.assertRaisesRegex(regex.error, self.INVALID_GROUP_REF, lambda: - regex.sub('x', r'\800', 'x')) # r'\80' + '0' - - # In Python 2.3 (etc), these loop endlessly in sre_parser.py. - self.assertEqual(regex.sub('(((((((((((x)))))))))))', r'\11', 'x'), - 'x') - self.assertEqual(regex.sub('((((((((((y))))))))))(.)', r'\118', 'xyz'), - 'xz8') - self.assertEqual(regex.sub('((((((((((y))))))))))(.)', r'\11a', 'xyz'), - 'xza') - - def test_qualified_re_sub(self): - self.assertEqual(regex.sub('a', 'b', 'aaaaa'), 'bbbbb') - self.assertEqual(regex.sub('a', 'b', 'aaaaa', 1), 'baaaa') - - def test_bug_114660(self): - self.assertEqual(regex.sub(r'(\S)\s+(\S)', r'\1 \2', 'hello there'), - 'hello there') - - def test_bug_462270(self): - # Test for empty sub() behaviour, see SF bug #462270 - self.assertEqual(regex.sub('(?V0)x*', '-', 'abxd'), '-a-b-d-') - self.assertEqual(regex.sub('(?V1)x*', '-', 'abxd'), '-a-b--d-') - self.assertEqual(regex.sub('x+', '-', 'abxd'), 'ab-d') - - def test_bug_14462(self): - # chr(255) is not a valid identifier in Python 2. - group_name = u'\xFF' - self.assertRaisesRegex(regex.error, self.BAD_GROUP_NAME, lambda: - regex.search(ur'(?P<' + group_name + '>a)', u'a')) - - def test_symbolic_refs(self): - self.assertRaisesRegex(regex.error, self.MISSING_GT, lambda: - regex.sub('(?Px)', r'\gx)', r'\g<', 'xx')) - self.assertRaisesRegex(regex.error, self.MISSING_LT, lambda: - regex.sub('(?Px)', r'\g', 'xx')) - self.assertRaisesRegex(regex.error, self.BAD_GROUP_NAME, lambda: - regex.sub('(?Px)', r'\g', 'xx')) - self.assertRaisesRegex(regex.error, self.BAD_GROUP_NAME, lambda: - regex.sub('(?Px)', r'\g<1a1>', 'xx')) - self.assertRaisesRegex(IndexError, self.UNKNOWN_GROUP_I, lambda: - regex.sub('(?Px)', r'\g', 'xx')) - - # The new behaviour of unmatched but valid groups is to treat them like - # empty matches in the replacement template, like in Perl. - self.assertEqual(regex.sub('(?Px)|(?Py)', r'\g', 'xx'), '') - self.assertEqual(regex.sub('(?Px)|(?Py)', r'\2', 'xx'), '') - - # The old behaviour was to raise it as an IndexError. - self.assertRaisesRegex(regex.error, self.BAD_GROUP_NAME, lambda: - regex.sub('(?Px)', r'\g<-1>', 'xx')) - - def test_re_subn(self): - self.assertEqual(regex.subn("(?i)b+", "x", "bbbb BBBB"), ('x x', 2)) - self.assertEqual(regex.subn("b+", "x", "bbbb BBBB"), ('x BBBB', 1)) - self.assertEqual(regex.subn("b+", "x", "xyz"), ('xyz', 0)) - self.assertEqual(regex.subn("b*", "x", "xyz"), ('xxxyxzx', 4)) - self.assertEqual(regex.subn("b*", "x", "xyz", 2), ('xxxyz', 2)) - - def test_re_split(self): - self.assertEqual(regex.split(":", ":a:b::c"), ['', 'a', 'b', '', 'c']) - self.assertEqual(regex.split(":*", ":a:b::c"), ['', 'a', 'b', 'c']) - self.assertEqual(regex.split("(:*)", ":a:b::c"), ['', ':', 'a', ':', - 'b', '::', 'c']) - self.assertEqual(regex.split("(?::*)", ":a:b::c"), ['', 'a', 'b', 'c']) - self.assertEqual(regex.split("(:)*", ":a:b::c"), ['', ':', 'a', ':', - 'b', ':', 'c']) - self.assertEqual(regex.split("([b:]+)", ":a:b::c"), ['', ':', 'a', - ':b::', 'c']) - self.assertEqual(regex.split("(b)|(:+)", ":a:b::c"), ['', None, ':', - 'a', None, ':', '', 'b', None, '', None, '::', 'c']) - self.assertEqual(regex.split("(?:b)|(?::+)", ":a:b::c"), ['', 'a', '', - '', 'c']) - - self.assertEqual(regex.split("x", "xaxbxc"), ['', 'a', 'b', 'c']) - self.assertEqual([m for m in regex.splititer("x", "xaxbxc")], ['', 'a', - 'b', 'c']) - - self.assertEqual(regex.split("(?r)x", "xaxbxc"), ['c', 'b', 'a', '']) - self.assertEqual([m for m in regex.splititer("(?r)x", "xaxbxc")], ['c', - 'b', 'a', '']) - - self.assertEqual(regex.split("(x)|(y)", "xaxbxc"), ['', 'x', None, 'a', - 'x', None, 'b', 'x', None, 'c']) - self.assertEqual([m for m in regex.splititer("(x)|(y)", "xaxbxc")], - ['', 'x', None, 'a', 'x', None, 'b', 'x', None, 'c']) - - self.assertEqual(regex.split("(?r)(x)|(y)", "xaxbxc"), ['c', 'x', None, - 'b', 'x', None, 'a', 'x', None, '']) - self.assertEqual([m for m in regex.splititer("(?r)(x)|(y)", "xaxbxc")], - ['c', 'x', None, 'b', 'x', None, 'a', 'x', None, '']) - - self.assertEqual(regex.split(r"(?V1)\b", "a b c"), ['', 'a', ' ', 'b', - ' ', 'c', '']) - self.assertEqual(regex.split(r"(?V1)\m", "a b c"), ['', 'a ', 'b ', - 'c']) - self.assertEqual(regex.split(r"(?V1)\M", "a b c"), ['a', ' b', ' c', - '']) - - def test_qualified_re_split(self): - self.assertEqual(regex.split(":", ":a:b::c", 2), ['', 'a', 'b::c']) - self.assertEqual(regex.split(':', 'a:b:c:d', 2), ['a', 'b', 'c:d']) - self.assertEqual(regex.split("(:)", ":a:b::c", 2), ['', ':', 'a', ':', - 'b::c']) - self.assertEqual(regex.split("(:*)", ":a:b::c", 2), ['', ':', 'a', ':', - 'b::c']) - - def test_re_findall(self): - self.assertEqual(regex.findall(":+", "abc"), []) - self.assertEqual(regex.findall(":+", "a:b::c:::d"), [':', '::', ':::']) - self.assertEqual(regex.findall("(:+)", "a:b::c:::d"), [':', '::', - ':::']) - self.assertEqual(regex.findall("(:)(:*)", "a:b::c:::d"), [(':', ''), - (':', ':'), (':', '::')]) - - self.assertEqual(regex.findall(r"\((?P.{0,5}?TEST)\)", - "(MY TEST)"), ["MY TEST"]) - self.assertEqual(regex.findall(r"\((?P.{0,3}?TEST)\)", - "(MY TEST)"), ["MY TEST"]) - self.assertEqual(regex.findall(r"\((?P.{0,3}?T)\)", "(MY T)"), - ["MY T"]) - - self.assertEqual(regex.findall(r"[^a]{2}[A-Z]", "\n S"), [' S']) - self.assertEqual(regex.findall(r"[^a]{2,3}[A-Z]", "\n S"), ['\n S']) - self.assertEqual(regex.findall(r"[^a]{2,3}[A-Z]", "\n S"), [' S']) - - self.assertEqual(regex.findall(r"X(Y[^Y]+?){1,2}( |Q)+DEF", - "XYABCYPPQ\nQ DEF"), [('YPPQ\n', ' ')]) - - self.assertEqual(regex.findall(r"(\nTest(\n+.+?){0,2}?)?\n+End", - "\nTest\nxyz\nxyz\nEnd"), [('\nTest\nxyz\nxyz', '\nxyz')]) - - def test_bug_117612(self): - self.assertEqual(regex.findall(r"(a|(b))", "aba"), [('a', ''), ('b', - 'b'), ('a', '')]) - - def test_re_match(self): - self.assertEqual(regex.match('a', 'a')[:], ('a',)) - self.assertEqual(regex.match('(a)', 'a')[:], ('a', 'a')) - self.assertEqual(regex.match(r'(a)', 'a')[0], 'a') - self.assertEqual(regex.match(r'(a)', 'a')[1], 'a') - self.assertEqual(regex.match(r'(a)', 'a').group(1, 1), ('a', 'a')) - - pat = regex.compile('((a)|(b))(c)?') - self.assertEqual(pat.match('a')[:], ('a', 'a', 'a', None, None)) - self.assertEqual(pat.match('b')[:], ('b', 'b', None, 'b', None)) - self.assertEqual(pat.match('ac')[:], ('ac', 'a', 'a', None, 'c')) - self.assertEqual(pat.match('bc')[:], ('bc', 'b', None, 'b', 'c')) - self.assertEqual(pat.match('bc')[:], ('bc', 'b', None, 'b', 'c')) - - # A single group. - m = regex.match('(a)', 'a') - self.assertEqual(m.group(), 'a') - self.assertEqual(m.group(0), 'a') - self.assertEqual(m.group(1), 'a') - self.assertEqual(m.group(1, 1), ('a', 'a')) - - pat = regex.compile('(?:(?Pa)|(?Pb))(?Pc)?') - self.assertEqual(pat.match('a').group(1, 2, 3), ('a', None, None)) - self.assertEqual(pat.match('b').group('a1', 'b2', 'c3'), (None, 'b', - None)) - self.assertEqual(pat.match('ac').group(1, 'b2', 3), ('a', None, 'c')) - - def test_re_groupref_exists(self): - self.assertEqual(regex.match(r'^(\()?([^()]+)(?(1)\))$', '(a)')[:], - ('(a)', '(', 'a')) - self.assertEqual(regex.match(r'^(\()?([^()]+)(?(1)\))$', 'a')[:], ('a', - None, 'a')) - self.assertEqual(regex.match(r'^(\()?([^()]+)(?(1)\))$', 'a)'), None) - self.assertEqual(regex.match(r'^(\()?([^()]+)(?(1)\))$', '(a'), None) - self.assertEqual(regex.match('^(?:(a)|c)((?(1)b|d))$', 'ab')[:], ('ab', - 'a', 'b')) - self.assertEqual(regex.match('^(?:(a)|c)((?(1)b|d))$', 'cd')[:], ('cd', - None, 'd')) - self.assertEqual(regex.match('^(?:(a)|c)((?(1)|d))$', 'cd')[:], ('cd', - None, 'd')) - self.assertEqual(regex.match('^(?:(a)|c)((?(1)|d))$', 'a')[:], ('a', - 'a', '')) - - # Tests for bug #1177831: exercise groups other than the first group. - p = regex.compile('(?Pa)(?Pb)?((?(g2)c|d))') - self.assertEqual(p.match('abc')[:], ('abc', 'a', 'b', 'c')) - self.assertEqual(p.match('ad')[:], ('ad', 'a', None, 'd')) - self.assertEqual(p.match('abd'), None) - self.assertEqual(p.match('ac'), None) - - def test_re_groupref(self): - self.assertEqual(regex.match(r'^(\|)?([^()]+)\1$', '|a|')[:], ('|a|', - '|', 'a')) - self.assertEqual(regex.match(r'^(\|)?([^()]+)\1?$', 'a')[:], ('a', - None, 'a')) - self.assertEqual(regex.match(r'^(\|)?([^()]+)\1$', 'a|'), None) - self.assertEqual(regex.match(r'^(\|)?([^()]+)\1$', '|a'), None) - self.assertEqual(regex.match(r'^(?:(a)|c)(\1)$', 'aa')[:], ('aa', 'a', - 'a')) - self.assertEqual(regex.match(r'^(?:(a)|c)(\1)?$', 'c')[:], ('c', None, - None)) - - self.assertEqual(regex.findall("(?i)(.{1,40}?),(.{1,40}?)(?:;)+(.{1,80}).{1,40}?\\3(\ |;)+(.{1,80}?)\\1", - "TEST, BEST; LEST ; Lest 123 Test, Best"), [('TEST', ' BEST', - ' LEST', ' ', '123 ')]) - - def test_groupdict(self): - self.assertEqual(regex.match('(?Pfirst) (?Psecond)', - 'first second').groupdict(), {'first': 'first', 'second': 'second'}) - - def test_expand(self): - self.assertEqual(regex.match("(?Pfirst) (?Psecond)", - "first second").expand(r"\2 \1 \g \g"), - 'second first second first') - - def test_repeat_minmax(self): - self.assertEqual(regex.match(r"^(\w){1}$", "abc"), None) - self.assertEqual(regex.match(r"^(\w){1}?$", "abc"), None) - self.assertEqual(regex.match(r"^(\w){1,2}$", "abc"), None) - self.assertEqual(regex.match(r"^(\w){1,2}?$", "abc"), None) - - self.assertEqual(regex.match(r"^(\w){3}$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){1,3}$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){1,4}$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){3,4}?$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){3}?$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){1,3}?$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){1,4}?$", "abc")[1], 'c') - self.assertEqual(regex.match(r"^(\w){3,4}?$", "abc")[1], 'c') - - self.assertEqual(regex.match("^x{1}$", "xxx"), None) - self.assertEqual(regex.match("^x{1}?$", "xxx"), None) - self.assertEqual(regex.match("^x{1,2}$", "xxx"), None) - self.assertEqual(regex.match("^x{1,2}?$", "xxx"), None) - - self.assertEqual(regex.match("^x{1}", "xxx")[0], 'x') - self.assertEqual(regex.match("^x{1}?", "xxx")[0], 'x') - self.assertEqual(regex.match("^x{0,1}", "xxx")[0], 'x') - self.assertEqual(regex.match("^x{0,1}?", "xxx")[0], '') - - self.assertEqual(bool(regex.match("^x{3}$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{1,3}$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{1,4}$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{3,4}?$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{3}?$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{1,3}?$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{1,4}?$", "xxx")), True) - self.assertEqual(bool(regex.match("^x{3,4}?$", "xxx")), True) - - self.assertEqual(regex.match("^x{}$", "xxx"), None) - self.assertEqual(bool(regex.match("^x{}$", "x{}")), True) - - def test_getattr(self): - self.assertEqual(regex.compile("(?i)(a)(b)").pattern, '(?i)(a)(b)') - self.assertEqual(regex.compile("(?i)(a)(b)").flags, regex.A | regex.I | - regex.DEFAULT_VERSION) - self.assertEqual(regex.compile(u"(?i)(a)(b)").flags, regex.I | regex.U - | regex.DEFAULT_VERSION) - self.assertEqual(regex.compile("(?i)(a)(b)").groups, 2) - self.assertEqual(regex.compile("(?i)(a)(b)").groupindex, {}) - - self.assertEqual(regex.compile("(?i)(?Pa)(?Pb)").groupindex, - {'first': 1, 'other': 2}) - - self.assertEqual(regex.match("(a)", "a").pos, 0) - self.assertEqual(regex.match("(a)", "a").endpos, 1) - - self.assertEqual(regex.search("b(c)", "abcdef").pos, 0) - self.assertEqual(regex.search("b(c)", "abcdef").endpos, 6) - self.assertEqual(regex.search("b(c)", "abcdef").span(), (1, 3)) - self.assertEqual(regex.search("b(c)", "abcdef").span(1), (2, 3)) - - self.assertEqual(regex.match("(a)", "a").string, 'a') - self.assertEqual(regex.match("(a)", "a").regs, ((0, 1), (0, 1))) - self.assertEqual(repr(type(regex.match("(a)", "a").re)), - self.PATTERN_CLASS) - - # Issue 14260. - p = regex.compile(r'abc(?Pdef)') - p.groupindex["n"] = 0 - self.assertEqual(p.groupindex["n"], 1) - - def test_special_escapes(self): - self.assertEqual(regex.search(r"\b(b.)\b", "abcd abc bcd bx")[1], 'bx') - self.assertEqual(regex.search(r"\B(b.)\B", "abc bcd bc abxd")[1], 'bx') - self.assertEqual(regex.search(r"\b(b.)\b", "abcd abc bcd bx", - regex.LOCALE)[1], 'bx') - self.assertEqual(regex.search(r"\B(b.)\B", "abc bcd bc abxd", - regex.LOCALE)[1], 'bx') - self.assertEqual(regex.search(ur"\b(b.)\b", u"abcd abc bcd bx", - regex.UNICODE)[1], u'bx') - self.assertEqual(regex.search(ur"\B(b.)\B", u"abc bcd bc abxd", - regex.UNICODE)[1], u'bx') - - self.assertEqual(regex.search(r"^abc$", "\nabc\n", regex.M)[0], 'abc') - self.assertEqual(regex.search(r"^\Aabc\Z$", "abc", regex.M)[0], 'abc') - self.assertEqual(regex.search(r"^\Aabc\Z$", "\nabc\n", regex.M), None) - - self.assertEqual(regex.search(ur"\b(b.)\b", u"abcd abc bcd bx")[1], - u'bx') - self.assertEqual(regex.search(ur"\B(b.)\B", u"abc bcd bc abxd")[1], - u'bx') - self.assertEqual(regex.search(ur"^abc$", u"\nabc\n", regex.M)[0], - u'abc') - self.assertEqual(regex.search(ur"^\Aabc\Z$", u"abc", regex.M)[0], - u'abc') - self.assertEqual(regex.search(ur"^\Aabc\Z$", u"\nabc\n", regex.M), - None) - - self.assertEqual(regex.search(r"\d\D\w\W\s\S", "1aa! a")[0], '1aa! a') - self.assertEqual(regex.search(r"\d\D\w\W\s\S", "1aa! a", - regex.LOCALE)[0], '1aa! a') - self.assertEqual(regex.search(ur"\d\D\w\W\s\S", u"1aa! a", - regex.UNICODE)[0], u'1aa! a') - - def test_bigcharset(self): - self.assertEqual(regex.match(ur"(?u)([\u2222\u2223])", u"\u2222")[1], - u'\u2222') - self.assertEqual(regex.match(ur"(?u)([\u2222\u2223])", u"\u2222", - regex.UNICODE)[1], u'\u2222') - self.assertEqual(u"".join(regex.findall(u".", - u"e\xe8\xe9\xea\xeb\u0113\u011b\u0117", flags=regex.UNICODE)), - u'e\xe8\xe9\xea\xeb\u0113\u011b\u0117') - self.assertEqual(u"".join(regex.findall(ur"[e\xe8\xe9\xea\xeb\u0113\u011b\u0117]", - u"e\xe8\xe9\xea\xeb\u0113\u011b\u0117", flags=regex.UNICODE)), - u'e\xe8\xe9\xea\xeb\u0113\u011b\u0117') - self.assertEqual(u"".join(regex.findall(ur"e|\xe8|\xe9|\xea|\xeb|\u0113|\u011b|\u0117", - u"e\xe8\xe9\xea\xeb\u0113\u011b\u0117", flags=regex.UNICODE)), - u'e\xe8\xe9\xea\xeb\u0113\u011b\u0117') - - def test_anyall(self): - self.assertEqual(regex.match("a.b", "a\nb", regex.DOTALL)[0], "a\nb") - self.assertEqual(regex.match("a.*b", "a\n\nb", regex.DOTALL)[0], - "a\n\nb") - - def test_non_consuming(self): - self.assertEqual(regex.match(r"(a(?=\s[^a]))", "a b")[1], 'a') - self.assertEqual(regex.match(r"(a(?=\s[^a]*))", "a b")[1], 'a') - self.assertEqual(regex.match(r"(a(?=\s[abc]))", "a b")[1], 'a') - self.assertEqual(regex.match(r"(a(?=\s[abc]*))", "a bc")[1], 'a') - self.assertEqual(regex.match(r"(a)(?=\s\1)", "a a")[1], 'a') - self.assertEqual(regex.match(r"(a)(?=\s\1*)", "a aa")[1], 'a') - self.assertEqual(regex.match(r"(a)(?=\s(abc|a))", "a a")[1], 'a') - - self.assertEqual(regex.match(r"(a(?!\s[^a]))", "a a")[1], 'a') - self.assertEqual(regex.match(r"(a(?!\s[abc]))", "a d")[1], 'a') - self.assertEqual(regex.match(r"(a)(?!\s\1)", "a b")[1], 'a') - self.assertEqual(regex.match(r"(a)(?!\s(abc|a))", "a b")[1], 'a') - - def test_ignore_case(self): - self.assertEqual(regex.match("abc", "ABC", regex.I)[0], 'ABC') - self.assertEqual(regex.match(u"abc", u"ABC", regex.I)[0], u'ABC') - - self.assertEqual(regex.match(r"(a\s[^a]*)", "a bb", regex.I)[1], - 'a bb') - self.assertEqual(regex.match(r"(a\s[abc])", "a b", regex.I)[1], 'a b') - self.assertEqual(regex.match(r"(a\s[abc]*)", "a bb", regex.I)[1], - 'a bb') - self.assertEqual(regex.match(r"((a)\s\2)", "a a", regex.I)[1], 'a a') - self.assertEqual(regex.match(r"((a)\s\2*)", "a aa", regex.I)[1], - 'a aa') - self.assertEqual(regex.match(r"((a)\s(abc|a))", "a a", regex.I)[1], - 'a a') - self.assertEqual(regex.match(r"((a)\s(abc|a)*)", "a aa", regex.I)[1], - 'a aa') - - # Issue 3511. - self.assertEqual(regex.match(r"[Z-a]", "_").span(), (0, 1)) - self.assertEqual(regex.match(r"(?i)[Z-a]", "_").span(), (0, 1)) - - self.assertEqual(bool(regex.match(ur"(?iu)nao", u"nAo")), True) - self.assertEqual(bool(regex.match(ur"(?iu)n\xE3o", u"n\xC3o")), True) - self.assertEqual(bool(regex.match(ur"(?iu)n\xE3o", u"N\xC3O")), True) - self.assertEqual(bool(regex.match(ur"(?iu)s", u"\u017F")), True) - - def test_case_folding(self): - self.assertEqual(regex.search(ur"(?fiu)ss", u"SS").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)SS", u"ss").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)SS", - u"\N{LATIN SMALL LETTER SHARP S}").span(), (0, 1)) - self.assertEqual(regex.search(ur"(?fi)\N{LATIN SMALL LETTER SHARP S}", - u"SS").span(), (0, 2)) - - self.assertEqual(regex.search(ur"(?fiu)\N{LATIN SMALL LIGATURE ST}", - u"ST").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)ST", - u"\N{LATIN SMALL LIGATURE ST}").span(), (0, 1)) - self.assertEqual(regex.search(ur"(?fiu)ST", - u"\N{LATIN SMALL LIGATURE LONG S T}").span(), (0, 1)) - - self.assertEqual(regex.search(ur"(?fiu)SST", - u"\N{LATIN SMALL LETTER SHARP S}t").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)SST", - u"s\N{LATIN SMALL LIGATURE LONG S T}").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)SST", - u"s\N{LATIN SMALL LIGATURE ST}").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)\N{LATIN SMALL LIGATURE ST}", - u"SST").span(), (1, 3)) - self.assertEqual(regex.search(ur"(?fiu)SST", - u"s\N{LATIN SMALL LIGATURE ST}").span(), (0, 2)) - - self.assertEqual(regex.search(ur"(?fiu)FFI", - u"\N{LATIN SMALL LIGATURE FFI}").span(), (0, 1)) - self.assertEqual(regex.search(ur"(?fiu)FFI", - u"\N{LATIN SMALL LIGATURE FF}i").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)FFI", - u"f\N{LATIN SMALL LIGATURE FI}").span(), (0, 2)) - self.assertEqual(regex.search(ur"(?fiu)\N{LATIN SMALL LIGATURE FFI}", - u"FFI").span(), (0, 3)) - self.assertEqual(regex.search(ur"(?fiu)\N{LATIN SMALL LIGATURE FF}i", - u"FFI").span(), (0, 3)) - self.assertEqual(regex.search(ur"(?fiu)f\N{LATIN SMALL LIGATURE FI}", - u"FFI").span(), (0, 3)) - - sigma = u"\u03A3\u03C3\u03C2" - for ch1 in sigma: - for ch2 in sigma: - if not regex.match(ur"(?fiu)" + ch1, ch2): - self.fail() - - self.assertEqual(bool(regex.search(ur"(?iuV1)ff", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)ff", u"\uFB01\uFB00")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)fi", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)fi", u"\uFB01\uFB00")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)fffi", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)f\uFB03", - u"\uFB00\uFB01")), True) - self.assertEqual(bool(regex.search(ur"(?iuV1)ff", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)fi", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)fffi", u"\uFB00\uFB01")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)f\uFB03", - u"\uFB00\uFB01")), True) - self.assertEqual(bool(regex.search(ur"(?iuV1)f\uFB01", u"\uFB00i")), - True) - self.assertEqual(bool(regex.search(ur"(?iuV1)f\uFB01", u"\uFB00i")), - True) - - self.assertEqual(regex.findall(ur"(?iuV0)\m(?:word){e<=3}\M(?ne", u"affine", - options=[u"\N{LATIN SMALL LIGATURE FFI}"]).span(), (0, 6)) - self.assertEqual(regex.search(ur"(?fi)a\Lne", - u"a\N{LATIN SMALL LIGATURE FFI}ne", options=[u"ffi"]).span(), (0, 4)) - - def test_category(self): - self.assertEqual(regex.match(r"(\s)", " ")[1], ' ') - - def test_not_literal(self): - self.assertEqual(regex.search(r"\s([^a])", " b")[1], 'b') - self.assertEqual(regex.search(r"\s([^a]*)", " bb")[1], 'bb') - - def test_search_coverage(self): - self.assertEqual(regex.search(r"\s(b)", " b")[1], 'b') - self.assertEqual(regex.search(r"a\s", "a ")[0], 'a ') - - def test_re_escape(self): - p = "" - self.assertEqual(regex.escape(p), p) - for i in range(0, 256): - p += chr(i) - self.assertEqual(bool(regex.match(regex.escape(chr(i)), chr(i))), - True) - self.assertEqual(regex.match(regex.escape(chr(i)), chr(i)).span(), - (0, 1)) - - pat = regex.compile(regex.escape(p)) - self.assertEqual(pat.match(p).span(), (0, 256)) - - def test_constants(self): - if regex.I != regex.IGNORECASE: - self.fail() - if regex.L != regex.LOCALE: - self.fail() - if regex.M != regex.MULTILINE: - self.fail() - if regex.S != regex.DOTALL: - self.fail() - if regex.X != regex.VERBOSE: - self.fail() - - def test_flags(self): - for flag in [regex.I, regex.M, regex.X, regex.S, regex.L]: - self.assertEqual(repr(type(regex.compile('^pattern$', flag))), - self.PATTERN_CLASS) - - def test_sre_character_literals(self): - for i in [0, 8, 16, 32, 64, 127, 128, 255]: - self.assertEqual(bool(regex.match(r"\%03o" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"\%03o0" % i, chr(i) + "0")), - True) - self.assertEqual(bool(regex.match(r"\%03o8" % i, chr(i) + "8")), - True) - self.assertEqual(bool(regex.match(r"\x%02x" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"\x%02x0" % i, chr(i) + "0")), - True) - self.assertEqual(bool(regex.match(r"\x%02xz" % i, chr(i) + "z")), - True) - - self.assertRaisesRegex(regex.error, self.UNKNOWN_GROUP, lambda: - regex.match(r"\911", "")) - - def test_sre_character_class_literals(self): - for i in [0, 8, 16, 32, 64, 127, 128, 255]: - self.assertEqual(bool(regex.match(r"[\%03o]" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"[\%03o0]" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"[\%03o8]" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"[\x%02x]" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"[\x%02x0]" % i, chr(i))), True) - self.assertEqual(bool(regex.match(r"[\x%02xz]" % i, chr(i))), True) - - self.assertRaisesRegex(regex.error, self.BAD_OCTAL_ESCAPE, lambda: - regex.match(r"[\911]", "")) - - def test_bug_113254(self): - self.assertEqual(regex.match(r'(a)|(b)', 'b').start(1), -1) - self.assertEqual(regex.match(r'(a)|(b)', 'b').end(1), -1) - self.assertEqual(regex.match(r'(a)|(b)', 'b').span(1), (-1, -1)) - - def test_bug_527371(self): - # Bug described in patches 527371/672491. - self.assertEqual(regex.match(r'(a)?a','a').lastindex, None) - self.assertEqual(regex.match(r'(a)(b)?b','ab').lastindex, 1) - self.assertEqual(regex.match(r'(?Pa)(?Pb)?b','ab').lastgroup, - 'a') - self.assertEqual(regex.match("(?Pa(b))", "ab").lastgroup, 'a') - self.assertEqual(regex.match("((a))", "a").lastindex, 1) - - def test_bug_545855(self): - # Bug 545855 -- This pattern failed to cause a compile error as it - # should, instead provoking a TypeError. - self.assertRaisesRegex(regex.error, self.BAD_SET, lambda: - regex.compile('foo[a-')) - - def test_bug_418626(self): - # Bugs 418626 at al. -- Testing Greg Chapman's addition of op code - # SRE_OP_MIN_REPEAT_ONE for eliminating recursion on simple uses of - # pattern '*?' on a long string. - self.assertEqual(regex.match('.*?c', 10000 * 'ab' + 'cd').end(0), - 20001) - self.assertEqual(regex.match('.*?cd', 5000 * 'ab' + 'c' + 5000 * 'ab' + - 'cde').end(0), 20003) - self.assertEqual(regex.match('.*?cd', 20000 * 'abc' + 'de').end(0), - 60001) - # Non-simple '*?' still used to hit the recursion limit, before the - # non-recursive scheme was implemented. - self.assertEqual(regex.search('(a|b)*?c', 10000 * 'ab' + 'cd').end(0), - 20001) - - def test_bug_612074(self): - pat = u"[" + regex.escape(u"\u2039") + u"]" - self.assertEqual(regex.compile(pat) and 1, 1) - - def test_stack_overflow(self): - # Nasty cases that used to overflow the straightforward recursive - # implementation of repeated groups. - self.assertEqual(regex.match('(x)*', 50000 * 'x')[1], 'x') - self.assertEqual(regex.match('(x)*y', 50000 * 'x' + 'y')[1], 'x') - self.assertEqual(regex.match('(x)*?y', 50000 * 'x' + 'y')[1], 'x') - - def test_scanner(self): - def s_ident(scanner, token): return token - def s_operator(scanner, token): return "op%s" % token - def s_float(scanner, token): return float(token) - def s_int(scanner, token): return int(token) - - scanner = regex.Scanner([(r"[a-zA-Z_]\w*", s_ident), (r"\d+\.\d*", - s_float), (r"\d+", s_int), (r"=|\+|-|\*|/", s_operator), (r"\s+", - None), ]) - - self.assertEqual(repr(type(scanner.scanner.scanner("").pattern)), - self.PATTERN_CLASS) - - self.assertEqual(scanner.scan("sum = 3*foo + 312.50 + bar"), (['sum', - 'op=', 3, 'op*', 'foo', 'op+', 312.5, 'op+', 'bar'], '')) - - def test_bug_448951(self): - # Bug 448951 (similar to 429357, but with single char match). - # (Also test greedy matches.) - for op in '', '?', '*': - self.assertEqual(regex.match(r'((.%s):)?z' % op, 'z')[:], ('z', - None, None)) - self.assertEqual(regex.match(r'((.%s):)?z' % op, 'a:z')[:], ('a:z', - 'a:', 'a')) - - def test_bug_725106(self): - # Capturing groups in alternatives in repeats. - self.assertEqual(regex.match('^((a)|b)*', 'abc')[:], ('ab', 'b', 'a')) - self.assertEqual(regex.match('^(([ab])|c)*', 'abc')[:], ('abc', 'c', - 'b')) - self.assertEqual(regex.match('^((d)|[ab])*', 'abc')[:], ('ab', 'b', - None)) - self.assertEqual(regex.match('^((a)c|[ab])*', 'abc')[:], ('ab', 'b', - None)) - self.assertEqual(regex.match('^((a)|b)*?c', 'abc')[:], ('abc', 'b', - 'a')) - self.assertEqual(regex.match('^(([ab])|c)*?d', 'abcd')[:], ('abcd', - 'c', 'b')) - self.assertEqual(regex.match('^((d)|[ab])*?c', 'abc')[:], ('abc', 'b', - None)) - self.assertEqual(regex.match('^((a)c|[ab])*?c', 'abc')[:], ('abc', 'b', - None)) - - def test_bug_725149(self): - # Mark_stack_base restoring before restoring marks. - self.assertEqual(regex.match('(a)(?:(?=(b)*)c)*', 'abb')[:], ('a', 'a', - None)) - self.assertEqual(regex.match('(a)((?!(b)*))*', 'abb')[:], ('a', 'a', - None, None)) - - def test_bug_764548(self): - # Bug 764548, regex.compile() barfs on str/unicode subclasses. - class my_unicode(str): pass - pat = regex.compile(my_unicode("abc")) - self.assertEqual(pat.match("xyz"), None) - - def test_finditer(self): - it = regex.finditer(r":+", "a:b::c:::d") - self.assertEqual([item[0] for item in it], [':', '::', ':::']) - - def test_bug_926075(self): - if regex.compile('bug_926075') is regex.compile(u'bug_926075'): - self.fail() - - def test_bug_931848(self): - pattern = u"[\u002E\u3002\uFF0E\uFF61]" - self.assertEqual(regex.compile(pattern).split("a.b.c"), ['a', 'b', - 'c']) - - def test_bug_581080(self): - it = regex.finditer(r"\s", "a b") - self.assertEqual(it.next().span(), (1, 2)) - self.assertRaises(StopIteration, lambda: it.next()) - - scanner = regex.compile(r"\s").scanner("a b") - self.assertEqual(scanner.search().span(), (1, 2)) - self.assertEqual(scanner.search(), None) - - def test_bug_817234(self): - it = regex.finditer(r".*", "asdf") - self.assertEqual(it.next().span(), (0, 4)) - self.assertEqual(it.next().span(), (4, 4)) - self.assertRaises(StopIteration, lambda: it.next()) - - def test_empty_array(self): - # SF buf 1647541. - import array - for typecode in 'cbBuhHiIlLfd': - a = array.array(typecode) - self.assertEqual(regex.compile("bla").match(a), None) - self.assertEqual(regex.compile("").match(a)[1 : ], ()) - - def test_inline_flags(self): - # Bug #1700. - upper_char = unichr(0x1ea0) # Latin Capital Letter A with Dot Below - lower_char = unichr(0x1ea1) # Latin Small Letter A with Dot Below - - p = regex.compile(upper_char, regex.I | regex.U) - self.assertEqual(bool(p.match(lower_char)), True) - - p = regex.compile(lower_char, regex.I | regex.U) - self.assertEqual(bool(p.match(upper_char)), True) - - p = regex.compile('(?i)' + upper_char, regex.U) - self.assertEqual(bool(p.match(lower_char)), True) - - p = regex.compile('(?i)' + lower_char, regex.U) - self.assertEqual(bool(p.match(upper_char)), True) - - p = regex.compile('(?iu)' + upper_char) - self.assertEqual(bool(p.match(lower_char)), True) - - p = regex.compile('(?iu)' + lower_char) - self.assertEqual(bool(p.match(upper_char)), True) - - self.assertEqual(bool(regex.match(r"(?i)a", "A")), True) - self.assertEqual(bool(regex.match(r"a(?i)", "A")), True) - self.assertEqual(bool(regex.match(r"(?iV1)a", "A")), True) - self.assertEqual(regex.match(r"a(?iV1)", "A"), None) - - def test_dollar_matches_twice(self): - # $ matches the end of string, and just before the terminating \n. - pattern = regex.compile('$') - self.assertEqual(pattern.sub('#', 'a\nb\n'), 'a\nb#\n#') - self.assertEqual(pattern.sub('#', 'a\nb\nc'), 'a\nb\nc#') - self.assertEqual(pattern.sub('#', '\n'), '#\n#') - - pattern = regex.compile('$', regex.MULTILINE) - self.assertEqual(pattern.sub('#', 'a\nb\n' ), 'a#\nb#\n#') - self.assertEqual(pattern.sub('#', 'a\nb\nc'), 'a#\nb#\nc#') - self.assertEqual(pattern.sub('#', '\n'), '#\n#') - - def test_ascii_and_unicode_flag(self): - # Unicode patterns. - for flags in (0, regex.UNICODE): - pat = regex.compile(u'\xc0', flags | regex.IGNORECASE) - self.assertEqual(bool(pat.match(u'\xe0')), True) - pat = regex.compile(u'\w', flags) - self.assertEqual(bool(pat.match(u'\xe0')), True) - - pat = regex.compile(u'\xc0', regex.ASCII | regex.IGNORECASE) - self.assertEqual(pat.match(u'\xe0'), None) - pat = regex.compile(u'(?a)\xc0', regex.IGNORECASE) - self.assertEqual(pat.match(u'\xe0'), None) - pat = regex.compile(u'\w', regex.ASCII) - self.assertEqual(pat.match(u'\xe0'), None) - pat = regex.compile(u'(?a)\w') - self.assertEqual(pat.match(u'\xe0'), None) - - # String patterns. - for flags in (0, regex.ASCII): - pat = regex.compile('\xc0', flags | regex.IGNORECASE) - self.assertEqual(pat.match('\xe0'), None) - pat = regex.compile('\w') - self.assertEqual(pat.match('\xe0'), None) - self.assertRaisesRegex(ValueError, self.MIXED_FLAGS, lambda: - regex.compile('(?au)\w')) - - def test_subscripting_match(self): - m = regex.match(r'(?\w)', 'xy') - if not m: - self.fail("Failed: expected match but returned None") - elif not m or m[0] != m.group(0) or m[1] != m.group(1): - self.fail("Failed") - if not m: - self.fail("Failed: expected match but returned None") - elif m[:] != ('x', 'x'): - self.fail("Failed: expected \"('x', 'x')\" but got %s instead" % - repr(m[:])) - - def test_new_named_groups(self): - m0 = regex.match(r'(?P\w)', 'x') - m1 = regex.match(r'(?\w)', 'x') - if not (m0 and m1 and m0[:] == m1[:]): - self.fail("Failed") - - def test_properties(self): - self.assertEqual(regex.match('(?i)\xC0', '\xE0'), None) - self.assertEqual(regex.match(r'(?i)\xC0', '\xE0'), None) - self.assertEqual(regex.match(r'\w', '\xE0'), None) - self.assertEqual(bool(regex.match(ur'(?u)\w', u'\xE0')), True) - - # Dropped the following test. It's not possible to determine what the - # correct result should be in the general case. -# self.assertEqual(bool(regex.match(r'(?L)\w', '\xE0')), -# '\xE0'.isalnum()) - - self.assertEqual(bool(regex.match(r'(?L)\d', '0')), True) - self.assertEqual(bool(regex.match(r'(?L)\s', ' ')), True) - self.assertEqual(bool(regex.match(r'(?L)\w', 'a')), True) - self.assertEqual(regex.match(r'(?L)\d', '?'), None) - self.assertEqual(regex.match(r'(?L)\s', '?'), None) - self.assertEqual(regex.match(r'(?L)\w', '?'), None) - - self.assertEqual(regex.match(r'(?L)\D', '0'), None) - self.assertEqual(regex.match(r'(?L)\S', ' '), None) - self.assertEqual(regex.match(r'(?L)\W', 'a'), None) - self.assertEqual(bool(regex.match(r'(?L)\D', '?')), True) - self.assertEqual(bool(regex.match(r'(?L)\S', '?')), True) - self.assertEqual(bool(regex.match(r'(?L)\W', '?')), True) - - self.assertEqual(bool(regex.match(ur'(?u)\p{Cyrillic}', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{IsCyrillic}', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{Script=Cyrillic}', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{InCyrillic}', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{Block=Cyrillic}', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:Cyrillic:]]', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:IsCyrillic:]]', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:Script=Cyrillic:]]', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:InCyrillic:]]', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:Block=Cyrillic:]]', - u'\N{CYRILLIC CAPITAL LETTER A}')), True) - - self.assertEqual(bool(regex.match(ur'(?u)\P{Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\P{IsCyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\P{Script=Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\P{InCyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\P{Block=Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{^Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{^IsCyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{^Script=Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{^InCyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{^Block=Cyrillic}', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:^Cyrillic:]]', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:^IsCyrillic:]]', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:^Script=Cyrillic:]]', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:^InCyrillic:]]', - u'\N{LATIN CAPITAL LETTER A}')), True) - self.assertEqual(bool(regex.match(ur'(?u)[[:^Block=Cyrillic:]]', - u'\N{LATIN CAPITAL LETTER A}')), True) - - self.assertEqual(bool(regex.match(ur'(?u)\d', u'0')), True) - self.assertEqual(bool(regex.match(ur'(?u)\s', u' ')), True) - self.assertEqual(bool(regex.match(ur'(?u)\w', u'A')), True) - self.assertEqual(regex.match(ur"(?u)\d", u"?"), None) - self.assertEqual(regex.match(ur"(?u)\s", u"?"), None) - self.assertEqual(regex.match(ur"(?u)\w", u"?"), None) - self.assertEqual(regex.match(ur"(?u)\D", u"0"), None) - self.assertEqual(regex.match(ur"(?u)\S", u" "), None) - self.assertEqual(regex.match(ur"(?u)\W", u"A"), None) - self.assertEqual(bool(regex.match(ur'(?u)\D', u'?')), True) - self.assertEqual(bool(regex.match(ur'(?u)\S', u'?')), True) - self.assertEqual(bool(regex.match(ur'(?u)\W', u'?')), True) - - self.assertEqual(bool(regex.match(ur'(?u)\p{L}', u'A')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{L}', u'a')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{Lu}', u'A')), True) - self.assertEqual(bool(regex.match(ur'(?u)\p{Ll}', u'a')), True) - - self.assertEqual(bool(regex.match(ur'(?u)(?i)a', u'a')), True) - self.assertEqual(bool(regex.match(ur'(?u)(?i)a', u'A')), True) - - self.assertEqual(bool(regex.match(ur'(?u)\w', u'0')), True) - self.assertEqual(bool(regex.match(ur'(?u)\w', u'a')), True) - self.assertEqual(bool(regex.match(ur'(?u)\w', u'_')), True) - - self.assertEqual(regex.match(ur"(?u)\X", u"\xE0").span(), (0, 1)) - self.assertEqual(regex.match(ur"(?u)\X", u"a\u0300").span(), (0, 2)) - self.assertEqual(regex.findall(ur"(?u)\X", - u"a\xE0a\u0300e\xE9e\u0301"), [u'a', u'\xe0', u'a\u0300', u'e', - u'\xe9', u'e\u0301']) - self.assertEqual(regex.findall(ur"(?u)\X{3}", - u"a\xE0a\u0300e\xE9e\u0301"), [u'a\xe0a\u0300', u'e\xe9e\u0301']) - self.assertEqual(regex.findall(ur"(?u)\X", u"\r\r\n\u0301A\u0301"), - [u'\r', u'\r\n', u'\u0301', u'A\u0301']) - - self.assertEqual(bool(regex.match(ur'(?u)\p{Ll}', u'a')), True) - - chars_u = u"-09AZaz_\u0393\u03b3" - chars_b = "-09AZaz_" - word_set = set("Ll Lm Lo Lt Lu Mc Me Mn Nd Nl No Pc".split()) - - tests = [ - (ur"(?u)\w", chars_u, u"09AZaz_\u0393\u03b3"), - (ur"(?u)[[:word:]]", chars_u, u"09AZaz_\u0393\u03b3"), - (ur"(?u)\W", chars_u, u"-"), - (ur"(?u)[[:^word:]]", chars_u, u"-"), - (ur"(?u)\d", chars_u, u"09"), - (ur"(?u)[[:digit:]]", chars_u, u"09"), - (ur"(?u)\D", chars_u, u"-AZaz_\u0393\u03b3"), - (ur"(?u)[[:^digit:]]", chars_u, u"-AZaz_\u0393\u03b3"), - (ur"(?u)[[:alpha:]]", chars_u, u"AZaz\u0393\u03b3"), - (ur"(?u)[[:^alpha:]]", chars_u, u"-09_"), - (ur"(?u)[[:alnum:]]", chars_u, u"09AZaz\u0393\u03b3"), - (ur"(?u)[[:^alnum:]]", chars_u, u"-_"), - (ur"(?u)[[:xdigit:]]", chars_u, u"09Aa"), - (ur"(?u)[[:^xdigit:]]", chars_u, u"-Zz_\u0393\u03b3"), - (ur"(?u)\p{InBasicLatin}", u"a\xE1", u"a"), - (ur"(?u)\P{InBasicLatin}", u"a\xE1", u"\xE1"), - (ur"(?iu)\p{InBasicLatin}", u"a\xE1", u"a"), - (ur"(?iu)\P{InBasicLatin}", u"a\xE1", u"\xE1"), - - (r"(?L)\w", chars_b, "09AZaz_"), - (r"(?L)[[:word:]]", chars_b, "09AZaz_"), - (r"(?L)\W", chars_b, "-"), - (r"(?L)[[:^word:]]", chars_b, "-"), - (r"(?L)\d", chars_b, "09"), - (r"(?L)[[:digit:]]", chars_b, "09"), - (r"(?L)\D", chars_b, "-AZaz_"), - (r"(?L)[[:^digit:]]", chars_b, "-AZaz_"), - (r"(?L)[[:alpha:]]", chars_b, "AZaz"), - (r"(?L)[[:^alpha:]]", chars_b, "-09_"), - (r"(?L)[[:alnum:]]", chars_b, "09AZaz"), - (r"(?L)[[:^alnum:]]", chars_b, "-_"), - (r"(?L)[[:xdigit:]]", chars_b, "09Aa"), - (r"(?L)[[:^xdigit:]]", chars_b, "-Zz_"), - - (r"\w", chars_b, "09AZaz_"), - (r"[[:word:]]", chars_b, "09AZaz_"), - (r"\W", chars_b, "-"), - (r"[[:^word:]]", chars_b, "-"), - (r"\d", chars_b, "09"), - (r"[[:digit:]]", chars_b, "09"), - (r"\D", chars_b, "-AZaz_"), - (r"[[:^digit:]]", chars_b, "-AZaz_"), - (r"[[:alpha:]]", chars_b, "AZaz"), - (r"[[:^alpha:]]", chars_b, "-09_"), - (r"[[:alnum:]]", chars_b, "09AZaz"), - (r"[[:^alnum:]]", chars_b, "-_"), - (r"[[:xdigit:]]", chars_b, "09Aa"), - (r"[[:^xdigit:]]", chars_b, "-Zz_"), - ] - for pattern, chars, expected in tests: - try: - if chars[ : 0].join(regex.findall(pattern, chars)) != expected: - self.fail("Failed: %s" % pattern) - except Exception, e: - self.fail("Failed: %s raised %s" % (pattern, repr(e))) - - self.assertEqual(bool(regex.match(ur"(?u)\p{NumericValue=0}", u"0")), - True) - self.assertEqual(bool(regex.match(ur"(?u)\p{NumericValue=1/2}", - u"\N{VULGAR FRACTION ONE HALF}")), True) - self.assertEqual(bool(regex.match(ur"(?u)\p{NumericValue=0.5}", - u"\N{VULGAR FRACTION ONE HALF}")), True) - - def test_word_class(self): - self.assertEqual(regex.findall(ur"(?u)\w+", - u" \u0939\u093f\u0928\u094d\u0926\u0940,"), - [u'\u0939\u093f\u0928\u094d\u0926\u0940']) - self.assertEqual(regex.findall(ur"(?u)\W+", - u" \u0939\u093f\u0928\u094d\u0926\u0940,"), [u' ', u',']) - self.assertEqual(regex.split(ur"(?uV1)\b", - u" \u0939\u093f\u0928\u094d\u0926\u0940,"), [u' ', - u'\u0939\u093f\u0928\u094d\u0926\u0940', u',']) - self.assertEqual(regex.split(ur"(?uV1)\B", - u" \u0939\u093f\u0928\u094d\u0926\u0940,"), [u'', u' \u0939', - u'\u093f', u'\u0928', u'\u094d', u'\u0926', u'\u0940,', u'']) - - def test_search_anchor(self): - self.assertEqual(regex.findall(r"\G\w{2}", "abcd ef"), ['ab', 'cd']) - - def test_search_reverse(self): - self.assertEqual(regex.findall(r"(?r).", "abc"), ['c', 'b', 'a']) - self.assertEqual(regex.findall(r"(?r).", "abc", overlapped=True), ['c', - 'b', 'a']) - self.assertEqual(regex.findall(r"(?r)..", "abcde"), ['de', 'bc']) - self.assertEqual(regex.findall(r"(?r)..", "abcde", overlapped=True), - ['de', 'cd', 'bc', 'ab']) - self.assertEqual(regex.findall(r"(?r)(.)(-)(.)", "a-b-c", - overlapped=True), [("b", "-", "c"), ("a", "-", "b")]) - - self.assertEqual([m[0] for m in regex.finditer(r"(?r).", "abc")], ['c', - 'b', 'a']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)..", "abcde", - overlapped=True)], ['de', 'cd', 'bc', 'ab']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r).", "abc")], ['c', - 'b', 'a']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)..", "abcde", - overlapped=True)], ['de', 'cd', 'bc', 'ab']) - - self.assertEqual(regex.findall(r"^|\w+", "foo bar"), ['', 'foo', - 'bar']) - self.assertEqual(regex.findall(r"(?V1)^|\w+", "foo bar"), ['', 'foo', - 'bar']) - self.assertEqual(regex.findall(r"(?r)^|\w+", "foo bar"), ['bar', 'foo', - '']) - self.assertEqual(regex.findall(r"(?rV1)^|\w+", "foo bar"), ['bar', - 'foo', '']) - - self.assertEqual([m[0] for m in regex.finditer(r"^|\w+", "foo bar")], - ['', 'foo', 'bar']) - self.assertEqual([m[0] for m in regex.finditer(r"(?V1)^|\w+", - "foo bar")], ['', 'foo', 'bar']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)^|\w+", - "foo bar")], ['bar', 'foo', '']) - self.assertEqual([m[0] for m in regex.finditer(r"(?rV1)^|\w+", - "foo bar")], ['bar', 'foo', '']) - - self.assertEqual(regex.findall(r"\G\w{2}", "abcd ef"), ['ab', 'cd']) - self.assertEqual(regex.findall(r".{2}(?<=\G.*)", "abcd"), ['ab', 'cd']) - self.assertEqual(regex.findall(r"(?r)\G\w{2}", "abcd ef"), []) - self.assertEqual(regex.findall(r"(?r)\w{2}\G", "abcd ef"), ['ef']) - - self.assertEqual(regex.findall(r"q*", "qqwe"), ['qq', '', '', '']) - self.assertEqual(regex.findall(r"(?V1)q*", "qqwe"), ['qq', '', '', '']) - self.assertEqual(regex.findall(r"(?r)q*", "qqwe"), ['', '', 'qq', '']) - self.assertEqual(regex.findall(r"(?rV1)q*", "qqwe"), ['', '', 'qq', - '']) - - self.assertEqual(regex.findall(".", "abcd", pos=1, endpos=3), ['b', - 'c']) - self.assertEqual(regex.findall(".", "abcd", pos=1, endpos=-1), ['b', - 'c']) - self.assertEqual([m[0] for m in regex.finditer(".", "abcd", pos=1, - endpos=3)], ['b', 'c']) - self.assertEqual([m[0] for m in regex.finditer(".", "abcd", pos=1, - endpos=-1)], ['b', 'c']) - - self.assertEqual([m[0] for m in regex.finditer("(?r).", "abcd", pos=1, - endpos=3)], ['c', 'b']) - self.assertEqual([m[0] for m in regex.finditer("(?r).", "abcd", pos=1, - endpos=-1)], ['c', 'b']) - self.assertEqual(regex.findall("(?r).", "abcd", pos=1, endpos=3), ['c', - 'b']) - self.assertEqual(regex.findall("(?r).", "abcd", pos=1, endpos=-1), - ['c', 'b']) - - self.assertEqual(regex.findall(r"[ab]", "aB", regex.I), ['a', 'B']) - self.assertEqual(regex.findall(r"(?r)[ab]", "aB", regex.I), ['B', 'a']) - - self.assertEqual(regex.findall(r"(?r).{2}", "abc"), ['bc']) - self.assertEqual(regex.findall(r"(?r).{2}", "abc", overlapped=True), - ['bc', 'ab']) - self.assertEqual(regex.findall(r"(\w+) (\w+)", - "first second third fourth fifth"), [('first', 'second'), ('third', - 'fourth')]) - self.assertEqual(regex.findall(r"(?r)(\w+) (\w+)", - "first second third fourth fifth"), [('fourth', 'fifth'), ('second', - 'third')]) - - self.assertEqual([m[0] for m in regex.finditer(r"(?r).{2}", "abc")], - ['bc']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r).{2}", "abc", - overlapped=True)], ['bc', 'ab']) - self.assertEqual([m[0] for m in regex.finditer(r"(\w+) (\w+)", - "first second third fourth fifth")], ['first second', - 'third fourth']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)(\w+) (\w+)", - "first second third fourth fifth")], ['fourth fifth', - 'second third']) - - self.assertEqual(regex.search("abcdef", "abcdef").span(), (0, 6)) - self.assertEqual(regex.search("(?r)abcdef", "abcdef").span(), (0, 6)) - self.assertEqual(regex.search("(?i)abcdef", "ABCDEF").span(), (0, 6)) - self.assertEqual(regex.search("(?ir)abcdef", "ABCDEF").span(), (0, 6)) - - self.assertEqual(regex.sub(r"(.)", r"\1", "abc"), 'abc') - self.assertEqual(regex.sub(r"(?r)(.)", r"\1", "abc"), 'abc') - - def test_atomic(self): - # Issue 433030. - self.assertEqual(regex.search(r"(?>a*)a", "aa"), None) - - def test_possessive(self): - # Single-character non-possessive. - self.assertEqual(regex.search(r"a?a", "a").span(), (0, 1)) - self.assertEqual(regex.search(r"a*a", "aaa").span(), (0, 3)) - self.assertEqual(regex.search(r"a+a", "aaa").span(), (0, 3)) - self.assertEqual(regex.search(r"a{1,3}a", "aaa").span(), (0, 3)) - - # Multiple-character non-possessive. - self.assertEqual(regex.search(r"(?:ab)?ab", "ab").span(), (0, 2)) - self.assertEqual(regex.search(r"(?:ab)*ab", "ababab").span(), (0, 6)) - self.assertEqual(regex.search(r"(?:ab)+ab", "ababab").span(), (0, 6)) - self.assertEqual(regex.search(r"(?:ab){1,3}ab", "ababab").span(), (0, - 6)) - - # Single-character possessive. - self.assertEqual(regex.search(r"a?+a", "a"), None) - self.assertEqual(regex.search(r"a*+a", "aaa"), None) - self.assertEqual(regex.search(r"a++a", "aaa"), None) - self.assertEqual(regex.search(r"a{1,3}+a", "aaa"), None) - - # Multiple-character possessive. - self.assertEqual(regex.search(r"(?:ab)?+ab", "ab"), None) - self.assertEqual(regex.search(r"(?:ab)*+ab", "ababab"), None) - self.assertEqual(regex.search(r"(?:ab)++ab", "ababab"), None) - self.assertEqual(regex.search(r"(?:ab){1,3}+ab", "ababab"), None) - - def test_zerowidth(self): - # Issue 3262. - self.assertEqual(regex.split(r"\b", "a b"), ['a b']) - self.assertEqual(regex.split(r"(?V1)\b", "a b"), ['', 'a', ' ', 'b', - '']) - - # Issue 1647489. - self.assertEqual(regex.findall(r"^|\w+", "foo bar"), ['', 'foo', - 'bar']) - self.assertEqual([m[0] for m in regex.finditer(r"^|\w+", "foo bar")], - ['', 'foo', 'bar']) - self.assertEqual(regex.findall(r"(?r)^|\w+", "foo bar"), ['bar', 'foo', - '']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)^|\w+", - "foo bar")], ['bar', 'foo', '']) - self.assertEqual(regex.findall(r"(?V1)^|\w+", "foo bar"), ['', 'foo', - 'bar']) - self.assertEqual([m[0] for m in regex.finditer(r"(?V1)^|\w+", - "foo bar")], ['', 'foo', 'bar']) - self.assertEqual(regex.findall(r"(?rV1)^|\w+", "foo bar"), ['bar', - 'foo', '']) - self.assertEqual([m[0] for m in regex.finditer(r"(?rV1)^|\w+", - "foo bar")], ['bar', 'foo', '']) - - self.assertEqual(regex.split("", "xaxbxc"), ['xaxbxc']) - self.assertEqual([m for m in regex.splititer("", "xaxbxc")], - ['xaxbxc']) - - self.assertEqual(regex.split("(?r)", "xaxbxc"), ['xaxbxc']) - self.assertEqual([m for m in regex.splititer("(?r)", "xaxbxc")], - ['xaxbxc']) - - self.assertEqual(regex.split("(?V1)", "xaxbxc"), ['', 'x', 'a', 'x', - 'b', 'x', 'c', '']) - self.assertEqual([m for m in regex.splititer("(?V1)", "xaxbxc")], ['', - 'x', 'a', 'x', 'b', 'x', 'c', '']) - - self.assertEqual(regex.split("(?rV1)", "xaxbxc"), ['', 'c', 'x', 'b', - 'x', 'a', 'x', '']) - self.assertEqual([m for m in regex.splititer("(?rV1)", "xaxbxc")], ['', - 'c', 'x', 'b', 'x', 'a', 'x', '']) - - def test_scoped_and_inline_flags(self): - # Issues 433028, 433024, 433027. - self.assertEqual(regex.search(r"(?i)Ab", "ab").span(), (0, 2)) - self.assertEqual(regex.search(r"(?i:A)b", "ab").span(), (0, 2)) - self.assertEqual(regex.search(r"A(?i)b", "ab").span(), (0, 2)) - self.assertEqual(regex.search(r"A(?iV1)b", "ab"), None) - - self.assertRaisesRegex(regex.error, self.CANT_TURN_OFF, lambda: - regex.search(r"(?V0-i)Ab", "ab", flags=regex.I)) - - self.assertEqual(regex.search(r"(?V0)Ab", "ab"), None) - self.assertEqual(regex.search(r"(?V1)Ab", "ab"), None) - self.assertEqual(regex.search(r"(?V1-i)Ab", "ab", flags=regex.I), None) - self.assertEqual(regex.search(r"(?-i:A)b", "ab", flags=regex.I), None) - self.assertEqual(regex.search(r"A(?V1-i)b", "ab", - flags=regex.I).span(), (0, 2)) - - def test_repeated_repeats(self): - # Issue 2537. - self.assertEqual(regex.search(r"(?:a+)+", "aaa").span(), (0, 3)) - self.assertEqual(regex.search(r"(?:(?:ab)+c)+", "abcabc").span(), (0, - 6)) - - def test_lookbehind(self): - self.assertEqual(regex.search(r"123(?<=a\d+)", "a123").span(), (1, 4)) - self.assertEqual(regex.search(r"123(?<=a\d+)", "b123"), None) - self.assertEqual(regex.search(r"123(?[ \t]+\r*$)|(?P(?<=[^\n])\Z)') - self.assertEqual(pat.subn(lambda m: '<' + m.lastgroup + '>', - 'foobar '), ('foobar', 1)) - self.assertEqual([m.group() for m in pat.finditer('foobar ')], [' ', - '']) - pat = regex.compile(r'(?mV1)(?P[ \t]+\r*$)|(?P(?<=[^\n])\Z)') - self.assertEqual(pat.subn(lambda m: '<' + m.lastgroup + '>', - 'foobar '), ('foobar', 2)) - self.assertEqual([m.group() for m in pat.finditer('foobar ')], [' ', - '']) - - def test_overlapped(self): - self.assertEqual(regex.findall(r"..", "abcde"), ['ab', 'cd']) - self.assertEqual(regex.findall(r"..", "abcde", overlapped=True), ['ab', - 'bc', 'cd', 'de']) - self.assertEqual(regex.findall(r"(?r)..", "abcde"), ['de', 'bc']) - self.assertEqual(regex.findall(r"(?r)..", "abcde", overlapped=True), - ['de', 'cd', 'bc', 'ab']) - self.assertEqual(regex.findall(r"(.)(-)(.)", "a-b-c", overlapped=True), - [("a", "-", "b"), ("b", "-", "c")]) - - self.assertEqual([m[0] for m in regex.finditer(r"..", "abcde")], ['ab', - 'cd']) - self.assertEqual([m[0] for m in regex.finditer(r"..", "abcde", - overlapped=True)], ['ab', 'bc', 'cd', 'de']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)..", "abcde")], - ['de', 'bc']) - self.assertEqual([m[0] for m in regex.finditer(r"(?r)..", "abcde", - overlapped=True)], ['de', 'cd', 'bc', 'ab']) - - self.assertEqual([m.groups() for m in regex.finditer(r"(.)(-)(.)", - "a-b-c", overlapped=True)], [("a", "-", "b"), ("b", "-", "c")]) - self.assertEqual([m.groups() for m in regex.finditer(r"(?r)(.)(-)(.)", - "a-b-c", overlapped=True)], [("b", "-", "c"), ("a", "-", "b")]) - - def test_splititer(self): - self.assertEqual(regex.split(r",", "a,b,,c,"), ['a', 'b', '', 'c', '']) - self.assertEqual([m for m in regex.splititer(r",", "a,b,,c,")], ['a', - 'b', '', 'c', '']) - - def test_grapheme(self): - self.assertEqual(regex.match(ur"(?u)\X", u"\xE0").span(), (0, 1)) - self.assertEqual(regex.match(ur"(?u)\X", u"a\u0300").span(), (0, 2)) - - self.assertEqual(regex.findall(ur"(?u)\X", - u"a\xE0a\u0300e\xE9e\u0301"), [u'a', u'\xe0', u'a\u0300', u'e', - u'\xe9', u'e\u0301']) - self.assertEqual(regex.findall(ur"(?u)\X{3}", - u"a\xE0a\u0300e\xE9e\u0301"), [u'a\xe0a\u0300', u'e\xe9e\u0301']) - self.assertEqual(regex.findall(ur"(?u)\X", u"\r\r\n\u0301A\u0301"), - [u'\r', u'\r\n', u'\u0301', u'A\u0301']) - - def test_word_boundary(self): - text = u'The quick ("brown") fox can\'t jump 32.3 feet, right?' - self.assertEqual(regex.split(ur'(?V1)\b', text), [u'', u'The', u' ', - u'quick', u' ("', u'brown', u'") ', u'fox', u' ', u'can', u"'", u't', - u' ', u'jump', u' ', u'32', u'.', u'3', u' ', u'feet', u', ', - u'right', u'?']) - self.assertEqual(regex.split(ur'(?V1w)\b', text), [u'', u'The', u' ', - u'quick', u' ', u'(', u'"', u'brown', u'"', u')', u' ', u'fox', u' ', - u"can't", u' ', u'jump', u' ', u'32.3', u' ', u'feet', u',', u' ', - u'right', u'?', u'']) - - text = u"The fox" - self.assertEqual(regex.split(ur'(?V1)\b', text), [u'', u'The', u' ', - u'fox', u'']) - self.assertEqual(regex.split(ur'(?V1w)\b', text), [u'', u'The', u' ', - u' ', u'fox', u'']) - - text = u"can't aujourd'hui l'objectif" - self.assertEqual(regex.split(ur'(?V1)\b', text), [u'', u'can', u"'", - u't', u' ', u'aujourd', u"'", u'hui', u' ', u'l', u"'", u'objectif', - u'']) - self.assertEqual(regex.split(ur'(?V1w)\b', text), [u'', u"can't", u' ', - u"aujourd'hui", u' ', u"l'", u'objectif', u'']) - - def test_line_boundary(self): - self.assertEqual(regex.findall(r".+", "Line 1\nLine 2\n"), ["Line 1", - "Line 2"]) - self.assertEqual(regex.findall(r".+", "Line 1\rLine 2\r"), - ["Line 1\rLine 2\r"]) - self.assertEqual(regex.findall(r".+", "Line 1\r\nLine 2\r\n"), - ["Line 1\r", "Line 2\r"]) - self.assertEqual(regex.findall(r"(?w).+", "Line 1\nLine 2\n"), - ["Line 1", "Line 2"]) - self.assertEqual(regex.findall(r"(?w).+", "Line 1\rLine 2\r"), - ["Line 1", "Line 2"]) - self.assertEqual(regex.findall(r"(?w).+", "Line 1\r\nLine 2\r\n"), - ["Line 1", "Line 2"]) - - self.assertEqual(regex.search(r"^abc", "abc").start(), 0) - self.assertEqual(regex.search(r"^abc", "\nabc"), None) - self.assertEqual(regex.search(r"^abc", "\rabc"), None) - self.assertEqual(regex.search(r"(?w)^abc", "abc").start(), 0) - self.assertEqual(regex.search(r"(?w)^abc", "\nabc"), None) - self.assertEqual(regex.search(r"(?w)^abc", "\rabc"), None) - - self.assertEqual(regex.search(r"abc$", "abc").start(), 0) - self.assertEqual(regex.search(r"abc$", "abc\n").start(), 0) - self.assertEqual(regex.search(r"abc$", "abc\r"), None) - self.assertEqual(regex.search(r"(?w)abc$", "abc").start(), 0) - self.assertEqual(regex.search(r"(?w)abc$", "abc\n").start(), 0) - self.assertEqual(regex.search(r"(?w)abc$", "abc\r").start(), 0) - - self.assertEqual(regex.search(r"(?m)^abc", "abc").start(), 0) - self.assertEqual(regex.search(r"(?m)^abc", "\nabc").start(), 1) - self.assertEqual(regex.search(r"(?m)^abc", "\rabc"), None) - self.assertEqual(regex.search(r"(?mw)^abc", "abc").start(), 0) - self.assertEqual(regex.search(r"(?mw)^abc", "\nabc").start(), 1) - self.assertEqual(regex.search(r"(?mw)^abc", "\rabc").start(), 1) - - self.assertEqual(regex.search(r"(?m)abc$", "abc").start(), 0) - self.assertEqual(regex.search(r"(?m)abc$", "abc\n").start(), 0) - self.assertEqual(regex.search(r"(?m)abc$", "abc\r"), None) - self.assertEqual(regex.search(r"(?mw)abc$", "abc").start(), 0) - self.assertEqual(regex.search(r"(?mw)abc$", "abc\n").start(), 0) - self.assertEqual(regex.search(r"(?mw)abc$", "abc\r").start(), 0) - - def test_branch_reset(self): - self.assertEqual(regex.match(r"(?:(a)|(b))(c)", "ac").groups(), ('a', - None, 'c')) - self.assertEqual(regex.match(r"(?:(a)|(b))(c)", "bc").groups(), (None, - 'b', 'c')) - self.assertEqual(regex.match(r"(?:(?a)|(?b))(?c)", - "ac").groups(), ('a', None, 'c')) - self.assertEqual(regex.match(r"(?:(?a)|(?b))(?c)", - "bc").groups(), (None, 'b', 'c')) - - self.assertEqual(regex.match(r"(?a)(?:(?b)|(?c))(?d)", - "abd").groups(), ('a', 'b', None, 'd')) - self.assertEqual(regex.match(r"(?a)(?:(?b)|(?c))(?d)", - "acd").groups(), ('a', None, 'c', 'd')) - self.assertEqual(regex.match(r"(a)(?:(b)|(c))(d)", "abd").groups(), - ('a', 'b', None, 'd')) - - self.assertEqual(regex.match(r"(a)(?:(b)|(c))(d)", "acd").groups(), - ('a', None, 'c', 'd')) - self.assertEqual(regex.match(r"(a)(?|(b)|(b))(d)", "abd").groups(), - ('a', 'b', 'd')) - self.assertEqual(regex.match(r"(?|(?a)|(?b))(c)", "ac").groups(), - ('a', None, 'c')) - self.assertEqual(regex.match(r"(?|(?a)|(?b))(c)", "bc").groups(), - (None, 'b', 'c')) - self.assertEqual(regex.match(r"(?|(?a)|(?b))(c)", "ac").groups(), - ('a', 'c')) - - self.assertEqual(regex.match(r"(?|(?a)|(?b))(c)", "bc").groups(), - ('b', 'c')) - - self.assertEqual(regex.match(r"(?|(?a)(?b)|(?c)(?d))(e)", - "abe").groups(), ('a', 'b', 'e')) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(?c)(?d))(e)", - "cde").groups(), ('d', 'c', 'e')) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(?c)(d))(e)", - "abe").groups(), ('a', 'b', 'e')) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(?c)(d))(e)", - "cde").groups(), ('d', 'c', 'e')) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(d))(e)", - "abe").groups(), ('a', 'b', 'e')) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(d))(e)", - "cde").groups(), ('c', 'd', 'e')) - - # Hg issue 87. - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(?d))(e)", - "abe").groups(), ("a", "b", "e")) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(?d))(e)", - "abe").capturesdict(), {"a": ["a"], "b": ["b"]}) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(?d))(e)", - "cde").groups(), ("d", None, "e")) - self.assertEqual(regex.match(r"(?|(?a)(?b)|(c)(?d))(e)", - "cde").capturesdict(), {"a": ["c", "d"], "b": []}) - - def test_set(self): - self.assertEqual(regex.match(r"[a]", "a").span(), (0, 1)) - self.assertEqual(regex.match(r"(?i)[a]", "A").span(), (0, 1)) - self.assertEqual(regex.match(r"[a-b]", r"a").span(), (0, 1)) - self.assertEqual(regex.match(r"(?i)[a-b]", r"A").span(), (0, 1)) - - self.assertEqual(regex.sub(r"(?V0)([][])", r"-", "a[b]c"), "a-b-c") - - self.assertEqual(regex.findall(ur"[\p{Alpha}]", u"a0"), [u"a"]) - self.assertEqual(regex.findall(ur"(?i)[\p{Alpha}]", u"A0"), [u"A"]) - - self.assertEqual(regex.findall(ur"[a\p{Alpha}]", u"ab0"), [u"a", u"b"]) - self.assertEqual(regex.findall(ur"[a\P{Alpha}]", u"ab0"), [u"a", u"0"]) - self.assertEqual(regex.findall(ur"(?i)[a\p{Alpha}]", u"ab0"), [u"a", - u"b"]) - self.assertEqual(regex.findall(ur"(?i)[a\P{Alpha}]", u"ab0"), [u"a", - u"0"]) - - self.assertEqual(regex.findall(ur"[a-b\p{Alpha}]", u"abC0"), [u"a", - u"b", u"C"]) - self.assertEqual(regex.findall(ur"(?i)[a-b\p{Alpha}]", u"AbC0"), [u"A", - u"b", u"C"]) - - self.assertEqual(regex.findall(ur"[\p{Alpha}]", u"a0"), [u"a"]) - self.assertEqual(regex.findall(ur"[\P{Alpha}]", u"a0"), [u"0"]) - self.assertEqual(regex.findall(ur"[^\p{Alpha}]", u"a0"), [u"0"]) - self.assertEqual(regex.findall(ur"[^\P{Alpha}]", u"a0"), [u"a"]) - - self.assertEqual("".join(regex.findall(r"[^\d-h]", "a^b12c-h")), - 'a^bc') - self.assertEqual("".join(regex.findall(r"[^\dh]", "a^b12c-h")), - 'a^bc-') - self.assertEqual("".join(regex.findall(r"[^h\s\db]", "a^b 12c-h")), - 'a^c-') - self.assertEqual("".join(regex.findall(r"[^b\w]", "a b")), ' ') - self.assertEqual("".join(regex.findall(r"[^b\S]", "a b")), ' ') - self.assertEqual("".join(regex.findall(r"[^8\d]", "a 1b2")), 'a b') - - all_chars = u"".join(unichr(c) for c in range(0x100)) - self.assertEqual(len(regex.findall(ur"(?u)\p{ASCII}", all_chars)), 128) - self.assertEqual(len(regex.findall(ur"(?u)\p{Letter}", all_chars)), - 117) - self.assertEqual(len(regex.findall(ur"(?u)\p{Digit}", all_chars)), 10) - - # Set operators - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}&&\p{Letter}]", - all_chars)), 52) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}&&\p{Alnum}&&\p{Letter}]", - all_chars)), 52) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}&&\p{Alnum}&&\p{Digit}]", - all_chars)), 10) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}&&\p{Cc}]", - all_chars)), 33) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}&&\p{Graph}]", - all_chars)), 94) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{ASCII}--\p{Cc}]", - all_chars)), 95) - self.assertEqual(len(regex.findall(ur"(?u)[\p{Letter}\p{Digit}]", - all_chars)), 127) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{Letter}||\p{Digit}]", - all_chars)), 127) - self.assertEqual(len(regex.findall(ur"(?u)\p{HexDigit}", all_chars)), - 22) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{HexDigit}~~\p{Digit}]", - all_chars)), 12) - self.assertEqual(len(regex.findall(ur"(?uV1)[\p{Digit}~~\p{HexDigit}]", - all_chars)), 12) - - self.assertEqual(repr(type(regex.compile(r"(?V0)([][-])"))), - self.PATTERN_CLASS) - self.assertEqual(regex.findall(r"(?V1)[[a-z]--[aei]]", "abc"), ["b", - "c"]) - self.assertEqual(regex.findall(r"(?iV1)[[a-z]--[aei]]", "abc"), ["b", - "c"]) - self.assertEqual(regex.findall("(?V1)[\w--a]","abc"), ["b", "c"]) - self.assertEqual(regex.findall("(?iV1)[\w--a]","abc"), ["b", "c"]) - - def test_various(self): - tests = [ - # Test ?P< and ?P= extensions. - ('(?Pa)', '', '', regex.error, self.BAD_GROUP_NAME), # Begins with a digit. - ('(?Pa)', '', '', regex.error, self.BAD_GROUP_NAME), # Begins with an illegal char. - ('(?Pa)', '', '', regex.error, self.BAD_GROUP_NAME), # Begins with an illegal char. - - # Same tests, for the ?P= form. - ('(?Pa)(?P=foo_123', 'aa', '', regex.error, - self.MISSING_RPAREN), - ('(?Pa)(?P=1)', 'aa', '', regex.error, - self.BAD_GROUP_NAME), - ('(?Pa)(?P=!)', 'aa', '', regex.error, - self.BAD_GROUP_NAME), - ('(?Pa)(?P=foo_124)', 'aa', '', regex.error, - self.UNKNOWN_GROUP), # Backref to undefined group. - - ('(?Pa)', 'a', '1', repr('a')), - ('(?Pa)(?P=foo_123)', 'aa', '1', repr('a')), - - # Mal-formed \g in pattern treated as literal for compatibility. - (r'(?a)\ga)\g<1>', 'aa', '1', repr('a')), - (r'(?a)\g', 'aa', '', repr(None)), - (r'(?a)\g', 'aa', '', regex.error, - self.UNKNOWN_GROUP), # Backref to undefined group. - - ('(?a)', 'a', '1', repr('a')), - (r'(?a)\g', 'aa', '1', repr('a')), - - # Test octal escapes. - ('\\1', 'a', '', regex.error, self.UNKNOWN_GROUP), # Backreference. - ('[\\1]', '\1', '0', "'\\x01'"), # Character. - ('\\09', chr(0) + '9', '0', repr(chr(0) + '9')), - ('\\141', 'a', '0', repr('a')), - ('(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k)(l)\\119', 'abcdefghijklk9', - '0,11', repr(('abcdefghijklk9', 'k'))), - - # Test \0 is handled everywhere. - (r'\0', '\0', '0', repr('\0')), - (r'[\0a]', '\0', '0', repr('\0')), - (r'[a\0]', '\0', '0', repr('\0')), - (r'[^a\0]', '\0', '', repr(None)), - - # Test various letter escapes. - (r'\a[\b]\f\n\r\t\v', '\a\b\f\n\r\t\v', '0', - repr('\a\b\f\n\r\t\v')), - (r'[\a][\b][\f][\n][\r][\t][\v]', '\a\b\f\n\r\t\v', '0', - repr('\a\b\f\n\r\t\v')), - (r'\c\e\g\h\i\j\k\o\p\q\y\z', 'ceghijkopqyz', '0', - repr('ceghijkopqyz')), - (r'\xff', '\377', '0', repr(chr(255))), - - # New \x semantics. - (r'\x00ffffffffffffff', '\377', '', repr(None)), - (r'\x00f', '\017', '', repr(None)), - (r'\x00fe', '\376', '', repr(None)), - - (r'\x00ff', '\377', '', repr(None)), - (r'\t\n\v\r\f\a\g', '\t\n\v\r\f\ag', '0', repr('\t\n\v\r\f\ag')), - ('\t\n\v\r\f\a\g', '\t\n\v\r\f\ag', '0', repr('\t\n\v\r\f\ag')), - (r'\t\n\v\r\f\a', '\t\n\v\r\f\a', '0', repr(chr(9) + chr(10) + - chr(11) + chr(13) + chr(12) + chr(7))), - (r'[\t][\n][\v][\r][\f][\b]', '\t\n\v\r\f\b', '0', - repr('\t\n\v\r\f\b')), - - (r"^\w+=(\\[\000-\277]|[^\n\\])*", - "SRC=eval.c g.c blah blah blah \\\\\n\tapes.c", '0', - repr("SRC=eval.c g.c blah blah blah \\\\")), - - # Test that . only matches \n in DOTALL mode. - ('a.b', 'acb', '0', repr('acb')), - ('a.b', 'a\nb', '', repr(None)), - ('a.*b', 'acc\nccb', '', repr(None)), - ('a.{4,5}b', 'acc\nccb', '', repr(None)), - ('a.b', 'a\rb', '0', repr('a\rb')), - # The new behaviour is that the inline flag affects only what follows. - ('a.b(?s)', 'a\nb', '0', repr('a\nb')), - ('a.b(?sV1)', 'a\nb', '', repr(None)), - ('(?s)a.b', 'a\nb', '0', repr('a\nb')), - ('a.*(?s)b', 'acc\nccb', '0', repr('acc\nccb')), - ('a.*(?sV1)b', 'acc\nccb', '', repr(None)), - ('(?s)a.*b', 'acc\nccb', '0', repr('acc\nccb')), - ('(?s)a.{4,5}b', 'acc\nccb', '0', repr('acc\nccb')), - - (')', '', '', regex.error, self.TRAILING_CHARS), # Unmatched right bracket. - ('', '', '0', "''"), # Empty pattern. - ('abc', 'abc', '0', repr('abc')), - ('abc', 'xbc', '', repr(None)), - ('abc', 'axc', '', repr(None)), - ('abc', 'abx', '', repr(None)), - ('abc', 'xabcy', '0', repr('abc')), - ('abc', 'ababc', '0', repr('abc')), - ('ab*c', 'abc', '0', repr('abc')), - ('ab*bc', 'abc', '0', repr('abc')), - - ('ab*bc', 'abbc', '0', repr('abbc')), - ('ab*bc', 'abbbbc', '0', repr('abbbbc')), - ('ab+bc', 'abbc', '0', repr('abbc')), - ('ab+bc', 'abc', '', repr(None)), - ('ab+bc', 'abq', '', repr(None)), - ('ab+bc', 'abbbbc', '0', repr('abbbbc')), - ('ab?bc', 'abbc', '0', repr('abbc')), - ('ab?bc', 'abc', '0', repr('abc')), - ('ab?bc', 'abbbbc', '', repr(None)), - ('ab?c', 'abc', '0', repr('abc')), - - ('^abc$', 'abc', '0', repr('abc')), - ('^abc$', 'abcc', '', repr(None)), - ('^abc', 'abcc', '0', repr('abc')), - ('^abc$', 'aabc', '', repr(None)), - ('abc$', 'aabc', '0', repr('abc')), - ('^', 'abc', '0', repr('')), - ('$', 'abc', '0', repr('')), - ('a.c', 'abc', '0', repr('abc')), - ('a.c', 'axc', '0', repr('axc')), - ('a.*c', 'axyzc', '0', repr('axyzc')), - - ('a.*c', 'axyzd', '', repr(None)), - ('a[bc]d', 'abc', '', repr(None)), - ('a[bc]d', 'abd', '0', repr('abd')), - ('a[b-d]e', 'abd', '', repr(None)), - ('a[b-d]e', 'ace', '0', repr('ace')), - ('a[b-d]', 'aac', '0', repr('ac')), - ('a[-b]', 'a-', '0', repr('a-')), - ('a[\\-b]', 'a-', '0', repr('a-')), - ('a[b-]', 'a-', '0', repr('a-')), - ('a[]b', '-', '', regex.error, self.BAD_SET), - - ('a[', '-', '', regex.error, self.BAD_SET), - ('a\\', '-', '', regex.error, self.BAD_ESCAPE), - ('abc)', '-', '', regex.error, self.TRAILING_CHARS), - ('(abc', '-', '', regex.error, self.MISSING_RPAREN), - ('a]', 'a]', '0', repr('a]')), - ('a[]]b', 'a]b', '0', repr('a]b')), - ('a[]]b', 'a]b', '0', repr('a]b')), - ('a[^bc]d', 'aed', '0', repr('aed')), - ('a[^bc]d', 'abd', '', repr(None)), - ('a[^-b]c', 'adc', '0', repr('adc')), - - ('a[^-b]c', 'a-c', '', repr(None)), - ('a[^]b]c', 'a]c', '', repr(None)), - ('a[^]b]c', 'adc', '0', repr('adc')), - ('\\ba\\b', 'a-', '0', repr('a')), - ('\\ba\\b', '-a', '0', repr('a')), - ('\\ba\\b', '-a-', '0', repr('a')), - ('\\by\\b', 'xy', '', repr(None)), - ('\\by\\b', 'yz', '', repr(None)), - ('\\by\\b', 'xyz', '', repr(None)), - ('x\\b', 'xyz', '', repr(None)), - - ('x\\B', 'xyz', '0', repr('x')), - ('\\Bz', 'xyz', '0', repr('z')), - ('z\\B', 'xyz', '', repr(None)), - ('\\Bx', 'xyz', '', repr(None)), - ('\\Ba\\B', 'a-', '', repr(None)), - ('\\Ba\\B', '-a', '', repr(None)), - ('\\Ba\\B', '-a-', '', repr(None)), - ('\\By\\B', 'xy', '', repr(None)), - ('\\By\\B', 'yz', '', repr(None)), - ('\\By\\b', 'xy', '0', repr('y')), - - ('\\by\\B', 'yz', '0', repr('y')), - ('\\By\\B', 'xyz', '0', repr('y')), - ('ab|cd', 'abc', '0', repr('ab')), - ('ab|cd', 'abcd', '0', repr('ab')), - ('()ef', 'def', '0,1', repr(('ef', ''))), - ('$b', 'b', '', repr(None)), - ('a\\(b', 'a(b', '', repr(('a(b',))), - ('a\\(*b', 'ab', '0', repr('ab')), - ('a\\(*b', 'a((b', '0', repr('a((b')), - ('a\\\\b', 'a\\b', '0', repr('a\\b')), - - ('((a))', 'abc', '0,1,2', repr(('a', 'a', 'a'))), - ('(a)b(c)', 'abc', '0,1,2', repr(('abc', 'a', 'c'))), - ('a+b+c', 'aabbabc', '0', repr('abc')), - ('(a+|b)*', 'ab', '0,1', repr(('ab', 'b'))), - ('(a+|b)+', 'ab', '0,1', repr(('ab', 'b'))), - ('(a+|b)?', 'ab', '0,1', repr(('a', 'a'))), - (')(', '-', '', regex.error, self.TRAILING_CHARS), - ('[^ab]*', 'cde', '0', repr('cde')), - ('abc', '', '', repr(None)), - ('a*', '', '0', repr('')), - - ('a|b|c|d|e', 'e', '0', repr('e')), - ('(a|b|c|d|e)f', 'ef', '0,1', repr(('ef', 'e'))), - ('abcd*efg', 'abcdefg', '0', repr('abcdefg')), - ('ab*', 'xabyabbbz', '0', repr('ab')), - ('ab*', 'xayabbbz', '0', repr('a')), - ('(ab|cd)e', 'abcde', '0,1', repr(('cde', 'cd'))), - ('[abhgefdc]ij', 'hij', '0', repr('hij')), - ('^(ab|cd)e', 'abcde', '', repr(None)), - ('(abc|)ef', 'abcdef', '0,1', repr(('ef', ''))), - ('(a|b)c*d', 'abcd', '0,1', repr(('bcd', 'b'))), - - ('(ab|ab*)bc', 'abc', '0,1', repr(('abc', 'a'))), - ('a([bc]*)c*', 'abc', '0,1', repr(('abc', 'bc'))), - ('a([bc]*)(c*d)', 'abcd', '0,1,2', repr(('abcd', 'bc', 'd'))), - ('a([bc]+)(c*d)', 'abcd', '0,1,2', repr(('abcd', 'bc', 'd'))), - ('a([bc]*)(c+d)', 'abcd', '0,1,2', repr(('abcd', 'b', 'cd'))), - ('a[bcd]*dcdcde', 'adcdcde', '0', repr('adcdcde')), - ('a[bcd]+dcdcde', 'adcdcde', '', repr(None)), - ('(ab|a)b*c', 'abc', '0,1', repr(('abc', 'ab'))), - ('((a)(b)c)(d)', 'abcd', '1,2,3,4', repr(('abc', 'a', 'b', 'd'))), - ('[a-zA-Z_][a-zA-Z0-9_]*', 'alpha', '0', repr('alpha')), - - ('^a(bc+|b[eh])g|.h$', 'abh', '0,1', repr(('bh', None))), - ('(bc+d$|ef*g.|h?i(j|k))', 'effgz', '0,1,2', repr(('effgz', - 'effgz', None))), - ('(bc+d$|ef*g.|h?i(j|k))', 'ij', '0,1,2', repr(('ij', 'ij', - 'j'))), - ('(bc+d$|ef*g.|h?i(j|k))', 'effg', '', repr(None)), - ('(bc+d$|ef*g.|h?i(j|k))', 'bcdd', '', repr(None)), - ('(bc+d$|ef*g.|h?i(j|k))', 'reffgz', '0,1,2', repr(('effgz', - 'effgz', None))), - ('(((((((((a)))))))))', 'a', '0', repr('a')), - ('multiple words of text', 'uh-uh', '', repr(None)), - ('multiple words', 'multiple words, yeah', '0', - repr('multiple words')), - ('(.*)c(.*)', 'abcde', '0,1,2', repr(('abcde', 'ab', 'de'))), - - ('\\((.*), (.*)\\)', '(a, b)', '2,1', repr(('b', 'a'))), - ('[k]', 'ab', '', repr(None)), - ('a[-]?c', 'ac', '0', repr('ac')), - ('(abc)\\1', 'abcabc', '1', repr('abc')), - ('([a-c]*)\\1', 'abcabc', '1', repr('abc')), - ('^(.+)?B', 'AB', '1', repr('A')), - ('(a+).\\1$', 'aaaaa', '0,1', repr(('aaaaa', 'aa'))), - ('^(a+).\\1$', 'aaaa', '', repr(None)), - ('(abc)\\1', 'abcabc', '0,1', repr(('abcabc', 'abc'))), - ('([a-c]+)\\1', 'abcabc', '0,1', repr(('abcabc', 'abc'))), - - ('(a)\\1', 'aa', '0,1', repr(('aa', 'a'))), - ('(a+)\\1', 'aa', '0,1', repr(('aa', 'a'))), - ('(a+)+\\1', 'aa', '0,1', repr(('aa', 'a'))), - ('(a).+\\1', 'aba', '0,1', repr(('aba', 'a'))), - ('(a)ba*\\1', 'aba', '0,1', repr(('aba', 'a'))), - ('(aa|a)a\\1$', 'aaa', '0,1', repr(('aaa', 'a'))), - ('(a|aa)a\\1$', 'aaa', '0,1', repr(('aaa', 'a'))), - ('(a+)a\\1$', 'aaa', '0,1', repr(('aaa', 'a'))), - ('([abc]*)\\1', 'abcabc', '0,1', repr(('abcabc', 'abc'))), - ('(a)(b)c|ab', 'ab', '0,1,2', repr(('ab', None, None))), - - ('(a)+x', 'aaax', '0,1', repr(('aaax', 'a'))), - ('([ac])+x', 'aacx', '0,1', repr(('aacx', 'c'))), - ('([^/]*/)*sub1/', 'd:msgs/tdir/sub1/trial/away.cpp', '0,1', - repr(('d:msgs/tdir/sub1/', 'tdir/'))), - ('([^.]*)\\.([^:]*):[T ]+(.*)', 'track1.title:TBlah blah blah', - '0,1,2,3', repr(('track1.title:TBlah blah blah', 'track1', - 'title', 'Blah blah blah'))), - ('([^N]*N)+', 'abNNxyzN', '0,1', repr(('abNNxyzN', 'xyzN'))), - ('([^N]*N)+', 'abNNxyz', '0,1', repr(('abNN', 'N'))), - ('([abc]*)x', 'abcx', '0,1', repr(('abcx', 'abc'))), - ('([abc]*)x', 'abc', '', repr(None)), - ('([xyz]*)x', 'abcx', '0,1', repr(('x', ''))), - ('(a)+b|aac', 'aac', '0,1', repr(('aac', None))), - - # Test symbolic groups. - ('(?Paaa)a', 'aaaa', '', regex.error, self.BAD_GROUP_NAME), - ('(?Paaa)a', 'aaaa', '0,id', repr(('aaaa', 'aaa'))), - ('(?Paa)(?P=id)', 'aaaa', '0,id', repr(('aaaa', 'aa'))), - ('(?Paa)(?P=xd)', 'aaaa', '', regex.error, self.UNKNOWN_GROUP), - - # Character properties. - (ur"\g", u"g", '0', repr(u'g')), - (ur"\g<1>", u"g", '', regex.error, self.UNKNOWN_GROUP), - (ur"(.)\g<1>", u"gg", '0', repr(u'gg')), - (ur"(.)\g<1>", u"gg", '', repr((u'gg', u'g'))), - (ur"\N", u"N", '0', repr(u'N')), - (ur"\N{LATIN SMALL LETTER A}", u"a", '0', repr(u'a')), - (ur"\p", u"p", '0', repr(u'p')), - (ur"\p{Ll}", u"a", '0', repr(u'a')), - (ur"\P", u"P", '0', repr(u'P')), - (ur"\P{Lu}", u"p", '0', repr(u'p')), - - # All tests from Perl. - ('abc', 'abc', '0', repr('abc')), - ('abc', 'xbc', '', repr(None)), - ('abc', 'axc', '', repr(None)), - ('abc', 'abx', '', repr(None)), - ('abc', 'xabcy', '0', repr('abc')), - ('abc', 'ababc', '0', repr('abc')), - - ('ab*c', 'abc', '0', repr('abc')), - ('ab*bc', 'abc', '0', repr('abc')), - ('ab*bc', 'abbc', '0', repr('abbc')), - ('ab*bc', 'abbbbc', '0', repr('abbbbc')), - ('ab{0,}bc', 'abbbbc', '0', repr('abbbbc')), - ('ab+bc', 'abbc', '0', repr('abbc')), - ('ab+bc', 'abc', '', repr(None)), - ('ab+bc', 'abq', '', repr(None)), - ('ab{1,}bc', 'abq', '', repr(None)), - ('ab+bc', 'abbbbc', '0', repr('abbbbc')), - - ('ab{1,}bc', 'abbbbc', '0', repr('abbbbc')), - ('ab{1,3}bc', 'abbbbc', '0', repr('abbbbc')), - ('ab{3,4}bc', 'abbbbc', '0', repr('abbbbc')), - ('ab{4,5}bc', 'abbbbc', '', repr(None)), - ('ab?bc', 'abbc', '0', repr('abbc')), - ('ab?bc', 'abc', '0', repr('abc')), - ('ab{0,1}bc', 'abc', '0', repr('abc')), - ('ab?bc', 'abbbbc', '', repr(None)), - ('ab?c', 'abc', '0', repr('abc')), - ('ab{0,1}c', 'abc', '0', repr('abc')), - - ('^abc$', 'abc', '0', repr('abc')), - ('^abc$', 'abcc', '', repr(None)), - ('^abc', 'abcc', '0', repr('abc')), - ('^abc$', 'aabc', '', repr(None)), - ('abc$', 'aabc', '0', repr('abc')), - ('^', 'abc', '0', repr('')), - ('$', 'abc', '0', repr('')), - ('a.c', 'abc', '0', repr('abc')), - ('a.c', 'axc', '0', repr('axc')), - ('a.*c', 'axyzc', '0', repr('axyzc')), - - ('a.*c', 'axyzd', '', repr(None)), - ('a[bc]d', 'abc', '', repr(None)), - ('a[bc]d', 'abd', '0', repr('abd')), - ('a[b-d]e', 'abd', '', repr(None)), - ('a[b-d]e', 'ace', '0', repr('ace')), - ('a[b-d]', 'aac', '0', repr('ac')), - ('a[-b]', 'a-', '0', repr('a-')), - ('a[b-]', 'a-', '0', repr('a-')), - ('a[b-a]', '-', '', regex.error, self.BAD_CHAR_RANGE), - ('a[]b', '-', '', regex.error, self.BAD_SET), - - ('a[', '-', '', regex.error, self.BAD_SET), - ('a]', 'a]', '0', repr('a]')), - ('a[]]b', 'a]b', '0', repr('a]b')), - ('a[^bc]d', 'aed', '0', repr('aed')), - ('a[^bc]d', 'abd', '', repr(None)), - ('a[^-b]c', 'adc', '0', repr('adc')), - ('a[^-b]c', 'a-c', '', repr(None)), - ('a[^]b]c', 'a]c', '', repr(None)), - ('a[^]b]c', 'adc', '0', repr('adc')), - ('ab|cd', 'abc', '0', repr('ab')), - - ('ab|cd', 'abcd', '0', repr('ab')), - ('()ef', 'def', '0,1', repr(('ef', ''))), - ('*a', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('(*)b', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('$b', 'b', '', repr(None)), - ('a\\', '-', '', regex.error, self.BAD_ESCAPE), - ('a\\(b', 'a(b', '', repr(('a(b',))), - ('a\\(*b', 'ab', '0', repr('ab')), - ('a\\(*b', 'a((b', '0', repr('a((b')), - ('a\\\\b', 'a\\b', '0', repr('a\\b')), - - ('abc)', '-', '', regex.error, self.TRAILING_CHARS), - ('(abc', '-', '', regex.error, self.MISSING_RPAREN), - ('((a))', 'abc', '0,1,2', repr(('a', 'a', 'a'))), - ('(a)b(c)', 'abc', '0,1,2', repr(('abc', 'a', 'c'))), - ('a+b+c', 'aabbabc', '0', repr('abc')), - ('a{1,}b{1,}c', 'aabbabc', '0', repr('abc')), - ('a**', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('a.+?c', 'abcabc', '0', repr('abc')), - ('(a+|b)*', 'ab', '0,1', repr(('ab', 'b'))), - ('(a+|b){0,}', 'ab', '0,1', repr(('ab', 'b'))), - - ('(a+|b)+', 'ab', '0,1', repr(('ab', 'b'))), - ('(a+|b){1,}', 'ab', '0,1', repr(('ab', 'b'))), - ('(a+|b)?', 'ab', '0,1', repr(('a', 'a'))), - ('(a+|b){0,1}', 'ab', '0,1', repr(('a', 'a'))), - (')(', '-', '', regex.error, self.TRAILING_CHARS), - ('[^ab]*', 'cde', '0', repr('cde')), - ('abc', '', '', repr(None)), - ('a*', '', '0', repr('')), - ('([abc])*d', 'abbbcd', '0,1', repr(('abbbcd', 'c'))), - ('([abc])*bcd', 'abcd', '0,1', repr(('abcd', 'a'))), - - ('a|b|c|d|e', 'e', '0', repr('e')), - ('(a|b|c|d|e)f', 'ef', '0,1', repr(('ef', 'e'))), - ('abcd*efg', 'abcdefg', '0', repr('abcdefg')), - ('ab*', 'xabyabbbz', '0', repr('ab')), - ('ab*', 'xayabbbz', '0', repr('a')), - ('(ab|cd)e', 'abcde', '0,1', repr(('cde', 'cd'))), - ('[abhgefdc]ij', 'hij', '0', repr('hij')), - ('^(ab|cd)e', 'abcde', '', repr(None)), - ('(abc|)ef', 'abcdef', '0,1', repr(('ef', ''))), - ('(a|b)c*d', 'abcd', '0,1', repr(('bcd', 'b'))), - - ('(ab|ab*)bc', 'abc', '0,1', repr(('abc', 'a'))), - ('a([bc]*)c*', 'abc', '0,1', repr(('abc', 'bc'))), - ('a([bc]*)(c*d)', 'abcd', '0,1,2', repr(('abcd', 'bc', 'd'))), - ('a([bc]+)(c*d)', 'abcd', '0,1,2', repr(('abcd', 'bc', 'd'))), - ('a([bc]*)(c+d)', 'abcd', '0,1,2', repr(('abcd', 'b', 'cd'))), - ('a[bcd]*dcdcde', 'adcdcde', '0', repr('adcdcde')), - ('a[bcd]+dcdcde', 'adcdcde', '', repr(None)), - ('(ab|a)b*c', 'abc', '0,1', repr(('abc', 'ab'))), - ('((a)(b)c)(d)', 'abcd', '1,2,3,4', repr(('abc', 'a', 'b', 'd'))), - ('[a-zA-Z_][a-zA-Z0-9_]*', 'alpha', '0', repr('alpha')), - - ('^a(bc+|b[eh])g|.h$', 'abh', '0,1', repr(('bh', None))), - ('(bc+d$|ef*g.|h?i(j|k))', 'effgz', '0,1,2', repr(('effgz', - 'effgz', None))), - ('(bc+d$|ef*g.|h?i(j|k))', 'ij', '0,1,2', repr(('ij', 'ij', - 'j'))), - ('(bc+d$|ef*g.|h?i(j|k))', 'effg', '', repr(None)), - ('(bc+d$|ef*g.|h?i(j|k))', 'bcdd', '', repr(None)), - ('(bc+d$|ef*g.|h?i(j|k))', 'reffgz', '0,1,2', repr(('effgz', - 'effgz', None))), - ('((((((((((a))))))))))', 'a', '10', repr('a')), - ('((((((((((a))))))))))\\10', 'aa', '0', repr('aa')), - - # Python does not have the same rules for \\41 so this is a syntax error - # ('((((((((((a))))))))))\\41', 'aa', '', repr(None)), - # ('((((((((((a))))))))))\\41', 'a!', '0', repr('a!')), - ('((((((((((a))))))))))\\41', '', '', regex.error, - self.UNKNOWN_GROUP), - ('(?i)((((((((((a))))))))))\\41', '', '', regex.error, - self.UNKNOWN_GROUP), - - ('(((((((((a)))))))))', 'a', '0', repr('a')), - ('multiple words of text', 'uh-uh', '', repr(None)), - ('multiple words', 'multiple words, yeah', '0', - repr('multiple words')), - ('(.*)c(.*)', 'abcde', '0,1,2', repr(('abcde', 'ab', 'de'))), - ('\\((.*), (.*)\\)', '(a, b)', '2,1', repr(('b', 'a'))), - ('[k]', 'ab', '', repr(None)), - ('a[-]?c', 'ac', '0', repr('ac')), - ('(abc)\\1', 'abcabc', '1', repr('abc')), - ('([a-c]*)\\1', 'abcabc', '1', repr('abc')), - ('(?i)abc', 'ABC', '0', repr('ABC')), - - ('(?i)abc', 'XBC', '', repr(None)), - ('(?i)abc', 'AXC', '', repr(None)), - ('(?i)abc', 'ABX', '', repr(None)), - ('(?i)abc', 'XABCY', '0', repr('ABC')), - ('(?i)abc', 'ABABC', '0', repr('ABC')), - ('(?i)ab*c', 'ABC', '0', repr('ABC')), - ('(?i)ab*bc', 'ABC', '0', repr('ABC')), - ('(?i)ab*bc', 'ABBC', '0', repr('ABBC')), - ('(?i)ab*?bc', 'ABBBBC', '0', repr('ABBBBC')), - ('(?i)ab{0,}?bc', 'ABBBBC', '0', repr('ABBBBC')), - - ('(?i)ab+?bc', 'ABBC', '0', repr('ABBC')), - ('(?i)ab+bc', 'ABC', '', repr(None)), - ('(?i)ab+bc', 'ABQ', '', repr(None)), - ('(?i)ab{1,}bc', 'ABQ', '', repr(None)), - ('(?i)ab+bc', 'ABBBBC', '0', repr('ABBBBC')), - ('(?i)ab{1,}?bc', 'ABBBBC', '0', repr('ABBBBC')), - ('(?i)ab{1,3}?bc', 'ABBBBC', '0', repr('ABBBBC')), - ('(?i)ab{3,4}?bc', 'ABBBBC', '0', repr('ABBBBC')), - ('(?i)ab{4,5}?bc', 'ABBBBC', '', repr(None)), - ('(?i)ab??bc', 'ABBC', '0', repr('ABBC')), - - ('(?i)ab??bc', 'ABC', '0', repr('ABC')), - ('(?i)ab{0,1}?bc', 'ABC', '0', repr('ABC')), - ('(?i)ab??bc', 'ABBBBC', '', repr(None)), - ('(?i)ab??c', 'ABC', '0', repr('ABC')), - ('(?i)ab{0,1}?c', 'ABC', '0', repr('ABC')), - ('(?i)^abc$', 'ABC', '0', repr('ABC')), - ('(?i)^abc$', 'ABCC', '', repr(None)), - ('(?i)^abc', 'ABCC', '0', repr('ABC')), - ('(?i)^abc$', 'AABC', '', repr(None)), - ('(?i)abc$', 'AABC', '0', repr('ABC')), - - ('(?i)^', 'ABC', '0', repr('')), - ('(?i)$', 'ABC', '0', repr('')), - ('(?i)a.c', 'ABC', '0', repr('ABC')), - ('(?i)a.c', 'AXC', '0', repr('AXC')), - ('(?i)a.*?c', 'AXYZC', '0', repr('AXYZC')), - ('(?i)a.*c', 'AXYZD', '', repr(None)), - ('(?i)a[bc]d', 'ABC', '', repr(None)), - ('(?i)a[bc]d', 'ABD', '0', repr('ABD')), - ('(?i)a[b-d]e', 'ABD', '', repr(None)), - ('(?i)a[b-d]e', 'ACE', '0', repr('ACE')), - - ('(?i)a[b-d]', 'AAC', '0', repr('AC')), - ('(?i)a[-b]', 'A-', '0', repr('A-')), - ('(?i)a[b-]', 'A-', '0', repr('A-')), - ('(?i)a[b-a]', '-', '', regex.error, self.BAD_CHAR_RANGE), - ('(?i)a[]b', '-', '', regex.error, self.BAD_SET), - ('(?i)a[', '-', '', regex.error, self.BAD_SET), - ('(?i)a]', 'A]', '0', repr('A]')), - ('(?i)a[]]b', 'A]B', '0', repr('A]B')), - ('(?i)a[^bc]d', 'AED', '0', repr('AED')), - ('(?i)a[^bc]d', 'ABD', '', repr(None)), - - ('(?i)a[^-b]c', 'ADC', '0', repr('ADC')), - ('(?i)a[^-b]c', 'A-C', '', repr(None)), - ('(?i)a[^]b]c', 'A]C', '', repr(None)), - ('(?i)a[^]b]c', 'ADC', '0', repr('ADC')), - ('(?i)ab|cd', 'ABC', '0', repr('AB')), - ('(?i)ab|cd', 'ABCD', '0', repr('AB')), - ('(?i)()ef', 'DEF', '0,1', repr(('EF', ''))), - ('(?i)*a', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('(?i)(*)b', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('(?i)$b', 'B', '', repr(None)), - - ('(?i)a\\', '-', '', regex.error, self.BAD_ESCAPE), - ('(?i)a\\(b', 'A(B', '', repr(('A(B',))), - ('(?i)a\\(*b', 'AB', '0', repr('AB')), - ('(?i)a\\(*b', 'A((B', '0', repr('A((B')), - ('(?i)a\\\\b', 'A\\B', '0', repr('A\\B')), - ('(?i)abc)', '-', '', regex.error, self.TRAILING_CHARS), - ('(?i)(abc', '-', '', regex.error, self.MISSING_RPAREN), - ('(?i)((a))', 'ABC', '0,1,2', repr(('A', 'A', 'A'))), - ('(?i)(a)b(c)', 'ABC', '0,1,2', repr(('ABC', 'A', 'C'))), - ('(?i)a+b+c', 'AABBABC', '0', repr('ABC')), - - ('(?i)a{1,}b{1,}c', 'AABBABC', '0', repr('ABC')), - ('(?i)a**', '-', '', regex.error, self.NOTHING_TO_REPEAT), - ('(?i)a.+?c', 'ABCABC', '0', repr('ABC')), - ('(?i)a.*?c', 'ABCABC', '0', repr('ABC')), - ('(?i)a.{0,5}?c', 'ABCABC', '0', repr('ABC')), - ('(?i)(a+|b)*', 'AB', '0,1', repr(('AB', 'B'))), - ('(?i)(a+|b){0,}', 'AB', '0,1', repr(('AB', 'B'))), - ('(?i)(a+|b)+', 'AB', '0,1', repr(('AB', 'B'))), - ('(?i)(a+|b){1,}', 'AB', '0,1', repr(('AB', 'B'))), - ('(?i)(a+|b)?', 'AB', '0,1', repr(('A', 'A'))), - - ('(?i)(a+|b){0,1}', 'AB', '0,1', repr(('A', 'A'))), - ('(?i)(a+|b){0,1}?', 'AB', '0,1', repr(('', None))), - ('(?i))(', '-', '', regex.error, self.TRAILING_CHARS), - ('(?i)[^ab]*', 'CDE', '0', repr('CDE')), - ('(?i)abc', '', '', repr(None)), - ('(?i)a*', '', '0', repr('')), - ('(?i)([abc])*d', 'ABBBCD', '0,1', repr(('ABBBCD', 'C'))), - ('(?i)([abc])*bcd', 'ABCD', '0,1', repr(('ABCD', 'A'))), - ('(?i)a|b|c|d|e', 'E', '0', repr('E')), - ('(?i)(a|b|c|d|e)f', 'EF', '0,1', repr(('EF', 'E'))), - - ('(?i)abcd*efg', 'ABCDEFG', '0', repr('ABCDEFG')), - ('(?i)ab*', 'XABYABBBZ', '0', repr('AB')), - ('(?i)ab*', 'XAYABBBZ', '0', repr('A')), - ('(?i)(ab|cd)e', 'ABCDE', '0,1', repr(('CDE', 'CD'))), - ('(?i)[abhgefdc]ij', 'HIJ', '0', repr('HIJ')), - ('(?i)^(ab|cd)e', 'ABCDE', '', repr(None)), - ('(?i)(abc|)ef', 'ABCDEF', '0,1', repr(('EF', ''))), - ('(?i)(a|b)c*d', 'ABCD', '0,1', repr(('BCD', 'B'))), - ('(?i)(ab|ab*)bc', 'ABC', '0,1', repr(('ABC', 'A'))), - ('(?i)a([bc]*)c*', 'ABC', '0,1', repr(('ABC', 'BC'))), - - ('(?i)a([bc]*)(c*d)', 'ABCD', '0,1,2', repr(('ABCD', 'BC', 'D'))), - ('(?i)a([bc]+)(c*d)', 'ABCD', '0,1,2', repr(('ABCD', 'BC', 'D'))), - ('(?i)a([bc]*)(c+d)', 'ABCD', '0,1,2', repr(('ABCD', 'B', 'CD'))), - ('(?i)a[bcd]*dcdcde', 'ADCDCDE', '0', repr('ADCDCDE')), - ('(?i)a[bcd]+dcdcde', 'ADCDCDE', '', repr(None)), - ('(?i)(ab|a)b*c', 'ABC', '0,1', repr(('ABC', 'AB'))), - ('(?i)((a)(b)c)(d)', 'ABCD', '1,2,3,4', repr(('ABC', 'A', 'B', - 'D'))), - ('(?i)[a-zA-Z_][a-zA-Z0-9_]*', 'ALPHA', '0', repr('ALPHA')), - ('(?i)^a(bc+|b[eh])g|.h$', 'ABH', '0,1', repr(('BH', None))), - ('(?i)(bc+d$|ef*g.|h?i(j|k))', 'EFFGZ', '0,1,2', repr(('EFFGZ', - 'EFFGZ', None))), - - ('(?i)(bc+d$|ef*g.|h?i(j|k))', 'IJ', '0,1,2', repr(('IJ', 'IJ', - 'J'))), - ('(?i)(bc+d$|ef*g.|h?i(j|k))', 'EFFG', '', repr(None)), - ('(?i)(bc+d$|ef*g.|h?i(j|k))', 'BCDD', '', repr(None)), - ('(?i)(bc+d$|ef*g.|h?i(j|k))', 'REFFGZ', '0,1,2', repr(('EFFGZ', - 'EFFGZ', None))), - ('(?i)((((((((((a))))))))))', 'A', '10', repr('A')), - ('(?i)((((((((((a))))))))))\\10', 'AA', '0', repr('AA')), - #('(?i)((((((((((a))))))))))\\41', 'AA', '', repr(None)), - #('(?i)((((((((((a))))))))))\\41', 'A!', '0', repr('A!')), - ('(?i)(((((((((a)))))))))', 'A', '0', repr('A')), - ('(?i)(?:(?:(?:(?:(?:(?:(?:(?:(?:(a))))))))))', 'A', '1', - repr('A')), - ('(?i)(?:(?:(?:(?:(?:(?:(?:(?:(?:(a|b|c))))))))))', 'C', '1', - repr('C')), - ('(?i)multiple words of text', 'UH-UH', '', repr(None)), - - ('(?i)multiple words', 'MULTIPLE WORDS, YEAH', '0', - repr('MULTIPLE WORDS')), - ('(?i)(.*)c(.*)', 'ABCDE', '0,1,2', repr(('ABCDE', 'AB', 'DE'))), - ('(?i)\\((.*), (.*)\\)', '(A, B)', '2,1', repr(('B', 'A'))), - ('(?i)[k]', 'AB', '', repr(None)), - # ('(?i)abcd', 'ABCD', SUCCEED, 'found+"-"+\\found+"-"+\\\\found', repr(ABCD-$&-\\ABCD)), - # ('(?i)a(bc)d', 'ABCD', SUCCEED, 'g1+"-"+\\g1+"-"+\\\\g1', repr(BC-$1-\\BC)), - ('(?i)a[-]?c', 'AC', '0', repr('AC')), - ('(?i)(abc)\\1', 'ABCABC', '1', repr('ABC')), - ('(?i)([a-c]*)\\1', 'ABCABC', '1', repr('ABC')), - ('a(?!b).', 'abad', '0', repr('ad')), - ('a(?=d).', 'abad', '0', repr('ad')), - ('a(?=c|d).', 'abad', '0', repr('ad')), - - ('a(?:b|c|d)(.)', 'ace', '1', repr('e')), - ('a(?:b|c|d)*(.)', 'ace', '1', repr('e')), - ('a(?:b|c|d)+?(.)', 'ace', '1', repr('e')), - ('a(?:b|(c|e){1,2}?|d)+?(.)', 'ace', '1,2', repr(('c', 'e'))), - - # Lookbehind: split by : but not if it is escaped by -. - ('(?]*?b', 'a>b', '', repr(None)), - # Bug 490573: minimizing repeat problem. - (r'^a*?$', 'foo', '', repr(None)), - # Bug 470582: nested groups problem. - (r'^((a)c)?(ab)$', 'ab', '1,2,3', repr((None, None, 'ab'))), - # Another minimizing repeat problem (capturing groups in assertions). - ('^([ab]*?)(?=(b)?)c', 'abc', '1,2', repr(('ab', None))), - ('^([ab]*?)(?!(b))c', 'abc', '1,2', repr(('ab', None))), - ('^([ab]*?)(?(.){0,2})d", "abcd").captures(1), - ['b', 'c']) - self.assertEqual(regex.search(r"(.)+", "a").captures(1), ['a']) - - def test_guards(self): - m = regex.search(r"(X.*?Y\s*){3}(X\s*)+AB:", - "XY\nX Y\nX Y\nXY\nXX AB:") - self.assertEqual(m.span(0, 1, 2), ((3, 21), (12, 15), (16, 18))) - - m = regex.search(r"(X.*?Y\s*){3,}(X\s*)+AB:", - "XY\nX Y\nX Y\nXY\nXX AB:") - self.assertEqual(m.span(0, 1, 2), ((0, 21), (12, 15), (16, 18))) - - m = regex.search(r'\d{4}(\s*\w)?\W*((?!\d)\w){2}', "9999XX") - self.assertEqual(m.span(0, 1, 2), ((0, 6), (-1, -1), (5, 6))) - - m = regex.search(r'A\s*?.*?(\n+.*?\s*?){0,2}\(X', 'A\n1\nS\n1 (X') - self.assertEqual(m.span(0, 1), ((0, 10), (5, 8))) - - m = regex.search('Derde\s*:', 'aaaaaa:\nDerde:') - self.assertEqual(m.span(), (8, 14)) - m = regex.search('Derde\s*:', 'aaaaa:\nDerde:') - self.assertEqual(m.span(), (7, 13)) - - def test_turkic(self): - # Turkish has dotted and dotless I/i. - pairs = u"I=i;I=\u0131;i=\u0130" - - all_chars = set() - matching = set() - for pair in pairs.split(";"): - ch1, ch2 = pair.split("=") - all_chars.update((ch1, ch2)) - matching.add((ch1, ch1)) - matching.add((ch1, ch2)) - matching.add((ch2, ch1)) - matching.add((ch2, ch2)) - - for ch1 in all_chars: - for ch2 in all_chars: - m = regex.match(ur"(?iu)\A" + ch1 + ur"\Z", ch2) - if m: - if (ch1, ch2) not in matching: - self.fail("%s matching %s" % (repr(ch1), repr(ch2))) - else: - if (ch1, ch2) in matching: - self.fail("%s not matching %s" % (repr(ch1), - repr(ch2))) - - def test_named_lists(self): - options = [u"one", u"two", u"three"] - self.assertEqual(regex.match(ur"333\L444", u"333one444", - bar=options).group(), u"333one444") - self.assertEqual(regex.match(ur"(?i)333\L444", u"333TWO444", - bar=options).group(), u"333TWO444") - self.assertEqual(regex.match(ur"333\L444", u"333four444", - bar=options), None) - - options = ["one", "two", "three"] - self.assertEqual(regex.match(r"333\L444", "333one444", - bar=options).group(), "333one444") - self.assertEqual(regex.match(r"(?i)333\L444", "333TWO444", - bar=options).group(), "333TWO444") - self.assertEqual(regex.match(r"333\L444", "333four444", - bar=options), None) - - self.assertEqual(repr(type(regex.compile(r"3\L4\L+5", - bar=["one", "two", "three"]))), self.PATTERN_CLASS) - - self.assertEqual(regex.findall(r"^\L", "solid QWERT", - options=set(['good', 'brilliant', '+s\\ol[i}d'])), []) - self.assertEqual(regex.findall(r"^\L", "+solid QWERT", - options=set(['good', 'brilliant', '+solid'])), ['+solid']) - - options = [u"STRASSE"] - self.assertEqual(regex.match(ur"(?fiu)\L", - u"stra\N{LATIN SMALL LETTER SHARP S}e", words=options).span(), (0, - 6)) - - options = [u"STRASSE", u"stress"] - self.assertEqual(regex.match(ur"(?fiu)\L", - u"stra\N{LATIN SMALL LETTER SHARP S}e", words=options).span(), (0, - 6)) - - options = [u"stra\N{LATIN SMALL LETTER SHARP S}e"] - self.assertEqual(regex.match(ur"(?fiu)\L", u"STRASSE", - words=options).span(), (0, 7)) - - options = ["kit"] - self.assertEqual(regex.search(ur"(?iu)\L", u"SKITS", - words=options).span(), (1, 4)) - self.assertEqual(regex.search(ur"(?iu)\L", - u"SK\N{LATIN CAPITAL LETTER I WITH DOT ABOVE}TS", - words=options).span(), (1, 4)) - - self.assertEqual(regex.search(ur"(?fiu)\b(\w+) +\1\b", - u" stra\N{LATIN SMALL LETTER SHARP S}e STRASSE ").span(), (1, 15)) - self.assertEqual(regex.search(ur"(?fiu)\b(\w+) +\1\b", - u" STRASSE stra\N{LATIN SMALL LETTER SHARP S}e ").span(), (1, 15)) - - self.assertEqual(regex.search(r"^\L$", "", options=[]).span(), - (0, 0)) - - def test_fuzzy(self): - # Some tests borrowed from TRE library tests. - self.assertEqual(repr(type(regex.compile('(fou){s,e<=1}'))), - self.PATTERN_CLASS) - self.assertEqual(repr(type(regex.compile('(fuu){s}'))), - self.PATTERN_CLASS) - self.assertEqual(repr(type(regex.compile('(fuu){s,e}'))), - self.PATTERN_CLASS) - self.assertEqual(repr(type(regex.compile('(anaconda){1i+1d<1,s<=1}'))), - self.PATTERN_CLASS) - self.assertEqual(repr(type(regex.compile('(anaconda){1i+1d<1,s<=1,e<=10}'))), - self.PATTERN_CLASS) - self.assertEqual(repr(type(regex.compile('(anaconda){s<=1,e<=1,1i+1d<1}'))), - self.PATTERN_CLASS) - - text = 'molasses anaconda foo bar baz smith anderson ' - self.assertEqual(regex.search('(znacnda){s<=1,e<=3,1i+1d<1}', text), - None) - self.assertEqual(regex.search('(znacnda){s<=1,e<=3,1i+1d<2}', - text).span(0, 1), ((9, 17), (9, 17))) - self.assertEqual(regex.search('(ananda){1i+1d<2}', text), None) - self.assertEqual(regex.search(r"(?:\bznacnda){e<=2}", text)[0], - "anaconda") - self.assertEqual(regex.search(r"(?:\bnacnda){e<=2}", text)[0], - "anaconda") - - text = 'anaconda foo bar baz smith anderson' - self.assertEqual(regex.search('(fuu){i<=3,d<=3,e<=5}', text).span(0, - 1), ((0, 0), (0, 0))) - self.assertEqual(regex.search('(?b)(fuu){i<=3,d<=3,e<=5}', - text).span(0, 1), ((9, 10), (9, 10))) - self.assertEqual(regex.search('(fuu){i<=2,d<=2,e<=5}', text).span(0, - 1), ((7, 10), (7, 10))) - self.assertEqual(regex.search('(?e)(fuu){i<=2,d<=2,e<=5}', - text).span(0, 1), ((9, 10), (9, 10))) - self.assertEqual(regex.search('(fuu){i<=3,d<=3,e}', text).span(0, 1), - ((0, 0), (0, 0))) - self.assertEqual(regex.search('(?b)(fuu){i<=3,d<=3,e}', text).span(0, - 1), ((9, 10), (9, 10))) - - self.assertEqual(repr(type(regex.compile('(approximate){s<=3,1i+1d<3}'))), - self.PATTERN_CLASS) - - # No cost limit. - self.assertEqual(regex.search('(foobar){e}', - 'xirefoabralfobarxie').span(0, 1), ((0, 6), (0, 6))) - self.assertEqual(regex.search('(?e)(foobar){e}', - 'xirefoabralfobarxie').span(0, 1), ((0, 3), (0, 3))) - self.assertEqual(regex.search('(?b)(foobar){e}', - 'xirefoabralfobarxie').span(0, 1), ((11, 16), (11, 16))) - - # At most two errors. - self.assertEqual(regex.search('(foobar){e<=2}', - 'xirefoabrzlfd').span(0, 1), ((4, 9), (4, 9))) - self.assertEqual(regex.search('(foobar){e<=2}', 'xirefoabzlfd'), None) - - # At most two inserts or substitutions and max two errors total. - self.assertEqual(regex.search('(foobar){i<=2,s<=2,e<=2}', - 'oobargoobaploowap').span(0, 1), ((5, 11), (5, 11))) - - # Find best whole word match for "foobar". - self.assertEqual(regex.search('\\b(foobar){e}\\b', 'zfoobarz').span(0, - 1), ((0, 8), (0, 8))) - self.assertEqual(regex.search('\\b(foobar){e}\\b', - 'boing zfoobarz goobar woop').span(0, 1), ((0, 6), (0, 6))) - self.assertEqual(regex.search('(?b)\\b(foobar){e}\\b', - 'boing zfoobarz goobar woop').span(0, 1), ((15, 21), (15, 21))) - - # Match whole string, allow only 1 error. - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foobar').span(0, 1), - ((0, 6), (0, 6))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'xfoobar').span(0, - 1), ((0, 7), (0, 7))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foobarx').span(0, - 1), ((0, 7), (0, 7))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'fooxbar').span(0, - 1), ((0, 7), (0, 7))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foxbar').span(0, 1), - ((0, 6), (0, 6))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'xoobar').span(0, 1), - ((0, 6), (0, 6))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foobax').span(0, 1), - ((0, 6), (0, 6))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'oobar').span(0, 1), - ((0, 5), (0, 5))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'fobar').span(0, 1), - ((0, 5), (0, 5))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'fooba').span(0, 1), - ((0, 5), (0, 5))) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'xfoobarx'), None) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foobarxx'), None) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'xxfoobar'), None) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'xfoxbar'), None) - self.assertEqual(regex.search('^(foobar){e<=1}$', 'foxbarx'), None) - - # At most one insert, two deletes, and three substitutions. - # Additionally, deletes cost two and substitutes one, and total - # cost must be less than 4. - self.assertEqual(regex.search('(foobar){i<=1,d<=2,s<=3,2d+1s<4}', - '3oifaowefbaoraofuiebofasebfaobfaorfeoaro').span(0, 1), ((6, 13), (6, - 13))) - self.assertEqual(regex.search('(?b)(foobar){i<=1,d<=2,s<=3,2d+1s<4}', - '3oifaowefbaoraofuiebofasebfaobfaorfeoaro').span(0, 1), ((26, 33), - (26, 33))) - - # Partially fuzzy matches. - self.assertEqual(regex.search('foo(bar){e<=1}zap', 'foobarzap').span(0, - 1), ((0, 9), (3, 6))) - self.assertEqual(regex.search('foo(bar){e<=1}zap', 'fobarzap'), None) - self.assertEqual(regex.search('foo(bar){e<=1}zap', 'foobrzap').span(0, - 1), ((0, 8), (3, 5))) - - text = ('www.cnn.com 64.236.16.20\nwww.slashdot.org 66.35.250.150\n' - 'For useful information, use www.slashdot.org\nthis is demo data!\n') - self.assertEqual(regex.search(r'(?s)^.*(dot.org){e}.*$', text).span(0, - 1), ((0, 120), (120, 120))) - self.assertEqual(regex.search(r'(?es)^.*(dot.org){e}.*$', text).span(0, - 1), ((0, 120), (93, 100))) - self.assertEqual(regex.search(r'^.*(dot.org){e}.*$', text).span(0, 1), - ((0, 119), (24, 101))) - - # Behaviour is unexpected, but arguably not wrong. It first finds the - # best match, then the best in what follows, etc. - self.assertEqual(regex.findall(r"\b\L{e<=1}\b", - " book cot dog desk ", words="cat dog".split()), ["cot", "dog"]) - self.assertEqual(regex.findall(r"\b\L{e<=1}\b", - " book dog cot desk ", words="cat dog".split()), [" dog", "cot"]) - self.assertEqual(regex.findall(r"(?e)\b\L{e<=1}\b", - " book dog cot desk ", words="cat dog".split()), ["dog", "cot"]) - self.assertEqual(regex.findall(r"(?r)\b\L{e<=1}\b", - " book cot dog desk ", words="cat dog".split()), ["dog ", "cot"]) - self.assertEqual(regex.findall(r"(?er)\b\L{e<=1}\b", - " book cot dog desk ", words="cat dog".split()), ["dog", "cot"]) - self.assertEqual(regex.findall(r"(?r)\b\L{e<=1}\b", - " book dog cot desk ", words="cat dog".split()), ["cot", "dog"]) - self.assertEqual(regex.findall(ur"\b\L{e<=1}\b", - u" book cot dog desk ", words=u"cat dog".split()), [u"cot", u"dog"]) - self.assertEqual(regex.findall(ur"\b\L{e<=1}\b", - u" book dog cot desk ", words=u"cat dog".split()), [u" dog", u"cot"]) - self.assertEqual(regex.findall(ur"(?e)\b\L{e<=1}\b", - u" book dog cot desk ", words=u"cat dog".split()), [u"dog", u"cot"]) - self.assertEqual(regex.findall(ur"(?r)\b\L{e<=1}\b", - u" book cot dog desk ", words=u"cat dog".split()), [u"dog ", u"cot"]) - self.assertEqual(regex.findall(ur"(?er)\b\L{e<=1}\b", - u" book cot dog desk ", words=u"cat dog".split()), [u"dog", u"cot"]) - self.assertEqual(regex.findall(ur"(?r)\b\L{e<=1}\b", - u" book dog cot desk ", words=u"cat dog".split()), [u"cot", u"dog"]) - - self.assertEqual(regex.search(r"(\w+) (\1{e<=1})", "foo fou").groups(), - ("foo", "fou")) - self.assertEqual(regex.search(r"(?r)(\2{e<=1}) (\w+)", - "foo fou").groups(), ("foo", "fou")) - self.assertEqual(regex.search(ur"(\w+) (\1{e<=1})", - u"foo fou").groups(), (u"foo", u"fou")) - - self.assertEqual(regex.findall(r"(?:(?:QR)+){e}","abcde"), ["abcde", - ""]) - self.assertEqual(regex.findall(r"(?:Q+){e}","abc"), ["abc", ""]) - - # Hg issue 41. - self.assertEqual(regex.match(r"(?:service detection){0[^()]+)|(?R))*\)", "(ab(cd)ef)")[ - : ], ("(ab(cd)ef)", "ef")) - self.assertEqual(regex.search(r"\(((?>[^()]+)|(?R))*\)", - "(ab(cd)ef)").captures(1), ["ab", "cd", "(cd)", "ef"]) - - self.assertEqual(regex.search(r"(?r)\(((?R)|(?>[^()]+))*\)", - "(ab(cd)ef)")[ : ], ("(ab(cd)ef)", "ab")) - self.assertEqual(regex.search(r"(?r)\(((?R)|(?>[^()]+))*\)", - "(ab(cd)ef)").captures(1), ["ef", "cd", "(cd)", "ab"]) - - self.assertEqual(regex.search(r"\(([^()]+|(?R))*\)", - "some text (a(b(c)d)e) more text")[ : ], ("(a(b(c)d)e)", "e")) - - self.assertEqual(regex.search(r"(?r)\(((?R)|[^()]+)*\)", - "some text (a(b(c)d)e) more text")[ : ], ("(a(b(c)d)e)", "a")) - - self.assertEqual(regex.search(r"(foo(\(((?:(?>[^()]+)|(?2))*)\)))", - "foo(bar(baz)+baz(bop))")[ : ], ("foo(bar(baz)+baz(bop))", - "foo(bar(baz)+baz(bop))", "(bar(baz)+baz(bop))", - "bar(baz)+baz(bop)")) - - self.assertEqual(regex.search(r"(?r)(foo(\(((?:(?2)|(?>[^()]+))*)\)))", - "foo(bar(baz)+baz(bop))")[ : ], ("foo(bar(baz)+baz(bop))", - "foo(bar(baz)+baz(bop))", "(bar(baz)+baz(bop))", - "bar(baz)+baz(bop)")) - - rgx = regex.compile(r"""^\s*(<\s*([a-zA-Z:]+)(?:\s*[a-zA-Z:]*\s*=\s*(?:'[^']*'|"[^"]*"))*\s*(/\s*)?>(?:[^<>]*|(?1))*(?(3)|<\s*/\s*\2\s*>))\s*$""") - self.assertEqual(bool(rgx.search('')), True) - self.assertEqual(bool(rgx.search('')), False) - self.assertEqual(bool(rgx.search('')), True) - self.assertEqual(bool(rgx.search('')), False) - self.assertEqual(bool(rgx.search('')), False) - - self.assertEqual(bool(rgx.search('')), False) - self.assertEqual(bool(rgx.search('')), True) - self.assertEqual(bool(rgx.search('< fooo / >')), True) - # The next regex should and does match. Perl 5.14 agrees. - #self.assertEqual(bool(rgx.search('foo')), False) - self.assertEqual(bool(rgx.search('foo')), False) - - self.assertEqual(bool(rgx.search('foo')), True) - self.assertEqual(bool(rgx.search('foo')), True) - self.assertEqual(bool(rgx.search('')), True) - - def test_copy(self): - # PatternObjects are immutable, therefore there's no need to clone them. - r = regex.compile("a") - self.assert_(copy.copy(r) is r) - self.assert_(copy.deepcopy(r) is r) - - # MatchObjects are normally mutable because the target string can be - # detached. However, after the target string has been detached, a - # MatchObject becomes immutable, so there's no need to clone it. - m = r.match("a") - self.assert_(copy.copy(m) is not m) - self.assert_(copy.deepcopy(m) is not m) - - self.assert_(m.string is not None) - m2 = copy.copy(m) - m2.detach_string() - self.assert_(m.string is not None) - self.assert_(m2.string is None) - - # The following behaviour matches that of the re module. - it = regex.finditer(".", "ab") - it2 = copy.copy(it) - self.assertEqual(it.next().group(), "a") - self.assertEqual(it2.next().group(), "b") - - # The following behaviour matches that of the re module. - it = regex.finditer(".", "ab") - it2 = copy.deepcopy(it) - self.assertEqual(it.next().group(), "a") - self.assertEqual(it2.next().group(), "b") - - # The following behaviour is designed to match that of copying 'finditer'. - it = regex.splititer(" ", "a b") - it2 = copy.copy(it) - self.assertEqual(it.next(), "a") - self.assertEqual(it2.next(), "b") - - # The following behaviour is designed to match that of copying 'finditer'. - it = regex.splititer(" ", "a b") - it2 = copy.deepcopy(it) - self.assertEqual(it.next(), "a") - self.assertEqual(it2.next(), "b") - - def test_format(self): - self.assertEqual(regex.subf(r"(\w+) (\w+)", "{0} => {2} {1}", - "foo bar"), "foo bar => bar foo") - self.assertEqual(regex.subf(r"(?\w+) (?\w+)", - "{word2} {word1}", "foo bar"), "bar foo") - - self.assertEqual(regex.subfn(r"(\w+) (\w+)", "{0} => {2} {1}", - "foo bar"), ("foo bar => bar foo", 1)) - self.assertEqual(regex.subfn(r"(?\w+) (?\w+)", - "{word2} {word1}", "foo bar"), ("bar foo", 1)) - - self.assertEqual(regex.match(r"(\w+) (\w+)", - "foo bar").expandf("{0} => {2} {1}"), "foo bar => bar foo") - - def test_fullmatch(self): - self.assertEqual(bool(regex.fullmatch(r"abc", "abc")), True) - self.assertEqual(bool(regex.fullmatch(r"abc", "abcx")), False) - self.assertEqual(bool(regex.fullmatch(r"abc", "abcx", endpos=3)), True) - - self.assertEqual(bool(regex.fullmatch(r"abc", "xabc", pos=1)), True) - self.assertEqual(bool(regex.fullmatch(r"abc", "xabcy", pos=1)), False) - self.assertEqual(bool(regex.fullmatch(r"abc", "xabcy", pos=1, - endpos=4)), True) - - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "abc")), True) - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "abcx")), False) - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "abcx", endpos=3)), - True) - - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "xabc", pos=1)), - True) - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "xabcy", pos=1)), - False) - self.assertEqual(bool(regex.fullmatch(r"(?r)abc", "xabcy", pos=1, - endpos=4)), True) - - def test_hg_bugs(self): - # Hg issue 28. - self.assertEqual(bool(regex.compile("(?>b)", flags=regex.V1)), True) - - # Hg issue 29. - self.assertEqual(bool(regex.compile("^((?>\w+)|(?>\s+))*$", - flags=regex.V1)), True) - - # Hg issue 31. - self.assertEqual(regex.findall(r"\((?:(?>[^()]+)|(?R))*\)", - "a(bcd(e)f)g(h)"), ['(bcd(e)f)', '(h)']) - self.assertEqual(regex.findall(r"\((?:(?:[^()]+)|(?R))*\)", - "a(bcd(e)f)g(h)"), ['(bcd(e)f)', '(h)']) - self.assertEqual(regex.findall(r"\((?:(?>[^()]+)|(?R))*\)", - "a(b(cd)e)f)g)h"), ['(b(cd)e)']) - self.assertEqual(regex.findall(r"\((?:(?>[^()]+)|(?R))*\)", - "a(bc(d(e)f)gh"), ['(d(e)f)']) - self.assertEqual(regex.findall(r"(?r)\((?:(?>[^()]+)|(?R))*\)", - "a(bc(d(e)f)gh"), ['(d(e)f)']) - self.assertEqual([m.group() for m in - regex.finditer(r"\((?:[^()]*+|(?0))*\)", "a(b(c(de)fg)h")], - ['(c(de)fg)']) - - # Hg issue 32. - self.assertEqual(regex.search("a(bc)d", "abcd", regex.I | - regex.V1).group(0), "abcd") - - # Hg issue 33. - self.assertEqual(regex.search("([\da-f:]+)$", "E", regex.I | - regex.V1).group(0), "E") - self.assertEqual(regex.search("([\da-f:]+)$", "e", regex.I | - regex.V1).group(0), "e") - - # Hg issue 34. - self.assertEqual(regex.search("^(?=ab(de))(abd)(e)", "abde").groups(), - ('de', 'abd', 'e')) - - # Hg issue 35. - self.assertEqual(bool(regex.match(r"\ ", " ", flags=regex.X)), True) - - # Hg issue 36. - self.assertEqual(regex.search(r"^(a|)\1{2}b", "b").group(0, 1), ('b', - '')) - - # Hg issue 37. - self.assertEqual(regex.search("^(a){0,0}", "abc").group(0, 1), ('', - None)) - - # Hg issue 38. - self.assertEqual(regex.search("(?>.*/)b", "a/b").group(0), "a/b") - - # Hg issue 39. - self.assertEqual(regex.search(r"(?V0)((?i)blah)\s+\1", - "blah BLAH").group(0, 1), ("blah BLAH", "blah")) - self.assertEqual(regex.search(r"(?V1)((?i)blah)\s+\1", "blah BLAH"), - None) - - # Hg issue 40. - self.assertEqual(regex.search(r"(\()?[^()]+(?(1)\)|)", - "(abcd").group(0), "abcd") - - # Hg issue 42. - self.assertEqual(regex.search("(a*)*", "a").span(1), (1, 1)) - self.assertEqual(regex.search("(a*)*", "aa").span(1), (2, 2)) - self.assertEqual(regex.search("(a*)*", "aaa").span(1), (3, 3)) - - # Hg issue 43. - self.assertEqual(regex.search("a(?#xxx)*", "aaa").group(), "aaa") - - # Hg issue 44. - self.assertEqual(regex.search("(?=abc){3}abc", "abcabcabc").span(), (0, - 3)) - - # Hg issue 45. - self.assertEqual(regex.search("^(?:a(?:(?:))+)+", "a").span(), (0, 1)) - self.assertEqual(regex.search("^(?:a(?:(?:))+)+", "aa").span(), (0, 2)) - - # Hg issue 46. - self.assertEqual(regex.search("a(?x: b c )d", "abcd").group(0), "abcd") - - # Hg issue 47. - self.assertEqual(regex.search("a#comment\n*", "aaa", - flags=regex.X).group(0), "aaa") - - # Hg issue 48. - self.assertEqual(regex.search(r"(?V1)(a(?(1)\1)){1}", - "aaaaaaaaaa").span(0, 1), ((0, 1), (0, 1))) - self.assertEqual(regex.search(r"(?V1)(a(?(1)\1)){2}", - "aaaaaaaaaa").span(0, 1), ((0, 3), (1, 3))) - self.assertEqual(regex.search(r"(?V1)(a(?(1)\1)){3}", - "aaaaaaaaaa").span(0, 1), ((0, 6), (3, 6))) - self.assertEqual(regex.search(r"(?V1)(a(?(1)\1)){4}", - "aaaaaaaaaa").span(0, 1), ((0, 10), (6, 10))) - - # Hg issue 49. - self.assertEqual(regex.search("(?V1)(a)(?<=b(?1))", "baz").group(0), - "a") - - # Hg issue 50. - self.assertEqual(regex.findall(ur'(?fi)\L', - u'POST, Post, post, po\u017Ft, po\uFB06, and po\uFB05', - keywords=['post','pos']), [u'POST', u'Post', u'post', u'po\u017Ft', - u'po\uFB06', u'po\uFB05']) - self.assertEqual(regex.findall(ur'(?fi)pos|post', - u'POST, Post, post, po\u017Ft, po\uFB06, and po\uFB05'), [u'POS', - u'Pos', u'pos', u'po\u017F', u'po\uFB06', u'po\uFB05']) - self.assertEqual(regex.findall(ur'(?fi)post|pos', - u'POST, Post, post, po\u017Ft, po\uFB06, and po\uFB05'), [u'POST', - u'Post', u'post', u'po\u017Ft', u'po\uFB06', u'po\uFB05']) - self.assertEqual(regex.findall(ur'(?fi)post|another', - u'POST, Post, post, po\u017Ft, po\uFB06, and po\uFB05'), [u'POST', - u'Post', u'post', u'po\u017Ft', u'po\uFB06', u'po\uFB05']) - - # Hg issue 51. - self.assertEqual(regex.search("(?V1)((a)(?1)|(?2))", "a").group(0, 1, - 2), ('a', 'a', None)) - - # Hg issue 52. - self.assertEqual(regex.search(r"(?V1)(\1xx|){6}", "xx").span(0, 1), - ((0, 2), (2, 2))) - - # Hg issue 53. - self.assertEqual(regex.search("(a|)+", "a").group(0, 1), ("a", "")) - - # Hg issue 54. - self.assertEqual(regex.search(r"(a|)*\d", "a" * 80), None) - - # Hg issue 55. - self.assertEqual(regex.search("^(?:a?b?)*$", "ac"), None) - - # Hg issue 58. - self.assertRaisesRegex(regex.error, self.UNDEF_CHAR_NAME, lambda: - regex.compile("\\N{1}")) - - # Hg issue 59. - self.assertEqual(regex.search("\\Z", "a\na\n").span(0), (4, 4)) - - # Hg issue 60. - self.assertEqual(regex.search("(q1|.)*(q2|.)*(x(a|bc)*y){2,}", - "xayxay").group(0), "xayxay") - - # Hg issue 61. - self.assertEqual(regex.search("(?i)[^a]", "A"), None) - - # Hg issue 63. - self.assertEqual(regex.search(u"(?iu)[[:ascii:]]", u"\N{KELVIN SIGN}"), - None) - - # Hg issue 66. - self.assertEqual(regex.search("((a|b(?1)c){3,5})", "baaaaca").group(0, - 1, 2), ('aaaa', 'aaaa', 'a')) - - # Hg issue 71. - self.assertEqual(regex.findall(r"(?<=:\S+ )\w+", ":9 abc :10 def"), - ['abc', 'def']) - self.assertEqual(regex.findall(r"(?<=:\S* )\w+", ":9 abc :10 def"), - ['abc', 'def']) - self.assertEqual(regex.findall(r"(?<=:\S+? )\w+", ":9 abc :10 def"), - ['abc', 'def']) - self.assertEqual(regex.findall(r"(?<=:\S*? )\w+", ":9 abc :10 def"), - ['abc', 'def']) - - # Hg issue 73. - self.assertEqual(regex.search(r"(?:fe)?male", "female").group(), - "female") - self.assertEqual([m.group() for m in - regex.finditer(r"(fe)?male: h(?(1)(er)|(is)) (\w+)", - "female: her dog; male: his cat. asdsasda")], ['female: her dog', - 'male: his cat']) - - # Hg issue 78. - self.assertEqual(regex.search(r'(?\((?:[^()]++|(?&rec))*\))', - 'aaa(((1+0)+1)+1)bbb').captures('rec'), ['(1+0)', '((1+0)+1)', - '(((1+0)+1)+1)']) - - # Hg issue 80. - self.assertRaisesRegex(regex.error, self.BAD_ESCAPE, lambda: - regex.sub('x', '\\', 'x'), ) - - # Hg issue 82. - fz = "(CAGCCTCCCATTTCAGAATATACATCC){1a(?b))', "ab").spans("x"), [(1, - 2), (0, 2)]) - - # Hg issue 91. - # Check that the replacement cache works. - self.assertEqual(regex.sub(r'(-)', lambda m: m.expand(r'x'), 'a-b-c'), - 'axbxc') - - # Hg issue 94. - rx = regex.compile(r'\bt(est){i<2}', flags=regex.V1) - self.assertEqual(rx.search("Some text"), None) - self.assertEqual(rx.findall("Some text"), []) - - # Hg issue 95. - self.assertRaisesRegex(regex.error, - '^nothing to repeat at position 3$', lambda: regex.compile(r'.???')) - - # Hg issue 97. - self.assertEquals(regex.escape(u'foo!?'), u'foo\\!\\?') - self.assertEquals(regex.escape(u'foo!?', special_only=True), - u'foo!\\?') - - self.assertEquals(regex.escape('foo!?'), 'foo\\!\\?') - self.assertEquals(regex.escape('foo!?', special_only=True), 'foo!\\?') - - # Hg issue 100. - self.assertEquals(regex.search('^([^z]*(?:WWWi|W))?$', - 'WWWi').groups(), ('WWWi', )) - self.assertEquals(regex.search('^([^z]*(?:WWWi|w))?$', - 'WWWi').groups(), ('WWWi', )) - self.assertEquals(regex.search('^([^z]*?(?:WWWi|W))?$', - 'WWWi').groups(), ('WWWi', )) - - # Hg issue 101. - pat = regex.compile(r'xxx', flags=regex.FULLCASE | regex.UNICODE) - self.assertEquals([x.group() for x in pat.finditer('yxxx')], ['xxx']) - self.assertEquals(pat.findall('yxxx'), ['xxx']) - - raw = 'yxxx' - self.assertEquals([x.group() for x in pat.finditer(raw)], ['xxx']) - self.assertEquals(pat.findall(raw), ['xxx']) - - pat = regex.compile(r'xxx', flags=regex.FULLCASE | regex.IGNORECASE | - regex.UNICODE) - self.assertEquals([x.group() for x in pat.finditer('yxxx')], ['xxx']) - self.assertEquals(pat.findall('yxxx'), ['xxx']) - - raw = 'yxxx' - self.assertEquals([x.group() for x in pat.finditer(raw)], ['xxx']) - self.assertEquals(pat.findall(raw), ['xxx']) - - # Hg issue 106. - self.assertEquals(regex.sub('(?V0).*', 'x', 'test'), 'x') - self.assertEquals(regex.sub('(?V1).*', 'x', 'test'), 'xx') - - self.assertEquals(regex.sub('(?V0).*?', '|', 'test'), '|t|e|s|t|') - self.assertEquals(regex.sub('(?V1).*?', '|', 'test'), '|||||||||') - - # Hg issue 112. - self.assertEquals(regex.sub(r'^(@)\n(?!.*?@)(.*)', - r'\1\n==========\n\2', '@\n', flags=regex.DOTALL), '@\n==========\n') - - # Hg issue 109. - self.assertEquals(regex.match(r'(?:cats|cat){e<=1}', - 'caz').fuzzy_counts, (1, 0, 0)) - self.assertEquals(regex.match(r'(?e)(?:cats|cat){e<=1}', - 'caz').fuzzy_counts, (1, 0, 0)) - self.assertEquals(regex.match(r'(?b)(?:cats|cat){e<=1}', - 'caz').fuzzy_counts, (1, 0, 0)) - - self.assertEquals(regex.match(r'(?:cat){e<=1}', 'caz').fuzzy_counts, - (1, 0, 0)) - self.assertEquals(regex.match(r'(?e)(?:cat){e<=1}', - 'caz').fuzzy_counts, (1, 0, 0)) - self.assertEquals(regex.match(r'(?b)(?:cat){e<=1}', - 'caz').fuzzy_counts, (1, 0, 0)) - - self.assertEquals(regex.match(r'(?:cats){e<=2}', 'c ats').fuzzy_counts, - (1, 1, 0)) - self.assertEquals(regex.match(r'(?e)(?:cats){e<=2}', - 'c ats').fuzzy_counts, (0, 1, 0)) - self.assertEquals(regex.match(r'(?b)(?:cats){e<=2}', - 'c ats').fuzzy_counts, (0, 1, 0)) - - self.assertEquals(regex.match(r'(?:cats){e<=2}', - 'c a ts').fuzzy_counts, (0, 2, 0)) - self.assertEquals(regex.match(r'(?e)(?:cats){e<=2}', - 'c a ts').fuzzy_counts, (0, 2, 0)) - self.assertEquals(regex.match(r'(?b)(?:cats){e<=2}', - 'c a ts').fuzzy_counts, (0, 2, 0)) - - self.assertEquals(regex.match(r'(?:cats){e<=1}', - 'c ats').fuzzy_counts, (0, 1, 0)) - self.assertEquals(regex.match(r'(?e)(?:cats){e<=1}', - 'c ats').fuzzy_counts, (0, 1, 0)) - self.assertEquals(regex.match(r'(?b)(?:cats){e<=1}', - 'c ats').fuzzy_counts, (0, 1, 0)) - -if not hasattr(str, "format"): - # Strings don't have the .format method (below Python 2.6). - del RegexTests.test_format - -def test_main(): - run_unittest(RegexTests) - -if __name__ == "__main__": - test_main() diff --git a/sickbeard/name_parser/parser.py b/sickbeard/name_parser/parser.py index bfa0cf8c..12aad199 100644 --- a/sickbeard/name_parser/parser.py +++ b/sickbeard/name_parser/parser.py @@ -24,7 +24,6 @@ import regexes import sickbeard from sickbeard import logger, helpers, scene_numbering -from regex import regex from dateutil import parser nameparser_lock = threading.Lock() @@ -104,8 +103,8 @@ class NameParser(object): for regex_type, regex_pattern in regexItem.items(): for (cur_pattern_name, cur_pattern) in regex_pattern: try: - cur_regex = regex.compile(cur_pattern, regex.V1 | regex.VERBOSE | regex.IGNORECASE | regex.BESTMATCH) - except regex.error, errormsg: + cur_regex = re.compile(cur_pattern, re.VERBOSE | re.IGNORECASE) + except re.error, errormsg: logger.log(u"WARNING: Invalid episode_pattern, %s. %s" % (errormsg, cur_pattern)) else: self.compiled_regexes[(regex_type,cur_pattern_name)] = cur_regex @@ -116,7 +115,7 @@ class NameParser(object): result = ParseResult(name) for (cur_regex_type, cur_regex_name), cur_regex in self.compiled_regexes.items(): - match = cur_regex.fullmatch(name) + match = cur_regex.match(name) if not match: continue @@ -185,8 +184,8 @@ class NameParser(object): tmp_extra_info = match.group('extra_info') # Show.S04.Special or Show.S05.Part.2.Extras is almost certainly not every episode in the season - if tmp_extra_info and cur_regex_name == 'season_only' and regex.search( - r'([. _-]|^)(special|extra)s?\w*([. _-]|$)', tmp_extra_info, regex.I): + if tmp_extra_info and cur_regex_name == 'season_only' and re.search( + r'([. _-]|^)(special|extra)s?\w*([. _-]|$)', tmp_extra_info, re.I): continue result.extra_info = tmp_extra_info @@ -286,7 +285,7 @@ class NameParser(object): # break it into parts if there are any (dirname, file name, extension) dir_name, file_name = os.path.split(name) - ext_match = regex.match('(.*)\.\w{3,4}$', file_name) + ext_match = re.match('(.*)\.\w{3,4}$', file_name) if ext_match and self.file_name: base_file_name = ext_match.group(1) else:

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