https://github.com/qemu/qemu
Raw File
Tip revision: d1b725ee12539906b72777fde1f6c73c2273d806 authored by Michael Roth on 20 April 2017, 21:14:52 UTC
Update version for 2.8.1.1 release
Tip revision: d1b725e
slof.bin
؈(headermagic123
´¸aikqemu0 	X1Jµ³ÿÿÿÿÿÿÿÿÃ@Ã(stage1H?Þ­¾à?||C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦èà|	¦8€N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦èà|	¦8€N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦èà|	¦8€N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8	N€ A@|C¦|	¦|C¦|¦|C¦è	`|	¦8
N€ A@|C¦|	¦|C¦|¦|C¦è
`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8
N€ A@|C¦|	¦|C¦|¦|C¦è
`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8N€ A@|C¦|	¦|C¦|¦|C¦è`|	¦8 N€ A@|C¦|	¦|C¦|¦|C¦è `|	¦8!N€ A@|C¦|	¦|C¦|¦|C¦è!`|	¦8"N€ A@|C¦|	¦|C¦|¦|C¦è"`|	¦8#N€ A@|C¦|	¦|C¦|¦|C¦è#`|	¦8$N€ A@|C¦|	¦|C¦|¦|C¦è$`|	¦8%N€ A@|C¦|	¦|C¦|¦|C¦è%`|	¦8&N€ A@|C¦|	¦|C¦|¦|C¦è&`|	¦8'N€ A@|C¦|	¦|C¦|¦|C¦è'`|	¦8(N€ A@|C¦|	¦|C¦|¦|C¦è(`|	¦8)N€ A@|C¦|	¦|C¦|¦|C¦è)`|	¦8*N€ A@|C¦|	¦|C¦|¦|C¦è*`|	¦8+N€ A@|C¦|	¦|C¦|¦|C¦è+`|	¦8,N€ A@|C¦|	¦|C¦|¦|C¦è,`|	¦8-N€ A@|C¦|	¦|C¦|¦|C¦è-`|	¦8.N€ A@|C¦|	¦|C¦|¦|C¦è.`|	¦8/N€ A@|x}`¦9€ yŒƒÆ}kcx}`dL,8`
HE8`
H=8`
H58`SH-8`LH%8`OH8`FHHq8`I|i¦N€!xfÁÆ8`X8€8 D"N€ git-efd65f49929d7db7èb€è#èA@èaHèPè¡XèÁ`èáhépé!xéA€éaˆéé¡˜éÁ éá¨ê°ê!¸êAÀêaÈêÐê¡ØêÁàêáèëðë!øëAëaëë¡ëÁ ëá(éÁ8}Ú¦éÁ@}Û¦éÁH}Ïñ è/ð|	¦è0è!8N€ |)¦< ø!þ¡øA@øaHøPø¡XøÁ`øáhùpù!xùA€ùaˆùù¡˜ùÁ ùá¨ú°ú!¸úAÀúaÈúÐú¡ØúÁàúáèûðû!øûAûaûû¡ûÁ ûá(ø0}ɦùÁ8}Ú¦ùÁ8}Û¦ùÁ@}À&ùÁH}Á¦ùÁPHÁèb€ø#|xH1éÁ8}Ú¦éÁ@}Û¦éÁH}Ïñ éÁP}Á¦èA@èaHèPè¡XèÁ`èáhépé!xéA€éaˆéé¡˜éÁ éá¨ê°ê!¸êAÀêaÈêÐê¡ØêÁàêáèëðë!øëAëaëë¡ëÁ ëá(è!8|B¦|	¦|B¦|¦|B¦L$è„øƒ`N€ |ˆ¦H¹[?25l **********************************************************************
QEMU Starting
 Build Date = Oct 19 2016 09:58:38
 FW Version = git-efd65f49929d7db7
|h¦|ˆ¦H<


E1001 - Boot ROM CRC failure




E1002 - Memory could not be initialized




E1003 - Firmware image incomplete

       internal FLS1-FFS-0.


E1004 - Unspecified Internal Firmware Error

       internal FLSX-SE-0.|x|ž#x|½+x|Ü3x9@sã
@‚(£ëx|J¦|c#xHáƒãx;€|#àA‚HÅH}è¦|#x8à|#8A‚HÙ}B¦,A‚4HxèÄ}B¦8à|'0A‚8àè„|' 8`A‚P|ˆ#x|qB¦ùèˆ8à|' A‚|„øèˆøèˆøèˆ|„ø(8ˆ ø 8`~ƒx}è¦N€ }è¦|°+x|±+xH9,@‚}è¦N€ |ɦ:ÿÿ8¥ÿÿŽEžPBÿø~%‹x}è¦N€ }(¦|ˆ#x|jx|…#x8¥ |«+xHE,@‚ è¤,|„*@‚ÿÔ8`}(¦N€ 8`è¤èÄèä|¥B}(¦N€ 9Jÿø9kÿøéª	éË	|-p9€A‚N€ qÎÿ@‚ÿä9€N€ ø!ÿ±|¦ø0ùá8ùÁ@ù¡H|¯+xKÿÿYè0|¦øø¯øÏøïé¡HéÁ@éá88!PN€ }¦|ixˆi,A‚H	9)Kÿÿì}¦N€ }¦|ixy#' pc,
A€8c8c0HÕy#F pc,
A€8c8c0H¹y#e pc,
A€8c8c0Hy#„ pc,
A€8c8c0Hy#£ pc,
A€8c8c0Hey# pc,
A€8c8c0HIy#á pc,
A€8c8c0H-y#"pc,
A€8c8c0Hy#'pc,
A€8c8c0Hõy#Fpc,
A€8c8c0HÙy#epc,
A€8c8c0H½y#„pc,
A€8c8c0H¡y#£pc,
A€8c8c0H…y#Âpc,
A€8c8c0Hiy#ápc,
A€8c8c0HMy#pc,
A€8c8c0H1}¦N€ }¦|ixKÿÿ}¦|ixKÿÿt}¦|ixKÿÿ xfÁÆ8`X8€8 D"N€ |jx8`T8€D"|ƒ#yA‚x£F ˜jN€ <``cxcÆdc`cx<€`„x„Æd„`„K€T„èÿA‚8 |‰¦ø£	Bÿü< `!x!Æd!`!À8a€|¦øH58`äûxHé< `!x!Æd!`!À8!€èa|h¦N€ <@`BxBÆdB`BDN€ |fx8`8€< `¥D\Kÿúá|„8„Tc0T„0|ƒ PT„Éþ|‰¦|l|¬|¬|¬L,8c€BÿèN€ ``|¦ûáÿø=Bÿÿ9J|¨xiÉÂ?âÿÿ;ÿˆy)$øø!ÿø}*H*/©AÞ4øA(éIéi}I¦èIN€!èA(8!€èëáÿø|¦N€ 9 /ðé)/©@ž|èŸ<bÿÿ8c/HÝ`|º¦<bÿÿx¤"8c/HÅ`|»¦<bÿÿx¤"8c/0H­`|²B¦<bÿÿx¤"8c/HH•`|³B¦<bÿÿx¤"8c/`H}`HKÿõu`Kÿÿ€€``="ÿÿ9)|¨|c>pxc$|‰*N€ ```|¦ûÿàû¡ÿè||xûÁÿðûáÿø|#x8 <bÿÿ8c¼<‚ÿÿ8„. øø!ÿ!H$)`/£@ž¼/½AžÔ?ýÿ¿< @{ÿä8€ãûxHÝ`="ÿÿ9)| 9@<bÿÿ8c/¸ùIH`<bÿÿäûx8¡8c/àKÿúm`|dy@‚Øé!˜?Âÿÿ8¡p;Þ0äûxÃóxû‰KÿúA`/£@ž耡„èx8`H]`9 éA€}JJ9JU)0UJ0}IPPUJÉþ}I¦|Hl|¬|O¬|¬L,9)€Bÿè<bÿÿäûx8¡8c0@KÿùÍ`|dy@‚ø<Ÿþ4„@èa˜<âÿÿ8À8ç1è8¡pH`<¢ÿÿ<‚ÿÿ<bÿÿ8¥0€8„0ˆ8c0H•`é!pù!xL,|¬é!p<ÀeP§ëxøA(éa€`ÆAP8 äûx£ëx})¦èAxN€!èA(L,|¬8!àèëÿàë¡ÿèëÁÿðëáÿø|¦N€ <bÿÿ8c/€H`KÿõE`/½@žþ4<bÿÿ8c/ˆHY`Kÿþ ```<bÿÿ8c/ðHÙ`<Ÿþ4„Aÿ<bÿÿø°8c0PH`聰Kÿþä``<bÿÿ?Âÿÿ8c/ð;Þ0H‘`é!˜8¡päûxÃóxû‰Kÿø]`/£Ažþ <bÿÿÄóx8c0 HY`Kÿþ\€|¦øûáÿøø!ÿ|?x|ix™?°‰?°}#KxKÿúm``8?€è|¦ëáÿøN€ €|¦øûáÿøø!ÿq|?x|jxøŸÈ|©+x‘_À‘?Ðé?Èù?x?À/‰Až?À/‰Až9 H`9 ‘?pH@é?x‰)+‰
@ž8`
KÿÿAé?x9Iù_x‰)}#KxKÿÿ)?p9)‘?p_p?ЊH@Aœÿ¸?p}#Kx8?è|¦ëáÿøN€ €|¦ùÁÿpùáÿx|hxúÿ€ú!ÿˆúAÿøø!ÿ|€#x|x}CxKÿõa`8!èéÁÿpéáÿxêÿ€ê!ÿˆêAÿ|¦N€ €N€ #m*E/ŠLF@ž”|¦ûáÿø|xøø!ÿ‰#/‰Až ‰#/‰AžX/‰@žHM`¡?9)ÿþU)>+‰AT¡?9)ÿìU)>+‰APˆ8!€èëáÿø|¦N€ `HÁ`Kÿÿ´`8`ÿÿN€ ``8`ÿýKÿÿÄ``8`ÿüKÿÿ´€```|¦ûaÿØûÿà|Û3xû¡ÿèûÁÿð|#x|~xûáÿø|¼+xøø!ÿaKÿþñ/ƒ|xAž”/ƒAž<è}/£@ž;à8! ãûxèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ fÛx…ãx8€ÃóxH!`ø}‰>/‰Ažÿ¨ÃóxHÕ`xc +ƒè}Až@;àKÿÿ„`fÛx…ãx8€ÃóxH`ø}‰>/‰AžÿX;àKÿÿP;àKÿÿH€```|¦ûAÿÐûaÿØ|ú;xûÿàû¡ÿè|¼+x|}xûÁÿðûáÿø|Û3x|Ÿ#xøø!ÿaKÿýÉ/ƒ|~xAž|/ƒ@žD£ëxH-`FÓxeÛxãøP£ëxäûxH!`äûxÿ£ëxûüHy`8! ÃóxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `£ëxHí`FÓxeÛxãøP£ëxäûxHá`8! |cúø|ÃóxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûáÿø|xøø!ÿKÿü½/ƒAžD/ƒAž8!€8`ÿÿèëáÿø|¦N€ ãûxH
`8!€èëáÿø|¦N€ ãûxH`8!€èëáÿø|¦N€ €}€&|¦û!ÿÈûAÿÐ|Ù3xûaÿØû¡ÿè|»+x|}xûáÿøûÿÀ|š#x;àûÿàûÁÿð‘.%-¦øø!ÿQƒÃÃòH$`¡=,9_¡*}_´‰PÞBAœØ>/‰@žÿ܀¾€ž… @š*ƒãx@žôƒA’,øA(é;€žé{})¦è[N€!èA(/£@žÿ”€¾|ÂƒãxH…`>€¾8€|©(P|iâx¥ HÅ`€žƒãx/¤AžÿPAŽÿLøA(é9éy})¦èYN€!èA(¡=,9_¡*}_´‰PÞB@œÿ08!°€}聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ <bÿÿ8c0˜HY`8!°8`聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ €` ã,}#@.}B/‰AžL Ã*9 H```H/ŠAž(9)}2‰8})´@ÿä8`N€ ``€hN€ ```€c$N€ ```9C8à} T,9C}@V,±C9C}@V,‘#y) }#J±C9C}@T,‘C9C}@T,‘C9C }@T,‘C 9C$}@T,‘C$9C(}@V,±C(9C*}@V,±C*9C,}@V,±C,9C.}@V,±C.9C0}@V,±C09C2}@V,±C2``I9}´}@M,9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I¡C, Ã*Š@})2@œÿŒN€ }€&|¦û!ÿÈûAÿÐ|Ù3xûaÿØû¡ÿè|»+x|}xûáÿøûÿÀ|š#x;àûÿàûÁÿð‘.%-¦øø!ÿQëà ÃòH$`¡=89_¡6}_´‰PÞBAœØ>/‰@žÿÜè¾èž¥ @š*ƒãx@žôëA’,øA(é;èž(é{})¦è[N€!èA(/£@žÿ”€¾$|ÂƒãxHµ`é> è¾(8€|©(P||Jx¥ Hõ`èž(ƒãx/¤AžÿPAŽÿLøA(é9éy})¦èYN€!èA(¡=89_¡6}_´‰PÞB@œÿ08!°è}聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ <bÿÿ8c0ØH‰`8!°8`聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ €`é  ã8}#@.}B/‰AžL Ã69 H```H/ŠAž(9)}2‰8})´@ÿä8`N€ ``èhN€ ```|¦û!ÿÈûAÿÐ|™#xûaÿØûÿà?bÿÿ?‚ÿÿûÁÿðûáÿø;@|xúáÿ¸ûÿÀ;{18;œ1û¡ÿèøø!ÿAë£(£ê;Ý H `¡?<9Z;Þ@}Z´‰PAœ\>ÿä/‰@žÿà>y)6d}=Jé)y'ÿãA‚ÿÈé~/«Ažÿ¼‚þ;9 z÷6d~ýº`è~ÿøé éW|i}?@.}B}ŸèŒ/‰x‡"xé$xç.¤|é8P}'R ÿ8|¿JAž€ ß69 HH/ŠAžh9)}2‰8})´@ÿä}_*x„ èìé%}R+„@|ù:}'JA=Bÿÿ9JPx‡d|ê:ª}GR}I¦N€ àPàà˜ èààà00ààààààààààààààààààààààààààÄ€à°àà0àà0000¼ààààà”00ààà00```}_*é(©P@@þ¨ƒãxH`é~é>	´¸X@	ÃxAœþ¡?<9Z;Þ@}Z´‰P@œý¬8!Àèêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ y)d±(é>é~	´¸X@	ÃxAœýœKÿÿé(})Êù(é>é~	´¸X@	ÃxAœýpKÿÿdy*ây)„}*J±(é>é~	´¸X@	ÃxAœý@Kÿÿ4``y)„±(é>é~	´¸X@	ÃxAœýKÿÿ``‘(é>é~	´¸X@	ÃxAœüäKÿþØ```y)"±(é>é~	´¸X@	ÃxAœü°Kÿþ¤``y)„ ±(é>é~	´¸X@	ÃxAœü€Kÿþt``cÛxH]`é>é~	´¸X@	ÃxAœüLKÿþ@€	``ûÁÿðûáÿø8£ 8À9C;À|æ,,} ,,8À8£(þT,}T,;Ã}@,,xçÆ{ÿÆ});x|æ,,}ûx;ã08£4ùù# 98Ã6xçÆ}#J}J;x8ã8ùC(9C}F,±9:}@V,±C9C<Àô,“Ã;Ã>àü,“ã0| .,°£4|À6,°Ã6|à>,°ã88à}F,±:}@V,±C<Àö,³Ã>`;é9	8 9@}`ü,|€D,|Åü,ÊD,;é9I | ü,xÆÆ{ÞÆ}k3x|„óx8À;À}ü,þT,|ÀT,;À9I({ÿÆyÆ|ÆûxþT,|¥Cx}T,;É0{ÿÆ}@ô,}ûx;à|ô,ø©€©øÉ ù	(8É9ùiø‰}´xÆ| M,}JxùI0|À4,É¡C8 Ã6Š@})2@œÿ,ëÁÿðëáÿøN€ €c0N€ /¥8¥ÿÿx¥ 9#ÿÿ|£*T„>|©(P|©¦Mž ```œ‰BÿüN€ /¥8¥ÿÿx¥ 9#ÿÿ|£*8„ÿÿ|©(P|©¦Mž ```DIBÿøN€ ¤@@œL}$*£H@A@/¥9%ÿÿ|„JMž 9%ÿÿ8„y) |£*9)})¦`$ÿÿ%ÿÿBÿøN€ /¥Až,8¥ÿÿ9#ÿÿx¥ 8„ÿÿ8¥|©¦DIBÿøN€ N€ |¦øø!ÿ‘ø¨|dx<bÿÿ8c.Àø¡°8¡¨øÁ¸øáÀùÈù!ÐùAØH	`8!pè|¦N€ €|¦û¡ÿèûáÿø|}xûÁÿð?âÿÿ;ÿ.Àøø!ÿqëßHi`¤ëx|exÃóxKÿìu`<‚ÿÿ8 8„1h|~xèKÿìY`8!Ã´èë¡ÿèëÁÿðëáÿø|¦N€ €‰#/‰Až49 ````C9)})´/Š@žÿðy# N€ 8`N€ |¦ûÁÿðûáÿø|¦+x|~x|…#x8€@øø!þA8apHé`8p|xè~{å Kÿë‘`8!ÀãûxèëÁÿðëáÿø|¦N€ €}€&|¦=BÿÿûaÿØûÿà9J1pû¡ÿèûÁÿð9&ÿýûáÿø+‰
éjéJ‘øø!ÿQùApùaxA/¥|Ü3x|{xAž(|ª+x9 H``````}Jã’9)})´/ª@žÿðy? „ø@8`Aœ|.'þûxH /½;Þÿÿé;{Þ ¥ëx|iñ®AžD¥ã’}=áÒ|©(P|¡*ˆepA’ÿÐH	í`/½;Þÿÿé;{Þ ¥ëxTc>|iñ®@žÿÄé;8`})úù;8!°èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦} N€ ``8!°8`聁ëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦} N€ ;àKÿÿ€```|¦û!ÿÈûAÿÐ}9KxûaÿØû¡ÿè|›#x8€ûÁÿðûáÿø|~x|ß3xûÿà|£+x8 
|ý;x}Cxøø!ÿQëžH	`/¿|c´AžÀ9@H`````ÿë’9J}J´/¿@žÿðyJ }9RƒH@Pé^})P})´9)ÿÿ}PPy) »@9)})¦AH$@œ ›Jé^9J}<PP©Øù^Bÿä8!°8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 9@Kÿÿt€```|¦ûaÿØû¡ÿè|›#xûÁÿðûáÿø|~x|½+xûÿà;àøø!ÿaëƒH4``é^}<PP©Ø@œ4}=ø®y ™*é>9)ù>£ëxKÿûõ`9ƒø@AÿÄ8! 8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûaÿØùÁÿp|{yùáÿxúÿ€ú!ÿˆúAÿúaÿ˜úÿ ú¡ÿ¨úÁÿ°øúáÿ¸ûÿÀû!ÿÈûAÿÐûÿàû¡ÿèûÁÿðûáÿøø!þ±øa€A‚´/¤8`Až”=Bÿÿ8„ÿÿ9J1È>Bÿÿ|¯+x|Ó3xùA°xœ Ûx;:À :R1p‰//©AžD»øPþûx½à@œ4+‰%8Á9Ažð™?9ï‰//©ëá€;ÿûá€@žÿÄ9 ™?èa€{Pc´8!PèéÁÿpéáÿxêÿ€ê!ÿˆêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀ|¦ë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿøN€ ```+‰iAžl+‰uAžd+‰xAž\+‰XAžT+‰pAžL+‰cAžD+‰sAž<+‰%Ažô+‰OAž,+‰oAž$|è;x&8è/|ç´+‰d@žÿ˜`99Ap}´|ê:}
B™' › ˆÁ‘9&ÿÒq*ýA‚è:€ 9Á‘/¦Až˜½àP{½!A‚ŒëS:: :à; }ZÐùA¸```9&ÿ±U(>+ˆ+A=ÿÿ9%Ly)¨}(Jª}	B}	¦N€ Dôôôôôôôô´ôôôôôôôôôô”ôôôÄ”ôô¤ôôD4ôôdô”ôô¸ôä`: zé$}Ê}2J|èP8à~ˆ£x›pëé8¡p9 x„ 8a€_ø8æûxKÿú¥~§«x8À聀åûx|ž P|„èPx„ 8a€KÿøáŒÎëá€/¦Až~øP°èAœþ¤:s9ïKÿüô`zé$}Ê}2J|èP8à~ˆ£x›pëé8¡p9 x„ 8a€_ø8æûxKÿú~§«x8ÀKÿÿt``+†u}!ÊQÓx›	pAžVé89@9)ÿÿ}IH6JH9@‚ˆè€|ž P8à
|„èP~&‹x8¡px„ 9 ~ˆ£x8a€Kÿù­è€~§«x8À
~%‹x|ž P|„èPKÿÿ```áÊ|èP9 8À9 8à
›p8¡px„ 8a€KÿùYŒÎé!€›Iëá€;ÿûá€KÿþÈ``}!Ê8€8 
8ap›	pH}`|q´CÓxKÿö­`聀|c´‘@pé!€|ðèP|cˆPxç |c´|ßHP}$Kx§0@L8cÿÿxc 8c|i¦H ```}HP}$Kx§@@šÉé!€9)ù!€Bÿà}$Kx|ž PEÓx|„èP8a€x„ KÿùµŒÎëá€Kÿýô`áÊ|èP8àFÓx9 9 ›p8¡px„ 8a€Kÿø9聀衰8a€|ž P|„èPx„ Kÿù]聀~§«x8ÀEÓx|ž P|„èPKÿýx```ˆÎ9.+†lAžäëá€}.Kx:àKÿý`ˆÎ9.+†hAž´ëá€}.Kx:àKÿý@ŒÎëá€:àKÿý09&ÿÐ+‰	Aý}!Ê;9ëá€{9 ˜ÉpŒÎKÿý``9?9ïù!€9 %™?`Bëá€Kÿùð9 -éA¸™?zé$}2Jè	}Q8聀8„ø€KÿýX`|.x:€0ŒÎ’KÿûŒÎëá€:àKÿüŒÎëá€:àKÿü€8`Kÿùè€9#ÿŸ+‰M 8cÿà|c´N€ ,$A‚`+…$ødA<àxçƒä`ç&‰#|hx8c+‰ |êL6yFá@¸/¥@žà+‰0@žÀ‰(8 
/‰xAž9 08`H4``}J4Š(9}%ÒLœ ù|jJ‰(/©AžÌ9IÿÐ8éÿŸUF>+‡*†	}J4@•ÿÄ9Iÿ¿*Š9Iÿ©@ÿ°9)ÿÉM• }*49Š(}%ÒAœÿ¨N€ ```A‚ødKÿÿ(`/¥@ž8 
/©@žÿP8`N€ `/…@žÿè+‰08 @žÿ܉(/‰x@žÿ 9HùD‰(}HSxKÿÿ¼```N€ 8ÿðKÿþ 9HùD‰(}HSxKÿÿ¬|¦.¥ûÿàû¡ÿèûÁÿðûaÿØ|¾+x|}xûáÿø|œ#xøA–t%=@HaJ})Rx})4U;Ù~< D8`(8€`¥"H9` }ˆ¦}kb«|Xl|¬|_¬L,8c+£@èA–$.»@–|<àÿÿ<À<xç ¾è¥ëx@d=àÉóxaH9)ÿü©è@HIŠ@@žÿìI/Š@žÿàI/Š@žÿԁI/Š@žÿȁI/Š@žÿ¼}%Kx}=Kx¼(Šãx@Ð¼ëxH```;œ¼P@œè<‰8@žÿì<‰0@žÿàŠãx@–ü<À|<àD`Æh`ç"¥à@œx8 H`;½½P@œ`=‰8@žÿìÝ©ëx|¨+x}J9U)0U0}	@PUÉþ}	¦|Hl|¬|O¬|¬L,9)€Bÿè;½½PAœÿ¨èëaÿØëÿàë¡ÿè8`ëÁÿðëáÿø|¦N€ `8àÿÿ8À<xç KÿþˆA– <Àh<à"`Æ|`çDKÿÿ@``<À|<àD`Æh`ç"Kÿÿ$<Àh<à"`Æ|`çDKÿÿ``èëaÿØëÿàë¡ÿè8`ëÁÿðëáÿø|¦N€ ```;`Kÿý¤``.»¥ëxŠãx@–ÿ˜KÿþœÀPÀPP
 exception %llx 
SRR0 = %08llx%08llx  SRR1 = %08llx%08llx 
SPRG2 = %08llx%08llx  SPRG3 = %08llx%08llx 


SLOFERROR: Flatten device tree not available! Press "s" to enter Open Firmware.

bootinfo  !!! roomfs lookup(bootinfo) = %d
xvectCannot find romfs file %s
ofw_mainERROR: Not enough memory for Open Firmware[?25h%s%sELF32: VirtAddr(%lx) != PhysAddr(%lx) not supported, aborting
ELF64: VirtAddr(%lx) != PhysAddr(%lx) not supported, aborting

ELF relocation out of bounds!
ERROR: Unhandled relocation (A) type %i

0123456789abcdefÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0x@”DIàDJ0DK@DKpDNPDN DOpDOàDPÀDQàDSDS DUDVDV0DWpDY`DYàD^pD`@D``D`°DaDaDaðDb€DbÐDc@DdàDf DfàDnDn@DoÐDDÀ ÿÿÿÿÿÿÿÿ?0?(xvectè`/ð|i¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8€N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8€N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8€N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8	N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8
N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8
N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8 N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8!N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8"N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8#N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8$N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8%N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8&N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8'N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8(N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8)N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8*N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8+N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8,N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8-N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8.N€ |C¦|	¦|C¦|¦|C¦è/ð|	¦8/N€ 6ÿÿÿÿÿÿÿÿ	ȸ	Ȁ0ofw_mainELF@	Ā@8@
{t²8dtåQ?à˜cÿø?à˜cÿ!øŸ?àcÿñøß?àcÿÀøÿ|¦|¦<``cècø`/ð<``c<€`„Gä8 Hz5H|1C¦BŸ|(¦è!ÿðøAøaø ø¡(øÁ0øá8ù@ù!HùAPùaXù`ù¡hùÁpùáxú€ú!ˆúAúa˜ú ú¡¨úÁ°úá¸ûÀû!ÈûAÐûaØûàû¡èûÁðûáø8`|x|B¦ø|B¦ø,	@‚|¶¦<ÿ|¦|&ø|¦ø|B¦ø|B¦ø|¦ø |¦ø(|¦ø0|¦ø8BŸ
¨O|H¦è"|!8øÿñø!ÿ<@èHP|¦èBHXL$|¦BŸˆ¼}¦|¦è}Bèø(|xèøH|xèøh|xè øˆ |xè(ø¨(|xè0øÈ0|xè8øè8|xèhù¨h|
xèpùÈp|xèxùèx|xè€ú€|xèˆú(ˆ|xèúH|xè˜úh˜|xè úˆ |xè¨ú¨¨|xè°úÈ°|xè¸úè¸|xèÀûÀ|xèÈû(È|xèÐûHÐ|xèØûhØ|xèàûˆà|xèèû¨è|xèðûÈð|xèøûèø|xè} &|ñ ù(è(} ¦|d|¬L,ù((N€ |ˆ¦Kÿþu|ˆ¦8`N€ |ˆ¦|i¦Kÿþ],
A‚N€!H } ¦i­}»¦}©¦}¬kx}º¦L$Kÿþ-|ˆ¦8`ÿÿN€ [?25lQEMU Starting
 Build Date = Oct 19 2016 09:58:39
 FW Version = git-efd65f49929d7db7
`````|„8„Tc0T„0|ƒ PT„Éþ|‰¦|l|¬|¬|¬L,8c€BÿèN€ ``|¦øø!ÿ‘H`Y`8!pè|¦N€ €8cÿÿ+ƒ@8`N€ ```/¥Ažÿè|¦9%ÿÿû¡ÿèûÁÿðy) ûáÿø|½+x;äÿÿÄJøø!ÿqH``H_Ù`¿ð@Až0Œ+ƒ
@žÿè8`
H_¹`ˆH_­`¿ð@@žÿØ8!£´èë¡ÿèëÁÿðëáÿø|¦N€ €``/¤Mž |¦Tc>øø!ÿ‘H_Q`8!pè|¦N€ €`+ƒA<xi$=xc.¤9¡°})P}HH./ŠAž9@8`}HI.N€ ``8`ÿÿN€ ```|¦=")¤°ûáÿø?âûÿàû¡ÿè||x|½+xûÁÿðúaÿ˜|ž#x;ÿ¡°/‰úÿ ú¡ÿ¨úÁÿ°úáÿ¸øûÿÀû!ÿÈûAÿÐûaÿØø!ÿ@ž`=…91¸8ÿ8`<…8Æ1À<¢8¥±¨=Bÿý9J*Ð>â`8‚¥X9?øèw¤°<â`=ø¦ø‚¥PùG©¸ù(©È=B¥9JSÀ9!x©P@@œ=")©Ð/‰AžD„{—ÿãA‚="…9)1ÀéI9
ûªù	{‡áA‚="…9)1ÀéI9
ûÊù	{‰÷ã@‚h{ŠïãA‚0=B…9J1¸`;ÿ;b£È9; é
ù!x8èûèøêëé?Bÿÿ; ; ÿÿ;Zi°;Ðé?})¦N€ ```{Šçã8`A‚="…9)1ÀéI9
ÿøèjù	8!èêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿè|¦ëÁÿðëáÿøN€ é!x=…91À<…8Æ2°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<Â8ÆÑ°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<Â8Æ!°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<…8ÆC°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<Â8ÆÑ°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<Â8Æâ°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À<Âÿý8Æ"°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À`èÂ3PëééH9)ù!xèÿ8ªøÊø¨|é¦N€ é!x=…91À`èÂ3XëééH9)ù!xèÿ8ªøÊø¨|é¦N€ éAx="…9)1°<â…8ç1ÀëêèÉé9JùAxé?8¨øÈø§})¦N€ éAx="…9)B°<â…8ç1ÀëêèÉé9JùAxé?8¨øÈø§})¦N€ éAx="9)°<â…8ç1ÀëêèÉé9JùAxé?8¨øÈø§})¦N€ éAx="9)á°<â…8ç1ÀëêèÉé9JùAxé?8¨øÈø§})¦N€ =B…9J1¸éx8ÿøáxé*ù	9)ù*ëÿé?})¦N€ <â…8ç1¸è¡x=…91À8ßé'éHø©9)8ªù'ø¨é?øÊù!xëéé?})¦N€ ëÿé?})¦N€ ëÿé?})¦N€ =…91ÀèßéAxé(8êøáxøÉ9)ù(ëêé?})¦N€ =…91ÀèßéAxé(8êøáxøÉ9)ù(ëêé?})¦N€ =…91Àé?éAxé8ÊøÁxèè}'Jù(ëêé?})¦N€ =…91À;ÿéAxé(8êøáxûé9)ù(ëêé?})¦N€ =…91À;ÿéAxé(8êøáxûé9)ù(ëêé?})¦N€ éAxé*9J}*J9IëéùAxé?})¦N€ ?…;Þ1Àèáxé^8Ç|É3xøÁxé
/¨@žé}&B``9Jÿøëé9)ù^ù!xé?})¦N€ ="…9)1¸èáxëûÐûxéI9
øêù	é?})¦N€ éAx=…91ÀèÊé(8êøáxøÉ9)ù(ëêé?})¦N€ éAx=…91ÀèÊé(8êøáxøÉ9)ù(ëêé?})¦N€ é!x=…91ÀëééH9)ù!xèÿèÊ8ªø¨|é¦øÊN€ é!x=…91ÀëééH9)ù!xèÿèÊÿø8ªø¨|é¦øÊN€ =B…9J1Àé!xé
ëé9)ù!xéHé?})¦yJ$!Jÿø}HP*ùHN€ é!x=…91ÀëééH9)ù!xèÿ9JÿøùH|é¦N€ é!x=B…9J1ÀëééJ9)ù!xéèÊÿøèê}	¦øÊøêÿøN€ éx<â…8ç1À<¢…8¥1¸ëèéGèÅ9ùxé?èŠ8f9JÿøøeùG})¦ø†N€ éx<â…8ç1¸<¢…8¥1ÀëèéGèÅ9ùxé?èŠ8f9JÿøøeùG})¦ø†N€ éAx="…9)1¸<â…8ç1ÀëêèÉé9JùAxé?èÆ8¨ø§})¦øÈN€ é!x<â…8ç1À=B9J±°ëéé9)ù!xè¿8È}J0P}JtøÇ|©¦ùHN€ <â…8ç1Àé!x=9±°èÇ9IëéùAxé&y)$9)ÿø}IBé?ùG})¦N€ éx="…9)1¸<…8Æ1ÀëèéI="9)ò°èæ9ùx}IPPé?8§}Jt9Jø¦})¦ùGN€ èáx<¢…8¥1À<Â8Æò°<‚…8„1¸éëç8çøáxéHé?9ÿøù})¦yJ$9Jÿø}J2ùDN€ =…91À="…9)1¸éAxéèéëê9JùAxé(y)$})8PéIé?})¦ùHN€ <â…8ç1Àé!xéGëé9)ù!xèªÿøé
èß|ɦ}Bù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xèªÿøé
èß|ɦ}(Pù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xèÊÿøé
é?})¦}AÒù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xèªé
ÿøèß|ɦ}(6ù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xèªé
ÿøèß|ɦ},6ù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xèªé
ÿøèß|ɦ}.4ù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xé
ÿøèªèß|ɦ}(8ù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xé
ÿøèªèß|ɦ}+xù
ÿùùGN€ <â…8ç1Àé!xéGëé9)ù!xé
ÿøèªèß|ɦ}*xù
ÿùùGN€ é!x=B…9J1ÀëééJ9)ù!xé?é
})¦éù
N€ é!x=…91ÀëééH9)ù!xè¿èêèÊÿø9JÿðùH|©¦øÇN€ é!x=B…9J1ÀëééJ9)ù!xé?é
})¦‰ù
N€ é!x=…91ÀëééH9)ù!xè¿èêˆÊÿÿ9JÿðùH|©¦˜ÇN€ é!x=B…9J1ÀëééJ9)ù!xé?é
})¦¡ù
N€ é!x=…91ÀëééH9)ù!xè¿èê Êÿþ9JÿðùH|©¦°ÇN€ é!x=B…9J1ÀëééJ9)ù!xé?é
})¦ù
N€ é!x=…91ÀëééH9)ù!xè¿èê€Êÿü9JÿðùH|©¦ÇN€ é!x=B…9J1ÀëééJ9)ù!xé?é
})¦éù
N€ é!x=…91ÀëééH9)ù!xè¿èêèÊÿø9JÿðùH|©¦øÇN€ =B…9J1Àé!xéJëé9)ù!xé
é?})¦ˆè˜áp‰™q`B¡pù
N€ <â…8ç1ÀéAxé'ëê9JùAxèÉÿøé	9)ÿðè¿ù'|©¦xÄ°Áp˜ˆ`B‰Aq™HN€ =B…9J1Àé!xé
ëé9)ù!xéHé?})¦ˆê˜ápˆê˜áqˆê˜ár‰J™As`BApùHN€ <â…8ç1ÀéAxé'ëê9
ùxèÉÿøéI9)ÿðè¿ù'|©¦TÄF>Áp˜Š`B‰q™
‰r™
‰s™
N€ <…8Æ1Àé!xéFëé8éøáxé*ÿøé
©@é?}&Uïþ})¦}Ðù
ÿùùFN€ <â…8ç1Àé!xéGëé9)ù!xèÊÿøé
è¿|©¦}0}A}´ù
ÿùùGN€ é!x=B…9J1Àëé9)é
ù!xé?éH})¦}JþvùHN€ <â…8ç1Àé!xéGëé9)ù!xé
ÿøèªèß|ɦ}*x1ÿÿ}Aù
ÿùùGN€ é!x=B…9J1Àëéé
9)ù!xé?éH})¦1Jÿÿ}JQùHN€ éx<…8Æ1À<¢…8¥1¸ëèéFèå9ùxé?éjÿøèŠ8g9JÿðøeùF})¦ùgø‡N€ <¢…8¥1ÀèáxéE9'ù!xé
èÊÿø9JÿðùE¦@Až2¨<â…8ç1¸éG8ªøÊù
ø§ëé9IùAxé?})¦N€ <¢…8¥1¸éxéEé(9ùxèêèÊÿø}(J8ç§0øêAž2,ëé9IùAxé?})¦N€ <b…8c1À<‚…8„1¸éaxéCé8«ø¡xèêé(8ÊÿøéKøÃ/§|çJøèAœ1À|æ;xèèÿø|É0P}ER8çÿÿ})8P©0@@œ9ÿð|ª+xù`ëê9JùAxé?})¦N€ <â…8ç1¸é!xééI9ÿð9J})Rù9)ëéù!xé?})¦N€ <â…8ç1ÀéxéG9(èÈù!xé
9JÿøùG/¨Až =…91¸})2éH9JÿðùH`ëé9IùAxé?})¦N€ =B…9J1¸é*9	ÿøé)ù
ëé9IùAxé?})¦N€ =B…9J1¸é*9	ÿøé)ù
ëé9IùAxé?})¦N€ ="…9)1ÀéI9
ÿøëêù	é?})¦N€ <b…8c1ÀéAxé#ëê8ŠøxéIÿøé	ÿðè©8Éÿèé?øÃ}Sx|ç+xxç`+§Až@0X+§@žôª@@Aœ0€|åBª8@@œ0t/¥}J*Až(|è;x|§(P``„Èÿü|è*”Êÿü/§@žÿð})¦N€ <‚…8„1ÀéDé*ÿøèêÿðˆª9JÿèùD|æKxx¨EäxÆ`}+x+¦yƒä}x}*KxAž+¦Až´/¦AžH/©9Gÿÿ})R}*HP})¦@Ý``œªBÿüé!xëé9IùAxé?})¦N€ 8Éÿøy
Æ/¦}Sx8§ÿø|Ê3xAœL9)ÿðxÊèÂ/©ÿø9J@ü 9@H`````,*ù	8Æÿø9Jÿÿ@‚ÿð|Ê3x9*ÿüy /©}*Kx8ÇÿüAœL9Iÿü/ªÿüy*ð‚9J@ü 9@H`````,*”¦9)ÿü9Jÿÿ@‚ÿð}*Kx5*ÿþA€ÿ9Jÿüy)øB/ªÿþU>8çÿþ9)AÜ.|`,)µ9)ÿÿ@‚ÿôKÿþè```+§@ž+\ª@@Aœ-¬|è*ª8@@œ- /¥}J*Ažþ0|§(PH````¤Çÿþ}*´Êÿþ/¨@žÿðKÿþ``?…;Þ1Àé>éI9	ÿè8©ÿðèéÿøùé	ÿð/ª@-ˆˆˆÇ† @Aœ,ÐA<}I¦H``````B@,ЍHŒÇŠ0@A,˜@œÿìû©ÿðé!xø¾ëé9IùAxé?})¦N€ `é!x=B…9J1À8` ëÊëé9)ù!xêÿ€žÿôèÞè¾ÿø9ÿðù
HaM`~é¦ø~ÿðN€ é!x=B…9J1À8`ëéëÊ9)ù!xêÿèžHaõ`~é¦ø~N€ =…91Àé!x8`éHëé9)ù!xèªÿøèŠëß9JÿðùHT¥>HaÍ`ɦN€ é!x=B…9J1À8`ëéëÊ9)ù!xêÿèžHaq`~é¦ø~N€ =…91Àé!x8`éHëé9)ù!xèªÿøèŠëß9JÿðùHT¥>HaI`ɦN€ é!x=B…9J1À8`ëéëÊ9)ù!xêÿèžH`í`~é¦ø~N€ =…91Àé!x8`éHëé9)ù!xèªÿøèŠëß9JÿðùHx¥ H`Å`ɦN€ é!x=B…9J1À8`ëéëÊ9)ù!xêÿèžH`i`~é¦ø~N€ é!x=…91À8`éHëé9)ù!xèŠèªÿøëß9JÿðùHH`E`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿàèþèÞÿø9ÿàè¾ÿðèžÿèù
H``~é¦ø~ÿàN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿðè¾èžÿø9ÿðù
H_í`~é¦ø~ÿðN€ é!x=B…9J1À8``cðëÊëé9)ù!xêÿèžÿøè¾9ÿøù
H^]`~é¦ø~ÿøN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHH^`ɦN€ é!x=…91ÀëééH9)ù!xèŠèjÿøèªÿðëß9JÿèùHHX%`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ9ù
H`Í`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~Hb•`~é¦ø~N€ é!x=…91À<Â8ÆÑ°ëééH9)ù!xèÿ8ªøÊø¨|é¦N€ ?…;Þ1Àé!xéëé9)ù!xêˆ9HÿøêêÈÿøù^/´Až'4:Öÿÿ~•£x:à````Œvz÷¤~÷¢xH`,5:µÿÿ|wºx@‚ÿà=9Ñ°é^z÷h~÷B~i¦úêN€ é!x=…91ÀëééH9)ù!xèŠÿþˆjëß9JÿðùHH\Y`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xè~êÿH\9`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xè~êÿH\1`~é¦ø~N€ é!x=B…9J1À8`üëÊëé9)ù!xêÿ€žÿôèÞè¾ÿø9ÿðù
H[™`~é¦ø~ÿðN€ é!x=…91À8`éHëé9)ù!x€Šëß9JÿøùHH[U`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~ÿüèž9ÿøù
H[µ`~é¦ø~ÿøN€ ?…;Þ1Àé!xé^ëé9	ùxêêèêÿð8ÊÿèêêÊÿøøÞ·8@Až$´~i¦9ù
ÿèN€ ?…;Þ1Àé!xé^ëé9)ù!xé
8ÊÿøèÿøÞ/¨Ažé*ÿøù*ÿð`|é¦9Jÿðù^N€ ?…;Þ1Àé!xé^ëé9)ù!xèjêÿHù}`~é¦é^9
øjùN€ é!x<b8cÑ°8 8€`¥€ëé9)ù!xëßHûõ`ɦN€ <…8Æ1ÀéAxé&ëê9
ùxè‰ÿøè©ÿðèé9IÿèëßùF|©#x});xy)`+©Ažˆ@%+©@žt8`8À`cðxçð‚9D"ɦN€ =…91Àé!xéHëé9)ù!xèªèŠÿøèjÿðëß9JÿèùHT¥>HVY`ɦN€ ``+©@ž!Ü8`8À`cðxçøB9D"ɦN€ ``<…8Æ1ÀéAxé&ëê9
ùxèéè‰ÿøè©ÿð9IÿèëßùF|é#x})+xy)`+©Až!4@#h+©@ž! 8`8À`cðxçð‚9D"ɦN€ ```é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
H]±`~é¦ø~ÿøN€ ?…;Þ1ÀéAxé>ëê9
ùxè‰èiÿø9Iÿðêÿù^H6í`é^,#9
A‚!8~é¦ûªùN€ `=…91Àé!xéHëé9)ù!xèªÿøèjÿèèʀŠÿô9JÿàëßùHx¥ xc H)`ɦN€ é!x=…91ÀëééH9)ù!x9 èÿ8Êù*øÈ|é¦N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ9ù
H<Q`~é¦ø~N€ é!x=…91ÀëééH9)ù!x9 èÿ8Êù*øÈ|é¦N€ é!x=…91ÀëééH9)ù!x9 èÿ8Êù*øÈ|é¦N€ é!x=…91ÀëééH9)ù!x9 èÿ8Êù*øÈ|é¦N€ ?…;Þ1ÀéAxé>ëê9
ùxèÉè©ÿøèiÿè9Iÿèêÿè‰ÿöù^HEÝ`é^,#A‚ Ð~é¦8êøjûªøþN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHHu`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xèžÿþêÿè~ÿðè¾9ÿðù
HI!`~é¦ø~ÿðN€ é!x=B…9J1ÀëéëÊ9)ù!xèžÿþêÿè~ÿðè¾9ÿðù
HJ™`~é¦ø~ÿðN€ ?…;Þ1ÀéAxé>ëê9
ùxèi9Iÿøêÿù^HO™`é^,#A‚˜~é¦8êøjûªøþN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHS`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
HU`~é¦ø~ÿøN€ é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
HV}`~é¦ø~ÿøN€ ?…;Þ1ÀéAxé>ëê9
ùxêÉè‰ÿðè©ÿø iÿî9Iÿèêÿù^~ƳxT„>HW¹`é^/£@ž~é¦9
úÊû*ûªùN€ ``=b…9k1Àé!xëËëé9IùAxé>êþÿØè~ÿÐéÿø8ÿÐèþÿöè¾ÿàèÞÿî~ä´êÿøHZÙ`~é¦ø~ÿÐN€ =…91ÀéAxé(ëê9JùAxéI}Vû¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}6ú¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}@d9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ} ¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}Y¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}9¦|é¦ù*N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}?B¦|é¦ù*N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}?ú¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}Qû¦}Qû¦L,9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}1ú¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI|¬}Tû¦L,9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}4ú¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI|¬}Pû¦}Pú¦}Pú¦}Pú¦}Pú¦}Pú¦}Pú¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}0ú¦|é¦ù*N€ é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
Hq9`~é¦ø~ÿøN€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ},B¦|é¦ù*N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}-B¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}Uû¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}5ú¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}WK¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}7J¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}PC¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}0B¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}QC¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}1B¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}RC¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}2B¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}SC¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}3B¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}PK¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}0J¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI}QK¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}1J¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI|¬}[æL,9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ|¬}3¦|é¦ù*N€ =…91ÀéAxé(ëê9JùAxéI|Pl|¬|W¬|¬L,9Iÿøé?ùH})¦N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~Kÿ΅`~é¦ø~N€ H`é!x=B…9J1À8 ëÊëé9)ù!xêÿè~ÿðèÞèžÿø9ÿðù
H-á`~é¦ø~ÿðN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿèèÞè¾ÿø9ÿèèžÿðù
H-•`~é¦ø~ÿèN€ <…8Æ1ÀéAxé&ëê8êøáxé	éIÿø9)ÿðè¿ù&}R9UJ0U0}
@PUÉþ}	¦|Pl|¬|W¬|¬L,9J€Bÿè|©¦N€ =…91ÀéAxé(ëê9JùAxéI}V¦9Iÿøé?ùH})¦N€ =…91Àé!xéHëé9)ù!x8ÊèÿøÈ}6¦|é¦ù*N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿðè¾èžÿø9ÿðù
H(`~é¦ø~ÿðN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿøèž9ÿøù
H(Ñ`~é¦ø~ÿøN€ é!x=…91ÀëééH9)ù!xèªèŠÿøèjÿðëß9JÿèùHH*y`ɦN€ ```;b£È9[¨}ISxùAxKÿÐé!x=B…9J1ÀëéëÊ9)ù!xêÿè~Hšu`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿðè¾èžÿø9ÿðù
H–-`~é¦ø~ÿðN€ é!x=B…9J1ÀëéëÊ9)ù!xéêÿè~ÿØèþÿø9~ÿØèžÿæèÞÿðè¾ÿèùjH•ù`~é¦ø~ÿØN€ =…91Àé!xéHëé9)ù!xèjëß9JÿøùH|c4H/y`ɦN€ é!x=…91ÀëééH9)ù!x¨ªÿþèŠëß9Jÿè¨jùHH/½`ɦN€ é!x=…91ÀëééH9)ù!x¨jÿþèŠëß9JÿðùHH/u`ɦN€ é!x=…91ÀëééH9)ù!x¨ªÿþèŠëß9Jÿè¨jùHH/Q`ɦN€ é!x=…91ÀëééH9)ù!x¨jÿþˆŠëß9JÿðùHH/Q`ɦN€ =…91Àé!xëÈëé9)ù!xÊóxˆžêÿèjÿù|c4ùHH.é`~é¦|c4TjÙ~iJ}JÐù^ÿøN€ é!xëé9)ù!xëßH.ù`ɦN€ ?…;Þ1Àé!x<¢ÿÿ8¥mFÓx8pé^ëé9)ù!xèjêÿH/`~é¦é^èáp9
øêøjùN€ ?…;Þ1ÀéAx<Âÿÿ8ÆmGÓx8¡pé>ëê9JùAxè‰èiÿøêÿ9)ÿøù>H0U`~é¦é^èáp9
øêøjùN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~H	`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~H‘`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~H‰`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿ€~H`~é¦ø~N€ ?…;Þ1Àé!xé^ëé9)ù!xˆŠÿÿ€jêÿHU`~é¦é^9Jÿðù^N€ ?…;Þ1Àé!xé^ëé9)ù!x Šÿþ€jêÿHA`~é¦é^9Jÿðù^N€ ?…;Þ1Àé!xé^ëé9)ù!x€Šÿü€jêÿH-`~é¦é^9Jÿðù^N€ ?…;Þ1Àé!xé^ëé9)ù!xèŠÿø€jêÿH`~é¦é^9Jÿðù^N€ ?…;Þ1Àé!x8 8a€é^ëé9)ù!x€ŠêÿH¡`éˆèÁ€9H+ªé^@
h~é¦8êù
øÊ9øþù
N€ ?…;Þ1ÀéAx8a€é>ëê9
ùxè©è‰ÿø9Iÿøêÿù^Hí`éˆèÁ€9H+ªé^@è~é¦8êù
øÊ9øþù
N€ >â…:÷1ÀéAx8a€é7ëê9
ùxèÉÿþè©ÿð9Iÿàëßèéè‰ÿîùWH a`éˆèÁ€éW/¨@ž¸É¦9
ûªùN€ ?…;Þ1ÀéAxé>ëê9
ùxè©ÿöèiè‰ÿø9Iÿèêÿù^H"½`é^/£9*ù>@ž
ô~é¦ûªN€ `é!xëé9)ù!xëßH%`ɦN€ >â…:÷1ÀéAxé7ëê9jùaxé	èéÿøè©ÿèè‰ÿà9IÿÐèÉÿöèiÿØëßùWH*]`éW,#9
A‚
¸É¦ûªùN€ `?…;Þ1ÀéAxé>ëê9
ùxèÉè©ÿøè‰ÿðèiÿè9Iÿàêÿù^H+i`é^,#9
A‚
~é¦ûªùN€ é!xëé9)ù!xëßH%`ɦN€ >â…:÷1ÀéAxé7ëê9jùaxé	èéÿøè©ÿèè‰ÿà9IÿÐèÉÿöèiÿØëßùWH,`éW,#9
A‚	˜É¦ûªùN€ `?…;Þ1ÀéAxé>ëê9
ùxè‰èiÿø9Iÿðêÿù^H ‘`é^,#9
A‚	~é¦ûªùN€ ``é!xëé9)ù!xëßH}`ɦN€ >…:Ö1ÀéAxé6ëê9JùAxèÉè©ÿøè‰ÿðèiÿè9)ÿàêÿù6H&Å`|hyA‚	˜ëÖù9>ù6HÞU`~é¦éVø~9
ûªùN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~Hp=`~é¦ø~N€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHr½`ɦN€ =…91Àé!xéHëé9)ù!xèŠèjÿøëß9JÿðùHT„>HrÉ`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~Ht…`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HvÝ`~é¦ø~N€ é!xëé9)ù!xëßH°¥`ɦN€ é!xëé9)ù!xëßHñ`ɦN€ é!xëé9)ù!xëßHÍ`ɦN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHH‡Ñ`ɦN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHˆe`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HŒÑ`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~H9`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~Hف`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HØÙ`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HÚ¡`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HŒù`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~ÿðè¾ÿøèž9ÿðù
HZA`~é¦ø~ÿðN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~H`	`~é¦ø~N€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHai`ɦN€ =b…9k1Àé!xëËëé9)ù!xé^ÿèêÿèþÿØéÿà8ÿØè¾ÿøèžÿðè~ø0Êÿÿ|ÆQH\¡`~é¦ø~ÿØN€ ?…;Þ1Àé!xé^ëé9)ù!xèjêÿHa)`é^,#A‚ð~é¦8êøjûªøþN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHeA`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
He±`~é¦ø~ÿøN€ é!x=B…9J1ÀëéëÊ9)ù!xèžêÿè~ÿø9ÿøù
Hh­`~é¦ø~ÿøN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHOM`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿèžÿèèÞÿøè¾ÿð9ÿèè~ù
HOU`~é¦ø~ÿèN€ =B…9J1Àé!xëÊëé9)ù!xèÞè~ÿèè¾ÿøèžÿð9ÿèêÿù
HU)`~é¦|c4TjÙ~}JÐù^ÿèN€ é!x=…91ÀëééH9)ù!xèjëß9JÿøùHHVÝ`ɦN€ =…91Àé!xéHëé9)ù!xèŠÿþèªèjÿðëß9JÿèùHx¥ HB5`ɦN€ é!x=B…9J1ÀëéëÊ9)ù!xêÿè~HL1`~é¦ø~N€ é!x=B…9J1ÀëéëÊ9)ù!xè¾êÿè~ÿð9ÿðèžÿþù
HHé`~é¦ø~ÿðN€ `+©@ž8`8À`cðxçøB9D"ɦN€ ~é¦øjN€ ```8`8À`cð9D"ɦN€ `ª@@@œ,|©¦/¥9Jÿÿ9ÿÿAžÒÜ`ŒèœêBÿøKÿÒÈ|è*ª8@@œÿÐ/¥}J*AžÒ°|©¦`ÿÿ
ÿÿBÿøKÿҘ~é¦9ù
N€ ~é¦øjùN€ ~é¦øjùN€ ~é¦9ù
N€ ~é¦øjùN€ ɦøjùN€ 8`8À`cð9D"ɦN€ `ɦøjùN€ ɦ8êù
øÊ9ø÷ù
N€ /·êªÿèûªÿèAžl:µÿÿ:ÖÿÿH`,7:÷ÿÿA‚HŒuHÛq`|txŒvHÛa`ƒ AžÿÔ~i¦é^9ù
N€ >â:÷Ñ°KÿÙ~i¦N€ ~i›xKÿÑh~é¦éV8êù
øöN€ ~é¦ûªN€ ~é¦ûªN€ ~é¦8êøjøþN€ ~é¦øjN€ /©@žþÜ8`8À`cðxçèÂ9D"ɦN€ 9éAxø¾ù	ÿð9*ù!xëêé?})¦N€ 9éAxø¾ù	ÿð9*ù!xëêé?})¦N€ /¥9ÿþ9JÿþAžÐ``¤è4¥ÿþ´ê@‚ÿôKÿÐt/©@žýX8`8À`cðxçèÂ9D"ɦN€ }&Kx|é;xKÿÎ@9Jÿð}	CxùEKÿÍÌéG})RKÿÍp`8b€Hâõ`9 =b‘+©ÐKÿ»d9 Kÿш/§@žýª@@@œ\/¥9ÿø9JÿøAžÏÜ`èè	4¥ÿøøê	@‚ÿôKÿÏÄ/¥9ÿü9JÿüAžÏ´```„è4¥ÿü”ê@‚ÿôKÿϔ|åBª8@@œÿ /¥}J*AžÏ||è;x|§(PH``````èÈÿù|è*øÊÿù/§@žÿðKÿÏ@€
```|¦ûÁÿðûáÿø8 |Ÿ#x|~x8`øø!ÿKÿ¹}ãûx`HÒa`8 ;â€(|dx8`Kÿ¹Y8 Äóx8`Kÿ¹IãûxHÒ1`åûx|dx8`Kÿ¹-8 8€8`Kÿ¹/£@ž$8!€èëÁÿðëáÿø|¦N€ ``8!€8 8€8`èëÁÿðëáÿø|¦Kÿ¸Ð€|¦ûaÿØûÿà?‚ûáÿøûAÿÐ;œ¡°|Û3xû¡ÿèûÁÿð;à`¡"@`éB8`é0øø!ÿA±!€9 ùAx9\H})¦ùpH``}´B@Œ*99J/‰@žÿè`;ÃóxHÑ`Åóx|dx8`Kÿ¸8 8€8`Kÿ¸|zyA‚€`{þ.¤8‚€`KÿþM{é$ÉðP/£¼òø}Ažp`CÓx8‚€Kÿþ%/£ø}Ažl8 8p8``Kÿ·¥8ap;¢€ÀHЉ`8 |dx8`Kÿ·…8 DÓx8`Kÿ·u£ëxHÐ]`¥ëx|dx8`Kÿ·Y8 8€8`Kÿ·I/£@ž¼8 8€8`Kÿ·18 8€|}x8`Kÿ·¤´8 8„ÿú|ƒ"cÛxHÓ`9 ãûx}<ñ.8!ÀèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8b€ÐHß`8!À8`ÿþèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`ÿÿKÿÿ`8b€8HÞÕ`8`ÿÿKÿÿx`8b€hHÞ½`8`ÿÿKÿÿ``8b€˜HÞ¥`8`ÿÿKÿÿH€``+ƒA¼|¦ûÁÿðûáÿøxi$=Bxc.¤|iP9J¡°Êøø!ÿ}*.8`ÿÿ/‰Až\|¿+x8`8 KÿµÑäûx8 8``Kÿµ½èž8 ;âH8`Kÿµ©ãûxHΑ`åûx|dx8`Kÿµ|c´8!€èëÁÿðëáÿø|¦N€ ```8`ÿÿN€ €```+ƒA¼|¦ûÁÿðûáÿøxi$=Bxc.¤|iP9J¡°Êøø!ÿ}*.8`ÿÿ/‰Až\|¿+x8`8 Kÿ´ñäûx8 8``Kÿ´Ýèž8 ;âH8`Kÿ´ÉãûxHͱ`åûx|dx8`Kÿ´­|c´8!€èëÁÿðëáÿø|¦N€ ```8`ÿÿN€ €```Tcð~Tc>/ƒAž8`N€ ``/¥Ažÿì|¦ûÿà`ûaÿØ;‚Pû¡ÿèûÁÿð|½´ûáÿø›ãx;äÿÿ;Àøø!ÿaH```}>´œAžXƒãxHÌÑ`eÛx|dx8`Kÿ³Í9>‰èpcÿ@‚ÿÌ8! ÃóxèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8! £ëxèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûáÿø`;âhãûxøø!ÿHÌ%`åûx|dx8`Kÿ³!`8 8€8`Kÿ³
`8!€èëáÿøxc |¦N€ €|¦ûáÿø|xøø!ÿKÿÿ}|cúx H```Kÿÿaƒø@Aœÿø8!€èëáÿø|¦N€ €`|¦ûáÿø`|dx;âx8 8`øø!ÿKÿ²]`ãûxHËA`åûx|dx8`Kÿ²=`8!€èëáÿø|¦N€ €`|¦ûáÿø|xøø!ÿKÿþ­8!€="…è|cúëáÿøiS°|¦N€ €```|¦ûáÿø?⅃ÿS°øø!ÿKÿþY8!€è|cøPëáÿø|c´|¦N€ €```8`èN€ ```|¦ûáÿø`|dx;⁀8 8`øø!ÿKÿ±-`ãûxHÊ`åûx|dx8`Kÿ±
`8 8€8`Kÿ°ù`8!€èëáÿø|¦N€ €|¦ûÁÿðûáÿø|ž#x8 |dx`8`;⁐øø!ÿKÿ°¥`Äóx8 8`Kÿ°‘`ãûxHÉu`åûx|dx8`Kÿ°q`8!€èëÁÿðëáÿø|¦N€ €`|¦ûáÿø`|dx;⁠8 8`øø!ÿKÿ°`ãûxHÉ`åûx|dx8`Kÿ¯ý`8 8€8`Kÿ¯é`8!€èëáÿø|¦N€ €|¦ûÁÿðûáÿø|ž#x8 |dx`8`;⁰øø!ÿKÿ¯•`Äóx8 8`Kÿ¯`ãûxHÈe`åûx|dx8`Kÿ¯a`8!€èëÁÿðëáÿø|¦N€ €`|¦ûÁÿðûáÿø|~x|Ÿ#xøø!ÿKÿþÕ}#û’|jx})ùÒ£HAž(ÄóxKÿÿ9|~ú8cÿÿKÿþ­9?ÿÿ}_Ð|i}J88!€}CSxèëÁÿðëáÿø|¦N€ €|¦ûÁÿðûáÿø|¾+x|Ÿ#x8 |dx8`øø!ÿKÿ®‰`äûx8 `8`Kÿ®q`;âÀÄóx8 8`Kÿ®Y`ãûxHÇ=`åûx|dx8`Kÿ®9`8 8€8`Kÿ®%`8!€èëÁÿðëáÿø|¦N€ €``|¦ûÁÿðûáÿø|¾+x|x8 8`øø!ÿKÿ­Í`äûx8 `8`Kÿ­µ`;âÐÄóx8 8`Kÿ­`ãûxHƁ`åûx|dx8`Kÿ­}`8!€èëÁÿðëáÿø|¦N€ €|¦ûáÿø`|dx;âà8 8`øø!ÿKÿ­-`ãûxHÆ`åûx|dx8`Kÿ­
`8 8€8`Kÿ¬ù`8!€èëáÿø|¦N€ €|¦ûáÿø`|dx;âð8 8`øø!ÿKÿ¬­`ãûxHő`åûx|dx8`Kÿ¬`8 8€8`Kÿ¬y`8!€èëáÿø|¦N€ €|¦ûáÿø`|dx;â‚8 8`øø!ÿKÿ¬-`ãûxHÅ`åûx|dx8`Kÿ¬
`8 8€8`Kÿ«ù`8!€èëáÿø|¦N€ €|¦ûÁÿðûáÿø|~x8 `8`;â‚øø!ÿKÿ«©`Äóx8 8`Kÿ«•`ãûxHÄy`åûx|dx8`Kÿ«u`8!€èëÁÿðëáÿø|¦N€ €``|¦ûÁÿðûáÿø|~x8 `8`;₠øø!ÿKÿ«`Äóx8 8`Kÿ«`ãûxHÃé`åûx|dx8`Kÿªå`8!€èëÁÿðëáÿø|¦N€ €``|¦ûÁÿðûáÿø|~x8 `8`;â‚0øø!ÿKÿª‰`Äóx8 8`Kÿªu`ãûxHÃY`åûx|dx8`KÿªU`8!€èëÁÿðëáÿø|¦N€ €``|¦ûáÿø`|dx;â‚@8 8`øø!ÿKÿ©ý`ãûxHÂá`åûx|dx8`Kÿ©Ý`8 8€8`Kÿ©É`8!€èëáÿø|¦N€ €|¦ûÁÿðûáÿø|¾+x|Ÿ#x8 |dx8`øø!ÿKÿ©y`äûx8 `8`Kÿ©a`;â‚XÄóx8 8`Kÿ©I`ãûxHÂ-`åûx|dx8`Kÿ©)`8!€èëÁÿðëáÿø|c´|¦N€ €``,#M‚ |¦ûAÿÐûaÿØ|zxûÿàû¡ÿèûÁÿðûáÿøøø!ÿaèÃè£èƒ`8b‚hHЭ``8b‚˜HН`ééZ}(S’}IQÒ}
Rx1Jÿÿ})”/©Až´```;º(;à;‚ð;b™X;‚“ é´{ä y)тÃóxy)$}=H*}$$6x„àHÐ1`ééZ8ÿxé¡xÿ .¿}(S’O}IQÒ}
Rx1Jÿÿ})”¿H@@œ4A–ÿ xéaAš@‚ÿ”cÛxHÏÝ`Kÿÿ„ƒãxHÏÍ`Kÿÿt`8b‚èHϹ`8! èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûaÿØ|›#yûAÿÐûÿàû¡ÿèûÁÿðûáÿøøø!ÿaA‚¨/¥|zx|½+x@ž; Ûë’}>éÒiJx1)ÿÿÞ”{É {Üт1)ÿÿœ”8|xc$KÿöÅ`|yA‚Xû_û{…(8€ÿûŸû¿8(ûß H…`8! ãûxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8! 8`èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €``ûáÿø|yûaÿØûÿàû¡ÿèûÁÿð@‚(8`ÿÿëaÿØëÿàë¡ÿèëÁÿðëáÿøN€ ``ë¿ëŸ 8`ÿÿÄë’}>éÒ|„Jx0„ÿÿÞ”¾à@Aÿ¼é_{Å }*ë’}	éÒ}JBx1Šÿÿ}ŒQ}ŒJyŒ!A‚ÿ”8ß(9``}´y x‰Ñ‚|›#xy)$|H*|	\6y'áA‚tŒ(@AœÿTˆ(@}	Cx@œX9HŠ(@}
@ø}J*yJ 9J}I¦@ýHÔ`}FP*}J<6yGáA‚ 9)}*´y' yJтy) yJ$Bÿ؉(@Až 98¥Œ@@x¥ y @žÿXKÿþÐ/„ÿÿ8`ÿÿAÞþÈ}^"ª@@@P8àH|H*}´y 9(x„Ñ‚y( |ëX6¨P@})´|Xxx„$y)тy)$|!*AœÿÈëŸ ë¿|{éÒé?ÞàPûß |cJKÿþX9@}I¦Kÿÿ<```|¦|iyøø!ÿ‘A‚ éIèi¤P@Aœ |ä*}
¨8@Aœèé|Ê Pèi };’|Æ;’|è9ÒxÄ xÊ |¥:x0¥ÿÿ}”|È2}B¤0@ù	 @œ@8i(8€`}I´8ªy)тyH y)$xª ª0@|ˆ@6|ãH*|èCx}I*AœÿÔ8!pè|¦N€ |§+x|ex`|†#x8b‚ø}DSxH˙`8!pè|¦N€ €`="…9)S¸=	 éH/ªAž,}*8`ÿÿ©@@M ù(}CSxN€ ```}*Kxù(}*8`ÿÿ©@@@ÿÔN€ |ɦN€ }è¦|#x8à|#8A‚HÙ}B¦,A‚4HxèÄ}B¦8à|'0A‚8àè„|' 8`A‚P|ˆ#x|qB¦ùèˆ8à|' A‚|„øèˆøèˆøèˆ|„ø(8ˆ ø 8`~ƒx}è¦N€ }è¦|°+x|±+xH9,@‚}è¦N€ |ɦ:ÿÿ8¥ÿÿŽEžPBÿø~%‹x}è¦N€ }(¦|ˆ#x|jx|…#x8¥ |«+xHE,@‚ è¤,|„*@‚ÿÔ8`}(¦N€ 8`è¤èÄèä|¥B}(¦N€ 9Jÿø9kÿøéª	éË	|-p9€A‚N€ qÎÿ@‚ÿä9€N€ ø!ÿ±|¦ø0ùá8ùÁ@ù¡H|¯+xKÿÿYè0|¦øø¯øÏøïé¡HéÁ@éá88!PN€ N€ xfÁÆ8`X8€8 D"N€ |jx8`T8€D"|ƒ#yA‚x£F ˜jN€ }¦|ixˆi,A‚Kÿÿ±9)Kÿÿì}¦N€ }¦|ixy#' pc,
A€8c8c0Kÿÿ}y#F pc,
A€8c8c0Kÿÿay#e pc,
A€8c8c0KÿÿEy#„ pc,
A€8c8c0Kÿÿ)y#£ pc,
A€8c8c0Kÿÿ
y#Â pc,
A€8c8c0Kÿþñy#á pc,
A€8c8c0KÿþÕy#"pc,
A€8c8c0Kÿþ¹y#'pc,
A€8c8c0Kÿþy#Fpc,
A€8c8c0Kÿþy#epc,
A€8c8c0Kÿþey#„pc,
A€8c8c0KÿþIy#£pc,
A€8c8c0Kÿþ-y#Âpc,
A€8c8c0Kÿþy#ápc,
A€8c8c0Kÿýõy#pc,
A€8c8c0KÿýÙ}¦N€ }¦|ixKÿÿ}¦|ixKÿÿt}¦|ixKÿÿ |è¦H|Ȧ|è¦8ÆÿxxgÆj|æ8î|8N€ }h¦|ix8`CKÿüù}#KxKÿÿ18`
Kÿüé}h¦N€ }h¦|ix|Š#x|¬+x8`
KÿüÉ8`
KÿüÁ}ƒcxKÿü¹}#KxKÿþñ8` Kÿü©}CSxKÿüÝ8`
Kÿü™8`
Kÿü‘}h¦N€ 8 EKÿÿ¤}h¦KÿÿQ}h¦8 W@ÿN€ }h¦8¥ Kÿÿ5}h¦8 D@ÿtN€ }h¦|…#xTc@.Kÿÿ8`A8`}h¦N€ |¨¦H|Ȧ8Æþtpc|Ã2˜†|¨¦N€ N€ `#m*E/ŠLF@ž”|¦ûáÿø|xøø!ÿ‰#/‰Až ‰#/‰AžX/‰@žHM`¡?9)ÿþU)>+‰AT¡?9)ÿìU)>+‰APˆ8!€èëáÿø|¦N€ `HÁ`Kÿÿ´`8`ÿÿN€ ``8`ÿýKÿÿÄ``8`ÿüKÿÿ´€```|¦ûaÿØûÿà|Û3xû¡ÿèûÁÿð|#x|~xûáÿø|¼+xøø!ÿaKÿþñ/ƒ|xAž”/ƒAž<è}/£@ž;à8! ãûxèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ fÛx…ãx8€ÃóxH!`ø}‰>/‰Ažÿ¨ÃóxHÕ`xc +ƒè}Až@;àKÿÿ„`fÛx…ãx8€ÃóxH`ø}‰>/‰AžÿX;àKÿÿP;àKÿÿH€```|¦ûAÿÐûaÿØ|ú;xûÿàû¡ÿè|¼+x|}xûÁÿðûáÿø|Û3x|Ÿ#xøø!ÿaKÿýÉ/ƒ|~xAž|/ƒ@žD£ëxH-`FÓxeÛxãøP£ëxäûxH!`äûxÿ£ëxûüHy`8! ÃóxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `£ëxHí`FÓxeÛxãøP£ëxäûxHá`8! |cúø|ÃóxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûáÿø|xøø!ÿKÿü½/ƒAžD/ƒAž8!€8`ÿÿèëáÿø|¦N€ ãûxH
`8!€èëáÿø|¦N€ ãûxH`8!€èëáÿø|¦N€ €`}€&|¦û!ÿÈûAÿÐ|Ù3xûaÿØû¡ÿè|»+x|}xûáÿøûÿÀ|š#x;àûÿàûÁÿð‘.%-¦øø!ÿQƒÃÃòH$`¡=,9_¡*}_´‰PÞBAœØ>/‰@žÿ܀¾€ž… @š*ƒãx@žôƒA’,øA(é;€žé{})¦è[N€!èA(/£@žÿ”€¾|ÂƒãxH´å`>€¾8€|©(P|iâx¥ H´%`€žƒãx/¤AžÿPAŽÿLøA(é9éy})¦èYN€!èA(¡=,9_¡*}_´‰PÞB@œÿ08!°€}聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ `8bƒ@H¿Ù`8!°8`聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ €` ã,}#@.}B/‰AžL Ã*9 H```H/ŠAž(9)}2‰8})´@ÿä8`N€ ``€hN€ ```€c$N€ ```9C8à} T,9C}@V,±C9C}@V,‘#y) }#J±C9C}@T,‘C9C}@T,‘C9C }@T,‘C 9C$}@T,‘C$9C(}@V,±C(9C*}@V,±C*9C,}@V,±C,9C.}@V,±C.9C0}@V,±C09C2}@V,±C2``I9}´}@M,9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I9I}@T,‘I¡C, Ã*Š@})2@œÿŒN€ ``}€&|¦û!ÿÈûAÿÐ|Ù3xûaÿØû¡ÿè|»+x|}xûáÿøûÿÀ|š#x;àûÿàûÁÿð‘.%-¦øø!ÿQëà ÃòH$`¡=89_¡6}_´‰PÞBAœØ>/‰@žÿÜè¾èž¥ @š*ƒãx@žôëA’,øA(é;èž(é{})¦è[N€!èA(/£@žÿ”€¾$|ÂƒãxH±`é> è¾(8€|©(P||Jx¥ H°U`èž(ƒãx/¤AžÿPAŽÿLøA(é9éy})¦èYN€!èA(¡=89_¡6}_´‰PÞB@œÿ08!°è}聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ `8bƒ€H¼	`8!°8`聁ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}‘ } N€ €`é  ã8}#@.}B/‰AžL Ã69 H```H/ŠAž(9)}2‰8})´@ÿä8`N€ ``èhN€ ```|¦û!ÿÈûAÿÐ|™#xûaÿØûÿà``ûÁÿðûáÿø;@|xúáÿ¸ûÿÀ;bƒà;‚ƒÀû¡ÿèøø!ÿAë£(£ê;Ý H `¡?<9Z;Þ@}Z´‰PAœ\>ÿä/‰@žÿà>y)6d}=Jé)y'ÿãA‚ÿÈé~/«Ažÿ¼‚þ;9 z÷6d~ýº`è~ÿøé éW|i}?@.}B}ŸèŒ/‰x‡"xé$xç.¤|é8P}'R ÿ8|¿JAž€ ß69 HH/ŠAžh9)}2‰8})´@ÿä}_*x„ èìé%}R+„@|ù:}'JA=Bÿþ9J—€x‡d|ê:ª}GR}I¦N€ àPàà˜ èààà00ààààààààààààààààààààààààààÄ€à°àà0àà0000¼ààààà”00ààà00```}_*é(©P@@þ¨ƒãxH¸`é~é>	´¸X@	ÃxAœþ¡?<9Z;Þ@}Z´‰P@œý¬8!Àèêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ y)d±(é>é~	´¸X@	ÃxAœýœKÿÿé(})Êù(é>é~	´¸X@	ÃxAœýpKÿÿdy*ây)„}*J±(é>é~	´¸X@	ÃxAœý@Kÿÿ4``y)„±(é>é~	´¸X@	ÃxAœýKÿÿ``‘(é>é~	´¸X@	ÃxAœüäKÿþØ```y)"±(é>é~	´¸X@	ÃxAœü°Kÿþ¤``y)„ ±(é>é~	´¸X@	ÃxAœü€Kÿþt``cÛxH¶Ý`é>é~	´¸X@	ÃxAœüLKÿþ@€	``ûÁÿðûáÿø8£ 8À9C;À|æ,,} ,,8À8£(þT,}T,;Ã}@,,xçÆ{ÿÆ});x|æ,,}ûx;ã08£4ùù# 98Ã6xçÆ}#J}J;x8ã8ùC(9C}F,±9:}@V,±C9C<Àô,“Ã;Ã>àü,“ã0| .,°£4|À6,°Ã6|à>,°ã88à}F,±:}@V,±C<Àö,³Ã>`;é9	8 9@}`ü,|€D,|Åü,ÊD,;é9I | ü,xÆÆ{ÞÆ}k3x|„óx8À;À}ü,þT,|ÀT,;À9I({ÿÆyÆ|ÆûxþT,|¥Cx}T,;É0{ÿÆ}@ô,}ûx;à|ô,ø©€©øÉ ù	(8É9ùiø‰}´xÆ| M,}JxùI0|À4,É¡C8 Ã6Š@})2@œÿ,ëÁÿðëáÿøN€ €c0N€ ```|¦ûÁÿðûáÿø|ž#x8 |dx`8`;â„øø!ÿKÿŒ…`Äóx8 8`KÿŒq`ãûxH¥U`åûx|dx8`KÿŒQ`8 8€8`KÿŒ=`8!€èëÁÿðëáÿø|c´|¦N€ €```|¦.¥ûÿàû¡ÿèûÁÿðûaÿØ|¾+x|}xûáÿø|œ#xøA–t%=@HaJ})Rx})4U;Ù~< D8`(8€`¥"H9` }ˆ¦}kb«|Xl|¬|_¬L,8c+£@èA–$.»@–|<àÿÿ<À<xç ¾è¥ëx@d=àÉóxaH9)ÿü©è@HIŠ@@žÿìI/Š@žÿàI/Š@žÿԁI/Š@žÿȁI/Š@žÿ¼}%Kx}=Kx¼(Šãx@Ð¼ëxH```;œ¼P@œè<‰8@žÿì<‰0@žÿàŠãx@–ü<À|<àD`Æh`ç"¥à@œx8 H`;½½P@œ`=‰8@žÿìÝ©ëx|¨+x}J9U)0U0}	@PUÉþ}	¦|Hl|¬|O¬|¬L,9)€Bÿè;½½PAœÿ¨èëaÿØëÿàë¡ÿè8`ëÁÿðëáÿø|¦N€ `8àÿÿ8À<xç KÿþˆA– <Àh<à"`Æ|`çDKÿÿ@``<À|<àD`Æh`ç"Kÿÿ$<Àh<à"`Æ|`çDKÿÿ``èëaÿØëÿàë¡ÿè8`ëÁÿðëáÿø|¦N€ ```;`Kÿý¤``.»¥ëxŠãx@–ÿ˜Kÿþœ|¦+¤ûÿàû¡ÿèûÁÿðûáÿø|#x||x|¤+xøø!ýq@¤8 x¥ 8apH¤¥`+½;Ýýÿ{ÞºBŸãx;ÞAHH¬+©Až<+©@ž8`äûx`cð8¡p8À8à9D",>;ÿ;ÞÿÿA‚L{é`+©AžÿÈAÿ´/©@ž¼8`äûx`cð8¡p8À8à@9D",>;ÿ;Þÿÿ@‚ÿ¼9=ýÿ;½þy)ºB9Iy)M¤yJM¤©èPœR‰ëxy)`+©AžÔ@X+©@žÀ8`„ãx`cð8¡p8À§t9D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8`äûx`cð8¡p8À8à9D"Kÿÿ```8`äûx`cð8¡p8À8à€9D"KÿþÐ```¥ëxKÿþ```+©@žL8`„ãx`cð8¡p8À§t9D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8`„ãx`cð8¡p8À§ëx9D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ /©@žÿ¼8`„ãx`cð8¡p8À§t9D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ €`<€`„ < `¥Œøƒø£N€ D"N€ xfÁÆ8`X8 D"N€ }H¦H-}H¦,M‚ = ¸a)R€‰|dH®8„‰N€ |dx8`ÿÿ= ¸a)R€©€É|0@L‚ 8`TD"= ¸a)R‰8`i(M‚ 8`ÿÿø©øÉN€ è¤èÄ|dx8`D"N€ 9`}*Kx}	Cx|è;x|Ç3x|¦+x|…#x|dx8` D"N€ |…#x|dx8`<D",#|ƒ#xM‚ 8`ÿÿN€ |¦+x|…#x|dx8`@D"N€ |è;x|Ç3x|¦+x|…#x|dx<``cðD"N€ |¦+x|…#x|dx<``cðD"N€ ```|¦û¡ÿèûÁÿð|~xûáÿø|#xøø!ÿqˆc8cTc:|c´Kÿ×a`xiá|x@‚Pxi÷ã@‚ˆ9 {ãä™>	KÿÚi`8!|cêø~èë¡ÿèëÁÿðëáÿø|¦N€ ```9 xcd™>	KÿÚ%`8!|cêø~èë¡ÿèëÁÿðëáÿø|¦N€ ``ˆ~8cTc:|c´KÿÖ±`xcÆÿxKÿÿ\€ûÁÿð|~xûáÿø8€8`<ÅóxD"/£@žPT‰@>8`<P‰À8¾P‰Ä.8€y? D"/£@žHT‰@>ëÁÿðP‰ÀP‰Ä.}$KxxƒÆ|cûxëáÿøN€ ;àÿÿ8`<{ÿ 8€8¾D"/£AžÿÀ8`ÿÿëÁÿðxcÄ|cûxëáÿøN€ ```|¦û¡ÿèûaÿØ8`pûÿàûÁÿðûáÿøøø!ÿQKÿÒ½`|}yA‚ 8`4Kÿ֙`p~ÿ@‚$H¸`8|c´KÿÖy`p~ÿA‚œÃóxß´KÿÖa`Tc>/ƒ	@žÿÐ8KÿÖI`T|>8KÿÖ9`T{>8KÿÕ)`+œxd Ažø@ä+œAžÌ+œ;ÝH@žÿ€›~ÃóxKÿýe›ž
8|c´KÿÕå`p~ÿ@‚ÿp`‰="/‰Až‰=2/‰@žL9 8}8€‘=™=™=Kÿý£ëx8!°èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `‰=B/‰Ažÿ°‰=R/‰Ažÿ¤9 £ëx‘=Kÿÿ´``;Ý8Kÿÿ@``+œ;ÝAžÿ,Kÿþ¤8~øp;Ý(KÿÔ`}hèpKÿÿ`8b„(H©I`8`KÿÿT€```xj¤xi&ä}*Jxc$9)8cy)äxcä|iN€ ```ûáÿø|x#/‰Ažpè£T‰D.T†Æ>|ÆKx8`@8€TÆ>8¥D"|¬è¿8`<8€8¥D"/£8`ÿÿxc @žTŠÆ>T‰D.}JKxUC>ëáÿøN€ ``è£TŠD.T†Æ>|ÆSx8`@8€TÆ>8¥D"|¬è¿8`<8€8¥D"/£8`ÿÿxc @žÿ¨T‰Æ>TŠD.ëáÿø})SxU#>N€ ûáÿø|x#/‰@ž€è£T‰D.T†Æ>|ÆKx8`@8€TÆ>8¥D"|¬è¿8`<8€8¥D"/£Až<`ÿëáÿø`cÿÿxcƒä`cðN€ T‰@>ëáÿøP‰ÀP‰Ä.}$KxxƒeN€ `ëãT‰D.T†Æ>|ÆKx8`@8€TÆ>8¿D"|¬8 ëáÿøKÿûP|¦û¡ÿèûÁÿðûáÿøøø!ÿqC/Š@žP|ž#x|xKÿÿÄóx|}xãûxKÿþ8!èxc&äëÁÿðëáÿø|}ë¡ÿè|¦N€ ```ëãT‰D.T†Æ>|ÆKx8`@8€TÆ>8¿D"|¬8!8(èë¡ÿèëÁÿðëáÿø|¦KÿúŒ€```|¦û¡ÿèûÁÿðûáÿøøø!ÿqC/Š@žP|#x|xKÿÿ¤ëx|~xãûxKÿý58!;Þÿèxcdë¡ÿèëáÿø|còëÁÿðxcä|¦N€ `ëãT‰D.T†Æ>|ÆKx8`@8€TÆ>8¿D"|¬8!80èë¡ÿèëÁÿðëáÿø|¦Kÿù¼€```/¤@žø£Ã°ã±N€ `9 xª"| ,}I,9#9C8c|ÀM,|àW,},N€ ``ûáÿøû¡ÿè|xûÁÿð#/‰Až˜ë£T‰D.TžÆ>ÞKx8`@WÞ>8€8½ÆóxD"|¬8`<8€8½D"/£9 ÿÿy) @žT‰D.TŠÆ>}JKxUI>€Ÿhè¿(8`@Æóx}$IÖ8€y) |¥JD"ë¡ÿèëÁÿðëáÿøN€ `è£TŠD.T†Æ>|ÆSx8`@8€TÆ>8¥D"ë¡ÿèëÁÿðëáÿøN€ |¦ûÁÿðûÿà|~xû¡ÿèûáÿøøø!ÿq#/‰@žxé#TˆD.T†Æ>|ÆCxx¿ 8`@8€8©TÆ>D"|¬Wÿ£>è¾8`@Wæ@>8€SæÀSæÄ.8¥xÆ D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ |¿+xKÿú­ëžWæ@>8€SæÀSæÄ.|}x8¼ 8`@xÆ D"{é"8`@U&@>8€Q&À8¼$Q&Ä.xÆ D"{¥&äëž8`@åú8€Wæ@>SæÀ8¼(SæÄ.xÆ D"{é"8`@U&@>8€Q&À8¼,Q&Ä.xÆ D"{½¤8`@;½8€ýúë¾{ÿäWæ@>SæÀ8½0SæÄ.xÆ D"{ÿ"8`@Wæ@>8€SæÀ8½4SæÄ.xÆ D"è¾8`@8€8À8¥D"8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ €|¦ûÿàû¡ÿè|¼+xûÁÿðûáÿø|¾´|Ÿ#xÄóx|}xøø!ÿqKÿùA8€xj¤xi&ä}*Jxc$9)8cy)äxcä|iKÿÊÁ`/£øAޘ?8€y*&äy%¤|¥Ry)$8¥9)y)äx¥ä|¥JT¥&H•]`è¿Äóx£ëxKÿýiÄóx£ëxKÿúmÄóxø £ëxKÿû-ûŸ9 ø(8!}#Kxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8b„HH¡A`9 ÿÿKÿÿÈ€`#|†#x/‰@ž$è£8€8`@TÆ>8¥D"N€ `è£8€8`@TÆ>8¥D"N€ ``8€Kÿÿœ```ûáÿø|Ÿ#x#/‰Až@è£8€8`<8¥D"/£9 ÿ@žT‰>‘?ëáÿøN€ ```è£8€8`<8¥D"/£9 ÿAžÿȑ?ëáÿøN€ ``ûáÿøû¡ÿè|Ÿ#xûÁÿð#/‰@ž8è£T†@>8`@P†ÀP†Ä.8€8¥xÆ D"ë¡ÿèëÁÿðëáÿøN€ ëÃ8€8`@<À;¾¥ëxD"{é";ÞU&@>8`@Q&À8€Q&Ä.ÅóxxÆ D"8`@8€¥ëx8ÀD"Wæ@>8`@SæÀ8€SæÄ.ÅóxxÆ D"ë¡ÿèëÁÿðëáÿøN€ ```#|jx/‰Až¤û¡ÿèûÁÿð8€<ÀûáÿøëÃ8`@ÅóxD";¾8`<8€¥ëxD"/£Až¤;àÿÿ{ÿÄ8`@8€Åóx8ÀD"8`<8€¥ëxD"/£9 ÿÿy) @žT‰@>P‰ÀP‰Ä.y) ãKxë¡ÿèëÁÿðëáÿøN€ 8`<8€èªD"/£8`ÿÿxc Lž T‰@>P‰ÀP‰Ä.y# N€ ```T‰@>P‰ÀP‰Ä.}$KxxŸÆKÿÿT```|¦ûÁÿðûáÿø|ž#x|xøø!ÿqKÿþÅxiãA‚¬ÄóxãûxKÿýÁãûxKÿþ©Éy@‚`8pãûxKÿý!pãûxa)}$´‘!pKÿü}ãûx8pKÿüñ!py)ïâ1)ÿÿ|c8!èëÁÿðëáÿø|¦N€ `<b8c `Åóx8‚„˜Hœý`8`ÿÿKÿÿÄ```|ex<b8c `8‚„hHœÍ`8`ÿÿKÿÿ”€û¡ÿèûáÿø|#x|xûÿàûÁÿð#/‰Až /…ëÃHAž¤@`/…Ažø/…@ž8`<8€|¾êD"/£;€ÿÿ{œ @žxœ 8½8`<8€|¾*D"/£9@ÿÿyJ @žxŠ ?yCÆ|cãx/‰@žpëÿàë¡ÿèëÁÿðëáÿøN€ ``/…ëÃ;Þ@žÿd8`<8€|¾êD"/£Až8`ÿÿxc |jx?/‰Ažÿ¨UCÆ>UID.ëÿàë¡ÿèëÁÿðëáÿø|cKxTc>N€ ```8`<8€|¾êD"/£Až¬8`ÿÿxc |jx?/‰AžÿHUC@>ëÿàë¡ÿèëÁÿðëáÿøQCÀQCÄ.xc N€ ```/…@ž<8`<8€|¾êD"/£8`ÿ@žþôëÿàë¡ÿèëÁÿðëáÿøTƒ>N€ `ëÿàë¡ÿèëÁÿðëáÿø8`ÿÿN€ ``xŠ xƒ Kÿÿ\`TŠ>xƒ Kÿþì`UI@>Wƒ@>QIÀSƒÀQIÄ.SƒÄ.xc y)Æ}#xKÿþp```ûÿàû¡ÿè|Ü3xûÁÿðûáÿø#/‰AžtëÃH/œ@L;üÿÿÞ*{ÿ ;¤ÿÿ;ÿ8`<8€ÅóxD"/£9 ÿ;Þ@žT‰>,?=;ÿÿÿ@‚ÿЃãxë¡ÿèëÿàëÁÿðëáÿøN€ `ëÃ;ÞKÿÿŒ``|¦ûáÿøûÁÿð9 |xøø!ÿq‘!pKÿù!`èrãûxKÿø±`!pãûxa)}$´‘!pKÿø•`?/‰Až„<€ãûxx„ƒä`„@Kÿû‘`/£Až$``8‚„°8b„ÀH™q`!pãûxa)€}$´‘!pKÿø5`9 8!}#KxèëÁÿðëáÿø|¦N€ ```8€@ãûxKÿù	`<‚¥8 8„sØãûxKÿö±`|~y@‚ÿt8€ãûxKÿñÉ`?|jx³Ããûx})4U)Ù~})Ðy)ÁÂy)@9)±*!pa)}$´‘!pKÿ÷…`ãûxKÿùy`9 xj×ãA‚ÿ@8 8€ãûxKÿûy`|i´Kÿÿ$``8pãûxKÿ÷¹`Kÿÿ@€|¦ûáÿø8€€|xøø!ÿKÿ÷	`ãûxKÿ÷]`8!€èëáÿø|¦N€ €`|¦úÁÿ°ûAÿÐ9 ÿÿû¡ÿèûáÿø|º+x|–#xúaÿ˜úÿ 8 8€ú¡ÿ¨úáÿ¸|Ý3x|xûÿÀû!ÿÈøûaÿØûÿàûÁÿðø!ÿ™!pKÿú‘`9:ÿÿ})ê£H@Aœ¼8 8€ãûxKÿúm`xs ||´zhá@‚(8€ãûxKÿîm`8€|uxãûxKÿïI`8€|wxãûxKÿð`8€|xxãûxKÿðÁ`?£x|~x||ÑÒ/‰£ž@žP= €=¥xc¸"=B¥‘(t9 =¥‘*tøhtWz<€Ÿ<¢¥ZÚ8à}Z«–8À8¥t}J©ÖJÐP;:C´}Y«–xc&ä|w{T ;ZV”>}J©Ö*ÈP{9 W(>Kÿðñ`}Z«–|ݙրŸ{#&ä8à~ųxxÆ |w}J©ÖJÐP{Z WH>Kÿð¹`€Ÿ{C&ä98à8À8¡p|wKÿð•`};«–_/Š})©Ö})ØPy) AžVŠÆ>VˆD.}JCxUT>y)¤}8J²‰|¬?;{W{>/‰AžWiÆ>WjD.})SxU;>³xãûx8€Kÿð`KÿºI`8cˆx H`|¬Kÿº-`ƒø@A¡>‰à@Ažÿä‰!p£´/©AžDˆp`8b…(H•E`8`H(`<b8c `…ãx8‚…H”Í`8`8!ðèêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿè|¦ëÁÿðëáÿøN€ ````8b„ÐH•`8`Kÿÿœ``9 €=B¥=¥xc¸"‘*t= WjD.‘(tWiÆ>=¥})Sx9tU;>xj"9 |`E,}IE,Kÿý”€
```|¦ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀ|·+x|xxû!ÿÈûAÿÐ|š#x8€ûaÿØûÿà|Û3x|ü;xû¡ÿèûÁÿðøûáÿøø!ÿ1Kÿë`8€|}xÃxKÿëí`8€|uxÃxKÿì©`8€|vxÃxKÿíe`€˜£6|x£Ã/¤AžW)Æ>W'D.});xU9>W)<zæ }IÊEÓx}*ë–8à})éÖ})PP:é}#´}Wë–y: xc&ä|u}*éÖ~é¸Pz÷ Vè>Kÿí½`€Ü€˜zã&ä98àeÛx|uKÿí™`}9떁WJ>/ˆ})éÖ})ÈPy) AžUHÆ>UGD.};xU
>y)¤}6J±I|¬8;9W9>/‰AžW)Æ>W*D.})SxU9>³68€ÃxKÿí`¡?<à˜=@˜`疀aJ–|馞H@AžH,`}
´B@ |¬¡?9
ÿÿžH@Ažÿè/ªAžh}@Ü,<‰P@AP‘<8`8!Ðèê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``}ISxKÿÿ°8`ÿÿKÿÿ°€`|¦=B¥ûÿàû¡ÿèûÁÿðûáÿø*tøø!ÿa/‰9 ‘!p@ž°|x|¼+xÊt|#xKÿðÍ`èrãûxKÿð]`!pãûxa)}$´‘!pKÿðA`?/‰@žÐ8€ãûxKÿñ5`<‚¥8 8„t ãûxKÿîÝ`|~y@‚Ð8€ãûxKÿéõ`?|jx³Ããûx})4U)Ù~})Ðy)ÁÂy)@9)±*!pa)}$´‘!pKÿï±`<bÿÿ†ãx¥ëxäûx8cn¸HÅ`8! Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``<€ãûxx„ƒäKÿòu`/£@ž8pãûxKÿï½`Kÿÿ``8‚…P8b„ÀHA`!pãûx;Àÿÿa)€}$´‘!pKÿï`8! Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ `;ÀÿÿKÿÿ@€```|¦ûáÿø8€€|xøø!ÿKÿî™`ãûxKÿîí`8!€9 =B¥èëáÿø‘*t|¦N€ €``|¦ûÿàû¡ÿè`ûÁÿðûáÿø9 9B…`=¥t|¼+x8 |}xøø!þ¡ù!ù!(;Áù!ðù! ùAù!ø9@ù!9 ø08€‘‘A(‘!ðûÁKÿñõ`8ÀTc>+ƒA|fx;ápTÆ>äûx8 £ëxKÿô`Ãóxûá H5`|yA‚X`äûx8b…hHŽ™`€(ÃóxH©`8!`ãûxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```ÃóxH]`8€|yA‚\`äûx8b…ˆHŽ-`€(ÃóxH=`8!`ãûxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ é!0‰)/‰Ažt8Á08 ÃóxH¥`8€/ƒ|x@œÿÐ|dx`8b… H±`€(ÃóxHÁ`8!`ãûxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8aðH%-`|yA‚``äûx8b…¸HQ`€ðÃóxHa`€(ÃóxHQ`8!`ãûxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8€8aðH"I`|y@‚|è¡; ;à/¥@žKÿÿŒA–X衽¥è@@H|½(P¦ëx|œêx¥ 8aðH"ù`/ƒ|x.£@œÿÄ|dx`8b…èHŒ…`Kÿÿ4¿ëxKÿÿ,`äûx8b…ÐHŒe`Kÿÿ€```|¦úAÿúaÿ˜|Ò3xúÿ ú¡ÿ¨|³+x|õ;xúÁÿ°û!ÿÈ}CxûAÿÐûÿà|zxû¡ÿèûÁÿð|#x8€øûáÿøúáÿ¸ûÿÀûaÿØø!ÿ!Kÿã`8€|xCÓxKÿãÝ`8€|vxCÓxKÿä™`8€|yxCÓxKÿåU`€š£™|~x/¤AžW‰Æ>WˆD.})CxU<>W˜<¥ëx£¾â8à}8û–8À8})ùÖ	ÀP;x´};û–xc&ä|v{ })ùÖiØP{{ Wh>Kÿå­`/µAž/´@ž(€š{c&ä98à8Àl~e›x|vKÿåy`}<û–ZV÷>/Š})ùÖ})àPy) AžVêÆ>VèD.}JCxUW>y)¤}9J²é|¬:;œWœ>/‰AžW‰Æ>WŠD.})SxU<>³™8€CÓxKÿåa`Kÿ¯)`8cˆx H`|¬Kÿ¯
`ƒø@A¡>H@Ažÿä8!à8`èêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿà|¦ë¡ÿèëÁÿðëáÿøN€ `;€š{c&ä}8û–~e›x|v8à8Àl})ùÖ	ÀP{ W>KÿäA`0òÿÿ€š{&ä|ç‘9xç¤z† ~¥«x|vKÿä`Kÿþœ€```|¦ûÁÿðûÿà9 û¡ÿèûáÿø8€|~xøø!ÿa‘!pKÿè%`!pÃóxa)}$´‘!pKÿè	`>/‰Až8<€Ãóxx„ƒäKÿë	`/£@žÜ8pÃóxKÿèQ`H`8€ÃóxKÿèÉ`;à;€HL`Kÿß¡`¤ëxÃóxKÿá‘`>;ÿ{ÿ ³ƒ})4U)Ù~})Ðy)ÁÂy)@9)±#ý´Ãóx¤ëxKÿߑ`/£@žÿ¤!pÃóxa)}$´‘!pKÿç-`8`8! èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8‚†8b„ÀHˆ`!pÃóxa)€}$´‘!pKÿæÕ`8`ÿÿKÿÿ¨€``|¦ûáÿø8€€|xøø!ÿKÿæ™`ãûxKÿæí`8!€èëáÿø|¦N€ €`|¦ûAÿÐûáÿø|xûÿÀû!ÿÈ8`ûaÿØûÿàû¡ÿèûÁÿðøø!ÿAKÿ¯
`|zyA‚/¿9 ‘:Ažt?b¥;{tÐ8 päûx?Â¥;ÞtPcÛxH{`cÛxKÿæE`8 ÄóxãûxKÿä¡`/£@ž„8 8ž0ãûxKÿä…`/£@žh8€cÛxKÿå`:/‰9 ‘!pAžDCÓx8!ÀèëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8€cÛxKÿå9`;/‰@ž$9 
8€cÛx‘>`Kÿæ%`="¥)t°8iêxc8(Kÿ­Ý`="¥/£|xøit`AÞ€›; ;; H```ëþ€Þ`è~¨ëx8à;ÿÿ;½Wœ>9&ê|cÂ})ÉÖy) ÿJåûxKÿà)`é>€¾`€›8x98à8Àê|i|¥úKÿßý`€›9Y{)¤é /Š€.¤A–W‡Æ>W†D.|ç3xTü>}(J}Y´; W½>³‰@žÿT|¬;=¥éHtp})4U)Ù~i)})Ðy) 9)±*;})4U)Ù~i)})ÐU)p9)€éHtp±*;=B¥éJtx/‰`B¡*AžP=¥=B¥éJt 9t´} G,9 ±*9@cÛx;Úÿÿ;à="¥é)t ±I!pa)}$´‘!pKÿã]`8€cÛxKÿßM`9 ‘:```äûx8 ;ÿcÛxKÿçA`/Ÿÿ´œ~@žÿÜKÿýˆ<€cÛxx„ƒä`„ Kÿæ`/£@ž09 8pcÛx‘>`KÿãU`KÿýÀ`8b†8Hƒá`!pcÛxa)€}$´‘!pKÿâ¥`CÓx8€Kÿ«õ`8`8!ÀèëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ <Â¥=B¥éJt ±&t´9 Kÿþ¸8€ƒãûxKÿâ9`CÓx8€Kÿ«‰`8`Kÿÿ”`8b†Hƒ1`8`Kÿüˆ€`,#M‚ |¦ûáÿø|xøø!ÿ#/‰@ž,ãûx8€Kÿ«!`8!€èëáÿø|¦N€ `<b¥8ctÐ8€€Kÿá•`<b¥8ctÐKÿáå`9 ãûx8€‘?KÿªÍ`8!€èëáÿø|¦N€ €`,#A‚|¦ûÿàû¡ÿè<â¥ûÁÿðûáÿø||x8çtP?¢¥;½tÐ<¢¥è¥txøø!ÿq]¡/Š@žT="¥¡)t´ˆH@Ažt€Ç`x„ }IC–}JAÖ}*HPy)H}%JƒéƒÉ;ÿÆðP}?C–ž @{Þ }	AÖèøP{ÿ AÝ€éG{é&ä|ŠH*ÅóxƒãxHu¡`]="¥<â¥èçtp¡	t´/Š9H¡±It´Až´UD.=B¥JtXU	Æ>})+x8ßÿÿU(>TßÆ>}(S–TÅD.ÿ+xWÿ>}IQÖ}J@PyI y)¤}'J³é|¬=9=B¥éJtpU>/‰AžU	Æ>UD.});xU(>±
£ëx8€KÿÛÍ`8!Ã´èëÿàë¡ÿèëÁÿðëáÿø|¦N€ UÆ>U
D.="¥¡)t´|ÆSxTÈ>ˆH@Až€Ç`xž }IC–}JAÖ}JHPyJH}%R9I9)àT,} L,;ÿ}&HP}_C–‰ð@y) }
AÖèøP{ÿ @ð`8b†`H€E`==¥éth{ê&ä/‰|ˆP*AÞþ|x‡"T†@>Tè@>P†ÀPèÀP†Ä.PèÄ.xÆÆ|ÆCxÅóx|Ä3xƒãxHsñ`]="¥<â¥èçtp¡	t´/Š9H¡±It´@žþT=B¥JtX;ÿÿÿWÿ>}(S–}IQÖ}J@PyI Kÿþl```8!8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```é{ê&ä}>Kx|ˆP*Kÿÿ0```8`ÿÿN€ |ž#xKÿþè€`,#A‚|¦/„êûAÿÐû¡ÿèûaÿØûÿà|#x|zxûÁÿðûáÿøøø!ÿaA¨?‚¥;œtЁ</‰@ž„?b¥;{t¶<¢¥€¥t°8€cÛxHri`€œ="¥é)t /¤£ÉAžWÉÆ>WÇD.});xU>>="¥)tˆWß<<b¥èct˜eÛx<Â¥€Æt°8à}_K–}*IÖéøPû´Wÿ>{{&ä9|cÚU>KÿØÁ`<b¥èct˜€œ;{98à{¦ EÓx|cÚKÿؕ`="¥)tˆ\=¥ét |þK–/Š}'IÖ})ðPy) AžWêÆ>WçD.}J;xU_>y)¤}(J³é|¬<;Þ=B¥éJt WÞ>/‰AžWÉÆ>WÇD.});xU>>³Ê|¬8€ƒãxKÿØe`8! £ëxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ?b¥;{tÀKÿþ€``8b†H}9`8! 8`èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8`ÿÿN€ €```|¦û¡ÿèûÁÿð9 ûáÿø|}xøø!ÿa‘!pKÿÛý`èr£ëxKÿۍ`!p£ëxa)}$´‘!pKÿÛq`=/‰Až„<€£ëxx„ƒäKÿÞq`/£AžX``8‚†°8b„ÀH|Q`!p£ëxa)€}$´‘!pKÿÛ`8`8! èë¡ÿèëÁÿðëáÿø|¦N€ 8p£ëxKÿÛe`?Â¥8 ;Þu@£ëxÄóxKÿٙ`/£@žÿ|8`Kÿ£•`<Â¥/£|ixøfuPAžt;àHé>è~€{ê&ä{åd|©*98à8À|cRKÿÖ	`]é´Wè>;ÿy)¤*¿€/Šé^ AžUÆ>UD.|ç3xTè>}*J±	@–ÿ”==¥éHu`})4U)Ù~i)})Ðy) 9)±*=})4U)Ù~i)})ÐU)p9)€éHu`±*|¬==B¥éJuh/‰¡*AžU*Æ>U(D.}JCxUI>=B¥8 8ž8£ëx±*upKÿØe`|y@‚þH8€£ëxKÿÓ}`=|jx³ã£ëx})4U)Ù~i)})Ðy) 9)±*!pa)}$´‘!pKÿÙ9`8`Kÿþ$`8b†ÈHzA`KÿýØ€``|¦ûáÿø8€€|xøø!ÿKÿØé`ãûxKÿÙ=`8!€èëáÿø|¦N€ €`|¦û!ÿÈûAÿÐûaÿØûÿà|{xûÁÿðûáÿøû¡ÿèøø!ÿQ˜è8€Kÿн`8€|xcÛxKÿљ`8€|yxcÛxKÿÒU`8€|zxcÛxKÿÓ`€›£š|~x/¤AžW‰Æ>WˆD.})CxU<>}<û–9£¾8à8À8¡èéùÖÿàPã´{ÿ xc&ä|yKÿӅ`;Wê>/‰AžUIÆ>UHD.})CxU*>{ÿ¤úú±_|¬;;œWœ>/‰AžW‰Æ>WŠD.})SxU<>³š8€cÛxKÿÓ}`KÿE`8cˆx H|¬Kÿ-`ƒø@A@¡>H@Ažÿä8!°8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8b†øHx)`8!°8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €`|¦ûÁÿðûáÿø|~x8 €8€øø!ÿ8apHkm`><Â¥èÆuh<â¥<¢¥8¥u@¡Gup/‰¡&AžàU'Æ>U(D.|çCxTé>‰P@Ažø%èå8ap}
K–}IÖ}PPyH}FB9JàT,;ÿ}_K–}*IÖ9@éøPé´{ÿ y)&ä}'J9)ÿð|ªL,|€L,x¥Æ|„+x8 Hk`^="¥<â¥èçu`¡	up/Š9H¡±Iup@ž¸=B¥JuH;ÿÿÿWÿ>}(S–}IQÖ}J@PyI HÐ```‰P@Až,%èå8ap8 }
K–}IÖ}HPPyJH}FRƒê;ÿ}_K–}*IÖéøPé´{ÿ y)&ä}'Jè‰ÿðHj]`^="¥<â¥èçu`¡	up/Š9H¡±IupAžÿPUD.=B¥JuHU	Æ>})+xU(>9?ÿÿ|ÈS–U?Æ>U%D.ÿ+xWÿ>}FQÖ}J@PyI y)¤}'J³é|¬>9=B¥éJu`U>/‰AžU	Æ>UD.});xU(>±
|¬8€ÃóxKÿЅ`ˆap8!èëÁÿðëáÿø|¦N€ 8!8`èëÁÿðëáÿø|¦N€ €``#=B¥éJuh/‰ jAžTiÆ>TjD.})SxU#>="¥¡)up}#x|c4TcÙ~hcN€ ````="¥øiu¨="¥ø‰u°="¥ø©u¸="¥øÉuÀN€ |¦<b¥ècu¸8  8€øø!ÿ‘HhU`<b¥ècuÀ8  8€Hh=`="¥9)uÈ=B¥éJu¸8!pùIè|¦N€ €`|¦ûáÿø=¥éu¨="¥9)uÈ?â¥<‚¥è„u¸;ÿu¨/¨øø!þ±é)C}$HP‘A8AÞ/¤AÞèß/¦AÞø+Š AÐ}%´y) ŠH@Aœ } %,øA(8á8èé(éh})¦èHN€!èA(/£@ž éé_8È} 6,8Ê|à6,‰8@@ž`‰*+‰kAޔˆh8c|cJx|c4TcÙ~hc|cÐxcèBxc8!Pèëáÿø|¦N€ ``8`ÿüKÿÿà``8`ÿúKÿÿÐ``8`ÿóKÿÿÀ``8`ÿùKÿÿ°``8`ÿôKÿÿ 8`ÿøKÿÿ˜8 È8€8apHf•`é?8 Ç8é8‰	}@>,+ŠÆAyE 8apHdÙ``8p8b‡Hr¥`8`ÿýKÿÿ<€``|¦ûÿàû¡ÿè||xûÁÿðûáÿø`;‡(øø!ÿqKÿý™?â¥;ÿuÈ9@Ãóxé?‘Ié?9Iù_9@d™I`Bé?9Iù_9@ÿÿ±I`Bé?9Iù_}@ä,‘I`Bë¿9=;½ù?HbÕ`|`ï,Ãóxë¿;½û¿Hb¹`Äóx|ex£ëxHeµ`ÃóxHb™`é?})ƒãxù?KÿýA,#@‚L="¥é)uÀ\8é}<,Š@@A\‘\8‰
9)`8b‡8| N,Hb‘`0cÿÿ|cxc¤8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```}
CxKÿÿ¤€```|¦ûÁÿðûáÿø|~xûaÿØûÿàû¡ÿèøø!ÿaècHa¹`|xè~Ha©`>|cú8cƒH@A€KÿûÝ?â¥;ÿuÈ9@;€ÿÿé?‘Ié?9Iù_9@h™I`Bé?9Iù_9@±I`Bé?9Iù_9^}@T,‘I`Bé?9Iù_“‰`Bë¿è~9=;½ù?H`ý`|`ï,ë¿ë~;½cÛxû¿H`Ý`dÛx|ex£ëxHcÙ`è~H`½`ë|}xè~};êù?H`¡`|{ï,ë¿ë~;½cÛxû¿H``dÛx|ex£ëxHc}`è~H`a`é_8! |ixÃóx}
JùŠI.é?9)ù?èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦KÿúÔ8! 8`ÿüèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûáÿø|Ÿ#xøø!ÿqøapKÿú	="¥9)uÈ9èap8!éI‘
éI9
ù	9x™
`BéI9
ù	9±
`BéI9
ù	àE,`BéI9JùIèëáÿø|¦Kÿùü€```|¦û¡ÿèë¦úÿ ú¡ÿ¨úÁÿ°úáÿ¸/½ûÿÀû!ÿÈûAÿÐûaÿØøûÿàûÁÿðûáÿøø!ÿ1Až|¾+x|—#x|yx|Ü3xKÿù?¥;uÈ9@`¿ëx;`;B‡@é8‘Ié89	ù9n™	`Bé89	ù9±	`Bé89	ù~àE,`Bé89	ùÀE,`Bé89	ù±I`Bé89)ù8``‰?/©Ažp+‰/þûx@ž,``>+‰/Ažÿø/©ßóx:à: Až0ßóxH``Až?*‰//©@–ÿð~¾øPz· ~å»xÄóxCÓxH]ù`/£Ažÿ|èø="¥é)u¸Y:Û
~Ô´})8P9)})º9	‰P@A¬Š@@Aœ¤~ ?,~å»xÄóx~›£xé89)}#Kxù8H`M`é8/–~©ªú¸@žÿ=B¥éJu¸9 ûü#Ëx±*Kÿ÷É/£Až˜8!Ðèêÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿøN€ ‹þÿÿkÿ/ÿ4WÿÙ~ÿðP/»@žÀ£ëxH\`/£@žÈ9 =B¥éJu¸ûü#Ëx±*Kÿ÷5/£@žÿp="¥é)uÀ9)}@N,ŠØAž„9*ÿÿ/‰ÿÿ}*´AžH‰=+‰/@ž`=+‰/Ažÿø/©AžÿЍ=*‰//©@–ÿð9*ÿÿ/‰ÿÿ}*´@žÿÀû¼ˆ}|c4TcÙ~hcKÿþìWiÆ>WhD.})CxU)>KÿÿLë¼KÿÿÔ8`ÿöKÿþÈ8`ÿ÷KÿþÀ€```|¦ûÁÿðûáÿø|ž#xû¡ÿè|xøø!ÿqë£KÿõÍ9@="¥9)uÈsÄ_‘_£ëxé	‘HéI9
ù	9p™
`BéI9
ù	9±
`BéI9
ù	}ü,‘
`BéI9
ù	˜Š`BéI9JùIKÿõ±,#@‚="¥é)uÀ9)} L,‘?8!èë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûAÿÐûaÿØ|š#xûÿàûÁÿð|¼+x|~xûáÿøû¡ÿè|Û3xøø!ÿaë£Kÿô¹ƒý;ÿÿõŸà@@Ÿãx="¥9)uÈ9{g"£ëxéI‘
éI9
ù	9t™
`BéI9
ù	9±
`BéI9
ù	Àô,“Ê`BéI9
}
Cxù	9`U,|èU,éI9
9JàE,ùIKÿô},#@‚4<‚¥è„uÀ9DÀT,Ÿð@{Å AœH8„CÓxH\`ô8! èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8`ÿõKÿÿÌ€```|¦ûáÿøûÁÿð|xøø!ÿëÃKÿóe="¥9)uÈ9@ù_™_Ãóxé	‘HéI9
ù	9|™
éI9
ù	9±
éI9
ù	|àü,ê`BéI9JùIKÿóe,#@‚0="¥é)uÀ8à8É*}4,}@4,yÆ}JCxù_‰)™?8!€èëÁÿðëáÿø|¦N€ €``|¦ûÁÿðûáÿø?Â¥;ÞuÐøø!ÿëþ/¿AžLé?8 €8€ãûxù>HZÅ`9 ù?8!€ãûxèëÁÿðëáÿø|¦N€ ``8`KÿŽ`,#A‚D9 |ix}	¦9@H``Ažù)ÿ€ùI9)€/©€Bÿìø~|xKÿÿhûþKÿÿ„€``,#="¥9)uÐéI@‚H,``}*Kxé*/©@žÿôøjù#N€ `/ª@žÿàN€ ``|¦|iyøø!ÿ‘AÂ`é)/©AžTé)/©AžHé)0/©Až<øA(éIéi}I¦èIN€!èA(8!pè|¦N€ `````8‚‡H8b‡˜He‘`8`KÿÿÈ€`|iyM‚ é)/©Mž é)/©Mž é)/©Mž é)@/©Mž |¦øø!ÿ‘øA(éIéi}I¦èIN€!èA(8!pè|¦N€ €`|iyA‚|é)/©Ažpé)/©Aždé)/©AžXé)H9@/©AžL|¦øø!ÿ‘øA(éIéi}I¦èIN€!èA(8!pè|¦N€ ```9@}CSxN€ €``|¦ûáÿø|yøø!ÿA‚d="¥9)uØéI/ª@žH4}*Kxé*P/©@žÿôûêP8!€èëáÿø|¦N€ ``ûé8!€èëáÿø|¦N€ `8b‡¨HcÑ`Kÿÿ€``|¦,#="¥9)uØøø!ÿ‘é)A‚ˆ/©Až4éIXª@@žH8`IXª@Až(é)P/©@žÿì8!pè|¦N€ ``ù#é)øA(éIéi}I¦èIN€!èA(8!pè|¦N€ `8b‡°Hc`Kÿÿ¤€```|¦|iyøø!ÿ‘A‚@é)é)/©Až øA(éIéi}I¦èIN€!èA(8!pè|¦N€ `8b‡°Hb‰`Kÿÿà€|iyA‚œ|¦øø!ÿ‘é)/©AžTé)/©AžHé)/©Až<é)(/©Až0øA(éIéi}I¦èIN€!èA(8!pè|¦N€ ``8‚‡X8b‡˜Hañ`8!p8`è|¦N€ `8`N€ €```,#A‚lèã9@/§Až`|¦8 øø!ÿ¡#èg 8p±Ar±Av}	Kx9™p9™q9t} G,Kÿþå8!€è|¦N€ 9@}CSxN€ €``,#A‚\|¦9@ÿ€|©+x|…#xøø!ÿ™Ap9@èc 8p™Aq9@±At9Av} W,9 ±!rKÿþe8!€è|¦N€ 8`N€ €```,#A‚\|¦9@ÿ€|©+x|…#xøø!ÿ™Ap9@èc 8p™Aq9@±At9Av} W,9 ±!rKÿýå8!€è|¦N€ 8`N€ €```|iyM‚ èi Kÿý¤`|iyA‚˜/¤Až„èi(/£Až„|¦|ë;x|Ê3x|¤+xøø!ÿ‘é)/©Ažté)/©Ažhé)8/©Až\øA(}ESx}f[x}CxéIéi}I¦èIN€!èA(8!pè|¦N€ èi0/£@žÿ„8`N€ `````8‚‡h8b‡˜H_A`8!p8`è|¦N€ €``|¦‰$ûáÿø|xy) +‰øø!ÿAž0+‰Ažx8!€8`èëáÿø|¦N€ ```‰$U)Éþ/‰Až$Kÿø¡8!€ø(8`èëáÿø|¦N€ Kÿø8!€ø08`èëáÿø|¦N€ Kÿøa8!€ø8`èëáÿø|¦N€ €`|¦|iyûáÿøøø!ÿA‚\)d=@;àaJ‰PAž$8!€ãûxèëáÿø|¦N€ ``HJ`8!€ãûxèëáÿø|¦N€ 8!€;àãûxèëáÿø|¦N€ €``|¦|iyûáÿøøø!ÿA‚\)d=@;àaJ‰PAž$8!€ãûxèëáÿø|¦N€ ``HKQ`8!€ãûxèëáÿø|¦N€ 8!€;àãûxèëáÿø|¦N€ €``,#A‚¼‰#e+‰Až8`N€ ``/ˆAžÿì|¦û¡ÿèûÁÿð; ûáÿø|~x;ã8øø!ÿq‰?y) /‰AžD9=;ÿˆH@}=´Aÿà8!8`èë¡ÿèëÁÿðëáÿø|¦N€ ```äûx8À8 ÃóxKÿýA`Kÿÿ¨`8`N€ €```,#A‚l‰#e+‰Až8`N€ `|¦ûáÿø|xøø!ÿèc(/£AžKÿöqè0/£AžKÿöa8!€8`èëáÿø|¦N€ `8`N€ €```,#A‚\|¦|ix9@9)x9!8 øø!ÿ±Av±Ar8p}@N,èc ™p9ÿÿ™q±AtKÿøÕ8!€è|¦N€ 8`N€ €```|¦ûáÿø|xøø!ÿèc(KÿùIè0KÿùA8`Kÿ€	`8!€èëáÿø|¦N€ €|¦ûÁÿð;Àû¡ÿèûáÿøû!ÿÈ9 8ÀûAÿÐûaÿØ8 |#xûÿà|xøø!ÿ!ƒt“Ãl8“±!—›Á•›Á–KÿôY8 8pø ãûxKÿù5/£Až˜é? ‰Aw±I?h/‰AžX9=›Á‚³Á†8 ³Áˆëßè 8‚‘?t9 ™!ƒ9>.} N,±!„Kÿ÷‰,#A‚@é>(9Iù^(‘?l|¬8`dKÿ~õ`8 8pãûxKÿø¡/£@ž88`8!àèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8 	8‚ãûxKÿøÕ/£Ažÿ¸9!„€N,+œ	Ažÿ¨ƒãxKÿ€`|zyA‚4…ãxDÓxãûxKÿø™/£Ažà9 9‰A‡è 8 8‹™‹±!9	±!‘9!™Œ}@O,Kÿö‰/£Až |¬8`d;Ú	Kÿ~`9<ÿ÷; U=>H<``@ž ?`‰Y+‰±_x@p9)‘?`};èPÞÚq=ÿÿA‚¤‰>‹~.‰/‰@–ÿÀ‰^‰>‰ÙóxUJ€U)@.}IKx})Cx‘?dKÿÿ¸`„ãxCÓxKÿy`KÿþŒy#$Äóx})P8 |J8c8HL%`?`Kÿÿp``¥ëx8‚‡€8b‡ÀHX`8`KÿþDCÓx„ãxKÿ`8`Kÿþ,€```````N€ ûáÿø|yûÁÿðA‚Äé?|ž#x8`<8€é)é) è©8¥<D"/£9 ÿÿy) Ažp<‚¥ „uà„HAž€é?8`<8€é)é) è©8¥<D"/£8àÿÿxç Až`9?ÿôé8_Lè | L,9?ÿø9Jÿÿ|€L,yJ |¨(P|©&t|£*8ÉT„:}&SÒ} P<‚¥}B°äuà}IQÒ}*0Py+'y) |ãZ§@@Ažè¡_èß(é@}*IÖy) }FJ|ÆL,})B/¦Až,99Jÿÿ}	¦8žÿÿ```
Bÿø9@ð9y) }CY.9@‘G} E,¡_9Jÿÿ}*J9G} U,é_ é?8|ê8P|çJTé@>PéÀPéÄ.‘%|¬‘?ÿô8`ëÁÿðëáÿøN€ ```Tˆ@>PˆÀPˆÄ.<‚¥ „uàU	>„H@žþˆëÁÿðëáÿø8`N€ Tˆ@>PˆÀPˆÄ.U>Kÿþ”,#M‚ é#/©Mž |¦ûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿaé)ëÉ é> /©Ažløi#|x/‰Ažh9 ûþ 8  8€ãûxù?ù?HHÙ`8! èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```ø~Kÿÿ˜``뿁=dm*/ŠAž=@	‰P@žÿ€?ÿðëžë0e)@‘?ÿð|¬9 €¿HèŸ(è@‘?ÿø‘?ÿô‘?ÿüKÿ~`€¿LèŸ è8x¥&äKÿ~…`€ŸLè x„&äKÿ{‘`]dmI/‰Až= 	ŠH@žþü;œ`å,KÿþðWi@>SiÀSiÄ.‘<‘< ‘<@‘<`KÿþЀ`|¦,#úÿ ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèøûÁÿðûáÿøø!ÿ1A‚é#|Ü3x|»+x|ž#x|}xë) ëù/¿AžÜé?/©ù9Až8  8€ãûxHG-`9 û¿9~ù?‰>y) y* +‰‘_=h‘?} ^,±?U:>‰y ±‰>y)$U)>‘?AžÀ+ŠAžH8!Ðãûxèêÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿøN€ €ßh]l¡? ¿|Æ4yJ`a@U)^TÆÙ~|èSx|ÆÐ}
KxxÆ$T©=p}IKx8Æ})3x9_ÿð} U,Kÿÿl```ù9 Kÿþä``=dm'/‡Až<à	‰8@žÿ,{X =l€ýhU80ë9~ÜÖy*``éP}IKx}(CxWI^}Kx9?ÿð}M,êÿ0:–~•´zµ&ä~£«xKÿx©`|~yA‚~¤«x8 Kÿ{1`8€z… (|uxÃóxHEy`…ãx8€cÛxHEe`8 „ãxcÛxKÿzñ`/”9 ûß ú¿8’ŸLû(“ŸHø@@l:Öÿÿ8ØÿÿzÖ xÆ 8¶9>x¥&ä8€ð|¾*xh 9iÿô}^HP|è2}],}Jª9	ÿø‰ÿð|cÒ}@E,9Iÿü9)¥H@|àU,@žÿÈzÉ&äÞJ9@}5J9ÿø9ÿô‘^~ ],} E,‘_ÿü]dmI/‰AžH= 	ŠHAž_Kÿý°``8`Kÿwm`/£|zxøy°Ažè8 8€Kÿyí``_Óx:Ú`:à|xxøy¸:¢ˆH(`¿°@}:øP})Â9_pù?@Až<ù_;ÿ`{è!úÿA‚ÿØ~£«xHPA`¿°@}:øP})Â9_pù?@@žÿÌé9/©Až é9 9ZùIëù;ZpûY Kÿüd;úûùKÿÿì``8‚‡Ø8bˆPHOÝ`_Kÿü´```;àKÿü¨;9~àÍ,?ÿð_U)H~U)¸>‘?ÿðKÿü€Vé@>RéÀRéÄ.‘9‘9 ‘9@‘9`KÿÿÌ€```,#A‚Ü|¦ûáÿøøø!ÿëã è¿8¥|¬<ÀÃ8`@xÆ 8€D"8`KÿtA`è¿8¥|¬8`@8€8ÀD"蟰/¤Až$è¸8 Kÿxù`è°8€Kÿv	`èŸ/¤Až$è¨8 hKÿxÍ`è8€hKÿuÝ`ãûx8€ÀKÿvÝ`8!€èëáÿø|¦N€ é# à€```|¦úaÿ˜úÿ `}€&ú¡ÿ¨úÁÿ°|Ö3x>‚úáÿ¸ûÿÀ|ø;x`û!ÿÈûAÿÐÃx;@ûaÿØûÿà|»+x||xû¡ÿèûÁÿð|#x:àøúAÿ:bˆ{{ ûáÿø‘:”šp:¢ˆ¨ø!ÿ!Kÿr‰`8cˆx~ ``|¬è½8`<8€8¥D"/£@žpTŠ@>PŠÀPŠÄ.}DSxy_ x‰ÿã``@ÂLKÿr-`ƒð@AÀ|¬è½8`<8€8¥D"TŠ@>/£PŠÀPŠÄ.}DSxy_ x‰ÿãAžÿ¸9<„|€L,/¤Ažÿh’ü„|¬.9@‘$~V P~I&t¸HAÀ`~c›xHLý`è½8¥|¬8`@8€<ÀD"|¬è½8`<8€8¥D"A‘ÿCÓxH ``äûx8bˆhHL¥`8`8!à聁êAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØ|¦ëÿàë¡ÿèëÁÿðëáÿø} N€ ~RÚAÂÿD;9ÿÿ|¬2U?@>Q?ÀQ?Ä.Wÿ'>{ê!@‚ha)9R|€T,‘2’ò|¬.¤~V P~I&t.9~RÚ©ÀA–þøA’þô@œþäAÂþà;9ÿÿ|¬2U?@>Q?ÀQ?Ä.Wÿ'>{ê!A‚ÿ yJ$~E“x~£«x|”P*HK©`+Ÿ2ÿÐ@ÿxú´Kÿÿp€```|¦ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿA#/‰@ž|éfp})”+‰A\/¤|ž#xAž|x|½+x8€8 ÃóxƒŸøÁpøáxH>­`èáx=ðèÁp3œÿÿy }JQxé!yJ$}JBA‚èUC@>;€QCÀ9`QCÄ.Êóxxc HL```;jÿô}(HPy)!|ÆB|€Ý,8Šÿü;œ|à%,T¤@>jÿðP¤ÀP¤Ä.x… ŠÿøA‚l*‰9J/¦xÄ |¾PP}(Kx@•9|è"|½*8çÿÿy @žÿ”}(HPT¤@>Êÿô‘jÿüy)!P¤ÀjÿðP¤Ä.x… |ÆBŠÿø;œ@‚ÿœW«@>S«ÀS«Ä.é?€ß 	h€‰l|Æ4¡?Tj^TÆÙ~a@xˆ`€Ÿÿø|èCx|ÆÐ}
SxxÆ$U)=p8Æ}IKx9ÿð})3xTŠŽ}J[x} E,9 ¿ÿô‘_ÿø‘?ÿü|¬?ÿðé_4U)H~U)¸>‘?ÿðé(ë) ëY|¬UF@>;(QFÀ8`@QFÄ.8€xÆ ÃxD"|¬|¬8`@8€8º<ÀD"KÿmÅ`8cˆx{ H?ÿø_ÿôU)0¾U)Ð>‰PAžKÿm™`ƒØ@AœÿÜ|¬èyÅóx‡ãx¦ëx8™Kÿúa|~x|¬?ÿðe)@‘?ÿð|¬|¬8`@8€Ãx8ÀD"|¬8`@8€8º,8ÀD"9_ÿø} T,y;á@‚è8!ÀÃþp|~PèëÿÀë!ÿÈëAÿÐTcþëaÿØëÿàë¡ÿèëÁÿð|c´ëáÿø|¦N€ ``8bˆÀHH`8`8!ÀèëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ````|ä;x8bˆàHGÅ`8!À8`èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```;ÿø8b‰(HGu`9?ÿü8Ÿÿð| Ü,9_ÿô`}$,|àL,`8b‰8|ÀT,8‚‡ðHGA`?ÿøU)8~U)È>‘?ÿø|¬/žÿü@žþ¼èKÿì	`8`Kÿÿ``8‚‡ð8b‰HFù`8`KÿþàW«@>;€S«ÀS«Ä.ye Kÿüä€`}€&|¦úAÿúáÿ¸|²+xûÿÀû!ÿÈ8¤ûaÿØûÿà|œ#xû¡ÿèûáÿø|x8`0‘úÿ€øú!ÿˆúaÿ˜úÿ ú¡ÿ¨úÁÿ°ûAÿÐûÁÿðø!ÿ‹Ä~ .,Kÿm`8 8€0|}xKÿo`8 08€Þtz» |yx£ëxH9Í`8 8€ƒãx{7 KÿoU`97|xyA‚ä{
 8Ý9
8ý}@5,.;9]}=,} U,9 ò‘=@’Ô/ž9=:€:`Aœ9ó9@‘	W(@>S(À8¿ÿð‘I‘IS(Ä.‘I¡?€ÿÿøU&^TçŽ|èCxé?)l‘ÿø‘_ÿü‘_ÿôy)`a)@})3x} -,|¬?ÿðé_4U)H~U)¸>‘?ÿðé(ëI ëz|¬UF@>:Û QFÀ8`@QFÄ.8€xÆ ~ųxD"|¬|¬8`@8€8»<ÀD"Kÿi‘`8cˆx~ H```‰PAž”Kÿii`?ÿø_ÿôƒð@U)0¾U)Ð>Aœÿ܉PAÞl``8‚ˆ8b‰pHD```8b‰ˆ;ÜÿÿHDi`::"‰˜``Œž~#‹xHDI`°ð@@žÿì`8b“ HD1`èz~‡£x&Ëx¥ëx8šKÿõµ|~x|¬?ÿðe)@‘?ÿð|¬|¬8`@8€~ųx8ÀD"|¬8`@8€8»$8ÀD"8 „ãxÃxKÿmÍ`A’~¥«x~D“x~c›xKÿmµ`8 0¤ëx~ã»xKÿm¡`£ëx8€0Kÿj±`8!ðÃþp|~P聁êÿ€ê!ÿˆTcþêAÿêaÿ˜êÿ ê¡ÿ¨|c´êÁÿ°êáÿ¸ëÿÀë!ÿÈ|¦ëAÿÐëaÿØëÿàë¡ÿè} ëÁÿðëáÿøN€ 9].;““} U,9 ò‘=A’ý48 ~¤«x~C“xKÿl5`Èðø/ž}þv9= |syy$9ó8÷ @‚,’}’}9]‘:€|àU,@œüô9óKÿüð`zf 8½9[ÿÿ}J2|À-,8Ý}@5,KÿÿÄ€`|¦û¡ÿèûáÿø|xúÁÿ°úáÿ¸`ûÿÀû!ÿÈ8b‰ ûAÿÐûaÿØûÿàûÁÿðøø!ÿ1HB!`8`ÀKÿiÕ`|}yA‚$9 û¿ 8€8 Àù?(H5¡`9 ûý8`hù=ù= é?ù=Kÿh}`/£|dxø}Ažxi /‰Ažl`8b‰àHA¡`è}8€hKÿhÁ`8€À£ëxKÿiÁ`8!ÐèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8 8€hKÿj‰`ëÝø}¨|¬8`@8€8¾8ÀD"8`dKÿf-`|¬8Àÿÿ8`@8€8¾xÆ D"|¬;Þ8`@8€Åóx<ÀD"|¬;à`8`<8€ÅóxD"TŠ@>/£PŠÀ9?ÿÿPŠÄ.y? }DSx.¿x‰á8`@žA‚$A–Kÿeý`Kÿÿ´`8bŠH@i`é=8À8 ëý8p8}(ù=89 ™!s9 ±!tKÿÚ%`/£|~xø}@AÞ„è}8 8€ëž0H3½`8 8€8~ÿðH3©`9@ W‡@>}I¦= @S‡ÀS‡Ä.‘>ÿð9 xç H``````éy*d9)y) |èQ.Bÿì=¬|¬U&@>8`@Q&À8€Q&Ä.8¿xÆ D"|¬8`@8€8¿ 8ÀD"|¬8`@8€8¿(8ÀD";ß8`<8€ÅóxD"/£<À·xÆ @ž(T‰@>P‰ÀP‰Ä.U)¬a)·U&@>Q&ÀQ&Ä.xÆ |¬8`@Åóx8€D"8`dKÿd`|¬<Àß.8`@`Æx'8€8¿4xÆ D"|¬8`@8€8¿@<À/*D";ßH8`<8€ÅóxD"/£<Àÿö`ÆÿÿxÆ Ažl|¬8`@8€ÅóxD"|¬8`@8€8¿L8ÀD"|¬8`dKÿce`ë]8`<8€8ºHD"/£; ÿAžð|¬8`@8€8ºP8ÀD"8`d;ZTKÿc`/¹;à;`Ažüp``;Š`:âŠxHØ|¬8`@8€EÓx<ÀD"|¬8`dgÿ{ÿ KÿbÉ`8`<8€EÓxD"/£@žìT‰@>P‰ÀP‰Ä.}$KxU<œxŠgãU$Z{œ xž @ÂÌ/¼Ažgÿ{ÿ /¾Ažgÿ{ÿ {éäy?!A‚(|¬U&@>8`@Q&À8€Q&Ä.EÓxxÆ D"8›;Z„È@x› Ažûˆ8`<8€EÓxD"/£@žÿTŠ@>PŠÀPŠÄ.}DSxx‰‡ãAâÿ0xŠá@ÂþøÃxH<Á`8`<8€EÓxD"/£Ažÿ?À?€KÿÕI`é=dÛxgÿ{ÿ |vxù#Kÿá¹`/£Až~óxHÕ`Kÿþü``dÛx~ã»xH<I`Kÿþà```T‰@>P‰ÀP‰Ä.U9>Kÿþ```TŠ@>9 öÿPŠÀPŠÄ.})P8a)U&@>Q&ÀQ&Ä.xÆ Kÿýp`8b‰¸H;Ý`8!ÐèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8bŠ0H;•`KÿýP€
```N€ |¦<b8cšðøø!ÿ‘KÿÖý`8!pè|¦N€ €``N€ ,#M‚ é#/©Mž |¦øø!ÿ‘é)é) éI0/ªAž@øj9@øi08  8€ùCùCH.q`8!pè|¦N€ ``9@øi(øi08  8€ùCùCH.5`8!pè|¦N€ €|¦,#ûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿaA‚Té#|ž#x|}xë‰ ëü(/¿Až é?/©ù<(Až€8  8€ãûxH-±`9 û¿ù?‰>y) ‘?=h‘?¡>±?‰>U)Éþ‘?‰>y) ±?8! ãûxèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ù<0Kÿÿ€``8`Kÿ`-`/£|{xø|XAž€8 8€Kÿb­`9@ iÛx}I¦9ø|`H```9IÀ9)€ùIÿÈ}[HPù	H}JùI`Bÿäé<(/©Až(é<09[@ùIëü(;{Àû|0KÿþÐ;àKÿÿ,;û@ûü(Kÿÿä€``|¦û¡ÿèûáÿø|xûÿÀû!ÿÈ`ûAÿÐûaÿØ8b‹ÈûÿàûÁÿðøø!ÿQH8‰`8`hKÿ`=`|}yA‚Ø8 h8€H,`9 û¿ 8`<8€ù?(ûýè¿ø½ëÿD"/£9 ÿ@žT‰>}?Jù=Kÿ\Í`8€è½8cúx 8`<D"/£= Ïÿa)ÿÿy& Ažè½|¬8`@8€D"HKÿ\`ƒø@Aœÿô8`<8€è½D"/£@žTxœ W‰@>S‰ÀS‰Ä.y*ÿã@Â<8`Kÿ^=`|zyA¬8 8€Kÿ`Å`|yx8`@Kÿ^`|yAÂ8 8€@Kÿ``8 @8€|xxãûxH*å`= 9}	¦‘?‘?‘?‘?= @‘?c	U*@>Q*ÀQ*Ä.9:ÿüyJ •IBÿüé=8©|¬W&@>8`@S&À8€S&Ä.xÆ D"8`@Kÿ]m`|~yA¤8 8€@Kÿ_õ`8 @8€|{xÃóxH*=`= cj‘>}@õ,=@€‘>= @‘^‘>è½8¥|¬Wf@>8`@SfÀ8€SfÄ.xÆ D"ûÝû}@ûý ûHû]8û=Pè½|¬g†!8`@8€xÆ D"è½8¥@|¬8`@8€<ÀD"è½8`<8€8¥D"/£@ž0T‰@>P‰ÀP‰Ä.}$KxpœA‚¤`;à;@;"Œ¸;`þûH$```@Â\;ÿŸà@{ÿ @œlè½;ß8`<{Éd8€|¥J8¥D"TŠ@>/£PŠÀ{ÉdPŠÄ.8`<}DSxxˆá8€Ažÿ¨è½|¥J8¥D"/£T‰@>P‰À<ÀûÿP‰Ä.`Æÿÿ{ØddH8xÆ @ž`„T†@>P†ÀP†Ä.xÆ è½|¥Â8¥|¬8`@8€D"8`KÿYé`è½8`<8€|¥Â8¥D"/£<Àÿþ`Æÿÿ{ÞdxÆ @žx†xBxƈ è½Åò8¾|¬8`@8€D"8`KÿY‰`KÿÍ`é=äûx“Ch|~xù#Kÿم`äûx/£ÃóxAž€;ÿH
™`Ÿà@{ÿ Aœþœ8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ Tˆ@>9 ÿÍPˆÀPˆÄ.}*@8aJUI@>QIÀQIÄ.y& KÿûÔ``#ËxH3­`Kÿþ;€Kÿýè`8b‹àH3‘`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8bŒH3Q`Kÿý``8bŒPH3=`DÓx#Ëx8 Kÿ]9`8€CÓxKÿZI`Kÿý(`8bŒˆH3`äûxÃx8 @Kÿ]`8€@ãûxKÿZ`Kÿÿ¤`8bŒ H2Í`KÿüÜ€`,#A‚¼|¦=B¥ûÁÿðûáÿø|~x*uä9)øø!ÿ/‰‘*uä@<``8‚‹8bŒèH2i`8!€èëÁÿðëáÿø|¦N€ ``ëã /¿Až8`<8€è¿D"/£8ÀÿÿxÆ Ažè¿|¬8`@8€D"è¿8¥|¬8`@8€8ÀD"èŸX/¤Až$è`8 Kÿ[á`èX8€KÿXñ`èŸ /¤Až$èH8 @Kÿ[µ`è 8€@KÿXÅ`èŸ/¤Až$è@8 @Kÿ[‰`è8€@KÿX™`èŸ8/¤Až$èP8 Kÿ[]`è88€KÿXm`ãûx8€hKÿYm`9 8!€ù> èëÁÿðëáÿø|¦N€ `d„þÿ`†ÿÿxÆ Kÿþàé# à€```|¦ûÁÿðûáÿø|~xøø!ÿ|¬8`<8€è¾D"/£@žðd„@x† è¾|¬8`@8€D"|¬KÿU-`8cˆx KÿU`8€ƒø@8`<@œ„`è¾8¥D"T‰@>/£P‰ÀP‰Ä.}$Kxx‰ßãAž<è¾8¥|¬8`@8€<À D"8!€8`èëÁÿðëáÿø|¦N€ @ÂÿÈKÿT`8€ƒø@8`<Aœÿˆ8!€8`èëÁÿðëáÿø|¦N€ ``8ÀÿÿxÆ Kÿÿ€``|¦ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèûÁÿðøûáÿøø!ÿ1#/‰@ž é#|x8``|›#x|¸+xé)ë‰ KÿUá`|}yA‚˜8 8€`KÿXi`8 `8€|yx£ëxH"±`8 8€cÛxKÿX=`99 9]8à|é¦} í,= |zx9‘== €a)‘=|`U,9#y)ä©@@œ9J} U,9)Bÿì9‹Û~àF,Þtzõ!@‚l9] :à:ÀÉðø=U)Mî9Je)€‘
ÿø‘
ÿüa)€} U,|¬9ÿÐ8¿ÿÀ E,_¡?¡UJ`&U)€U@.èü@èß`ç|à-,€æl}J;x8ÿÿÄ}IKx})Cx} =,|¬é? é\a)} U,|¬KÿR‘`¿ëx> 8cˆx~ H(`|¬KÿRm`ƒð@A4?‰¨AžD9} D,y*Ïã@‚ÿÔKÿRA`;ÿ ƒð@@ÿÔ`;à8b@H-q`é<@é\a)} U,|¬8|Kÿü/£AždÛxCÓx8 KÿWI`~å»xÃx~óxKÿW5`8 `¤ëx{# KÿW!`£ëx8€`KÿT1`8!Ðãûxèê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8bH,©`8`8!Ðèê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ é<@é\;àa)} U,|¬8|Kÿûu/£@žþø``8‚‹ 8bhH,)`;àKÿþØ``8 ~ä»xÃxKÿUU`9@8ý WÉMî8 |©¦}=,e)€=a*€V©€|vx}IKx‘$9],9(} E,|`U,9#}y)ä©@@œ9J} U,9)Bÿì9]@Kÿý$`8b(H+…`8`KÿþÜ€``|¦úÿ ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèøûÁÿðûáÿøø!ÿ1#/‰@žl= |þ;xa)@‡HApƒcé#:… |ux|Ÿ#x|¹+x|Ö3xz” {4é);¤€|—#x?@W{Ù~k{ë‰ W{@.g{€c{€{x 8  8€~ã»xHY`98à|é¦96~ÀE,{Ê y)ä}J²ªH@l9} E,9)BÿìªH@T})PP8÷})´ÉðP/©WʀÞ´}JÃx}@=,AÞ<~€½,“W:÷ :” ·è@~Öòz” Až,}>KxKÿÿ`Wހ9ÛÛx`E,= ‘7‘7`|¬9ÿÐ8µÿÀ E,U¡5¡UJ`&U)€U@.èü@èÕ`ç|à-,€æl}J;x8õÿÄ}IKx})Cx} =,|¬é5 é\a)} U,|¬?`KÿN5`8cˆx~ H9} D,y*ÏãA‚KÿN`ƒð@Aœÿä|¬?‰ØAž 8¿} ,,y'Ïã@‚Ð;ÿ ¿è@@žÿ¤;Àé<@é\a)} U,|¬8|Kÿø9|yA‚€ßóx8!Ðãûxèêÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿøN€ ``;à8b€H(¥`Kÿÿ¤`;à8b H(`KÿÿŒ``8‚‹°8bhH(q`Kÿÿp`;À8bÈH(Y`Kÿÿ0€N€ |¦<b8c›Pøø!ÿ‘KÿÃÍ`8!pè|¦N€ €``|¦ûáÿøøø!ÿaCt#léøap‘Ax‘!|=@#daJ‰PéH‘A€éH‘A„Až¨m*/ŠAž¼y*†"+ŠAžÐ=@	‰PAž$8! 8`èëáÿø|¦N€ ```8 8p;⎀8`9 ‘!ˆKþÿE`ãûxH)`åûx|dx8`Kþÿ%`8! 8`èëáÿø|¦N€ ``8p;⎠8 8`9 Kÿÿ ``8p;âŽ@8 8`9 Kÿÿ€``8p;âŽ`8 8`9 Kÿÿ`€``|¦ûáÿøøø!ÿ€ƒdx‰†"+‰AžD+‰	Ažl+‰Ažd`8bŽÐH&Y`8!€èëáÿø|¦N€ ```p‰P+‰P@žH|xKÿʑ`/£Ažd8`dKÿK-`ãûx8!€èëáÿø|¦Kÿþ````8bŽ˜H%Ù`8!€èëáÿø|¦N€ `````8‚Ž8bŽ¸H%¡`KÿÿH€``=b¥ékuèùÁÿpùáÿxúÿ€ú!ÿˆúAÿ/«úaÿ˜úÿ ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèûÁÿðûáÿøAžl=‚¥éŒuð/¬Až\‰#q)"/‰Až=B¥9Jw‰*U)ð~U)>™*=B¥<¢¥ˆ¥uø8ã9Juè9#|è;x8Š}FSx8;à[:`A:€B: D:ÀC:à6;À~; O;F; 3;@5;`2;€1`Ž:Pÿÿ+’cAD:*~Q P~I¦ŽQ’€Až,Bÿô:PÿÎVQ>+‘!A¨>"ÿþ:1-zR¨~Q’ª~2Š~)¦N€ ´ˆˆˆˆˆˆ´Ìdü”,ä \ÔŒ	Dˆ
ˆ

¬ ´H¸
L
¼,œœ>B¥:RwŠRzQÿã@‚tŠC/²AžtrO"@‚ rOA‚Ì`:B‘Ð~€®/°Až0Š*~2´9ò(Až:1~F’š&š ``©@@@žþ¬}'HP9J})¦```'*BÿøéÁÿpéáÿxêÿ€ê!ÿˆêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿøN€ ```9b“`9‚’ ="¥=â¥ùiuèùuðKÿýˆ>"¥:1wŠQjRšQKÿÿH>"¥:1wŠQjRšQKÿÿ0ŠJ~Q´:(Ažÿ:~&ŠV>~´˜ 9ÏšŽ(AÞþø:2}æzV1>~0´›ï 9К&Ž(AÞþÔ9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞþ°:R~&ŠšF:@PšQ Kÿþ˜ŠJ~Q´:(Ažþ„:~&ŠV>~´˜ 9ÏšŽ(AÞþ`:2}æzV1>~0´›ï 9К&Ž(AÞþ<9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞþ:R~&ŠšF:@QšQ KÿþŠJ~Q´:(Ažýì:~&ŠV>~´˜ 9ÏšŽ(AÞýÈ:2}æzV1>~0´›ï 9К&Ž(AÞý¤9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞý€:R~&ŠšF:@RšQ KÿýhŠJ~Q´:(AžýT:~&ŠV>~´˜ 9ÏšŽ(AÞý0:2}æzV1>~0´›ï 9К&Ž(AÞý9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞüè:R~&Š9àSšF™ñ KÿüЊJ~Q´:(Ažü¼9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞü˜9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞüt9ò~&ŠUï>}ð´›‘ 9ЙæŽ(AÞüP9ò~‚Uï>}ñ´›P 9Ñ™æŽ(AÞü,:R~&ŠšF›Ñ KÿüŠJ~Q´:(Ažü9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞûà9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞû¼9ò~&ŠUï>}ð´›‘ 9ЙæŽ(AÞû˜9ò~‚Uï>}ñ´9Ñ™æ9à7Ž(™ð AÞûp:R~&ŠšF›Ñ Kÿû\ŠJ~Q´:(AžûH9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞû$9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞû9ò~&ŠUï>}ð´›‘ 9ЙæŽ(AÞúÜ9ò~‚Uï>}ñ´9Ñ™æ9à8Ž(™ð AÞú´:R~&ŠšF›Ñ Kÿú ŠJ~Q´:(AžúŒ9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞúh9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞúD9ò~&ŠUï>}ð´›‘ 9ЙæŽ(AÞú 9ò~‚Uï>}ñ´9Ñ™æ9à9Ž(™ð AÞùø:R~&ŠšF›Ñ KÿùäŠJ~Q´:(AžùÐ9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞù¬9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞùˆ9ò~&ŠUï>}ð´›q 9ЙæŽ(AÞùd9ò~‚Uï>}ñ´9Ñ™æ9à0Ž(™ð AÞù<:R~&ŠšF›Ñ Kÿù(ŠJ~Q´:(Ažù9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞøð9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞøÌ9ò~&ŠUï>}ð´›q 9ЙæŽ(AÞø¨9ò~‚Uï>}ñ´› 9Ñ™æŽ(AÞø„:R~&ŠšF›Ñ KÿøpŠJ~Q´:(Ažø\9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞø89ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞø9ò~&ŠUï>}ð´›q 9ЙæŽ(AÞ÷ð9ò~‚Uï>}ñ´›0 9Ñ™æŽ(AÞ÷Ì:R~&ŠšF›Ñ Kÿ÷¸ŠJ~Q´:(Až÷¤9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞ÷€9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞ÷\9ò~&ŠUï>}ð´›q 9ЙæŽ(AÞ÷89ò~‚Uï>}ñ´9Ñ™æ9à4Ž(™ð AÞ÷:R~&ŠšF›Ñ Kÿöü>"¥:1wŠQjRšQKÿöäŠJ~Q´:(AžöÐ:~&ŠV>~´˜ 9ÏšŽ(AÞö¬:2}æzV1>~0´›ï 9К&Ž(AÞöˆ9ò~‚Uï>}ñ´›p 9Ñ™æŽ(AÞöd:R~&ŠšF›Ñ KÿöPŠJ~Q´:(Ažö<9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞö9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞõô:R~&Š9àHšF™ñ Kÿõ܊J~Q´:(AžõÈ:~&ŠV>~´˜ 9ÏšŽ(AÞõ¤:2}æzV1>~0´›ï 9К&Ž(AÞõ€9ò~‚Uï>}ñ´›P 9Ñ™æŽ(AÞõ\:R~&ŠšF›Ñ KÿõHŠJ~Q´:(Ažõ4:~&ŠV>~´˜ 9ÏšŽ(AÞõ:2}æzV1>~0´›ï 9К&Ž(AÞôì9ò~‚Uï>}ñ´›0 9Ñ™æŽ(AÞôÈ:R~&ŠšF›Ñ Kÿô´ŠJ~Q´:(Ažô 9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞô|9ò~‚Uï>}ñ´›° 9Ñ™æŽ(AÞôX:R~&ŠšF› KÿôDŠJ~Q´:(Ažô0:~&ŠV>~´˜ 9ÏšŽ(AÞô:2}æzV1>~0´›ï 9К&Ž(AÞóè9ò~‚Uï>}ñ´šð 9Ñ™æŽ(AÞóÄ:R~&ŠšF›Ñ Kÿó°ŠJ~Q´:(Ažóœ9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞóx9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞóT:R~&ŠšFšÑ Kÿó@ŠJ~Q´:(Ažó,9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞó9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞòä:R~&ŠšFš± KÿòЊJ~Q´:(Ažò¼9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞò˜9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞòt:R~&ŠšFš‘ Kÿò`ŠJ~Q´:(AžòL9ò~&ŠUï>}ð´˜ 9ЙæŽ(AÞò(9ò~‚Uï>}ñ´›ð 9Ñ™æŽ(AÞò:R~&ŠšFšq Kÿñð:Pÿü+’@8~€®/°Ažñ؊*~2´9ò(AžñÄ:1~F’š&š Kÿñ°~€®/°Ažñ¤Š*~2´9ò(Ažñ:1~F’š&š Kÿñ|+’@@žñt`:B’8~€®/°Ažñ`Š*~2´9ò(AžñL:1~F’š&š Kÿñ8``|¦ûáÿø|x8 8€øø!ÿq8apHñ`è8pKÿ¯A`|yA‚8apKÿî8!ãûxèëáÿø|¦N€ €`|¦ûÁÿð|~yûÿàû¡ÿèûáÿøøø!ÿaA‚€9 è~ ;à; !8 ™!q9>x8p³ár›¡p³áv} N,±!tKÿ±)`9 
è~ 8 ›¡p8p³áv™!q9 }±!r9>x} N,±!tKÿ°ñ`8 8€8axHý`9 ÿ¡è~ 8¡x8p™!p9 ™!q9>x} N,±!t9 ±!v9 ±!rKÿ°`/£@ž 8`€Kÿ9©`?‚¥;œw/£ø|Až°^`;þ8; /ŠAž(‰?y) /‰Až<9=;ÿŠH@}=´Aÿà8`8! èëÿàë¡ÿèëÁÿðëáÿø|¦N€ è¼äûx8À€ÃóxKÿ³a`^`Kÿÿ¬8axKÿìÝKÿÿ\`8 8€8axHõ`Kÿÿ@````8‚Žø8bH!`8`Kÿÿt€`|¦ûáÿø|xøø!ÿèc/£AžKÿ¬q`9 ù?="¥9)w8€€èiKÿ8ñ`8!€8`èëáÿø|¦N€ €`/£AžL|¦øø!ÿ‘Kÿý8!p="¥‰)uø<b¥ˆcvè}#x|c4|¦TcÙ~hcN€ ``8`N€ €```/£Až\|¦øø!ÿ‘Kÿü­="¥‰)uø=B¥‰Jv=¥8`9uèŠHAž9I}(J=¥ˆi ™Huø8!pè|¦N€ 8`N€ €```,#A‚l|¦9#|ª+x9$8 øø!ÿ™p9èc 8p™q9±v9r}@G,9At} W,Kÿ­á`8!€è|¦N€ ``8`N€ €```,#A‚\|¦9@ÿ£9$øø!ÿ™Ap9@èc 8p™Aq9@±Ar9At} W,9 ±!vKÿ­Y`8!€è|¦N€ 8`N€ €```|¦ûÁÿð|~yûÿàû¡ÿèûáÿøøø!ÿaA‚8 8€8ax`H
`9 ÿ è~ 8¡x8p;à™!p9 ;‚H™!q9 ±!t9 ±!v9 )±!rKÿ¬©`‰!z/‰@ž$H„y*á@‚¼‰!z9_}_´‰P@h8¡päûxÃóxKÿþÉ/£AžÿØ9Ap} V,y*Çã@‚ÿÀ8 äûxÃóxKÿþ8`dKÿ3É`Kÿ3Q`8cˆx} H0```8¡päûxÃóxKÿþe9Ap} V,y*á@‚$Kÿ3`ƒè@AœÿÔ9Ap} V,y*áA‚ÿL8 äûxÃóxKÿý•8`dKÿ3M`Kÿ2Õ`8cˆx} `Kÿ2Á`ƒè@@œÿ8¡päûxÃóxKÿýå9Ap} V,y*çã@‚ÿÔé>é)/©Až”Kÿ¦`{ä ûÃ|}xé>ù#Kÿ²õ`/£@žXäûxƒãxH
`‰!z9_}_´‰PAþ 8! 8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```£ëxKÿæ½`KÿþL8¡päûxÃóxKÿý%9Ap<À } V,y*¿ã@‚y&·â0Æÿÿ|Æ1xÆ_¦xƪä<Æ@é>{å Äóxèi H%`/£@þýðKÿÿ@`8b8HÙ`8! 8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ €````|¦ûÿàû¡ÿè||xûÁÿðûáÿø|#xøø!ÿq|¬ëÃ4h9àD,Kÿ1
`k¤ „½és½ˆ|cêx} H(``|¬9àD,Kÿ0Õ`ƒè@A8<4|{ÿàŸH@žÿØ|¬9>}@L,yI¶¢+‰!y$ Až<+‰"Až+‰ Až`8bˆHÑ`9 9^ù\4h‘>9@àô,}
ô,ù>9<4|yÆÿCx} L,‘>é4Pé<4hèÜ4p}(HPy*!}*fp}J”UJ`&}*HP})´|É2@‚<4|ù4h})4U)Ù~‘<4|è¼8¥8|¬xÉ"TÈ@>PÈÀU*@>PÈÄ.Q*ÀQ*Ä.yÆ}Sx8`@8€}CxD"/¿Ažþûx8!Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8!;ÀÃóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``9} D,U)F>+‰Až9 ‘<4äKÿþÌUJF>‘\4äKÿþÀ€``,#M‚ éC/ªMž |¦ûáÿøûÁÿð|xøø!ÿ#éJ+‰ëÊ Ažˆ+‰Až\é>48/©Ažˆûé9 ûþ488  8€ãûxù?ù?Hý­`8!€èëÁÿðëáÿø|¦N€ ```èƒ(€£8èc0Kÿ3Õ`€Ÿ8è(Kÿ0å`9 ù? é>48/©@žÿ€9 ûþ40ûþ488  8€ãûxù?ù?Hý)`8!€èëÁÿðëáÿø|¦N€ €```}€&|¦ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèûÁÿðøûáÿø‘ø!ÿ1é#/©AžéI/ªAžë‰XëJ |ž#x|½+x8€8 Ãóxƒ|ëëüPKÿ2`99 @}@F,|yx/ªAž ‰>y)Ïâ1)ÿÿ})Iy)ä=)9)@9}@D,éyJày"‘iJ}IKx=@ÿ‘_9_} U,|¬9~àF,zõ .5@’ì;ÿ:À9 9_} T,9@‘_‘_y)à‘_i)})Cx9} E,|¬|¬{ed8`@|¸*8€<ÀD";ÿ8€CÓxKÿûEûüP8 Äóx3ãÿÿÿ#ËxKÿ1É`A’~å»x¤ëx~óxKÿ1±`8!Ðãûx聁ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿø} N€ 8 ~ä»x£ëxKÿ0•`9_9} T,|`E,xj"9|vx}@E,9_9y)ài)~ U,e)a)} E,|¬=;ÿ a KÿþÀ``;àKÿÿD€```|¦ûÁÿðûáÿø|x8`|ž#xøø!ÿKÿ-Q`9 /£øAž<9 ›ß8 8€‘?Hú%`è8 8€Kÿ/±`9 ø8!€}#KxèëÁÿðëáÿø|¦N€ €``|¦ûáÿø|xøø!ÿèƒ/¤Až$èc 8 Kÿ0	`è8€Kÿ-`8 88€ãûxHù…`8!€èëáÿø|¦N€ €```|¦û¡ÿèûÁÿð9 ûáÿø|x; |ž#x8 øø!ÿqèc‘?(9 Ÿ0û¿8€‘?,øøHù`+žAž@?(é8À;ÿ }Fü,|àü,y)&ä9)ÿðyJÆ|çSx}HJ|èI*= “ª‘*8!èë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûÁÿðûáÿø|x8`|ž#xøø!ÿKÿ+a`9 /£øAž,ÄóxãûxKÿþñè8 8€Kÿ-Ñ`9 ø 8!€}#KxèëÁÿðëáÿø|¦N€ €``|¦ûÁÿðûáÿø|~xøø!ÿëã4˜éC9} D,9|€ý,‘9y)ài)|ÆKx9?| M,|ÀE,|¬8`@}ESx8€8ÀD";ÿ8€ÃóxKÿ÷=ûþ4˜8!€èëÁÿðëáÿø|¦N€ €|¦,#ûAÿÐûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿaA‚xé#|ž#x|}xë‰ ëü40/¿Až¼é?/©ù<40Až|8  8€ãûxHöí`9 û¿ù?‰>y) y* +‰‘_=h‘?¡>±?‰>U)Éþ‘?‰>y) ±?Ažü+ŠAžT8! ãûxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ }	QÖèÞ ÿ;@ƒãxTç€}(J`ç>y) 9}&J}
P08©aJ9)|à-,< ¤èþ˜©8¦};x8ày"}M,|‡M,}@-,“F€ÞxÆÀ(`Æ0èž x…"T„6Kÿýíû éˆèÞx€þ }&@P8§ÿÿy*á9JŠ(@Až9Hù^ˆ ß})&t8è8ˆ}@<,èÿ0})1ÖyJàiJy) aJ }):y'"} E,9(9|àM,|À%,}@E,|¬?/‰@žþÀ```ëX/¼Ažþ¨?é]/‰ëj AžÄ;¼°;Àé=8€£ëx/©Až8Kÿûµ9 ð±?‰</‰Ažx¡_< <ÀUJ<}JCxé}JIÖWÉ8e)ða)yJ }HR98ª9J} -,=,èý Ê8À});xy'"} U,|æU,‘àù<48Kÿý„¡?€Ü èücÛxU)<}(CxWÉ8}H1Öe)ða)}FRyJ }GR8ª9J} -,9 < }(@0a=,èÝ ª8§})3x8Ày$"} U,9 |†U,}-,‘'€ÜxÆÀ(`Æ0èœ x…"T„6Kÿûíû¿ 8! ãûxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``=dm*/ŠAžÔ``åûx8‚x8bHÿÍ`_KÿüØ```;¼è;ÀKÿþ@`8`Kÿ&M`/£|{xø|4ðAžˆ8€8 Kÿ(Í`8€@iÛx|‰¦9@ø|4øH```/©@Ažù)ÿÈùI9)@Bÿìé<40/©Až8é<48ûiëü40;{Àû|48KÿûÀ`9 ëÝX8€±?;~xcÛxé>x/©Až°KÿùM¡?y)B(}#Kx‘?8Kÿ%‰`€Ÿ88 ø(Kÿ(`¡_ø0UJ<}JCx‰>/‰> Ažûè}*IÖé¡_UJ€y) aJ>}(J98É9)}@5,<À^¤èþ˜É}J;x8àyD"}@M,|‡M,‘àKÿùq/£@žÿP`8b˜Hþ-`KÿþDKÿùQ/£@žüÈ`8bÐHþ
`Kÿû$;àKÿûÛxû|40KÿþÐ9^˜8€xé&ä|¤T,|àT,9)ÿðøވ}FJ“^¤x¥Æ|ç+x|æI*= “J‘*|¬èÞx}&@PKÿû¬€`|¦ûÁÿð;Ãû¡ÿèûáÿø|#x|x8€8`<Åóxøø!ÿqD"/£@žøT‰@>P‰ÀP‰Ä.}$KxxŠ¯ã@ÂÄ8`<8€åûxD"/£9 ÿÿy) @žT‰@>P‰ÀP‰Ä.y) /½U*<@žÄåûx|¬UF@>8`@QFÀ8€QFÄ.xÆ D"|¬;à@`8`<8€ÅóxD"TŠ@>/£PŠÀ9?ÿÿPŠÄ.y? }DSx.¿x‰¯ã8`d@žA‚AÖKÿ"
`Kÿÿ´8`8!èë¡ÿèëÁÿðëáÿø|¦N€ 8!8`èë¡ÿèëÁÿðëáÿø|¦N€ ©Kxy* Kÿÿ8€``,#A‚ø|¦ûÿàûaÿØ||xû¡ÿèûÁÿðûáÿøøø!ÿaë£ /½Až€ë}8€;ý;Ý3¸cÛxKÿþEé?ÿP/©AžlãûxKÿõ¡88Kÿõ™8ÿÈKÿõ‘8ÿKÿõ‰èŸÿhèÿp8 Kÿ%©`èÿh8€Kÿ"¹`èŸÿ€èÿˆ8 Kÿ%…`èÿ€8€Kÿ"•`;ÿ(¿ð@@žÿ„è½8¥0|¬8`@8€8ÀD"|¬è4À/¤Až$è}4È8 Kÿ%-`è}4À8€Kÿ"=`8}4P;ûKÿôÝ8`<8€åûxD"/£Až´<À?xÆÆ|¬8`@åûx8€D"8}4ˆKÿô¡|¬8`@8€8»08ÀD"è4@/¤Až$è}4H8 Kÿ$¡`è}4@8€Kÿ!±`8`2Kÿ•`£ëx8€5Kÿ"¥`9 8! ù< èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ x†dxÆñÆKÿÿPé# à€,#A‚lé#/©Až`é	/¨AžT|¦ûÿà|œ#xûáÿø<‚¥û¡ÿèûÁÿð|xDwøø!ÿq/Šëà AžLé)Xë¨ ¡C)è½y)d|¥J|¬UI<8`@})Cx8€U&@>Q&ÀQ&Ä.xÆ D"8€£ëxKÿìÙ/£Ažà|¬éèހþ(}&@P8çÿÿy*á9JŠ8@Až¨9ù¡_})&të¿(8 ƒãx}*IÖy) ½J¤ëxHí	`8 8€£ëxHì¥`èÞé^€¾(}&PP8åÿÿy(áxç 9ˆ8@@ž¬9 9 x¥&ä|‰D,|àD,8¥ÿð9øÞ}&*‘,x„Æ|ç#x|æ)*‘	=‘	|¬èÞ}&PPHd`é^èހ¾(9‘w}&PP8åÿÿy)á9)‰8@y) xç Ažð9Jù^é^}&PPy(á9ˆ8@Ažÿ\9
ù ß})&t8ê8Š}<,èÿ0})1Öyàiy) a }):y'"} U,9*9J|àM,|À%,}U,|¬8!8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`N€ ``øÞKÿþ```8!8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```øÞ}'KxKÿÿ€``éC/ªAžØèª/¥AžÌé# /©AžÀ|¦9ûAÿÐûaÿØaðûÿàû¡ÿè‡@ûÁÿðûáÿøøø!ÿaALëI艁i(é
Xë¥ }DÐP8ÿÿyJáè½9JŠ@Ažx9ZùI9zëé ;Ú}@\,xË"|ÀÕ,}`õ,9zyIà}Zúi)äPPa) 9Z|àU,} ],|¬¡#CU)<})Sx|¬U&@>8`@Q&À8€Q&Ä.y	d|¥JxÆ D"KÿÑ`?b¥;€;{w8cˆx~ HAžÀ“›Kÿ©`ƒð@Al8€£ëxKÿéQ~£ø@/£@–ÿÔ8`9 ù:‘:‘:|¬8! èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8b(Hõ‰`8! 8`èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8`N€ ``8`Kÿÿp``9I ;Àyk&ä|T,àT,9kÿðø‰}DZxÆÿx8	,äY*<€
Š|¬è‰KÿþL€``|¦ú¡ÿ¨û!ÿÈ|Ù3xûaÿØû¡ÿè|›#x|½+xûáÿøúaÿ˜|x8 úÿ úÁÿ°8À$8€úáÿ¸ûÿÀøûAÿÐûÿàûÁÿðø!ÿ!Kÿð5‚¿4ä/µ@žX8`8!àèêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿè|¦ëÁÿðëáÿøN€ ```+•,A¼ƒß4èÕ(8€Þ4}?²:ö0WÞÙ~~ÿºÞВ©0;—{Þ¤ƒãx;Þ@“ÉHKÿí
/£Ažÿ`‰7/‰Až9 ‘)à``ë= ‘89 ‘89 ‰W/ŠèÜAžL/»;½|ÆJ{º {© Až|jÛx```€êtéJU) 6/ªxè }	Kxy) @žÿäg9U)á>)KxTç‚?²8€} 5,8Æ;9h#Ëx|à5,Kÿî5/£Až€‰WéÉóx/ŠAžÈ=@&}(JaJ@~²<à9)‘Iÿü:ö@8€~ÿº:—~ƒ£xS”鈐é8à}JCxyH"}@M,}M,KÿëÕ/£Až:s`9 é4@}Iœ,|àœ,9 yJÆ|çSxzª$|èQ*‰Wêô/ŠAžd~²V¾ÀWÆãûxè“H`Æ,~÷Jx…"T„6Kÿíí|¬= WÆ`Æ0ãûx‘89 ‘8è“Hx…"T„6Kÿí½|¬KÿŠ¥`é? ;ó(DÓx|~xù#9 ‘#h‰7“£tûcûãX‘#løs(Kÿ–ù`/£@žœè”èt8 Kÿ­`èt8€Kÿ½`#ËxKÿëaèœè|8 Kÿ`è|8€Kÿ‘`Kÿüô``8 ,~¤«x8bPHñA`KÿüÔ`ÉóxKÿý´``WÊ<yI Kÿþ4`ÃóxKÿÊ}`8`Kÿü ```ÉóxKÿþœGÓxKÿý´€
`|¦ûAÿÐû¡ÿè|zxûÿÀû!ÿÈ|#x8€ûaÿØûÿàûÁÿðûáÿøøø!ÿQëãëƒ8`<8¿D"/£;Àÿ@žT‰@>P‰ÀP‰Ä.}$KxxžF"8`<8€8¿D"/£@ž T‰@>P‰ÀP‰Ä.}$Kxx‰„#A‚; y)d8`<ÿJ8€åûxD"/£@žTT‰@>P‰ÀP‰Ä.y$ +„@ž<8`<8€åûxD"/£9 ÿ@žT‰@>P‰ÀP‰Ä.}$Kxx‰F"H@Ažô8`<8€åûxD"/£@ž¬T‰@>P‰ÀP‰Ä.}$Kxx‰Æ#@‚ÿd/¹Ažlyò;Ùÿÿ;{ÿÿ?žØ@c{Þ {{ #9AœTH$```+T‰@>P‰ÀP‰Ä.Až`+@žH8„ÀAÞP``;ÞžØ@{Þ @œØ;þ@8`<{ÿ&ä8€üúåûxD"/£Ažÿ +Až+@žÿÀ8`<8€åûxD"/£AžØ8ÀÿÿxÆ |¬8`@8€åûxD"8`KÿÅ`8€CÓxKÿâ8`<8€åûxD"/£<Àð@žT‰@>P‰ÀP‰Ä.U&RxÆ |¹ò8€;Þx¥ CÓxKÿù}žØ@{Þ Aœÿ08!°8`èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``9 ÿKÿýÌ``d„x† Kÿÿ,`q$+„@þþ¸Kÿþø8`<8€åûxD"/£@žýüT‰@>P‰ÀP‰Ä.}$Kxx‰†#@Âýä;8`<8€eÛxD"/£;Àÿ@žT‰@>P‰ÀP‰Ä.}$KxxžÆ"8`<8€eÛxD"/£; ÿ@žý”T‰@>P‰ÀP‰Ä.U9>Kÿý€```9 ÿÿy) Kÿüô`8!°8`èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €|¦ûÁÿðûáÿø|xûÿÀû!ÿÈ`ûAÿÐûaÿØ8b€ûÿàû¡ÿèøø!ÿQHì©`é?8`5y)$ù?KÿQ`|~yA‚d8 58€Hà)`9 ûß 8`<8€ù?(ûþ è¿ø¾ë¿D"/£9 ÿ@žT‰>}=Jè¾8`<8€ù>8¥ë¿D"/£9 ÿÿy) @žTˆ@>PˆÀPˆÄ.y	 }=Jè¾8`<8€ù>8¥ëÿD"/£9 ÿÿy) @žT‰@>P‰ÀP‰Ä.y) ëž}?Jë~8`<8€ù>;¼¥ëxD"/£@ž0TŠ@>PŠÀPŠÄ.}DSxxˆá@‚8€ƒãxKÿíÝ/£AžÔ8`<8€¥ëxD"/£@ž¼T‰@>P‰ÀP‰Ä.}$KxxŠ¯ã@¤8`<8€…ãxD"/£8ÀÿÿxÆ Ažä|¬8`@8€…ãxD";à@``8`<8€¥ëxD"Tˆ@>/£PˆÀ9?ÿÿPˆÄ.y? }Cx.¿x‰¯ã8`d@žA‚AÖKÿ-`Kÿÿ´|¬8`@8€8¼8<À,D"è¾8`<8€8¥D"/£@ž TŠ@>PŠÀPŠÄ.}DSxxˆ÷ãx„÷␞4è@Â8`Kÿù`/£ø~4@Až¨8 8€HÝÝ`è~4@8 8€Kÿi`ø~4H|¬xi"Tf@>PfÀU*@>PfÄ.Q*À;¼0Q*Ä.xÆÆ8`@|ÆSx8€¥ëxD";^4ˆ8€CÓxKÿäõ/£Ažì;ü8`<8€åûxD"/£8À?@ž,x‰"Tˆ@>PˆÀU*@>PˆÄ.Q*ÀQ*Ä.yÆ}Sxy é>4¨y)d}&3x|¬xÉ"TÈ@>PÈÀU*@>PÈÄ.Q*ÀQ*Ä.yÆ}Sx8`@}Cx8€åûxD";>4P8€#ËxKÿäM/£@ž@8`<8€åûxD"/£@žx†dxÆñÆ|¬8`@8€åûxD"|¬CÓxKÿâµ|¬8`@8€¥ëx8ÀD"|¬èž4@è~4H8 Kÿ¹`è~4@8€KÿÉ``8bðHè‰`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 9 ‘>4è`8bÀHèA`Kÿÿ¨`d„x† Kÿý``8b˜Hè`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ <À?xÆÆKÿþè8`Kÿ`/£ø~4ÀAž¬8 8€Kÿ`9 è¾4ÀèÞ4pø~4ȑ>4Ð|¬xÉ"TÈ@>PÈÀU*@>PÈÄ.Q*ÀQ*Ä.yÆ}Sx8`@8€}CxD"è¾4À>4x8¥|¬U&@>8`@Q&À8€Q&Ä.xÆ D"è¾4À8¥|¬8`@8€8ÀD";88`<8€ÃxD"/£8À@ž,x‰"Tˆ@>PˆÀU*@>PˆÄ.Q*ÀQ*Ä.yÆ}Sxy é>4py)ä}&3x|¬xÉ"TÈ@>PÈÀU*@>PÈÄ.Q*ÀQ*Ä.yÆ}Sx8`@8€Ãx}CxD";(8`<8€ÃxD"/£=@ÿÿyJ @žTˆ@>PˆÀPˆÄ.}CxTŠ>4Ð})Sx|¬U&@>8`@Q&À8€Q&Ä.ÃxxÆ D";{08`<8€eÛxD"/£8À?@ž,xŠ"T‰@>P‰ÀUH@>P‰Ä.QHÀQHÄ.y)Æ})Cxy& é>4Èy)d}&3x|¬xÊ"TÉ@>PÉÀUH@>PÉÄ.QHÀQHÄ.y)Æ})Cx8`@}&Kx8€eÛxD"|¬8€ƒãxKÿçù/£Až,8€ÃóxKÿô¥8€||xÃóxKÿô•|cãx/ƒ@žüØ|¬8`@8€eÛx8ÀD"|¬èž4Àè~4È8 Kÿ=`è~4À8€KÿM`#ËxKÿÞñKÿûü€```|¦<b8c›°øø!ÿ‘Kÿ€`8!pè|¦N€ €``|¦="¥)w 9@øø!ÿa‘!p9 a|8`8p`cðùAˆ‘!t9 ‘!x9!‘!€9 ‘!„Kÿ6`ˆa8! è|¦N€ €``|¦="¥)w$û¡ÿèx} ûÁÿðûáÿø;À|xûÿà9)ÿÿ½H@øø!ÿq@¨;ÿ;½?‚¥{ÿ {½ ;œw H,``;ÿޝø@WÞ>{ÿ Až<<9)ÿÿ¿H@8`AÿØãûx;ÿKÿþíø@{ÿ Tc>ÞWÞ>@žÿÌ8!WÃÂ>|còèëÿàë¡ÿèëÁÿðTc>ëáÿø|¦N€ `£ëxKÿþ="¥)w$T~>9)ÿÿKÿÿD€``|¦="¥)w$ûáÿø;àû!ÿÈûAÿÐûaÿØûÿà/‰û¡ÿèûÁÿðøø!ÿ!Ažx?¢¥8`;½w ; ;@;€;a``Kÿþ9;À}
´/£AÞ<=9)ÿÿªH@@\ãûxKÿþe9}	´ƒð@ž]9Jÿþ©P@@D8!àãûxèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ y Kÿý|~xKÿÿœ=8`8pû!ˆ`cð“At“x‘|“a€‘!p“„Kÿ3¹`¡A/ªUI 6})úy# AÞÿx}?´‰@@9Hÿÿ~£P@@œÿ`@•ÿ8!àãûxèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦="¥)w$ûáÿøxh 9@@x 8éÿþ¨8@øø!ÿQ±A–@9y
 ª8@9@±A”@ˆ;ÿ9)ÿü{ê ªH@9 ‘!AP="¥)w(8`9@“á|8p`cðùAˆ‘!p9 ‘!t9 ‘!x9!‘!€9 ‘!„Kÿ2‰`8!°èëáÿø|¦N€ ``=B¥Jw(9 8à‘|8`8p`cð‘!x‘!„‘Ap9@øሑAt9A”‘A€Kÿ2%`="¥)w$Kÿÿ,```=B¥Jw(9 9“á|8`8p`cð‘!x‘!„‘Ap9@ùˆ‘At9A–‘A€Kÿ1Å`="¥)w$8éÿþKÿþ°€```|¦úáÿ¸ûÿÀ|—#xû!ÿÈûAÿÐ;|Ù3xûaÿØûÿà|zx{äûÁÿðûáÿø|¾+x?‚¥úÿ ú¡ÿ¨;œw øúÁÿ°û¡ÿèø!ÿKÿüe?⥃ÿw$|{xKÿüU|cøPƒÀ@Aœh="¥)w${} šá”9Iÿÿ½P@@¬99)ÿþy
 &p”ªH@³@ø;à;½:€: :À:á“;H``;ÿ{ÿ ÃóxHÏå`}úy	 ƒø@@`\|þø®9Jÿÿ˜á“©P@Aÿȁ<8`8púˆ`cð’¡t’Áx‘|’ထ!p“„Kÿ0M`Kÿÿ```cÛxKÿúM=B¥Jw$9y	 ˜a’9Jÿÿ©P@@l;{û:{´ûz8!CÓxèêÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿøN€ `9 ù:ù:Kÿÿ¬="¥)w(9@8`‘|8p`cðùAˆ‘!p9 ‘!t9 ‘!x9!’‘!€9 ‘!„Kÿ/a`KÿÿL<9@8`“¡|8p`cðùAˆ&p”‘!p9 ‘!t9 ‘!x9!”‘!€9 ‘!„Kÿ/
`<9³y
 9)ÿþªH@Aþ=B¥Jw(9 8à‘|8`8p`cðøሑ!x‘Ap9@‘!„‘At9A‘A€Kÿ.©`KÿýÄ€```|¦ûáÿø?⥃ÿw$;ÿÿðøø!ÿqKÿù•`8€8¢“p|ÃøP8ap|Æ´Kÿü¹é!p8!èëáÿø0iÿÿ|cI|¦N€ €``="¥iw ="¥‰w(="¥©w$="¥øÉw0N€ ="¥)w$9)ÿÿ£H@@8`N€ `Kÿ÷`|¦="¥)w$9)ÿÿ£H@øø!ÿq˜ÈAT=B¥Jw(|ix98`8p‘!|9!È`cðùˆ‘Ap9@‘!€9 ‘At9@‘!„‘AxKÿ-I`8!è|¦N€ €="¥)w$9)ÿþ£H@@8`N€ `|¦=¥w |ix9@8à8``cðøø!ÿa‘p‘!|99!8pøሑAx‘t‘!€‘A„Kÿ,µ` a8! è|¦N€ €``|¦="¥)w$9)ÿþ£H@øø!ÿq°ÈAP=¥w(|ix9@8`8à‘!|9!È8p‘Ax‘p9`cðøሑ!€‘A„‘tKÿ,`8!è|¦N€ €`="¥)w$9)ÿü£H@@8`N€ `|¦=B¥Jw |ix98``cðøø!ÿa‘Ap‘!|9@9!8pùˆ‘At‘!€9@9 ‘Ax‘!„Kÿ+`€a8! è|¦N€ €`|¦="¥)w$9)ÿü£H@øø!ÿqÈAT=B¥Jw(|ix98`8p‘!|9!È`cðùˆ‘Ap9@‘!€9 ‘At9@‘!„‘AxKÿ*é`8!è|¦N€ €="¥)w$9)ÿø£H@@8`N€ `|¦=B¥Jw |ix98``cðøø!ÿa‘Ap‘!|9@9!8pùˆ‘At‘!€9@9 ‘Ax‘!„Kÿ*Q`èa8! è|¦N€ €`|¦="¥)w$9)ÿø£H@øø!ÿqøÈAT=B¥Jw(|ix98`8p‘!|9!È`cðùˆ‘Ap9@‘!€9 ‘At9@‘!„‘AxKÿ)¹`8!è|¦N€ €="¥)w$=B¥9Jw ‰@Aœ,="¥‰)w8/‰@ž9 ÿÿèj™*N€ ``8`N€ ```9 =B¥™*w8N€ `|¦û¡ÿèûÁÿðûáÿøøø!þqøÈø¡Ð|dx8¡È8apøÁØøáàùèù!ðùAøH֑`/ƒ|}x@Ý<;Ãÿÿ9!p{Þ ;áoÉò``Œ8 8€Kþ®E`¿ð@@þÿè8!£ëxèë¡ÿèëÁÿðëáÿø|¦N€ €``}€&|¦="¥)w$ûAÿÐ|zxúÿ€ú!ÿˆúAÿúaÿ˜/©úÿ ú¡ÿ¨úÁÿ°úáÿ¸øûÿÀû!ÿÈûaÿØûÿàû¡ÿèûÁÿðûáÿø‘ø!þáAž¼>"¥.$:1w -%-„ÿÿ|›#x|¹+x;à;À:€:ñ : ;:Á8~9)ÿÿ|j´; ªH@@|ÃóxKÿñµƒè@ž\19}
´8éÿþª8@@d@’@; 9)ÿÿ¿H@A@ãûxKÿðùƒØAÞ01W¿ 6ÿòŸH@þ´{ÿ Aœÿ„9 ÿÿ;€Hœ`AŠp9>;ž}3´:Qy? { H9?œr‰€@y? Až818`9)ÿÿ©˜@:sAœÿØãûxKÿðq9?‰€@y? œr@žÿÐ8 $Ëx~ã»xHÆ=`/£@žÿT9=ÿÿœ´U) 6})´ûšù:8! CÓx聁êÿ€ê!ÿˆêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈ|¦ëAÿÐëaÿØëÿàë¡ÿè}’ }‘ } ëÁÿðëáÿøN€ xc Kÿï½|}xKÿþ|18`8púˆ`cð’¡t“x‘|’Á€‘!p“„Kÿ%é`£¡AÒ0/½AÞþ AŽþ¬19Iÿÿ¿P@AýþtKÿþ\`;žKÿÿ1Kÿþ<€`|¦ûÿàû¡ÿè9%ûÁÿðûáÿø})´||x9)|¾+xy)äx¥ })Ðøø!ÿqéA|?x}AIj;¡p£ëxHǑ`9 8€ÿÿ¥ëxƒãxx„ }=ñ®KÿüÑ8?ƒãxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦="¥)w$ûÁÿðxž û¡ÿè?¢¥ûáÿø|xúáÿ¸ûÿÀ;½w žH@û!ÿÈûAÿÐûaÿØûÿàøø!ÿA?b¥‹{w8/›AžÔ|„ú„ø|ž´@;€:à;; ;A;`H`;ÿžøÿ´Až`={ê 9)ÿÿ›ªH@Aÿ܁=8`;ÿúáˆ8p`cð“t“!x‘A|“A€‘!p“a„Kÿ#ý`žøÿ´@žÿ¨8!ðèêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ë9@ÿÿ™]/¼AÞÿ Åóx8€ƒãxHő`=9@8`“á|8p`c𓁀“Á„ùAˆ‘!p9 ‘!t9 ‘!xKÿ#U`8!ð›}èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €	`="¥8`è‰w&Kÿþ`|¦/¥8cÿð|c´øø!ÿ‘@ž(8„|„´KÿýÝ8!p8`è|¦N€ `8€Kÿý½8!p8`è|¦N€ €``|¦ûÿàû¡ÿè|¼+xûÁÿðûáÿø|~x|#x8 8€|ß3xøø!ÿa8apKÿùéé!xèap9)+©@8cÿð8€|c´Kÿý5…ãx¤ëxæûx8apKÿðqë¡xëp¿èAž; ;€Kÿóeûžû¾8! Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûáÿø9}	¦|x9 9`øø!ÿq9ApH`|eH®|jI®9)B@†HAÿì}jI®9)Bÿð9 ãûx|æ;x}ESx™!|KÿþÉ8!ãûxèëáÿø|¦N€ €9$+©@¸|¦="¥)w$ûÿàxœ ûÁÿðÃâú¡ÿ¨"¼ÿðúÁÿ°úáÿ¸zµ žH@ûÿÀû!ÿÈÞ´ûAÿÐûaÿØøû¡ÿèûáÿøø!þñ@œÐ>Â¥:à:Öw ;; ;A;`H0``6˜a9Iÿÿ¿P@@L9^ŠH@}^´@œ„{Ê 9)ÿÿªH@ªª8`{¿ AÿÄ}CSxKÿé݁6˜a9Iÿÿ¿P@Aÿ¼68`8púáˆ`cð“t“!x“¡|“A€‘!p“a„Kÿý`69^}^´ŠH@Aœÿ„|iª8œÿð|„´|c´Kÿúí8 8a 8€Kÿ÷m聨èa 8„8cÿð|„´|c´KÿúÁKÿñ8!8`èê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8`N€ €```,#@‚8`N€ |¦|c´|„´øø!ÿ‘Kÿú-8!p8`è|¦N€ €``¥ @œ8`N€ |¦úAÿûÿà||xû¡ÿèûáÿø|½+x|Ÿ#xúaÿ˜úÿ 8 8€ú¡ÿ¨úÁÿ°úáÿ¸ûÿÀøû!ÿÈûAÿÐûaÿØûÁÿðø!þá8a Kÿö%é!¨êA /©ÿÿAž”}_èP©PAœˆ{œ {þ 9Rÿð~\òŠ}W´~Z´@¸="¥)w$~RPP?b¥;{w ’H@AL=B¥‰Jw8/ª@ž<ë;9@ÿÿ™[/¹AÞ(;9ÿÿ_Óx8ËxH `;ÿ8—øÿ´@8;9)ÿÿ{ã £H@9 AÿØKÿçU;ÿ—øÿ´|ix8AÿÐ{¸ 8€üÂ~ã»x~_’Kÿø¥Ÿÿ´~R´@œ”:`:€: :Á’:àH``;ÿŸÿ´Ažd;{ê 9)ÿÿ™’ªH@Aÿ؁;8`;ÿúaˆ8p`cð’t’¡x‘A|’Á€‘!p’á„Kÿù`Ÿÿ´@žÿ¤9 =B¥™*w8Hd8`8! èêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿà|¦ë¡ÿèëÁÿðëáÿøN€ `8€~ã»xKÿ÷™{¸ |žÀPCÓx|„´;œÿòKÿ÷=B¥Jw${‰ ³¡9Jÿþ©P@@KÿíÁ8`Kÿÿl`=B¥Jw(9 9“|8`8p`cðùˆ‘!x‘Ap9@‘!„‘At9A‘A€Kÿõ`Kÿÿ¨€``|¦="¥ûÁÿðûáÿø8`?àibè‰w&cÿm,øø!ÿaKÿöÉ= CP8¡p“ápa)U08a€y)Æ8Àðe)lo8€Qa)gù!tKÿéé= CP8¡pëÁ€“ápa)U18Àðy)Æ8€Qe)lo8a€a)gù!tKÿéµëá€ÃóxKÿè	ãûxKÿè`8b“€Kÿò`8Àð8¢“¨8€p8a€Kÿé}Kÿì‰8! èëÁÿðëáÿø|¦N€ €N€ <b¥€cw$N€ ``````|¦ûÿàû¡ÿè|œ#xûÁÿðûáÿø|~xx} £ëxÞ´¼êøø!ÿqKÿì`žè@œp|x½´H}>´A–\{à Kÿìe`9>~‰è|ûxWÿ>/Ÿ|x@žÿÔ8!Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8!8`ÿÿèëÿàë¡ÿèëÁÿðëáÿø|¦N€ €|¦û!ÿÈûAÿÐ|™#xûaÿØûÿà?‚¥|»+xûáÿøû¡ÿè;œwP|´ûÁÿð8 8€ƒãx{{ øø!ÿQ;\ÿÿH»q```]Óx;ÀH`Aވœ}}>´9?8iÿÿ}?´xc KÿëU`/ž9>,#@‚ÿÐeÛx„ãx#ËxH¸¡`/£AžX/¾@žÿœ8!°8`ÿÿèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ eÛx„ãx#ËxH¸M`/£@žÿP8!°ãûxèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €,#@‚8`N€ |¦ûÿÀû!ÿÈ?"¥ûAÿÐûaÿØ;9wP|º+xûÿàûáÿøxÛ |´û¡ÿèûÁÿð;™;øø!ÿQ``;¹ÿ;ÀH`Aޔ=}^´9?8iÿÿ}?´xc Kÿê`/ž9^|iy@‚ÿÐ}YòeÛx„ãxCÓx™*H·I`/£AžÀ/¾@žÿ”8`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ eÛx„ãx›CÓxH¶í`/£@žÿ@‰9/‰=Ažl/ž9>ÿÿy) Šãx9)8`})¦AýHT```B@*8c|c´/‰=@žÿì8c||KÿÿT‰9/‰=Až/¾@žÿœ8`||Kÿÿ49 })¦Kÿÿ¸€`|¦ûÿÀû!ÿÈ|˜#xûAÿÐûaÿØ|Ù3x|{xû¡ÿèûÁÿð}Cx|½+xûáÿøûÿà|þ;xxÚøø!ÿQKÿûÉ}9Ò9)x ØP›HAœð{)!A‚ÜŸJ;½ÿÿ{› H`````Œãûx;ÿKÿèe`ŸØ@{ÿ @žÿ䜴cÛx8€=;üKÿèA`{I!A‚D;©{ÿ ½â;Þÿÿ{½ ```Œžãûx;ÿKÿè`Ÿè@{ÿ @žÿä8`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ||xãûxKÿÿl8`ÿÿKÿÿÀ€```|iyA‚œ|¦û!ÿÈûAÿÐû¡ÿèûÁÿð|Ý3x|¾+xûáÿøúÁÿ°}?Kxúáÿ¸ûÿÀûaÿØûÿàøø!ÿAKÿúY¥ëxÄóx|yxãûxKÿû%;ãÿÿ|zxÿ´H}?´{ý £ëxKÿæå`9?ÿÿ/£@žÿä~ÚÈP;ß~ôKÿë`/–|wx@”{_ ;ƒÿÿ²›ãx{ H``````ãûx;ÿKÿæy`ŸÀ@{ÿ œ{@žÿä:Ö{ß ¶ê{½ ````Œœãûx;ÿKÿæe`Ÿè@{ÿ @žÿä~ã»xKÿêÍ`|™ò#Ëx|š P|„´Kÿï`8!À8`èêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`ÿÿN€ €
```}€&|¦ûáÿø|yú¡ÿ¨úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèøûÁÿð‘ø!ÿ1A‚l}Cx|ü;x|Ú3x|½+x|ž#xKÿúµ|{yA‚\H²Y`z· ƒ¸@AžÄóxãûxKÿø]EÓx¤ëx|{xãûxKÿù)CØP|~xC´KÿéI`|yyAÂü.{Ý @‘h~Úê¿ëx;ÿÿzÖ ```ãûx;ÿKÿä¹`Ÿ°@{ÿ œx@žÿä£ëxKÿä`9>ÿÿ/ƒ=Až,``}>´{Ý £ëxKÿäu`9>ÿÿ/ƒ=@žÿä/•;ÞÉ´@\97{Þ ©ê;œÿÿ{½ ßóxH`````Œœãûx;ÿKÿäE`Ÿè@{ÿ @žÿä×òÉ´y< :é8€ƒãx~ÿ´Kÿä`@‘D;ºz÷ ½â;Ùÿÿ{½ ~ÿ»xŒžãûx;ÿKÿãå`Ÿè@{ÿ @žÿä~÷Ò~ÿ´#ËxKÿèE`›ø@(`{ã 8€;ÿKÿã¥`›øÿ´@žÿä8`8!Ð聁ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿø} N€ ``|ex„ãxcÛxH°u`/£@žýÔKÿÿ”8`ÿÿKÿÿ``8!Ð~¨«x‡ãxFÓx聁¥ëxãûxê¡ÿ¨êÁÿ°Äóxêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿø} Kÿù¸€``|¦ûaÿØûÿà||xû¡ÿèûáÿø8`|Ÿ#xûAÿÐûÁÿð|»+xøø!ÿaKþæ-`|}yA„/ŸAžH8 „ãx£ëx?‚¥H²E`[9 =¥8€8` ‘=;œyX‘]=@€‘HyX=B¥‘*y\KþæÝ`=¥8€|ix9C8`ù(y`="¥ùIyhKþæµ`=B¥øjyp<``cKþå`<¢¥è¥y`="¥øiyx/¥Ažð<â¥èçyh/§Ažàé\/ªAžÔ/£AžÌé8À`i€yF,=@€9)aJyFy„8`ù<(;àKÿ	`|dy@‚X?@€?`cZ``é<(8`}Iúy^,}Iù*{^;ÿÅóx€KÿÁ`¿Ø@žÿÐ9 8! £ëx‘=èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8b“ÐH¼¹`<b¥ècy`/£Až8€ KþäÝ`<b¥ècyp/£Až8€KþäÁ`<b¥ècyx/£Až<€`„Kþä¡`£ëx8€Kþä‘`8`8! èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```‰</‰@žý´‰</‰@žý¨;œKÿý `8b“øH»é`Kÿÿ0`8b“°H»Õ`8`Kÿÿ„€``,#M‚ |¦ûáÿø|xøø!ÿ#/‰@ž,ãûx8€KþãÁ`8!€èëáÿø|¦N€ `€ƒ8`Kÿ

`<b¥ècy`/£Až8€ Kþã}`<b¥ècyp/£Až8€Kþãa`<b¥ècyx/£Až<€`„KþãA`9 ãûx8€‘?Kþã)`8!€èëáÿø|¦N€ €,#A‚¤|¦û!ÿÈûAÿÐ`ûaÿØûÿà?€€|›#xû¡ÿèûáÿø?â¥|½+xúáÿ¸ûÿÀ|yx;ÿyXûÁÿð=B¥Jy\;B”(cœøø!ÿA```èÿyI&ä€ß;}GH.}'JêéyHãyH$ˆ0@žØA‚()UJ>CÓx‰Ø@}$Kx}%Kx@˜Hº`zþ,€8`{žÅóxKÿ`?/¸9)y) y*!‘?@‚?=)€‘?Ažÿh8!ÀÃxèêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```|—R#Ëx}8´H­e`Kÿÿ```8!À8`èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`ÿÿN€ €	`|¦,#ûáÿøøø!ÿA‚\|Ÿ#x8€xd,€egé€y$99 8à8À8 Kÿ)`,#@‚08!€ãûxèëáÿø|¦N€ `;àÿÿKÿÿà``|dx`8b”X;àÿÿH¸q`Kÿÿ¼€``99Cÿÿ}	¦9 
}(Jy) Bÿô|¦/©ûAÿÐûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿQAžè} ,8c?Â¥;Þyà,<¢¥è¥y˜U&@>8`@Q&À8€Q&Ä.8¥TxÆ D"gÿ€<¢¥è¥y˜8`@Wæ@>8€SæÀSæÄ.8¥TxÆ D";àT; `è¾8`@8€8À|¿*D"é>8¿8`@8€8À|¥JD",=;ÿ;½ÿÿ@‚ÿÀ8`8!°èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ?Â¥|{x;An;€;Þyé>q*"A‚¤; 9 ‰H0è¾8`@a)8€U&@>Q&À8¥Q&Ä.xÆ D"è¾8`<8€8¥D"/£@ž$Tˆ@>PˆÀPˆÄ.©@8y /‰@ވ;àçH ```y_!x„ AÂ\@Þd8`Kþۍ`è¾8`<8€8¥D"T‰@>.£P‰À9_ÿÿP‰Ä.}$Kx©H8/‰A–ÿ°+Ÿ@ž˜8€ÿÿx„ |è8/Až;œT„„>+œ{œ ´š@žþð``="¥é)yy(çã@‚£át¡Ar¡!pWèÂ>›û{ÿ ™UGÂ>U&Â>™[™;UJ€})Sx˜Û˜ûy) Kÿý°```;œ8€ÿÿ+œx„ T„„>{œ ´š@žþhKÿÿ€```; 9 Kÿþ`<¢¥è¥y˜8`<8€8¥D"/££át@žTŠ@>PŠÀPŠÄ.}DSxxˆ÷ãAâÿ@kÿKÿÿ8`8b–ØHµ	`8`ÿÿKÿý´€```ûáÿø8€|x<¢¥è¥y˜8`<D"/£x‰ Až9 ÿÿy) Wæ@>8`@<¢¥è¥y˜SæÀ8€SæÄ.|ÆKxxÆ D"ëáÿøN€ `liÿÿ/‰€†@žDx„ +„Až|`9 8─99G0HAž0*9J.©‰ @9@–ÿè8`ÿÿN€ ```y	$y.¤}	@P}Bé(=B¥8`ù*y9 =B¥ù*y˜N€ 9  Kÿÿà```|¦ûAÿÐûaÿØ<Â¥û!ÿÈûÿà?b¥û¡ÿèûÁÿð;{yûáÿøøfy˜8`øø!ÿQKþÛE`|zyA‚Ì8 8€H§`<€8 `„@ cÛxKþÜ¥`<¢¥è¥y˜?›8Àÿÿ8€xÆ |{P8¥Øø|@ 8`@D"<¢¥è¥y˜8`<8€8¥D"/£@žtT‰@>P‰ÀP‰Ä.}$Kxx†ÿã@Â\;à1HAÂì@ÖL8`dKþ×õ`è»8`<8€8¥D"T‡@>/£P‡À9?ÿÿy?!P‡Ä.Tä¼x„ .¤Ažÿ´CÓxKÿú=/£@ž˜;;?û=Ëx;Û;ÿ(```8 8€£ëxH¦`|¬é<@ ;½8À9ÿð}^J;Þ0¾ø@yG"}@E,|æE,@žÿÀÙJè»8`@{É"8€U&@>Q&À8¥8Q&Ä.xÆ D"è»WÆ@>8`@SÆÀ8€SÆÄ.8¥8xÆ D"è»8`@8€<À8¥8D"è»8`@8€8À8¥8D"è»8`@8€8À8¥8D"è»<Àú8`@`Æ8€xÆ 8¥D"è»8`@8€8À8¥D";;;¼@>Ëx8 8€ÃóxH¤å`|¬é<@ ;Þ8À9ÿð}Iú;ÿ0½ø@yG"}@E,|æE,@žÿÀùJè»8`@{é"8€U&@>Q&À8¥(Q&Ä.9 xÆ ‘<@D"è»Wæ@>8`@SæÀ8€SæÄ.8¥(xÆ D"è»8`@8€<À8¥(D"è»8`@8€8À8¥(D"è»8`@8€<À8¥(D"è»8`@8€8À8¥( D"è»8`@8€<À€8¥D"9 CÓx‘:8!°èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ /¤@Þý`CÓx8€KþØ%`8!°8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8b†H¯¥`8`Kÿÿx€``#/‰Mž |¦<¢¥è¥y˜ûáÿø8€ûÁÿð|x8À8`@8¥øø!ÿD"<¢¥è¥y˜8`@8€8À8¥D"8`
KþÔA`<¢¥è¥y˜8`@8€8À8¥(D"<¢¥è¥y˜8`@8€8À8¥(D"<¢¥è¥y˜8`@8€8À8¥8D"<¢¥è¥y˜8`@8€8À8¥8D"<¢¥è¥y˜8`<8€8¥TD"/£<Àÿÿ`ÆÿxÆ @žx†ÀBxÆ@ <¢¥è¥y˜?Â¥8`@;Þy8€8¥TD"<`€xc Kÿùm8`
KþÓe`<`KÿùY8`
KþÓQ`<~èc@ < Äóx`¥@ |~KþØ!`9 ãûx8€‘?KþÖ9`8!€èëÁÿðëáÿø|¦N€ €```|¦ûáÿø|yûÿàû¡ÿèûÁÿðøø!ÿqA‚€<¢¥è¥y˜8`<8€8¥(D"/£9 ÿÿy) AžX?Â¥;Þy?¾]@ŠH@Ažh9J8`yJ&ä}R‰(y%á@‚t8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ?Â¥T‡@>;ÞyP‡À?¾P‡Ä.xé ]@ŠH@@žÿ 8!8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8È8¾|žT,èý@ ;ˆãûx} 6,|ÅT,xÆÆ9)ÿü|„3xy% |‡ P}?´H ™`8 8€ƒãxH 5`|¬è¾8ý@8`@8€|À<,8¥(D"=@8!ãûx9)y)`‘=@èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8`ÿÿKÿþÜ€```|¦û¡ÿè|}yûÿàûÁÿðûáÿøøø!ÿqA‚P<¢¥è¥y˜|ž#x8`<8€8¥8D"/£;àÿÿ{ÿ @žTˆ@>PˆÀPˆÄ.y <¢¥è¥y˜8`<8€8¥8D"/£Až´9 ÿÿ;€y) ?â¥9);ÿyy)&ä9=_|L,¤ëx{Å |èL,éJ@ ÿJxçÆ|c;x|jPHŸ9`9 9™?9 ÀG,™?|¬<¢¥è¥y˜8`@8€†ãx8¥8D"Ãóx8!èëÿàë¡ÿèëÁÿðëáÿø|¦N€ `T‡@>;ÿP‡À{ÿ`P‡Ä.Ÿ8@xé AžÿÀ8‡x„`Tœ@>PœÀPœÄ.{œ Kÿÿ$`8`ÿÿKÿÿ˜€```|¦liÿÿûáÿø/‰€†øø!ÿAž(8!€8`ÿÿèëáÿø|¦N€ ```x„ +„Ažœ`9 8─99G0H```*9J.©‰ @9A–ÿ˜@žÿèy	$y.¤}	@P}BéH=¥|©+x8€8 ùHy=B¥|Ã3x|ß3xù*y˜H]`8!€ãûxèëáÿø|¦Kÿñ@9@ Kÿÿ¸€``}€&|¦ûáÿø;åûÿÀûÿàû¡ÿè|¸+x||xûÁÿðúáÿ¸|Þ3x|#xû!ÿÈûAÿÐÿ´‘-ûaÿØøø!ÿAAŠÌ/†Ažô``8‚” 8b™0H©`HY‰`H‰Á``?b.>-ž;B˜Ø;{p; :à;ÿÿÿCÓxÿ´äûxH¨¹`Hµ¡`/ƒAžt/¿Až,A’ÈAŠ@ŽÿÈè}:8€’ûH1`¤ëxƒãxH‰¡`|~yA‚d/žÿÿ@Þ¬;ÿÿÿCÓxÿ´äûxH¨I`Hµ1`/ƒ@žÿ”`8b˜àH¨)`8`ÿÿ8!À聁êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦}’ }‘ } N€ ``¤ëxƒãx“;HXµ`/ƒÿÿ|~xAžÿ(`8b™H§©`ÃóxKÿÿ€``¤ëxƒãx“;HXu`|~xKÿÿ``Ãx8b˜ðH§e`8`ÿÿKÿÿ<```8‚™(8b™0H§A`HWÉ`KÿþH`````8‚™`8b™0H§`Kÿþ`HzÁ`8 |dx8}Hší`Kÿÿ4€	`}€&|¦úáÿ¸ûÿÀ}7Kxû!ÿÈûAÿÐ9 |ú;xûaÿØûÿà||x`û¡ÿèûáÿø8b™h|Û3x‘úÿ }Cx|#xøú¡ÿ¨|¹+x;àúÁÿ°ûÁÿðø!ûA‘!P9 ù!8ù!@H¦±`8 <8€8apH™í`8ÁH8 8€8`KþÅe`/ƒÿþ|jx@žhH³`/ƒAžÔ9?/‰
}?´AžÄKþ́`KþËÙ`KþÌ!`/ƒAÿô8ÁH8 8€8`KþÅ`/ƒÿþ|jxAžÿ /ƒÿÿAžœ‰!M‰LˆáKˆÁJ`ˆ¡IˆH8b™¨‘A¨H¥`8aHH#õ`|lB¦!J}#xxc H ]`/—@Ü/—ÿzå A
$;Á°ÃxÃóx;°H—Q`9p9 ~èº8 ¸8€Ãx™7@H˜½`ÃóxH`.#|vx@’X=Bé*r9@‘A/‰Až
ô/‰Až@:á09 
9@‘Ad}?HP/‰	AÄ9 
‘!`8 ~ä»x8apH˜`=Bé*r/‰AžÀ/‰Až@!+‰A¤}*Kx="ÿÿ9)¬ðyJd}IRª}*J})¦N€ €0DP°```8a°8‚žH”µ`8·8`0KþÞY`8a°H”ù`8 ‘|dx8a°KþÒU`8`ÿ›8!À聁êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿè|¦ëÁÿðëáÿø} N€ €¡`8À8p#ËxKÿú!|x/ŸAœ„=é(r/‰Až¸/‰AžÄ;ÿ+Ÿ@Ý
¼‰!°/‰@ž=?â;ÿpéHr/ŠAž0/ŠAž$€ÁdIÓxhÛx8áh¥ëx„ãx8apHl5`!|x/‰AžXèaªKþz™`/ŸAŒ/ŸÿÿAÞ
$/ŸÿþAÞx/ŸÿýAÞ /ŸÿüAÞ
Ì/ŸÿûAÞ
x/ŸÿúAÞà/ŸÿùAÞŒ/ŸÿøAÞ8/Ÿÿ÷AÞä9?+‰@€/ŸÿØAÞ(/Ÿÿ×AÞÐ/ŸÿÖãûx@þþ”€Át€¡p`8a°8‚žPH¡e`8·8`0Kþܙ`8a°H“9`8 ‘|dx8a°KþЕ`8`ÿKÿþ@`€¡`8À8p#ËxKÿø¡|x/Ÿ@œþ„/ŸÿÿAž
ì=Bé*r/‰Až„/‰@ž(8at8°H~ù``8°8bš€H¡Å`/Ÿÿþ@žþP€¡„`8a°8‚š T¨>x§Æ"x¦†"x¥FH •`8·8`0KþÛÉ`8a°H’i`8 ‘|dx8a°KþÏÅ`èaªKþxù`8`ÿšKÿýd``8 8P8aHH–%`/£@žì9 ÿÿ‘!„€¡`8p#ËxHC`|xKÿý|;Á88 Äóx8a8H•á`/£èaªAž°88Hy‰`;à=é(r/‰@žýP8 8P~ã»xH•¡`/£@ž
,8 8P8aH•…`/£@žԀapH*`=Bé*r/‰@žþ„€p`8bšXT‡>x†Æ"x…†"x„FH M`Kÿþˆ;Á88 Äóx8a H•!`/£Až‰!°/‰@žô9 ‘!€¡`8À8p#ËxKÿö|xKÿül8 ~ä»x‘!`8apH“á`=Bé*r/‰@žûH8 8P~ã»xH”­`/£Ažû48 8P8aH”‘`/£Ažû‰!°/‰Ažû8 88a„;àH“u`9 ‘!Kÿþ˜`åVp8¨8b›xHŸQ`ãûxKÿû\8 ÿÃx8a¨?âH‘Q`=9 ;ÿpéHr™!§/Š@žû؀¡„`8¨8b›T¨>x§Æ"x¦†"x¥FHží`="€ÁdhÛx8áh¥ëxéIr„ãxIÓx8apHgá`!|x/‰@žû°èaªHR`Kÿû :¡Ð8Àd~¥«x8€ÃóxHõ``~£«x8‚šH“á`/£@ž(8€Ãóx9 ‘!Ha`=:ÖÿÿzÖ é(r|~x/‰Až€/‰.6:á0AžàA’ùT:¡Ð8Àd~¥«x8€ÃóxHu`‰!Ð/‰@žô9 
‘!`Ãóx8€Hñ`+–|~xAÞ@8Àd~¥«x8€H1`‰!Ð/‰@žà9 ‘!d8€ÃóxH­`é!bKÿøÔ`~£«x8‚š(H’ñ`/£@žœ9 Ãóx8€:Öÿÿ‘!Hm`9 =zÖ ‘(p|~x.6AÒ¬:¡h8Àd~¥«x8€ÃóxH•`8 ~£«xHx`/£@ž$‰!h8 8€8a /‰@ž¸H`:öÿÿÃóx8€z÷ Hå`/·|~xAžP8ÀdÃx8€ÃóxH!`‰!°
Ãx9//©@žH*/©Až+‰\@žÿð™
Kÿÿè;°8 ¸8€ÃxH`9 :á0‘!9 
‘!`9 ‘!dKÿ÷˜`~£«x8‚š H‘¡`/£@žþ˜8€Ãóx9 KÿýÀ`8¨8b›PHœ`8aˆ8°Hy``8°8b‡ H›á`é_Kÿø¤8 
8€~£«xH”Å`|c´/ƒad@œþKÿþ;Á88 Äóx8a8H‰`/£@ž¤8 Äóx8a Hm`/£Ažùx8 8ˆ8a HQ`/£Ažù\8 8 8aˆHE`KÿùD``8€;àHsÙ`Hná`8 |dx8atH
`Kÿú88 
8€~£«xH“õ`|c´/ƒa`@œüøKÿüì=Bé*r9@‘A/‰Až/‰Ažý„:á0Kÿü .6AÒÈ:¡h8Àd~¥«x8€ÃóxH`8~£«xHå`/£@ž$‰!h8 8€8a/‰@ž8HŽ
`:–ÿÿÃóx8€z” HU`/´|~xAžl8ÀdÃx8€ÃóxH‘`‰!°
Ãx9//©@žH*/©Ažô+‰\@žÿð™
Kÿÿè8 8€8a:ÀH…`.69 ™!°:á08 8€~ã»xHa`8 8€8aHHM`Kÿûx8 8€8a :ÀH1`.69 ™!°8 8€8a8H`8 8€8aP:á0HŒù`Kÿû$8 8H8a„H1`Kÿø8 8 8aˆH`9 ‘!KÿøÃóx8€H
`+”|~xAÞÿ,8Àd~¥«x8€:á0HI`~ä»x~£«xH)`/£@ž$‰!h8 8€~ã»x/‰@žŒHŒQ`Ãóx8€H¡`94ÿþy) /©|~xAÞþÐ8Àd~¥«x8€ÃóxHÕ`8H~£«xHµ`/£@žH‰!h8 8€8aH/‰Až(H‹Ý`Kÿú`8b™ðH˜y`8`ÿùKÿô$H‹¹`Ãóx8€H	`|~xKÿùÐ8 8t8a8HŒÍ`/£AžüH8 888atH‹Á`Kÿü08 8„8aHŒ™`/£Až÷8 88a„H‹`Kÿ÷Ãóx8€H‰`+—|~xAÞýü8Àd~¥«x8€HÉ`88~£«xHrI`/£@ž$‰!h8 8€8a8/‰@žàHŠÑ`Ãóx8€H!`97ÿþy) /©|~xAÞý 8Àd~¥«x8€ÃóxHU`8P~£«xHqÕ`/£@ž4‰!h8 8€8aP/‰AžHŠ]`:á0Kÿø„HŠM`Ãóx8€H`:á0|~xKÿø`8 8p~ã»xH‹]`/£AžõÀ8 ~ä»x8apHŠQ`Kÿõ¨H‰õ`KÿÿHH‰é`~׳xKÿùlH‰Ù`~Ô³xKÿûìH‰É`Kÿýœ`8a°8‚™€H†‘`8·8`0KþÐ5`8a°H†Õ`8 ‘|dx8a°KþÄ1`8`ÿœKÿñÜ`8`08‚› KþÏù`8`ÿ™KÿñÀ`8a°8‚šàH†)`8·8`0KþÏÍ`8a°H†m`8 ‘|dx8a°KþÃÉ`èaªKþlý`8`ÿ•Kÿñh`8a°8‚œHH…Ñ`8·8`0KþÏu`8a°H†`8 ‘|dx8a°KþÃq`8`ÿ’Kÿñ`8a°8‚œ H……`8·8`0KþÏ)`8a°H…É`8 ‘|dx8a°KþÃ%`8`ÿ“KÿðÐ`8¡¨8‚œ8a°H“¥`8·8`0	KþÎÙ`8a°H…y`8 ‘|dx8a°KþÂÕ`8`ÿ”Kÿð€`8Á¨¥ëx8‚›À8a°H“Q`8·8`0Kþ΅`8a°H…%`8 ‘|dx8a°Kþ`8`ÿ˜Kÿð,`8a°8‚š0H„•`8·8`0KþÎ9`8a°H„Ù`8 ‘|dx8a°KþÂ5`èaªKþki`8`ÿ›KÿïԀ¡l`8a°8‚žH’©`8·8`0KþÍÝ`8a°H„}`8 ‘|dx8a°KþÁÙ`8`ÿŽKÿ¡h`8a°8‚ÐH’Y`8·8`0Kþ͍`8a°H„-`8 ‘|dx8a°KþÁ‰`8`ÿKÿï4;Á°`8‚ Ãóx;ÿH’`+ŸAd="ÿÿ9)¾l{ÿˆÃóx}Iúª}*J})¦N€ àÀL `8a°8‚œèHƒE`8·8`0KþÌé`8a°Hƒ‰`8 ‘|dx8a°KþÀå`8`ÿ‹Kÿî`8a°8‚œ¸H‚ù`8·8`0Kþ̝`8a°Hƒ=`8 ‘|dx8a°KþÀ™`8`ÿŒKÿîD`8a°8‚œ˜H‚­`8·8`0KþÌQ`8a°H‚ñ`8 ‘|dx8a°KþÀM`8`ÿKÿíø`8a°8‚œpH‚a`8·8`0KþÌ`8a°H‚¥`8 ‘|dx8a°KþÀ`8`ÿ‘Kÿí¬é!bKÿìÈH‚y``8‚h|~Hu`ÃóxH‚Y``8‚8|~HU`8·8`0Kþˉ`ÃóxH‚)`8 ‘|dxÃóxKþ¿…`8`ÿ—Kÿí0H‚``8‚€|~H`KÿÿŒHå``8‚˜|~Há`KÿÿlHÅ``8‚P|~HÁ`KÿÿLH¥``8‚@|~H¡`Kÿÿ,ÃóxH``8‚¸|~H}`Kÿÿ€`|¦ûAÿÐûaÿØ|Ú3xûÿàû¡ÿè|}x|œ#xûÁÿðûáÿøxþ |»+xû!ÿÈÃóxøø!þAH‹A`|yAÂ,¤ëxÅóxH‚)``8 8‚žøãûxH1`|}y@‚´8€[ãûxH‰`|~yA‚‰>/‰[Ažð8€.ãûxHe`|~yAÂ8€.8~HM`/£AÞÃóx8€/H5`|~yA¨8Ÿ9@}$ðP8ap})´}DI®Hí`8À8¡p8pCÓxH)µ`/£Až8„ãx8apHlM`8žcÛxH­`ãûxHñ`8!À£ëxèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``8€]H~}`,#A}>P8€/Ãóx}:´H~]`|yyAÂоѮ„ãx8~Hi‘`/£Až,8™cÛxH	`ãûxHM`8!À£ëxèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``äûx8bŸ; ÿÿHŽ!`ãûxHŒõ`Kÿÿ```; ÿÿ8bŸ°Hõ`Kÿþä`; ÿÿ8bžÈHÝ`KÿþÌ`äûx8bŸ0; ÿÿHÁ`ãûxHŒ•`Kÿþ¤`äûx8bŸx; ÿÿH™`ãûxHŒm`Kÿþ|`äûx8bŸ˜; ÿÿHq`ãûxHŒE`KÿþT`äûx8bŸP; ÿÿHI`ãûxHŒ`Kÿþ,`äûx8bŸ; ÿÿH!`ãûxH‹õ`Kÿþ€```|¦ûÁÿðûáÿø|~xû¡ÿè|Ÿ#x8 8€øø!ý8a°H€u`/ŸAœ{å Äóx8a°H€©`9!p8a°éú9 ™?@H
`9 
|y‘!¼A‚Ø+Ÿ8À@8¡p8€8a°Až HÍ`8°8apH
­`/£AžÐ8À@8¡p8€8a°H`8°8apH
}`/£Ažp8€8a°H`|}x8À@8¡p8€£ëxHY`8¡À8´8apHe`/£Až(8€£ëxHÍ`+Ÿ|~x@ž¬``8 <8€8apHE``8b¡(H‹…`8ÁÈ8 8€8`Kþª­`/ƒÿÿ|xAÞ /ŸÿþAž‰!͉̈áˈÁÊ`ˆ¡ɈÈ8b x“á¨H‹-`8aÈH	¡`!´/‰@ž`8À8 8p8`Kÿá`|c4/ƒÿÿAÞȀapHe`€p`8b ÀT‡>x†Æ"x…†"x„FHŠÁ`H¹`|~y@‚p8°8 8a„H~`€„`8b¡T‡>x†Æ"x…†"x„FHŠy`€„ãûxH¹`Kþ°ñ`=@ffaJfg}#P–|cþp})p|cHP!¼|cIÖ|c´Kþ°%`H$``H	1`Hy`/£AžKþ°I`/ƒãûxAÿØ`8b‰€H‰í`èaªKþa`8`ÿÿ8!ðèë¡ÿèëÁÿðëáÿø|¦N€ ``8 8´8apH}¥`€a¸/£@ž4€aÀ/£AžHe`€apHù`€p`8b ÀT‡>x†Æ"x…†"x„FH‰U`HM`|~yA‚þ˜`8b àH‰5``WÇ>{ÆÆ"{ņ"{ÄF"8b ðH‰`Kÿþd```8b¡Hˆù`èaªKþ``8!ð8`èë¡ÿèëÁÿðëáÿø|¦N€ `H1`8°8apH`/£@žý`8bŸÈHˆ™`8!ð8`ÿÿèë¡ÿèëÁÿðëáÿø|¦N€ 8€8a°Hy`8À@8¡p8€;ßÿÿ|}xH½`8°8apH`{ß /£AÞÿŒ£ëx8€H1`+ž|}xAþüpKÿü``8À@8¡p8€He`8¸8apHE`/£Ažÿ8Ãóx8€HÝ`+Ÿ|~xAžü8À@8¡p8€H`8 
8€ÃóxH€™`a¼Kÿûì``8a´H`aÀKÿýì```H`KÿýÈ`8b HH‡M`8`ÿ›Kÿýl`8b  H‡5`8`ÿœKÿýT`8b ˜H‡`èaªKþ^±`8`ÿÿKÿý0€`,$9@A‚P`‰#+‰,Až/©Až0#*‰,/©@–ÿð9*8c„H@y* @žÿÌN€ `8`N€ N€ ``|jx8```‰*+‰,Až,/©@žN€ ``Až0**‰,/©@–ÿð5JAÂ8cxc Kÿÿ¼``N€ N€ ```‰#+‰,AžH/©Až@|jx8`H````*8cxc *‰,/©M– @žÿèN€ 8`N€ ```|¦,$ûÁÿðûáÿø|¾+xøø!ÿA‚L9@```‰#+‰,Až/©Až°#*‰,/©@–ÿð9*8c„H@y* @žÿÌ/£Aބ‰#+‰,Až”/©AžŒ|jx;àHAž*;ÿ{ÿ *‰,/©@–ÿè|dx|Å3xÃóxHvù`/£Až,9 8!€Ãóx}>ù®èëÁÿðëáÿø|¦N€ `8!€8`èëÁÿðëáÿø|¦N€ ;àKÿÿœ€}€&|¦úáÿ¸ûÿÀ|·+xû!ÿÈûAÿÐ; ;@ûaÿØûÿà`;„ÿÿû¡ÿèûáÿø; |x‘úÁÿ°.%;b‡@øûÁÿð;ÿÿø!ÿ1ˆ/£Až+Až,Hz‰`/£AždÛxãûxHv¡`|vyA‚TdÛxãûxHv‰`|P|~4+ž	{Þ AàäûxÅóx8apÿòHu½`}!ò›)p8 
8€8apH|`+ƒÿA¤œ|/º;½{½ ‰?i).})4U)Ù~ÿJAžÿ@;ÿ8 	äûx8apHuY`8 
8€›!y8apH|!`|~x8apHt`9>ÿÿÞ´+‰ÿA(A’ä#Þ ;@ð0“×KÿþÔ```8`8!Ð聁êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦} N€ ```8€\ãûxHr)`|~yA‚Œ8€\ãûxHr`|P|~4+ž	{Þ AÿxäûxÅóx8apÿòHtU`}!ò;@šÉpKÿþ”```;@Kÿþ``k£|c4TcÙ~|cÐ|c´Kÿÿ ``äûx8 	8apHsõ`8ap›ÁyHrµ`ÿKÿþ,€
``8 Kÿý,```|¦|dy8 øø!ÿ‘A‚,<b®8c¹¸Hua`8!pè|¦N€ ``<b®8€8c¹¸Htå`8!pè|¦N€ €<b®8c¹¸N€ ``|¦ûÿàû¡ÿè?¢®ûÁÿðûáÿø;½¹¸||x;Ý8 î8€Ãóxøø!ÿaHti`8À8 îÄóxƒãxKþ¢`,#A‚„/ƒ
x @H`8 8‚¡PÃóxHue`/£@žˆ="®¡)¹Ì/‰Ažèm*ÿÿ/Š†ÝAž\/‰Až8! 8`ÿÿèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8! 8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```<‚8 8„xÃóxHtÁ`/£Ažÿ`8 ¤ëxÃóxHt¥`/£AžÿD|$x9 338 Ãóxµ$pHt`/£@žÿDKÿÿ```8¿ÿò8x¥ ƒãxHq`8! èëÿàë¡ÿèëÁÿð|c´ëáÿø|¦N€ `8¿ÿò8x¥ ƒãxH
ñ`8! èëÿàë¡ÿèëÁÿð|c´ëáÿø|¦N€ `8¿ÿò8x¥ ƒãxHRÁ`8! èëÿàë¡ÿèëÁÿð|c´ëáÿø|¦N€ €``|¦8Àøø!ÿ‘Kþ¡Q`8!pè|¦N€ €```|¦ûÁÿðûáÿø|©+x|Þ3x|x8 8cøø!ÿ°ƒ}$KxHr1`Äóx8 ãûxHr`8!€èëÁÿðëáÿø|¦N€ €|¦9 û¡ÿèûÁÿð=B®ûáÿø?¢®;½¿°;À‘*¿°=B®;ý;½<‘*¿´=B®øø!ÿq‘*¿¸``“ßÿüãûx8 ;ÿ8€Hq=`¿è@“ßÿô“ßÿø@žÿØ="¯9)¸=Bÿÿ8!9JxØùIèë¡ÿèëÁÿðëáÿø|¦N€ €``9%+©îA”$/©Ažœ+‰Ažd9
9 }	¦9Dÿþ±$
9 ``¥
})BBÿø|¦û¡ÿèûÁÿðy*„ûáÿøúÿ y) |#xú¡ÿ¨úÁÿ°}*J|~xúáÿ¸ûÿÀy*„|¿+xû!ÿÈûAÿÐ})RøûaÿØ})Høûÿàø!ÿ±$
‰	/ˆAž胄/œÿÿAžü=®ûÄ?b®;{¿°Š@ø/ŠAž =B®JûÀŠàAž`;<})âx})@8/‰@ž ;€û‰8@Až°y(M¤y:]$}HÐP<ÀÌÌ}[R`ÆÌ́JŠà@žT`;}ÐPXB`;::¢¡X8 8•#ËxHp½`/£@ž|<⮀翸H\JŠàAžÿ¸9)}I0UJèþUH<UJ8}HR}*HP‰8@y) y(M¤y:]$}HÐP}[R@žÿÀ?®;¿¼`;@:¢¡Xxé]$xùM¤9HP8 *~ØÊ8€:Ö
;9~óx8ÊHná`Kÿú`9@9 >‚®‚”û¼8 ±Y9@±9
|dx±98y™Y9@™YHné`’™~¤«x8 8yHnÑ`“™"Kÿùµ`~¦«x8€|ex~óxKÿüM`8 *~ijxÃóxKÿûù`/º@žÄ=®¿¸<àÌÌ<®€Æ¿´`çÌÍ8¨}E8UJèþUI<UJ8})R=B®})(P†H‘*¿¸Ažy	M¤y]$})@P8 [J|xJ9 8€“š8c{ÿ ‘:HmÅ`Kÿøý`8Õ8€|ex8{< Kÿû•`åûx¤ëx8{<.Hmá`9?=®_Óx‘(ÀKþ Y`KþŸ±`H`KþŸñ`/ƒ@ÃóxKÿø­`?/‰@žÿÜ8`H”="®)û¼‘$Kÿüd?b®;{¿°="®)¿¸9`;"¡Xy:M¤y)]$}:HPHJKÿø5`;š
&Ëx8€{ÿ |exƒãxKÿúÅ`åûx¤ëx8zHm`8¿„ãx|¥´ÃóxKÿúY`8!ðèêÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿð|¦ëáÿøN€ ="®)û¼})âx})@8/‰Ažÿ4;<‰àAž°="®)¿´<⮀翸?‚®ƒœûȉ8@Ažýy(M¤y&]$}H0P< ÌÌ}[R`¥Ì́JŠà@ž(``;}0PXBKÿüPJŠàAžÿè9)}I(UJèþUH<UJ8}HR}*HP‰8@y) y(M¤y&]$}H0P}[R@žÿÀKÿü€``="®)¿¸9?";9€y*M¤y)]$}*HPHJKÿþx``=B®Jû¼="®)ûÀ‘D‘$Kÿúˆ`9 8 8ap±$8€Hk-`¡=‰]	ƒy'!™Ay‘|9@“€±!rA‚89 H````}J9)‡H@y) ¡}JBAÿè9
9!n}	¦``¥	}JBBÿøyI„yJ })Ry*„})RU)>}*HøqHÿÿ@‚±=Kÿú\8`ÿþKÿýÔ±KÿúL8Æ|æ8TéèþU*<U)8}*J})0P‘;KÿüT8`ÿÿN€ €="®iû¼Kÿøˆ``<b®€cû¼N€ ``=@ÿ=# aJÿÿ‰P@A`=®<âxj†bTiÂ>hûÀ9™€9<♝9^<♝‚=<â™Hƒ=B˜g…™*„N€ ```|¦9 <â®<b8 8€ÿ8c€‘'ûÀøø!ÿ‘HiY`8!pè|¦N€ €`<b®€cûÀN€ ``="®iûÈKÿ÷h``<b®€cûÈN€ ``="®iûÄKÿ÷(``<b®€cûÄN€ ``‰C}It/‰@<`ÿxc N€ `iI€<`ÿÿ+‰?xc L 9J@UJ>+Š |p&Tcïþ|cÐTc.N€ 9@E9 °ƒ˜£	Ãã™C9@±#±#±#
™C9@ÿÿ™CN€ ``+…@Ì|¦û¡ÿèûÁÿð|}xûáÿøûÿÀ|ž#xû!ÿÈûAÿÐûaÿØûÿàøø!ÿQ="®)ûÀ|?x€Ä/©Až ‰0@Až$/†ÿÿAž="®)û¼/©Až‰0@@ž9
9  þ
}	¦9^ÿþ±>
9 ``¥
})BBÿøy*„y) }*Jy*„})R})HøU)>‡H@ž¸¡>q*ÿ@‚èy*Ÿã@‚Љ>	/‰Ažä/‰Ažœ/‰@žˆ‰^£~/Š{h AžÈ/ŠAžÔ/Š@ž¼¡>m*ÿÿ/ŠÔv@žT¡>/‰@žH=®>H¿°ŠH@ž4/©Až,9 8`‘(¿°Hx`=ÿ=F aÿÿŠ@@AþÔ8?°8`ÿÿèëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``="®¡)Ì¡?‚®;œ¿°‰@Až88`8?°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ="®‰)щ	‰@@žÿ¼<B$‰@@žÿ¬<B(‰0@žÿ  ¾yJ$;|B8j8ž|{8¥ÿìx¥ HeÑ`¡>y*Ÿã@‚ÿl¡^U)8~Ûx})R±<BKÿþ\` ¾8ž£ëx8¥ÿìx¥ H
`Kÿÿ4 ¾<b®Äóx8cÈHeq`8`Kÿÿ ž8~8„ÿì|„´H‘`Kÿþø8¨ÿìèá|:x|ª´;9J#; yJäx¥ }JÐ8ž|áQj8àE;p^˜áp8à8a„±9ÿÿ˜ü™<	‘\³³™“<³<
HdÕ`›³<9!‚8áÞ9@``¥	§H@}JB@žÿôyI„yJ })ReÛxy*„„ãx})R£ëx})Hø±<KÿóIé!8`ù:AÓxKÿþ8`ÿÿN€ ‰>%/‰Až,/‰@žýôˆ¾8ˆÿ|8~0x„ Hõ`8`Kÿý؈¾8ˆÿ|8~0x„ Hu`8`Kÿý¸€``+…@œ¡$/‰@ž|¦úÁÿ°úáÿ¸ûÿÀû!ÿÈûAÿÐûaÿØûÿàû¡ÿèûÁÿðûáÿøøø!ÿA£d/›@žäD="®)û¼?¢®;½¿°‰P@žÈ£ä|ž#x||x/ŸAžð/Ÿ@ž¬KÿîU`8 8žHdE`/£@žÐ€þ/§Až€=€Ý‰0@Ažpy*M¤y?]$êøP< ÌÌ}]ú`¥Ì́JŠ8@žHāJŠ8Až¸9)}I(UJèþUH<UJ8}HR}*HP‰0@y) y*M¤y?]$êøP}]ú@žÿÀ8!À8`ÿÿèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ /ª@žL8`8!ÀèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```ƒ]:ý8€‚Þ8 *;{IM¤{Z]$IÐP7Ò;Z;9
×Ò#ËxHa©`Kÿìá`Ãx8€|ex#ËxKÿïy`KÿìÁ`9 ³þ
³~8 ƒ½<™>9 |dx8~™>9 ±>Ha™`“¾8 Ãx8~Ha`’Þ"8 *$ËxƒãxKÿîÉ`8`Kÿþè``8`ÿÿN€ ``}ú`;{8 8‚¡`cÛxHb`|zy@‚þ`ýú8 8žcÛxHa	`?/‰Ažþ€;Ý< 8 dÛxÃóxH`å`è½BÄóxƒãxKÿî1`“_“_KÿþH€
/¤=®ˆ¿°Mž |¦ûáÿø8àE|‰#x99@|x8 T8€*øø!ÿ˜áp8à‘!€9 8aŒ±t±v˜áq8àp™!„9 Ôv‘A|±Az°ár8àÿÿ±!ˆ9 ™…±A†˜áx8à±!Š˜áyH_É`9.9A‚}	¦9 ¥
})BBÿøy*„y) }*J8py*„8 p})Rãûx})Hø±!†Kÿî8!ðèëáÿø|¦N€ €``<b®€c¿°N€ ``|¦+…øø!ÿ‘@°¡$|Š#x/‰"Ažà+‰"@X/‰ÑAž°m(ÿÿ/ˆ€@ž„¡$/‰5@žx8…ÿø8j|„´H
É`8!pè|ct|¦N€ ```/‰D@ž<¡$/‰C@ž08¥ÿø8„|¥´H±`8!pè|¦N€ ``8!p8`ÿÿè|¦N€ ```|¥´H-
`8!pè|ct|¦N€ 8…ÿø8j|„´HLµ`8!pè|ct|¦N€ €```+„L ¡#/‰ÑLž |¦|£+xøø!ÿ‘H3
`8!pè|¦N€ €``9 °£°Ã°ƒ±#N€ ```8`ÿÿN€ ```N€ |¦ûaÿØûÿà|{xû¡ÿèûÁÿð|½+x|¾+xûáÿø;€|Ÿ#xøø!ÿa```‰_}ðPäûxÃóx}Jt}I´}R8©U)2/‰Àx¥ /*.¨þAž`AšxA•´H]`‰?})t9)ÿJÞJ}ðPäûx‰_Ãóx}Jt}I´}R8©U)2/‰Àx¥ /*.¨þ@žÿ¨ ;Ÿx ûúKÿÿ\``/¼™^8Ažƒãx8! èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```£ëx8‚” HXå`8! 8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €``|¦úáÿ¸ûaÿØ|wxûÿàûÁÿð|¼+x|ƒ#xúÁÿ°ûÿÀ|›#xû!ÿÈûAÿÐû¡ÿèûáÿøøø!ÿ1HX½`+œ;ÃAž\;0; (:À(8c?â¯;ÿÀ£ê{¥ 8€ãûx; H[=`9@4}?Â;IdÛx}_Ã.9@³)CÓx;Þ±IWÞ>HWé`cÛxHX=`+œ8cxi }ZJAžä98 8À5`¥€}K.³*Äóx|²Kÿý!`8 8Ÿø8apHZý`H:µ`8áp8 Äóx|fxãûxH;™`øA(="¯9)¸¥´äûx~ã»xé)éIéi}I¦èIN€!èA(8!ÐèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `;; :ÀKÿþ¨:K.³*8 Äóx|²`¥€8À5KÿüE`<⯀ç
°|–ò8À8 T„>ãûxKÿñ‘`Kÿÿ8€
``/…Až="¯i
°8`N€ ``|¦<b¯8 8c
¸øø!ÿ‘HY¹`8!p8`è|¦N€ €|¦9 úÁÿ°ûAÿÐûaÿØûÿà`|{xû¡ÿèûÁÿð?¯:” ûáÿøúáÿ¸;ÞÀ|Ÿ#xûÿÀû!ÿÈ;¾~ijxøø!ÿA£ëx|º+x™%|Ü3xHU¹``ãûx8‚¡hHWÕ`/£Až`ãûx8‚¡pHW¹`;ã`ãûx;"‚$ËxHW`/£Ažãûx$ËxHW…`;ã`ãûx;"¡x$ËxHWi`/£Ažü$ËxãûxHWQ``;"¡€|P$ËxTx>ãûxHW1`/£Ažô$ËxãûxHW`|PTc>˜@@|xxW>98ÿÿ+‰þAÀÃxäûx£ëxÂHV=`9 ;>~ijx#Ëx™8HT‘`£ëxHTå`+ƒÿAØ;þ:þ	'Ëxªëx`?;}DSxÃx*‰.ªøPW¨>{¥ /©+?A–@ž(™A™|HU¹`‰?|øê~ê»x/‰AžÀ:÷Kÿÿ¨``;à8b¡øHce`8!ÀãûxèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ~ijx#ËxHS©``;à8b¢Hc`8!ÀãûxèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ =B¯J
°™'/ŠAžÀ+œAž$‘>9 =B¯;¾ ~ijx£ëx™*Ü;HS`£ëxHSi`…ãx/£Ažˆ¤ëxcÛxKÿúMKþˆé`KþˆA`H8`>/‰AžAš”‰>/‰AžA–ÔKþˆa`/ƒ@DcÛxKÿá`ˆ~*œ+|uA‚ÿ´;àKÿþð``$ËxcÛxKÿùÉKÿÿ|;ÿÿ{!@‚ÿL`8€8b¡ÐHa¹`KÿþT```ãûx`HR‰`;"¡€$ËxTx>ãûxHTA`/£@žýãûxHR]`Tc>Kÿý```8ž8 CÓx;àHUA`8!ÀãûxèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ````;à8b¡ˆH`å`8!ÀãûxèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8 8žCÓx;àHT‘`Kÿý,8 8€8~HT)`KÿýЀ
¡#/‰4Až8`N€ ```¡CUI(m(ÿÿ/ˆ€@žÿÜyI!@‚È|¦ûÁÿðûáÿø;ÃûÿÀû!ÿÈ|xûAÿÐûaÿØûÿàû¡ÿèøø!ÿQ¡#/‰Až¨?‚¯;œà; H`¡?‰P@ˆÄóx…ãxãûxKÿö)9]}]´,#;Ã@‚ÿÔ8`ÿÿ8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```9 =B¯8`™*ÜN€ ```¡?/‰Až¼?b¯; ;{À;[ ;›	 ;;XÓxH`¡?9]}]´‰P@„Äóx…ãxãûxKÿõa|~yA‚ÿH¡>/‰@žÿÌ$ËxƒãxHNÑ`/£@žT¡>/‰Ažh/‰Až /‰Ažx¡>9)
ÞJKÿÿˆ`8 8ž
8{HR…`8`KÿþÜ`DÓxƒãxHNi`/£AžÿœKÿÿ´`Ãx8ž
ãûxKÿôµ/£@žÿ˜Kÿþ˜`>
=B¯8`‘*ØKÿþ„€|¦9 úÿ úÁÿ°úáÿ¸ûÿÀ:…`û!ÿÈûaÿØ:¢Xz› ûÿàû¡ÿè|#x`ûÁÿðûáÿø|~x`øúAÿ8b¢0; úaÿ˜ú¡ÿ¨:à;¢ˆûAÿÐø!ÿ!;€‘$|?xH]`="¯d´~óxûÉàH]u`/»Až˜é!|:x8 V8€ù!þ¡;ÁpÃóxHPù`€ýÃóx8À8 8€HKÿè­`8ÀC8 D8a„8€4Kÿó%`›>›>Ãx8aøšþHM‰`KÿÛá`8 |dx8a¨HPÝ`è}: ¾ÄóxKÿߙ`é!8 Ð8€ù:AÓxé!ù!ø1;Áp:aÃóx:¡¶HPE`Kþƒ`Kþ‚u````è}:8À8 ÐÄóxKþ~A`/£AžH þ³ž9>9@¥	³H@}JB@žÿôyI„yJ }IRyI„}JJ}JPøUJ>‡PAž°Kþ‚M`/ƒAÿé!;{ÿÿ~óx{{ d´ù:AÓxH[á`/»@žþp`z„ 8b¢`:@ÿÿH[Á`8?à~C“xèêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿà|¦ë¡ÿèëÁÿðëáÿøN€ ```‰>/‰@žÿL¡>$/‰D@žÿ@¡>"/‰C@žÿ4‰>*/‰@žÿ(KÿÚ!`~¤«x8 HP`8ž*|ry@‚ÿ<b¯ècà/£Až8 ¸HNù`>>^:8ž–8}8‘=‘]HKi`é!`8b¢ù:AÓxHZ½`Kÿþü€`|¦ûaÿØûÿà;eû¡ÿèûÁÿð{{ |#xûáÿø#åÿþ|Ü3x|~xøø!ûa€„}#Ø®ÿ"éøP{ÿ |Ÿ Påûx|ƒ"8apHNE`‰<€}åûx8p|cJ|P|~HN!`€}ˆ¼8œ|P|~HN`}^Ø®‰<}*J}>Ù®‰<]}*J‘=8! èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûaÿØûÿà|Û3xû¡ÿèûáÿø|œ#x|xûAÿÐûÁÿð|½+xøø!ÿa€ä/§Ažd‰C9 +Šÿ@ž,H°```}	Cx‡H@@8}_H®+ŠÿAžŒ/ª9	y 9)AžÿØ}_@®}*Jy) ‡H@AÿÐ/»;ÀAžX}ð®]ò/ˆAž8+ˆÿ@ž€8! 8`èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ;Þ{Þ žØ@Aœÿ°8! còx|c4èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿøTcÙ~|ct|¦N€ ``€|/£Ažp‰?ˆH@Až´+‰ÿAž\8 H,``}ESxƒ(@@@}?(®ˆH@*‰ÿAžˆA–,/©9EyJ 8¥AžÿÐ}?P®|©*x¥ ƒ(@AÿȈºDÓx|8¥HKÙ`<‰Z9)})R‘<9>;Þy) }=H®Éò{Þ Kÿþü‘<Kÿþœ8 `FÓx„ãxãûxKÿüåKÿÿÄ€|¦ûÿàû¡ÿè|½+xûÁÿðúáÿ¸|~x8 ûÿÀû!ÿÈ|œ#x£ëxûAÿÐûaÿØ8€ûáÿøøø!ÿAHJÙ`<‚8 8„ˆÃóxHL`/£@ž„+œ;à@ˆ;`;;@;=}>ø®}^ú}I®}>ø®/‰4Až€```+‰4@Œ/‰BAžô+‰B@/‰]Až/‰ÿAž¼/‰CAžt9?;ÿy) }>H®ÿJ{ÿ Ÿà@Aœÿ8!Àƒúx|ctèêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèxcтëÁÿðëáÿø|¦N€ /‰Až<+‰AD/‰Až/‰@žÿ„™=9?;ÿy) J‘]}>H®éú{ÿ H|``/‰Ažl/‰2@žÿDJ9?;ÿy) ‘]}>H®éú{ÿ H@```/‰5Až\/‰6@žÿJ9?;ÿy) ‘]}>H®éú{ÿ Ÿà@@œþü}>ø®}^ú}I®}>ø®/‰4@žþ”9_9?yH y) }@®™}>H®êJ{ÿ Kÿÿ¼``:ÿ8Ÿz÷ |ž"#Ëx;ÿ|¾¸®HI`}>¸®}=J›I}>¸®éú{ÿ Kÿÿt8!À8`èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``9?9_y) yJ ;ÿ}>H®}^P®{ÿ U)@.})Sx±=Kÿÿ›}9?;ÿy) J‘]}>H®éú{ÿ KÿþÜ``9_yI }H®9(ÿÿ+‰A¬™9?y) }>H®êJ{ÿ Kÿþ ```;ÿ{ÿ Kÿþˆ`›}9?;ÿy) J‘]}>H®éú{ÿ Kÿþ\``:ÿ8Ÿz÷ |ž"Ãx;ÿ|¾¸®HG¥`}>¸®}=J›I}>¸®éú{ÿ Kÿþ8!À8`èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €	```|¦û¡ÿèûÁÿð?¢¯ûáÿø|~x;½è<‚8 8„ˆ8}øø!ÿqHFý`‰>8`+‰A98`}
H6qGš@‚$8!èë¡ÿèëÁÿðëáÿø|¦N€ `‰^8à5™
;ý™=˜ý/ªAž9 4™™];ý™=‰>2/‰Až 9 2;ÿ™?ÿú9 ™?ÿû>‘?ÿü‰>6/‰@žÜ98þÿ}	¦|ê;x9 `
}(JU)>Bÿô/©Až@™?9 79@;ÿ™?ÿþ`'9
/‰Až™_;ÿU
>+Š@žÿà‰>B/‰@žÌ‰>C/‰@žx‰>]/‰Až$9@]9 ;ÿ™_ÿü9@™?ÿþ™?ÿÿ™_ÿý9 ÿÿ8!8`™?èë¡ÿèëÁÿðëáÿø|¦N€ 9 6;ÿ™?ÿú9 ™?ÿû>‘?ÿüKÿÿ9 C;¾£ëx™?HB1`¤ëx8cTi>8}%Kx™?HE!`‰?9)ÿJKÿÿH9 B;¾£ëx™?HAé`¤ëx8cTi>8}%Kx™?HDÙ`‰?9)ÿJKÿþô€`|¦û¡ÿèûÁÿð?¯ûáÿø;Þè8 H8€|}xÃóx;àøø!ûQHD-`=B¯=¯="¯)؛ê›è9@=¯™H=B¯‘*KÿÏ9`8 |dx8~8HD5`8 8€8apHCÑ`9 8ap›á„›áq›áv›ás™!͛á²›á³KÿüÅ8~8ÀC8 D8€4Kÿåñ`<¯€ÆÜ8àÿÿÃóxxç 8 8€HKÿÛ=`Äóx8 H£ëxKÿÒy`8!°èë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûáÿøøø!ÿHJ!`|xHJ`8!€Wé€èëáÿø}#x="¯iØ|¦N€ €```|¦û!ÿÈûAÿÐ`ûÿàû¡ÿè9 ;B” ûÁÿðûáÿø?¯|yxûaÿØ;Þè|Ÿ#x;žø;¾øøø!ÿAƒãxëd:DÓx‘!pH?E`DÓx£ëxH?5`=¯cÛx;@û(àKÿýÝ9 =B¯™*èKþu
`Kþte`cÛxKÿÍy`‰>.‰/‰A–D@ž@8`ÿÿ8!Àèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```?/©Až‘>ô?/©@žˆ‰?8/‰@ž£ëxH>Õ`/£@ž ="¯)ì/©Až‘!p=B¯Jܑ?„ãx88‘_H>9`8!À8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ =¯‘(ì‰?8/‰Ažÿx8Ÿ8ƒãxH=å`£ëxH>9`/£Ažÿh8p£ëxKÿˑ`/£Až4!pKÿÿ\``KþsQ`/ƒAþ˜;Zÿÿ{Z!Aâþ¬Kÿþx8À8¡p¤ëxcÛxKÿçQ`/£@žÿ´>/©@žÿ8`ÿüKÿþx```8`ÿýKÿþd€```|¦û¡ÿèûÁÿð8 Hûáÿø?â¯|}x;ÿè8€ãûx;Àøø!ûQH@
`=B¯=¯="¯)Ø`8ˆ›Ê›È9@=¯8‚” ™H=B¯‘*H<­`KÿË`8 |dx88H@`="¯)Ü=B¯8 8€8ap‘*H?`="¯)ð9@8ap›Á¦™A„‘!pKÿø‰88ÀC8 D8€4Kÿáµ`<⯀çð<¯€ÆÜãûx8 8€HKÿ×`äûx8 H£ëxKÿÎ=`8!°èë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûAÿÐûaÿØ|zxûáÿøû!ÿÈ|Ÿ#x|»+xûÿàû¡ÿè8€8 ûÁÿðøø!÷8aˆH>¡`‰?/‰@ž(?=B¯JØ?‚¯;œè‰P@ž;ßì<‚8 8„ˆÃóxH?`/£@ž{y 8¡ˆ;¹ÿÃóx{½ ¤ëxKÿó/£Ažĉ!/‰@ž@‰!œ/©Až$?¯‹Þè/žAžÔ/ž@ž”+‰AžÔ+‰@žÄ9 8`‘<ô‘<9 ™<H¸```_?;ß,Ãóx‘\ô‘<?ýܑ<H:á`/£Až4ƒ¼/@ž(8 @Äóx8|øH;é`›¼8```;ÿlãûxH:™`/£Až$8 €äûx8|øH;­`9 =B¯™*`9 =¯8`™(è8!ðèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```99ÿ¥ëxÄóx8ap‘! H=`‰!/‰Ažø/‰AžÔ/‰@žD8À€8¿l8 8atKÿïI|c4/£AÞ$€ 8¡ˆ8ap8„x„ KÿñU/£@žþP8!ð8`ÿÿèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``+‰Až¬8`8!ðèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``_=¯?;ß,Ãóx‘HÜ=B¯‘*ìH9`/£@ž´;ßlÃóxH8ù`/£@ž\?ýÜ=¯=B¯‘(ð9 ™*è<b¯€cÜKÿÑY`<b¯ècà/£Až/›¸AÌ%ËxäûxH;±`‰!‰/‰Až‰!‹/‰@ž@‰!Ž/‰Ažÿ€a8 8€Kÿá‰`8`Kÿþø``?¢¯ƒ½ì/@žÿD8 @Äóx8|øH9e`›¼8Kÿÿ(`8À€8¿l8 8atKÿí/£Ažþ`8À@8¿,8 8atKÿíe|c4Kÿþ``8 ¸äûxH:é`Kÿÿ8```?8 H8€ƒãx‘<ô!ˆ‘<H:e`<ð9@›Ü›Ü™\‘< KÿŅ`8 |dx8|8H:`8 8€8apH:`9 8 8œô8at™!„H:Q`8 8œ›Á¢8apH:9`9 8ap›Á¦›Áq›Áv›Ás™!͙!͛Á²›Á³KÿòÙ8ÀC8 D8€48|KÿÜ`8àÿÿ8Àxç 8 8€HƒãxKÿÑU`8 H„ãxCÓxKÿȑ`9 8`™<KÿüD``8 €Äóx8|øH7µ`9 =B¯™*`Kÿýˆ```‰!ʁ_/‰‘\ô?Aˆ‘<‘\Až@8ž8|øH5Õ`‹ÁË/žAž„8ž8|øH5¹`9 =¯™(èKÿý4;Üø`8‚” ÃóxH5‘`‰!9)ÿþU)>+‰@ÿ¬ƒ¼/@žÿ 8 @8Ÿ,ÃóxH6í`›¼8Kÿÿ„```;¼ø`8‚” £ëxH51`‰!q)ý/‰Ažÿl;_lCÓxH5q`/£AžÿT8 €DÓx£ëxH6…`›ÜxKÿÿ8€a”KÿÎñ`€a˜KÿÏ%`Kÿü¬€```|¦="¯ûÁÿðûáÿøè©ú}% Pøø!ÿ})¦p/‰@¸="¯)ü`|Ÿ#x;¢ /‰AžLäVtÃóxHCÑ`="¯=B¯“éø9 ‘*ü9 8!ð=BèëÁÿðëáÿø‘*Œ|¦N€ |¥VtÄóx8apHB…`‰!p9Ap9/‰Až``™
*/‰@žÿô8apHCM`Kÿÿl=")Œy*¡A‚ÿ@/£9)y) @žÿ0Kÿÿp€|¦ûaÿØûÿà|›#xû¡ÿèûÁÿð||x|½+xûáÿøûAÿÐ?â¯8€;ÿø8 ;ßøø!ÿaÃóxH6y`=B¯é*/‰Ažä/‰Až,¦ëx8 Ñ8€8`KÿØ©`9 ±)à`HA`èÿ8 8€;ÿ0;@4|fxÃóx8çH`¦ëxãûx8 Ñ8€KÿØQ`9 ³
EÓxÄóxƒãx±?øA(="¯9)¸é)éIéi}I¦èIN€!èA(8! èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ="¯é)8À8 8€ Ãóx;ÿ;@ €éKÿÍ-`KÿÿT€`|¦ûAÿÐûaÿØ?B¯û¡ÿèúÁÿ°;Zø|{xúáÿ¸ûÿÀ;º8 û!ÿÈûÿà8€£ëxûÁÿðûáÿøøø!ÿ1`B¢¸`¡"¢¼‘Ap±!tH4Ù`=B¯é*/‰Ažä/‰èzAžx8c8H1ñ`|x8apH1á`ãú`8b¢°Wÿ>H1É`;ÿ|~x8zH1µ`ÿò8ÀE8 Ñ|Td>8`KÿÖµ`9 ±)à8c8;pH1y``;Ú;"¢°:Ú0|xÃxH1Y`ãú#ËxH1I`ÿÃóxH19`ÿHý`èú8Ÿ;Ÿ68 T„>|fx£ëx8眴HÑ`<b¯èc:ö
8c8H0é`|xÃxH0Ù`ãú#ËxH0É`Wÿ>;ÿ|zxÃóxH0±`ÿÒ8ÀE8 Ñ|Td>~óxKÿÕ±`9 ?B¯ëZ±6;Z8CÓxH0q`DÓx8£~ã»xx¥ H3i`<b¯èc8c8H0E`8cx ÃxH01`÷úÃx8£ãûxx¥ H3%`ÃxH0	`8cxi #ËxÿJH/ñ`$Ëx8£ãûxx¥ H2é`#ËxH/Í`8cxi ÃóxÿJH/µ`Äóx8£ãûxx¥ H2­`øA(="¯9)¸…ãx¤ëxcÛxé)éIéi}I¦èIN€!èA(8!ÐèêÁÿ°êáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``<b¯èc;p`;"¢°;Ú:Ú8c8H/`||xÃxH.ñ`ƒâ#ËxH.á`;œ"|xÃóxH.Í`="¯é)œú8À8 œ£ëx€éW„>œ´KÿÉ-`Kÿýœ€
`|¦="¯é)ûAÿÐ?B¯ûaÿØûÿà;Zøû¡ÿèûÁÿð/©ûáÿøøø!ÿaAž¨=¯|ž#x||x8`èˆ"|¿+xKÿùKþcÉ`Kþc!`©> ¾=B¯+‰|¦4°Ê$Ažp+‰Až¸U*>/ŠAž|+‰AžÄéZ@; *9)‘*8! £ëxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8! ; £ëxèëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ¡>
U*>+ŠAô=Bÿÿ9Jìy)¨}*Jª}IR}I¦N€ Ô´”ÔtTÔ4`¡:4¡
8é}´‡ Až\m*ÿÿ/ŠÿÿAžÀ‰@@AždA”="¯é)89@ÿÖ; ÿ֐é<⯑G(¡^
‘I8! £ëx9 =¯èëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø‘(D|¦N€ `{å ;þ
Þ*¿ð@@œØ`;b¢°H@8€ãûxH+)`,#A‚¬8€8cH+`,#A‚$;ã¿ð@@œcÛxH,1`dÛx8£ãûxx¥ H0`|}y@‚ÿœcÛxH,`8 
8€8c|H2m`<â¯Tc>9#ÿÿ+‰“°g&AÝ´<¢¯ ¥$8€ƒãxKÿ÷½Kÿýì`=¯¨È$9 =B¯±*&;º8 8€£ëxTß>H.I`<â¯é'/‰Až/‰Ažæûx8 Ñ8€
8`KÿÐy`9 ±)à`9 8€ƒãx; ±:.Kÿ÷-Kÿý\`="¯¨É$Kÿÿp`9 ÿù=¯; ÿù‘((Kÿþ4```9 ÿú<â¯; ÿú‘'(Kÿþ```9 ÿû=B¯; ÿû‘*(Kÿýô```9 ÿü=¯; ÿü‘((KÿýÔ```9 ÿý<â¯; ÿý‘'(Kÿý´```9 ÿÿ=B¯; ÿÿ‘*(Kÿý”H
-`èú8 8€
;Ú0;`5|fx£ëx8çH`æûx8 Ñ8€
ÃóxKÿÏ=`9 ¤ëxeÛxƒãx±>9 ; ÿø±>
9 ™>øA(="¯9)¸é)éIéi}I¦èIN€!èA(9 ÿø‘:0Kÿüð``°ú4=B¯="¯é)8<⯀ç@é
"9@‘I¡^}*B9)ÿô‰8@\9 ÿþ=B¯; ÿþ‘*(Kÿüœ`=B¯éJ8; *9)‘*Kÿû|`Z8/ŠAžü<+ˆAü4±4Kÿÿ|`<b¯èc8ªÿô8žx¥ |cBH,`<¢¯ ¥$ ž
ƒãxKÿôñ="¯¡)&¡^<⯁ 9)‰P9Jÿô}JB‘G @œ˜¡:4m*ÿÿ/Šÿÿ@žû:8/‰@žû9 ÿ÷; ÿ÷‘:0Kÿû̃ãx; Kÿô=¯é8=B¯J4<⯁(9J‘G49)‘(Kÿú”="¯é)8À8 8€!£ëx;Ú;`!€éKÿÂÉ`Kÿþ9 ; ‘:LKÿúT=B¯¨Ê$Kÿüx€`="¯ cÿö=B¯i(9 ‘*DN€ ``|¦ûÁÿð|ž#xûáÿø<‚¯9`/‰ÄH<¯<‚¯‘g‘gøf<¯¤@<‚¯øø!ÿ‘0=¯<¯øä8<‚¯‘H=B¯=¯±f,<¯‘d4<‚¯‘j(=B¯‘h =¯‘jD9@ÿÿ±F$9@ÿÿ‘Hü=B¯‘jø9@±D&@Ô/‰”AÜ}%´?â¯`;ÿø8‚‚ð8H5``8b¢ÀH6`8€8`ÿÿKÿñÑ<¯ûÆKþ\u``;¢ØKþ[Å`="¯é)èi:Kÿô1H<``é?èi:Kÿ´¹`é@_P(‰P@A¬(‰P@A¤?L/‰@ž8Kþ[µ`/ƒAÿ¸é_@*+‰@¨ ¿,|¨4/ˆÿÿAž¤ Ÿ4+„@é?T¥>èi:Kÿòé_@*9)‘*Kþ[©`Kþ[`é?èi:Kÿ´`é@_P(‰P@@ÿ\9 ÿØ8`ÿؑ?08!€9 =B¯èëÁÿðëáÿøù*|¦N€ `©,/ˆÿÿ@žÿˆ¡4/ˆ@žÿ|y( +ˆ@žÿpÃóxH4‰`é?èi:Kÿòéé_@*KÿÿL``8 Kÿþ8``9 ”Kÿþ$``è29 ù? /£@Þ4èŸ*8`ÿÿKÿð`8b“ H4`èŸ>/¤@ž8="¯èi"8!€èëÁÿðëáÿø|¦N€ `9 ÿ×8`ÿב?0Kÿþü`8b£H3É`Kÿÿ¼€|¦û¡ÿèûÁÿð|}xûáÿø|ž#x|¿+x|dx8 (øø!ÿA8apH'`/Ÿ‰]9 ‘!p™!v™Aw@„;ÿÿÿ8žÿþ{ÿ 9 ;ÿé¦`¥D})RBÿø99An}	¦``¥
})BBÿø8!Ày*„y) è}*Jë¡ÿèëÁÿðëáÿøy#„})|¦}#HøTc>N€ 9 Kÿÿ¤€``,#A‚¬|¦ûáÿø?â¯ëÿPûÁÿð|~x/¿øø!ÿ@ž H````ëÿ8/¿AžHãûx8 ÄóxH'Y`/£@žÿÜ8!€8`èëÁÿðëáÿø|¦N€ ```8!€8`èëÁÿðëáÿø|¦N€ `8`N€ €```|¦ûaÿØûÁÿð|{xûáÿøû!ÿÈ|¿+x|ž#xûAÿÐûÿà8 8„û¡ÿèøø!ÿ18apH%±`9?+©îAÀ?‚¯;¾;œP8 8œ£ëxH&u`;^(/£Až$‰>+‰Až<+‰:Ažà‰!p/‰ÿAž¤="¯é)P/©Až<épéIª@@ž Hà```éIª@AžÈé)8/©@žÿì£ëxHõ`,#A‚?¢¯;½X|zxºèAÞKÿ¯Ñ`;¼(8€FÓx`„†Ý|ex{ÿ £ëxKÿ²]`åûxÄóx8|6H$©`8¿¤ëx|¥´cÛxKÿ±ñ`8!Ðèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```8apH½`|yyA‚è;¼8 ¤ëx:ËxH%`/£@ž 8 ¤ëx£ëxºëxH$ý`/£@ž 9/‰@žÿ8pcÛxH`Kÿ®Ñ`8€FÓx{ý `„†Ý|ex8y(Kÿ±a`¥ëxÄóx8y6H#­`“¹KþV1`KþU‰`H ```KþUÁ`/ƒ@€cÛxKÿ®}`‰9/‰@žÿÜãûxKÿþÌ<‚¯è„p8 £ëxH#A`‰>+‰@žýÌ ¾DÓxÃóxx¥übKÿûm,#A‚°°~.Kÿý°``8 ¤ëx#ËxH#å`/£@þþKÿþè8!Ð8`ÿÿèë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 9 38 8|8a‚™!€™!;A€H"•`Kÿý¬`` ¾DÓxÃóxx¥übKÿúÁ°~*Kÿý9 ÿÿ±>.Kÿý8` H)u`|yyA‚ÿh8  8€H!í`8 8p8yH")`‰99@#Ëx™Y9)™9Hi`?¢¯;½XKÿýÜ8`Kÿýh€|¦ûaÿØûÿà;`û¡ÿèûÁÿð|~x|œ#xûáÿø; øø!ÿQˆc/£Až¸`+AžìH$Y`/£AžÜ8€:ÃóxH1`|yA‚ôþøPÿ4+Ÿ{ÿ A°Äóxåûx8apÞúHm`}!ú›ip8 8€8apH&1`+ƒÿÿ|i´Apy)Æ"˜|;½{½ ™<ˆ~+ƒ:Až@;œ/£@žÿT8!°£´èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``ˆ~;œ;ÞKÿÿ¼8!°8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ``Äóx8 8apH•`8ap›átHU`ÞKÿÿ€``<b¯ècpN€ ``|¦û¡ÿèûÁÿð|}xûáÿø8d|ž#x|¿+xøø!ÿqKÿù9/£Až +Ÿ'@‰>/‰Až\/‰:Až$8!8`ÿÿèë¡ÿèëÁÿðëáÿø|¦N€ Åóx8žÿ<£ëxH`8!èë¡ÿèëÁÿðëáÿø|¦N€  ¾8ž(£ëxKÿ¿õ`8!èë¡ÿèëÁÿðëáÿø|¦N€ €`|¦= `ûÁÿðûáÿø|þ;x|x8cøø!ÿ‘#ÿø9 ÿÿ°ƒÿü|Ä3x˜£ÿþ8 ™#ÿÿH`Äóx8 8Hí`8!€èëÁÿðëáÿø|¦N€ €|¦ûáÿø|dx|x8 øø!ÿq8axH¡`8Ÿ8 8a}H`9 ÿÿ8x8 8ap™!{9 ÿþ™!|Hi`èap8!èëáÿø|¦N€ €```|¦= þ€ûáÿøy)Æ|Ÿ#xù$øø!ÿKÿÿQ8!€øèëáÿø|¦N€ €``="¯é)P/©Až<ééIª@@ž H0```éIª@Ažé)8/©@žÿì8`N€ 8`N€ ```|¦ûáÿø8`(øø!ÿH$}`|yA‚8 (8€Hõ`8!€ãûxèëáÿø|¦N€ €``|¦ûáÿøøø!ÿqøaÀ8`@øÈH$`|yA‚L8 @8€H`8 8ÀãûxHÉ`Kÿ§±`Kÿýù|$x8 ødq8H¥`8!ãûxèëáÿø|¦N€ €``|¦ûáÿø|yûÁÿðøø!ÿA‚ÈKÿõ•/£@ž¼‰?/‰ÿAžd8`@H#Y`|~yA‚œ8 @8€HÑ`= =@ÿa)ÿyJÆy)ƒäÃóxù^ù>‰?
™>
‰?™>‰?™>Kÿÿq=B¯é*P/©Až`="¯é)!hûé8="¯8!€8`ûé!h9 ù?8èëÁÿðëáÿø|¦N€ `8!€8`èëÁÿðëáÿø|¦N€ `ûêPKÿÿ¬€```}€&|¦û¡ÿèûÁÿð|#xûáÿø|x8`@‘øø!ÿqH"E`|~yA‚$.=8 @8€H¹`="¯ûÉpA’|8 ¤ëxÃóxHé`<b¯ècp;ÀKÿþe<â¯8ç!°9="¯9)!p<¯8Ƹ<¢ÿÿ8¥{ˆ‰G}#Kxø¦yJ`™G=B¯ù
`=B¯ù
h=@ÿyJÆùI9@ùIKÿþH`ãûxH
•`Hm`/£@žXKþLÝ`KþL5`H``KþLq`/ƒ@ ãûxKÿ¥-`H%`/£AžÿØ9>ÿÿy>!@‚ÿ A’(8!èë¡ÿèëÁÿðëáÿø|¦} N€ ="¯é)P/©AžÿÐ=þ€yÆH`é)8/©Ažÿ´‰I/ŠÿAžÿìéIyJDª@AžÿÜ=B¯ù*pKÿÿŒKÿ¤m`?¯ëÞp= þ€y)Æù>Kÿú¡ø~Kÿþx€``|¦8 øø!ÿ‘H!`8!pè|c4TcÙ~|¦N€ €`|¦ûaÿØûÿà|›#xû¡ÿèûÁÿð||x8 ûáÿø8€cÛx; ;Àøø!ÿ1Hu`8€:ƒãxHe`|y@‚HX/£}>´|xAž@88€:H9`9>ÿP/¿@žÿÔ/£;Þÿÿ;½Þ´½´|x@žÿÈ/@08`8!ÐèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `Až€/ž@žÿÌÝò/žAÞÿÀ`ƒãx8‚£H½`|~yA‚ð`ƒãx8‚£ Há`/£@žD9 8!Ð8`™;èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ /ž@ÿˆKÿÿL`üðPWÿ>+ŸAÿ8åûx„ãx8apáúH‘`9 88~™?pKÿõy|yA‚ÿ {å |c´8|{H9`88apKÿõI|eyA‚þÔx¥ 8cÛxH`ãûxKÿþ¼dÛxƒãxKÿõKÿþ¬€`|¦9 ûÿÀû!ÿÈûAÿÐûÁÿð````ûaÿØûÿàû¡ÿèûáÿø|#x|x;c;ƒø;"£@ø!ÿQ;B£8™$;£(;¡€H8``H!q`¿à@Äóx£ëx;ÿAÞxH¥`¿Ø@Ažh‰?ˆß/©.¦@ž4¥ëxDÓx£ëx@–ÿ´$Ëx£ëxHi`Kÿÿ¨```|Ç3x¥ëx}&KxÃx£ëxH í`Kÿÿ|`¾ëx;‚£H`„ãxÃóxH‰`|y}>øP}*´/ª}^RA‚Ô;ßAž‰*ÿÿ/‰:@žÿÈ}=øP9@})´/©}]I®@žà`£ëx8‚£HÁ`‰?;ÿ/‰AžD`;£PH```?/‰Až ãûx8 ÄóxHi`/£AžÿÜäûx£ëxHa``£ëx8‚£XHý`/£@ž`£ëx8‚£Hq`8!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```£ëx8‚¡€Hå`Kÿÿ$€```|¦ûÁÿðûáÿø8 î8€|~x?â¯;ÿ!¸øø!ù‘8apHõ`Kÿóý`çûx8 8€*|fx8a~Kÿôá`8À#8a¦8 "8€*Kÿ¶`9 8Ÿ@8 8a¯™!®Hí`9@
9 ±A´9@±!²±!¸±A¶Kÿž¹`8 |dx8aºHµ`9 9@8~8 R±!Ʊ!È9 Ãóx±AÀ9@±!Ê9 ±AÂ9@±!Ì9 ;±Aı!ÎKÿíu`8!pèëÁÿðëáÿø|¦N€ €``|¦øø!ÿ‘Hå`="¯˜i!øHÕ`="¯˜i!ùHÅ`8!p="¯è˜i!ú|¦N€ €``|¦= ÿû¡ÿèûÁÿðy)Æ=B¯ûáÿøëä:?Â; ù*!¸= =B¯a)øø!ÿqãûx;ޝù*!À="¯ø‰"Kÿþ
9 =B‘*KþDý`KþDU`ãûxKÿi`>.‰+‰A–T@ž08!8`ÿÿèë¡ÿèëÁÿðëáÿø|¦N€ ```KþDQ`/ƒAÿ¨;½ÿÿ{½!Aâÿ¼Kÿÿˆ8!8`èë¡ÿèëÁÿðëáÿø|¦N€ €`|¦û¡ÿèûÁÿð?¢¯ûáÿøûaÿØ;½!¸|~xûÿà|Ÿ#x8 8@8cøø!þaHu`,#A‚88! 8`ÿÿèëaÿØëÿàë¡ÿèxc ëÁÿðëáÿø|¦N€ ``‰>/‰AžH;ÿÿü;Þÿ´;€/ŸA„H´``/‰Až„/‰;@ž| ¾8ž8ap9%åøP~JH	`èH þ8ap;ÿÿüÿ´èÄ:}!:8¤88„›‰pKÿŒY`/ƒÿÿAžD~Ûx/Ÿ@8‰>/‰AžT+‰Aÿ|¡^êøP9J;ÿÿüÞRÿ´/ŸAÿÐ8! 8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ¡>è}H;~8 dÛxéøP9I8c(ÞR;ÿÿüH`8 dÛx8`ÿ´Kÿ¶`KÿÿT`="iKÿþ´€``|¦ûáÿø= ÿy)Æ|xøø!ùù!`9 ù!hKÿïi`8á`8 :8€|fx8a~KÿðM`9@ÿ…9 ™A¦9@™!®™!¯™A§KÿšY`8 |dx8a°HU`øA(="¯9)¸8~8 8ãûxé)éIéi}I¦èIN€!èA(8!€èëáÿø|¦N€ €``="¯èi"
N€ ``|¦ûÁÿðûáÿø8 î|Ÿ#x|~x8€øø!ù8apHY`= ‰‰_ˆÿ
<Àÿa)ÿxÆÆy)ƒäøÁ`ù!h™n™Ao˜ámKÿî-`8á`8 :8€ |fx8a~Kÿï`9 ÿ‡äûx8 8a®™!¦9 ™!§H-`9 ™!¾™!¿Kÿ™	`8 |dx8aÀH`øA(="¯9)¸8~8 HÃóxé)éIéi}I¦èIN€!èA(8!€èëÁÿðëáÿø|¦N€ €`|¦ûÿàû¡ÿè||xûÁÿðûáÿø;Å|¿+xûaÿØ|#x8 Äóxøø!óA8axH
e`8 88apH
Q`‰?(/‰‡Až0/‰ˆAž˜/‰†8`ÿÿAž,8!ÀèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `9 Ãóx‘!€±!„HA`|}yA‚ì¡?.<â¯8ç!°;ß8?€þ€{œƑ=‰'y* ?0‘=?4‘= ‰-U	0y×â}IKxU02})Cx™'¡_9Jÿð}_´/ŸAlH¨``/‰@ž88 8ž8aH]`é!y)D©àAž>^‰P@@¸‰>U)8}IøP})´/Š}_´ÞJ@D‰>/‰@žÿœ8ž8 £ëxHý`‰>U)8}IøP})´/Š}_´ÞJAÿÄ8!À9 =B¯èëaÿØëÿàë¡ÿè8`ëÁÿðëáÿø‘*"|¦N€ 9?(;¿ÿòûá˜8 Äóx8a€ù! û¡H`8a€Hå`|yA‚H聐8 8„HY`?/‰9 ™?@žp8`8!ÀèëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `KÿêÑ`;à8áx8 :8€ |fx8ažKÿë±`8x8 8aÎH
Ý`›áޛáßKÿ•½`8 |dx8aàH
¹`¡!Ê9@ÿˆ8 ›áß8€8aΙAÆ9@y)`a)`™ADZ!Ê9 ™!ÞH
)`Kÿê1`8 |dx8aÎH
]`Kÿ•E`8 |dx8aàH
A`øA(="¯9)¸8ž8 Hƒãxé)éIéi}I¦èIN€!èA(8!À8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```;ß(8 äûxÃóxH	Á`€¿Äóxƒãx8¥|¥´Kÿ—`9 8`‘?KÿþX```èaè˜Kÿìi`|{yA‚ý8Kÿë‰`/£Ažý(Kÿëé`|dyA‚ý8 (8{H	A`cÛxKÿìÅ`Kÿüø``8£ëxHé`/£AžýÐHi`8`KÿýÄÄóx8a€H¡`|}xH%`Kÿûü€```|iyAÂT=¯éH"/ªAž,=¯8`éH"ù("ù*(9@ùI(N€ ``ù("=¯ùI(8`ù("N€ 8`ÿÿN€ `|¦û¡ÿèûÁÿð|}xûáÿø8`0|ž#xøø!ÿqHM`|yA‚<8 08€HÅ`8 ¤ëxãûxH`8 Äóx8Hí`8!ãûxèë¡ÿèëÁÿðëáÿø|¦N€ €``|¦ûáÿø?â¯ëÿ"ûÁÿð|~x/¿øø!ÿ@žHH`ëÿ(/¿Až88ÄóxKÿî-`/£Ažÿà8!€ãûxèëÁÿðëáÿø|¦N€ 8!€8`èëÁÿðëáÿø|¦N€ €``<â¯èç"/§Až<éé'©@Až,|é;xH``éIª@Ažé)(/©@žÿì|ã;xN€ }'Kx|ã;xN€ ``|iyAÂT=¯éH" /ªAž,=¯8`éH"(ù("(ù* 9@ùI N€ ``ù(" =¯ùI 8`ù("(N€ 8`ÿÿN€ `|¦ûÁÿðûáÿø8` |ž#xøø!ÿH
5`|yA‚L8  8€H­`èž8 ãûx8„Hå`èž8 88„HÍ`9 ™?8!€ãûxèëÁÿðëáÿø|¦N€ €`|¦ûáÿø?â¯ëÿ" ûÁÿð|~x/¿øø!ÿ@žHH`ëÿ /¿Až88ÄóxKÿì
`/£Ažÿà8!€ãûxèëÁÿðëáÿø|¦N€ 8!€8`èëÁÿðëáÿø|¦N€ €``9 =B¯ù*"=B¯ù*"=B¯ù*" =B¯ù*"(N€ ```|¦ûáÿø|xøø!ÿqøpH‰`èp|c´|H`8!ãûxèëáÿø|¦N€ €``‰#T„>/©Až(„H@@žH$`Mž #.©„H@@–ÿð8`N€ N€ `‰C‰$/ªAžH/©Až\ŠH@Až(HP```$/©~ŠH@Až4@–0C/ª@žÿä‰$8`|iP|c´N€ ```}C´|iP|c´N€ `8„ÿÿ9CÿÿH`````$*‰$/‰@žÿðN€ ```````‰#/‰Až49 ````C9)})´/Š@žÿðy# N€ 8`N€ ,%A‚œ‰/¨Až¤‰D/ªAž¤+…Až„ˆP@@ž|9%ÿþy) 9)})¦H(```$/©~ŠH@Až4B@0@–,C/ª@žÿà‰$8`|iP|c´N€ ``}C´|iP|c´N€ 8`N€ }´}ISxKÿÿä‰$8`KÿÿØ}´9 KÿÿÌ``‰/¨Až€/¥9EÿÿyJ |ix9J}I¦@žN€ `B@P9)™	ÿÿ8¥ÿÿx¥ /¨@žÿä/¥Až08¥ÿÿ9)ÿÿx¥ 9@8¥|©¦IBÿüN€ `N€ N€ |ixKÿÿÄ`|¦ûáÿø|yûÿàû¡ÿèûÁÿðøø!ÿqA‚ /¤|ž#xAž”Kÿþ`|}´ÃóxKÿýñ`/ƒ||x@H¿ê¿è@Aœ H````;ÿ¿è@AžHãûx…ãxÄóxKÿýù`/£@žÿÜ8!ãûxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ `8!8`èëÿàë¡ÿèëÁÿðëáÿø|¦N€ €/¥8¥ÿÿx¥ 9#ÿÿ|£*T„>|©(P|©¦Mž ```œ‰BÿüN€ ``/¥8¥ÿÿx¥ 9#ÿÿ|£*8„ÿÿ|©(P|©¦Mž ```DIBÿøN€ `¤@@œL}$*£H@A@/¥9%ÿÿ|„JMž 9%ÿÿ8„y) |£*9)})¦`$ÿÿ%ÿÿBÿøN€ /¥Až,8¥ÿÿ9#ÿÿx¥ 8„ÿÿ8¥|©¦DIBÿøN€ N€ ````/¥8¥ÿÿx¥ AžT‰C‰$8¥|©¦‰P@@ž0H`````B@ C$ŠH@Ažÿð})PP}#´N€ 8`N€ ```|¦û¡ÿèûÁÿð|}xûáÿøøø!ÿqˆc/£Ažä‰$/‰Až€|ž#xH `Œ}/£Až˜>/‰Až\Hy`|xˆ~Hi`ƒøAžÿ̈}‰>8!|iP|c´èë¡ÿèëÁÿðëáÿø|¦N€ ```8!9 |iPèë¡ÿèëÁÿðëáÿø|c´|¦N€ ``8!‰>èë¡ÿèëÁÿðëáÿø|iP|c´|¦N€ ‰$Kÿÿt€`8cÿÐ+ƒ	OÝèB|p&TcÿþN€ ```xc TiÐ~8cÿÐU)0>*ƒ	9)ÿ¿NÕ¨B+‰OÝèB} &U#¿þU)ÿþ}#x|c´N€ ``9#ÿ¿+‰M 8c |c´N€ ```9#ÿŸ+‰M 8cÿà|c´N€ ```,$A‚`+…$ødA<àxçƒä`ç&‰#|hx8c+‰ |êL6yFá@¸/¥@žà+‰0@žÀ‰(8 
/‰xAž9 08`H4``}J4Š(9}%ÒLœ ù|jJ‰(/©AžÌ9IÿÐ8éÿŸUF>+‡*†	}J4@•ÿÄ9Iÿ¿*Š9Iÿ©@ÿ°9)ÿÉM• }*49Š(}%ÒAœÿ¨N€ ```A‚ødKÿÿ(`/¥@ž8 
/©@žÿP8`N€ `/…@žÿè+‰08 @žÿ܉(/‰x@žÿ 9HùD‰(}HSxKÿÿ¼```N€ 8ÿðKÿþ 9HùD‰(}HSxKÿÿ¬`|‹#yA‚l+…$øk9 Aü<àxçƒä`ç&```‰#|hx8c+‰ |êL6yFá@Ø+‰-@žà9H/¥8€ùK‰(}HSx@žÐ+‰08 
Až/©Až 8`H0`}J4Š(9}%Ò@œ`ù|jJ‰(/©AžL9IÿÐ8éÿŸUF>+‡*†	}J4@•ÿÄ9Iÿ¿*Š9Iÿ©@ÿ°9)ÿÉA•}*49Š(}%ÒAœÿ¨/¤|ixAž}#Ð}#KxN€ ``A‚økKÿÿ`/¥8€Ažÿ8/…@žÿ<+‰08 @žÿ0‰(/‰x@ž,9HùK‰(}HSxKÿÿ9aÿðKÿþ”‰(/‰xAž9 0Kÿþü9HùK‰(}HSxKÿÿ¨8`Kÿÿ\```="é)˜=@IÆaJNm}*IÒ=B=)9)‡y#„bù*˜N€ ``="øi˜N€ ``|¦û!ÿÈûAÿÐ?B¯ûaÿØûÿà|{x;Z"0û¡ÿèûÁÿð;ÃûáÿøûÿÀ;ã{Ù {ÿä=´øø!ÿQ{ü ÿ´èz``/£Ažôé:}CʪH@@éZ}ISx‰	©@qð@‚4ˆÉˆéy ˆ‰x¨ÁäxƃäxçEä|ÈCx|èCx|ˆCx~ˆØ@@”D@œH‰	ˆ©ˆÉˆéyÁ(x¨ƒä}#xxÆEä|ÈCx|èCx9})BKÿÿŒ``©@Aœàª@@œ 9`8 HÀ`Až0ˆ
ˆå‰…ˆÊy)Á(‰e‰
‹xäÁ(yŒƒäxƒäykEä|	Kx}„#xxÆEä}d#x|ÆKx#x}	3xxçä}$J9`9)y(G"y&†"|çCxy(Æ"™%˜Å˜å™‰*ˆÊˆê‰
y$Á(xɃä})#xxçEä|éKx}	Kx9)}JJª@@œP‰*/¥q(ðA‚ÿ<‰*ˆÊˆê‰
8 y$Á(xɃä})#xxçEä|éKx}	Kx9)}JJª@Aœÿ¸/«@þþ8£ëxKþ7A`é:£H@žd|cÊøzKÿþ}ESxKÿÿLãûxKþ7`/£ÿÿøzAž8}#â}CÊøzªH@ù:Aýô{iG"{g†"›ca){hÆ"˜ã8c™#ÿü="¯™ÿþùI"08!°èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ˆð@@€}@P8é›i{fG"}GÚ{`†"{cÆ"`ÆyG"y†"yÆ"˜i˜	˜É}gÙ®8!°|ã;x˜Š˜ª™
èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ `¥8!°8i˜©èëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`Kÿÿ€``‰#ÿüy) ™#ÿüN€ `|¦/£øø!ÿ‘ø¡°øÁ¸øáÀùÈù!ÐùAØAÞ(/¤Až 8¡°H9`8!pè|¦N€ 8`ÿÿKÿÿì€```|¦|¦+x|…#x8€ÿÿx„`øø!ÿ‘H¥`8!pè|¦N€ €|¦øø!ÿ‘ø¡°8¡°øÁ¸øáÀùÈù!ÐùAØH
9`8!pè|¦N€ €`|¦øø!ÿ‘ø¨|dx<b8cÀø¡°8¡¨øÁ¸øáÀùÈù!ÐùAØHÙ`8!pè|¦N€ €`|¦û¡ÿèûáÿø|}xûÁÿð?â;ÿÀøø!ÿqëßKÿði`¤ëx|exÃóxKýÕõ``8 8‚£`|~xèKýÕÙ`8!Ã´èë¡ÿèëÁÿðëáÿø|¦N€ €`é#/‰L 9)ÿÿ‘#N€ ```/ƒ
Až|c4TcÙ~N€ ```8`N€ ```|¦ûáÿø|xøø!ÿq#/‰Až„èƒ/¤Ažxé#
/©Až/‰OA}H®}DJ/ˆ@ž´è8 PKþ!é`|c´/ƒAœx/ƒO@té_9 ‘?ˆj8!èëáÿø|¦N€ ``è8 8pKþ!•`/£@žXˆap8!èëáÿø|¦N€ ```8`é?9@}I®Kÿÿ„```9)})´Kÿÿt`8`ÿÿKÿÿp€```‰/¨Až |¦ûÿÀû!ÿÈ;ûAÿÐûaÿØ|¹+x;Dûÿàû¡ÿè;€|}xûáÿøúáÿ¸;à;`ûÁÿðøø!þA``9(ÿ±U*>+Š)Aô=Bÿÿ9JT\y)¨}*Jª}IR}I¦N€ „ÔÔÔÔÔÔÔÔ„ÔÔÔÔÔÔÔÔÔÔ´ôÔÔÔÔôÔÔÔÔÔ„ÔÔÔDÔÔÔÔ„```£ëxKÿýT~>ô/ƒ Ažÿì9>ÿ÷+‰@ÿàKÿý-/£@žÿÔé9£ëx9IùYé)›ÉKÿýITi>/‰ }#´Až(9)ÿ÷+‰@Kÿüé/£@ށ=/‰@ž¨/¨@žþ˜8!À8`èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ ```£ëxKÿü½/¼T~>xc Až¼/ƒ |w´Až/ƒ	Ažˆ/ƒ
@ž H|``/‰	Ažl/‰
Ažd~ã»xKÿü-/£@Þ”œø@Œ~ã»xKÿñµ`/£Ažx}!ú£ëx;ÿ›ÉpKÿü5ÿ´xi T~>/‰ }7´@žÿœ``}!ú›ip8apKÿë•`/£Až˜é98 9I8€8apùYëÉKÿóy`~Kÿþ¼``£ëxKÿû½/¼xi T~>AžL/‰ }#´@ždHl``/‰
Až\KÿûI/£@Þ@œø@89>ÿÐ+‰A,}!ú£ëx;ÿ›ÉpKÿûYÿ´xi T~>/‰ }#´Až/‰	@žÿ¨`}!ú›ip8apKÿêµ`/£Až¸é98 Kÿÿ ``£ëxKÿúý/¼xi T~>Ažœ/‰ }#´@žXH\``/‰
AžLKÿú‰/£@Þ4œø@,}!ú£ëx;ÿ›ÉpKÿú¥ÿ´xi T~>/‰ }#´Až/‰	@žÿ´}!ú›ipé98p9IùYèiKÿé•`KÿýL``£ëxKÿúM/¼T~>xc AžL/ƒ |w´Až/ƒ	Ažˆ/ƒ
@ž H|``/‰	Ažl/‰
Ažd~ã»xKÿù½/£@ÞÔœø@Ì~ã»xKÿï`/£Až¸}!ú£ëx;ÿ›ÉpKÿùÅÿ´xi T~>/‰ }7´@žÿœ``}!ú›ip8apKÿé%`/£Až(é98 
Kÿý``9ÿÐU	>+‰	AüT}â}´KÿüH`/‰ }#´AžþÈ`/‰	Ažþ¼/‰
Ažþ´Kÿøñ/£@Þœ}!ú£ëx;ÿ›ÉpKÿùÿ´xi T~>/‰ }#´@žÿ¼Kÿþx`/ƒ |w´AžüØ/ƒ	AžüÐ/ƒ
@žKÿüÄ/‰	Ažü¼/‰
Ažü´~ã»xKÿø}/£@Þä~ã»xKÿî
`/£AžÐ}!ú£ëx;ÿ›ÉpKÿøÿ´xi T~>/‰ }7´@žÿ¤Kÿü````/‰ }#´@žTKÿý$/‰
AžýKÿø	/£@Þ9>ÿÐ+‰Aô}!ú£ëx;ÿ›ÉpKÿø!ÿ´xi T~>/‰ }#´AžüØ/‰	@žÿ°KÿüÌ``/ƒ |w´AžþH/ƒ	Ažþ@/ƒ
@žKÿþ4/‰	Ažþ,/‰
Ažþ$~ã»xKÿ÷}/£@ޔ~ã»xKÿìÝ`/£Až€}!ú£ëx;ÿ›ÉpKÿ÷ÿ´xi T~>/‰ }7´@žÿ¤KÿýÐÃxKÿöùKÿúT8!À8`èêáÿ¸ëÿÀë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 8`N€ ô}!ú/ƒ ›ipAÞýx9>ÿ÷+‰@ýlKÿöÁ/£@Þý`=/‰AžýTÃxKÿöuKÿýH```ô}!ú/ƒ ›ipAžú¸9>ÿ÷+‰@ú¬Kÿöq/£@Þú =/‰Ažú”ÃxKÿö%KÿúˆÃ´}!ú/ƒ ›ipAžü;Þÿ÷+ž@ÝûøKÿö-/£@Þûì=/‰AžûàÃxKÿõáKÿûÔ``ô}!ú/ƒ ›ipAÞû;Þÿ÷+ž@úüKÿõá/£@Þúð=/‰AžúäÃxKÿõ•KÿúØ€	|¦ûÿàû¡ÿèûÁÿðûáÿøøø!ÿQ‰$ø¡ð/©Až(|Ÿ#x|}x;À;€H‰);ÿ/©Ažà+‰%éûx@žÿèˆß8áo9HX`+‰iAžl+‰xAžd+‰XAž\+‰pAžT+‰cAžL+‰sAžD+‰%Ažt+‰OAž4+‰oAž,}&Kx}HSx?9HœÇ}J´+‰d@žÿœ``9}AR}´8¡ð}B8p™*p£ëx›ˆpKÿö/ƒ@ ;ÞÞ´éûx;ÿ‰)/©@žÿ(8!°Ãóxèëÿàë¡ÿèëÁÿðëáÿø|¦N€ ;ÀKÿÿØ€```Kÿô€<b8càKÿôh``|¦ûÁÿðûáÿø|¦+x|~x|…#x8€@øø!þA8apHù`8p|xè~{å KýÉA`8!ÀãûxèëÁÿðëáÿø|¦N€ €````}€&|¦`ûaÿØûÿà9B£hû¡ÿèûÁÿð9&ÿýûáÿø+‰
éjéJ‘øø!ÿQùApùaxA/¥|Ü3x|{xAž(|ª+x9 H``````}Jã’9)})´/ª@žÿðy? „ø@8`Aœ|.'þûxH /½;Þÿÿé;{Þ ¥ëx|iñ®AžD¥ã’}=áÒ|©(P|¡*ˆepA’ÿÐKÿèÍ`/½;Þÿÿé;{Þ ¥ëxTc>|iñ®@žÿÄé;8`})úù;8!°èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦} N€ ``8!°8`聁ëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦} N€ ;àKÿÿ€```|¦û!ÿÈûAÿÐ}9KxûaÿØû¡ÿè|›#x8€ûÁÿðûáÿø|~x|ß3xûÿà|£+x8 
|ý;x}Cxøø!ÿQëžKÿçñ`/¿|c´AžÀ9@H`````ÿë’9J}J´/¿@žÿðyJ }9RƒH@Pé^})P})´9)ÿÿ}PPy) »@9)})¦AH$@œ ›Jé^9J}<PP©Øù^Bÿä8!°8`èë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ 9@Kÿÿt€```|¦ûaÿØû¡ÿè|›#xûÁÿðûáÿø|~x|½+xûÿà;àøø!ÿaëƒH4``é^}<PP©Ø@œ4}=ø®y ™*é>9)ù>£ëxKÿà`9ƒø@AÿÄ8! 8`èëaÿØëÿàë¡ÿèëÁÿðëáÿø|¦N€ €```|¦ûaÿØùÁÿp|{yùáÿxúÿ€ú!ÿˆúAÿúaÿ˜úÿ ú¡ÿ¨úÁÿ°øúáÿ¸ûÿÀû!ÿÈûAÿÐûÿàû¡ÿèûÁÿðûáÿøø!þ±øa€A‚´/¤8`Až”`8„ÿÿ9B£À`|¯+x|Ó3xùA°xœ Ûx;:À :B£h‰//©AžD»øPþûx½à@œ4+‰%8Á9Ažð™?9ï‰//©ëá€;ÿûá€@žÿÄ9 ™?èa€{Pc´8!PèéÁÿpéáÿxêÿ€ê!ÿˆêAÿêaÿ˜êÿ ê¡ÿ¨êÁÿ°êáÿ¸ëÿÀ|¦ë!ÿÈëAÿÐëaÿØëÿàë¡ÿèëÁÿðëáÿøN€ ```+‰iAžl+‰uAžd+‰xAž\+‰XAžT+‰pAžL+‰cAžD+‰sAž<+‰%Ažô+‰OAž,+‰oAž$|è;x&8è/|ç´+‰d@žÿ˜`99Ap}´|ê:}
B™' › ˆÁ‘9&ÿÒq*ýA‚è:€ 9Á‘/¦Až˜½àP{½!A‚ŒëS:: :à; }ZÐùA¸```9&ÿ±U(>+ˆ+A=ÿÿ9dÜy)¨}(Jª}	B}	¦N€ Dôôôôôôôô´ôôôôôôôôôô”ôôôÄ”ôô¤ôôD4ôôdô”ôô¸ôä`: zé$}Ê}2J|èP8à~ˆ£x›pëé8¡p9 x„ 8a€_ø8æûxKÿú¥~§«x8À聀åûx|ž P|„èPx„ 8a€KÿøáŒÎëá€/¦Až~øP°èAœþ¤:s9ïKÿüô`zé$}Ê}2J|èP8à~ˆ£x›pëé8¡p9 x„ 8a€_ø8æûxKÿú~§«x8ÀKÿÿt``+†u}!ÊQÓx›	pAžVé89@9)ÿÿ}IH6JH9@‚ˆè€|ž P8à
|„èP~&‹x8¡px„ 9 ~ˆ£x8a€Kÿù­è€~§«x8À
~%‹x|ž P|„èPKÿÿ```áÊ|èP9 8À9 8à
›p8¡px„ 8a€KÿùYŒÎé!€›Iëá€;ÿûá€KÿþÈ``}!Ê8€8 
8ap›	pKÿá]`|q´CÓxKÿÚÍ`聀|c´‘@pé!€|ðèP|cˆPxç |c´|ßHP}$Kx§0@L8cÿÿxc 8c|i¦H ```}HP}$Kx§@@šÉé!€9)ù!€Bÿà}$Kx|ž PEÓx|„èP8a€x„ KÿùµŒÎëá€Kÿýô`áÊ|èP8àFÓx9 9 ›p8¡px„ 8a€Kÿø9聀衰8a€|ž P|„èPx„ Kÿù]聀~§«x8ÀEÓx|ž P|„èPKÿýx```ˆÎ9.+†lAžäëá€}.Kx:àKÿý`ˆÎ9.+†hAž´ëá€}.Kx:àKÿý@ŒÎëá€:àKÿý09&ÿÐ+‰	Aý}!Ê;9ëá€{9 ˜ÉpŒÎKÿý``9?9ïù!€9 %™?`Bëá€Kÿùð9 -éA¸™?zé$}2Jè	}Q8聀8„ø€KÿýX`|.x:€0ŒÎ’KÿûŒÎëá€:àKÿüŒÎëá€:àKÿü€8`Kÿù耠ÞPðÞP ÞPðÞP0ÞPÞPMðÞPNÐÞPQpÞPRPÞPS0ÞPT@ÞPT°ÞPUÞPU€ÞPUÐÞPV ÞPV@ÞPVÀÞPWPÞPWÐÞPX`ÞPXàÞPY ÞPZ@ÞPZÀÞP[@ÞP[ÀÞP\PÞP\àÞP]pÞP]ðÞP^ ÞP` ÞPa0ÞPc ÞPd ÞPÄÞPØÞPdˆÞPj`ÞPk@ÞPl`ÞPmÞPn ÞPpÞPpÞPp°ÞPqðÞPsàÞPt`ÞPxðÞPzÀÞPzàÞP{ÞP~`ÞP‚°ÞPƒ°ÞP„pÞP†pÞP†°ÞP‡ ÞPˆpÞP‰@ÞPŠÞPŠpÞP‹`ÞP@ÞPŽpÞPŽÐÞPŽðÞP€ÞPpÞP‘ÞP’ÞP”àÞP•ÞP—PÞP— ÞP›PÞPÀÞPŸÀÞP  ÞP£PÞP¦ ÞP§ÀÞP¨ÞP¬€ÞP­0ÞP°pÞP²°ÞPµpÞPµÀÞP·°ÞPº@ÞPº ÞPºÐÞP»@ÞP½ÞP¾ ÞPÀ°ÞPÁ`ÞPÄàÞPÅàÞPÇPÞPÈ@ÞPÉ ÞPɀÞPÊ ÞPÊ ÞPË@ÞPËàÞPÌ°ÞPÍ ÞPÍàÞPÎpÞPÎðÞPÏpÞPϐÞPЀÞPÑPÞPÑðÞPҐÞPÓpÞPÔÞPԀÞPÔÐÞP×àÞP×ðÞPÙðÞPېÞPà0ÞPá0ÞPä ÞPèÐÞPí0ÞPô ÞPô0ÞPôpÞPô€ÞPõ0ÞPöÐÞPüàÞPþÀÞPÞP0ÞPPÞP`ÞP ÞP	ÞP
ÞP0ÞP ÞPÞPÞPpÞPðÞP€ÞP ÞP#ÞP% ÞP&PÞP(ÐÞP)pÞP)ðÞP*ÀÞP+PÞP+ðÞP2ÞP3pÞP5€ÞP8`ÞP:ÀÞP>ÀÞPB°ÞPJ ÞPJàÞPK`ÞPLpÞPNÞPO°ÞPRÀÞPS0ÞPS`ÞPSÞPT ÞPTÀÞPUPÞPUðÞPV€ÞPW ÞPW°ÞPXÞPX0ÞPXðÞP[°ÞP\`ÞP^@ÞP^`ÞP^ÐÞP_ ÞP`0ÞPbÞPb`ÞPepÞPf`ÞPfpÞPf ÞPg€ÞPhÐÞPjÞPlÞPmÀÞPpðÞPsàÞPtÐÞPvÞPw@ÞPz°ÞP{ ÞP{ÐÞP€ÞPÐÞPƒÞP… ÞP† ÞPˆÀÞPŸ0ÞP¢ ÞP¨ ÞP©ÞP©ÞPªÞP« ÞP­ðÞP®ÞP®€ÞP® ÞP°ðÞP±0ÞP± ÞP²`ÞP¹ÞP¹0ÞP¹PÞPºÞPº0ÞPºPÞPºpÞPºÞPº°ÞP»ÞP»`ÞP¿ ÞPÂàÞPÃðÞPÄÞPÅPÞPÅ ÞPÅÐÞPÅðÞPÆÞPǀÞPÉ ÞPÊÞPÏ0ÞPрÞPÔðÞPÕðÞPØ ÞPÜ`ÞPÞàÞPà ÞPà€ÞPãÞPä`ÞPëpÞPì€ÞPîÞPòÞPø€ÞPø°ÞPûàÞPüÐÞPý ÞP°ÞPPÞPpÞPPÞPÐÞP`ÞP°ÞP ÞP€ÞP ÞP@ÞP
PÞP
ÞP°ÞP ÞP`ÞPÀÞPÐÞPÀÞP ÞPÀÞPðÞPÐÞP@ÞPàÞP€ÞPðÞP`ÞPÞP ÞPàÞP@ÞPÞP  ÞP €ÞP ÐÞP!°ÞP"PÞP#@ÞP#ÞP#àÞP$€ÞP%ÞP& ÞP&PÞP& ÞP&ÐÞP'ÞP(ÞP*PÞP*ÞP*°ÞP.pÞP.ÞP/ÞP/@ÞP/ÞP/ðÞP0€ÞP0°ÞP0ðÞP2 ÞP;ÞP<pÞP<€ÞP< ÞP= ÞP>ÀÞP@ÞP@ÀÞPERROR: stack overflow in engine()!find-methodCan not open socket, no parent instancereadCan not open socket, no 'read' methodwriteCan not open socket, no 'write' methodget-propertyCan not open socket, file descriptor list is fullmy-parent ?dup IF ihandle>phandle THENlocal-mac-addressEXECUTEkey? IF key ELSE 0 THENget-msecsusdma-allocdma-freealloc-memfree-memdma-map-indma-map-outconfig-l@config-w@config-b@config-l!config-w!config-b!translate-my-addresswrite-mm-logBITMAP: start %lx, size %ld, blocksize %ld

0                 16                32                48              63


%dError: Bitmap start %lx, size %ld, requested address %lx, size %ld
ELF32: VirtAddr(%lx) != PhysAddr(%lx) not supported, aborting
ELF64: VirtAddr(%lx) != PhysAddr(%lx) not supported, aborting

ELF relocation out of bounds!
ERROR: Unhandled relocation (A) type %i
elf-claim-segmentFailed to allocate memorymemory allocation failed!
Device does not support virtio 1.0 %llx
Features error %llx
virtioblk_init%s: failed
virtioblk_read: Access beyond end of device!virtio-blk: Unaligned sector read %d
virtioblk_read failed! status = %i
virtio_9p_initslofVersion check failed, rc = %d
Attach failed, rc = %d
Walk failed, rc = %d
Stat failed, rc = %d
Open failed, rc = %d
Read failed, rc = %d
virtioscsi_initUnable to allocate virtio-net driver
virtionet: Failed to allocate buffers!
virtio-net: Receive buffer not big enough!
virtionet: Packet too big!
virtio_serial_initvirtio-serial: Failed to allocate buffers!
virtio_serial_putchar failed! 

Error: %s
9P2000.uunknown.usb_get_pipeusb_send_ctrlusb_transfer_bulkusb_setup_new_device%s: Failed
ErrorDevice Error%s: alloc failed %d
ohci_get_pipe_introhci_transfer_bulkohci_send_ctrlusb-ohci: Warning ED not aligned to 16byte boundary%s: alloc failed
Timed out waiting for interrupt %x
USB: Error TD null %p
USB: Error %s %p
usb-ohci: Not a bulk pipe.
usb-ohci: buffer size not supported - %d
%s: tds NULL recieved
ED Halted
%s: headp %08X tailp %08X next_td %08X attr %08X
%s: timed out - failed
Request: %02X   OHCI: initializing
usb-ohci: Unable to allocate memory
usb-ohci: Unable to allocate/unaligned HCCA memory %p
 ** HCD Reset failed...usb-ohci: oops could not allocate intr_pipe
Start removing device
usb-ohci: unable to setup device on port %d
ohci-hcdNOERRORCRCBITSTUFFINGDATATOGGLEMISMATCHSTALLDEVICENOTRESPONDINGPIDCHECKFAILUREUNEXPECTEDPIDDATAOVERRUNDATAUNDERRUNreservedBUFFEROVERRUNBUFFERUNDERRUNNOT ACCESSEDehci_exitehci_send_ctrlehci_transfer_bulk  EHCI: Initializing
usb-ehci: Unable to allocate memory
usb-ehci: reset failed
usb-ehci: Unable to allocate frame list
usb-ehci: Unable to allocate interrupt queue head
usb-ehci: Unable to allocate async queue head
usb-ehci: unable to setup device on port %d
%s: already called once 
usb-ehci: Not a control pipe.
Error allocating qTDs.
usb-ehci: control transfer timed out_
%s: handshake failed
usb-ehci: Not a bulk pipe.
usb-ehci: bulk transfer size too big
usb-ehci: bulk transfer timed out_
ehci-hcdusb_slof_populate_new_devices" dev-keyb.fs" INCLUDEDs" dev-mouse.fs" INCLUDEDs" dev-storage.fs" INCLUDEDs" dev-hub.fs" INCLUDEDDevice not supported %06X
%s: bulk reset failed
USB Interface class -%x- Not supported
usb_hid_kbd_init%s: unable to allocate keyboard buffer
usb-hub: NULL
usb-hub: unable to setup device on port %d
xhci_get_pipeTRB_TYPE  %d
usb-xhci: allocation failed for interrupt endpoint
usb-xhci: allocation failed for bulk endpoint
usb-xhci: %s alloc_intr failed  %p
usb-xhci: bulk transfer size too big
USB3 slot ID %d is too high (max is %d)
  XHCI: Initializing
usb-xhci: Unable to allocate memory
usb-xhci: 64 Byte context not supported
usb-xhci: failed to initialize XHCI controller.
xhci-hcdPowered-OFFPolling***  Disconnected ***DisabledLoopbackCompliancek******  Reset  ************ Enabled ******ERROR	

@{[]}\~|ABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$%^&*()
	 _+{}||:"~<>?079.136428/*-+
1234567890.|abcdefghijklmnopqrstuvwxyz1234567890
	 -=[]\\;'`,.//*-+
1234567890.\free spaceCreating common NVRAM partition
commonUnable to allocate veth driver
veth: Failed to allocate memory !
veth: Error %ld registering interface !
veth: Dropping too big packet [%d bytes]
veth: Error %ld sending packet !
 uX upu€u yuÀzuà{vv v0&v@'vP(v`vpv€vv vv°wvÀxvÐ|vàvèvøwwFailed to read MAC address from EEPROM!
82547EI/GI Copper82547EI Mobile52546EB Copper, Dual Port82546EB Fiber, Dual Port82546GB Copper, Dual Port82546GB Fiber, Dual Port82546GB SerDes, Dual Port82545EM Copper82545EM Fiber82545GM Copper82545GM Fiber82545GM SerDes82544EI Copper82544GC Copper82541EI Copper82541EI Mobile82541GI Copper82541GI Mobile82541ER Copper82541PI82540EM Mobile82540EP Mobile82540EP Desktop82540EM Desktop%03d
Aborted

Giving up after %d DHCP requests
done
v4  Requesting information via DHCP%s:     v6
 Initializing NICE3000: (net) Could not read MAC address  Reading MAC address from device: %02x:%02x:%02x:%02x:%02x:%02x
ERROR: Parameter string is too long.bootpdhcpipv6E3001: (net) Could not get IP address  Using IPv4 address: %d.%d.%d.%d
  Using IPv6 address: %s
E3002: (net) ARP request to TFTP server (%d.%d.%d.%d) failedE3008: (net) Can't obtain TFTP server IP address  Requesting file "%s" via TFTP from %d.%d.%d.%d
  Requesting file "%s" via TFTP from   TFTP: Received %s (%d KBytes)
(net) unknown TFTP errorE3004: (net) TFTP buffer of %d bytes is too small for %sE3009: (net) file not found: %sE3010: (net) TFTP access violationE3011: (net) illegal TFTP operationE3012: (net) unknown TFTP transfer IDE3013: (net) no such TFTP userE3017: (net) TFTP blocksize negotiation failedE3018: (net) file exceeds maximum TFTP transfer sizeE3005: (net) ICMP ERROR "net unreachablehost unreachableprotocol unreachableport unreachablefragmentation needed and DF setsource route failedE3014: (net) TFTP error occurred after %d bad packets receivedE3015: (net) TFTP error occurred after missing %d responsesE3016: (net) TFTP error missing block %d, expected block was %dE3006: (net) Could not initialize network device
 unable to allocate memory, parsing failed
tftp://
 tftp missing in %s

 missing ] in %s

 missing filename in %s

 wrong format IPV6 address in %s

 missing . seperator in %s

 missing domain in %s

 DNS failed for IPV6

ping device-path:[device-args,]server-ip,[client-ip[\nn]],[gateway-ip][,timeout]

E3000: Could not read MAC address

E3006: Could not initialize network device
%02x:%02x:%02x:%02x:%02x:%02x

  DHCP: Could not get ip address
  Own IP address: %d.%d.%d.%d
  Netmask : %d.%d.%d.%d
  Ping to %d.%d.%d.%d success

  Reading MAC address from device: ÿÿÿÿÿÿÿÿÿÿÿÿ://///:
ERROR:			Can't resolve domain name (DNS server is not presented)!

Giving up after %d DNS requests

ERROR:			Bad URL!

ERROR:			Bad host name!
  Requesting IP address via BOOTP:    %02d
Giving up after %d bootp requests
bladone
%d KBytesblksizeoctet  Receiving data:  
Repeating TFTP read request...
Lost ACK packets: %d
::::1%s%x%02x%s%x00:0:0:::0
0123456789abcdefÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0xî@EVALUATE¤çPŒ’¶†µðˆ@»ˆ@’µÐ…øîX´Pçð´èŠØŒ(‡8†…à‰à…¨(†p†XH…ˆ8†…à8‰à…¨ ëHñ`ËàFORTH-WORDLISTØËø0LASTWORD¤ŠØ…BP
(TIB	ˆƒðPOCKETS	Ä„EREGS
„(CIREGS
<„@CISTACK
x„XCOMP-BUFFER
´„xPAFLOF-START
ð„˜
HEAP-START,„¸HEAP-ENDh„Ø	FDT-START¤„ø
ROMFS-BASEä…EPAPR-MAGIC$…8EPAPR-IMA-SIZEd…XBRANCH`…x0BRANCHˆƒÐ
BREAKPOINTà…°LIT…ÐDOTICKH…èDUP€†OVER¸†PICKð†0DROP,†HSWAP\†`>R”†xR>à†R@,†¨RPICK †ÀDEPTHp†ØDEPTH!´†ðRDEPTHø‡RDEPTH!L‡ +è‡@-$‡X*`‡pLSHIFTœ‡ˆRSHIFT؇ ASHIFT‡¸ANDP‡ÐORŒ‡èXORȈ@ˆ!8ˆ0C@tˆHC!¨ˆ`W@äˆxW!ˆL@Tˆ¨L!ˆˆÀX@ĈØX!øˆðUNALIGNED-W@4‰UNALIGNED-W!|‰(UNALIGNED-L@̉HUNALIGNED-L!$‰h<„‰ˆU<̉ 0<‰¸=D‰Ð0=ˆ‰èDODOÀŠDO?DOŠDOLOOPxŠ0DO+LOOPÈŠHDOLEAVEXŠhDO?LEAVE”ŠˆEXITøŠ¨	SEMICOLON(ŠÀEXECUTEXŠàMOVE|‹RMOVE(P‹MRMOVE'\‹0RFILL'ЋHZCOUNT&à‹`	HASH-SIZE
H‹xHASH$,‹ 
CLEAN-HASH'$‹¸
HASH-TABLE#ð°-1
Hÿÿÿÿÿÿÿÿ‹ø0
HŒ1
HŒ82
HŒX3
HŒx4
HŒ˜8
HŒ¸H#10
HίH#20
H οH#FF
HÿH#FFFF
Hÿÿ8
H#FFFFFFFF
HÿÿÿÿXD#10
H
€/C
H /W
HÀ/L
Hà/X
HŽ/N
HŽ CELL
HŽ@/C*¤°‡€ŠØŽ`/W*¤Ð‡€ŠØŽ/L*¤ð‡€ŠØŽÀ/X*¤Ž‡€ŠØŽð/N*¤Ž0‡€ŠØ CA+¤Žp‡PŠØPWA+¤Ž ‡PŠØ€LA+¤ŽÐ‡PŠØ°XA+¤‡PŠØàNA+¤0‡PŠØCA1+¤°‡PŠØ@WA1+¤Ð‡PŠØpLA1+¤ð‡PŠØ XA1+¤Ž‡PŠØÐNA1+¤Ž0‡PŠØ‘CHAR+¤PŠØ‘0CELL+¤‘ŠØ‘XCHAR-¤°‡hŠØ‘€CELL-¤Ž0‡hŠØ‘°CHARS¤ŽpŠØ‘àCELLS¤0ŠØ’CHARS+¤`ŠØ’0CELLS+¤ ŠØ’XDOTO¤† ‘h††ˆˆ(‘hˆ@ŠØ’€SLITERAL¤† ‘h††ˆX‡P…àÿÿÿÿÿÿÿø‡à†ˆŠØ’Ø?DUP¤†…¨†ŠØ“PTUCK¤†p†(ŠØ“2DUP¤†(†(ŠØ“À3DUP¤Œh†@Œh†@Œh†@ŠØ“ð2OVER¤Œˆ†@Œˆ†@ŠØ”@2DROP¤†X†XŠØ”€3DROP¤†X†X†XŠØ”°NIP¤†p†XŠØ”èCLEAR¤Œ(‡ŠØ•ROT¤†ˆ†p† †pŠØ•H-ROT¤†p†ˆ†p† ŠØ•ˆ2SWAP¤†ˆ•˜† •˜ŠØ•È2ROT¤†ˆ†ˆ•Ø† † •ØŠØ–ROLL¤†“`…¨0•X†ˆŒH‡h…ˆÿÿÿÿÿÿÿ¸“`…¨0† •˜ŒH‡h…ˆÿÿÿÿÿÿÿ¸ŠØ–X-ROLL¤†“`…¨H†ˆ•X† †p†ˆŒH‡h…ˆÿÿÿÿÿÿÿ “`…¨0† †pŒH‡h…ˆÿÿÿÿÿÿÿ¸ŠØ—2>R¤† •X†ˆ†p†ˆ†ˆŠØ—à2R>¤† † † •X†ˆ†pŠØ˜02R@¤† † †¸†(†ˆ•X†ˆ†pŠØ˜€?PICK&˜à2*¤ŒH‡˜ŠØ˜øU2/¤ŒH‡°ŠØ™(2/¤ŒH‡ÈŠØ™X<<¤‡˜ŠØ™ˆ>>¤‡°ŠØ™°>>A¤‡ÈŠØ™ØINVERT¤ŒˆŠØšNOT¤šŠØš0TRUE
HÿÿÿÿÿÿÿÿšXFALSE
Hšx>¤†p‰˜ŠØš˜U>¤†p‰°ŠØšÈ<=¤š¨‰øŠØšø<>¤‰à‰øŠØ›(>=¤‰˜‰øŠØ›X0<=¤Œ(›ŠØ›ˆ0<>¤Œ(›8ŠØ›¸0>¤Œ(š¨ŠØ›è0>=¤Œ(›hŠØœU<=¤šØ‰øŠØœHU>=¤‰°‰øŠØœxWITHIN¤•X†•X›h…¨”šˆŠ¸š¨…¨šˆŠ¸šhŠØœ¨BETWEEN¤ŒH‡Pœ¸ŠØ@D2*¤™†(‰È‡h†ˆ™† ŠØ€UD2/¤†ˆ™8†¸…à?‡˜‡ø† ™8ŠØØD2/¤†ˆ™8†¸…à?‡˜‡ø† ™hŠØž@NEGATE¤Œ(†p‡hŠØž¨ABS¤†‰È…¨ž¸ŠØžàMAX¤“Љ˜…¨†p†XŠØŸ(MIN¤“К¨…¨†p†XŠØŸxU*¤‡€ŠØŸÈ1+¤ŒH‡PŠØŸð1-¤ŒH‡hŠØ  2+¤Œh‡PŠØ P2-¤Œh‡hŠØ €EVEN¤ Œ‡àŠØ °BOUNDS¤†(‡P†pŠØ èS>D¤†‰ÈŠØ¡ DNEGATE¤š†ˆž¸†‰ø† †p‡hŠØ¡PDABS¤†‰È…¨¡hŠØ¡¸M+¤†p†ˆ††ˆ‡P†† ‰°† †p‡hŠØ¢D+¤†ˆ¢† ‡PŠØ¢xD-¤¡h¢ˆŠØ¢¸*'¤†ˆ†‰È†ˆ† …¨†¸¢† ŠØ¢èUM*¤Œ(•˜…à@Œ(Š¢øŠ@ÿÿÿÿÿÿÿè†XŠØ£`M*¤“Ј†ˆ†ˆžð† žð£p† ‰È…¨¡hŠØ£Ð/'¤†ˆ†‰È†ˆ† †(†¸œˆ‡ø…¨0†ˆŒH‡ø† †¸‡h† ŠØ¤XUM/MOD¤…à@Œ(Š¤hŠ@ÿÿÿÿÿÿÿè†X†pŠØ¥SM/REM¤†(†ˆ†ˆ¡È†¸žð¥ † ‰È…¨ž¸† ‰È…¨ ž¸†pž¸†pŠØ¥xFM/MOD¤††ˆ“Ј‰È†ˆ¥ˆ†(›È† ‡à…¨0 0†p† ‡P†pŠ¸† †XŠØ¦8U/MOD¤Œ(†p¥ ŠØ§/MOD¤†ˆ¡0† ¦HŠØ§8/¤§H”øŠØ§xMOD¤§H†XŠØ§¨*/MOD¤†ˆ£à† ¦HŠØ§Ø*/¤§è”øŠØ¨WBSPLIT¤†(‡à†pŒÈ‡°ŠØ¨HLWSPLIT¤†H‡à†pŒè‡°ŠØ¨ XLSPLIT¤†p‡à†p‡°ŠØ¨øLBSPLIT¤¨¸†ˆ¨`† ¨`ŠØ©PXWSPLIT¤©†ˆ¨¸† ¨¸ŠØ© XBSPLIT¤©†ˆ©h† ©hŠØ©ðBWJOIN¤ŒÈ‡˜‡øŠØª@WLJOIN¤Œè‡˜‡øŠØªxBLJOIN¤ªP†ˆªP† ªˆŠØª°WBFLIP¤¨`†pªPŠØªøLWFLIP¤¨¸†pªˆŠØ«0LXJOIN¤‡˜‡øŠØ«hXLFLIP¤©†p«xŠØ« LBFLIP¤©h†p•Ø†pªÀŠØ«ØWXJOIN¤ªˆ†ˆªˆ† «xŠØ¬ XWFLIP¤©¸†p•Ø†p¬0ŠØ¬hBXJOIN¤ªÀ†ˆªÀ† «xŠØ¬°XBFLIP¤©«è†p«è«xŠØ¬øALIGNED¤Ž0 0‡PŽ0ž¸‡àŠØ­@I¤† †¸†p†ˆŠØ­˜J¤† † † †¸†p†ˆ†p†ˆ†p†ˆŠØ­ØUNLOOP¤† † † ”†ˆŠØ®H+!¤“ ˆ(‡P†pˆ@ŠØ®COMP ®ØOFF¤šˆ†pˆ@ŠØ®ðON¤šh†pˆ@ŠØ¯(<W@¤ˆˆ†…à€›h…¨…à‡hŠØ¯`2@¤†‘hˆ(†pˆ(ŠØ¯Ð2!¤††ˆˆ@† ‘hˆ@ŠØ°WBFLIPS¤ øŠ(@­¨ˆˆ«­¨ˆ ÐŠ`ÿÿÿÿÿÿÿÀŠØ°hLWFLIPS¤ øŠ(@­¨ˆ¸«@­¨ˆÐðŠ`ÿÿÿÿÿÿÿÀŠØ°èLBFLIPS¤ øŠ(@­¨ˆ¸«è­¨ˆÐðŠ`ÿÿÿÿÿÿÿÀŠØ±hXBFLIPS¤ øŠ(@­¨ˆè­­¨‰ŽŠ`ÿÿÿÿÿÿÿÀŠØ±èXWFLIPS¤ øŠ(@­¨ˆè¬x­¨‰ŽŠ`ÿÿÿÿÿÿÿÀŠØ²hXLFLIPS¤ øŠ(@­¨ˆè«°­¨‰ŽŠ`ÿÿÿÿÿÿÿÀŠØ²èFILL³hBLANK¤…à ³xŠØ³€ERASE¤…à³xŠØ³¸CATCHER
ð³ð
ABORT"-STR
ð´CATCH¤†è†ˆ´ˆ(†ˆ‡´ˆ@Šø† ´ˆ@† †XŒ(ŠØ´@THROW¤“`…¨`´ˆ(‡8† ´ˆ@† †p†ˆ‡†X† ŠØ´ØABORT¤Œ´èŠØµp#TIB
ðµ IB
€µÀ#IB
ðµà	SOURCE-ID
€¶SOURCE¤µÐµðˆ(ŠØ¶(>IN
ð¶`TERMINAL¤„’µÐµ°ˆ(µðˆ@Œ(’¶ŠØ¶€BL
H ¶øBELL
H·BS
H·8CARRET
H
·XLINEFEED
H
·xEMIT
(· CR
(·ÀTYPE¤ øŠ((­¨ˆX·°Š@ÿÿÿÿÿÿÿ؊طàLL-CR¤·h·°··°ŠØ¸@SPACE¤··°ŠØ¸€SPACES¤Œ(Š(¸Š@ÿÿÿÿÿÿÿèŠØ¸°COUNT¤†‘@†pˆXŠØ¹PACK¤††ˆ †p††¸ˆp‹† ŠØ¹@UPC¤†…àa…àzX…¨…à ‡hŠØ¹¨LCC¤†…àA…àZX…¨…à ‡PŠØº KEY
(º˜KEY?
(º¸ACCEPT
(ºØSPAN
ðºøEXPECT¤ºè»ˆ@ŠØ»REFILL¤¶‰ø…¨8¶8»(Œ(¶pˆ@šhŠ¸¶Œ‰à…¨šˆŠ¸…àe´èŠØ»PBASE
ð¼DECIMAL¤¼(ˆ@ŠØ¼8HEX¤Œè¼(ˆ@ŠØ¼xOCTAL¤ŒÈ¼(ˆ@ŠØ¼°PAD¤À…à‡PŠØ¼èTODIGIT¤†…à	š¨…¨…à'‡P…à0‡PŠØ½(MU/MOD¤††ˆ§† †p†ˆ¥ † ŠØ½°<#¤¼ø†ˆ@ŠØ¾HOLD¤¼ø†ˆ( 0“ †pˆ@ˆpŠØ¾HSIGN¤‰È…¨…à-¾XŠØ¾¨#¤¼(ˆ(½À•X½@¾XŠØ¾ø#S¤¿“Їø…¨…ˆÿÿÿÿÿÿÿÈŠØ¿H#>¤”¼ø†ˆ(“ ‡hŠØ¿ (.)¤¾ ††ˆžðŒ(¿X† ¾¸¿°ŠØ¿ðU#¤¼(ˆ(§†p½@¾XŠØÀXU#S¤Àh†…¨…ˆÿÿÿÿÿÿÿЊØÀ¨U#>¤†X¼ø†ˆ(“ ‡hŠØÀø(U.)¤¾ À¸ÁŠØÁH.¤À·ð¸ŠØÁ€S.¤ÁŠØÁ¸U.¤ÁX·ð¸ŠØÁà.R¤†pÀ•X“Љ˜…¨(†(‡h¸À…ˆ†X·ðŠØÂU.R¤†pÁX•X“Љ˜…¨(†(‡h¸À…ˆ†X·ðŠØ¨.D¤¼(ˆ(†p¼PÁ¼(ˆ@ŠØÃ8.H¤¼(ˆ(†p¼ˆÁ¼(ˆ@ŠØÐ.S¤†è†‰È…¨†XŠ¸Œ(Š(@†è­¨‡h 0†@ÁŠ@ÿÿÿÿÿÿÿÀŠØÃè?¤ˆ(ÁŠØĘDIGIT¤†(¹¸†…àA…àZX…¨…à‡h…à0‡h†•XŒ(†pœ¸…¨ ”øšh…ˆ†XšˆŠØÄÈ>NUMBER¤†‰ø…¨Š¸†(ˆX¼(ˆ(ÄØ…¨¸†p†ˆ†p†ˆ†ˆ¼(ˆ(ŸØ†p¼(ˆ(£p•X‡P† Œ(¢ˆ† ‘@†  0…ˆÿÿÿÿÿÿþè†XŠØÅÐ$NUMBER¤†‰ø…¨ †X†XšhŠ¸†ˆ††ˆˆX…à-‰à†…¨x† ‘@†  0†‰ø…¨(†X†X†XšhŠ¸†ˆ†ˆŒ(Œ(† † Åè”ø‰ø…¨8†X†p…¨ž¸šˆŠ¸†X†X†XšhŠØÇALLOT¤À‡P’ÀŠØÈè,¤Àˆ@Ž0ÈøŠØÉ(C,¤Àˆp°ÈøŠØÉhW,¤Àˆ ÐÈøŠØɨL,¤ÀˆÐðÈøŠØÉèX,¤À‰ŽÈøŠØÊ(ALIGN¤ÀŽ0 0‡à…¨ Œ(Éx…ˆÿÿÿÿÿÿÿ°ŠØÊhPLACE¤“Јp‘@†p‘ð øŠ(H†ˆX­¨ˆp‘@ŒH‘ðŠ`ÿÿÿÿÿÿÿ¸†XŠØÊØSTRING,¤À†( ‘ðÈøÊèŠØˈNOOP¤ŠØƒpCURRENT
€ƒ˜ÌLAST¤Ì‘hŠØÌ(SEARCH-ORDER
ðƒ˜ÌXCONTEXT
€ÌxÌø	LINK>NAME¤‘hŠØÍ NAME>¤‘@†ˆX ’@­XŠØÍPLINK>¤Í8Í`ŠØÍ NAME>STRING¤‘@¹ŠØÍÐLATEST
ðÎ(REVEAL)
(Î(HEADER¤ÊxÀÌ8ˆ(É8Έ@Œ(ÉxË ÊxŠØÎPREVEAL¤Îˆ(Í8ÍèÎ@Έ(Ì8ˆ@ŠØÎÈ	STRING=CI&DÏ0(FIND)
(ÏP((FIND))¤†…¨x†ˆ“І¸Í8ÍèÏH…¨”† Š¸† ˆ(…ˆÿÿÿÿÿÿÿp”ÀšˆŠØÏp(FIND-ORDER)¤Í††ˆÌpœˆ…¨“І¸ˆ(‘hˆ(Ï`“`…¨(”ø”ø† †XŠ¸† ‘À…ˆÿÿÿÿÿÿÿ@† ”ÀŒ(ŠØÐ8($FIND)¤ÐP†…¨0Í8†Í`†pˆXšhŠØÑ@$FIND¤“ÐÑX…¨0†X”ø”øšh…ˆšˆŠØѸ
'IMMEDIATE
HÒ0
IMMEDIATE?¤ÒH‡à›ÈŠØÒX	IMMEDIATE¤Ì8ˆ(‘h†ˆXÒH‡ø†pˆpŠØҘFINDCHAR¤†pŒ(Š(À†(­¨‡PˆX†(†·‰à…¨›…ˆ‰à…¨0­¨®X”ø”øšhŠ¸Š@ÿÿÿÿÿÿÿ@†X†XšˆŠØÓPARSE¤†ˆµÐ¶pˆ(‡P»ˆ(¶pˆ(‡h“І Ó …¨0”ø†ŒH‡P…ˆ†¶p® ŠØÔ(SKIPWS¤µÐ»ˆ(†¶pˆ(š¨…¨p†(¶pˆ(‡PˆX·›…¨(ŒH¶p® …ˆÿÿÿÿÿÿÿ`†X†XŠØÕ
PARSE-WORD¤Õ·Ô8ŠØÕðWHICHPOCKET
ðÖ0POCKET¤„ ÖHˆ(…à‡€‡PÖHˆ(ŒH‡P†…à‰à…¨†XŒ(ÖHˆ@ŠØÖXWORD¤Öh†ˆÔ8††¸ˆp ø† †•ØŠ(8‘@­¨ˆX†(ˆpŠ@ÿÿÿÿÿÿÿȆXŠØ× CHAR¤Ö†XˆXŠØ×à(¤…à)Ô8”ŠØØ\¤¶pˆ( 0¶pˆ@·Ô8”ŠØØXSTATE
ðظ[¤ØȯŠØØØ]¤…àØȈ@ŠØÙ?COMP¤ØȈ(…¨Š¸…àÿÿÿÿÿÿÿz´èŠØÙHCOMPILE,¤É8ŠØÙ¨:¤ÖÎ`…ø¤ÙÀÙŠØÙØ:NONAME¤ÊxÀ…ø¤ÙÀÙŠØÚ(;¤ÙX…øŠØÙÀÎØØèŠØڀC"¤ÙX…à"Ô8…ø’ðÙÀ†Éx øŠ((­¨ˆXÉxŠ@ÿÿÿÿÿÿÿØÊxŠØÚÐS"¤ØȈ(…¨(Úà…ø¹ÙÀŠ¸…à"Ô8††ˆÖh††ˆ†p‹† † ŠØۀZ"¤ې“ЇPŒ(†pˆp†XŠØÜH."¤ØȈ(…¨(ې…ø·ðÙÀŠ¸…à"Ô8·ðŠØÜ .(¤…à)Ô8·ðŠØÝ(COMPILE¤† ‘h†ˆ(ÙÀ†ˆŠØÝhTHERE
ðÝÀ+COMP¤ØȈ(ŒHØÈ® …¨Š¸ÀÝЈ@„’À݀¤ŠØÝà-COMP¤ŒØÈ® ØȈ(…¨Š¸݀Š¸ÝЈ(’À„ŠøŠØހRESOLVE-ORIG¤À†(‘h‡h†pˆ@ŠØß AHEAD¤Ýð…ø…ˆÙÀÀŒ(ÙÀŠØßxIF¤Ýð…ø…¨ÙÀÀŒ(ÙÀŠØßÐTHEN¤ÙXß8ސŠØà(ELSE¤ÙX…ø…ˆÙÀÀŒ(ÙÀ†pß8ŠØà`CASE¤ÝðŒ(ŠØàÈENDCASE¤ÙX…ø†XÙÀ“`…¨( 0†pà8…ˆÿÿÿÿÿÿÿÀސŠØàøOF¤ÙX †ˆ…ø†(ÙÀ…ø‰àÙÀßà…ø†XÙÀ† ŠØáˆENDOF¤ÙX†ˆàp† ŠØâRESOLVE-DEST¤À‘h‡hÙÀŠØâXBEGIN¤ÝðÀŠØâ AGAIN¤ÙX…ø…ˆÙÀâpސŠØâÐUNTIL¤ÙX…ø…¨ÙÀâpސŠØã WHILE¤ÙXßà†pŠØãpREPEAT¤ÙXâàà8ŠØã¨LEAVES
ðãàRESOLVE-LOOP¤ãðˆ(“`…¨P†ˆ(†pÀ†(‡h†pˆ@…ˆÿÿÿÿÿÿÿ˜À‡hÙÀãðˆ@ŠØäDO¤Ýðãðˆ(À…øŠÙÀŒ(ãðˆ@ŠØäÈ?DO¤Ýðãðˆ(…øŠ(ÙÀÀÀãðˆ@Œ(ÙÀŠØå8LOOP¤ÙX…øŠ@ÙÀäސŠØå¸+LOOP¤ÙX…øŠ`ÙÀäސŠØæLEAVE¤ÙX…øŠ€ÙÀãðˆ(Àãðˆ@ÙÀŠØæX?LEAVE¤ÙX…øŠ ÙÀãðˆ(Àãðˆ@ÙÀŠØæÈSAVE-SOURCE¤† µÐ†ˆµðˆ(†ˆ¶†ˆ»ˆ(†ˆ¶pˆ(†ˆ†ˆŠØç8RESTORE-SOURCE¤† † ¶pˆ@† »ˆ@† ’¶† µðˆ@† ’µÐ†ˆŠØçØOK-STRokèˆABORTED-STRAbortedè 
EXCEPTION-STRException #èÀUNKNOWN-STRUndefined wordèèHW-EXCEPTION-HANDLER
(éSHOW-STACK?
€é@	SHOWSTACK¤Œ’éXŠØéhNOSHOWSTACK¤Œ(’éXŠØé¨PRINT-STACK¤éX…¨(†ˆ†ˆÃø† † ŠØéèPRINT-EXCEPTION¤†…àÿÿÿÿÿÿÿ‰à…¨8…øé¹·ð·Ð†XŠ¸†…à‰à…¨†XŠ¸é0ŠØêPPRINT-STATUS¤¸†‰ø…¨(ê…ø蘅ˆ8†Œ‰à…¨0…ø踹·ð…ˆP†…àÿÿÿÿÿÿÿþ‰à…¨8´0ˆ(¹·ð†X…ˆêp·ÐŠØë0COMPILE-WORD¤“ÐÑX…¨PÒp…¨ ”ø”øŠøŠ¸ÙÀ”Š¸“ÐÇ0…¨ ·ð…àÿÿÿÿÿÿÿ´è…ø…àÙÀÙÀ”ŠØìxINTERPRET-WORD¤“ÐÑX…¨(†X”ø”øŠøŠ¸“ÐÇ0…¨ ·ð…àÿÿÿÿÿÿÿ´è†ˆ”† ŠØíx	INTERPRET¤Œ(¶pˆ@Ö†…¨PØȈ(…¨ì…ˆí…ˆÿÿÿÿÿÿÿ”ŠØ‚EVAL¤‚0ŠØîøDOABORT"¤†p…¨(´0ˆ@…àÿÿÿÿÿÿÿþ´è†XŠØï ABORT"¤Úà…øï8ÙÀŠØï
UNDEFINED-STRundefined word ïÐSET-UNDEFINED-WORD¤Öh†ˆ…øï膈X †¸†p‹†¸†ˆX ‡P†p††¸ˆX‡P†¸ˆp‹† ŠØïø'¤ÖÑȉø…¨ ðšh†pï8ŠØðèQUIT¤Œ(‡8Ø趘†èÁ…à>·°¸»`…¨P¸…øîX´P†ëH…¨ÿÿÿÿÿÿÿx…ˆÿÿÿÿÿÿÿHŠØñPMAP-FILE
(ò(
UNMAP-FILE
(òP
WRITE-FILE
(òxINCLUDED¤ò@“Іˆ†ˆ øŠ(¨† †¸†p†ˆ†¸‡h†¸†p“зÓ …¨”ø††ˆ‚0†  Š`ÿÿÿÿÿÿÿX† † òhŠØò INCLUDE¤Öò¸ŠØóÀ$CREATE¤Î`…øØÙÀ…øËð‘hÙÀÎØŠØóøCREATE¤ÖôŠØôhDODOES>¤† ‘hΈ(Í°‘hˆ@ŠØô˜DOES>¤…øô°ÙÀŠØôøCONSTANT¤ÖÎ`…ø
HÙÀÙÀÎØŠØõ0VALUE¤ÖÎ`…ø
€ÙÀÙÀÎØŠØõVARIABLE¤ÖÎ`…ø
ðÙÀŒ(ÙÀÎØŠØõèBUFFER:¤ÖÎ`…ø(ÙÀÈøÎØŠØöPDEFER¤ÖÎ`…ø
(ÙÀ…øµ€ÙÀÎØŠØö°ALIAS¤ÖÎ`…ø
8ÙÀðøÙÀÎØŠØ÷STRUCT¤Œ(ŠØ÷x
END-STRUCT¤†XŠØ÷ FIELD¤ÖÎ`…ø
¸ÙÀ†(É8‡PÎØŠØ÷ÐLITERAL¤…ø…àÙÀÙÀŠØø8	[COMPILE]¤ðøÙÀŠØø€POSTPONE¤Ö“ÐÑX‰ø…¨ ðšh†pï8Òp‰ø…¨0…ø…øÙÀÙÀ…øÙÀÙÀ”ŠØø¸[CHAR]¤×ðøPŠØù[']¤ðø…ø…øÙÀÙÀŠØùÀFIND¤†¹ÑX…¨H•X†Xšh†pÒp…¨ž¸Š¸šˆŠ¸ŠØúTO¤ðøØȈ(…¨(…ø’ÙÀÙÀŠ¸‘hˆ@ŠØú¨BEHAVIOR¤‘hˆ(ŠØû(>BODY¤Œh’‡PŠØû`BODY>¤Œh’‡hŠØû˜	RECURSIVE¤ÎØŠØûÐRECURSE¤Îˆ(Í°ÙÀŠØüd#¤Ö¼(ˆ(†ˆ¼P‚0† ¼(ˆ@ŠØüHh#¤Ö¼(ˆ(†ˆ¼ˆ‚0† ¼(ˆ@ŠØü°o#¤Ö¼(ˆ(†ˆ¼À‚0† ¼(ˆ@ŠØý
hv-putchar$Äý€
hv-getchar%ý 
hv-haschar%<ýÀ
hv-reg-crq%týàhv-free-crq%Àþhv-send-crq&þ 
hv-put-tceÀþ@check-and-patch-sc1#8þ`RB@ þˆRB! Hþ RW@ þ¸RW! ÌþÐRL@!þèRL!!PÿRX@!˜ÿRX!!Ôÿ0hv-logical-memop"ÿHhv-cas"hÿphv-rtas-update"°ÿˆget-print-version"üÿ¨virtio-setup-vd#|ÿÐvirtio-vring-size#¸ÿøvirtio-get-qsize(Ð virtio-get-configItHvirtio-set-qaddrHôpvirtio-blk-initI<˜virtio-blk-shutdownGØÀvirtio-blk-readHèvirtio-scsi-initEôvirtio-scsi-shutdownF,8virtio-scsi-sendFh`virtio-fs-initH`ˆvirtio-fs-shutdownH¸¨virtio-fs-loadE¬Ðvirtio-net-openFÄðvirtio-net-closeGvirtio-net-readGP@virtio-net-writeG”hvirtio-serial-initBPvirtio-serial-shutdownBˆ¸virtio-serial-putcharBÄàvirtio-serial-getcharCvirtio-serial-hascharC@0USB-OHCI-REGISTERCxXUSB-EHCI-REGISTERCœ€USB-XHCI-REGISTERCÀ¨USB-HCD-INITCäÐUSB-HCD-EXITD ðUSB-HID-INITD\USB-HID-EXITD”0
USB-READ-KEYBDÌPUSB-KEY-AVAILABLEEpUSB-HUB-INITE<˜USB-MSC-INITEt¸USB-MSC-EXIT8ØØUSB-TRANSFER-CTRL9øUSB-TRANSFER-BULK9X 
bootmsg-cp9¬Hbootmsg-warning9ìh
bootmsg-error:0bootmsg-debugcp:p°bootmsg-setlevel:´Øbootmsg-nvupdate;Lbootmsg-checklevel:ô(
ELF-LOAD-FILE;pPELF-LOAD-FILE-TO-ADDR;Ìpnvram-c@<4˜nvram-c!=¸nvram-w@<lØnvram-w!=Xønvram-l@<¤nvram-l!=œ8nvram-x@<ÜXnvram-x!=àxinternal-reset-nvram?Иnvram-debug@ÀÀ
wipe-nvramA°àget-nvram-partition>$get-named-nvram-partition>(new-nvram-partition?Xincrease-nvram-partition?p€erase-nvram-partitionAP°delete-nvram-partition)Øinternal-get-envAÔ	internal-add-env?ô	(internal-del-env@`	Pinternal-set-env@ä	xinternal-nvram-init)p	 get-nvram-base)À	Èget-nvram-size)ø	èget-flash-base*4
get-flash-size*l
(get-mbx-base*¤
HLIBVETH-OPEN*Ü
h
LIBVETH-CLOSE+@
ˆLIBVETH-READ+|
¨
LIBVETH-WRITE+Ä
ÈE1K-OPEN,
è	E1K-CLOSE,dE1K-READ, (	E1K-WRITE,äH
E1K-MAC-SETUP-(hNET-LOAD- ˆNET-PING18¨HID0!0¬ÈHID0@1àHID1!/¼øHID1@/üHID4!04(HID4@0t@HID5!-üXHID5@.4pMSR@.¤ˆMSR!.l SDR1@/¸SDR1!.ÜÐPVR@/LèPIR@/„
TBL@1|
TBU@1´
0DABR@2$
HDABR!1ì
`HIOR@2”
xHIOR!2\
SPRG0@3
¨SPRG0!2Ì
ÀSPRG1@3t
ØSPRG1!3<
ðSPRG2@3äSPRG2!3¬ SPRG3@4T8SPRG3!4PHSPRG0@4ÄhHSPRG0!4ŒˆHSPRG1@54¨HSPRG1!4üÈDEC@7°èDEC!7xMMCR0!5lPMC1@5¬0ICBI5èÐJUMP-CLIENT60`CLIENTINTERFACE
(.WRITE-LOG-BYTE-ENTRY
HH°WRITE-LOG-BYTE-ENTRY¤Ðˆ(ŠØàCALL-C6¼ 
START-RTAS6p8
FLUSHCACHE7XBM-ALLOCATOR-INIT7èxBM-ALLOC80 BM-FREE8tÀCRASH6hàDAAR
ððøDUMBER¤ˆ(ˆp…à® ŠØBOOT-EXCEPTION-HANDLER
(˜‹ØHERE
€ÂHCLIENT-ENTRY-POINT
HJP€ROMFS-LOOKUP-ENTRY
HfpNICEINIT¤…ø†X’·°…øψ’Ï`…ø”’Î@…à…àx¹†(‡h…ø‚0´PŠØhex
' ll-cr to cr
get-flash-base VALUE flash-addr
get-nvram-base CONSTANT nvram-base
get-nvram-size CONSTANT nvram-size
0 CONSTANT default-hvtermno
4096 CONSTANT disp-size
CREATE prevga-disp-buf 4096 allot
0 value disp-ptr
true value store-prevga?
: store-to-disp-buffer         ( ch  --  )
prevga-disp-buf disp-ptr disp-size MOD + c!
disp-ptr 1 + to disp-ptr
;
: hvterm-emit
store-prevga? IF
dup store-to-disp-buffer
THEN
default-hvtermno SWAP hv-putchar
;
: hvterm-key?  default-hvtermno hv-haschar ;
: hvterm-key   BEGIN hvterm-key? UNTIL default-hvtermno hv-getchar ;
' hvterm-emit to emit
' hvterm-key  to key
' hvterm-key? to key?
: serial-emit hvterm-emit ;
: serial-key? hvterm-key? ;
: serial-key  hvterm-key  ;
clean-hash
: hash-find ( str len head -- 0 | link )
>r 2dup 2dup hash                  ( str len str len hash          R: head )
dup >r @ dup                       ( str len str len *hash *hash   R: head hash )
IF                                 ( str len str len *hash         R: head hash )
link>name name>string string=ci ( str len true|false            R: head hash )
dup 0=
IF
THEN
ELSE
nip nip                         ( str len 0                     R: head hash )
THEN
IF                                 \ hash found
2drop r> @ r> drop              (  *hash                        R: )
exit
THEN                               \ hash not found
r> r> swap >r ((find))             ( str len head                  R: hash=0 )
dup
IF
dup r> !                        ( link                          R: )
ELSE
r> drop                         ( 0                             R: )
THEN
;
: hash-reveal  hash off ;
' hash-reveal to (reveal)
' hash-find to (find)
: >name ( xt -- nfa ) \ note: still has the "immediate" field!
BEGIN char- dup c@ UNTIL ( @lastchar )
dup dup aligned - cell+ char- ( @lastchar lenmodcell )
dup >r -
BEGIN dup c@ r@ <> WHILE
cell- r> cell+ >r
REPEAT
r> drop char-
;
VARIABLE mask -1 mask !
: default-hw-exception s" Exception #" type . ;
' default-hw-exception to hw-exception-handler
: diagnostic-mode? false ;	\ 2B DOTICK'D later in envvar.fs
: memory-test-suite ( addr len -- fail? )
diagnostic-mode? IF
." Memory test mask value: " mask @ . cr
." No memory test suite currently implemented! " cr
THEN
false
;
: 0.r  0 swap <# 0 ?DO # LOOP #> type ;
: 2log ( n -- lb{n} )
8 cells 0 DO 1 rshift dup 0= IF drop i LEAVE THEN LOOP
;
: log2  ( n -- log2-n )
1- 2log 1+
;
CREATE $catpad 400 allot
: $cat ( str1 len1 str2 len2 -- str3 len3 )
>r >r dup >r $catpad swap move
r> dup $catpad + r> swap r@ move
r> + $catpad swap ;
: $cat-comma ( str2 len2 str1 len1 -- "str1, str2" len1+len2+2 )
2dup + s" , " rot swap move 2+ 2swap $cat
;
: $cat-space ( str2 len2 str1 len1 -- "str1 str2" len1+len2+1 )
2dup + bl swap c! 1+ 2swap $cat
;
: $cathex ( str len val -- str len' )
(u.) $cat
;
: 2CONSTANT    CREATE , , DOES> [ here ] 2@ ;
CONSTANT <2constant>
: $2CONSTANT  $CREATE , , DOES> 2@ ;
: 2VARIABLE    CREATE 0 , 0 ,  DOES> ;
: (is-user-word) ( name-str name-len xt -- ) -rot $CREATE , DOES> @ execute ;
: zplace ( str len buf -- )  2dup + 0 swap c! swap move ;
: rzplace ( str len buf -- )  2dup + 0 swap rb! swap rmove ;
: strdup ( str len -- dupstr len ) here over allot swap 2dup 2>r move 2r> ;
: str= ( str1 len1 str2 len2 -- equal? )
rot over <> IF 3drop false ELSE comp 0= THEN ;
: test-string ( param len -- true | false )
0 ?DO
dup i + c@                     \ Get character / byte at current index
dup 20 <  swap 7e >  OR IF     \ Is it out of range 32 to 126 (=ASCII)
drop FALSE UNLOOP EXIT      \ FALSE means: No ASCII string
THEN
LOOP
drop TRUE    \ Only ASCII found --> it is a string
;
: #aligned ( adr alignment -- adr' ) negate swap negate and negate ;
: #join  ( lo hi #bits -- x )  lshift or ;
: #split ( x #bits -- lo hi )  2dup rshift dup >r swap lshift xor r> ;
: /string ( str len u -- str' len' )
>r swap r@ chars + swap r> - ;
: skip ( str len c -- str' len' )
>r BEGIN dup WHILE over c@ r@ = WHILE 1 /string REPEAT THEN r> drop ;
: scan ( str len c -- str' len' )
>r BEGIN dup WHILE over c@ r@ <> WHILE 1 /string REPEAT THEN r> drop ;
: split ( str len char -- left len right len )
>r 2dup r> findchar IF >r over r@ 2swap r> 1+ /string ELSE 0 0 THEN ;
: rfindchar ( str len char -- offs true | false )
swap 1 - 0 swap do
over i + c@
over dup bl = if <= else = then if
2drop i dup dup leave
then
-1 +loop =
;
: rsplit ( str len char -- left len right len )
>r 2dup r> rfindchar IF >r over r@ 2swap r> 1+ /string ELSE 0 0 THEN ;
: left-parse-string ( str len char -- R-str R-len L-str L-len )
split 2swap ;
: replace-char ( str len chout chin -- )
>r -rot BEGIN 2dup 4 pick findchar WHILE tuck - -rot + r@ over c! swap REPEAT
r> 2drop 2drop
;
: \-to-/ ( str len -- str' len ) strdup 2dup [char] \ [char] / replace-char ;
: isdigit ( char -- true | false )
30 39 between
;
: ishexdigit ( char -- true | false )
30 39 between 41 46 between OR 61 66 between OR
;
: $dh-number ( addr len -- true | number false )
base @ >r
decimal
dup 2 > IF
over dup c@ [char] 0 =
over 1 + c@ 20 or [char] x =
AND IF hex 2 + swap 2 - rot THEN drop
THEN
$number
r> base !
;
: //  dup >r 1- + r> / ; \ division, round up
: c@+ ( adr -- c adr' )  dup c@ swap char+ ;
: 2c@ ( adr -- c1 c2 )  c@+ c@ ;
: 4c@ ( adr -- c1 c2 c3 c4 )  c@+ c@+ c@+ c@ ;
: 8c@ ( adr -- c1 c2 c3 c4 c5 c6 c7 c8 )  c@+ c@+ c@+ c@+ c@+ c@+ c@+ c@ ;
: 4dup  ( n1 n2 n3 n4 -- n1 n2 n3 n4 n1 n2 n3 n4 )  2over 2over ;
: 4drop  ( n1 n2 n3 n4 -- )  2drop 2drop ;
: 5dup  ( 1 2 3 4 5 -- 1 2 3 4 5 1 2 3 4 5 )
4 pick 4 pick 4 pick 4 pick 4 pick ;
: 5drop 4drop drop ;
: 5nip
nip nip nip nip nip ;
: 6dup  ( 1 2 3 4 5 6 -- 1 2 3 4 5 6 1 2 3 4 5 6 )
5 pick 5 pick 5 pick 5 pick 5 pick 5 pick ;
: signed ( n1 -- n2 ) dup 80000000 and IF FFFFFFFF00000000 or THEN ;
: <l@ ( addr -- x ) l@ signed ;
: -leading  BEGIN dup WHILE over c@ bl <= WHILE 1 /string REPEAT THEN ;
: (parse-line)  skipws 0 parse ;
: hex-byte ( char0 char1 -- value true|false )
10 digit IF
swap 10 digit IF
4 lshift or true EXIT
ELSE
2drop 0
THEN
ELSE
drop
THEN
false EXIT
;
: parse-hexstring ( dst-adr -- dst-adr' )
[char] ) parse cr                 ( dst-adr str len )
bounds ?DO                        ( dst-adr )
i c@ i 1+ c@ hex-byte IF       ( dst-adr hex-byte )
>r dup r> swap c! 1+ 2      ( dst-adr+1 2 )
ELSE
drop 1                      ( dst-adr 1 )
THEN
+LOOP
;
: add-specialchar ( dst-adr special -- dst-adr' )
over c! 1+                        ( dst-adr' )
1 >in +!                          \ advance input-index
;
: parse-" ( dst-adr -- dst-adr' )
[char] " parse dup 3 pick + >r    ( dst-adr str len R: dst-adr' )
>r swap r> move r>                ( dst-adr' )
;
: (") ( dst-adr -- dst-adr' )
begin                             ( dst-adr )
parse-"                        ( dst-adr' )
>in @ dup span @ >= IF         ( dst-adr' >in-@ )
drop
EXIT
THEN
ib + c@
CASE
[char] ( OF parse-hexstring ENDOF
[char] " OF [char] " add-specialchar ENDOF
dup      OF EXIT ENDOF
ENDCASE
again
;
CREATE "pad 100 allot
: " ( [text<">< >] -- text-str text-len )
state @ IF                        \ compile sliteral, pstr into dict
"pad dup (") over -            ( str len )
['] sliteral compile, dup c,   ( str len )
bounds ?DO i c@ c, LOOP
align ['] count compile,
ELSE
pocket dup (") over -          \ Interpretation, put string
THEN                              \ in temp buffer
; immediate
: (cr carret emit ;
: $forget ( str len -- )
2dup last @            ( str len str len last-bc )
BEGIN
dup >r             ( str len str len last-bc R: last-bc )
cell+ char+ count  ( str len str len found-str found-len R: last-bc )
string=ci IF       ( str len R: last-bc )
r> @ last ! 2drop clean-hash EXIT ( -- )
THEN
2dup r> @ dup 0=   ( str len str len next-bc next-bc )
UNTIL
drop 2drop 2drop            \ clean hash table
;
: forget ( "old-name<>" -- )
parse-word $forget
;
: linked ( var -- )  here over @ , swap ! ;
HEX
VARIABLE wordlists  forth-wordlist wordlists !
: wordlist ( -- wid )  here wordlists linked 0 , ;
10 CONSTANT max-in-search-order	\ should define elsewhere
: also ( -- )  clean-hash  context dup cell+ dup to context  >r @ r> ! ;
: previous ( -- )  clean-hash  context cell- to context ;
: only ( -- )  clean-hash  search-order to context  ( minimal-wordlist search-order ! ) ;
: seal ( -- )  clean-hash  context @  search-order dup to context  ! ;
: get-order ( -- wid_n .. wid_1 n )
context >r search-order BEGIN dup r@ u<= WHILE
dup @ swap cell+ REPEAT r> drop
search-order - cell / ;
: set-order ( wid_n .. wid_1 n -- )	\ XXX: special cases for 0, -1
clean-hash  1- cells search-order + dup to context
BEGIN dup search-order u>= WHILE
dup >r ! r> cell- REPEAT drop ;
: get-current ( -- wid )  current ;
: set-current ( wid -- )  to current ;
: definitions ( -- )  context @ set-current ;
: VOCABULARY ( C: "name" -- ) ( -- )  CREATE wordlist drop  DOES> clean-hash  context ! ;
: FORTH ( -- )  clean-hash  forth-wordlist context ! ;
: .voc ( wid -- ) \ display name for wid \ needs work ( body> or something like that )
dup cell- @ ['] vocabulary ['] forth within IF
2 cells - >name name>string type ELSE u. THEN  space ;
: vocs ( -- ) \ display all wordlist names
cr wordlists BEGIN @ dup WHILE dup .voc REPEAT drop ;
: order ( -- )
cr ." context:  " get-order 0 ?DO .voc LOOP
cr ." current:  " get-current .voc ;
: voc-find ( wid -- 0 | link )
clean-hash  cell+ @ (find)  clean-hash ;
: (function) ;
defer (defer)
0 value (value)
0 constant (constant)
variable (variable)
create (create)
alias (alias) (function)
cell buffer: (buffer:)
' (function) @        \ ( <colon> )
' (function) cell + @ \ ( ... <semicolon> )
' (defer) @           \ ( ... <defer> )
' (value) @           \ ( ... <value> )
' (constant) @	      \ ( ... <constant> )
' (variable) @        \ ( ... <variable> )
' (create) @          \ ( ... <create> )
' (alias) @           \ ( ... <alias> )
' (buffer:) @         \ ( ... <buffer:> )
forget (function)
constant <buffer:>
constant <alias>
constant <create>
constant <variable>
constant <constant>
constant <value>
constant <defer>
constant <semicolon>
constant <colon>
' lit      constant <lit>
' sliteral constant <sliteral>
' 0branch  constant <0branch>
' branch   constant <branch>
' doloop   constant <doloop>
' dotick   constant <dotick>
' doto     constant <doto>
' do?do    constant <do?do>
' do+loop  constant <do+loop>
' do       constant <do>
' exit     constant <exit>
' doleave  constant <doleave>
' do?leave  constant <do?leave>
500 CONSTANT AVAILABLE-SIZE
4000 CONSTANT MIN-RAM-RESERVE \ prevent from using first pages
: MIN-RAM-SIZE         \ Initially available memory size
epapr-ima-size IF
epapr-ima-size
ELSE
20000000         \ assumed minimal memory size
THEN
;
MIN-RAM-SIZE CONSTANT MIN-RAM-SIZE
STRUCT
cell field available>address
cell field available>size
CONSTANT /available
CREATE available AVAILABLE-SIZE /available * allot available AVAILABLE-SIZE /available * erase
VARIABLE mem-pre-released 0 mem-pre-released !
: available>size@	available>size @ ;
: available>address@	available>address @ ;
: available>size!	available>size ! ;
: available>address!	available>address ! ;
: available! ( addr size available-ptr -- )
dup -rot available>size! available>address!
;
: available@ ( available-ptr -- addr size )
dup available>address@ swap available>size@
;
: (?available-segment<) ( start1 end1 start2 end2 -- true/false ) drop < nip ;
: (?available-segment>) ( start1 end1 start2 end2 -- true/false ) -rot 2drop > ;
: (?available-segment-#) ( start1 end1 start2 end2 -- true/false )
2dup 5 roll -rot                ( e1 s2 e2 s1 s2 e2 )
between >r between r> and not
;
: (find-available) ( addr addr+size-1 a-ptr a-size -- a-ptr' found )
?dup 0= IF -rot 2drop false EXIT THEN	\ Not Found
2dup 2/ dup >r /available * +
dup available>size@ 0= IF 2drop r> RECURSE EXIT THEN
dup >r available@
over + 1- 2>r 2swap
2dup 2r@ (?available-segment>) IF
2swap 2r> 2drop r>
/available + -rot r> - 1- nip RECURSE EXIT	\ Look Right
THEN
2dup 2r@ (?available-segment<) IF
2swap 2r> 2drop r>
2drop r> RECURSE EXIT	\ Look Left
THEN
2dup 2r@ (?available-segment-#) IF	\ Conflict - segments overlap
2r> 2r> 3drop 3drop 2drop
1212 throw
THEN
2r> 3drop 3drop r> r> drop	( a-ptr' -- )
dup available>size@ 0<>		( a-ptr' found -- )
;
: (find-available) ( addr size -- seg-ptr found )
over + 1- available AVAILABLE-SIZE ['] (find-available) catch IF
2drop 2drop 0 false
THEN
;
: dump-available ( available-ptr -- )
cr
dup available - /available / AVAILABLE-SIZE swap - 0 ?DO
dup available@ ?dup 0= IF
2drop UNLOOP EXIT
THEN
swap . . cr
/available +
LOOP
dup
;
: .available available dump-available ;
: (drop-available) ( available-ptr -- )
dup available - /available /	\ current element index
AVAILABLE-SIZE swap -		\ # of remaining elements
( first nelements ) 1- 0 ?DO
dup /available + dup available@
( current next next>address next>size ) ?dup 0= IF
2drop LEAVE \ NULL element - goto last copy
THEN
3 roll available!		( next )
LOOP
0 0 rot available!
;
: (stick-to-previous-available) ( addr size available-ptr -- naddr nsize nptr success )
dup available = IF
false EXIT		\ This was the first available segment
THEN
dup /available - dup available@
+ 4 pick = IF
nip	\ Drop available-ptr since we are going to previous one
rot drop	\ Drop start addr, we take the previous one
dup available@ 3 roll + rot true
ELSE
drop false
THEN
;
: (insert-available) ( available-ptr -- available-ptr )
dup				\ current element
dup available - /available /	\ current element index
AVAILABLE-SIZE swap -		\ # of remaining elements
dup 0<= 3 pick available>size@ 0= or IF
drop drop EXIT
THEN
over available@ rot
( first	first/=current/ first>address first>size nelements ) 1- 0 ?DO
2>r
/available + dup available@
2r> 4 pick available! dup 0= IF
rot /available + available!
UNLOOP EXIT
THEN
LOOP
( first next/=last/ last[0]>address last[0]>size ) ?dup 0<> IF
cr ." release error: available map overflow"
cr ." Dumping available property"
.available
cr ." No space for one before last entry:" cr swap . .
cr ." Dying ..." cr 123 throw
THEN
2drop
;
: insert-available ( addr size available-ptr -- addr size available-ptr )
dup available>address@ 0<> IF
dup available>address@ rot dup -rot -
3 pick = IF	\ if (available>address@ - size == addr)
over available>size@ + swap
(stick-to-previous-available) IF
dup /available + (drop-available)
THEN
ELSE
swap (stick-to-previous-available)
not IF (insert-available) THEN
THEN
ELSE
(stick-to-previous-available) drop
THEN
;
defer release
: drop-available ( addr size available-ptr -- addr )
dup >r available@
over 4 pick swap - ?dup 0<> IF
dup 3 roll swap r> available! -
over - ?dup 0= IF
drop
ELSE
swap 2 pick + swap release
THEN
ELSE
nip ( req_addr req_size segment_size )
over - ?dup 0= IF
drop r> (drop-available)
ELSE
-rot over + rot r> available!
THEN
THEN
;
: pwr2roundup ( value -- pwr2value )
dup CASE
0 OF EXIT ENDOF
1 OF EXIT ENDOF
ENDCASE
dup 1 DO drop i dup +LOOP
dup +
;
: (claim-best-fit) ( len align -- len base )
pwr2roundup 1- -1 -1
available AVAILABLE-SIZE /available * + available DO
i		\ Must be saved now, before we use Return stack
-rot >r >r swap >r
available@ ?dup 0= IF drop r> r> r> LEAVE THEN		\ EOL
2 pick - dup 0< IF
2drop			\ Can't Fit: Too Small
ELSE
dup 2 pick r@ and - 0< IF
2drop		\ Can't Fit When Aligned
ELSE
r> -rot dup r@ U< IF
2r> 2drop
swap 2 pick + 2 pick invert and >r >r >r
ELSE
2drop >r
THEN
THEN
THEN
r> r> r>
/available +LOOP
-rot 2drop	( len best-fit-base/or -1 if none found/ )
;
: (adjust-release0) ( 0 size -- addr' size' )
2dup MIN-RAM-SIZE dup 3 roll + -rot -
dup 0< IF 2drop ELSE
2swap 2drop 0 mem-pre-released !
THEN
;
: claim ( [ addr ] len align -- base )
?dup 0<> IF
(claim-best-fit) dup -1 = IF
2drop cr ." claim error : aligned allocation failed" cr
." available:" cr .available
321 throw EXIT
THEN
swap
THEN
2dup (find-available) not IF
drop
2drop
321 throw EXIT
THEN
( req_addr req_size available-ptr ) drop-available
;
: .release ( addr len -- )
over 0= mem-pre-released @ and IF (adjust-release0) THEN
2dup (find-available) IF
drop swap
cr ." release error: region " . ." , " . ." already released" cr
ELSE
?dup 0= IF
swap 
cr ." release error: Bad/conflicting region " . ." , " .
." or available list full " cr
ELSE
( addr size available-ptr ) insert-available
( addr size available-ptr ) available!
THEN
THEN
;
' .release to release
0 MIN-RAM-SIZE release 1 mem-pre-released !
0 MIN-RAM-RESERVE 0 ' claim CATCH IF ." claim failed!" cr 2drop THEN drop
paflof-start ffff not and 1f00000 0 ' claim CATCH IF
." claim failed!" cr 2drop
THEN drop
heap-end heap-start - log2 1+ CONSTANT (max-heads#)
CREATE heads (max-heads#) cells allot
heads (max-heads#) cells erase
: size>head  ( size -- headptr )  log2 3 max cells heads + ;
: alloc-mem  ( len -- a-addr )
dup 0= IF EXIT THEN
1 over log2 3 max                   ( len 1 log_len )
dup (max-heads#) >= IF cr ." Out of internal memory." cr 3drop 0 EXIT THEN
lshift >r                           ( len  R: 1<<log_len )
size>head dup @ IF
dup @ dup >r @ swap ! r> r> drop EXIT
THEN                                ( headptr  R: 1<<log_len)
r@ 2* recurse dup                   ( headptr a-addr2 a-addr2  R: 1<<log_len)
dup 0= IF r> 2drop 2drop 0 EXIT THEN
r> + >r 0 over ! swap ! r>
;
: free-mem  ( a-addr len -- )
dup 0= IF 2drop EXIT THEN size>head 2dup @ swap ! !
;
: #links  ( a -- n )
@ 0 BEGIN over WHILE 1+ swap @ swap REPEAT nip
;
: .free  ( -- )
0 (max-heads#) 0 DO
heads i cells + #links dup IF
cr dup . ." * " 1 i lshift dup . ." = " * dup .
THEN
+
LOOP
cr ." Total " .
;
heap-start heap-end heap-start - free-mem
false VALUE debug-find-component?
VARIABLE device-tree
VARIABLE current-node
: get-node  current-node @ dup 0= ABORT" No active device tree node" ;
STRUCT
cell FIELD node>peer
cell FIELD node>parent
cell FIELD node>child
cell FIELD node>properties
cell FIELD node>words
cell FIELD node>instance-template
cell FIELD node>instance-size
cell FIELD node>space?
cell FIELD node>space
cell FIELD node>addr1
cell FIELD node>addr2
cell FIELD node>addr3
END-STRUCT
: find-method ( str len phandle -- false | xt true )
node>words @ voc-find dup IF link> true THEN ;
0 VALUE my-self
400 CONSTANT max-instance-size
STRUCT
/n FIELD instance>node
/n FIELD instance>parent
/n FIELD instance>args
/n FIELD instance>args-len
/n FIELD instance>size
/n FIELD instance>#units
/n FIELD instance>unit1          \ For instance-specific "my-unit"
/n FIELD instance>unit2
/n FIELD instance>unit3
/n FIELD instance>unit4
CONSTANT /instance-header
: >instance  ( offset -- myself+offset )
my-self 0= ABORT" No instance!"
dup my-self instance>size @ >= ABORT" Instance access out of bounds!"
my-self +
;
: (create-instance-var) ( initial-value -- )
get-node
dup node>instance-size @ cell+ max-instance-size
>= ABORT" Instance is bigger than max-instance-size!"
dup node>instance-template @      ( iv phandle tmp-ih )
swap node>instance-size dup @     ( iv tmp-ih *instance-size instance-size )
dup ,                             \ compile current instance ptr
swap 1 cells swap +!              ( iv tmp-ih instance-size )
+ !
;
: create-instance-var ( "name" initial-value -- )
CREATE (create-instance-var) PREVIOUS
;
: (create-instance-buf) ( buffersize -- )
aligned                               \ align size to multiples of cells
dup get-node node>instance-size @ +   ( buffersize' newinstancesize )
max-instance-size > ABORT" Instance is bigger than max-instance-size!"
get-node node>instance-template @  get-node node>instance-size @ +
over erase                            \ clear according to IEEE 1275
get-node node>instance-size @         ( buffersize' old-instance-size )
dup ,                                 \ compile current instance ptr
+ get-node node>instance-size !       \ store new size
;
: create-instance-buf ( "name" buffersize -- )
CREATE (create-instance-buf) PREVIOUS
;
VOCABULARY instance-words  ALSO instance-words DEFINITIONS
: VARIABLE  0 create-instance-var DOES> [ here ] @ >instance ;
: VALUE       create-instance-var DOES> [ here ] @ >instance @ ;
: DEFER     0 create-instance-var DOES> [ here ] @ >instance @ execute ;
: BUFFER:     create-instance-buf DOES> [ here ] @ >instance ;
PREVIOUS DEFINITIONS
CONSTANT <instancebuffer>
CONSTANT <instancedefer>
CONSTANT <instancevalue>
CONSTANT <instancevariable>
: (instance?) ( xt -- xt true|false )
dup @ <create> = IF
dup cell+ @ cell+ @ ['] >instance =
ELSE
false
THEN
;
: (doito) ( value R:*CFA -- )
r> cell+ dup >r
@ cell+ cell+ @ >instance !
;
' (doito) CONSTANT <(doito)>
: to ( value wordname<> -- )
' (instance?)
state @ IF
IF ['] (doito) ELSE ['] DOTO THEN
, , EXIT
THEN
IF
cell+ cell+ @ >instance ! \ interp mode instance value
ELSE
cell+ !                   \ interp mode normal value
THEN
; IMMEDIATE
: behavior  ( defer-xt -- contents-xt )
dup cell+ @ <instancedefer> = IF   \ Is defer-xt an INSTANCE DEFER ?
2 cells + @ >instance @
ELSE
behavior
THEN
;
: INSTANCE  ALSO instance-words ;
: my-parent  my-self instance>parent @ ;
: my-args    my-self instance>args 2@ swap ;
: set-my-args   ( old-addr len -- )
dup alloc-mem                   \ allocate space for new args ( old-addr len new-addr )
2dup my-self instance>args 2!   \ write into instance struct  ( old-addr len new-addr )
swap move                       \ and copy the args           ( )
;
: create-instance-data ( -- instance )
get-node dup node>instance-template @    ( phandle instance-template )
swap node>instance-size @                ( instance-template instance-size )
dup >r
dup alloc-mem dup >r swap move r>        ( instance )
dup instance>size r> swap !              \ Store size for destroy-instance
dup instance>#units 0 swap !             \ Use node unit by default
;
: create-instance ( -- )
my-self create-instance-data
dup to my-self instance>parent !
get-node my-self instance>node !
;
: destroy-instance ( instance -- )
dup instance>args @ ?dup IF               \ Free instance args?
over instance>args-len @  free-mem
THEN
dup instance>size @  free-mem
;
: ihandle>phandle ( ihandle -- phandle )
dup 0= ABORT" no current instance" instance>node @
;
: push-my-self ( ihandle -- )  r> my-self >r >r to my-self ;
: pop-my-self ( -- )  r> r> to my-self >r ;
: call-package  push-my-self execute pop-my-self ;
: $call-static ( ... str len node -- ??? )
find-method IF execute ELSE -1 throw THEN
;
: $call-my-method  ( str len -- )
my-self ihandle>phandle $call-static
;
: $call-method  ( str len ihandle -- )
push-my-self
['] $call-my-method CATCH ?dup IF
pop-my-self THROW
THEN
pop-my-self
;
0 VALUE calling-child
: $call-parent
my-self ihandle>phandle TO calling-child
my-parent $call-method
0 TO calling-child
;
: create-node ( parent -- new )
max-instance-size alloc-mem        ( parent instance-mem )
dup max-instance-size erase >r     ( parent  R: instance-mem )
align wordlist >r wordlist >r      ( parent  R: instance-mem wl wl )
here                               ( parent new  R: instance-mem wl wl )
0 , swap , 0 ,                     \ Set node>peer, node>parent & node>child
r> , r> ,                          \ Set node>properties & node>words to wl
r> , /instance-header ,            \ Set instance-template & instance-size
FALSE , 0 ,                        \ Set node>space? and node>space
0 , 0 , 0 ,                        \ Set node>addr*
;
: peer    node>peer   @ ;
: parent  node>parent @ ;
: child   node>child  @ ;
: peer  dup IF peer ELSE drop device-tree @ THEN ;
: link ( new head -- ) \ link a new node at the end of a linked list
BEGIN dup @ WHILE @ REPEAT ! ;
: link-node ( parent child -- )
swap dup IF node>child link ELSE drop device-tree ! THEN ;
: set-node ( phandle -- )
current-node @ IF previous THEN
dup current-node !
?dup IF node>words @ also context ! THEN
definitions ;
: get-parent  get-node parent ;
: new-node ( -- phandle ) \ active node becomes new node's parent;
current-node @ dup create-node
tuck link-node dup set-node ;
: finish-node ( -- )
get-node parent set-node
;
: device-end ( -- )  0 set-node ;
CREATE $indent 100 allot  VARIABLE indent 0 indent !
true value encode-first?
: decode-int  over >r 4 /string r> 4c@ swap 2swap swap bljoin ;
: decode-64 decode-int -rot decode-int -rot 2swap swap lxjoin ;
: decode-string ( prop-addr1 prop-len1 -- prop-addr2 prop-len2 str len )
dup 0= IF 2dup EXIT THEN \ string properties with zero length
over BEGIN dup c@ 0= IF 1+ -rot swap 2 pick over - rot over - -rot 1-
EXIT THEN 1+ AGAIN ;
: (prune) ( name len head -- )
dup >r (find) ?dup IF r> BEGIN dup @ WHILE 2dup @ = IF
>r @ r> ! EXIT THEN @ REPEAT 2drop ELSE r> drop THEN ;
: prune ( name len -- )  last (prune) ;
: set-property ( data dlen name nlen phandle -- )
true to encode-first?
get-current >r  node>properties @ set-current
2dup prune  $2CONSTANT  r> set-current ;
: delete-property ( name nlen -- )
get-node get-current >r  node>properties @ set-current
prune r> set-current ;
: property ( data dlen name nlen -- )  get-node set-property ;
: get-property ( str len phandle -- true | data dlen false )
?dup 0= IF cr cr cr ." get-property for " type ."  on zero phandle"
cr cr true EXIT THEN
node>properties @ voc-find dup IF link> execute false ELSE drop true THEN ;
: get-package-property ( str len phandle -- true | data dlen false )
get-property ;
: get-my-property ( str len -- true | data dlen false )
my-self ihandle>phandle get-property ;
: get-parent-property ( str len -- true | data dlen false )
my-parent ihandle>phandle get-property ;
: get-inherited-property ( str len -- true | data dlen false )
my-self ihandle>phandle
BEGIN
3dup get-property 0= IF
rot drop rot drop rot drop false EXIT
THEN
parent dup 0= IF
3drop true EXIT
THEN
AGAIN
;
20 CONSTANT indent-prop
: .prop-int ( str len -- )
space
400 min 0
?DO
i over + dup                                 ( str act-addr act-addr )
c@ 2 0.r 1+ dup c@ 2 0.r 1+ dup c@ 2 0.r 1+ c@ 2 0.r ( str )
i c and c = IF                           \ check for multipleof 16 bytes
cr indent @ indent-prop + 1+ 0        \ linefeed + indent
DO
space                              \ print spaces
LOOP
ELSE
space space                           \ print two spaces
THEN
4 +LOOP
drop
;
: .prop-bytes ( str len -- )
2dup -4 and .prop-int                       ( str len )
dup 3 and dup IF                            ( str len len%4 )
>r -4 and + r>                           ( str' len%4 )
bounds                                   ( str' str'+len%4 )
DO
i c@ 2 0.r                            \ Print last 3 bytes
LOOP
ELSE
3drop
THEN
;
: .prop-string ( str len )
2dup space type
cr indent @ indent-prop + 0 DO space LOOP   \ Linefeed
.prop-bytes
;
: .propbytes ( xt -- )
execute dup
IF
over cell- @ execute
ELSE
2drop
THEN
;
: .property ( lfa -- )
cr indent @ 0
?DO
space
LOOP
link> dup >name name>string 2dup type nip ( len )
indent-prop swap -                        ( xt 20-len )
dup 0< IF drop 0 THEN 0                   ( xt number-of-space 0 )
?DO
space
LOOP
.propbytes
;
: (.properties) ( phandle -- )
node>properties @ cell+ @ BEGIN dup WHILE dup .property @ REPEAT drop ;
: .properties ( -- )
get-node (.properties) ;
: next-property ( str len phandle -- false | str' len' true )
?dup 0= IF device-tree @ THEN  \ XXX: is this line required?
node>properties @
>r 2dup 0= swap 0= or IF 2drop r> cell+ ELSE r> voc-find THEN
@ dup IF link>name name>string true THEN ;
: encode-start ( -- prop 0 )
['] .prop-int compile,
false to encode-first?
here 0
;
: encode-int ( val -- prop prop-len )
encode-first? IF
['] .prop-int compile,             \ Execution token for print
false to encode-first?
THEN
here swap lbsplit c, c, c, c, /l
;
: encode-bytes ( str len -- prop-addr prop-len )
encode-first? IF
['] .prop-bytes compile,           \ Execution token for print
false to encode-first?
THEN
here over 2dup 2>r allot swap move 2r>
;
: encode-string ( str len -- prop-addr prop-len )
encode-first? IF
['] .prop-string compile,          \ Execution token for print
false to encode-first?
THEN
encode-bytes 0 c, char+
;
: encode+ ( prop1-addr prop1-len prop2-addr prop2-len -- prop-addr prop-len )
nip + ;
: encode-int+  encode-int encode+ ;
: encode-64    xlsplit encode-int rot encode-int+ ;
: encode-64+   encode-64 encode+ ;
: device-name  encode-string s" name"        property ;
: device-type  encode-string s" device_type" property ;
: model        encode-string s" model"       property ;
: compatible   encode-string s" compatible"  property ;
: #address-cells  s" #address-cells" rot parent get-property
ABORT" parent doesn't have a #address-cells property!"
decode-int nip nip
;
: my-#address-cells  ( -- #address-cells )
get-node #address-cells
;
: child-#address-cells  ( -- #address-cells )
s" #address-cells" get-node get-property
ABORT" node doesn't have a #address-cells property!"
decode-int nip nip
;
: child-#size-cells  ( -- #address-cells )
s" #size-cells" get-node get-property
ABORT" node doesn't have a #size-cells property!"
decode-int nip nip
;
: encode-phys  ( phys.hi ... phys.low -- prop len )
encode-first?  IF  encode-start  ELSE  here 0  THEN
my-#address-cells 0 ?DO rot encode-int+ LOOP
;
: encode-child-phys  ( phys.hi ... phys.low -- prop len )
encode-first?  IF  encode-start  ELSE  here 0  THEN
child-#address-cells 0 ?DO rot encode-int+ LOOP
;
: encode-child-size  ( size.hi ... size.low -- prop len )
encode-first? IF  encode-start  ELSE  here 0  THEN
child-#size-cells 0 ?DO rot encode-int+ LOOP
;
: decode-phys
my-#address-cells BEGIN dup WHILE 1- >r decode-int r> swap >r REPEAT drop
my-#address-cells BEGIN dup WHILE 1- r> swap REPEAT drop ;
: decode-phys-and-drop
my-#address-cells BEGIN dup WHILE 1- >r decode-int r> swap >r REPEAT 3drop
my-#address-cells BEGIN dup WHILE 1- r> swap REPEAT drop ;
: reg  >r encode-phys r> encode-int+ s" reg" property ;
: >space    node>space @ ;
: >space?   node>space? @ ;
: >address  dup >r #address-cells dup 3 > IF r@ node>addr3 @ swap THEN
dup 2 > IF r@ node>addr2 @ swap THEN
1 > IF r@ node>addr1 @ THEN r> drop ;
: >unit     dup >r >address r> >space ;
: (my-phandle)  ( -- phandle )
my-self ?dup IF
ihandle>phandle
ELSE
get-node dup 0= ABORT" no active node"
THEN
;
: my-space ( -- phys.hi )
(my-phandle) >space
;
: my-address  (my-phandle) >address ;
: my-unit
my-self instance>#units @ IF
0 my-self instance>#units @ 1- DO
my-self instance>unit1 i cells + @
-1 +LOOP
ELSE
my-self ihandle>phandle >unit
THEN
;
: my-unit-64 ( -- phys.lo+1|phys.lo )
my-unit                                ( phys.lo ... phys.hi )
(my-phandle) #address-cells            ( phys.lo ... phys.hi #ad-cells )
CASE
1   OF EXIT ENDOF
2   OF lxjoin EXIT ENDOF
3   OF drop lxjoin EXIT ENDOF
dup OF 2drop lxjoin EXIT ENDOF
ENDCASE
;
: set-space    get-node dup >r node>space ! true r> node>space? ! ;
: set-address  my-#address-cells 1 ?DO
get-node node>space i cells + ! LOOP ;
: set-unit     set-space set-address ;
: set-unit-64 ( phys.lo|phys.hi -- )
my-#address-cells 2 <> IF
." set-unit-64: #address-cells <> 2 " abort
THEN
xlsplit set-unit
;
: set-args ( arg-str len unit-str len -- )
s" decode-unit" get-parent $call-static set-unit set-my-args
;
: $cat-unit
dup parent 0= IF drop EXIT THEN
dup >space? not IF drop EXIT THEN
dup >r >unit s" encode-unit" r> parent $call-static
dup IF
dup >r here swap move s" @" $cat here r> $cat
ELSE
2drop
THEN
;
: $cat-instance-unit
dup parent 0= IF drop EXIT THEN
dup instance>#units @ 0= IF
ihandle>phandle $cat-unit
EXIT
THEN
dup >r push-my-self
['] my-unit CATCH IF pop-my-self r> drop EXIT THEN
pop-my-self
s" encode-unit"
r> ihandle>phandle parent
$call-static
dup IF
dup >r here swap move s" @" $cat here r> $cat
ELSE
2drop
THEN
;
: node>name  dup >r s" name" rot get-property IF r> (u.) ELSE 1- r> drop THEN ;
: node>qname dup node>name rot ['] $cat-unit CATCH IF drop THEN ;
: node>path
here 0 rot
BEGIN dup WHILE dup parent REPEAT
2drop
dup 0= IF [char] / c, THEN
BEGIN
dup
WHILE
[char] / c, node>qname here over allot swap move
REPEAT
drop here 2dup - allot over -
;
: interposed? ( ihandle -- flag )
dup instance>parent @ dup 0= IF 2drop false EXIT THEN
ihandle>phandle swap ihandle>phandle parent <> ;
: instance>qname
dup >r interposed? IF s" %" ELSE 0 0 THEN
r@ dup ihandle>phandle node>name
rot ['] $cat-instance-unit CATCH IF drop THEN
$cat r> instance>args 2@ swap
dup IF 2>r s" :" $cat 2r> $cat ELSE 2drop THEN
;
: instance>qpath \ With interposed nodes.
here 0 rot BEGIN dup WHILE dup instance>parent @ REPEAT 2drop
dup 0= IF [char] / c, THEN
BEGIN dup WHILE [char] / c, instance>qname here over allot swap move
REPEAT drop here 2dup - allot over - ;
: instance>path \ Without interposed nodes.
here 0 rot BEGIN dup WHILE
dup interposed? 0= IF dup THEN instance>parent @ REPEAT 2drop
dup 0= IF [char] / c, THEN
BEGIN dup WHILE [char] / c, instance>qname here over allot swap move
REPEAT drop here 2dup - allot over - ;
: .node  node>path type ;
: pwd  get-node .node ;
: .instance instance>qpath type ;
: .chain    dup instance>parent @ ?dup IF recurse THEN
cr dup . instance>qname type ;
defer find-node
: set-alias ( alias-name len device-name len -- )
encode-string
2swap s" /aliases" find-node ?dup IF
set-property
ELSE
4drop
THEN
;
: find-alias ( alias-name len -- false | dev-path len )
s" /aliases" find-node dup IF
get-property 0= IF 1- dup 0= IF nip THEN ELSE false THEN
THEN
;
: .alias ( alias-name len -- )
find-alias dup IF type ELSE ." no alias available" THEN ;
: (.print-alias) ( lfa -- )
link> dup >name name>string
2dup s" name" string=ci IF 2drop drop
ELSE cr type space ." : " execute type
THEN ;
: (.list-alias) ( phandle -- )
node>properties @ cell+ @ BEGIN dup WHILE dup (.print-alias) @ REPEAT drop ;
: list-alias ( -- )
s" /aliases" find-node dup IF (.list-alias) THEN ;
8 CONSTANT MAX-ALIAS
1 VALUE alias-ind
: get-next-alias ( $alias-name -- $next-alias-name|FALSE )
2dup find-alias IF
drop
1 TO alias-ind
BEGIN
2dup alias-ind $cathex 2dup find-alias
WHILE
drop 2drop
alias-ind 1 + TO alias-ind
alias-ind MAX-ALIAS = IF
2drop FALSE EXIT
THEN
REPEAT
strdup 2swap 2drop
THEN
;
: devalias ( "{alias-name}<>{device-specifier}<cr>" -- )
parse-word parse-word dup IF set-alias
ELSE 2drop dup IF .alias
ELSE 2drop list-alias THEN THEN ;
: sub-alias ( arg-str arg-len -- arg' len' | false )
2dup
2dup [char] / findchar ?dup IF ELSE 2dup [char] : findchar THEN
( a l a l [p] -1|0 ) IF nip dup ELSE 2drop 0 THEN >r
find-alias ?dup IF ( a l a' p' -- R:p | a' l' -- R:0 )
r@ IF
2swap r@ - swap r> + swap $cat strdup ( a" l-p+p' -- )
ELSE
( a' l' -- R:0 ) r> drop ( a' l' -- )
THEN
ELSE
( a l -- R:p | -- R:0 ) r> IF 2drop THEN
false ( 0 -- )
THEN
;
: de-alias ( arg-str arg-len -- arg' len' )
BEGIN
over c@ [char] / <> dup IF drop 2dup sub-alias ?dup THEN
WHILE
2swap 2drop
REPEAT
;
: +indent ( not-last? -- )
IF s" |   " ELSE s"     " THEN $indent indent @ + swap move 4 indent +! ;
: -indent ( -- )  -4 indent +! ;
: ls-phandle ( node -- )  . ." :  " ;
: ls-node ( node -- )
cr dup ls-phandle
$indent indent @ type
dup peer IF ." |-- " ELSE ." +-- " THEN
node>qname type
;
: (ls) ( node -- )
child BEGIN dup WHILE dup ls-node dup child IF
dup peer +indent dup recurse -indent THEN peer REPEAT drop ;
: ls ( -- )
get-node cr
dup ls-phandle
dup node>path type
(ls)
0 indent !
;
: show-devs ( {device-specifier}<eol> -- )
skipws 0 parse dup IF de-alias ELSE 2drop s" /" THEN   ( str len )
find-node dup 0= ABORT" No such device path" (ls)
;
VARIABLE interpose-node
2VARIABLE interpose-args
: interpose ( arg len phandle -- )  interpose-node ! interpose-args 2! ;
0 VALUE user-instance-#units
CREATE user-instance-units 4 cells allot
: copy-instance-unit  ( -- )
user-instance-#units IF
user-instance-#units my-self instance>#units !
user-instance-units my-self instance>unit1 user-instance-#units cells move
0 to user-instance-#units
THEN
;
: open-node ( arg len phandle -- ihandle|0 )
current-node @ >r  my-self >r            \ Save current node and instance
set-node create-instance set-my-args
copy-instance-unit
s" open" get-node find-method IF execute ELSE TRUE THEN
0= IF
my-self destroy-instance 0 to my-self
THEN
my-self                                  ( ihandle|0 )
r> to my-self  r> set-node               \ Restore current node and instance
interpose-node @ IF
my-self >r to my-self
interpose-args 2@ interpose-node @
interpose-node off recurse
r> to my-self
THEN
;
: close-node ( ihandle -- )
my-self >r to my-self
s" close" ['] $call-my-method CATCH IF 2drop THEN
my-self destroy-instance r> to my-self ;
: close-dev ( ihandle -- )
my-self >r to my-self
BEGIN my-self WHILE my-parent my-self close-node to my-self REPEAT
r> to my-self ;
: new-device ( -- )
my-self new-node                     ( parent-ihandle phandle )
node>instance-template @             ( parent-ihandle ihandle )
dup to my-self                       ( parent-ihanlde ihandle )
instance>parent !
get-node my-self instance>node !
max-instance-size my-self instance>size !
;
: finish-device ( -- )
get-node >space? 0= IF
s" reg" get-node get-property 0= IF
decode-int set-space 2drop
THEN
THEN
finish-node my-parent to my-self
;
: extend-device  ( phandle -- )
my-self >r
dup set-node
node>instance-template @
dup to my-self
r> swap instance>parent !
;
: split ( str len char -- left len right len )
>r 2dup r> findchar IF >r over r@ 2swap r> 1+ /string ELSE 0 0 THEN ;
: generic-decode-unit ( str len ncells -- addr.lo ... addr.hi )
dup >r -rot BEGIN r@ WHILE r> 1- >r [char] , split 2swap
$number IF 0 THEN r> swap >r >r REPEAT r> 3drop
BEGIN dup WHILE 1- r> swap REPEAT drop ;
: generic-encode-unit ( addr.lo ... addr.hi ncells -- str len )
0 0 rot ?dup IF 0 ?DO rot (u.) $cat s" ," $cat LOOP 1- THEN ;
: hex-decode-unit ( str len ncells -- addr.lo ... addr.hi )
base @ >r hex generic-decode-unit r> base ! ;
: hex-encode-unit ( addr.lo ... addr.hi ncells -- str len )
base @ >r hex generic-encode-unit r> base ! ;
: hex64-decode-unit ( str len ncells -- addr.lo ... addr.hi )
dup 2 <> IF
hex-decode-unit
ELSE
drop
base @ >r hex
$number IF 0 0 ELSE xlsplit THEN
r> base !
THEN
;
: hex64-encode-unit ( addr.lo ... addr.hi ncells -- str len )
dup 2 <> IF
hex-encode-unit
ELSE
drop
base @ >r hex
lxjoin (u.)
r> base !
THEN
;
: handle-leading-/ ( path len -- path' len' )
dup IF over c@ [char] / = IF 1 /string device-tree @ set-node THEN THEN ;
: match-name ( name len node -- match? )
over 0= IF 3drop true EXIT THEN
s" name" rot get-property IF 2drop false EXIT THEN
1- string=ci ; \ XXX should use decode-string
0 VALUE #search-unit
CREATE search-unit 4 cells allot
: match-unit ( node -- match? )
dup >space? IF
node>space search-unit #search-unit 0 ?DO 2dup @ swap @ <> IF
2drop false UNLOOP EXIT THEN cell+ swap cell+ swap LOOP 2drop true
ELSE drop true THEN
;
: match-node ( name len node -- match? )
dup >r match-name r> match-unit and ; \ XXX e3d
: find-kid ( name len -- node|0 )
dup -1 = IF \ are we supposed to stay in the same node? -> resolve-relatives
2drop get-node
ELSE
get-node child >r BEGIN r@ WHILE 2dup r@ match-node
IF 2drop r> EXIT THEN r> peer >r REPEAT
r> 3drop false
THEN ;
: set-search-unit ( unit len -- )
0 to #search-unit
0 to user-instance-#units
dup 0= IF 2drop EXIT THEN
s" #address-cells" get-node get-property THROW
decode-int to #search-unit 2drop
s" decode-unit" get-node $call-static
#search-unit 0 ?DO search-unit i cells + ! LOOP
;
: resolve-relatives ( path len -- path' len' )
2dup 2 = swap s" .." comp 0= and IF
get-node parent ?dup IF
set-node drop -1
ELSE
s" Already in root node." type
THEN
THEN
2dup 1 = swap c@ [CHAR] . = and IF
drop -1
THEN
;
: set-instance-unit  ( unitaddr len -- )
dup 0= IF 2drop  0 to user-instance-#units  EXIT THEN
2dup 0 -rot bounds ?DO
i c@ [char] , = IF 1+ THEN      \ Count the commas
LOOP
1+ dup to user-instance-#units
hex-decode-unit
user-instance-#units 0 ?DO
user-instance-units i cells + !
LOOP
;
: split-component  ( path. -- path'. args. name. unit. )
[char] / split 2swap     ( path'. component. )
[char] : split 2swap     ( path'. args. name@unit. )
[char] @ split           ( path'. args. name. unit. )
;
: find-component  ( path len -- path' len' args len node|0 )
debug-find-component? IF
." find-component for " 2dup type cr
THEN
split-component           ( path'. args. name. unit. )
debug-find-component? IF
." -> unit  =" 2dup type cr
." -> stack =" .s cr
THEN
['] set-search-unit CATCH IF
." WARNING: Obsolete old wildcard hack " .s cr
set-instance-unit
THEN
resolve-relatives find-kid        ( path' len' args len node|0 )
dup IF dup >space? not #search-unit 0 > AND user-instance-#units 0= AND IF
#search-unit dup to user-instance-#units 0 ?DO
search-unit i cells + @ user-instance-units i cells + !
LOOP
THEN THEN
dup IF dup >space? user-instance-#units 0 > AND IF
cr ." find-component with unit mismatch!" .s cr
drop 0
THEN THEN
;
: .find-node ( path len -- phandle|0 )
current-node @ >r
handle-leading-/ current-node @ 0= IF 2drop r> set-node 0 EXIT THEN
BEGIN dup WHILE \ handle one component:
find-component ( path len args len node ) dup 0= IF
3drop 2drop r> set-node 0 EXIT THEN
set-node 2drop REPEAT 2drop
get-node r> set-node ;
' .find-node to find-node
: find-node ( path len -- phandle|0 ) de-alias find-node ;
: delete-node ( phandle -- )
dup node>instance-template @ max-instance-size free-mem
dup node>parent @ node>child @ ( phandle 1st peer )
2dup = IF
node>peer @ swap node>parent @ node>child !
EXIT
THEN
dup node>peer @
BEGIN
2 pick 2dup <>
WHILE
drop
nip dup node>peer @
dup 0= IF 2drop drop unloop EXIT THEN
REPEAT
drop
node>peer @  swap node>peer !
drop
;
: open-dev ( path len -- ihandle|0 )
0 to user-instance-#units
de-alias current-node @ >r
handle-leading-/ current-node @ 0= IF 2drop r> set-node 0 EXIT THEN
my-self >r
0 to my-self
0 0 >r >r
BEGIN
dup
WHILE \ handle one component:
( arg len ) r> r> get-node open-node to my-self
find-component ( path len args len node ) dup 0= IF
3drop 2drop my-self close-dev
r> to my-self
r> set-node
0 EXIT
THEN
set-node
>r >r
REPEAT
2drop
r> r> get-node open-node to my-self
my-self r> to my-self r> set-node
;
: select-dev  open-dev dup to my-self ihandle>phandle set-node ;
: unselect-dev  my-self close-dev  0 to my-self  device-end ;
: find-device ( str len -- ) \ set as active node
find-node dup 0= ABORT" No such device path" set-node ;
: dev  parse-word find-device ;
: (lsprop) ( node --)
dup cr $indent indent @ type ."     node: " node>qname type
false +indent (.properties) cr -indent
;
: (show-children) ( node -- )
child BEGIN
dup
WHILE
dup (lsprop) dup child IF false +indent dup recurse -indent THEN peer
REPEAT
drop
;
: lsprop ( {device-specifier}<eol> -- )
skipws 0 parse dup IF de-alias ELSE 2drop s" /" THEN
find-device get-node dup dup
cr ." node: " node>path type (.properties) cr (show-children)
0 indent !
;
: (node>path) node>path ;
: node>path ( phandle -- str len )
node>path dup allot
;
0 VALUE packages
: find-package  ( name len -- false | phandle true )
dup 0 <= IF
2drop FALSE EXIT
THEN
over c@ [char] / = IF
find-node dup IF TRUE THEN EXIT
THEN
0 >r packages child
BEGIN
dup
WHILE
dup >r node>name 2over string=ci r> swap IF
r> drop dup >r
THEN
peer
REPEAT
3drop
r> dup IF true THEN
;
: open-package ( arg len phandle -- ihandle | 0 )  open-node ;
: close-package ( ihandle -- )  close-node ;
: $open-package ( arg len name len -- ihandle | 0 )
find-package IF open-package ELSE 2drop false THEN ;
: pci-address-type  ( node address prop_type -- type )
-rot 2 pick ( prop_type node address prop_type )
0= IF
swap s" reg" rot get-property  ( prop_type address data dlen false )
ELSE
swap s" assigned-addresses" rot get-property  ( prop_type address data dlen false )
THEN
IF  2drop -1  EXIT  THEN  4 / 5 /
0 DO
dup l@ FF AND 0<> ( prop_type address data cfgspace_offset? )
3 pick 0= ( prop_type address data cfgspace_offset? reg_prop? )
AND NOT IF 
2dup 4 + ( prop_type address data address data' )
2dup @ 2 pick 8 + @ + <= -rot @  >= and  IF
l@ 03000000 and 18 rshift nip
swap drop ( type )
UNLOOP EXIT
THEN
THEN
4 5 * +
LOOP
3drop -1
;
: (range-read-cells)  ( range-addr #cells -- range-value )
1 =  IF  l@  ELSE  @  THEN
;
: (map-one-range)  ( type range pnac nsc nac address -- address true | address false )
over 3 = 5 pick l@ 3000000 and 18 rshift 7 pick <> and  IF
>r 2drop 3drop r> false EXIT
THEN
4 pick 4 pick 3 pick + 4 * +
3 pick
(range-read-cells)
5 pick 3 pick 3 =  IF
4 +
THEN
3 pick
(range-read-cells)
dup >r dup 3 pick > >r + over <= r> or  IF
>r 2drop 3drop r> r> drop false EXIT
THEN
dup r> -
5 pick 5 pick 3 =  IF
4 +
THEN
3 pick 4 * +
5 pick
(range-read-cells)
+ >r 3drop 3drop r> true
;
: translate-address  ( node address -- address )
2dup 1 pci-address-type  ( node address type )
dup -1 = IF
drop 2dup 0 pci-address-type ( node address type )
THEN
rot parent BEGIN
dup parent 0=  IF  2drop EXIT  THEN
s" #address-cells" 2 pick get-property 2drop l@ >r        \ nac
s" #size-cells" 2 pick get-property 2drop l@ >r           \ nsc
s" #address-cells" 2 pick parent get-property 2drop l@ >r \ pnac
-rot ( node address type )
s" ranges" 4 pick get-property  IF
3drop
ABORT" no ranges property; not translatable"
THEN
r> r> r> 3 roll
4 / >r 3dup + + >r 5 roll r> r> swap / 0 ?DO
6dup (map-one-range) IF
nip leave
THEN
nip
4 roll
4 pick 4 pick 4 pick + + 4 * + 4 -roll
LOOP
>r 2drop 2drop r> ( node type address )
swap rot parent ( address type node )
dup 0=
UNTIL
;
: translate-my-address  ( address -- address' )
get-node swap translate-address
;
: find-substr ( basestr-ptr basestr-len substr-ptr substr-len -- pos )
dup 0 = IF
2drop 2drop 0 exit THEN
dup 3 pick <= IF
2 pick over - 1+ 0 DO dup 0 DO
over i + c@ 4 pick j + i + c@ = IF
dup i 1+ = IF
2drop 2drop j unloop unloop exit THEN
ELSE leave THEN
LOOP LOOP
THEN
2drop nip
;
: find-isubstr ( basestr-ptr basestr-len substr-ptr substr-len -- pos )
dup 0 = IF
2drop 2drop 0 exit THEN
dup 3 pick <= IF
2 pick over - 1+ 0 DO dup 0 DO
over i + c@ lcc 4 pick j + i + c@ lcc = IF
dup i 1+ = IF
2drop 2drop j unloop unloop exit THEN
ELSE leave THEN
LOOP LOOP
THEN
2drop nip
;
: find-nextline ( str-ptr str-len -- pos )
dup 0 ?DO over i + c@ CASE
0a OF
dup 1- i = IF
2drop i 1+ unloop exit THEN
over i 1+ + c@ 0d = IF
2drop i 2+ ELSE
2drop i 1+ THEN
unloop exit
ENDOF
0d OF
dup 1- i = IF
2drop i 1+ unloop exit THEN
over i 1+ + c@ 0a = IF
2drop i 2+ ELSE
2drop i 1+ THEN
unloop exit
ENDOF
ENDCASE LOOP nip
;
: string-at ( str1-ptr str1-len pos -- str2-ptr str2-len )
-rot 2 pick - -rot swap chars + swap
;
: string-cat ( addr1 len1 addr2 len2 -- addr1 len1+len2 )
rot dup >r over + -rot
3 pick r> chars + -rot
0 ?DO
2dup c@ swap c!
char+ swap char+ swap
LOOP 2drop
;
: char-cat ( addr len character -- addr len+1 )
-rot 2dup >r >r 1+ rot r> r> chars + c!
;
: overlap ( src dest size -- true|false )
3dup over + within IF 3drop true ELSE rot tuck + within THEN
;
: parse-2int ( str len -- val.lo val.hi )
[char] , split ?dup IF eval ELSE drop 0 THEN
-rot ?dup IF eval ELSE drop 0 THEN
;
: cpeek ( addr -- false | byte true ) c@ true ;
: cpoke ( byte addr -- success? ) c! true ;
: wpeek ( addr -- false | word true ) w@ true ;
: wpoke ( word addr -- success? ) w! true ;
: lpeek ( addr -- false | lword true ) l@ true ;
: lpoke ( lword addr -- success? ) l! true ;
defer reboot ( -- )
defer halt ( -- )
defer disable-watchdog ( -- )
defer reset-watchdog ( -- )
defer set-watchdog ( +n -- )
defer set-led ( type instance state -- status )
defer get-flashside ( -- side )
defer set-flashside ( side -- status )
defer read-bootlist ( -- )
defer furnish-boot-file ( -- adr len )
defer set-boot-file ( adr len -- )
defer mfg-mode? ( -- flag )
defer of-prompt? ( -- flag )
defer debug-boot? ( -- flag )
defer bmc-version ( -- adr len )
defer cursor-on ( -- )
defer cursor-off ( -- )
: nop-reboot ( -- ) ." reboot not available" abort ;
: nop-halt ( -- ) ." halt not available" abort ;
: nop-disable-watchdog ( -- )  ;
: nop-reset-watchdog ( -- )  ;
: nop-set-watchdog ( +n -- ) drop ;
: nop-set-led ( type instance state -- status ) drop drop drop ;
: nop-get-flashside ( -- side ) ." Cannot get flashside" cr ABORT ;
: nop-set-flashside ( side -- status ) ." Cannot set flashside" cr ABORT ;
: nop-read-bootlist ( -- ) ;
: nop-furnish-bootfile ( -- adr len ) s" net:" ;
: nop-set-boot-file ( adr len -- ) 2drop ;
: nop-mfg-mode? ( -- flag ) false ;
: nop-of-prompt? ( -- flag ) false ;
: nop-debug-boot? ( -- flag ) false ;
: nop-bmc-version ( -- adr len ) s" XXXXX" ;
: nop-cursor-on ( -- ) ;
: nop-cursor-off ( -- ) ;
' nop-reboot to reboot
' nop-halt to halt
' nop-disable-watchdog to disable-watchdog
' nop-reset-watchdog   to reset-watchdog
' nop-set-watchdog     to set-watchdog
' nop-set-led          to set-led
' nop-get-flashside    to get-flashside
' nop-set-flashside    to set-flashside
' nop-read-bootlist    to read-bootlist
' nop-furnish-bootfile to furnish-boot-file
' nop-set-boot-file    to set-boot-file
' nop-mfg-mode?        to mfg-mode?
' nop-of-prompt?       to of-prompt?
' nop-debug-boot?      to debug-boot?
' nop-bmc-version      to bmc-version
' nop-cursor-on        to cursor-on
' nop-cursor-off       to cursor-off
: reset-all reboot ;
10000000 VALUE default-load-base
2000000 VALUE flash-load-base
0 VALUE load-base-override
: get-load-base
load-base-override 0<> IF load-base-override ELSE
" load-base" evaluate 
THEN
;
: xt>name ( xt -- str len )
BEGIN
cell - dup c@ 0 2 within IF
dup 2+ swap 1+ c@ exit
THEN
AGAIN
;
cell -1 * CONSTANT -cell
: cell- ( n -- n-cell-size )
[ cell -1 * ] LITERAL +
;
: find-xt-addr ( addr -- xt )
BEGIN
dup @ <colon> = IF
EXIT
THEN
cell-
AGAIN
;
: (.immediate) ( xt -- )
xt>name drop 2 - c@ \ skip len and flags
immediate? IF
."  IMMEDIATE"
THEN
;
: (.xt) ( xt -- )
xt>name type
;
: trace-back (  )
1
BEGIN
cr dup dup . ."  : " rpick dup . ."  : "
['] tib here within IF
dup rpick find-xt-addr (.xt)
THEN
1+ dup rdepth 5 - >= IF cr drop EXIT THEN
AGAIN
;
VARIABLE see-my-type-column
: (see-my-type) ( indent limit xt str len -- indent limit xt )
dup see-my-type-column @ + dup 50 >= IF
-rot over "  " comp 0= IF
2drop see-my-type-column !
ELSE
rot drop                     ( indent limit xt str len )
pocket swap 2dup >r >r       ( indent limit xt str pk len  R: len pk )
move r> r>                   ( indent limit xt pk len )
2 pick (u.) dup -rot
cr type                      ( indent limit xt pk len xt-len )
" :" type 1+                 ( indent limit xt pk len prefix-len )
5 pick dup spaces +          ( indent limit xt pk len prefix-len )
over + see-my-type-column !  ( indent limit xt pk len )
type
THEN                            ( indent limit xt )
ELSE
see-my-type-column ! type       ( indent limit xt )
THEN
;
: (see-my-type-init) ( -- )
ffff see-my-type-column !        \ just enforce a new line
;
: (see-colon-body) ( indent limit xt -- indent limit xt )
(see-my-type-init)                              \ enforce new line
BEGIN                                           ( indent limit xt )
cell+ 2dup <>
over @
dup <semicolon> <>
rot and			                   ( indent limit xt @xt flag )
WHILE                                           ( indent limit xt @xt )
xt>name (see-my-type) "  " (see-my-type)
dup @                                        ( indent limit xt @xt)
CASE
<0branch>  OF cell+ dup @
over + cell+ dup >r
(u.) (see-my-type) r>          ( indent limit xt target)
2dup < IF
over 4 pick 3 + -rot recurse
nip nip nip cell-           ( indent limit xt )
ELSE
drop                        ( indent limit xt )
THEN
(see-my-type-init) ENDOF       \ enforce new line
<branch>   OF cell+ dup @ over + cell+ (u.)
(see-my-type) "  " (see-my-type) ENDOF
<do?do>    OF cell+ dup @ (u.) (see-my-type)
"  " (see-my-type) ENDOF
<lit>      OF cell+ dup @ (u.) (see-my-type)
"  " (see-my-type) ENDOF
<dotick>   OF cell+ dup @ xt>name (see-my-type)
"  " (see-my-type) ENDOF
<doloop>   OF cell+ dup @ (u.) (see-my-type)
"  " (see-my-type) ENDOF
<do+loop>  OF cell+ dup @ (u.) (see-my-type)
"  " (see-my-type) ENDOF
<doleave>  OF cell+ dup @ over + cell+ (u.)
(see-my-type) "  " (see-my-type) ENDOF
<do?leave> OF cell+ dup @ over + cell+ (u.)
(see-my-type) "  " (see-my-type) ENDOF
<sliteral> OF cell+ " """ (see-my-type) dup count dup >r
(see-my-type) " """ (see-my-type)
"  " (see-my-type)
r> -cell and + ENDOF
ENDCASE
REPEAT
drop
;
: (see-colon) ( xt -- )
(see-my-type-init)
1 swap 0 swap                                    ( indent limit xt )
" : " (see-my-type) dup xt>name (see-my-type)
rot drop 4 -rot (see-colon-body)                 ( indent limit xt )
rot drop 1 -rot (see-my-type-init) " ;" (see-my-type)
3drop 
;
: (see-create) ( xt -- )
dup cell+ @
CASE
<2constant> OF
dup cell+ cell+ dup @ swap cell+ @ . .  ." 2CONSTANT "
ENDOF
<instancevalue> OF
dup cell+ cell+ @ . ." INSTANCE VALUE "
ENDOF
<instancevariable> OF
." INSTANCE VARIABLE "
ENDOF
dup OF
." CREATE "
ENDOF
ENDCASE
(.xt)
;
: (see) ( xt -- )
cr dup dup @
CASE
<variable> OF ." VARIABLE " (.xt) ENDOF
<value>    OF dup execute . ." VALUE " (.xt) ENDOF
<constant> OF dup execute . ." CONSTANT " (.xt) ENDOF
<defer>    OF dup cell+ @ swap ." DEFER " (.xt) ."  is " (.xt) ENDOF
<alias>    OF dup cell+ @ swap ." ALIAS " (.xt) ."  " (.xt) ENDOF
<buffer:>  OF ." BUFFER: " (.xt) ENDOF
<create>   OF (see-create) ENDOF
<colon>    OF (see-colon)  ENDOF
dup        OF ." ??? PRIM " (.xt) ENDOF
ENDCASE
(.immediate) cr
;
: see ( "old-name<>" -- )
' (see)
;
0    value forth-ip
true value trace>stepping?
true value trace>print?
true value trace>up?
0    value trace>depth
0    value trace>rdepth
0    value trace>recurse
: trace-depth+ ( -- ) trace>depth 1+ to trace>depth ;
: trace-depth- ( -- ) trace>depth 1- to trace>depth ;
: stepping ( -- )
true to trace>stepping?
;
: tracing ( -- )
false to trace>stepping?
;
: trace-print-on ( -- )
true to trace>print?
;
: trace-print-off ( -- )
false to trace>print?
;
: fip-add ( n -- )
forth-ip + to forth-ip
;
0 value debug-last-xt
0 value debug-last-xt-content
: trace-print ( -- )
forth-ip cr u. ." : "
forth-ip @ 
dup ['] breakpoint = IF drop debug-last-xt-content THEN
xt>name type ."  "
."     ( " .s  ."  )  | "
;
: trace-interpret ( -- )
rdepth 1- to trace>rdepth
BEGIN
depth . [char] > dup emit emit space
source expect                        ( str len )
['] interpret catch print-status
AGAIN
;
: trace-xt ( xt -- )
trace>recurse IF
r> drop                                \ Drop return of 'trace-xt call
cell+                                  \ Step over ":"
ELSE
debug-last-xt-content <colon> = IF
['] breakpoint @ debug-last-xt !    \ Re-arm break point
r> drop                             \ Drop return of 'trace-xt call
cell+                               \ Step over ":"
ELSE
['] breakpoint debug-last-xt !      \ Re-arm break point
2r> 2drop
THEN
THEN
to forth-ip
true to trace>print?
BEGIN
trace>print? IF trace-print THEN
forth-ip                                              ( ip )
trace>stepping? IF
BEGIN
key
CASE
[char] d OF dup @ @ <colon> = IF             \ recurse only into colon definitions
trace-depth+
1 to trace>recurse
dup >r @ recurse
THEN true ENDOF
[char] u OF trace>depth IF tracing trace-print-off true ELSE false THEN ENDOF
[char] f OF drop cr trace-interpret ENDOF	\ quit trace and start interpreter FIXME rstack
[char] c OF tracing true ENDOF
[char] t OF trace-back false ENDOF
[char] q OF drop cr quit ENDOF
20       OF true ENDOF
dup      OF cr ." Press d:       Down into current word" cr
." Press u:       Up to caller" cr
." Press f:       Switch to forth interpreter, 'resume' will continue tracing" cr
." Press c:       Switch to tracing" cr
." Press <space>: Execute current word" cr
." Press q:       Abort execution, switch to interpreter" cr
false ENDOF
ENDCASE
UNTIL
THEN	                                              ( ip' )
dup to forth-ip @                                      ( xt )
dup ['] breakpoint = IF drop debug-last-xt-content THEN
dup                                                    ( xt xt )
CASE
<sliteral>  OF drop forth-ip cell+ dup dup c@ + -cell and to forth-ip ENDOF
<dotick>    OF drop forth-ip cell+ @ cell fip-add ENDOF
<lit>       OF drop forth-ip cell+ @ cell fip-add ENDOF
<doto>      OF drop forth-ip cell+ @ cell+ ! cell fip-add ENDOF
<(doito)>   OF drop forth-ip cell+ @ cell+ cell+ @ >instance ! cell fip-add ENDOF
<0branch>   OF drop IF
cell fip-add
ELSE
forth-ip cell+ @ cell+ fip-add THEN
ENDOF
<do?do>     OF drop 2dup <> IF
swap >r >r cell fip-add
ELSE
forth-ip cell+ @ cell+ fip-add 2drop THEN
ENDOF
<branch>    OF drop forth-ip cell+ @ cell+ fip-add ENDOF
<doleave>   OF drop r> r> 2drop forth-ip cell+ @ cell+ fip-add ENDOF		
<do?leave>  OF drop IF
r> r> 2drop forth-ip cell+ @ cell+ fip-add
ELSE
cell fip-add
THEN
ENDOF		
<doloop>    OF drop r> 1+ r> 2dup = IF
2drop cell fip-add
ELSE >r >r
forth-ip cell+ @ cell+ fip-add THEN
ENDOF
<do+loop>   OF drop r> + r> 2dup >= IF
2drop cell fip-add
ELSE >r >r
forth-ip cell+ @ cell+ fip-add THEN
ENDOF
<semicolon> OF trace>depth 0> IF
trace-depth- 1 to trace>recurse
stepping drop r> recurse
ELSE
drop exit THEN
ENDOF
<exit>      OF trace>depth 0> IF
trace-depth- stepping drop r> recurse
ELSE
drop exit THEN
ENDOF
dup         OF execute ENDOF
ENDCASE
forth-ip cell+ to forth-ip
AGAIN
;
: resume ( -- )
trace>rdepth rdepth!
forth-ip cell - trace-xt
;
: debug-off ( -- )
debug-last-xt IF
debug-last-xt-content debug-last-xt !  \ Restore overwritten token
0 to debug-last-xt
THEN
;
: (break-entry) ( -- )
debug-last-xt dup @ ['] breakpoint <> swap  ( debug-addr? debug-last-xt )
debug-last-xt-content swap !                \ Restore overwritten token
r> drop                                     \ Don't return to bp, but to caller
debug-last-xt-content <colon> <> and IF     \ Execute non colon definition
debug-last-xt cr u. ." : "
debug-last-xt xt>name type ."  "
."     ( " .s  ."  )  | "
key drop
debug-last-xt execute
ELSE
debug-last-xt 0 to trace>depth 0 to trace>recurse trace-xt   \ Trace colon definition
THEN
;
' (break-entry) to BP
: debug-address ( addr --  )
debug-off                       ( xt )  \ Remove active breakpoint
dup to debug-last-xt            ( xt )  \ Save token for later debug
dup @ to debug-last-xt-content  ( xt )  \ Save old value
['] breakpoint swap !
;
: (debug ( xt --  )
debug-off                       ( xt )  \ Remove active breakpoint
dup to debug-last-xt            ( xt )  \ Save token for later debug
dup @ to debug-last-xt-content  ( xt )  \ Save old value
['] breakpoint @ swap !
;
: debug ( "old-name<>" -- )
parse-word $find IF                       \ Get xt for old-name
(debug
ELSE
." undefined word " type cr
THEN
;
: words
last @
BEGIN ?dup WHILE
dup cell+ char+ count type space @
REPEAT
;
: .calls    ( xt -- )
current-node @ >r 0 set-node    \ only search commands, according too IEEE1275
last BEGIN @ ?dup WHILE    ( xt currxt )
dup cell+ char+         ( xt currxt name* )
dup dup c@ + 1+ aligned ( xt currxt name* CFA )
dup @ <colon> = IF      ( xt currxt name* CFA )
BEGIN
cell+ dup @ ['] semicolon <>
WHILE		      ( xt currxt *name pos )
dup @ 4 pick = IF ( xt currxt *name pos )
over count type space
BEGIN cell+ dup @ ['] semicolon = UNTIL cell - \ eat up other occurrences
THEN
REPEAT
THEN
2drop ( xt currxt )
REPEAT
drop
r> set-node		   \ restore node
;
0 value #sift-count
false value sift-compl-only
: $inner-sift ( text-addr text-len LFA -- ... word-addr word-len true | false )
dup cell+ char+ count           \ get word name
2dup 6 pick 6 pick find-isubstr \ is there a partly match?
sift-compl-only IF 0= ELSE over < THEN
IF
#sift-count 1+ to #sift-count \ count completions
true
ELSE
2drop false
THEN
;
: $sift    ( text-addr text-len -- )
current-node @ >r 0 set-node	\ only search commands, according too IEEE1275
sift-compl-only >r false to sift-compl-only \ all substrings, not only compl.
last BEGIN @ ?dup WHILE	\ walk the whole dictionary
$inner-sift IF type space THEN
REPEAT
2drop
0 to #sift-count	   \ we don't need completions here.
r> to sift-compl-only    \ restore previous sifting mode
r> set-node		   \ restore node
;
: sifting    ( "text< >" -- )
parse-word $sift
;
: ([IF])
BEGIN
BEGIN parse-word dup 0= WHILE
2drop refill
REPEAT
2dup s" [IF]" str= IF 1 throw THEN
2dup s" [ELSE]" str= IF 2 throw THEN
2dup s" [THEN]" str= IF 3 throw THEN
s" \" str= IF linefeed parse 2drop THEN
AGAIN
;
: [IF] ( flag -- )
IF exit THEN
1 BEGIN
['] ([IF]) catch 
CASE
1 OF 1+ ENDOF
2 OF dup 1 = if 1- then ENDOF
3 OF 1- ENDOF
ENDCASE
dup 0 <=
UNTIL drop
; immediate
: [ELSE] 0 [COMPILE] [IF] ; immediate
: [THEN] ; immediate
: $dnumber base @ >r decimal $number r> base ! ;
: (.d) base @ >r decimal (.) r> base ! ;
4000 to default-load-base
deadbeef here l!
here c@ de = CONSTANT ?bigendian
here c@ ef = CONSTANT ?littleendian
?bigendian [IF]
: x!-le >r xbflip r> x! ;
: x@-le x@ xbflip ;
: l!-le  >r lbflip r> l! ;
: l@-le  l@ lbflip ;
: w!-le  >r wbflip r> w! ;
: w@-le  w@ wbflip ;
: rx!-le  >r xbflip r> rx! ;
: rx@-le  rx@ xbflip ;
: rl!-le  >r lbflip r> rl! ;
: rl@-le  rl@ lbflip ;
: rw!-le  >r wbflip r> rw! ;
: rw@-le  rw@ wbflip ;
: l!-be  l! ;
: l@-be  l@ ;
: w!-be  w! ;
: w@-be  w@ ;
: rl!-be  rl! ;
: rl@-be  rl@ ;
: rw!-be  rw! ;
: rw@-be  rw@ ;
[ELSE]
: x!-le x! ;
: x@-le x@ ;
: l!-le  l! ;
: l@-le  l@ ;
: w!-le  w! ;
: w@-le  w@ ;
: rx!-le  rx! ;
: rx@-le  rx@ ;
: rl!-le  rl! ;
: rl@-le  rl@ ;
: rw!-le  rw! ;
: rw@-le  rw@ ;
: l!-be  >r lbflip r> l! ;
: l@-be  l@ lbflip ;
: w!-be  >r wbflip r> w! ;
: w@-be  w@ wbflip ;
: rl!-be  >r lbflip r> rl! ;
: rl@-be  rl@ lbflip ;
: rw!-be  >r wbflip r> rw! ;
: rw@-be  rw@ wbflip ;
[THEN]
: #join  ( lo hi #bits -- x )  lshift or ;
: #split ( x #bits -- lo hi )  2dup rshift dup >r swap lshift xor r> ;
: blink ;
: reset-dual-emit ;
: console-clean-fifo ;
: bootmsg-nvupdate ;
: asm-cout 2drop drop ;
defer nvramlog-write-byte
: .nvramlog-write-byte ( byte -- )
drop
;
' .nvramlog-write-byte to nvramlog-write-byte
: nvramlog-write-string ( str len -- )
dup 0> IF
0 DO dup c@ 
nvramlog-write-byte char+ LOOP
ELSE
drop
THEN drop ;
: nvramlog-write-number ( number format -- )
0 swap <# 0 ?DO # LOOP #> 
nvramlog-write-string ;
: nvramlog-write-string-cr ( str len -- )
nvramlog-write-string
a nvramlog-write-byte d nvramlog-write-byte ;
: log-string ( str len -- ) type ;
: log-string 2drop ;
create debugstr 255 allot
0 VALUE debuglen
: cp ( checkpoint -- )
bootmsg-cp ;
: (warning) ( id level ptr len -- )
dup TO debuglen
debugstr swap move           \ copy into buffer
0 debuglen debugstr + c!     \ terminate '\0'
debugstr bootmsg-warning
;
: warning" ( id level [text<">] -- )
postpone s" state @
IF
['] (warning) compile,
ELSE
(warning)
THEN
; immediate
: (debug-cp) ( id level ptr len -- )
dup TO debuglen
debugstr swap move           \ copy into buffer
0 debuglen debugstr + c!     \ terminate '\0'
debugstr bootmsg-debugcp
;
: debug-cp" ( id level [text<">] -- )
postpone s" state @
IF
['] (debug-cp) compile,
ELSE
(debug-cp)
THEN
; immediate
: (error) ( id ptr len -- )
dup TO debuglen
debugstr swap move           \ copy into buffer
0 debuglen debugstr + c!     \ terminate '\0'
debugstr bootmsg-error
;
: error" ( id level [text<">] -- )
postpone s" state @
IF
['] (error) compile,
ELSE
(error)
THEN
; immediate
bootmsg-nvupdate
000 cp
STRUCT
cell FIELD >r0   cell FIELD >r1   cell FIELD >r2   cell FIELD >r3
cell FIELD >r4   cell FIELD >r5   cell FIELD >r6   cell FIELD >r7
cell FIELD >r8   cell FIELD >r9   cell FIELD >r10  cell FIELD >r11
cell FIELD >r12  cell FIELD >r13  cell FIELD >r14  cell FIELD >r15
cell FIELD >r16  cell FIELD >r17  cell FIELD >r18  cell FIELD >r19
cell FIELD >r20  cell FIELD >r21  cell FIELD >r22  cell FIELD >r23
cell FIELD >r24  cell FIELD >r25  cell FIELD >r26  cell FIELD >r27
cell FIELD >r28  cell FIELD >r29  cell FIELD >r30  cell FIELD >r31
cell FIELD >cr   cell FIELD >xer  cell FIELD >lr   cell FIELD >ctr
cell FIELD >srr0 cell FIELD >srr1 cell FIELD >dar  cell FIELD >dsisr
CONSTANT ciregs-size
: .16  10 0.r 3 spaces ;
: .8   8 spaces 8 0.r 3 spaces ;
: .4regs  cr 4 0 DO dup @ .16 8 cells+ LOOP drop ;
: .fixed-regs
cr ."     R0 .. R7           R8 .. R15         R16 .. R23         R24 .. R31"
dup 8 0 DO dup .4regs cell+ LOOP drop
;
: .special-regs
cr ."     CR / XER           LR / CTR          SRR0 / SRR1        DAR / DSISR"
cr dup >cr  @ .8   dup >lr  @ .16  dup >srr0 @ .16  dup >dar @ .16
cr dup >xer @ .16  dup >ctr @ .16  dup >srr1 @ .16    >dsisr @ .8
;
: .regs
cr .fixed-regs
cr .special-regs
cr cr
;
: .hw-exception ( reason-code exception-nr -- )
." ( " dup . ." ) "
CASE
200 OF ." Machine Check" ENDOF
300 OF ." Data Storage" ENDOF
380 OF ." Data Segment" ENDOF
400 OF ." Instruction Storage" ENDOF
480 OF ." Instruction Segment" ENDOF
500 OF ." External" ENDOF
600 OF ." Alignment" ENDOF
700 OF ." Program" ENDOF
800 OF ." Floating-point unavailable" ENDOF
900 OF ." Decrementer" ENDOF
980 OF ." Hypervisor Decrementer" ENDOF
C00 OF ." System Call" ENDOF
D00 OF ." Trace" ENDOF
F00 OF ." Performance Monitor" ENDOF
F20 OF ." VMX Unavailable" ENDOF
1200 OF ." System Error" ENDOF
1600 OF ." Maintenance" ENDOF
1800 OF ." Thermal" ENDOF
dup OF ." Unknown" ENDOF
ENDCASE
."  Exception [ " . ." ]"
;
: .sw-exception ( exception-nr -- )
."  Exception [ " . ." ] triggered by boot firmware."
;
: be-hw-exception ( [reason-code] exception-nr -- )
cr cr
dup 0> IF .hw-exception ELSE .sw-exception THEN
cr eregs .regs
;
' be-hw-exception to hw-exception-handler
: (boot-exception-handler) ( x1...xn exception-nr -- x1...xn)
dup IF
dup 0 > IF
negate cp 9 emit ." : " type
ELSE
CASE
-6d OF cr ." W3411: Client application returned." cr ENDOF
-6c OF cr ." E3400: It was not possible to boot from any device "
." specified in the VPD." cr
ENDOF
-6b OF cr ." E3410: Boot list successfully read from VPD "
." but no useful information received." cr
ENDOF
-6a OF cr ." E3420: Boot list could not be read from VPD." cr
ENDOF
-69 OF
cr ." E3406: Client application returned an error"
abort"-str @ count dup IF
." :    " type cr
ELSE
." ." cr
2drop
THEN
ENDOF
-68 OF cr ." E3405: No such device" cr ENDOF
-67 OF cr ." E3404: Not a bootable device!" cr ENDOF
-66 OF cr ." E3408: Failed to claim memory for the executable" cr
ENDOF
-65 OF cr ." E3407: Load failed" cr ENDOF
-64 OF cr ." E3403: Bad executable:   " abort"-str @ count type cr
ENDOF
-63 OF cr ." E3409: Unknown FORTH Word" cr ENDOF
-2 OF cr ." E3401: Aborting boot,  " abort"-str @ count type cr
ENDOF
dup OF ." E3402: Aborting boot, internal error" cr ENDOF
ENDCASE
THEN
ELSE
drop
THEN
;
' (boot-exception-handler) to boot-exception-handler
: throw-error ( error-code "error-string" -- )
skipws 0a parse rot throw
;
: enable-ext-int ( -- )
msr@ 8000 or msr!
;
: disable-ext-int ( -- )
msr@ 8000 not and msr!
;
: gen-ext-int ( -- )
7fffffff dec!               \ Reset decrementer
enable-ext-int              \ Enable interrupt
FF 20000508418 rx!          \ Interrupt priority mask
10 20000508410 rx!          \ Interrupt priority
;
: mm-log-warning 2drop ;
: write-mm-log ( data length type -- status )
3drop 0
;
100 cp
: beep  bell emit ;
: TABLE-EXECUTE
CREATE DOES> swap cells+ @ ?dup IF execute ELSE beep THEN ;
0 VALUE accept-adr
0 VALUE accept-max
0 VALUE accept-len
0 VALUE accept-cur
: esc  1b emit ;
: csi  esc 5b emit ;
: move-cursor ( -- )
esc ." 8" accept-cur IF
csi base @ decimal accept-cur 0 .r base ! ." C"
THEN
;
: redraw-line ( -- )
accept-cur accept-len = IF EXIT THEN
move-cursor
accept-adr accept-len accept-cur /string type
csi ." K" move-cursor
;
: full-redraw-line ( -- )
accept-cur 0 to accept-cur move-cursor
accept-adr accept-len type
csi ." K" to accept-cur move-cursor
;
: redraw-prompt ( -- )
cr depth . [char] > emit
;
: insert-char ( char -- )
accept-len accept-max = IF drop beep EXIT THEN
accept-cur accept-len <> IF csi ." @" dup emit
accept-adr accept-cur + dup 1+ accept-len accept-cur - move
ELSE dup emit THEN
accept-adr accept-cur + c!
accept-cur 1+ to accept-cur
accept-len 1+ to accept-len redraw-line
;
: delete-char ( -- )
accept-cur accept-len = IF beep EXIT THEN
accept-len 1- to accept-len
accept-adr accept-cur + dup 1+ swap accept-len accept-cur - move
csi ." P" redraw-line
;
STRUCT
cell FIELD his>next
cell FIELD his>prev
cell FIELD his>len
0 FIELD his>buf
CONSTANT /his
0 VALUE his-head
0 VALUE his-tail
0 VALUE his-cur
: add-history ( -- )
accept-len 0= IF EXIT THEN
/his accept-len + alloc-mem
his-tail IF dup his-tail his>next ! ELSE dup to his-head THEN
his-tail over his>prev !  0 over his>next !  dup to his-tail
accept-len over his>len !  accept-adr swap his>buf accept-len move
;
: history  ( -- )
his-head BEGIN dup WHILE
cr dup his>buf over his>len @ type
his>next @ REPEAT drop
;
: select-history ( his -- )
dup to his-cur dup IF
dup his>len @ accept-max min dup to accept-len to accept-cur
his>buf accept-adr accept-len move ELSE
drop 0 to accept-len 0 to accept-cur THEN
full-redraw-line
;
0 value ?tab-pressed
0 value tab-last-adr
0 value tab-last-len
: $same-string ( addr-1 len-1 addr-2 len-2 -- addr-1 len-1' )
dup 0= IF    \ The second parameter is not a string.
2drop EXIT \ bail out
THEN
rot min 0 0 -rot ( addr1 addr2 0 len' 0 )
DO ( addr1 addr2 len-1' )
2 pick i + c@ lcc
2 pick i + c@ lcc
= IF 1 + ELSE leave THEN
LOOP
nip
;
: $tab-sift-words    ( text-addr text-len -- sift-count )
sift-compl-only >r true to sift-compl-only \ save sifting mode
last BEGIN @ ?dup WHILE \ loop over all words
$inner-sift IF \ any completions possible?
2dup bounds DO I c@ lcc I c! LOOP
?tab-pressed IF 2dup type space THEN  \ <tab><tab> prints possibilities
tab-last-adr tab-last-len $same-string \ find matching substring ...
to tab-last-len to tab-last-adr       \ ... and save it
THEN
repeat
2drop
#sift-count 0 to #sift-count	\ how many words were found?
r> to sift-compl-only		\ restore sifting completion mode
;
0 value current-stack
: new-stack ( cells <>name -- )
create >r here    ( here R: cells )
dup r@ 2 + cells  ( here here bytes R: cells )
dup allot erase   ( here R: cells)
cell+ r>          ( here+1cell cells )
swap !            ( )
DOES> to current-stack
;
: reset-stack ( -- )
0 current-stack !
;
: stack-depth ( -- depth )
current-stack @
;
: push ( value -- )
current-stack @
current-stack cell+ @ over <= ABORT" Stack overflow"
cells
1 current-stack +!
current-stack 2 cells + + !
;
: pop ( -- value )
current-stack @ 0= ABORT" Stack underflow"
current-stack @ cells
current-stack + cell+ @
-1 current-stack +!
;
10 new-stack device-stack
: (next-dev) ( node -- node' addr len )
device-stack
dup (node>path) rot
dup child IF dup push child -rot EXIT THEN
dup peer IF peer -rot EXIT THEN
drop
BEGIN
stack-depth
WHILE
pop peer ?dup IF -rot EXIT THEN
REPEAT
0 -rot
;
: $inner-sift-nodes ( text-addr text-len node -- ... path-addr path-len true | false )
(next-dev) ( text-addr text-len node' path-addr path-len )
dup 0= IF drop false EXIT THEN
2dup 6 pick 6 pick find-isubstr ( text-addr text-len node' path-addr path-len pos )
0= IF
#sift-count 1+ to #sift-count \ count completions
true
ELSE
2drop false
THEN
;
: .nodes ( -- )
s" /" find-node BEGIN dup WHILE
(next-dev)
type cr
REPEAT
drop
reset-stack
;
create sift-node-buffer 1000 allot
0 value sift-node-num
: sift-node-buffer
sift-node-buffer sift-node-num 100 * +
sift-node-num 1+ dup 10 = IF drop 0 THEN
to sift-node-num
;
: $tab-sift-nodes    ( text-addr text-len -- sift-count )
s" /" find-node BEGIN dup WHILE
$inner-sift-nodes IF \ any completions possible?
sift-node-buffer swap 2>r 2r@ move 2r> \ make an almost permanent copy without strdup
?tab-pressed IF 2dup type space THEN  \ <tab><tab> prints possibilities
tab-last-adr tab-last-len $same-string \ find matching substring ...
to tab-last-len to tab-last-adr       \ ... and save it
THEN
REPEAT
2drop drop
#sift-count 0 to #sift-count	\ how many words were found?
reset-stack
;
: $tab-sift    ( text-addr text-len -- sift-count )
?tab-pressed IF beep space THEN \ cosmetical fix for <tab><tab>
dup IF bl rsplit dup IF 2swap THEN ELSE 0 0 THEN >r >r
0 dup to tab-last-len to tab-last-adr	\ reset last possible match
current-node @ IF			\ if we are in a node?
2dup 2>r				\ save text
$tab-sift-words to #sift-count	\ search in current node first
2r>				\ fetch text to complete, again
THEN
2dup 2>r
current-node @ >r 0 set-node		\ now search in global words
$tab-sift-words to #sift-count
r> set-node
2r> $tab-sift-nodes
r> r> dup IF s"  " $cat THEN tab-last-adr tab-last-len $cat
to tab-last-len to tab-last-adr  \ ... and save the whole string
;
: handle-^A
0 to accept-cur move-cursor ;
: handle-^B
accept-cur ?dup IF 1- to accept-cur ( csi ." D" ) move-cursor THEN ;
: handle-^D
delete-char ( redraw-line ) ;
: handle-^E
accept-len to accept-cur move-cursor ;
: handle-^F
accept-cur accept-len <> IF accept-cur 1+ to accept-cur csi ." C" THEN ;
: handle-^H
accept-cur 0= IF beep EXIT THEN
handle-^B delete-char
;
: handle-^I
accept-adr accept-len
$tab-sift 0 > IF
?tab-pressed IF
redraw-prompt full-redraw-line
false to ?tab-pressed
ELSE
tab-last-adr accept-adr tab-last-len move    \ copy matching substring
tab-last-len dup to accept-len to accept-cur \ len and cursor position
full-redraw-line		\ redraw new string
true to ?tab-pressed	\ second tab will print possible matches
THEN
THEN
;
: handle-^K
BEGIN accept-cur accept-len <> WHILE delete-char REPEAT ;
: handle-^L
history redraw-prompt full-redraw-line ;
: handle-^N
his-cur IF his-cur his>next @ ELSE his-head THEN
dup to his-cur select-history
;
: handle-^P
his-cur IF his-cur his>prev @ ELSE his-tail THEN
dup to his-cur select-history
;
: handle-^Q  \ Does not handle terminal formatting yet.
key insert-char ;
: handle-^R
full-redraw-line ;
: handle-^U
0 to accept-len 0 to accept-cur full-redraw-line ;
: handle-fn
key drop beep
;
TABLE-EXECUTE handle-CSI
0 , ' handle-^P , ' handle-^N , ' handle-^F ,
' handle-^B , 0 , 0 , 0 ,
' handle-^A , 0 , 0 , ' handle-^E ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
: handle-CSI-key
key 1f and handle-CSI
;
TABLE-EXECUTE handle-meta
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , ' handle-fn ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 ,
0 , 0 , 0 , ' handle-CSI-key ,
0 , 0 , 0 , 0 ,
: handle-ESC-O
key
dup 48 = IF
handle-^A
ELSE
dup 46 = IF
handle-^E
THEN
THEN drop
;
: handle-ESC-5b
key
dup 31 = IF \ HOME
key drop ( drops closing 7e ) handle-^A
ELSE
dup 33 = IF \ DEL
key drop handle-^D
ELSE
dup 34 = IF \ END
key drop handle-^E
ELSE
dup 1f and handle-CSI
THEN
THEN
THEN drop
;
: handle-ESC
key
dup 5b = IF
handle-ESC-5b
ELSE
dup 4f = IF
handle-ESC-O
ELSE
dup 1f and handle-meta
THEN
THEN drop
;
TABLE-EXECUTE handle-control
0 , \ ^@:
' handle-^A ,
' handle-^B ,
0 , \ ^C:
' handle-^D ,
' handle-^E ,
' handle-^F ,
0 , \ ^G:
' handle-^H ,
' handle-^I , \ tab
0 , \ ^J:
' handle-^K ,
' handle-^L ,
0 , \ ^M: enter: handled in main loop
' handle-^N ,
0 , \ ^O:
' handle-^P ,
' handle-^Q ,
' handle-^R ,
0 , \ ^S:
0 , \ ^T:
' handle-^U ,
0 , \ ^V:
0 , \ ^W:
0 , \ ^X:
0 , \ ^Y: insert save buffer
0 , \ ^Z:
' handle-ESC ,
0 , \ ^\:
0 , \ ^]:
0 , \ ^^:
0 , \ ^_:
: (accept) ( adr len -- len' )
cursor-on
to accept-max to accept-adr
0 to accept-len 0 to accept-cur
0 to his-cur
1b emit 37 emit
BEGIN
key dup 0d <>
WHILE
dup 9 <> IF 0 to ?tab-pressed THEN \ reset state machine
dup 7f = IF drop 8 THEN \ Handle DEL as if it was BS. ??? bogus
dup bl < IF handle-control ELSE
dup 80 and IF
dup a0 < IF 7f and handle-meta ELSE drop beep THEN
ELSE
insert-char
THEN
THEN
REPEAT
drop add-history
accept-len to accept-cur
move-cursor space
accept-len
cursor-off
;
' (accept) to accept
120 cp
1 VALUE /dump
' c@ VALUE 'dump
0 VALUE dump-first
0 VALUE dump-last
0 VALUE dump-cur
: .char ( c -- )  dup bl 7f within 0= IF drop [char] . THEN emit ;
: dump-line ( -- )
cr dump-cur dup 8 0.r [char] : emit 10 /dump / 0 DO
space dump-cur dump-first dump-last within IF
dump-cur 'dump execute /dump 2* 0.r ELSE
/dump 2* spaces THEN dump-cur /dump + to dump-cur LOOP
/dump 1 <> IF drop EXIT THEN
to dump-cur 2 spaces
10 0 DO dump-cur dump-first dump-last within IF
dump-cur 'dump execute .char ELSE space THEN dump-cur 1+ to dump-cur LOOP ;
: (dump) ( addr len reader size -- )
to /dump to 'dump bounds /dump negate and to dump-first to dump-last
dump-first f invert and to dump-cur
base @ hex BEGIN dump-line dump-cur dump-last >= UNTIL base ! ;
: du ( -- )  dump-last 100 'dump /dump (dump) ;
: dump     ['] c@      1 (dump) ;
: wdump    ['] w@      2 (dump) ;
: ldump    ['] l@      4 (dump) ;
: xdump    ['] x@      8 (dump) ;
: rdump    ['] rb@     1 (dump) ;
cistack ciregs >r1 ! \ kernel wants a stack :-)
140 cp
STRUCT
cell field romfs>file-header
cell field romfs>data
cell field romfs>data-size
cell field romfs>flags
CONSTANT /romfs-lookup-control-block
CREATE romfs-lookup-cb /romfs-lookup-control-block allot
romfs-lookup-cb /romfs-lookup-control-block erase
: create-filename ( string -- string\0 )
here >r dup 8 + allot
r@ over 8 + erase
r@ zplace r> ;
: romfs-lookup ( fn-str fn-len -- data size | false )
create-filename romfs-base
romfs-lookup-cb romfs-lookup-entry call-c
0= IF romfs-lookup-cb dup romfs>data @ swap romfs>data-size @ ELSE
false THEN ;
: ibm,romfs-lookup ( fn-str fn-len -- data-high data-low size | 0 0 false )
romfs-lookup dup
0= if drop 0 0 false else
swap dup 20 rshift swap ffffffff and then ;
: romfs-lookup-client ibm,romfs-lookup ;
STRUCT
cell field romfs>next-off
cell field romfs>size
cell field romfs>flags
cell field romfs>data-off
cell field romfs>name
CONSTANT /romfs-cb
: romfs-map-file ( fn-str fn-len -- file-addr file-size )
romfs-base >r
BEGIN 2dup r@ romfs>name zcount string=ci not WHILE
( fn-str fn-len ) ( R: rom-cb-file-addr )
r> romfs>next-off dup @ dup 0= IF 1 THROW THEN + >r REPEAT
( fn-str fn-len ) ( R: rom-cb-file-addr )
2drop r@ romfs>data-off @ r@ + r> romfs>size @ ;
: flash-header ( -- address | false )
get-flash-base 28 +         \ prepare flash header file address
dup rx@                     \ fetch "magic123"
6d61676963313233 <> IF      \ IF flash is not valid
drop                     \ | forget address
false                    \ | return false
THEN                        \ FI
;
CREATE bdate-str 10 allot
: bdate2human ( -- addr len )
flash-header 40 + rx@ (.)
drop dup 0 + bdate-str 6 + 4 move
dup 4 + bdate-str 0 + 2 move
dup 6 + bdate-str 3 + 2 move
dup 8 + bdate-str b + 2 move
a + bdate-str e + 2 move
2d bdate-str 2 + c!
2d bdate-str 5 + c!
20 bdate-str a + c!
3a bdate-str d + c!
bdate-str 10
;
: included  ( fn fn-len -- )
2dup >r >r romfs-lookup dup IF
r> drop r> drop evaluate
ELSE
drop ." Cannot open file : " r> r> type cr
THEN
;
: include  ( " fn " -- )
parse-word included
;
: ?include  ( flag " fn " -- )
parse-word rot IF included ELSE 2drop THEN
;
: include?  ( nargs flag " fn " -- )
parse-word rot IF
rot drop included
ELSE
2drop 0 ?DO drop LOOP
THEN
;
: (print-romfs-file-info)  ( file-addr -- )
9 emit  dup b 0.r  2 spaces  dup 8 + @ 6 0.r  2 spaces  20 + zcount type cr
;
: romfs-list  ( -- )
romfs-base 0 cr BEGIN + dup (print-romfs-file-info) dup @ dup 0= UNTIL 2drop
;
200 cp
: .slof-logo
cr ."         ..`. ..     .......  ..           ......      ......."
cr ."     ..`...`''.`'. .''``````..''.       .`''```''`.  `''``````"
cr ."        .`` .:' ': `''.....  .''.       ''`     .''..''......."
cr ."          ``.':.';. ``````''`.''.      .''.      ''``''`````'`"
cr ."          ``.':':`   .....`''.`'`...... `'`.....`''.`'`       "
cr ."         .`.`'``   .'`'`````.  ``''''''  ``''`'''`. `'`       "
;
201 cp
: banner
cr ."   Type 'boot'  and press return  to  continue  booting  the system."
cr ."   Type 'reset-all'  and  press  return  to   reboot   the   system."
cr cr
;
: .banner banner console-clean-fifo ;
: .banner .slof-logo .banner ;
220 cp
DEFER find-boot-sector ( -- )
240 cp
d# 512000000 VALUE tb-frequency   \ default value - needed for "ms" to work
-1 VALUE cpu-frequency
: slof-build-id  ( -- str len )
flash-header 10 + a
;
: slof-revision s" 001" ;
: read-version-and-date
flash-header 0= IF
s"  " encode-string
ELSE
flash-header 10 + 10
here swap rmove
here 10
s" , " $cat
bdate2human $cat encode-string THEN
;
: from-cstring ( addr - len )  
dup dup BEGIN c@ 0 <> WHILE 1 + dup REPEAT
swap -
;
: invert-region-cs ( addr len cellsize -- )
>r over swap r@ rshift r> swap 1 hv-logical-memop drop
;
: invert-region ( addr len -- )
2dup or 7 and CASE
0 OF 3 invert-region-cs ENDOF
4 OF 2 invert-region-cs ENDOF
3 and
2 OF 1 invert-region-cs ENDOF
dup OF 0 invert-region-cs ENDOF
ENDCASE
;
260 cp
: tb@  ( -- tb )
BEGIN tbu@ tbl@ tbu@ rot over <> WHILE 2drop REPEAT
20 lshift swap ffffffff and or
;
: milliseconds ( -- ms ) tb@ d# 1000 * tb-frequency / ;
: microseconds ( -- us ) tb@ d# 1000000 * tb-frequency / ;
: ms ( ms-to-wait -- ) milliseconds + BEGIN milliseconds over >= UNTIL drop ;
: get-msecs ( -- n ) milliseconds ;
: us  ( us-to-wait -- )  microseconds +  BEGIN microseconds over >= UNTIL  drop ;
2e0 cp
100 CONSTANT quiesce-xt#
CREATE quiesce-xts quiesce-xt# cells allot
quiesce-xts quiesce-xt# cells erase
0 VALUE quiesce-done?
: add-quiesce-xt  ( xt -- )
quiesce-xt# 0 DO
quiesce-xts I cells +    ( xt arrayptr )
dup @ 0=                 ( xt arrayptr true|false )
IF
! UNLOOP EXIT
ELSE                     ( xt arrayptr )
over swap             ( xt xt arrayptr )
@ =                   \ xt already stored ?
IF
drop UNLOOP EXIT
THEN                  ( xt )
THEN
LOOP
drop                        ( xt -- )
." Warning: quiesce xt list is full." cr
;
: quiesce  ( -- )
quiesce-done? IF EXIT THEN
true to quiesce-done?
quiesce-xt# 0 DO
quiesce-xts I cells +    ( arrayptr )
@ dup IF                 ( xt )
EXECUTE
ELSE
drop UNLOOP EXIT
THEN
LOOP
;
300 cp
: load-dev-hci ( num name-str name-len )
s" dev-hci.fs" INCLUDED
;
0 VALUE ohci-init
0 VALUE ehci-init
0 VALUE xhci-init
0 VALUE usb-alias-num
: get-usb-alias-num
usb-alias-num dup 1+ to usb-alias-num
;
: set-ohci-alias  (  -- )
1 to ohci-init 
get-usb-alias-num       ( num )
s" ohci" 1 load-dev-hci
;
: set-ehci-alias  (  -- )
1 to ehci-init
get-usb-alias-num       ( num )
s" ehci" 2 load-dev-hci
;
: set-xhci-alias  (  -- )
1 to xhci-init 
get-usb-alias-num       ( num )
s" xhci" 3 load-dev-hci
;
: usb-enumerate ( hcidev -- )
USB-HCD-INIT
;
: usb-scan ( -- )
." Scanning USB " cr
ohci-init 1 = IF USB-OHCI-REGISTER THEN
ehci-init 1 = IF USB-EHCI-REGISTER THEN
xhci-init 1 = IF USB-XHCI-REGISTER THEN
usb-alias-num 0 ?DO
" usb" i $cathex find-device
" get-hci-dev" get-node find-method
IF
execute usb-enumerate
ELSE
." get-base-address method not found for usb@" i . 
."  Device type: "
" device_type" get-node get-property 0= IF decode-string type cr 2drop THEN
THEN
LOOP
0 set-node     \ FIXME Setting it back
;
320 cp
false VALUE scsi-supp-present?
: scsi-xt-err ." SCSI-ERROR (Intern) " ;
' scsi-xt-err VALUE scsi-open-xt        \ preset with an invalid token
: .wordlists      ( -- )
get-order      ( -- wid1 .. widn n )
dup space 28 emit .d ." word lists : "
0 DO
. 08 emit 2c emit
LOOP
08 emit                 \ 'bs'
29 emit                 \ ')'
cr space 28 emit
." Context: " context dup .
@ 5b emit . 8 emit 5d emit
space
." / Current: " current .
cr
;
: scsi-open  ( -- )
scsi-supp-present? NOT
IF
s" scsi-support.fs" included  ( xt-open )
to scsi-open-xt               (  )
true to scsi-supp-present?
THEN
scsi-open-xt execute
;
340 cp
0 VALUE fdt-debug
TRUE VALUE fdt-cas-fix?
fdt-start 0 = IF -1 throw THEN
struct
4 field >fdth_magic
4 field >fdth_tsize
4 field >fdth_struct_off
4 field >fdth_string_off
4 field >fdth_rsvmap_off
4 field >fdth_version
4 field >fdth_compat_vers
4 field >fdth_boot_cpu
4 field >fdth_string_size
4 field >fdth_struct_size
drop
h# d00dfeed constant OF_DT_HEADER
h#        1 constant OF_DT_BEGIN_NODE
h#        2 constant OF_DT_END_NODE
h#        3 constant OF_DT_PROP
h#        4 constant OF_DT_NOP
h#        9 constant OF_DT_END
0 value fdt-start-addr
0 value fdt-struct
0 value fdt-strings
: fdt-init ( fdt-start -- )
dup to fdt-start-addr
dup dup >fdth_struct_off l@ + to fdt-struct
dup dup >fdth_string_off l@ + to fdt-strings
drop
;
fdt-start fdt-init
: fdt-check-header ( -- )
fdt-start-addr dup 0 = IF
." No flat device tree !" cr drop -1 throw EXIT THEN
hex
fdt-debug IF
." Flat device tree header at 0x" dup . s" :" type cr
."  magic            : 0x" dup >fdth_magic l@ . cr
."  total size       : 0x" dup >fdth_tsize l@ . cr
."  offset to struct : 0x" dup >fdth_struct_off l@ . cr
."  offset to strings: 0x" dup >fdth_string_off l@ . cr
."  offset to rsvmap : 0x" dup >fdth_rsvmap_off l@ . cr
."  version          : " dup >fdth_version l@ decimal . hex cr
."  last compat vers : " dup >fdth_compat_vers l@ decimal . hex cr
dup >fdth_version l@ 2 >= IF
."  boot CPU         : 0x" dup >fdth_boot_cpu l@ . cr
THEN
dup >fdth_version l@ 3 >= IF
."  strings size     : 0x" dup >fdth_string_size l@ . cr
THEN
dup >fdth_version l@ 17 >= IF
."  struct size      : 0x" dup >fdth_struct_size l@ . cr
THEN
THEN
dup >fdth_magic l@ OF_DT_HEADER <> IF
." Flat device tree has incorrect magic value !" cr
drop -1 throw EXIT
THEN
dup >fdth_version l@ 10 < IF
." Flat device tree has usupported version !" cr
drop -1 throw EXIT
THEN
drop
;
fdt-check-header
: fdt-next-tag ( addr -- nextaddr tag )
0	       	      	 	( dummy tag on stack for loop )
BEGIN
drop			( drop previous tag )
dup l@			( read new tag )
swap 4 + swap		( increment addr )
dup OF_DT_NOP <> UNTIL 	( loop until not nop )
;
: fdt-fetch-unit ( addr -- addr $name )
dup from-cstring	       \  get string size
2dup + 1 + 3 + fffffffc and -rot
;
: fdt-reg-unit ( prop-addr prop-len -- )
decode-phys               ( prop-addr' prop-len' phys.lo ... phys.hi )
set-unit                  ( prop-addr' prop-len' )
2drop
;
: fdt-fetch-string ( index -- str-addr str-len )  
fdt-strings + dup from-cstring
;
: fdt-create-dec  s" decode-unit" $CREATE , DOES> @ hex64-decode-unit ;
: fdt-create-enc  s" encode-unit" $CREATE , DOES> @ hex64-encode-unit ;
: fdt-prop-is-string?  ( addr len -- string? )
dup 1 < IF 2drop FALSE EXIT THEN                \ Check for valid length
1-
2dup + c@ 0<> IF 2drop FALSE EXIT THEN          \ Check zero-termination
test-string
;
: fdt-encode-prop  ( addr len -- )
2dup fdt-prop-is-string? IF
1- encode-string
ELSE
encode-bytes
THEN
;
: fdt-unflatten-node ( start -- end )
recursive
fdt-next-tag dup OF_DT_BEGIN_NODE <> IF
s" Weird tag 0x" type . " at start of node" type cr
-1 throw
THEN drop
new-device
fdt-fetch-unit
dup 0 = IF drop drop " /" THEN
40 left-parse-string
device-name
dup IF
" #address-cells" get-parent get-package-property IF
2drop
ELSE
decode-int nip nip
hex-decode-unit
set-unit
THEN
ELSE 2drop THEN
BEGIN
fdt-next-tag dup OF_DT_END_NODE <>
WHILE
dup OF_DT_PROP = IF
drop dup			( drop tag, dup addr     : a1 a1 )
dup l@ dup rot 4 +	( fetch size, stack is   : a1 s s a2)
dup l@ swap 4 +		( fetch nameid, stack is : a1 s s i a3 )
rot			( we now have: a1 s i a3 s )
fdt-encode-prop rot	( a1 s pa ps i)
fdt-fetch-string		( a1 s pa ps na ns )
2dup s" reg" str= IF
2swap 2dup fdt-reg-unit 2swap
THEN
property
+ 8 + 3 + fffffffc and
ELSE dup OF_DT_BEGIN_NODE = IF
drop			( drop tag )
4 -
fdt-unflatten-node
ELSE
drop -1 throw
THEN THEN
REPEAT drop \ drop tag
" #address-cells" get-node get-package-property IF ELSE
decode-int dup fdt-create-dec fdt-create-enc 2drop
THEN
finish-device  
;
: fdt-unflatten-tree
fdt-debug IF
." Unflattening device tree..." cr THEN
fdt-struct fdt-unflatten-node drop
fdt-debug IF
." Done !" cr THEN
;
fdt-unflatten-tree
: fdt-parse-memory
" /memory@0" find-device
" reg" get-node get-package-property IF throw -1 THEN
decode-phys 2drop decode-phys
my-#address-cells 1 > IF 20 << or THEN
fdt-debug IF
dup ." Memory size: " . cr
THEN
MIN-RAM-SIZE swap MIN-RAM-SIZE - release
2drop device-end
;
fdt-parse-memory
: fdt-claim-reserve
fdt-start-addr
dup dup >fdth_tsize l@ 0 claim drop
dup >fdth_rsvmap_off l@ +
BEGIN
dup dup x@ swap 8 + x@
dup 0 <>
WHILE
fdt-debug IF
2dup swap ." Reserve map entry: " . ." : " . cr
THEN
0 claim drop
10 +
REPEAT drop drop drop
;
fdt-claim-reserve 
0 VALUE (fdt-phandle-replaced)
: fdt-replace-interrupt-map  ( old new prop-addr prop-len -- old new )
BEGIN
dup                    ( old new prop-addr prop-len prop-len )
WHILE
swap dup 10 +          ( old new prop-len prop-addr prop-addr+10 )
dup l@ 5 pick = IF
3 pick swap l!
TRUE TO (fdt-phandle-replaced)
ELSE
drop
THEN
1c + swap 1c -
REPEAT
2drop
;
: fdt-replace-all-phandles ( old new node -- )
>r
s" interrupt-map" r@ get-property 0= IF
fdt-replace-interrupt-map
THEN
s" interrupt-parent" r@ get-property 0= IF
decode-int -rot 2drop                  ( old new val  R: node )
2 pick = IF                            ( old new      R: node )
dup encode-int s" interrupt-parent" r@ set-property
TRUE TO (fdt-phandle-replaced)
THEN
THEN
r>
child BEGIN
dup
WHILE
3dup RECURSE
PEER
REPEAT
3drop
;
: fdt-fix-node-phandle  ( node -- )
>r
FALSE TO (fdt-phandle-replaced)
s" phandle" r@ get-property 0= IF
decode-int                       ( p-addr2 p-len2 val )
r@ s" /" find-node               ( p-addr2 p-len2 val node root )  
fdt-replace-all-phandles         ( p-addr2 p-len2 )
2drop
(fdt-phandle-replaced) IF
r@ set-node
s" phandle" delete-property
s" linux,phandle" delete-property
ELSE
diagnostic-mode? IF
cr ." Warning: Did not replace phandle in " r@ node>path type cr
THEN
THEN
THEN
r> drop
;
: fdt-fix-phandles  ( node -- )
dup fdt-fix-node-phandle
child BEGIN
dup
WHILE
dup RECURSE
PEER
REPEAT
drop
device-end
;
: fdt-create-cas-node ( name  -- )
2dup
2dup " memory@" find-substr 0 = IF
fdt-debug IF ." Creating memory@ " cr THEN
new-device
2dup " @" find-substr nip device-name       \ Parse the node name
2dup
2dup " @" find-substr rot over + 1 + -rot - 1 - \ Jump to addr afte "@"
parse-2int nip xlsplit set-unit                 \ Parse and set unit
finish-device
ELSE
2dup " ibm,dynamic-reconfiguration-memory" find-substr 0 = IF
fdt-debug IF  ." Creating ibm,dynamic-reconfiguration-memory " cr THEN
new-device
device-name
finish-device
ELSE
2drop 2drop
false to fdt-cas-fix?
." Node not supported " cr
EXIT
THEN
THEN
find-node ?dup 0 <> IF set-node THEN
;
: fdt-fix-cas-node ( start -- end )
recursive
fdt-next-tag dup OF_DT_BEGIN_NODE <> IF
." Error " cr
false to fdt-cas-fix?
EXIT
THEN drop
fdt-fetch-unit
dup 0 = IF drop drop " /" THEN
40 left-parse-string
2swap ?dup 0 <> IF
nip
1 + + \ Add the string len +@
ELSE
drop
THEN
fdt-debug IF ." Setting node: " 2dup type cr THEN
2dup find-node ?dup 0 <> IF
set-node 2drop
ELSE
fdt-debug IF ." Node not found, creating " 2dup type cr THEN
fdt-create-cas-node
THEN
fdt-debug IF ." Current  now: " pwd cr THEN
BEGIN
fdt-next-tag dup OF_DT_END_NODE <>
WHILE
dup OF_DT_PROP = IF
fdt-debug IF ." Found property " cr THEN
drop dup		( drop tag, dup addr     : a1 a1 )
dup l@ dup rot 4 +	( fetch size, stack is   : a1 s s a2)
dup l@ swap 4 +	( fetch nameid, stack is : a1 s s i a3 )
rot			( we now have: a1 s i a3 s )
fdt-encode-prop rot	( a1 s pa ps i)
fdt-fetch-string		( a1 s pa ps na ns )
property
fdt-debug IF ." Setting property done " cr THEN
+ 8 + 3 + fffffffc and
ELSE dup OF_DT_BEGIN_NODE = IF
drop			( drop tag )
4 -
fdt-fix-cas-node
get-parent set-node
fdt-debug IF ." Returning back " pwd cr THEN
ELSE
." Error " cr
drop
false to fdt-cas-fix?
EXIT
THEN
THEN
REPEAT
drop \ drop tag
;
: fdt-fix-cas-success
fdt-cas-fix?
;
s" /" find-node fdt-fix-phandles
360 cp
defer (client-exec)
defer client-exec
defer callback
defer continue-client
0 VALUE chosen-node
: chosen
chosen-node dup 0= IF
drop s" /chosen" find-node dup to chosen-node
THEN
;
: set-chosen ( prop len name len -- )
chosen set-property ;
: get-chosen ( name len -- [ prop len ] success )
chosen get-property 0= ;
" /" find-node dup 0= IF
drop
new-device
s" /" device-name
ELSE
extend-device
THEN
" /chosen" find-node dup 0= IF
drop
new-device
s" chosen" device-name
s" " encode-string s" bootargs" property
s" " encode-string s" bootpath" property
finish-device
ELSE
drop
THEN
new-device
s" aliases" device-name
finish-device
new-device
s" options" device-name
finish-device
new-device
s" openprom" device-name
0 0 s" relative-addressing" property
finish-device
new-device 
s" packages" device-name
get-node to packages
new-device
s" deblocker" device-name
INSTANCE VARIABLE offset
INSTANCE VARIABLE block-size
INSTANCE VARIABLE max-transfer
INSTANCE VARIABLE my-block
INSTANCE VARIABLE adr
INSTANCE VARIABLE len
INSTANCE VARIABLE fail-count
: open
s" block-size" ['] $call-parent CATCH IF 2drop false EXIT THEN
block-size !
s" max-transfer" ['] $call-parent CATCH IF 2drop false EXIT THEN
max-transfer !
block-size @ alloc-mem my-block !
0 offset !
true ;
: close  my-block @ block-size @ free-mem ;
: seek ( lo hi -- status ) \ XXX: perhaps we should fail if the underlying
lxjoin offset !  0 ;
: block+remainder ( -- block# remainder )  offset @ block-size @ u/mod swap ;
: read-blocks ( addr block# #blocks -- actual )  s" read-blocks" $call-parent ;
: read ( addr len -- actual )
dup >r  len ! adr !
block+remainder dup IF ( block# offset-in-block )
>r my-block @ swap 1 read-blocks drop
my-block @ r@ + adr @ block-size @ r> - len @ min dup >r move
r> dup negate len +! dup adr +! offset +! ELSE 2drop THEN
0 fail-count !
BEGIN len @ block-size @ >= WHILE
adr @ block+remainder drop len @ max-transfer @ min block-size @ / read-blocks
dup 0= IF
1 fail-count +!
fail-count @ 5 >= IF r> drop EXIT THEN
ELSE
0 fail-count !
THEN
block-size @ * dup negate len +! dup adr +! offset +!
REPEAT
len @ IF my-block @ block+remainder drop 1 read-blocks drop
my-block @ adr @ len @ move THEN
r> ;
finish-device
new-device
false VALUE debug-disk-label?
d# 65536 value max-prep-partition-blocks
d# 4096 CONSTANT block-array-size
s" disk-label" device-name
0 INSTANCE VALUE partition
0 INSTANCE VALUE part-offset
0 INSTANCE VALUE disk-chrp-boot
0 INSTANCE VALUE part-start
0 INSTANCE VALUE lpart-start
0 INSTANCE VALUE part-size
0 INSTANCE VALUE dos-logical-partitions
0 INSTANCE VALUE block-size
0 INSTANCE VALUE block
0 INSTANCE VALUE args
0 INSTANCE VALUE args-len
0 INSTANCE VALUE gpt-part-size
0 INSTANCE VALUE seek-pos
INSTANCE VARIABLE block#  \ variable to store logical sector#
INSTANCE VARIABLE hit#    \ partition counter
INSTANCE VARIABLE success-flag
0ff constant END-OF-DESC
3 constant  PARTITION-ID
48 constant VOL-PART-LOC
STRUCT
1b8 field mbr>boot-loader
/l field mbr>disk-signature
/w field mbr>null
40 field mbr>partition-table
/w field mbr>magic
CONSTANT /mbr
STRUCT
/c field part-entry>active
/c field part-entry>start-head
/c field part-entry>start-sect
/c field part-entry>start-cyl
/c field part-entry>id
/c field part-entry>end-head
/c field part-entry>end-sect
/c field part-entry>end-cyl
/l field part-entry>sector-offset
/l field part-entry>sector-count
CONSTANT /partition-entry
STRUCT
8 field gpt>signature
4 field gpt>revision
4 field gpt>header-size
4 field gpt>header-crc32
4 field gpt>reserved
8 field gpt>current-lba
8 field gpt>backup-lba
8 field gpt>first-lba
8 field gpt>last-lba
10 field gpt>disk-guid
8 field gpt>part-entry-lba
4 field gpt>num-part-entry
4 field gpt>part-entry-size
4 field gpt>part-array-crc32
1a4 field gpt>reserved
CONSTANT /gpt-header
STRUCT
10 field gpt-part-entry>part-type-guid
10 field gpt-part-entry>part-guid
8 field gpt-part-entry>first-lba
8 field gpt-part-entry>last-lba
8 field gpt-part-entry>attribute
48 field gpt-part-entry>part-name
CONSTANT /gpt-part-entry
: offset ( d.rel -- d.abs )
part-offset xlsplit d+
;
: seek  ( pos.lo pos.hi -- status )
offset
debug-disk-label? IF 2dup ." seek-parent: pos.hi=0x" u. ." pos.lo=0x" u. THEN
s" seek" $call-parent
debug-disk-label? IF dup ." status=" . cr THEN
;
: read ( addr len -- actual )
debug-disk-label? IF 2dup swap ." read-parent: addr=0x" u. ." len=" .d THEN
s" read" $call-parent
debug-disk-label? IF dup ." actual=" .d cr THEN
;
: read-sector ( sector-number -- )
block-size * 0 seek drop      \ seek to sector
block block-size read drop    \ read sector
;
: (.part-entry) ( part-entry )
cr ." part-entry>active:        " dup part-entry>active c@ .d
cr ." part-entry>start-head:    " dup part-entry>start-head c@ .d
cr ." part-entry>start-sect:    " dup part-entry>start-sect c@ .d
cr ." part-entry>start-cyl:     " dup part-entry>start-cyl  c@ .d
cr ." part-entry>id:            " dup part-entry>id c@ .d
cr ." part-entry>end-head:      " dup part-entry>end-head c@ .d
cr ." part-entry>end-sect:      " dup part-entry>end-sect c@ .d
cr ." part-entry>end-cyl:       " dup part-entry>end-cyl c@ .d
cr ." part-entry>sector-offset: " dup part-entry>sector-offset l@-le .d
cr ." part-entry>sector-count:  " dup part-entry>sector-count l@-le .d
cr
;
: (.name) r@ begin cell - dup @ <colon> = UNTIL xt>name cr type space ;
: init-block ( -- )
s" block-size" ['] $call-parent CATCH IF ABORT" parent has no block-size." THEN
to block-size
block-array-size alloc-mem
dup block-array-size erase
to block
debug-disk-label? IF
." init-block: block-size=" block-size .d ." block=0x" block u. cr
THEN
;
: partition>part-entry ( partition -- part-entry )
1- /partition-entry * block mbr>partition-table +
;
: partition>start-sector ( partition -- sector-offset )
partition>part-entry part-entry>sector-offset l@-le
;
: no-mbr? ( -- true|false )
0 read-sector
1 partition>part-entry part-entry>id c@ ee = IF TRUE EXIT THEN \ GPT partition found
block mbr>magic w@-le aa55 <>
;
: no-gpt? ( -- true|false )
0 read-sector
1 partition>part-entry part-entry>id c@ ee <> IF true EXIT THEN
block mbr>magic w@-le aa55 <>
;
: pc-extended-partition? ( part-entry-addr -- true|false )
part-entry>id c@      ( id )
dup 5 = swap          ( true|false id )
dup f = swap          ( true|false true|false id )
85 =                  ( true|false true|false true|false )
or or                 ( true|false )
;
: count-dos-logical-partitions ( -- #logical-partitions )
no-mbr? IF 0 EXIT THEN
0 5 1 DO                                ( current )
i partition>part-entry               ( current part-entry )
dup pc-extended-partition? IF
part-entry>sector-offset l@-le    ( current sector )
dup to part-start to lpart-start  ( current )
BEGIN
part-start read-sector          \ read EBR
1 partition>start-sector IF
1+
THEN \ another logical partition
2 partition>start-sector
?dup IF lpart-start + to part-start false ELSE true THEN
UNTIL
ELSE
drop
THEN
LOOP
;
: (get-dos-partition-params) ( ext-part-start part-entry -- offset count active? id )
dup part-entry>sector-offset l@-le rot + swap ( offset part-entry )
dup part-entry>sector-count l@-le swap        ( offset count part-entry )
dup part-entry>active c@ 80 = swap            ( offset count active? part-entry )
part-entry>id c@                              ( offset count active? id )
;
: find-dos-partition ( partition# -- false | offset count active? id true )
to partition 0 to part-start 0 to part-offset
partition 0<= IF 0 to partition false EXIT THEN
no-mbr? IF 0 to partition false EXIT THEN
partition 4 <= IF \ Is this a primary partition?
0 partition partition>part-entry
(get-dos-partition-params)
true EXIT
ELSE
partition 4 - 0 5 1 DO                      ( logical-partition current )
i partition>part-entry                   ( log-part current part-entry )
dup pc-extended-partition? IF
part-entry>sector-offset l@-le        ( log-part current sector )
dup to part-start to lpart-start      ( log-part current )
BEGIN
part-start read-sector             \ read EBR
1 partition>start-sector IF        \ first partition entry
1+ 2dup = IF                    ( log-part current )
2drop
part-start 1 partition>part-entry
(get-dos-partition-params)
true UNLOOP EXIT
THEN
2 partition>start-sector
?dup IF lpart-start + to part-start false ELSE true THEN
ELSE
true
THEN
UNTIL
ELSE
drop
THEN
LOOP
2drop false
THEN
;
: try-dos-partition ( -- okay? )
no-mbr? IF
debug-disk-label? IF cr ." No DOS disk-label found." cr THEN
false EXIT
THEN
count-dos-logical-partitions TO dos-logical-partitions
debug-disk-label? IF
." Found " dos-logical-partitions .d ." logical partitions" cr
." Partition = " partition .d cr
THEN
partition 1 5 dos-logical-partitions +
within 0= IF
cr ." Partition # not 1-" 4 dos-logical-partitions + . cr false EXIT
THEN
partition find-dos-partition IF
2drop
to part-size
block-size * to part-offset
true
ELSE
false
THEN
;
: has-iso9660-filesystem  ( -- TRUE|FALSE )
10 800 * 0 seek drop      \ seek to sector
block 800 read drop       \ read sector
block c@ 1 =
block 1+ 5 s" CD001"  str=
and
dup IF 800 to block-size THEN
;
: fat-bootblock? ( addr -- flag )
dup c@ e9 = IF drop true EXIT THEN
dup c@ eb = swap 2+ c@ 90 = and
;
: load-from-dos-boot-partition ( addr -- size )
no-mbr? IF drop FALSE EXIT THEN  \ read MBR and check for DOS disk-label magic
count-dos-logical-partitions TO dos-logical-partitions
debug-disk-label? IF
." Found " dos-logical-partitions .d ." logical partitions" cr
." Partition = " partition .d cr
THEN
5 dos-logical-partitions + 1 DO
i find-dos-partition IF        ( addr offset count active? id )
41 = and                    ( addr offset count prep-boot-part? )
IF                          ( addr offset count )
max-prep-partition-blocks min  \ reduce load size
swap                     ( addr count offset )
block-size * to part-offset
0 0 seek drop            ( addr offset )
block-size * read        ( size )
UNLOOP EXIT
ELSE
2drop                    ( addr )
THEN
THEN
LOOP
drop 0
;
9E1A2D38            CONSTANT GPT-PREP-PARTITION-1
C612                CONSTANT GPT-PREP-PARTITION-2
4316                CONSTANT GPT-PREP-PARTITION-3
AA268B49521E5A8B    CONSTANT GPT-PREP-PARTITION-4
: gpt-prep-partition? ( -- true|false )
block gpt-part-entry>part-type-guid
dup l@-le     GPT-PREP-PARTITION-1 <> IF drop false EXIT THEN
dup 4 + w@-le GPT-PREP-PARTITION-2 <> IF drop false EXIT THEN
dup 6 + w@-le GPT-PREP-PARTITION-3 <> IF drop false EXIT THEN
8 + x@    GPT-PREP-PARTITION-4 =
;
EBD0A0A2            CONSTANT GPT-BASIC-DATA-PARTITION-1
B9E5                CONSTANT GPT-BASIC-DATA-PARTITION-2
4433                CONSTANT GPT-BASIC-DATA-PARTITION-3
87C068B6B72699C7    CONSTANT GPT-BASIC-DATA-PARTITION-4
: gpt-basic-data-partition? ( -- true|false )
block gpt-part-entry>part-type-guid
dup l@-le     GPT-BASIC-DATA-PARTITION-1 <> IF drop false EXIT THEN
dup 4 + w@-le GPT-BASIC-DATA-PARTITION-2 <> IF drop false EXIT THEN
dup 6 + w@-le GPT-BASIC-DATA-PARTITION-3 <> IF drop false EXIT THEN
8 + x@    GPT-BASIC-DATA-PARTITION-4 =
;
4546492050415254 CONSTANT GPT-SIGNATURE
: get-gpt-partition ( -- true|false )
no-gpt? IF false EXIT THEN
debug-disk-label? IF cr ." GPT partition found " cr  THEN
1 read-sector
block gpt>part-entry-lba x@-le
block-size * to seek-pos
block gpt>part-entry-size l@-le to gpt-part-size
gpt-part-size block-array-size > IF
cr ." GPT part size exceeds buffer allocated " cr
false exit
THEN
block gpt>signature x@ GPT-SIGNATURE =
;
: load-from-gpt-prep-partition ( addr -- size )
get-gpt-partition 0= IF false EXIT THEN
block gpt>num-part-entry l@-le dup 0= IF false exit THEN
1+ 1 ?DO
seek-pos 0 seek drop
block gpt-part-size read drop gpt-prep-partition? IF
debug-disk-label? IF  ." GPT PReP partition found " cr THEN
block gpt-part-entry>first-lba x@-le ( addr first-lba )
block gpt-part-entry>last-lba x@-le  ( addr first-lba last-lba)
over - 1+                            ( addr first-lba blocks )
swap                                 ( addr blocks first-lba )
block-size * to part-offset          ( addr blocks )
0 0 seek drop                        ( addr blocks )
block-size * read                    ( size )
UNLOOP EXIT
THEN
seek-pos gpt-part-size + to seek-pos
LOOP
false
;
: try-gpt-dos-partition ( -- true|false )
get-gpt-partition 0= IF false EXIT THEN
block gpt>num-part-entry l@-le dup 0= IF false EXIT THEN
1+ 1 ?DO
seek-pos 0 seek drop
block gpt-part-size read drop
gpt-basic-data-partition? IF
debug-disk-label? IF ." GPT BASIC DATA partition found " cr THEN
block gpt-part-entry>first-lba x@-le       ( first-lba )
dup to part-start                          ( first-lba )
block gpt-part-entry>last-lba x@-le        ( first-lba last-lba )
over - 1+                                  ( first-lba s1 )
block-size * to part-size                  ( first-lba )
block-size * to part-offset                ( )
0 0 seek drop
block block-size read drop
block fat-bootblock?                    ( true|false )
UNLOOP EXIT
THEN
seek-pos gpt-part-size + to seek-pos
LOOP
false
;
: parse-bootinfo-txt  ( addr len -- str len )
2dup s" <boot-script>" find-substr       ( addr len pos1 )
2dup = IF
3drop 0 0 EXIT
THEN
dup >r - swap r> + swap                  ( addr1 len1 )
2dup s" &device;:" find-substr           ( addr1 len1 posdev )
2dup = IF
3drop 0 0 EXIT
THEN
9 +                                      \ Skip the "&device;:" string
dup >r - swap r> + swap                  ( addr2 len2 )
2dup s" </boot-script>" find-substr nip  ( addr2 len3 )
debug-disk-label? IF
." Extracted boot loader from bootinfo.txt: '"
2dup type ." '" cr
THEN
;
: load-chrp-boot-file ( addr -- size )
my-parent instance>path
disk-chrp-boot @ 1 = IF
s" :1,\ppc\bootinfo.txt" $cat strdup       ( addr str len )
ELSE
s" :\ppc\bootinfo.txt" $cat strdup       ( addr str len )
THEN
open-dev dup 0= IF 2drop 0 EXIT THEN
>r dup                                   ( addr addr R:ihandle )
dup s" load" r@ $call-method             ( addr addr size R:ihandle )
r> close-dev                             ( addr addr size )
parse-bootinfo-txt                       ( addr fnstr fnlen )
dup 0= IF 3drop 0 EXIT THEN
2dup 20 findchar IF
>r 2dup r@ - 1- swap r@ + 1+ swap     ( addr fnstr fnlen pstr plen  R: offset )
encode-string s" bootargs" set-chosen
drop r>
THEN
my-parent instance>path      ( addr fnstr fnlen nstr nlen )
s" :" $cat 2swap $cat strdup             ( addr str len )
2dup encode-string s" bootpath" set-chosen
open-dev dup 0= IF ." failed to load CHRP boot loader." 2drop 0 EXIT THEN
>r s" load" r@ $call-method              ( size R:ihandle )
r> close-dev                             ( size )
;
: load-from-boot-partition ( addr -- size )
debug-disk-label? IF ." Trying DOS boot " .s cr THEN
dup load-from-dos-boot-partition ?dup 0 <> IF nip EXIT THEN
debug-disk-label? IF ." Trying CHRP boot " .s cr THEN
1 disk-chrp-boot !
dup load-chrp-boot-file ?dup 0 <> IF nip EXIT THEN
0 disk-chrp-boot !
debug-disk-label? IF ." Trying GPT boot " .s cr THEN
load-from-gpt-prep-partition
;
: parse-partition ( -- okay? )
0 to partition
0 to part-offset
0 to part-size
my-args to args-len to args
debug-disk-label? IF
cr ." disk-label parse-partition: my-args=" my-args type cr
THEN
args-len 0 = IF true EXIT THEN
my-args [char] , findchar 0= IF \ no comma?
args c@ isdigit not IF       \ ... and not a partition number?
true EXIT                 \ ... then it's not a partition we can parse
THEN
ELSE
drop
THEN
my-args [char] , split to args-len to args
dup 0= IF 2drop true EXIT THEN \ no first argument
base @ >r decimal $number r> base !
IF cr ." Not a partition #" false EXIT THEN
to partition
true
;
: (interpose-filesystem) ( str len -- )
find-package IF args args-len rot interpose THEN
;
: try-dos-files ( -- found? )
no-mbr? IF false EXIT THEN
block fat-bootblock? 0= IF false EXIT THEN
s" fat-files" (interpose-filesystem)
true
;
: try-ext2-files ( -- found? )
2 read-sector               \ read first superblock
block d# 56 + w@-le         \ fetch s_magic
ef53 <> IF false EXIT THEN  \ s_magic found?
s" ext2-files" (interpose-filesystem)
true
;
: try-iso9660-files
has-iso9660-filesystem 0= IF false exit THEN
s" iso-9660" (interpose-filesystem)
true
;
: try-files ( -- found? )
args-len 0= IF true EXIT THEN
try-dos-files IF true EXIT THEN
try-ext2-files IF true EXIT THEN
try-iso9660-files IF true EXIT THEN
false
;
: try-partitions ( -- found? )
try-dos-partition IF try-files EXIT THEN
try-gpt-dos-partition IF try-files EXIT THEN
false
;
: close ( -- )
debug-disk-label? IF ." Closing disk-label: block=0x" block u. ." block-size=" block-size .d cr THEN
block block-array-size free-mem
;
: open ( -- true|false )
init-block
parse-partition 0= IF
close
false EXIT
THEN
partition IF
try-partitions
ELSE
try-files
THEN
dup 0= IF debug-disk-label? IF ." not found." cr THEN close THEN \ free memory again
;
: load ( addr -- size )
debug-disk-label? IF
." load: " dup u. cr
THEN
args-len IF
TRUE ABORT" Load done w/o filesystem"
ELSE
partition IF
0 0 seek drop
part-size IF
part-size max-prep-partition-blocks min   \ Load size
ELSE
max-prep-partition-blocks
THEN
200 *  read
ELSE
has-iso9660-filesystem IF
dup load-chrp-boot-file ?dup 0 > IF nip EXIT THEN
THEN
load-from-boot-partition
dup 0= ABORT" No boot partition found"
THEN
THEN
;
finish-device
new-device
s" fat-files" device-name
INSTANCE VARIABLE bytes/sector
INSTANCE VARIABLE sectors/cluster
INSTANCE VARIABLE #reserved-sectors
INSTANCE VARIABLE #fats
INSTANCE VARIABLE #root-entries
INSTANCE VARIABLE fat32-root-cluster
INSTANCE VARIABLE total-#sectors
INSTANCE VARIABLE media-descriptor
INSTANCE VARIABLE sectors/fat
INSTANCE VARIABLE sectors/track
INSTANCE VARIABLE #heads
INSTANCE VARIABLE #hidden-sectors
INSTANCE VARIABLE fat-type
INSTANCE VARIABLE bytes/cluster
INSTANCE VARIABLE fat-offset
INSTANCE VARIABLE root-offset
INSTANCE VARIABLE cluster-offset
INSTANCE VARIABLE #clusters
: seek  s" seek" $call-parent ;
: read  s" read" $call-parent ;
INSTANCE VARIABLE data
INSTANCE VARIABLE #data
: free-data
data @ ?dup IF #data @ free-mem  0 data ! THEN ;
: read-data ( offset size -- )
free-data  dup #data ! alloc-mem data !
xlsplit seek            -2 and ABORT" fat-files read-data: seek failed"
data @ #data @ read #data @ <> ABORT" fat-files read-data: read failed" ;
CREATE fat-buf 8 allot
: read-fat ( cluster# -- data )
fat-buf 8 erase
1 #split fat-type @ * 2/ 2/ fat-offset @ +
xlsplit seek -2 and ABORT" fat-files read-fat: seek failed"
fat-buf 8 read 8 <> ABORT" fat-files read-fat: read failed"
fat-buf 8c@ bxjoin fat-type @ dup >r 2* #split drop r> #split
rot IF swap THEN drop ;
INSTANCE VARIABLE next-cluster
: read-cluster ( cluster# -- )
dup bytes/cluster @ * cluster-offset @ + bytes/cluster @ read-data
read-fat dup #clusters @ >= IF drop 0 THEN next-cluster ! ;
: read-dir ( cluster# -- )
?dup 0= IF
#root-entries @ 0= IF
fat32-root-cluster @ read-cluster
ELSE
root-offset @ #root-entries @ 20 * read-data 0 next-cluster !
THEN
ELSE
read-cluster
THEN
;
: get-cluster ( direntry -- cluster# )
fat-type @ 20 = IF
dup 14 + 2c@ bwjoin 10 lshift
ELSE 0 THEN
swap 1a + 2c@ bwjoin +
;
: .time ( x -- )
base @ >r decimal
b #split 2 0.r [char] : emit  5 #split 2 0.r [char] : emit  2* 2 0.r
r> base ! ;
: .date ( x -- )
base @ >r decimal
9 #split 7bc + 4 0.r [char] - emit  5 #split 2 0.r [char] - emit  2 0.r
r> base ! ;
: .attr ( attr -- )
6 0 DO dup 1 and IF s" RHSLDA" drop i + c@ ELSE bl THEN emit u2/ LOOP drop ;
: .dir-entry ( adr -- )
dup 0b + c@ 8 and IF drop EXIT THEN \ volume label, not a file
dup c@ e5 = IF drop EXIT THEN \ deleted file
cr
dup get-cluster [char] # emit 8 0.r space \ starting cluster
dup 18 + 2c@ bwjoin .date space
dup 16 + 2c@ bwjoin .time space
dup 1c + 4c@ bljoin base @ decimal swap a .r base ! space \ size in bytes
dup 0b + c@ .attr space
dup 8 BEGIN 2dup 1- + c@ 20 = over and WHILE 1- REPEAT type
dup 8 + 3 BEGIN 2dup 1- + c@ 20 = over and WHILE 1- REPEAT dup IF
[char] . emit type ELSE 2drop THEN
drop ;
: .dir-entries ( adr n -- )
0 ?DO dup i 20 * + dup c@ 0= IF drop LEAVE THEN .dir-entry LOOP drop ;
: .dir ( cluster# -- )
read-dir BEGIN data @ #data @ 20 / .dir-entries next-cluster @ WHILE
next-cluster @ read-cluster REPEAT ;
: str-upper ( str len adr -- ) \ Copy string to adr, uppercase
-rot bounds ?DO i c@ upc over c! char+ LOOP drop ;
CREATE dos-name b allot
: make-dos-name ( str len -- )
dos-name b bl fill
2dup [char] . findchar IF
3dup 1+ /string 3 min dos-name 8 + str-upper nip THEN
8 min dos-name str-upper ;
: (find-file) ( -- cluster file-len is-dir? true | false )
data @ BEGIN dup data @ #data @ + < WHILE
dup dos-name b comp WHILE 20 + REPEAT
dup get-cluster
swap dup 1c + 4c@ bljoin swap 0b + c@ 10 and 0<> true
ELSE drop false THEN ;
: find-file ( dir-cluster name len -- cluster file-len is-dir? true | false )
make-dos-name read-dir BEGIN (find-file) 0= WHILE next-cluster @ WHILE
next-cluster @ read-cluster REPEAT false ELSE true THEN ;
: find-path ( dir-cluster name len -- cluster file-len true | false )
dup 0= IF 3drop false ."  empty name " EXIT THEN
over c@ [char] \ = IF 1 /string  RECURSE EXIT THEN
[char] \ split 2>r find-file 0= IF 2r> 2drop false ."  not found " EXIT THEN
r@ 0<> <> IF 2drop 2r> 2drop false ."  no dir<->file match " EXIT THEN
r@ 0<> IF drop 2r> RECURSE EXIT THEN
2r> 2drop true ;
: do-super ( -- )
0 200 read-data
data @ 0b + 2c@ bwjoin bytes/sector !
data @ 0d + c@ sectors/cluster !
bytes/sector @ sectors/cluster @ * bytes/cluster !
data @ 0e + 2c@ bwjoin #reserved-sectors !
data @ 10 + c@ #fats !
data @ 11 + 2c@ bwjoin #root-entries !
data @ 13 + 2c@ bwjoin total-#sectors !
data @ 15 + c@ media-descriptor !
data @ 16 + 2c@ bwjoin sectors/fat !
data @ 18 + 2c@ bwjoin sectors/track !
data @ 1a + 2c@ bwjoin #heads !
data @ 1c + 2c@ bwjoin #hidden-sectors !
total-#sectors @ 0= IF data @ 20 + 4c@ bljoin total-#sectors ! THEN
sectors/fat @ 0= IF data @ 24 + 4c@ bljoin sectors/fat ! THEN
#root-entries @ 0= IF data @ 2c + 4c@ bljoin ELSE 0 THEN fat32-root-cluster !
total-#sectors @ #reserved-sectors @ - sectors/fat @ #fats @ * -
#root-entries @ 20 * bytes/sector @ // - sectors/cluster @ /
dup #clusters !
dup ff5 < IF drop c ELSE fff5 < IF 10 ELSE 20 THEN THEN fat-type !
base @ decimal base !
#reserved-sectors @ bytes/sector @ * fat-offset !
#fats @ sectors/fat @ * bytes/sector @ * fat-offset @ + root-offset !
#root-entries @ 20 * bytes/sector @ tuck // * root-offset @ +
bytes/cluster @ 2* - cluster-offset ! ;
INSTANCE VARIABLE file-cluster
INSTANCE VARIABLE file-len
INSTANCE VARIABLE current-pos
INSTANCE VARIABLE pos-in-data
: seek ( lo hi -- status )
lxjoin dup current-pos ! file-cluster @ read-cluster
BEGIN dup #data @ >= WHILE #data @ - next-cluster @ dup 0= IF
2drop true EXIT THEN read-cluster REPEAT pos-in-data ! false ;
: read ( adr len -- actual )
file-len @ current-pos @ - min \ can't go past end of file
#data @ pos-in-data @ - min >r \ length for this transfer
data @ pos-in-data @ + swap r@ move \ move the data
r@ pos-in-data +!  r@ current-pos +!  pos-in-data @ #data @ = IF
next-cluster @ ?dup IF read-cluster 0 pos-in-data ! THEN THEN r> ;
: read ( adr len -- actual )
file-len @ min                \ len cannot be greater than file size
dup >r BEGIN dup WHILE 2dup read dup 0= ABORT" fat-files: read failed"
/string ( tuck - >r + r> ) REPEAT 2drop r> ;
: load ( adr -- len )
file-len @ read dup file-len @ <> ABORT" fat-files: failed loading file" ;
: close  free-data ;
: open
do-super
0 my-args find-path 0= IF close false EXIT THEN
file-len !  file-cluster !  0 0 seek 0= ;
finish-device
new-device
s" rom-files" device-name
INSTANCE VARIABLE length
INSTANCE VARIABLE next-file
INSTANCE VARIABLE buffer
INSTANCE VARIABLE buffer-size
INSTANCE VARIABLE file
INSTANCE VARIABLE file-size
INSTANCE VARIABLE found
: open  true 
100 dup buffer-size ! alloc-mem buffer ! false found ! ;
: close buffer @ buffer-size @ free-mem ;
: read ( addr len -- actual ) s" read" $call-parent ;
: seek ( lo hi -- status ) s" seek" $call-parent ;
: .read-file-name ( offset -- str len )
0 seek drop 
buffer @ buffer-size @ read drop
buffer-size @ 1 - buffer @ + 0 swap c!
buffer @ zcount ;
: .print-info ( offset -- )
dup 2 spaces 6 0.r 2 spaces dup
8 + 0 seek drop length 8 read drop
6 length @ swap 0.r 2 spaces
20 + .read-file-name type cr ;
: .list-header cr
s" --offset---size-----file-name----" type cr ;
: list
.list-header
0 0 BEGIN + dup 
.print-info dup 0 seek drop
next-file 8 read drop next-file @
dup 0= UNTIL 2drop ;
: (find-file)  ( name len -- offset | -1 )
0 0 seek drop false found !
file-size ! file ! 0 0 BEGIN + dup
20 + .read-file-name file @ file-size @
str= IF true found ! THEN
dup 0 seek drop
next-file 8 read drop next-file @
dup 0= found @ or UNTIL drop found @ 0=
IF drop -1 THEN ;
: load  ( addr -- size )
my-parent instance>args 2@ [char] \ left-parse-string 2drop
(find-file) dup -1 = IF 2drop 0 ELSE
0 0 seek drop
dup 8 + 0 seek drop
here 8 read drop here @  ( dest-addr offset file-size )
over 18 + 0 seek drop
here 8 read drop here @  ( dest-addr offset file-size data-offset )
rot + 0 seek drop  ( dest-addr file-size )
read 
THEN
;
finish-device
new-device
s" ext2-files" device-name
INSTANCE VARIABLE first-block
INSTANCE VARIABLE inode-size
INSTANCE VARIABLE block-size
INSTANCE VARIABLE inodes/group
INSTANCE VARIABLE group-desc-size
INSTANCE VARIABLE group-descriptors
: seek  s" seek" $call-parent ;
: read  s" read" $call-parent ;
INSTANCE VARIABLE data
INSTANCE VARIABLE #data
INSTANCE VARIABLE indirect-block
INSTANCE VARIABLE dindirect-block
: free-data
data @ ?dup IF #data @ free-mem  0 data ! THEN ;
: read-data ( offset size -- )
free-data  dup #data ! alloc-mem data !
xlsplit seek            -2 and ABORT" ext2-files read-data: seek failed"
data @ #data @ read #data @ <> ABORT" ext2-files read-data: read failed" ;
: read-block ( block# -- )
block-size @ * block-size @ read-data ;
INSTANCE VARIABLE inode
INSTANCE VARIABLE file-len
INSTANCE VARIABLE blocks
INSTANCE VARIABLE #blocks
INSTANCE VARIABLE ^blocks
INSTANCE VARIABLE #blocks-left
: blocks-read ( n -- )  dup negate #blocks-left +! 4 * ^blocks +! ;
: read-indirect-blocks ( indirect-block# -- )
read-block data @ data off
dup #blocks-left @ 4 * block-size @ min dup >r ^blocks @ swap move
r> 2 rshift blocks-read block-size @ free-mem ;
: read-double-indirect-blocks ( double-indirect-block# -- )
read-block data @ indirect-block ! data off
BEGIN
indirect-block @ l@-le dup 0 <>
WHILE
read-indirect-blocks
4 indirect-block +!       \ point to next indirect block
REPEAT
drop                         \ drop 0, the invalid block number
;
: read-triple-indirect-blocks ( triple-indirect-block# -- )
read-block data @ dindirect-block ! data off
BEGIN
dindirect-block @ l@-le dup 0 <>
WHILE
read-double-indirect-blocks
4 dindirect-block +!      \ point to next double indirect block
REPEAT
drop                         \ drop 0, the invalid block number
;
: read-block#s ( -- )
blocks @ ?dup IF #blocks @ 4 * free-mem THEN
inode @ 4 + l@-le file-len !
file-len @ block-size @ // #blocks !
#blocks @ 4 * alloc-mem blocks !
blocks @ ^blocks !  #blocks @ #blocks-left !
#blocks-left @ c min \ # direct blocks
inode @ 28 + over 4 * ^blocks @ swap move blocks-read
#blocks-left @ IF inode @ 58 + l@-le read-indirect-blocks THEN
#blocks-left @ IF inode @ 5c + l@-le read-double-indirect-blocks THEN
#blocks-left @ IF inode @ 60 + l@-le read-triple-indirect-blocks THEN ;
: read-inode ( inode# -- )
1- inodes/group @ u/mod \ # in group, group #
20 * group-descriptors @ + 8 + l@-le block-size @ * \ # in group, inode table
swap inode-size @ * + xlsplit seek drop  inode @ inode-size @ read drop
;
: .rwx ( bits last-char-if-special special? -- )
rot dup 4 and IF ." r" ELSE ." -" THEN
dup 2 and IF ." w" ELSE ." -" THEN
swap IF 1 and 0= IF upc THEN emit ELSE
1 and IF ." x" ELSE ." -" THEN drop THEN ;
CREATE mode-chars 10 allot s" ?pc?d?b?-?l?s???" mode-chars swap move
: .mode ( mode -- )
dup c rshift f and mode-chars + c@ emit
dup 6 rshift 7 and over 800 and 73 swap .rwx
dup 3 rshift 7 and over 400 and 73 swap .rwx
dup          7 and swap 200 and 74 swap .rwx ;
: .inode ( -- )
base @ >r decimal
inode @      w@-le .mode \ file mode
inode @ 1a + w@-le 5 .r \ link count
inode @ 02 + w@-le 9 .r \ uid
inode @ 18 + w@-le 9 .r \ gid
inode @ 04 + l@-le 9 .r \ size
r> base ! ;
: do-super ( -- )
400 400 read-data
data @ 14 + l@-le first-block !
400 data @ 18 + l@-le lshift block-size !
data @ 28 + l@-le inodes/group !
data @ 4c + l@-le 0= IF
80 inode-size !
ELSE
data @ 58 + w@-le inode-size !
THEN
data @ 20 + l@-le group-desc-size !
first-block @ 1+ block-size @ *
group-desc-size @
read-data
data @ group-descriptors !
data off
;
INSTANCE VARIABLE current-pos
: read ( adr len -- actual )
file-len @ current-pos @ - min \ can't go past end of file
current-pos @ block-size @ u/mod 4 * blocks @ + l@-le read-block
block-size @ over - rot min >r ( adr off r: len )
data @ + swap r@ move r> dup current-pos +! ;
: read ( adr len -- actual )
dup >r BEGIN dup WHILE 2dup read dup 0= ABORT" ext2-files: read failed"
/string REPEAT 2drop r> ;
: seek ( lo hi -- status )
lxjoin dup file-len @ > IF drop true EXIT THEN current-pos ! false ;
: load ( adr -- len )
file-len @ read dup file-len @ <> ABORT" ext2-files: failed loading file" ;
: .name ( adr -- )  dup 8 + swap 6 + c@ type ;
: read-dir ( inode# -- adr )
read-inode read-block#s file-len @ alloc-mem
0 0 seek ABORT" ext2-files read-dir: seek failed"
dup file-len @ read file-len @ <> ABORT" ext2-files read-dir: read failed" ;
: .dir ( inode# -- )
read-dir dup BEGIN 2dup file-len @ - > over l@-le tuck and WHILE
cr dup 8 0.r space read-inode .inode space space dup .name
dup 4 + w@-le + REPEAT 2drop file-len @ free-mem ;
: (find-file) ( adr name len -- inode#|0 )
2>r dup BEGIN 2dup file-len @ - > over l@-le and WHILE
dup 8 + over 6 + c@ 2r@ str= IF 2r> 2drop nip l@-le EXIT THEN
dup 4 + w@-le + REPEAT 2drop 2r> 2drop 0 ;
: find-file ( inode# name len -- inode#|0 )
2>r read-dir dup 2r> (find-file) swap file-len @ free-mem ;
: find-path ( inode# name len -- inode#|0 )
dup 0= IF 3drop 0 ."  empty name " EXIT THEN
over c@ [char] \ = IF 1 /string ."  slash " RECURSE EXIT THEN
[char] \ split 2>r find-file ?dup 0= IF
2r> 2drop false ."  not found " EXIT THEN
r@ 0<> IF 2r> ."  more... " RECURSE EXIT THEN
2r> 2drop ."  got it " ;
: close
inode @ inode-size @ free-mem
group-descriptors @ group-desc-size @ free-mem
free-data
blocks @ ?dup IF #blocks @ 4 * free-mem THEN
;
: open
0 data ! 0 blocks ! 0 #blocks !
do-super
inode-size @ alloc-mem inode !
my-args nip 0= IF 0 0 ELSE
2 my-args find-path ?dup 0= IF close false EXIT THEN THEN
read-inode read-block#s 0 0 seek 0= ;
finish-device
new-device
s" obp-tftp" device-name
VARIABLE huge-tftp-load 1 huge-tftp-load !
: open ( -- okay? ) 
true
;
: load ( addr -- size )
s" bootargs" get-chosen 0= IF 0 0 THEN >r >r
s" bootpath" get-chosen 0= IF 0 0 THEN >r >r
my-parent ihandle>phandle node>path encode-string
s" bootpath" set-chosen
60000000                        ( addr maxlen )
6B8 alloc-mem dup >r            ( addr maxlen replybuf )
huge-tftp-load @  d# 1428       ( addr maxlen replybuf hugetftp blocksize )
my-args
net-load dup 0< IF drop 0 THEN
r>
r> r> over IF s" bootpath" set-chosen ELSE 2drop THEN
r> r> over IF s" bootargs" set-chosen ELSE 2drop THEN
dup 6B8 encode-bytes s" bootp-response" s" /chosen" find-node set-property
6B8 free-mem
;
: close ( -- )
;
: ping  ( -- )
my-args net-ping
;
finish-device
new-device
s" iso-9660" device-name
0 VALUE iso-debug-flag
: iso-debug-print ( str len -- )  iso-debug-flag IF type cr ELSE 2drop THEN  ;
0 VALUE  path-tbl-size
0 VALUE  path-tbl-addr
0 VALUE  root-dir-size
0 VALUE  vol-size
0 VALUE  logical-blk-size
0 VALUE  path-table
0 VALUE  count
INSTANCE VARIABLE dir-addr
INSTANCE VARIABLE data-buff
INSTANCE VARIABLE #data
INSTANCE VARIABLE ptable
INSTANCE VARIABLE file-loc
INSTANCE VARIABLE file-size
INSTANCE VARIABLE cur-file-offset
INSTANCE VARIABLE self
INSTANCE VARIABLE index
: seek  ( pos.lo pos.hi -- status )  s" seek" $call-parent  ;
: read  ( addr len -- actual )  s" read" $call-parent  ;
: free-data ( -- )
data-buff @                              ( data-buff )
?DUP  IF  #data @  free-mem  0 data-buff ! 0 #data ! THEN
;
: read-data ( offset size -- )
dup #data @ > IF
free-data dup dup                  ( offset size size size )
#data ! alloc-mem data-buff !      ( offset size )
THEN
swap xlsplit                          ( size pos.lo pos.hi )
seek   -2 and ABORT" seek failed."
data-buff @ over read                 ( size actual )
<> ABORT" read failed."
;
: extract-vol-info  (  --  )
10  800 * 800 read-data
data-buff @  88  + l@-be  to path-tbl-size   \ read path table size
data-buff @  94  + l@-be  to path-tbl-addr   \ read big-endian  path table
data-buff @  a2  + l@-be   dir-addr !        \ gather of root directory info
data-buff @  0aa + l@-be  to root-dir-size   \ get volume info
data-buff @  54  + l@-be  to vol-size        \ size in blocks
data-buff @  82  + l@-be  to logical-blk-size
path-tbl-size alloc-mem dup  TO path-table path-tbl-size erase
path-tbl-addr 800 *  xlsplit seek  drop
path-table  path-tbl-size  read  drop     \ pathtable in-system-memory copy
;
: file-name  ( str len --  str' len' )
2dup  [char] ; findchar  IF
nip                 \ Omit the trailing ";1" revision of ISO9660 file name
2dup + 1-           ( str newlen endptr )
c@ [CHAR] . = IF
1-               ( str len' )    \ Remove trailing dot
THEN
THEN
;
: dup3  ( num  -- num num num ) dup dup dup  ;
: get-next-record  ( rec-addr -- next-rec-offset )
dup3               ( rec-addr rec-addr rec-addr rec-addr )
self @ 1 +  self ! ( rec-addr rec-addr rec-addr rec-addr )
c@  1 AND  IF      ( rec-addr rec-addr rec-addr )
c@ +  9         ( rec-addr rec-addr' rec-len )
ELSE
c@ +  8         ( rec-addr rec-addr' rec-len )
THEN
+ swap  -          ( next-rec-offset )
;
: path-table-search ( str len -- TRUE | FALSE )
path-table path-tbl-size +  path-table ptable @ +  DO ( str len )
2dup  I 6 + w@-be index @ =                        ( str len str len )
-rot  I 8 +  I c@
iso-debug-flag IF
." ISO: comparing path name '"
4dup type ." ' with '" type ." '" cr
THEN
string=ci and  IF                                  ( str len )
s" Directory Matched!!  "   iso-debug-print     ( str len )
self @   index !                                ( str len )
I 2 + l@-be   dir-addr ! I  dup                 ( str len rec-addr )
get-next-record + path-table -   ptable !       ( str len )
2drop  TRUE UNLOOP EXIT                         ( TRUE )
THEN
I get-next-record                           ( str len next-rec-offset )
+LOOP
2drop
FALSE                                          ( FALSE )
s" Invalid path / directory "  iso-debug-print
;
: search-file-dir ( str len  -- TRUE | FALSE )
dir-addr @  800 *  dir-addr !             ( str len )
dir-addr @ 100 read-data                  ( str len )
data-buff @  0e + l@-be  dup >r           ( str len rec-len )
100 >  IF                                 ( str len )
s" size dir record"  iso-debug-print   ( str len )
dir-addr @ r@  read-data               ( str len )
THEN
r> data-buff @  + data-buff @  DO         ( str len )
I 19 + c@  2 and 0=  I c@ 0<> and IF   ( str len )
2dup                                ( str len  str len )
I 21 + I 20 + c@                    ( str len  str len  str' len' )
iso-debug-flag IF
." ISO: comparing file name '"
4dup type ." ' with '" type ." '" cr
THEN
file-name  string=ci  IF            ( str len )
s" File found!"  iso-debug-print ( str len )
I 6 + l@-be 800 *                ( str len file-loc )
file-loc !                       ( str len )
I 0e + l@-be  file-size !        ( str len )
2drop
TRUE                             ( TRUE )
UNLOOP
EXIT
THEN
THEN
I c@ ?dup 0= IF
800 I 7ff AND -
iso-debug-flag IF
." skipping " dup . ." bytes at end of sector" cr
THEN
THEN
+LOOP
2drop
FALSE                                     ( FALSE )
s" file not found"   iso-debug-print
;
: search-path ( str len -- FALSE|TRUE )
0  ptable !
1  self !
1  index !
dup                                             ( str len len )
0=  IF
3drop FALSE                                  ( FALSE )
s"  Empty path name "  iso-debug-print  EXIT ( FALSE )
THEN
OVER c@                                         ( str len char )
[char] \ =  IF                                  ( str len )
swap 1 + swap 1 -  BEGIN                     ( str len )
[char] \  split                           ( str len  str' len ' )
dup 0 =   IF                              ( str len  str' len ' )
2drop search-file-dir EXIT             ( TRUE | FALSE )
ELSE
2swap path-table-search  invert  IF    ( str' len ' )
2drop FALSE  EXIT                   ( FALSE )
THEN
THEN
AGAIN
ELSE   BEGIN
[char] \  split   dup 0 =   IF               ( str len str' len' )
2drop search-file-dir EXIT                ( TRUE | FALSE )
ELSE
2swap path-table-search  invert  IF       ( str' len ' )
2drop FALSE  EXIT                      ( FALSE )
THEN
THEN
AGAIN
THEN
;
0 VALUE loc
: load ( addr -- len )
dup to loc                     ( addr )
file-loc @  xlsplit seek drop
file-size @  read              ( file-size )
iso-debug-flag IF s" Bytes returned from read:" type dup . cr THEN
dup file-size @  <> ABORT" read failed!"
;
: close ( -- )
free-data   count 1 - dup to count  0 =  IF
path-table path-tbl-size free-mem
0 TO path-table
THEN
;
: open ( -- TRUE | FALSE )
0 data-buff !
0 #data !
0 ptable !
0 file-loc !
0 file-size !
0 cur-file-offset !
1 self !
1 index !
count 0 =  IF
s" extract-vol-info called "   iso-debug-print
extract-vol-info
THEN
count  1 + to count
my-args search-path  IF
file-loc @  xlsplit seek drop
TRUE    ( TRUE )
ELSE
close
FALSE   ( FALSE )
THEN
0 cur-file-offset !
s" opened ISO9660 package" iso-debug-print
;
: seek ( pos.lo pos.hi -- status )
lxjoin dup  cur-file-offset !  ( offset )
file-loc @  + xlsplit          ( pos.lo pos.hi )
s" seek" $call-parent          ( status )
;
: read ( addr len -- actual )
file-size @ cur-file-offset @ -             ( addr len remainder-of-file )
min                                         ( addr len|remainder-of-file )
s" read" $call-parent                       ( actual )
dup cur-file-offset @ +  cur-file-offset !  ( actual )
cur-file-offset @                           ( offset actual )
xlsplit seek drop                           ( actual )
;
finish-device
finish-device
: open true ;
: close ;
finish-device
370 cp
: check-boot-menu
s" qemu,boot-menu" get-chosen IF
decode-int 1 = IF
." Press F12 for boot menu." cr cr
THEN
2drop
THEN
;
check-boot-menu
380 cp
371 cp
STRUCT
/l field rtas>token
/l field rtas>nargs
/l field rtas>nret
/l field rtas>args0
/l field rtas>args1
/l field rtas>args2
/l field rtas>args3
/l field rtas>args4
/l field rtas>args5
/l field rtas>args6
/l field rtas>args7
/l C * field rtas>args
/l field rtas>bla
CONSTANT /rtas-control-block
CREATE rtas-cb /rtas-control-block allot
rtas-cb /rtas-control-block erase
0 VALUE rtas-base
0 VALUE rtas-size
0 VALUE rtas-entry
0 VALUE rtas-node
372 cp
: find-qemu-rtas ( -- )
" /rtas" find-device get-node to rtas-node
" linux,rtas-base" rtas-node get-package-property IF
device-end EXIT THEN
drop l@ to rtas-base
" linux,rtas-base" delete-property
" rtas-size" rtas-node get-package-property IF
device-end EXIT THEN
drop l@ to rtas-size
" linux,rtas-entry" rtas-node get-package-property IF
rtas-base to rtas-entry
ELSE
drop l@ to rtas-entry
" linux,rtas-entry" delete-property
THEN
0
rtas-base
dup rtas-size +
check-and-patch-sc1
device-end
;
find-qemu-rtas
373 cp
: enter-rtas ( -- )
rtas-cb rtas-base 0 rtas-entry call-c drop
;
: rtas-get-token ( str len -- token | 0 )
rtas-node get-package-property IF 0 ELSE drop l@ THEN
;
: rtas-power-off   ( x y -- status )
[ s" power-off" rtas-get-token ] LITERAL rtas-cb rtas>token l!
2 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
rtas-cb rtas>args0 l!
rtas-cb rtas>args1 l!
enter-rtas
rtas-cb rtas>args2 l@
;
: power-off  ( -- )  0 0 rtas-power-off ;
: rtas-system-reboot  ( -- status )
[ s" system-reboot" rtas-get-token ] LITERAL rtas-cb rtas>token l!
0 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
rtas-cb rtas>args0 l!
enter-rtas
rtas-cb rtas>args1 l@
;
: rtas-start-cpu  ( pid loc r3 -- status )
[ s" start-cpu" rtas-get-token ] LITERAL rtas-cb rtas>token l!
3  rtas-cb rtas>nargs l!
1  rtas-cb rtas>nret l!
rtas-cb rtas>args2 l!
rtas-cb rtas>args1 l!
rtas-cb rtas>args0 l!
0 rtas-cb rtas>args3 l!
enter-rtas
rtas-cb rtas>args3 l@
;
: rtas-set-tce-bypass ( unit enable -- )
" ibm,set-tce-bypass" rtas-get-token rtas-cb rtas>token l!
2 rtas-cb rtas>nargs l!
0 rtas-cb rtas>nret l!
rtas-cb rtas>args1 l!
rtas-cb rtas>args0 l!
enter-rtas
;
: rtas-quiesce ( -- )
" quiesce" rtas-get-token rtas-cb rtas>token l!
0 rtas-cb rtas>nargs l!
0 rtas-cb rtas>nret l!
enter-rtas
;
0 value puid
: rtas-do-config-@ ( config-addr size -- value)
[ s" ibm,read-pci-config" rtas-get-token ] LITERAL rtas-cb rtas>token l!
4 rtas-cb rtas>nargs l!
2 rtas-cb rtas>nret l!
( addr size ) rtas-cb rtas>args3 l!
puid rtas-cb rtas>args2 l!
puid 20 rshift rtas-cb rtas>args1 l!
( addr ) rtas-cb rtas>args0 l!
enter-rtas
rtas-cb rtas>args4 l@ dup IF
drop ffffffff
ELSE
drop rtas-cb rtas>args5 l@
THEN
;
: rtas-do-config-! ( value config-addr size )
[ s" ibm,write-pci-config" rtas-get-token ] LITERAL rtas-cb rtas>token l!
5 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
( value addr size ) rtas-cb rtas>args3 l!
puid rtas-cb rtas>args2 l!
puid 20 rshift rtas-cb rtas>args1 l!
( value addr ) rtas-cb rtas>args0 l!
( value ) rtas-cb rtas>args4 l!
enter-rtas
rtas-cb rtas>args5 l@ dup IF
." RTAS write config err " . cr
ELSE drop THEN
;
: rtas-config-b@ ( config-addr -- value )
1 rtas-do-config-@ ff and
;
: rtas-config-b! ( value config-addr -- )
1 rtas-do-config-!
;
: rtas-config-w@ ( config-addr -- value )
2 rtas-do-config-@ ffff and
;
: rtas-config-w! ( value config-addr -- )
2 rtas-do-config-!
;
: rtas-config-l@ ( config-addr -- value )
4 rtas-do-config-@ ffffffff and
;
: rtas-config-l! ( value config-addr -- )
4 rtas-do-config-!
;
: of-start-cpu rtas-start-cpu ;
' power-off to halt
' rtas-system-reboot to reboot
rtas-node set-node
: open true ;
: close ;
: instantiate-rtas ( adr -- entry )
dup rtas-base swap rtas-size move
dup rtas-entry rtas-base - +
2dup hv-rtas-update dup 0 <> IF
dup -2 <> IF ." HV-RTAS-UPDATE error: " . cr ELSE drop THEN
ELSE
drop
THEN
nip
;
device-end
374 cp
3f0 cp
: strequal ( str1 len1 str2 len2 -- flag )
rot dup rot = IF comp 0= ELSE 2drop drop 0 THEN ; 
400 cp
" /" find-device
200000 CONSTANT cas-buffer-size
: ibm,client-architecture-support         ( vec -- err? )
cas-buffer-size alloc-mem             ( vec memaddr )
dup 0= IF ." out of memory during ibm,client-architecture-support" cr THEN
swap over cas-buffer-size             ( memaddr vec memaddr size )
hv-cas 0= IF                          ( memaddr )
dup l@ 1 >= IF                    \ Version number >= 1
" /" find-node set-node
dup 4 + fdt-init
fdt-check-header
fdt-struct fdt-fix-cas-node
fdt-fix-cas-success NOT
ELSE
FALSE
THEN
ELSE
TRUE
THEN
>r cas-buffer-size free-mem r>
;
480 cp
new-device
s" mmu" 2dup device-name device-type
0 0 s" translations" property
: open  true ;
: close ;
finish-device
device-end
4c0 cp
: fixup-tbfreq
" /cpus" find-device
get-node child dup 0= ABORT" CPU not found"
set-node
" timebase-frequency" get-node get-package-property IF
2drop
ELSE
decode-int to tb-frequency 2drop
THEN
device-end
;
fixup-tbfreq
4d0 cp
include fbuffer.fs
500 cp
: populate-vios ( -- )
." Populating /vdevice methods" cr
" /vdevice" find-device get-node child
BEGIN
dup 0 <>
WHILE
dup set-node
dup " compatible" rot get-package-property 0 = IF
drop dup from-cstring
2dup " hvterm1" strequal IF
" vio-hvterm.fs" included
THEN
2dup " IBM,v-scsi" strequal IF
" vio-vscsi.fs" included
THEN
2dup " IBM,l-lan" strequal IF
" vio-veth.fs" included
THEN
2dup " qemu,spapr-nvram" strequal IF
" rtas-nvram.fs" included
THEN
2drop
THEN
peer
REPEAT drop
device-end
;
populate-vios
580 cp
5a0 cp
VARIABLE pci-next-mem           \ prefetchable memory mapped
VARIABLE pci-max-mem
VARIABLE pci-next-mmio          \ non-prefetchable memory
VARIABLE pci-max-mmio
VARIABLE pci-next-io            \ I/O space
VARIABLE pci-max-io
VARIABLE pci-next-mem64           \ prefetchable 64-bit memory mapped
VARIABLE pci-max-mem64
0 VALUE pci-bus-number
0 VALUE pci-device-number
0 VALUE pci-device-slots
here 100 allot CONSTANT pci-device-vec
0 VALUE pci-device-vec-len
0 VALUE pci-hotplug-enabled
: next-pci-mem ( addr -- addr ) pci-next-mem ;
: next-pci-mmio ( addr -- addr ) pci-next-mmio ;
: next-pci-io ( addr -- addr ) pci-next-io ;
: int2str ( int len -- str len ) swap s>d rot <# 0 ?DO # LOOP #> ;
: pci-addr2bus ( addr -- busnr ) 10 rshift FF and ;
: pci-addr2dev ( addr -- dev ) B rshift 1F and ;
: pci-addr2fn ( addr -- dev ) 8 rshift 7 and ;
: pci-bus2addr ( busnr devnr -- addr ) B lshift swap 10 lshift + ;
: pci-addr-out ( addr -- ) dup pci-addr2bus 2 0.r space FFFF and 4 0.r ;
: pci-dump ( addr -- )
10 0 DO
dup
cr i 4 * +
dup pci-addr-out space
rtas-config-l@ 8 0.r
LOOP
drop cr
;
: pci-vendor@ ( addr -- id )                 rtas-config-l@ FFFF and ;
: pci-device@ ( addr -- id )                 rtas-config-l@ 10 rshift ;
: pci-status@ ( addr -- status )         4 + rtas-config-l@ 10 rshift ;
: pci-revision@ ( addr -- id )           8 + rtas-config-b@ ;
: pci-class@  ( addr -- class )          8 + rtas-config-l@ 8 rshift ;
: pci-cache@  ( addr -- size )           C + rtas-config-b@ ;
: pci-htype@  ( addr -- type )           E + rtas-config-b@  ;
: pci-sub-vendor@ ( addr -- sub-id )    2C + rtas-config-l@ FFFF and ;
: pci-sub-device@ ( addr -- sub-id )    2C + rtas-config-l@ 10 rshift FFFF and ;
: pci-interrupt@  ( addr -- interrupt ) 3D + rtas-config-b@ ;
: pci-min-grant@  ( addr -- min-gnt )   3E + rtas-config-b@ ;
: pci-max-lat@  ( addr -- max-lat )     3F + rtas-config-b@ ;
: pci-capabilities?  ( addr -- 0|1 ) pci-status@ 4 rshift 1 and ;
: pci-cap-next  ( cap-addr -- next-cap-off ) rtas-config-b@ FC and ;
: pci-cap-next-addr  ( cap-addr -- next-cap-addr ) 1+ dup pci-cap-next dup IF swap -100 and + ELSE nip THEN ;
: pci-cap-dump ( addr -- )
cr
dup pci-capabilities? IF
33 + BEGIN
pci-cap-next-addr dup 0<>
WHILE
dup pci-addr-out s"  : " type
dup rtas-config-b@ 2 0.r cr
REPEAT
s" end found "
ELSE
s" capabilities not enabled!"
THEN
type cr drop
;
: pci-cap-find ( addr id -- capp-addr|0 )
swap dup pci-capabilities? IF
33 + BEGIN
pci-cap-next-addr dup 0<> IF
dup rtas-config-b@ 2 pick =
ELSE
true
THEN
UNTIL
nip
ELSE
2drop 0
THEN
;
: pci-express? ( addr -- 0|1 ) 10 pci-cap-find 0<> ;
: pci-x? ( addr -- 0|1 ) 07 pci-cap-find 0<> ;
: pci-config-ext? ( addr -- 0|1 ) pci-express? ;
: pci-device-disable ( -- ) my-space 4 + dup rtas-config-l@ 7 invert and swap rtas-config-l! ;
: pci-master-enable ( -- ) my-space 4 + dup rtas-config-l@ 4 or swap rtas-config-l! ;
: pci-master-disable ( -- ) my-space 4 + dup rtas-config-l@ 4 invert and swap rtas-config-l! ;
: pci-mem-enable ( -- ) my-space 4 + dup rtas-config-w@ 2 or swap rtas-config-w! ;
: pci-io-enable ( -- ) my-space 4 + dup rtas-config-w@ 1 or swap rtas-config-w! ;
: pci-enable ( -- ) my-space 4 + dup rtas-config-w@ 7 or swap rtas-config-w! ;
: pci-error-enable ( -- ) my-space 4 + dup rtas-config-w@ 140 or swap rtas-config-w! ;
: pci-out ( addr char -- )
15 spaces
over pci-addr-out
s"  (" type emit s" ) : " type
dup pci-vendor@ 4 0.r space
pci-device@ 4 0.r
4 spaces
;
: pci-irq-line@  ( addr -- irq-pin ) 3C + rtas-config-b@ ;
: pci-irq-line!  ( pin addr -- ) 3C + rtas-config-b! ;
: pci-bus-prim! ( nr addr -- ) 18 + dup rtas-config-l@ FFFFFF00 and rot + swap rtas-config-l! ;
: pci-bus-prim@ ( addr -- nr ) 18 + rtas-config-l@ FF and ;
: pci-bus-scnd! ( nr addr -- ) 18 + dup rtas-config-l@ FFFF00FF and rot 8 lshift + swap rtas-config-l! ;
: pci-bus-scnd@ ( addr -- nr ) 18 + rtas-config-l@ 8 rshift FF and ;
: pci-bus-subo! ( nr addr -- ) 18 + dup rtas-config-l@ FF00FFFF and rot 10 lshift + swap rtas-config-l! ;
: pci-bus-subo@ ( addr -- nr ) 18 + rtas-config-l@ 10 rshift FF and ;
: pci-bus! ( subo scnd prim addr -- ) swap rot 8 lshift + rot 10 lshift + swap 18 + dup rtas-config-l@ FF000000 and rot + swap rtas-config-l! ;
: pci-bus@ ( addr -- subo scnd prim ) 18 + rtas-config-l@ dup 10 rshift FF and swap dup 8 rshift FF and swap FF and ;
: pci-reset-2nd ( addr -- ) 1C + dup rtas-config-l@ FFFF0000 or swap rtas-config-l! ;
: pci-vec ( -- )
cr s" device-vec(" type
pci-device-vec-len dup 2 0.r s" ):" type
1+ 0 DO
pci-device-vec i + c@
space 2 0.r
LOOP
cr
;
: pci-var-out ( -- )
s"   mem:" type pci-next-mem @ 16 0.r cr
s"  mmio:" type pci-next-mmio @ 16 0.r cr
s"    io:" type pci-next-io @ 16 0.r cr
;
: pci-set-slot ( addr -- )
pci-addr2dev dup                \ calc slot number
pci-device-vec-len              \ the end of the vector
pci-device-vec + c!             \ and update the vector
80000000 swap rshift            \ calc bit position of the device slot
pci-device-slots or             \ set this bit
TO pci-device-slots             \ and write it back
;
: pci-bridge-set-mmio-base ( addr -- )
pci-next-mmio @ 100000 #aligned         \ read the current Value and align to 1MB boundary
dup 100000 + pci-next-mmio !            \ and write back with 1MB for bridge
10 rshift                               \ mmio-base reg is only the upper 16 bits
pci-max-mmio @ 1- FFFF0000 and or       \ and Insert mmio Limit (set it to max)
swap 20 + rtas-config-l!                \ and write it into the bridge
;
: pci-bridge-set-mmio-limit ( addr -- )
pci-next-mmio @ 100000 #aligned         \ fetch current value and align to 1MB
dup pci-next-mmio !                     \ and write it back
1- FFFF0000 and                         \ make it one less and keep upper 16 bits
over 20 + rtas-config-l@ 0000FFFF and   \ fetch original value
or swap 20 + rtas-config-l!             \ and write it into the Reg
;
: pci-bridge-set-mem-base ( addr -- )
pci-next-mem @ 100000 #aligned          \ read the current Value and align to 1MB boundary
dup 100000 + pci-next-mem !             \ and write back with 1MB for bridge
over 24 + rtas-config-w@                \ check if 64bit support
1 and IF                                \ IF 64 bit support
pci-next-mem64 @ 100000000 #aligned \ | read the current Value of 64-bit and align to 4GB boundary
dup 100000000 + pci-next-mem64 x!   \ | and write back with 1GB for bridge
2 pick swap                         \ |
20 rshift                           \ | keep upper 32 bits
swap 28 + rtas-config-l!            \ | and write it into the Base-Upper32-bits
pci-max-mem64 @ 20 rshift           \ | fetch max Limit address and keep upper 32 bits
2 pick 2C + rtas-config-l!          \ | and set the Limit
THEN                                    \ FI
10 rshift                               \ keep upper 16 bits
pci-max-mem @ 1- FFFF0000 and or        \ and Insert mmem Limit (set it to max)
swap 24 + rtas-config-l!                \ and write it into the bridge
;
: pci-bridge-set-mem-limit ( addr -- )
pci-next-mem @ 100000 #aligned          \ read the current Value and align to 1MB boundary
dup pci-next-mem !                      \ and write it back
1-                                      \ make limit one less than boundary
over 24 + rtas-config-w@                \ check if 64bit support
1 and IF                                \ IF 64 bit support
pci-next-mem64 @ 100000000 #aligned \ | Reat current value of 64-bar and align at 4GB
dup pci-next-mem64 x!               \ | and write it back
1-                                  \ | make limite one less than boundary
2 pick swap                         \ |
20 rshift                           \ | keep upper 32 bits
swap 2C + rtas-config-l!            \ | and write it into the Limit-Upper32-bits
THEN                                    \ FI
FFFF0000 and                            \ keep upper 16 bits
over 24 + rtas-config-l@ 0000FFFF and   \ fetch original Value
or swap 24 + rtas-config-l!             \ and write it into the bridge
;
: pci-bridge-set-io-base ( addr -- )
pci-next-io @ 1000 #aligned             \ read the current Value and align to 4KB boundary
dup 1000 + pci-next-io !                \ and write back with 4K for bridge
over 1C + rtas-config-l@                \ check if 32bit support
1 and IF                                \ IF 32 bit support
2dup 10 rshift                  \ | keep upper 16 bits
pci-max-io @ FFFF0000 and or    \ | insert upper 16 bits of Max-Limit
swap 30 + rtas-config-l!        \ | and write it into the Base-Upper16-bits
THEN                                    \ FI
8 rshift 000000FF and                   \ keep upper 8 bits
pci-max-io @ 1- 0000FF00 and or         \ insert upper 8 bits of Max-Limit
over rtas-config-l@ FFFF0000 and        \ fetch original Value
or swap 1C + rtas-config-l!             \ and write it into the bridge
;
: pci-bridge-set-io-limit ( addr -- )
pci-next-io @ 1000 #aligned             \ read the current Value and align to 4KB boundary
dup pci-next-io !                       \ and write it back
1-                                      \ make limit one less than boundary
over 1D + rtas-config-b@                \ check if 32bit support
1 and IF                                \ IF 32 bit support
2dup FFFF0000 and               \ | keep upper 16 bits
over 30 + rtas-config-l@        \ | fetch original Value
or swap 30 + rtas-config-l!     \ | and write it into the Limit-Upper16-bits
THEN                                    \ FI
0000FF00 and                            \ keep upper 8 bits
over 1C + rtas-config-l@ FFFF00FF and   \ fetch original Value
or swap 1C + rtas-config-l!             \ and write it into the bridge
;
: pci-bridge-set-bases ( addr -- )
dup pci-bridge-set-mmio-base
dup pci-bridge-set-mem-base
pci-bridge-set-io-base
;
: pci-bridge-set-limits ( addr -- )
dup pci-bridge-set-mmio-limit
dup pci-bridge-set-mem-limit
pci-bridge-set-io-limit
;
DEFER func-pci-probe-bus
DEFER func-pci-bridge-range-props
: pci-bridge-probe ( addr -- )
dup pci-bridge-set-bases                        \ SetUp all Base Registers
dup func-pci-bridge-range-props                 \ Setup temporary "range
pci-bus-number 1+ TO pci-bus-number             \ increase number of busses found
pci-device-vec-len 1+ TO pci-device-vec-len     \ increase the device-slot vector depth
dup                                             \ stack config-addr for pci-bus!
FF swap                                         \ Subordinate Bus Number ( for now to max to open all subbusses )
pci-bus-number swap                             \ Secondary   Bus Number ( the new busnumber )
dup pci-addr2bus swap                           \ Primary     Bus Number ( the current bus )
pci-bus!                                        \ and set them into the bridge
pci-enable                                      \ enable mem/IO transactions
dup pci-bus-scnd@ func-pci-probe-bus            \ and probe the secondary bus
dup pci-bus-number swap pci-bus-subo!           \ set SubOrdinate Bus Number to current number of busses
pci-device-vec-len 1- TO pci-device-vec-len     \ decrease the device-slot vector depth
dup pci-bridge-set-limits                       \ SetUp all Limit Registers
drop                                            \ forget the config-addr
;
DEFER func-pci-bridge-probe
' pci-bridge-probe TO func-pci-bridge-probe
: pci-device-setup ( addr -- )
drop                            \ since the config-addr is coded in my-space, drop it here
s" pci-device.fs" included      \ and setup the device as node in the device tree
;
: pci-bridge-setup ( addr -- )
drop                            \ since the config-addr is coded in my-space, drop it here
s" pci-bridge.fs" included      \ and setup the bridge as node in the device tree
;
: pci-add-device ( addr -- )
new-device                      \ create a new device-tree node
dup set-space               \ set the config addr for this device tree entry
dup pci-set-slot            \ set the slot bit
dup pci-htype@              \ read HEADER-Type
7f and                      \ Mask bit 7 - multifunction device
CASE
0 OF pci-device-setup ENDOF  \ | set up the device
1 OF pci-bridge-setup ENDOF  \ | set up the bridge
dup OF dup pci-htype@ pci-out ENDOF
ENDCASE
finish-device                   \ and close the device-tree node
;
: pci-setup-device ( addr -- )
dup pci-htype@                      \ read HEADER-Type
80 and IF 8 ELSE 1 THEN             \ check for multifunction
0 DO                                \ LOOP over all possible functions (either 8 or only 1)
dup
i 8 lshift +                \ calc device-function-config-addr
dup pci-vendor@             \ check if valid function
FFFF = IF
drop                \ non-valid so forget the address
ELSE
pci-device-number 1+    \ increase the number of devices
TO pci-device-number    \ and store it
pci-add-device          \ and add the device to the device tree and set it up
THEN
LOOP                                \ next function
drop                                \ forget the device-addr
;
: pci-probe-device ( busnr devicenr -- )
pci-bus2addr                                    \ calc pci-address
dup pci-vendor@                                 \ fetch Vendor-ID
FFFF = IF                                       \ check if valid
drop                                    \ if not forget it
ELSE
pci-setup-device                        \ if valid setup the device
THEN
;
: pci-probe-bus ( busnr -- )
0 TO pci-device-slots           \ reset slot array to unpoppulated
20 0 DO
dup
i pci-probe-device
LOOP
drop
;
' pci-probe-bus TO func-pci-probe-bus
: pci-probe-all ( bus-max bus-min -- )                  \ Check all busses from bus-min up to bus-max if needed
0 TO pci-device-vec-len                         \ reset the device-slot vector
DO
i TO pci-bus-number                     \ set current Busnumber
0 TO pci-device-number                  \ reset Device Number
pci-bus-number pci-probe-bus            \ and probe this bus
pci-device-number 0 > IF LEAVE THEN     \ if we found a device we're done
LOOP                                            \ else next bus
;
: (probe-pci-host-bridge) ( bus-max bus-min -- )
0d emit ."  Adapters on " puid 10 0.r cr        \ print the puid we're looking at
( bus-max bus-min ) pci-probe-all               \ and walk the bus
pci-device-number 0= IF                         \ IF no devices found
15 spaces                               \ | indent the output
." None" cr                             \ | tell the world our result
THEN                                            \ FI
;
: probe-pci-host-bridge ( bus-max bus-min mmio-max mmio-base mem-max mem-base io-max io-base my-puid -- )
puid >r TO puid                                 \ save puid and set the new
pci-next-io !                                   \ save the next io-base address
pci-max-io !                                    \ save the max io-space address
pci-next-mem !                                  \ save the next mem-base address
pci-max-mem !                                   \ save the max mem-space address
pci-next-mmio !                                 \ save the next mmio-base address
pci-max-mmio !                                  \ save the max mmio-space address
(probe-pci-host-bridge)
r> TO  puid                                     \ restore puid
;
0 VALUE pci-net-num
0 VALUE pci-disk-num
0 VALUE pci-cdrom-num
: pci-set-alias ( str-addr str-len num -- )
$cathex strdup       \ create alias name
get-node node>path   \ get path string
set-alias            \ and set the alias
;
: unknown-enet ( -- pci-net-num )
pci-net-num dup 1+ TO pci-net-num
;
: pci-alias-net ( config-addr -- )
drop                                   \ forget the config address
pci-net-num dup 1+ TO pci-net-num      \ increase the pci-net-num
s" net" rot pci-set-alias              \ create the alias
;
: pci-alias-disk ( config-addr -- )
drop                                    \ forget the config address
pci-disk-num dup 1+ TO pci-disk-num     \ increase the pci-disk-num
s" disk" rot pci-set-alias              \ create the alias
;
: pci-alias-cdrom ( config-addr -- )
drop                                    \ forget the config address
pci-cdrom-num dup 1+ TO pci-cdrom-num     \ increase the pci-cdrom-num
s" cdrom" rot pci-set-alias              \ create the alias
;
: pci-alias ( config-addr -- )
dup pci-class@ 
10 rshift CASE
01 OF   pci-alias-disk ENDOF
02 OF   pci-alias-net  ENDOF
dup OF   drop           ENDOF
ENDCASE
;
: pci-gen-irq-map-one ( prop-addr prop-len slot pin -- prop-addr prop-len )
2dup + 1- 3 and 1+          ( prop-addr prop-len slot pin parentpin )
>r >r                       ( prop-addr prop-len slot R: parentpin pin )
B lshift encode-int+        ( prop-addr prop-len R: parentpin pin )
0 encode-64+
r> encode-int+              ( prop-addr prop-len R: parentpin )
get-parent encode-int+
get-node >space
pci-addr2dev B lshift       ( prop-addr prop-len parent-slot R: parentpin )
encode-int+
0 encode-64+
r> encode-int+              ( prop-addr prop-len R: )
;
: pci-gen-irq-entry ( prop-addr prop-len config-addr -- prop-addr prop-len )
pci-addr2dev                ( prop-addr prop-len slot )
-rot                        ( slot prop-addr prop-len )
5 1 DO
2 pick i                ( slot prop-addr prop-len slot pin )
pci-gen-irq-map-one
LOOP
rot drop
;
: pci-set-irq-line ( config-addr -- )
drop
;
: pci-msi-prop ( addr -- )
5 pci-cap-find          ( capaddr )
?dup IF
2+ rtas-config-w@   ( msi-control )
1 rshift 7 and      ( msi-control:3:1 )
dup 6 < IF
1 swap lshift   ( vectors# )
encode-int " ibm,req#msi" property
ELSE
." Invalid MSI vectors number " . cr
THEN
THEN
;
: pci-msix-prop ( addr -- )
11 pci-cap-find         ( capaddr )
?dup IF
2+ rtas-config-w@   ( msix-control )
7ff and             ( msix-control:10:0 )
1+                  ( vectors# )
?dup IF
encode-int " ibm,req#msi-x" property
THEN
THEN
;
: pci-set-capabilities ( config-addr -- )
dup pci-msi-prop
dup pci-msix-prop
drop
;
: pci-class-name-00 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
01  OF s" display"               ENDOF
dup OF s" unknown-legacy-device" ENDOF
ENDCASE
;
: pci-class-name-01 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" scsi"         ENDOF
01  OF s" ide"          ENDOF
02  OF s" fdc"          ENDOF
03  OF s" ipi"          ENDOF
04  OF s" raid"         ENDOF
05  OF s" ata"          ENDOF
06  OF s" sata"         ENDOF
07  OF s" sas"          ENDOF
dup OF s" mass-storage" ENDOF
ENDCASE
;
: pci-class-name-02 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" ethernet"   ENDOF
01  OF s" token-ring" ENDOF
02  OF s" fddi"       ENDOF
03  OF s" atm"        ENDOF
04  OF s" isdn"       ENDOF
05  OF s" worldfip"   ENDOF
05  OF s" picmg"      ENDOF
dup OF s" network"    ENDOF
ENDCASE
;
: pci-class-name-03 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" vga"             ENDOF
0001  OF s" 8514-compatible" ENDOF
0100  OF s" xga"             ENDOF
0200  OF s" 3d-controller"   ENDOF
dup OF s" display"           ENDOF
ENDCASE
;
: pci-class-name-04 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" video"             ENDOF
01  OF s" sound"             ENDOF
02  OF s" telephony"         ENDOF
dup OF s" multimedia-device" ENDOF
ENDCASE
;
: pci-class-name-05 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" memory"            ENDOF
01  OF s" flash"             ENDOF
dup OF s" memory-controller" ENDOF
ENDCASE
;
: pci-class-name-06 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" host"                 ENDOF
01  OF s" isa"                  ENDOF
02  OF s" eisa"                 ENDOF
03  OF s" mca"                  ENDOF
04  OF s" pci"                  ENDOF
05  OF s" pcmcia"               ENDOF
06  OF s" nubus"                ENDOF
07  OF s" cardbus"              ENDOF
08  OF s" raceway"              ENDOF
09  OF s" semi-transparent-pci" ENDOF
0A  OF s" infiniband"           ENDOF
dup OF s" unknown-bridge"       ENDOF
ENDCASE
;
: pci-class-name-07 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" serial"                   ENDOF
0001  OF s" 16450-serial"             ENDOF
0002  OF s" 16550-serial"             ENDOF
0003  OF s" 16650-serial"             ENDOF
0004  OF s" 16750-serial"             ENDOF
0005  OF s" 16850-serial"             ENDOF
0006  OF s" 16950-serial"             ENDOF
0100  OF s" parallel"                 ENDOF
0101  OF s" bi-directional-parallel"  ENDOF
0102  OF s" ecp-1.x-parallel"         ENDOF
0103  OF s" ieee1284-controller"      ENDOF
01FE  OF s" ieee1284-device"          ENDOF
0200  OF s" multiport-serial"         ENDOF
0300  OF s" modem"                    ENDOF
0301  OF s" 16450-modem"              ENDOF
0302  OF s" 16550-modem"              ENDOF
0303  OF s" 16650-modem"              ENDOF
0304  OF s" 16750-modem"              ENDOF
0400  OF s" gpib"                     ENDOF
0500  OF s" smart-card"               ENDOF
dup   OF s" communication-controller" ENDOF
ENDCASE
;
: pci-class-name-08 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" interrupt-controller" ENDOF
0001  OF s" isa-pic"              ENDOF
0002  OF s" eisa-pic"             ENDOF
0010  OF s" io-apic"              ENDOF
0020  OF s" iox-apic"             ENDOF
0100  OF s" dma-controller"       ENDOF
0101  OF s" isa-dma"              ENDOF
0102  OF s" eisa-dma"             ENDOF
0200  OF s" timer"                ENDOF
0201  OF s" isa-system-timer"     ENDOF
0202  OF s" eisa-system-timer"    ENDOF
0300  OF s" rtc"                  ENDOF
0301  OF s" isa-rtc"              ENDOF
0400  OF s" hot-plug-controller"  ENDOF
0500  OF s" sd-host-conrtoller"   ENDOF
dup   OF s" system-periphal"      ENDOF
ENDCASE
;
: pci-class-name-09 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" keyboard"         ENDOF
01  OF s" pen"              ENDOF
02  OF s" mouse"            ENDOF
03  OF s" scanner"          ENDOF
04  OF s" gameport"         ENDOF
dup OF s" input-controller" ENDOF
ENDCASE
;
: pci-class-name-0A ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" dock"            ENDOF
dup OF s" docking-station" ENDOF
ENDCASE
;
: pci-class-name-0B ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" 386"           ENDOF
01  OF s" 486"           ENDOF
02  OF s" pentium"       ENDOF
10  OF s" alpha"         ENDOF
20  OF s" powerpc"       ENDOF
30  OF s" mips"          ENDOF
40  OF s" co-processor"  ENDOF
dup OF s" cpu"           ENDOF
ENDCASE
;
: pci-class-name-0C ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" firewire"      ENDOF
0100  OF s" access-bus"    ENDOF
0200  OF s" ssa"           ENDOF
0300  OF s" usb-uhci"      ENDOF
0310  OF s" usb-ohci"      ENDOF
0320  OF s" usb-ehci"      ENDOF
0330  OF s" usb-xhci"      ENDOF
0380  OF s" usb"           ENDOF
03FE  OF s" usb-device"    ENDOF
0400  OF s" fibre-channel" ENDOF
0500  OF s" smb"           ENDOF
0600  OF s" infiniband"    ENDOF
0700  OF s" ipmi-smic"     ENDOF
0701  OF s" ipmi-kbrd"     ENDOF
0702  OF s" ipmi-bltr"     ENDOF
0800  OF s" sercos"        ENDOF
0900  OF s" canbus"        ENDOF
dup OF s" serial-bus"      ENDOF
ENDCASE
;
: pci-class-name-0D ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" irda"                ENDOF
01  OF s" consumer-ir"         ENDOF
10  OF s" rf-controller"       ENDOF
11  OF s" bluetooth"           ENDOF
12  OF s" broadband"           ENDOF
20  OF s" enet-802.11a"        ENDOF
21  OF s" enet-802.11b"        ENDOF
dup OF s" wireless-controller" ENDOF
ENDCASE
;
: pci-class-name-0E ( addr -- str len )
pci-class@ 8 rshift FF and CASE
dup OF s" intelligent-io" ENDOF
ENDCASE
;
: pci-class-name-0F ( addr -- str len )
pci-class@ 8 rshift FF and CASE
01  OF s" satelite-tv"     ENDOF
02  OF s" satelite-audio"  ENDOF
03  OF s" satelite-voice"  ENDOF
04  OF s" satelite-data"   ENDOF
dup OF s" satelite-devoce" ENDOF
ENDCASE
;
: pci-class-name-10 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" network-encryption"       ENDOF
01  OF s" entertainment-encryption" ENDOF
dup OF s" encryption"               ENDOF
ENDCASE
;
: pci-class-name-11 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" dpio"                       ENDOF
01  OF s" counter"                    ENDOF
10  OF s" measurement"                ENDOF
20  OF s" managment-card"             ENDOF
dup OF s" data-processing-controller" ENDOF
ENDCASE
;
: pci-class-name ( addr -- str len )
dup pci-class@ 10 rshift CASE
00  OF pci-class-name-00 ENDOF
01  OF pci-class-name-01 ENDOF
02  OF pci-class-name-02 ENDOF
03  OF pci-class-name-03 ENDOF
04  OF pci-class-name-04 ENDOF
05  OF pci-class-name-05 ENDOF
06  OF pci-class-name-06 ENDOF
07  OF pci-class-name-07 ENDOF
08  OF pci-class-name-08 ENDOF
09  OF pci-class-name-09 ENDOF
0A  OF pci-class-name-0A ENDOF
0B  OF pci-class-name-0B ENDOF
0C  OF pci-class-name-0C ENDOF
0C  OF pci-class-name-0D ENDOF
0C  OF pci-class-name-0E ENDOF
0C  OF pci-class-name-0F ENDOF
0C  OF pci-class-name-10 ENDOF
0C  OF pci-class-name-11 ENDOF
dup OF drop s" unknown"  ENDOF
ENDCASE
;
: pci-bar-size@     ( bar-addr -- bar-size ) -1 over rtas-config-l! rtas-config-l@ ;
: pci-bar-size-mem@ ( bar-addr -- mem-size ) pci-bar-size@ -10 and invert 1+ FFFFFFFF and ;
: pci-bar-size-io@  ( bar-addr -- io-size  ) pci-bar-size@ -4 and invert 1+ FFFFFFFF and ;
: pci-bar-size ( bar-addr -- bar-size-raw )
dup rtas-config-l@ swap \ fetch original Value  ( bval baddr )
-1 over rtas-config-l!  \ make BAR show size    ( bval baddr )
dup rtas-config-l@      \ and fetch the size    ( bval baddr bsize )
-rot rtas-config-l!     \ restore Value
;
: pci-bar-size-mem32 ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
-10 and invert 1+       \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-size-rom ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
FFFFF800 and invert 1+  \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-size-mem64 ( bar-addr -- bar-size )
dup pci-bar-size        \ fetch raw size lower 32 bits
swap 4 + pci-bar-size   \ fetch raw size upper 32 bits
20 lshift +             \ and put them together
-10 and invert 1+       \ calc size
;
: pci-bar-size-io ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
-4 and invert 1+        \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-code@ ( bar-addr -- 0|1..4|5 )
rtas-config-l@ dup                \ fetch the BaseAddressRegister
1 and IF                          \ IO BAR ?
2 and IF 0 ELSE 1 THEN    \ only '01' is valid
ELSE                              \ Memory BAR ?
F and CASE
0   OF 2 ENDOF    \ Memory 32 Bit Non-Prefetchable
8   OF 3 ENDOF    \ Memory 32 Bit Prefetchable
4   OF 4 ENDOF    \ Memory 64 Bit Non-Prefetchable
C   OF 5 ENDOF    \ Memory 64 Bit Prefechtable
dup OF 0 ENDOF    \ Not a valid BarType
ENDCASE
THEN
;
: assign-var ( size var -- al-mem )
2dup @                          \ ( size var size cur-mem ) read current free mem
swap #aligned                   \ ( size var al-mem )       align the mem to the size
dup 2swap -rot +                \ ( al-mem var new-mem )    add size to aligned mem
swap !                          \ ( al-mem )                set variable to new mem
;
: assign-bar-value32 ( bar size var -- 4 )
over IF                         \ IF size > 0
assign-var              \ | ( bar al-mem ) set variable to next mem
swap rtas-config-l!     \ | ( -- )         set the bar to al-mem
ELSE                            \ ELSE
2drop drop              \ | clear stack
THEN                            \ FI
4                               \ size of the base-address-register
;
: assign-bar-value64 ( bar size var -- 8 )
over IF                         \ IF size > 0
assign-var              \ | ( bar al-mem ) set variable to next mem
swap                    \ | ( al-mem addr ) calc config-addr of this bar
2dup rtas-config-l!     \ | ( al-mem addr ) set the Lower part of the bar to al-mem
4 + swap 20 rshift      \ | ( al-mem>>32 addr ) prepare the upper part of the al-mem
swap rtas-config-l!     \ | ( -- ) and set the upper part of the bar
ELSE                            \ ELSE
2drop drop              \ | clear stack
THEN                            \ FI
8                               \ size of the base-address-register
;
: assign-mem64-bar ( bar-addr -- 8 )
dup pci-bar-size-mem64         \ fetch size
pci-next-mem64 @ 0 = IF          \ Check if we have 64-bit memory range
pci-next-mem
ELSE
pci-next-mem64
THEN
assign-bar-value64              \ and set it all
;
: assign-mem32-bar ( bar-addr -- 4 )
dup pci-bar-size-mem32          \ fetch size
pci-next-mem                    \ var to change
assign-bar-value32              \ and set it all
;
: assign-mmio64-bar ( bar-addr -- 8 )
dup pci-bar-size-mem64          \ fetch size
pci-next-mem64 @ 0 = IF          \ Check if we have 64-bit memory range
pci-next-mmio
ELSE
pci-next-mem64              \ for board-qemu we will use same range
THEN
assign-bar-value64              \ and set it all
;
: assign-mmio32-bar ( bar-addr -- 4 )
dup pci-bar-size-mem32          \ fetch size
pci-next-mmio                   \ var to change
assign-bar-value32              \ and set it all
;
: assign-io-bar ( bar-addr -- 4 )
dup pci-bar-size-io             \ fetch size
pci-next-io                     \ var to change
assign-bar-value32              \ and set it all
;
: assign-rom-bar ( bar-addr -- )
dup pci-bar-size-rom            \ fetch size
dup IF                          \ IF size > 0
over >r                 \ | save bar addr for enable
pci-next-mmio           \ | var to change
assign-bar-value32      \ | and set it
drop                    \ | forget the BAR length
r@ rtas-config-l@       \ | fetch BAR
1 or r> rtas-config-l!  \ | and enable the ROM
ELSE                            \ ELSE
2drop                   \ | clear stack
THEN
;
: assign-bar ( bar-addr -- reg-size )
dup pci-bar-code@                       \ calc BAR type
dup IF                                  \ IF >0
CASE                            \ | CASE Setup the right type
1 OF assign-io-bar     ENDOF    \ | - set up an IO-Bar
2 OF assign-mmio32-bar ENDOF    \ | - set up an 32bit MMIO-Bar
3 OF assign-mem32-bar  ENDOF    \ | - set up an 32bit MEM-Bar (prefetchable)
4 OF assign-mmio64-bar ENDOF    \ | - set up an 64bit MMIO-Bar
5 OF assign-mem64-bar  ENDOF    \ | - set up an 64bit MEM-Bar (prefetchable)
ENDCASE                         \ | ESAC
ELSE                                    \ ELSE
ABORT                           \ | Throw an exception
THEN                                    \ FI
;
: assign-all-device-bars ( configaddr -- )
28 10 DO                        \ BARs start at 10 and end at 27
dup i +                 \ calc config-addr of the BAR
assign-bar              \ and set it up
+LOOP                           \ add 4 or 8 to the index and loop
30 + assign-rom-bar             \ set up the ROM if available
;
: assign-all-bridge-bars ( configaddr -- )
18 10 DO                        \ BARs start at 10 and end at 17
dup i +                 \ calc config-addr of the BAR
assign-bar              \ and set it up
+LOOP                           \ add 4 or 8 to the index and loop
38 + assign-rom-bar             \ set up the ROM if available
;
: gen-mem64-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch lower 32 bits ( paddr plen baddr val.lo R: size)
over 4 + rtas-config-l@         \ | fetch upper 32 bits               ( paddr plen baddr val.lo val.hi R: size)
20 lshift + -10 and >r          \ | calc 64 bit value and save it     ( paddr plen baddr R: size val )
83000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ sizeof(BAR) = 8 Bytes
;
: gen-pmem64-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch lower 32 bits ( paddr plen baddr val.lo R: size)
over 4 + rtas-config-l@         \ | fetch upper 32 bits               ( paddr plen baddr val.lo val.hi R: size)
20 lshift + -10 and >r          \ | calc 64 bit value and save it     ( paddr plen baddr R: size val )
C3000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ sizeof(BAR) = 8 Bytes
;
: gen-mem32-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-10 and >r                      \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
82000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-pmem32-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-10 and >r                      \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
C2000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-io-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-io                     \ fetch BAR Size                      ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-4 and >r                       \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
81000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-rom-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len )
dup pci-bar-size-rom                    \ fetch BAR Size                      ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
FFFFF800 and >r                 \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
82000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
;
: pci-add-assigned-address ( prop-addr prop-len bar-addr -- prop-addr prop-len bsize )
dup pci-bar-code@                               \ calc BAR type                         ( paddr plen baddr btype)
CASE                                            \ CASE for the BAR types                ( paddr plen baddr )
0 OF drop 4              ENDOF          \ - not a valid type so do nothing
1 OF gen-io-bar-prop     ENDOF          \ - IO-BAR
2 OF gen-mem32-bar-prop  ENDOF          \ - MEM32
3 OF gen-pmem32-bar-prop ENDOF          \ - MEM32 prefetchable
4 OF gen-mem64-bar-prop  ENDOF          \ - MEM64
5 OF gen-pmem64-bar-prop ENDOF          \ - MEM64 prefetchable
ENDCASE                                         \ ESAC ( paddr plen bsize )
;
: pci-device-assigned-addresses-prop ( addr -- )
encode-start                                    \ provide mem for property              ( addr paddr plen )
2 pick 30 + gen-rom-bar-prop                    \ assign the rom bar
28 10 DO                                        \ we have 6 possible BARs
2 pick i +                              \ calc BAR address                      ( addr paddr plen bar-addr )      
pci-add-assigned-address                \ and generate the props for the BAR
+LOOP                                           \ increase Index by returned len
s" assigned-addresses" property drop            \ and write it into the device tree
;
: pci-bridge-assigned-addresses-prop ( addr -- )
encode-start                                    \ provide mem for property
2 pick 38 + gen-rom-bar-prop                    \ assign the rom bar
18 10 DO                                        \ we have 2 possible BARs
2 pick i +                              \ ( addr paddr plen current-addr )
pci-add-assigned-address                \ and generate the props for the BAR
+LOOP                                           \ increase Index by returned len
s" assigned-addresses" property drop            \ and write it into the device tree
;
: pci-bridge-gen-range ( paddr plen base limit type -- paddr plen )
>r over -                       \ calc size             ( paddr plen base size R:type )
dup 0< IF                       \ IF Size < 0           ( paddr plen base size R:type )
2drop r> drop           \ | forget values       ( paddr plen )
ELSE                            \ ELSE
1+ swap 2swap           \ | adjust stack        ( size base paddr plen R:type )
r@ encode-int+          \ | Child type          ( size base paddr plen R:type )
2 pick encode-64+       \ | Child address       ( size base paddr plen R:type )
r> encode-int+          \ | Parent type         ( size base paddr plen )
rot encode-64+          \ | Parent address      ( size paddr plen )
rot encode-64+          \ | Encode size         ( paddr plen )
THEN                            \ FI
;
: pci-bridge-gen-mmio-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 20 + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 0000FFF0 and 10 lshift      \ calc base-address     ( addr paddr plen val base )
swap 000FFFFF or                \ calc limit-address    ( addr paddr plen base limit )
02000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-gen-mem-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 24 + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 000FFFFF or                 \ calc limit Bits 31:0  ( addr paddr plen val limit.31:0 )
swap 0000FFF0 and 10 lshift     \ calc base Bits 31:0   ( addr paddr plen limit.31:0 base.31:0 )
4 pick 28 + rtas-config-l@      \ fetch upper Basebits  ( addr paddr plen limit.31:0 base.31:0 base.63:32 )
20 lshift or swap               \ and calc Base         ( addr paddr plen base.63:0 limit.31:0 )
4 pick 2C + rtas-config-l@      \ fetch upper Limitbits ( addr paddr plen base.63:0 limit.31:0 limit.63:32 )
20 lshift or                    \ and calc Limit        ( addr paddr plen base.63:0 limit.63:0 )
42000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-gen-io-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 1C + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 0000F000 and 00000FFF or    \ calc Limit Bits 15:0  ( addr paddr plen val limit.15:0 )
swap 000000F0 and 8 lshift      \ calc Base Bits 15:0   ( addr paddr plen limit.15:0 base.15:0 )
4 pick 30 + rtas-config-l@      \ fetch upper Bits      ( addr paddr plen limit.15:0 base.15:0 val )
dup FFFF and 10 lshift rot or   \ calc Base             ( addr paddr plen limit.15:0 val base.31:0 )
-rot FFFF0000 and or            \ calc Limit            ( addr paddr plen base.31:0 limit.31:0 )
01000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-range-props ( addr -- )
encode-start                    \ provide mem for property
pci-bridge-gen-mmio-range       \ generate the non prefetchable Memory Entry
pci-bridge-gen-mem-range        \ generate the prefetchable Memory Entry
pci-bridge-gen-io-range         \ generate the IO Entry
dup IF                          \ IF any space present (propsize>0)
s" ranges" property     \ | write it into the device tree
ELSE                            \ ELSE
s" " s" ranges" property
2drop                   \ | forget the properties
THEN                            \ FI
drop                            \ forget the address
;
: pci-bridge-interrupt-map ( -- )
encode-start                                    \ create the property                           ( paddr plen )
get-node child                                  \ find the first child                          ( paddr plen handle )
BEGIN dup WHILE                                 \ Loop as long as the handle is non-zero        ( paddr plen handle )
dup >r >space                           \ Get the my-space                              ( paddr plen addr R: handle )
pci-gen-irq-entry                       \ and Encode the interrupt settings             ( paddr plen R: handle)
r> peer                                 \ Get neighbour                                 ( paddr plen handle )
REPEAT                                          \ process next childe node                      ( paddr plen handle )
drop                                            \ forget the null                               ( paddr plen )
s" interrupt-map" property                      \ and set it                                    ( -- )
1 encode-int s" #interrupt-cells" property      \ encode the cell#
f800 encode-int 0 encode-int+ 0 encode-int+     \ encode the bit mask for config addr (Dev only)
7 encode-int+ s" interrupt-map-mask" property   \ encode IRQ#=7 and generate property
;
: encode-mem32-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 02000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-pmem32-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 42000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-mem64-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 03000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ BAR-Len = 8 (64Bit)
;
: encode-pmem64-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 43000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ BAR-Len = 8 (64Bit)
;
: encode-rom-bar ( prop-addr prop-len configaddr -- prop-addr prop-len )
dup pci-bar-size-rom                            \ fetch raw BAR-size
dup IF                                          \ IF BAR is used
>r 02000000 or encode-int+              \ | save size and encode BAR addr
0 encode-64+                            \ | make mid and lo zero
r> encode-64+                           \ | calc and encode the size
ELSE                                            \ ELSE
2drop                                   \ | don't do anything
THEN                                            \ FI
;
: encode-io-bar ( prop-addr prop-len BAR-addr BAR-value -- prop-addr prop-len 4 )
dup pci-bar-size-io                     \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 01000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-bar ( prop-addr prop-len bar-addr -- prop-addr prop-len bar-len )
dup pci-bar-code@                               \ calc BAR type
CASE                                            \ CASE for the BAR types ( paddr plen baddr val )
0 OF drop 4             ENDOF           \ - not a valid type so do nothing
1 OF encode-io-bar      ENDOF           \ - IO-BAR
2 OF encode-mem32-bar   ENDOF           \ - MEM32
3 OF encode-pmem32-bar  ENDOF           \ - MEM32 prefetchable
4 OF encode-mem64-bar   ENDOF           \ - MEM64
5 OF encode-pmem64-bar  ENDOF           \ - MEM64 prefetchable
ENDCASE                                         \ ESAC ( paddr plen blen )
;
: pci-reg-props ( configaddr -- )
dup encode-int                  \ configuration space           ( caddr paddr plen )
0 encode-64+                    \ make the rest 0
0 encode-64+                    \ encode the size as 0
2 pick pci-htype@               \ fetch Header Type             ( caddr paddr plen type )
1 and IF                        \ IF Bridge                     ( caddr paddr plen )
18 10 DO                \ | loop over all BARs
2 pick i +      \ | calc bar-addr               ( caddr paddr plen baddr )
encode-bar      \ | encode this BAR             ( caddr paddr plen blen )
+LOOP              \ | increase LoopIndex by the BARlen
2 pick 38 +             \ | calc ROM-BAR for a bridge   ( caddr paddr plen baddr )
encode-rom-bar          \ | encode the ROM-BAR          ( caddr paddr plen )
ELSE                            \ ELSE ordinary device          ( caddr paddr plen )
28 10 DO                 \ | loop over all BARs
2 pick i +      \ | calc bar-addr               ( caddr paddr plen baddr )
encode-bar      \ | encode this BAR             ( caddr paddr plen blen )
+LOOP              \ | increase LoopIndex by the BARlen
2 pick 30 +             \ | calc ROM-BAR for a device   ( caddr paddr plen baddr )
encode-rom-bar          \ | encode the ROM-BAR          ( caddr paddr plen )
THEN                            \ FI                            ( caddr paddr plen )
s" reg" property                \ and store it into the property
drop
;
: pci-common-props ( addr -- )
dup pci-class-name device-name
dup pci-vendor@    encode-int s" vendor-id"      property
dup pci-device@    encode-int s" device-id"      property
dup pci-revision@  encode-int s" revision-id"    property
dup pci-class@     encode-int s" class-code"     property
3 encode-int s" #address-cells" property
2 encode-int s" #size-cells"    property
dup pci-config-ext? IF 1 encode-int s" ibm,pci-config-space-type" property THEN
dup pci-status@
dup 9 rshift 3 and encode-int s" devsel-speed" property
dup 7 rshift 1 and IF 0 0 s" fast-back-to-back" property THEN
dup 6 rshift 1 and IF 0 0 s" 66mhz-capable" property THEN
5 rshift 1 and IF 0 0 s" udf-supported" property THEN
dup pci-cache@     ?dup IF encode-int s" cache-line-size" property THEN
pci-interrupt@ ?dup IF encode-int s" interrupts"      property THEN
;
: pci-device-props ( addr -- )
dup pci-common-props
dup pci-min-grant@ encode-int s" min-grant"   property
dup pci-max-lat@   encode-int s" max-latency" property
dup pci-sub-device@ ?dup IF encode-int s" subsystem-id" property THEN
dup pci-sub-vendor@ ?dup IF encode-int s" subsystem-vendor-id" property THEN
dup pci-device-assigned-addresses-prop
pci-reg-props
pci-hotplug-enabled IF
dup dup pci-addr2bus 8 lshift
swap pci-addr2dev 3 lshift or
40000000 + encode-int s" ibm,my-drc-index" property
dup dup pci-addr2bus 20 *
swap pci-addr2dev +
a base !
s" Slot " rot $cathex
hex
encode-string s" ibm,loc-code" property
THEN
;
: pci-bridge-props ( addr -- )
dup pci-bus@
encode-int s" primary-bus" property
encode-int s" secondary-bus" property
encode-int s" subordinate-bus" property
dup pci-bus@ drop encode-int rot encode-int+ s" bus-range" property
pci-device-slots encode-int s" slot-names" property
dup pci-bridge-range-props
dup pci-bridge-assigned-addresses-prop
s" interrupt-map" get-node get-property IF
pci-bridge-interrupt-map
ELSE 2drop THEN
pci-reg-props
;
: pci-bridge-generic-setup ( addr -- )
pci-device-slots >r             \ save the slot array on return stack
dup pci-common-props            \ set the common properties before scanning the bus
s" pci" device-type             \ the type is allways "pci"
dup func-pci-bridge-probe       \ find all device connected to it
dup assign-all-bridge-bars      \ set up all memory access BARs
dup pci-set-irq-line            \ set the interrupt pin
dup pci-set-capabilities        \ set up the capabilities
pci-bridge-props            \ and generate all properties
r> TO pci-device-slots          \ and reset the slot array
;
DEFER func-pci-device-props
: pci-device-generic-setup ( config-addr -- )
dup assign-all-device-bars      \ calc all BARs
dup pci-set-irq-line            \ set the interrupt pin
dup pci-set-capabilities        \ set up the capabilities
dup func-pci-device-props       \ and generate all properties
drop                            \ forget the config-addr
;
' pci-device-props TO func-pci-device-props
' pci-bridge-range-props TO func-pci-bridge-range-props
: populate-pci-busses ( -- )
" /" find-device get-node child
BEGIN
dup 0 <>
WHILE
dup set-node
dup " name" rot get-package-property 0 = IF
drop dup from-cstring
2dup s" pci" strequal IF
s" pci-phb.fs" included
THEN
2drop
THEN
peer
REPEAT drop
device-end
;
populate-pci-busses
600 cp
: check-patch-kernel-sc1 ( -- )
ciregs >r4 @
dup 1000000 +
dup 2000000 < IF 0 ELSE dup 2000000 - THEN
swap
check-and-patch-sc1
;
' check-patch-kernel-sc1 add-quiesce-xt
' rtas-quiesce add-quiesce-xt
640 cp
690 cp
6a0 cp
6a8 cp
6b0 cp
6b8 cp
6c0 cp
: set-chosen-cpu
" /cpus" find-device
get-node child dup 0= ABORT" CPU not found"
node>path open-dev encode-int s" cpu" set-chosen
;
set-chosen-cpu
s" /memory@0" open-dev encode-int s" memory" set-chosen
6e0 cp
700 cp
s" /openprom" find-device
s" SLOF," slof-build-id here swap rmove here slof-build-id nip $cat encode-string s" model" property
0 0 s" relative-addressing" property
device-end
s" /aliases" find-device
: open  true ;
: close ;
device-end
s" /mmu" open-dev encode-int s" mmu" set-chosen
VARIABLE chosen-memory-ih 0 chosen-memory-ih !
: (chosen-memory-ph) ( -- phandle )
chosen-memory-ih @ ?dup 0= IF
s" memory" get-chosen IF
decode-int nip nip dup chosen-memory-ih !
ihandle>phandle
ELSE 0 THEN
ELSE ihandle>phandle THEN
;
: (set-available-prop) ( prop plen -- )
s" available"
(chosen-memory-ph) ?dup 0<> IF set-property ELSE
cr ." Can't find chosen memory node - "
." no available property created" cr
2dup 2dup
THEN
;
: update-available-property ( available-ptr -- )
dup >r available>size@
0= r@ available AVAILABLE-SIZE /available * + >= or IF
available r> available - encode-bytes (set-available-prop)
ELSE
r> /available + RECURSE
THEN
;
: update-available-property available update-available-property ;
: claim ( [ addr ] len align -- base ) claim update-available-property ;
: release ( addr len -- ) release update-available-property ;
update-available-property
: input  ( dev-str dev-len -- )
open-dev ?dup IF
s" stdin" get-chosen IF
decode-int nip nip ?dup IF close-dev THEN
THEN
encode-int s" stdin"  set-chosen
THEN
;
: output  ( dev-str dev-len -- )
open-dev ?dup IF
s" stdout" get-chosen IF
decode-int nip nip ?dup IF close-dev THEN
THEN
encode-int s" stdout" set-chosen
THEN
;
: io  ( dev-str dev-len -- )
2dup input output
;
1 BUFFER: (term-io-char-buf)
: term-io-key  ( -- char )
s" stdin" get-chosen IF
decode-int nip nip dup 0= IF 0 EXIT THEN
>r BEGIN
(term-io-char-buf) 1 s" read" r@ $call-method
0 >
UNTIL
(term-io-char-buf) c@
r> drop
ELSE
[ ' key behavior compile, ]
THEN
;
' term-io-key to key
: term-io-key?  ( -- true|false )
s" stdin" get-chosen IF
decode-int nip nip dup 0= IF drop 0 EXIT THEN \ return false and exit if no stdin set
>r \ store ihandle on return stack
s" device_type" r@ ihandle>phandle ( propstr len phandle )
get-property ( true | data dlen false )
IF
false
ELSE
1 - \ remove 1 from length to ignore null-termination char
2dup s" serial" str= IF
2drop serial-key? r> drop EXIT
THEN \ call serial-key, cleanup return-stack, exit
2dup s" keyboard" str= IF 
2drop ( )
s" key-available?" r@ ihandle>phandle find-method IF 
drop s" key-available?" r@ $call-method  
ELSE 
false 
THEN
r> drop EXIT \ cleanup return-stack, exit
THEN
2drop r> drop false EXIT \ unknown device_type cleanup return-stack, return false
THEN
ELSE
false
THEN
;
' term-io-key? to key?
800 cp
51 CONSTANT nvram-partition-type-cpulog
60 CONSTANT nvram-partition-type-sas
61 CONSTANT nvram-partition-type-sms
6e CONSTANT nvram-partition-type-debug
6f CONSTANT nvram-partition-type-history
70 CONSTANT nvram-partition-type-common
7f CONSTANT nvram-partition-type-freespace
a0 CONSTANT nvram-partition-type-linux
: rztype ( str len -- ) \ stop at zero byte, read with nvram-c@
0 DO
dup i + nvram-c@ ?dup IF ( str char )
emit
ELSE                     ( str )
drop UNLOOP EXIT
THEN
LOOP
;
create tmpStr 500 allot
: rzcount ( zstr -- str len )
dup tmpStr >r BEGIN
dup nvram-c@ dup r> dup 1+ >r c!
WHILE
char+
REPEAT
r> drop over - swap drop tmpStr swap
;
: calc-header-cksum ( offset -- cksum )
dup nvram-c@
10 2 DO
over I + nvram-c@ +
LOOP
wbsplit + nip
;
: bad-header? ( offset -- flag )
dup 2+ nvram-w@        ( offset length )
0= IF                  ( offset )
drop true EXIT      ( )
THEN
dup calc-header-cksum  ( offset checksum' )
swap 1+ nvram-c@       ( checksum ' checksum )
<>                     ( flag )
;
: .header ( offset -- )
cr                         ( offset )
dup bad-header? IF         ( offset )
."   BAD HEADER -- trying to print it anyway" cr
THEN
space                      ( offset )
dup nvram-c@ 2 0.r         ( offset )
space space                ( offset )
dup 2+ nvram-w@ 10 * 5 .r  ( offset )
space space                ( offset )
4 + 0c rztype              ( )
;
: .headers ( -- )
cr cr ." Type  Size  Name"
cr ." ========================"
0 BEGIN                      ( offset )
dup nvram-c@              ( offset type )
WHILE
dup .header               ( offset )
dup 2+ nvram-w@ 10 * +    ( offset offset' )
dup nvram-size < IF       ( offset )
ELSE
drop EXIT              ( )
THEN
REPEAT
drop                         ( )
cr cr
;
: reset-nvram ( -- )
internal-reset-nvram
;
: dump-partition     ['] nvram-c@      1 (dump) ;
: type-no-zero ( addr len -- )
0 DO
dup I + dup nvram-c@ 0= IF drop ELSE nvram-c@ emit THEN
LOOP
drop
;
: type-no-zero-part ( from-str cnt-str addr len )
0 DO
dup i + dup nvram-c@ 0= IF
drop
ELSE
3 pick 0= 3 pick 0 > AND IF
dup 1 type-no-zero
THEN
nvram-c@ a = IF
2 pick 0= IF
over 1- 0 max
rot drop swap
THEN
2 pick 1- 0 max
3 roll drop rot rot
THEN
THEN
LOOP
drop
;
: (dmesg-prepare) ( base-addr -- base-addr' addr len act-off )
10 - \ go back to header
dup 14 + nvram-l@ dup >r
( base-addr act-off ) ( R: act-off )
over over over + swap 10 + nvram-w@ + >r
( base-addr act-off ) ( R:  act-off nvram-act-addr )
over 2 + nvram-w@ 10 * swap - over swap
( base-addr base-addr start-size ) ( R:  act-off nvram-act-addr )
r> swap rot 10 + nvram-w@ - r>
;
: .dmesg ( base-addr -- )
(dmesg-prepare) >r
cr type-no-zero
( base-addr ) ( R: act-off )
dup 10 + nvram-w@ + r> type-no-zero
;
: .dmesg-part ( from-str cnt-str base-addr -- )
(dmesg-prepare) >r
>r >r -rot r> r>
cr type-no-zero-part rot
( base-addr ) ( R: act-off )
dup 10 + nvram-w@ + r> type-no-zero-part
;
: dmesg-part ( from-str cnt-str -- left-from-str left-cnt-str )
2dup
s" ibm,CPU0log" get-named-nvram-partition IF
2drop EXIT
THEN
drop .dmesg-part nip nip
;
: dmesg2 ( -- )
s" ibm,CPU1log" get-named-nvram-partition IF
." No log partition." cr EXIT
THEN
drop .dmesg
;
: dmesg ( -- )
s" ibm,CPU0log" get-named-nvram-partition IF
." No log partition." cr EXIT
THEN
drop .dmesg
;
880 cp
wordlist CONSTANT envvars
: listenv  ( -- )
get-current envvars set-current  words  set-current
;
: create-env ( "name" -- )
get-current  envvars set-current  CREATE  set-current
;
: env-int     ( n -- )  1 c, align , DOES> char+ aligned @ ;
: env-bytes   ( a len -- )
2 c, align dup , here swap dup allot move
DOES> char+ aligned dup @ >r cell+ r>
;
: env-string  ( str len -- )  3 c, align dup , here over allot swap move DOES> char+ aligned dup @ >r cell+ r> ;
: env-flag    ( f -- )  4 c, c, DOES> char+ c@ 0<> ;
: env-secmode ( sm -- )  5 c, c, DOES> char+ c@ ;
: default-int     ( n "name" -- )      create-env env-int ;
: default-bytes   ( a len "name" -- )  create-env env-bytes ;
: default-string  ( a len "name" -- )  create-env env-string ;
: default-flag    ( f "name" -- )      create-env env-flag ;
: default-secmode ( sm "name" -- )     create-env env-secmode ;
: set-option ( option-name len option len -- )
2swap encode-string
2swap s" /options" find-node dup IF set-property ELSE drop 2drop 2drop THEN
;
: findenv ( name len -- adr def-adr type | 0 )
2dup envvars voc-find dup 0<> IF ( ABORT" not a configuration variable" )
link> >body char+ >r (find-order) link> >body dup char+ swap c@ r> swap
ELSE
nip nip
THEN
;
: test-flag ( param len -- true | false )
2dup s" true" string=ci -rot s" false" string=ci or
;
: test-secmode ( param len -- true | false )
2dup s" none" string=ci -rot 2dup s" command" string=ci -rot s" full"
string=ci or or
;
: test-int ( param len -- true | false )
$dh-number IF false ELSE drop true THEN
;
: findtype ( param len name len -- param len name len type )
2dup findenv                         \ try to find type of envvar
dup IF                               \ found a type?
nip nip
EXIT
THEN
drop 2swap
2dup test-flag IF
4 -rot                         \ boolean type
ELSE
2dup test-secmode IF
5 -rot                      \ secmode type
ELSE
2dup test-int IF
1 -rot                   \ integer type
ELSE
2dup test-string
IF 3 ELSE 2 THEN         \ 3 = string, 2 = default to bytes
-rot
THEN
THEN
THEN
rot
>r 2swap r>
;
: $setenv ( param len name len -- )
4dup set-option
findtype
-rot $CREATE
CASE
1 OF $dh-number IF 0 THEN env-int ENDOF \ XXX: wants decimal and 0x...
2 OF env-bytes ENDOF
3 OF env-string ENDOF
4 OF evaluate env-flag ENDOF
5 OF evaluate env-secmode ENDOF \ XXX: recognize none, command, full
ENDCASE
;
: (printenv) ( adr type -- )
CASE
1 OF aligned @ . ENDOF
2 OF aligned dup cell+ swap @ swap . . ENDOF
3 OF aligned dup @ >r cell+ r> type ENDOF
4 OF c@ IF ." true" ELSE ." false" THEN ENDOF
5 OF c@ . ENDOF \ XXX: print symbolically
ENDCASE
;
: .printenv-header ( -- )
cr
s" ---environment variable--------current value-------------default value------"
type cr
;
DEFER old-emit
0 VALUE emit-counter
: emit-and-count emit-counter 1 + to emit-counter old-emit ;
: .enable-emit-counter
0 to emit-counter
['] emit behavior to old-emit
['] emit-and-count to emit
;
: .disable-emit-counter
['] old-emit behavior to emit
;
: .spaces ( number-of-spaces -- )
dup 0 > IF
spaces
ELSE
drop space
THEN
;
: .print-one-env ( name len -- )
3 .spaces
2dup dup -rot type 1c swap - .spaces
findenv rot over
.enable-emit-counter
(printenv) .disable-emit-counter
1a emit-counter - .spaces
(printenv)
;
: .print-all-env
.printenv-header
envvars cell+
BEGIN
@ dup
WHILE
dup link> >name
name>string .print-one-env cr
REPEAT
drop
;
: printenv
parse-word dup 0= IF
2drop .print-all-env
ELSE
findenv dup 0= ABORT" not a configuration variable"
rot over cr ." Current: " (printenv)
cr ." Default: " (printenv)
THEN
;
: (set-default)  ( def-xt -- )
dup >name name>string $CREATE dup >body c@ >r execute r> CASE
1 OF env-int ENDOF
2 OF env-bytes ENDOF
3 OF env-string ENDOF
4 OF env-flag ENDOF
5 OF env-secmode ENDOF ENDCASE
;
true default-flag auto-boot?
s" " default-string boot-device
s" " default-string boot-file
s" boot" default-string boot-command
s" " default-string diag-device
s" " default-string diag-file
false default-flag diag-switch?
true default-flag fcode-debug?
s" " default-string input-device
s" " default-string nvramrc
s" " default-string oem-banner
false default-flag oem-banner?
0 0 default-bytes oem-logo
false default-flag oem-logo?
s" " default-string output-device
200 default-int screen-#columns
200 default-int screen-#rows
0 default-int security-#badlogins
0 default-secmode security-mode
s" " default-string security-password
0 default-int selftest-#megs
false default-flag use-nvramrc?
false default-flag direct-serial?
true default-flag real-mode?
default-load-base default-int load-base
VARIABLE nvoff \ offset in envvar partition
: (nvupdate-one) ( adr type -- "value" )
CASE
1 OF aligned @ (.d) ENDOF
2 OF drop 0 0 ENDOF
3 OF aligned dup @ >r cell+ r> ENDOF
4 OF c@ IF s" true" ELSE s" false" THEN ENDOF
5 OF c@ (.) ENDOF \ XXX: print symbolically
ENDCASE
;
: nvupdate-one   ( def-xt -- )
>r nvram-partition-type-common get-nvram-partition       ( part.addr part.len FALSE|TRUE R: def-xt )
ABORT" No valid NVRAM." r>      ( part.addr part.len def-xt )
>name name>string               ( part.addr part.len var.a var.l )
2dup findenv nip (nvupdate-one)
internal-add-env
drop
;
: (nvupdate) ( -- )
nvram-partition-type-common get-nvram-partition ABORT" No valid NVRAM."
erase-nvram-partition drop
envvars cell+
BEGIN @ dup WHILE dup link> nvupdate-one REPEAT
drop
;
: nvupdate ( -- )
." nvupdate is obsolete." cr
;
: set-default
parse-word envvars voc-find
dup 0= ABORT" not a configuration variable" link> (set-default)
;
: (set-defaults)
envvars cell+
BEGIN @ dup WHILE dup link> (set-default) REPEAT
drop
;
(set-defaults)
: set-defaults
(set-defaults) (nvupdate)
;
: setenv  parse-word ( skipws ) 0d parse -leading 2swap $setenv (nvupdate) ;
: get-nv  ( -- )
nvram-partition-type-common get-nvram-partition ( addr offset not-found | not-found ) \ find partition header
IF
." No NVRAM common partition, re-initializing..." cr
internal-reset-nvram
(nvupdate)
nvram-partition-type-common get-nvram-partition IF ." NVRAM seems to be broken." cr EXIT THEN
THEN
drop ( addr )           \ throw away offset
BEGIN
dup rzcount  dup     \ make string from offset and make condition
WHILE                   ( offset offset length )
2dup [char] = split  \ Split string at equal sign (=)
2swap                ( offset offset length param len name len )
$setenv              \ Set envvar
nip                  \ throw away old string begin
+ 1+                 \ calc new offset
REPEAT
2drop drop              \ cleanup
;
get-nv
: check-for-nvramrc  ( -- )
use-nvramrc?  IF
s" Executing following code from nvramrc: "
s" nvramrc" evaluate $cat
nvramlog-write-string-cr
s" (!) Executing code specified in nvramrc" type
cr s"  SLOF Setup = " type
.enable-emit-counter
s" nvramrc" evaluate ['] evaluate  CATCH  IF
2drop
emit-counter 0  DO  8 emit  LOOP
s" (!) Code in nvramrc triggered exception. "
2dup nvramlog-write-string
type cr 12 spaces s" Aborting nvramrc execution" 2dup
nvramlog-write-string-cr type cr
s"  SLOF Setup = " type
THEN
.disable-emit-counter
THEN
;
: (nv-findalias) ( alias-ptr alias-len -- pos )
here 0
s" devalias " string-cat
3 pick 3 pick string-cat
s"  " string-cat
s" nvramrc" evaluate
2swap find-substr
nip nip
;
: (nv-build-real-entry) ( name-ptr name-len dev-ptr dev-len -- str-ptr str-len )
2swap here 0
s" devalias " string-cat
2swap string-cat
s"  " string-cat
2swap string-cat
0d char-cat
0a char-cat
;
: (nv-build-null-entry) ( name-ptr name-len dev-ptr dev-len -- str-ptr str-len )
4drop here 0
;
: (nv-build-nvramrc) ( name-str name-len dev-str dev-len xt-build-entry -- )
4 pick 4 pick (nv-findalias)
dup s" nvramrc" evaluate nip >= IF
drop execute
s" nvramrc" evaluate string-cat
dup allot
s" nvramrc" $setenv
ELSE  \ if our alias is still defined in nvramrc
5 pick 5 pick 5 pick 5 pick 5 pick execute nip over +
s" nvramrc" evaluate 3 pick string-at
2dup find-nextline string-at nip +
alloc-mem 0
s" nvramrc" evaluate drop 3 pick string-cat
rot >r >r >r execute r> r> 2swap string-cat
( mem, len ) ( R: alias-pos )
s" nvramrc" evaluate r> string-at
2dup find-nextline string-at string-cat
2dup s" nvramrc" $setenv free-mem
THEN
;
: $nvalias ( name-str name-len dev-str dev-len -- )
4dup ['] (nv-build-real-entry) (nv-build-nvramrc)
set-alias
s" true" s" use-nvramrc?" $setenv
(nvupdate)
;
: nvalias ( "alias-name< >device-specifier<eol>" -- )
parse-word parse-word dup 0<> IF
$nvalias
ELSE
2drop 2drop
cr
"    Usage: nvalias (""alias-name< >device-specifier<eol>"" -- )" type
cr
THEN    
;
: $nvunalias ( name-str name-len -- )
s" " ['] (nv-build-null-entry) (nv-build-nvramrc)
(nvupdate)
;
: nvunalias ( "alias-name< >" -- )
parse-word $nvunalias
;
: diagnostic-mode? ( -- diag-switch? ) diag-switch? ;
check-for-nvramrc
890 cp
defer set-boot-device
defer add-boot-device
8 CONSTANT MAX-ALIAS
: add-boot-aliases ( str -- )
2dup add-boot-device               ( $str )
MAX-ALIAS 1 DO
2dup i $cathex 2dup              ( $str $strN $strN )
find-alias 0 > IF                ( $str $strN false | $result )
drop strdup add-boot-device  ( $str )
ELSE 2drop THEN
LOOP
2drop
;
: qemu-read-bootlist ( -- )
" qemu,boot-list" get-chosen IF
s" boot-device" $setenv
EXIT
THEN
0 0 set-boot-device
" qemu,boot-device" get-chosen not IF
" boot-device" evaluate swap drop 0= IF
" disk" add-boot-aliases
" cdrom" add-boot-aliases
" net" add-boot-aliases
THEN
EXIT
THEN
0 ?DO
dup i + c@ CASE
0        OF ENDOF
[char] a OF ENDOF
[char] b OF ENDOF
[char] c OF " disk"  add-boot-aliases ENDOF
[char] d OF " cdrom" add-boot-aliases ENDOF
[char] n OF " net"   add-boot-aliases ENDOF
ENDCASE cr
LOOP
drop
;
' qemu-read-bootlist to read-bootlist
8a0 cp
0 VALUE debug-client-interface?
VOCABULARY client-voc \ We store all client-interface callable words here.
6789  CONSTANT  sc-exit
4711  CONSTANT  sc-yield
VARIABLE  client-callback \ Address of client's callback function
: client-data  ciregs >r3 @ ;
: nargs  client-data la1+ l@ ;
: nrets  client-data la1+ la1+ l@ ;
: client-data-to-stack
client-data 3 la+ nargs 0 ?DO dup l@ swap la1+ LOOP drop ;
: stack-to-client-data
client-data nargs nrets + 2 + la+ nrets 0 ?DO tuck l! /l - LOOP drop ;
: call-client ( args len client-entry -- )
>r  ciregs >r7 !  ciregs >r6 !  client-entry-point @ ciregs >r5 !
cistack ciregs >r1 !
r> jump-client drop
BEGIN
client-data-to-stack
client-data l@ zcount
ALSO client-voc $find PREVIOUS
dup 0= >r IF 
CATCH
?dup IF
dup CASE
sc-exit OF drop r> drop EXIT ENDOF
sc-yield OF drop r> drop EXIT ENDOF
ENDCASE
THROW
THEN
stack-to-client-data
ELSE
cr type ."  NOT FOUND"
THEN
r> ciregs >r3 !  ciregs >r4 @ jump-client 
UNTIL ;
: flip-stack ( a1 ... an n -- an ... a1 )  ?dup IF 1 ?DO i roll LOOP THEN ;
: (callback) ( "service-name<>" "arguments<cr>" -- )
client-callback @  \ client-callback points to the function prolog
dup 8 + @ ciregs >r2 !  \ Set up the TOC pointer (???)
@ call-client ;  \ Resolve the function's address from the prolog
' (callback) to callback
: (continue-client)
s" "  \ make call-client happy, client won't use the string anyways.
ciregs >r4 @ call-client ;
' (continue-client) to continue-client
: string-to-buffer ( str len buf len -- len' )
2dup erase rot min dup >r move r> ;
ALSO client-voc DEFINITIONS
: exit  sc-exit THROW ;
: yield  sc-yield THROW ;
: test ( zstr -- missing? )
zcount
debug-client-interface? IF
." ci: test " 2dup type cr
THEN
ALSO client-voc $find PREVIOUS IF
drop FALSE
ELSE
2drop TRUE
THEN 
;
: finddevice ( zstr -- phandle )
zcount
debug-client-interface? IF
." ci: finddevice " 2dup type cr
THEN
2dup " /memory" str= IF
2drop
" /memory@0"
THEN
find-node dup 0= IF drop -1 THEN
;
: getprop ( phandle zstr buf len -- len' )
>r >r zcount rot                     ( str-adr str-len phandle   R: len buf )
debug-client-interface? IF
." ci: getprop " 3dup . ." '" type ." '"
THEN
get-property
debug-client-interface? IF
dup IF ."  ** not found **" THEN
cr
THEN
0= IF
r> swap dup r> min swap >r move r>
ELSE
r> r> 2drop -1
THEN
;
: getproplen ( phandle zstr -- len )
zcount rot get-property 0= IF nip ELSE -1 THEN ;
: setprop ( phandle zstr buf len -- size|-1 )
dup >r            \ save len
encode-bytes      ( phandle zstr prop-addr prop-len )
2swap zcount rot  ( prop-addr prop-len name-addr name-len phandle )
current-node @ >r \ save current node
set-node          \ change to specified node
property          \ set property
r> set-node       \ restore original node
r>                \ always return size, because we can not fail.
;
: canon ( zstr buf len -- len' )
2dup erase
>r >r zcount
>r dup c@ [char] / = IF
r> r> swap r> over >r min move r>
ELSE
r> find-alias ?dup 0= IF
r> r> 2drop -1
ELSE
dup -rot r> swap r> min move
THEN
THEN
;
: nextprop ( phandle zstr buf -- flag ) \ -1 invalid, 0 end, 1 ok
>r zcount rot next-property IF r> zplace 1 ELSE r> drop 0 THEN ; 
: open ( zstr -- ihandle )
zcount
debug-client-interface? IF
." ci: open " 2dup type cr
THEN
open-dev
;
: close ( ihandle -- )
debug-client-interface? IF
." ci: close " dup . cr
THEN
s" stdin" get-chosen IF
decode-int nip nip over = IF
close-dev
quiesce
ELSE
close-dev
THEN
ELSE
close-dev
THEN
;
: write ( ihandle str len -- len' )      rot s" write" rot
['] $call-method CATCH IF 2drop 3drop -1 THEN ;
: read  ( ihandle str len -- len' )      rot s" read"  rot
['] $call-method CATCH IF 2drop 3drop -1 THEN ;
: seek  ( ihandle hi lo -- status  ) swap rot s" seek" rot
['] $call-method CATCH IF 2drop 3drop -1 THEN ;
: claim  ( addr len align -- base )
debug-client-interface? IF
." ci: claim " .s cr
THEN
dup  IF  rot drop
['] claim CATCH  IF  2drop -1  THEN
ELSE
['] claim CATCH  IF  3drop -1  THEN
THEN
;
: release ( addr len -- )
debug-client-interface? IF
." ci: release " .s cr
THEN
release
;
: instance-to-package ( ihandle -- phandle )
ihandle>phandle ;
: package-to-path ( phandle buf len -- len' )
2>r node>path 2r> string-to-buffer ;
: instance-to-path ( ihandle buf len -- len' )
2>r instance>path 2r> string-to-buffer ;
: instance-to-interposed-path ( ihandle buf len -- len' )
2>r instance>qpath 2r> string-to-buffer ;
: call-method ( str ihandle arg ... arg -- result return ... return )
nargs flip-stack zcount
debug-client-interface? IF
." ci: call-method " 2dup type cr
THEN
rot ['] $call-method CATCH
nrets 0= IF drop ELSE \ if called with 0 return args do not return the catch result
dup IF nrets 1 ?DO -444 LOOP THEN
nrets flip-stack 
THEN
;
: test-method ( phandle str -- missing? )
zcount
debug-client-interface? IF
." ci: test-method " 2dup type cr
THEN
rot find-method dup IF nip THEN 0=
;
: milliseconds  milliseconds ;
: start-cpu ( phandle addr r3 -- )
>r >r 
s" reg" rot get-property 0= IF drop l@ 
ELSE true ABORT" start-cpu called with invalid phandle" THEN 
r> r> of-start-cpu drop
;
: quiesce  ( -- )
debug-client-interface? IF
." ci: quiesce" cr
THEN
quiesce
;
: boot  ( zstr -- )
zcount
debug-client-interface? IF
." ci: boot " 2dup type cr
THEN
" boot " 2swap $cat " boot-command" $setenv (nvupdate)
reset-all
;
: interpret ( ... zstr -- result ... )
zcount
debug-client-interface? IF
." ci: interpret " 2dup type cr
THEN
['] evaluate CATCH
;
: set-callback ( newfunc -- oldfunc )
client-callback @ swap client-callback ! ;
PREVIOUS DEFINITIONS
false value elf-claim?
0     value last-claim
0 VALUE cur-brk
: elf-claim-segment ( addr size -- errorcode )
2dup
elf-claim? IF
>r
here last-claim , to last-claim                \ Setup ptr to last claim
dup , r> dup , ( addr size )
0 ['] claim CATCH IF
." Memory for ELF file is already in use!" cr
true ABORT" Memory for ELF file already in use "
THEN
drop
ELSE
2drop
THEN
+ to cur-brk
0 
;
: elf-load-claim ( file-addr destaddr -- claim-list entry imagetype )
true to elf-claim?
0 to last-claim
dup -1 = IF             \ If destaddr == -1 then load to addr from ELF header
drop ['] elf-load-file CATCH IF false to elf-claim? ABORT THEN
ELSE
['] elf-load-file-to-addr CATCH IF false to elf-claim? ABORT THEN
THEN
>r
last-claim swap
false to elf-claim?
r>
;
: elf-release ( claim-list -- )
BEGIN
dup cell+                   ( claim-list claim-list-addr )
dup @ swap cell+ @          ( claim-list claim-list-addr claim-list-sz )
release                     ( claim-list )
@ dup 0=                    ( Next-element )
UNTIL
drop
;
CREATE bootdevice 2 cells allot bootdevice 2 cells erase
CREATE bootargs 2 cells allot bootargs 2 cells erase
CREATE load-list 2 cells allot load-list 2 cells erase
: start-elf ( arg len entry -- )
msr@ 7fffffffffffffff and 2000 or ciregs >srr1 ! call-client
;
: start-elf64 ( arg len entry r2 -- )
msr@ 2000 or ciregs >srr1 !
ciregs >r2  !
call-client \ entry point is pointer to .opd
;
: set-bootpath
s" disk" find-alias
dup IF ELSE drop s" boot-device" evaluate find-alias THEN
dup IF strdup ELSE 0 THEN
encode-string s" bootpath" set-chosen
;
: set-netbootpath
s" net" find-alias
?dup IF strdup encode-string s" bootpath" set-chosen THEN
;
: set-bootargs
skipws 0 parse dup 0= IF
2drop s" boot-file" evaluate
THEN
encode-string s" bootargs" set-chosen
;
: .(client-exec) ( arg len -- rc )
s" snk" romfs-lookup 0<> IF
paflof-start f00000 +
elf-load-file-to-addr drop \ FIXME - check this for LE, currently its BE only
dup @ swap 8 + @         \ populate entry r2
start-elf64 client-data
ELSE
2drop false
THEN
;
' .(client-exec) to (client-exec)
: .client-exec ( arg len -- rc ) set-bootargs (client-exec) ;
' .client-exec to client-exec
: netsave  ( "addr len {filename}[,params]" -- rc )
(parse-line) dup 0> IF
s" netsave " 2swap $cat set-netbootpath client-exec
ELSE
cr
." Usage: netsave addr len [bootp|dhcp,]filename[,siaddr][,ciaddr][,giaddr][,bootp-retries][,tftp-retries][,use_ci]"
cr 2drop
THEN
;
: ping  ( "{device-path:[device-args,]server-ip,[client-ip[\nn]],[gateway-ip][,timeout]}" -- )
my-self >r current-node @ >r  \ Save my-self
(parse-line) open-dev dup  IF
dup to my-self dup ihandle>phandle set-node
dup
s" ping" rot ['] $call-method CATCH  IF
cr
." Not a pingable device"
cr 3drop
THEN
swap close-dev
ELSE
cr
." Usage: ping device-path:[device-args,]server-ip,[client-ip[\nn]],[gateway-ip][,timeout]"
cr drop
THEN
r> set-node r> to my-self  \ Restore my-self
;
8a8 cp
CREATE version-str 10 ALLOT
0 value temp-ptr
: dump-display-write
s" screen" find-alias  IF
drop terminal-write drop
ELSE
s" vsterm" find-alias  IF
drop type
THEN
THEN
;
: dump-display-buffer
disp-ptr to temp-ptr
" SLOF **********************************************************************" dump-display-write
cr
version-str get-print-version
version-str @                   \ start
version-str 8 + @               \ end
over - dump-display-write
" Press 's' to enter Open Firmware." dump-display-write
cr cr
temp-ptr disp-size > IF
temp-ptr disp-size MOD
dup
prevga-disp-buf + swap disp-size swap - dump-display-write
temp-ptr disp-size MOD
prevga-disp-buf swap 1 - dump-display-write
ELSE
prevga-disp-buf temp-ptr dump-display-write
THEN
;
: enable-framebuffer-output  ( -- )
s" screen" find-alias ?dup  IF
open-dev close-node
false to store-prevga?
s" display-emit" $find  IF
to emit
dump-display-buffer
ELSE
2drop
THEN
THEN
;
enable-framebuffer-output
8b0 cp
usb-scan
8c0 cp
romfs-base 400000 0 ' claim CATCH IF ." claim failed!" cr 2drop THEN drop
8d0 cp
: set-default-console
s" linux,stdout-path" get-chosen IF
decode-string
." Using default console: " 2dup type cr
io
2drop
ELSE
." No console specified "
" screen" find-alias dup IF nip THEN
" keyboard" find-alias dup IF nip THEN
AND IF
." using screen & keyboard" cr
" screen" output
" keyboard" input
ELSE
" hvterm" find-alias IF
drop
." using hvterm" cr
" hvterm" io
ELSE
" vsterm" find-alias IF
drop
." using vsterm" cr
" vsterm" io
false to store-prevga?
dump-display-buffer
ELSE
" /openprom" find-node ?dup IF
set-node
." and no default found, creating dev-null" cr
" dev-null.fs" included
" devnull-console" io
0 set-node
THEN
THEN
THEN
THEN
THEN
;
set-default-console
8e0 cp
0 VALUE direct-ram-boot-base
0 VALUE direct-ram-boot-size
: (boot-ram)
direct-ram-boot-size 0<> IF
." Booting from memory..." cr
s" go-args 2@ " evaluate
direct-ram-boot-base 0
s" true state-valid ! " evaluate
s" disable-watchdog go-64" evaluate
THEN
;
8e8 cp
: check-boot-from-ram
s" qemu,boot-kernel" get-chosen IF
decode-int -rot decode-int -rot ( n1 n2 p s )
decode-int -rot decode-int -rot ( n1 n2 n3 n4 p s )
2drop
swap 20 << or to direct-ram-boot-size
swap 20 << or to direct-ram-boot-base
." Detected RAM kernel at " direct-ram-boot-base .
." (" direct-ram-boot-size . ." bytes) "
s" boot-command" $create " (boot-ram)" env-string
THEN
;
check-boot-from-ram
8ff cp
: (boot) ( -- )
s" Executing following boot-command: "
boot-command $cat nvramlog-write-string-cr
s" boot-command" evaluate      \ get boot command
['] evaluate catch ?dup IF     \ and execute it
." boot attempt returned: "
abort"-str @ count type cr
nip nip                     \ drop string from 1st evaluate
throw
THEN
;
: (function-key) ( -- n )
key? IF
key CASE
50  OF 1 ENDOF
7e  OF 1 ENDOF
dup OF 0 ENDOF
ENDCASE
THEN
;
: (esc-sequence) ( -- n )
key? IF
key CASE
4f  OF (function-key) ENDOF
5b  OF
key key (function-key) ENDOF
dup OF 0 ENDOF
ENDCASE
THEN
;
: (s-pressed) ( -- )
s" An 's' has been pressed. Entering Open Firmware Prompt"
nvramlog-write-string-cr
;
: (boot?) ( -- )
of-prompt? not auto-boot? and IF
(boot)
THEN
;
TRUE VALUE use-load-watchdog?
1 value my-boot-dev
1 value digit-val
0 value boot-dev-no
: boot-selected
1 to my-boot-dev
BEGIN parse-word dup WHILE
boot-dev-no my-boot-dev = IF
s" boot " 2swap $cat
['] evaluate catch ?dup IF     \ and execute it
." boot attempt returned: "
abort"-str @ count type cr
throw
THEN
0 0 load-list 2!
UNLOOP EXIT
ELSE
2drop
THEN
my-boot-dev 1 + to my-boot-dev
REPEAT 2drop 0 0 load-list 2!
(boot)
;
: boot-start
decimal
BEGIN parse-word dup WHILE
my-boot-dev (u.) s" . " $cat type 2dup type ." : " de-alias type cr
my-boot-dev 1 + to my-boot-dev
REPEAT 2drop 0 0 load-list 2!
BEGIN key? WHILE
key drop
REPEAT
cr
BEGIN
KEY
dup 1b = IF         \ ESC sequence ... could be yet another F12 key press
BEGIN key? WHILE
key drop
REPEAT
ELSE
dup emit
THEN
dup isdigit IF
dup 30 - to digit-val
boot-dev-no a * digit-val + to boot-dev-no
THEN
d = UNTIL
boot-dev-no my-boot-dev < IF
s" boot-selected " s" $bootdev" evaluate $cat strdup evaluate
ELSE
." Invalid choice!" cr
THEN
hex
;
: boot-menu-start
." Select boot device:" cr cr
s" boot-start " s" $bootdev" evaluate $cat strdup evaluate
;
: boot-menu-enabled? ( -- true|false )
s" qemu,boot-menu" get-chosen IF
decode-int 1 = IF
2drop TRUE EXIT
THEN
2drop
THEN
FALSE
;
: f12-pressed?
34 = >r 32 = r> and IF
TRUE
ELSE
FALSE
THEN
;
: start-it ( -- )
key? IF
key CASE
[char] s  OF (s-pressed) ENDOF
1b        OF
(esc-sequence) CASE
1   OF
console-clean-fifo
f12-pressed? boot-menu-enabled? and IF
boot-menu-start
ELSE
(boot?)
THEN
ENDOF
dup OF (boot?) ENDOF
ENDCASE
ENDOF
dup OF (boot?) ENDOF
ENDCASE
ELSE
(boot?)
THEN
disable-watchdog  FALSE to use-load-watchdog?
.banner
;
."      "   \ Clear last checkpoint
0 VALUE load-size
0 VALUE go-entry
VARIABLE state-valid false state-valid !
CREATE go-args 2 cells allot go-args 2 cells erase
: $bootargs
bootargs 2@ ?dup IF
ELSE s" diagnostic-mode?" evaluate and IF s" diag-file" evaluate
ELSE s" boot-file" evaluate THEN THEN
;
: $bootdev ( -- device-name len )
bootdevice 2@ dup IF s"  " $cat THEN
s" diagnostic-mode?" evaluate IF
s" diag-device" evaluate
ELSE
s" boot-device" evaluate
THEN
$cat \ prepend bootdevice setting from vpd-bootlist
strdup
?dup 0= IF
disable-watchdog
drop true ABORT" No boot device!"
THEN
;
: set-boot-args ( str len -- ) dup IF strdup ELSE nip dup THEN bootargs 2! ;
: (set-boot-device) ( str len -- )
?dup IF 1+ strdup 1- ELSE drop 0 0 THEN bootdevice 2!
;
' (set-boot-device) to set-boot-device
: (add-boot-device) ( str len -- )	\ Concatenate " str" to "bootdevice"
bootdevice 2@ ?dup IF $cat-space ELSE drop THEN set-boot-device
;
' (add-boot-device) to add-boot-device
0 value claim-list
: no-go ( -- ) -64 boot-exception-handler ABORT ;
defer go ( -- )
: go-32 ( -- )
state-valid @ IF
0 ciregs >r3 ! 0 ciregs >r4 !
go-args 2@ go-entry start-elf client-data
claim-list elf-release 0 to claim-list
THEN
-6d boot-exception-handler ABORT
;
: go-64 ( args len entry r2 -- )
0 ciregs >r3 ! 0 ciregs >r4 !
start-elf64 client-data
claim-list elf-release 0 to claim-list
;
: set-le ( -- )
1 ciregs >r13 !
;
: set-be ( -- )
0 ciregs >r13 !
;
: go-64-be ( -- )
state-valid @ IF
set-be
go-args 2@
go-entry @
go-entry 8 + @
go-64
THEN
-6d boot-exception-handler ABORT
;
: go-32-be
set-be
go-32
;
: go-32-lev1
set-le
go-32
;
: go-64-lev1
state-valid @ IF
go-args 2@
go-entry @ xbflip
go-entry 8 + @ xbflip
set-le
go-64
THEN
-6d boot-exception-handler ABORT
;
: go-64-lev2
state-valid @ IF
go-args 2@
go-entry 0
set-le
go-64
THEN
-6d boot-exception-handler ABORT
;
: load-elf-init ( arg len file-addr -- success )
false state-valid !                            \ Not valid anymore ...
claim-list IF                                    \ Release claimed mem
claim-list elf-release 0 to claim-list        \ from last load
THEN
true swap -1                       ( arg len true file-addr -1 )
elf-load-claim                     ( arg len true claim-list entry elftype )
CASE
1  OF ['] go-32-be   ENDOF           ( arg len true claim-list entry go )
2  OF ['] go-64-be   ENDOF           ( arg len true claim-list entry go )
3  OF ['] go-64-lev1 ENDOF           ( arg len true claim-list entry go )
4  OF ['] go-64-lev2 ENDOF           ( arg len true claim-list entry go )
5  OF ['] go-32-lev1 ENDOF           ( arg len true claim-list entry go )
dup OF ['] no-go to go
2drop 3drop false EXIT   ENDOF                   ( false )
ENDCASE
to go to go-entry to claim-list
dup state-valid ! -rot
2 pick IF
go-args 2!
ELSE
2drop
THEN
;
: init-program ( -- )
$bootargs get-load-base ['] load-elf-init CATCH ?dup IF
boot-exception-handler
2drop 2drop false          \ Could not claim
ELSE IF
0 ciregs 2dup >r3 ! >r4 !  \ Valid (ELF ) Image
THEN
THEN
;
: do-load ( devstr len -- img-size )	\ Device method wrapper
use-load-watchdog? IF
4ec set-watchdog
THEN
2dup " HALT" str= IF 2drop 0 EXIT THEN
my-self >r current-node @ >r         \ Save my-self
." Trying to load: " $bootargs type ."  from: " 2dup type ."  ... "
2dup open-dev dup IF
dup to my-self
dup ihandle>phandle set-node
-rot                              ( ihandle devstr len )
encode-string s" bootpath" set-chosen
$bootargs encode-string s" bootargs" set-chosen
get-load-base s" load" 3 pick ['] $call-method CATCH IF
-67 boot-exception-handler 3drop drop false
ELSE
dup 0> IF
init-program
ELSE
false state-valid !
drop 0                                     \ Could not load
THEN
THEN
swap close-dev device-end dup to load-size
ELSE -68 boot-exception-handler 3drop false THEN
r> set-node r> to my-self                           \ Restore my-self
;
: parse-load ( "{devlist}" -- success )	\ Parse-execute boot-device list
cr BEGIN parse-word dup WHILE
de-alias do-load dup 0< IF drop 0 THEN IF
state-valid @ IF ."   Successfully loaded" cr THEN
true 0d parse strdup load-list 2! EXIT
THEN
REPEAT 2drop 0 0 load-list 2! false
;
: load ( "{params}<eol>"} -- success )	\ Client interface to load
parse-word 0d parse -leading 2swap ?dup IF
de-alias
set-boot-device
ELSE
drop
THEN
set-boot-args s" parse-load " $bootdev $cat strdup evaluate
;
: load-next ( -- success )	\ Continue after go failed
load-list 2@ ?dup IF s" parse-load " 2swap $cat strdup evaluate
ELSE drop false THEN
;
: noload false ;
' no-go to go
: (go-and-catch)  ( -- )
get-load-base c@ 5c =  get-load-base 1+ c@ 20 = AND IF
load-size alloc-mem            ( allocated-addr )
?dup 0= IF ." alloc-mem failed." cr EXIT THEN
load-size >r >r                ( R: allocate-addr load-size )
get-load-base r@ load-size move    \ Move away from load-base
r@ load-size evaluate          \ Run the script
r> r> free-mem
EXIT
THEN
['] go behavior CATCH IF -69 boot-exception-handler THEN
;
read-bootlist
: boot
load 0= IF -65 boot-exception-handler EXIT THEN
disable-watchdog (go-and-catch)
BEGIN load-next WHILE
disable-watchdog (go-and-catch)
REPEAT
.banner
;
: load load 0= IF -65 boot-exception-handler THEN ;
cr .(   Welcome to Open Firmware)
cr
cr .(   Copyright (c) char ) emit .(  2004, 2011 IBM Corporation All rights reserved.)
cr .(   This program and the accompanying materials are made available)
cr .(   under the terms of the BSD License available at)
cr .(   http://www.opensource.org/licenses/bsd-license.php)
cr cr
' start-it CATCH drop
cr ." Ready!"
iiii(i@iHi`ipi€ii i i°iÀiÐiÐhøPˆPHP˜PPxP8PhP(Pl@PèPøQ8P¸QPØQ(PÈoxRøR¨R(RˆRÈRR¸oˆo˜o˜o o¸eøoÈ
oØoèpp^ÿÿÿÿÿÿc‚Scÿÿÿÿ˜PÂèPGNUÃü´"ÇY‘ùÙÇÆH@(N>}†GCC: (GNU) 5.3.1 20160406 (Red Hat 5.3.1-6).symtab.strtab.shstrtab.rela.slof.loader.rela.text.rela.opd.got.rela.data.comment.note.GNU-stack.bssH^P€_€{^P
|tVø,[øD3M¸¸FWxVHPFT]ZøèkOÄx]h\]H@ˆh˜–L˜¯ ¾T8¼ÌH€ÔÑTÈïKèÐWè@VhhiÜ,HàD6W(°@IN{ð ZjXkNX¤t\h|SøŽX4™‚ˆ KÈ4²Ip ÃZ(„Í[˜œÝJhéN¨ØùTØðHÐlLèL$°€/Q¸dAI €WW¨hJ0üuO˜˜‚0€“Mˆ¬£\XLªKh¤ºVXü¿¸2 Ð]xŒÕ[ˆlâOˆÌøN˜èN(È\¸$W8(SȜ9e|F]¸MI€€dMX˜t^8$~MôVÈpL¨½K¸ôÍNØ|ÚN0ëX(Hú°\ØŒJ¨'X¨P2TH¤CpðeUWØ8aHp˜h¸T pKHІMHÄ–‚(©J¸(¿Z¨ËKxÐÜZXXóHÔøUè´MhLVØ&HðD0\¨H9|0 DXN\è´UX8$adˆiZh˜yfT†pˆe–Nˆdž[Hl©T¸H¿Q¨lÐI0€ßfîT¨ÔM˜<T&‚L:JPMH ÈSOxèe]XLmwfX‚ZØX¡[ÈX¨Y˜(¸SèœÉK8ßTèë¸T(ðUˆ¼ýp eUØ8O¨˜!NȜ.M8$=[xhU¸S p_[ØxYH„LÄšV¨ÈªJÁÀÐLø¤ß\8ðæ\ø8ëI€úZ¸dH ÁTT,\Ø4M(XGLØÀVQÈtd\(œlLH,\ˆŒS˜Ñ ®NH¸L(ðÌS¨˜ÜñèSˆ0øY¨0ýI Œ	Uhè	Vxt	'VHd	7Nxø	?U8d	MiT	X\xt	_	kQH8	}KX	j	¢Zè	©HÀ\	µ[¨˜	ÃV¸	ËZÜ	×L8à	èY(t	ïI`¸	ÿOèP
J@h
JØì
.Kì
BIà€
\L¸D
nYˆ|
zZ˜<
‚Q˜ì
“
§€
°Áæ
¸\HH
¿Z€
ËTˆÈ
ßÁÿÀ@
ìMÈL]	LxˆU˜¨)˜3O¸Ô@QøðMØZYØdy]èX˜0ŒZHd›Lh¯·JètË˜ÎÙäåV(œêUø´ói0[èŒMxl[8Ô$KˆÄ/[(,KYTjOȄw]8dLŠV8l’UH´ Nl®O(´¼LȨÑŒã¸UXìOØtúx¹

¸T
Sؐ
"P¨8
4`
?Oøô
TMøP
jX¸l
pY8T
‚[X˜
Vø4
›iô
«˜
®Qh
Ëi|
ÕV˜ 
ÝXX
ìJ ä
úRØüYø¸U`$N8„/OhA| M\˜$UÂ_MèˆuW˜†Tø•iÔ£Ið¨°Zx¼UX(ÊOp×˜ßj4ð[ÿM¨4MØì%[h˜1Gä@˜!KS¸Œ\ÄpT˜‡qXe—TXÜ£‚d´KØðÅLXX×S8éWøóXHþWÈH	\PXˆ`\È$!Nht)Uxð7LXH(YSx0d rJ€yU(¼‡IP€ž[ØL¥K(t¹[¸4ÂW¸`ÛNø˜ìüK8ˆZˆ H0<)Wp5Nè˜CI@ŒQH@TWf”`DkVèHy]øp‚˜"“V„Lˆä·](¼H°pÊKøÄáThìT(¸.LC24.LC3.patch_broken_sc1e1k_mac_setupstrcpyvirtio_serial_initset_ipv4_routerenginehandle_dhcpv6usb_hcd_initprintfvsprintfio_printhex16virtio_get_host_featuresthe_data_stackget_partitionrecvincrease_nvram_partition_sizevirtio_get_vring_deschandle_arpget_arg_ptrbootmsg_warningset_timersend_ipv4get_sec_ticksstderr_databootmsg_nvupdatep9_clunkmemmovenvram_write_qwordhandle_udphv_casvirtio_vring_sizeSLOF_dma_map_outmac2eui64neighbor_createcall_clientusb_devpool_getreset_nvramSLOF_usleepvirtioblk_shutdownhash_tableusb_key_availableSLOF_pci_config_read8get_ipv4_netmaskSLOF_bm_freeusb_hid_initthe_client_stackvirtionet_closememcpyelf_forth_claimpingthe_system_stackputsneighbor_addusb_dev_populate_pipep9_statp9_transactiontolowerset_ipv4_addressnvram_read_dwordromfs_lookupmallocSLOF_pci_config_read32virtioscsi_initvsnprintfvirtio_9p_initset_mac_addressvirtio_negotiate_guest_featuresvirtio_setup_vdusb_put_pipep9_reg_transporthandle_udp_dunthe_pocketsstrtoul_slof_textelf_load_filehandle_dnsget_partition_fskeycodes_shift_UShandle_ipv4socketdevpoolelf_byteswap_header64virtioscsi_sendhv_logical_ci_loadelf_load_file_to_addrstr_to_ipv6patch_broken_sc1ip6_create_prefix_infosende1k_closevirtioscsi_shutdownget_mac_addressget_timerisxdigitstdin_datapong_ipv4strtolfill_udphdr.call_cip6_prefix2addrwriteLogBytekeycodes_alt_GRp9_readrouter_addclear_nvram_partitionusb_hid_kbd_exitSLOF_alloc_memc_romfs_lookupdelete_nvram_partitionvirtionet_readfree_nvram_bufferhv_logical_ci_storeclient_entry_pointwriteusb_transfer_bulkfprintf_start_OFio_putchardhcpv6_generate_transaction_idstrcathandle_tftp_dunnvram_read_qwordelf_byteswap_header32nvram_debugheadlibveth_readkeycodes_ctrle1k_openusb_hid_exitusb_get_pipevirtio_9p_loadipv6_get_default_routervirtiodevsend_router_solicitationhandle_dhcpvirtio_get_vring_usedstrtoip_netmaskSLOF_bm_allocator_initepapr_ima_sizevirtioblk_readstrstrrandSLOF_dma_allocipv6_to_strreadthe_comp_bufferget_nvram_bufferstrncmpvirtio_9p_shutdownvirtioblk_initusb_read_keybstrncpyvirtio_queue_init_vqstrcasecmpnvram_write_bytethe_return_stackp9_attachvirtio_queue_notifynvram_read_wordepapr_magicnvram_read_bytetftpSLOF_dma_freelibveth_openget_args_countparse_tftp_argsp9_opennvram_add_envbootmsg_cpmemcmp.hv_hascharusb_ehci_registerelf_get_eflags_64bootmsg_checkleveldhcpv6SLOF_msleepfind_neighborstrtoiphandle_ipv6virtio_set_qaddrdhcpv4SLOF_dma_map_inusb_msc_resetrecoverysbrkelf_load_segments32elf_load_segments64SLOF_translate_my_addressvirtio_get_confighandle_tftpip6_cmpusb_hid_kbd_initthe_exception_framethe_heapsend_ipmemsetfill_ip6hdrnew_nvram_partitionall_nodes_llvirtio_serial_shutdownsrandvirtio_get_statuslibveth_writefdt_startusb_msc_initusb_hub_init.call_clientsend_ipv6_binary_OF_fsi_startgetchardns_get_ipunknown_prefixvirtio_reset_devicethe_memelf_get_base_addr32rphv_hascharhv_send_crqdhcpe1k_readGET_WRNG_LVLstrcmpvirtionet_openhandle_icmpv6fast_rfillsend_neighbour_solicitationdhcpv4_generate_transaction_idusb_msc_exitsprintfhv_putcharnetloadnvram_del_envreset_buffersusb_send_ctrl__virtio_read_configprint_version_endset_ledsusb_msc_reset_binary_OF_fsi_endspnvram_write_dwordusb_ohci_registerhv_getcharusb_setup_new_devicevirtio_serial_hascharbootpdhcp_send_releaserouter_createsend_etherbootmsg_debugcpdpusb_slof_populate_new_deviceprint_msgargncpyhandle_tcp_dunSLOF_bm_allocusb3_dev_initget_ipv6_addresskbd_bufferp9_versionusb_transfer_ctrlstdout_dataisdigitip6_statevirtio_serial_getcharset_ipv4_netmaskget_nvram_sizebootmsg_errorwrite_mm_logip6addr_addnvram_set_envusb_hcd_exitthe_tibbootmsg_setlevelis_ra_receivedvirtionet_writevirtio_serial_putcharfind_router_slof_text_endromfs_basenvram_write_word.client_entry_pointnew_nvram_partition_fskeycodes_std_USerase_nvramhv_logical_memopvirtio_get_qsizevirtio_set_statususb_xhci_registerping_ipv4handle_tcpfill_iphdrstrlendns_inittoupperp9_walklibveth_closevirtio_fill_descget_print_bannernvram_initprint_versioncall_cnvram_get_envSLOF_alloc_mem_alignedstrchrelf_get_base_addr64ndp_initget_default_ipv4_netmaskusb_hcd_registerhv_send_logical_lanelf_relocate64set_ipv6_addressasm_coutfill_ethhdrusb_poll_intrSLOF_free_memcloseio_printhv_genericreceive_ethervfprintfthe_client_framee1k_writevirtio_set_guest_featuresfreeSLOF_GetTimervirtio_get_vring_availwipe_nvramnvramlog_printfÕÕ!!ªª&•*•:T>TJTNTR V \
&Ê&=, *.969HK,üo
€€
 €
¬€
€
>2F0–2š0¢2Â0öá2úá02
02ÿÿÿÿÿÿÿø0ÿÿÿÿÿÿÿø2 0 2"2%X&0%X2062:2%P>2F@%PJ@N@R=2V=0f2 j0 ~2‚0ž2¢0Æá2Êá0Î2#ÈÖ0#Èö2	0	.2	20	Ž2	’0	–2	š0	Ê2	Î0	ÒR2	ÖR0
2

0
Ê2
Ê0
B2
F0
JK2
NK0
~2
‚0
†82€
Š80€
º2
¾0
œ2
Ɯ0
ö2
ú0
þ202260:2³P>@³Pn2r0v2³Xz@³XªÕ2®Õ0²2¶0ê!2î!0ò2ö0*ª2.ª02260j•2n•0r2v0¦á2ªá0Úá2Þá0æ2ê0
J2
N0
‚2
†0
º2
¾0
ò2
ö0*2.0Š2Ž0âá2æá020N2R0†2Š0¾2Â0ò2ö02260b2f0š2ž0¢á2¦á0æá2êá0î2ò02á26á0:2>0v2z0~2‚0¶2º0Â2Æ0þá2á02
0¦2¦0R2V0Z¦2^¦0bá2fá0¢2¦0ªá2®á0ê2î0&2*0b2f0ž2¢0Ú2Þ020R2V0Ž2’0Ê2Î0
20>2B0z2~0®2²0ê2î02"0Z2^0Ž2’0Ê2Î0þ2062:0~2‚0Î2Ò0&2*0†2Š0Î2Ò020F2J0Ž2’0Æ2Ê0Îá2Òá020Fá2Já0zá2~á0Ê2Î0Òá2Öá0Zá2^á0–2š0Æá2Êá0úá2þá0*á2.á0Z2^0~2‚02"0"2&0Æ2Ê0øH
 2 0 4^
 J2 N0 €z
 –2 š0 ¸^
 Î2 Ò0!z
!2!0!<^
!R2!V0!ˆz
!ž2!¢0!À^
!Ú2!Þ0"z
"2""0"T'
"n2"r0"œ(
"¶2"º0"èH
#2#0#(4
#>2#B0#la
#‚2#†0#¤N
#¾2#Â0#Ü)
#ö2#ú0#þ22$20$.2$20$ŒC
$¦22$ª20$Ê2$Î0$ôï
%
2%0%(ü
%B2%F0%`â
%z2%~0%¬H
%Æ2%Ê0%ðH
&2&
0&0ã
&F2&J0&’2&–0&â2&æ0'.
'*22'.20'LÍ
'^2'b0'Ò2'Ö0(ê
(R2(V0(Ö2(Ú0)(
)2)0)Dw
)r2)v0)°5
)Æ2)Ê0)þ2*0* 
*:2*>0*r2*v0*ª2*®0*Þ2*â0+®
+F2+J0+l2
+‚2+†0+°ˆ
+Ê2+Î0+øÔ
,2,0,8Š
,j2,n0,d
,¦2,ª0,Ðå
,ê2,î0-L
-*2-.0-h
-¢2-¦0-èð
-þ2.0.62.:0.n2.r0.¦2.ª0.Þ2.â0/2/0/N2/R0/†2/Š0/¾2/Â0/þ2000620:00v20z00®20²012101>21B01h<
1~21‚01¶21º01î21ò02&22*02^22b02–22š02Î22Ò0323
03>23B03v23z03®23²03æ23ê0424"04V24Z04Ž24’04Æ24Ê04þ2505625:05n25r05®25²05ê25î06626:06T-
6v26z06¨7
6Â26Æ06ô7
7
2707z27~07²27¶07î27ò08”
8628:08`	
8z28~08¨6
8Â2#È8Æ0#È8Þ28â08üí
92909D
9^29b09˜}
9®29²09ܳ
9ò29ö0: 
:62::0:`
:v2:z0:¤
:º2:¾0:ä
:ö2:ú0;(¸
;`#
;r2;v0;~;2;‚;0;¤U
;Î2;Ò0;Ú;2;Þ;0<_
<:2<>0<X«
<r2<v0<©
<ª2<®0<ÈE
<â2<æ0=„
=2=0=<¥
=Z2=^0=€"
=ž2=¢0=Äú
=â2=æ0>&
>&2>*0>P
>’2>–0>ÄW
?2?
0?@$
?r2?v0?¤
?ä/
?ö2?ú0@4²
@b2@f0@˜ñ
@Ԇ
@æ2@ê0A$
AR2AV0A€s
AÄQ
AÖ2AÚ0B8
B,.
BV2BZ0Bt
BŽ2B’0B´Ñ
BÆ2BÊ0Bø
C2C0C,
CF2CJ0Cdþ
CΞ
C°¶
CÔ*
Cê2Cî0D
D&2D*0DL
Db2Df0D€7
Dš2Dž0D¸‹
DÒ2DÖ0Dð¡
E
2E0E(3
EB2EF0E`×
Ez2E~0E˜Ö
E²2E¶0Eà
Eú2Eþ0FI
F22F60FXe
Fj2Fn0F°]
FÆ2FÊ0Fèè
G2G0G@9
GV2GZ0G€x
Gš2Gž0GÄ
GÞ2Gâ0H1
H2H0HL–
Hb2Hf0H˜K
H¾2HÂ0HäŸ
Hö2Hú0I,¾
IB2IF0I` 
Iz2I~0I¨Æ
K`0
Kp0
K–22Kš20Lö2Lú0Lü>
M
2 M0 N
N2(N .
N.0(N8
NH
NP.
Nd
Nt
NÀ
NÞ2Nê0Nþ2O0O2O
@O20O@0O^2Ob0Oh.
O|
OŒ
Oš2`O¢0`O¤
`OÂ2OÊ0OÌ
`Oê2ÀOì
Oö0ÀOø.
P
P
P$.
P8
PH
P`
Pt
PŒ:
PÒ2ÐPÖ0ÐPØ>
Q28Q08Q>
Q.2hQ20hQ4>
QF2˜QJ0˜QL>
QŠ2Q–0QÀ
QÒ2HQÔ
Qâ0HQè
Qð.
R
Rj2Rv0R 
R²2HR´
RÂ0HRÈ
RÐ.
Rä
Sb2PSj0PS°.
SÄ
TJ2hTN0hT\.
Tp
T„
TÄO
TàO
U2xU"0xU4
U@.
UT
U”O
Už2²U®0²UÚ2²UÞ0²UèO
VJ2€VR0€Vd
Vp.
V„
V˜
VÚ2Vâ0Vì
W
W.
W 
WZ2 Wb0 Wt
W€.
W”
W¨
Wê2°Wò0°Wü
X
X.
X0
X|u
X˜E
X¤u
Y
Y2ÀY 
Y*0ÀY8
YD.
YX
Yl
YÄ
YÖ2ÐYÜ
Yæ0ÐYô
Z.
Z
ZJ2àZR0àZd
Zp.
Z„
Z˜
ZÊ2ðZÒ0ðZä
Zð.
[
[
[J2[R0[d
[p.
[„
[˜
[Ö2[Þ0[è
[ü
\.
\
\f2 \n0 \x
\Œ
\˜.
\¬
\ö20\þ00]
]
](.
]<
]z2@]‚0@]”
] .
]´
]È
^
^*2X^0
^:0X^H
^T.
^h
^Þ2h^â0h^ä
^î2˜^ò0˜^ô
_"2ð_&2X_*2 _60ð_:0X_>0 _`
_´
_Ä
_Ò2è_Ö0è_Ø
`Œu
`¼Í
cê2øcò0øcø
d"2²d&0²d¤F
eDF
f$F
f¨€
f܀
fø€
g€
g0€
gL€
gh€
g„€
g €
g¼€
g؀
gô€
h€
h,€
hH€
hd€
h€€
i`€
ih
ip€
i€
i˜€
i €
i¨
i°€
i¸G
i
iȀ
iØ
iàæ
iìiüæ
jjæ
j¤\
jð…
kp
˜kÐÄ
kì·
l Ã
l˜
˜l´;
lÐÄ
lè@
m$à
m@Ã
m¤
˜mÔ;
môà
nü%
oÍ
o²2@o¶0@o¸
rÌ%
rìÍ
s‚2€s†0€sˆ
tz2àt~2Àtš0àtž0Àu¶2sÐuº0sÐvô
x´
zú2{0{
{ 
{,.
{@
{T
~œÍ
*6.62õ6õdµ
v¡Òz¡Òš¡Òž¡Òº¡Ò¾¡Ò‚àH
ā
ƒLÅ
ƒH
„”u
„¨4
„È4
„à4
„ø4
…4
…H
…L
˜…\4
… 
˜†,H
†B2(†F0(†H
ˆ`
¨ˆœ
ˆ¬(
‰$
¨‰lP
‰|(
‰ô
¨Œ(
p(
 9
äÍ
ø¾
ŽP
Ž’
ŽJ2HŽN0HŽP
ŽÔ)
‘¬
‘ÀM
‘È
‘ÜÓ
‘ô)
’Ó
’2"2’6"0’:2˜’B0˜’D~
’f"2’j"0’n2h’r0h’t~
•°Þ
•À)
•Ü)
–M
–2°–2À–0°–0À– 
–<)
–xM
–‚2¡Ò(–Š0¡Ò(–£
–¨P
–ì)
–ø
—Æ
—8Ó
—h)
—tÞ
˜Æ
˜$Æ
˜D(
˜X
˜lP
˜€’
˜ª2¡ÒX˜²2¡Ò\˜¶0¡ÒX˜¾2¡Ò`˜Â0¡Ò\˜Æ@¡Ò`˜Ò2¡ÒX˜æ0¡ÒX™ 3
™X3
™|3
™ð¨
™øO
šO
šF2(šJ0(šL
šb"2šf"0šj2šr0št~
šÒ2КÖ0КØ>
šö2¡ÒXšú2¡Ò\›0¡ÒX›0¡Ò\›2¡Ò`›0¡Ò`› (
›´
›ÈP
›Ü’
œT3
œx3
œð¨
Æ2¡ÒhÚ0¡Òhþ0¡ÒhžÞ
ž)
ž0)
žLM
žV2¡Òpž^0¡Òpžd£
ž|P
žÀ)
žÊ2žÚ0žÜP
ŸM
Ÿ4Ó
ŸB2PŸF2ÀŸJ0PŸN0ÀŸP
Ÿp)
ŸØ)
ŸäÞ
Ÿö2¡Òh 0¡Òh .2` >0` B2¡Òh F0¡Òh œÆ
 Ìô
 Ü

 î2h ö0h ø
¡$
¡D§
¡Z2ˆ¡b0ˆ¡d
¡t$
¡¼1
¡Ú2 ¡Þ0 ¡à
¡ð$
¢$A
¢62¸¢>0¸¢@
¢P$
¢`$
¢˜±
¢èq
£2è£
0è£
£"2У*0У,
£°(
£Ä
£ØP
£ì’
¤d3
¤˜3
¥¨
¥O
¥4O
¥Ð3
¥ü3
¦L)
¦h)
¦ˆM
¦ Ó
¦¸M
¦Ð)
¦àP
§ (
§D)
§r2§v2À§z0§~0À§€
§œ)
§Ø)
§äÞ
¨Du
¨f2¨j0¨v2¡Ò ¨z0¡Ò ¨€:
¨ŒÞ
¨ £
¨¼£
¨Ô)
©8)
©\M
©f2¡Ó©j0¡Ó©tu
©~2¡Ò°©Š@¡Ò°©è3
ª3
ªj2¡ÒÀªn@¡ÒÀªª@¡ÒÀª¶2¡ÒȪº@¡ÒȪÎ2¡ÓªÒ2¡ÒðªÖ@¡ÒðªÚ0¡Óªú2¡Òðªþ@¡Òð«)
«$¨
«PÆ
«|M
«œÓ
ǻ28Ǩ08ǡ
«Ì)
«ÜE
¬2¡Ó¬2¡Òð¬"@¡Òð¬&0¡Ó¬8)
¬HE
¬Z2¬^0¬`
¬°E
¬Ò2¬Ö0¬Ü)
¬æ2¬ê0¬ìÞ
­E
­F2¡Ò ­V0¡Ò ­Z2­^0­b2¡ÒÈ­f@¡ÒÈ­‚2¡Ó­†0¡Ó­ð:
­þ2¡Ó®2¡ÒÀ®@¡ÒÀ®
0¡Ó®0¡Ó®&2¡Ò¨®*0¡Ò¨®v2¡ÒÀ®z@¡ÒÀ®¤¨
®Ú2¡Ó®Þ0¡Ó¯F2`¯J0`¯L
¯Z2¡Ò¸¯^@¡Ò¸¯ :
¯®2¡Ó¯²2¡ÒÀ¯¶@¡ÒÀ¯º0¡Ó¯Ê0¡Ó¯Ò2¡Ò¨¯Ö0¡Ò¨°®2°²0°Â2¡Ó°Æ0¡Ó°Ê2¡Ó°Î0¡Ó°ØÍ
°æ2¡Òð°ê@¡Òð±
2¡Òر0¡Òر2¡Òè±@¡Òè±"2¡Ó±&0¡Ó±P3
±Z2¡Òè±^@¡Òè±|3
±†2¡ÒرŠ0¡Òر’2¡Òð±–@¡Òð±Ú2¡Òð±Þ@¡Òð²¨
²B2¡Ó²F0¡Ó²R2²V0²X
²ÔÞ
²ä)
³)
³ M
³22°³62À³:0°³>0À³@
³\)
³ŒÓ
³–2¡Ó³ž0¡Ó³¨£
³¼u
³Æ2¡Ó ³Ò@¡Ó ´3
´V2¡Ó°´Z@¡Ó°´–@¡Ó°´¦2¡Ó¸´ª@¡Ó¸´Ê2¡ÓÀ´Ú0¡ÓÀ´Ü£
´ôP
µ8)
µJ2ȵN0ȵP
µˆ)
µ”Þ
µô(
¶
¶P
¶0’
¶Œ3
¶ô¨
¶üO
·O
·b2ø·f0ø·h
·ÔÍ
·â2¡Ó¸·æ@¡Ó¸·ê2¡ÓÀ·î2¡Ó·ò0¡Ó·ö0¡ÓÀ¸€:
¸Ž2¡ÓÀ¸’2¡Ó°¸–@¡Ó°¸š0¡ÓÀ¸ª0¡ÓÀ¸²2¡Ó˜¸¶0¡Ó˜¹4:
¹B2¡ÓÀ¹F2¡Ó°¹J@¡Ó°¹N0¡ÓÀ¹^0¡ÓÀ¹j2¡Ó˜¹n0¡Ó˜¹º2¡Ó°¹¾@¡Ó°¹ì¨
ºF2¡Ó¸ºJ@¡Ó¸ºj2¡ÓÀºn0¡ÓÀº¢2¡Óøº¦@¡Óøºª2¡Ôº®@¡Ôº²2¡Ôº¶@¡Ôºº2¡Ôº¾@¡ÔºÖ2¡ÔºÚ@¡ÔºìÍ
ºö2¡Ôºú@¡Ô»Í
»ù2»ù0»2¡Ô»@¡Ô»J2¡Óø»N@¡Óø»Rù2»Vù0»Z2¡Óø»^2¡Ô»b@¡Ô»f0¡Óø¼¬Í
¼Ø¢
¼â2¼ê0¼ì
½*2(½.0(½8ò
½>ù2½Bù0½¬.
½È.
½Ü:
½è.
¾B
¾2¡Ô¾@¡Ô¾628¾:08¾@ž
¾È.
¾Ø.
¾ôò
¾úù2¾þù0¿„.
¿¤.
¿¸:
¿Ä.
¿à.
À.
À:
À .
ÀlB
ÀÈò
ÀÎù2ÀÒù0ÁDB
Á¸ò
Á¾ù2ÁÂù0ÁÊ2@ÁÖ0@Â؞
Âî2¡ÔÂò@¡ÔÃD:
Ãb2¡ÔÃf@¡ÔÃxB
Ãä.
Ãú2¡ÔÃþ@¡ÔÄB
Ä2¡ÔÄ@¡ÔÅò
Åù2Åù0ŐB
Ş2¡ÔÅ¢@¡ÔÆò
Æ2ù2Æ6ù0ÆÄB
ÆÒ2¡ÔÆÖ@¡ÔÆô:
Çlò
Çrù2Çvù0ÇÜB
Çê2¡ÔÇî@¡ÔÈN[2ÈR[0È|Í
È´u
É&[2É*[0Éò2HÉö2˜Éú0HÉþ0˜Ê
ËZ‡2Ë^‡0˺2¨˾0¨ËÀ
Ëê‡2Ëî‡0̆2°̊0°̌
Í2°Í0°Í
͒2X͖2˜͚0X͞0˜Í 
Î<ó
μó
Ï<ó
Ï|ó
ÐB2hÐF2˜ÐJ0hÐN0˜ÐP
ÐàŒ
ь
Ñ Œ
Ñ É
Ò@t
Ó@@
Ó°O
ÓÀO
ÔLó
Ԙ
8Ô 
8לּ
Õ(Œ
Õ<
H՘ó
Õ¼º
ÕÐ
HÖ
XÖ<™
ÖX
X֘ó
Ö°º
×H­
×l:
×~2€ׂ2À׊0€׎0Àא
ר­
Ø62¡Ô0Ø:0¡Ô0ض2¡Ô0ؾ0¡Ô0Ù®2¡Ô0Ù²0¡Ô0ÚhÍ
Û*
Û*
Û0­
ÜÍ
ݘ™
Ý°À
ÝÈÍ
ÝÜÍ
ÝðÀ
Þԙ
ÞôÀ
Þþ2ß0ßP
ߦ2Øߪ2Pß®0Øß²0Pß´
àpº
à¨*
อ
àÔ*
àä­
àôE
á>2áR2páb2¨áž0á®0pá²0¨á¸O
âO
â”
ââ2hâê0hâì
ãè
ä”Í
æ|O
æ¨O
æÐ
Xçr2Àçv0Àçx
çÂ2àçÊ0àçÌ
è2	(è0	(è
è62	8èB2ðèF0	8èN0ðèP
èxÁ
èŠ2ðèŽ2	è’0ðè–0	è˜
é@™
éTÀ
étÍ
éŒÀ
ê°O
êØO
ë2ë2	pë
0ë0	pë
ë2	ˆë2	˜ë"0	ˆë(
ë60	˜ëH
ëZ2 ë^0 ë`
ë|
XëÔ*
ëì*
ì*
ì­
ì¬À
íJ2	 íV0	 íp
í|u
í Í
íę
íê2	àíî0	àíð
î­
îE
îXÀ

ï0
ï"2
ï&0
ï(
ï\Œ
ï„Í
ï˜Í
ð°º
ñLº
ñ”º
ñ®2
`ñ²2
xñ¶0
`ñº0
xñèº
òÐ
òø.
óý
ó,
óH
ó®2	¸ó²0	¸ó´
óö2
0óú0
0óü
ô62ðô:0ðôD>
ôÐÍ
õÍ
õÍ
ö™
ö4À
öê2Èöö0È÷
÷u
÷,Í
÷tO
÷ÀO
ø™
øÀ
ø,™
øDÀ
ø\Í
øԙ
øìÀ
ùÍ
ùÞ2¸ùê0¸úȺ
û(º
û0.
ûLý
ûh
ûä
ûú2àûþ0àü
ü:2ü>0ü@
üN2PüR0PüT
üh*
üx­
ü†2ˆüŠ0ˆüŒ
ü *
ü°­
ü¾2 üÂ0 üÄ
üî2¡Ô4üþ0¡Ô4ý0¡Ô4ý2ý2èý"0ý&0èý(
ýÀ*
ýЭ
ýì*
ýü­
þ*
þ(­
þD*
þT­
þdE
ÿO
ÿ$O
ÿ¤O
`™
xÀ
Í
¤À
°O
ÔO
O
2
@0
@ 
@
	X*
l*
€*
­
â2
æ0
è
L
	Z2 ^2
hb0 f0
hh
ŒÀ
2
(
0
(
èÍ
O
0O
ˆ
	â2
ې0
ۓ
ú2
 0
 
2°2
h0°0
h 
.2
È60
È8
f2Pj0Pt>
22€>0€L
X.
l
’2 š0 ²2@º0@Ò2`Ú0`	22Ð	60Ð	8
	p÷
	„º
	 
	X	²2˜	¶0˜	¸
	â2	æ2¸	ê0	î0¸	ð

2¡Ô8
@¡Ô8
j2¡Ô@
n@¡Ô@
Šö2
Žö0
¢2¡Ô8
¦2¡ÔH
ª0¡ÔH
²0¡Ô8>2	XB0	Xâö2æö0‰2‰0Ò%2Ö%0ÚX2ÞX0â2¡Ô8æ2¡Ô@ê@¡Ô8î@¡Ô@öö2úö0
ö2
ö0Zö2^ö0âp2æp0PÍ
`D
t
	xøó
0ó
DÍ
„ó
˜™
¢2¦0 @
4
	xLÍ
b2øf2j0øn0p
°O
Â2Æ0Э

	ˆ2¡ÔH"0¡ÔH&2¡ÔV*0¡ÔV„
	ˆŠ2¡ÔHŽ0¡ÔH’2¡ÔV–0¡ÔVš2¡Ô8¢0¡Ô8¶2¡ÔH¾0¡ÔH@ó
Èó
 22H 4Í
 Z0H xó
 ¸
	è à
	Ø èº
 ðO
!
	è!0O
!\
	Ø!dº
!lO
!€O
!œ
	è!À.
!Üý
!ô
"D
"\
	è"œ

"²28"¶08"¸
#4O
#lO
#º2ˆ#¾0ˆ#À
%”Í
%Ì*
%Ü­
&Í
&ÐÀ
'¼

'Ø*
'ð*
(LÀ
(ð™
)Í
)0À
)˜*
)¨­
)¼Í
*@Í
*à™
+

X+À
+Ä

,TÍ
-d

x.<

X/d

x/²2x/¶2/¾0x/Â0/Ä
/ô™
0À
0¤

X0¸™
0ÌÀ
1P

h1^2˜1b0˜1d
1p

h1~2Ð1‚0Ð1„
30
3¼

˜3Ð

H3Ø

H3à

H3è

H3ø*
4­
4*
4,­
4t*
4„­
4”

H4Ð

H5*
5­
5º
5,E
5²2¡Õh5Â0¡Õh6(

6ˆ:
6œÍ
720¡Õh9pO
9z2¡Õh9‚0¡Õh9˜O
9°

:2(:0(:
;

x;Ä

8<Œ

h<ü

8=d

x=”

x=œ.
=Øý
=ô*
>­
>

H> *
>0­
>B2P>N0P>P
>„
@ìº
@ü

AD

BÊ2€BÖ0€Bè
Cu
CÍ
D$

˜Dä0
EH™
EdÍ
ExÀ
EÌ

hFt

hF¼

HFè*
Fø­
G2ðG0ðG
GJ2ÀGN0ÀGP
Gr2˜Gv0˜Gx
GÀ™
GÜÀ
J

˜J

èJ,

èJd*
Jt­
J€

HJ¦2°Jª0°J´>
Jæ2¡ÕpJê0¡ÕpK0H
Kf2¡ÕtKj0¡ÕtK¦2¡ÕpK²0¡ÕpKô
LD
LJ2¡ÕtLN0¡ÕtLv2¡ÕtLz0¡ÕtL®2¡ÕpL¶0¡ÕpLÐ
Lü
(MT
MŒH
N2¡ÕtN0¡ÕtNz2¡ÕxN~0¡ÕxN¼H
Nâ2¡ÕxNæ0¡ÕxO H
O*2¡ÕtO.0¡ÕtOB2¡ÕxOF0¡ÕxO€H
OŠ2¡ÕtOŽ0¡ÕtOî2¡ÕpOú0¡ÕpP
8P2¡ÕtP0¡ÕtP
8P.2¡ÕtP20¡ÕtPœ.
PøH
Q
(Q2¡ÕtQ0¡ÕtQ¢2¡ÕxQ¦0¡ÕxQäH
R8H
R^2¡ÕxRb0¡ÕxRœH
RÊ2¡ÕtRÎ0¡ÕtRÜ
8Râ2pRê0pRø
XS22¡ÕpS60¡ÕpS:2¡ÕxS>0¡ÕxSB2¡ÕtSF0¡ÕtSJ2¡Õ€SN@¡Õ€Sb2¡ÕtSf0¡ÕtS€
S–2¡ÕtSš0¡ÕtS¶2¡ÕxSº0¡ÕxSüH
T"2¡ÕtT&0¡ÕtTF2¡ÕpTJ0¡ÕpTH
TÆ2¡ÕtTÊ0¡ÕtTæ2¡ÕxTê0¡ÕxU(H
UR2¡ÕtUV0¡ÕtUv2¡ÕpUz0¡ÕpUÄH
Uö2¡ÕtUú0¡ÕtV2¡ÕxV0¡ÕxV\H
V‚2¡ÕtV†0¡ÕtV¦2¡ÕpVª0¡ÕpVôH
W&2¡ÕtW*0¡ÕtWF2¡ÕxWJ0¡ÕxWŒH
W²2¡ÕtW¶0¡ÕtWº2¡ÕpW¾0¡ÕpWÊ2¡ÕˆWÎ0¡ÕˆX2¡ÕˆX0¡ÕˆXp
X¬B
Xú2¡ÕtXþ0¡ÕtYZ2¡ÕpYb0¡ÕpY¬
(Yè
Zp
Z”ž
[$
[\H
\:
\ 
\f2¡Õt\j0¡Õt\z2¡Õp\Ž0¡Õp\²2¡Õˆ\¶0¡Õˆ]HH
]°Í
]ðH
^B2¡Õt^J@¡Õt^L&
^„&
^¤&
_
_,&
_@
X_\
h`Ï
`B2¡Õt`F0¡Õt`š2¡Õp`¢0¡Õpa
aHH
at&
a„
a &
a¤
hb4&
bÌ
c2¡Õtc0¡Õtc2¡Õpc0¡Õpc*2¡Õˆc.0¡ÕˆcŒ
c¼&
dLH
df2¡Õˆdj0¡ÕˆdÈ&
dà&
dæ2¡Õtdê0¡Õte
he2¡Õxe0¡ÕxePH
ev2¡ÕteŠ@¡Õte˜&
eÈ
Xeü
Xf
Hf
Hf2€f0€fR
f"2¨f*0¨f4
Xf8
hfr2¡Õtfv0¡ÕtfÔ«
fü«
gš2¡Õ gª0¡Õ gÐÍ
h«
h0ž
h„ž
hî2¡Õ hú0¡Õ i\«
iˆž
iäž
jØ

k,¥
kP¥
kδ
lH

l\

l|«
lœ
lè«
m,¥
mDy
m\&
n8
n(.
nD

nX

nh
n¨«
nī
nì«
oL¥
o|¥
o´
oÌy
oì¥
p\ž
pز
q$u
qJ2¡×¨qL:
q^2¡×¨qn0¡×¨qz0¡×¨q~2¡×¬q‚0¡×¬q„9
qŽ2¡×°q¢@¡×°q¦2¡×¸qª@¡×¸q¬9
q¶2¡×Àqº@¡×ÀqÄu
qÎ2¡×°qÒ@¡×°qÖ2¡×ÈqÚ@¡×Èqæ2¡×¸qê@¡×¸r<H
r„H
rÒ2ÐrÖ0ÐrØ
râ2¡×°ræ@¡×°rôE
rþ2¡×Às@¡×ÀsE
s2¡×Ès@¡×Ès0E
s@E
s¢2øs¦0øs¨
s¶2°sº0°s¼
tE
t8H
tB2¡×°tF@¡×°tTE
t^2¡×Àtb@¡×ÀtpE
tz2¡×Èt~@¡×ÈtE
t¨E
tæ2(u2¡×¨u0¡×¨u2¡×¬u"0¡×¬u&0(uŒ
u¨H
v,:
vÔ?
w2Xw0Xw 
w–2¡×àwš0¡×àw¢2¡×èw¦@¡×èwÎ2¡×èwÒ@¡×èxr2¡×àx‚0¡×ày$º
y¢2¡×ày¦@¡×àz>2¡×èzB@¡×èz‚2Øz†0Øzˆ
z¾2¡×èzÂ@¡×èzê2¡×èzî@¡×è{:2€{B0€{–2¡×à{ž@¡×à{¦2¡×è{ª@¡×è{Þ2¡×è{ê2¡×à{ö0¡×à{þ@¡×è|u
|$Í
|<À
|F2¡×è|J@¡×è|r2¡×è|v@¡×è|¼º
}

¨}<Í
~\Í
¬E
æ2ê0ì
€"2¡×è€&@¡×è€R2¡×è€V@¡×è€pº
€z2¡×è€~@¡×耖2¡×耚@¡×耲2¡×耶@¡×è€Î2¡×è€Ò@¡×è€ê2¡×è€î@¡×è2¡×è"@¡×è&2¡×à.0¡×àD

¸Lº
X

¸`º
€*
˜E
ö2¡×èú@¡×è‚2¡×à‚"0¡×à‚r2¡×à‚z0¡×à‚ø:
ƒÍ
ƒ¶2¡×胺@¡×èƒò2¡×èƒö@¡×è„2¡×à„&0¡×à„X:
„~2¡×è„‚@¡×è…n2€…v0€…Â2¡×à…Ò@¡×à…Ö2¡×è…â@¡×è…äÍ
†

¨†‚2 ††20†Š0 †Ž00†
†˜ì
† 
†ª2؆®2p†º0؆¾0p†Ø
†àÛ
‡A
‡ ¹
‡H
‡PÛ
‡b2à‡f0à‡h
‡Ì¿
‡â2‡æ0‡è
ˆ¿
ˆ"2ðˆ*0ðˆ,
ˆB2(ˆF20ˆJ0(ˆN00ˆP
ˆXì
ˆr2`ˆv20ˆz0`ˆ~00ˆ€
ˆ
ˆ¤:
ˆò2hˆþ0h‰@>
‰TÍ
‰lZ
‰€Û
‰ !
‰¨
‰°g
‰ÐZ
‰þ2¨Š
0¨Š
ŠL
Š4Ò
Š`¢
Š„Í
Š¯
Š¦2pŠª@pŠô:
Šþ2p‹@p‹&2‰@‹*0‰@‹b2‹j0‹l

‹|
‹ˆ.
‹œ
Ί
Œ2pŒ@pŒB2pŒF2pŒJ0pŒN@pŒ|¬
Œ˜F
"2P*0P,î
<
H.
\
€ä
š2pž@p¸š
Â2€Ê0€Ì
â2 ê0 üî
Ž
Ž.
Ž,
Ž8F
Ž\´
Ž€ÿ
Ž ´
Ž¸A
ŽÆ2pŽÊ@pŽà´
Žü´
D
2p@p.2X20XD
`´
”ä
°:
º2p¾@pÔ´
ð´
:
22x>0x@
^2p`¢
j2pr0pv@pŠ2’0¤
®2pÂ@pÐ¬
ì
‘
‘2‘0‘ ¤
‘@
‘J2p‘V@p‘Œ
‘°
‘Ð
‘ô
’2(’0(’¤
’4
’B2p’J0p’l
’|`
’¤Í
’¼
’à
“,Í
“V2 “^0 “`¤
“‚2P“Š0P“Œ
“œš
“¦2 “®0 “°
“Ìk
“ø´
”´
”0´
”L:
”hA
”p
”„:
”œk
”º2p”¾@p”ü
•¼
•4Í
•L
•p
•¼Í
•àÍ
•ôÍ
–Í
–0Í
–HÍ
–`:
–x:
–”
–¸
–ȼ
–ðÍ
—
—,
—<¼
—dÍ
—r2ð—v0ð—x>
—ˆÍ
—˜
—´´
—Ð:
—è´
˜:
˜
˜8
˜H`
˜pÍ
˜€
˜¬
˜¼`
˜äÍ
˜ôÍ
™
™$´
™@:
™LÍ
™XÍ
™hÍ
™xÍ
™†2€™Ž0€™

™ 
™¬.
™À
™Ò2 ™Ú0 ™Ü
™î2à™ö0à™ø

š
š.
š(
š4F
šF2HšN0HšP

š`
šl.
š€
š’2 šš0 šœ

š¬
š¸.
šÌ
šÞ2šæ0šìî
šü
›.
›
›.2À›:0À›@î
›P
›\.
›p
›‚20›Š00›Œ

›œ
ݬ.
›¼
›ÈF
›Þ2›æ0›èî
›ø
œ.
œ
œ.2Ðœ60Ðœ8î
œH
œT.
œh
œ~2 œ‚0 œŒî
œž2š¼œ¢0š¼œÒ2èœÚ0èœÜ

ϓ
Ͽ.

2¸&0¸(

8
D.
X
j2˜r0˜t

„
.
¤
¶2p¾0pÀ

Ð
Ü.
ð
ž.
ž2hž0hžî
ž(.
ž228ž608ž<î
žL
žX.
žl
ž|.
ž†2€žŠ0€žî
žœ.
ž¦2˜žª0˜ž°î
ž¼.
žÆ2PžÊ0PžÐî
žÜ.
žæ2@žê0@žðî
Ÿ.
Ÿ
2¸Ÿ0¸Ÿî
ŸpG
Ÿˆ¢
Ÿ’2øŸš0øŸ ž
Ÿ¸:
ŸÜ:
Ÿô:
 :
 4

 LÜ
 dš
 t

 €N
 Ä:
 ä:
¡`
¡

¡$N
¡b2¡j0¡p
¡|N
¡’2°¡š0°¡œ
¡ª2È¡²0È¡´
¡Â20¡Ê00¡Ð
¡ÜN
¡ê2x¡ò0x¡ø
¢N
¢2˜¢0˜¢ 
¢,N
¢:2P¢B0P¢H
¢TN
¢b2¢j0¢p
¢|N
¢ÌÍ
¢è:
£¯
£4
£D¼
£d
£t¼
£Œ
£¨
£¼“
£Ô
£üÍ
¤2!(¤
0!(¤
¤$Z
¤R2 x¤^0 x¤d
¤pL
¤”ä
¤¬D
¤º2 À¤¾0 À¤Ð
¤Ø5
¤ô:
¥2!¥0!¥
¥(+
¥0!
¥\
¥pI
¥xj
¥ˆg
¥ž2	€¥¢0	€¥¤
¥°F
¥ì:
¦
¦D
¦&2 À¦*0 À¦<
¦D5
¦V2 à¦Z0 à¦\
¦f2 ð¦z0 ð¦|
¦’2!¦–0!¦˜
¦¤F
¦Ð
¦à¼
¦ò2Ȧö0Ȧø
§(
§D
§T¼
§p
§œ
§¬¼
§Ä
§ä
§øk
¨=
¨0
¨>2 H¨B0 H¨D
¨V2  ¨Z0  ¨\
¨n2 ˜¨r0 ˜¨t
¨€F
ª¸¢
«N2@«r0@«˜
«°—
«È—
«ô¢
¬k
¬X¢
¬pk
¬€.
­:
­0:
­\¢
­¼¢
­Ì.
­ô“
®*2ª®.0ª®0:
®R2ª®Z0ª®\Í
®‚2ª®†0ª®®2ª®º0ª®ØÍ
®ð
¯2!P¯0!P¯´
¯.2ª¯20ª¯²2x¯º0x¯À´
¯Ü´
°´
°0
°pY
°°½
±c
±`:
±t:
±²2ª±º2ª±¾0ª±Æ0ª±Ê2ª±Ö0ª±Ú2ª±æ0ª²Í
²Ì2²"Ì0²& 2². 0³*2ªZ³.0ªZ³22ª³60ª³F2ªZ³J0ªZ³®2!X³¶0!X³Ä´
³Ö2ª³Ú0ª´&2ª´*0ª´.2!X´60!X´`Í
´hf
´z2ªZ´~0ªZ´¨:
´À:
´Ìf
´äC
´ø
µ
2ªµ0ªµ2ªµ0ªµ:2ªµF0ªµ|Í
µ„f
µœC
µ°:
µ¾2ª`µÆ0ª`µÈ!
µÐ
µàg
µôI
¶2ªZ¶0ªZ¶"2ª¶&0ª¶*2ª¶.0ª¶62!X¶:0!X¶Lf
¶lC
¶€:
¶˜
¶â2ªZ¶æ0ªZ·2ª·
0ª·2ª·0ª·2ªZ·0ªZ·²2ª·¶0ª·¾2€·Â0€·â2ªZ·æ0ªZ·ê2ªZ·î0ªZ¸Í
¹2ªZ¹0ªZ¹
¹22ªZ¹60ªZ¹f2ªZ¹j2€¹v0ªZ¹~0€¹†2¹Š0¹’2‚¹–0‚¹š2ƒ¹ž2…¹¢0ƒ¹¦2„¹ª0…¹®0„¹Ê2ªZ¹Î2€¹Ú0€¹Þ0ªZ¹èÍ
º2ªZº0ªZº22ªZº60ªZº8
ºR2ªZºV0ªZºr2ªZºv0ªZºx
º’2ªZº–0ªZ»ž2ªZ»¢0ªZ»Æ2ªZ»Ê0ªZ¼¢2ª¼ª0ª¼Æ0ª½"2ª`½&0ª`½.2ª½20ª½r2ª`!½v0ª`!½À:
¾'
¾2ª`¾0ª`¾ :
¾@,
¾¼:
¿ 
¿\Q
¿|
¿ú2ªZ¿þ0ªZÀ2ªÀ0ªÀ,f
À<´
Á˜Í
Á f
Á¸C
ÁÀf
Áø:
Â:
Â(
ÂV2!`Âb0!`Âh´
ˆ:
¬:
ÂÀ
Âæ2ªÂê0ªÃxÍ
ÃÄ 
Ãò2ªÃö0ªÄhV
Ä°‘
ÄôÇ
Å
Åtƒ
ƀ:
Ç22 Ç:0 Ç<

ÇÄ.
Çê2«fÇî0«fÈÍ
È8

ÈD.
Ȁl
Ȕ:
Ȝ
ȸÎ
ÈÆÌ2ÈÊÌ0É\l
Éf2«lÉj0«lɀ-
ɪ2«lÉ®0«lÉÆ2«lÉÎ0«lÉØ:
Ê2 Ê*2«fÊ.0 Ê:0«fÊh

Êr2!hÊz0!hÊ|—
ʎ2!pʖ0!pʘ—
ʦ2Ê®0Ê´—
Ê̗
ÊÚ2!xÊâ0!xÊè—
˗
Ë
2!€Ë0!€Ë —
Ë8—
Ët¢
ː

˜.
Ëø¢
Ì"2!øÌ*0!øÌ,
Ìx

̂2"̊0"̌
ÌÒ2«lÌÖ0«lÌö2«n,Í0«n,Í

Í.
Í4
xÍ8!
Í@
Ípg
̈́I
͸
xÍÎ2!ÐÍÖ0!ÐÍØ
Íö2!€Íø.
Î0!€Î—
Î$.
ÎP:
΢2!ˆΪ0!ˆά
Ï:
ÏÍ
Ï®2«o0ϲ0«o0ÏØ
hÐ62«n,Ð>0«n,Ð^2«fÐf0«fР
hÐÀç
Ñ:
Ñ(ç
ÑL
hÑf2«n(Ñn0«n(ў2"XѪ0"XѾ2"ˆÑÎ2"0ÑÚ0"0Ñî0"ˆÒ
Ò2«p0Ò@«p0Ò
ÒHÍ
Òd-
Ò|l
Ҙ

Ò f
Ò´:
ÒÈ 
ÒüÍ
Ó!
Ó
Ó0
ӄg
Ó°
ÓÂ2"`ÓÊ0"`ÓÐ
Ô`f
Ôp´
Ԇ2«p0Ԋ@«p0Ԙ:
Ô¸

ÔÆ2"ÔÊ0"ÔÔ
ÕL:
Õp:
Ռ:
׸:
Ø
ÈØhÍ
Ør2ˆØz0ˆ؀´
ڌ:
Ûì:
Ün2«p8Üz0«p8Ü~2ˆ܆0ˆܔ:
ÞP.
Þp:
ޘ.
Þ¸:
Þî2«p8Þö0«p8ßÍ
ß2«pTß"2«pUß&2«v(ß*0«v(ß.0«pTß20«pUß:2«pVß>0«pVßB2«pXßF0«pXßHf
ß\:
ßpÍ
ߜ
øß°l
ߺ2«v,ß¾0«v,ßÔ-
ßè 
à0˜
à<˜
àZ2«v(à^0«v(àŽ2 àž0 àª2«p8à¶0«p8àÜ

àì

àö2«x0á@«x0á
á2«x8á0«x8á!
á
á(I
á¬.
á¾2«x<áÂ0«x<áÒ2«v,áÖ0«v,áè

â"2«x<â&0«x<â<

âH.
â`¼
â€g
â°Ü
ã2«p8ã0«p8ã4Í
ã>2«pTãB2«pUãF2«v(ãJ0«v(ãN2 ãV0«pTãZ0«pUãb2«pVãf0 ãj0«pVãn2«pXãr0«pXãt

ã|f
ã:
ãš2«v,ãž0«v,ã¢2«p`ã²0«p`ã´Í
ã¾2«x@ãÂ0«x@ãØ
øãìl
ãö2«x@ãú0«x@ãþ2«v,ä0«v,ä-
ä$ 
ä Í
äº2«v(ä¾0«v(äÂ2«p8äÆ0«p8äÖ2ˆäÞ0ˆää´
å
èå22«x8å60«x8å .
åÈ¢
åè.
æ¢
æ2«v°æ0«v°æ2«x8æ&0«x8æt:
æ¨
ØæÌ
èçV2«v,çf0«v,çj2«x<çn0«x<çp.
çˆ.
çž2«x@ç¢2«x8ç¦0«x@ç®0«x8ç²2«v,ç¶0«v,ç¸D
çÂ2«x0çÆ@«x0çà:
è/
è22«x<è60«x<èL¢
èp
ØèŒ
Øè¨:
èÜÍ
èüf
é:
é$Í
é@:
éX:
éˆ
øéœl
é¼-
éÐ 
éü¢
ê
2«v°ê0«v°êL

êh

êv2«x8êz0«x8ê†2 êŠ0 ê

êÄ¢
êæ2 êê0 êð

ë.
ë,¢
ë@
ëL
ëv2«xHë‚@«xHëž2«xLë¢0«xLë¦2" ë®0" ëÀ
ëÊ2«xHëÎ2«xLëÒ0«xHëÚ0«xLëæ2Œëö0Œìî
ìD
ìR2ŒìV0Œìª2«xHì²0«xHìÈÍ
ìÒ2«yPìÖ@«yPìøl
í
í8Î
íPl
ívÌ2ízÌ0íÂ2«yXíÆ@«yXíä-
î2«xHî0«xHîR2"¸îV0"¸îZ2î^0îhÍ
îr2«yPîv@«yPî.
î .
î®2"°î²0"°î¸.
îÌ.
îìl
ï.
ï2"°ï0"°ï(.
ï8.
ïH.
ïT
ï€Î
ïŠ2«yXïŽ@«yXï˜.
ï¨.
ï¸.
ïÐ.
ïðl
ïþ2«yXð@«yXð.
ð(:
ð22«yXð6@«yXð<.
ðP.
ðl:
ðx.
ð.
ð¨:
ð´.
ðÌ.
ðä:
ðòÌ2ðöÌ0ñb2«yXñf@«yXñn2"°ñr0"°ñ€.
ñ.
ñ .
ñ´.
ñ¾2«yXñÂ@«yXñä-
ò2«yhò
@«yhò2«xHò0«xHò>2«ypòN@«ypòT
XòX!
ò`
òr2«ytò~0«ytó"2ñ<ó&0ñ<ó’2«yˆó–@«yˆó¦2«yxóª0«yxóÂ2«y”óâ0«y”ô2"°ô
0"°ô:
ô0:
ôP.
ôh´
ô|.
ô”S
ôž2«yvô®0«yvô¶2«ytôº0«ytôÄ
hôÒ2«ytôÖ0«ytôÞ2«yvôâ0«yvôøÍ
õ2«yPõ@«yPõ(l
õT
hõb2«ytõf0«ytõv2«yxõ~0«yxõ–2«yxõž0«yxõ¶2«yxõ¾0«yxõÖ2«yxõÞ0«yxõö2«yxõþ0«yxö2«yxö0«yxö$
öLÎ
ödl
öšÌ2öžÌ0öÖ2«ypöÚ2«yˆöÞ@«yˆöâ2«yöæ0«yöê@«yp÷2«yx÷0«yx÷"2«yˆ÷&@«yˆ÷b2«yh÷f@«yh÷x:
÷‚2«yt÷†0«yt÷
h÷–2«yv÷š0«yv÷¢2«yp÷¦0«yp÷º0«yp÷ô
h÷ú2«yˆ÷þ@«yˆø2«y„ø0«y„ø
2«y„ø0«y„ø&2«yXø*@«yXøH-
øf2«ytøj0«ytø‚2«yxøŠ2«y”øŽ0«yxø–0«y”øÂ2«y˜øÎ0«y˜øÒ2«yXøÖ2«yøâ@«yXøæ2«y€øê0«yøî2«yˆøú0«y€øþ2«yPù2«y|ù@«yˆù
2«y„ù0«yPù2«yxù2«ypù0«y|ù2«ytù"0«y„ù&2«yvù*0«yxù.2«y”ù20«ypù62«xLù:0«y”ùB0«ytùJ0«xLùN2«xHùR0«xHùZ0«yvùn2«xHùr2ðùv0«xHùz0ðù€î
ùŠ2"ÀùŽ0"Àù
ù 
Xù¦2«yhùª@«yhù¬!
ù¶2"Øùº0"Øù¼
ùÆ2«yXùÊ@«yXùÐ
xùèI
úg
úd
húx!
ú€
úI
úÂ2«yhúÒ@«yhû
û
xûl
Xûr2 ûv0 ûx
ûŽ2«ypû’@«ypûÂ2#ûÆ0#ûÈ
ü:
üâ2«y üæ@«y ý(´
ýà:
ýö2«y ýþ0«y þ´
þB2«y þF@«y þŒŽ
þž2«y¨þ¢0«y¨þ°f
þÔC
þè:
ÿ
ÿD»
ÿd´
ÿ„´
ÿ¨ë
ÿ°f
ÿÐC
ÿä:
ÿð!
ÿø
g
$I
B2«yÀF@«yÀP:
t
¸œ´
ü:
 
¸<G
TÍ
h:
ˆ?
’2«y¨–0«y¨øh
:
D¢
`k
¢
,.
R2«yÀV@«yÀ˜
Èìé
'
:
¤:
ð:
:
(:
€+
²2«y ¶@«y 4G
LÍ
œG
´Í
È:
Ðf
Ø+
ì:
<
ÈXG
pÍ
°
¶2«y º@«y Æ2«¸Ê@«¸Ò2«¸Þ@«¸"@«y lG
ˆÍ
’2«yÀ–@«yÀ¨:
²2«yÀ¶@«yÀ¼
Â2Æ0ÎÐ2ÒÐ0ÖÌ2ÚÌ0ÞÙ2âÙ0ú2«y°þ@«y°	2«y¸	@«y¸	
	 <
	,
	4
	D!
	L
	`g
	tI
	|
	Â2«y 	Æ@«y 

2«yÀ
@«yÀ
f

2«yÀ
"@«yÀ
0+

`´

ÌÍ

Ü:
:
Š2#’0#”—
¦2# ®0# °ç
 ¢
8
èX:
h
è€:
˜
èÊ2#@Î2#8Ò2#(Ö2!€þ0#@
0#8
0#(
0!€
 î

<‚

x‚

¤î

²2#H
º0#H
ȗ
2#0# ‚
:2#P>0#Phž
€‚
Š2#X’0#X”ç
¦2#®0#°

ò2!€ú0!€ü‚
:2«€>0«€LÍ
T
pÎ
ˆl
¤:
Èf
Ü:
,Ù
l˜
v2«€Hz0«€H|˜
†2«€IŠ0«€IŒ˜
š2«€J¢0«€JÖ2«€â2ê@«€ò2«€0
@«€2«€P@«€P
È2"0$!
,
8I
€g
Þ2«€ê0«€´
¨¢
Ø°
x:
/
¢2¦0è
Î
(f
<:
JÌ2NÌ0¢2«€X¦@«€XèÍ
$
@Î
d:
xf
Œ:
šÌ2žÌ0,:
@:
 
¶2º04:
”:
Æ2«€Xæ0«€X:
»
8:
€
 Î
´:
Äf
Ø:
Í
 
4:
<f
P:
^Ì2bÌ0Ð:
ì
n
(Ý
8b
P:
\
x,
ˆ?
 
¬r
Ú2«€`Þ@«€`ê2«€hò@«€hö@«€h@«€`2«€h"@«€hdG
|Í
:
¤:
ê2«€`î@«€`$È
‚2«€`†@«€`ú2«€pþ@«€p
2«€x@«€x@«€x2@«€p62«€xB@«€x|G
”Í
¬:
Ä:

2«€p@«€pDÈ
¦2«€`ª@«€`®2«€h²@«€h¶2«€pº@«€p¾2«€xÂ@«€xø.


"€.
".
"؞
%X0
%h0
*R2˜*V@˜*f2˜*v@˜*’2˜*–@˜*¾2«€€*Î0«€€,àÂ
-Â
-Z2«€€-b@«€€.È
/J
/hJ
/¦2/ª0/ÈJ
020
00.
0,|
062#`0>0#`0H|
1H›
1œ›
2’20¬2–00¬3d
¨3„
˜3¨
¨3È
˜44
¨4„
˜4œh
4¼
¨4ì.
5k
54
¨5h
˜5˜
¨5Ì.
5ô
¨6(
˜6L
¨6Œ

6¤
¨6ô
˜7
7,
¨7\.
7À
˜7Ü
¨84
˜8Dh
8d
¨8¨
˜8Ð
¨94
˜9D
9d
¨9ˆ
ˆ9ð
˜:
ˆ:@
˜:\
ˆ:„
˜: 
ˆ:Ð
˜:ì
ˆ<
¸<p
¨<‚i2<†i0<ˆ
¨<ÈJ
<à|
=*2#h=60#h>0
?S
@l.
A.2#ÀA60#ÀA:2#hAZ0#hC2A,C0A,D
D@
D¨
E
Eh
E¤S
E´.
FL
(Fˆ
F¤
(JP#&JX3JhØ&Jp3J€m&Jˆ3H& H3H&ðH3H & H(3H0&ðH83H@&0HH3HP&HX3H`&KðHh3Hp&LÐHx3H€&OpHˆ3H&PPH˜3H &Q0H¨3H°&R@H¸3HÀ&R°HÈ3HÐ&SHØ3Hà&S€Hè3Hð&SÐHø3I&T I3I&T@I3I &TÀI(3I0&UPI83I@&UÐIH3IP&V`IX3I`&VàIh3Ip&W Ix3I€&X@Iˆ3I&XÀI˜3I &Y@I¨3I°&YÀI¸3IÀ&ZPIÈ3IÐ&ZàIØ3Ià&[pIè3Ið&[ðIø3J&\ J3J&^ J3J &_0J(3J0&a J83J@&b JH3J˜&h`J 3J¨&i@J°3J¸&j`JÀ3JÈ&kJÐ3JØ&l Jà3Jè&nJð3Jø&nK3K&n°K3K&oðK 3K(&qàK03K8&r`K@3KH&vðKP3KX&xÀK`3Kh&xàKp3Kx&yK€3Kˆ&|`K3K˜&€°K 3K¨&°K°3K¸&‚pKÀ3KÈ&„pKÐ3KØ&„°Kà3Kè&… Kð3Kø&†pL3L&‡@L3L&ˆL 3L(&ˆpL03L8&‰`L@3LH&‹@LP3LX&ŒpL`3Lh&ŒÐLp3Lx&ŒðL€3Lˆ&€L3L˜&ŽpL 3L¨&L°3L¸&LÀ3LÈ&’àLÐ3LØ&“Là3Lè&•PLð3Lø&• M3M&™PM3M&›ÀM 3M(&ÀM03M8&ž M@3MH&¡PMP3MX&¤ M`3Mh&¥ÀMp3Mx&¦M€3Mˆ&ª€M3M˜&«0M 3M¨&®pM°3M¸&°°MÀ3MÈ&³pMÐ3MØ&³ÀMà3Mè&µ°Mð3Mø&¸@N3N&¸ N3N&¸ÐN 3N(&¹@N03N8&»N@3NH&¼ NP3NX&¾°N`3Nh&¿`Np3Nx&ÂàN€3Nˆ&ÃàN3N˜&ÅPN 3N¨&Æ@N°3N¸&Ç NÀ3NÈ&ǀNÐ3NØ&È Nà3Nè&È Nð3Nø&É@O3O&ÉàO3O&Ê°O 3O(&Ë O03O8&ËàO@3OH&ÌpOP3OX&ÌðO`3Oh&ÍpOp3Ox&͐O€3Oˆ&΀O3O˜&ÏPO 3O¨&ÏðO°3O¸&АOÀ3OÈ&ÑpOÐ3OØ&ÒOà3Oè&ҀOð3Oø&ÒÐP3P&ÕàP3P&ÕðP 3P(&×ðP03P8&ِP@3PH&Þ0PP3PX&ß0P`3Ph&â Pp3Px&æÐP€3Pˆ&ë0P3P˜&ò P 3P¨&ò0P°3P¸&òpPÀ3PÈ&ò€PÐ3PØ&ó0Pà3Pè&ôÐPð3Pø&úàQ3Q&üÀQ3Q&þQ 3Q(&0Q03Q8&PQ@3QH&`QP3QX& Q`3Qh&Qp3Qx&Q€3Qˆ&0Q3Q˜& Q 3Q¨&Q°3Q¸&QÀ3QÈ&pQÐ3QØ&ðQà3Qè&€Qð3Qø&R3R&!R3R&# R 3R(&$PR03R8&&ÐR@3RH&'pRP3RX&'ðR`3Rh&(ÀRp3Rx&)PR€3Rˆ&)ðR3R˜&0R 3R¨&1pR°3R¸&3€RÀ3RÈ&6`RÐ3RØ&8ÀRà3Rè&<ÀRð3Rø&@°S3S&H S3S&HàS 3S(&I`S03S8&JpS@3SH&LSP3SX&M°S`3Sh&PÀSp3Sx&Q0S€3Sˆ&Q`S3S˜&QS 3S¨&R S°3S¸&RÀSÀ3SÈ&SPSÐ3SØ&SðSà3Sè&T€Sð3Sø&U T3T&U°T3T&VT 3T(&V0T03T8&VðT@3TH&Y°TP3TX&Z`T`3Th&\@Tp3Tx&\`T€3Tˆ&\ÐT3T˜&] T 3T¨&^0T°3T¸&`TÀ3TÈ&``TÐ3TØ&cpTà3Tè&d`Tð3Tø&dpU3U&d U3U&e€U 3U(&fÐU03U8&hU@3UH&jUP3UX&kÀU`3Uh&nðUp3Ux&qàU€3Uˆ&rÐU3U˜&tU 3U¨&u@U°3U¸&x°UÀ3UÈ&y UÐ3UØ&yÐUà3Uè&~Uð3Uø&ÐV3V&V3V&ƒ V 3V(&„ V03V8&†ÀV@3VH&0VP3VX&  V`3Vh&¦ Vp3Vx&§V€3Vˆ&§V3V˜&¨V 3V¨&© V°3V¸&«ðVÀ3VÈ&¬VÐ3VØ&¬€Và3Vè&¬ Vð3Vø&®ðW3W&¯0W3W&¯ W 3W(&°`W03W8&·W@3WH&·0WP3WX&·PW`3Wh&¸Wp3Wx&¸0W€3Wˆ&¸PW3W˜&¸pW 3W¨&¸W°3W¸&¸°WÀ3WÈ&¹WÐ3WØ&¹`Wà3Wè&½ Wð3Wø&ÀàX3X&ÁðX3X&ÂX 3X(&ÃPX03X8&àX@3XH&ÃÐXP3XX&ÃðX`3Xh&ÄXp3Xx&ŀX€3Xˆ&Ç X3X˜&ÈX 3X¨&Í0X°3X¸&πXÀ3XÈ&ÒðXÐ3XØ&ÓðXà3Xè&Ö Xð3Xø&Ú`Y3Y&ÜàY3Y&Þ Y 3Y(&ހY03Y8&áY@3YH&â`YP3YX&épY`3Yh&ê€Yp3Yx&ìY€3Yˆ&ðY3Y˜&ö€Y 3Y¨&ö°Y°3Y¸&ùàYÀ3YÈ&úÐYÐ3YØ&û Yà3Yè&ÿ°Yð3Yø&PZ3Z&pZ3Z&PZ 3Z(&ÐZ03Z8&`Z@3ZH&°ZP3ZX& Z`3Zh&€Zp3Zx& Z€3Zˆ&@Z3Z˜&PZ 3Z¨&Z°3Z¸&
°ZÀ3ZÈ&
 ZÐ3ZØ&`Zà3Zè&ÀZð3Zø&Ð[3[&À[3[& [ 3[(&À[03[8&ð[@3[H&Ð[P3[X&@[`3[h&à[p3[x&€[€3[ˆ&ð[3[˜&`[ 3[¨&[°3[¸& [À3[È&à[Ð3[Ø&@[à3[è&[ð3[ø& \3\&€\3\&Ð\ 3\(&°\03\8& P\@3\H&!@\P3\X&!\`3\h&!à\p3\x&"€\€3\ˆ&#\3\˜&$ \ 3\¨&$P\°3\¸&$ \À3\È&$Ð\Ð3\Ø&%\à3\è&&\ð3\ø&(P]3]&(]3]&(°] 3](&,p]03]8&,]@3]H&-]P3]X&-@]`3]h&-]p3]x&-ð]€3]ˆ&.€]3]˜&.°] 3]¨&.ð]°3]¸&0 ]À3]È&9]Ð3]Ø&:p]à3]è&:€]ð3]ø&: ^3^&; ^3^&<À^ 3^(&>^03^8&>À^@3‚&ð‚0&
¤‚8&‰‚@&-¸‚H&4@‚P&WÈ‚X&'À‚`&W ‚h&)ð‚p&\¸‚x&)ð‚€&4@‚ˆ&W€‚&'¨‚˜&‚ &V‚¨&‰ ‚°&V˜‚¸&,ˆ‚À&-Ø‚È&(è‚Ð&'À‚Ø&'‚è&+‚ð&'Xƒ&( ƒ&(ƒ&³øƒ&'8ƒ(&'Àƒ0&'ƒ@&+ƒH&'XƒX&±Pƒ`&Œøƒh&“ƒp&mƒˆ&
؃&m¨ƒ¨&³àƒÀ&
¤ƒÈ&,ˆƒÐ&'@ƒà&(„&ˆ„&% „ &Ä„(&%¸„8&„@&%Ø„P&<„X&%ð„p&x„x&&„&´„˜&&(„°&ð„¸&&H„Ð&	,„Ø&&h„ð&	h„ø&&ˆ…&	¤…&&¨…0&	ä…8&&È…P&
$…X&&è…p&
d…x&'…ˆ&`…&'(…¨&ˆ…°&%€…È&à…Ð&'`…à&
…è&'€…ø&
H†&'˜†&
€†&'°†(&
¸†0&'Ȇ@&
ð†H&'à†X&,†`&'ø†p&\†x&(†ˆ&”†&((† &à†¨&(@†¸&,†À&(X†Ð& †Ø&(p†è&p†ð&(ˆ‡&´‡&( ‡&ø‡ &(¸‡8&L‡@&(ЇP&è‡X&(ð‡h&$‡p&)‡€&`‡ˆ&) ‡˜&œ‡ &)8‡°&؇¸&)P‡È&‡Ð&)h‡à&P‡è&)€‡ø&Œˆ&)˜ˆ&Ȉ&)°ˆ(&ˆ0&)Ȉ@&8ˆH&)àˆX&tˆ`&)øˆp&¨ˆx&*ˆˆ&䈐&*(ˆ &ˆ¨&*@ˆ¸&TˆÀ&*XˆÐ&ˆˆØ&*pˆè&Ĉð&*ˆ‰&ø‰&* ‰ &4‰(&*¸‰@&|‰H&*؉`&̉h&*ø‰€&$‰ˆ&+‰˜&„‰ &+8‰°&̉¸&+P‰È&‰Ð&+h‰à&D‰è&+€‰ø&ˆŠ&+˜Š&ÀŠ&+°Š(&Š0&+ÈŠ@&xŠH&+àŠ`&ÈŠh&+øŠ€&XŠˆ&,Š &”Š¨&,8Š¸&øŠÀ&,XŠØ&(Šà&,pŠø&X‹&,‹&|‹&,°‹(&&P‹0&,È‹@&%\‹H&,à‹X&%Ћ`&,ø‹p&$à‹x&-‹&H‹ &-(‹°&",‹¸&-P‹Ð&%$‹Ø&-h‹ð&!ð‹ø&³`Œ&HŒ&-¨Œ(&HŒ8&-ÈŒH&HŒX&-èŒh&HŒx&.Œˆ&HŒ˜&.(Œ¨&HŒ¸&.HŒÈ&HŒØ&.hŒè&HŒø&.ˆ&H&.¨(&H8&.ȍH&HX&.èp&H€&/&H &/0°&HÀ&/PÐ&Hà&/pð&HŽ&/Ž&HŽ &/°Ž0&HŽ@&/ÐŽP&HŽ`&/ðŽp&
¤Žx&/`Ž€&)0Žˆ&,ˆŽ&0Ž &
¤Ž¨&/€Ž°&)0Ž¸&,ˆŽÀ&0@ŽÐ&
¤ŽØ&/ Žà&)0Žè&,ˆŽð&0p&
¤&/À&)0&,ˆ &0 0&
¤8&/à@&)0H&,ˆP&0Џ`&
¤h&0 p&)x&,ˆ€&1&
¤˜&0P &)¨&,ˆ°&10À&
¤È&0€Ð&)Ø&,ˆà&1`ð&
¤ø&0°&)&,ˆ&1 &
¤(&0à0&)8&,ˆ@&1ÀP&
¤X&/``&)h&,ˆp&1ð€&
¤ˆ&/€&)˜&,ˆ &2 °&
¤¸&/ À&)È&,ˆÐ&2Pà&
¤è&/Àð&)ø&,ˆ‘&2€‘&
¤‘&/à‘ &)‘(&,ˆ‘0&2°‘@&
¤‘H&2‘P&,ˆ‘X&2à‘h&
¤‘p&2À‘x&,ˆ‘€&3‘&
¤‘˜&/`‘ &)‘¨&,ˆ‘°&30‘À&
¤‘È&/à‘Ð&)‘Ø&,ˆ‘à&3`‘ð&
¤‘ø&0 ’&,ˆ’&3’&
¤’ &0à’(&,ˆ’0&3¸’@&
¤’H&1’P&,ˆ’X&3à’h&
¤’p&1Ð’x&,ˆ’€&4’&
¤’˜&(P’ &3’¨&'À’°&(8’¸&)Ø’À&3’È&)ð’Ð&,ˆ’Ø&40’ð&
¤’ø&(P“&3“&'À“&'À“&*“ &)“(&'“8&)“@&(8“H&,ˆ“P&4ˆ“`&
¤“h&'À“p&'X“€&'À“ˆ&,ˆ“&5“ &
¤“¨&( “°&'Ø“¸&,ˆ“À&5@“Ð&
¤“Ø&'Ø“à&'Ø“è&,ˆ“ð&5p”&
¤”&.”&'ð”&.” &'ð”(&.”0&'ð”8&,ˆ”@&5 ”P&
¤”X&.8”`&'ð”h&.8”p&'ð”x&,ˆ”€&5ð”&
¤”˜&(” &(”¨&,ˆ”°&60”À&
¤”È&(”Ð&(”Ø&(”à&,ˆ”è&6`”ø&
¤•&( •&(•&,ˆ•&6˜•(&
¤•0&-Ø•8&(°•@&,ˆ•H&6È•X&
¤•`&(8•h&( •p&(P•x&( •€&,ˆ•ˆ&6ø•˜&
¤• &( •¨&(8•°&( •¸&(P•À&,ˆ•È&78•Ø&
¤•à&(8•è&7H•ð&(P•ø&7H–&,ˆ–&7x–&
¤– &(8–(&(8–0&7ˆ–8&(P–@&(P–H&7ˆ–P&,ˆ–X&7¸–h&
¤–p&'À–x&5–€&'X–&7–˜&(8– &-ø–¨&)–°&'8–À&5–È&'X–Ø&(P–à&7H–è&-ø–ð&)–ø&'8—&,ˆ—&8— &
¤—(&'À—0&5—8&'X—H&(8—P&7—X&(P—`&( —h&(8—p&-ø—x&)—€&'8—&5—˜&'X—¨&(P—°&( —¸&-ø—À&)—È&'8—Ø&,ˆ—à&8À—ð&
¤—ø&(P˜&7˜&(8˜&( ˜&(8˜ &(8˜(&,ˆ˜0&9˜@&
¤˜H&(P˜P&(P˜X&(P˜`&7˜h&(8˜p&( ˜x&,ˆ˜€&9à˜&
¤˜˜&(P˜ &(P˜¨&(h˜°&'ؘ¸&(8˜À&7˜È&(8˜Ð&( ˜Ø&,ˆ˜à&:0˜ð&$˜ø&:™&
¤™&-ø™&)H™ &,ˆ™(&:¨™8&
¤™@&-ø™H&)`™P&,ˆ™X&:Ø™h&
¤™p&-ø™x&)x™€&,ˆ™ˆ&;™˜&
¤™ &)H™¨&,ˆ™°&;8™À&
¤™È&)`™Ð&,ˆ™Ø&;`™è&
¤™ð&)x™ø&,ˆš&;ˆš&
¤š&-¸š &)Àš(&,ˆš0&;°š@&
¤šH&;ÀšP&,ˆšX&;àšh&Hšx&<šˆ&Hš˜&<(š¨&
¤š°&( š¸&+HšÀ&,ˆšÈ&<HšØ&
¤šà&( šè&+`šð&,ˆšø&<x›&
¤›&<X›&+¨› &,ˆ›(&<¨›8&
¤›@&+›H&+¨›P&,ˆ›X&<Ø›h&
¤›p&+H›x&+¨›€&,ˆ›ˆ&=›˜&
¤› &-Ø›¨&<¸›°&,ˆ›¸&=8›È&
¤›Ð&-Ø›Ø&<è›à&,ˆ›è&=h›ø&
¤œ&-Øœ&<Xœ&,ˆœ&=˜œ(&
¤œ0&-Øœ8&=œ@&,ˆœH&=ÈœX&
¤œ`&<ˆœh&+¨œp&,ˆœx&=øœˆ&
¤œ&+`œ˜&+¨œ &,ˆœ¨&>(œ¸&
¤œÀ&7œÈ&'ÀœÐ&7œØ&=œà&'Xœð&6@œø&<8&,h&<X&'X &<8(&,h0&<8&,ˆ@&>XX&
¤`&-øh&)p&>hx&,ˆ€&>ð&
¤˜&:¸ &'؝¨&+x°&)¸&(8À&:¸È&(PÐ&,ˆØ&?0è&
¤ð&(8ø&:èž&(hž&'ž&)Hž &)¨ž(&(Pž0&:èž8&,ˆž@&?ˆžP&
¤žX&(8ž`&:èžh&(hžp&'ž€&)Hžˆ&)¨ž&(Pž˜&;ž &,ˆž¨&?ðž¸&
¤žÀ&-ØžÈ&( žÐ&)žØ&,ˆžà&@Xžð&
¤žø&'ÀŸ&+xŸ&'XŸ&@hŸ &,ˆŸ(&@Ÿ8&
¤Ÿ@&5€ŸH&+HŸP&'XŸ`&( Ÿh&(Ÿp&,ˆŸx&@ØŸˆ&
¤Ÿ&5€Ÿ˜&<XŸ &'XŸ°&( Ÿ¸&(ŸÀ&,ˆŸÈ&A(ŸØ&
¤Ÿà&)0Ÿè&,ˆŸð&Ax &
¤ &-ø &) &,ˆ  &A  0&
¤ 8&-ø @&) H&,ˆ P&AР`&
¤ h&. p&) x&,ˆ €&B &
¤ ˜&.  &) ¨&,ˆ °&B0 À&
¤ È&A° Ð&-¸ Ø&) à&,ˆ è&B` ø&
¤¡&'Ø¡&)¡&( ¡&,ˆ¡ &B˜¡0&
¤¡8&'À¡@&+x¡H&,ˆ¡P&BСh&
¤¡p&;À¡x&(8¡€&@h¡ˆ&'À¡&+¨¡˜&(P¡ &( ¡¨&)¡°&,ˆ¡¸&C¡È&
¤¡Ð&'À¡Ø&+x¡à&'X¡ð&C¡ø&,ˆ¢&Ch¢&
¤¢&( ¢ &(8¢(&'À¢0&(8¢8&)¢@&'À¢H&(P¢P&+`¢X&(P¢`&( ¢h&)¢p&,ˆ¢x&C°¢ˆ&
¤¢&(8¢˜&CÀ¢ &(P¢¨&)¢°&,ˆ¢¸&D(¢È&
¤¢Ð&C¢Ø&D8¢à&,ˆ¢è&Dh¢ø&
¤£&(8£&'À£&+x£&(8£ &?@£(&(P£0&'X£@&(h£H&CÀ£P&(P£X&,ˆ£`&D˜£p&
¤£x&-Ø£€&7H£ˆ&'£˜&-Ø£ &+À£¨&D¨£°&+ð£À&(£È&,ˆ£Ð&E£à&
¤£è&5€£ð&)À£ø&(8¤&(8¤&@ ¤&(P¤&@ ¤ &E ¤(&(P¤0&+x¤8&'X¤H&C¤P&,ˆ¤X&E€¤h&
¤¤p&(8¤x&'À¤€&+x¤ˆ&(8¤&?@¤˜&(P¤ &'ؤ¨&(h¤°&>8¤¸&)¨¤À&'X¤Ð&(8¤Ø&-ø¤à&)¨¤è&(P¤ð&(h¤ø&)¥&(P¥&,ˆ¥&F¥ &
¤¥(&'¥8&-Ø¥@&+À¥H&F¥P&+ð¥`&(¥h&( ¥p&,ˆ¥x&FÀ¥ˆ&
¤¥&'Ø¥˜&(8¥ &(8¥¨&Cx¥°&(h¥¸&@ ¥À&FÐ¥È&(P¥Ð&+x¥Ø&'X¥è&@h¥ð&(P¥ø&+x¦&'X¦&@h¦&( ¦ &@h¦(&( ¦0&,ˆ¦8&G(¦H&
¤¦P&'À¦X&(8¦`&5€¦h&)À¦p&+x¦x&(8¦€&G8¦ˆ&'ئ&=x¦˜&(P¦ &)¦¨&'X¦¸&Aà¦À&( ¦È&(P¦Ð&)¦Ø&( ¦à&,h¦è&(P¦ð&(¦ø&,ˆ§&Gè§&
¤§&-ا &( §(&FЧ0&,ˆ§8&H°§H&
¤§P&(8§X&Bà§`&(P§h&Gø§p&,ˆ§x&H览&
¤§&Hø§˜&6¨§ &,ˆ§¨&I(§¸&
¤§À&Hø§È&(§Ð&,ˆ§Ø&IX§è&
¤§ð&(8§ø&E¨&(P¨&Gø¨&,ˆ¨&Iˆ¨(&
¤¨0&I˜¨8&6¨¨@&,ˆ¨H&IȨ`&
¤¨h&'À¨p&.بx&)¨€&( ¨ˆ&.x¨&)`¨˜&,ˆ¨ &Iø¨¸&
¤¨À&'À¨È&.ø¨Ð&)¨Ø&( ¨à&.˜¨è&)`¨ð&,ˆ¨ø&JP©&
¤©&'À© &/ ©(&)©0&( ©8&.¸©@&)`©H&,ˆ©P&J¨©h&
¤©p&Jh©x&(8©€&J©ˆ&(P©&J©˜&,ˆ© &K©¸&
¤©À&JÀ©È&(8©Ð&Jh©Ø&(P©à&Jh©è&,ˆ©ð&KPª&
¤ª&JÀª&(8ª &Kª(&(Pª0&Kª8&,ˆª@&K ªP&
¤ªX&.xª`&)Hªh&)¨ªp&,ˆªx&Kðªˆ&
¤ª&.˜ª˜&)Hª &)¨ª¨&,ˆª°&L(ªÀ&
¤ªÈ&LªÐ&(8ªØ&Lªà&(Pªè&L8ªð&,ˆªø&L`«&
¤«&J«&( « &L«(&,ˆ«0&L¨«@&
¤«H&Jh«P&( «X&L8«`&,ˆ«h&Là«x&
¤«€&.¸«ˆ&)H«&)¨«˜&,ˆ« &M«°&
¤«¸&JÀ«À&( «È&M(«Ð&,ˆ«Ø&MP«è&
¤«ð&K«ø&( ¬&7ˆ¬&( ¬&Lp¬&,ˆ¬ &Mˆ¬0&
¤¬8&L8¬@&(8¬H&L8¬P&(P¬X&M(¬`&,ˆ¬h&MЬx&
¤¬€&Kh¬ˆ&( ¬&7ˆ¬˜&( ¬ &Mନ&,ˆ¬°&N¬À&
¤¬È&Lp¬Ð&(8¬Ø&Lp¬à&(P¬è&M(¬ð&,ˆ¬ø&N`­&
¤­&JÀ­&M˜­ &( ­(&M˜­0&M(­8&,ˆ­@&N¨­X&
¤­`&/à­h&Aà­p&)­x&/à­€&@h­ˆ&)­&,ˆ­˜&Nð­¨&
¤­°&(P­¸&(h­À&( ­È&(8­Ð&,ˆ­Ø&OH­è&
¤­ð&(P­ø&(P®&(P®&(h®&( ®&(8® &( ®(&(8®0&( ®8&(8®@&,ˆ®H&Oˆ®X&
¤®`&(P®h&(P®p&(P®x&6@®€&(8®ˆ&,ˆ®&Oø® &
¤®¨&5P®°&)Ø®¸&)®À&( ®È&)ð®Ð&,ˆ®Ø&P@®è& ®ð&Pˆ¯&
¤¯&<8¯&( ¯&)ð¯ &,ˆ¯(&P ¯8&
¤¯@&<¯H&( ¯P&)ð¯X&,ˆ¯`&Pدp&
¤¯x&*8¯€&'À¯ˆ&'¯˜&=¯ &'X¯°&'¯À&)¯È&,ˆ¯Ð&Q¯à&
¤¯è&'À¯ð&3¯ø&)Ø°&( °&)Ø°&,ˆ°&Q€°(&
¤°0&'À°8&(8°@&)ð°H&(P°P&3°X&)ð°`&,ˆ°h&QÈ°€&
¤°ˆ&B¨°&+Ø° &OX°¨&*8°°&L¸°¸&OX°À&*P°È&/€°Ð&,°à&,ˆ°è&R±&
¤±&B¨±&+ر &OX±(&*h±0&Lð±8&OX±@&*€±H&/ ±P&,±`&,ˆ±h&R˜±€&
¤±ˆ&B¨±&+ر &OX±¨&*h±°&M˜±¸&OX±À&*€±È&/ ±Ð&,±à&,ˆ±è&S²&
¤²&B¨²&+ز &OX²(&*˜²0&N¸²8&OX²@&*°²H&/À²P&,²`&,ˆ²h&S˜²€&
¤²ˆ&B¨²&+ز &OX²¨&*˜²°&N(²¸&OX²À&*°²È&/À²Ð&,²à&,ˆ²è&T³&
¤³&B¨³&+س &OX³(&*˜³0&M`³8&OX³@&*°³H&/À³P&,³`&,ˆ³h&T˜³x&³€&U³&
¤³˜&'³¨&U(³°&,ˆ³¸&U0³È&
¤³Ð&'³à&U(³è&,ˆ³ð&Uh´&ð´&U ´0&ð´@&UÈ´P&
¤´X&(˜´`&(8´h&U¸´p&)Ø´x&(8´€&(È´ˆ&U¸´&)ð´˜&,¨´ &(P´¨&U¸´°&)ð´¸&(P´À&(´È&-Ø´Ð&,ˆ´Ø&Uð´è&
¤´ð&5´ø&'Xµ&U¸µ&)ص&(èµ &(Pµ(&U¸µ0&)ðµ8&(Pµ@&( µH&(8µP&(°µX&(µ`&(Pµh&,ˆµp&Vˆµ€&
¤µˆ&-¸µ&V˜µ˜&,ˆµ &W µ°&ðµÀ&WPµÐ&€µà&Wpµð&ð¶&W¶&€¶(&W°¶8&
¤¶@&W€¶H&W ¶P&)ضX&,ˆ¶`&Wضp&ð¶€&X¶˜&
¤¶ &%°¶¨&4@¶°&W€¶¸&W`¶À&)ضÈ&W ¶Ð&)ð¶Ø&-ضà&4@¶è&Wȶð&,ˆ¶ø&X0·&H·&X¨·(&H·8&XÈ·H&H·X&Xè·h&H·x&Y·&H· &Y(·°&(·À&YP·Ð&(·à&Yp·ð&
¤·ø&B¨¸&+ظ&OX¸&*¸ &Y`¸(&+ð¸8&,ˆ¸@&Y¸P&
¤¸X&Y¸`&Y`¸h&Y@¸p&Y`¸x&,ˆ¸€&Yð¸&
¤¸˜&X¸¸ &Y`¸¨&,ˆ¸°&Z0¸À&
¤¸È&-ظÐ&+ظà&Z@¸è&+ð¸ø&,ˆ¹&Z`¹&
¤¹&'À¹ &2ð¹(&( ¹0&*¹8&,ˆ¹@&Z°¹P&
¤¹X&'À¹`&(8¹h&A°¹p&( ¹x&'À¹€&(h¹ˆ&* ¹&,À¹˜&(P¹ &,ˆ¹¨&Zð¹¸&
¤¹À&'À¹È&'¹Ø&'¹è&?¹ð&'Xº&'º&)º&,ˆº &[Xº0&
¤º8&'Àº@&'ºP&'º`&?ºh&'Xºx&'ºˆ&)º&,ˆº˜&[к¨&(º¸&\HºÈ&(ºØ&\hºè&(ºø&\ˆ»&ð»&\¨»(&
¤»0&\˜»8&\¸»@&)ð»H&,ˆ»P&\È»`&
¤»h&WÈ»p&+¨»x&'X»ˆ&W軐&\Ø»˜&-Ø» &X »¨&)ð»°&<»¸&,h»À&WÈ»È&-¸»Ð&+»Ø&'X»è&<8»ð&,h»ø&'¼&V˜¼&,ˆ¼&]¼(&ð¼8&]ȼP&
¤¼X&/@¼`&]ؼh&)ð¼p&,ˆ¼x&]輈&
¤¼&.˜¼˜&]ؼ &)ð¼¨&,ˆ¼°&^(¼À&
¤¼È&.x¼Ð&]ؼØ&)ð¼à&,ˆ¼è&^`¼ø&
¤½&³p½&'½&)½ &,ˆ½(&^˜½@&
¤½H&'À½P&'½`&<X½h&'X½x&'½ˆ&)½&'½ &)½¨&,ˆ½°&^ؽÀ&
¤½È&'À½Ð&(8½Ø&HÀ½à&(P½è&( ½ð&(8½ø&Fо&(P¾&,ˆ¾&_`¾ &
¤¾(&^¨¾0&'À¾8&)ð¾@&,ˆ¾H&_À¾X&
¤¾`&^¨¾h&'À¾p&)ؾx&Aྀ&5P¾ˆ&( ¾&)ð¾˜&* ¾ &,ˆ¾¨&_ø¾¸&
¤¾À&+x¾È&'X¾Ø&'¾è&`¾ð&,ˆ¾ø&`X¿&
¤¿&]Ø¿&)Ø¿ &_p¿(&7¿0&^ð¿8&`¿@&,ˆ¿H&`¨¿X&
¤¿`&`¸¿h&5€¿p&)¨¿x&'X¿ˆ&'8¿˜&,ˆ¿ &`ø¿°&
¤¿¸&6@¿À&^¨¿È&'À¿Ð&)Ø¿Ø&5P¿à&)¿è&,ˆ¿ð&aPÀ&
¤À&_ÐÀ&'ÀÀ&(8À &@ À(&-ØÀ0&aÀ8&(PÀ@&`hÀH&a`ÀP&,ˆÀX&a Àh&
¤Àp&]ØÀx&)ØÀ€&HÀÀˆ&( À&^ðÀ˜&`À &,ˆÀ¨&bÀ¸&
¤ÀÀ&bÀÈ&'ÀÀÐ&'XÀà&'8Àð&,ˆÀø&bXÁ&
¤Á&(Á&^¨Á &'ÀÁ(&)ØÁ0&5PÁ8&)Á@&,ˆÁH&b¨ÁX&
¤Á`&_ÐÁh&bhÁp&b¸Áx&,ˆÁ€&bøÁ&
¤Á˜&a°Á &Y Á¨&Z@Á°&,ˆÁ¸&c0ÁÈ&
¤ÁÐ&c@ÁØ&,ˆÁà&chÁð&
¤Áø&cÂ&Y Â&Z@Â&,ˆÂ&cÂ(&
¤Â0&( Â8&a°Â@&7ÂH&5€ÂP&+HÂX&'XÂh&'ØÂp&)Âx&Zp€&'8&(˜&Y  &,ˆ¨&cȸ&
¤ÂÀ&( ÂÈ&cÂÐ&7ÂØ&5€Âà&+HÂè&'XÂø&'ØÃ&)Ã&ZpÃ&'8à &(Ã(&Y Ã0&,ˆÃ8&dXÃH&
¤ÃP&]ØÃX&)ØÃ`&( Ãh&^Ãp&c@Ãx&]ØÀ&)ðÈ&,ˆÐ&dèà&
¤è&]Øð&)Øø&( ÃÀ&^8ÃÈ&c@ÃÐ&]ØÃØ&)ðÃà&,ˆÃè&e@Ãø&
¤Ä&(˜Ä&'ÀÄ&+xÄ&'XÄ(&(Ä0&,hÄ8&-ØÄ@&+ØÄP&(˜ÄX&OXÄ`&)Äh&AàÄp&'ðÄx&c@Ā&+ðĐ&,ˆĘ&e˜Ĩ&
¤Ä°&)Øĸ&c@ÄÀ&,ˆÄÈ&fHÄØ&
¤Äà&'ØÄè&[hÄð&'ÀÄø&'Å&'Å&?Å &'XÅ0&'Å@&)ÅH&'ÅX&)Å`&'ÀÅh&7Åp&-ØÅx&( ŀ&>hň&'XŘ&6¨Å &<Ũ&'8Ÿ&(ÅÀ&<8ÅÈ&,ˆÅÐ&fxÅè&
¤Åð&'ÀÅø&+¨Æ&'XÆ&,hÆ&'ØÆ &*Æ(&]ØÆ0&)ØÆ8&fˆÆ@&'XÆP&( ÆX&(8Æ`&( Æh&(8Æp&(8Æx&]Øƀ&)Øƈ&AˆƐ&( Ƙ&]ØÆ &)Øƨ&E Æ°&7Ƹ&)ÆÀ&(PÆÈ&-ØÆÐ&D8ÆØ&(PÆà&2ðÆè&(PÆð&AàÆø&'8Ç&(Ç&,ˆÇ&g€Ç0&
¤Ç8&'ÀÇ@&+¨ÇH&'XÇX&(Ç`&(Çh&<Çp&,hÇx&(8ǀ&'ÀLj&(8ǐ&*ǘ&'Ǩ&+Ç°&'ÀǸ&'XÇÈ&(PÇÐ&2ðÇØ&(PÇà&AàÇè&'ÀÇð&+¨Çø&'XÈ&(È&(È&(È &<È(&,hÈ0&(8È8&(8È@&-ØÈH&-ØÈP&(PÈX&(PÈ`&g˜Èh&6¨Èp&+¨Èx&'XȈ&(Ȑ&( Ș&'XȨ&@hÈ°&<8ȸ&,hÈÀ&(ÈÈ&(ÈÐ&(ÈØ&<Èà&,ˆÈè&hÈÈø&
¤É&³pÉ&)É&4@É&³pÉ &,ˆÉ(&j˜É8&
¤É@&³pÉH&)ðÉP&/àÉX&j¨É`&,ˆÉh&jØÉx&
¤ɀ&³pɈ&* ɐ&/`ɘ&j¨É &,ˆɨ&kɸ&
¤ÉÀ&³pÉÈ&*PÉÐ&/€ÉØ&j¨Éà&,ˆÉè&kXÉø&
¤Ê&³pÊ&*€Ê&/ Ê&j¨Ê &,ˆÊ(&k˜Ê8&
¤Ê@&³pÊH&*°ÊP&/ÀÊX&j¨Ê`&,ˆÊh&kØÊx&
¤ʀ&³pʈ&/àʐ&Aàʘ&)Ê &'XÊ°&-Øʸ&k(ÊÀ&'8ÊÐ&,ˆÊØ&lÊè&
¤Êð&5€Êø&* Ë&2ðË&( Ë&3 Ë&B¨Ë &+ØË0&'ÀË8&*Ë@&OXËH&* ËP&2ðËX&-øË`&3 Ëh&,Ëx&(ˀ&,ˆˈ&lˆË &
¤˨&³pË°&'Ø˸&A°ËÀ&3 ËÈ&j¨ËÐ&l˜ËØ&,ˆËà&m8Ëð&
¤Ëø&,ˆÌ&% Ì&€Ì &%HÌ(&m°Ì8&
¤Ì@&mÈÌH&3ÌP&,ˆÌX&mØÌp&ðÌx&%HÌø&nÍ&€Í&n(Í &n¨Í8&
¤Í@&3ÍH&,ˆÍP&nÐÍ`&
¤Íh&2ðÍp&'ÀÍx&*̀&A°͈&3ð͐&O͘&,ˆÍ &oÍ°&
¤͸&nèÍÀ&oÍÈ&,ˆÍÐ&oPÍè&
¤Íð&2ðÍø&ZÀÎ&,ˆÎ&o€Î&ðÎ(&o¸Î@&(ÎP&oØÎ`&
¤Îh&l(Îp&³pÎx&mè΀&)ØΈ&jèΐ&oÈΘ&)ðΠ&-ØΨ&k(ΰ&mPθ&l(ÎÀ&,ˆÎÈ&pÎØ&
¤Îà&oÈÎè&)ØÎð&nèÎø&o˜Ï&oðÏ&oÈÏ&)ØÏ&mèÏ &)ðÏ(&,ˆÏ0&pxÏH&$DÏP&pàÏ`&(Ïp&qψ&
¤ϐ&'ÀϘ&'XϨ&(8Ï°&5€ϸ&(hÏÀ&nèÏÈ&o˜ÏÐ&pøÏØ&'XÏè&6@Ïð&(PÏø&,hÐ&(PÐ&)ØÐ&'8Ð &6pÐ(&<8Ð0&,ˆÐ8&q ÐP&
¤ÐX&nÀÐ`&'ÀÐh&(8Ðp&n Ðx&>8Ѐ&'XА&5€И&(hР&)ØШ&3а&)Øи&qÐÀ&5ÐÈ&'XÐØ&6¨Ðà&6¨Ðè&(PÐð&(Ðø&,hÑ&(PÑ&3pÑ&'8Ñ &(PÑ(&6pÑ0&-ØÑ8&,ˆÑ@&qèÑX&
¤Ñ`&rÑh&'ÀÑp&'Xр&nèш&'Àѐ&oј&( Ñ &*Ѩ&<Ñ°&,ˆѸ&rðÑÈ&
¤ÑÐ&5€ÑØ&sÑà&'XÑð&(Ñø&6¨Ò&6¨Ò&<Ò&'8Ò &<8Ò(&,ˆÒ0&shÒH&HÒX&sàÒp&
¤Òx&søҀ&)҈&=xҐ&,ˆҘ&tÒ°&
¤Ò¸&mèÒÀ&)ØÒÈ&3ÒÐ&'ÀÒØ&*Òà&søÒè&)¨Òð&( Òø&* Ó&,ˆÓ&tHÓ &
¤Ó(&( Ó0&-ØÓ8&+ØÓH&'ØÓP&OXÓX&)Ó`&*Óh&'ØÓp&'ÀÓx&X¸Ӏ&+ӈ&'XӘ&<¸Ó &'8Ó°&+Ó¸&'XÓÈ&OXÓÐ&PÓØ&6¨Óà&6¨Óè&<Óð&,hÓø&+ðÔ&(Ô&(Ô&<8Ô &,ˆÔ(&t¸Ô8&
¤Ô@&(8ÔH&W€ÔP&X ÔX&)ØÔ`&)Ôh&\¸Ôp&)ØÔx&X Ԁ&)ØԈ&)Ԑ&5€Ԙ&(PÔ &tÐÔ¨&'XÔ¸&6¨ÔÀ&'ÀÔÈ&-øÔÐ&)ÔØ&'8Ôè&'ÀÔð&X Ôø&PPÕ&,ˆÕ&uØÕ&
¤Õ &W€Õ(&\¸Õ0&)ØÕ8&'ÀÕ@&X ÕH&)ØÕP&<XÕX&'XÕh&'ØÕp&X Õx&)ØՀ&)Ո&*Ր&X¸՘&<¸Õ &'XÕ°&-øÕ¸&X ÕÀ&PPÕÈ&'8ÕØ&(Õà&(Õè&,ˆÕð&v¸Ö&
¤Ö&vÈÖ&X¸Ö &uèÖ(&,ˆÖ0&w ÖH&ðÖX&wàÖh&
¤Öp&%ÐÖx&wøր&)Øֈ&'֘&)0Ö &)Ö¨&wøÖ°&)ØÖ¸&-øÖÀ&)ÖÈ&'ÀÖÐ&'Öà&+Öè&'XÖø&(×&-Ø×&wø×&)ð×&,ˆ× &x×0&
¤×8&x×@&(8×H&uè×P&'À×X&(h×`&* ×h&B¨×p&(P×x&'À׀&7ˆ׈&+Øט&2ð× &OXר&*×°&'Ø׸&* ×À&+ð×Ð&(×Ø&,ˆ×à&xÐ×ð&
¤×ø&w¸Ø&(Ø&*Ø&,ˆØ&yØ(&
¤Ø0&'Ø@&uèØH&6@ØP&,ˆØX&yÈØh&
¤Øp&X Øx&)Ø؀&Aà؈&X ؐ&)ðؘ&Y@Ø &uèب&6@Ø°&,ˆظ&zØÈ&ðØØ&zhØè&
¤Øð&zxØø&P°Ù&,ˆÙ&zˆÙ&
¤Ù &'Ù0&zxÙ8&)ðÙ@&,ˆÙH&z¸ÙX&
¤Ù`&zxÙh&)ØÙp&'Xـ&,hو&'٘&V˜Ù &,ˆÙ¨&zøÙÀ&
¤ÙÈ&jèÙÐ&,ˆÙØ&{XÙè&
¤Ùð&w¸Ùø&pÚ&'¨Ú&
¤Ú&{pÚ&zÈÚ &,ˆÚ(&{ˆÚ@&
¤ÚH&l(ÚP&³pÚX&'¨Ú`&
¤Úh&{pÚp&zÈÚx&,ˆڀ&{Øڐ&
¤ژ&{Ú &'¨Ú¨&,ˆÚ°&{pÚ¸&pˆÚÀ&z˜ÚÈ&,ˆÚÐ&|0Úà&
¤Úè&{Úð&'Û&uèÛ&'¨Û&4 Û&{pÛ &'ÀÛ(&k(Û0&B¨Û8&+ØÛH&OXÛP&*ÛX&k(Û`&+ðÛp&l(Ûx&,ˆۀ&|€ې&
¤ۘ&zxÛ &)ØÛ¨&'XÛ¸&|ÛÀ&'¨ÛÈ&ZÀÛÐ&{pÛØ&,hÛà&'Ûð&uèÛø&'ÀÜ&(8Ü&xÜ&'ÀÜ&(8Ü &( Ü(&,ÀÜ0&(PÜ8&(PÜ@&,ˆÜH&}0ÜX&
¤Ü`&}@Üh&5€Üp&)Üx&-Ø܀&( ܈&* ܐ&(ܘ&,ˆÜ &}øÜ°&
¤ܸ&zxÜÀ&)ØÜÈ&'XÜØ&}@Üà&'¨Üè&Y Üð&{pÜø&,hÝ&'Ý&uèÝ&Y Ý &,ˆÝ(&~PÝ8&
¤Ý@&'ÝP&uèÝX&Y Ý`&,ˆÝh&~Ø݀&
¤݈&(Pݐ&3ݘ&'ÀÝ &)Øݨ&{pÝ°&(8ݸ&,ˆÝÀ&ÝÐ&ðÝà&pÝð&
¤Ýø&zxÞ&)ØÞ&-øÞ&zxÞ&PPÞ &'XÞ0&,hÞ8&³pÞ@&€ÞH&)ðÞP&&@ÞX&4@Þ`&³pÞh&0Þp&
¤Þx&,ˆހ&ސ&
¤ޘ&-¸Þ &zxÞ¨&PPÞ°&zxÞ¸&)ØÞÀ&'XÞÐ&,hÞØ&0Þà&,hÞè&€Þð&)ØÞø&4@ß&³pß&&@ß&,¨ß&,ˆß &€0ß8&
¤ß@&³pßH&'ØßP&3ßX&)ß`&( ßh&)ðßp&,ˆßx&€Ð߈&
¤ߐ& ߘ&'¨ß &'8ߨ&{pß°&³p߸&-ØßÀ&{pßÈ&,ˆßÐ&(ßà&
¤ßè& ßð&'¨ßø&'Xà&{pà&³pà&-Øà&{pà &,ˆà(&€à8&
¤à@&{àH&€èàP&€@àX&,ˆà`&Øàp&
¤àx&{à€&'¨àˆ&'8à&{pà˜&³pà &-Øà¨&{pà°&( à¸&€èàÀ&,ˆàÈ&‚àØ&
¤àà& àè&-Øàð&,ˆàø&‚xá&
¤á&{á &'¨á(&(á0&{pá8&5á@&'XáP&AàáX&( á`&èáh&'8áx&€@á€&,ˆáˆ&‚¨á˜&
¤á &{á¨&A°á°&(8á¸&'¨áÀ&'ØáÈ&{páÐ&'¨áØ&+áà&{páè&áð&'¨áø&(â&{pâ&(Pâ&,ˆâ&ƒ8â(&
¤â0&{â8&(8â@&‚ âH&(PâP&,ˆâX&ƒÈâp&
¤âx&³pâ€&3âˆ&)â&{pâ˜&,ˆâ &„â°&
¤â¸& âÀ&³pâÈ&,ˆâÐ&„Pâà&
¤âè&{âð&'¨âø&'8ã&{pã&„ ã&€@ã&,ˆã &„€ã0&
¤ã8&{ã@&'¨ãH&'XãP&{pãX&„ ã`&€@ãh&,ˆãp&„Ðã€&
¤ãˆ&{ã&ã˜&( ã &,ˆã¨&… ã¸&
¤ãÀ&{ãÈ&„ãÐ&èãØ&,ˆãà&…Xãð&ðä&…ä&
¤ä &… ä(&)Øä0&5ä8&'XäH&'ÀäP&)ØäX&( ä`&³päh&'Øäp&)äx&( ä€&)ðäˆ&'8ä˜&³pä &)ä¨&{pä°&… ä¸&)ðäÀ&,ˆäÈ&…°äØ&
¤äà& äè&… äð&)Øäø&³på&'¨å&+Àå&{på&-Øå &… å(&)ðå0&,ˆå8&†xåH&
¤åP& åX&… å`&)Øåh&'¨åp&+Øåx&{på€&³påˆ&³på&… å˜&)ðå &-Øå¨&{på°&,ˆå¸&†èåÈ&
¤åÐ&{åØ&'¨åà&+ðåè&{påð&…Èåø&€@æ&,ˆæ&‡hæ&
¤æ &{æ(&'¨æ0&,æ8&{pæ@&…ÈæH&€@æP&,ˆæX&‡¸æh&
¤æp&{æx&'¨æ€&,0æˆ&{pæ&… æ˜&)Øæ &³pæ¨&… æ°&)ðæ¸&{pæÀ&,ˆæÈ&ˆæØ&
¤æà&{æè&'¨æð&,Pæø&{pç&… ç&)Øç&³pç&… ç &)ðç(&{pç0&,ˆç8&ˆxçP&
¤çX&(Pç`&W€çh&(8çp&W çx&)Øç€&(8çˆ&WÈç&(8ç˜&\¸ç &)Øç¨&(8ç°&X ç¸&)ØçÀ&(8çÈ&(8çÐ&,ˆçØ&ˆèçð&
¤çø&(Pè&(Pè&X è&)ðè&(Pè &\¸è(&)ðè0&(Pè8&4@è@&WÈèH&(PèP&W èX&)ðè`&(Pèh&4@èp&W€èx&(8è€&,ˆèˆ&‰ˆè &Š8èÀ&ŠPèè&Špé&Š˜é0&(é@&ŠÀéX&€éh&Šðé€&
¤éˆ&-¸é&4@é˜&‹é &,ˆé¨&‹éÀ&
¤éÈ&-ØéÐ&4@éØ&‹éà&,ˆéè&‹Xê&
¤ê&‹ê&'Xê &(8ê(&(8ê0&e¨ê8&(Pê@&(PêH&,ˆêP&‹˜êp&
¤êx&'Àê€&'ê&+ê˜&'Xê¨&'¨ê°&Š°ê¸&ZÀêÀ&Y êÈ&Y€êÐ&(êØ&,hêà&'Àêè&'êø&+ë&'Xë&(ë&,hë &Šàë(&,ˆë0&ŒëH&
¤ëP&Z@ëX&'Àë`&+¨ëh&'Xëx&‹°ë€&'¨ëˆ&ŠHë&'8ë &'Àë¨&-¸ë°&+ë¸&'XëÈ&'¨ëÐ&ŠhëØ&ZÀëà&Y ëè&'8ëø&'Àì&'ì&+ì&'Xì(&Uàì0&)Øì8&ZÀì@&Y ìH&(ìP&'8ì`&Œ ìh&Y€ìp&,ˆìx&Œàì&
¤ì˜&5€ì &sì¨&'Xì¸&t ìÀ&'XìÐ&6¨ìØ&6¨ìà&,¨ìè&,hìð&{pìø&6@í&,hí&5€í&hàí&'Xí(&Y í0&'í@&V˜íH&'¨íP&'íX&{pí`&{píh&6@íp&,ˆíx&Ž(í&
¤í˜&5€í &sí¨&'Xí¸&(íÀ&6¨íÈ&6¨íÐ&,¨íØ&,híà&5€íè&hàíð&'Xî&Y î&'î&V˜î &(8î(&6@î0&(Pî8&,ˆî@&(îX&
¤î`&-Øîh&X îp&)ðîx&w¸î€&'Àîˆ&'Xî˜&zxî &)Øî¨&'Xî¸&Ž@îÀ&'8îÐ&@îØ&'8îè&6@îð&,ˆîø&#Èï&
¤ï&#àï&,ˆï &¨ï8&
¤ï@&( ïH&'XïX&Uàï`&)ðïh&'ïx&V˜ï€&(ïˆ&,ˆï&Ðï &
¤ï¨&|ï°&'¨ï¸&èïÀ&{pïÈ&,ˆïÐ&‘@ïø&‘€ð&
¤ð &xð(&(8ð0&'¨ð8&‘˜ð@&'ÀðH&*ðP&A°ðX&(hð`&( ðh&,Àðp&(hðx&'Àð€&*ðˆ&A°ð&)ð˜&( ð &'Àð¨&(hð°&*ð¸&)ðÀ&(hðÈ&* ðÐ&,ÀðØ&(Pðà&,ˆðè&‘¨ðø&
¤ñ&w¸ñ&sxñ&+¨ñ&'Xñ(&‘Èñ0&<ñ8&( ñ@&èñH&,ˆñP&’˜ñ`&
¤ñh&-Øñp&(èñx&z˜ñ€&XHñˆ&(˜ñ&c@ñ˜&'ñ¨&Y`ñ°&Z@ñ¸&]ñÀ&'XñÐ&Z@ñØ&'¨ñà&ñè&Vñð&'Àñø&Œøò&'Xò&'8ò &,ˆò(&“ò@&(òP&“Øòh&(òx&”ò&(ò &”(ò¸&
¤òÀ&“ðòÈ&5€òÐ&(8òØ&(8òà&B¨òè&+Øòø&(Pó&(hó&( ó&(8ó&(hó &)ó(&(hó0&( ó8&5€ó@&Y@óH&tÐóP&'Xó`&6¨óh&'Àóp&(8óx&#àó€&(Póˆ&A°ó&,ó &(Pó¨&(Pó°&”ó¸&,ˆóÀ&”PóØ&
¤óà&w¸óè&”hóð&,ˆóø&•pô&
¤ô&pô &'¨ô(&
Øô0&{pô8&'¨ô@&m ôH&3ôP&{pôX&pˆô`&,ˆôh&•¨ôx&
¤ô€&w¸ôˆ&•Àô&,ˆô˜&–ô°&
¤ô¸&(PôÀ&3ôÈ&oÈôÐ&)ØôØ&o`ôà&3ôè&)ðôð&,ˆôø&–Hõ&
¤õ&'¨õ&–`õ &{põ(&,ˆõ0&–¨õH&
¤õP&w¸õX&põ`&'¨õh&Hõp&{põx&{põ€&pˆõˆ&,ˆõ&–àõ &
¤õ¨&w¸õ°&põ¸&'¨õÀ&€õÈ&{põÐ&{põØ&pˆõà&,ˆõè&—@ö&
¤ö&w¸ö&pö&'¨ö &ðö(&{pö0&-Øö8&{pö@&pˆöH&,ˆöP&—˜öh&
¤öp&w¸öx&pö€&'¨öˆ&(ö&{pö˜&j¨ö &pˆö¨&,ˆö°&˜öÀ&
¤öÈ&w¸öÐ&pöØ&'¨öà&(öè&{pöð&'¨öø&W0÷&{p÷&pˆ÷&,ˆ÷&˜`÷(&
¤÷0&w¸÷8&p÷@&'¨÷H&8÷P&{p÷X&’¨÷`&{p÷h&pˆ÷p&,ˆ÷x&˜È÷ˆ&
¤÷&-Ø÷˜&,ˆ÷ &™(÷¸&
¤÷À&(÷È&,ˆ÷Ð&™P÷à&
¤÷è&w¸÷ð&p÷ø&'¨ø&¸ø&{pø&'Øø&jèø &)ø(&pˆø0&,ˆø8&™€øP&
¤øX&'¨ø`&'øh&{pøp&{pøx&,ˆø€&™èø˜&
¤ø &’¨ø¨&{pø°&,ˆø¸&š0øÐ&
¤øØ&w¸øà&5€øè&søð&+¨øø&'Xù&‘Èù&<ù&( ù &èù(&t ù0&+¨ù8&'XùH&'¨ùP&'¨ùX&{pù`&{pùh&'¨ùp&{pùx&{pù€&6@ùˆ&,ˆù&šhù &
¤ù¨&y ù°&šù¸&,ˆùÀ&›@ùÐ&
¤ùØ&’¨ùà&'¨ùè&'¨ùð&{pùø&{pú&,ˆú&›pú&
¤ú &'Àú(&ZÀú0&sú8&'XúH&7úP&(úX&<ú`&( úh&t úp&'Xú€&@húˆ&,hú&<8ú˜&,hú &,ˆú¨&›¸ú¸&
¤úÀ&’¨úÈ&zxúÐ&)ØúØ&'Xúè&'¨úð&4@úø&{pû&{pû&,hû&3û&)ðû &,ˆû(&œXû@&
¤ûH&3ûP&)ØûX&,ˆû`&œØûp&
¤ûx&.û€&3Èûˆ&)û&,ˆû˜&û¨&
¤û°&.û¸&3ÈûÀ&)ûÈ&,ˆûÐ&Hûè&
¤ûð&pˆûø&,ˆü&€ü&
¤ü &oÈü(&)Øü0&o`ü8&{pü@&,ˆüH&°üX&
¤ü`&w¸üh&]Øüp&)Øüx&(8ü€&^üˆ&#àü&(Pü˜&]Øü &)ðü¨&,ˆü°&øüÀ&
¤üÈ&w¸üÐ&]ØüØ&)Øüà&(8üè&^8üð&#àüø&(Pý&]Øý&)ðý&,ˆý&ž`ý(&
¤ý0&w¸ý8&]Øý@&)ØýH&(8ýP&^pýX&#àý`&(Pýh&]Øýp&)ðýx&,ˆý€&žÈý˜&"Äý &Ÿ0ý¸&#ýÀ&ŸPýØ&#<ýà&Ÿpýø&#tþ&Ÿþ&#Àþ &Ÿ°þ8&$þ@&ŸÐþX&Àþ`&Ÿðþ€&!8þˆ& þ˜&þ & 8þ°&Hþ¸& PþÈ&þÐ& hþà&Ìþè& €þø&ÿ& ˜ÿ&Pÿ& °ÿ(&˜ÿ0& Èÿ@&ÔÿH& àÿh& ÿp& øÿ€& hÿˆ&¡ ÿ & °ÿ¨&¡8ÿÈ& üÿÐ&¡Xÿð&!|ÿø&¡€&!¸ &¡¨@&&ÐH&¡Ðh&Gtp&¡ø&Fô˜&¢ ¸&G<À&¢Hà&EØè&¢p&F&¢˜0&Cô8&¢ÀX&D,`&¢è€&Dhˆ&£ &F`¨&£8È&F¸Ð&£Xè&C¬ð&£€&DÄ&£ 8&E@&£È`&EPh&£ðˆ&E”&¤°&@P¸&¤@Ø&@ˆà&¤h&@Ä&¤(&A0&¤¸P&A@X&¤àx&Ax€&¥ &Aœ¨&¥0È&AÀÐ&¥Xè&Aäð&¥€&B &¥ (&B\0&¥ÀH&B”P&¥àh&BÌp&¦&C˜&¦ °&C<¸&¦HÐ&CtØ&¦hð&6Øø&¦ˆ&7 &¦¨@&7XH&¦Ð`&7¬h&¦øˆ&7ì&§¨&80°&§@Ð&8pØ&§`ø&8´&§ˆ &9L(&§°H&8ôP&§Øh&9pp&¨&9̘&¨ °&:4¸&¨HÐ&;Ø&¨hð&:lø&¨ˆ&;X&¨¨0&:¤8&¨ÈP&;œX&¨èp&:Üx&©&;à˜&©(¸&=ÐÀ&©HØ&>Àà&©pø&?°&© &<$(&©°P&<X&©Øx&=€&ª¨&=p°&ª0Ð&?PØ&ª`ø&'	&ªˆ	 &?Ô	(&ª°	H&=ô	P&ªØ	p&>`	x&«	˜&>ä	 &«(	À&'p	È&«P	à&'À	è&«x
&'ø
&«˜
 &(4
(&«¸
@&(l
H&«Ø
`&(¤
h&«ø
€&(Ü
ˆ&¬
 &)@
¨&¬8
À&)|
È&¬X
à&)Ä
è&¬x&*&¬˜ &*d(&¬¸@&* H&¬Ø`&*äh&¬ø€&+(ˆ&­ &+ ¨&­8À&/8È&­XØ&.¬à&­xð&/ø&­&-¼&­¨ &-ü(&­À8&.4@&­ØP&.tX&­ðh&+üp&®€&,4ˆ&® ˜&,¤ &®8°&,l¸&®PÈ&-Ð&®hà&,Üè&®€ø&-L
&®˜
&-„
&®°
(&/|
0&®È
@&/´
H&®à
X&0$
`&®ø
p&/ì
x&¯
ˆ&0”
&¯(
 &0\
¨&¯@
¸&1
À&¯X
Ð&0Ì
Ø&¯p
è&1t
ð&¯ˆ&1<&¯ &1ä &¯¸0&1¬8&¯ÐH&2TP&¯è`&2h&°€&2Ĉ&° &2Œ¨&°8À&34È&°Xà&2üè&°xø&5°&°˜&5x&°°(&3l0&°È@&3¬H&°àX&3è`&³€x&40€&± &(°&³°Ð&HØ&à&±`&
¤&±€&)Ø&,ˆ &±0&4¼8&±ÐP&4pX&±èp&5x&²˜&5è &²(¸&60À&²PØ&6tà&²pð&4hø&²&ð&²¨(&
¤0&²¸8&)Ø@&* H&'X&²¸`&PPh&,ˆp&²È&( Ë&¨Ë&€°&-ˆÀ&€Èß&Ð&°øð&Hø{&&±0 &H(v&0&³ H&
¤P&'¨X&(`&4@h&Y`p&'¨x&q8€&4@ˆ&q&'¨˜&6@ &4@¨&oð°&'¸Ú&À&'Èø&Ð&'ØØ&)à&'¨è&#àð&Vø&³@&,ˆxÀ&
¸xÈ&
ÀxÐ&
ÈxØ&
Øxà&
ðxè&
øxð&xø& y&0y&@y&Py&Py &`y(&py0&€y8&€y@&
¨yH&ˆyP&HyX&˜y`&yh&xyp&8yx&hy€&(yˆ&y &
ðy¨&èy°&øy¸&	8yÀ&¸yÈ&	yÐ&ØyØ&	(yà&Èz&(z&
øz&
¨z(&
(z0&
ˆz8&
Èz@&
zH&
¸zx&8z˜&Hz¸&HzØ&Pzø&h{&¨{8&x{X&ˆ{x&˜{˜&°{¸&Èrà&rø& s&0s(&Ps@&psX&sp&°sˆ&Ðs &às¸&ðsÐ&sè&t& t&0t0&@tH&Pt`&`tx&pt&€t¨&tÀ&˜tØ&¨tð&¸u&È| &«€˜|@&«€è d@®Øh2Eä -@°@ƒH=HHP8@3ˆBB^P^PL^P^P$G@vNhR0|t|t,[| k€|t«8| p}È	œØüÿÿÿÿÿÿÿÿH0bootinfoÿÿÿÿÿÿÿÿ<<_(ide.fs1 encode-int s" #address-cells" property
0 encode-int s" #size-cells" property
: decode-unit  1 hex-decode-unit ;
: encode-unit  1 hex-encode-unit ;
0 VALUE >ata                                 \ base address for command-block
0 VALUE >ata1                                \ base address for control block
true VALUE no-timeout                        \ flag that no timeout occurred
0c  CONSTANT #cdb-bytes                      \ command descriptor block (12 bytes)
800 CONSTANT atapi-size
200 CONSTANT ata-size
: ata-ctrl! 2 >ata1 + io-c! ;                      \ device control reg
: ata-astat@ 2 >ata1 + io-c@ ;                     \ read alternate status
: ata-data@ 0 >ata + io-w@ ;                       \ data reg
: ata-data! 0 >ata + io-w! ;                       \ data reg
: ata-err@  1 >ata + io-c@ ;                       \ error reg
: ata-feat! 1 >ata + io-c! ;                       \ feature reg
: ata-cnt@  2 >ata + io-c@ ;                       \ sector count reg
: ata-cnt!  2 >ata + io-c! ;                       \ sector count reg
: ata-lbal! 3 >ata + io-c! ;                       \ lba low reg
: ata-lbal@ 3 >ata + io-c@ ;                       \ lba low reg
: ata-lbam! 4 >ata + io-c! ;                       \ lba mid reg
: ata-lbam@ 4 >ata + io-c@ ;                       \ lba mid reg
: ata-lbah! 5 >ata + io-c! ;                       \ lba high reg
: ata-lbah@ 5 >ata + io-c@ ;                       \ lba high reg
: ata-dev!  6 >ata + io-c! ;                       \ device reg
: ata-dev@  6 >ata + io-c@ ;                       \ device reg
: ata-cmd!  7 >ata + io-c! ;                       \ command reg
: ata-stat@ 7 >ata + io-c@ ;                       \ status reg
00 CONSTANT cmd#nop                                \ ATA and ATAPI
08 CONSTANT cmd#device-reset                       \ ATAPI only (mandatory)
20 CONSTANT cmd#read-sector                        \ ATA and ATAPI
90 CONSTANT cmd#execute-device-diagnostic          \ ATA and ATAPI
a0 CONSTANT cmd#packet                             \ ATAPI only (mandatory)
a1 CONSTANT cmd#identify-packet-device             \ ATAPI only (mandatory)
ec CONSTANT cmd#identify-device                    \ ATA and ATAPI
: set-regs ( n -- )
dup
01 and                                    \ only Chan 0 or Chan 1 allowed
3 lshift dup 10 + config-l@ -4 and to >ata
14 + config-l@ -4 and to >ata1
02 ata-ctrl!                              \ disable interrupts
02 and
IF
10
ELSE
00
THEN
ata-dev!
;
ata-size VALUE block-size
80000    VALUE max-transfer            \ Arbitrary, really
CREATE sector d# 512 allot
CREATE packet-cdb #cdb-bytes allot
CREATE return-buffer atapi-size allot
scsi-open                             \ add scsi functions
: show-regs
cr
cr ." alt. Status: " ata-astat@ .
cr ." Status     : " ata-stat@ .
cr ." Device     : " ata-dev@ .
cr ." Error-Reg  : " ata-err@ .
cr ." Sect-Count : " ata-cnt@ .
cr ." LBA-Low    : " ata-lbal@ .
cr ." LBA-Med    : " ata-lbam@ .
cr ." LBA-High   : " ata-lbah@ .
;
: status-check               ( -- )
ata-stat@
dup   
01 and                                    \ is 'check' flag set ?
IF
cr
."    - ATAPI-Status: " .
ata-err@                               \ retrieve sense code
dup
60 =                                   \ sense code = 6 ?
IF
." ( media changed or reset )"      \ 'unit attention'
drop                                \ drop err-reg content
ELSE
dup
." (Err : " .                       \ show err-reg content
space
rshift 4 .sense-text                \ show text string
29 emit
THEN
cr
ELSE
drop                                   \ remove unused status      
THEN      
;
: wait-for-ready
get-msecs                                 \ start timer
BEGIN
ata-stat@ 80 and 0<>                   \ busy flag still set ?
no-timeout and
WHILE                                  \ yes
dup get-msecs swap
-                                   \ calculate timer difference
FFFF AND                            \ reduce to 65.5 seconds
d# 5000 >                           \ difference > 5 seconds ?
IF
false to no-timeout
THEN
REPEAT
drop
;
: wait-for-status          ( val mask -- )
get-msecs                                 \ initial timer value (start)
>r
BEGIN
2dup                                   \ val mask
ata-stat@ and <>                       \ expected status ?
no-timeout and                         \ and no timeout ?
WHILE      
get-msecs r@ -                         \ calculate timer difference
FFFF AND                               \ mask-off overflow bits
d# 5000 >                              \ 5 seconds exceeded ?
IF
false to no-timeout                 \ set global flag
THEN      
REPEAT                  
r>                                        \ clean return stack
3drop
;
: cut-string      ( saddr nul -- )
swap
over +
swap   
1 rshift                                  \ bytecount -> wordcount
0 do
/w -
dup               ( addr -- addr addr )
w@                ( addr addr -- addr nuw )
dup               ( addr nuw -- addr nuw nuw )
2020 =
IF
drop
0 
ELSE
LEAVE         
THEN
over         
w!
LOOP
drop
drop
; 
: show-model          ( dev# chan# -- )
2dup
."    CH " .                  \ channel 0 / 1
0= IF ." / MA"                \ Master / Slave
ELSE  ." / SL"
THEN
swap
2 * + ."  (@" . ." ) : "      \ device number
sector 1 +
c@
80 AND 0=
IF
." ATA-Drive    "
ELSE
." ATAPI-Drive  "
THEN
22 emit                       \ start string display with "
sector d# 54 +                \ string starts 54 bytes from buffer start
dup
d# 40                         \ and is 40 chars long
cut-string                    \ remove all trailing spaces
BEGIN
dup
w@
wbflip
wbsplit
dup 0<>                    \ first char
IF                   
emit
dup 0<>                 \ second char
IF
emit
wa1+                 \ increment address for next
false
ELSE                    \ second char = EndOfString
drop
true
THEN   
ELSE                       \ first char = EndOfString
drop
drop
true
THEN
UNTIL                         \ end of string detected
drop
22 emit                       \ end string display
sector c@                     \ get lower byte of first doublet
80 AND                        \ check bit 7
IF
."  (removable media)"
THEN
sector 1 +
c@
80 AND 0= IF                  \ is this an ATA drive ?
sector d# 120 +            \ get word 60 + 61
rl@-le                     \ read 32-bit as little endian value
d# 512                     \ standard ATA block-size
swap
.capacity-text ( block-size #blocks -- )
THEN
sector d# 98 +               \ goto word 49
w@
wbflip
200 and 0= IF cr ."    ** LBA is not supported " THEN   
sector c@                     \ get lower byte of first doublet
03 AND 01 =                   \ we use 12-byte packet commands (=00b)
IF
cr ."    packet size = 16 ** not supported ! **"
THEN
no-timeout not                \ any timeout occurred so far ?
IF
cr   ."    ** timeout **"
THEN
;
: pio-sector ( addr -- )  100 0 DO ata-data@
over w! wa1+ LOOP drop ;
: pio-sector ( addr -- ) 
wait-for-ready pio-sector ;
: pio-sectors ( n addr -- )  swap 0 ?DO dup pio-sector 200 + LOOP drop ;
: lba!  lbsplit   
0f and 40 or                  \ always set LBA-mode + LBA (27..24)
ata-dev@ 10 and or            \ add current device-bit (DEV)
ata-dev!                      \ set LBA (27..24)
ata-lbah!                     \ set LBA (23..16)
ata-lbam!                     \ set LBA (15..8)
ata-lbal!                     \ set LBA (7..0)
;
: read-sectors ( lba count addr -- ) 
>r dup >r ata-cnt! lba! 20 ata-cmd! r> r> pio-sectors ;
: read-sectors ( lba count addr dev-nr -- )
set-regs             ( lba count addr ) \ Set ata regs 
BEGIN >r dup 100 > WHILE
over 100 r@ read-sectors
>r 100 + r> 100 - r> 20000 + REPEAT
r> read-sectors
;
: ata-read-blocks                ( addr block# #blocks dev# -- #read )
swap dup >r swap >r rot r>    ( addr block# #blocks dev # R: #blocks )
read-sectors r>               ( R: #read )
;    
: set-lba                              ( block-length -- )
lbsplit                             ( quad -- b1.lo b2 b3 b4.hi )
drop                                \ skip upper two bytes
drop
ata-lbah!
ata-lbam!
;
: read-pio-block                        ( buff-addr -- buff-addr-new )
ata-lbah@ 8 lshift                  \ get block length High
ata-lbam@ or                        \ get block length Low
1 rshift                            \ bcount -> wcount
dup
0> IF                               \ any data to transfer?
0 DO                             \ words to read
dup                           \ buffer-address
ata-data@ swap w!             \ write 16-bits
wa1+                          \ address of next entry
LOOP
ELSE
drop                          ( buff-addr wcount -- buff-addr )
THEN
wait-for-ready
;
: send-atapi-packet                    ( req-buffer -- )
>r                                  (   R: req-buffer )
atapi-size set-lba                  \ set regs to length limit
00 ata-feat!
cmd#packet ata-cmd!                 \ A0 = ATAPI packet command
48 C8  wait-for-status     ( val mask -- )  \ BSY:0 DRDY:1 DRQ:1
6 0  do
packet-cdb i 2 * +                \ transfer command block (12 bytes)
w@
ata-data!                        \ 6 doublets PIO transfer to device
loop                             \ copy packet to data-reg
status-check                        ( -- ) \ status err bit set ? -> display
wait-for-ready                      ( -- ) \ busy released ?
BEGIN
ata-stat@ 08 and 08 = WHILE         \ Data-Request-Bit set ?
r>                               \ get last target buffer address
read-pio-block                   \ only if from device requested
>r                               \ start of next block
REPEAT
r>                                  \ original value
drop                                \ return clean
;   
: atapi-packet-io                      ( -- )
return-buffer atapi-size erase      \ clear return buffer
return-buffer send-atapi-packet     \ send 'packet-cdb' , get 'return-buffer'
;
: atapi-test ( -- true|false )
packet-cdb scsi-build-test-unit-ready     \ command-code: 00
atapi-packet-io                           ( )  \ send CDB, get return-buffer
ata-stat@ 1 and IF false ELSE true THEN
;
: atapi-sense ( -- ascq asc sense-key )
d# 252 packet-cdb scsi-build-request-sense ( alloc-len cdb -- )
atapi-packet-io                           ( )  \ send CDB, get return-buffer
return-buffer scsi-get-sense-data         ( cdb-addr -- ascq asc sense-key )
;
: atapi-read-blocks                    ( address block# #blocks dev# -- #read-blocks )
set-regs                            ( address block# #blocks )
dup >r                              ( address block# #blocks )
packet-cdb scsi-build-read-10       ( address block# #blocks cdb -- )
send-atapi-packet                   ( address -- )
r>                                  \ return requested number of blocks
;
: atapi-read-capacity                        ( -- )
packet-cdb scsi-build-read-cap-10         \ fill block with command
atapi-packet-io                           ( )  \ send CDB, get return-buffer
return-buffer scsi-get-capacity-10        ( cdb -- block-size #blocks )
.capacity-text                            ( block-size #blocks -- )
status-check                              ( -- )
;
: atapi-read-capacity-ext                    ( -- )
packet-cdb scsi-build-read-cap-16         \ fill block with command
atapi-packet-io                           ( )  \ send CDB, get return-buffer
return-buffer scsi-get-capacity-16        ( cdb -- block-size #blocks )
.capacity-text                            ( block-size #blocks -- )
status-check                              ( -- )
;
: wait-for-media-ready                 ( -- true|false )
get-msecs                                 \ initial timer value (start)
>r
BEGIN
atapi-test                             \ unit ready? false if not      
not
no-timeout and
WHILE
atapi-sense  ( -- ascq asc sense-key )
02 =                                \ sense key 2 = media error
IF                                  \ check add. sense code
3A =                             \ asc: device not ready ?
IF
false to no-timeout
."  empty (" . 29 emit        \ show asc qualifier
ELSE
drop                          \ discard asc qualifier
THEN                             \ medium not present, abort waiting
ELSE
drop                             \ discard asc
drop                             \ discard ascq
THEN
get-msecs r@ -                      \ calculate timer difference
FFFF AND                            \ mask-off overflow bits
d# 5000 >                           \ 5 seconds exceeded ?
IF
false to no-timeout              \ set global flag
THEN      
REPEAT
r>
drop
no-timeout
;
2 CONSTANT #chan 
2 CONSTANT #dev
: #totaldev #dev #chan * ;
CREATE read-blocks-xt #totaldev cells allot read-blocks-xt #totaldev cells erase
: dev-read-blocks  ( address block# #blocks dev# -- #read-blocks )
dup cells read-blocks-xt + @ execute
;
: read-ident  ( -- true|false )
false
00 ata-lbal!                              \ clear previous signature
00 ata-lbam!
00 ata-lbah!
cmd#identify-device ata-cmd! wait-for-ready \ first try ATA, ATAPI aborts command
ata-stat@ CF and 48 =
IF
drop true                                          \ cmd accepted, this is a ATA
d# 512 set-lba                                     \ set LBA to sector-length
ELSE                                                  \ ATAPI sends signature instead
ata-lbam@ 14 = IF                                  \ cylinder low  = 14 ?
ata-lbah@ EB = IF                               \ cylinder high = EB ?
cmd#device-reset ata-cmd! wait-for-ready     \ only supported by ATAPI
cmd#identify-packet-device ata-cmd! wait-for-ready                     \ first try ata
ata-stat@ CF and 48 = IF               
drop true                                 \ replace flag
THEN
THEN
THEN
THEN
dup IF
ata-stat@ 8 AND IF                        \ data requested (as expected) ?      
sector read-pio-block 
drop                                   \ discard address end 
ELSE
drop false
THEN
THEN
no-timeout not IF                            \ check without any timeout ?
drop
false                                     \ no, detection discarded
THEN
;
scsi-close                             \ remove scsi commands from word list
: find-disks      ( -- )   
#chan 0 DO                                      \ check 2 channels (primary & secondary)
#dev 0 DO                                    \ check 2 devices per channel (master / slave)
i 2 * j +
set-regs                                  \ set base address and dev-register for register access
ata-stat@ 7f and 7f <>                    \ Check, if device is connected
IF
true to no-timeout                     \ preset timeout-flag
read-ident        ( -- true|false )
IF
i j show-model                      \ print manufacturer + device string
sector 1+ c@ C0 and 80 =            \ Check for ata or atapi
IF
wait-for-media-ready             \ wait up to 5 sec if not ready
no-timeout and
IF
atapi-read-capacity
atapi-size to block-size      \ ATAPI: 2048 bytes
80000 to max-transfer
['] atapi-read-blocks i 2 * j + cells read-blocks-xt + !
s" cdrom" strdup i 2 * j + s" generic-disk.fs" included
ELSE
."  -"                        \ show hint for not registered
THEN    
ELSE
ata-size to block-size           \ ATA: 512 bytes
80000 to max-transfer
['] ata-read-blocks i 2 * j + cells read-blocks-xt + !
s" disk" strdup i 2 * j + s" generic-disk.fs" included
THEN
cr
THEN    
THEN
i 2 * j + 200 + cp
LOOP
LOOP
;
find-disks
ÿÿÿÿÿÿÿÿ-P-0fbuffer.fs0 VALUE line#
0 VALUE column#
false VALUE inverse?
false VALUE inverse-screen?
18 VALUE #lines
50 VALUE #columns
false VALUE cursor
false VALUE saved-cursor
defer draw-character	\ 2B inited by display driver
defer reset-screen	\ 2B inited by display driver
defer toggle-cursor	\ 2B inited by display driver
defer erase-screen	\ 2B inited by display driver
defer blink-screen	\ 2B inited by display driver
defer invert-screen	\ 2B inited by display driver
defer insert-characters	\ 2B inited by display driver
defer delete-characters	\ 2B inited by display driver
defer insert-lines	\ 2B inited by display driver
defer delete-lines	\ 2B inited by display driver
defer draw-logo		\ 2B inited by display driver
: nop-toggle-cursor ( nop ) ;
' nop-toggle-cursor to toggle-cursor
: (cursor-off) ( -- ) cursor dup to saved-cursor
IF toggle-cursor false to cursor THEN ;
: (cursor-on) ( -- ) cursor dup to saved-cursor
0= IF toggle-cursor true to cursor THEN ;
: restore-cursor ( -- ) saved-cursor dup cursor
<> IF toggle-cursor to cursor ELSE drop THEN ;
' (cursor-off) to cursor-off
' (cursor-on) to cursor-on
false VALUE esc-on
false VALUE csi-on
defer esc-process
0 VALUE esc-num-parm
0 VALUE esc-num-parm2
0 VALUE saved-line#
0 VALUE saved-column#
: get-esc-parm ( default -- value )
esc-num-parm dup 0> IF nip ELSE drop THEN 0 to esc-num-parm ;
: get-esc-parm2 ( default -- value )
esc-num-parm2 dup 0> IF nip ELSE drop THEN 0 to esc-num-parm2 ;
: set-esc-parm ( newdigit -- ) [char] 0 - esc-num-parm a * + to esc-num-parm ;
: reverse-cursor ( oldpos -- newpos) dup IF 1 get-esc-parm - THEN ;
: advance-cursor ( bound oldpos -- newpos) tuck > IF 1 get-esc-parm + THEN ;
: erase-in-line #columns column# - dup 0> IF delete-characters ELSE drop THEN ;
: terminal-line++ ( -- )
line# 1+ dup #lines = IF 1- 0 to line# 1 delete-lines THEN
to line#
;
0 VALUE dang
0 VALUE blipp
false VALUE stopcsi
0 VALUE term-background
7 VALUE term-foreground
: set-term-color
dup d# 30 d# 39 between IF dup d# 30 - to term-foreground THEN
dup d# 40 d# 49 between IF dup d# 40 - to term-background THEN
0 = IF
0 to term-background
7 to term-foreground
THEN
term-foreground term-background <= to inverse?
;
: ansi-esc ( char -- )
csi-on IF
dup [char] 0 [char] 9 between IF set-esc-parm
ELSE true to stopcsi CASE
[char] A OF line# reverse-cursor to line# ENDOF
[char] B OF #lines line# advance-cursor to line# ENDOF
[char] C OF #columns column# advance-cursor to column# ENDOF
[char] D OF column# reverse-cursor to column# ENDOF
[char] E OF ( FIXME: Cursor Next Line - No idea what does it mean )
#lines line# advance-cursor to line#
ENDOF
[char] f OF
1 get-esc-parm2 to line# column# get-esc-parm to column#
ENDOF
[char] H OF
1 get-esc-parm2 to line# column# get-esc-parm to column#
ENDOF
[char] ; OF false to stopcsi 0 get-esc-parm to esc-num-parm2 ENDOF
[char] ? OF false to stopcsi ENDOF ( FIXME: Ignore that for now )
[char] l OF ENDOF ( FIXME: ?25l should hide cursor )
[char] h OF ENDOF ( FIXME: ?25h should show cursor )
[char] J OF
#lines line# - dup 0> IF
line# 1+ to line# delete-lines line# 1- to line#
ELSE drop THEN
erase-in-line
ENDOF
[char] K OF erase-in-line ENDOF
[char] L OF 1 get-esc-parm insert-lines ENDOF
[char] M OF 1 get-esc-parm delete-lines ENDOF
[char] @ OF 1 get-esc-parm insert-characters ENDOF
[char] P OF 1 get-esc-parm delete-characters ENDOF
[char] m OF 0 get-esc-parm set-term-color ENDOF
[char] p OF inverse-screen? IF false to inverse-screen?
inverse? 0= to inverse? invert-screen
THEN
ENDOF
[char] q OF inverse-screen? 0= IF true to inverse-screen?
inverse? 0= to inverse? invert-screen
THEN
ENDOF
[char] u OF saved-line# to line# saved-column# to column# ENDOF
dup dup to dang OF blink-screen ENDOF
ENDCASE stopcsi IF false to csi-on
false to esc-on 0 to esc-num-parm 0 to esc-num-parm2 THEN
THEN
ELSE CASE
[char] 7 OF line# to saved-line# column# to saved-column# ENDOF
[char] 8 OF saved-line# to line# saved-column# to column# ENDOF
[char] [ OF true to csi-on ENDOF
dup dup OF false to esc-on to blipp ENDOF
ENDCASE
csi-on 0= IF false to esc-on THEN 0 to esc-num-parm 0 to esc-num-parm2
THEN
;
' ansi-esc to esc-process
CREATE twtracebuf 4000 allot twtracebuf 4000 erase
twtracebuf VALUE twbp
0 VALUE twbc
0 VALUE twtrace-enabled?
: twtrace
twbc 4000 = IF 0 to twbc twtracebuf to twbp THEN
dup twbp c! twbp 1+ to twbp twbc 1+ to twbc
;
: terminal-write ( addr len -- actual-len )
cursor-off
tuck bounds ?DO i c@
twtrace-enabled? IF twtrace THEN
esc-on IF esc-process
ELSE CASE
1B OF true to esc-on ENDOF
carret OF 0 to column# ENDOF
linefeed OF terminal-line++ ENDOF
bell OF blink-screen ENDOF
9 ( TAB ) OF column# 7 + -8 and dup #columns < IF
to column#
ELSE drop THEN
ENDOF
B ( VT ) OF line# ?dup IF 1- to line# THEN ENDOF
C ( FF ) OF 0 to line# 0 to column# erase-screen ENDOF
bs OF	column# 1- dup 0< IF
line# IF
line# 1- to line#
drop #columns 1-
ELSE drop column#
THEN
THEN
to column# ( bl draw-character )
ENDOF
dup OF
i c@ draw-character
column# 1+ dup #columns >= IF
drop 0 terminal-line++
THEN
to column#
ENDOF
ENDCASE
THEN
LOOP
restore-cursor
;
0 VALUE char-height
0 VALUE char-width
0 VALUE fontbytes
CREATE display-emit-buffer 20 allot
defer dis-old-emit
' emit behavior to dis-old-emit
: display-write terminal-write ;
: display-emit dup dis-old-emit display-emit-buffer tuck c! 1 terminal-write drop ;
: is-install ( 'open -- )
s" defer vendor-open to vendor-open" eval
s" : open deadbeef vendor-open dup deadbeef = IF drop true ELSE nip THEN ;" eval
s" defer write ' display-write to write" eval
s" : draw-logo ['] draw-logo CATCH IF 2drop 2drop THEN ;" eval
s" : reset-screen ['] reset-screen CATCH drop ;" eval
;
: is-remove ( 'close -- )
s" defer close to close" eval
;
: is-selftest ( 'selftest -- )
s" defer selftest to selftest" eval
;
STRUCT
cell FIELD font>addr
cell FIELD font>width
cell FIELD font>height
cell FIELD font>advance
cell FIELD font>min-char
cell FIELD font>#glyphs
CONSTANT /font
CREATE default-font-ctrblk /font allot default-font-ctrblk
dup font>addr 0 swap !
dup font>width 8 swap !
dup font>height -10 swap !
dup font>advance 1 swap !
dup font>min-char 20 swap !
font>#glyphs 7f swap !
: display-default-font ( str len -- )
romfs-lookup dup 0= IF drop EXIT THEN
600 <> IF ." Only support 60x8x16 fonts ! " drop EXIT THEN
default-font-ctrblk font>addr !
;
s" default-font.bin" display-default-font
: .scan-lines ( height -- scanlines ) dup 0>= IF 1- ELSE negate THEN ;
: set-font ( addr width height advance min-char #glyphs -- )
default-font-ctrblk /font + /font 0
DO
1 cells - dup >r ! r> 1 cells
+LOOP drop
default-font-ctrblk dup font>height @ abs to char-height
dup font>width @ to char-width font>advance @ to fontbytes
;
: >font ( char -- addr )
dup default-font-ctrblk dup >r font>min-char @ dup r@ font>#glyphs + within
IF
r@ font>min-char @ -
r@ font>advance @ * r@ font>height @ .scan-lines *
r> font>addr @ +
ELSE
drop r> font>addr @
THEN
;
: default-font ( -- addr width height advance min-char #glyphs )
default-font-ctrblk /font 0 DO dup cell+ >r @ r> 1 cells +LOOP drop
;
0 VALUE frame-buffer-adr
0 VALUE screen-height
0 VALUE screen-width
0 VALUE screen-depth
0 VALUE screen-line-bytes
0 VALUE window-top
0 VALUE window-left
0 VALUE .sc
: screen-#rows  ( -- rows )
.sc IF
screen-height char-height /
ELSE
true to .sc
s" screen-#rows" eval
false to .sc
THEN
;
: screen-#columns ( -- columns )
.sc IF
screen-width char-width /
ELSE
true to .sc
s" screen-#columns" eval
false to .sc
THEN
;
: fb8-background inverse? ;
: fb8-foreground inverse? invert ;
: fb8-lines2bytes ( #lines -- #bytes ) char-height * screen-line-bytes * ;
: fb8-columns2bytes ( #columns -- #bytes ) char-width * screen-depth * ;
: fb8-line2addr ( line# -- addr )
char-height * window-top + screen-line-bytes *
frame-buffer-adr + window-left screen-depth * +
;
: fb8-erase-block ( addr len ) fb8-background rfill ;
0 VALUE .ab
CREATE bitmap-buffer 400 4 * allot
: active-bits ( -- new ) .ab dup 8 > IF 8 - to .ab 8 ELSE
char-width to .ab ?dup 0= IF recurse THEN
THEN ;
: fb8-char2bitmap ( font-height font-addr -- bitmap-buffer )
bitmap-buffer >r
char-height rot 0> IF r> char-width 2dup fb8-erase-block + >r 1- THEN
r> -rot char-width to .ab
fontbytes * bounds ?DO
i c@ active-bits 0 ?DO
dup 80 and IF fb8-foreground ELSE fb8-background THEN
( fb-addr fbyte colr ) 2 pick ! 1 lshift
swap screen-depth + swap
LOOP drop
LOOP drop
bitmap-buffer
;
: fb8-draw-logo ( line# addr width height -- ) ." fb8-draw-logo ( " .s ."  )" cr
2drop 2drop
;
: fb8-toggle-cursor ( -- )
line# fb8-line2addr column# fb8-columns2bytes +
char-height 2 - screen-line-bytes * +
2 0 ?DO
dup char-width screen-depth * invert-region
screen-line-bytes +
LOOP drop
;
: fb8-draw-character ( char -- )
>r default-font over + r@ -rot between IF
2swap 3drop r> >font fb8-char2bitmap ( bitmap-buf )
line# fb8-line2addr column# fb8-columns2bytes + ( bitmap-buf fb-addr )
char-height 0 ?DO
2dup char-width screen-depth * mrmove
screen-line-bytes + >r char-width screen-depth * + r>
LOOP 2drop
ELSE 2drop r> 3drop THEN
;
: fb8-insert-lines ( n -- )
fb8-lines2bytes >r line# fb8-line2addr dup dup r@ +
#lines line# - fb8-lines2bytes r@ - rmove
r> fb8-erase-block
;
: fb8-delete-lines ( n -- )
fb8-lines2bytes >r line# fb8-line2addr dup dup r@ + swap
#lines fb8-lines2bytes r@ - dup >r rmove
r> + r> fb8-erase-block
;
: fb8-insert-characters ( n -- )
line# fb8-line2addr column# fb8-columns2bytes + >r
#columns column# - 2dup >= IF
nip dup 0> IF fb8-columns2bytes r> ELSE r> 2drop EXIT THEN
ELSE
fb8-columns2bytes swap fb8-columns2bytes tuck -
over r@ tuck + rot char-height 0 ?DO
3dup rmove
-rot screen-line-bytes tuck + -rot + swap rot
LOOP
3drop r>
THEN
char-height 0 ?DO
dup 2 pick fb8-erase-block screen-line-bytes +
LOOP
2drop
;
: fb8-delete-characters ( n -- )
line# fb8-line2addr column# fb8-columns2bytes + >r
#columns column# - 2dup >= IF
nip dup 0> IF fb8-columns2bytes r> ELSE r> 2drop EXIT THEN
ELSE
fb8-columns2bytes swap fb8-columns2bytes tuck -
over r@ + 2dup + r> swap >r rot char-height 0 ?DO
3dup rmove
-rot screen-line-bytes tuck + -rot + swap rot
LOOP
3drop r> over -
THEN
char-height 0 ?DO
dup 2 pick fb8-erase-block screen-line-bytes +
LOOP
2drop
;
: fb8-reset-screen ( -- ) ( Left as no-op by design ) ;
: fb8-erase-screen ( -- )
frame-buffer-adr screen-height screen-line-bytes * fb8-erase-block
;
: fb8-invert-screen ( -- )
frame-buffer-adr screen-height screen-line-bytes * invert-region
;
: fb8-blink-screen ( -- ) fb8-invert-screen fb8-invert-screen ;
: fb8-install ( width height #columns #lines -- )
1 to screen-depth
2swap  to screen-height  to screen-width
screen-width to screen-line-bytes
screen-#rows min to #lines
screen-#columns min to #columns
screen-height char-height #lines * - 2/ to window-top
screen-width char-width #columns * - 2/ to window-left
['] fb8-toggle-cursor to toggle-cursor
['] fb8-draw-character to draw-character
['] fb8-insert-lines to insert-lines
['] fb8-delete-lines to delete-lines
['] fb8-insert-characters to insert-characters
['] fb8-delete-characters to delete-characters
['] fb8-erase-screen to erase-screen
['] fb8-blink-screen to blink-screen
['] fb8-invert-screen to invert-screen
['] fb8-reset-screen to reset-screen
['] fb8-draw-logo to draw-logo
;
: fb-install  ( width height #columns #lines depth -- )
>r
fb8-install
r> to screen-depth
screen-width screen-depth * to screen-line-bytes
;
: fb8-dump-bitmap cr char-height 0 ?do char-width 0 ?do dup c@ if ." @" else ." ." then 1+ loop cr loop drop ;
: fb8-dump-char >font -b swap fb8-char2bitmap fb8-dump-bitmap ;
ÿÿÿÿÿÿÿÿðµ0graphics.fs: draw-rectangle ( adr x y w h -- )
frame-buffer-adr 0= IF 4drop drop EXIT THEN
0 ?DO
4dup drop                              ( adr x y w adr x y )
i + screen-width * + screen-depth *    ( adr x y w adr offs )
frame-buffer-adr +                     ( adr x y w adr fb_adr )
over 3 pick screen-depth * i * +       ( adr x y w adr fb_adr src )
swap 3 pick screen-depth *             ( adr x y w adr src fb_adr len )
rmove                                  \ copy line ( adr x y w adr )
drop                                   ( adr x y w )
LOOP
4drop
;
: fill-rectangle ( col x y w h -- )
frame-buffer-adr 0= IF 4drop drop EXIT THEN
0 ?DO
4dup drop                              ( col x y w col x y )
i + screen-width * + screen-depth *    ( col x y w col offs )
frame-buffer-adr +                     ( col x y w col adr )
2 pick screen-depth * 2 pick           ( col x y w col adr len col )
rfill                                  \ draw line ( col x y w col )
drop                                   ( col x y w )
LOOP
4drop
;
: read-rectangle ( adr x y w h -- )
frame-buffer-adr 0= IF 4drop drop EXIT THEN
0 ?DO
4dup drop                              ( adr x y w adr x y )
i + screen-width * + screen-depth *    ( adr x y w adr offs )
frame-buffer-adr +                     ( adr x y w adr fb_adr )
over 3 pick screen-depth * i * +       ( adr x y w adr fb_adr dst )
3 pick                                 ( adr x y w adr fb_adr dst w )
rmove                                  \ copy line ( adr x y w adr )
drop                                   ( adr x y w )
LOOP
4drop
;
: dimensions ( -- width height )
screen-width screen-height
;
: init-default-palette
100 10 DO
i i i i color!
LOOP
00 00 00 0 color!
00 00 aa 1 color!
00 aa 00 2 color!
00 aa aa 3 color!
aa 00 00 4 color!
aa 00 aa 5 color!
aa 55 00 6 color!
aa aa aa 7 color!
55 55 55 8 color!
55 55 ff 9 color!
55 ff 55 a color!
55 ff ff b color!
ff 55 55 c color!
ff 55 ff d color!
ff ff 55 e color!
ff ff ff f color!
;
ÿÿÿÿÿÿÿÿÐ0generic-disk.fsnew-device set-unit                                          ( str len )
2dup device-name 
s" 0 pci-alias-" 2swap $cat evaluate
s" block" device-type      
s" block-size" $call-parent   CONSTANT block-size
s" max-transfer" $call-parent CONSTANT max-transfer 
: read-blocks ( addr block# #blocks -- #read )
my-unit s" dev-read-blocks" $call-parent
;    
INSTANCE VARIABLE deblocker
: open ( -- okay? )
0 0 s" deblocker" $open-package dup deblocker ! dup IF 
s" disk-label" find-package IF
my-args rot interpose
THEN
THEN 0<> ;
: close ( -- )
deblocker @ close-package ;
: seek ( pos.lo pos.hi -- status )
s" seek" deblocker @ $call-method ;
: read ( addr len -- actual )
s" read" deblocker @ $call-method ;
finish-device
ÿÿÿÿÿÿÿÿH0dma-function.fs: dma-alloc ( size -- virt )
my-phandle TO calling-child
s" dma-alloc" my-phandle parent $call-static
0 TO calling-child
;
: dma-free ( virt size -- )
my-phandle TO calling-child
s" dma-free" my-phandle parent $call-static
0 TO calling-child
;
: dma-map-in ( virt size cacheable? -- devaddr )
my-phandle TO calling-child
s" dma-map-in" my-phandle parent $call-static
0 TO calling-child
;
: dma-map-out ( virt devaddr size -- )
my-phandle TO calling-child
s" dma-map-out" my-phandle parent $call-static
0 TO calling-child
;
ÿÿÿÿÿÿÿÿ¨i0pci-device.fsget-node CONSTANT my-phandle
s" my-puid" my-phandle parent $call-static CONSTANT my-puid
: config-b@  puid >r my-puid TO puid my-space + rtas-config-b@ r> TO puid ;
: config-w@  puid >r my-puid TO puid my-space + rtas-config-w@ r> TO puid ;
: config-l@  puid >r my-puid TO puid my-space + rtas-config-l@ r> TO puid ;
: config-b!  puid >r my-puid TO puid my-space + rtas-config-b! r> TO puid ;
: config-w!  puid >r my-puid TO puid my-space + rtas-config-w! r> TO puid ;
: config-l!  puid >r my-puid TO puid my-space + rtas-config-l! r> TO puid ;
: config-dump puid >r my-puid TO puid my-space pci-dump r> TO puid ;
: open
puid >r             \ save the old puid
my-puid TO puid     \ set up the puid to the devices Hostbridge
pci-master-enable   \ And enable Bus Master, IO and MEM access again.
pci-mem-enable      \ enable mem access
pci-io-enable       \ enable io access
r> TO puid          \ restore puid
true
;
: close 
puid >r             \ save the old puid
my-puid TO puid     \ set up the puid
pci-device-disable  \ and disable the device
r> TO puid          \ restore puid
;
s" dma-function.fs" included
: devicefile ( -- str len )
s" pci-device_"
my-space pci-vendor@ 4 int2str $cat
s" _" $cat
my-space pci-device@ 4 int2str $cat
s" .fs" $cat
;
: classfile ( -- str len )
s" pci-class_"
my-space pci-class@ 10 rshift 2 int2str $cat
s" .fs" $cat
;
: setup ( -- )
devicefile romfs-lookup ?dup
IF
evaluate
ELSE
classfile romfs-lookup ?dup
IF
evaluate
ELSE
my-space pci-class-name type 2a emit cr
my-space pci-device-generic-setup
THEN
THEN
;
pci-device-disable
pci-error-enable
my-space 44 pci-out     \ config-addr ascii('D')
setup
ÿÿÿÿÿÿÿÿ°s0pci-bridge.fsget-node CONSTANT my-phandle
s" my-puid" my-phandle parent $call-static CONSTANT my-puid
pci-bus-number 1+ CONSTANT my-bus
s" pci-config-bridge.fs" included
s" dma-function.fs" included
: filename ( -- str len )
s" pci-bridge_"
my-space pci-vendor@ 4 int2str $cat
s" _" $cat
my-space pci-device@ 4 int2str $cat
s" .fs" $cat
;
: setup ( -- )
filename romfs-lookup ?dup
IF
evaluate
ELSE
my-space pci-class-name type 2a emit cr
my-space pci-bridge-generic-setup
my-space pci-reset-2nd
THEN
;
pci-device-disable
pci-error-enable
my-space 42 pci-out     \ config-addr ascii('B')
setup
pci-master-enable
pci-mem-enable
pci-io-enable
ÿÿÿÿÿÿÿÿ†ð†¬8pci-properties.fs: pci-class-name-00 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
01  OF s" display"               ENDOF
dup OF s" unknown-legacy-device" ENDOF
ENDCASE
;
: pci-class-name-01 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" scsi"         ENDOF
01  OF s" ide"          ENDOF
02  OF s" fdc"          ENDOF
03  OF s" ipi"          ENDOF
04  OF s" raid"         ENDOF
05  OF s" ata"          ENDOF
06  OF s" sata"         ENDOF
07  OF s" sas"          ENDOF
dup OF s" mass-storage" ENDOF
ENDCASE
;
: pci-class-name-02 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" ethernet"   ENDOF
01  OF s" token-ring" ENDOF
02  OF s" fddi"       ENDOF
03  OF s" atm"        ENDOF
04  OF s" isdn"       ENDOF
05  OF s" worldfip"   ENDOF
05  OF s" picmg"      ENDOF
dup OF s" network"    ENDOF
ENDCASE
;
: pci-class-name-03 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" vga"             ENDOF
0001  OF s" 8514-compatible" ENDOF
0100  OF s" xga"             ENDOF
0200  OF s" 3d-controller"   ENDOF
dup OF s" display"           ENDOF
ENDCASE
;
: pci-class-name-04 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" video"             ENDOF
01  OF s" sound"             ENDOF
02  OF s" telephony"         ENDOF
dup OF s" multimedia-device" ENDOF
ENDCASE
;
: pci-class-name-05 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" memory"            ENDOF
01  OF s" flash"             ENDOF
dup OF s" memory-controller" ENDOF
ENDCASE
;
: pci-class-name-06 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" host"                 ENDOF
01  OF s" isa"                  ENDOF
02  OF s" eisa"                 ENDOF
03  OF s" mca"                  ENDOF
04  OF s" pci"                  ENDOF
05  OF s" pcmcia"               ENDOF
06  OF s" nubus"                ENDOF
07  OF s" cardbus"              ENDOF
08  OF s" raceway"              ENDOF
09  OF s" semi-transparent-pci" ENDOF
0A  OF s" infiniband"           ENDOF
dup OF s" unknown-bridge"       ENDOF
ENDCASE
;
: pci-class-name-07 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" serial"                   ENDOF
0001  OF s" 16450-serial"             ENDOF
0002  OF s" 16550-serial"             ENDOF
0003  OF s" 16650-serial"             ENDOF
0004  OF s" 16750-serial"             ENDOF
0005  OF s" 16850-serial"             ENDOF
0006  OF s" 16950-serial"             ENDOF
0100  OF s" parallel"                 ENDOF
0101  OF s" bi-directional-parallel"  ENDOF
0102  OF s" ecp-1.x-parallel"         ENDOF
0103  OF s" ieee1284-controller"      ENDOF
01FE  OF s" ieee1284-device"          ENDOF
0200  OF s" multiport-serial"         ENDOF
0300  OF s" modem"                    ENDOF
0301  OF s" 16450-modem"              ENDOF
0302  OF s" 16550-modem"              ENDOF
0303  OF s" 16650-modem"              ENDOF
0304  OF s" 16750-modem"              ENDOF
0400  OF s" gpib"                     ENDOF
0500  OF s" smart-card"               ENDOF
dup   OF s" communication-controller" ENDOF
ENDCASE
;
: pci-class-name-08 ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" interrupt-controller" ENDOF
0001  OF s" isa-pic"              ENDOF
0002  OF s" eisa-pic"             ENDOF
0010  OF s" io-apic"              ENDOF
0020  OF s" iox-apic"             ENDOF
0100  OF s" dma-controller"       ENDOF
0101  OF s" isa-dma"              ENDOF
0102  OF s" eisa-dma"             ENDOF
0200  OF s" timer"                ENDOF
0201  OF s" isa-system-timer"     ENDOF
0202  OF s" eisa-system-timer"    ENDOF
0300  OF s" rtc"                  ENDOF
0301  OF s" isa-rtc"              ENDOF
0400  OF s" hot-plug-controller"  ENDOF
0500  OF s" sd-host-conrtoller"   ENDOF
dup   OF s" system-periphal"      ENDOF
ENDCASE
;
: pci-class-name-09 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" keyboard"         ENDOF
01  OF s" pen"              ENDOF
02  OF s" mouse"            ENDOF
03  OF s" scanner"          ENDOF
04  OF s" gameport"         ENDOF
dup OF s" input-controller" ENDOF
ENDCASE
;
: pci-class-name-0A ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" dock"            ENDOF
dup OF s" docking-station" ENDOF
ENDCASE
;
: pci-class-name-0B ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" 386"           ENDOF
01  OF s" 486"           ENDOF
02  OF s" pentium"       ENDOF
10  OF s" alpha"         ENDOF
20  OF s" powerpc"       ENDOF
30  OF s" mips"          ENDOF
40  OF s" co-processor"  ENDOF
dup OF s" cpu"           ENDOF
ENDCASE
;
: pci-class-name-0C ( addr -- str len )
pci-class@ FFFF and CASE
0000  OF s" firewire"      ENDOF
0100  OF s" access-bus"    ENDOF
0200  OF s" ssa"           ENDOF
0300  OF s" usb-uhci"      ENDOF
0310  OF s" usb-ohci"      ENDOF
0320  OF s" usb-ehci"      ENDOF
0330  OF s" usb-xhci"      ENDOF
0380  OF s" usb"           ENDOF
03FE  OF s" usb-device"    ENDOF
0400  OF s" fibre-channel" ENDOF
0500  OF s" smb"           ENDOF
0600  OF s" infiniband"    ENDOF
0700  OF s" ipmi-smic"     ENDOF
0701  OF s" ipmi-kbrd"     ENDOF
0702  OF s" ipmi-bltr"     ENDOF
0800  OF s" sercos"        ENDOF
0900  OF s" canbus"        ENDOF
dup OF s" serial-bus"      ENDOF
ENDCASE
;
: pci-class-name-0D ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" irda"                ENDOF
01  OF s" consumer-ir"         ENDOF
10  OF s" rf-controller"       ENDOF
11  OF s" bluetooth"           ENDOF
12  OF s" broadband"           ENDOF
20  OF s" enet-802.11a"        ENDOF
21  OF s" enet-802.11b"        ENDOF
dup OF s" wireless-controller" ENDOF
ENDCASE
;
: pci-class-name-0E ( addr -- str len )
pci-class@ 8 rshift FF and CASE
dup OF s" intelligent-io" ENDOF
ENDCASE
;
: pci-class-name-0F ( addr -- str len )
pci-class@ 8 rshift FF and CASE
01  OF s" satelite-tv"     ENDOF
02  OF s" satelite-audio"  ENDOF
03  OF s" satelite-voice"  ENDOF
04  OF s" satelite-data"   ENDOF
dup OF s" satelite-devoce" ENDOF
ENDCASE
;
: pci-class-name-10 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" network-encryption"       ENDOF
01  OF s" entertainment-encryption" ENDOF
dup OF s" encryption"               ENDOF
ENDCASE
;
: pci-class-name-11 ( addr -- str len )
pci-class@ 8 rshift FF and CASE
00  OF s" dpio"                       ENDOF
01  OF s" counter"                    ENDOF
10  OF s" measurement"                ENDOF
20  OF s" managment-card"             ENDOF
dup OF s" data-processing-controller" ENDOF
ENDCASE
;
: pci-class-name ( addr -- str len )
dup pci-class@ 10 rshift CASE
00  OF pci-class-name-00 ENDOF
01  OF pci-class-name-01 ENDOF
02  OF pci-class-name-02 ENDOF
03  OF pci-class-name-03 ENDOF
04  OF pci-class-name-04 ENDOF
05  OF pci-class-name-05 ENDOF
06  OF pci-class-name-06 ENDOF
07  OF pci-class-name-07 ENDOF
08  OF pci-class-name-08 ENDOF
09  OF pci-class-name-09 ENDOF
0A  OF pci-class-name-0A ENDOF
0B  OF pci-class-name-0B ENDOF
0C  OF pci-class-name-0C ENDOF
0C  OF pci-class-name-0D ENDOF
0C  OF pci-class-name-0E ENDOF
0C  OF pci-class-name-0F ENDOF
0C  OF pci-class-name-10 ENDOF
0C  OF pci-class-name-11 ENDOF
dup OF drop s" unknown"  ENDOF
ENDCASE
;
: pci-bar-size@     ( bar-addr -- bar-size ) -1 over rtas-config-l! rtas-config-l@ ;
: pci-bar-size-mem@ ( bar-addr -- mem-size ) pci-bar-size@ -10 and invert 1+ FFFFFFFF and ;
: pci-bar-size-io@  ( bar-addr -- io-size  ) pci-bar-size@ -4 and invert 1+ FFFFFFFF and ;
: pci-bar-size ( bar-addr -- bar-size-raw )
dup rtas-config-l@ swap \ fetch original Value  ( bval baddr )
-1 over rtas-config-l!  \ make BAR show size    ( bval baddr )
dup rtas-config-l@      \ and fetch the size    ( bval baddr bsize )
-rot rtas-config-l!     \ restore Value
;
: pci-bar-size-mem32 ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
-10 and invert 1+       \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-size-rom ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
FFFFF800 and invert 1+  \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-size-mem64 ( bar-addr -- bar-size )
dup pci-bar-size        \ fetch raw size lower 32 bits
swap 4 + pci-bar-size   \ fetch raw size upper 32 bits
20 lshift +             \ and put them together
-10 and invert 1+       \ calc size
;
: pci-bar-size-io ( bar-addr -- bar-size )
pci-bar-size            \ fetch raw size
-4 and invert 1+        \ calc size
FFFFFFFF and            \ keep lower 32 bits
;
: pci-bar-code@ ( bar-addr -- 0|1..4|5 )
rtas-config-l@ dup                \ fetch the BaseAddressRegister
1 and IF                          \ IO BAR ?
2 and IF 0 ELSE 1 THEN    \ only '01' is valid
ELSE                              \ Memory BAR ?
F and CASE
0   OF 2 ENDOF    \ Memory 32 Bit Non-Prefetchable
8   OF 3 ENDOF    \ Memory 32 Bit Prefetchable
4   OF 4 ENDOF    \ Memory 64 Bit Non-Prefetchable
C   OF 5 ENDOF    \ Memory 64 Bit Prefechtable
dup OF 0 ENDOF    \ Not a valid BarType
ENDCASE
THEN
;
: assign-var ( size var -- al-mem )
2dup @                          \ ( size var size cur-mem ) read current free mem
swap #aligned                   \ ( size var al-mem )       align the mem to the size
dup 2swap -rot +                \ ( al-mem var new-mem )    add size to aligned mem
swap !                          \ ( al-mem )                set variable to new mem
;
: assign-bar-value32 ( bar size var -- 4 )
over IF                         \ IF size > 0
assign-var              \ | ( bar al-mem ) set variable to next mem
swap rtas-config-l!     \ | ( -- )         set the bar to al-mem
ELSE                            \ ELSE
2drop drop              \ | clear stack
THEN                            \ FI
4                               \ size of the base-address-register
;
: assign-bar-value64 ( bar size var -- 8 )
over IF                         \ IF size > 0
assign-var              \ | ( bar al-mem ) set variable to next mem
swap                    \ | ( al-mem addr ) calc config-addr of this bar
2dup rtas-config-l!     \ | ( al-mem addr ) set the Lower part of the bar to al-mem
4 + swap 20 rshift      \ | ( al-mem>>32 addr ) prepare the upper part of the al-mem
swap rtas-config-l!     \ | ( -- ) and set the upper part of the bar
ELSE                            \ ELSE
2drop drop              \ | clear stack
THEN                            \ FI
8                               \ size of the base-address-register
;
: assign-mem64-bar ( bar-addr -- 8 )
dup pci-bar-size-mem64         \ fetch size
pci-next-mem64 @ 0 = IF          \ Check if we have 64-bit memory range
pci-next-mem
ELSE
pci-next-mem64
THEN
assign-bar-value64              \ and set it all
;
: assign-mem32-bar ( bar-addr -- 4 )
dup pci-bar-size-mem32          \ fetch size
pci-next-mem                    \ var to change
assign-bar-value32              \ and set it all
;
: assign-mmio64-bar ( bar-addr -- 8 )
dup pci-bar-size-mem64          \ fetch size
pci-next-mem64 @ 0 = IF          \ Check if we have 64-bit memory range
pci-next-mmio
ELSE
pci-next-mem64              \ for board-qemu we will use same range
THEN
assign-bar-value64              \ and set it all
;
: assign-mmio32-bar ( bar-addr -- 4 )
dup pci-bar-size-mem32          \ fetch size
pci-next-mmio                   \ var to change
assign-bar-value32              \ and set it all
;
: assign-io-bar ( bar-addr -- 4 )
dup pci-bar-size-io             \ fetch size
pci-next-io                     \ var to change
assign-bar-value32              \ and set it all
;
: assign-rom-bar ( bar-addr -- )
dup pci-bar-size-rom            \ fetch size
dup IF                          \ IF size > 0
over >r                 \ | save bar addr for enable
pci-next-mmio           \ | var to change
assign-bar-value32      \ | and set it
drop                    \ | forget the BAR length
r@ rtas-config-l@       \ | fetch BAR
1 or r> rtas-config-l!  \ | and enable the ROM
ELSE                            \ ELSE
2drop                   \ | clear stack
THEN
;
: assign-bar ( bar-addr -- reg-size )
dup pci-bar-code@                       \ calc BAR type
dup IF                                  \ IF >0
CASE                            \ | CASE Setup the right type
1 OF assign-io-bar     ENDOF    \ | - set up an IO-Bar
2 OF assign-mmio32-bar ENDOF    \ | - set up an 32bit MMIO-Bar
3 OF assign-mem32-bar  ENDOF    \ | - set up an 32bit MEM-Bar (prefetchable)
4 OF assign-mmio64-bar ENDOF    \ | - set up an 64bit MMIO-Bar
5 OF assign-mem64-bar  ENDOF    \ | - set up an 64bit MEM-Bar (prefetchable)
ENDCASE                         \ | ESAC
ELSE                                    \ ELSE
ABORT                           \ | Throw an exception
THEN                                    \ FI
;
: assign-all-device-bars ( configaddr -- )
28 10 DO                        \ BARs start at 10 and end at 27
dup i +                 \ calc config-addr of the BAR
assign-bar              \ and set it up
+LOOP                           \ add 4 or 8 to the index and loop
30 + assign-rom-bar             \ set up the ROM if available
;
: assign-all-bridge-bars ( configaddr -- )
18 10 DO                        \ BARs start at 10 and end at 17
dup i +                 \ calc config-addr of the BAR
assign-bar              \ and set it up
+LOOP                           \ add 4 or 8 to the index and loop
38 + assign-rom-bar             \ set up the ROM if available
;
: gen-mem64-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch lower 32 bits ( paddr plen baddr val.lo R: size)
over 4 + rtas-config-l@         \ | fetch upper 32 bits               ( paddr plen baddr val.lo val.hi R: size)
20 lshift + -10 and >r          \ | calc 64 bit value and save it     ( paddr plen baddr R: size val )
83000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ sizeof(BAR) = 8 Bytes
;
: gen-pmem64-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch lower 32 bits ( paddr plen baddr val.lo R: size)
over 4 + rtas-config-l@         \ | fetch upper 32 bits               ( paddr plen baddr val.lo val.hi R: size)
20 lshift + -10 and >r          \ | calc 64 bit value and save it     ( paddr plen baddr R: size val )
C3000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ sizeof(BAR) = 8 Bytes
;
: gen-mem32-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-10 and >r                      \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
82000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-pmem32-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ fetch BAR Size        ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-10 and >r                      \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
C2000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-io-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len 4 )
dup pci-bar-size-io                     \ fetch BAR Size                      ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
-4 and >r                       \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
81000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ sizeof(BAR) = 4 Bytes
;
: gen-rom-bar-prop ( prop-addr prop-len bar-addr -- prop-addr prop-len )
dup pci-bar-size-rom                    \ fetch BAR Size                      ( paddr plen baddr bsize )
dup IF                                  \ IF Size > 0
>r dup rtas-config-l@           \ | save size and fetch value         ( paddr plen baddr val R: size)
FFFFF800 and >r                 \ | calc 32 bit value and save it     ( paddr plen baddr R: size val )
82000000 or encode-int+         \ | Encode config addr                ( paddr plen R: size val )
r> encode-64+                   \ | Encode assigned addr              ( paddr plen R: size )
r> encode-64+                   \ | Encode size                       ( paddr plen )
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
;
: pci-add-assigned-address ( prop-addr prop-len bar-addr -- prop-addr prop-len bsize )
dup pci-bar-code@                               \ calc BAR type                         ( paddr plen baddr btype)
CASE                                            \ CASE for the BAR types                ( paddr plen baddr )
0 OF drop 4              ENDOF          \ - not a valid type so do nothing
1 OF gen-io-bar-prop     ENDOF          \ - IO-BAR
2 OF gen-mem32-bar-prop  ENDOF          \ - MEM32
3 OF gen-pmem32-bar-prop ENDOF          \ - MEM32 prefetchable
4 OF gen-mem64-bar-prop  ENDOF          \ - MEM64
5 OF gen-pmem64-bar-prop ENDOF          \ - MEM64 prefetchable
ENDCASE                                         \ ESAC ( paddr plen bsize )
;
: pci-device-assigned-addresses-prop ( addr -- )
encode-start                                    \ provide mem for property              ( addr paddr plen )
2 pick 30 + gen-rom-bar-prop                    \ assign the rom bar
28 10 DO                                        \ we have 6 possible BARs
2 pick i +                              \ calc BAR address                      ( addr paddr plen bar-addr )      
pci-add-assigned-address                \ and generate the props for the BAR
+LOOP                                           \ increase Index by returned len
s" assigned-addresses" property drop            \ and write it into the device tree
;
: pci-bridge-assigned-addresses-prop ( addr -- )
encode-start                                    \ provide mem for property
2 pick 38 + gen-rom-bar-prop                    \ assign the rom bar
18 10 DO                                        \ we have 2 possible BARs
2 pick i +                              \ ( addr paddr plen current-addr )
pci-add-assigned-address                \ and generate the props for the BAR
+LOOP                                           \ increase Index by returned len
s" assigned-addresses" property drop            \ and write it into the device tree
;
: pci-bridge-gen-range ( paddr plen base limit type -- paddr plen )
>r over -                       \ calc size             ( paddr plen base size R:type )
dup 0< IF                       \ IF Size < 0           ( paddr plen base size R:type )
2drop r> drop           \ | forget values       ( paddr plen )
ELSE                            \ ELSE
1+ swap 2swap           \ | adjust stack        ( size base paddr plen R:type )
r@ encode-int+          \ | Child type          ( size base paddr plen R:type )
2 pick encode-64+       \ | Child address       ( size base paddr plen R:type )
r> encode-int+          \ | Parent type         ( size base paddr plen )
rot encode-64+          \ | Parent address      ( size paddr plen )
rot encode-64+          \ | Encode size         ( paddr plen )
THEN                            \ FI
;
: pci-bridge-gen-mmio-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 20 + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 0000FFF0 and 10 lshift      \ calc base-address     ( addr paddr plen val base )
swap 000FFFFF or                \ calc limit-address    ( addr paddr plen base limit )
02000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-gen-mem-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 24 + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 000FFFFF or                 \ calc limit Bits 31:0  ( addr paddr plen val limit.31:0 )
swap 0000FFF0 and 10 lshift     \ calc base Bits 31:0   ( addr paddr plen limit.31:0 base.31:0 )
4 pick 28 + rtas-config-l@      \ fetch upper Basebits  ( addr paddr plen limit.31:0 base.31:0 base.63:32 )
20 lshift or swap               \ and calc Base         ( addr paddr plen base.63:0 limit.31:0 )
4 pick 2C + rtas-config-l@      \ fetch upper Limitbits ( addr paddr plen base.63:0 limit.31:0 limit.63:32 )
20 lshift or                    \ and calc Limit        ( addr paddr plen base.63:0 limit.63:0 )
42000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-gen-io-range ( addr prop-addr prop-len -- addr prop-addr prop-len )
2 pick 1C + rtas-config-l@      \ fetch Value           ( addr paddr plen val )
dup 0000F000 and 00000FFF or    \ calc Limit Bits 15:0  ( addr paddr plen val limit.15:0 )
swap 000000F0 and 8 lshift      \ calc Base Bits 15:0   ( addr paddr plen limit.15:0 base.15:0 )
4 pick 30 + rtas-config-l@      \ fetch upper Bits      ( addr paddr plen limit.15:0 base.15:0 val )
dup FFFF and 10 lshift rot or   \ calc Base             ( addr paddr plen limit.15:0 val base.31:0 )
-rot FFFF0000 and or            \ calc Limit            ( addr paddr plen base.31:0 limit.31:0 )
01000000 pci-bridge-gen-range   \ and generate it       ( addr paddr plen )
;
: pci-bridge-range-props ( addr -- )
encode-start                    \ provide mem for property
pci-bridge-gen-mmio-range       \ generate the non prefetchable Memory Entry
pci-bridge-gen-mem-range        \ generate the prefetchable Memory Entry
pci-bridge-gen-io-range         \ generate the IO Entry
dup IF                          \ IF any space present (propsize>0)
s" ranges" property     \ | write it into the device tree
ELSE                            \ ELSE
s" " s" ranges" property
2drop                   \ | forget the properties
THEN                            \ FI
drop                            \ forget the address
;
: pci-bridge-interrupt-map ( -- )
encode-start                                    \ create the property                           ( paddr plen )
get-node child                                  \ find the first child                          ( paddr plen handle )
BEGIN dup WHILE                                 \ Loop as long as the handle is non-zero        ( paddr plen handle )
dup >r >space                           \ Get the my-space                              ( paddr plen addr R: handle )
pci-gen-irq-entry                       \ and Encode the interrupt settings             ( paddr plen R: handle)
r> peer                                 \ Get neighbour                                 ( paddr plen handle )
REPEAT                                          \ process next childe node                      ( paddr plen handle )
drop                                            \ forget the null                               ( paddr plen )
s" interrupt-map" property                      \ and set it                                    ( -- )
1 encode-int s" #interrupt-cells" property      \ encode the cell#
f800 encode-int 0 encode-int+ 0 encode-int+     \ encode the bit mask for config addr (Dev only)
7 encode-int+ s" interrupt-map-mask" property   \ encode IRQ#=7 and generate property
;
: encode-mem32-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 02000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-pmem32-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 4 )
dup pci-bar-size-mem32                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 42000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-mem64-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 03000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ BAR-Len = 8 (64Bit)
;
: encode-pmem64-bar ( prop-addr prop-len BAR-addr -- prop-addr prop-len 8 )
dup pci-bar-size-mem64                  \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 43000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
8                                       \ BAR-Len = 8 (64Bit)
;
: encode-rom-bar ( prop-addr prop-len configaddr -- prop-addr prop-len )
dup pci-bar-size-rom                            \ fetch raw BAR-size
dup IF                                          \ IF BAR is used
>r 02000000 or encode-int+              \ | save size and encode BAR addr
0 encode-64+                            \ | make mid and lo zero
r> encode-64+                           \ | calc and encode the size
ELSE                                            \ ELSE
2drop                                   \ | don't do anything
THEN                                            \ FI
;
: encode-io-bar ( prop-addr prop-len BAR-addr BAR-value -- prop-addr prop-len 4 )
dup pci-bar-size-io                     \ calc BAR-size ( not changing the BAR )
dup IF                                  \ IF BAR-size > 0       ( paddr plen baddr bsize )
>r 01000000 or encode-int+      \ | save size and encode BAR addr
0 encode-64+                    \ | make mid and lo zero
r> encode-64+                   \ | encode size
ELSE                                    \ ELSE
2drop                           \ | don't do anything
THEN                                    \ FI
4                                       \ BAR-Len = 4 (32Bit)
;
: encode-bar ( prop-addr prop-len bar-addr -- prop-addr prop-len bar-len )
dup pci-bar-code@                               \ calc BAR type
CASE                                            \ CASE for the BAR types ( paddr plen baddr val )
0 OF drop 4             ENDOF           \ - not a valid type so do nothing
1 OF encode-io-bar      ENDOF           \ - IO-BAR
2 OF encode-mem32-bar   ENDOF           \ - MEM32
3 OF encode-pmem32-bar  ENDOF           \ - MEM32 prefetchable
4 OF encode-mem64-bar   ENDOF           \ - MEM64
5 OF encode-pmem64-bar  ENDOF           \ - MEM64 prefetchable
ENDCASE                                         \ ESAC ( paddr plen blen )
;
: pci-reg-props ( configaddr -- )
dup encode-int                  \ configuration space           ( caddr paddr plen )
0 encode-64+                    \ make the rest 0
0 encode-64+                    \ encode the size as 0
2 pick pci-htype@               \ fetch Header Type             ( caddr paddr plen type )
1 and IF                        \ IF Bridge                     ( caddr paddr plen )
18 10 DO                \ | loop over all BARs
2 pick i +      \ | calc bar-addr               ( caddr paddr plen baddr )
encode-bar      \ | encode this BAR             ( caddr paddr plen blen )
+LOOP              \ | increase LoopIndex by the BARlen
2 pick 38 +             \ | calc ROM-BAR for a bridge   ( caddr paddr plen baddr )
encode-rom-bar          \ | encode the ROM-BAR          ( caddr paddr plen )
ELSE                            \ ELSE ordinary device          ( caddr paddr plen )
28 10 DO                 \ | loop over all BARs
2 pick i +      \ | calc bar-addr               ( caddr paddr plen baddr )
encode-bar      \ | encode this BAR             ( caddr paddr plen blen )
+LOOP              \ | increase LoopIndex by the BARlen
2 pick 30 +             \ | calc ROM-BAR for a device   ( caddr paddr plen baddr )
encode-rom-bar          \ | encode the ROM-BAR          ( caddr paddr plen )
THEN                            \ FI                            ( caddr paddr plen )
s" reg" property                \ and store it into the property
drop
;
: pci-common-props ( addr -- )
dup pci-class-name device-name
dup pci-vendor@    encode-int s" vendor-id"      property
dup pci-device@    encode-int s" device-id"      property
dup pci-revision@  encode-int s" revision-id"    property
dup pci-class@     encode-int s" class-code"     property
3 encode-int s" #address-cells" property
2 encode-int s" #size-cells"    property
dup pci-config-ext? IF 1 encode-int s" ibm,pci-config-space-type" property THEN
dup pci-status@
dup 9 rshift 3 and encode-int s" devsel-speed" property
dup 7 rshift 1 and IF 0 0 s" fast-back-to-back" property THEN
dup 6 rshift 1 and IF 0 0 s" 66mhz-capable" property THEN
5 rshift 1 and IF 0 0 s" udf-supported" property THEN
dup pci-cache@     ?dup IF encode-int s" cache-line-size" property THEN
pci-interrupt@ ?dup IF encode-int s" interrupts"      property THEN
;
: pci-device-props ( addr -- )
dup pci-common-props
dup pci-min-grant@ encode-int s" min-grant"   property
dup pci-max-lat@   encode-int s" max-latency" property
dup pci-sub-device@ ?dup IF encode-int s" subsystem-id" property THEN
dup pci-sub-vendor@ ?dup IF encode-int s" subsystem-vendor-id" property THEN
dup pci-device-assigned-addresses-prop
pci-reg-props
pci-hotplug-enabled IF
dup dup pci-addr2bus 8 lshift
swap pci-addr2dev 3 lshift or
40000000 + encode-int s" ibm,my-drc-index" property
dup dup pci-addr2bus 20 *
swap pci-addr2dev +
a base !
s" Slot " rot $cathex
hex
encode-string s" ibm,loc-code" property
THEN
;
: pci-bridge-props ( addr -- )
dup pci-bus@
encode-int s" primary-bus" property
encode-int s" secondary-bus" property
encode-int s" subordinate-bus" property
dup pci-bus@ drop encode-int rot encode-int+ s" bus-range" property
pci-device-slots encode-int s" slot-names" property
dup pci-bridge-range-props
dup pci-bridge-assigned-addresses-prop
s" interrupt-map" get-node get-property IF
pci-bridge-interrupt-map
ELSE 2drop THEN
pci-reg-props
;
: pci-bridge-generic-setup ( addr -- )
pci-device-slots >r             \ save the slot array on return stack
dup pci-common-props            \ set the common properties before scanning the bus
s" pci" device-type             \ the type is allways "pci"
dup func-pci-bridge-probe       \ find all device connected to it
dup assign-all-bridge-bars      \ set up all memory access BARs
dup pci-set-irq-line            \ set the interrupt pin
dup pci-set-capabilities        \ set up the capabilities
pci-bridge-props            \ and generate all properties
r> TO pci-device-slots          \ and reset the slot array
;
DEFER func-pci-device-props
: pci-device-generic-setup ( config-addr -- )
dup assign-all-device-bars      \ calc all BARs
dup pci-set-irq-line            \ set the interrupt pin
dup pci-set-capabilities        \ set up the capabilities
dup func-pci-device-props       \ and generate all properties
drop                            \ forget the config-addr
;
' pci-device-props TO func-pci-device-props
ÿÿÿÿÿÿÿÿ	`	8pci-config-bridge.fs: config-xt  ( config-addr xt -- data )
puid >r                            \ Safe puid
my-puid TO puid                    \ Set my-puid
swap dup ffff00 AND 0= IF          \ Has bus-device-function been specified?
my-space OR                     \ No: use my-space instead
THEN
swap execute                       \ Execute the rtas-config-xx function
r> TO puid                         \ Restore previous puid
;
: config-b@  ( config-addr -- data )  ['] rtas-config-b@ config-xt ;
: config-w@  ( config-addr -- data )  ['] rtas-config-w@ config-xt ;
: config-l@  ( config-addr -- data )  ['] rtas-config-l@ config-xt ;
: config-b!  ( data config-addr -- )  ['] rtas-config-b! config-xt ;
: config-w!  ( data config-addr -- )  ['] rtas-config-w! config-xt ;
: config-l!  ( data config-addr -- )  ['] rtas-config-l! config-xt ;
: config-dump puid >r my-puid TO puid my-space pci-dump r> TO puid ;
: decode-unit ( addr len -- phys.lo ... phys.hi )
2 hex-decode-unit       \ decode string
B lshift swap           \ shift the devicenumber to the right spot
8 lshift or             \ add the functionnumber
my-bus 10 lshift or     \ add the busnumber
0 0 rot                 \ make phys.lo = 0 = phys.mid
;
: encode-unit ( phys.lo ... phys.hi -- unit-str unit-len )
nip nip                         \ forget the both zeros
dup 8 rshift 7 and swap         \ calc Functionnumber
B rshift 1F and                 \ calc Devicenumber
over IF                         \ IF Function!=0
2 hex-encode-unit       \ | create string with DevNum,FnNum
ELSE                            \ ELSE
nip 1 hex-encode-unit   \ | create string with only DevNum
THEN                            \ FI
;
: map-in ( phys.lo phys.mid phys.hi size -- virt )
drop nip nip                         ( phys.hi )
dup FF AND dup 10 28 WITHIN NOT swap 30 <> AND IF
cr ." phys.hi = " . cr
ABORT" map-in with illegal config space address"
THEN
00FFFFFF AND                         \ Need only bus-dev-fn+register bits
dup config-l@                        ( phys.hi' bar.lo )
dup 7 AND 4 = IF                     \ Is it a 64-bit BAR?
swap 4 + config-l@ lxjoin         \ Add upper part of 64-bit BAR
ELSE
nip
THEN
F NOT AND                            \ Clear indicator bits
;
: map-out ( virt size -- )
2drop 
;
: dma-sync ( virt devaddr size -- )
2drop drop
;
: open true ;
: close ;
ÿÿÿÿÿÿÿÿø¾0update_flash.fsfalse value flash-new
: update-flash-help ( -- )
cr ." update-flash tool to flash host FW " cr
."              -f <filename>      : Flash from file (e.g. net:\boot_rom.bin)" cr
."              -l                 : Flash from load-base" cr
."              -d                 : Flash from old load base (used by drone)" cr
."              -c                 : Flash from temp to perm" cr
."              -r                 : Flash from perm to temp" cr
;
: flash-read-temp ( -- success? )
get-flashside 1 = IF flash-addr get-load-base over flash-image-size rmove true
ELSE
false
THEN
;
: flash-read-perm ( -- success? )
get-flashside 0= IF
flash-addr get-load-base over flash-image-size rmove true
ELSE
false
THEN
;
: flash-switch-side ( side -- success? )
set-flashside 0<> IF
s" Cannot change flashside" type cr false
ELSE
true
THEN
;
: flash-ensure-temp ( -- success? )
get-flashside 0= IF
cr ." Cannot flash perm! Switching to temp side!"
1 flash-switch-side
ELSE
true
THEN
;
: update-flash ( "text" )
get-flashside >r                              \ Save old flashside
parse-word                      ( str len )   \ Parse first string
drop dup c@                     ( str first-char )
[char] - <> IF
update-flash-help r> 2drop EXIT
THEN
1+ c@                           ( second-char )
CASE
[char] f OF
parse-word cr s" do-load" evaluate
flash-ensure-temp TO flash-new
ENDOF
[char] l OF
flash-ensure-temp
ENDOF
[char] d OF
flash-load-base get-load-base 200000 move
flash-ensure-temp
ENDOF
[char] c OF
flash-read-temp 0= flash-new or IF
." Cannot commit temp, need to boot on temp first " cr false
ELSE
0 flash-switch-side
THEN
ENDOF
[char] r OF
flash-read-perm 0= IF
." Cannot commit perm, need to boot on perm first " cr false
ELSE
1 flash-switch-side
THEN
ENDOF
dup      OF
false
ENDOF
ENDCASE
0= IF
update-flash-help r> drop EXIT
THEN
get-load-base flash-write 0= IF ." Flash write failed !! " cr THEN
r> set-flashside drop                           \ Restore old flashside
;
ÿÿÿÿÿÿÿÿ0ø0xmodem.fs01 CONSTANT XM-SOH   \ Start of header
04 CONSTANT XM-EOT   \ End-of-transmission
06 CONSTANT XM-ACK   \ Acknowledge
15 CONSTANT XM-NAK   \ Neg. acknowledge
0 VALUE xm-retries   \ Retry count
0 VALUE xm-block#
: xmodem-get-byte  ( timeout -- byte|-1 )
d# 1000 *
0 DO
key? IF key UNLOOP EXIT THEN
1 ms
LOOP
-1
;
: xmodem-rx-packet  ( address -- success? )
1 xmodem-get-byte    \ Get block number
dup 0 < IF
2drop false EXIT  \ Timeout
THEN
1 xmodem-get-byte    \ Get neg. block number
dup 0 < IF
3drop false EXIT  \ Timeout
THEN
rot 0                ( blk# ~blk# address chksum )
80 0 DO
1 xmodem-get-byte dup 0 < IF     ( blk# ~blk# address chksum byte )
3drop 2drop UNLOOP FALSE EXIT
THEN
dup 3 pick c!            ( blk# ~blk# address chksum byte )
+ swap 1+ swap           ( blk# ~blk# address+1 chksum' )
LOOP
0ff and
1 xmodem-get-byte <> IF
3drop FALSE EXIT
THEN
drop                        ( blk# ~blk# )
over xm-block# <> IF
2drop FALSE EXIT
THEN                        ( blk# ~blk# )
ff xor =
;
: (xmodem-load)  ( address -- bytes )
1 to xm-block#
0 to xm-retries
dup
BEGIN
d# 10 xmodem-get-byte dup >r
CASE
XM-SOH OF
dup xmodem-rx-packet IF
XM-ACK emit
80 +                     ( start-addr next-addr  R: rx-byte )
0 to xm-retries                    \ Reset retry count
xm-block# 1+ ff and to xm-block#   \ Increase current block#
ELSE
XM-NAK emit
xm-retries 1+ to xm-retries  \ Increase retry count
THEN
ENDOF
XM-EOT OF
XM-ACK emit
ENDOF
dup OF
XM-NAK emit
xm-retries 1+ to xm-retries  \ Increase retry count
ENDOF
ENDCASE
r> XM-EOT =
xm-retries d# 10 >= OR
UNTIL                         ( start-address end-address )
swap -                        ( bytes received )
;
: xmodem-load  ( -- bytes )
cr ." Waiting for start of XMODEM upload..." cr
get-load-base (xmodem-load)
;
ÿÿÿÿÿÿÿÿ(ï0scsi-disk.fsnew-device
s" disk" device-name
s" block" device-type
false VALUE scsi-disk-debug?
scsi-open
: execute-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len -- ... )
" execute-scsi-command" $call-parent
;
: retry-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len #retries -- ... )
" retry-scsi-command" $call-parent
;
0 INSTANCE VALUE block-size
0 INSTANCE VALUE max-transfer
0 INSTANCE VALUE max-block-num
0 INSTANCE VALUE is_cdrom
INSTANCE VARIABLE deblocker
CREATE scratch 100 allot
CREATE cdb 10 allot
: dump-scsi-error ( sense-buf sense-len stat name namelen -- )
." SCSI-DISK: " my-self instance>path type ." ," type ."  failed" cr
." SCSI-DISK: Status " dup . .status-text
0<> IF
."  Sense " scsi-get-sense-data dup . .sense-text
."  ASC " . ." ASCQ " . cr
ELSE drop THEN
;
: read-blocks ( addr block# #blocks -- #read )
scsi-disk-debug? IF
." SCSI-DISK: read-blocks " .s cr
THEN
2dup + max-block-num > IF
." SCSI-DISK: Access beyond end of device ! " cr
drop
dup max-block-num > IF
drop drop 0 EXIT
THEN
dup max-block-num swap -
THEN
dup block-size *                            ( addr block# #blocks len )
>r rot r> 			                ( block# #blocks addr len )
2swap                                       ( addr len block# #blocks )
dup >r
cdb                                         ( addr len block# #blocks cdb )
max-block-num FFFFFFFF > IF
scsi-build-read-16                      ( addr len )
ELSE
scsi-build-read-10                      ( addr len )
THEN
r> -rot                                     ( #blocks addr len )
scsi-dir-read cdb scsi-param-size 10
retry-scsi-command
dup 0<> IF " read-blocks" dump-scsi-error -65 throw ELSE drop THEN
;
: (inquiry) ( size -- buffer | NULL )
dup cdb scsi-build-inquiry
scratch swap scsi-dir-read cdb scsi-param-size 10 retry-scsi-command
0= IF scratch ELSE 2drop 0 THEN
;
: inquiry ( -- buffer | NULL )
scsi-disk-debug? IF
." SCSI-DISK: inquiry " .s cr
THEN
d# 36 (inquiry) 0= IF 0 EXIT THEN
scratch inquiry-data>add-length c@ 5 +
(inquiry)
;
: read-capacity ( -- blocksize #blocks )
scsi-disk-debug? IF
." SCSI-DISK: read-capacity " .s cr
THEN
scratch 10 erase
cdb scsi-build-read-cap-10 scratch scsi-length-read-cap-10-data scsi-dir-read
cdb scsi-param-size 1 retry-scsi-command
dup 0<> IF " read-capacity" dump-scsi-error 0 0 EXIT THEN
drop scratch scsi-get-capacity-10 1 +
;
: read-capacity-16 ( -- blocksize #blocks )
scsi-disk-debug? IF
." SCSI-DISK: read-capacity-16 " .s cr
THEN
scratch scsi-length-read-cap-16-data erase
cdb scsi-build-read-cap-16 scratch scsi-length-read-cap-16-data scsi-dir-read
cdb scsi-param-size 1 retry-scsi-command
dup 0<> IF " read-capacity-16" dump-scsi-error 0 0 EXIT THEN
drop scratch scsi-get-capacity-16 1 +
;
100 CONSTANT test-unit-retries
: test-unit-ready ( true | [ ascq asc sense-key false ] )
scsi-disk-debug? IF
." SCSI-DISK: test-unit-ready " .s cr
THEN
cdb scsi-build-test-unit-ready
0 0 0 cdb scsi-param-size test-unit-retries retry-scsi-command
0= IF true EXIT THEN
0= IF drop 0 0 4 false EXIT THEN
scsi-get-sense-data false
;
: start-stop-unit ( state# -- true | false )
scsi-disk-debug? IF
." SCSI-DISK: start-stop-unit " .s cr
THEN
cdb scsi-build-start-stop-unit
0 0 0 cdb scsi-param-size 10 retry-scsi-command
0= IF true ELSE 2drop false THEN
;
: compare-sense ( ascq asc key ascq2 asc2 key2 -- true | false )
3 pick =	    ( ascq asc key ascq2 asc2 keycmp )
swap 4 pick =   ( ascq asc key ascq2 keycmp asccmp )
rot 5 pick =    ( ascq asc key keycmp asccmp ascqcmp )
and and nip nip nip
;
0 CONSTANT CDROM-READY
1 CONSTANT CDROM-NOT-READY
2 CONSTANT CDROM-NO-DISK
3 CONSTANT CDROM-TRAY-OPEN
4 CONSTANT CDROM-INIT-REQUIRED
5 CONSTANT CDROM-TRAY-MAYBE-OPEN
: cdrom-try-close-tray ( -- )
scsi-const-load start-stop-unit drop
;
: cdrom-must-close-tray ( -- )
scsi-const-load start-stop-unit not IF
." Tray open !" cr -65 throw
THEN
;
: get-media-event ( -- true | false )
scsi-disk-debug? IF
." SCSI-DISK: get-media-event " .s cr
THEN
cdb scsi-build-get-media-event
scratch scsi-length-media-event scsi-dir-read cdb scsi-param-size 1 retry-scsi-command
0= IF true ELSE 2drop false THEN
;
: cdrom-status ( -- status )
test-unit-ready
IF CDROM-READY EXIT THEN
scsi-disk-debug? IF
." TestUnitReady sense: " 3dup . . . cr
THEN
3dup 1 4 2 compare-sense IF
3drop CDROM-NOT-READY EXIT
THEN
get-media-event IF
scratch w@ 4 >= IF
scratch 2 + c@ 04 = IF
scratch 5 + c@
dup 02 and 0<> IF drop 3drop CDROM-READY EXIT THEN
dup 01 and 0<> IF drop 3drop CDROM-TRAY-OPEN EXIT THEN
drop 3drop CDROM-NO-DISK EXIT
THEN
THEN
THEN
3dup 2 4 2 compare-sense IF
3drop CDROM-INIT-REQUIRED EXIT
THEN
over 4 = over 2 = and IF
3drop CDROM-READY EXIT
THEN
over 3a = IF
3drop CDROM-NO-DISK EXIT
THEN
3drop CDROM-TRAY-MAYBE-OPEN
;
: prep-cdrom ( -- ready? )
5 0 DO
cdrom-status CASE
CDROM-READY           OF UNLOOP true EXIT ENDOF
CDROM-NO-DISK         OF ." No medium !" cr UNLOOP false EXIT ENDOF
CDROM-TRAY-OPEN       OF cdrom-must-close-tray ENDOF
CDROM-INIT-REQUIRED   OF cdrom-try-close-tray ENDOF
CDROM-TRAY-MAYBE-OPEN OF cdrom-try-close-tray ENDOF
ENDCASE
d# 1000 ms
LOOP
." Drive not ready !" cr false
;
: prep-disk ( -- ready? )
test-unit-ready not IF
." SCSI-DISK: Disk not ready ! "
." Sense " dup .sense-text ." [" . ." ]"
."  ASC " . ."  ASCQ " . cr
false EXIT THEN true
;
: open ( -- true | false )
scsi-disk-debug? IF
." SCSI-DISK: open [" .s ." ] unit is " my-unit . . ."  [" .s ." ]" cr
THEN
my-unit " set-address" $call-parent
inquiry dup 0= IF drop false EXIT THEN
scsi-disk-debug? IF
." ---- inquiry: ----" cr
dup 100 dump cr
." ------------------" cr
THEN
dup inquiry-data>peripheral c@ e0 and 0 <> IF
." SCSI-DISK: Unsupported PQ != 0" cr
false EXIT
THEN
inquiry-data>peripheral c@ CASE
5   OF true to is_cdrom ENDOF
7   OF true to is_cdrom ENDOF
ENDCASE
scsi-disk-debug? IF
is_cdrom IF
." SCSI-DISK: device treated as CD-ROM" cr
ELSE
." SCSI-DISK: device treated as disk" cr
THEN
THEN
is_cdrom IF prep-cdrom ELSE prep-disk THEN
not IF false EXIT THEN
" max-transfer" $call-parent to max-transfer
read-capacity to max-block-num to block-size
max-block-num 100000000 = IF
read-capacity-16 to max-block-num to block-size
THEN
max-block-num 0= block-size 0= OR IF
." SCSI-DISK: Failed to get disk capacity!" cr
FALSE EXIT
THEN
scsi-disk-debug? IF
." Capacity: " max-block-num . ." blocks of " block-size . cr
THEN
0 0 " deblocker" $open-package dup deblocker ! dup IF 
" disk-label" find-package IF
my-args rot interpose
THEN
THEN 0<>
;
: close ( -- )
deblocker @ close-package ;
: seek ( pos.lo pos.hi -- status )
s" seek" deblocker @ $call-method ;
: read ( addr len -- actual )
s" read" deblocker @ $call-method ;
scsi-close
finish-device
ÿÿÿÿÿÿÿÿ ^8scsi-host-helpers.fs: check-retry-sense? ( sense-buf sense-len -- retry? )
8 < IF -1 EXIT THEN
dup sense-data>response-code c@ 7e and 70 = IF
dup sense-data>sense-key c@ e0 and IF drop -1 EXIT THEN
THEN
scsi-get-sense-data? IF 	( ascq asc sense-key )
dup 2 < IF 3drop 0 EXIT THEN
dup 2 = swap 6 = or nip nip IF 1 EXIT THEN
THEN
-1
;
0 INSTANCE VALUE rcmd-buf-addr
0 INSTANCE VALUE rcmd-buf-len
0 INSTANCE VALUE rcmd-dir
0 INSTANCE VALUE rcmd-cmd-addr
0 INSTANCE VALUE rcmd-cmd-len
: retry-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len #retries -- ... )
>r \ stash #retries
to rcmd-cmd-len to rcmd-cmd-addr to rcmd-dir to rcmd-buf-len to rcmd-buf-addr
0  \ dummy status & sense
r> \ retreive #retries              ( stat #retries )
0 DO
0<> IF 2drop THEN
rcmd-buf-addr
rcmd-buf-len
rcmd-dir
rcmd-cmd-addr
rcmd-cmd-len
execute-scsi-command		( [ sense-buf sense-len ] stat )
dup 0= IF LEAVE THEN
dup -1 = IF LEAVE THEN
dup 2 = IF  			( sense-buf sense-len stat )
>r	\ stash stat		( sense-buf sense len )
2dup
check-retry-sense?	        ( sense-buf sense-len retry? )
r> swap \ unstash stat	( sense-buf sense-len stat retry? )
CASE
0 OF 3drop 0 LEAVE ENDOF	\ Swallow error, return 0
-1 OF LEAVE ENDOF		\ No retry
ENDCASE
ELSE \ Anything other than busy -> exit
dup 8 <> IF LEAVE THEN
THEN
a ms
LOOP
;
CREATE sector d# 512 allot
CREATE cdb 10 allot
: (inquiry) ( size -- buffer | NULL )
dup cdb scsi-build-inquiry
sector swap scsi-dir-read cdb scsi-param-size 10 retry-scsi-command
0= IF sector ELSE 2drop 0 THEN
;
: inquiry ( -- buffer | NULL )
d# 36 (inquiry) 0= IF 0 EXIT THEN
sector inquiry-data>add-length c@ 5 +
(inquiry)
;
: report-luns ( -- [ sector ] true | false )
200 cdb scsi-build-report-luns
sector 200 scsi-dir-read cdb scsi-param-size 10 retry-scsi-command
0= IF sector true ELSE drop false THEN
;
: make-disk-alias                               ( $name srplun -- )
>r 2dup r> -rot                             ( $name srplun $name)
find-alias 0<> IF 4drop exit THEN
get-node node>path
20 allot
" /disk@" string-cat                        ( $name srplun npath npathl )
rot base @ >r hex (u.) r> base ! string-cat ( $name $diskpath )
set-alias
;
ÿÿÿÿÿÿÿÿ°l8scsi-probe-helpers.fs: wrapped-inquiry ( -- true | false )
inquiry 0= IF false EXIT THEN
sector inquiry-data>peripheral c@ e0 and 0 =
;
: scsi-read-lun     ( addr -- lun true | false )
dup c@ C0 AND CASE
40 OF w@-be 3FFF AND TRUE ENDOF
0  OF w@-be          TRUE ENDOF
dup dup OF ." Unsupported LUN format = " . cr FALSE ENDOF
ENDCASE
;
: vscsi-report-luns ( -- array ndev )
dev-max-target 3 << alloc-mem dup
0                                    ( devarray devcur ndev )
dev-max-target 0 DO
i 0 dev-generate-srplun (set-target)
report-luns nip IF
sector l@                     ( devarray devcur ndev size )
sector 8 + swap               ( devarray devcur ndev lunarray size )
dup 8 + dup alloc-mem         ( devarray devcur ndev lunarray size size+ mem )
dup rot 0 fill                ( devarray devcur ndev lunarray size mem )
dup >r swap move r>           ( devarray devcur ndev mem )
dup sector l@ 3 >> 0 ?DO      ( devarray devcur ndev mem memcur )
dup dup scsi-read-lun IF
j swap dev-generate-srplun  swap x! 8 +
ELSE
2drop
THEN
LOOP drop
rot                           ( devarray ndev mem devcur )
dup >r x! r> 8 +              ( devarray ndev devcur )
swap 1 +
ELSE
dev-max-target 1 = IF
16 alloc-mem ( devarray devcur ndev mem )
dup 16 0 fill ( devarray devcur ndev mem )
dup 0 0 dev-generate-srplun swap x!  ( devarray devcur ndev mem )
rot x!  ( devarray ndev )
1 +
UNLOOP EXIT
THEN
THEN
LOOP
nip
;
: make-media-alias ( $name srplun -- )
>r
get-next-alias ?dup IF
r> make-disk-alias
ELSE
r> drop
THEN
;
: scsi-find-disks      ( -- )
."        SCSI: Looking for devices" cr
vscsi-report-luns
0 ?DO
dup x@
BEGIN
dup x@
dup 0= IF drop TRUE ELSE
(set-target) wrapped-inquiry IF
."           " current-target (u.) type ."  "
sector inquiry-data>peripheral c@ CASE
0   OF ." DISK     : " " disk"  current-target make-media-alias ENDOF
5   OF ." CD-ROM   : " " cdrom" current-target make-media-alias ENDOF
7   OF ." OPTICAL  : " " cdrom" current-target make-media-alias ENDOF
e   OF ." RED-BLOCK: " " disk"  current-target make-media-alias ENDOF
dup dup OF ." ? (" . 8 emit 29 emit 5 spaces ENDOF
ENDCASE
sector .inquiry-text cr
THEN
8 + FALSE
THEN
UNTIL drop
8 +
LOOP drop
;
ÿÿÿÿÿÿÿÿM`M%0scsi-support.fsvocabulary scsi-words                  \ create new word list named 'scsi-words'
also scsi-words  definitions           \ place next definitions into new list
false  value   scsi-param-debug        \ common debugging flag
d# 0   value   scsi-param-size         \ length of CDB processed last
h# 0   value   scsi-param-control      \ control word for CDBs as defined in SAM-4
d# 0   value   scsi-param-errors       \ counter for detected errors
: scsi-inc-errors
scsi-param-errors 1 + to scsi-param-errors
;
00 CONSTANT scsi-cmd-test-unit-ready
STRUCT
/c	FIELD test-unit-ready>operation-code     \ 00h
4	FIELD test-unit-ready>reserved           \ unused
/c	FIELD test-unit-ready>control            \ control byte as specified in SAM-4
CONSTANT scsi-length-test-unit-ready
: scsi-build-test-unit-ready  ( cdb -- )
dup scsi-length-test-unit-ready erase  ( cdb )
scsi-param-control swap test-unit-ready>control c!  ( )
scsi-length-test-unit-ready to scsi-param-size   \ update CDB length
;
a0 CONSTANT scsi-cmd-report-luns
STRUCT
/c	FIELD report-luns>operation-code     \ a0h
1	FIELD report-luns>reserved           \ unused
/c      FIELD report-luns>select-report      \ report select byte
3       FIELD report-luns>reserved2          \ unused
/l      FIELD report-luns>alloc-length       \ report length
1	FIELD report-luns>reserved3          \ unused
/c	FIELD report-luns>control            \ control byte
CONSTANT scsi-length-report-luns
: scsi-build-report-luns ( alloc-len cdb -- )
dup scsi-length-report-luns erase              \ 12 bytes CDB
scsi-cmd-report-luns over	          ( alloc-len cdb cmd cdb )
report-luns>operation-code c!	          ( alloc-len cdb )
scsi-param-control over report-luns>control c! ( alloc-len cdb )
report-luns>alloc-length l!	  \ size of Data-In Buffer
scsi-length-report-luns to scsi-param-size     \ update CDB length
;
03 CONSTANT scsi-cmd-request-sense
STRUCT
/c	FIELD request-sense>operation-code     \ 03h
3	FIELD request-sense>reserved           \ unused
/c	FIELD request-sense>allocation-length  \ buffer-length for data response
/c	FIELD request-sense>control            \ control byte as specified in SAM-4
CONSTANT scsi-length-request-sense
: scsi-build-request-sense    ( alloc-len cdb -- )
>r                         ( alloc-len )  ( R: -- cdb )
r@ scsi-length-request-sense erase  ( alloc-len )
scsi-cmd-request-sense r@           ( alloc-len cmd cdb )
request-sense>operation-code c!     ( alloc-len )
dup d# 252 >                        \ buffer length too big ?
IF
scsi-inc-errors
drop d# 252                      \ replace with 252
ELSE
dup d# 18 <                      \ allocated buffer too small ?
IF
scsi-inc-errors
drop 0                        \ reject return data
THEN
THEN                                      ( alloclen )
r@ request-sense>allocation-length c!     (  )
scsi-param-control r> request-sense>control c!  ( alloc-len cdb )  ( R: cdb -- )
scsi-length-request-sense to scsi-param-size  \ update CDB length
;
70 CONSTANT scsi-response(request-sense-0)
71 CONSTANT scsi-response(request-sense-1)
STRUCT
/c FIELD sense-data>response-code   \ 70h (current errors) or 71h (deferred errors)
/c FIELD sense-data>obsolete
/c FIELD sense-data>sense-key       \ D3..D0 = sense key, D7 = EndOfMedium
/l FIELD sense-data>info
/c FIELD sense-data>alloc-length    \ <= 244 (for max size)
/l FIELD sense-data>command-info
/c FIELD sense-data>asc             \ additional sense key
/c FIELD sense-data>ascq            \ additional sense key qualifier
/c FIELD sense-data>unit-code
3  FIELD sense-data>key-specific
/c FIELD sense-data>add-sense-bytes \ start of appended extra bytes
CONSTANT scsi-length-sense-data
: scsi-get-sense-data                  ( addr -- ascq asc sense-key )   
>r                                  ( R: -- addr )
r@ sense-data>response-code c@ 7f and 72 >= IF
r@ 3 + c@                           ( ascq )
r@ 2 + c@                           ( ascq asc ) 
r> 1 + c@ 0f and                    ( ascq asc sense-key )
ELSE
r@ sense-data>ASCQ c@               ( ascq )
r@ sense-data>ASC c@                ( ascq asc )
r> sense-data>sense-key c@ 0f and   ( ascq asc sense-key ) ( R: addr -- )
THEN
;
: scsi-get-sense-data?                 ( addr -- false | ascq asc sense-key true )
dup
sense-data>response-code c@
7e AND dup 70 = swap 72 = or         \ Response code (some devices have MSB set)
IF
scsi-get-sense-data TRUE
ELSE
drop FALSE        \ drop addr
THEN
;
: scsi-get-sense-ID?                 ( addr -- false | ascq asc sense-key true )
dup
sense-data>response-code c@
7e AND 70 =          \ Response code (some devices have MSB set)
IF
scsi-get-sense-data        ( ascq asc sense-key )
10 lshift                  ( ascq asc sense-key16 )
swap 8 lshift or           ( ascq sense-key+asc )
swap or                    \ 24-bit sense-ID ( sense-key+asc+ascq )
TRUE
ELSE
drop FALSE        \ drop addr
THEN
;
12 CONSTANT scsi-cmd-inquiry
STRUCT
/c	FIELD inquiry>operation-code     \ 0x12
/c	FIELD inquiry>reserved           \ + EVPD-Bit (vital product data)
/c	FIELD inquiry>page-code          \ page code for vital product data (if used)
/w	FIELD inquiry>allocation-length  \ length of Data-In-Buffer
/c	FIELD inquiry>control            \ control byte as specified in SAM-4
CONSTANT scsi-length-inquiry
: scsi-build-inquiry                   ( alloc-len cdb -- )
dup scsi-length-inquiry erase       \ 6 bytes CDB
scsi-cmd-inquiry over				   ( alloc-len cdb cmd cdb )
inquiry>operation-code c!	         ( alloc-len cdb )
scsi-param-control over inquiry>control c! ( alloc-len cdb )
inquiry>allocation-length w!	      \ size of Data-In Buffer
scsi-length-inquiry to scsi-param-size    \ update CDB length
;
STRUCT
/c	   FIELD inquiry-data>peripheral       \ qualifier and device type
/c	   FIELD inquiry-data>reserved1
/c	   FIELD inquiry-data>version          \ supported SCSI version (1,2,3)
/c	   FIELD inquiry-data>data-format
/c	   FIELD inquiry-data>add-length       \ total block length - 4
/c	   FIELD inquiry-data>flags1
/c	   FIELD inquiry-data>flags2
/c	   FIELD inquiry-data>flags3
d# 8	FIELD inquiry-data>vendor-ident     \ vendor string
d# 16	FIELD inquiry-data>product-ident    \ device string
/l 	FIELD inquiry-data>product-revision \ revision string
d# 20	FIELD inquiry-data>vendor-specific  \ optional params
CONSTANT scsi-length-inquiry-data
25 CONSTANT scsi-cmd-read-capacity-10  \ command code
STRUCT                                 \ SCSI 10-byte CDB structure
/c	FIELD read-cap-10>operation-code
/c	FIELD read-cap-10>reserved1
/l	FIELD read-cap-10>lba
/w	FIELD read-cap-10>reserved2
/c	FIELD read-cap-10>reserved3
/c	FIELD read-cap-10>control
CONSTANT scsi-length-read-cap-10
: scsi-build-read-cap-10                     ( cdb -- )
dup scsi-length-read-cap-10 erase         ( cdb )
scsi-cmd-read-capacity-10 over            ( cdb cmd cdb )
read-cap-10>operation-code c!             ( cdb )
scsi-param-control swap read-cap-10>control c! ( )
scsi-length-read-cap-10 to scsi-param-size    \ update CDB length
;
STRUCT
/l	FIELD read-cap-10-data>max-lba
/l	FIELD read-cap-10-data>block-size
CONSTANT scsi-length-read-cap-10-data
: scsi-get-capacity-10                 ( addr -- block-size #blocks )
>r                                  ( addr -- ) ( R: -- addr )
r@ read-cap-10-data>block-size l@   ( block-size )
r> read-cap-10-data>max-lba l@      ( block-size #blocks ) ( R: addr -- )
;
9e CONSTANT scsi-cmd-read-capacity-16        \ command code
STRUCT                                       \ SCSI 16-byte CDB structure
/c	FIELD read-cap-16>operation-code
/c	FIELD read-cap-16>service-action
/l	FIELD read-cap-16>lba-high
/l	FIELD read-cap-16>lba-low
/l	FIELD read-cap-16>allocation-length    \ should be 32
/c	FIELD read-cap-16>reserved
/c	FIELD read-cap-16>control
CONSTANT scsi-length-read-cap-16
: scsi-build-read-cap-16  ( cdb -- )
>r r@                                     ( R: -- cdb )
scsi-length-read-cap-16 erase             (  )
scsi-cmd-read-capacity-16                 ( code )
r@ read-cap-16>operation-code c!          (  )
10 r@ read-cap-16>service-action c!
d# 32                                     \ response size 32 bytes
r@ read-cap-16>allocation-length l!       (  )
scsi-param-control r> read-cap-16>control c! ( R: cdb -- )
scsi-length-read-cap-16 to scsi-param-size \ update CDB length
;
STRUCT
/l	FIELD read-cap-16-data>max-lba-high    \ upper quadlet of Max-LBA
/l	FIELD read-cap-16-data>max-lba-low     \ lower quadlet of Max-LBA
/l	FIELD read-cap-16-data>block-size      \ logical block length in bytes
/c	FIELD read-cap-16-data>protect         \ type of protection (4 bits)
/c	FIELD read-cap-16-data>exponent        \ logical blocks per physical blocks
/w	FIELD read-cap-16-data>lowest-aligned  \ first LBA of a phsy. block
10 FIELD read-cap-16-data>reserved        \ 16 reserved bytes
CONSTANT scsi-length-read-cap-16-data        \ results in 32
: scsi-get-capacity-16                       ( addr -- block-size #blocks )
>r                                        ( R: -- addr )
r@ read-cap-16-data>block-size l@         ( block-size )
r@ read-cap-16-data>max-lba-high l@       ( block-size #blocks-high )
d# 32 lshift                              ( block-size #blocks-upper )
r> read-cap-16-data>max-lba-low l@ +      ( block-size #blocks ) ( R: addr -- )
;
5a CONSTANT scsi-cmd-mode-sense-10
STRUCT
/c	FIELD mode-sense-10>operation-code
/c	FIELD mode-sense-10>res-llbaa-dbd-res
/c	FIELD mode-sense-10>pc-page-code       \ page code + page control
/c	FIELD mode-sense-10>sub-page-code
3	FIELD mode-sense-10>reserved2
/w	FIELD mode-sense-10>allocation-length
/c	FIELD mode-sense-10>control
CONSTANT scsi-length-mode-sense-10
: scsi-build-mode-sense-10                   ( alloc-len subpage page cdb -- )
>r                                        ( alloc-len subpage page ) ( R: -- cdb )
r@ scsi-length-mode-sense-10 erase        \ 10 bytes CDB
scsi-cmd-mode-sense-10                    ( alloc-len subpage page cmd )
r@  mode-sense-10>operation-code c!		   ( alloc-len subpage page )
10 r@ mode-sense-10>res-llbaa-dbd-res c!  \ long LBAs accepted
r@ mode-sense-10>pc-page-code c!	         ( alloc-len subpage )
r@ mode-sense-10>sub-page-code c!	      ( alloc-len )
r@ mode-sense-10>allocation-length w!     ( )
scsi-param-control r> mode-sense-10>control c!  ( R: cdb -- )
scsi-length-mode-sense-10 to scsi-param-size  \ update CDB length
;
STRUCT
/w	FIELD mode-sense-10-data>head-length
/c	FIELD mode-sense-10-data>head-medium
/c	FIELD mode-sense-10-data>head-param
/c	FIELD mode-sense-10-data>head-longlba
/c	FIELD mode-sense-10-data>head-reserved
/w	FIELD mode-sense-10-data>head-descr-len
CONSTANT scsi-length-mode-sense-10-data
: .mode-sense-data   ( addr -- )
cr
dup mode-sense-10-data>head-length
w@ ." Mode Length: " .d space
dup mode-sense-10-data>head-medium
c@ ." / Medium Type: " .d space
dup mode-sense-10-data>head-longlba
c@ ." / Long LBA: " .d space
mode-sense-10-data>head-descr-len
w@ ." / Descr. Length: " .d
;
28 CONSTANT scsi-cmd-read-10
STRUCT
/c FIELD read-10>operation-code
/c FIELD read-10>protect
/l FIELD read-10>block-address      \ logical block address (32bits)
/c FIELD read-10>group
/w FIELD read-10>length             \ transfer length (16-bits)
/c FIELD read-10>control
CONSTANT scsi-length-read-10
: scsi-build-read-10                         ( block# #blocks cdb -- )
>r                                        ( block# #blocks )  ( R: -- cdb )
r@ scsi-length-read-10 erase             \ 10 bytes CDB
scsi-cmd-read-10 r@ read-10>operation-code c! ( block# #blocks )
r@ read-10>length w!                      ( block# )
r@ read-10>block-address l!               (  )
scsi-param-control r> read-10>control c!  ( R: cdb -- )
scsi-length-read-10 to scsi-param-size    \ update CDB length
;
a8 CONSTANT scsi-cmd-read-12
STRUCT
/c FIELD read-12>operation-code     \ code: a8
/c FIELD read-12>protect            \ RDPROTECT, DPO, FUA, FUA_NV
/l FIELD read-12>block-address      \ lba
/l FIELD read-12>length             \ transfer length (32bits)
/c FIELD read-12>group              \ group number
/c FIELD read-12>control
CONSTANT scsi-length-read-12
: scsi-build-read-12                         ( block# #blocks cdb -- )
>r                                        ( block# #blocks )  ( R: -- cdb )
r@ scsi-length-read-12 erase             \ 12 bytes CDB
scsi-cmd-read-12 r@ read-12>operation-code c! ( block# #blocks )
r@ read-12>length l!                      ( block# )
r@ read-12>block-address l!               (  )
scsi-param-control r> read-12>control c!  ( R: cdb -- )
scsi-length-read-12 to scsi-param-size    \ update CDB length
;
88 CONSTANT scsi-cmd-read-16
STRUCT
/c FIELD read-16>operation-code     \ code: 88
/c FIELD read-16>protect            \ RDPROTECT, DPO, FUA, FUA_NV
/x FIELD read-16>block-address      \ lba
/l FIELD read-16>length             \ transfer length (32bits)
/c FIELD read-16>group              \ group number
/c FIELD read-16>control
CONSTANT scsi-length-read-16
: scsi-build-read-16                         ( block# #blocks cdb -- )
>r                                        ( block# #blocks )  ( R: -- cdb )
r@ scsi-length-read-16 erase              \ 16 bytes CDB
scsi-cmd-read-16 r@ read-16>operation-code c! ( block# #blocks )
r@ read-16>length l!                      ( block# )
r@ read-16>block-address x!               (  )
scsi-param-control r> read-16>control c!  ( R: cdb -- )
scsi-length-read-16 to scsi-param-size    \ update CDB length
;
: scsi-build-read?   ( block# #blocks cdb -- length )
over              ( block# #blocks cdb #blocks )
fffe >            \ tx-length (#blocks) exceeds 16-bit limit ?
IF
scsi-build-read-12   ( block# #blocks cdb -- )
scsi-length-read-12  ( length )
ELSE                    ( block# #blocks cdb )
scsi-build-read-10   ( block# #blocks cdb -- )
scsi-length-read-10  ( length )
THEN
;
1b CONSTANT scsi-cmd-start-stop-unit
STRUCT
/c FIELD start-stop-unit>operation-code
/c FIELD start-stop-unit>immed
/w FIELD start-stop-unit>reserved
/c FIELD start-stop-unit>pow-condition
/c FIELD start-stop-unit>control
CONSTANT scsi-length-start-stop-unit
f1 CONSTANT scsi-const-active-power    \ param used for start-stop-unit
f2 CONSTANT scsi-const-idle-power      \ param used for start-stop-unit
f3 CONSTANT scsi-const-standby-power   \ param used for start-stop-unit
3  CONSTANT scsi-const-load            \ param used for start-stop-unit
2  CONSTANT scsi-const-eject           \ param used for start-stop-unit
1  CONSTANT scsi-const-start
0  CONSTANT scsi-const-stop
: scsi-build-start-stop-unit                 ( state# cdb -- )
>r                                        ( state# )  ( R: -- cdb )
r@ scsi-length-start-stop-unit erase      \ 6 bytes CDB
scsi-cmd-start-stop-unit r@ start-stop-unit>operation-code c!
dup 3 >
IF
4 lshift                         \ shift to upper nibble
THEN                                ( state )
r@ start-stop-unit>pow-condition c!       (  )
scsi-param-control r> start-stop-unit>control c!  ( R: cdb -- )
scsi-length-start-stop-unit to scsi-param-size  \ update CDB length
;
2b CONSTANT scsi-cmd-seek
STRUCT
/c FIELD seek>operation-code
/c FIELD seek>reserved1
/l FIELD seek>lba
3  FIELD seek>reserved2
/c FIELD seek>control
CONSTANT scsi-length-seek
: scsi-build-seek  ( lba cdb -- )
>r              ( lba )  ( R: -- cdb )
r@ scsi-length-seek erase           \ 10 bytes CDB
scsi-cmd-seek r@ seek>operation-code c!
r> seek>lba l!  (  )  ( R: cdb -- )
scsi-length-seek to scsi-param-size \ update CDB length
;
STRUCT
/w FIELD media-event-data-len
/c FIELD media-event-nea-class
/c FIELD media-event-supp-class
/l FIELD media-event-data
CONSTANT scsi-length-media-event
: scsi-build-get-media-event                     ( cdb -- )
dup c erase				         ( cdb )
4a over c!				         ( cdb )
01 over 1 + c!
10 over 4 + c!
08 over 8 + c!
drop
;
: .sense-text ( scode -- )
case
0    OF s" OK"               ENDOF
1    OF s" RECOVERED ERR"    ENDOF
2    OF s" NOT READY"        ENDOF
3    OF s" MEDIUM ERROR"     ENDOF
4    OF s" HARDWARE ERR"     ENDOF
5    OF s" ILLEGAL REQUEST"  ENDOF
6    OF s" UNIT ATTENTION"   ENDOF
7    OF s" DATA PROTECT"     ENDOF
8    OF s" BLANK CHECK"      ENDOF
9    OF s" VENDOR SPECIFIC"  ENDOF
a    OF s" COPY ABORTED"     ENDOF
b    OF s" ABORTED COMMAND"  ENDOF
d    OF s" VOLUME OVERFLOW"  ENDOF
e    OF s" MISCOMPARE"       ENDOF
dup  OF s" UNKNOWN"          ENDOF
endcase
5b emit type 5d emit
;
: .status-text  ( stat -- )
case
00  OF s" GOOD"                  ENDOF
02  OF s" CHECK CONDITION"       ENDOF
04  OF s" CONDITION MET"         ENDOF
08  OF s" BUSY"                  ENDOF
18  OF s" RESERVATION CONFLICT"  ENDOF
28  OF s" TASK SET FULL"         ENDOF
30  OF s" ACA ACTIVE"            ENDOF
40  OF s" TASK ABORTED"          ENDOF
dup OF s" UNKNOWN"               ENDOF
endcase
5b emit type 5d emit
;
: .dec3-2 ( prenum postnum -- )
swap
base @ >r                           \ save actual base setting
decimal                             \ show decimal values
4 .r 2e emit
dup 9 <= IF 30 emit THEN .d         \ 3 pre-decimal, right aligned
r> base !                           \ restore base
;
: .capacity-text  ( block-size #blocks -- )
scsi-param-debug                    \ debugging flag set ?
IF                                  \ show additional info
2dup
cr
." LBAs: " .d                    \ highest logical block number
." / Block-Size: " .d
." / Total Capacity: "
THEN
*                                   \ calculate total capacity
dup d# 1000000000000 >=             \ check terabyte limit
IF
d# 1000000000000 /mod
swap
d# 10000000000 /                 \ limit remainder to two digits
.dec3-2 ." TB"                   \ show terabytes as xxx.yy
ELSE
dup d# 1000000000 >=             \ check gigabyte limit
IF
d# 1000000000 /mod
swap
d# 10000000 /
.dec3-2 ." GB"                \ show gigabytes as xxx.yy
ELSE
dup d# 1000000 >=
IF
d# 1000000 /mod            \ check mega byte limit
swap
d# 10000 /
.dec3-2 ." MB"             \ show megabytes as xxx.yy
ELSE
dup d# 1000 >=             \ check kilo byte limit
IF
d# 1000 /mod
swap
d# 10 /
.dec3-2 ." kB"
ELSE
.d ."  Bytes"
THEN
THEN
THEN
THEN
;
: .inquiry-text  ( addr -- )
22 emit     \ enclose text with "
dup inquiry-data>vendor-ident      8 type space
dup inquiry-data>product-ident    10 type space
inquiry-data>product-revision  4 type
22 emit
;
: scsi-supp-init  ( -- )
false   to scsi-param-debug         \ no debug strings
h# 0   to scsi-param-size
h# 0   to scsi-param-control        \ common CDB control byte
d# 0   to scsi-param-errors         \ local errors (param limits)
;
true  CONSTANT scsi-dir-read
false CONSTANT scsi-dir-write
0 VALUE scsi-context                   \ addr of word list on top
: scsi-init  ( -- )
also scsi-words                     \ append scsi word-list
context  to scsi-context            \ save for close process
scsi-supp-init                      \ preset all scsi-param-xxx values
scsi-param-debug
IF
space ." SCSI-SUPPORT OPENED" cr
.wordlists
THEN
;
: scsi-close  ( -- )
scsi-param-debug
IF
space ." Closing SCSI-SUPPORT .. " cr
THEN
context scsi-context =              \ scsi word list still active ?
IF
scsi-param-errors 0<>          \ any errors occurred ?
IF
cr ." ** WARNING: " scsi-param-errors .d
." SCSI Errors occurred ** " cr
THEN
previous                         \ remove scsi word list on top
0 to scsi-context                \ prevent from being misinterpreted
ELSE
cr ." ** WARNING: Trying to close non-open SCSI-SUPPORT (1) ** " cr
THEN
scsi-param-debug
IF
.wordlists
THEN
;
s" scsi-init" $find drop               \ return execution pointer, when included
previous                               \ remove scsi word list from search path
definitions                            \ place next definitions into previous list
ÿÿÿÿÿÿÿÿq pâ0evaluator.fsvariable ip
variable fcode-end 
variable fcode-num
1 value fcode-spread
2 value fcode-offset
false value eva-debug?
true value fcode-debug?
defer fcode-rb@
defer fcode@
' c@ to fcode-rb@
create token-table 2000 cells allot    \ 1000h = 4096d
: ?offset16 ( -- true|false )
fcode-offset 2 =
;
: ?arch64 ( -- true|false )
cell 8 =
;
: ?bigendian ( -- true|false )
deadbeef fcode-num !
fcode-num ?arch64 IF 4 + THEN
c@ de =
;
: reset-fcode-end ( -- )
false fcode-end !
;
: get-ip ( -- n )
ip @
;
: set-ip ( n -- )
ip !
;
: next-ip ( -- )
get-ip 1+ set-ip
;
: jump-n-ip ( n -- )
get-ip + set-ip
;
: read-byte ( -- n )
get-ip fcode-rb@
;
: ?compile-mode ( -- on|off )
state @
;
: save-evaluator-state
get-ip               eva-debug? IF ." saved ip "           dup . cr THEN
fcode-end @          eva-debug? IF ." saved fcode-end "    dup . cr THEN
fcode-offset         eva-debug? IF ." saved fcode-offset " dup . cr THEN
fcode-spread         eva-debug? IF ." saved fcode-spread " dup . cr THEN
['] fcode@ behavior  eva-debug? IF ." saved fcode@ "       dup . cr THEN
;
: restore-evaluator-state
eva-debug? IF ." restored fcode@ "       dup . cr THEN  to fcode@
eva-debug? IF ." restored fcode-spread " dup . cr THEN  to fcode-spread
eva-debug? IF ." restored fcode-offset " dup . cr THEN  to fcode-offset
eva-debug? IF ." restored fcode-end "    dup . cr THEN  fcode-end !
eva-debug? IF ." restored ip "           dup . cr THEN  set-ip
;
: token-table-index ( fcode# -- addr )
cells token-table +
;
: join-immediate ( xt immediate? addr -- xt+immediate? addr )
-rot + swap
;
: split-immediate ( xt+immediate? -- xt immediate? )
dup 1 and 2dup - rot drop swap
;
: literal, ( n -- )
postpone literal
;
: fc-string,
postpone sliteral
dup c, bounds ?do i c@ c, loop
;
: set-token ( xt immediate? fcode# -- )
token-table-index join-immediate !
;
: get-token ( fcode# -- xt immediate? )
token-table-index @ split-immediate
;
?bigendian [IF]                       \ Big endian access functions first
: read-fcode-num16 ( -- n )
0 fcode-num !
?arch64 IF
read-byte fcode-num 6 + C!
next-ip
read-byte fcode-num 7 + C!
ELSE
read-byte fcode-num 2 + C!
next-ip
read-byte fcode-num 3 + C!
THEN
fcode-num @
;
: read-fcode-num32 ( -- n )
0 fcode-num !
?arch64 IF
read-byte fcode-num 4 + C!
next-ip
read-byte fcode-num 5 + C!
next-ip
read-byte fcode-num 6 + C!
next-ip
read-byte fcode-num 7 + C!
ELSE
read-byte fcode-num 0 + C!
next-ip
read-byte fcode-num 1 + C!
next-ip
read-byte fcode-num 2 + C!
next-ip
read-byte fcode-num 3 + C!
THEN
fcode-num @
;
[ELSE]                                \ Now the little endian access functions
: read-fcode-num16 ( -- n )
0 fcode-num !
?arch64 IF
read-byte fcode-num 7 + C!
next-ip
read-byte fcode-num 6 + C!
ELSE
read-byte fcode-num 1 + C!
next-ip
read-byte fcode-num 0 + C!
THEN
fcode-num @
;
: read-fcode-num32 ( adr -- n )
0 fcode-num !
?arch64 IF
read-byte fcode-num 7 + C!
next-ip
read-byte fcode-num 6 + C!
next-ip
read-byte fcode-num 5 + C!
next-ip
read-byte fcode-num 4 + C!
ELSE
read-byte fcode-num 3 + C!
next-ip
read-byte fcode-num 2 + C!
next-ip
read-byte fcode-num 1 + C!
next-ip
read-byte fcode-num 0 + C!
THEN
fcode-num @
;
[THEN]
: read-fcode# ( -- FCode# )
read-byte
dup 01 0F between IF drop read-fcode-num16 THEN
;
: read-header ( adr -- )
next-ip read-byte        drop
next-ip read-fcode-num16 drop
next-ip read-fcode-num32 drop
;
: read-fcode-string ( -- str len )
read-byte            \ get string length ( -- len )
next-ip get-ip       \ get string addr   ( -- len str )
swap                 \ type needs the parameters swapped ( -- str len )
dup 1- jump-n-ip     \ jump to the end of the string in FCode
;
-1 VALUE break-fcode-addr
0 VALUE break-fcode-steps
: evaluate-fcode ( -- )
BEGIN
get-ip break-fcode-addr = IF
TRUE fcode-end !
THEN
fcode-end @ 0=
WHILE
fcode@                               ( fcode# )
eva-debug? IF
dup
get-ip 8 u.r ." : "
." [" 3 u.r ." ] "
THEN
get-token 0= ?compile-mode AND IF    ( xt )
compile,
ELSE                                 \ immediate or "interpretation" mode
eva-debug? IF dup xt>name type space THEN
execute
THEN
eva-debug? IF .s cr THEN
break-fcode-steps IF
break-fcode-steps 1- TO break-fcode-steps
break-fcode-steps 0= IF
TRUE fcode-end !
THEN
THEN
next-ip
REPEAT
;
: steps-fcode  ( n -- )
to break-fcode-steps
break-fcode-addr >r -1 to break-fcode-addr
reset-fcode-end
evaluate-fcode
r> to break-fcode-addr
;
: step-fcode  ( -- )
1 steps-fcode
;
: fcode-revision ( -- n )
00030000 \ major * 65536 + minor
;
: b(lit) ( -- n )
next-ip read-fcode-num32
?compile-mode IF literal, THEN
;
: b(")
next-ip read-fcode-string
?compile-mode IF fc-string, align postpone count THEN
;
: b(')
next-ip read-fcode# get-token drop ?compile-mode IF literal, THEN
;
: ?jump-direction ( n -- )
dup 8000 >= IF
10000 -           \ Create cell-sized negative value
THEN
fcode-offset -       \ IP is already behind offset, so subtract offset size
;
: ?negative
8000 and
;
: dest-on-top
0 >r BEGIN dup @ 0= WHILE >r REPEAT
BEGIN r> dup WHILE swap REPEAT
drop
;
: read-fcode-offset
next-ip
?offset16 IF
read-fcode-num16
ELSE
read-byte
dup 80 and IF FF00 or THEN       \ Fake 16-bit signed offset
THEN
;
: b?branch ( flag -- )
?compile-mode IF
read-fcode-offset ?negative IF
dest-on-top postpone until
ELSE
postpone if
THEN
ELSE
( flag ) IF
fcode-offset jump-n-ip       \ Skip over offset value
ELSE
read-fcode-offset
?jump-direction jump-n-ip
THEN
THEN
; immediate
: bbranch ( -- )
?compile-mode IF
read-fcode-offset
?negative IF
dest-on-top postpone again
ELSE
postpone else
get-ip next-ip fcode@ B2 = IF
drop
ELSE
set-ip
THEN
THEN
ELSE
read-fcode-offset ?jump-direction jump-n-ip
THEN
; immediate
: b(<mark) ( -- )
?compile-mode IF postpone begin THEN
; immediate
: b(>resolve) ( -- )
?compile-mode IF postpone then THEN
; immediate
: b(;)
<semicolon> compile, reveal
postpone [
; immediate
: b(:) ( -- )
<colon> compile, ]
; immediate
: b(case) ( sel -- sel )
postpone case
; immediate
: b(endcase)
postpone endcase
; immediate
: b(of)
postpone of
read-fcode-offset drop   \ read and discard offset
; immediate
: b(endof)
postpone endof
read-fcode-offset drop
; immediate
: b(do)
postpone do
read-fcode-offset drop
; immediate
: b(?do)
postpone ?do
read-fcode-offset drop
; immediate
: b(loop)
postpone loop
read-fcode-offset drop
; immediate
: b(+loop)
postpone +loop
read-fcode-offset drop
; immediate
: b(leave)
postpone leave
; immediate
0 VALUE fc-instance?
: fc-instance  ( -- )   \ Mark next defining word as instance-specific.
TRUE TO fc-instance?
;
: new-token  \ unnamed local fcode function
align here next-ip read-fcode# 0 swap set-token
;
: external-token ( -- )  \ named local fcode function
next-ip read-fcode-string
header         ( str len -- )  \ create a header in the current dictionary entry
new-token
;
: new-token
eva-debug? IF
s" x" get-ip >r next-ip read-fcode# r> set-ip (u.) $cat strdup
header
THEN
new-token
;
: named-token
fcode-debug? IF
external-token
ELSE
next-ip read-fcode-string 2drop       \ Forget about the name
new-token
THEN
;
: b(to) ( val -- )
next-ip read-fcode#
get-token drop                           ( val xt )
dup @                                    ( val xt @xt )
dup <value> =  over <defer> = OR IF
drop
>body cell -
?compile-mode IF
literal, postpone !
ELSE
!
THEN
ELSE
<create> <> IF                         ( val xt )
TRUE ABORT" Invalid destination for FCODE b(to)"
THEN
dup cell+ @                           ( val xt @xt+1cell )
dup <instancevalue> <>  swap <instancedefer> <> AND IF
TRUE ABORT" Invalid destination for FCODE b(to)"
THEN
>body @                               ( val instance-offset )
?compile-mode IF
literal,  postpone >instance  postpone !
ELSE
>instance !
THEN
ELSE
THEN
; immediate
: b(value)
fc-instance? IF
<create> ,                \ Needed for "(instance?)" for example
<instancevalue> ,
(create-instance-var)
FALSE TO fc-instance?
ELSE
<value> , ,
THEN
reveal
;
: b(variable)
fc-instance? IF
<create> ,                \ Needed for "(instance?)"
<instancevariable> ,
0 (create-instance-var)
FALSE TO fc-instance?
ELSE
<variable> , 0 ,
THEN
reveal
;
: b(constant)
<constant> , , reveal
;
: undefined-defer
cr cr ." Uninitialized defer word has been executed!" cr cr
true fcode-end !
;
: b(defer)
fc-instance? IF
<create> ,                \ Needed for "(instance?)"
<instancedefer> ,
['] undefined-defer (create-instance-var)
reveal
FALSE TO fc-instance?
ELSE
<defer> , reveal
postpone undefined-defer
THEN
;
: b(create)
<variable> ,
postpone noop reveal
;
: b(field) ( E: addr -- addr+offset ) ( F: offset size -- offset+size )
<colon> , over literal,
postpone +
<semicolon> compile,
reveal
+
;
: b(buffer:) ( E: -- a-addr) ( F: size -- )
fc-instance? IF
<create> ,                \ Needed for "(instance?)"
<instancebuffer> ,
(create-instance-buf)
FALSE TO fc-instance?
ELSE
<buffer:> , allot
THEN
reveal
;
: suspend-fcode ( -- )
noop        \ has to be implemented more efficiently ;-)
;
: offset16 ( -- )
2 to fcode-offset
;
: version1 ( -- )
1 to fcode-spread
1 to fcode-offset
read-header
;
: start0 ( -- )
0 to fcode-spread
offset16
read-header
;
: start1 ( -- )
1 to fcode-spread
offset16
read-header
;
: start2 ( -- )
2 to fcode-spread
offset16
read-header
;
: start4 ( -- )
4 to fcode-spread
offset16
read-header
;
: end0 ( -- )
true fcode-end !
;
: end1 ( -- )
end0
;
: ferror ( -- )
clear end0
cr ." FCode# " fcode-num @ . ." not assigned!"
cr ." FCode evaluation aborted." cr
." ( -- S:" depth . ." R:" rdepth . ." ) " .s cr
abort
;
: reset-local-fcodes
FFF 800 DO ['] ferror 0 i set-token LOOP
;
: byte-load ( addr xt -- )
>r >r
save-evaluator-state
r> r>
reset-fcode-end
1 to fcode-spread
dup 1 = IF drop ['] rb@ THEN to fcode-rb@
set-ip
reset-local-fcodes
depth >r
evaluate-fcode
r> depth 1- <> IF
clear end0
cr ." Ambiguous stack depth after byte-load!"
cr ." FCode evaluation aborted." cr cr
ELSE
restore-evaluator-state
THEN
['] c@ to fcode-rb@
;
: fc-c@   ( addr -- byte )   dup MIN-RAM-SIZE > IF rb@ ELSE c@ THEN ;
: fc-w@   ( addr -- word )   dup MIN-RAM-SIZE > IF rw@ ELSE w@ THEN ;
: fc-<w@  ( addr -- word )   fc-w@ dup 8000 >= IF 10000 - THEN ;
: fc-l@   ( addr -- long )   dup MIN-RAM-SIZE > IF rl@ ELSE l@ THEN ;
: fc-<l@  ( addr -- long )   fc-l@ signed ;
: fc-x@   ( addr -- dlong )  dup MIN-RAM-SIZE > IF rx@ ELSE x@ THEN ;
: fc-c!   ( byte addr -- )   dup MIN-RAM-SIZE > IF rb! ELSE c! THEN ;
: fc-w!   ( word addr -- )   dup MIN-RAM-SIZE > IF rw! ELSE w! THEN ;
: fc-l!   ( long addr -- )   dup MIN-RAM-SIZE > IF rl! ELSE l! THEN ;
: fc-x!   ( dlong addr -- )  dup MIN-RAM-SIZE > IF rx! ELSE x! THEN ;
: fc-fill ( add len byte -- )  2 pick MIN-RAM-SIZE > IF rfill ELSE fill THEN ;
: fc-move ( src dst len -- )
2 pick MIN-RAM-SIZE >        \ Check src
2 pick MIN-RAM-SIZE >        \ Check dst
OR IF rmove ELSE move THEN
;
: free-virtual  ( virt size -- )
s" map-out" $call-parent
;
: map-low  ( phys.lo ... size -- virt )
my-space swap s" map-in" $call-parent
;
: mac-address  ( -- mac-str mac-len )
s" local-mac-address" get-my-property IF
0 0
THEN
;
VARIABLE #line
0 #line !
VARIABLE #out
0 #out !
: display-status  ( n -- )
." Device status: " . cr
;
VARIABLE group-code
0 group-code !
: dma-alloc  ( byte -- virtual )
s" dma-alloc" $call-parent
;
: my-params  ( -- addr len )
s" params" get-my-property IF
0 0
THEN
;
: sbus-intr>cpu  ( sbus-intr# -- cpu-intr# )
;
: intr  ( interrupt# vector -- )
>r sbus-intr>cpu encode-int r> encode-int+ s" intr" property
;
: driver  ( addr len -- )
encode-string s" name" property
;
: processor-type  ( -- cpu-type )
0
;
: firmware-version  ( -- n )
10000                          \ Just a dummy value
;
: fcode-version  ( -- n )
fcode-revision
;
: fc-abort ." FCode called abort: IP " get-ip . ( ." STACK: " .s ) depth dup 0< IF abort THEN . rdepth . cr  abort ;
: fc-0 ." 0(lit): STACK ( S: " depth . ." R: " rdepth . ." ): " depth 0> IF .s THEN 0 ;
: fc-1 ." 1(lit): STACK ( S: " depth . ." R: " rdepth . ." ): " depth 0> IF .s THEN 1 ;
: parse-1hex 1 hex-decode-unit ;
: fc-set-pci-mmio-tokens  ( -- )
['] rw@-le  0 232 set-token
['] rw!-le  0 233 set-token
['] rl@-le  0 234 set-token
['] rl!-le  0 235 set-token
['] rx@-le  0 22E set-token
['] rx!-le  0 22F set-token
;
: fc-set-normal-mmio-tokens  ( -- )
['] rw@  0 232 set-token
['] rw!  0 233 set-token
['] rl@  0 234 set-token
['] rl!  0 235 set-token
['] rx@  0 22E set-token
['] rx!  0 22F set-token
;
: reset-token-table
FFF 0 DO ['] ferror 0 i set-token LOOP
;
reset-token-table
' end0 0        00 set-token
' b(lit)      1 10 set-token
' b(')        1 11 set-token
' b(")        1 12 set-token
' bbranch     1 13 set-token
' b?branch    1 14 set-token
' b(loop)     1 15 set-token
' b(+loop)    1 16 set-token
' b(do)       1 17 set-token
' b(?do)      1 18 set-token
' i           0 19 set-token
' j           0 1A set-token
' b(leave)    1 1B set-token
' b(of)       1 1C set-token
' execute     0 1D set-token
' +           0 1E set-token
' -           0 1F set-token
' *           0 20 set-token
' /           0 21 set-token
' mod         0 22 set-token 
' and         0 23 set-token 
' or          0 24 set-token 
' xor         0 25 set-token 
' invert      0 26 set-token 
' lshift      0 27 set-token 
' rshift      0 28 set-token 
' >>a         0 29 set-token 
' /mod        0 2A set-token 
' u/mod       0 2B set-token
' negate      0 2C set-token 
' abs         0 2D set-token 
' min         0 2E set-token 
' max         0 2F set-token 
' >r          0 30 set-token 
' r>          0 31 set-token 
' r@          0 32 set-token 
' exit        0 33 set-token 
' 0=          0 34 set-token 
' 0<>         0 35 set-token 
' 0<          0 36 set-token 
' 0<=         0 37 set-token 
' 0>          0 38 set-token 
' 0>=         0 39 set-token 
' <           0 3A set-token
' >           0 3B set-token
' =           0 3C set-token
' <>          0 3D set-token
' u>          0 3E set-token
' u<=         0 3F set-token 
' u<          0 40 set-token 
' u>=         0 41 set-token 
' >=          0 42 set-token 
' <=          0 43 set-token 
' between     0 44 set-token 
' within      0 45 set-token 
' DROP        0 46 set-token
' DUP         0 47 set-token
' OVER        0 48 set-token
' SWAP        0 49 set-token
' ROT         0 4A set-token
' -ROT        0 4B set-token
' TUCK        0 4C set-token
' nip         0 4D set-token 
' pick        0 4E set-token 
' roll        0 4F set-token 
' ?dup        0 50 set-token 
' depth       0 51 set-token 
' 2drop       0 52 set-token 
' 2dup        0 53 set-token 
' 2over       0 54 set-token 
' 2swap       0 55 set-token 
' 2rot        0 56 set-token 
' 2/          0 57 set-token 
' u2/         0 58 set-token 
' 2*          0 59 set-token 
' /c          0 5A set-token
' /w          0 5B set-token 
' /l          0 5C set-token 
' /n          0 5D set-token 
' ca+         0 5E set-token 
' wa+         0 5F set-token 
' la+         0 60 set-token 
' na+         0 61 set-token 
' char+       0 62 set-token 
' wa1+        0 63 set-token 
' la1+        0 64 set-token 
' cell+       0 65 set-token 
' chars       0 66 set-token 
' /w*         0 67 set-token 
' /l*         0 68 set-token 
' cells       0 69 set-token 
' on          0 6A set-token 
' off         0 6B set-token 
' +!          0 6C set-token 
' @           0 6D set-token 
' fc-l@       0 6E set-token 
' fc-w@       0 6F set-token 
' fc-<w@      0 70 set-token 
' fc-c@       0 71 set-token 
' !           0 72 set-token 
' fc-l!       0 73 set-token 
' fc-w!       0 74 set-token 
' fc-c!       0 75 set-token 
' 2@          0 76 set-token 
' 2!          0 77 set-token 
' fc-move     0 78 set-token 
' fc-fill     0 79 set-token 
' comp        0 7A set-token 
' noop        0 7B set-token
' lwsplit     0 7C set-token 
' wljoin      0 7D set-token 
' lbsplit     0 7E set-token 
' bljoin      0 7F set-token 
' wbflip      0 80 set-token 
' upc         0 81 set-token 
' lcc         0 82 set-token 
' pack        0 83 set-token 
' count       0 84 set-token 
' body>       0 85 set-token 
' >body       0 86 set-token 
' fcode-revision 0 87 set-token 
' span        0 88 set-token 
' unloop      0 89 set-token 
' expect      0 8A set-token 
' alloc-mem   0 8B set-token
' free-mem    0 8C set-token
' key?        0 8D set-token 
' key         0 8E set-token 
' emit        0 8F set-token 
' type        0 90 set-token 
' (cr         0 91 set-token
' cr          0 92 set-token 
' #out        0 93 set-token
' #line       0 94 set-token
' hold        0 95 set-token 
' <#          0 96 set-token 
' u#>         0 97 set-token 
' sign        0 98 set-token 
' u#          0 99 set-token 
' u#s         0 9A set-token 
' u.          0 9B set-token 
' u.r         0 9C set-token 
' .           0 9D set-token 
' .r          0 9E set-token 
' .s          0 9F set-token 
' base        0 A0 set-token 
' $number     0 A2 set-token 
' digit       0 A3 set-token 
' -1          0 A4 set-token
'  0          0 A5 set-token
'  1          0 A6 set-token
'  2          0 A7 set-token
'  3          0 A8 set-token
' bl          0 A9 set-token
' bs          0 AA set-token 
' bell        0 AB set-token 
' bounds      0 AC set-token 
' here        0 AD set-token 
' aligned     0 AE set-token 
' wbsplit     0 AF set-token 
' bwjoin      0 B0 set-token 
' b(<mark)    1 B1 set-token
' b(>resolve) 1 B2 set-token
' new-token   0 B5 set-token 
' named-token 0 B6 set-token
' b(:)        1 B7 set-token
' b(value)    1 B8 set-token 
' b(variable) 1 B9 set-token 
' b(constant) 1 BA set-token 
' b(create)   1 BB set-token 
' b(defer)    1 BC set-token 
' b(buffer:)  1 BD set-token 
' b(field)    1 BE set-token 
' fc-instance 1 C0 set-token 
' b(;)        1 C2 set-token
' b(to)       1 C3 set-token 
' b(case)     1 C4 set-token
' b(endcase)  1 C5 set-token
' b(endof)    1 C6 set-token
' #           0 C7 set-token
' #s          0 C8 set-token
' #>          0 C9 set-token
' external-token 0 CA set-token 
' $find       0 CB set-token
' offset16    0 CC set-token 
' evaluate    0 CD set-token
' c,          0  D0 set-token
' w,          0  D1 set-token
' l,          0  D2 set-token
' ,           0  D3 set-token
' um*         0  D4 set-token
' um/mod      0  D5 set-token
' d+          0  D8 set-token
' d-          0  D9 set-token
' get-token   0  DA set-token 
' set-token   0  DB set-token 
' state       0  DC set-token  \ possibly broken
' compile,    0  DD set-token
' behavior    0  DE set-token 
' start0            0  F0 set-token
' start1            0  F1 set-token
' start2            0  F2 set-token
' start4            0  F3 set-token
' ferror            0  FC set-token
' version1          0  FD set-token
' end1              0  FF set-token
' dma-alloc         0 101 set-token    \ Obsolete
' my-address        0 102 set-token 
' my-space          0 103 set-token
' free-virtual      0 105 set-token
' my-params         0 10f set-token    \ Obsolete
' property          0 110 set-token
' encode-int        0 111 set-token
' encode+           0 112 set-token
' encode-phys       0 113 set-token
' encode-string     0 114 set-token
' encode-bytes      0 115 set-token
' reg               0 116 set-token
' intr              0 117 set-token    \ Obsolete
' driver            0 118 set-token    \ Obsolete
' model             0 119 set-token
' device-type       0 11A set-token
' parse-2int        0 11B set-token
' is-install        0 11C set-token    \ for framebuffer code
' is-remove         0 11D set-token    \ for framebuffer code
' is-selftest       0 11E set-token    \ for framebuffer code
' new-device        0 11F set-token
' diagnostic-mode?  0 120 set-token
' display-status    0 121 set-token    \ Maybe obsolete
' memory-test-suite 0 122 set-token
' group-code        0 123 set-token    \ Obsolete
' mask              0 124 set-token
' get-msecs         0 125 set-token
' ms                0 126 set-token
' finish-device     0 127 set-token
' decode-phys       0 128 set-token
' interpose         0 12B set-token    \ Recommended practice: Interposition
' map-low           0 130 set-token
' sbus-intr>cpu     0 131 set-token    \ Obsolete
' #lines            0 150 set-token
' #columns          0 151 set-token
' line#             0 152 set-token
' column#           0 153 set-token
' inverse?          0 154 set-token
' inverse-screen?   0 155 set-token
' draw-character    0 157 set-token
' reset-screen      0 158 set-token
' toggle-cursor     0 159 set-token
' erase-screen      0 15A set-token
' blink-screen      0 15B set-token
' invert-screen     0 15C set-token
' insert-characters 0 15D set-token
' delete-characters 0 15E set-token
' insert-lines      0 15F set-token
' delete-lines      0 160 set-token
' draw-logo         0 161 set-token
' frame-buffer-adr  0 162 set-token
' screen-height     0 163 set-token
' screen-width      0 164 set-token
' window-top        0 165 set-token
' window-left       0 166 set-token
' default-font      0 16A set-token
' set-font          0 16B set-token
' char-height       0 16C set-token
' char-width        0 16D set-token
' >font             0 16E set-token
' fontbytes         0 16F set-token
' fb8-draw-character 0 180 set-token
' fb8-reset-screen   0 181 set-token
' fb8-toggle-cursor  0 182 set-token
' fb8-erase-screen   0 183 set-token
' fb8-blink-screen   0 184 set-token
' fb8-invert-screen  0 185 set-token
' fb8-insert-characters 0 186 set-token
' fb8-delete-characters 0 187 set-token
' fb8-insert-lines   0 188 set-token
' fb8-delete-lines   0 189 set-token
' fb8-draw-logo      0 18A set-token
' fb8-install        0 18B set-token
' mac-address       0 1A4 set-token
' device-name       0 201 set-token
' my-args           0 202 set-token
' my-self           0 203 set-token
' find-package      0 204 set-token
' open-package      0 205 set-token
' close-package     0 206 set-token
' find-method       0 207 set-token
' call-package      0 208 set-token
' $call-parent      0 209 set-token
' my-parent         0 20A set-token
' ihandle>phandle   0 20B set-token
' my-unit           0 20D set-token
' $call-method      0 20E set-token
' $open-package     0 20F set-token
' processor-type    0 210 set-token       \ Obsolete
' firmware-version  0 211 set-token       \ Obsolete
' fcode-version     0 212 set-token       \ Obsolete
' (is-user-word)    0 214 set-token
' suspend-fcode     0 215 set-token
' fc-abort          0 216 set-token
' catch             0 217 set-token
' throw             0 218 set-token
' get-my-property   0 21A set-token
' decode-int        0 21B set-token
' decode-string     0 21C set-token
' get-inherited-property 0 21D set-token  
' delete-property   0 21E set-token  
' get-package-property 0 21F set-token
' cpeek             0 220 set-token 
' wpeek             0 221 set-token 
' lpeek             0 222 set-token 
' cpoke             0 223 set-token 
' wpoke             0 224 set-token 
' lpoke             0 225 set-token 
' lwflip            0 226 set-token 
' lbflip            0 227 set-token 
' lbflips           0 228 set-token
' rb@               0 230 set-token
' rb!               0 231 set-token
fc-set-normal-mmio-tokens                 \ Set rw@, rw!, rl@, rl!, rx@ and rx!
' wbflips           0 236 set-token 
' lwflips           0 237 set-token 
' child             0 23B set-token
' peer              0 23C set-token
' next-property     0 23D set-token
' byte-load         0 23E set-token
' set-args          0 23F set-token
' left-parse-string 0 240 set-token
' bxjoin            0 241 set-token
' fc-<l@            0 242 set-token
' lxjoin            0 243 set-token
' wxjoin            0 244 set-token
' x,                0 245 set-token
' fc-x@             0 246 set-token
' fc-x!             0 247 set-token
' /x                0 248 set-token
' /x*               0 249 set-token
' xa+               0 24A set-token
' xa1+              0 24B set-token
' xbflip            0 24C set-token
' xbflips           0 24D set-token
' xbsplit           0 24E set-token
' xlflip            0 24F set-token
' xlflips           0 250 set-token
' xlsplit           0 251 set-token
' xwflip            0 252 set-token
' xwflips           0 253 set-token
' xwsplit           0 254 set-token
80 cells CONSTANT LOCALS-STACK-SIZE
LOCALS-STACK-SIZE BUFFER: localsstackbuf
localsstackbuf VALUE localsstack
: fc-local@  ( n -- val )
cells localsstack swap - @
;
: fc-local-1-@  1 fc-local@ ;
: fc-local-2-@  2 fc-local@ ;
: fc-local-3-@  3 fc-local@ ;
: fc-local-4-@  4 fc-local@ ;
: fc-local-5-@  5 fc-local@ ;
: fc-local-6-@  6 fc-local@ ;
: fc-local-7-@  7 fc-local@ ;
: fc-local-8-@  8 fc-local@ ;
: fc-local!  ( val n -- )
cells localsstack swap - !
;
: fc-local-1-!  1 fc-local! ;
: fc-local-2-!  2 fc-local! ;
: fc-local-3-!  3 fc-local! ;
: fc-local-4-!  4 fc-local! ;
: fc-local-5-!  5 fc-local! ;
: fc-local-6-!  6 fc-local! ;
: fc-local-7-!  7 fc-local! ;
: fc-local-8-!  8 fc-local! ;
0 VALUE uses-locals?
: (fc-push-locals)  ( ... n -- )
8 cells localsstack + TO localsstack
localsstack localsstackbuf -
LOCALS-STACK-SIZE > ABORT" Locals stack exceeded!"
?dup IF
( ... n ) 1 swap DO
i fc-local!              \ Store pre-initialized locals
-1 +LOOP
THEN
;
: fc-push-locals  ( n -- )
uses-locals? ABORT" Definition pushes locals multiple times!"
true TO uses-locals?
( n ) ['] literal execute
['] (fc-push-locals) compile,
;
: fc-push-0-locals  0 fc-push-locals ;
: fc-push-1-locals  1 fc-push-locals ;
: fc-push-2-locals  2 fc-push-locals ;
: fc-push-3-locals  3 fc-push-locals ;
: fc-push-4-locals  4 fc-push-locals ;
: fc-push-5-locals  5 fc-push-locals ;
: fc-push-6-locals  6 fc-push-locals ;
: fc-push-7-locals  7 fc-push-locals ;
: fc-push-8-locals  8 fc-push-locals ;
: fc-pop-locals  ( -- )
localsstack 8 cells - TO localsstack
localsstack localsstackbuf - 0 < ABORT" Locals stack undeflow!"
;
: fc-locals-exit
uses-locals? IF
['] fc-pop-locals compile,
THEN
['] exit compile,
;
: fc-locals-b(;)
uses-locals? IF
['] fc-pop-locals compile,
THEN
false TO uses-locals?
['] b(;) execute
;
: fc-set-locals-tokens  ( -- )
['] fc-push-0-locals 1 407 set-token
['] fc-push-1-locals 1 408 set-token
['] fc-push-2-locals 1 409 set-token
['] fc-push-3-locals 1 40a set-token
['] fc-push-4-locals 1 40b set-token
['] fc-push-5-locals 1 40c set-token
['] fc-push-6-locals 1 40d set-token
['] fc-push-7-locals 1 40e set-token
['] fc-push-8-locals 1 40f set-token
['] fc-local-1-@ 0 410 set-token
['] fc-local-2-@ 0 411 set-token
['] fc-local-3-@ 0 412 set-token
['] fc-local-4-@ 0 413 set-token
['] fc-local-5-@ 0 414 set-token
['] fc-local-6-@ 0 415 set-token
['] fc-local-7-@ 0 416 set-token
['] fc-local-8-@ 0 417 set-token
['] fc-local-1-! 0 418 set-token
['] fc-local-2-! 0 419 set-token
['] fc-local-3-! 0 41a set-token
['] fc-local-4-! 0 41b set-token
['] fc-local-5-! 0 41c set-token
['] fc-local-6-! 0 41d set-token
['] fc-local-7-! 0 41e set-token
['] fc-local-8-! 0 41f set-token
['] fc-locals-exit 1 33 set-token
['] fc-locals-b(;) 1 c2 set-token
;
fc-set-locals-tokens
0 value buff
0 value buff-size
' read-fcode# to fcode@
: execute-rom-fcode ( addr len | false -- )
reset-fcode-end
?dup IF
diagnostic-mode? IF ." , executing ..." cr THEN
dup >r r@ alloc-mem dup >r swap rmove
r@ set-ip evaluate-fcode
diagnostic-mode? IF ." Done." cr THEN
r> r> free-mem
THEN
;
: rom-code-ignored  ( image-addr name len -- image-addr )
diagnostic-mode? IF
type ."  code found in image " dup .  ." , ignoring ..." cr
ELSE
2drop
THEN
;
: pci-find-rom ( baseaddr -- addr )
dup IF
dup rw@-le aa55 = IF
diagnostic-mode? IF ." Device ROM header found at " dup . cr THEN
ELSE
drop 0
THEN
THEN
;
: pci-find-fcode ( baseaddr -- addr len | false )
BEGIN
1ff NOT and                       \ Image must start at 512 byte boundary
pci-find-rom dup
WHILE
dup 18 + rw@-le +              ( pcir-addr )
dup rw@-le 4350 ( 'PC' ) <>    ( pcir-addr hasPC? )
over 2+ rw@-le 5249 ( 'IR' ) <> OR IF
diagnostic-mode? IF
." Invalid PCI Data structure, ignoring ROM contents" cr
THEN
drop false EXIT
THEN                           ( pcir-addr )
dup 14 + rb@ CASE              \ Get image code type
0 OF s" Intel x86 BIOS" rom-code-ignored ENDOF
1 OF
diagnostic-mode? IF
." Open Firmware FCode found in image at " dup . cr
THEN
dup 1ff NOT AND          \ Back to the ROM image header
dup 2+ rw@-le +          \ Pointer to FCODE (PCI bus binding ch.9)
swap 10 + rw@-le 200 *   \ Image length
EXIT
ENDOF
2 OF s" HP PA RISC" rom-code-ignored ENDOF
3 OF s" EFI" rom-code-ignored ENDOF
dup OF s" Unknown type" rom-code-ignored ENDOF
ENDCASE
dup 15 + rb@ 80 and IF         \ End of last image?
drop false EXIT
THEN
dup 10 + rw@-le  200 * +       \ Next image start
REPEAT
;
: pci-execute-fcode  ( baseaddr -- )
pci-find-fcode dup 0= IF
2drop EXIT
THEN                                 ( addr len )
fc-set-pci-mmio-tokens               \ Prepare PCI access functions
['] execute-rom-fcode CATCH IF
cr ." FCODE failed!" cr
2drop
THEN
fc-set-normal-mmio-tokens            \ Restore normal MMIO access functions
;
ÿÿÿÿÿÿÿÿ@8default-font.bin(($$~$$~$$*((

*0H00@8DD@"THT"    |(||00  @8DDDDDDDD88DD @x8DD8@@@HH~~@@@xx @@@xDDD8~B   8DDD8DDDD88DDD<D800000000 @ @@ ~~  "$BNRN@@$$$$~BBBB|BBB||BBB|<"`@@@@`"<xDBBBBBBDx~@@@~~@@@~~@@@~~@@@@<B@@@@NBB<BBBB~~BBBB<<$BDHP``PHDB@@@@@@@@@~Bf~ZBBBBBBBbbRRJJFFB$BBBBBB$pHDDHp@@@@$BBBBBJ$pHDDHpPHDB @@ ~~BBBBBBBBB<BBBBB$$$$BBBBBBBZfBBB$$$$BBBB$$~B  B~0        0@  <fB~ 8D<D:@@@@XdDDdX8D@@D8<LDDL<8Dx@D884LDL4D8@@@XdDDDDDH0@@@DHPpHDB08T****jX$$$$v""""XdDdX@@@4LDL4xD@@@@$$8$$$$$DDD((*****DD((D"" < <  $THDDD((ÿÿÿÿÿÿÿÿ! !b0pci-phb.fs0 VALUE phb-debug?
." Populating " pwd cr
: decode-unit ( addr len -- phys.lo ... phys.hi )
2 hex-decode-unit       \ decode string
b lshift swap           \ shift the devicenumber to the right spot
8 lshift or             \ add the functionnumber
0 0 rot                 \ make phys.lo = 0 = phys.mid
;
: encode-unit ( phys.lo phys-mid phys.hi -- unit-str unit-len )
nip nip                     \ forget the phys.lo and phys.mid
dup 8 rshift 7 and swap     \ calculate function number
B rshift 1F and             \ calculate device number
over IF 2 ELSE nip 1 THEN   \ create string with dev#,fn# or dev# only?
hex-encode-unit
;
0 VALUE my-puid
: setup-puid
s" reg" get-node get-property 0= IF
decode-64 to my-puid 2drop
THEN
;
setup-puid
: config-b@  puid >r my-puid TO puid rtas-config-b@ r> TO puid ;
: config-w@  puid >r my-puid TO puid rtas-config-w@ r> TO puid ;
: config-l@  puid >r my-puid TO puid rtas-config-l@ r> TO puid ;
: config-b!  puid >r my-puid TO puid rtas-config-b! r> TO puid ;
: config-w!  puid >r my-puid TO puid rtas-config-w! r> TO puid ;
: config-l!  puid >r my-puid TO puid rtas-config-l! r> TO puid ;
: map-in ( phys.lo phys.mid phys.hi size -- virt )
phb-debug? IF cr ." map-in called: " .s cr THEN
drop nip nip                         ( phys.hi )
dup FF AND dup 10 28 WITHIN NOT swap 30 <> AND IF
cr ." phys.hi = " . cr
ABORT" map-in with illegal config space address"
THEN
00FFFFFF AND                         \ Need only bus-dev-fn+register bits
dup config-l@                        ( phys.hi' bar.lo )
dup 7 AND 4 = IF                     \ Is it a 64-bit BAR?
swap 4 + config-l@ lxjoin         \ Add upper part of 64-bit BAR
ELSE
nip
THEN
F NOT AND                            \ Clear indicator bits
translate-my-address
phb-debug? IF ." map-in done: " .s cr THEN
;
: map-out ( virt size -- )
phb-debug? IF ." map-out called: " .s cr THEN
2drop 
;
: dma-alloc ( size -- virt )
phb-debug? IF cr ." dma-alloc called: " .s cr THEN
fff + fff not and                  \ Align size to next 4k boundary
alloc-mem
dup fff and IF
." Warning: dma-alloc got unaligned memory!" cr
THEN
;
: dma-free ( virt size -- )
phb-debug? IF cr ." dma-free called: " .s cr THEN
fff + fff not and                  \ Align size to next 4k boundary
free-mem
;
0 VALUE dma-window-liobn        \ Logical I/O bus number
0 VALUE dma-window-base         \ Start address of window
0 VALUE dma-window-size         \ Size of the window
0 VALUE bm-handle               \ Bitmap allocator handle
0 VALUE my-virt
0 VALUE my-size
0 VALUE dev-addr
0 VALUE tmp-dev-addr
: (init-dma-window-vars)  ( -- )
s" ibm,dma-window" calling-child get-property IF
s" ibm,dma-window" calling-child parent get-property 
ABORT" no dma-window property available"
THEN
decode-int TO dma-window-liobn
decode-64 TO dma-window-base
decode-64 TO dma-window-size
2drop
bm-handle 0= IF
dma-window-base dma-window-size 1000 bm-allocator-init to bm-handle
dma-window-base 0= IF
bm-handle 1000 bm-alloc drop
THEN
THEN
;
: (clear-dma-window-vars)  ( -- )
0 TO dma-window-liobn
0 TO dma-window-base
0 TO dma-window-size
;
: dma-virt2dev  ( virt -- devaddr )
dma-window-size mod dma-window-base +
;
: dma-map-in  ( virt size cachable? -- devaddr )
phb-debug? IF cr ." dma-map-in called: " .s cr THEN
(init-dma-window-vars)
drop                               ( virt size )
to my-size
to my-virt
bm-handle my-size bm-alloc
to dev-addr
dev-addr 0 < IF
." Bitmap allocation Failed " dev-addr .
FALSE EXIT
THEN
dev-addr to tmp-dev-addr
my-virt my-size
bounds dup >r                      ( v+s virt  R: virt )
swap fff + fff not and             \ Align end to next 4k boundary
swap fff not and                   ( v+s' virt'  R: virt )
?DO
dma-window-liobn                \ liobn
tmp-dev-addr                    \ ioba
i 3 OR                          \ Make a read- & writeable TCE
hv-put-tce ABORT" H_PUT_TCE failed"
tmp-dev-addr 1000 + to tmp-dev-addr
1000 +LOOP
r> drop
my-virt FFF and dev-addr or
(clear-dma-window-vars)
;
: dma-map-out  ( virt devaddr size -- )
phb-debug? IF cr ." dma-map-out called: " .s cr THEN
(init-dma-window-vars)
to my-size
to dev-addr
to my-virt
dev-addr fff not and to dev-addr
dev-addr to tmp-dev-addr
my-virt my-size                    ( virt size )
bounds                             ( v+s virt )
swap fff + fff not and             \ Align end to next 4k boundary
swap fff not and                   ( v+s' virt' )
?DO
dma-window-liobn                \ liobn
tmp-dev-addr                    \ ioba
i                               \ Lowest bits not set => invalid TCE
hv-put-tce ABORT" H_PUT_TCE failed"
tmp-dev-addr 1000 + to tmp-dev-addr
1000 +LOOP
bm-handle dev-addr my-size bm-free
(clear-dma-window-vars)
;
: dma-sync  ( virt devaddr size -- )
phb-debug? IF cr ." dma-sync called: " .s cr THEN
3drop
;
: open  true ;
: close ;
: phb-parse-ranges ( -- )
0  pci-next-io !
0  pci-max-io !
0  pci-next-mem !
0  pci-max-mem !
0  pci-next-mmio !
0  pci-max-mmio !
0  pci-next-mem64 !
0  pci-max-mem64 !
s" ranges" get-node get-property 0<> ABORT" ranges property not found"
BEGIN
dup
WHILE
decode-int                      \ Decode phys.hi
3000000 AND                     \ Filter out address space in phys.hi
CASE
1000000 OF                             \ I/O space?
decode-64 dup >r pci-next-io !      \ Decode PCI base address
decode-64 drop                      \ Forget the parent address
decode-64 r> + pci-max-io !         \ Decode size & calc max address
pci-next-io @ 0= IF
pci-next-io @ 10 + pci-next-io ! \ BARs must not be set to zero
THEN
ENDOF
2000000 OF                             \ 32-bit memory space?
decode-64 pci-next-mem !            \ Decode mem base address
decode-64 drop                      \ Forget the parent address
decode-64 2 / dup >r                \ Decode and calc size/2
pci-next-mem @ + dup pci-max-mem !  \ and calc max mem address
dup pci-next-mmio !                 \ which is the same as MMIO base
r> + pci-max-mmio !                 \ calc max MMIO address
ENDOF
3000000 OF                             \ 64-bit memory space?
decode-64 pci-next-mem64 !
decode-64 drop                      \ Forget the parent address
decode-64 pci-max-mem64 !
ENDOF
ENDCASE
REPEAT
2drop
phb-debug? IF
." pci-next-io   = " pci-next-io @ . cr
." pci-max-io    = " pci-max-io  @ . cr
." pci-next-mem  = " pci-next-mem @ . cr
." pci-max-mem   = " pci-max-mem  @ . cr
." pci-next-mmio = " pci-next-mmio @ . cr
." pci-max-mmio  = " pci-max-mmio @ . cr
." pci-next-mem64  = " pci-next-mem64 @ . cr
." pci-max-mem64   = " pci-max-mem64  @ . cr
THEN
;
: phb-pci-walk-bridge ( -- )
phb-debug? IF ."   Calling pci-walk-bridge " pwd cr THEN
get-node child ?dup 0= IF EXIT THEN    \ get and check if we have children
0 to pci-device-slots                  \ reset slot array to unpoppulated
BEGIN
dup                                \ Continue as long as there are children
WHILE
dup set-node                       \ Set child node as current node
my-space pci-set-slot              \ set the slot bit
my-space pci-htype@                \ read HEADER-Type
7f and                             \ Mask bit 7 - multifunction device
CASE
0 OF my-space pci-device-setup ENDOF  \ | set up the device
1 OF my-space pci-bridge-setup ENDOF  \ | set up the bridge
dup OF my-space [char] ? pci-out ENDOF
ENDCASE
peer
REPEAT drop
get-parent set-node
;
: phb-pci-bridge-probe ( addr -- )
dup pci-bridge-set-bases                      \ Set up all Base Registers
dup func-pci-bridge-range-props               \ Set up temporary "range"
pci-device-vec-len 1+ TO pci-device-vec-len   \ increase the device-slot vector depth
pci-enable                                    \ enable mem/IO transactions
phb-pci-walk-bridge                           \ and walk the secondary bus
pci-device-vec-len 1- TO pci-device-vec-len   \ decrease the device-slot vector depth
pci-bridge-set-limits                         \ Set up all Limit Registers
;
: phb-pci-device-props ( addr -- )
dup pci-class-name device-name
dup pci-device-assigned-addresses-prop
drop
;
: phb-setup-children
puid >r                          \ Save old value of puid
my-puid TO puid                  \ Set current puid
phb-parse-ranges
1 TO pci-hotplug-enabled
s" qemu,phb-enumerated" get-node get-property 0<> IF
1 0 (probe-pci-host-bridge)
ELSE
2drop
['] phb-pci-bridge-probe TO func-pci-bridge-probe
['] phb-pci-device-props TO func-pci-device-props
phb-pci-walk-bridge          \ PHB device tree is already populated.
THEN
r> TO puid                       \ Restore previous puid
;
phb-setup-children
ÿÿÿÿÿÿÿÿ ð(rtas.fs371 cp
STRUCT
/l field rtas>token
/l field rtas>nargs
/l field rtas>nret
/l field rtas>args0
/l field rtas>args1
/l field rtas>args2
/l field rtas>args3
/l field rtas>args4
/l field rtas>args5
/l field rtas>args6
/l field rtas>args7
/l C * field rtas>args
/l field rtas>bla
CONSTANT /rtas-control-block
CREATE rtas-cb /rtas-control-block allot
rtas-cb /rtas-control-block erase
0 VALUE rtas-base
0 VALUE rtas-size
0 VALUE rtas-entry
0 VALUE rtas-node
372 cp
: find-qemu-rtas ( -- )
" /rtas" find-device get-node to rtas-node
" linux,rtas-base" rtas-node get-package-property IF
device-end EXIT THEN
drop l@ to rtas-base
" linux,rtas-base" delete-property
" rtas-size" rtas-node get-package-property IF
device-end EXIT THEN
drop l@ to rtas-size
" linux,rtas-entry" rtas-node get-package-property IF
rtas-base to rtas-entry
ELSE
drop l@ to rtas-entry
" linux,rtas-entry" delete-property
THEN
0
rtas-base
dup rtas-size +
check-and-patch-sc1
device-end
;
find-qemu-rtas
373 cp
: enter-rtas ( -- )
rtas-cb rtas-base 0 rtas-entry call-c drop
;
: rtas-get-token ( str len -- token | 0 )
rtas-node get-package-property IF 0 ELSE drop l@ THEN
;
: rtas-power-off   ( x y -- status )
[ s" power-off" rtas-get-token ] LITERAL rtas-cb rtas>token l!
2 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
rtas-cb rtas>args0 l!
rtas-cb rtas>args1 l!
enter-rtas
rtas-cb rtas>args2 l@
;
: power-off  ( -- )  0 0 rtas-power-off ;
: rtas-system-reboot  ( -- status )
[ s" system-reboot" rtas-get-token ] LITERAL rtas-cb rtas>token l!
0 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
rtas-cb rtas>args0 l!
enter-rtas
rtas-cb rtas>args1 l@
;
: rtas-start-cpu  ( pid loc r3 -- status )
[ s" start-cpu" rtas-get-token ] LITERAL rtas-cb rtas>token l!
3  rtas-cb rtas>nargs l!
1  rtas-cb rtas>nret l!
rtas-cb rtas>args2 l!
rtas-cb rtas>args1 l!
rtas-cb rtas>args0 l!
0 rtas-cb rtas>args3 l!
enter-rtas
rtas-cb rtas>args3 l@
;
: rtas-set-tce-bypass ( unit enable -- )
" ibm,set-tce-bypass" rtas-get-token rtas-cb rtas>token l!
2 rtas-cb rtas>nargs l!
0 rtas-cb rtas>nret l!
rtas-cb rtas>args1 l!
rtas-cb rtas>args0 l!
enter-rtas
;
: rtas-quiesce ( -- )
" quiesce" rtas-get-token rtas-cb rtas>token l!
0 rtas-cb rtas>nargs l!
0 rtas-cb rtas>nret l!
enter-rtas
;
0 value puid
: rtas-do-config-@ ( config-addr size -- value)
[ s" ibm,read-pci-config" rtas-get-token ] LITERAL rtas-cb rtas>token l!
4 rtas-cb rtas>nargs l!
2 rtas-cb rtas>nret l!
( addr size ) rtas-cb rtas>args3 l!
puid rtas-cb rtas>args2 l!
puid 20 rshift rtas-cb rtas>args1 l!
( addr ) rtas-cb rtas>args0 l!
enter-rtas
rtas-cb rtas>args4 l@ dup IF
drop ffffffff
ELSE
drop rtas-cb rtas>args5 l@
THEN
;
: rtas-do-config-! ( value config-addr size )
[ s" ibm,write-pci-config" rtas-get-token ] LITERAL rtas-cb rtas>token l!
5 rtas-cb rtas>nargs l!
1 rtas-cb rtas>nret l!
( value addr size ) rtas-cb rtas>args3 l!
puid rtas-cb rtas>args2 l!
puid 20 rshift rtas-cb rtas>args1 l!
( value addr ) rtas-cb rtas>args0 l!
( value ) rtas-cb rtas>args4 l!
enter-rtas
rtas-cb rtas>args5 l@ dup IF
." RTAS write config err " . cr
ELSE drop THEN
;
: rtas-config-b@ ( config-addr -- value )
1 rtas-do-config-@ ff and
;
: rtas-config-b! ( value config-addr -- )
1 rtas-do-config-!
;
: rtas-config-w@ ( config-addr -- value )
2 rtas-do-config-@ ffff and
;
: rtas-config-w! ( value config-addr -- )
2 rtas-do-config-!
;
: rtas-config-l@ ( config-addr -- value )
4 rtas-do-config-@ ffffffff and
;
: rtas-config-l! ( value config-addr -- )
4 rtas-do-config-!
;
: of-start-cpu rtas-start-cpu ;
' power-off to halt
' rtas-system-reboot to reboot
rtas-node set-node
: open true ;
: close ;
: instantiate-rtas ( adr -- entry )
dup rtas-base swap rtas-size move
dup rtas-entry rtas-base - +
2dup hv-rtas-update dup 0 <> IF
dup -2 <> IF ." HV-RTAS-UPDATE error: " . cr ELSE drop THEN
ELSE
drop
THEN
nip
;
device-end
374 cp
ÿÿÿÿÿÿÿÿp)8pci-device_1234_1111.fs." qemu vga" cr
s" qemu-vga.fs" included
ÿÿÿÿÿÿÿÿ8ñ8pci-device_1013_00b8.fsmy-space pci-device-generic-setup
d# 800 VALUE disp-width
d# 600 VALUE disp-height
d#   8 VALUE disp-depth
10 config-l@ translate-my-address f not AND  VALUE fb-base
-1 VALUE io-base
false VALUE is-installed?
: vga-io-xlate ( port -- addr )
io-base -1 = IF
dup translate-my-address fff not and to io-base
THEN
io-base +
;
: vga-w! ( value port -- )
vga-io-xlate rw!-le
;
: vga-w@ ( port -- value )
vga-io-xlate rw@-le
;
: vga-b! ( value port -- )
vga-io-xlate rb!
;
: vga-b@ ( port -- value )
vga-io-xlate rb@
;
: vga-crt@ ( index -- value )
3d4 vga-b!
3d5 vga-b@
;
: vga-crt! ( value index -- )
3d4 vga-b!
3d5 vga-b!
;
: vga-seq@ ( index -- value )
3c4 vga-b!
3c5 vga-b@
;
: vga-seq! ( value index -- )
3c4 vga-b!
3c5 vga-b!
;
: vga-att@ ( index -- value )
3c0 vga-b!
3c1 vga-b@
;
: vga-att! ( value index -- )
3c0 vga-b!
3c0 vga-b!
;
: vga-gfx@ ( index -- value )
3ce vga-b!
3cf vga-b@
;
: vga-gfx! ( value index -- )
3ce vga-b!
3cf vga-b!
;
: color! ( r g b number -- ) 
3c8 vga-b!
rot 2 >> 3c9 vga-b!
swap 2 >> 3c9 vga-b!
2 >> 3c9 vga-b!
;
: color@ ( number -- r g b ) 
3c8 vga-b!
3c9 vga-b@ 2 <<
3c9 vga-b@ 2 <<
3c9 vga-b@ 2 <<
;
: set-colors ( adr number #numbers -- )
over 3c8 vga-b!
swap DO
rb@ 2 >> 3c9 vga-b!
rb@ 2 >> 3c9 vga-b!
rb@ 2 >> 3c9 vga-b!
LOOP
3drop
;
: get-colors ( adr number #numbers -- )
3drop
;
include graphics.fs
: init-mode
3da vga-b@ drop \ reset flip flop
0f 3c2 vga-b!   \ color mode, ram enable, ...
12 06 vga-seq!  \ unlock extensions
05 06 vga-gfx!  \ graphic mode  
disp-depth CASE \ set depth
8 OF 01 07 vga-seq! ENDOF
f OF 07 07 vga-seq! ENDOF
10 OF 07 07 vga-seq! ENDOF
20 OF 09 07 vga-seq! ENDOF
ENDCASE
ff 02 vga-seq!  \ enable plane write
0a 04 vga-seq!  \ memory mode
03 17 vga-crt!  \ disable display
disp-width disp-depth 7 + 8 / * 3 >>
dup ff and 13 vga-crt!  \ bottom bits
4 >> 10 and 1b vga-crt! \ top bit
disp-width 3 >> 1 -                  01 vga-crt! \ H_DISP
disp-height 1 - ff and               12 vga-crt! \ V_DISP
disp-height 1 - 7 >> 2 and
disp-height 1 - 3 >> 40 and
or 10 or                             07 vga-crt! \ OFLOW
ff 18 vga-crt! \ LINE_COMPARE
40 09 vga-crt! \ MAX_SCAN
08 04 vga-crt! \ SYNC_START
0f 02 vga-crt! \ BLANK_START
00 0c vga-crt!
00 0d vga-crt!
40 05 vga-gfx! \ gfx mode
83 17 vga-crt! \ enable display
33 3c0 vga-b!  \ gfx in ar index
00 3c0 vga-b!
01 01 vga-seq! \ enable seq
;
: clear-screen
fb-base disp-width disp-height disp-depth 7 + 8 / * * 0 rfill
;
: read-settings
s" qemu,graphic-width" get-chosen IF
decode-int to disp-width 2drop
THEN
s" qemu,graphic-height" get-chosen IF
decode-int to disp-height 2drop
THEN
s" qemu,graphic-depth" get-chosen IF
decode-int nip nip     
dup 8 =
over f = or
over 10 = or
over 20 = or IF
to disp-depth
ELSE
." Unsupported bit depth, using 8bpp " drop cr
THEN
THEN
;
: add-legacy-reg
s" reg" get-node get-property IF
encode-start
ELSE
encode-bytes
THEN
my-space a1000000 or encode-int+ \ non-relocatable, aliased I/O space
1ce encode-64+ 4 encode-64+ \ addr size
my-space a1000000 or encode-int+ \ non-relocatable, aliased I/O space
3b0 encode-64+ c encode-64+ \ addr size
my-space a1000000 or encode-int+ \ non-relocatable, aliased I/O space
3c0 encode-64+ 20 encode-64+ \ addr size
my-space a2000000 or encode-int+ \ non-relocatable, <1MB Memory space
a0000 encode-64+ 20000 encode-64+ \ addr size
s" reg" property \ store "reg" property
;
: setup-properties
disp-width encode-int s" width" property
disp-height encode-int s" height" property
disp-width disp-depth 7 + 8 / * encode-int s" linebytes" property
disp-depth encode-int s" depth" property
s" ISO8859-1" encode-string s" character-set" property \ i hope this is ok...
s" display" device-type
;
: display-remove ( -- ) 
;
: display-install ( -- )
is-installed? NOT IF
." Installing QEMU fb" cr
fb-base to frame-buffer-adr
default-font 
set-font
disp-width disp-height
disp-width char-width / disp-height char-height /
disp-depth 7 + 8 /                      ( width height #lines #cols depth )
fb-install
true to is-installed?
THEN
;
: set-alias
s" screen" find-alias 0= IF
s" screen" get-node node>path set-alias
ELSE
drop
THEN 
;
." cirrus vga" cr
pci-master-enable
pci-mem-enable
pci-io-enable
add-legacy-reg
read-settings
init-mode
clear-screen
init-default-palette
setup-properties
' display-install is-install
' display-remove is-remove
set-alias
ÿÿÿÿÿÿÿÿ¸q8pci-device_8086_100e.fss" e1000 [ net ]" type cr
my-space pci-device-generic-setup
pci-io-enable
s" e1k.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿÕ(e1k.fss" network" device-type
INSTANCE VARIABLE obp-tftp-package
get-node CONSTANT my-phandle
10 config-l@ translate-my-address 3 not AND CONSTANT baseaddr
0 VALUE e1k-priv
0 VALUE open-count
: open  ( -- okay? )
open-count 0= IF
open IF
baseaddr
e1k-open dup not IF ." e1k-open failed" EXIT THEN
drop TO e1k-priv
true
ELSE
false
THEN
ELSE
true
THEN
my-args s" obp-tftp" $open-package obp-tftp-package !
open-count 1 + to open-count
;
: close  ( -- )
my-phandle set-node
open-count 0> IF
open-count 1 - dup to open-count
0= IF
e1k-priv e1k-close
close
THEN
THEN
s" close" obp-tftp-package @ $call-method
;
: read ( buf len -- actual )
dup IF
e1k-read
ELSE  
nip
THEN
;
: write ( buf len -- actual )
dup IF
e1k-write
ELSE
nip
THEN
;
: load  ( addr -- len )
s" load" obp-tftp-package @ $call-method
;
: ping  ( -- )
s" ping" obp-tftp-package @ $call-method
;
6 BUFFER: local-mac
: setup-mac ( -- )
pci-mem-enable
" vendor-id" get-node get-property IF EXIT THEN
decode-int nip nip
" device-id" get-node get-property IF EXIT THEN
decode-int nip nip
baseaddr
local-mac e1k-mac-setup IF
encode-bytes  " local-mac-address"  property
THEN
;
setup-mac
: setup-alias  ( -- )
" net" get-next-alias ?dup IF
get-node node>path set-alias
THEN
;
setup-alias
ÿÿÿÿÿÿÿÿ
°
u0qemu-vga.fsmy-space pci-device-generic-setup
d# 800 VALUE disp-width
d# 600 VALUE disp-height
d#   8 VALUE disp-depth
: map-in  " map-in" my-phandle parent $call-static ;
: map-out  " map-out" my-phandle parent $call-static ;
0 0  my-space h# 02000010 + 1  map-in VALUE fb-base
0 0  my-space h# 02000018 + 1 map-in VALUE reg-base
false VALUE is-installed?
: vga-w! ( value port -- )
3c0 - reg-base 400 + + rw!-le
;
: vga-w@ ( port -- value )
3c0 - reg-base 400 + + rw@-le
;
: vga-b! ( value port -- )
3c0 - reg-base 400 + + rb!
;
: vga-b@ ( port -- value )
3c0 - reg-base 400 + + rb@
;
: vbe!	( value index -- )
1 << reg-base 500 + + rw!-le
;
: vbe@	( index -- value )
1 << reg-base 500 + + rw@-le
;
: color! ( r g b number -- )
3c8 vga-b!
rot 3c9 vga-b!
swap 3c9 vga-b!
3c9 vga-b!
;
: color@ ( number -- r g b )
3c8 vga-b!
3c9 vga-b@
3c9 vga-b@
3c9 vga-b@
;
: set-colors ( adr number #numbers -- )
over 3c8 vga-b!
swap DO
rb@ 3c9 vga-b!
rb@ 3c9 vga-b!
rb@ 3c9 vga-b!
LOOP
3drop
;
: get-colors ( adr number #numbers -- )
3drop
;
include graphics.fs
0 CONSTANT VBE_DISPI_INDEX_ID
1 CONSTANT VBE_DISPI_INDEX_XRES
2 CONSTANT VBE_DISPI_INDEX_YRES
3 CONSTANT VBE_DISPI_INDEX_BPP
4 CONSTANT VBE_DISPI_INDEX_ENABLE
5 CONSTANT VBE_DISPI_INDEX_BANK
6 CONSTANT VBE_DISPI_INDEX_VIRT_WIDTH
7 CONSTANT VBE_DISPI_INDEX_VIRT_HEIGHT
8 CONSTANT VBE_DISPI_INDEX_X_OFFSET
9 CONSTANT VBE_DISPI_INDEX_Y_OFFSET
a CONSTANT VBE_DISPI_INDEX_NB
00 CONSTANT VBE_DISPI_DISABLED
01 CONSTANT VBE_DISPI_ENABLED
02 CONSTANT VBE_DISPI_GETCAPS
20 CONSTANT VBE_DISPI_8BIT_DAC
40 CONSTANT VBE_DISPI_LFB_ENABLED
80 CONSTANT VBE_DISPI_NOCLEARMEM
: init-mode
0 3c0 vga-b!
VBE_DISPI_DISABLED VBE_DISPI_INDEX_ENABLE vbe!
0 VBE_DISPI_INDEX_X_OFFSET vbe!
0 VBE_DISPI_INDEX_Y_OFFSET vbe!
disp-width VBE_DISPI_INDEX_XRES vbe!
disp-height VBE_DISPI_INDEX_YRES vbe!
disp-depth VBE_DISPI_INDEX_BPP vbe!
VBE_DISPI_ENABLED VBE_DISPI_8BIT_DAC or VBE_DISPI_INDEX_ENABLE vbe!
0 3c0 vga-b!
20 3c0 vga-b!
;
: clear-screen
fb-base disp-width disp-height disp-depth 7 + 8 / * * 0 rfill
;
: read-settings
s" qemu,graphic-width" get-chosen IF
decode-int to disp-width 2drop
THEN
s" qemu,graphic-height" get-chosen IF
decode-int to disp-height 2drop
THEN
s" qemu,graphic-depth" get-chosen IF
decode-int nip nip
dup 8 =
over f = or
over 10 = or
over 20 = or IF
to disp-depth
ELSE
." Unsupported bit depth, using 8bpp " drop cr
THEN
THEN
;
: setup-properties
disp-width encode-int s" width" property
disp-height encode-int s" height" property
disp-width disp-depth 7 + 8 / * encode-int s" linebytes" property
disp-depth encode-int s" depth" property
s" ISO8859-1" encode-string s" character-set" property \ i hope this is ok...
s" display" device-type
s" qemu,std-vga" encode-string s" compatible" property
;
: display-remove ( -- )
;
: slow-blink-screen ( -- )
invert-screen 20 ms invert-screen
;
: display-install ( -- )
is-installed? NOT IF
." Installing QEMU fb" cr
fb-base to frame-buffer-adr
clear-screen
default-font
set-font
disp-width disp-height
disp-width char-width / disp-height char-height /
disp-depth 7 + 8 /                      ( width height #lines #cols depth )
fb-install
['] slow-blink-screen to blink-screen
true to is-installed?
THEN
;
: set-alias
s" screen" find-alias 0= IF
s" screen" get-node node>path set-alias
ELSE
drop
THEN
;
pci-master-enable
pci-mem-enable
read-settings
init-mode
init-default-palette
setup-properties
' display-install is-install
' display-remove is-remove
set-alias
ÿÿÿÿÿÿÿÿ€E0pci-class_02.fss" network [ " type my-space pci-class-name type s"  ]" type
my-space pci-device-generic-setup
my-space pci-alias-net
s" network" device-type
cr
INSTANCE VARIABLE obp-tftp-package
: open  ( -- okay? )
open IF           \ enables PCI mem, io and Bus master and returns TRUE
my-args s" obp-tftp" $open-package obp-tftp-package ! true
ELSE
false
THEN ;
: close  ( -- )
obp-tftp-package @ close-package
close ;         \ disables PCI mem, io and Bus master
: load  ( addr -- len )
s" load" obp-tftp-package @ $call-method  ;
: ping  ( -- )  s" ping" obp-tftp-package @ $call-method  ;
ÿÿÿÿÿÿÿÿ@0pci-class_0c.fss" serial bus [ " type my-space pci-class-name type s"  ]" type cr
my-space pci-device-generic-setup
STRUCT
/n FIELD hcd>base
/n FIELD hcd>type
/n FIELD hcd>num
/n FIELD hcd>ops
/n FIELD hcd>priv
/n FIELD hcd>nextaddr
CONSTANT /hci-dev
: usb-setup-hcidev ( num hci-dev -- )
>r
10 config-l@ F AND case
0 OF 10 config-l@ translate-my-address ENDOF       \ 32-bit memory space
4 OF                                               \ 64-bit memory space
14 config-l@ 20 lshift                         \ Read two bars
10 config-l@ OR translate-my-address
ENDOF
ENDCASE
F not AND
( io-base ) r@ hcd>base !
08 config-l@ 8 rshift  0000000F0 AND 4 rshift
( usb-type ) r@ hcd>type !
( usb-num )  r@ hcd>num !
r> drop
;
: handle-usb-class  ( -- )
4 config-w@ 110 or 4 config-w!
pci-master-enable               \ set PCI Bus master bit and
pci-mem-enable                  \ memory space enable for USB scan
;
: handle-sbc-subclass  ( -- )
my-space pci-class@ ffff and CASE         \ get PCI sub-class and interface
0310 OF                      \ OHCI controller
handle-usb-class
set-ohci-alias
ENDOF
0320 OF                      \ EHCI controller
handle-usb-class
set-ehci-alias
ENDOF
0330 OF                      \ XHCI controller
handle-usb-class
set-xhci-alias
ENDOF
ENDCASE
;
handle-sbc-subclass
ÿÿÿÿÿÿÿÿ˜[0dev-hci.fsVALUE usb_type \ USB type
device-type
" usb" 2dup device-name
rot
VALUE usb_num                           \ controller number
usb_num $cathex strdup			\ create alias name
2dup find-alias 0= IF
get-node node>path set-alias
ELSE 3drop THEN
/hci-dev BUFFER: hcidev
usb_num hcidev usb-setup-hcidev
TRUE VALUE first-time-init?
0 VALUE open-count
false VALUE dev-hci-debug?
1 encode-int s" #address-cells" property
0 encode-int s" #size-cells" property
: encode-unit ( port -- unit-str unit-len ) 1 hex-encode-unit ;
: decode-unit ( addr len -- port ) 1 hex-decode-unit ;
: get-hci-dev ( -- hcidev )
hcidev
;
: hc-cleanup ( -- )
my-phandle set-node
dev-hci-debug? IF ." USB-HCI: Cleaning up " pwd cr THEN
hcidev USB-HCD-EXIT
0 set-node
;
: open   ( -- true | false )
true
;
: close
;
first-time-init? IF
['] hc-cleanup add-quiesce-xt
false to first-time-init?
THEN
ÿÿÿÿÿÿÿÿè¯0slofdev.fsSTRUCT
/n FIELD slof-dev>udev
/l FIELD slof-dev>port
/l FIELD slof-dev>devaddr
/l FIELD slof-dev>hcitype
/l FIELD slof-dev>num
/l FIELD slof-dev>devtype
CONSTANT slof-usb-dev
ÿÿÿÿÿÿÿÿ€:8dev-parent-calls.fsget-node CONSTANT my-phandle
s" dma-function.fs" included
ÿÿÿÿÿÿÿÿp10dev-keyb.fsnew-device
VALUE sudev
false VALUE usb-keyb-debug?
s" slofdev.fs" included
sudev slof-dev>port l@ dup set-unit encode-phys " reg" property
sudev slof-dev>udev @ VALUE udev
s" usb-keyboard" device-name
s" keyboard" device-type
s" EN" encode-string s" language" property
s" keyboard" get-node node>path set-alias
s" dev-parent-calls.fs" included
0 VALUE open-count
: open   ( -- true | false )
usb-keyb-debug? IF ." USB-KEYB: Opening (count is " open-count . ." )" cr THEN
open-count 0= IF
udev USB-HID-INIT 0= IF
." USB keyboard setup failed " pwd cr false EXIT
THEN
THEN
open-count 1 + to open-count
true
;
: close
usb-keyb-debug? IF ." USB-KEYB: Closing (count is " open-count . ." )" cr THEN
open-count 0> IF
open-count 1 - dup to open-count
0= IF
my-phandle set-node
udev USB-HID-EXIT drop
0 set-node
THEN
THEN
;
: key-available? ( -- true|false )
udev USB-KEY-AVAILABLE IF TRUE ELSE FALSE THEN
;
: read                     ( addr len -- actual )
0= IF drop 0 EXIT THEN
udev USB-READ-KEYB ?dup IF swap c! 1 ELSE 0 swap c! 0 then
;
."     USB Keyboard " cr
finish-device
ÿÿÿÿÿÿÿÿÎ0dev-mouse.fsnew-device
VALUE sudev
s" slofdev.fs" included
sudev slof-dev>port l@ dup set-unit encode-phys " reg" property
sudev slof-dev>udev @ VALUE udev
s" usb-mouse" device-name
."     USB mouse " cr
finish-device
ÿÿÿÿÿÿÿÿà¨0dev-storage.fsnew-device
VALUE usbdev
s" slofdev.fs" included
false VALUE usb-disk-debug?
usbdev slof-dev>port l@ dup set-unit encode-phys " reg" property
s" storage" device-name
s" dev-parent-calls.fs" included
2 encode-int s" #address-cells" property
0 encode-int s" #size-cells" property
: decode-unit 2 hex64-decode-unit ;
: encode-unit 2 hex64-encode-unit ;
0 CONSTANT USB_PIPE_OUT
1 CONSTANT USB_PIPE_IN
usbdev slof-dev>udev @ VALUE udev
usbdev slof-dev>port l@ VALUE port
usbdev slof-dev>hcitype l@ VALUE hcitype
0 INSTANCE VALUE lun
10000 VALUE dev-max-transfer
0     VALUE resp-buffer
0     VALUE resp-size
0f CONSTANT SCSI-COMMAND-OFFSET
STRUCT
dev-max-transfer FIELD usb>data
40 FIELD usb>cmd
20 FIELD usb>csw
CONSTANT /dma-buf
0 VALUE dma-buf
0 VALUE dma-buf-phys
0 VALUE td-buf
0 VALUE td-buf-phys
1000 CONSTANT /td-buf
: (dma-buf-init)  ( -- )
/dma-buf dma-alloc TO dma-buf
dma-buf /dma-buf 0 dma-map-in TO dma-buf-phys
/td-buf dma-alloc TO td-buf
td-buf /td-buf 0 dma-map-in TO td-buf-phys
;
: (dma-buf-free)  ( -- )
td-buf td-buf-phys /td-buf dma-map-out
td-buf /td-buf dma-free
0 TO td-buf
0 TO td-buf-phys
dma-buf dma-buf-phys /dma-buf dma-map-out
dma-buf /dma-buf dma-free
0 TO dma-buf
0 TO dma-buf-phys
;
scsi-open
0 INSTANCE VALUE current-target
: do-bulk-command ( resp-buffer resp-size -- TRUE | FALSE )
TO resp-size
TO resp-buffer
udev USB_PIPE_OUT td-buf td-buf-phys dma-buf-phys usb>cmd 1F
usb-transfer-bulk IF \ transfer CBW
resp-size IF
d# 125 us
udev USB_PIPE_IN td-buf td-buf-phys resp-buffer resp-size
usb-transfer-bulk 1 = not IF \ transfer data
usb-disk-debug?	IF ." Data phase failed " cr THEN
THEN
THEN
d# 125 us
udev USB_PIPE_IN td-buf td-buf-phys dma-buf-phys usb>csw 0D
usb-transfer-bulk \ transfer CSW
ELSE
FALSE EXIT
THEN
;
STRUCT \ cbw
/l FIELD cbw>sig
/l FIELD cbw>tag
/l FIELD cbw>len
/c FIELD cbw>flags
/c FIELD cbw>lun     \ 0:3 bits
/c FIELD cbw>cblen   \ 0:4 bits
CONSTANT cbw-length
STRUCT \ csw
/l FIELD csw>sig
/l FIELD csw>tag
/l FIELD csw>data-residue
/c FIELD csw>status
CONSTANT cbw-length
0 VALUE cbw-addr
0 VALUE csw-addr
: build-cbw ( tag xfer-len dir lun cmd-len addr -- )
TO cbw-addr               ( tag xfer-len dir lun cmd-len )
cbw-addr cbw-length erase ( tag xfer-len dir lun cmd-len )
cbw-addr cbw>cblen c!     ( tag xfer-len dir lun )
cbw-addr cbw>lun c!       ( tag xfer-len dir )
IF 80 ELSE 0 THEN
cbw-addr cbw>flags c!     ( tag xfer-len )
cbw-addr cbw>len l!-le    ( tag )
cbw-addr cbw>tag l!-le    ( )
43425355 cbw-addr cbw>sig l!-le
;
0 INSTANCE VALUE usb-buf-addr
0 INSTANCE VALUE usb-buf-len
0 INSTANCE VALUE usb-dir
0 INSTANCE VALUE usb-cmd-addr
0 INSTANCE VALUE usb-cmd-len
1 VALUE tag
: execute-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len -- ... )
to usb-cmd-len to usb-cmd-addr to usb-dir to usb-buf-len to usb-buf-addr
dma-buf usb>cmd 40 0 fill
dma-buf usb>csw 20 0 fill
tag usb-buf-len usb-dir lun usb-cmd-len dma-buf usb>cmd
build-cbw
1 tag + to tag
usb-cmd-addr
dma-buf usb>cmd SCSI-COMMAND-OFFSET +
usb-cmd-len
move
dma-buf-phys usb>data usb-buf-len
do-bulk-command IF
dma-buf usb>data usb-buf-addr usb-buf-len move
ELSE
." USB-DISK: Bulk commad failed!" cr
0 0 -1 EXIT
THEN
dma-buf usb>csw to csw-addr
csw-addr csw>sig l@ 55534253 <> IF
." USB-DISK: CSW signature invalid " cr
0 0 -1 EXIT
THEN
csw-addr csw>status c@ CASE
0 OF ENDOF			\ Good
1 OF
usb-disk-debug? IF
." USB-DISK: CSW Data residue: "
csw-addr csw>data-residue l@-le . cr
THEN
0 0 8 EXIT ENDOF	\ Command failed, Retry
dup OF 0 0 -1 EXIT ENDOF	\ Anything else -> HW error
ENDCASE
csw-addr csw>status c@ dup 0<> IF
usb-disk-debug? IF
over scsi-get-sense-data
." USB-DISK: Sense key [ " dup . ." ] " .sense-text
."  ASC,ASCQ: " . . cr
THEN
rot
THEN
;
" scsi-host-helpers.fs" included
0 VALUE open-count
: usb-storage-init  (  -- TRUE )
td-buf 0= IF
usb-disk-debug? IF ." USB-DISK: Allocating buffer "  cr THEN
(dma-buf-init)
udev USB-MSC-INIT 0= IF
." USB-DISK: Unable to initialize MSC " cr
FALSE
ELSE
TRUE
THEN
THEN
;
: usb-storage-cleanup
td-buf 0<> IF
usb-disk-debug? IF ." USB-DISK: Freeing buffer " cr THEN
(dma-buf-free)
udev USB-MSC-EXIT 0= IF ." USB-DISK: Unable to exit MSC " cr THEN
THEN
;
: open
usb-disk-debug? IF ." USB-DISK: Opening (count is " open-count . ." )" cr THEN
open-count 0= IF
usb-storage-init IF
1 to open-count true
ELSE ." USB-DISK initialization failed !" cr false THEN
ELSE
open-count 1 + to open-count
true
THEN
;
: close
usb-disk-debug? IF ." USB-DISK: Closing (count is " open-count . ." )" cr THEN
open-count 0> IF
open-count 1 - dup to open-count
0= IF
usb-storage-cleanup
THEN
THEN
;
: (set-target)
dup 20 >> FFFF and to lun
dup 30 >> FF and to port
to current-target
usb-disk-debug? IF ." USB-DISK: udev " udev . ." lun:" lun . ." port:" port . cr THEN
;
: dev-generate-srplun ( target lun-id -- srplun )
swap drop port 0100 or 10 << or 20 <<
;
: max-transfer ( -- n )
dev-max-transfer
;
: set-address ( srplun.lo srplun.hi -- )
lxjoin (set-target)
usb-disk-debug? IF ." USB-DISK: udev " udev . ." lun:" lun . ." port:" port . cr THEN
;
1 CONSTANT #target
: dev-max-target ( -- #target )
#target
;
" scsi-probe-helpers.fs" included
scsi-close        \ no further scsi words required
: setup-alias
s" scsi" find-alias 0= IF
s" scsi" get-node node>path set-alias
ELSE
drop
THEN
;
: usb-storage-init-and-scan ( -- )
usb-disk-debug? IF ." Initializing usb-disk: udev " udev . cr THEN
0 0 get-node open-node ?dup 0= IF EXIT THEN
my-self >r
dup to my-self
hcitype
CASE
1 OF 4000 TO dev-max-transfer ENDOF \ OHCI
2 OF 10000 TO dev-max-transfer ENDOF \ EHCI
3 OF F000 TO dev-max-transfer ENDOF \ XHCI
ENDCASE
usb-storage-init
scsi-find-disks
setup-alias
usb-storage-cleanup
close-node
r> to my-self
;
."     USB Storage " cr
: usb-scsi-add-disk
" scsi-disk.fs" included
;
usb-scsi-add-disk
usb-storage-init-and-scan
finish-device
ÿÿÿÿÿÿÿÿ8ú0dev-hub.fsnew-device
VALUE sudev
s" slofdev.fs" included
sudev slof-dev>port l@ dup set-unit encode-phys " reg" property
sudev slof-dev>udev @ VALUE udev
s" hub" device-name
s" dev-parent-calls.fs" included
1 encode-int s" #address-cells" property
0 encode-int s" #size-cells" property
: decode-unit  1 hex-decode-unit ;
: encode-unit  1 hex-encode-unit ;
: usb-hub-init ( usbdev -- true | false )
udev USB-HUB-INIT
;
: open   ( -- true | false )
TRUE
;
: close
;
."     USB HUB " cr
usb-hub-init drop
finish-device
ÿÿÿÿÿÿÿÿÀy8pci-device_1af4_1000.fss" virtio [ net ]" type cr
my-space pci-device-generic-setup
pci-io-enable
s" virtio-net.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿh%8pci-device_1af4_1041.fss" pci-device_1af4_1000.fs" included
ÿÿÿÿÿÿÿÿàž8pci-device_1af4_1001.fss" virtio [ block ]" type cr
my-space pci-device-generic-setup
pci-master-enable
pci-mem-enable
pci-io-enable
s" virtio-block.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿh%8pci-device_1af4_1042.fss" pci-device_1af4_1001.fs" included
ÿÿÿÿÿÿÿÿà 8pci-device_1af4_1003.fss" virtio [ serial ]" type cr
my-space pci-device-generic-setup
pci-master-enable
pci-mem-enable
pci-io-enable
s" virtio-serial.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿh%8pci-device_1af4_1043.fss" pci-device_1af4_1003.fs" included
ÿÿÿÿÿÿÿÿàœ8pci-device_1af4_1004.fss" virtio [ scsi ]" type cr
my-space pci-device-generic-setup
pci-master-enable
pci-mem-enable
pci-io-enable
s" virtio-scsi.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿh%8pci-device_1af4_1048.fss" pci-device_1af4_1004.fs" included
ÿÿÿÿÿÿÿÿø·8pci-device_1af4_1009.fss" virtio [ network ]" type cr
my-space pci-device-generic-setup
s" virtio-9p" device-name
pci-master-enable
pci-mem-enable
pci-io-enable
s" virtio-fs.fs" included
pci-device-disable
ÿÿÿÿÿÿÿÿh%8pci-device_1af4_1049.fss" pci-device_1af4_1009.fs" included
ÿÿÿÿÿÿÿÿx48pci-device_1af4_1050.fss" virtio [ vga ]" type cr
s" qemu-vga.fs" included
ÿÿÿÿÿÿÿÿ°x0vio-hvterm.fs." Populating " pwd cr
: open true ;
: close ;
: write ( adr len -- actual )
tuck
0 ?DO
dup c@ my-unit SWAP hv-putchar
1 +
LOOP
drop
;
: read  ( adr len -- actual )
0= IF drop 0 EXIT THEN
my-unit hv-haschar 0= IF 0 swap c! -2 EXIT THEN
my-unit hv-getchar swap c! 1
;
: setup-alias
" hvterm" find-alias 0= IF
" hvterm" get-node node>path set-alias
ELSE
drop
THEN
;
setup-alias
ÿÿÿÿÿÿÿÿ Î0vio-vscsi.fs." Populating " pwd
false VALUE vscsi-debug?
0 VALUE vscsi-unit
: l2dma ( laddr - dma_addr)      
;
0    VALUE     crq-real-base
0    VALUE     crq-base
0    VALUE     crq-dma
0    VALUE     crq-offset
1000 CONSTANT  CRQ-SIZE
CREATE crq 10 allot
: crq-alloc ( -- )
CRQ-SIZE fff + alloc-mem to crq-real-base
crq-real-base fff + fffff000 AND to crq-base 0 to crq-offset
crq-base l2dma to crq-dma
;
: crq-free ( -- )
vscsi-unit hv-free-crq
crq-real-base CRQ-SIZE fff + free-mem 0 to crq-base 0 to crq-real-base
;
: crq-init ( -- res )
crq-alloc
vscsi-debug? IF
." VSCSI: allocated crq at " crq-base . cr
THEN
crq-base CRQ-SIZE erase
vscsi-unit crq-dma CRQ-SIZE hv-reg-crq
dup 0 <> IF
." VSCSI: Error " . ."  registering CRQ !" cr
crq-free
THEN
;
: crq-cleanup ( -- )
crq-base 0 = IF EXIT THEN
vscsi-debug? IF
." VSCSI: freeing crq at " crq-base . cr
THEN
crq-free
;
: crq-send ( msgaddr -- true | false )
vscsi-unit swap hv-send-crq 0 =
;
: crq-poll ( -- true | false)
crq-offset crq-base + dup
vscsi-debug? IF
." VSCSI: crq poll " dup .
THEN
c@
vscsi-debug? IF
."  value=" dup . cr
THEN
80 and 0 <> IF
dup crq 10 move
0 swap c!
crq-offset 10 + dup CRQ-SIZE >= IF drop 0 THEN to crq-offset
true
ELSE drop false THEN
;
: crq-wait ( -- true | false)
0 BEGIN drop crq-poll dup not WHILE d# 1 ms REPEAT
dup not IF
." VSCSI: Timeout waiting response !" cr EXIT
ELSE
vscsi-debug? IF
." VSCSI: got crq: " crq dup l@ . ."  " 4 + dup l@ . ."  "
4 + dup l@ . ."  " 4 + l@ . cr
THEN
THEN
;
01 CONSTANT VIOSRP_SRP_FORMAT
02 CONSTANT VIOSRP_MAD_FORMAT
03 CONSTANT VIOSRP_OS400_FORMAT
04 CONSTANT VIOSRP_AIX_FORMAT
06 CONSTANT VIOSRP_LINUX_FORMAT
07 CONSTANT VIOSRP_INLINE_FORMAT
struct
1 field >crq-valid
1 field >crq-format
1 field >crq-reserved
1 field >crq-status
2 field >crq-timeout
2 field >crq-iu-len
8 field >crq-iu-data-ptr
constant /crq
: srp-send-crq ( addr len -- )
80                crq >crq-valid c!
VIOSRP_SRP_FORMAT crq >crq-format c!
0                 crq >crq-reserved c!
0                 crq >crq-status c!
0                 crq >crq-timeout w!
( len )           crq >crq-iu-len w!
( addr ) l2dma    crq >crq-iu-data-ptr x!
crq crq-send
not IF
." VSCSI: Error sending CRQ !" cr
THEN
;
: srp-wait-crq ( -- [tag true] | false )
crq-wait not IF false EXIT THEN
crq >crq-format c@ VIOSRP_SRP_FORMAT <> IF
." VSCSI: Unsupported SRP response: "
crq >crq-format c@ . cr
false EXIT
THEN
crq >crq-iu-data-ptr x@ true
;
scsi-open
0 VALUE >srp_opcode
00 CONSTANT SRP_LOGIN_REQ
01 CONSTANT SRP_TSK_MGMT
02 CONSTANT SRP_CMD
03 CONSTANT SRP_I_LOGOUT
c0 CONSTANT SRP_LOGIN_RSP
c1 CONSTANT SRP_RSP
c2 CONSTANT SRP_LOGIN_REJ
80 CONSTANT SRP_T_LOGOUT
81 CONSTANT SRP_CRED_REQ
82 CONSTANT SRP_AER_REQ
41 CONSTANT SRP_CRED_RSP
42 CONSTANT SRP_AER_RSP
02 CONSTANT SRP_BUF_FORMAT_DIRECT
04 CONSTANT SRP_BUF_FORMAT_INDIRECT
struct
1 field >srp-login-opcode
3 +
8 field >srp-login-tag
4 field >srp-login-req-it-iu-len
4 +
2 field >srp-login-req-buf-fmt
1 field >srp-login-req-flags
5 +
10 field >srp-login-init-port-ids
10 field >srp-login-trgt-port-ids
constant /srp-login
struct
1 field >srp-lresp-opcode
3 +
4 field >srp-lresp-req-lim-delta
8 field >srp-lresp-tag
4 field >srp-lresp-max-it-iu-len
4 field >srp-lresp-max-ti-iu-len
2 field >srp-lresp-buf-fmt
1 field >srp-lresp-flags
constant /srp-login-resp
struct
1 field >srp-lrej-opcode
3 +
4 field >srp-lrej-reason
8 field >srp-lrej-tag
8 +
2 field >srp-lrej-buf-fmt
constant /srp-login-rej
00 CONSTANT SRP_NO_DATA_DESC
01 CONSTANT SRP_DATA_DESC_DIRECT
02 CONSTANT SRP_DATA_DESC_INDIRECT
struct
1 field >srp-cmd-opcode
1 field >srp-cmd-sol-not
3 +
1 field >srp-cmd-buf-fmt
1 field >srp-cmd-dout-desc-cnt
1 field >srp-cmd-din-desc-cnt
8 field >srp-cmd-tag
4 +
8 field >srp-cmd-lun
1 +
1 field >srp-cmd-task-attr
1 +
1 field >srp-cmd-add-cdb-len
10 field >srp-cmd-cdb
0 field >srp-cmd-cdb-add
constant /srp-cmd
struct
1 field >srp-rsp-opcode
1 field >srp-rsp-sol-not
2 +
4 field >srp-rsp-req-lim-delta
8 field >srp-rsp-tag
2 +
1 field >srp-rsp-flags
1 field >srp-rsp-status
4 field >srp-rsp-dout-res-cnt
4 field >srp-rsp-din-res-cnt
4 field >srp-rsp-sense-len
4 field >srp-rsp-resp-len
0 field >srp-rsp-data
constant /srp-rsp
01 CONSTANT SRP_RSP_FLAG_RSPVALID
02 CONSTANT SRP_RSP_FLAG_SNSVALID
04 CONSTANT SRP_RSP_FLAG_DOOVER
05 CONSTANT SRP_RSP_FLAG_DOUNDER
06 CONSTANT SRP_RSP_FLAG_DIOVER
07 CONSTANT SRP_RSP_FLAG_DIUNDER
CREATE srp 100 allot
0 VALUE srp-len
: srp-prep-cmd-nodata ( srplun -- )
srp /srp-cmd erase
SRP_CMD srp >srp-cmd-opcode c!
1 srp >srp-cmd-tag x!
srp >srp-cmd-lun x!         \ 8 bytes lun
/srp-cmd to srp-len   
;
: srp-prep-cmd-io ( addr len srplun -- )
srp-prep-cmd-nodata		( addr len )
swap l2dma			( len dmaaddr )
srp srp-len +    		( len dmaaddr descaddr )
dup >r x! r> 8 +		( len descaddr+8 )
dup 0 swap l! 4 +		( len descaddr+c )
l!    
srp-len 10 + to srp-len
;
: srp-prep-cmd-read ( addr len srplun -- )
srp-prep-cmd-io
01 srp >srp-cmd-buf-fmt c!	\ in direct buffer
1 srp >srp-cmd-din-desc-cnt c!
;
: srp-prep-cmd-write ( addr len srplun -- )
srp-prep-cmd-io
10 srp >srp-cmd-buf-fmt c!	\ out direct buffer
1 srp >srp-cmd-dout-desc-cnt c!
;
: srp-send-cmd ( -- )
vscsi-debug? IF
." VSCSI: Sending SCSI cmd " srp >srp-cmd-cdb c@ . cr
THEN
srp srp-len srp-send-crq
;
: srp-rsp-find-sense ( -- addr len true | false )
srp >srp-rsp-flags c@ SRP_RSP_FLAG_SNSVALID and 0= IF
false EXIT
THEN
srp >srp-rsp-data srp >srp-rsp-sense-len l@ true
;
: srp-wait-rsp ( -- stat )
srp-wait-crq not IF false EXIT THEN
dup 1 <> IF
." VSCSI: Invalid CRQ response tag, want 1 got " . cr
-1 EXIT
THEN drop
srp >srp-rsp-tag x@ dup 1 <> IF
." VSCSI: Invalid SRP response tag, want 1 got " . cr
-1 EXIT
THEN drop
srp >srp-rsp-status c@
vscsi-debug? IF
." VSCSI: Got response status: "
dup .status-text cr
THEN
;
8000000000000000 INSTANCE VALUE current-target
: execute-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len -- ... )
>r >r				( buf-addr buf-len dir )
over 0= IF
3drop current-target srp-prep-cmd-nodata
ELSE
current-target swap IF srp-prep-cmd-read ELSE srp-prep-cmd-write THEN
THEN
r> r>
srp >srp-cmd-cdb swap move
srp-send-cmd
srp-wait-rsp
dup -1 = IF
0 0 rot EXIT
THEN
dup 0<> IF
srp-rsp-find-sense IF
vscsi-debug? IF
over scsi-get-sense-data
." VSCSI: Sense key [ " dup . ." ] " .sense-text
."  ASC,ASCQ: " . . cr
THEN
ELSE 0 0
." VSCSI: No sense data" cr
THEN
rot
THEN
;
" scsi-host-helpers.fs" included
TRUE VALUE first-time-init?
0 VALUE open-count
: vscsi-cleanup
vscsi-debug? IF ." VSCSI: Cleaning up" cr THEN
crq-cleanup
vscsi-unit 0 rtas-set-tce-bypass
;
: vscsi-init ( -- true | false )
vscsi-debug? IF ." VSCSI: Initializing" cr THEN
my-unit to vscsi-unit
vscsi-unit 1 rtas-set-tce-bypass
crq-init 0 <> IF false EXIT THEN
" "(C0 01 00 00 00 00 00 00 00 00 00 00 00 00 00 00)" drop
crq-send not IF
." VSCSI: Error sending init command"
crq-cleanup false EXIT
THEN
crq-wait not IF
crq-cleanup false EXIT
THEN
crq c@ c0 <> crq 1 + c@ 02 <> or IF
." VSCSI: Initial handshake failed"
crq-cleanup false EXIT
THEN
first-time-init? IF
['] vscsi-cleanup add-quiesce-xt
false to first-time-init?
THEN
true
;
: open
vscsi-debug? IF ." VSCSI: Opening (count is " open-count . ." )" cr THEN
open-count 0= IF
vscsi-init IF
1 to open-count true
ELSE ." VSCSI initialization failed !" cr false THEN
ELSE
open-count 1 + to open-count
true
THEN
;
: close
vscsi-debug? IF ." VSCSI: Closing (count is " open-count . ." )" cr THEN
open-count 0> IF
open-count 1 - dup to open-count
0= IF
vscsi-cleanup
THEN
THEN
;
: (set-target)
to current-target
;
: dev-generate-srplun ( target lun -- )
swap 8 << 8000 or or 30 <<
;
: set-address ( srplun.lo srplun.hi -- )
lxjoin (set-target)
;
: max-transfer ( -- n )
10000 \ Larger value seem to have problems with some CDROMs
;
8 CONSTANT #dev
: dev-max-target ( -- #max-target )
#dev
;
" scsi-probe-helpers.fs" included
scsi-close
: setup-alias
" scsi" find-alias 0= IF
" scsi" get-node node>path set-alias
ELSE
drop
THEN 
;
: vscsi-init-and-scan  ( -- )
0 0 get-node open-node ?dup 0= IF EXIT THEN
my-self >r
dup to my-self
scsi-find-disks
setup-alias
close-node
r> to my-self
;
: vscsi-add-disk
" scsi-disk.fs" included
;
vscsi-add-disk
vscsi-init-and-scan
ÿÿÿÿÿÿÿÿ8ú0vio-veth.fs." Populating " pwd cr
" network" device-type
INSTANCE VARIABLE obp-tftp-package
0 VALUE veth-priv
0 VALUE open-count
: open  ( -- okay? )
open-count 0= IF
my-unit 1 rtas-set-tce-bypass
s" local-mac-address" get-node get-property not
s" reg" get-node get-property not 3 pick and IF
>r nip r>
libveth-open dup not IF ." libveth-open failed" EXIT THEN
drop TO veth-priv
THEN
THEN
my-args s" obp-tftp" $open-package obp-tftp-package !
open-count 1 + to open-count
true
;
: close  ( -- )
open-count 0> IF
open-count 1 - dup to open-count
0= IF
veth-priv libveth-close
my-unit 0 rtas-set-tce-bypass
THEN
THEN
s" close" obp-tftp-package @ $call-method
;
: read ( buf len -- actual )
dup IF
veth-priv libveth-read
ELSE
nip
THEN
;
: write ( buf len -- actual )
dup IF
veth-priv libveth-write
ELSE
nip
THEN
;
: load  ( addr -- len )
s" load" obp-tftp-package @ $call-method 
;
: ping  ( -- )
s" ping" obp-tftp-package @ $call-method
;
: setup-alias
" net" get-next-alias ?dup IF
get-node node>path set-alias
THEN
;
setup-alias
ÿÿÿÿÿÿÿÿ°u0rtas-nvram.fs." Populating " pwd cr
0 VALUE my-nvram-fetch
0 VALUE my-nvram-store
0 VALUE my-nvram-size
0 VALUE nvram-addr
: open true ;
: close ;
: write ( adr len -- actual )
nip
;
: read  ( adr len -- actual )
nip
;
: setup-alias
" nvram" find-alias 0= IF
" nvram" get-node node>path set-alias
ELSE
drop
THEN
;
" #bytes" get-node get-package-property 0= IF
decode-int to my-nvram-size 2drop
" nvram-fetch" rtas-get-token to my-nvram-fetch
" nvram-store" rtas-get-token to my-nvram-store
my-nvram-size to nvram-size
nvram-size alloc-mem to nvram-addr
my-nvram-fetch my-nvram-store nvram-size nvram-addr internal-nvram-init
THEN
setup-alias
ÿÿÿÿÿÿÿÿ8ý0virtio-net.fss" network" device-type
INSTANCE VARIABLE obp-tftp-package
virtio-setup-vd VALUE virtiodev
0 VALUE virtio-net-priv
0 VALUE open-count
6 BUFFER: local-mac
: setup-mac  ( -- )
s" local-mac-address" get-node get-property not IF 2drop EXIT THEN
6 0 DO
virtiodev i 1 virtio-get-config
local-mac i + c!
LOOP
local-mac 6 encode-bytes  s" local-mac-address"  property
;
: open  ( -- okay? )
open-count 0= IF
open IF
virtiodev virtio-net-open not IF ." virtio-net-open failed" false EXIT THEN
TO virtio-net-priv
setup-mac true
ELSE
false
THEN
ELSE
true
THEN
my-args s" obp-tftp" $open-package obp-tftp-package !
open-count 1 + to open-count
;
: close  ( -- )
open-count 0> IF
open-count 1 - dup to open-count
0= IF
virtio-net-priv virtio-net-close
close
THEN
THEN
s" close" obp-tftp-package @ $call-method
;
: read ( buf len -- actual )
dup IF
virtio-net-read
ELSE
nip
THEN
;
: write ( buf len -- actual )
dup IF
virtio-net-write
ELSE
nip
THEN
;
: load  ( addr -- len )
s" load" obp-tftp-package @ $call-method 
;
: ping  ( -- )
s" ping" obp-tftp-package @ $call-method
;
: setup-alias  ( -- )
" net" get-next-alias ?dup IF
get-node node>path set-alias
THEN
;
setup-alias
: virtio-net-init ( -- )
0 0 get-node open-node ?dup 0= IF ." exiting " cr EXIT THEN
close-node
;
virtio-net-init
ÿÿÿÿÿÿÿÿÀ{8virtio-serial.fss" serial" device-type
FALSE VALUE initialized?
virtio-setup-vd VALUE virtiodev
: shutdown  ( -- )
initialized? IF
my-phandle node>path open-dev ?dup IF
virtiodev virtio-serial-shutdown
close-dev
THEN
FALSE to initialized?
THEN
;
: virtio-serial-term-emit
virtiodev SWAP virtio-serial-putchar
;
: virtio-serial-term-key?  virtiodev virtio-serial-haschar ;
: virtio-serial-term-key   BEGIN virtio-serial-term-key? UNTIL virtiodev virtio-serial-getchar ;
: init  ( -- )
virtiodev virtio-serial-init drop
TRUE to initialized?
['] virtio-serial-term-emit to emit
['] virtio-serial-term-key  to key
['] virtio-serial-term-key? to key?
['] shutdown add-quiesce-xt
;
0 VALUE open-count
: open  ( -- okay? )
open-count 0= IF
open IF initialized? 0= IF init THEN
true
ELSE false exit
THEN
ELSE true THEN
open-count 1 + to open-count
;
: close
open-count 0> IF
open-count 1 - dup to open-count
0= IF close THEN
THEN
close
;
: write ( addr len -- actual )
tuck
0 ?DO
dup c@ virtiodev SWAP virtio-serial-putchar
1 +
LOOP
drop
;
: read ( addr len -- actual )
0= IF drop 0 EXIT THEN
virtiodev virtio-serial-haschar 0= IF 0 swap c! -2 EXIT THEN
virtiodev virtio-serial-getchar swap c! 1
;
: setup-alias
" vsterm" find-alias 0= IF
" vsterm" get-node node>path set-alias
ELSE drop THEN
;
setup-alias
: serial-emit virtio-serial-term-emit ;
: serial-key? virtio-serial-term-key? ;
: serial-key  virtio-serial-term-key  ;
ÿÿÿÿÿÿÿÿÑ0virtio-block.fss" block" device-type
FALSE VALUE initialized?
200 VALUE block-size
8000 CONSTANT max-transfer 
INSTANCE VARIABLE deblocker
virtio-setup-vd VALUE virtiodev
: shutdown  ( -- )
initialized? IF
my-phandle node>path open-dev ?dup IF
virtiodev virtio-blk-shutdown
close-dev
THEN
FALSE to initialized?
THEN
;
: init  ( -- )
virtiodev virtio-blk-init to block-size
TRUE to initialized?
['] shutdown add-quiesce-xt
;
: read-blocks  ( addr block# #blocks -- #read )
virtiodev virtio-blk-read
;
: open  ( -- okay? )
open 0= IF false EXIT THEN
dup initialized? 0= AND IF
init
THEN
0 0 s" deblocker" $open-package dup deblocker ! dup IF
s" disk-label" find-package IF
my-args rot interpose
THEN
THEN
0<>
;
: close  ( -- )
deblocker @ close-package
close
;
: seek  ( pos.lo pos.hi -- status )
s" seek" deblocker @ $call-method
;
: read  ( addr len -- actual )
s" read" deblocker @ $call-method
;
: (set-alias)
s" disk" get-next-alias ?dup IF
get-node node>path set-alias
THEN
;
(set-alias)
ÿÿÿÿÿÿÿÿ8ú0virtio-fs.fs." Populating " pwd cr
s" network" device-type
0 VALUE virtfs-rx-buffer
0 VALUE virtfs-tx-buffer
FALSE VALUE initialized?
2000 CONSTANT VIRTFS-BUF-SIZE \ 8k
virtio-setup-vd VALUE virtiodev
: shutdown  ( -- )
initialized? 0= IF EXIT THEN
virtiodev virtio-fs-shutdown
virtfs-rx-buffer VIRTFS-BUF-SIZE free-mem
virtfs-tx-buffer VIRTFS-BUF-SIZE free-mem
FALSE to initialized?
;
: init  ( -- success )
VIRTFS-BUF-SIZE alloc-mem to virtfs-rx-buffer
VIRTFS-BUF-SIZE alloc-mem to virtfs-tx-buffer
virtiodev			( dev )
virtfs-tx-buffer		( dev tx )
virtfs-rx-buffer		( reg tx rx )
VIRTFS-BUF-SIZE		( reg tx rx size )   
virtio-fs-init		( success )
dup IF
TRUE to initialized?
['] shutdown add-quiesce-xt
THEN
;
: open  ( -- okay? )
open 0= IF false EXIT THEN
initialized? 0= IF
init 0= IF false EXIT THEN
THEN   
true
;
: load ( addr -- len )
virtiodev swap		( dev addr )   
my-args   			( dev addr str strlen )
1 +		\ hack to make the following allocate 1 more byte
\-to-/	\ convert path elements
1 - 2dup + 0 swap c! drop
virtio-fs-load		( length )
;
: close  ( -- )
initialized? IF
shutdown
THEN
close
;
: ping ( -- )
cr s" ping not supported for this device" type cr cr
;
: (set-alias)
" virtfs" find-alias 0= IF
" virtfs" get-node node>path set-alias
ELSE
drop
THEN
;
(set-alias)
ÿÿÿÿÿÿÿÿð±0dev-null.fsnew-device
" devnull-console" device-name
: open true ;
: close ;
: write ( adr len -- actual )
nip
;
: read  ( adr len -- actual )
2drop 0
;
: setup-alias
" devnull-console" find-alias 0= IF
" devnull-console" get-node node>path set-alias
ELSE
drop
THEN
;
: dummy-term-emit drop ;
: dummy-term-key  0 ;
: dummy-term-key? FALSE ;
' dummy-term-emit to emit
' dummy-term-key  to key
' dummy-term-key? to key?
setup-alias
finish-device
ÿÿÿÿÿÿÿÿ
@
0virtio-scsi.fs." Populating " pwd cr
FALSE CONSTANT virtio-scsi-debug
2 encode-int s" #address-cells" property
0 encode-int s" #size-cells" property
: decode-unit 2 hex64-decode-unit ;
: encode-unit 2 hex64-encode-unit ;
FALSE VALUE initialized?
virtio-setup-vd VALUE virtiodev
STRUCT \ virtio-scsi-config
/l FIELD vs-cfg>num-queues
/l FIELD vs-cfg>seg-max
/l FIELD vs-cfg>max-sectors
/l FIELD vs-cfg>cmd-per-lun
/l FIELD vs-cfg>event-info-size
/l FIELD vs-cfg>sense_size
/l FIELD vs-cfg>cdb-size
/w FIELD vs-cfg>max-channel
/w FIELD vs-cfg>max-target
/l FIELD vs-cfg>max-lun
CONSTANT vs-cfg-length
STRUCT \ virtio-scsi-req
8  FIELD vs-req>lun
8  FIELD vs-req>tag
/c FIELD vs-req>task-attr
/c FIELD vs-req>prio
/c FIELD vs-req>crn
20 FIELD vs-req>cdb
CONSTANT vs-req-length
STRUCT \ virtio-scsi-resp
/l FIELD vs-rsp>sense-len
/l FIELD vs-rsp>residual
/w FIELD vs-rsp>status-qualifier
/c FIELD vs-rsp>status
/c FIELD vs-rsp>response
60 FIELD vs-rsp>sense
CONSTANT vs-rsp-length
CREATE vs-req vs-req-length allot
CREATE vs-rsp vs-rsp-length allot
scsi-open
0 INSTANCE VALUE current-target
: execute-scsi-command ( buf-addr buf-len dir cmd-addr cmd-len -- ... )
vs-req vs-req-length erase
vs-rsp vs-rsp-length erase
current-target vs-req vs-req>lun x!
vs-req vs-req>cdb swap move
vs-req vs-rsp virtiodev
virtio-scsi-send
0 <> IF
." VIRTIO-SCSI: Queuing failure !" cr
0 0 -1 EXIT
THEN
vs-rsp vs-rsp>response c@ CASE
0 OF ENDOF			\ Good
5 OF drop 0 0 8 EXIT ENDOF	\ Busy
dup OF 0 0 -1 EXIT ENDOF	\ Anything else -> HW error
ENDCASE
vs-rsp vs-rsp>status c@ dup 0<> IF
vs-rsp vs-rsp>sense-len l@ dup 0= IF
." VIRTIO-SCSI: No sense data" cr
0 EXIT
THEN
vs-rsp vs-rsp>sense swap
virtio-scsi-debug IF
over scsi-get-sense-data
." VIRTIO-SCSI: Sense key [ " dup . ." ] " .sense-text
."  ASC,ASCQ: " . . cr
THEN
rot
THEN    
;
" scsi-host-helpers.fs" included
: max-transfer ( -- n )
10000 \ Larger value seem to have problems with some CDROMs
;
: (set-target)
to current-target
;
: dev-generate-srplun ( target lun-id -- srplun )
swap 0100 or 10 << or 20 <<
;
: set-address ( srplun.lo srplun.hi -- )
lxjoin (set-target)
;
100 CONSTANT #target
: dev-max-target ( -- #target )
#target
;
" scsi-probe-helpers.fs" included
scsi-close        \ no further scsi words required
0 VALUE queue-control-addr
0 VALUE queue-event-addr
0 VALUE queue-cmd-addr
: setup-virt-queues
virtiodev 0 virtio-get-qsize virtio-vring-size
alloc-mem to queue-control-addr
virtiodev 0 queue-control-addr virtio-set-qaddr
virtiodev 1 virtio-get-qsize virtio-vring-size
alloc-mem to queue-event-addr
virtiodev 1 queue-event-addr virtio-set-qaddr
virtiodev 2 virtio-get-qsize virtio-vring-size
alloc-mem to queue-cmd-addr
virtiodev 2 queue-cmd-addr virtio-set-qaddr
;
: setup-alias
s" scsi" find-alias 0= IF
s" scsi" get-node node>path set-alias
ELSE
drop
THEN
;
: shutdown ( -- )
initialized? IF
my-phandle node>path open-dev ?dup IF
virtiodev virtio-scsi-shutdown
close-dev
THEN
FALSE to initialized?
THEN
;
: virtio-scsi-init-and-scan  ( -- )
0 0 get-node open-node ?dup 0= IF ." exiting " cr EXIT THEN
my-self >r
dup to my-self
virtiodev virtio-scsi-init
0= IF
setup-virt-queues
scsi-find-disks
setup-alias
TRUE to initialized?
['] shutdown add-quiesce-xt
THEN
close-node
r> to my-self
;
: virtio-scsi-add-disk
" scsi-disk.fs" included
;
virtio-scsi-add-disk
virtio-scsi-init-and-scan
ÿÿÿÿÿÿÿÿø0build_info.imgprintf t[CC]t%sn build_info.img; gcc -m64 
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/libexec/gcc/ppc64-redhat-linux/5.3.1/lto-wrapper
Target: ppc64-redhat-linux
Configured with: ../configure --enable-bootstrap --enable-languages=c,c++,objc,obj-c++,fortran,ada,go,lto --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-shared --enable-threads=posix --enable-checking=release --enable-multilib --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-gnu-unique-object --enable-linker-build-id --with-linker-hash-style=gnu --enable-plugin --enable-initfini-array --disable-libgcj --with-isl --disable-libmpx --enable-gnu-indirect-function --enable-secureplt --with-long-double-128 --build=ppc64-redhat-linux
Thread model: posix
gcc version 5.3.1 20160406 (Red Hat 5.3.1-6) (GCC) 
GNU ld version 2.25-17.fc23
  Supported emulations:
   elf64ppc
   elf32ppc
   elf32ppclinux
   elf32ppcsim
   elf32_spu
ÿÿÿÿÿÿÿÿ†?Q
back to top