From 957886d08456598630bcd982db8ebb28c732dde6 Mon Sep 17 00:00:00 2001 From: Thomas Petersen Date: Thu, 20 Aug 2026 08:15:23 -0400 Subject: [PATCH] evidence: PR #6368 native keyboard journey Publish the sanitized exact-head receipt, MP4, AX snapshots, cleanup record, and causal native mutant needed for inspectable review. Signed-off-by: Thomas Petersen --- pr-6368-native-evidence/MANIFEST.sha256 | 23 + pr-6368-native-evidence/README.md | 17 + pr-6368-native-evidence/cleanup.txt | 10 + pr-6368-native-evidence/environment.txt | 15 + pr-6368-native-evidence/exact-adjacent.json | 15 + pr-6368-native-evidence/exact-diagnostics.log | 9 + pr-6368-native-evidence/exact-focus-crop.png | Bin 0 -> 2243 bytes pr-6368-native-evidence/exact-focused.json | 15 + pr-6368-native-evidence/exact-journey.mp4 | Bin 0 -> 92140 bytes pr-6368-native-evidence/exact-receipt.json | 55 +++ .../exact-selected-crop.png | Bin 0 -> 2417 bytes pr-6368-native-evidence/exact-selected.json | 15 + pr-6368-native-evidence/mutant-adjacent.json | 15 + .../mutant-diagnostics.log | 9 + pr-6368-native-evidence/mutant-focus-crop.png | Bin 0 -> 1074 bytes pr-6368-native-evidence/mutant-focused.json | 15 + pr-6368-native-evidence/mutant-receipt.json | 41 ++ pr-6368-native-evidence/mutant.patch | 6 + pr-6368-native-evidence/native_journey.swift | 455 ++++++++++++++++++ .../restored-adjacent.json | 15 + .../restored-diagnostics.log | 10 + pr-6368-native-evidence/restored-focused.json | 15 + pr-6368-native-evidence/restored-receipt.json | 55 +++ .../restored-selected.json | 15 + 24 files changed, 825 insertions(+) create mode 100644 pr-6368-native-evidence/MANIFEST.sha256 create mode 100644 pr-6368-native-evidence/README.md create mode 100644 pr-6368-native-evidence/cleanup.txt create mode 100644 pr-6368-native-evidence/environment.txt create mode 100644 pr-6368-native-evidence/exact-adjacent.json create mode 100644 pr-6368-native-evidence/exact-diagnostics.log create mode 100644 pr-6368-native-evidence/exact-focus-crop.png create mode 100644 pr-6368-native-evidence/exact-focused.json create mode 100644 pr-6368-native-evidence/exact-journey.mp4 create mode 100644 pr-6368-native-evidence/exact-receipt.json create mode 100644 pr-6368-native-evidence/exact-selected-crop.png create mode 100644 pr-6368-native-evidence/exact-selected.json create mode 100644 pr-6368-native-evidence/mutant-adjacent.json create mode 100644 pr-6368-native-evidence/mutant-diagnostics.log create mode 100644 pr-6368-native-evidence/mutant-focus-crop.png create mode 100644 pr-6368-native-evidence/mutant-focused.json create mode 100644 pr-6368-native-evidence/mutant-receipt.json create mode 100644 pr-6368-native-evidence/mutant.patch create mode 100644 pr-6368-native-evidence/native_journey.swift create mode 100644 pr-6368-native-evidence/restored-adjacent.json create mode 100644 pr-6368-native-evidence/restored-diagnostics.log create mode 100644 pr-6368-native-evidence/restored-focused.json create mode 100644 pr-6368-native-evidence/restored-receipt.json create mode 100644 pr-6368-native-evidence/restored-selected.json diff --git a/pr-6368-native-evidence/MANIFEST.sha256 b/pr-6368-native-evidence/MANIFEST.sha256 new file mode 100644 index 0000000000..fdfa161a33 --- /dev/null +++ b/pr-6368-native-evidence/MANIFEST.sha256 @@ -0,0 +1,23 @@ +23d329e23dfb7fc3a1710af8f29ae44a79896ea6958a5c212ad7e9201aaa5d38 README.md +ebb0a53f87a1e71708510937462b1e927c8ce6d9256c24ef299ccdabea776901 cleanup.txt +a60139a0b5918cec82e63d49c9377091b98c466a3fa56ee4a5eb90da189900e7 environment.txt +36690b6554077cfea3f30aace8b7bd9dbc738a26dd6f9267f758f73379436591 exact-adjacent.json +1e590f5113181a330d7a02e019f039fc18e001c952cd1cf70864c5d75937b39b exact-diagnostics.log +12761900cf63596841eaf546778eeabea80573744e2fa2003221544e1ee07ac2 exact-focus-crop.png +dc99f878a4802783d45b2ca2eeca3faeb71bce3420960d3c64228ea1778d04e4 exact-focused.json +2c39cd7fff5a2c37f15fd451e780359ce1b9aeeda130d74cad0b3a11bd6c40bb exact-journey.mp4 +9e3934e6e67a1aa09ddb100f2365f5869bd317369f64b6185852e11f456a171f exact-receipt.json +484533763f9650aa381aff7c51ddc8dd826eddb1df019690b51e084f6b2db072 exact-selected-crop.png +1919e6d1ad9c769cd6c41fb4a225b53f01ad1e500e04ff76fc3e75d3d19bf802 exact-selected.json +36690b6554077cfea3f30aace8b7bd9dbc738a26dd6f9267f758f73379436591 mutant-adjacent.json +8bc29f598afe4a34d0902574b9863c8b4a2a2bf79a762a9721ecb47c7cbb0518 mutant-diagnostics.log +fec3651b16e5abc0852d1ec04dcfb167a42887fbdfbfb713897818b529f1938d mutant-focus-crop.png +dc99f878a4802783d45b2ca2eeca3faeb71bce3420960d3c64228ea1778d04e4 mutant-focused.json +3f0a5d2fc4182d7e966e4ee62a8aacece16180f6a10f5bb0d7606a96dff9de10 mutant-receipt.json +8070b9f873a0f49ccea41765b2dbca30df52a4ece47e6e2b29635b09094ee534 mutant.patch +e3784c2a95178b30fe8580d89d4c164b0a11a66fc3db3b09fc018af22219469f native_journey.swift +06d5865e68cb0085649934a4103df853e5fc305063d81f26485bf2acec0c7481 restored-adjacent.json +005aeada458090833df23d95e86082cf321c0d0dfb28a31cfb5dc94cfbc8a013 restored-diagnostics.log +dcd1a3efe372f5d5bb7ff412a4a59fa3b444c3d6ef850fa64660ec1b792f6794 restored-focused.json +332105d66ccd3b5db46ca2fd54d25492abf71bb3b801603d95b396c4a5305b3d restored-receipt.json +ddbb9a48ae499c31e571fcafde2d37e1b795203e2303a61708c1c3c7cf89d848 restored-selected.json diff --git a/pr-6368-native-evidence/README.md b/pr-6368-native-evidence/README.md new file mode 100644 index 0000000000..cf9fecb724 --- /dev/null +++ b/pr-6368-native-evidence/README.md @@ -0,0 +1,17 @@ +# PR #6368 native keyboard evidence (sanitized public bundle) + +Exact head: `ffb765e49e2db60fdb167fe58440f3c6d5efa17b`. + +The native Tauri/WKWebView harness focused the adjacent row action, delivered macOS Tab (`key code 48`), asserted an entity-specific focused `AXCheckBox`, measured 732 bright focus-ring pixels, delivered Space (`key code 49`), and asserted checkbox value `1`, heading `1 task`, and `Clear selection`. + +`exact-journey.mp4` is the complete 30-second interaction timeline cropped to the checkbox region so no workspace content is published on this public OSS PR. `exact-focus-crop.png` and `exact-selected-crop.png` show the focused and selected pixels. Semantic snapshots preserve the entity-specific `Open task` / `Select` prefixes while redacting the fixture title. + +The feature-specific `mutant.patch` removes only `group-focus-within:opacity-100`. The same native harness then exited `1`: Tab still reached the named AX checkbox, but the visual measurement fell from 732 to 0 pixels. Restoring the class returned the harness to exit `0` and 732 pixels. + +Artifacts: +- exact, mutant, and restored receipts plus AX snapshots +- exact, mutant, and restored step diagnostics +- native harness source and feature-specific mutant patch +- sanitized MP4 and focus/selected/mutant crops +- environment/isolation and cleanup records +- SHA-256 manifest diff --git a/pr-6368-native-evidence/cleanup.txt b/pr-6368-native-evidence/cleanup.txt new file mode 100644 index 0000000000..f3846697be --- /dev/null +++ b/pr-6368-native-evidence/cleanup.txt @@ -0,0 +1,10 @@ +Cleanup command: TERM process group 84227 +Native launcher completion: observed + +PASS app process group exited +PASS Vite port 30355 released +PASS no worktree agent sidecars remain + +Post-cleanup HEAD: ffb765e49e2db60fdb167fe58440f3c6d5efa17b +Post-cleanup git status: clean +Post-cleanup git diff --check: pass diff --git a/pr-6368-native-evidence/environment.txt b/pr-6368-native-evidence/environment.txt new file mode 100644 index 0000000000..2089c2e720 --- /dev/null +++ b/pr-6368-native-evidence/environment.txt @@ -0,0 +1,15 @@ +PR: block/buzz#6368 +HEAD: ffb765e49e2db60fdb167fe58440f3c6d5efa17b +Branch: projects-v6-pt2-selectable-workspaces +Pre-run git status: clean +Pre-run git diff --check: pass +Application: Buzz Dev (projects-v6-pt2-selectable-workspaces) +Application identifier: xyz.block.buzz.app.dev.projects-v6-pt2-selectable-workspaces +Launch command: BUZZ_SHARE_IDENTITY=1 just production +Vite port: 30355 +Binary SHA-256: 1600d8d63cfca8942e7d809879ccd3738b3fc04239839f87be27ee6fd4ec9f4f +OS: macOS 26.6.1 (25G76) +Architecture: arm64 +Display: 2560x1440 points, scale 2.0 +Isolation: worktree-specific app identifier and Vite port; mutant restored before cleanup. +Publication note: full-screen artifacts remain local because this is a public OSS PR. Published crops, MP4, and semantic records redact workspace content without altering checkbox pixels or harness results. diff --git a/pr-6368-native-evidence/exact-adjacent.json b/pr-6368-native-evidence/exact-adjacent.json new file mode 100644 index 0000000000..e2e8ab9f91 --- /dev/null +++ b/pr-6368-native-evidence/exact-adjacent.json @@ -0,0 +1,15 @@ +{ + "description": "", + "focused": true, + "position": [ + 317, + 224 + ], + "role": "AXButton", + "size": [ + 1921, + 40 + ], + "title": "Open task [redacted fixture title]", + "value": "" +} diff --git a/pr-6368-native-evidence/exact-diagnostics.log b/pr-6368-native-evidence/exact-diagnostics.log new file mode 100644 index 0000000000..72f775b835 --- /dev/null +++ b/pr-6368-native-evidence/exact-diagnostics.log @@ -0,0 +1,9 @@ +[2026-08-20T11:58:25Z] application=Buzz Dev (projects-v6-pt2-selectable-workspaces) pid=84587 windowId=29941 mode=exact +[2026-08-20T11:58:25Z] AXPress Projects +[2026-08-20T11:58:26Z] AXPress Tasks +[2026-08-20T11:58:26Z] AXPress List layout +[2026-08-20T11:58:27Z] focused setup control Open task [redacted fixture title] +[2026-08-20T11:58:28Z] posted macOS HID Tab +[2026-08-20T11:58:30Z] focus-ring bright pixels=732 +[2026-08-20T11:58:30Z] posted macOS HID Space +[2026-08-20T11:58:31Z] PASS native Tab → entity checkbox → visible focus ring → Space selection diff --git a/pr-6368-native-evidence/exact-focus-crop.png b/pr-6368-native-evidence/exact-focus-crop.png new file mode 100644 index 0000000000000000000000000000000000000000..0671300feba52a31c6ef41e6636e6c9dd66f2aa6 GIT binary patch literal 2243 zcmZ`)3pkYd8vo|f<`TI(xlV&9%Z$l&%uJYZ&1H5(W2NIZnlV>1qZykzM#bStAyl#& zMVV~uT14(AS?wNTv!t?-kRG>II9hVP!HMnZe9!ZK|M&lU-{1Rt|KI<8o-d8;@2R4s zrvw0iinkYu08d;_?G|5m7V}L%?H2B#`$5fJN5H z%pVTkC#$tL2bW0W)eH>`Floe`Y^8gSRobLDg`n0qIZZcZneCq0$ZZa*lH^s1QWr-j z6^nILxPI~V*sJ29>!S&%v|{8p7e-Dc&eV@MBAhrp&LXVTxheF>&z4t9tjy-m!5a}f z#@-f`SNMD=KQOXFc=x;iFCopVs~N576E?T6@Y=^}O<3u%tgQycT}$ck-i}!=16i3lli>tVP>1(@ZS< zp4D!``7^JL0_R}7i9`tOR-|Teo@yxg)!|XzMDh+50K$Qd%z*oJ8r3_-&kxuK`U(IX zq6cgPJqTz7i2g_417ZQd)^I2Qq%r{bMvgzY%AZWotmYo7@2X`8viKWnw*=Q+j z(+6XKYar3v8(agU_%s?vK<5fo7Ypk_K#}JaA^-p#Gr2*$DWG!g+0dudAOVd}OTFFGk$iUb{_3zsRIy=~rcLMPv&K;y+zOy>VmOUSqDZ1arpUosAa@>O?U|`P`#ugOFPW?M()K zUB&gv9mnBwcTJ>K@6>{VzAgEA{Tfzr27W*_I z@V%_GMe?9fS6x+KI7zqBHs&o1r5o@R2t`uY;Y`r6oudP@swtXHKdggjj#y&vcW92=X|6H%yl^Cdb5#(>@i%1>>nj0*arshK9^uAYo28_Ra zUU0B4<+vH@%yMGLfI1;{bYIrAvuG?Qcg!eaO1wbw&zsEk~1d4k19%34h zu8hp2XLNq~J?ZgMzGm?Buby5otjd!e+6jsVUa=C*=g4UG>%d|uCix{4MMpTKkt~x6 z%pQeSrWn3Y7W4jSu%Js7pGI3KyM%1dRc``(UGn~x*2gO8FM{Mx`uNvq>uEW1>|O-N z!qGV@QXfIZd^ub8u*U7QPsdMhzY5;vde-#nklD>cu>-*=Q&2QNKK^WOe9W;(Ep(@0 z9hR-V!e}e}$MS0e{^YM7SK6XVr*yJa##vW_j&>Yfu4vf4aJ{3`woduUzn$xQ7WMmQ W>0W~uI?LpL6mNHbQn_1r@_zx-VQxtP literal 0 HcmV?d00001 diff --git a/pr-6368-native-evidence/exact-focused.json b/pr-6368-native-evidence/exact-focused.json new file mode 100644 index 0000000000..b8de370033 --- /dev/null +++ b/pr-6368-native-evidence/exact-focused.json @@ -0,0 +1,15 @@ +{ + "description": "Select [redacted fixture title]", + "focused": true, + "position": [ + 335, + 238 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "0" +} diff --git a/pr-6368-native-evidence/exact-journey.mp4 b/pr-6368-native-evidence/exact-journey.mp4 new file mode 100644 index 0000000000000000000000000000000000000000..3dbffffeedaa88007739ff310c87116f0582a134 GIT binary patch literal 92140 zcmd?R2_RM7*EoEyA#*a7xho-4W}(D2W{5~q<}ouFGKZ)LMIn*7jH!^JQjwv7WS*xG zQDi7Y^6h;&PrBdpe7(Q-d7t<9`+tA6oU`_t*Is+=bIv_33WdVhc=)*5xw|-_Py{G= z1R!dD#!|$|Ra^vxQdV+uaXEuRp&Xsg*jj<(rXRu&D3qr#3XOvQfByV}fMGmb{wL?3 zoe`i=O3of`<_>^pdWfMT&9vz|90WM}yR(7&d$d0uV*9;o)3(I6WQ? zI{AgacNbQv5h^_$EGlI?g}v>lb-o$%w<%{wsj?<5? zZ&Un8ei3;b|0aKNI3VKq0D|Nh8OOu)!nKK%OKH|z%Lw*&;f!kkKn)X{|O(W7qNrL{W88u4ySMH z&p2>$o8m^~apU0EFE|kXm+(z?@%{T#9N*smHvSLBhs!&D{o?l{>fhG|GOx%yAowr& z1jdkYoLzw6^U9$gfQJIL~n>j|R9b$-NeuqEN-5gejW9}>?$O$V*(|I_~O=>N2TztfMK zr%m(sJO00l2g(2MX5Ah#aUkD%4FOYGB51~V~ zo8ttn?oZbZ!Vk6_938fY^~Jn?MC^dA7B`OAL2#rFAsNacIHCuMAE6`uBJzlSd^#eB z=)__ zM`S%AdcdvIFY6ImKS;f9+n^(I_;hgTgOkUnBmDxQBl?hWB#+?I|4;2BeE-#cgVYmL zx4EAo=Regyq;LI|{|Nox?f?IXeJ~kF zJpZT1i}?S4TR-?uSx^5X^$3a)iRWMK*Z)V)KL{F$`*(T#U7X1E0;1<%%_Aa*`17yI zBmVuB{O{<0*Zw~(|2zMGNB^h&`=|9I@%_8{EdKokQfG)i$bN>8|J}U&Vizb!?BeT1 z?BkFBtLx~WmPh&ok|%uskn4XWPJH^`_3z(ZM}OD<-^nBK;pY#*e<%O%rXzkLb%NaQ zA$5RHM{s;PcodDh$VBwu(~;G;&IJW`K{JmL>R|10_5=|}FD5qtRh5&!Y+ zBkTOH<{6>?ZXS{6fPa-gJ>kqh<~_vKynZqKOgw`U*++4ap2qe9Y2y+#6GeP z5I=t>|2sN<-VnXW{33DwOMU|(L=N#A(TC{&onQay^nZF@{?p_Coqzx7`9b_c>J(X5 z2>!eH{%QJux_`fmAMqbq|44rStLq=>*N7cN9?^&FulW5O=`+alZUo1d|DAux^##I* z$Rqj?{rGewKIHlZ>92@9LPwt0FkUB)x@!!?|Ps{(i{r_E`MdlC51AcyyeFCX>d^+-80RH?SeG}=!NZ&x@5q`uz zk|%_Y%vyZ(@;0Tkp}?ujRpX;2lYa~LBm9cf+LJ;F93c3X#k*Ky8(cAa#3yo zARX#}@;U%uT+k2LaE}0heDE9sc;62N-o^a`2R@;80RZoVceb0hdA^N z(!l$=I6A};eVgg<{LgUcC!!nr1M>~y*`f#Lb3cgpA;4n+za|1wfxlv>2*I-Npz%~Go4+8W9;oFQu9tcntt~)>@ zybq2rZaD9V9!N*xhVuAv`h&5{0E_{En#7&M{6HC4^Kee!IZ{(_9l|+5VuSc*oqvYI zJ_6?r+K2gpH2`HG4%dSV0GLOJO9K!CAPfN3z7PN{08lTi3z#>g#v%Wo*@L=aZV);f zIN$6qK927{>^m?nhq6!y1n48A!Lg$N_HUd+9LB}535UM_yK&6F(I1#6xVGUD<^stF zJR)N-Kk)p&gF~6k@}PzZ^T8NgZ`7Lr_7=FW!7*67&^`tL!t=k4Lw{f`AKdT(+DB?0 z`t+ZU!}S8!Da=3IW8iv%J%$bd^dF8RYaHUa0AQa2{e&PC9PI%BI`~6ITu(wvgCp!i zuy??9=>h=udAQ#IodmE~!LAPRsx0H_Db!?g(adr<(ecfh>_*u?n+ za|(Md^asN4atveGJSQ+lh(ljM%@KrvqdEX24?5r+%0L?splt|n4E9zr05B(z2J-~< z!B`O+Fh5W?;@{?c!Z8>RltbvSo;UNucsB245Z}yy0N}_z0Cm9n!vKIjKpgtHnO_Xx zu-`$Qzz$(BI35Nd1OSf1eGBFr0|1Eu#s}kqYYYO^3CI2lhcW*Z9r^@o3-(ob4s;O8 zfTR8ft^n$18l1!2Lb@=(Pkr2s4er~$kU9OD3h+@QfZfgd=IfFlQh zS^yvxf@%PUU_1>#7~pLJN2vEBfOY^^0jvUO1_0Mg8US|yX8=GyP6L3o0?%Q-nE*h4 z;5h`Co6R`X2j>RL+yb_a0Kfo%ILI>^tYuUqfGTjV1KvINu$IyL01X2G){`uN zKeLJN!|!l>AAiUH{|7o)H-F60|3p0hiaz{&|4-nXd)$9VAC!kNK!Ec93J&x4ckORp zBmW)$@#X&&|Nqr^|5bjNAK1eXpEmaf{Ji~F@c*fK!moS$yyMgVRUBX6{|5eN`9szw zGH>|#|F7ore>#5H^EcNm+!yHGJuF?o5&odTV=NDFwD7d@FbBtzPS&_1q;YKiMi1~U zAa3Tau8xp^{0Q2ue{Bd?u7?X$$Yy1Z69!7bZfSnT27IlC2>3573UE>zH*0GYdRLGW z-~v11y)DFRYx#Z36Hmsv50%9WbYZ$Vr$58*-oOZAEaCTsh)7Cc+{8phMKKm)5|Y9a z=74Z$FJKTld_-AQP#lBRR|K3^)|P;v=;G?*Xl>(x5fv5|6BHE|l>mdb9v-eTLPB0% zUVGs;lDIgUJMVRIJ0%3I?6vi9as)gst{!$S&h9c8OLGfzOIZ;N_{I@gF^rY9g`*u#7Oq+}YgG$K6_1*jr3S*jq$I4C7=iYisR|ard+UXZtX&?mj>i{5Ey7k`>u2 z41~ZhjFX+WwUsH!oUS{D_<99Ygthd0TB_5jk&vrsjIt#oh#&6S8&?Z)Wyce-P%J|P!!`~>jor% zBJeFHE-nt{wg59l21POMj&_#78Du~hR{~ybjylL2ydL4g71g{D8}8= z+S%ID(?eEV7`o|Z4s+^e?QRRi-7HQ22p7`bEM+a-Y%osXTUM-LSOAd~k=iSaISqr6 z72YcePFJdM z?l+FzCHyJ9ien|BL+&q^cExIxxt5v!u#hrRwOYk$Z)I5`yPj4!K_#=DoRZpQk#kQ^ z`{MJbgZHfZoF#7^y!za$e2_|vjlCtT)97NFZNY;z|9bVRs;iy69d_hjls^kKXT8)J zm~wa`)u&KHdu2%?)2c5OO^hg=$}qZD6Wi^v zV#iz^&0Dt)KJRIJG(8+fNAvaVK|wMxh6irvEleJ+RCu{5GailpPH@&c&-u9DkzK-G zsPIR_*6yrBPRdI9o^%+MYxj$_-E{d)E(bNNR+ot!YVkHy=2LHsT(s+ZUQGG?tcJ4E zJ&od_2#X)V!loZWxGpwO)63UhG#{b8cUW*MA;Bf$cU2l|CizU4)r$$mItbB{(%}jw zkGFgvLbb0RI71p>jTYRSc=qe1lTT`T+#RBKeIHU6EgAOSt|zk6TY3C=s{>V(kL`$H znSGbH9ZJmdf;myjs+E*}h*23Gra~j2>tblzPBM>Pdav`@_XuzMaI_|p)OmmWf~L4( znrd;0ilK}m?8wb@YLdt`k>DF={T4njHguli|0Ku3blv#fdyd9)Stn|8mafbx|cwlOsLXuC?w}mhw}A+iQXqPsIAxI>;F7K;F9;?I6-joOR><)<~3!yg_KGPh{>R&TfPoy1~y z%}QHrbCP%Sowm-2t#dn4Zr}Z|#NN`iFZ2oNqSr2#GZ|D|uHtgj_Qs){4^FL6N&Pq_ zy%_KSvrnM<{vb>4eWeAP?9cXAHpll_2EL3=8`F$tA|5f&&XtLpxos z&V;+nvPJKGqzH|ZLWdS6@nTW;_;aGa?9}fw`AnGEk$A4pz}@C`m47YyRl6e@{ zJN7NPjXGx-sWcR<_z;+(P{ajb17*b~?simI`;k?6B}YEbdi*6HSNEH$E#JI)L%XKv zT)OYkmge-TJTIqlu2pL?t6OkZInSAt-Ic?6@cEYFEoD7^-D43vJ1_Iy{U)sU^5Ue@ zyB3vk*&jD14R(%aoZ8cZI+CXl<{!UyhNQfwH{pD2@LLLj7OLY>3Zlw!@>Wy*5q9?S z(qWPe2T&ftgM3vka`%mO!;Y{UO6*(7Ot9wKA5u7`GfTdxO|EldD}U%Q$xpS}Z}-MC zrxL314I5$3e)$@IS@RWpayIIaz}NZA&>sYMSa$b&Jl`govFqJZQ`pqX_>Jn z{34>O%n{r&#xIYZFplD#Z=q{$%J7|gmmx6aRprSkH@~O(>8mj^nRd%B_E zjDn#xInT}ofx#=#yRlSw#epft%QM#^QNFCW<9WQtPZcTpdh37|; zd}j69z52y$b<*!oi6wH?#Udil$S7Ku5 z6ia)+JA697?>t@Evw#36pup-E~ACj6$yGCz7|sFkyu;|8^MOn2kMD;{iDuNW$hI`kD#(+IyWc4+N> zC{6N?_I5#r?g1gO$4@yNL`|$eR+?nDn+D#T(1<_KV$_u6JvVrhN@M(7Z~2)gty99z z=citV-za52WMY*xFWzt&x4J7 z>PC71hD)bAQJ+cr8;L-U*)Ac`zVKLOkxBEp9U6yQd+S`Q*mtHaM7=ecpnTdve@9|h zq+zG5vjUOM2@5(em5MvuwUqtmYDIPVbyFBgi+|XK_vm!1V?YnJg4wPYbSf6ouSMQbV@dyNUG+0ra1#^ zqz!a9=C?!xJHQM(OHqr0-5rqWD6c@2tsK_kP#)M84 z1Wu!?;?eDj=F_DywS1ALU!#jJ zH$<#iujvG?@y|Nymiq zrznOe$v0G_j^yy{yxmow_E8jbS1~bHQ&1#A8{r0jBa;@%MY<^=9$eJTIRri+(TBF!4Ece!*g?k`)o9361Kr30^TZVPEyG>llZ|SoZ z4ErYpO&C34e&0~}&Ew-j4hs)UdTT(x-QMd4jPWzuIGMj4$YwcvoWVMw85Y9XKGgOx4WGk0ewkLGa`3|*zRE-%{koMkDwz?Yl7%%7yIuEBm9=cMgFhDAARFn( zOnK_6>6Hbv-rs|v|Qs58ItP-Sh@6nxR5DdY-;@a!XMP|2<$Kjt*+~rV!sx>l+vg0%IUdtVyUO6 zbVvP5<7}r_EAFeQI?X}H5Bhc73nFG>Azg_<32X7@ImC6|*iNbC*S1D-$p4ZK=h2HH z?=Ye>Boz`Qz`|~HY6+aKGes;PuItC&UQSAKVY3j<+D=)XaMzkgVdxsSCo$ktL#LL( zZc!+&%?fUOqm|5aL+?GgUU%@8I4MWQHsx*h5szz*Ix)$OWs|m3i{14)`b4l>>61nt zi_bY8&h7Tc_ikH_#h{pZf`Kv@Y*NMMX<}KReqQlIae8Mk?4 zjXFN@5y>QOXdR9j|4MPucr`Fa+FoxiYB+9uM8Y5^Q^KmD&5z26A4ftRA#6!!IG3{@^{yU|ffZ+`dCgTa7tCN({3CFZP<8f`g+ zQnu%2T(QI})kn94$NT_N%;*$ZkQG8@vezfbcWUZ5)@r;j5|Ck?R;vV533Q6wdOAMn za_zEdsa;W{6(5ki_LbB(S+7Z1cUXKNXWTI>!j*paowVSMHAq9b|YoS z*M8*2%hh<@x-zcP#>}Xi9gzJ>K0&T*{9c<=?e>IsFG^8w^IMGhHK@+>lq=f3;cN9t ziaSlFLR5}62-fsBE3rFC(caPZSfw${N3(u)n^OPo9M{+IKbklp|$L6VaBmor7 z4xD*CJ8qAD)ah6n!9-vc`3G|=$_hUXJkDnzaJEQgd+sYh*+w1t@!;2`0aCsu+QijQ zZowaRb`}(zs}=|*2>8OK(gw362QE&L%zruZl(N71*-u#kp)%=UyziACL5m*<1}*V`6y{9djtinTA0w zK7p*yaCBSMwaL)roMpb6?CuHrJmUkC-}Yu||0v5azm@wU+Y zRk;HmrrH6mLKI6^b3;O9O=}j0Zl+aSdmTzcKO45(OE>g@RN&0${)neT*+upe8i$&= zhSez8GU`~jelxjwNU-c~r)#Fy;q4WIc1f>kzn0wId)iZ3nbxL@^fpVQNukww`p}2f zpROCq@N}wF=3je%l3z@J;{IE28~W2duO3_|8#qKlqM%;A6ixW$fLB~oa!KbxASU*V zb1A{JUfbk=Krp9eEOE20kvl3$az3<8LM?<@P`x0}B{N-OheJ=LPWGkxN`KNmkTWg0Yga7G41r{+Zd)DNbX<+4+=8+ulAByMx9s5r z=27#W@lFFFllxaipI5I9T>rGCMz~dkmGPEt@oQGe2Aem`HaWLc8S7gzJML93HVApA zg;_qT&32!0qY-mXxb1i+%dGy=-E#DDRzzUB(XkPnt+!K&pZ0_&U9!jPB0n_or$@5o#%;@|6Ls`0>cr^%B@9)C^-kS z{)R7vYqeX(eWX552c^2TF?}@F*d57h;@z&F85t^u-4%VeRO$0fr^0)O-=uz&jUrgP_lk-p=IGMF zlM+ve7V>VyGCVgV_sTeky@@UeB!02e-kh(Qbs#|K?cA|lpCu2~1ZOmTIY%7A_1va7 z>-c?|$^6|mEmgrZt9^+Cvhh#TXt)H zIHoF9&Rl-B>dWpu0hc|u5a-f6943u=QCXx)YRvIwHD>W`_$e02OL7ZkcIW7wt-r^A zlV=$yU?|GHqH~$}R&00Y_!%eg2>{v$oiYiUw{VpRt(!)pKh2H5`|>TGCpqReufv3AlaG?RzbS_V z5ld9;8#6B(&4UGIZbP}l3C9V4m`w1gWj*sSZTXf&QuXM5_aphT3xXEfV@jpI(huI0 zY`;b8y|53Y0qgEPY?BQFv3GTNmOWRvj^Io?W;RE?;8|5_krexDZA zbEAnU-FB^!L4kr5!Yduxsg>5;e)sq#uI;<}ehM8(yt9gPBkFPge5=!*4QX;};29y#6AI`uaH zt0QsMBdoyz%vrmW&n=Q?cYjb{=*Si?o3o+%A>P0iP`ofsoYbEDvE!A4N6;>x8=v+k zrJNN@ZdIiDY!TL~d+9*RT)@!a-kTR0Jh6Oz)AE}7q_Y}NueiDHJ}&i`Ho77v>Tr2i zMQ0-e*79CyJ)J{&j-tbGC`;48#Hj!GH^r>Nv;m{Hh(n}|mPZor7EzIXyMI>T%dCqb zmyc$Mp5bx5w5}IV3iB>KB~KOd-*f9mv4P3-ojVVl63u$4tzRg=p1%=0AwqNa^k;=p zlluB=ubD8|MNWY$&CL4m3rdpCyvuP{y?D>Ae43NJIpaI$Hp3Xp19TEM(dR9U+K-V_ zM(8$rSQbBzc~8LN*KtL*MDOcv)09;0r11A%l6~LU&y$c;vSz;3p!{q!6+WCKI31UI zB&&U?Ot+0G-5-@)5%bn#RkxokDfsT}U7o&r^$Jq@%F`FFGn~!pO3-VJH03C@ln@~6 zveh0lDChL}kVobDkVQo`kE&PCa?cCttQ7IL%M$0PCU=&p&WFwM2%V#UbopH7p6}jw;zntQJH9=l(90(fIiB*O=VP(z zTz}wlNnIhuNrJmc8a~mzqeHi9xYLXnV`P>kG-QiLyhXd7Iv8UKm?I?LX_t`f&$S&7 z&~o8?Ey+1{;~Jd8BBdsCg^D^4s{48_y&r&ie--%icLT%aGCp#A99JW7;$%!a6pOH!h zJUm5Vv8hz+moo$2q9v0j=(?_3HxxD#c-9{j;Pgfn9L<=&ru1>AX7>3bbvr0W_wVXi zJ@1=!^Eji0OdPd*^oPJIpkyyPRbbQYf$rkvc@5{D>*3;;6$%+bMo+Tto^eUAs0!{V z?4Zv!`vxRv(W!gk-P4(R3WL5heXjThcqNyBO%nUL@WB%!sn5F!EY4Ncygwx<#}y;k zUwY|g^(W`;pK_wrrKfL%R8Y=S4j$$X&$0e=dbqu#HFk8yCX>tli}pcE{fBq^>^;vu zFn$zGHkDm`Wo$(0;%M;NyXwmP1P7|&*C%-AvhHE4@?^)H4VxbNE4T$@lG~>Hj1C-} zYdrlHRbJRuBbhcGtgmAXeLGgJI!ckQ`u4W&lb{yqt$iC6#L5;zJ#zAw9A;oZ4V&ck zOVC5Rv#dG_4-}+Er{U6FjGK41?F!X`c5>=>)lIB(Zu%)O~kK3U4UqAOOvqsD{z z^ml{~pER~FlD|B>@71NFAFQZ|`7Voo?7xOdkBb$4lohS8-%qa7pYgPn_MM=Pynr)?a=?wOn*XaqD?&OXfLYZp9!CVWYbQ=k-Oo zEQ}T|&#Emn$!N$w3^{v4EwAzY!67NuFR|(B4(aVqp0QbXzNGtQeR|5?vAtKrY*=AR z?9uo5wYZ(TNndcL^2tQb4)?vOzmm3>LljWY*0BynN`?CAbQCU%DNfP0Jj=M^Upv z#Uq(_ZpE0*Fp#|H4Yydg@;0KzAV0X)c+jcKV8RL2w(epyKB05qn%1`+E$pG0CGQ%G z?Cj1mo%#Owk?pJ^ywAOfO0S{1xM^5WQQ=>qMA4ARf#3*13L?l)-i z60P19G7$^5WR2x=Ueb;Mmo=gf9cAU_0^ia2EQR!x(5ba`)pUwSTgATB$*88aFl6Px zG@6&+@88z)KBuerj)_D5$ICtk_o#|A#K(CRI|^$kHCo<^d$WDmd~cRF)xLm-g9GW$ z2Hw5AO?t%t3Gi<>Hid1Y=&u`%#k9CQzVoDlfFp{rIQ&Qd&F?h4@~8nAG6tP;U?V{y z3uotg+bJ##Pk!5WOz}ggYasW7T|x@n0+?)f{_a=?J zuG*dL65JNcjv)sYBK#=sV>)*yvVr$ez+5@{T6*|S@m)>(2n|SJ%sD{wXgWq59ji2Trk>yFb)2=E1An%KyuSu`> zE3Nd|k)!U%RfkjB*aHq9zi{+ov-gPgVD@yHkRreI>!3pTRE!Cma(>-u^R~_?vw<6J zJo=>xlgEkSy)n2EzXjXRnIiUL;<J19kXm21)njta87~g59|Ig@9OZukgX5F>wd5=kwb4_ZuNh; z8U@}EaiEIJ%0w%*`@}03XdJI8NaBYW>3e(^_1eWt;=f!k0)rZ#zo?3g&uV4i&Nw@b;0 z$zWDpskeNwUk1ZV=r0l^_b^AuFU%<_R}dr*UMPKZpxbBbo2hMgguV8$bNe2UPUt?; z^xY}l@|EKeN&}IX%9#Zfi#2+pZw9P;J~?gEp?|*W(d1h@xxn6Xpu^j5xctIS&QMurTs!}$2w)T zlay%yymSSTYftB&`ci|FW9$B z?G@xu=JiDe%y2Vh#oHdiGbMTv2G(~LR1_}bP|$hMuzy^a;K22!~^Z5U2Cd~NF1b6io zbQRUM;r1V$0W88l+y-hknga8-ed+6Zk%sV+!yF6%y~tCt^>zUDntr84wFLnx-r~mT z#ei|37g^kY=tY+HdYUU%T{+5Rkmm_6tlE`|0rPt)aJ!X`k9hfC;rz_*v9O>j+8>(YX$lE2` zjg5PBKz@88Pvxv*gN9Q;Ij4M8@rfl1+Ci@YhD-}!416ka1Xq1+oqHU#yopXdmseMA z4J5dGS)oRXTxZS0Ofzl*{PpJ%>#%bua`1wb=MsJQY=@3n$)$(dQWEHw$HUvGu5C+` z5U?efCc5QgPRkkJl+#x1LF8^ry_z?Zm6#Xi0y1jQ+s>ctBOv;6!A{vLo%gaI z`Nbe!4$18*NxVy3dMm5<{Z`J-tL4$1n`0n$H=ge^lQBF(mTDdSl_jw0AE~+cyw8T8L9_W4Cu1%P8Q`YAfMf2`6Yi@Ly+u2QFBNMW$X7(z#M#rh_IC_Lgt3UjdNx+5r>y;R-n9>KK4egcP8W-C3{0Mnwe1cLhv-k#^x59~U z!IxI3?%(b;4tsk1#+Z;rdul(?ti5*w7TrIR%Dsf^UpGq>Gh8tPze__m*Io_;+Cj`%fbdc z#f8;233g8pr)@9j53E*{v)A#wH$Qa1aoKD8I5&ytyQ}R_YWC57_h~t(lV6fmrQ+93 z%{Fdb5IartLQv4dDzATmuC(A(iXf&vB8ZH@Wh+MnRjpLi5QPfQ@^vNlqE)ezZ?*`S zP&q23U;FCpO3eQ;R2-BWe6&VS_GjaDqj#OBnvbFlF9!{Z#4=1(KtPcKwhDJiJ`__}zuSl+3+Vfv%Frm8e7HC^Tn z$DXd}#mba$a#c%G)Y_?yN- z)uT%l@exy=sjc!P9g@^n)>w(drzleU&@`0Fa?hSwvUg%ANY!nrDCi!v>VG6vUr3tk zFILgId+CYR$V64PkPtb6yGuy9%s2Pd#OxkwP9qxvHkr{oCcH05ua?J8uu)gv2p5#J zI=?m5SV%s!Z}<$^(b}i+Yr}_%-gSFa$fl{asyCV#ycu&tjlBKVO4t3g=a$;{7TSS_ zDnVa72#6IZxd9&WP=9fIvGxNuGT3@|22mxKE)?u;%45CMvEKoPX)GFvpzHiJJ3!te4fl zn~miVc4K#*QxeE18K8f8{4>9rA^rDJ#-PKeF}B8cntlW<5}B@CUD{GJ#5MFNT83yp z_pP;-n`o()NGGAUhBnumlv}pzu^5V4hX&ouWgoezT5rK1<3oHnk~`_$_PbBKb@N36 z$dcu?mI%qC9}f13avZ*Zof5Ays+I_qxVg9QjGaMNZ9mhIoQ1(v_9hZl#&X)ROP`2t z4_17cp=Nw(v7=FZ;eKWwRn5|+!#8WTRt{S)uZ;#XzCTB`_px%s`ytIFvYLZSpNUAe zmP{)Po(4~kJR(1S*-IH;We{OCMg8se$dLr|J%eHTF@CI1o-&m4xmXC=W@wg4W~48M z5F4HQa_$M~H3#SKKUTE?rbow|peK%U?BVh9ci^Sleb~fZmSzf8`__JtQcR*(ON#`x$dcoph5T5XQTwc0!lH7j zmV2Dl?SV79331)IZk%_z5d6el!l+gE;xvHQYY9#|)Ra*)FPZlvgnIK@8IL26H~so2@i=W`q12kwZ@rF{O;h~{On zU7J?EaOql%QBT0r=SJEMlg>7D?^F7c znUOuDm!EKoJAHo;z=8Ewb?hAGBfDC>TBgcWNLSHVf6SonObhQ&)Tw56^^xf}EX<6r zcRuX5`;qQIJ*Vh(DIndk;z#j~8!w!PRt~-?q$GLiq8izHgU%{ul;8Jmlc3fKt`ITN zz^>COQEO{KIU!f8&E@MXlQZaJR>VyR{BG3N=xv$qlDRf-?`rksw)wLW zDM_;^o9K4y2ehk|Uth#HC{2phyY2iQUfeZaJE1ZaxDcHYbL}ZbPW+`#7VI=vWJu=e zeS^~DdobUWgM?q*CoDB*tnHT_ofW0OG^poZ)%Auefb63{d1kf#f!gekOpIO+X^d2^ z3%H94zw`_}T69OcX}jnu-*@SxU`M*ggt~SgE(EztTzfWX)>XcAM2+|UagmoFtK`wP zl2H~zX~a9-Xsff%zJIf_MwJ#ol=`Kwy!1=e&QwY9X1~){T(usPhhKFu4de5Fvwz10 zk-Bk4HIwMe=CW}@c6`@_zS73K_t%VeMURm=qldQ3F&=HCK3F!ZcCGSuaF(rfi;KKM zQOtaBB$Mu?hLf)^8!pT89`4{MVkOSwNvBQkQpmV9mEdMnkwNP_c|lgT=9GG7ynY&y z{1;-S5MSrJdkv@_1?vy;_$PDyQ2wAE?>=w%M99cKjIFkW{Z?AaVKr(2>t~b+Yyq72 zeG?XL`C;QG3j?=G2kY(>?R+Q}K7=9=IiUEu>{DtGc!XGjPQm(+ttrHuc8fdw)riGJ zX!6MHo@sbGsXcE!|GlJ<=IhR*Ssm{FWm|*EDOyIY)!BOY zYIB~T>mIdf?5XRn=D1twXozW03VPE^TT@3xEA8{9o$}b7ALzp-;)A^(V-5}0<`sF7 zJUHR!CZKnJ+34w&b8c;!Vx({O3-z0H1$=hQQaKSwNV@MNb#gAD{)b!G%YGsiWBWOp z_p67oi``tbtDy4UJ9&AVS;Xk{^NDBbHD@C0(SfMOBB!|HB%I|*Le|anMXlz-gVP35 zrHV19ijEnPaa$+re54N+soQI+%zbt#G4<8<_Nvyj=ZpH(7=Hqzp+nE6ugONKPzh75 z5I?m{*~Q)c`IX|5#nCqfb_#s$)8@&m-zHR!#`1Iw9(7QXA`4dAMJB?XZkJUlk~$iC ze>;XX^#|)d_Jdb>C_BI>?xPwV2?wn?&$R4W*x{-BZrfJEhTD!g_Z!jJM3n;^*LXug(+9WW%*u*o?e5oaRSp{Q?LT=B+fOL# z-P`-vwkWESQpz^%0F{cV2?Mu44Jk!NMemd9K#I)mG%;l-pGNF>FJY_VRZfGxynxmr zPj@$tab~*F)mhP4D|yd@+Z-KxPm~4Cf4ui*y6vKOKG&3MBKvLXu4I?@s)ug6$`Q|z z<{T4f^j%Sfk2~0~DOUDJp9i7{%tn*;uAN9Fnrn4TaF$r~*9^XK1~Q;iLg1Y>p=rBr zUM)l2+vLZZ9OH#|8=qN{eFi%jiUOT-9^PrA2nmk@)DD|?3EZ8*w~4)QVG@`Pm7&E~ z6qrps>R5d*j|F~sc&|S-uFrb5vhete+z!Fv5Z$e^ZxJhbxoGM(#bN zwWU6vm*Tlk z8^ZfYaBKYndX1tvQCe0+4c_;K56WKID?9^xuRc{S+sAWn;U8NwVG|qI? zv59J!pan<-+CPEkZu?+tsF%5M%E_nScFh0+_@ITtLjew>XQK2KtVR~^g3+z$R4RMi zD5{WRlnIQ`W0R;iwBuenf;oB)er00A8c^W&cv|lV@jkOv9=1I$$-|Q^Uz(awN*w-5 z=b|qPo&0<~^+LAA982-^J~}F+>jBF#(O(q!N%vjx+F~Q4Pu{3TzWyhBMT zpFo03PG@Gvd#^Y)ZiX?+mkVhqA?YML@nMFUWQPYaE3aj))w(-dJq-0&ex-S7|9#r0 z%GGSIYddKTj`9cT_n6)~0XwKJ& zqKA=jY;cf#pZAo|>**c3KDR$J-Y&R!ep+$Rg64w78>=Ngku_E8Z38z?@{@exePxZI zn#@x5rU<<>GyGn|HijfHcr1GAc5U_Q=h6e*+vv@A4l&yw(>js-dNP^2()EghnDWat z@JUs+-oeEx*JP?2|NGwimCr&*;^$G zCw$osJK7kNc(;V^Z(|cP7^du=9~P@K;a}<*cbiZ9Hb!mZ!FfL9)JV=VX@9c0Jx(JJ zMeh%m?|Hni^^FwcgLuZ_{j4Q^i{*5OS014zq9f>=MAC)tfE$8`7k26gM?W#QV4u(5 z_f?LRwCnK73l-9sP|eS5?(f~lyKC66r-XbamSk=x)62jWmRdGSL+9wkFmp1+ zv)(l-Y4Sry3N(+MnJKR?O_6zdsPC<*ws7s`GuMvwTMZN5p$R-(*FJUj{RehpySr9h z!imkFxAG=aIbFY1=5S_mncM&E>*AbGG`h_9iL)4GQi}HxbFT_54$$Xhnur(DnI5mY z@b=<iu|z6)FNid5gGjj~MO z$?fgw=I=s<7*VE`y^(*!=e|3-lb>ZDRX`uvhn0^vmc0#cl33Cj6g+%VNv#ueHB>kuSlA=ov;gLXY;quPnr=iq)fA>k?c5N-%9+Q{fX3QpW*m549zL9d^NF2dTQ^s zhR0T32!suLOa91ku=7QRx}FOk9|b)nGQQ=wLU~eNzEs+`V2_|yZubnQ+MWjOVC8Lr z5kYf1RLJ^YsSj!0NxoPlxh)mwW5uSrDbpMXLnOBy6-+T(i3DHvtU3Po7A__ z~cxF)$$WX(R;j3DwUyJqz!i?C| zWzb?l13&cMCTfdQYN4(45vMJNz9~CymVqG7Kkf3y3FnB``+y{Z$kPSUhEj>0dY(vk+MuYOL zT33_xhnli=x!Padd9leIpr!#|P35|pNjx>FWWRWmO7V*~N!vEmxZpNv@UN#l#O28B zzrTo1OdDrTVNIL)aSJoV5VmZi^}3#8ua|zvdkR*^mQe|($!m9+KPEYo79V<7#OL}(t!cWI%)d^p2+eNyS|B6-Q zyuiLMHTFJ@JdT;IIU0%k<_{Q>x$ivq^u6JO!Pq?e&mq?5+$%v0eCrDYd?NIyf%Lp? zMKg`t*U@_G8F#U=$1*hwbH(0;6cZf>b~qzX7 zZG7$RcEADNC&#U4(%Fnb2I`9hR8-`rEq%ZGa9@WdB#ytl3Cj0LAGq*wC5+ej%ZpPq zHyo0WG9P@H7(bxXoP}*&3%pV$3K#p%KUP19g6`frNq&aw1aspfVgyB*T2WU?;9ow0 zx07-G02;PEm>Jf~0DCU@C>+-oi0_0x;EOs(AWLv~=?EB?`q>}WKaT;9yF?$3UR>`JvHC5oHveXV3ZMDA;Z-G-E-M<o#2F4s z=2;8>aMUrwha7@gH9Lq7F5lV_SqT+kQ#M);i9>0Lphf^o$*Yq>=f>c=2Jgn;y3j`Q z(Jz}zm9s+1%mE2(Ex3;K|FHMo;at9L;PB^TWn_<#of$&e*<@!&HmU5DjAWHEBYUsx zRR|%nlFY2kC@Xt!3h#9rMc?tf&-2H79PjV={duqRJg@6M*L9uaLVgwVQgcfh%C(>t z{iT(T(3Xtup?0x!;;zxVP@Qqn76C7T_%5WPfIvVqAFL2#C=&lE5BitDGF?Al{>gF9 zo5SD+K%oc?5&5MA?0o=DG`Mx=Plbh0GB%8N*C)gw*8fcKL^zL~NvS{ayzTg%z{_lb3#^3bVAz=L6e4(aqXNvevDOR9}>3xO9j*fUB+xwW{IGHs&qDU&%s!wAE zXska-*8n1r*#s#-cNp3wQ9AZjhquOrc!C^kH(sXekKEFS2aqK`um-OInh#7q@+R{41tDZxe_qD+vpl5D8@HG#>5o(hz* zH-ne-=oc&J(cH+M77ZmtXS|8sYExt>R@6-A=q9l3ygtsg>W9j}-};^9!-mH+Le$fd zCJCmQY<`O8-g@?iUSzAVef$DgOa>R-1q&kxWH zN)}s=`DovN)L!P*(82bNZ^$z$lK2+-(`n1y0QjyVwVqU*n=(~WCc&` zfqvt)XEKYN$q%F52w(|00V4hPzg>Q7`IBBj0^b-_Kgl((L6o$y3!>@i?VaZN&zn=J|F}~3t&Alw1j3ywkK)Qrs_D01E%TH%f z$rUI1s!8o5a|E~8DJPy@(%|v)#{Np)6~`)q@uct8V4%*#05z%arw1~CxJc2&?Lz^e zEl9jg^r@>!);VerbqelOM04kngKvrZxtwT&hThyTYu)gqu@6oxW{LLhXlHnPvb|&t zCp~VAh<1nNw3nyhc)HxGgVAlNAo3|{uPDH!=2zH}+WTXuC**N96D`i>w?#SyTM^&+ zK~#DFu9%=h(b?O>HcTObg&f!hua@G9c>5dORb_8taGdWpF&nf3q=my1h#?7NHGWRR z$1ry`*{Ou~u16k6n+(4F&j;vMwMsJSo%xb#A4Y<=$Bmhg+R-nunXb_0NvStig!52r z*x=Y$`@RkoFe1P%=?gI*`6Spx`sj;iEsow+1Yxv{uUC(Gi~bLvk9BbFIZiN z@p0i0iCJI0R>c-@V+Khqa<4z@^2?zqVbS^PCMavy@J)g50($~aAU$NEWpkNSL4$KP z)jOAXC}jlph8hWYh!pcYIzL^ERpohe_p;3oJ5v>pWsd<SB_9k~ z4v+N2=e~f zVM9ftCFVXeEgQ_ti-3;XqA`@G8LP^_H+#+ozb{^|*F`$_`)H!@)Y5n{<;#+U@p~aA zZhiHxI8`OY_MhM3t-mYEW&ap!E;*N`T=dEAOyQd2^2ICYlrfp*`SlDUBb~&EmHMU& z)QsGb zvi*GwvQ_c>a;ex!U!tzy+NOFMl8yFgTwVlp{ag+@t@&^JBz0>2RMlk?Q#S4%02pwV z#ZL_nat9%LfU|6PNY5`nGQr~n6@aM65EVyzNC1xaU*JFp0Gza6aE`p?x+6G8PIvtg zoFk{Z`3TORPWSXLFo(W-BI+qHiRdTDx$=7(=g=-)Y-DnQv*%mvjk|n&6}b9hxP$c5 zS2Y*Q%Qc}y;T!8q#G=)JSbEV!R)EDF7C0!v#qdmqI^mwns}|p6kKjlniKruQ(Ukt8m_oe@xAK zPD#6N1KrZL%YL~-|G z7MY?5fO8(67zE7&ITCjr$rM5J3lkyFMsxDYPL%;i@Yofe7y``;R2}M$G$bO*llz5K zFTC#tqUh4?iw2vLV>?XYjQAIYyOy-_pI#+V7c}{ZgJm|-r|GBDw5@G1Ti&fNN?|{k z!h8cWzuT8@GPL>4-I87(iA%O9C@g{O(W!80odm?SbZ0t2HUajYaZ1a^8BH!lO6O&| zDTs}Ye%sp2nVMS!9$-_J;O2=rgzg3}ld4QZx zbwDwHoSYs-G!(^Id&n(*JGJ7GA-{hw+lcuqD!*3myTqEBuim+!n*ub7hgK4}IJ^bB zq%H*Xauh?X^MNvEOAS+mo2t2&pdo#i{nqT)`yYnUUKwU& z%GL7=p6%XpqOHN4u)c;&4L~x%6F-BQg;N^UdEM*oMZIh(5Z*ZIwQI?xi0l6plt2?H^04Z4OOjzWUFHXdL(#X%{7t;C!2jV!Bfm%7VNh+IItVP7HWsu z`bZmqEYV}72^Oo-Jt>WSxWcqYhIX6AsoFpxfS z3$LYpaVFsthlQSzC(hW`)km9pVQTS$!DZVGmN&&MJz47%vono;Ji4iDAUIWTAXp=2 zcRoyBUl$O_e5^is;}?)rO~2nbuexS~OKZR6a%t|R4AT$vE6yIxTeZrHkLw}!|3jsM zyirJ{LIqS--y3hsH1jptUv7@7osbh+L|(i6weHHb81NO%Z)NGezt{6DAHitjtD{3I zhP0X;)9ig(iyDaMu?{uo(Td#T5Szz|6**YnJcd@}v?R`=$pXS=rOa5R2L+ZMJ8qj@O@nQJ=jAC- z_Zr@Z;v&ZzHK2*i?@Pcy$IW4WF;ETo3h*V=DCN{n5omPs`$GUW<20P(z9qkQoQ~i? zO-HUA(4!&(AfJU=iX4Vf4tAix_3Tkt<$zw0xp-X2c35N#Ykz2iSGwNk52dZ+AEy68 zbWs&*&h2vUt3gSaz`|boO$}l$6o8Qf?EknDna7M1`9$_A$K<9*={jnIy?y_;sgi~fgaW9YR2VXA6KC(hS<@vRI=T$$7fu^&) zd)tU9h3nYlm)oC?7mM(@=lg`UtWd;yy!e23jq%KWl}C##j;#2=SaZ=E51IG2+0WlM zg{CaGVRrQkW3z}a4wfe+I-slZvJ5@Y*`|@yQ_;w;H&*hesHCOv$a{#pGl#1advV;N zQFwO$y+m&ddEWQpRed+c=er*k+`VPcpI6iE5+-%Q#;mOt442C@E>p!WzA87|o-emz zsv0BC3;WEC^x?-aQKACs<=1UkR2#@{)CdC{BdE5^uVsv`Oh%^3p4XU{yO?lc?#`}w z&h-f%qD7{r?J%nWS`*M200hroNwofeLJdOBJ-= z`+fJg2ISR8l_v{~cpfIH`-q`;nR2~t_5OyI6alg5MOaoe(n!3D`~JhSR$@}vCQ;25 zi8ZD9ZCJBVZ2^yPRAmFETy~wi3w}q(faANG&&hJ?JstCOU8>*x*Rv-t5tqK!EGHwT z`y?6fD*H?}H@75lHv$uRNiD3H+sy&D_2lR3(CsYL0< z_`W(rNj%v-$(vdV4+2|T;z)R=o2JEG1Cp&m^AY5T+Ml~FV8%T!VJGbLPoXVjR_mGa zcZ?8i*~xb5jzKevHJ)?~wa0hYd=|@8Tg=kX^X>L-26eYK%Carx91@9oj^YF1`G`AZ zw_ZH>7Snk~r!xtLZc+p9<}LO3k)NC!@^Nd7TT*x2d}=e}+d_)eJwg}ua*!oQgQ`9* zEG8DpD;LeNv+4%#C44hyo+zMfLPbO+!a?NFN>1;z!6`wd5^NgMhFw^8lROvyp-6+r zMsl4$wJV9%_(~L2s8j?$xp%krlHpzs#NC#n*0 zkMz~WX%b(;s2`F9EnF`34khu`YhT)1ie}q_^>uGp)&10O&GDLs$d8YW*BRNX3jN30AD?>p4>7!V+Km?jfKl8{Tx5bnWvH4_oMXO%Heu!9{BRL;t3>Dnr5dG1~h3 z5}O3<{;(MnLM;ciZo3sF>Pk(lJZJ7AhWp;-9)LJLXsd@)9;h&EGFr8q)pMMM&Nfkd zCQ3`DQhdB0p3$abDBPyBcllyZbZ$$!Z~jaCL@6jYVIi{tAG1OmK#;bp!V-xc959}Q zdwurM;vmOQ*Ahl>;V>%?rB zLPRb_5O{j-SBOVg)MX6WjkEmWrk{eRFn9!1V)rS1eHhmPvNi>H1^b)0wH;WF>_Ie=Ql|G@Ah{q0zLGJsDpU!{H<$&Ln z)(KX-`u-+WDFPGylOO$chVOU8gJ@!tFfVfx#S`XM2&@NQAxYi~H_Q>k51pYYc6oxk zTazKw@!@Vw5vP>qMscaN3Bkrb{ke1jfZI@X%J0W7(1lVD z)m>F#bhD%KyN5zpTt&J06jR1N3DHxoUb(evc3^y*giGBl$a9S8vgt79h#mHD_1DK) zNF_>l`H9^WHfUw`Mdd!3zf_lQ;6te4dMq+@9R)q_yct4)g3j5G*)g|h<*swRzMiq4 za1~=U))!EtDVm@U*o0vpc6Q@^RfweWFrBeanAC${3<{R0yZoCrm)7gN*mSP(d#Dcu z%=7&qU-X%Y71ha7*;8A8s%lr1fjx7f#4+yd#RC4iFGPB^KfZ{_k-OY=n1f#U!koSY-35_$|HqjaoPr z+mGp8_1gE|g|{UA5mnV8;yKX0T1qj&S? z5XF7YR9;*bZ#B1S=eRfdwk?suqE6e`)Mjmy)RVAfo%?TLD$BbtXFvpP7Jc zXy_!uaDo%$w#bOa+yRVq)TIvm%`?)=34#ev={LJKaWA};veISE;^X}K*t6_Q@YO+k zmsd)!Ts$jV$#XH^d3%(lr;w=8cFkeJu4{S#U|@g56L>EW6UX!#q29`(mvoIfThs;~ zfr^jhgSGfuimMNw_i>*C_jo}$1vC>Rtb2oc+?qF0Qa`0eM7BCz)L^LM#LpMB){I+N zrG7Dj8Q|W{dz)xchxJ2(2mHo&$iX=$8k2P-0EhAk=bYgibzj^k_FaBb4v-E zx0bF!e+WbrdJhq~gWZeC6lw94OH)@y4(Dp)#BjhOdJDps2z94Y6H_5XDU&(px;NWG zm(uviGFDGk>{BZF3ocG`$S)TZjom$k8jdQxeilJj+F{w&al3#7z20$4Zf1`d(@^4_ zjY|DY6t@zME;4@$l|s}+95~YfOiaT0L$VO2)-KXsKr!4Q4S*y8XjuLe^KcE6C>>D6 zMI+)Tc`=59CagG6Py6E6-Sas2{hfS&e)Eu%icU}CF({_eIixO626Nd9-Dj~#ue7+04p0ienzOvWNrkp~?)~hC=AnwX_&5<7 z*KfCGF@n$2TwZ+WgWw~2rD^s8$*tPNjUSo*AuJJHvhnI6;k1~eYwk@vT3>a{W@PE( z^}ZUJ20e$k7DTP|566edcO|>mjV7%c?p>XCWBIf5(%~rGPRu>mkurh`#UG{g>v`&= z`tQE4&D0ojeuCV%#8znjU22VVIBc2R%4vhIjHfQvnA7qvts0_p;?*vmK-!=ABaFh8+XF!6hJiY!fk3Hf!Jra{z z4SLjUdj6UIQnOCB0$5$ApDi;YcwP2SH36?k%!UgEjY(z;+I^`aF{G99(!?U2dMhFE zjPQf8i!59GswvxS@lP+Cxo65xDDcB}L>@j&81WSO0H9I*(kzJby0fCl$N}na>DdUx zw2-qr;ryd-qQE;KK6#*OAgbj{#&foXyTDzVf7CZ2GyeHZ(&_i0Nu~Hx&caYKu2>)*t56Pd32Q&#SQ>VC0 z1F2x3laCb6k+TI5oYXTwZ64^Ef71Do+5`yxR4+nhGIzWm;U6G4Rvo_(oKhK3&Gvs% zonR0Cv^Myy^pEBCw*z=mQUUM-x8a|thh(4OPoX@emyNE9Df`ulrzo(4S3!9BNEm-> z=RM5Hr$?Ib&{iMXvSX3^H~pNK2^NUsb)1|$5#GXFAbzwGjH*2|GqKE%UzBqND` zYTU0~L6kEU2wDQIR~Q9%MUeIL?Yry;tN|{t*>~DR|Djv;P!BSmehJO5|8~k)vm6=g zlS;61-+ltGW4!uJYaYqcea5)!SZ3;RYSH#kxb=TF+@Lb@Uko?$)3a*%-cE-I{x{6kLwsBN+fUWiKWwwTu`|F?5$XM6;VhHGnjGG zUse-gXG1fPG0NkEGYr3Em(kY)JSBpb0l-5+OgPWzOXzYltw%M+T@hL~GM$i0Wn7Jc zb)8x*fhe3bl|Au5`1l5v(_Cm$i)gR)oGo}+`A_j|{V*&#H1)s-PwlB`SY7Z3tS#4X zt~)(n&B`f!WQ6kd&e7fPP+`BW^M&EN%XCs==uZnJ+0TeQgvb<;4V~STs4f5~#VC6Aeb5wCE#|Gv zF#lpz>nfVbiouPE-Vnbp6S@pGkIjsyAzKWbn9Ng7%yCj6!lbOP`|aCt#LgtuN{Y*8 zBwtSXwFO_637xjya@43x*6Uv6TP~%1t!sHkRg%|_7N0_R4T*U~PqI@l1TCwcy7crkNbmkq8=JaXkG$ zZ;;q)2#{XIcj@Bca(mA^Q!tPy>D&6PkFx)Hw@*wp||m}t!0>6vMez@TfkQNpn%SsP5Hw94#% zp_1(!@L6iCJx8OP27!Qwf2C!{m}p`Ot${JN#anJ+b|WmV4`=0adVpcFT$EH}+XGz> zS_E`&>eoj7L2tvK-{q(zgCe2-P+HHMk$K3}_8O~g0HP&xkn9I8skR}K64uXHmF zs#I?D+Z4^tD*90#OkpDW;S??sD)ND%!Y(0}uC&PQYo0agdCNM4 zy07#c6H{VqOs2!;Pb1@t`N#b%KV-<(bJigRYC55L3pKxrRrPAg&7maD2~gT3)vzel z76B+g6Bi~(EUxL9S?h0BN0K|gSf-?IC0tALTJecdA3K|~n~HX)>^#ju7faBrfcd~W zz8PcO94iQzr#o}r13+OGjb%SIftTI9i&$7S#{Ta48kkNCJk71KNGDk$JV!hzL`h#O2~@S@d8~0+sC#D zRtdMQ;^E?--IW-Skt2d9T0+F{r3uZ=MO~}H_X$*5yBG|fkirwKAwr=i3pV4}dc9X{ z)C9e8LF)|Ysc7u|Q{=+9mEIZ972PiE1W(yS6GINEBYw)6^!5hLhwwPbC6$P%s1+iE z)Qs7&GAb1$qgBslzsu6hB2>fR6EH6Y5Ftp#lizfhn5#lws+L1#5`e(M!}%Khz*5f8 zZe!iSb%!AkJW&*lEj>j7W;m~tFvECq5F*|6;YE8VG!Cn46n!{K$r?+!ViEkL6h3o0 zQ@Cu;xaiDzn0y7_jNE@t7MYwdG9h?t@x6LA0Ldeo*z=3-IlAZHEjKTil&+M=*M`t@ za2HnF5ST<#{MaUXXi5D*n14n%Y{ev@99Dibk?SYuuT?eWXx4CsrV5N;^W+FDWBjlA z2tiX!EE@as)Cj;oFWiOQgGd3TGo**4fZCtSG38&#db8d)4KWCm;-D_TJ&#b@@Q<||BCHsYzNvA>CGYY9sar_Y^U|zZ*0d3 z=Wnnbj_pug95MQ7MmbUqf5rBPayWtQNDcfAw!^U<%J<)5JCN_wV>|qBf6DgJrV05k zvHlxuM`JrF#HYu0N{mm=)UUMSJME2m}UiBhO@UR<+SRH#hymtYogKkLn%+cVu1j7efL zH(D~sZwNjE+4Luc@W3UR1NRBx3GPsl5@O3i_M>OGRR3*Z=!5@c@Bje_r6ZQCBkpU0 zVg=*nh+YD$gRDu1AYVWc7R2TZA9dgRQWp!g`gR|I2Y`l?_O6XfwnzqYivX(s#@a<9 zA(JBnZ685AY3+WE3Sc^E>rP_&Z!FyrCXWN!Pg%NOF5Pbz_`uGc!1P~Pxl?00W#vv{ zI%(rhV*0~-{Z|WjdQ2xR+(}F)?b|O*ph)-FNj=4qz?2?&nkV(v=^>poZYL3)^d^5H z!V`_%K61A9_Y!b`lf@2p7&D;eQrP=@a|3S3JQtB4XcY(A8%1TL)7y7OT-VnYe6CTE zxh1J#EW9-rWrP)#^G-0F+O)4ZZzi$JJ!{_m-Qr7crrY{vJQQnu@*k)!#^yCnrU$^mc5+^eE+>odg(?y@OXVvCW#gB|FdSEFOlu z2oWZ^9*4NX*L?4eMy&lRR*^%*lp9V;Q-Xi|s+S^1`Q_WBKQV-9T`^>Kyy0S~=Si{I zr*E$GaNsX3*Lp_!t3Ht={3!;8}-cpz#czdd-IE}Xl}~eXyh;bc&mdi zqwgb^#0?~O&19t}vbMil;rrS;kY>aFQb_6L*SHr~O&Y%mU*|o?5r_%9=D8U5sc$L_ zm5Pv3E|}K&gLk*~#&~!S?~q#C{Odlu*k@9;;ng2Gi!;;Xs?9!I_japq6-STZ#l;9w z%AT`YBlAWQI`et8i93j;lzSqbKEd?a3!!uta+i`l;c^~hjt4(QZG1aJ(wAsZtQcZS z_Hgey`!CN7Jo4N9a&hTOH5sKubETxmhnHWuceQ$qoS2!fcy}{zcW;iP>+62p@8v99 zZg+mhMu!)C`<&?XjtCa#$m0*4x_j&on9hx2Tc`}rHZ2DmN?!<@$9Pcu`G)?pC)9o$ z8nds|h?!$u78{kyqHEhX_cPHuWWU5{ZKwzCPZrG9mAvwxQgytz`DH!z=Rlq8bwaoM z1tXl|Hi>OP(YwZ(Aq{5FDs5{RRV(~M3u#^!dm>+!af(wz<-N8*z-v04!lkQ6+GQ47 zSW2<YmPOQqhh^EHaW`0!xPJAQie4&Asi%1QnKVdP~ zx>++TxM)*(R%`AT3O$QjE`2ga>{C)WT=_!;UTJ{=H5t@ANVPjG1#V{J>HJyJp@Jgv zEPs=F$NXCiU6SPpO-1_Ut2T}PuRFI4F-twrG1oKQkS-IOjxVAP;IBDpKQAbYWO{3O z-(@2o)$L)To>lh?_Xm&Sd6z5TqEfB6&m5Hvi6^7NqmI$LU*;X5f>bxz?e<{d)W>)Uu39zw#R zMjmO*y|hqXEFlfgqe5b>}z*UBF_&^aa{0qj^sO0l$iQzF! z^>vnFdl$$O0=OWfuj<6mKti7|xID@<`SbX%BTWy=JF$+|pl{Ly8J#IJvA_7}5R}xz^-F|6o5TEstShqPhf4KwdQZIc1K{LkTwA8 z^tUT!05;;Es4YIEw)hAvlota+J_jcq{ie3!pTG|M6WF6kfDREl9yI_99T#*=JfL>? zAHW`+&GR>ta7gXJDLlWy9vr)Kd#Qx+hXUZ;lO^f&+0;0Bs$B5)-s>jZeC;ua5B}w zS&uZwoOmejo_Odg3#iHn&XJ87o3q#b?%qV;2J#9PLlAo^FW*i667wThwJHFICkfoA zJk+&tLavx+4W!?h--$8yS)gReFZh(>c%eOlqEQro=-=~ecrzuuK7q3V>knY5&{_{< z!5kfu_SK2vhO@PNT1-#h>j_0BHN=PDG4`+1&`?tFl2k>&E%5t=PuMxIqCVEezj_S4 z2d{y+`4LxlJdjUQtxQ?JxN@^R$))-b#KEDmf3JqqezzQk)+tzWmHp zpdQpwUPKX|2be>p?Bg!?4}ree6bBc*7R?Mw*w z$oGD^J}-Ec;7aM&Fo$y&K3u?ama9U~6&Z}@urKrFjo+gJ!=OIwi|!6XwU8#T^~JvX z3Kx085-~c_nBap#2nU^ycitpQomr9EnS9@(d|5D7Mt+INap=octQ#;G zf(KL$!?V9P)%dfSHD`RK)XOeyC)}C;mP<6xzU;s(*TU)puF9(D<$RU_*V1`1M$a3L ztwZ}W>%uJ-ooP=h-S~CXMih27d&nMdAehm0rE&5;=}1=+Sz_Hmw$~tiP@lv<;rj93 zmq(4YqkVVYF!;vsFg!O>#Ch{%<;j8uDof?UIJ@elWZ}Z3jMp{fy@@^P;ng>LCogR} zk-NZ!td<;**i~n8Q0qVUvDFY1rGLXzWf|1f`Z?%4m1h^ZwVL$$T_I=Cw<4 z@ZMBL>HLYE$Bp`21RGi3%!7N!zk<9ktzOlt3kp9>1nbWE;`%&7RBIrocpRmuHgz{Y z%riI<$>w|nwdcos3fm4oyrs&Kq}K;9_03+x>*{!24s* z#oy0SV5uvgH)rfR7o|;V+$$Fq;Gl!opeY!eEjloF^M*h5giq>rucUwj%sXe*VF<~L zj&5e~fr5*>j<)>=PphTKh+xF`#`KNO7pApdBpSs3+~f90DVefO@4NWfzXC^2XXu_j z0#g!3xX6&TKlRMt~eyb-nezPfMu6~WT?mgdo{=mo+1+VKRplQG-R(_JckV$9n0j9NQm z{4sxFRiwzA=!jArN!EoHFQZ#Y*QB!}clw$kl><6Ih(4g)hix`!^4aWDKG#jwHxa{$ zQvC^f3mSla7zZut*bY3TXZE%I%(E{;W*t5Wg+vQ8Dd;w|(UxwYUBA`j_0wo8VHf|| z)lA2f8AR%~%Y{f)ll8XFH_(T~g=alkYFEiTE%kToT|L$NsW^m`M&D+88?xqRIX*B5 zspuoPfYjDyT^hAszMTIBllqe!;ihG>CU!{uYw0egxz1;3W7W56hy5bo;dy+z&AR-3 zZRf}RZIWBw_mU`@DVe>hD%6@f1-)vA5`sNZU%gVQ(Xnva93&Q&VaU-o&c-LDWZn!9 zN#e+ni83ZM#hNE0Jxg2jZS;(Dz44HRrm_nrjJ!*~zr3L)fm zt`^K`xX(`WcQltXZdqtTFiYJ^WCa}?yL6T}a0?1W>F`~93_L;cUEUp1zE8WCUHn8o zwnH6&8%PEQVL_`QnFF7)gOw~z{t%rYOl^ft;Utn-ln2T~c0 zAO#L(@p!)BMr%wApkjql@{eudcu;3cD5<-;zm87V9)(lNLP z)Wwa;o?~6_rHyH~mcTpLMs(J3^<42s;h9;$Lm3Z&sol0==!d3MaV9^{)PUF7Zu8R?DWKr z^P2@X*kX*X_1tDHoIzSvFg0z@frJa>uw+0# z7n{Sd#3uSqhQPBad2kz~r9f+ED0}^|XpKpjAl=snXB}}beC)>V>tY<&Fjw@~QT=5z zS27+~UdR%VsJP&;?NdAuLic>u%$+U4V zr5rs&rFBNYn{Yn|RCWDotu)Sr*69in0D!c*zNy3pdVA(n zdPj@oodDe#M9WYY1`Nwp9RISG>4f>k0=Uy{?d{uTzRRzomsokIysQN@>PlV)4Wl~1D-hnn0)?)~^_C^1+`#kIg#hfZ@DwT91JM~%|U z0LK}R3(JS9?>6JTVuLgrU-c2pqP$C9)KbhNFA61ld4p>Ri>6(|Qh8h4>?z>|1ZaT; zQeOH_%k*|ukC>b!v_~y+5wXR_#}pqT?wjLj(v$9eIIF+8;n&^cbFtW*o?C90_SRjl5XyLPt_JI{~fNnGTCI z-C;&ffqB=k2;TjO7w({_lM$>%;=2@g$v%QrIO!^`N*l^c@Nx=Nx(Ouec7TfscO}l3 z*Ma;r8D=#TGb!AaR@xsEgzN-$Iop{1+vEI)^^pCRc{-9k&Up2jshu-?I9%O{wOwz! z$F&jT77S~rVj8hS58uNa32;MTs<&-z>#^)0fZZC63yV#oE1 zS922mS8jUoE-jFa55691Kz*AbK`rFXPdI2y=6f-T9oKcIQj+ohrDZXU44p<~wrbv8 zqo+A}Z}Wp2)vk!K#g2BZyDJFgBlAt-Ro#ktJYh?7pYG;&p#)Xi=o*q|+{@YKLwt@+ zQdc7qJ>UlZv0uXLw0R<9y_6HC-Pwu}J5Y%#S{`s#YK@k=$KA4x&NQLp>d@q>#%T!C zamOQ3MNF`Fi%)q|sp~LYsHZ9=J=~l7Z{pK;t|^iGWj9)nQtj~++v4&_$+8Lu6IJL4KkaK0wN9#TuY8PN4Aq(<#w82+_E}|= z(c9vzW2U@@0ptAaiZi3MZ(68ynMEU(Bd!rSUZmYWf785x9s4Qm`CU>+fm6OO|IC%+lI4Z1}bGJcz=%2$? z)$8cJahfknXwG`Z3K(7p_>4}@kj=G$TBl3SOMsaZoO|n&_nm7x4UdC9zpVT^Gj$WR>;Wb9 zh_GeY8{D=q&2?U}0072UG&Wpr1XaA@0-TmqLlGCQdBy&xYtg6o->q*E8Ct zZOWBF^JdWir2%M_0rU-=bk1GkVS+!Am{09O#eTSmyp^YsWG8dV6md`CgBLTe)K^5z z(h>Cci`4l%U~e$ld~oaQGjtwp)sLEQy!vb_PwiA!Kx^{a;?)=SPpQG!6E8lw@4p>e z@_Pqx$co1HAGrgETj{*Bi`t{SN#ClK3oNlSq7tsUT{M54pqo|HQuWbYV-W?{115CN z7PYP#b{BLu1O+2tn*+7ZGFy)tKm$2(n}^nZ5j764Hpk+j`t+OOhgdJ##Jr_56Yt=E zOE)iCLpN7izqk33aCm(Bq5jvmTZ|sy(;#>P5!l-}JcGWKvR#?(ipSa6HZ6f9GD`Oi>CKisei>a(q-3}dUYoSEdeMxj0Z*VmtAC)E2$D3lgen@@qmt*j{!T#NP^q*vHdK<1 zpNO=OqKtZ`C{+z;x&*pN{r&-d>&#!o&ZsI^re76E6Zdw%#}9Mpeey7CD@Q_oabk#Y z7JR|-yU6r#I)~v)3=xJ_N^$zl-rtb}CY&TuU-p(zH$}A8@PPN}L=&za?k8_bbf$*C z`9x3ZN_0bXO^0ow2{{(`f?km74i^=85o{i4K|6{7#+wy9c`w7Z9UPy-5bXdO>jR%8Y&#y2fH|O_-(@J9ZQcRP=~RGn5TaM zDpQ3%;n*1zb2c0h6A ziGcthoRZLySNMjk0TelhP6Z7DVBwVTI0>a^ zZUFmD-bIzvSh0Jt0(D{I!MF?AR*D>2lc?9Gyv7M4+)@?hsU+n88r$(J#xGbYY$A*cb&Iv|M4al zoZ#tV?~pcE$fWp)Eds7&k6zE@S67Gb@Y2$pQLSbPPkff~x|%l=8l|ja`{%K1s@1NH zb|A!8bfmvyiA4_5%1J>aKUbmmWZQfp7WtxO&x$g{ zG~Da#vxvLhccX&qk#TN?I;{cPn}RkgmQ2=NB_+iAaU?#GcX@P7@%-8aOEM~AC1#YQ zWURhw^R!8F(wU$8YrcpD7SgYUj3@|CoYn8T&yB-G_+sN3^0&9fS*QZ}WETz@d zCuL(M()yeqe7_;7*F7i~*;*0%l7KMPtL(89A!pM4EZ46N z4DiOJp_WW**hqA!<;aZ6Qh#L|PsKhH_S}9@#nDy+^f>eo4bH`1B+dEsf}!m5wD)V( zd}7p&86pCc$4IZfHL-|J`0tB-sz+_J&M@vz{+W3$7OgxY6uAiXY#2=OzQq|jua+y{ z(JT}qXJ;n8%9O}nKP#gWDCyky09Bfr1blNvC_l0&U@Y(P`z1c*jEM$`&~#^{ns2vX zBJv@`j%{5`?&01mjH7pC=PAh-*6$lmr6;dUnMO#CcB|jBo4>A*nAI{|?t?k3g`lU- z-{n(5YkbD_BhU}#WH6WFVUjMqU|Pm3FkHt-6HATDtK`k}#rLTiUfE^yslkC1}t zSt3CKY0NyX_>qWK*Y2v*H^2L@A|IpXEI|!;P(X_@94g3ffm2u9x)W~g|p_Fcp&y; zLEqE;p|a`UV&mj7HM&rxZ`WYA5vt!+KsR=*IC$|uS2OG*7$~kZ%wkgRX$I5r7YQVo zUm&Lom|b}hp3CiP0A2*yQCd)f7E*-OlN=)RvZ&#bIaY8V)HxpLXXICicXzrT5v7>F z0(U`K=xH?#M@yky{~mbp3D$zZJ&CJRVO>3+URZhGc&PBIAdj*Od;)gVj}$mkwGq7Xz-n(B|U-7mnN#+T$)ykyWe_EKDwf}d-ru5A~?1L5CY;u1duH_ zwzq(O$O=H0km+MQsq>*)b@kvF7XUFgW_yd7D0uKV}kmGhbMEwYS20CX$^56~*!0=oygv=B8LkE)ZJIDfgHOFv) zn{eD0<7i@!qQ0Ohz>#lqFr|khKJ-G4X!yh70G)&X;N&S`R0PFl-cIkyYd_R_1v-Y8 z-9;rr!g1c<8WMCZW6z8z+B~!T0d{Ag=+hBP!`q|3-Za1J{~crIjB;{}_*IU>A^eMb zLi-nH#xW`rG|m_Iy&tz~_wI|!EhW8D00l(vkGvIx>1brnm`|fyH6KOu(Ypz{WJbVq zuw{0@+Xw=tk}IjKbocuRAyxJVhl4oRF^8XWKEQk(GxZ4;{1=vH`_0maTXE>(dx^sC|R%=@r{B~C;(GT;lK_=nT2RPgJsiC;zhD=%eddv5Y;=;JY_rRDUDDLG%@?!6@fFbsPou z4ZRw<3kt^Eb}_hb$mHni*Rlp-FVf#FmPR&iIEJ!!tqIGXBfSCiH!EA~y? za$~4WPRFYV;Eu}AbHS>ly&mtkF<`XwWT22w+fb)fSH5*_#I*+%`{@AXYH%@!fgc_3 z+k&pq#d5E2nwKlcDT|0mzLb8vRWPt5`fU~N+KU?R&Qza_2O~FY)t6UZqV5i%nJV<^ z2oeid+tpYUFzg)3%2mG~+q=rUH%gFW(JiQeW_y_@B~oIMgt_kh#$2PWTK{yk`o5jT zM6e-u1)02mP2GIe_ALP_mG~UpjjLkqh`XyLvnE$y9kzGrv{{Y6l-T|Je&hDWFv5_H z*JGB_dxbwOb~Ni(EGEkSfSDGg{bgbxqt4f)RSl z2GSmpml4Fl?(FwEJHw=UWsK`=^yEUUko5LtudX=M$SG_{?|5EN?V$HVNw6QN())m& zB$u{l3`4|oNto}hI{UEBch~uyFiZ_=n8oUpL$7j==Qn6l3IR;UvAt9!pBmC$Qf1#6KER^_MV85X;hK05M zhcIoAVL~tfOuJ*49^e|ZkU38HJA!%fPO}B@Hs4CC;1jwuRseqQkrss83?& zOpFayqIq-{m5uiSERaR@J6jX{N8w{~0V+i9-}xp7utOi!+3~o=F$S04Y8zR7IyJ?$ zGw8tcG~n*Gt|tYbM=H1H-GWtJk2AgYDDTNWT#MJawUtEcsWc)%F}%swB5|kwB?z#G zUu(Hqz+0j_0?*4E$mnq04F)pErps3 zroW-Xxp}6Ec`L6z0MVnI(PPKep^5t9b*nsPb`ufIEy1BSf?gz^q{0CdnZ6$G^JK58 z!a1neo)_&_uq=y_e`jbax=Yx2u8c8AA9lr+Zkx9^B7K!ii~Kfj{dX9id4v3>;Bk z}&R=f>wE-ksooNr6ml$s-ce%9uv4gDDRT;Ec=d#%Y$e5>y7$c99Y z)juDhlp+O)_kF*&H^80XUKYH|*V0jBjb=47EJop;c-2|e*{y0bK0qSVS0Lbn>GJ(^ z<_Ma!7bHqjUL!w!#igqFaPz95l=RiL*AIiO;T4+`p(MfiZf3kclC-b4n}*107EN|i z&)ny8__@hHpTRN0u7f<#iYGu7EbwldE?DKk9YniwbpI`lO<&dX`IL3JbX?`SB^hky z+h@+4dnT4>@+&`Ne+CeL z-V|i7BWT?Es6~CNYa8F%H7*a!6_;4qoJatjs;u)%$9Dz3)pR?24CTKj*P ze`M5*;bBgo33P`F9o@v)Gdf=vildk+6hyDSMN z{HK5*fF}R%@~!;;2*m|Jc4jRH+|4KGuhNksO{+oYCMc?+m3WE^6v3ExVF2w~fZC%u zN-CJwGYOxIrwV`|PER_V?HxSU|%EUy2E`>>cS#u*5pJ%^Vi(8kNiurcpjbW8~c# zoD%>({{GN0`ibI0WOrr^AvNWF(1G%#`VLrM5P=Vi>^i1hPSCY=XG3QNB#B=wv zPCGZNxEJC+r3Cq&i$g6|dxtyBvV}WqSbrEJf#33F8Ua*Rv2!%HS+is8x5@>?m<+nY z@(gtGjDrtUYIn@EL-V!Eh9$hve&_lW({3P&x!ssNHn8RFTun!>5C9(D=8%I2y`m_ zHzacqu#I9m>a&|fjc08?XaOArhzZUC?kk}&T>tMTUHby;iD|j&*pWVBptF`tcH*Hj z0wj-rW`XZ#)r>{DjV{UEl3ji7E{!OK!QW6&6a;ioW)w>LOcuE z(^y?Z0|`~~3)1G_DfZO@K^mhPnA@H>2y9?X1=4$69V`4JVnq3G(JGuEL}tb2!};95 zHsF6NS84wvYLK!eB(N{a=vi}mN|{_yN~D6>qrY)@F{9HS)7StZ+y1H?geU@RA+`Tu z4sQRLG!q}xx33!Noy-$N*Gh9x)a%JMiXj+yBPaXm=vv3KN3-_KgW09Gs+!ke&oj!f zx;o2JIcWbSQ-%ihKRn*>Q7UqxjLqc3*Z0j9|PF1Wpb(5vMw zeycT1D%O62BjPuRgFGuvwaU#SXC}tafNFikY}UZTPUvZ^?dzRdH(4I#dfm~MaO=wg zvME@KmV7_9;F*kv7Mu6{v_TSQAb-mz;>sG@rpovPrI3Uz?`j=jUP(Pqck~02v zp8@RdA1#JuwC5Z&;kRmIbG?*Ax0Ak=sM$Je8_gH7m+^RPeZ)iz9Ch1bU^|ahr570qe9CF zn*w`svzMd8UR@8x0e=(t8~!8um(c;J2E&`NsF=^%lc9h#4|`JG*^swo+AR`Y{y)q8 zOYH=J)a73_@n-)W0C2k=AR4H5MQ}2}0H6!Q|0Q?usZQ&1E@m1Mz)R{|j!eFU-||}& zRixI!IK|}k$hl=~UI2UXZ%fh-1N;gjYJ&h*j)3=+`w#y^ zRVh6M9svvhocDhSAgWq(p_C@np*S&tI+vnExL>`1gTk+oCn2w17dtD*hpbe;*3` zS4sn*o&UuO|2;w=DsO;JMxoWbl-Du#pHTml#>V+qzx;n5gWI|%@Dr|o zCjOTq(tzyxL;kJj1=wr=k_h;EdcnOYeLMKdNLuc_GeAd;|WI zn-AtVncjaV`Nv1HbeA3_H~e?tAEDfTZDHWk|1nJxU!NsG5R{Lj@%GnrM?89=#aiOD zx4oZi*)NZ=OAGZdcMa{=^a#eDO!_T+Quk|FVBt5Xro`3JEA0&#t_akjpD8@$2C9AA z`)aC`Qt!l{N;lT|8cT&La)Pu@88j9Qxc6U-%%%m;K=3Ay5h>E$phr zLiBO>@_ALW&p6JjiE;37#_A>qBa-JvX(>8NKQtYs)(=5J^n9fWbLf=kJ0=PZSx=nDcCfohdHI-2eKe_-oCW3qxqkK#q zQ_@C--c1%cTGS6nR+z#+V zN8L#FQTi16RXOn0$8W6B?#@Bpi_ufjZPPfl8RouFzoWJG+uGJJnEq~ue=^tpMpT#M?YS<{o2GjOFqj7mpF?frw4Q1Mf&UD{o~34@bAC34#R&eR#UI_8qjnt zgZ9Nv*>@22V-bEQ8&@hY3_bD5Lz}&@LLFNH0K#3vxJ~ zM$`3%eZF0Kw@A)x5@Tqx_xp22o6P@+XfxRg55?sN($*>(89qHitF0D3blp~)SLnpJ z(E1i$YZ;;43ViS5Ku5XbXa^Yvs-z~l%=ADN7uewOjlXlO0Nd8&$4giL9#%7SoAZ$G zfUNl((auQ?onOZ-8qg|{;FcS(8#xCDri>-nOve`SoB$u4iA~*fOO%&2IN#Yc3aZU` zXTAOhA!(jUQII5+^MK1+4xdSO8xY>qPH&!wAYR^aVrcc2m=I_*{St5eA8TG4gcKD9 zP2nPBUn~qV-bjUcTZuAiRT;F{F`y|+c;5q#9v^(-6@8B}>5Ctjdt#|zDa^S-tWlTT z5X}`Z)uTk7PA@#3NxH>K1$&|kiC$B-nhMNiaEC&NolwTy?+%I62irW$@7LP1uaC6p z(IGF@wH=BFCd0MAEcknvT!UL0fAt_^pVh3F($j;l$=dx)NepA3zyEA!Ar^3R^kh6mzaT^5_6QUXw5mFa#7tqj zW|lv`!a`@u$#aoDX3!zs8dQ_^;3#IS!K!mFa`7%UUhACv-L=K<2*x10`nw6IK&L;~ zW1BgYIl5RAqo}dsFoiC#hT7oIaGhyfcW~z)51=-7Hr1(LB=J)ZKE*TiqJ;4yk|Rxt zsl4zIZsP|UE(cK-m(qcb5hm8?N{!t#r3=Y3T;17W zn{Sa`OMjL@3RwZgY)Qs{@;fWSI2f^b>t#Nqc4l*UWtm9DhSFB_ zRB?0hLa6}t8c}h+KV4gWQN+E#glQOHy*ZP7e@<6W15h#$ioY$k0mrbZR6yk&3B@H7 zo|I6w_MN!q6B#(*u1;yu+!g9721@Xn2NK&^;Xd|A;I@m=3kf_u-{nt%QLnbM=@F?Q zw`aMMT#|F1owM>ewt3^Xhi;OX4=D=BW=rbfiMcN|vP7id@Tl|m zHC|wF&e5{DyZtFN*?ZC%vaAJa!n-<#poB(l>y1n~Xy5>ZMI2wIQQp?JoBozny^ZS( zBo-zAg`AV}2}!^sa}HW8OEKqC=JQ7aNXj0Jpct!gt3qi=hz$>v*H_jI;@ z1n)7rsR`c~`}?=NV$CFrtPDfuYpxwoj(?k9m(%g4JiU6uZ~frmF^j{8SZS@kYI=c@ zVGR-iy8Dyrgp}{&Y@itjdqC=Q+bS&SV=4I#JM>j??XUqyU%NA~SuW|oo*6yug6Eo` zR`Oi^06`@t9FXcfYL9cM{J45NeH7>EdI^Le%N-1nsz5u?O}4_ewH{koZnUHz{N|7+ z@%2bY)x@g`<$@+cjJNhV6Q9wQXW}3;wTu>RDbVSaqQe9) zVEq1$C#j*f8ZLN_ii;x%<5Snu3FumPk>~-$GQvG}&8Rs^aPdI^fg}g&y*1!{PScmE zAlNmiQn-cDdb~4Hei{6R;2W*j?TJm{X)&cBv`Ln)ZJpO|!dHSb>&id$=Wtiuccc#z zkE9BjZlC_4+3a+1oni_Qj0FYy+hX#civG&|0)I_86?^N=SLcDY=dvM;&v3W?Oy3_Q zb9B1U$zZ6D+VFSMDAwi)go6tBLP>Ze`g}*L7-)Kl*QkZV(q<<9Xt{SFx<34Qm^~ ziy-$8Cu7Tzr7z-p0K5D9%N%A75_g<+NlM6NzmUa9We&eqP?I%*Sp?8f8vGhhA%WJ? zeIRYNP9}`{zIOWac;B%jo_jUzF7JX9OVei#K@LH}_KR(3fP30}x{!L&J@-&J+FrNH zySo(Rk4|bTT1Fp-DknDU;wt96!2L7SXiDTEp^_KbVD7qo{ zt-%!{10jnQIA;7Z=zEt^5@8<=C|+v{MK$?D5gW<7*W-rANY>)_TnCNDv$_YbvFvkk z%D`Sh3@Ib)tYU}&-|f_i&ty#Sbul!g6^i(#m5y51Kt|)Q#ZL?U5-Bb8^LI*^T{QN1 z;0DdIc+Bdg0=g1bs0&H>G58xd)8)%Q`{t`Y_JTZVF^u*BGd^&U!h8j&ux(Eok2KaX zbi_rb(QrMK2&`E9;+FD%kR)zUz@<@q$k8hWQhR}AibIXjPvvGQMtzo$^OCm zJ!+^dTiZ&7?tu;}f3(~_@KwQ(OP^9^ga5okpL^jj?Pw(o z;fLb#BFJL2Dd|2Xm&^X~Pmu;td2}~eQ|kfn?#sKi4Q=#!?ya;u^)A9p zq*jJpvzzzJ$vW!8ks%Huf4#u1X6<2=krMS&mRGrx5}#b7NvWR205NUP1I6*cV*+5R zR1?MeH2_?y{g;d8%f+B(BwLr^r(7=PDfqWj?M3x&%^DE znl3)RdfhK<;rRU3q~>H#GtJZ(rh*8Uy>q%BQ!8guO~;@U#Cz}#xGn2RjB-#Dz* z!Yj*tOH$&$sGQqJTntcNXhZLj8LKd+@52IQb&?VHN*2qjgEZ(5N9$3bVymj|37Kd- zd`)6Gz?E(AzMo)AfeWpIT6EoE*pI~tGO%O~x({x4_U-7eh+mZB7>D-mmaSnxCxUo9 zuaettqLz@a%d%LavPu?+0eYRiBQepN-RGJ5U$I8EiMrXTOclaWILog)W;X1oU=2gn z8coCK-iG+dJzW;jH|~Cppgt3wZGfy7Of(fzqdSJdR_CKY;-Um!+CM{M*5xJ5%)3-z z{`^FNX3#NLdSPGg;s;JBBAT_DBP-nWq_W)X1A$G9N+nh@ah9a7zemH8TH1KY8k8;B zRO3mM!nc``_=z;VP5Ye@|2O%0vYg6^!y$AEy@vGSTM;3&Z2|wXqFIwF(p-{MZ($XH z?o7Zo!VJ_-nGblS)s=$OfiahkX0*MB`ng@4E0W^I^5KNq|G5iD1u{IbrdnsUJHT`w<|7l$RZ=yR50UAyvaD|5z zNf%x(#h7bx``08uSO5sdVPq^{UNu(ZbzcA>Z| zP%2sgc}Cg^!=Z5>`4AQHo^)NcNE*I|Gu%d`!SehqG4lK<)$JaI`EYLWHmMH%Iy)`! z%LnVAAXf>h2Sdb=b(oV!i|`f*_U3#LR&j-W-tg&10CjwvzFEFW6z!C~bMYCqC3TBx zCRY`sRb!tHY!{vRk!`r4BgRc|UZ!-a%Qbtgs8M;h$!xNA)Wj3t z{KcU`m`=K6c0kxwh2(wnDcX6VPE_S;jbi@1Z%F}%=&?eEUY8D0L8LjDJ$I432AT2h zLCr8AkqlE^m(&2YXsmb9VHK0e`ECEM@o1S1?J5NR;nIx5rn=4{vn31`Y!UQ}L|PXkr2@$4o^9y|=uGUJ z<+}QxXTo(@C}28SsN3f+)1UiikCEgj5$Ot+2=}VI+d!e6K-^GgG0NX8!11$>tk7y% zCmIu32wK23v2~ILB#W}~8?L7>9z!S9kl_u*ONhEY{W?^yH;wF9awW8a{lSbn_YNF6 z8j1~s7f*^2aV&+ttrkKWQ9HTyyEz1;U=}MaZboZbA>bD!0S)t!o`>G%3IhB%*MCAq ze-pJJueb38k-A5GQC`_8)k{w+G=5>Q2}a*lo;GE4SDx>8T{c|^1 z`(*dpAwhmv*O#b}#W*Nhl1rNhn1SZ+Wh8+7#tbPG;Oc#C*kPqZfMF?KXM@ql`0>bV zo7>(9+K;!sS&h~FB|v~q)XV^P6Oa*xcGL4$s03E>6ekE>b`7&y!5F8Id#PqE;i;c) zVTu5Jv3R*56I;ho0BuSl%Uu+i8lw!w-Hf)9{LZE>=@iHA%GoIJ)VrCV?!oFyKU;fz zp^#wO36%yClHW%KdFvlKH7e#zW(D$L#C4bf!sb5FL07lcpEh4z6fHC_TF>8`$)aYV zZ;{j{-ScxerzmqSdxSUbK=`qWXDH&#L8_@pDVhD z1k)EKg|$OeEV02xS{`G}qi8)MOOFRRI72p%;>QMw7fmsX6Ui=^jw z)OG@iU!Z@INHFaB=pV%={Rc0m3wL z1h!q^7KOvXmd(Crkp*+!-gelV8X~Hn6z%&DyUwKhm~bi}3o%ExS54Ytk%LGqXDwSZY>{O2H1i?;{fDDF zJx1Q2hmI!pJ7QTs1;)i9L^IE{+LV_ODVQ@G(}wRH9&za+`3OPaO>DU8{JtVL1>61g z`h#l0z)Y=>7HX?Z?wMOTU{~)SLDMXu`C8S6>y6}8qY2)oM+xFgWGeCOKF3~+?=9Wo zzS1kmhaT+D=%l=-Jg!TmUWoGuX8!z6S<)a^+oB2AV3bV}9|K<{0y1E;1LCYwVlJ+d z16)QF0_Q6IJ(ti+ytBYE{Wu#}94;|n$VsGh%pcyoh^()5zx=l-c6g#$YcB@`Hp|Mb zZ;J5-?X5e14cwe4r5ps;8N`=!Mf$YRKDva5d;Of3?}O=>*Ehmi@TvJ3l z6WhMN2VBcalt0Zb0;$kE4_|a8Vat8qGEZEuQ&ea*_NK83m$$q{t&#%L?45ILcl^%S z(^s|0@7)k~GxjEsX!Kl^dQ3ecGP&h(r70jk6cb0ur-7}(p%FLx;#;OQ0;K^pvgPMz zWHYBZ^C1wbNJfC$%lgJ!GaQnreCRZ^a&$1FRC$#6vGQ$(9w>lqB!P7NY!vu{?_5b>We7U8e?a^in5A6;Cy z#VnFk5XEc`FKf$>KeQh<`H(_IJH}!RR-_`CP)D$QG9T7?5zp)SJ_6RMR?8ZH#OU*$ ztWQEhKo0gk0!WLqP^S9-PM`w0y$=H7`jNBcCE{#jB8x^xXr}T|f{6>a;2W>XcjuD*kJBCo zf*9MjE(F>*Y9iDfMO?6BHGYZ_11GA$yt*}gHbAZS^44nd3${$Z&^E0ZPHD)SUlvtU zi{+HrsG7$6sFdR}nP@To!}Mc&KMLQ1IPESyzi&u}^X7=EeLJZ}b)k>B)KLh8UL>0F z;ohF4@wHC*q6rd;?mYBR^u6MMI&CzvIMu9ENWjU-goEH`5&t@r&Z9x53vEF{luUq}qFW>Hz z)WP>qIJwd|#u_}hfn{FwaGueJ9PGgi8SkXASDTb|dQi65?~#Erb2 z8BFC~AMsAZ#tb2qy?5|(?46K~+#lq=8S$ULUl2cGRf7*#{XvDU3}Cs3n$2%K>Yj~ri+|JtVhDW&<+!h#-Mb6W`NZT<8<>c4B2ex zZjE#i&Y6@X1}u&e(CzQ<#U5xgGTA8R!g)M?_V^jI1=73AoFWpl?=$Gsx2sBUwr_v+ z>G;68$$x`jilDzjbEKr?Yy)Z0Mr^joCHpNrF`D-g`s%n_%W3M|`9E zMz$ls-4Sgi6mo8-3`K-Y8oPw*bRCS*inrANwkX8sv(e9JLdW9O_tHoNC9nk->F#rG zYKC0L!nRzz!WkG7J5tya?Ks++gqZ!UyH%S7M~nNrDjMYKW2IdR=x&>fmp-9zzZR8RNiNNq zo%SXlBzPdW@9>7~&x0hgT(AgskdW4|cqgbIUn}l%v!z?drw1%kmoQ-Um{u`ZT?b zJ%70UzNu)yn|p)A{hcNaB7vQSW`$;~!@A~=FTLGRc?9WlqS`AnZPiX8OBC>>VMKVS z#*JqFmSCx*>37Jb_Tqr%6WQJE>JN82AYu@5X#!s;N<$lP1_X{|OId*KGc+IFgYu(GJz2J0>t5G|G$je-XmhuqFHC_~((GGA8McS$F-B;h0XitwG(0)-3 z%CxxqU$U51e(l&ktdRW~`3APMsCLf!)olib$V%39qv}B)5Em)~^2lj^c<~dF^*PGQ z7am!0%OK>yXZYsOz2s^p6Wh36HNl`D~c5_5djyY~^&yhrXJcHg^Um{OIk0JYN25)heR#`de*$4WB!o%WvPv zRn4e{6E-`pt*aS+RJV3`kM|=XiAQx$(Gcb6`V!D75!?kSmAx;q2@O=Pe(v75V$^6i zW!Rj0+sw^VJ~Z(Tr`dS@V#2ERT(+fJS|UB|S%d4`D$2PTHec99$^;9anf`S94raK} z_U|Wf$Y+#?THT|UrFC^_qB?xo$c54+KJV=Jg@wGJ1u2_*itU*Kx%_Noj=fY|Qr&LY zs$Zi!cpQTK1^FoW<$~qjKG#3fG-=a6--UgkBgl?eGDQwABfA^^tDXM2Rz6zwl-536+{NX7@gG1U(kzN4KC4m*s&QSjm90zamQwA-vYpt1UPr? zA24;g!G~T&|5ApCK}PY}6^|NYkqaSIu!=!(>IM9oqEP1c|H%gdM$*dUoT0n{5^?1Z zY6#m-CaH7RFrO;*s@um4J+bP^jZjsw=G%2_`qTL7Z~t@zHZiwSmLbLJ?fim`VAwSV zn3F;%_Z@Ka{?{PcNOwuOf_SfBU;R`!Ob-c7l#V(#Jajtz%%#NsE0O?op2PY3!GTsu zeTBaD4;w944T2qs4?bsp9S1O%oolmYUer2>STjaRe!Skyu?@0d}x za^>cqMhOJD0e(D%99*7)RJ3sZ$TPX0gt-ZZ%s-MQ;G-JaLi2WK$BwT9Re`W0-FGjM z6FlkN9%7py$>#Glm>J)M{w%&14XQL2bKbkWnpn=soXu&X`{_+!lrJ?Ihs2U62N2TB zb9wrgJ?OtZU2EcaF8;LW;uR#;oRugq^ZqDdM)>N(vRX+`m|Rd)Ns=W z75tW?J)x90Yy4HPhPff=nnS6)OXXf5sPN_U`?pxvn61tcvK`3p%;V~Ygk25_EL0Vs zc#d>*c>M?7=GR2S)OGxB`@TPeM&ito`(?^OVaHhloI@8+l30tn=)r}IGne}-XPzJ#jZ%m+wRjVK1sTjTkcQb zobl4olSI@W?dWtxPmntpJB+x+{LJo>8g?ySZ^&d?(zZZkyw|*NfaRJduY(Zz(vS0^ zMLe^FlmX9XBl}*M%PahrvT0LelyRy5?lwL%EK!zjJHm9yDuF4+7ln8YM)ABuIW2vM zZdy!s#occTwIha5Xdt-siwnFQdp6&dt_w2V4j(D7lRnFw09M39b-U0Unbc?moUqAL zV2yHvLwb44w`#Z!52cb{TE87ageH(%1#Po^%c*FDQ+MVS!vRQEKSZ>#bcq!0o>@WuY_RL4RA(iA^a>$sBrJ+Om=2hYr z++~}tsg+=p0UcdRm@axaOoIJxn_dR%4<(w?M|_VP9?*$eT7FdEE#zYBQpQbwH~krJ z#ad@v%t_HmQ`;jyPS*fon7XN!CL&RW-55u!y#q~$(>9`NXmD?2?p?! z%FGzj&ZwW|q0M{V*(u)lDSio-bIF2g3C;?`SE7 z!K-hB`$RqTtdAO)l}xTc5~iU@gs-i}Y5G)wJv;rg(At@)k?ggv>rm};4ca-B0D!|T zltcIrV4+I&No$zrzH#Wp>aQnlKW#MvOL_|*1)uISha~7}@vl?})haU_dmZyZwJ#rp%770ufbDJxWr+U|;589;xP6`B zupCFFE?bwIID=kL{rphSZ*gYvimzZP6NyWDinoRVH`1n}POQC*ILSKkXtS#6X1 zl@Z)Yg={%_gr8mAP>|h1lH?0?KYx8pRH~ug>K77@N_c!8jeH+?kIkvx&@zUB=Vw0r zMw|$!%rQuUj7aJko~U*9PsKb+}D%O-oCn}5;nR!_}sJl#g3)H`=ke^!YqN& zC>W(KF#7Fhq)?0Rb+~4t{hw|ih)W$PSN7y12z*Y}hW!V=q01;E!Q5OVUpd*2J< z5BSK{$f)VD9VbCywVYQg7VH=!+;Z5Z$0#EMIp>39uq9k&Z^*Fd5R>)~282ki0bYsa zZb)+7lN1%o7HJ=!aC7}1oe6hr)1n*#VD%Ro5A{nA_7KdvYPL*b^_u80Lrum|;e&x- z-;?h#mwDgf9)8;fbbEs(RaYFHNnha>hHXg@Z`FO5{BmA`O$Yl4u;@VbLOCXYbI0%n zH7|xBYJ@c$E00Xe)idF(>{IH{3mMcRi%9nNhU%A-NUIfy)B407Iv`5oAPJfJ`z^MD z=z9A3i@+RdGjDE3JfbFx67FQI+5FpUxH-4*Yx(?eMq|peLL(|-lGRoy#-kowZSkPQ z#7d=0rIP9xRqUXdEz^?DYsEMbUsCH_fvj@$;!(!L7CtAA{>czf0fiDkb!6tgM8W?W zU4!^`$D}OH45Y|!2nJZSK5$OpU!~_&$7TDq84>#Guy{(=x>m_OwhU45-^_bZ3NgyvN4r(SW=c}eD?NF7FuS+6jR%uGeF5% z5r!(ebeW2PM*vzP2LrUD@Uj+n(dJjeK-lEx5FgIW?YN1NDJOQRxo0SaMQx*EMN;R~ zmq`g-;1$|ve$>8UBMMsmUv{z^n#@S!r)U6t0+|)ci1-hL{1rzgdw?Gbs|JGMpKN^w z_{_iYP_nJ5gdF~g{2pnF`pPhC?A3`^iZmOm_v9MK6;W`2xZ+{$cp^3$6ua?GnI$YT z(|xAr!$lI9+tumQCu70*#6sYVbJyoyqpi(9TN+wY&6Qc@kZQi~nVa4N<=l&vNci}T zqkisUE1#iEn(o|S8eSRE+bAdjC(U9|yu;2!Xfu*#dG?kVIz14MDBEP8koKTEZn56$ zGm+`_!4Zo~eRMHSx}-$=6&`*P+^)S+ND1R`0`5sW>QO1scY(`5s^7`H%p|N*$voLt zAc4ku*AhHBkAUw>b!S*rQPfR)l8T%Ap$(rh2C`;s5FDJ5)5x)CdUykRI$A|ly-Y|8 zYwV|BH(YLMl_pRGZn4Mu#-X2Cf(;h`;nZ@#2r$mXn*L}wf8IpGiPv>v{7*QD;!e8h z+#FK$T74D9qGJBOk>xa7KAOTPm!*bu5i9Eg@TmKRjwDrChRWh3huhgFz#pD zUxPB=vKN0+oEYBM%4wfsqhns^pA=_OTTQ4K!S?WPc;E*oM1r&Wbp45`x4yzmy{d_? z#{C7&q3J=?BdqMF=nx~p%~SR@yaB%4ixj=UCr~qKsd2I$@ch+e^&Jd&`P6>O+vUM_ zeB!v5tMz;DN72_xrT+HHxd}Z)$tFe+5(2Em8cp1+(j*_~AE=fjDJ3@y1C}QNyituO z<`v>K#j^SK1u{RJ>;Z;Bm&*k;Wt;FgqC!PVeszm$8$!IOsNp?G@xM$ z!8@(khou9-i9#=8xi}!Y%+p;opgyC9R%{BKf#=UreP92;GYVeP`x&r%&%D7|HYtuj z=$uxEzr;#mB;LQXu^hB33Wyd5Bs@fOkjT^&$UMG{W$(8^4p}ZME%%9re)N|DC-jvE z#Bzs<-^NRZ;ddO7bUKULfixWh4oAFDPALF2SiT_Q<+Jc);Yfo^AkuWYbHez6cplSm zM9D}oSDXesi~4`La?Nl5EQw<}`@Ki`p0{suLQZ3OZKzHm=u{;k3FN-c1DQi1zJrkx zqnh}wHM(TkWf!i*`7Pw8W>lB}xA(}Kk}h>81A0j^-~dw~X)xW}d)JNcH*7+!+b_Q2 zSm$8y4u;KY8O@3V9ZlWAu0)kzz6Z^|7Y4t0H)$J(ZU^9Tt*? zUv=TYLm3f)h1hs*phj7K%?v)S%GznrcNMz`B5aG_C!;Pz_V}sy^ zBD7Y)3Nfx=j3B_!4i;>HOneI%GA|GbuPe(B_mGl4^Sh`&!G>TpfR4}PuZVUj2w>4Y zA^KieKwDN_R)s&1AoR4kRUgOes`nDA6P0ix_T#w5SuZ43v~$s)uzQG-)W<1U3t814 z;TVU5l8y=p4gD{;Z0Havgrz1;ohX$ErUpLa9oI)qs<XR3hS`*gGP**Ec}Lw_{ZllEvHk`MEnUMyIF)Z-V5J zr-{D1nY4@v&?K93Y3rpz$Q9OTiymriN`^I#k4VCG??=sF)1I)BYJ+DBJsOFX>YR`o z`Go%I9&i?ymX`rd>XN*vHQv5;X8C{(^?P!P$;19?!s(cJ*9ks{KqTu0K(d=q#?*fx z`Cn!Ek$$tAHB~BA9M8VgEJ#C7t9v&CCb`i8BXbL@4G|;ErKsZ2F4iaredV~SJ~mq zDbsdsmLlCMdE3O^ec&l(S+b~@q|n@}lC zc#j5{l3~*9B2Og3PBC9Jb~tsuRd9;a{}?gf^vE=(-lgTnrXB}cO-QXb*`q&joO(-WB*R=JwxUXV7$9BH zjfzg+PDQ2y*p_CK$Osrw@0op<-^mbN7SZcVj4{B95n_6vi_0*xh~OQzhw2Bg5sw(h zj|jWA)_04E*Zfz~^!wmLzrR1lTSF0_&=s*48$H9|-7w#p_`Nx%zdjZpAH3!?G8cen zz1`k)NKLxpvS;A5Dh*m<4+{dH1@JrXz74~4rr`Injxk#|mP#5Fd=fZ8y@QRQkvb7< zWhMlt#ex7@AYE}BH-?F-OJU&3ozJrlMpfA}9>q$uXw7Bp#_#|xPM=nj^HaL8dg@lC zG;ePd+J(k4FbnqLR*L7Q_|S)-INTz>{gM+!+nPKQZI6}0;1OZB4lKaFO#eJTP_5B=RQ0#OO~|=Fd)+DS#1rP5%PQLTB@$sl zA6t}U`EkwXjr9p8PobknDp=2ZLuEs!ux2kg2-XsWc=vpBrvsi_b#gpL%t{=`3K18h z3ebFoM4j#j^*Fl688KcUHb2Z&FEy~wZe{SNoHY>f$8YI=0>`Y zFA4j^0xA`1Hc*7*12wg|VX8a8z*k_ampMB$_s3_8c#x2}bsy=bn5AX%DLugFHv5zX z^fU7M=lc!&pok^Ak~#~xhJ}Q_vLlp#eM~7S94UPs6hgF(BAH~eQBlMAe$R$7uaPA% z{&-Wh74aiWk2N&Zt2@WEGqk2Q*Q&`4$wt1`S+vX+pl*IR>J~fjUqB9~Hn6_^nLNJ? znL{e)l`!~d;l*`*$WJ=Oo62h1pJ?f5FI!0e{z9<=CY~J)Uy_z(;%(AnY=V1Rs^I9dJYmas%7SAEOGrnGPv2Aw0%C{lY#E#kO z=Z=MyX2?E?QH*yF{R`$Yp=iQJB8M+2MNQrH^l^@bkwS1!q3WPU)1;Nf3s66Ltt7CJ z?;t+nyRS+F@2E^t$Z)PzH||~Vi3(7g*I^Q zH`3e=t3`g!Gkrsq$*3oE;ZW8xObhumPv8FG(|gAxPCdUDwI56BcK<`;WG`O!)mkW@ zJJuDb>?xGOvTZ`7FnuW;HZ2LI{bQjLJtoS9`u6AJs zU|3h^Z%smO73puNA{>EP^u1mbtgQu6k<*|sotKasG_9qd!$LYUZ$aAGnw3MjBH9DDz$CNss-#xS~)Ev2W^ znj(Glj5jNZ{!ofV|LyV`%ASPXj_pOBEk8vkf!IxEl5_}YRteH4l!^GS`9YKQ15~d= zrr&%xlpei5X$5gb%4}H+PT26Z%QVuyEX=d4Km$wC{-O9)2_=HdWBJ%(WLExC$ygsp zL>0LVgQODRv~QjNfk1e&i?!b5r4>(J&Oz#QFG7+=n~%a8<)BQUdQ^uKC8R#ca~Fd0 z{E*c1v=4o|%-|-{ehl|6uqZ7kZkCmD-6QWXWzD-@W7amLG#fCxR3I5zbH7T1k^fCw zRi1chY6^#wN+j)?w+WzULV9MVj9fE7+_tuZ#=5RHG;1JBAK0amguK>C7Gr)_6pWyO z4dN9IBTGEOB&dlo`ViA)cc*4zdZ}kL)Aj2oqK`l5*|x3wK_Z1Kg+0GFd1IuWgowwE z(8nZ5uG?R8$(U_8C?#$azYGkPI{YU|YwNO=s&{HXhzb%_Z(>p=J0Lhqo?EpLWV9nM0 z9kXuv_a9-IlmmruEZbdlCmoS>nP$T@-oZ&Zta+!cKy?)wAs;c#z5_KMUiG7B++GHn zRDo@ghB%maq`kb4S|FyQ&1Fqr_Twj{7)WpI+)NN@`T=VX?-aWQS67-10r`O1f_|w^8QuzEU3S zF+AWhPB)F!O;xTRNxze)*O<>sLwW5(vZQx<@yZ@;-X)4kAW;Lw7O0J%z|EqYh=_+A zqH8}YQmyYU=2nD14$+sno+Nby5emT0#(6Dk}S8h(k z8-4DDSu~Z7wU~a!*?}Xb#ulLIs+-XWOjfT}xnHAzswk4x@s}x*`GNLt38oLq>3ej^ zCQ}S7=(;8?mpFzOH2{*ZK>&Gx|CCgIJy@kz-m~Ip52J5=n}V&HHnV`6a_R{41eOP# zK!-ipFBxOtUect+ZPsV^BX`-e_4W8l?KXON8(&|LQj}!)!L(5l-j@c9gI#8tMEnam4{Ff`dq+zG6$Sgt3<8=z*HcKw6HfRY z*UIe)jlM$^v=VC7`&2OB4f~x8ulN~t9`v|8NwVe5Y;w~eDOKsB(I8fxxkLY~o{3`E z59sX2$3|NeY}>p$Vjc8;y46?ST!-S?4!VKY=@Bp`{Gof`ejN55`XQtfk4|d;w#{E~ z7a6REyI^J|UEiWqNroi)1KLI*eBT{cLLR6`iVv%9u=yJvFGjWoCV#8KXNN^k{A|443-YN&26b!2( zKEevPa=*+g;;Yk0?0TKjX7_S5*cJ8_SSHQKel%1}0bL~4Kncv$(A@!3h}I*^rb|96 zrA`ku8ppL`3LRGypfVS5Cl;AeP7_-mso#`>(LDh{l;ydf={8qARty*o{~+`y;J15t zJtO%Q>fMR2V&2%l8}r02A(gYqZtBkaBM-1AdW15W{*#a~0w~LgY^9>Y=K+6`PYuN5 z`;--nhkb(2x40HFpyuP3(SUpXJ@H2K>mvdPlkcXsX-OFDnmZcT)f{xMV^9%a!!UQD zCT4Oe1SAnC4=%KPZO&-d{#v{i3)N)DAcraOD20v>%sCH?ml6jF-Dk&D%k^8&@<&mA z{Y03ZQsYSSfgE%LYvJaJX!z9kdIiW}&_ZclTIW$)^P{9vv zKg(U3S#u~JwtRAQ{U^b8r(%WMlXQtM@>tfOI9=*Vo2-af4<{ zagqZiIdS|5dR7|DDlj+MU}ldA(tmod4I3!P7}~i6olxn$>OPkw=j9*M6@+52qS(`A z=^k{GxECn2zsTfCWOLFFi*Gnt;>S&AD1z{S6cE&_c3XEoTHz+nK{T=s|89}cp{Yo7C z6TH3~v{9?5((I|m|K{f1A(z9C^7e|b$-d4iKw{Ge9jiC}&_3Ek=5Z*9qhHe{a($y9 zctZLOK?2Tc5Hq;qPK~TSHZ(hG!B-gfU9u07FfIH9mA#?ioQ|(C|Ku>YhH5s*a?U2s z-v0l!_ubKSeQVc8@0}oeNz@R8h~8VYNC=6N5Jc1j(W3+rqDLf%L-ZD1i0A}CMDIOn z)adMdA>*c?rEpiK`+GZy6VRtJ|sXQZ&1M?4*Koe1wZN&_o zstG8use=$|Yr{@+L+$kAi7v#qFDPUQAFJu6J+1YU5=Z>TM~|0Yn?Llthw56e%qVUK zo>q|l@lII{x?7I;Qn_dCZ64jt@{-n()&<`D zfVN8Ql@8`?BJ&RgYU#eFk&*$x!`OYu?GL%3 z4UhK(y4c#^vp+T}Tf)D`(f0VMRym80Ovg|KcGr7Ip#3M7REOeX0Rnr-6A5n~(-1lr z&pdKwXNBUfQ1|4AEL$P0j|{+ObfHf-v3R>ADC=VH3e+PEU^LGDaD=p~&GgQ$1cijx z5eIp?hs0SRSh6gSoGr3wVYm2-}t zKfPc_mNApYx14?Kv%K)KE6Mo|xpFFaS{orsJW}oCjf%G^MoRe4uws(5AI4CWquzC6 z>ImF^q!vn-r$itmzs^~^-y_s0Ir#ZnP+9XzUH5!2W0AwN9n>Q^fe zjcXxkSP={a;MV`S+gnN3Om(u=EGhT_zV_>X$t z5WY12b+{@~A>!t+DnhgoTURK9>hj(TPG8P3*#%0n-dSc^CVe04;uYHE`@ZCsb4eN2 zGf!<8eaNu*?$2I-F4EHS_M><-(|)P0W}ki4mBF9$kJc&Py>6QN_-^ie=m4G~y2uxU ziY-nEOUG`W?$~{gj|F?d9tREu=9)1LEv%pkqboTAgG=xil{06~uV? z7#6KK93{EAl-I(RTSlTL9xe--skJ-FV&YEg%+nVVDObpT-Y@L%Em<-S#0vk>m*)i4 zT&2hPK+zH@-r`6ebI#j6djn5LjF+sMRv|<}kEF*J^{c{)$x|AVb;N4XCp)3P#J?$N z(YMLJjUDT^cxq*m8B6*@X5^ORvWnhIe(WC8*$;+ZoxKm2ykwBJ#vQJ7jB7l3{ByG{ zY>v9a1pP-K{?7SDT~nX9b62w5i*ZXX-%lH74k*lV(`8&jNdNWX7uz_BR1m+w+q{~% z)NkkP3CZa8w}X0!tt)NWdeYC^jQFi{T5rGK;)s=^u%5W2FK;j{)pu8GvOk?q$Z3y| zV4>Xwtm8I<=M{kjQx{%pbVux7Dy|CmDNuJ;`^ErmPr2hvk|l$3t+hEm#pl^ml9h23-p2B>BdQl69Q9%d-=zBQpmh^?(I z-YrVsFD#{?IS9|wrl{{e=F0SneK0pD`I_=v& z&f{}So2~G_8i84d8nDA@moL~X!AftB@SB3rd9wSSirpAx;SO1lz1jT+>9SI(&>Ee> zEEH9qVZbX5@yNG_mP@2CR>{ODTvAz|U7B^pc-Gszv|mY#+EIwpGi`D6Q|^n+8FH_J zAf~_!EmFVv1_tTEyw^0D*@=6tQI)?h1Z-{dIum6hP5UF?QtGGpFcG`@>~qm&cfWnN z%c3cY)>_1eo#FQ`^KXCM=T3k#VMQ`gd>EkoCM6ILoi?5(4B5_&s=Lo=T zm3rqA-&s9Yb|Wti$Z7eQW0wZX9{9<$*Qu^)yr*R4l<}-f}NTjpK+k; zBw@ay4zf&szFWvBNg7<)>+BA{wsY^`QGCzVDA{eBbdsvQyENx(u%DTuwf`l@&kT>2 zg;ToPtVWfs3mv195$A#tvVL!NP+q>Sw;!&4mJWr;w%33Zf65YV**UG18@BcvTSoIz zONr z%{n827%jq;vgrNtq41n`%C}nx5$VhA17Vw4t)V&GCK1>n^*x2&FIBAT7njpYKL>pj zSMHaDlyTqW!CwtDtiQ+mh9oA~O?tfdS;e!bO|9~nt3kiqVstWWpMSSh-w>as^6pxg z-4nniTPGyky|Ll=Xb27Y_7$E^=}+6dOi|>I&uRCWWTd zEAZK~T;j2==HR2Yb0@VJ$~n^Zxscd?UrEiRMmIHF7FK$t+qOx(!7kNp`*>vUorV+n zaB6)S5ke0!5e1hRqCf0`tQG`l2YAYX`sw&REh$8SpAdY4pjZ|TX_f4|5$}ENv}1pU z*Gmg%nLIQxXX_WW(u}Q&Vs7tWnC7H%{{9`38fMN^G=zZg!7c1AtD_I+tH8Fz(Kiq| zF}^k~dUJO*1v*D$t<3%GL4N}LzTOt0^<3;^0g=XhbetjvOp#!xxaZtdZ}7G|hsxW` zaiZVG@#9I8oAv7IQT?3inBs2wu^>!NAsx!d$UAe5pI`OeBRXC;$7%%j-#lI{8nPN$ z^BhKso-aC8DGS0SllDm;jEOqaf|&sc0M8nNnT}@{9mD2PD?`gZ_F+PQchLDwkQ0Uj z7S3F^;1!YOI7`0@>!fnr5<(suX2ul98!}I3F1`?&>L0f>>RD|jp0)}7LiuJu_T7q+ zl+K6i`WZHR7JU2zc3(PodB!Xp9ym0YrI-HZ`R>2myb`Satd!exqKee3(H4tyj_ZT{ zR{MRF7jnj#_t9hAKt!A3k$qrk2IjG)2PW%;zx(y}81%b^Mvimyt6fY@ks}?NTjMJ% z!%vwOnXYe$tSkMb`t$;W@AZ$nWJFF?nH=9zER^`piPMh9B!Busz#3-Ci((3myw5LN zF&agB{aqP;o~NUb&DAPW7mlJ_t4*HzY@C|gvP25(E%(yoc*Dn^BlhG@c!Hh2qe3U% z@ix3|Z6P$&$Vs7_eikFr3(?}dO6mDxAEzD~Ec&sz$W4Z6T*pj&@4eg1uj9wJp3&lfdwO`IQyv>xpR zHs8MzF1})>1q}k$8|MMP@W=0uwUZd0rqy9kIP|MJ9rd z$c((6v6VE2CvjdTYE{j7QXa{kO431w$qqkiPs0*x#x!u_+gvBdbvGsx!Oodop&L^^ zg>t&jqMqV@@VZ{Sm59(RSO4L*a{6RUEY~8T9!2{jeyvv`=*5zdtJN_eK1=av;e!XG zC{>t?GH`T+Xh|6^nmzh-)mgNHwwN_2hm*O9EED%;%M1|;{{4|3dtC)NzKSt}!q}0+ zQJr?}T5ilw2K-+6+=5Zv3zfSf`vFMXNCfA%rT9tdb_#8B)rC2vd*=#Y0 zS!hU22SOUQ|H#$tIZVvKbEvwov>*7M@}d=+kk}yXLv!&6$v>l$N)SRu=xb{1$BR2g zkx0)&^c%t4u(Pe6PjoNOx2%DC@(bjKJ3?Fv9i4E12|hVCW3C2h z$0q`uuW&eE->Zfr9Pp5BKC2r9;#dJ<0FEuw0EP*69>NIt0PNU`egva-c!&wRQ+?#; z5+ELldjtb}?&P*|p-1?w0f!Nt8m`8068leh>a|@(Q@+;V|=vm{!f+sfgdftdS);q&(t^tdbLkxYVql~abZP*r5gW1x7(rk7S- z-J@a4&aKS*F_RhDxn?r|a{k7+z^vLxN^MZtDZ)H|1^4%6#(?MV6dKQX&2q|CW|Ye$ zE2@Bk97Qol4AOX49?4cdqa3DGVf^&8gnaRf)f~d4=NeAI32xhU>*9QdqC=0Cxqklo zgqF{&BHF%QHPFYQ_+q=3U^J?yCzu&ywfZ*clYM+w=Ud;394|h%C0hvlKH)k?(&iZj zc}?Jv)4Bl7e2FP>Xtf0Z{om1D|X z}|qMMuFF1BBwmbPH8zrvEFtT6qrqPK7Oy%QT&CaSgO;=7l(|J6CNQ>#bh*K_76e&yQ;cjb}m;xz9o6THiySLnG>sy4A(cD)2o zg}{a={yN5%K%0RpweM9;224lYknJ{c+c0J~rCGt`?|r7{KT=1Rjy-P?P<3vJM|Ush z%)GeicgrppXSbQj=UYt%=4#BPv1dbX@_XyS+gS)eoW#L~;pYT5Qu2fvexl&TgyML_ zmQ`GniDRtUT*dCt{%%!P%*;2ceUm-crG;I;;Y%V#IT46L7ZX%&pHhdmm zMf9F|XYt3UjV88U&$xX**}O?;z`Ik7x*TR?&EY@xYe&=ig_rGKp`DE=zqD`wV%>$8 z+#dp-sv=Ma*B335g_}K&Zf)s(&{#IpVOVNH9f?t7&R}!ZZuteoy@#-lWNv_)axwLh z6z65r-tDB}(XoElMKvKq`E`p=9$`_K&=PLRE&BH=O+y$TzGW*Q^wc3hqz5LGk)<8J zqlgaWn%gCy@EN|J3VDEGO(OG<#IpQ>hU|`&7mEUNBeU8Tt%mC_?ioM!X&l{39N7Nm zbO_P<0 z2(Nv0y3s2}(NDg zZ!^1sJLa}kG&6=o+8#4pA(q|AiPwdU1o%~-6_b5w7MiM8TD@!(KcH5I_5^vVN{=bH z$_k>buhpsctMqz*!qxCQ$Qo}Al?#M;XdXQzaYD2y9-{9;4~#J%5zg6+yx#HQUBfMr zx>>#oxxp1hGW*WPYL~uft6n0v^amn6QBmS<}`@W)?@Ow}ztIpkd>CNgw zY;uR}do~gkWS>f(V~4rU zo->^rz}G;I4fcy#BgN7Ui<`l~@4zJ(6Sp&1oS3~Nh`nLG`y*x9H*ND|+k zX%3~e8^UHV{j=u#S=q#&$098llC~NQx?I~+p$o1JPV+b!Oni2`%#1cZ+ZJwouo&_AbshpCNG}-cC&l*3Gtm4pJ<*9ICH6au;EeZF^gnwFY@rC zRVdj!;~MCH08MKs5`Ko}aaq`!!IG5U3^V{i2_ZTWHnjq?l9CZGw$3Tyb@`u1E$|+` zi?hvUE)fo_ zW--sL%gFueVW<+cmxkdLI3tVRsqY@!_mQHK_wIfM)Jlh>qaWj5m|aq4Q>zzeck7lE z<3-}3y=CI}T1MMNBmEMdPcg12 zsGW)29BRSj-hZ23+BV|*u&EOk3(dxUPT^X;g=5(#Whn_qzS7bSH5I;C4YQWr+%XJ$ z(4j@*5y?ko&Hi4jL<1sw0&z@2q@33q2B69 zPoNJsrLx%C$<;M6sW*H7%*E>G{9sw~WSM(GeZP!OPQ}<%rF?6lykr^$iG_iZt9{(G zYLW1pck-Etqnz^;D%rK_Ii(k5q2{x0fjh=T{O4HH20jdF+FXydFV)-#sg}J|b<<3_ zc(AWdu&>4x# zEI2S()EC;9t6(Il+v-d1NTlnN&lGIp@x}X#^B^~!bEu5j#a3)iNm+HTW1<{D+ZlBt z7*_Sxr?L?<>4A2In%a_h7TZ*Lyt;m2hAC0yfmMvx+{; z>@szBW9^FmT*RfmTogNh^IM#(Oaw2-j7Vo>dHI;MzGbL`M-UdeadhdU8f3UN@E45Z zHsWxdDJMPnknt`HU-hk3O%%0ik$tbvS;sdGe6A1{VE#b|8_v;*?xkX@HI3TL0p5ceTXLsTTTQgJ;yN&dR^8AfkH|7`#r!dFg(kvRs zGa>ahf5r2;PzsTc4%%B?T3`ZOx~>jFd1^*!6yhfDjYLo|eoey{wTbhhMhOZM z6IO0PqTm*Pb)azKV~$7riEInT&D6SPbiWfG2j$h(DNXA;ak`nWSj@ZONyn!kg9HBsVixIwHGZf{^umw*@g=z@0)Kn7*#0>lw1V#KKJeW9+_}x3}YS!L_AG!p!b+->tQudiW0nYV0SL z@^5ID3kpuQL(W<61-(`4+%8ZIy5BJry44^NK&r&xIL=J|;)fn~PJ>_eMkoaUSyd0bo zvfGaSB_AHO#l7x(Y%jXpOO;I!eBN?P8LuVOdiZHTMLAk*(sL|?my3mW{kD*p-zBPb zjK_z+delkiJU1v;vL-$iQm0XB+`V9Uxjt9bN@bXxGqi!lNtm^UQipcTBl_;g7UH^d z^or7r+MKEUqYIgN7-dtc*Z~7}j+nOe?2v7a6r9pA8|`NUh>jD^Y_&-J5W>1XVt=Xx zH)`X-g1Vmy>sOL#bi|{UnP&E@J$dS$-_dBUsH06y<7raLDlGOA@X?Jeiz2%l*&gDQ z#5$%m?OQ=9QMGz?DRVd30kf)q^3`R6oetT-`c9jej?WH8tNl%t?mm8X||gTi&@Ooqd1Knf{WVm zcE34@mMAsnkcql%9UX)4u`;94)w;mDR|vr17W=?N*cqo1|0)>@0qm{}7y`thB`4z! zopGd`PaKZPoL5#Wso#KiQ|FP0M5vJJP;$)aw|S-L1=%$h>W3>PH#8s`Mg=Mp%-}`? zcgyT;%(l&bB@zN-o(J<8sa(LZ#5pXlq-&9ALoR7KLfO%emDYx#IVb(|WVwidSKBox zdQOty;v2~TU7SA?rn;&oXVr|)~{|;aa@hM&;)V^F(fp*{V>XhCr z_XFymBu~T%{bY7{n+Yi6hUXPZ9F1kSn@uv>n8@tJ*v$Aj!dE6M)qZ!p^s1i9q#pc2 z=<((=r`@z#zP_ZN%S`6SiLqYkuFvNK-1zU>&OSHkC&B)jZ%KyUIOK-pl6 z3>fKm(ry~N49K;kVC{)?8&Y)L@U=D4fPg&i;)DF8?HB;lSj+C z{^W}#yD`BRuLhsxbb8NJqjfz&pV}rmWQ+^v+0j@nx*j>!O8apZYYIHvvF%k)%)lGv z>MWlt$f``_3s9{Omu~v{74KnlG$uuoSVm*Hv*y&*{yO;-EY#P1#}3XSfQku8uTcV;CpIusPe%r2nbqup<&xce#FAUv=I578Ju*P-m6i&3@sdyr2{|-m@1m`fG zXqO|L!!@sHSGah<(%FL}oU==39sq_3Zs{yK_H;OLM@wh0V8Ke>agp|?d)&bnU)*%iQ^Q2ja-2-Jg70=;h1;c(cT$le2NBIQjXt)l@cEp!| zOrO)vlWqs?0`xib;5=TT{GUi4Fz(0n`OCP&_ye|6_%qOd;m_eTJshup&Ywe^BRY?t zrt|;u=eVE$3&;<)cr;9YT#xk^sMtSIpZ}!~(3}56ez3(4TkGO}#fjJN&K_cBiGXVp$j}r2ce&oWL8Umc-y62=-eWw->Q1xh;yn{pvr&|2R<4gJEy7)*GCet*>Z3j z5WpN~trHm79W-3=Xjsw$&OV@X)WpCiz=tsw-trL~gRN}of-^zg^XE)(Jb4D`m_Db*9Sj((@DV&XlO^T=2~<8uNU+if8+M%nhx~U80!T0h z9U;XYo@sst$?_Nph75|{V-o3|DtiBpMP+bo04x#(hX=QB;aGGs#md1C;D{fv2!4t| z|4H!-$D%VZ|0#>klJP%e(MdEF2aP&l(J3+l61l?qW(0f>QX+im3`e1}Ffa8O|e@?ah0XqFjA+1@G0Ja2<~skCh)oBprK^?HmkbkAHqbJx5wc?-0f? z;=bb#?r~7j-rFKcuzIzhW5on8!0r9Zv;YcM9A=$;oV{TQ3RKq;_TH|re>q4`Km*`y zNWr1OsoZ_m#rn7gi1r3cA8@PyCnlUq-qG-u)IeI&&(;!0=@Mo~4L5fH4zQmtgDKr% zO#s{w{~Q9G#j`kvbMU}?`VV}cn19-euK^v5(Bb_}kr7>`=_Cw;@34WJ|d)Ttuy9}r0t#DoZ|2?5Z< zzW~900n}aI0O(YXg10aQd`N;@-GL+0*;EH3(y7I!182>XMHv{6;KMoQ(Vuo5hI2q9 zc$`Cj%cFLHqV&Kl;Ljq_F^~S>!1@PdDVTfZVY7}Fn;xHDY_f)1LjziH%%Z>Gz-R>D zJ-~$$K7|AS$v=kx=gVKZ`6wP3iB83{c^YRME*>}ro$Y2AgW$sf1p4#)V6;Tx!U3ao zOrNtbF!sRrG9b?>7@$HYqXl4&$#Viz{)aoKV1NjnocHf>2fl9(U0LC|a~RxB@T+hd zbTYdRqdA}sJj|gr#R<$Q>inGq9Wm!reFKb6;Ti?AIdz2zL)PYy% z6Y87^=pPFYT*LlR2KxtBu?M;Xm%*?PGT8o!ih^U1!VZt!4!YMHN4YTwFaUxY6u=;>T|AGFTg@Nf0{8as`{`{HoM1S;0b{}}&K_F;0hr#?isf$oN QBIQV%!F$^Hpl0LxKR2^P1jjb##DJjg1bi^HMg(+*VLBPF%jOwC`Y4z^uSUs1i!~;`_h-UGk zWEzcXaPH)rzL$mF=U%CZDTUbRO)Gptan}OOrJ@5MIq+$EI7q~PU z{Em|~_P~tFw<}w_|@T|Y^Lu5Bmfb^dWXREQ9hR~@b(5AK-&O- zL(Bm^(1L)%fLMICH$v&CtscVZtUb&J!P4O@9T!S+R?l%!% zdcQ`@0RqG#1%on6@|F7wl&)WzuSm%c4`PWTz#-6eN1;+lbmBKdUqb`rd>K;`0U{NQ zxiOjre;NE5IL*nO<6K3i{EPF8&@7Zr)E(v*hdVPl(_V0N7zjG?^B6J^ScQ!lc-?~7 zEH{6l-e8c{2jzy2e|%JAoyjSdjudn_oR*Tw)>}fyq0x_zv=+}pO$=xc!cnV6dW{|z zMEixN<}M_WjSFmX<|u0jixEQi*pRR zW6Sb>)kJ5Gb|A)1YusYl-U6L{*I$}RVyeMTx%};Gt&yq{XvuGtcEcbjJG}t%o+b> zZ2A4(k;2lG2q`V6qO9Lw@Oc%nU;FHhFs#bw{ZMD22QCD$+mS$UwR;!bXJkn~BOmR4 zW%MMivpO|;zecogYuAW(DDY@w_J>y+_LY>#wp3m?lzj~A&{h_3rpVh5SJHZGgl%s1 z(ampim9umSGOp;@?kks<@6F(1g0J?ew!Q^)n zA87X7E7uERmzIuWYqvI9WFiHOl676BPi?>(Qj|>}CRq<7Q-v!9!O$$16Bd&=NXKhc z?U`icKy&ZN5{DHlx;5&vwJs$6P=6$&$#%hdTCol)2)zx*K+Rq zDcK(rVS&X}AFcJEHx&J&>iEh4^Q;NHqIWXjApLY*Z+tw#qp2;tp#(^igzXRZ9lJ8o z-rx6~sLhM9A`HqJ)jF9q4!*R2vy zd4G92{VpXA+8z&Gs6jN03RbD`x_pnt(2SG@{n^FNx=%$pWBV)uAYo1E!|D-}1M9ZH zYZL4p8)5D#0M+xz@Q3+Ri(@8R_l(}vD$Nd{1jenhK1yU{Ro>)e#7miWN^-CMBHh6h z2*GqdE_cU2$f(Y6%FnQ0w2v^qTqywhYEYu7AJ!GQGb%i3iCcojnKcIg=100 bright pixels, got 0 +Exit status: 1 diff --git a/pr-6368-native-evidence/mutant-focus-crop.png b/pr-6368-native-evidence/mutant-focus-crop.png new file mode 100644 index 0000000000000000000000000000000000000000..79a2e875dbec565cae0d2db562e1badb56cd7c9c GIT binary patch literal 1074 zcmeAS@N?(olHy`uVBq!ia0vp^1|ZDA1|-9oezr3(FeYa@I|pPtyF2ISxz6Q@wOd(Pa4eeq;@OiW4;DSG)bCuPRMr2uuIByj#}*2fc?Egj znO9ivi;g*^J$tFH>en8Yy$U?fKF(RU-s|5w`^SInzTERW9l8Ji|K5XLFAZ1CpCWlI zR^DU9kze!9tG*ZR-?>Gk(0h~Ur_LuuC!RN^?~PE{rxq4*c7?!xfz?mt?!J1s>u$nD zzM|h-UgoShX*oqW;s~Ej!3~28EljdE?f-0U+}{veWd1N{eydc?tCJIz)Mp$yU2wpF zd1{1nThQe4zIWx~cl~>}HmfHrRBqYPv2`k6ftkB{_VHU+Yz&N8Vz%ylDAjnyede05 z#_PceJ6L+|1)Sd&em3jjx0f~sA2g2KR+(VMvP)OduCL{VT<~Y+f|oUn%*&I6mrUb} z28KFIvZr$Z4=)2_9`ob(K)yw4glC$sFM}44&B4Ifp2@%hWHAD<6c95oFfCw$ix@0m zMzBGWKmPlf0Ts{A42dX-@b$4u&d=3LOvz75)vL%Y04ZRwsjvbvb5lza6)JLb@`|l0 zY?Z(&tblBgu)dN4SV>8?tx|+t?VyL%(9@GcP=o{)8=)=thYPA80S_NcQ zq~=7pWag&k6$96K38+RJeUS5!yaNdQ zmCSv@7Z?})o-U3d8LV$F9pr2=100 bright pixels, got 0", + "focusRingBrightPixels": 0, + "focusedCheckbox": { + "description": "Select [redacted fixture title]", + "focused": true, + "position": [ + 335, + 238 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "0" + }, + "mode": "mutant", + "pid": 84587, + "selectedHeadingFound": false, + "status": "failed", + "windowId": 29941 +} diff --git a/pr-6368-native-evidence/mutant.patch b/pr-6368-native-evidence/mutant.patch new file mode 100644 index 0000000000..94f2c85596 --- /dev/null +++ b/pr-6368-native-evidence/mutant.patch @@ -0,0 +1,6 @@ +diff --git a/desktop/src/features/projects/ui/ProjectEntityListRow.tsx b/desktop/src/features/projects/ui/ProjectEntityListRow.tsx +--- a/desktop/src/features/projects/ui/ProjectEntityListRow.tsx ++++ b/desktop/src/features/projects/ui/ProjectEntityListRow.tsx +@@ +- "absolute inset-0 flex items-center justify-center opacity-0 group-hover:opacity-100 group-focus-within:opacity-100", ++ "absolute inset-0 flex items-center justify-center opacity-0 group-hover:opacity-100", diff --git a/pr-6368-native-evidence/native_journey.swift b/pr-6368-native-evidence/native_journey.swift new file mode 100644 index 0000000000..59f122158c --- /dev/null +++ b/pr-6368-native-evidence/native_journey.swift @@ -0,0 +1,455 @@ +import AppKit +import ApplicationServices +import CoreGraphics +import Foundation +import ImageIO +import UniformTypeIdentifiers + +struct Snapshot: Codable { + let role: String + let title: String + let description: String + let value: String + let focused: Bool + let position: [Double] + let size: [Double] +} + +struct Receipt: Codable { + let status: String + let mode: String + let pid: Int32 + let applicationTitle: String + let windowId: Int + let adjacentControl: Snapshot + let focusedCheckbox: Snapshot + let focusRingBrightPixels: Int + let selectedCheckbox: Snapshot? + let selectedHeadingFound: Bool + let clearSelectionFound: Bool + let failure: String? +} + +enum HarnessError: Error, CustomStringConvertible { + case message(String) + + var description: String { + switch self { + case let .message(message): + return message + } + } +} + +let arguments = CommandLine.arguments +guard arguments.count == 4, let pid = Int32(arguments[1]) else { + fputs("usage: native_journey.swift \n", stderr) + exit(2) +} + +let outputDirectory = URL(fileURLWithPath: arguments[2], isDirectory: true) +let mode = arguments[3] +let application = AXUIElementCreateApplication(pid) +let encoder = JSONEncoder() +encoder.outputFormatting = [.prettyPrinted, .sortedKeys, .withoutEscapingSlashes] + +func timestamp() -> String { + ISO8601DateFormatter().string(from: Date()) +} + +func diagnostic(_ message: String) { + print("[\(timestamp())] \(message)") + fflush(stdout) +} + +func attribute(_ element: AXUIElement, _ name: String) -> AnyObject? { + var result: CFTypeRef? + guard AXUIElementCopyAttributeValue(element, name as CFString, &result) == .success else { + return nil + } + return result as AnyObject? +} + +func stringAttribute(_ element: AXUIElement, _ name: String) -> String { + attribute(element, name) as? String ?? "" +} + +func boolAttribute(_ element: AXUIElement, _ name: String) -> Bool { + attribute(element, name) as? Bool ?? false +} + +func pointAttribute(_ element: AXUIElement, _ name: String) -> CGPoint { + guard let rawValue = attribute(element, name) else { + return .zero + } + let value = rawValue as! AXValue + var point = CGPoint.zero + AXValueGetValue(value, .cgPoint, &point) + return point +} + +func sizeAttribute(_ element: AXUIElement, _ name: String) -> CGSize { + guard let rawValue = attribute(element, name) else { + return .zero + } + let value = rawValue as! AXValue + var size = CGSize.zero + AXValueGetValue(value, .cgSize, &size) + return size +} + +func snapshot(_ element: AXUIElement) -> Snapshot { + let position = pointAttribute(element, kAXPositionAttribute) + let size = sizeAttribute(element, kAXSizeAttribute) + return Snapshot( + role: stringAttribute(element, kAXRoleAttribute), + title: stringAttribute(element, kAXTitleAttribute), + description: stringAttribute(element, kAXDescriptionAttribute), + value: String(describing: attribute(element, kAXValueAttribute) ?? "" as AnyObject), + focused: boolAttribute(element, kAXFocusedAttribute), + position: [position.x, position.y], + size: [size.width, size.height] + ) +} + +func children(_ element: AXUIElement) -> [AXUIElement] { + attribute(element, kAXChildrenAttribute) as? [AXUIElement] ?? [] +} + +func find( + _ element: AXUIElement, + role: String? = nil, + title: String? = nil, + titlePrefix: String? = nil, + focused: Bool? = nil +) -> AXUIElement? { + let elementRole = stringAttribute(element, kAXRoleAttribute) + let elementTitle = stringAttribute(element, kAXTitleAttribute) + let matches = + (role == nil || elementRole == role) && + (title == nil || elementTitle == title) && + (titlePrefix == nil || elementTitle.hasPrefix(titlePrefix ?? "")) && + (focused == nil || boolAttribute(element, kAXFocusedAttribute) == focused) + if matches { + return element + } + for child in children(element) { + if let match = find( + child, + role: role, + title: title, + titlePrefix: titlePrefix, + focused: focused + ) { + return match + } + } + return nil +} + +func waitFor( + role: String? = nil, + title: String? = nil, + titlePrefix: String? = nil, + focused: Bool? = nil, + timeout: TimeInterval = 12 +) throws -> AXUIElement { + let deadline = Date().addingTimeInterval(timeout) + repeat { + if let match = find( + application, + role: role, + title: title, + titlePrefix: titlePrefix, + focused: focused + ) { + return match + } + Thread.sleep(forTimeInterval: 0.2) + } while Date() < deadline + throw HarnessError.message( + "timed out waiting for role=\(role ?? "*") title=\(title ?? titlePrefix ?? "*") focused=\(String(describing: focused))" + ) +} + +func press(_ element: AXUIElement, label: String) throws { + let result = AXUIElementPerformAction(element, kAXPressAction as CFString) + guard result == .success else { + throw HarnessError.message("AXPress failed for \(label): \(result.rawValue)") + } + diagnostic("AXPress \(label)") + Thread.sleep(forTimeInterval: 0.7) +} + +func focus(_ element: AXUIElement, label: String) throws { + let result = AXUIElementSetAttributeValue( + element, + kAXFocusedAttribute as CFString, + kCFBooleanTrue + ) + guard result == .success else { + throw HarnessError.message("AX focus failed for \(label): \(result.rawValue)") + } + diagnostic("focused setup control \(label)") + Thread.sleep(forTimeInterval: 0.8) +} + +func key(_ virtualKey: CGKeyCode, label: String) throws { + let process = Process() + process.executableURL = URL(fileURLWithPath: "/usr/bin/osascript") + process.arguments = [ + "-e", "tell application \"System Events\"", + "-e", "set frontmost of first application process whose unix id is \(pid) to true", + "-e", "key code \(virtualKey)", + "-e", "end tell", + ] + try process.run() + process.waitUntilExit() + guard process.terminationStatus == 0 else { + throw HarnessError.message( + "osascript could not deliver \(label): \(process.terminationStatus)" + ) + } + diagnostic("posted macOS HID \(label)") + Thread.sleep(forTimeInterval: 1.2) +} + +func writeJSON(_ value: T, to name: String) throws { + try encoder.encode(value).write(to: outputDirectory.appendingPathComponent(name)) +} + +func windowId() throws -> Int { + let windows = + CGWindowListCopyWindowInfo([.optionOnScreenOnly, .excludeDesktopElements], kCGNullWindowID) + as? [[String: Any]] ?? [] + for window in windows where window[kCGWindowOwnerPID as String] as? Int32 == pid { + if let number = window[kCGWindowNumber as String] as? Int { + return number + } + } + throw HarnessError.message("no onscreen window found for pid \(pid)") +} + +func captureScreen(to url: URL) throws -> CGImage { + let process = Process() + process.executableURL = URL(fileURLWithPath: "/usr/sbin/screencapture") + process.arguments = ["-x", "-D1", url.path] + try process.run() + process.waitUntilExit() + guard process.terminationStatus == 0 else { + throw HarnessError.message("screencapture failed with \(process.terminationStatus)") + } + guard + let source = CGImageSourceCreateWithURL(url as CFURL, nil), + let image = CGImageSourceCreateImageAtIndex(source, 0, nil) + else { + throw HarnessError.message("could not decode screenshot \(url.path)") + } + return image +} + +func writePNG(_ image: CGImage, to url: URL) throws { + guard + let destination = CGImageDestinationCreateWithURL( + url as CFURL, + UTType.png.identifier as CFString, + 1, + nil + ) + else { + throw HarnessError.message("could not create PNG destination \(url.path)") + } + CGImageDestinationAddImage(destination, image, nil) + guard CGImageDestinationFinalize(destination) else { + throw HarnessError.message("could not write PNG \(url.path)") + } +} + +func brightPixelCount(around element: AXUIElement, screenshot: CGImage) throws -> Int { + let position = pointAttribute(element, kAXPositionAttribute) + let size = sizeAttribute(element, kAXSizeAttribute) + let displayBounds = CGDisplayBounds(CGMainDisplayID()) + let scale = Double(screenshot.width) / displayBounds.width + let padding = 6.0 + let rect = CGRect( + x: (position.x - displayBounds.origin.x - padding) * scale, + y: (position.y - displayBounds.origin.y - padding) * scale, + width: (size.width + padding * 2) * scale, + height: (size.height + padding * 2) * scale + ).integral + guard let crop = screenshot.cropping(to: rect) else { + throw HarnessError.message("could not crop checkbox at \(rect)") + } + try writePNG(crop, to: outputDirectory.appendingPathComponent("\(mode)-focus-crop.png")) + + let width = crop.width + let height = crop.height + var pixels = [UInt8](repeating: 0, count: width * height * 4) + guard + let context = CGContext( + data: &pixels, + width: width, + height: height, + bitsPerComponent: 8, + bytesPerRow: width * 4, + space: CGColorSpaceCreateDeviceRGB(), + bitmapInfo: CGImageAlphaInfo.premultipliedLast.rawValue + ) + else { + throw HarnessError.message("could not create pixel-analysis context") + } + context.draw(crop, in: CGRect(x: 0, y: 0, width: width, height: height)) + var count = 0 + for index in stride(from: 0, to: pixels.count, by: 4) { + let red = Int(pixels[index]) + let green = Int(pixels[index + 1]) + let blue = Int(pixels[index + 2]) + if max(red, green, blue) >= 150 { + count += 1 + } + } + return count +} + +func writeFailure(_ message: String, adjacent: Snapshot?, focused: Snapshot?, bright: Int?) { + let receipt = Receipt( + status: "failed", + mode: mode, + pid: pid, + applicationTitle: stringAttribute(application, kAXTitleAttribute), + windowId: (try? windowId()) ?? 0, + adjacentControl: adjacent ?? Snapshot( + role: "", + title: "", + description: "", + value: "", + focused: false, + position: [], + size: [] + ), + focusedCheckbox: focused ?? Snapshot( + role: "", + title: "", + description: "", + value: "", + focused: false, + position: [], + size: [] + ), + focusRingBrightPixels: bright ?? 0, + selectedCheckbox: nil, + selectedHeadingFound: false, + clearSelectionFound: false, + failure: message + ) + try? writeJSON(receipt, to: "\(mode)-receipt.json") +} + +var adjacentSnapshot: Snapshot? +var focusedSnapshot: Snapshot? +var measuredBrightPixels: Int? + +do { + try FileManager.default.createDirectory( + at: outputDirectory, + withIntermediateDirectories: true + ) + let appTitle = stringAttribute(application, kAXTitleAttribute) + guard appTitle == "Buzz Dev (projects-v6-pt2-selectable-workspaces)" else { + throw HarnessError.message("unexpected application title: \(appTitle)") + } + let nativeWindowId = try windowId() + diagnostic("application=\(appTitle) pid=\(pid) windowId=\(nativeWindowId) mode=\(mode)") + + let projects = try waitFor(role: kAXButtonRole as String, title: "Projects") + try press(projects, label: "Projects") + let tasks = try waitFor(role: kAXCheckBoxRole as String, title: "Tasks") + try press(tasks, label: "Tasks") + let listLayout = try waitFor(role: kAXCheckBoxRole as String, title: "List layout") + try press(listLayout, label: "List layout") + + if let clearSelection = find(application, role: kAXButtonRole as String, title: "Clear selection") { + try press(clearSelection, label: "Clear selection") + } + + let adjacent = try waitFor(role: kAXButtonRole as String, titlePrefix: "Open task ") + try focus(adjacent, label: stringAttribute(adjacent, kAXTitleAttribute)) + adjacentSnapshot = snapshot(adjacent) + try writeJSON(adjacentSnapshot, to: "\(mode)-adjacent.json") + + try key(48, label: "Tab") + let focused = try waitFor(role: kAXCheckBoxRole as String, focused: true) + focusedSnapshot = snapshot(focused) + try writeJSON(focusedSnapshot, to: "\(mode)-focused.json") + guard focusedSnapshot?.title.hasPrefix("Select ") == true else { + throw HarnessError.message("Tab did not reach an entity-specific checkbox") + } + guard focusedSnapshot?.value == "0" else { + throw HarnessError.message("focused checkbox did not start unchecked") + } + + let focusedScreen = try captureScreen( + to: outputDirectory.appendingPathComponent("\(mode)-focused-screen.png") + ) + let brightPixels = try brightPixelCount(around: focused, screenshot: focusedScreen) + measuredBrightPixels = brightPixels + diagnostic("focus-ring bright pixels=\(brightPixels)") + guard brightPixels >= 100 else { + throw HarnessError.message( + "visible focus-ring assertion failed: expected >=100 bright pixels, got \(brightPixels)" + ) + } + + try key(49, label: "Space") + let selectionDeadline = Date().addingTimeInterval(6) + var selected = snapshot(focused) + var selectedHeadingFound = false + var clearSelectionFound = false + repeat { + selected = snapshot(focused) + selectedHeadingFound = + find(application, role: kAXHeadingRole as String, title: "1 task") != nil + clearSelectionFound = + find(application, role: kAXButtonRole as String, title: "Clear selection") != nil + if selected.value == "1", selectedHeadingFound, clearSelectionFound { + break + } + Thread.sleep(forTimeInterval: 0.2) + } while Date() < selectionDeadline + try writeJSON(selected, to: "\(mode)-selected.json") + guard selected.value == "1", selectedHeadingFound, clearSelectionFound else { + throw HarnessError.message( + "Space did not produce selected checkbox, 1 task heading, and Clear selection" + ) + } + _ = try captureScreen( + to: outputDirectory.appendingPathComponent("\(mode)-selected-screen.png") + ) + + let receipt = Receipt( + status: "passed", + mode: mode, + pid: pid, + applicationTitle: appTitle, + windowId: nativeWindowId, + adjacentControl: adjacentSnapshot ?? snapshot(adjacent), + focusedCheckbox: focusedSnapshot ?? snapshot(focused), + focusRingBrightPixels: brightPixels, + selectedCheckbox: selected, + selectedHeadingFound: selectedHeadingFound, + clearSelectionFound: clearSelectionFound, + failure: nil + ) + try writeJSON(receipt, to: "\(mode)-receipt.json") + diagnostic("PASS native Tab → entity checkbox → visible focus ring → Space selection") +} catch { + let message = String(describing: error) + diagnostic("FAIL \(message)") + writeFailure( + message, + adjacent: adjacentSnapshot, + focused: focusedSnapshot, + bright: measuredBrightPixels + ) + exit(1) +} diff --git a/pr-6368-native-evidence/restored-adjacent.json b/pr-6368-native-evidence/restored-adjacent.json new file mode 100644 index 0000000000..2af810442a --- /dev/null +++ b/pr-6368-native-evidence/restored-adjacent.json @@ -0,0 +1,15 @@ +{ + "description": "", + "focused": true, + "position": [ + 317, + 208 + ], + "role": "AXButton", + "size": [ + 1921, + 40 + ], + "title": "Open task [redacted fixture title]", + "value": "" +} diff --git a/pr-6368-native-evidence/restored-diagnostics.log b/pr-6368-native-evidence/restored-diagnostics.log new file mode 100644 index 0000000000..dd51cd4bbd --- /dev/null +++ b/pr-6368-native-evidence/restored-diagnostics.log @@ -0,0 +1,10 @@ +[2026-08-20T12:10:02Z] application=Buzz Dev (projects-v6-pt2-selectable-workspaces) pid=84587 windowId=29941 mode=restored +[2026-08-20T12:10:02Z] AXPress Projects +[2026-08-20T12:10:03Z] AXPress Tasks +[2026-08-20T12:10:03Z] AXPress List layout +[2026-08-20T12:10:04Z] focused setup control Open task [redacted fixture title] +[2026-08-20T12:10:05Z] posted macOS HID Tab +[2026-08-20T12:10:07Z] focus-ring bright pixels=732 +[2026-08-20T12:10:07Z] posted macOS HID Space +[2026-08-20T12:10:08Z] PASS native Tab → entity checkbox → visible focus ring → Space selection +Exit status: 0 diff --git a/pr-6368-native-evidence/restored-focused.json b/pr-6368-native-evidence/restored-focused.json new file mode 100644 index 0000000000..4f3fc22b40 --- /dev/null +++ b/pr-6368-native-evidence/restored-focused.json @@ -0,0 +1,15 @@ +{ + "description": "Select [redacted fixture title]", + "focused": true, + "position": [ + 335, + 294 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "0" +} diff --git a/pr-6368-native-evidence/restored-receipt.json b/pr-6368-native-evidence/restored-receipt.json new file mode 100644 index 0000000000..dbadc8dc15 --- /dev/null +++ b/pr-6368-native-evidence/restored-receipt.json @@ -0,0 +1,55 @@ +{ + "adjacentControl": { + "description": "", + "focused": true, + "position": [ + 317, + 208 + ], + "role": "AXButton", + "size": [ + 1921, + 40 + ], + "title": "Open task [redacted fixture title]", + "value": "" + }, + "applicationTitle": "Buzz Dev (projects-v6-pt2-selectable-workspaces)", + "clearSelectionFound": true, + "focusRingBrightPixels": 732, + "focusedCheckbox": { + "description": "Select [redacted fixture title]", + "focused": true, + "position": [ + 335, + 294 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "0" + }, + "mode": "restored", + "pid": 84587, + "selectedCheckbox": { + "description": "Select [redacted fixture title]", + "focused": false, + "position": [ + 335, + 294 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "1" + }, + "selectedHeadingFound": true, + "status": "passed", + "windowId": 29941 +} diff --git a/pr-6368-native-evidence/restored-selected.json b/pr-6368-native-evidence/restored-selected.json new file mode 100644 index 0000000000..9686d4c855 --- /dev/null +++ b/pr-6368-native-evidence/restored-selected.json @@ -0,0 +1,15 @@ +{ + "description": "Select [redacted fixture title]", + "focused": false, + "position": [ + 335, + 294 + ], + "role": "AXCheckBox", + "size": [ + 12, + 12 + ], + "title": "Select [redacted fixture title]", + "value": "1" +}