From be5ead408741cb2da50211cee074e8a3d2305a9b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jindra=20Pet=C5=99=C3=ADk?= Date: Fri, 1 Aug 2025 19:29:45 +0200 Subject: [PATCH] Do not parse imports from names with namespace suffix --- .../decompiler/flash/abc/types/Multiname.java | 8 ++ .../exporters/script/DependencyParser.java | 2 +- .../flash/ActionScriptTestBase.java | 2 + .../ActionScript3AssembledDecompileTest.java | 7 ++ .../as3_assembled-0/as3_assembled-0.main.abc | Bin 10450 -> 10716 bytes .../as3_assembled-0.main.asasm | 1 + .../TestCollidingPublicTraits.class.asasm | 80 ++++++++++++++++++ .../TestCollidingPublicTraits.script.asasm | 29 +++++++ .../as3_assembled/bin/as3_assembled.swf | Bin 6015 -> 6164 bytes 9 files changed, 128 insertions(+), 1 deletion(-) create mode 100644 libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.class.asasm create mode 100644 libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.script.asasm diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/types/Multiname.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/types/Multiname.java index f9f889692..a46059897 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/types/Multiname.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/types/Multiname.java @@ -174,6 +174,14 @@ public class Multiname { public void setDisplayNamespace(boolean displayNamespace) { this.displayNamespace = displayNamespace; } + + /** + * Checks whether this multiname displays its namespace as #suffix + * @return True when displays + */ + public boolean doesDisplayNamespace() { + return displayNamespace; + } /** * Checks if the multiname kind is valid. diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/exporters/script/DependencyParser.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/exporters/script/DependencyParser.java index b2e7e5828..752811ff9 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/exporters/script/DependencyParser.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/exporters/script/DependencyParser.java @@ -140,7 +140,7 @@ public class DependencyParser { Namespace ns = m.getNamespace(abc.constants); String name = m.getName(usedDeobfuscations, abc, abc.constants, fullyQualifiedNames, true, true); NamespaceSet nss = m.getNamespaceSet(abc.constants); - if (ns != null) { + if (ns != null && !m.doesDisplayNamespace()) { parseDependenciesFromNS(abcIndex, ignoredCustom, abc, dependencies, m.namespace_index, ignorePackage, name, dependencyType, uses); } if (nss != null) { diff --git a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/ActionScriptTestBase.java b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/ActionScriptTestBase.java index adee3879d..3e9402522 100644 --- a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/ActionScriptTestBase.java +++ b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/ActionScriptTestBase.java @@ -26,6 +26,8 @@ public class ActionScriptTestBase { pCode = pCode.replaceAll("\t", " ").trim(); pCode = pCode.replaceAll("( *[\r\n]+ *)+", "\n").trim(); pCode = pCode.replaceAll(" +", " ").trim(); + //replace ns suffixes, so testCollidingPublicTraits will work even when ns indices change + pCode = pCode.replaceAll("#[0-9]+", "#_"); return pCode; } } diff --git a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3AssembledDecompileTest.java b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3AssembledDecompileTest.java index 717af5971..a0d3eef70 100644 --- a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3AssembledDecompileTest.java +++ b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3AssembledDecompileTest.java @@ -90,6 +90,13 @@ public class ActionScript3AssembledDecompileTest extends ActionScript3DecompileT false); } + @Test + public void testCollidingPublicTraits() { + decompileMethod("assembled", "testCollidingPublicTraits", "trace(\"ns1 = \" + this.a#87);\r\n" + + "trace(\"ns2 = \" + this.a#88);\r\n", + false); + } + @Test public void testDeclareReg() { decompileMethod("assembled", "testDeclareReg", "var other:XML;\r\n" diff --git a/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.abc b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.abc index b6b6498f05da2efba73b21bb172a132ca51deee8..0fab917859c34cc1aa3cb95f15db16da923d7e6c 100644 GIT binary patch delta 3675 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 delta 3385 zcmZXVX;2$S7RTS~nNh2S1OkjSNE#tPAdrNS!3T~Va~J~#jEv9mfh~cN$2P=ve8&ga zj&nK*NyoYG+qn~OHi>gzyV>K`hcp-;>aq!j7P5h#B;e}H6E@?fD zzCj;zK8^lCKl4qY?>^K(e8)7ekNNxcvcTOKxCa9q1LrVszZmp?j(WMiN)PD4Kp8J~ zFXa)pI_T2m*QZ^t`LzSuVeN=^gVwK=YXL3jyd9mQnC}7fJ&3-C(DyL3$oz^XtX5Nt;DFelLzEDV%* zi;GH&TL;=SWiY+E-#mK4jyQ>eYG3&&?50G~mTo-W$vZt!oa8$^UrivfhnM>%mf6s& zpTsVyYu|9J1KsGrRbL<_PD;e@Uxj^$%-O)4Ds#@J`5cU&N_d7@(Bh-?Qg4;mn7fX@~Dm(8fzG;H0 z=vXIgy|4|!HVWG$Y)IJFnvzad2n1J(;s#-UaG;7ns|d@1OJYHoux(H%v8aNuQ7DmE zT20t?@JaO76E+S3iNQEw*FjifMUb#zs1i5<)ltGMsFmSZh_DfeOH9lrY%k1~*w{eW z9%z!-tP{2s=1W}AOxQuVM&hEmgdKt<5?fP*?Sl@9O9O;up-W=-e8P@Euf)D4!VbWI z#B_onOsrNmwxRQRM1)Ok#QA~%+|UkdP%S4c1M8*IY$WV@*d%fDJi-pcR*9K9!p2}k z;0@ZWr@4R z@rfE0OGLU84Hd+jSET~+Vps)b7FMXB>R7FU7Q%WJ91)DGK%*E`!C8k<6<88OD!5WO zTZMwT*r0;D1$7lXi?LaS!Zw_%LQyBCRPgp-K!xIdoUcO3N^DZ0bgi1`RAx<}!vp99 zv4Na$t=xwjuv~?*A#7B^m&JK1_(!o$1$_t3QlWetlPU!EVyz0n12{*8&=Fjqf^i&c zR0y9$jHpm?2C-6wh*)l!3YB*t`c$a88!@Ir^*Kbp3Q_qcAfV3A`{u0r97~)4m(tgO z*9|b#n^~Ugxs0e^>f1U0}A$1C=;uRI1MX5b(qG1{QW`9$tHIZ!<0(V~UqAfUL62q$E)BcS6 zIXiHJsTfw6x9jySgCo>i0>Fmpu(Nt{JU-&M{PnPwUad4yXYo&0uZn83^3|TVlaHFJ zVO8*_^!Y}2x*NKMLeDE+vK7Zn&9JKZzx9TuWyyDOSc^}(E+@t@y@h0!rME&i;66YX zgz{-`*lEX2hhf$8wdHk{T|(Uh*yRwaNM7}(tvX>+!;16A%WE3jhqbPDoZJnoJwz&H#3^gdD_mIFr9`K;ZMft)&tLGUz zauQ9KVTJgaz(LPjcH|VA1%@@7JA*a2iq8)E@EBhftP#h!d6~Tz+oh2T_7EBIs77Ew*$N@}xgzLuQ zhB?d)i}Q6Z+I7yLS!h_zd}Sz6*42erKZ-+3a!a~~;M6z{$vRUZ9eeosP&mxocmNQf zEnnh2yTnas78%xD{zIs4-AOqW@7kF;tdU%Z_I%b#{_jkDv*e#=c#Gue88#(Q;s zug&lse8hOKc~nHiTC5qjYsQTW7wG}$%unfUdrCK>={2kr9}Fk)b$%io!#DVI;aahR zcw48q2|aoFQ?~pTG>Z)@!2cFbU>EmQRC+$JDq(e#14Mz9Te@wgSwG#s0>vp@)3H)u^}QvvhbQ6%go5m@cSz*@xLrL+gUVyhSkX3 zRh1K~E~VDTr&FVtoETTUejy&kF;b!e$QOGQ#g&q~Zd{SR`1`9@y*_a?r7ov7Lj0R} zO1x-W7RRi`-G-Bhj(5sk(2b79X69CQ%Y$@}JV^I~;)HDecD!%T;SMzYhBc4BQdPfd zTYM;;=uJaBGm=RDh>7f?24wLP1K^WHJf2$`t&i@0F}uh{7F{DS;r;W~tM&EbO&raa zecdj5Cz`rp)$zLO##qbcY|GHXs4Kg$8%T>hG8O`H!H#^!BX-7J{6ux4X{>8KOl}kB zSFR(fJu&P^WIKi((f?$JMT_x#!Ua2F3eA9FCHbGK`-`uiPAZoJ4!K3VaeyS@Ezxez ztG4cLG=qj!%g;s|@H2if8p2Qcx6vN_ghy%yJnz_=d(aFS)*ODcCRUs6z{%3-%ejv+ zcjz0@_DH_%hqjcXX&BZ5{$lqcu$yyO*Iaxa=;!>ZxcwJiZ9P4RM+6c&gr zL6ghGl{aQ1;RkBx)GieP5$_OA7CMRfN-x-z&Y@XhSP}lm+C`$0NJ(p= zomvYOC(&6?IGgZ+xt-jXq|NKfo{4H98dVh&P4*TsP12njL-+&1%Dn p@pyf_aUkjL9f0X14y{OHZbb)7i`ks}bvBRN2@jzeH7vgv`5&dRh(Z7W diff --git a/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.asasm b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.asasm index 61760f42a..c12e584cb 100644 --- a/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.asasm +++ b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/as3_assembled-0.main.asasm @@ -41,5 +41,6 @@ program #include "tests/TestAlwaysBreak2.script.asasm" #include "tests/TestPushPlacement.script.asasm" #include "tests/TestConstructDynamically.script.asasm" + #include "tests/TestCollidingPublicTraits.script.asasm" ; place to add next end ; program diff --git a/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.class.asasm b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.class.asasm new file mode 100644 index 000000000..8f0a5b775 --- /dev/null +++ b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.class.asasm @@ -0,0 +1,80 @@ +class + refid "tests:TestCollidingPublicTraits" + instance QName(PackageNamespace("tests"), "TestCollidingPublicTraits") + extends QName(PackageNamespace(""), "Object") + flag SEALED + flag PROTECTEDNS + protectedns ProtectedNamespace("tests:TestCollidingPublicTraits") + iinit + refid "tests:TestCollidingPublicTraits/instance/init" + body + maxstack 1 + localcount 1 + initscopedepth 4 + maxscopedepth 5 + code + getlocal0 + pushscope + + getlocal0 + constructsuper 0 + returnvoid + end ; code + end ; body + end ; method + trait slot QName(PackageNamespace("test1"),"a") + slotid 0 + type QName(PackageNamespace(""),"int") + value Integer(1) + end ; trait + trait slot QName(PackageNamespace("test2"),"a") + slotid 0 + type QName(PackageNamespace(""),"int") + value Integer(2) + end ; trait + trait method QName(PackageNamespace(""), "run") + method + refid "tests:TestCollidingPublicTraits/instance/run" + returns QName(PackageNamespace(""), "void") + body + maxstack 2 + localcount 4 + initscopedepth 4 + maxscopedepth 5 + code + getlocal0 + pushscope + findpropstrict QName(PackageNamespace(""),"trace") + pushstring "ns1 = " + getlocal0 + getproperty QName(PackageNamespace("test1"),"a") + add + callpropvoid QName(PackageNamespace(""),"trace"), 1 + findpropstrict QName(PackageNamespace(""),"trace") + pushstring "ns2 = " + getlocal0 + getproperty QName(PackageNamespace("test2"),"a") + add + callpropvoid QName(PackageNamespace(""),"trace"), 1 + returnvoid + end ; code + end ; body + end ; method + end ; trait + end ; instance + cinit + refid "tests:TestCollidingPublicTraits/class/init" + body + maxstack 1 + localcount 1 + initscopedepth 3 + maxscopedepth 4 + code + getlocal0 + pushscope + + returnvoid + end ; code + end ; body + end ; method +end ; class diff --git a/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.script.asasm b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.script.asasm new file mode 100644 index 000000000..1d8c382ab --- /dev/null +++ b/libsrc/ffdec_lib/testdata/as3_assembled/abc/as3_assembled-0/tests/TestCollidingPublicTraits.script.asasm @@ -0,0 +1,29 @@ +script + sinit + refid "tests:TestCollidingPublicTraits/init" + body + maxstack 2 + localcount 1 + initscopedepth 1 + maxscopedepth 3 + code + getlocal0 + pushscope + + findpropstrict Multiname("TestCollidingPublicTraits", [PackageNamespace("tests")]) + getlex QName(PackageNamespace(""), "Object") + pushscope + + getlex Multiname("Object", [PrivateNamespace(null, "tests:TestCollidingPublicTraits"), PackageNamespace(""), PackageNamespace("tests"), PackageInternalNs("tests"), Namespace("http://adobe.com/AS3/2006/builtin")]) + newclass "tests:TestCollidingPublicTraits" + popscope + initproperty QName(PackageNamespace("tests"), "TestCollidingPublicTraits") + + returnvoid + end ; code + end ; body + end ; method + trait class QName(PackageNamespace("tests"), "TestCollidingPublicTraits") + #include "TestCollidingPublicTraits.class.asasm" + end ; trait +end ; script diff --git a/libsrc/ffdec_lib/testdata/as3_assembled/bin/as3_assembled.swf b/libsrc/ffdec_lib/testdata/as3_assembled/bin/as3_assembled.swf index 1f3441cb91b96fe2286d5b1ef5ac68ad701f2241..8bdb6ef118f5f3eddff6d165fbbb8cd28e31c462 100644 GIT binary patch literal 6164 zcmV+v80+UlS5qVwEC2v_+U;6tTw6zy?|O$?EkKA%h(k6Q8H^AhgimY}V=mh<#x{1W zIL7cKJ@FI^iAdtg={Rw&$$e+eWbVlvnaq7AlgZq(2RIAaYj$V$n(Q^>{jy*7gSNUK zLdeO^Z+Cz5VLvSRRaaH_`&V^$byYvx3xqBaQawY+CLjZ4HH476Dt-=x>`O(WJtqf- z8WyJGiF6N2`&*1mW~QgJbAEolW4^m1nVRbC+Oua*r$5jc2(;sf_Vi*Rqb;;2(oHSB z0$@N-hf}ecOe~pb;IbA<&Sv(vw5*{gnOdN z)U=lA)n;bmv9QMBIv3j0MlyV1UYpa~qj4>5?CZ=AgU3YQx-5LuGJ5Y3EzuCz>1zo116`&YT)VIH zn$=#@;0E@R0mnP?KGH8`v)QvY8F$!%k79Z0ED=Bc&V&2samRmX8_{A3@_Oa3TM0p# zL{r+d-bEawgD4;c2>A_IMngC2;S6XHs-BpbN={^w6A?WcOT@U*2}6(1Kv&#PCVO9Q46K z=vVl(=*VI}21!~zIh#%JRO;xo=Fcbgmn=Q zV;L=#DG_6mXjLDWouNXSohe&u`_k#yRDz=xam`RNHK>J+@(p}{Qcs~dYi>E%`nm|@ z!-+Mo>;+PwQ0x}s(Iid|r*k+e42;ZXa1|3%WAm|0*bp8apG_Ob;}}BxrIMWHj1i0L z0%1%S5rB?YZxDxKi3r~cJ(XD$$Yb-`hMCz+)w&Ur9nhoNY}|C))bL4d5RW8diORe< zlH^-8J)KO{apkGhV!wv!qsioq*yf}9oE|r)jeP@2;dE)C7${zog(SdFCvemC$oig% zZ3s@s`Q8{Ib%NQ)26Cc=EMGKDUycmU%`h*@KahA?+Y;V07` z!>H0QM$FeOaXm4WF_h`WMA|aFh>2~+lGek?M8w7q&a@cBIGZtWOH^?Ls`Ce-AXH#M z_P2M-UF|#NE{vC2)$9B2fzXx{6JGug}OWM^9yZiTPy(PAW4L|!ry$cJN zPDAh3FD@=#tKZkD_1gOe1_lQvPK{2Co$4DNv>c3OrnMP%a51CzrBd1=43rGS(lc>w z(M(m&0tpXT2D1U?i9vNRl}e^c#ewEy_;R6ssCo$Z<9Lc6YyH?*&w8eTVK`iNIDt7v z#A$=1s~OI9vB{xLhLGCKXpP5u)K>wIXH6EG7(RPcT7l{=FlRhUq@rQ#4%utLaF3@T2GB6Bf1*a(z;*JfHiDrseV*45qURgsjhV{poHV;E=~gF zSQ|T{cuGUbIW?QG^0dS=7Uc{A zt2n1AozqlC;W&D*SS;Q+gjLentl7j49mY3EFx9eS+wNkzTY`s8NzK1UGUdrwb%6vWFV5_jI zZzv%JwY{QHZ`Q-SE??)}?^158_8aUL)_ljtj%yq#sQ;DM>UolVmy+KFYOhu1Zv>6` zuK(g*P+2fy?K)8PUdljufmY}?n7;PDuwmcVZVk#@G8R$iW08y@W1WS?`@wnA$*doT z>XX&X`2;wh1C`+KwCZrO>Je8}?UPXZ6x2Qqwa-HB^VnJaQ*hO|#$2_oy4or+_V@8? z6TeP1tyZgZ>Y{q9dYd|;)~K~=o%La`qBG7H!1;b~egK>w1n1|$`89AloIeKVPr!Mq z`h?5va=NNr4%g4X^>c9j0l5AUTz>?vKL*zlxR$|n1zc}|>rcS70(9aU7vTC!aQy;Ye+90;2G=ja^(%1w4Y>XmTz?0yzX#Vpfa}-bdIwzp2(|87XKi)u zGf-PoJ62m;Telscgjpq3277I}qpY-|?7(QBDxW-lYUHN7E`d;4B^i{XHTS_GD#_}= z_}wsQ5wBS61+P-IQUXP`)`_P2UQp{fqq+s%Bbc>)(f_enqDrmEyErMK0)^j+RG_O zVlj?5?|~t~UGKUK!+co|p1TPBPz)9r`x#KlN+qQKgwGqmtR2j%Fl#537O3<&)ZNUi zekxIF`v_3mi>UY>(8Cff`XaJbRJxPGCJLJ=G*D=yu!TYs1rLR-6q+ftP}oMHm4cT- z8wDSQb_yL7Iw|-mbWsRU=%%op!VU_zQ`kvi7lqvv_E6}du$RI<3i~PaQn-%70SbMz z%0;Wb0qlrW*F~?p7kwI}QVM59rK40jMx|4<_$aj$(=!qcO0?vwKueC%^T%0OV)c~W z4HA1DA1kYCuM5<5Q+9+FeIIDin?R3!8K-oRN)KT3AU==a^HF@Rr_#&Vd={Ut;PV2^Ylibszg31=a@42do`f2e3|Heqdd|0>HX~Z3ngk*iK-(fb9mh2UriV zy}Z2XZ4`G5Jp zDa!}f+UtL>HgLPhL&Wtzdu96n<~mUYENAcu;&T?CoA5b@&v|?%o6858ok%c-VYx|S z)x-h{5ZWZMn~9CHMVlpN5Ibi}8zdGZ<(#eXNbCY}a<y7o1exNj(Jrwxxxm?Y zi^LKn$=R8J#1=@JvzgrzyOYdwcA;5f)8sbJ-rguN7rBeG7h#LUYREmng?ph&Voq|u z5FP-h#3sr6gzzwIlUR~GCWObqC9x2B3Lp&RX{eT%MxFzCh!6(yFj7gzQP1NfRl-OK zDI-;+hPX*1*-BbTJLw`j$R4tv^pQbwn2eAUau8SLAzTaTMqCxN2=bXeauU=V$XRlp zgh-U!OcEqT=E$w&PI3vzeLx-p@+goefjkSOS%GpiX@yM+!J^uv5Xk|X6(UzcgF+M+ zcod@6gI6Jz253_V^+3HstlMC#LNK+u6=L&4r$UOhLx)0&cSDUrO7_8ah1d_k4uzBs zK$k)shoDX&Wk+F`LduUrw?ZmTE4~3VVkseDB^bI^(#xa#MyORt)j0SS;?!WLLaKFW zRfsDFl?thuhIWP2-U2NOshfp>Lh2V`w?f=^K(j(N-3`#Fkj<9?wkV|GL4YcSG(H00 zRLGVm0JbTl=@|f*LOd@3R4ZgFPvSuE=I8&nqDi>g7MU#RgI45xkx6?W;D+FWTA94$ zM;0$3%+|Q%Uph=Ce+uPRLY7AN5(nn|@sY`+(d(C@dq+nk94N~Yvz0FS$B*UI$GBRN z5X-aV*U6;hpN#t_4gciL{>hksa?n5d5eO2u_%X_Htcv@nm}V^)II2aMMTts^qE;{Y zJ!HjWTfO2*1k7p~uE8=)n=A<06-Y3Q# zZJOi!fi~>`b{6N*UJ+=w2PL=Bg!+;^n!Nz6l%sVo`5VKkhpc+Y+a408AvJ7ql%WqH zONcgk!%9O1X0(v98nDo^cd}U=hOatuwmvIt-4T@C#%9!)Rw(*q+TPIJ2 zsiT~mpdoA1#TjqdvV0|^j@}>#sI~0Z*({E)%o+HcFmPv3aT^V&ugV*678t1J25M3A zPnJF59WQIs$~;n~imQEO^avTo5w0BM7X{>9LDg+|P+yaWtSx}7s3uJw8V%t5MK`KGXm>g2-@6+8((S9V|5f@b#ko3 zh^5xm;z?^ne{joCFX&E!nU;7WtBxjY$f~0r8(4KvY~)pk9UIk@EUS)Rh#>RlT=!z58j_;m%j2H}kFj@4mb`Q=rfW_%UcD%e(D zUiFo%;>+7}=DsP+-3P&9x6y$eJM!js7MR<$mOsvTSN%G~!TWaoIQTvWqX4*4Fi)U@ z?9QQnLZIFc!4kJogD>yNqxKY_?&YWhOaAlVdz?d^FC8i+Vby_?VW`90gi-E^*wJ}D z0SBIXM-k>vf7pWEhxr@eE5T+M%G$eZ#bjU3h1Z1(4?xiFHnyXs{dpI93tYHPmQ~vc z^Jw9WhKB%Jbr`=cdfm_@xik%^8|6BOi`!lHpC#T^ufI)n9OfNvtHc+?6LDV2W>Hzf zmBUcGrP)>t3;dro59FNso^a|x2$s5y9ca5R@6^Epr~3K2yef%>xx^R7aoSvw)10@1 z;BVmkf0+7l&c9>w6P#Z$`5QU^eUsNX|BA^!DnLJgA-HGt3TE54YArle9aB6+O#vKd zIW+~zF~Y;u6lBK%9>S)eIJ%KiQ&1hve6T5495qO-ra*ZhIyh%_5KgUf-9k2N^=GsA zXP@|UD4RW%%}!>s@oX0R(9Lplhbzpc(rlt;6EmB**(9)Oz_UD%TkG$LwSEYK4!6;T zOFEce>!E_R9_DL(ddcsw;nLv#y$XB-moN~^euLp==i82(z9Kf=ZH3&pFTK||$dB`= zha|~WZ!7j57{JIplymG;!m;;3u*_}Lq5Z>o$Bq;@cKuo^ zllQPs&U_JW8Q=bm=d;E>L75JoBfkz=&*Nxv|-L~SE0{bn< zlFg&0SDNQmTjt(&oG?T7vItqn<0xGz$BlaH*|K}_RALNarzHBUf|oguttxbr=G*s~ zZ=XboXM^Ri;=$V(Kiyl2qm}21H3=MbJPWKzlA{DGIKORfl^qhNR;BLsY*tQZvv+5+ zuV%9-@LSP%ZtmX}bAJqiPPf4)d_F(-iGsOL^0|+hxmyR{MVOWy)#x7PW2v0i3%uIt zfRY@&Wm@KK*{|@ZIn$+Zeu6<5z0FlE^siy9qbcFSoZ1O@sn*wP7?2Aw9WS~(5CHcmzlTRO~@N$f1v))~Cm`p5Sy zYkS6fJT|Rom`Hp0O|geajKp%-FAD4@Az0%!DiPx5JobeG>^R4EG2qwDjUjc-V|2wcvnByQ7#_*0)~#f-($BNmx3XE}7@sS@Ija23 zq3e!84)h}q)U^(@3F+WE5Qn{GO_BtxjIeLwbiba>elwf>b~gK_nC@(Dy5AMkeFlQ{ zZXU<>(I~dMm$BF6O}A6kyLn5I;zFW5=y|u-gj2 zZkMR|r14n2D<1U~Z#mAfb=hP4JpVw(%HT_4q2OuZjvVxt1oU$d+~hWzvE$A>^j!te z7lAuE%@bl7DeKFzFN>%3pjQO zR^}`ftcol)b}>}8dxessH2DL(f!OUrE;R=Yn9WO&fBlfD>c@u9;qv+%z98oC0t6e} z#un_kZ^In!FPy^zVh(4_DU>>TdFbOj##Nkvie4#p{3Jn17LrX&M@7d~;K>?UJF?hN zuE8j1F8eNCq*e4<6;3_4?$k@dsrN&$(QQ;=&qEuWdS9Va4-2Pm_}@6?e3w%^tGrg= z(ijmC|J^omEiw7QJD{$d)h0#a!y zzb(IbX>}Z~@Eadqe0ZLJV%^|ZguxF&u*q#~!=5KM7<{VG;M2mOYsv2`9zWqLK5~Mr z_+b3F52D8pk`)~A%sT4F1?q<&=y4k^?0I$r>T`vt&qMATAAH}0rRdO$;-=*L7V^U{ mns=oa)`34JfIkeut!|^5|BX@w|Bs&H|9#?D1o=;wD%n=#1nF@A literal 6015 zcmV-_7l7zPS5qVmD*ym^+U;6tTw6zy?|O$?EkKA%2!Svd*%%=}2%p#{#$3KIwy|Ty zF@`7UiKkddL=sm{$2lkWJ@-s9_hgPt=020jWM;3~1Du8IHM=u=O+M{-zU-I%psntQ z5OT8f+v~%ASm9S)Ro(C3Ro&H9EzBaJ%Y@X<64D4{u%eC-a&Ohofsg~~Xsq|l;BeF8 zOd^@-Md@IxkX}G7KAVlFl1*IJ!l}9J!PeGw)M#V_bapPC5RlPGm!8mP^kg>E)!o^RK+#BVER~+o zvVGd@Y$6`fI9%6aN5)7+E-z^FdPgjwWsCz|g@OE?Y&@IL`}(7)u--JB&=;F_HuV?Y z7o*J~d~md2Xx}C`HU4&IBsJ4Dn@&aNB4|?#p~TCZU*Qn5bKyihW9aF=x#ZIBG=-ZHmjapXkJEkR@g1h}q!9cLvG=pmobltGp z>l)m^J~HTdS3W=nq+Bj{!6xGlTkugVFJBu!-IO{Vj>>Sq$3w&v8W!IMB!pq z&t%avO)!~6Dx0~81NIAP|5>EtT-T{(EaS83cve@nSXNI%6k?W43WFyD^Ux26VL;(d z(b1&=43Ug{W-h7DEX`}_8iCZyk@^!0+EV5)?!skzK|7Mlrpk-OpgJ^X}00LKt7sWx5{251&hTVA)ZK~bLh^|n3!O6 zE{kiGoE~3@XCsEN=+s=sIF-Oa;V+ftHRp|ZLKg_*y4Ytlympf~98X61g6rw*l0Y6` z&^CEyGgTXtnCze))8-PU*`|g&wMjgdiYKcJ;%JI*)yzyPS(Pxp6Wb7)N$|ZZiSQU5)w4z_D(lH8Oxvdu zsj!w9o=ZmfU}YLjR`Hl6QV_SslT8tBlETlQJ&sYOVT_osTM~M5I%_C1OUaC7W(kwm ztR@C%Kn!N4v#xNE1} z6W9m4-(fHBUO~A6_`cgQhrK9HYAJwu(>3TxJ z1mq2{(WPM=pGq&WGdLVmc0#verZGFmagoJX%Xl`8Yh80gR^X$0%mc$CQi$E<8>ddl zK~^v^B!@;%SSAyx$gW9A(;QmVwChAXlhx5{OIXJusF#>cQvw6FB%DqyWc2iCDypjy zEu#kn4O%0HmL5PQ6OnhbmhRr*f=VQj>E63_fd=ilU{P8zW;4 zu<$C7G1OQ*oynGodfXW`ccs2a>MhzU@9*f_*vBo!gWj`0wZ;9Tsrfjrczm|HSZ@}J zQd6n(CCfBy7J6?86Z?ASB2Jgo5;jwu)>AX$i-;4Woa&rz;o;?CuKB#S@q)S^j``+cvm}1=(zR3C}!k4w7JL z{^0Y;HVZ*Hp3HjU*-oA`v}Ba8L1$(LOGGTSh`}(A2jMcktS^ZGNTjsrKx!_TRe8X4 z3mUYUd4gvw>&%iVU^d}0R?*qZ(i_2(9wMpW9&9YA->>ji zZ%TO^<=0cBys-$kZSMV@rMPO-$b3OAE6TAI1!=wfy56H%FUXs~Hp*=E`{;u2r|j9J zEL7!9a~0R-O@*MSLRS^*&8k+=6{@x8J<82Bd(*tdmD{no;|4>Ds(AH{dY&rZqvRFc zeWS8a*P9Dn|3P)HE*i03)N9^P8LTYQ3f-ouZ>;*8_IRiei~{|*D~kR;CvBOf;bgTZTs7`z!2K+^p9A*`;QkgffY@0eh8c&2Ioh>`B89w8Jyn&r^7j3 zd&=c;IbF3bhwEqH`aN*{KDhn>Tz?3zKLXd!!S%=B`V(;dDY*U&T+85E0oOHfy$!BE z2iGdN*1+`+xc&lMe+jO?0@q)I>u!1edw`Uh}(+)j6``+0EJ zxzD)W?)n~pGG>)j8SL&#M@4y6#Z4yNmd6g+&yR! zFIenFFH*Hy0!6mgi>CGps12M^J%Tn0x<$|?L7N5LDrk$KUO~4Bx?Rv#L3aq+Ca6!) zc0v7ub_m)jXqTV?LAwPF3fd#+PC<7Gx?9jag6h?icicpa(exNvy(A=ez-*VSsCDD0-Nhr(V8`zZ8M*iYdAg@Y9ODBMKh5Up|1n(qKRD%A&Q z-~DLNAeC;Xl0>EBR2rqyI4wO+Ev2;Vn?TD(>8)cdEU^a4u7JdTh>w-k`|G>wgOnYm zC2s&N`7zMZucIgZRC*YjNAP(ZpO^7DMx`%e^9nxSz~=|}j8W+)*t~_$KjHIhprzjh zYKc%wj9R9tB}HiirMFQ!OHXC#*$h25Pj3dQ%2bu8s#5hUXx6uZp8q~jXnh z8Q2({WE**uxc+Oe-1dKC zU8n+f!)jS`CzJ7>$c zNK7Y{oULk+*feo+wzf@TGsMl=dY{CSq>-~*>LnH?TRGd}m6$=cbGEfXViDrwYDqz$vi_@|X}FhgOMQCQk|BX{eRh zCGs4=6p-i97nLwlMk+`RsUsfJOtz6W(m}e(F0zjtB>iNF93`XVw0sVo{{Xry-HgsZ zii~`=pPT{pW^#dCB4H9Ew~-`ClX-FnxrbZ@@(_?mfjkN1Ss>dKsKm*w;86%x#;ppG z9MGr`xf-@8L~%ijLevImQ;4Mrd{3Xr4m%X$ibJ(R>Sn;N5cln{T_N>z(5;Y$CD@}7&)u+1A&vI|G$~}ug808WK$eFmUaAuTTe)GEZwGcpjon+1MbG6mP$qf=%5(1x5pI%V&N5j@&} z6By6 z_soQ&U2|Nzsa?AXJ4^FuuL!iIkmND8qQ0zvW-mf3=V(34f#!(nC2L;tj+aDeSdCa5 z6=*})5~eM_h|*Mr=_;(O1ueAV-CPcb;j51PT%Qwj-4T*KMkDGg3UgH!%~i$c+QC;M zVx2l2p^i#E1r1wUuFUu%mX&K^b!=P?QftMpb2%JeouAS8rjE#^H9O24Cen~*y6;eG$3+n3%knSSLdJc&pbl$fb z@Tw7YYRLaR2&=v;ww3l77`r4*4UJ9WK*$iVk%m0{YXbi6ki}!PA&RE}-&h2{g~OMe z4|s#VOT!3wgut)`ftvC_Ul&04gs8{x;rQkP(AFZL77kR8FZ74i;eNPs+2@PcV%pPT zTP*bS*hL=A-aO`~1?IgWtH-EE{k8(;_9DzyVcc?H#TPp?_ndYJRXaFF1!8qNF{DMcwr^1eEMbI-0I4wUOqyIKacepfps5*Y#yTlU+E}dbrxZD zajc_=rPjOgm^Gt4xL>FjbT{FN$QxaAv|vNl91YmOnuB5^uQ}}4sHS9DbNoU?SRil0 zw}c5-AyncqIU_!9SgdT3fE)1|UnR-8Fh-$(w9>_HbWBhlmjrc1cT;n;$UxlrL zZS{j|{<1ZEd1rpQZ;I*ehft}<=)jI$h3R$|O}A$~d7SsH1$0P&@12GT@P7)%05C~F zmOvHRn@4>~pgsVhGLPZHm-iJ=dy7!_bJW4*z$NfM#i1^h50{gO>Of~0>Q166ta_t% zG@d))z$5P{!Q>f;Sg`vDe*^qw*o;6$M>i`a2l6I-UzqS9gzO%p2WL81Frlx=gqvhp zwVgK46?!y04A7>-L|?3Lc!FG=0o0x3I){tTyArrSd~3cyyXZK=J3Lm2FNinlyq3$M zvWzQ7z`b=lD}_1!--L(qM*Tn-^$>*0J;qL)yT4%6;Uc33_`19%iG{h3FO1`yxguvd zZwJAj1<5hW!_^dI#~~iVrl2@_kWy1n9ozX}Q?NMdkXlWF@<4QO&gvkXTIKr1T+SNE z&1JKh!KMk%@?d_gza!TAVF)=q z24CQz!ded(t@Q|B>vPKihYgno_wQ@KH*gsPvEpAa-0XbYano1DrhBZAANSh(jf28C zuX;q1Tn(($cW4kJ^GM#XPYJ^wfl!6VaO3<(3x*vlGVJ(zCgs_lM<(Af%4fM2xEisC z)gyTG!P-bp)$F1llSJn7GCsb9Aqw7oYj&PCp)%ice`xwt~Y~^~rSFLptvU0uAtJ)b>8>`HZ z&2_iqm$B&v(1m!rV-fM)q~ggQ+ZFmCp>u+LRB6khz6hL$B182 z&hR@|7r%2&!1V^5BzPPn>p@mB*~VyIxg{!e_}Vz$g<-?}vztLG3m{bm5a$L+?FPs> zd`)UIFJZnwsM=$+M-LJ0;BQN=Z})!;E|s-wW!GE%ABRi!cFm42++0}y^F`|)%9kSB znpa)DhV|&P&wU{xW6v%56?j>!z+(`q@fda3aiM^9YZ2B(j`b$+yT)(ON-J(Du-||r z*}Q6Ib^H8U>-;;8(`Lv%AVSvhG)mVhaiiXTvEl(dl^8?VDT_X<;3dvus|wwe`Sye6 z+h?iv&jRa`{7N*D_x;<#_s1dR^cY>(ajD?@WRdSv-1jqP?$*J7?~LrIMe8sfOO?D_;I&Q% zl;l`)M&@nBukfTgZ%E{q4zwBvMlg+|k57UqCKe3GQaQ!HSIqM76}J=FO0>LvKNR*o z0ijxtu?x)z7wn4^*%#&Z^@|fM`=h>zvG!wQ#5Wab_y04rYx_HZ`6@kxyxH#a#Rj}> z-qb7Fe!(*DS!CP!<)DpU+w}a@UlUV52_cuq*nu6f!qn46QyYA0*Ka^nt@C)P4NUA^ z(e_U4^V+n1BShNEZ;AVeWFzrB_QwSFQxK~27}W@ITLJrW5q5%Od+_R!7(P#~L=il8 z*sH!2wzO-9!xrzqYGE8SlZX9=fPET5Zja%|j${EgRRlZBVHYqFZ{_h;g2}%GMmSTI zXQ~A=!W<{jt5|x~FR!fEEg!$dt<)*&H3oR;@vAHAwJTqGWKnu#E7ZS^@rN1cm0a!{ zx!e!M73}uB!Cw^yKLeq9kFgy)(glMvMFwYWR$Iw8fq#!!YrYy$rrv_4FIB#bla-?f zUb^Nug)N$kiE}0P6Tojaw}jPoi_sMC?79T}TzDm`TECjhNk7l!-p=KaW87DMaa8${ zL(?5Y9Oz9B)V%@Jh;(QJh{N8#E=dAbM%cH|-S6ab-^=BGkjuR#+?~t2`(5Ggvk+?V z7~R-0UvPJ!$lXQ0KUKKxRetR-T&Y@JiTxO23;aI0lm~lVfISBx{4%-+JMJie-B|>7 zmqf+a8L!p1>Q!I$Rick=D_+}I_?KfW4E`k637!@1&O?7iKtB(mMvt)#JMJk!-&+KI z1-PLzJReq&GOv1db;S#IFD4l3m&YiqcqMy@kcLolvsIPvv~;$uaB6j!`N^i9^CNZi^7K&A=KnC znz84hO+Gwa?876%hx4Wj<&Hic`sl}miVmn~m14(lBq&KjvI%!oG+YIqtdX@Niw)%( zjDqbIKf-&oidL(_s1Ixy^>Ja;2O-q#F>0{q(M?7@R&3Pc!l;}7J4QL*V-(LSuNT?$ z#D-0u5H@`XLR&qC6MLTAWYbf{Ha!jNzvAGxt}-mqxY3YV^-5RQR&du}%HT~vDlg}k z<(ICmO~5sN;lq0mF96SMO!%sp@WT*l@ffYx^X#SxpDUj5c`>1DIp8myIO#7vc9N|6 tVPez|vC+e16$iYqf%-{-`Vk0uJw`46rB4