From 2b048123202725cb1c5e62a58da6c0d5a852f800 Mon Sep 17 00:00:00 2001 From: Rodrigo Arias Mallo Date: Tue, 11 Feb 2025 12:56:30 +0100 Subject: [PATCH] Add new fox machine MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Aleix Boné --- flake.nix | 1 + keys.nix | 3 +- m/common/xeon/net.nix | 4 +++ m/fox/configuration.nix | 38 +++++++++++++++++++++++++ m/module/slurm-client.nix | 6 ++-- secrets/ceph-user.age | Bin 1002 -> 1023 bytes secrets/gitea-runner-token.age | 16 +++++------ secrets/gitlab-runner-docker-token.age | 17 +++++------ secrets/gitlab-runner-shell-token.age | 16 +++++------ secrets/jungle-robot-password.age | Bin 477 -> 477 bytes secrets/munge-key.age | Bin 2007 -> 2006 bytes secrets/nix-serve.age | Bin 641 -> 534 bytes 12 files changed, 74 insertions(+), 27 deletions(-) create mode 100644 m/fox/configuration.nix diff --git a/flake.nix b/flake.nix index ca0a530..037bba2 100644 --- a/flake.nix +++ b/flake.nix @@ -25,6 +25,7 @@ in bay = mkConf "bay"; lake2 = mkConf "lake2"; raccoon = mkConf "raccoon"; + fox = mkConf "fox"; }; packages.x86_64-linux = self.nixosConfigurations.hut.pkgs // { diff --git a/keys.nix b/keys.nix index 681fcbc..a2b8c2c 100644 --- a/keys.nix +++ b/keys.nix @@ -9,10 +9,11 @@ rec { koro = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIImiTFDbxyUYPumvm8C4mEnHfuvtBY1H8undtd6oDd67 koro"; bay = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICvGBzpRQKuQYHdlUQeAk6jmdbkrhmdLwTBqf3el7IgU bay"; lake2 = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINo66//S1yatpQHE/BuYD/Gfq64TY7ZN5XOGXmNchiO0 lake2"; + fox = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDa9lId4rB/EKGkkCCVOy0cuId2SYLs+8W8kx0kmpO1y fox"; }; hostGroup = with hosts; rec { - compute = [ owl1 owl2 ]; + compute = [ owl1 owl2 fox ]; playground = [ eudy koro ]; storage = [ bay lake2 ]; monitor = [ hut ]; diff --git a/m/common/xeon/net.nix b/m/common/xeon/net.nix index a5d87b6..ce1d3bc 100644 --- a/m/common/xeon/net.nix +++ b/m/common/xeon/net.nix @@ -85,6 +85,10 @@ 10.0.40.8 eudy xeon08 xeon08-eth0 10.0.42.8 eudy-ib xeon08-ib0 10.0.40.108 eudy-ipmi xeon08-ipmi0 + + # fox + 10.0.40.26 fox + 10.0.40.126 fox-ipmi ''; }; } diff --git a/m/fox/configuration.nix b/m/fox/configuration.nix new file mode 100644 index 0000000..38d69be --- /dev/null +++ b/m/fox/configuration.nix @@ -0,0 +1,38 @@ +{ lib, config, pkgs, ... }: + +{ + imports = [ + ../common/xeon.nix + ../module/ceph.nix + ../module/emulation.nix + ../module/slurm-client.nix + ../module/slurm-firewall.nix + ]; + + # Select the this using the ID to avoid mismatches + boot.loader.grub.device = "/dev/disk/by-id/wwn-0x500a07514b0c1103"; + + # No swap, there is plenty of RAM + swapDevices = lib.mkForce []; + + boot.initrd.availableKernelModules = [ "xhci_pci" "ahci" "nvme" "usbhid" "usb_storage" "sd_mod" ]; + boot.kernelModules = [ "kvm-amd" ]; + + hardware.cpu.amd.updateMicrocode = lib.mkDefault config.hardware.enableRedistributableFirmware; + hardware.cpu.intel.updateMicrocode = lib.mkForce false; + + networking = { + hostName = "fox"; + interfaces.enp1s0f0np0.ipv4.addresses = [ { + address = "10.0.40.26"; + prefixLength = 24; + } ]; + }; + + # Configure Nvidia driver to use with CUDA + hardware.nvidia.package = config.boot.kernelPackages.nvidiaPackages.production; + hardware.graphics.enable = true; + nixpkgs.config.allowUnfree = true; + nixpkgs.config.nvidia.acceptLicense = true; + services.xserver.videoDrivers = [ "nvidia" ]; +} diff --git a/m/module/slurm-client.nix b/m/module/slurm-client.nix index 7b2acb9..d745310 100644 --- a/m/module/slurm-client.nix +++ b/m/module/slurm-client.nix @@ -43,12 +43,14 @@ in { clusterName = "jungle"; nodeName = [ "owl[1,2] Sockets=2 CoresPerSocket=14 ThreadsPerCore=2 Feature=owl" + "fox Sockets=2 CoresPerSocket=96 ThreadsPerCore=2 Feature=fox" "hut Sockets=2 CoresPerSocket=14 ThreadsPerCore=2" ]; partitionName = [ - "owl Nodes=owl[1-2] Default=YES DefaultTime=01:00:00 MaxTime=INFINITE State=UP" - "all Nodes=owl[1-2],hut Default=NO DefaultTime=01:00:00 MaxTime=INFINITE State=UP" + "owl Nodes=owl[1-2] Default=YES DefaultTime=01:00:00 MaxTime=INFINITE State=UP" + "fox Nodes=fox Default=NO DefaultTime=01:00:00 MaxTime=INFINITE State=UP" + "all Nodes=owl[1-2],hut Default=NO DefaultTime=01:00:00 MaxTime=INFINITE State=UP" ]; # See slurm.conf(5) for more details about these options. diff --git a/secrets/ceph-user.age b/secrets/ceph-user.age index f23e2ff0558e216abb9940ca7ebc26287849466d..880fbbf33f23b68b298d1efcfde58e2581d46ba7 100644 GIT binary patch delta 936 zcmaFG{-1qe?v1dqVgs)F|VN|(kc5-%ZiCboIcwu6yexQGdOQBh5UZQJQ zR<@C0M81GgPPv(3hGmY)WxiqF1(}suK~X8jzPTQTQIWpcp5eaQCh3k`z8U(Z zNigsU?x#p1#IaF6GX7E~UO6KIXaZzFFSIIT>ad>E(`-;~B-n(=APk%zdLg zolJuY%Ca+yvoey+^}U@evh&K*1N?%`9P>>olM2gx%$z*A5{tu~qTCIVLj!U`%*u<3 z^MVrn%FA7iQ#`WW4J#|7vdmIV-9mzV3rk!lpJf!U_tbVa$qe^)^A9d?t*k69H#Vt^ zDk!P&^365#Ov`uA4K>%V@U}1rPsw!T3a#>p@-7Ups3=T~a5lCGH1RLbsPym+GWB;a zjLHnj^h)>eOAE;jHgonwj{)rv*Rb$F1;Yr}Aop_1ob>$Md`II-FR%Iv^YlEAFwZt7XA9T^qwrSItC6KKGttE;Qv zT3MLx6Vd<=2 z3z%OqtTA?F_9{bKJN8}z?4&*N%&W;B_t@xrnad0S4qsI$6~7ab=Y+BD@^ W)3(hrFZtAL!abK?l>NcIj28f9#X8sk delta 915 zcmey*{)&BqPQ90bL84ide@1p`L3V~usA+hhLAHy5sfVkZiMMxgaIsNFd6tKFQeK`% zD3_O^Nm#z0zjL8aL2z=Izq!9pL{ec$vX7@pNpe`IM~P{2VWfUUU~ZCoF_*5LLUD11 zZfc5=si~o*LUFodVy>e?wndPBQgCQWSy*n4lc!mwhg(3Vsh?9|fRnqgu~|-lS9x(} zk%fz!dwPW{mr0bjvvGQ4S!S}CV_1=&d%9m%c~wbLXjMi6m^0SNF zJ@Z2ge9{6Uvpj<;48tsqid>B|qQVW0^Sn~iv~!HJodVOjd{VOOJ#Ze51;;^OCuIJzT;ovO>#EQv5QV4Kqx9i$X0+y}gq?jf={&D;%A24YW<&B7LK> z^Rq$L)mh|Po2Tif7o{c^r*h@Ec$Vhmq&Zt!1Z5P2M49+zTbPHWXor;qPnc$cP!X6J^P7MX+=rkGc{YMa(O7CD-wW*6ymx$8%mxH@v_>gp;uSD6%-Sw@xS zIVFdsL^4T8I3Rwi!m{$uh1aeu3;)$$_GJ?=kGm0l!M9KQq}t0z-}t!p Oii)dPl=!Z=un7P?#yQ3S diff --git a/secrets/gitea-runner-token.age b/secrets/gitea-runner-token.age index 1c799cf..31d52cf 100644 --- a/secrets/gitea-runner-token.age +++ b/secrets/gitea-runner-token.age @@ -1,9 +1,9 @@ age-encryption.org/v1 --> ssh-ed25519 HY2yRg DQdgCk16Yu524BsrWVf0krnwWzDM6SeaJCgQipOfwCA -Ab9ocqra/UWJZI+QGMlxUhBu5AzqfjPgXl+ENIiHYGs --> ssh-ed25519 CAWG4Q KF9rGCenb3nf+wyz2hyVs/EUEbsmUs5R+1fBxlCibC8 -7++Kxbr3FHVdVfnFdHYdAuR0Tgfd+sRcO6WRss6LhEw --> ssh-ed25519 MSF3dg aUe4DhRsu4X8CFOEAnD/XM/o/0qHYSB522woCaAVh0I -GRcs5cm2YqA/lGhUtbpboBaz7mfgiLaCr+agaB7vACU ---- 9Q7Ou+Pxq+3RZilCb2dKC/pCFjZEt4rp5KnTUUU7WJ8 -1Mw4 :H@/gLtM,ƥ*zNV5mNoj1 $TG_E{%1ǯHAp \ No newline at end of file +-> ssh-ed25519 HY2yRg eRVX5yndWDLg9hw7sY1Iu8pJFy47luHvdL+zZGK2u1s +e1nXXiMW0ywkZYh2s6c7/quGMfBOJOaRhNQDjCD2Iyc +-> ssh-ed25519 CAWG4Q gYG7GRxRpJ0/5Wz0Z0J2wfLfkMFNmcy81dQEewM7gUA +lamdUdx+xOFWF1lmUM4x9TT0cJtKu9Sp7w9JHwm13u0 +-> ssh-ed25519 MSF3dg HEzfpR8alG6WPzhaEjAmmjOFoFcMSQUldx46dBsXri4 +OAD5H/zZGhfevYrFJzJrbNKPomKZDOS9Qx5tmTp78Jo +--- A0sMSiNXWaEIgRXR0x6UAIaluuVH6Zlv4CJ9sI0NXOw +6ph{>F|iv E}{ruƷ}^>c6j gGW:J3||Z \ No newline at end of file diff --git a/secrets/gitlab-runner-docker-token.age b/secrets/gitlab-runner-docker-token.age index 103d6a6..cd1432e 100644 --- a/secrets/gitlab-runner-docker-token.age +++ b/secrets/gitlab-runner-docker-token.age @@ -1,9 +1,10 @@ age-encryption.org/v1 --> ssh-ed25519 HY2yRg 0sEIUEJBJQ0k0rBfHaOEbq1pNBqsPin4Xq85v0ds9jY -4wzjLapoOcq53nT2K3hSGED4jTDXci25GLHkl/fL4EI --> ssh-ed25519 CAWG4Q f68ZbJGwXuCZVnqhwbh+8dh0X/MCdjEd+sVtPyBu/hU -u2TQreyWQvP6PGuwuUNKA/AL68560flqSlaItN3k41I --> ssh-ed25519 MSF3dg HdrtRW2j7mfkLH0/4aJK5R0cWdjf56HYtEZgzHi9EAs -A6MF6tXmSUq2RF2bpmav0GFTRERwluSZGh2snP/KqkA ---- drsezqi7J/g8gm6N10SkfeAWnYct99WUraB5djLJqpo -g (J!M63eA?\1yeFN\/MN`K^+"Y^>dH]PJ`x{ڱySyPX{wS ^5XJP;v \ No newline at end of file +-> ssh-ed25519 HY2yRg GdmdkW+BqqwBgu30b846jv3J7jtCM+a3rgOERuA050A +FeGqM75jG9egesR+yyVKHm0/M+uBBp5Hclg4+qN0BR8 +-> ssh-ed25519 CAWG4Q a0wTWHgulQUYDAMZmXf3dOf6PdYgCqNtSylzWVVRNVM +Bx+WSYaiY4ZwlSZJo2a1XPMQmbKOU7F0tKAqVRLBOPo +-> ssh-ed25519 MSF3dg KccUvZZUbxbCrRWUWrX8KcHF6vQ5FV/BqUqI59G7dj4 +CFr7GXpZ9rPgy7HBfOyiYF9FnZUw6KcZwq9f7/0KaU8 +--- E0Rp6RR/8+o0jvB1lRdhnlabxvI6uu/IgL2ZpPXzTc8 +#H$F;%62rfX\Dn шȉx>&;cUI=M?TǸ"pxӭ\sbFWD{ +AW>?UHԳ \ No newline at end of file diff --git a/secrets/gitlab-runner-shell-token.age b/secrets/gitlab-runner-shell-token.age index aaf939c..7c718fd 100644 --- a/secrets/gitlab-runner-shell-token.age +++ b/secrets/gitlab-runner-shell-token.age @@ -1,9 +1,9 @@ age-encryption.org/v1 --> ssh-ed25519 HY2yRg VY8s9s1zuHOv2axmIacwKg2ozsJnskHTQtslRZ3YI1M -fKkJuydLOzF/ciPYSYu4ziSCozdl6sowvDMYZmxqmHY --> ssh-ed25519 CAWG4Q 2ARFd/7RWQ/QOk47FnJFChaVBgoV4LE6EA+JHezkXgg -MV4g4Llv8Qcd/wUgJyoNG5AXb6o3aFTrOYGC+lXlSzw --> ssh-ed25519 MSF3dg SKoxWe8Mi8EkBjkESxStOCI5V4C0KYEXIOx7OdENgTA -p/owKwQ4e4pcGV+hqej2AfPU5QaM2i8VfxhlkjCM4Z4 ---- 0VWKU5CQiGbiOtQ2tsZZg88oZm1qcUDEnU5zDTtV+KU -ucl`M'Vk6Y!=Ly-OAzƘVEKR_qL|1V[)qƓLDy0_q)-T,ƪ_9 ?ib1 \ No newline at end of file +-> ssh-ed25519 HY2yRg xWRxJGWSzA5aplRYCYLB6aBwrUrQQJ2MtDYaD75V5nI +J07XF3NQiaYKKKNRcNWi9MloJD2wXHd+2K7bo6lF+QU +-> ssh-ed25519 CAWG4Q jNWymbyCczcm8RcaIEbFQBlOMALsuxTl4+pLUi0aR20 +z5NixlrRD+Y7Z/aFPs6hiDW4/lp8CBQCeJYpbuG9yYM +-> ssh-ed25519 MSF3dg QsUQloEKN3k1G49FQnNR/Do6ILgGpjFcw3zu5kk1Ako +IHwyFWUEWqCStNcFprnpBa8L5J6zKIsn+7HcgGRv3sM +--- oUia0fsL6opeYWACyXtHAu/Ld+bUIt/7S1VszYTvwgU +V*t2-7h&͢_!տ+(n (/}CNͷ|Nu5ù勚Kl"klOXyAe$ \ No newline at end of file diff --git a/secrets/jungle-robot-password.age b/secrets/jungle-robot-password.age index de9bf22ab4a215dacd44608e30f8f45b8b8c8cb7..7b8cd84284e84acf2ffa496148466fc590495dc0 100644 GIT binary patch delta 423 zcmcc1e3yBGPQ6=&fw5_&t6#8-r?$SAbEsFUai+FkRz$gDL`aBPW?r7VWr}aAg@2y0 z1($!Nho_OBL5P8yacYWVNM*WvWVuhScdDzee`ZQquy$H%Mp0%_X^~l&E0?aFLUD11 zZfc5=si~o*g0o||yGfuzh>L%+pL3SJg?UD$cU7pqgS-Ua2!rT#&oA))CW1sMS)g<-)NhW`2`5mhFR<}PU-fxeNYNg)^6 zULIcVDLKg@SsAXCx%nm)ex4P^j^UZkj#ZXnrDb`RPR_}ZTx|dOCi!`4+pV0;uvXLR z@I3Z)f1M0nmaH=@{%~z}z`_O74g7Rngy%0{+oyS7YQeqTFWKv5r<`lu+2#Jyqf24C T5l2f4=Zi=BxenCN&exSw;C=y1KdwJ{h6e`2~I@ z&c&4;&OTMHkyTD^#oA@5+5Xv%K_*VdVNQu*nZ9oNQEnFHT=}QxwqAd*`;c?feUHZv zAN>4VIbGW4#uU#I-xpV(ZuPvrQ9`KLSLj&GSwr28-cvdRmUOyX)qkBS%rtiy*WGln Thr4bj6}auWyzQ)NQ0DMNnQe?UTS(-l)h_XVxV(+Ub?Aextp7jZ&9ZmS=Iemy<_kMOt27il3vSkBfh1MPOq7 z#E;_P!LHe9o}RgxktW^+X~u~@hEW;Lj^UNs+Kwd_PF4N}W)&vsu7*x-l{wj5=E;#> zDG}i%RhebsL74%*720LSKH(X@-hs}p{$2%XMH%kluI^z@QTdUR;~B-n104%oe0)>W z&D?WJ9i3cCaxIFzJS+TClMTErLxMt#jWb=0U46p6^D{lUObc>zi~R!)JqwG%%ZiEv ziZcwe{1Zb>ydy#j0>WGk%9Dc3JuAHn@>~rjpJf!UcQW%2D$4W;42(*O2r7=$4@)*o zD|B)8G)~E|Fpf$~ad-1{FGM zvJl6N%&bDcsM74HfN=9*PcGlG^ziJm0E1lP6yu7hic*UzQ?Jb6s-n#N;Ph1g%z`A} z2=9;x%gRU>S9I%~9mCyC0u@qS49YXJD?Cio3tT+2!$VB6wDa^+48678Bhr1%GK!r- z>%+sGN(-}#!d4t4R%E%5em4f81S zugK>LHO$B}2=J^gj!bna!WQS%P?}R3^(%R($&>f zNXqpnG;lMpH1^X^_DxT7O^zt43et8=&Cd@s3Qlq?u}DnucP|Yri^xyrGUMOdYu8;W zcJ6;&n!$o4v#-d`)9zhsaCGUJ%a$jZ9fJNw&zdqjq4rnAwfcqXFHEd{8^uqWD9u;I z`oemaU>bmEaC&s_$aOzEcE7ONj@_z() zg#QL+%yBvGn6+<@W1mUCRjuQOg~v7Juf6*ED6G?P&lKAphl?9@nLfnst>pRWa*=V~ z;-joT-G8i7Ex361w5-Tifg|E&bvp~f9-h#dclyIiA?q#s#6OB3-SBhK@d*m`yH2tl z5J;@rk~HQ2-B+h?YxBpyc(;b{Re(Xmvpuss=Er_GH!D1N(aJQ%=$2!DqQBqWJ*Ab4 zMKj$jWXiS6QBvnhz8&g45+qR&)Mpg5^j7NQO0}v~f$raPdP^C&tG4og$emN^dUeJD z9>sNM`KG!lUNCRvXXQQacU@;A%MU}oH7xZ~>8DGZE$<1)UjG}vA*!V*2)o59ew(sTE)oTiJIxWsgPARo!Y%tRMbS|X9=oAyDtxR#yLQSKw5(^%S*xjB8?7zaxmoF=i_GGGO9H+zsXY!#`IKJInT5uiN*)qkhdDe>~kq#`PR$Bv41w<~Ie%)z<-j-G^1;bTbavH3QCj8}o zbNFS0_GRDYLN$}3IpY1F-71{DVMEHjbla_O{3S2ew$aHA?*J3QvJ$l=bzo{Ph5LOa_X!t(X&6ViWNBEyn5EunVV;BWKAypdtmv# z4`*&&D=AD)T$yu2n1#n>&vJ_szn49_aBD?Cf^!Pr>7R#f<5r#d@UT(msH<#J$@#mC zd4Wkh?rL9~CqInV3Vig|2m=VmF}GbSC6jHkruEv{ae^n+I3DeK*slW($=%< aFHSkdqO?m-h;!#8|L${N_m`~YHwFOQQYc#h delta 1927 zcmcb{f1Q7VPJMobyQyhvN?BH7mb+!DaYa%}WVyMaQLbBFm~&cckx5}`PN{FcvA>0f z1($JFmXmh2c5s@hnXj*bX=ftW1&~1yFqDWKvGaZKt@@%wwtqOiltd$ctLo!V@SGzhkH_y zsgYYyZm6>fmy1W0TTZ2Oo}r7Wsj-)Np+TsTp=YJ9qlbQ2qHnHGWMqC$NoHAzc0^+6 z#E;_PRYA^Gj{XH%W!@nn+J%{siKd<=ZpB3rRhcQJ9>(GR&R(U3QO4$lK6w^gW~rX# z$)$P8;Rc1dzB%PCC3!hM?&XeI`j%ff(_iWEle_ey^9M>e0*KPLK8DhQk~5!jjKYrO1%orQmc$plRf>k3oU|* z%k=a8tD?dj-J|?0-JJ4+4FW?mf?Y}yT}=WfpJf!U5A(=QH?VY!aPmxxEC}>8%8Sg5 z^a#nR$Z^SVF)?y23Cj&Gj?(rH3Cu|6DvR(jFv~D3ax70X$ThAobj{9kbT=&XH_x|l zD~k**DGN_2D9g^Us0M6y zNV6h;&+L-O;s~RPkesNHbS_`N)} zAlx{}y)fA)+|xZIr^qBJGBr1}KFhb=XJS63k{Sl_fr+chdQ$tc6vwLB=oC^glwJh8+z*U3C8yU?;MIp563G1o6Q zGo33+`cmp7i$2|H@*P!ik1p}wQfvy|@b|T|$D0oe=H-@MtD2{K_<}?92HAQa+4Fqc zSc92vx=oZ;KjwXy;kMoS>vQ;B%fsH=tbY=cz;kXv#m0h_GE)=&-*N4^v%vGd>XxZD zWW>GHuh+h?j&fo8e6M-#k2eC6MwtiqM6d)Ie7e7G8LzKuntxvp^XlS=)!7mkS<`>& z|9a-I=)05hgZNJ_75W>Vxh~`^zW2AIsGhZEW%M-<)kfXZEa%$z#eUY#53JV}eqzPh z=KMR~!HA)Vo_`hx{|F-LGSRimJ@mrB)vqS`zkkFZ)fy{!^1aeHAL= z*>ychVDc9|-9XlNuPwga;pVi`{c+;pyZ_s^n1(MgD#%_@@lE-I&Kj$4Ix{SL-#(jv z?MmUT*TEk=gSXkNcQ^60>vnn_>RHlo+}cZ->yl{o zD%NV>ZE=^AcUCX-sb@Fe!t$c}yx-l1#R``+P5D(Ul4tN+`b_WMcyeb&;#To3r_MeK z$lf?pBz~Sp=tY-`$$OJ79nUz?C>3FT;a`ownMvBaJ{oE7%?r#YeAwhR z=+2)u-Qdl~KEVqQJ2@+q(IR*v1j=JAVgJ9+^k(XUUYTslcm@l@5-OJ||+Ms+O!epm-ajx7wZ4ZsK zx;^dl-#hECcy)QgwKoRO6V?@c-mP_e8~21`YH4goraWhVzF3Fz;QbG3jPX0`{;0+u z*kIo`VeV|{rX?%cI9mAc>(1ZweP{KVg`1Pk@NP*8j%GL5#Nw~{Ve6-N`~|@AlWF{&Ck_4xFXcg$Slbuyez`c!!p0bBP%DWtjt$GpwJ?}$T=vV zD=Wp()5jw-+t@HQ%Og3}J0+mVr7SDkpu*5QJ=njv%&a6gBQm41I432POV>`JxHv;M zHO0u()X-AF*)iPRBv8T8K;J*R$UG=i-^nj0-5||1%2hwKAWB=?EITWt#6Q&8xgx+Y zvDCRJz|fT|J)_($Kiw=cF(e?zCDb+Fv^1rs+^oCeUJJA?Q{dDqU=bnWA{(aIUibDc_)ZjP4Je0 zV(Y}qTOLhzmfd#dWSQ9I=n&!ji`?}IYUN^l=GTrtUHW;$^@1{AfeS~kY(Dx|>Bh7e z;npA5Tw5~^9LVcw7PHyqSHHHs!O)SOxXDjM_D&Ap&$(Wcr!PG3f9J>r cg=H_EX$j<(&;I-O75me@?8i2Gy;M1& delta 587 zcmbQn(#SeNx8Bgi#6>%-tRf>a-Mhp?U%%AFsL-!8EH5&`EGfg>B(gBO($_dD%c(q+ z%fK@=EZ5C3%_P(!IM*P>z|h|;s@%&k%qS~IKR4Jn$E4iNz&F6ur^qv%OV>`JxHv;M zHO0u()X-AF*)iPRBv8S_B+t8|G*#a@OW)W#)XmgU+f~0Z-NQF4%dx0Dy}~%yGrT+^ zxzMeoGBlsdB-_-_E88cus5I3lGBY5%$jHaBJkTdRw=~h;v)Cm!Oy9z+D6y;{CpC29 zNAY@(g7i>FHxHkHVv}-%{!Ez%={3$k+b6U{s;EVa`u>qEWrLJD#WqdfHUOOw-rEDQ|G(p)Vn&COlH zjJztU^dr2=t12QZyxmQ?B3&~wL)?A+k|N6W!^~Yx6T^b5%$!n^xpZ}P72HcQJ-nTx zQaqe03oWw@oPvE)OifGzGLl@&L;MVlEnF=^+)^qs3sN&3xt8u<+}(25T_t$ep6ccx z$7cujg=EC$9kJ-u`ROsI_{95Lwgr1;-c;Y+`$hYUc-Gg;UwbS!YJRku!mKGeamSp< zNB=HbZ1%kI)xs)2r}y#{yTe(BT=h4kM d%g)V_kduCJHS|}pp_%mYeG7ehlD@Cl1OV#6+5P|k