From 639544adf888284b677604a5f04a9ea2978ff8c9 Mon Sep 17 00:00:00 2001 From: wavemotion-dave <75039837+wavemotion-dave@users.noreply.github.com> Date: Mon, 31 Jan 2022 07:34:09 -0500 Subject: [PATCH] V3.1 : 31-Jan-2022 by wavemotion-dave * Now using more VRAM for bank swapping and partial DMA transfer to speed up large games. * Reverted part of the sound core to improve sound quality. * File selection cleanups to scroll less fast and be generally easier to see. --- A7800DS.nds | Bin 390144 -> 390144 bytes Makefile | 2 +- arm9/gfx/pdev_bg0.png | Bin 3105 -> 3057 bytes arm9/source/a7800utils.c | 100 ++++++++++++++++++------------------ arm9/source/emu/Cartridge.c | 33 ++++++------ arm9/source/emu/Database.c | 3 +- arm9/source/emu/Memory.c | 17 ++++++ arm9/source/emu/Memory.h | 1 + arm9/source/emu/ProSystem.c | 2 +- readme.txt | 5 ++ 10 files changed, 96 insertions(+), 67 deletions(-) diff --git a/A7800DS.nds b/A7800DS.nds index 1d24e1698af59fe8b88b2eb1024cc2c18075ca1d..74d23dbe8424fbfc7042f61a0a4ddeb325f0f2dd 100644 GIT binary patch delta 27627 zcmbt-33!vm*8j}p&C+yBH=6G0LR+9fTFMTRvXoUVn-oL|f&vO!uqrB=0%aAX7<3SU z1_TASTV)9b>9p`JU&4=f}*PnK^Uj%*>fH z^S*DWI2T`WF1{*HBzIcdhGJ9s9YZPOVpq&{rKF?WUJ1AzWMG5_C+V4U%7lNnF$q!x@J1)TT*bmkM=LVRLX=Xi0hOS~W&#fe6E zIyGJ#b=}CPGK8`gpRja@7ySV65?^V!Sk)ca!$O5c&&7;+Q>U!IYgfyNANBlB`=#+d zUSYp2HBguPwqP2$Wj`)#EKwxmI+Pbv|pc`X)}vzPX(sbB-6K^iKu#q z;aiU=TR+$|! zin%sUi?j~u*_c^EH`c9~9d^*4#Z=uOFo1}AIP$sKVT;kAf&~d=#Bhi>1p-t+$%^44 z4>Q!eDgQ1ArZd%ggjt0~Kk`)MS9?N`W`-jkEArI!OY7C3Po+4RLx2mK`oLh7qU@+c z)t*RZKc{7{onsZ1o*MHft_Y}t=hz(Xe!SZA?g*NjG}T7Cb0IZ17d2?1M3qU?fGKB( zq>E{>As%BW!l;{;GzinudSMz|F9LLwQ7vMqqdvH_zCCy-CWlK^f5@%W-_j6Kzp7p_ zk7`iZE>8p->r&XFGuM2+M3v2a2rGE3D-;z}R`kMj@~p~KdzPCPH*hw_rDm+7V5iRt zGo{D61gk~<>7FRlbCs#uQ^~45yRQ2hIdiyokX2ZC;G94w)MkeYYF2Oe`ScuVO)$L$ zrXb9Wo}(>p8Qfq~mmp&L{EQmRx#^6Dq&kN}A}~Jw@mvQQjboM1w{k7=`UTewt&Lo) zmr|@tT(s`lIpQ^TrC8a(K!7Gp|g ztR2iy2=ecSxngAw7Y&7iJfcMgP1Nr&aUo_~z;~l! zmcg!C9j+AcwUwB${@HjpvtYSd7GnsGUS#&dlpPsrs>Q#Mko#hg+|AxGU1DJwG(P-zX9tZXV)rmm}Q}Oly!o6Y1}QX@UI7 zNPmrVnFT8Xbs|t^6lh;Gy?>#`aKdFqoH5(f2BvekOaK-944KTd&ci#5X+Yz>!eBf| z0LoK=sW2_B|KM+B&S9IPGQw0@Ph}3EQA*RKqk0@#+V{6QyPM5=I` zg3S|J;2p*`l-Wm5i?NX|%1ToL78AVyRS0VkAtf}x#&x7)%fbd``rPBQD6o-ZT%hZi z=~>LkBOXON#-+sfgw!+}w4>c)VG|SM7B=t>7-e4V(HIvt9EJ2+%Lg8m!9d+$-pl^P z^fVi>qRGp3W8B@a3He$6$#JZ^fU!Q!qzB9snma1fqWXp4=*CJqhoMrzBv9*hh-)p( zFY136GazNFbTwGbkS?TQ1DMr;nf>&1qisI8P-p))9IOEj4NKbg&#W}4pcGZG2Z?dm z8=#AiDr`Q+@?MJ;d84BJqd6U;3H$6) z%wKqDB)h;sC6MYc#Z=hopoZmx)9vrvojRVGTeUjY-Pf;GY;0|`+6P)yu*%wMH63z9 z(e4b^U}dZi>H?c!; z)JZOCUPS*}>7_w>2IxP4ZV9$TmW5jK{_%ceJ?JVE=8_is?%#Bs9IPLW`X>W=CADIe zK&PZjzfPfJEG>7cud9n3+Lr}(3HU#`Xe`$NJ)0N7HXeq{a@eB*nE8-rxA_n}>cbu# z5CRx5pzf6UmY5oLSkGM0NWOi-C(`;wWRR48TNHS@fUN>B~Gg|W$MpGdbjVRy#{>gRKp{{CIDm^C0yx(uPBbrIM(-3B`J;p@4N~1=`|D+yI7A&Qix(gFw_hkrOo-`=qHLV|5;-{E zz%3>ZYVm<{;r5idV-uVDu*SAj+Dm5w{a&!IoO|Kco&8W5j>q@d`9jQaJUYR2LymA5 zQ>P{1fIN-{$mw_utiHfB$!#|HPaOTA>rPqGVt$Zir{rk+k$JuOGW+#;X}q63<-w70 zvx&dCq~Q#NquF9X-)7jKcreXI`zxJcNT3BkCveRJDsfV!7FL0_1EBqvmpa^LOSMOB z!sZX@a>1o>NZ{l~(khVdEYcMEcPkhYD%UWCUC0ZI5_w?(yAX69Tv_I7ds2CL<|)*P z1ux>Ou!?%BL-mjQ>tX(fMeQ0{K1AeO(AB}4712xM6GmVFCLvY@vm|hKuq$UXG1cw@ zdZApeuozKfKlE@+c&SAtN-@ARs4aHa!|~a**WPa&*(1gUnBgK3#DjoK6Ds{8KQ$B_Ivj1 zNF1%xQv2LT;!{pu^EI{yLkpls1F2}xfZi2ceg8tKefuLbY=a>#tw%3(%diELuiFW> z@{Fn4a|V3RV8px?$6a-0$6R&R&t2Mb_)F6Ro}oJ2;eM;E*0tMO>za^+lQMiM@{5VS z32F5>hieCT@RB7iHBQeu9D;`+^cp^Q?JcQw4NPLw{YP)!4TBZC&_zz!enYKGB_s8{QWfbhSVPT&Z?xFN!TgINrD zATjRC<`edJAH_~~;G7x5LT6(-Bhy*A;|ul+j}~yXJ>{{%QRdB_g`%QfMZ13f#T2&GzEQ@8L1_*B_rIuJ*7;FBll|-cw|@9PU;2I~JsIqy32mnc)|EGXG@> z%!g8Le|E$C*Wy9PM&ZdSJ1vl^_}LHKS{1GBJg zo%On;jsBHLw1`!bahWe*bJ%y6_=ihi zScSvk+KW0S~f&6uvacP%c~gao?x#^M5TZH2vIF?BDZas$85zO%AxoHCp>IvAES#y=jD z(ZH+?lkAr&ABfvo$Qt*pAY*E9HPaCfqrclecgbLGvhQ6oQ1cM-&_v6U0zSi@zci1V zcip)(gWpCfA$5>AmKGsaWvaxvTyzsEAhoorVHCPP8Tb_r{(OX0KwFhjSFH1@J=TnB zkHKs|xonx)EIo>0lixh)Dpoge)6#}qvs9B`NaxOjQPpvP`X_9fl#aKrUY?YCAMC2a zZgZ{2vcU{@!^rbAsQPZub4~USm#6Z{cF*#hxIcylRH195ikt1}E3$G;XxF?HW?_u$ z4;+Bi;C%*#85S6=8E#t9K<%a4=d2jSx7puZ(JksCn* zf>U8P`dkaV2J8T8fK$L}=&%W)8B^dCjB=}6kc^8u+T7-2OQz{Ea5-z-k5$UdWcbIr zJK$JfgDF!3!_5ph!u$*70yif6&7Zm)W?WFrjdr)wA!-{aft4&F@5R^hp38W zwdXw))*W2!xxS1wl6ybjfb!T`s6qcFZTre-eHJFW1zqpBs3FX>*mKZ?-3cdd12778 z_8E@2Xf88&-XvH*Lv>s~gRNSvgT%z>B$y||Lm{Whi_7L%xBzse>3NK?C;H8TA%@1vaL}R!GP?*p#muC}h;Iw{<^}Ir8Md%n$nijVa#h)E z8h)tH3)|8JSPYe()ZYSU{xY1>vUs&;&#%5l6T;C5=`Mhq95J!^)p4w#%= z5qmO2V+w?bWgi69j}Z4xIDRFn6^HwxeeSA4n>FA@?S`7^n9NMic*3xEbuxY6*#VjX zaiS$#mv|J!b-+55D}i8nD6v6CvlH$iIm-z;O7 zq#NWar0Eu!*02gjFbsbqVFV*sIMXm4)3Oj2hPtF?TDUu)tsT62pr`2jn;WvsOFX&2 zvr91+){=&sFfLVVt36cFB$6E>tmaati|0Ot`mkuo>MrpmG-FioJM%s{EUC4!qmT$ zYkAJY91eFBjuVQ>ksoDpWa3=rR?Lokwb_wbUiO^FXkHC#GPoW$%di>)&00&PnOPi} zsxn8u9>b)s0xJ9-j{k{E7_7~Q*L?#U4UW|w1<(P>fD3B2Fas>;YPFHZ)Euzzxav(T zhxBAVa?Q`Fxp`1SIb0s2efZiW+jx$PZQS{im~f)}O%UfDbbpLVm|s(mL(^(cEx1>J zy8`ZM;I0I@|Au9nYkJN@EpWp?TnCJHA@5ntj79!dP>xzu(7jJ^We|q6$}|w&9pmC< z%WR7jx6M(cCkS3kM zWk5US>^Yl92Le;!yu=q{iPiasY8MLMO??bCG+gXfjbU@dFm{AOm8!(yI+a-+mkd2H z^WnI1!*ib6ZrI*p7S{8q#q}J^Cf2apW5anY1-3Vi`io^1!)|wDFZkMk4#h%Gspdr( zum?(9uj5{YBVhnTm0@8$Jr*+Ik&p)r$m;hued>V$hb>&)Ai$g~3v7t{Fic-wKFZ*- zcmjMIT2jUs^e%mI{i5`R^(NS4x*%eiM0@6Jjp4X!t3ACUEkRLLd-S9W)Hn*yq;(N` z?U(F1(btv))?h6jL~V=)3TO?gQFeNUy-QUhzu!J}T~|%v;c8Ezu)ndiqb-?j@=T|b zIt;@F)E3O(#u7}#5!GD|Lqyi94}}%W8$xl(&MF+4_ffiP1=17Utjdvjn(ATvaiUE8 z3UL$WJIe8?=-JIEdjd2A(W)H07_@xQXqsZK+Zyy(UbIkX!O#N2vRs0TmevCPe44kd z`B=J3Qjy;}FGDczX(HvpF;bZvt{mji1QTW)4lDpow2Gx3bYep<`w$EpqI_<9D@Ncz819+UBH!i^Rv6#pIuC#09n5eo+3^1lF`6IZ<)92Y|$;_y^(4vPl391UKF3rA48f|8~ zN7Zd{y^2@V{{oH0fwPL?K9%MeHvf#<7^{SvSUL#aC8Q$>Y13JZRRV3gONPVy=nbb2 zKGZ09n`$txDGN9cyAke%6VVmx-#n|@V}2Xh2|N$1z%pi*1{jUzv7u`n&Xw>|`!6=0Oi4tsuQ?4NJ-IN>7OkjxJGdqq7u zf%)_OAHK#>!IkI3WePSos1d$3>V5*@1(?r+FEyW4dVWUQdd1g>`SoX+Blh&?lWgx{ zXg&fe@u0>3I1pCjJ9L5fF*InggM~r7u=(Wqt@Ws}cQDhJo>b^hVR3GVAM@6SC!$!% zLQj2sbzGQXp#f6H;V#_`(}!nifiktot3kQed>$I-&H``nv(W`{A`e4B1MIA!Hm=5S zDk|BqFuKNYG)nvjy~t0;e&W)gE0yS~g&IL!YtQPq{R)IJFE%6_j>J_2>BB&OuMOQ0 zq?Y2!*L>5_cZ8x+tSff zEF(SYxKZA>QN}53LE3zg0Kp+gKqjUqmEaZE58_mS)%T* zZcvAhb*o8J)N5jbqyG!3Hmg5ci)ZM^{S&CheApFzle!@~f>=0I3{RbF%%?cmi5l}! z9)-N9|HvEU&kI2_A;D(6c+ASf0%FvdKRyOtpM%#IdX&-MC==s4=$CcSVH7%qLPsFi zXD?*pg#OD5nH|lwA27&^et1f|S9=z;#~}i@W_Tp-%Er#vx=QxxPS^)*j0<_E*9ljD z@O#yM$Hp|CYky+n(8PC)wXRNvPd(+B?6jnD|97DbQ*~pk{kx5cHaG0qMr`67*GQFE zX!Im!2#U0h)BG%qljc9i$qM@3HguYiG_J!yf2R#y1nFkb_qCzZ%%14;_0f+-W2+z! zJe`JAOq5j+qLhp~`VmWwn~z6{-kH(6&4;6~y!?Ip|4sO6`v)<2KsOpodhfY(O;(&JLgsh5GNr zBL?KTX-M`N>5g)01Kn??15|Gx=*L>{-~&DfEQ2c+d*1cm(KswdEcPL+cK5$peEO3Z zv!B_Zh6rXWac4nt4h=*@!YK6U7<$?P1&RJbPy=}JW+lV3`@3i%nH=tYaVK0=1!%;) zxIWo*#DjVl%;;GU{B^?vJl^QOAVA5k;MwZOf>Ro1IauJ^?BFfdQEl zOk(#6NN9l|xe#OnUbAQwBm)B84tjKuemjOD8beWxmr`J{pT#kM1Ik~Zp$Km?6u&IO z2?2b`4Y47Ng&Rl~!ESbh*)FD6doJb!IJ3Wtf|p>*X}r*DJ=_O3jn#>$z%9pj$cO32 z^q%0pHK>i6b|+j5P`_0hWcn#TB$)pe@+Y^+uSI?d_L^xB{E*KlR?fB`*b<*G4q}W$ zv9L0@P{1gNV@Gr6Dc6>T+^jaa$;e%XT)c$hpA&e@;x?enBhV!E6g$bEy``SgMLa|A z&oDZyp_LM}0z3>JUvx&NfX{*Bz%if>_&4ww@M&jO(D(@=cU|^1QbTHtFT{0n?p+u_se0Y7QNuPK`tJXAZnARl3$^b zdxd;f6bV6I@ESBxWx`Nlh^YCjDB6xzdyd%o_HO)3d-v_P@+0;o+q>C5S;#I-hvue3 zgVPNFGG|xRQ?N8(p2FL zIF_?j!Uq=!3K0uYzZUn&ZSIu0u=jguu&!b{6BXN-z^kZ6yW=HYJ9anjZvF$i-g_x~ zAb;KNIhTps%aHS(`1AJe=QDZLu8HR#2u*(7(txDJ$z0KuoJb%X5_|64i;~j{T$*`2r zQED9S3vm&KJ^L)^3LZUVd3=pzb&1~doUif223p;?{;N2UbdDa7auYGGC&D?JUOO}K}O`U?)mR%9+-DjD}b=EzTb^7hw%voL2jWd(H$Lx<@$w`a3 z(i`JoK?@%?vD^#Cii)XDLsQpu3g585eIPYnHy`@`d2cIc}rOzx*^uA_qY`K+> z+tt_ix!@OMq~L4#R#`2$lNZYgDsJb^&PEk~kn@3Zikk1?XJwp*&*g78muYxU&ZC|0 zYx#IVWId`@JGblk9h`fmDvWpIC!IaR_$%psGGOUdBi8Ox{EGjo>LfM^233 zIXp%#jNoY^%_p};@IFX>8^NcFhU?N2$&1B%*X8m^KASI-zeV!<_-HxRz~{ugb3J2L z-&x}ay^*j!p{Q81A;B9ZT?Rfntm)$ZGk_hmB~YLXDsiE9)181-&5Qqr<;H!(UKo&MWE)WO zktPk}>l3^WHp#?fo*0(kogSoEo1`U~r>cMP8NHL_v}B&CBzQ+R$(706#Pgi5CSxr5 zdgtdUd?IgG_$93ix&ii~KcCmcqxtbIa$p+2De;@@EZ0?MX39?AAG=yu?$>p`^ynQ% zZ-*ASA&pN;&1vb9-7C|?ei#>vUWJ*B-qaS-iwQguT4c0|--QYHkcp4xsq!Ne-y;gY zluxGf62o2Ktf|Xj`RuV_M(^#{<#*}4Pw0VWZR*iuX4F0|Gc)+aEN8Q0U{0N~Gne`P z@LUUr;*8$cn=1!K9m~MdQ+67?qnf27gXi%z^3x2SZg>)zU;dey(kxpt_y!T*EH`BG zYz^Jm4n8SA%;ZhHQof&ssl7~oo5kB3%CBjeFSikWeRa6eJK>s)#`^3Tc}-R2%l+&W z%l+gVlB)kTANm=cXf_(X4_)gB=}i#qhvvn_Ece}G)bnA*M(<4dV0*qsn661Bn;#F| zdzFTqs=p~+**qa4;%YZoj&!C+XHu_8T@HVYTjk;$-a9fEgHep#E1i7?wVaXv%HhKk z$J7b@T$(va@nz7t}cEF_Q}kSJjXEmN_fVgB}Ctl1Sk>fk@PJF6d*omhn)io(qXyWUQXQJ1~ zdw;`}i)qsO<%^UDIzhvyqHKG|~i?7`wOW2P3(n^!b-{3||R*&d#*W)=6wdpEZ{XXXXswia1v=Er%R z)aLVieqHv?=Wp_6*_hAqmWvE6;GOvwvUdTWn3#Q?Wto_^#=HOB;}Xa}BkNezpyFKC2Q$L=$0IFj%!_#MKbqyDZoDAkgKLA5 zW9w!Xt9HhFpK6weyYU_oFSeo0YL=QpZspVEj6yz?Z;<~ep@v?#`d) z`{jK-_%&Gm89jM_vFWOOsVA!Z=+yS&!$st7IBMj6tV4JP#(PR1KAe9lcT%uJ{@RCk z&{8&KW%lK_a!k>_XbLl?Z=0;fzIDJTUmkV5r6U_zeDdt>;i^}9v3A~nO5065oxd%&+{9lNcelt919+Ag z(;~|T@cTt#i?e)KkDd;2>}mr~~T1bWSSb4-0DJ_#o^lcR2?P=2~8I z@hZy{SWOi(+j%Rlwey|{rVk=L{~F8eRHnL_bzyZ=&vuzyselo<(-z}W15u!^ZJAtF7yzzwF>FM2#Wze(zv{A=)q!?liFeYj&9_~;n|$x z!_((_#ML8{=Ce-fI%VVw3s@&!ry5o^l$n~((pNeRzQWNi@lp=MRy|qf4Ch1m19HxA zsI@?@8O|Tgp;A8^x#*q1{UR73Mipole6BMX-~7zgar&M|b{)antB@fljNo^Rnt1u% z2tKgg^T;(omRO(}Ulz?bGLF1YtIF+j%SPTn1$oI#6 zEvL^S|CSOysa5^Zd5(s+&!kvJc*8yR8m|a1g2?`#I#_$PNBr!h$tRv*c%WmWOikMb{UnR&OwfuWL zPf<~cpT_eKdQtIM>OWXh6U1&@fQ6tYhy(S9ICKx=0#24-l|G*=yq&l2guBr+Jay<3 zsZCA8>x+HTC_L!y5vl#r#47MoW{C@a=sR@&a$dZR591w2VL^1pn{S<2g(wZgRk#!m z%Lk?-J*``}Zfb*?m2H-Hmhx0lw%Pe)DK`pJ@l`PlD)*f~dkSLhn~uxgJdjdSa!0UOqppb9h&VS-hICoCwPjOx= zyWa^DyiSh46Lx8t+;k_;jCvB^9ejnumLYiC{;TuYojg(%{$>fT2tX%3yX2**Jc+lL zA$Red&eN}{#3yN(+^C_$k?muAQ9!TBQNNESap4_`dwYk&MQ>@pA@8^gO)rt>@8V;5 zne0D}kDYisSkqaCUZ?G4Ug?>Jw0CHLfey4OZPL>*A-0*g*gcI4-E=O>frCH@j?~fE z;ak7ZqKkr&^87S@dq@{l-$$(F&C~g-v%-~MO$vY z(FMx?pXlNs-ibiB!*JoxaV%C$s~f^_OTfw;uBYVGyRleWbp&_Op!6jA)6@jBK=X^F922&MRd2 zO#VJEk)O`w6SzmVpT+y89J>XtxHwL@?hdwk9O>i1_`l^7voP`&xoH+o4G+tZd*LtN zD|_FIc~B}B-pjk`2X9xzY0R}zJDu;{%a4mtB9!dJ`;xG5FU;Y+d4cnbIlPnL!<@W~ zzsUJPxqU7?qN5VtLf7!E_yjRJ*j%;jKaU>?r#_G-N%k|&@CW%LJW7XR&S0@H!)i~6 ze6}1+esTU>&Zls`SdM-eN1`9(Lk~mV74q4K;YQo!0i@LPMna`>;VjI=bMpGbe1JhF>Da9F^FgX}Tvd-s~`pzC2t#{;}M|iiWRd@$Mp#if7o`gT;yz&U2 zqSA&nt3)0;I^}VmB2K+1pM0F(!pF-`ALsw(W96m=JQK4}9$vt+d4xQ_fG_5wGS_HMzzU5*CtMN%&7nOy2)*5!`j6EUJmIg zq5=g5KlxWCd1xdTwAO~hke&(bL)poXatyO@@k2!yQhqrM4uJh7< z{;tA}&Yg$&9~>_5mLuH8A9JSH^2a$(lAAu@zw+;#Yd_?X{@joFm+i7{5#r2)97{qG zzhhIJdKD*xX6MsK`7fL|$c6vJBzHPH|BFAs`R&e4pU|N-^T+{=tA;lG7 z@c#$nkT>pG=bb0HUKNsxYg~rw`W4Q(Utw;FtXt%UZ+J^;^JXrxUf_7KnTsmmG}5Pl z$-uhJa_?!r$aZ-X7uz;sG!WJxq;xBY{y%}rw#_>jcc=M#XT^M$~4#AR7MkCm41xz6eM zj#r6x7pt)$0Tk8+aj{w!yZAF5XjaVhsYG)NzL8+CSTI5F;yt!x7rUQ))yvz-C2l^&X57Yw)i-#fy}l7?Ejkp z4m3!#Pl65a3x==l1`Prvzk4H(1n9Swi`e&XG+GrDfaoF2;mX2be3^-@&s^nE$*Fjc zh}StE^6+0n_(nPFC!UnD_)y?!5MCZnEQMF2My)XR%sDgOB6?VE`3aly66Xg$VSR`H z)*fpMm;1i%4);NM#fx1qM#lZj2c+zLA52WJ@@Bl%hbHqd{vE-1K3naXCFlN(W}lNw zeuh;zFAw~TJ>tqi`Q6Xh`M#D{e&)-%(0uawezI-AZu}hZH1G`Y4}dYV1^3qjX54en zJ)4m}*eu`pg^$1{edQNyyidqEzha-5BVYfOzbIPvJI7q+Eus95J)=cm9W4K9ov7v| z&dwp?RnCj#S9)9Ht$ zLavS#4-(rr@f7^|)p24hyd+ng$l)htNIP*WE{-O)gH+(&PAucua!5S--y%KnqAzhV z3UZ?Q8_}DSa*0tK2_K)u8pFvm!pO$U@d=`9=PM~Uyae(Pgu&sy+=fQWojhOiIuf04 zqKfEGj#OJuqi4nq9@aLV#($$bWJ}=iSNpn2nEf z-kmBUMURVUDHncCGH@Aj<+@535TA}#==^3%#*{&td>=3JjmXctE?+T;Y(Bwx%mlTh z?mxrDnR*yEpv1++Mx@sR$-uZXf$dRlmb+tweeQLh!!mTXGo0^y|q!wZ;iJtKe!>V9n>KI46q9I4g!~fETGMH zV9gTP4qo%%YywbN6~t>E|8@}Z*X=;Qlp`|W)qR|U8JjG-=VGo!$|rKMEPT!bxx&V6 z-V4~s)WQ#?@kX3z>)YgoA@5=^{|v&|VBW!tTpayhptX&^g|FO-}&J2W!nrAAo-^ol_@VQNb7}=(pkZ9$1mtP1TbIW zqBV~Mm<`PwY$HHIqr_91 z5-d5(bvf^5F^_*JJvWPyu&epE2z-z!$KN6zOd!5=f;Yf|2n)o6HKAqylXTr8rua`n zs)Mis!9$z@Z+EbRcq^Lx3Uj@?Sx&uGbmNERv$u+&@KK%L-6{m<4>(;Vm~*g*H;;jR z{8WB5M*NHKlH13MR}~-r$dYlQil<4}IP35^9apc;L* zrZG8O|CHTtgGoLl=iVml5f@ED)C2p0Qj?6HAYSS*7fNKTX+UHSo+%?f-JkXjD5DUL z7h|#hjgc|0jj=4mlP$R|^2Z6H0o&oRQYdJ@R8JJ0uwms-6geHVL2=9~`oR{5>t0B# zhbW;C$$|L#{4_kQcetfoI8pTEaq{hnA}#I~RQ1?#x#3Yf_VFJ~yLfs1d<^}1@f~f^stL{h&`f8zA9zt>clKd7y zc&}~v*3$&7qScL3eY+T&@FPgAqGkmcxL0*c^CZc+w~M5>7-Z{EgFeiq8z^4ma4nNt zkj3wJ9=KhkDf|`r?G)_t9y!$twV#xmtk_83mQhnh3{P~npNbTpAfLZWjO;M@MMzx+ zPF9EOBXB0EHAExsXoW_bM!lO1p9Ur8$f9W?CS?Pa!~^_?@!nxcP$~2vetlA!C(&Po zFOW;7i6eZCbNF--FFM@46*U|IX*pZokc)I{C-0;@jK#K_(me1t?h)T~J_^!Kh(XFc zx8+9BRM7t}TC`j{L-Z|p16gZ=RX%G|MWHHqKl<<0{&2{a86q+650s_W8C{=Q1M`2B zv-3>&7r0A$VwULJZiVB91g%Ayx603EiA4Ub^ZYFAvifq&)K@rT%da~hyHD)pxZcU1 z19!wLkIlhcX)n*u!QODY%)ehe!e4dnydRDb|3qGT0O2<>zYJ6NCV590oSP5j5=y-* z-z-DLO!+Yp=gObU#LK*=e15K&CXViuEptV-DBCHs=ZVyW6`QcwFj8bzs2?<9m(%fS zhx3kkC@zj}lZVU2A|B%$@{o8JuMJ54i0BIcDgP1iJsiKN`C_PsdQf}adFOml%yEsn z{ZWj!Q-1ZRNNUZx`lyHyt%-;Qq8*R$VsXyJ@(flkctZ3D=;ABr0^H_3DMkptatcri zgbyo3pFjycUQ@2UF7=DVO}t(XUnD-_4jHvrObI#mHl{ebut7e$7;b8%Jhm9?>{S_3 z2~CvB{7Uf+?=Hiapeql_kC&he{pHT3C~{D`mO^J8~@+vj$%;MUuHQ;azpZI?oL0s)EjD;$BKTCFq82t6hxI*W=K50yx8D zi(Rx6pJ4EUVV8BHBh1Leb>jWh<>Q2y4U7VM0l9z?&;b|6I(s||HKiI9Ma)(yq8U$s z9Kacl@0NiQ&=(}hXP$#M@}AuD9Qw0YenG(-^0((iW`w}~Tr3J20TY+m5(S@^!=*?o zSi25g!D7baB)o`>pB}<>_bSk6GobI@>B{@B)twupz%#W|J7x3+u~js6mwPve&!Up? zB#iFG`@n^!h1)2feL)OLxc3P0pWwo;1tn^sD*8-|Cg>LV^9y2%o@&vJOY)m?(nirI zrPv-2hhF_Aae7j9N8l#2P`i(4D{zs*|Je&P?)hvJVxQ>O=5%! zkFR9oCb5MGPj42VQFv#ySVUn%wYWdB7rbWrtvdS6I{dz!oZ=7*{h1Dt?XMlWMYQJ! zWd0VI(TC)mE!fm&%e7l@ka|a6+Jc>anC!h3#E<12TQQ|>mFKsLwC)i&4U$6pU~bSo zEXU6$G~q%r;xN6&gslr-BJR%u_@wPW3UuAxrhxgs6qvGI zJd}72*Up#`7f$R!v%r4fC{VLU{ZY@RInD z&y%meEYjKqNP%K)I5oU1?v0|V{>Ld54p&r!!#zOWu>-2jlRI~aDY&u=*@>+!R<_?M zGHGx|>=a`{e&3C46RNx{x9=2v{bROM+`>o5{8z+NHd0R+o^X&G#17(nc&H}-DiiaE zUO#)@3AF}k=Ps*vfR1F2K|PAzNu%ngZo}?hEj5 z2fifKLkDh@Ie?DOw}E)-tw81$yhhr}p!2=}g9E{eFFze9v$#!f(v?8NJ%dAXf3R2G z+jQb9)s0R(pAabjaj-oz>P>HL@J*<`HNGi03^~CutZ6e3h6h!6B{)PYf`XN`sx(Ni z4+`D~V{Kok8YOG~r8e4)BMr`q*TwnwxW#$zY}GWi%`~KAVc~gi2QN2-D>s)|tp&e4 z8qxbjFZc42kQfm)=l-n7@TiBh+GXiaC__^o?H*}0X(N^@Q*9tl(Zab?kZ4K*@oE&cH5p%gld%KP4+ABP!u)9_05`~h}ooQ`G z16Ohl+BB8O_{b2cdrOyHpsP(AlKY7vJ5)8z*+p;FFBJby>29>Dv)J28_av^)RHqk4 z8m!uE_I9FTjhxj%`6Wc%QQcdpmHgVcqS2|{yLXQ(5utgZ5v)sy?gdsXl9)avB_mfO zQV+7VEKQ{LSE*F}L)6TsO}NFN9erow;9E1)iG>ra8exvK-fGR7VdQ3QNcYQ+B)nnj z-bt;uYErs)S29#qk<7H2N~{$;<3mjGg;6V&85(N}&yE%4Nl%6)eD=U?*^ar-o078A zbKWYP5}EXIluKpG?k(n7S?`1R@gJVbe0i_1b7>*<9hl9Fm#GT2v8Hr$n#f?j(A;H) z0amNNBhQ{Xz)-zVGopLrdI_Cn1UsnHhAx5@a&W6O-Tw7UfS7H!GCE-W8U^%YpGw(bQM z4&(^@BMJ&EhCiY$9R)|?{sGu``wtE&;Qf>Ih@}qAp?~{laHh@R2MyZYk91I51K&nET*(BWjS8ne5;SK>DhRyYt`DauWG8i1MW%4 zd^L0~&+gnYJwzL4k4TA%j4Y4Ou|~w6Y*#)M&GHYD1{x|d;vysUVP4yJ-T~*ArIijH zR^lB{@kiLoUcc&il4*E|L7Ne8Flh8WqtaFvqUYax`PBEL3yO40GK#4E+C%tIKHC-( z9x_C2`1R-az4;$6EBvv)HS~k;hyLvCOiEPJc(|c3{*m?x|5mz|XtU#^ zRl-X~9oK{&h*@alx_h&YYi(g)$K@D9hSbKMvwSXc&Cbw^KdCW&GF6HpTDK^g3wik6yDNa-ecCUTuv|&~!7Xbk>L*wFsG^$yJA0Loy;X z<`mtjyOrpfVcoepqA2dt1Ewe|o65r@LO6?0krp2D@+1HkQUNaNc%%{sjmj|yVn*8ccF(#&+-cOeDcHRCfA`9Q5nYqaX}jlZYs z;8ceiTl7}dz2OO(<_AJqMHJ_qUSky@N_7`~6VqmAyuvEN!s@x+mLjTD7gn|{J3f!w<&ge^DvH}-V)f~0EGWwBA6=v^DB?Hsf}%*Jps0>( zMbQwQszRiMsD`UT2LCKRjXSM&=nY1#RTRCQ8TLyYTN!QnNpdCU%&*}aI-O8H&uYxh z#Py`5e&CEfT}!xp{E+A&9fw4e{BFMLw{U(7yOou&(cbPA))2Y=u*irEWp}Y@EPcAS zcZHVS&1BSLDq}34%jU5MS-Cg=55Gy^)(|Eg{Z;X@PNm9FAM|nyciJ9P9oke{iFai2 zEfss>T_#4q$HX0nnfL(V^B>_|p^urk^lv7fsAFOU5PlqSpy&jC`2Z)!>nE9b{YxgU z01usFVhPf3qfYyO1-@U9HAY2=XhI8nuy<2S3pMhvQTficw;5lU0u|SpcnR2mcq=vs z;|9=={w=Sy%>Oa8{n=PsMy(CErM1RmTW$#0N~7@ppnxqDe`xk>Xp-Ikz_h6k&SY%b z1NXB}PSLg4jXxbwjxqaU)uiZ~;6x1uZUK4$T@CmlbB!a%-6q?It%44r6NwQ*>k|+oMQ;C*aYLs+U z$<2f4x6P&Fbw%;#Ig$5RoEWuPzW2RymnIKypjp3`+4ahu`UJ>AO{FOE>3XG$aek|h z4%*DEILra1xGhEV>;Gh^ILlm0mC|EWgbi>fgz_L3AS6@At5=4EQEx-APNx@`uQ;ey+?#FDu{6i36q1Ej*u`r zh;oF41wm9IBskaopzIUv{U$yF70hJn$UR;_T`z7oc>Ml-$}VGZyaP=)kq zUqSm`rqF98ia}HIMO<5*r#oq+e$+M#eB;Ft7vZ%YX&(k}hBl>;~#? zW&9k%u&$s1{g8heVV;@sUWgY0W?(G$VEI0Fi}_len7GfiC*2%3&1o9 z1i%QqhIB0ui+ENcdIl^23`p-ssOye~fH0)DA-oLe5LW;O4C?^_fo5p!G(ufZXbkbo zfESpIbPZs;h{QRdS1-oTAgl-GBfcKk2b@Ow6v9&o4ZZQ7A0V_KEC+S~bx5B^nAeB# zPY^!}lq0?kI04imt@MRvfCa!or1t~M5#Kiv2sAKQw{# zOoZ!!6Tl9nm76e@z-z!Zq}c!r6JVW$o&hHi#}g1<4wNEYi|_=+i!lC3FGm$z$nCr0jChp8;ltW3`V*Rp>7Bm02ZXH5HHmLpv_3fciGC`7sv z;YA?!W-v#3KEk8Gbi}KGRY3AB5EfXDxC3DgP>J|@U>%@fGHXil&#+wQ!(r+S#eg3c z3nOFY{Xz+&IJT{1xzC`Uj=QXsD0RG+esK&x3hL||rQXEj)H=(BNE4nDhm3JMaCJ#< z|4Ml&TD_(qUc)X#;9`$R^l5KQoAmZbhdZ)O+Kl{AjeH|Uoof48je5AXqI$m|&hQa% zq#>e#f|gylh^xJ{ztKm7PQTembo$Q$Sg`y^&?BN8uKmdCXW)Oy8;rb- zpi>*DBS*%nL&Qy5d0VWyhcIj9)3NG~H_g#m{I`_`{Nx!45TUhP2xubk6RFQ(%YGJ+ zKr%Gc3&;ZKznGZ+gZw>K{fm}i=Td~p{mILy>=DcIZhuov_eg$qvYfK-|5A^Hs8i#xK)N0S{ zH-Rm{T3{i5!3Xcqk@_DAu{3tkS>%23>ftv0=zu=V@Ejh)LNfeR2mQcU1`5?_>7}~~ zZY^_gl)=}*-}oEBb+x`8J!}2(J%xIKZ|bRjHp(5vCGR1sYyR3_{uri|0Kca+_(UJK7iI~|v)F^%N{1z%#$#3J;ooqAFPB+|X;=!GpetXx3$Hde* zDoXV?qbTHaeTF;}$Ny@K#~%nMgKK)({m4XYXy!(u#|{lr6M!why$ zO?{n<>Jl%*LA#o>J6+&m(;tO~{*O%bmH!(a5F!l1)UZ0dE;ib=?;r#**zD>sRzi~K zIa}4xkA_R{aG8KG^lTqPZ`i^Hg;8$~`Fo-;+{WWK7C7n|40bhos#d(4&d?X~U7&YZ zCPC|UBdhl8O%G@;*6=xgw(ExGDh>GER>QHg+-6$TAUZl+8Nl9jG-iV8OlZsi)tTB# zJjS*65F|GJO<*wkQ(!RM%Sqrx0fF(0Dq-M30>{GG2of0e!Cy^}gGgXq>n~TsBReXa z+N+P!S3!rf)ss|YMALF`c}OvNdk6Ipf8@mu>h!pM$#AED3Sb;S4@dMey`wtDd9i~! zjQcBJ>!{AhJF9)1UGmg@C?fCete!Mt_DH;F4IS~|?_w*^lLCFwqYt7}ejI*wNR5Xt z^gG_gSlIO@_yvG29X<%q3#c+VBf6+R6JX~2&a6)5c-{YczIp~id3QH;R|L;?Q+HD5 zHAjnK@`G;bN3_E*Jk*&%h3X}(3Fp5H)te%t=oiI<+2j!ORn8{{tFM_fRQqDG^U1r_ z_b3r1SRk}mD!Onsd!+njmO8`mR~o+3U#L2>ceYwg7mxR+&B{?94r!(Xb`DYnhOhc~HBn}6?xPn)mSQS8AcJdZW8PV5-IT}xM+H~rr1Q|c?y zx#?qkfwI6~Ivu5d^Ov67G-zOH(RqBC!%byFMY>^++O+9+cbgj1{55oc))>^pdr=+3 zfrG_ma>Z$NWWn&JdyB(I8q?LLmRG<-uPpleSv25t>Oi9@P4b_ov5%(zmwNBE zX*$kd@10=1O~3!V+v|2Ty?l*jhY0@&Ix8 a|E%r?RwM2L{FMU#*jK5Zf9X4QyZ;ApFI;{A delta 27276 zcmbuo33!u5*FHWod9rp(SJFLQ=*AXGQBanYrR-StMU)^2=!;kt1Qkt7%c6p!0R~xY z5L8t3tAGR*qzEc1Xjv3c)Fvge6gB#yY=!*qlcZAp`F{WRy1shd%*>fHXU?42mnW8= zX;prv)v~rCyWqL@Jw(pq&&~9SQTrWkZr)nX%X!?n&t-=-KRkW?+D8|^wQPOVKmN=1 zQyp=tyu7aW>a)$7%m?2Z{^N;tr5;mbNpbPH$@R}Z{^*By-={zD-rhMs99ZbM^4QiX zs>R`P>voq7`7V3U?fTgBTi^e8n97#e?F*OtcjaP~%lEr-CiL&tWvZ^aE&XQ+`}qVe zSP#EoJ%R3iv7=5Aj59uCJmc8~YQY#nK*}eeGrw4?_ls?oC}Av&5=0|E(Fof!qQrjp zjd20IL6accs3py^$H*+!A#li#&=VID}lP2a(*?N88&j!BN@zW?j_d0$W z-GR?>q>gztsbmCeJXN>U<9l}38ODY;Kpz7$Ive^8aeO}}Da|^BHGbmvpVOJ0ZgrW{ z-LqWh*@AF+H4eXWAxZUdwFlx$jVARSrDK$I^DtyA$?h+mO0%kOAu#) z1d@U{qHVK$?Cy#9ZKYqk)d;s9z#1uD3qB477+dJg>k~{rr z!#2x4H?vfEK|9msv}69bLIG#{xS{-yt?KbTIiK(7dwUjN=eXzgG4||x6_E$@L2Z=) z`ysq9-2T7-U?0LG&nn{4wThSvJPec~JQx^&bO#WB;EW=CP-wykC}eXY^A%ohh08`X zY_1#PiG~Hos-YZP;qBI`+N)xvh+~G^`ZIe#WTLZxf=AgTF2O!$BVne>?aG zz&`^1_LiRCd2dFb6oC$i=mP%`_$}~T;2#Ko$B@4t{M3+Ap@0sVE5@Z>zvIM&Ec-}N z?L9f1HI4)4c;k28+s)s3Cs@Dp@}f$&=u+ucx>dR-_s^=o1N7`ZPPc#XzJ|$tvg@gN z-ib7db%A#>q$@18L1lKv>dYU-YZ2BVJPURbx{(cv+35g%1)B3}YKicBIpVq5X^%A^ zffWH^amG$WCa_)n&W@-IV?7e?_1Zww>qj=I;hzM5d6~084*_?<&&|TaK<8*V%QC71 zc4o#81GWxFW@w7;WBsV|7I+apR|dIL_EdYLnB$C=Z9b#d+ebDq2&7WfSPr;<^ZTFb z#;Iw7jzqaA0kMMY(QF+m7SjMXmRnTl_ahqe zkd9<1rOs$x>Qo`lt*ZS91sduJuPv`vj9a{lvGP>7osDo`_4|`lmX8|L@P{Fx%C@jx zYySGQ%3OPzn=3sE8;(xK3WV|d)51dG5pH3uMf~?SgXd-iEo!Z~+PmqRzmYR1nk_~U z^dEsLLMK+i-0BT}zkwqhL5hW{;6)4_c3#%cqeX_?Z1tcD+>`+~{(yc`^7-Bd#0z9!3le^*`!kv(WF17y|}VUn_2Rw$4%) z=wJOAvm2ZhFgJBL%PN?CL<4oWhZU-`Ro=y@ujUSSAJrr3c`oW%u`Gsyi_zcqqrdG( zo7vx@zwJjm*pD`_-%ItczV2^irKKJVn0s(Hq0?|m4EX^_8&x@{ihi!kuhfL@8gn(7(p&{l$jd^^OE zj5x?^9@y<@AZ{{At6mgY8kh}Gd4`>qV{Yn}`%$-(P`d4ZuUFJ1jq7C?JD1R44jIg{ z+>6#8s9UN=b-)VCy=5(|&=j0~8f*b8RM}B)Rj9{(u);pnJ6ky6?qCc<`C_y*=QAtYNX5u1hP(6KoZmyg1R~#%^9l9^Xn;781CRs@Ppnfy1!CwU!O$fJ6&`x&FbpXx(FeK0FZsLY1gp<+=nb{xYo5T$+txEgPoI9m=-0nwG)yZ~I9jhW?}z$ImIk@8|3k z{^p?$;AQVTfKl@&MG((G$E4|PRN!(vJN>MkI4Fg|%9u^<7a7)a#>*MAfSXcqz13qu z(V{TwGK`*4=tXS{m>3C!w?*e^$3!;VKEPOD8?X;BBAyVA_+~%3aexKIQCM`tDYJ9y z#d|7L0c9S$@2tpA+d6gTGhF<3)$zyuL;DVdSxZADdUEmN#S4tRboD({plJjzz$jp( zaj@N4Bdhi%(p*W)6qvfkyqAWfGn96qZo`xc93T2EE(Iz!W)8Cbm5G4+9Sx2d}$t7WC0A29vu zE$G2*FhW9=2#Afv)J)=!K|~-MxL;ugExo1->`E5H+#^~Wge4?$M5@72{a{z#;5hMM zI$!0u{NSMY{oSaAlzL8K2F^29d#xzmUdOnH(sO8CMf)65s0bJVsUv|Z>}Dy4KA_pY zcD(pdQipz+Zq?{?q?iJQdLvA384cG#-0Ew(C66oa4UPetGgSA`~8i3FYj*L4BUaqUen}nYy;YUU2WqV zz!h}B)1bGd?rJ#_=xJ)~I%=-?8}pE!HUtU_E-a`CEV<-w#47gO1ZYzW>xCno4&yrQ zVi?;SpXTr2rZ_Ym$A~%6sRyq58=pZwuK@<+y9j#Fq_pPp?sF3y6?3N9m!VAk(Rcf! zW@;>l-8IHTZWSBmh9uqvv@S59%6RBB$9lQ~3$VA1%iK!s^Ijc$-mALB>COUbusy6X z9sp`7oqH}$7TTj;yBt%**od${RXp(Ui zZkD;v%k!M>UO?WmN^je;N^cjq-Qd;?-|OC9n7P;e8~fT_qe38Sue-8mm8ZtI*ByzH z{ANCm_Fn0UjDe6?TDHVC_$*&LKA)Quzi8JPDma}8(8)mXRKRg%ZXs{)X!l5;=)xDh z6`~wFA51(Q*Pf1xam;_@3k@Zyt#*ulbSm%U*!AdSk#w^o^RZs~@1ACj9P7=kj{6=< z=aG)3k7Y&Fbzy>3L?7&;fT zE%hFOC{~NoJ`n79E#m~TFnzel`x$sNMa~9u;UcfnvD%v=7I|wr?{jyv^!99ldjZz1 zs9xmpIghx{!*AG#4MXh__bK?p_rYI!#4Wll^3>FR>fYkqYY!a%P!)xjJKfWh0#)!Q zO`yu&1Z^`CbMpdJmkd^y`BS$*)rw_K_XtX(RJe8fQQcjfZo?+0TffTb9td|ZXanHy z4f>Y5_PMFrx53>qd7pb5kmsCG%M@X$_|S>)J7C))5rN2I-nCJFSoLdS4> zp$LE4vCvNRE%w#?pkqk+{d}@xS9vRYuz4sV&KxC*77DR>w-8Nx1)VOIH+>{T?H|B3 zgcYVf&zMrq*@Af(qicXCu+FK2+dOHRQP=Nb;(G2WoUn1Glwn-VF0J-H@f7XPjBeU0 zpsJVVO~gTxWmWz|;_SRky;=>XFp`h{K)Y~me$qpE_I1o&+?#*y zcz1E9=-&pi#xTU8lHI+cmU`ZETwC1p&t}tXhZ!jMJYWi71EvGZ0L2(4YT(lPt9iYX zf}_c7UhQ>SStB)>M;4>`Vn}G73~$C{7@kq>6)E#QTPz+o?^fwip)=tO$ejiEvfpnH zoCuyrJEF0IVVktmcrd{5csHkto1G2Ejn&>-Ob;Je4!Y~WW5lVU&b-uXf;}Qo6ciID zXG<~v9dut^#2RbBBg|EvNF&Xx!x}asJ#Rff#*jT<=**SKL;APBB{76j}-XQ+iTHqfYJm{3yU{TUgiU^t*vB*oL>+6sP( z+ku&&8~nr{4t^Z#o$K-mIw&UB(P)))d|z&VA39ihbdMOuXy&C8r^B?g+Ma^dHZ^||Oc|v>cw5Y4SXM)MX1IgaY&I063_!XrNJkCCXWQ$(1Xwex zyvHsC4=;*waHLB?9p3qGf1?TRmEVF99LK2P9joJUvKgO(c3F)@4Qo-ig|L`faW?oI zt)DKkmj?Fb4Rors114bR=e^s=45hHQ@j0&<$D^ANmxAy}!riOwcwe6@Zgv# z?{b8fBRmD+u?R0gcnQKrq=^Gez;wiwiYl)S@x!npszm9sE!AFo+3+gwmeRfM8ej{| zLdRhVXdn#c84N+au#}=p3o2#c{0q=Ud6XwkG3qlGLjrszCIStN^K`;d-VPWOetXRY#d0*?XoG{*}|vc_-4aG|GeT7yG3EP`qE-5wk|(89n~ z5TenFoTHuR^;+Sjm5!pSs%Lyrz28#n4aZqob|Kv%RC#Fam)C27Hyb1C(k$M~am&)Q zgg>zRAmT@`38}OJ>gL5bW-d+ZzQ35A%i9u^8K!zVAd~VTxhPIhZq3sHx$R+M(mZbq z$zR|tb9}nAZI{diFa@Sa+#ivx&%jpafeQeQBImm@(F8x)&NQvsYs#hRV5K+C(e9aa z@iuonGe0fqxTe~BE9^uO`*LW7Cw^`-4;;(?XBBMPUv6Y>j?xV)}-s6_}UeisuYJhvv@;o}shz86h@8$Jc>7Di9 zN^dkBme)8tM%OsA)a17~JE|?tETd(qH_XzfUW=n8#X88MwN_bFWzLS&0#v1_Dl7P% zsLXO;SztL8IKoV^EVX<82PeC_(xqs_OT7wU0`|e&R%Y}lY^gdPb*or{(+HYp(kzsM z6w51IspeQy%_>~zH6otQ!4;fTFgB(E=jAaNyl`+avY{^zZ647E=+Me{Ov7-ZkNXSvmpE|>!$e6Yg(;t#mAMe52CZySARZ=FH4C0df}PHWIS?!$_{~5; z#x|^nTq;BuWPC_zL$?Jgt1}~vjdANB*G}dO3hsvskD#W5NMO0MVKNCUHF_39kPUvN zh#H#FZA1pM#7gfaT(vP3_MW^F-Ks87EpLH$6qPW{=sDS`8dcxH8@v~x9+P&K#gvVCY^XSTYj`|5VF7>X(xl1ZWYgEZ<9n4OB6qdk&!BQ`zt&TIV z^M)JOdDATOQ9Y&Zml?Z-!ykuum9e6pZqUrQL1QHtAK<59uDki5m&1>nHLuyS)FY6W z+IVx7=N*iF-8+I2=hu_4a-uHP6oZmxRMyYWsHit%u%@H0Q&`!kGM+zOV?69$>sUHJ zJ@E{#`4&EHK1o?wMMwPAsW!Csm&B(Ri!dJ-R%$;XiQctHK?J^U+C?LxbC12tz?aK zaRa#xSjo959W`{SW+T}OV~H^^mW*gnTf%|^i5-*aD#xDXvH2wsk-}N)~|j$!p&># zz>@cWS?+T5W*UrXF>+&>>-bG&cW5X3{GiYq17C8P`F+6$($W62u zK>MvnR3FE(&f&E3j?aX7rIt^=VEa)7;8;j4K>u12WR+gaJOToryI4S z_f&h2z6-oo?X9*~d0wioN*lHap3$|CQ5-C+%3^Kn}+d|roi=$ zyBo`}A*0sP4fL|YD$LdxW1&o?(b+Hqij-mfLCXs|)Z2pPT{-wkhMBQ%IC#eD(bqA2 zj?Az2>Z!$*L&(mKb#9eqe!UTk9?sckA0SL6qO)ov?un^XN6?%%T=X{%4t0+|a8!iZ z2c~qo=R(HkD1dT-q+CHQRGgWw@J}k9!kfRE5Piu+j?9Fux${x#0U? z&ms3LxZxOsjBF3xNHl~YUI*T0zEZ^R1mEBwpFP0H!{QtIATwmp&=Ce#mE(#Nx>liV z*5<@U+@W>B0+JnZ8{slbWx!_TE#fcSjP*3)eQ=xOjV;8<7*uWJJxemH)WeaPDtvgu|G-^_W<-|}XnKd26;^#U2+c{|UF}gv1e8gl={%fd zVBh&dn*9vcL#%LL;KYxkwb2P)Ob@juCh`XR{=e{426&>u6WxMm<6n4!a`ebnk8G*s zFGjo%r+z#z-S0D+Cq%Afim>|5R7}kxEK09vpS2;DpqF|6z=LUkJUUN6AVJ95^)$#f*mJ{yokoU18bxk^VI=Zjvm$b$B zsk@Ewpx1_;LOsZj0j~_r+8FP6aZQr_7=qyt&CR_$Rp_a76NO>?T+2GG&qkey!|s!C z|EW%ELEnP-oh{<2@iy0~6ZGwfU)v&H1mnjWXb31r#5OR@Yr#O>V-O9MP-Y4A#R-8Y z4UG=%z&j8l8Vkl6BaNQJ8ko@;o5liAIkEHs)W7`U zZ^RwXIUat)ZZlM{cMRIBvCf@htiUm8ty>^|?{z#0f!PNCCB8TizZ3OIE1MeQ3HRW= zc2ul!l82j|?hF8#}m17 z;G6|!x(N)l0O*HGBg_0vQIy~lH(5y-ozZYrb2F>s0rksJv>VdXFi4$zGL*DJnLH@7 z2=7>$mC1yXoo`1(Oeo@Z)N2gtwFJ+8FvqO;1uGIHI7juG(4ti6ff#-or#WgiwQdpXkXMA7HLZ7w>^NW^0Z z@k~J62jHO#>t-IBkxDJS4W7x=1W}$bj_B%Ei4&j>v4@xABnKD?wKP!c48`WRMQqy^ zv2?(61xhWY42^-Ctp*c#N*oo{t?cKqxo4>I^Q_t%IAJb@OyDe1>}$sw_W~aRdw^PC zH}CF?z6vd@Fc~c)?J$0Nwcb7j zX{O*5qPaX1pv!*nt_Lrz$LP>uF%A{d7c>r|v;MU>e4s;yC~ z%CXhiRo@@V&=j8L_}!U{WqIoQWd4Yw>-vZIFvpwg+wc;{iS_rZ3&5puyuCilQTCF; z(;c&4>dCh`-g&7_WHMrC=}=Z&?X9nH{QOdqI8os+Y)BG^D;zl+()cn*-wmDk_l`$4 z+{Qn1e7d1iyrY7hBbx+lgHxO-u*n^c=#8-x#@@xm9?n?vp=|kmLd>fWqNpl(Rz1C~ zO04Rl66Lo94{52iMbmI|JyRw8=~%VmFt-Bf|9*Du$Dd=~#y&dhR3@yiFoCzeCP)27 zT|zAg|1Y*)-jzvO6rI*Y&H7;w4`f5tHz{smiKIDLNv&v)p5?-w3?hRc{44>hHE zraI4V#t9yU=t!K~0(*b=H#1n{l>1oY4AcR}aJT4Mi8rJlx;ueJ{S3o|VUXM3=sM+Z zeD|EcF&}>F?$%P;Q;l@ft4*xOzj+6Ag{|}&y#7WSeTg1+#^1QyL;V%^pXIxf&(H<) zAL%5xo(N~CrPQHy#2t5}{ZW*D>9WW)4M_HVc$sfX_KmyD@*2Ofuw>ta%MVzReVrW- z{L#Am#>*X9X-Tqg+2uhc!%O;?B-z&8o$O1#^6}~Zpgw+i&*>txC@bK5N5N@V0!wF= zH7qZtF4>poIP!<9!-UJK%+|;y=W_O-%;~FpY3dZ@_R%G=s^K&h! zvW)2^NxpJNn`^i6lC6(jJ0keW6}Rzc`SKM%a2M|)CFc(Qv#X8Z4{=^3t5y6RenO5? z_ygSO`b6P3bFR4jYCcL3S%;L*xx6}l2j?Ey+rT^V{jNC%eh=rd(jCShQt8Z5a!feS z;uiT>I8Wsn@`Z4o%Om8TaGoxvU6-D4ehZ%@QzQ5!VYx2LBY24jzb^Mj@EQCo**TK` zi&x9_k^H{cXRc-5bL%~$dcT#pDzUgkvpUf?QD#K(L89w5IWvl{joR15@-%gQPAdvc3f@A`nK#C!=KH+CqOI#s|BogAvEPsFxiAa zOtX+t@@x$6z+1`0Sl%_fq$0zc& zVM&*C5TqdAc*&D^e4j*L)+J{j!HP@78`Db?eVR)Oa!I`O8fXJblsEV$lds9IW~^q;e3@p>S|0vUGg7Yu_=5UPdFdw6%kCs{3y?nnpVu@YrH1sr}7?2yU{S+brz<) z=D)ZV{%`9188J|3_ci%VDj%PA^;-L!E?H*wTqRrQKKl!=a~yk_!QuE}~cZ_8WDhzy=#j6>wHKO^}y z*&~Cm7B63w-(>I{4V~OJ9g~_&eu>9Oe4b43gBehmhp))~t@)$qw0m3gu2J=3kuVZaqsx!W!bFe&isEfOOK!a6savsk$CR~ol?48n)DXUZtlW)XjxjK)Jj~sW& z(y?oqg&8tTzHcu{kl*t8rT|rm0{D~Ogo==W{?w){c9!1YyIuHtA~ zC))AW;>@*`?RjR}$Jb7ut}Pipd{Xg)4;D`v^}63*_72Zbv+{de`SxFv*7m$mym(E{ zYR?bz&t$(2ydy@iM>_Dg`OmVAg{O0k9Ax3`_$Tra3m=y>vx#M!nYPBa^Zk-7C9jn@ zOMJW9bZq6@)FjVa_;O)BA?J7G*(s}=l(eWiwybwa9=ioC!hdnjbv4>WE8oSd^23h2 zFw%XscS>B{^b*x;t$Z7Rvfirn3TR&iC96mlDXPrh2n`|&06mqPv=?=34j@fXA& zS7b^Ne}=y$-zef&d7ON;Gw&|Em*tP0k)+<$?yYkyOnrK&Kg%;B?s?9BYP+Wp`ec-I3E23DPLt?tPm7L-R!FU%=5E_*Mo z<)vj;S(ZR=DxaRlIOBE>N;i6nt7}ZuT%9e>&MJZr|A}zVWr^f7$uLDV5%;X)B5qg+#%oW z2eZB?zwE~!$tA8yNnE@JkP1d%2c^W658)3dy>o3uN%Hg;`g)G%X?vAm1n%v>_^<0H zPb2=Bp?rKob9x=hM)`#DxIUEc5OLS!j@x*4!n}fD9)IO={dOC=6o1h*Vi-Tc`?V-i zK%uozwh78L!OS~>aJ;xEr^193?}p6qgQ zh@-1Fs8HdEmJnb2{A#HD4SGwAJQocQjcaTda@f3c)d~FgR(Q7=SXseQfT}KzoQ{KA}_Vo)&(}8wp zi*OBUyh|n*{qN>tEufpq#mK3$$6Y*u50s1A+?wP_{ z6}|(K8fM&#b9BmZJ2sM}DybY)mj`!t*zJN9^4xHp!%xZQ zrtw=->xSYG!FkkucPNuX2p%N(M1LwPCbQxAIpUC^l zc!!AfgIQxtD7zQsYh`?I1eKw=sWiAAd4SL1(OR&%LTq&TsFT?C+|GY>-SH5gh;JF? zu36Z+{3_kEpzmVIXJfhhgv_7K)71|Qf(7MI)6lw3%X?Oo=2jfpFhG= zh52Q9?h!tekCa^>Uc}}zgSu0;4c$IeT58oC zrKHlTpk$hBsgqCRyhQ%Kp0B|m^4v>Y@;Nep11ezo-E!y#UWkQX#RlG!SI9jZc%|Y* zjmq*VSlCS1$nkBlyn7>>%q6*WBfk}U-%mI4Mr`0*+h68|D)OA$#6Q&Y_g!yp!Pc3! zcAl-M)HzbWjgO%CJGb#n!Jl+hY{!bt&K~Dt`aCYqul~=df9yuwyub18`&*dg)U=?T zY~lZhJSK`bC~(|;YtGn-a1$^XyuL@dXbZPlm=Sazu(m};%?kJ)bB%wO zU+4Ti*SPoj`wDO6im&AtIe$S$e8}zm5!ccW`D2_XN&P%>96m-BDsx-a=B=tFncVa@b|>-Rd0QoPDF=`hAm-c>F=f<&qE+7a%!C0ueb z3ut!9ziK6n^uOQ?;?AseeRh-^RQgmLvN9Z%FLr%*3~f|wyG?4o;n&mfC`Ig83+n>e z>oD>nJOl7mbCKtincwpH_Qmjbc@fqH`T!Je2GRc$h__|j$dH_tbkpB>TJned69bu1 zpe;ZNnlo=!jA$X|KV8a<=*^i@e6znLzv)Fe|0ExsP=)v%fDP%E1N(tXFS>p{iEV_b zd_CqTfZQn|kYCpQfE~$!ANbsSY7lu`5jz=N8rm=ly^q&uDH!fexImhR(`tqezu9$P zJqA)9FMoCOiT2Geb8+<3AZlCqiB{SoydVCWSAu+-;O-3hkH3l@@n4`hkH5M0K<545 z3JRXSiHoAwQB;JR@wWt`EqIz~ecrv{C))B|!SIsW8+6^i8~)~WH(Yx#vZVs0e^a0c z84}GF%6M?dwQdIu3e@bp5l0HtZQx>43k9-63J{$>!O2Ete4T{}(Xz~|iUVOfYDW93 zzi}j6iWdV;_m?hr1OK-^_0>JWE1Ial3xxUxHR5O%ZNlx-GxFD;Fb`J9h@UZWFLQPL z867?1LThv~v$Mh9+1c>9-17^M)sHnV^@OwM&!owUUod=c3s6%#L-br^H)}VtFk?2b z-~pd;DIOX-<(7uauWHqMG0CdO<7R;M^+v>c#CmU#=%7MqVT5svKt!mHZp|ok5J@`()=ZF`2(1 zUkDSu`D*zcg?^UB;i4awu1|)Gem-j`1xJI6cg0QD#s!?pfoVUk_1pQ=wG~(LI714-GmM5Y`atxK2O1TJF3oN-V zH8El#6j&Mq<|FcQjChE|#)_x0puZd|Mqo)bBu?aFn4TRcuyK+f#X&1bj~9!uL3leJ z<-aC}C5T%|N`jyj*J}wV%~$f*1hF?_WHxJzKm(vEPLO+Ai4K@?e{CgV6aSrhV;Mmm zpVlz61W9zInnVZDofcXxmmN1{-r(QVV%hOe^lJHJl1OehC!RH0;&8!K8r-?eK$zim zs|yz!DYHN~N-y08UxPS>F%eCNkUxDKU=C~?zf*ryaLpFY4g`1b)_;NOg_X>(>y z!8Ibnv^uIm+;QOib(xSZa`8UaH8lB|D^^l zHlN}`0Vv!IqW>olZ_Bv2kertEEZjthA4tmCQSAMRrb9>c!%x+o{z^WF0qP1-icEVr&Q;>Hq+)a%^|Hz-YnDAeq zIgh`&_CGVHh@%j+%y&bfzcK%Xm*Toz{44LKtHE&5^&9jZJXpAYmSz8IBq>nyHwBy_ z+5xyEWJk#Db^#@a0{gCT(Hut#Fj#723k7r`D-vCWQJx#?P8Fapy+CiYWa|R)7*Ch$ z3osy@wCPWZswQY4-yaZkL0kyVh{$?b%R9~wh(&;i-!_PJbh+h#26y1Pzd7*b^M>@ zkRf6sZPnfyBGND(9~>e&@ja3c75zYU4IC;2=QCYHZbNIrDEe+G2EXI7?=bN>-y)-j zi#KHLaIuWHk;6t{l%FE6jS$JBR=wYYnVs&h<;x>6)E<=X zk-`xIF93(R){han`LQ8&EGqh88mIeVXl#HgVNhu^{Hr>q<4KaU zVT1g2jJO#SR{mI#9zPy2G(%H)>FXT>QZABrj1`?CTBAH;Ei}bD&dibP#)?+_oP1|2 z(%vh78Y`0XCsW#GNL%i7|425o;>VIeYqlL}L7y57mmSBUeQl9L;6(Jbs7bN7ht94m_T|H3lkS6Ms*Z6!yJn}Gp; zf?PjC%;B3|iT7cFgARMgOt>fI`k83DJ>|ifShRd1f2Yt+nQ=c7X3MVkgZQAFbia5N z*XjB)F zorlEx7&qhtv$3YRORk?Se&B0m#lxbXhDuQ7cYX1&DB)-=@pDn%JLG`5BDp#0-nk-D zGzXq|R3z}o8f=0dK-Uc=e(5oBQ_vPCU<*j|%o77ez&M5A0^ugRxFyJ8zyhYqFCQ%z zJ+M%Fw_JRJTcL^yF;Rc`T{LkNVU0Xnf#v4{Sv(*8Y_oi1J}fa#uAeWy{;0C9@m0r#nZSSdRfLiFNPcF_-i?^QOKFkiv$se$_u$KJ}(OR z5AxIJ#qKoIXnaCCN{ExdeqaZ%30MWp8|8Y%0W+o5sTI){*r_PO25eL*;tXUPHTWh! zRf-i@VtgiBuRwV|lzqv0Pu{&kWJM0dA>C0h9tY}$TuF>C%Xh(1xNbR$g3gS)AG||$ zx=lF8UIiLW2J|BUbe8?s zQoUOAPW;zil0U|M0go@WFcp1UMGf>NIcc?+XrNSdwlZal{A{(jC3UzXs1DBh@e^ZC zcNa?T#7G2xXPL1Eby6ZbuMr&#vyjqxk0PdTku%qbOmd%JBOWC;a;+Gs!d;WReXUqe zgzIa?7vz4iPRu8F_={p@lntw3`rSVI{XYEGpZxMgQ4xr&7CC{`k5!A-`~$hZ8pG(r z^1Eux+xJQC#0Keod505|`2hKv6U5KtK_{A2sT{Xnq<4-AZ6|L*+n{YE$InF2&qqal zNH30@ZnBRCJltCDA^%Cl3Hj!Fu@xsplU@?ZNk_YoN|HiJ>^OUcX5^Z71{W#O(#WQe(CF5)!6)L5;I3% zR-Xw*ta;`}rgs>ErR)E0NJxmM*N$MgG9>(1DD#yq6uv_nOndN+An&1&W!Cs_$k*F- zK_(-ZnoIiAyTQ`m8cH|_C2EfQ^(vm6gsk*p{0e$Xbn8 zgWf4R_ZWj7LNNZgSg|30t9N!uWkl@WN>d~tSD$*rng@40s=KmdWjtbRa zS@XHtw0*NU`vEU^ox4{xS#3|8Q&dp&K#>neI>rbkvfY5jorS+ecHQ9PK7L1!a1~R9 zx9M&Pv*B3y3ae6DXDOO#O22NYouh1KZRA2_qE7#%xz&_uQRb)@jJfR=TD8uSO`@ou z5QzB@MN=b>Z-V}SGMq7TnUDsOSu|=J^-KI+tN^WPS)tR`GXVj*v z#Ncxjwh4lZwXJG{O>u&#=6$xw~lxk^V>(YWoOd$_4&+)*H6O>*`*9iIv!>C!+Pf#d)jP<0-iIe zXRWbXGq7{#9EGbk8MV1qZK{ajsYMZ)8k<&iA$n}8=1~*ZM6!v`7w0G{dzR)!pVp^! zY70G@gRHDwY?0=xv>2=AyObE~ZjCo9#+vXG@Oz9k$A0aUuuk$9T5X*Rt-Q0N&??{& zg@sn*#T7AD!4a6*6LW87cYPu6o@~hE-Luki@o!r9OwP3RncS$|HYZv@^84mDtvmD#R%n_g#Wue0eQ!iqW#HgVf8?h#+l(S_l$3%ci(Oe@oNP(_(sd2wG-+%mN> zsURlmnF6Ct|Ac`*7t?{Lixx!|$A6$3s7)?KT3iMnY~ zT>eS3J+gm}&+hAav42!rneoQxs4O0nn=>>>iph?SR#|dm zBA>#}o0Su>yD55h-duC8Q9CII&y#E)Xm{sm>U=$?j>~Ecdz&xLxvxO4jXx5Z8r?T4 zYFn-?GCm<;)}mjLFHbBsmS@ICMGc%CPHLR}B>m1g_Q>D-&(-xbg?H_wJ zSmbL*MpV*U@d#s4tJX3ORpu8N2-sFYk&L3wz>Bc`Gpp}Q#Bs1hv&;a26RU$|mcR7S;MQ+T{;U8XSF zcx-q=mMSa#U|ODPo<5g9!#t6?MYT-ZDD6hQO{;Jbrp`~|iuP88=cRI$P1oM2)nN^T zkx-+z%{LrL<=UKx`ks+S6*uYJaYYffqVU#Ay1`{IY72B0Ta@W?UN@bMixK*`ceOwN zPjZGnP5)r8&YDqKNnC5znv6DG$Hbd5u$t~2me|8!Q$-|}H2u#gdl)N^=DZCn*DKX` zw-4*Wv^klqJUqfI!`mpSVwsAS$2bq~wnenlm_8Qi(FVg{Ls;8XLpV<^%1Y{%l-#CU z`^Kk>s>h%Z;n50Diqy?%SEJ+__^nJEohVdFdV3w$v-fO5;XJ&1K}0u|{?qQ2g~f;4J|0u7EiC4|usG^orLee;Yelh6RW3TD>Qw_&`YLfS{-oNu)KF^D+C;H} z1Lmi`jIsW5j4QdPBED%GryQxyZp_K*oF}ZkroGdll*=o-#m&-OE23q=9M$jg=j%eR zu?_d#Yz>p`=c?%G+Ffiio5C{guJv^-*UCHQs!R#&0rnt!h|OY;&-Qhsmh9s;J(EL) zDw|}P6f5uE-Sx>_)t+@@yWuS-e%6?E-^E09EfcBxm{VVI~Fu z2amvi6u&$6H52&Gk?lIp#C<22co*pW4HJD4e&ll|ya$5cCB!^5h52ic!E7u{D5GMX zG_+E_w?BNHiB*8r&%{(yZCQ$%{>1{*ZyZ_Ed@1a+>+MpKl&dOX&<70 z0A**+o-qT4WHaxdJn5n7j7`3OCac0LL83MPoxO$?7jsmq#>ZU8I!VELCK9*=|IcdI z@I)n&>uB*zfAlNvuJR=1lv&g|T~lvW=Ff@!x2g*>@68*tsa5j#Erd98Ap>y=f?P4!VYsxAo%F=HD^&!}m~{l7#0 zd`h{~wfskAhp_i~4ZkN23=Ux=T*8D9robi42w@gn!n_cw;1ZUEupBO7Z3r9T5;ljh z4K8745O%Q-9>ReTj>09J4B-@9!ub#`z$G+=px|DMMLnwkv=oUbK zlpY?!;1EW_B}@om3S7dB5N5$8%nP9kZq@5@;8`U}L$^vb*X6xul{-}v+D5rPKdX$= zS~uOJi2n;{we8yctCFXL-`GAXBKYI~@|apZ%z=s0m8VfF++IGE@$A5whjKcVT@0Qe;M3*U<&*;U;H3@m1UL!*dAOEBSO_?da24D-;1X~Y;TfHvEKmpk0boC1EP{f-KKM7ntpjS| z-wEshvOA-?0sA%tY5;Z<H?s3oJqS0Nf^^PglklBU}ZP!e2fH^*;}RRR|mfif(~c2$#XF0erwLge|v1 zAz&>~hVTKn=5B}sW+05;0_CResME118L$@q^FX&A;6r!`+_mKIiTX#l6z)-AtQGZd z0^y_;4W}4w0DdFjg#QB2zZcpA!mHrc0p{K)J;Gz*)&hBb&;}4*0{0}q;BSILmw*|4 zkp{Q`zoi6L1$^+I2l|7r4q==R4;1CxDD@P6Sbi6!Zl$Fk|HAK|x~@j4*YS9Z&U!A&T#KLf#&_K~sH8`{PWfiE z`q{!K)$Cj(j`4^z81Hx&vE5w;-yakZQoqfWC=COXcjDBTqJ=?A@{jFBEr zKTUzl5~6>qVdv<#*wX(--wXQD5S@XaE?08k*y3iT?;p^#E)v=D{cHjMt>Zl zW}@_ET6)$trUA#m96v*XACUW&8*_#ShfyfJ07l5;V3DI%SKW=2FsK3Cy|1sCs9o1=^4|e@tsGbH_ z-ch9P0B32Dx{Z3|HG>!|cNMAU;C*$V+sa!zs~0o}T%UASuZxPNU$G8F3&`gSU92i}w#vq=`??)D-I~DsVPI&x8jE(=#LIzUwx!0aLQZyXw$ig nBl=8)0oc1Z(2wXCCAtGkfp-wr!wn<~{^MApdf}Dt)d~L}d`_X+ diff --git a/Makefile b/Makefile index a8b5805..81d4265 100644 --- a/Makefile +++ b/Makefile @@ -1,4 +1,4 @@ -VERSION=3.0 +VERSION=3.1 TARGNAME=A7800DS #--------------------------------------------------------------------------------- diff --git a/arm9/gfx/pdev_bg0.png b/arm9/gfx/pdev_bg0.png index 17de91ac1e2bd1720142a87dc66c3e31cfcdb3cd..7a8762ef342ca711de5054302bbaabf354c4d973 100644 GIT binary patch delta 2113 zcmaKtX*kpi1I7O{W9-Y=C;JGYYiwDv)M$9Jgj}KqLzZzX%Ov4W!~Dq>jXflVtm(#x zn`#ic*+r%z>%^5I3|V3pts*wY!cVqK%o_*JihDW(N@oiflTmt0sWGQx zImdl3-b?n!yzD9y8bv+3B1AOpq^Sc-s*SVf!yuYzjw7X_CoRDcC2AbvsW5*D|1X&H zwp7^3PiRf~Gn=m!zze}7)l$m#62M1H9(=E0F%+i=t=~eZ@U|G;pdK4_iZcH&-U1Ve zVAJ?w8lvK-C&l+Pmr(~#AbyVdgYxigk5Hma54UxnD}$MC3Sk_hPuA9ct*WZpB<=e$ zEGsG;*R|$e*+9-sxGqt-I_whPb)JH3b zD^fw&rdxr6s<_3`JT2UTUnqPrF)tO$HS-*EX)$b`K!Re@#{E!h=3pDUdXf?eNMly8 zp}u!q7oI=?Yl>)p{}9H0G$Q4|YJ5~NoG1FO7BN(&q=D*wxUJ^3HJs84=~t->MS>i% z$!)R%^qtV(1$`(I42WJ6z%;k%KsBS=)6CuG?Pzj^`1=s@qImifdJjs^ixo?3m)A`t zG;84TvODet5G437ru=LAUm=q#yqc-;2^;q1l7Bz?f}h>B{92am-g?6Dx6AkA=^LYuBcpFaM7cFbj;X&Z{P2z9%!T}(D(VA+LNQHpD&$ano2FJ4k6nM zQl3^y6x7{u0~S_|@lY@WifDKthI0nAQZzTMLaPZcyh6PZ3x}9Su$DDnW2IZ0R4PI+ zMbRZM>QQdbWITX|I*L~w?! z1|EkLrH`r+=?k{>o1;be^>?&)mxCUUrD0ro{LT3CDzCk+v}mldPd=58+% zizG4ge{CAAffmWi?rGY~dGK^-9RXdRU~0SCv73|y@0|!UBMPoM3b^+ZgH?|8wg0Tp z`L3#Wf!cpk7}&$aneR!+?44r4TG^-ff|o`+n{<`2#5o=sLq&O-AXbG1=NXUoWqf1A ze@g{Vhg8%YE_iS>Q;;nPR8KnB+KzlZM9BTaxoSkpVvohBsS&H4XzVr=i35``<{OGN z+*DwkK@m98`5o&U^@D&pBCIkTPJ+(qp-&(&<%4{?dCLkzJ4_QF2a!uA1CVfkL4D}Z z`RV78i==z7fPEaDd7KUO+mvWQ?-LV8cz2`QWlZur7S2fOat}&@4?BsqP*2O-iAuXk zZuW4|)|h6p2w-{|P1N=ne8xT-6Vc`ooJ({cpadLx!tMH?!RzNQq9Vp35-fe7g#e zkM7CC+OBJ?K$PKn8ROhjx!>k927j616hcJ9zN>LBY7<-Nu72wcBp-_@$}s>xk7Mvn zIq$jstelTzXVi5@rO3aV25~yU@!L>YeHi{862fjc3E<#%k{{YSqAkCQ?!3 z988)ya22aAFv%wZkEFXwHn z8s)wft9!W2(?gEo;I%zq6Rl~Woc%HDoXUzrDZx-D&vfR>0wtnisKb0FZcWL-2^r`i z3WtP7rIUMK>z$#o>P!W;WV0TkhQ6d~v|FO_Wrw1Bmy_-KB!7MBXS_9sgjS4qM3S#2 zU(<+8$Er(h`>eLD3ZE5*$9bRV)-H#`WKftDFYDeUOvXrrv}trE`|Y$FnkY~_qixJv zR~gjfk)6b$G`zQIxN-R{fLna|9aRxHG|hUod=?=F-1EM0;)Lzy#v9om#S9==g&J1s z#3YVf+!%GlNNx@BM*`7kfS}YJgcF=ew@Ona07MufvYvf2Q`|AWRHvGlaS>(f!~Gnr zWxa8 zTviC&)+w=@6CRrV&BJQ{Ct%F|W*qd-eQN&e7Tt;LS7JZD;{OH*a}ETM{6)O)gs>98 O582r`S=XNOjsFKKaoGw0 delta 2093 zcmV+|2-5fQ7oixiSOZk$3kC}_BpllyTmS$Fr%6OXRCwC$+zE5yI2Hil(c#T^8-P*$3dUOD^d z0DI6$0xtFI!vVWEe(2Hy91hre0`P#+SlBhShk6S@S!}uvb@<@{Z1ZRggpg%G07YN{!a`~s_{nBQ*=1~xhX66?joE3W!FIZvvECjXXrOC{9q60A68!3l;9F@2@lOp9 zYg#^U6yT3s;LMW$fBXL>fWYLl;$=~$CUpl-7VMa<=vO1 zY5L}vho{YO5CyjH@u`15eB%|q|6@ge2~TH>XH_?tx~}8hAOkP}16(IS={WS@OvZxO z+&9t>D?cWH0$3Q+f-^jS&3z;Nu=0Zf;Eu>2Th_LH4j(CJ|MjJ&|GPne5+d5_*p?~U z{$g$c>Y28R0{>cD+ETsKKin9A4<$Ct0z}|Xz;CJDzqbG-K<-0sV3AYltpWgPL=H?$ z-#|*(bcp^%&#^n?2=F{n;M^=gYa6WwfJKXm3VweDm_T0MFaY)WwjcR81fpliF_%O1 z3IOoz6M%SzTLe(>jEg&z=Si^an_iv)eCiR7t-Hw~&@Xh~Sn!5L(F|+i<+{k1!jr)R zNPmAZzD z+!iHyM$ujaog?6DDtgmA*_r)B3!VHroJJQb6(8OKpmXgH!Dg-~v0?PH(3pM!sTM;G zWG>wbrq;Ud@R&-8sVSu_$5+C0Ls%&$q`_u#oh7r5<=Ke&FMrRuzy^R z0H*^s3EXykr9D8bPse;PthL(Os^%il7{QpyRs z)3U7gu3R_BGY)}(hCtKz9jgC~0GrbZC&sr!V0#g0j6iP~K&0iy0#Lu{3xCb59|E&? z83O6k-k!3Z16m*a`twpl+KzL8T$@4+05sOuuARDG=Kxt9D;GTH4S=}_G)AB|T;SSZ zZ!g%?$KzZ$t*PU=d6IS#e0rZb;QT9$v=Y0z>tO5@) z9f93AIM;_=AV9cD+kF9W5onBH-!TKv-Y99|N#W#wH|2wl%u5%`_qh<_OW~gw0IoA} z4|p$tY25q|qAb6E`^+M)t{GrI&eDH66}aEsDzW}vy)Pba8UWY1#(#8y_uYOJTsweD z(`7eJcEfiU^JHt*X>E#RHce-(eQxr!G4)-JxoV!}+vl9J%{1E(fQ*wePusDeny1<0 z7{1CfS1h-0BK3i;2Y{yFfbNgI6m(zo7`H4T+!;^MM#-t^d8M3YApyj+(Zi%I@2LPU zj%zAO=sKt`u+L$*>3?QUUyg_(xQvw9Kvx7HCYcfuHhyAvYlZM@2coUg*>vu}^d4(+ z2yx##NrZmVDhokp0eD(Oi4p}~1I`{c2+;HeIUX?){kXyx#km&C#YH5)57b=I5ZE0j z5IS<{(WNVm={auvrXt)InGZ?h$TAS0mO@P?TFi08SJG*hLVx3y7GD_eu;heMw#&XC zz~`+aAM-E_6D;}_C&BI_Qq%`pU(qDE!_8|n0Z+MIKWTYFN>@yVz8piKbW_-lFYa*8 z#LlrVg#!NtUl^VNioPJQ+Xq>Ov|+#^1jwC>NLe4~;hI)~y$AXB{7vNyx9}w7q_hqC2mQC{3*sJNyZBy)O};Oo*HJRD*ElxLPpU)9qsVJ|92o0l=##N(Qtr zdN`^Hz}NzsRL%e$j&>DPZzA=9u5C9MC{UZ9cstzr!d>$B0Sv$Z48Q;kzyJ*Janip5 XVy2dJXXHq-00000NkvXXu0mjfbglME diff --git a/arm9/source/a7800utils.c b/arm9/source/a7800utils.c index 274dee7..fbf6778 100644 --- a/arm9/source/a7800utils.c +++ b/arm9/source/a7800utils.c @@ -96,40 +96,50 @@ static void DumpDebugData(void) #endif } - -u16 sampleExtender[256] = {0}; -u16 *aptr __attribute__((section(".dtcm"))) = (u16*)((u32)&sound_buffer[0] + 0xA000000); -u16 *bptr __attribute__((section(".dtcm"))) = (u16*)((u32)&sound_buffer[2] + 0xA000000); - u16 myTiaBufIdx __attribute__((section(".dtcm"))) = 0; -void VsoundHandler(void) +u8* snd_ptr __attribute__((section(".dtcm"))) = (u8*)((u32)sound_buffer + 0xA000000); +u8* snd_sta __attribute__((section(".dtcm"))) = (u8*)((u32)sound_buffer + 0xA000000); +u8* snd_end __attribute__((section(".dtcm"))) = (u8*)((u32)sound_buffer + 0xA000000 + SNDLENGTH); +ITCM_CODE void VsoundHandler(void) { extern unsigned char tia_buffer[]; extern u16 tiaBufIdx; - // If there is a fresh sample... - if (myTiaBufIdx != tiaBufIdx) + for (u8 i=0; i<4; i++) { - u16 sample = sampleExtender[tia_buffer[myTiaBufIdx]]; - myTiaBufIdx = (myTiaBufIdx+1) & (SNDLENGTH-1); - *aptr = sample; - *bptr = sample; + // If there is a fresh sample... + if (myTiaBufIdx != tiaBufIdx) + { + lastSample = tia_buffer[myTiaBufIdx]; + myTiaBufIdx = (myTiaBufIdx+1) & (SNDLENGTH-1); + } + *snd_ptr++ = lastSample; + if (snd_ptr == snd_end) + { + snd_ptr = snd_sta; + } } } u16 myPokeyBufIdx __attribute__((section(".dtcm"))) = 0; -void VsoundHandler_Pokey(void) +ITCM_CODE void VsoundHandler_Pokey(void) { extern unsigned char pokey_buffer[]; extern u16 pokeyBufIdx; - // If there is a fresh Pokey sample... - if (myPokeyBufIdx != pokeyBufIdx) + for (u8 i=0; i<2; i++) { - u16 sample = sampleExtender[pokey_buffer[myPokeyBufIdx]]; - myPokeyBufIdx = (myPokeyBufIdx+1) & (SNDLENGTH-1); - *aptr = sample; - *bptr = sample; + // If there is a fresh Pokey sample... + if (myPokeyBufIdx != pokeyBufIdx) + { + lastPokeySample = pokey_buffer[myPokeyBufIdx]; + myPokeyBufIdx = (myPokeyBufIdx+1) & (SNDLENGTH-1); + } + *snd_ptr++ = lastPokeySample; + if (snd_ptr == snd_end) + { + snd_ptr = snd_sta; + } } } @@ -489,7 +499,8 @@ void dsDisplayFiles(unsigned int NoDebGame,u32 ucSel) unsigned int dsWaitForRom(void) { bool bDone=false, bRet=false; - u32 ucHaut=0x00, ucBas=0x00,ucSHaut=0x00, ucSBas=0x00,romSelected= 0, firstRomDisplay=0,nbRomPerPage, uNbRSPage, uLenFic=0,ucFlip=0, ucFlop=0; + u32 ucHaut=0x00, ucBas=0x00,ucSHaut=0x00, ucSBas=0x00,romSelected= 0, firstRomDisplay=0,nbRomPerPage, uNbRSPage, uLenFic=0; + s32 ucFlip=0, ucFlop=0; char szName[64]; decompress(bgFileSelTiles, bgGetGfxPtr(bg0b), LZ77Vram); @@ -511,6 +522,9 @@ unsigned int dsWaitForRom(void) dsDisplayFiles(firstRomDisplay,romSelected); while (!bDone) { if (keysCurrent() & KEY_UP) { + ucFlip = -50; + ucFlop = 0; + uLenFic = 0; if (!ucHaut) { ucFicAct = (ucFicAct>0 ? ucFicAct-1 : countpro-1); if (romSelected>uNbRSPage) { romSelected -= 1; } @@ -536,6 +550,9 @@ unsigned int dsWaitForRom(void) ucHaut = 0; } if (keysCurrent() & KEY_DOWN) { + ucFlip = -50; + ucFlop = 0; + uLenFic = 0; if (!ucBas) { ucFicAct = (ucFicAct< countpro-1 ? ucFicAct+1 : 0); if (romSelected 29) { ucFlip++; - if (ucFlip >= 8) { + if (ucFlip >= 20) { ucFlip = 0; uLenFic++; if ((uLenFic+29)>strlen(proromlist[ucFicAct].filename)) { ucFlop++; - if (ucFlop >= 8) { + if (ucFlop >= 20) { uLenFic=0; ucFlop = 0; } @@ -733,57 +750,42 @@ void dsInstallSoundEmuFIFO(void) { return; // We've been asked to not install sound... } - - for (int i=0; i<256; i++) - { - sampleExtender[i] = (i << 8); - } FifoMessage msg; msg.SoundPlay.data = &sound_buffer; - msg.SoundPlay.freq = (isDSiMode() ? 48000: 32000); + msg.SoundPlay.freq = (cartridge_pokey ? SOUND_FREQ+21:(SOUND_FREQ*2)+21); msg.SoundPlay.volume = 127; msg.SoundPlay.pan = 64; msg.SoundPlay.loop = 1; - msg.SoundPlay.format = ((1)<<4) | SoundFormat_16Bit; + msg.SoundPlay.format = ((1)<<4) | SoundFormat_8Bit; msg.SoundPlay.loopPoint = 0; - msg.SoundPlay.dataSize = 4 >> 2; + msg.SoundPlay.dataSize = SNDLENGTH >> 2; msg.type = EMUARM7_PLAY_SND; fifoSendDatamsg(FIFO_USER_01, sizeof(msg), (u8*)&msg); if (isDS_LITE) { - aptr = (u16*)((u32)&sound_buffer[0] + 0x00400000); - bptr = (u16*)((u32)&sound_buffer[2] + 0x00400000); + snd_ptr = (u8*)((u32)sound_buffer + 0x00400000); + snd_sta = (u8*)((u32)sound_buffer + 0x00400000); + snd_end = (u8*)((u32)sound_buffer + 0x00400000 + SNDLENGTH); } else { - aptr = (u16*)((u32)&sound_buffer[0] + 0xA000000); - bptr = (u16*)((u32)&sound_buffer[2] + 0xA000000); + snd_ptr = (u8*)((u32)sound_buffer + 0xA000000); + snd_sta = (u8*)((u32)sound_buffer + 0xA000000); + snd_end = (u8*)((u32)sound_buffer + 0xA000000 + SNDLENGTH); } + TIMER2_DATA = TIMER_FREQ(SOUND_FREQ/2); + TIMER2_CR = TIMER_DIV_1 | TIMER_IRQ_REQ | TIMER_ENABLE; if (cartridge_pokey) - { - TIMER2_DATA = TIMER_FREQ(SOUND_FREQ+3); - TIMER2_CR = TIMER_DIV_1 | TIMER_IRQ_REQ | TIMER_ENABLE; irqSet(IRQ_TIMER2, VsoundHandler_Pokey); - } else - { - if (isDSiMode()) - { - TIMER2_DATA = TIMER_FREQ((SOUND_FREQ*2)+3); // For the DSi we can run at the full 31KHz. - } - else - { - TIMER2_DATA = TIMER_FREQ((SOUND_FREQ)+3); // For the older DS-LITE we only run at 15.5KHz - } - TIMER2_CR = TIMER_DIV_1 | TIMER_IRQ_REQ | TIMER_ENABLE; irqSet(IRQ_TIMER2, VsoundHandler); - } irqEnable(IRQ_TIMER2); } + void dsMainLoop(void) { static int lcd_swap_counter=0; diff --git a/arm9/source/emu/Cartridge.c b/arm9/source/emu/Cartridge.c index 95c3a9e..b6bdc69 100644 --- a/arm9/source/emu/Cartridge.c +++ b/arm9/source/emu/Cartridge.c @@ -48,7 +48,7 @@ uint cartridge_diff1 = DIFF_A; uint cartridge_diff2 = DIFF_A; extern int debug[]; -static byte* cartridge_buffer __attribute__((section(".dtcm"))) = NULL; +static byte cartridge_buffer[512 * 1024] ALIGN(32); static uint cartridge_size __attribute__((section(".dtcm"))) = 0; static uint maxbank = 9; @@ -93,9 +93,13 @@ inline static void cartridge_WriteBank(word address, byte bank) { last_bank = bank; uint offset = cartridge_GetBank(bank) * 16384; - if(offset < cartridge_size) { - memory_WriteROMFast(address, (16384/4), cartridge_buffer + offset); - cartridge_bank = bank; + if(offset < cartridge_size) + { + if (offset < (256*1024)) // If we are in fast VRAM memory + memory_WriteROM_DMA((u32*)&memory_ram[address], (u32*)(0x06860000 + offset), 16384); + else // Normal memory + memory_WriteROMFast(address, (16384/4), cartridge_buffer + offset); + cartridge_bank = bank; } } } @@ -201,7 +205,7 @@ static bool _cartridge_Load(const byte* data, uint size) uint offset = 0; if(cartridge_HasHeader(header)) { - cartridge_ReadHeader(header); + cartridge_ReadHeader(header); // cartridge_size will get filled in from this size -= 128; offset = 128; } @@ -211,10 +215,15 @@ static bool _cartridge_Load(const byte* data, uint size) cartridge_size = size; } - if (cartridge_size <= (144 * 1024)) - cartridge_buffer = (byte *) 0x06860000; // If smaller than 144k (98% of all carts are), we can use the VRAM buffer since it's faster to move stuff around... - else - cartridge_buffer = (byte *) malloc(cartridge_size); // Otherwise allocate memory + // ----------------------------------------------------------------------------- + // Copy up to 256K bytes of cart into the fast memory - used for bank swap only + // ----------------------------------------------------------------------------- + u32 *fast_mem = (u32*)0x06860000; + memcpy(fast_mem, &data[offset], (256 * 1024)); + + // ---------------------------------------------------- + // And copy the full ROM into the main cart area... + // ---------------------------------------------------- for(index = 0; index < cartridge_size; index++) { cartridge_buffer[index] = data[index + offset]; } @@ -410,13 +419,7 @@ void cartridge_Release( ) { // Snap out the High Score SRAM (if used) cartridge_SaveHighScoreSram(); - - if ((u32)cartridge_buffer != 0x06860000) - { - free(cartridge_buffer); - } cartridge_size = 0; - cartridge_buffer = NULL; // These values need to be reset so that moving between carts works // consistently. This seems to be a ProSystem emulator bug. diff --git a/arm9/source/emu/Database.c b/arm9/source/emu/Database.c index d88c311..c30dc39 100644 --- a/arm9/source/emu/Database.c +++ b/arm9/source/emu/Database.c @@ -119,7 +119,8 @@ Database_Entry game_list[] = { {"220121f771fc4b98cef97dc040e8d378", "Ninja Golf", CT_SUPROM, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_NO, 10, 22, 270, 220}, // title=Ninja Golf {"74569571a208f8b0b1ccfb22d7c914e1", "One On One", CT_NORMAL, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_NO, 0, 12, 256, 220}, // title=One On One {"5013b69cb05b21a1194ce48517df7bfc", "Pac-Man Collection", CT_NORMAL, POKEY_AT_4000, JOY, JOY, DIFF_B, DIFF_B, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_YES, 0, 19, 256, 216}, // title=Pac-Man Collection (homebrew) - {"a59d362e3a391ff1482131aa0818ad3e", "Pac-Man XM", CT_SUPCAR, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_YES, 9, 25, 278, 220}, // title=Pac-Man Collection 40th Anniversary Edition (homebrew) + {"a59d362e3a391ff1482131aa0818ad3e", "Pac-Man 40th", CT_SUPCAR, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_YES, 9, 25, 278, 220}, // title=Pac-Man Collection 40th Anniversary Edition (homebrew) + {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx", "PMC", CT_SUPCAR, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_YES, 9, 25, 278, 220}, // title=Pac-Man Collection 40th Anniversary Edition (homebrew) {"1a5207870dec6fae9111cb747e20d8e3", "Pete Rose Baseball", CT_NORMAL, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_NO, 0, 22, 256, 220}, // title=Pete Rose Baseball {"ec206c8db4316eb1ebce9fc960da7d8f", "Pit Fighter", CT_SUPROM, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_NO, 0, 22, 256, 220}, // title=Pit Fighter {"33aea1e2b6634a1dec8c7006d9afda22", "Planet Smashers", CT_SUPROM, POKEY_NONE, JOY, JOY, DIFF_A, DIFF_A, NTSC, STEAL_CYCLE, USES_WSYNC, HSC_NO, 0, 18, 256, 226}, // title=Planet Smashers diff --git a/arm9/source/emu/Memory.c b/arm9/source/emu/Memory.c index 50376c7..ce82a5d 100644 --- a/arm9/source/emu/Memory.c +++ b/arm9/source/emu/Memory.c @@ -250,6 +250,23 @@ ITCM_CODE void memory_WriteROMFast(word address, word size, const byte* data) } } +// ---------------------------------------------------------------------------- +// WriteROMFast (assumes memory_rom[] already set properly) +// size is already in multiples of u32 dwords +// ---------------------------------------------------------------------------- +ITCM_CODE void memory_WriteROM_DMA(u32 *dest, u32 *src, u32 size) +{ + // ------------------------------------------------------------------------- + // DMA is holding up the bus for sound so we do a mix of DMA and memcpy() + // which is a slight improvement but keeps the sound engine mostly running. + // ------------------------------------------------------------------------- + DC_InvalidateRange(dest, 4096); + dmaCopyWordsAsynch(3, src, dest, 4096); + memcpy(dest+(4096>>2), src+(4096>>2), size-4096); + while (dmaBusy(3)) asm("nop"); +} + + // ---------------------------------------------------------------------------- // ClearROM // ---------------------------------------------------------------------------- diff --git a/arm9/source/emu/Memory.h b/arm9/source/emu/Memory.h index 9097921..d8c5903 100644 --- a/arm9/source/emu/Memory.h +++ b/arm9/source/emu/Memory.h @@ -40,6 +40,7 @@ extern ITCM_CODE void memory_Write(word address, byte data); extern void memory_WriteROM(word address, word size, const byte* data); extern void memory_WriteROMFast(word address, word size, const byte* data); +extern void memory_WriteROM_DMA(u32 *dest, u32 *src, u32 size); extern void memory_WriteROM32(word address, word size, const byte* data); extern void memory_ClearROM(word address, word size); extern byte memory_ram[MEMORY_SIZE]; diff --git a/arm9/source/emu/ProSystem.c b/arm9/source/emu/ProSystem.c index fd70d8e..e3efb82 100644 --- a/arm9/source/emu/ProSystem.c +++ b/arm9/source/emu/ProSystem.c @@ -132,7 +132,7 @@ ITCM_CODE void prosystem_ExecuteFrame(const byte* input) // -------------------------------------------------------------------- pokey_Process(1); pokey_Scanline(); - } else tia_Process(isDSiMode() ? 2:1); // If all we have to deal with is the TIA, we can do so at 31KHz unless we are older DS-LITE in which case we run at 15.5KHz + } else tia_Process(2); // If all we have to deal with is the TIA, we can do so at 31KHz } } diff --git a/readme.txt b/readme.txt index 8d0f3cb..1c6ded0 100644 --- a/readme.txt +++ b/readme.txt @@ -37,6 +37,11 @@ Philosophy : -------------------------------------------------------------------------------- History : -------------------------------------------------------------------------------- +V3.1 : 31-Jan-2022 by wavemotion-dave + * Now using more VRAM for bank swapping and partial DMA transfer to speed up large games. + * Reverted part of the sound core to improve sound quality. + * File selection cleanups to scroll less fast and be generally easier to see. + V3.0 : 06-Nov-2021 by wavemotion-dave * Reworked sound output core so it's now zinger-free! * Refresh of bottom screen - improved font and button debounce.