From 14442e9201bd705df95f33d0f0764dc9b9402e5b Mon Sep 17 00:00:00 2001 From: Steven Hugg Date: Wed, 15 Aug 2018 00:43:52 -0400 Subject: [PATCH] more work on NES game, static locals, new neslib --- pixels.html | 7 +- presets/nes/crypto.c | 4 +- presets/nes/music.c | 121 ++++++++++++++++++ presets/nes/neslib.h | 3 + presets/nes/neslib1.c | 4 - presets/nes/neslib2.c | 4 - presets/nes/neslib3.c | 4 - presets/nes/neslib4.c | 4 - presets/nes/neslib5.c | 4 - presets/nes/shoot2.c | 250 +++++++++++++++++++++++--------------- presets/nes/siegegame.c | 4 - src/audio.ts | 9 +- src/platform/nes.js | 1 + src/views.ts | 2 +- src/worker/lib/nes/crt0.o | Bin 57756 -> 33919 bytes src/worker/workermain.js | 3 +- 16 files changed, 292 insertions(+), 132 deletions(-) create mode 100644 presets/nes/music.c diff --git a/pixels.html b/pixels.html index 432b775f..46c1c6f8 100644 --- a/pixels.html +++ b/pixels.html @@ -71,7 +71,12 @@ $("#btn_cancel").click(function(e) { } }); $("#btn_saveandclose").click(function(e) { - postToParentWindow({close:true,save:true}); + try { + postToParentWindow({close:true,save:true}); + } catch (ex) { + alert("Could not convert to bytes: " + ex); + throw ex; + } }); diff --git a/presets/nes/crypto.c b/presets/nes/crypto.c index 0dd719a9..11b1c0fc 100644 --- a/presets/nes/crypto.c +++ b/presets/nes/crypto.c @@ -1,4 +1,4 @@ - + #include "neslib.h" #pragma data-name (push,"CHARS") @@ -37,8 +37,6 @@ static const unsigned char paused_palette[]={ #pragma bss-name(push,"ZEROPAGE") #pragma data-name(push,"ZEROPAGE") -unsigned char oam_off; - static unsigned char i, j; static unsigned char player_dir[2]; diff --git a/presets/nes/music.c b/presets/nes/music.c new file mode 100644 index 00000000..525e57d1 --- /dev/null +++ b/presets/nes/music.c @@ -0,0 +1,121 @@ + + +#include +#include + +#include "neslib.h" + +typedef unsigned char byte; + +#pragma data-name (push,"CHARS") + +const unsigned char TILESET[8*128] = {/*{w:8,h:8,bpp:1,count:128,brev:1}*/ +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x7c,0x7c,0x7c,0x38,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6c,0x6c,0x48,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6c,0xfe,0x6c,0xfe,0x6c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0xfe,0xd0,0xfe,0x16,0xfe,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xce,0xdc,0x38,0x76,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x6c,0x7c,0xec,0xee,0x7e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x38,0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x70,0x70,0x70,0x70,0x70,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x70,0x38,0x38,0x38,0x38,0x38,0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6c,0x38,0x6c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x38,0xfe,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x30,0x30,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0e,0x1e,0x3c,0x78,0xf0,0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x7c,0xee,0xee,0xee,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x78,0x38,0x38,0x38,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0x0e,0x7c,0xe0,0xee,0xfe,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfc,0x0e,0x3c,0x0e,0x0e,0xfc,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x3e,0x7e,0xee,0xee,0xfe,0x0e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfc,0xe0,0xfc,0x0e,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xe0,0xfc,0xee,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfe,0xee,0x1c,0x1c,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0x7c,0xee,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0xee,0x7e,0x0e,0x3c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x60,0x60,0xc0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x1c,0x38,0x70,0x70,0x38,0x1c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0x00,0x00,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x70,0x38,0x1c,0x1c,0x38,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0x1c,0x38,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x7c,0xee,0xee,0xee,0xe0,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0xee,0xee,0xfe,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfc,0xee,0xfc,0xee,0xee,0xfc,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0xe0,0xe0,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xf8,0xec,0xee,0xee,0xee,0xfc,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfe,0xe0,0xf0,0xe0,0xe0,0xfe,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfe,0xe0,0xf8,0xe0,0xe0,0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xe0,0xee,0xee,0xee,0x7e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xee,0xfe,0xee,0xee,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0x38,0x38,0x38,0x38,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0e,0x0e,0x0e,0x0e,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xfc,0xf8,0xec,0xee,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe0,0xe0,0xe0,0xe0,0xee,0xfe,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc6,0xee,0xfe,0xfe,0xee,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xce,0xee,0xfe,0xfe,0xee,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0xee,0xee,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0xfc,0xee,0xee,0xee,0xfc,0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xee,0xee,0xee,0xec,0x7e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfc,0xee,0xee,0xee,0xfc,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7c,0xe0,0x7c,0x0e,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfe,0x38,0x38,0x38,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xee,0xee,0xee,0xee,0x7c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xee,0xee,0x6c,0x38,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xee,0xfe,0xfe,0xee,0xc6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0x7c,0x38,0x7c,0xee,0xee,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xee,0xee,0xee,0x7c,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xfe,0x1c,0x38,0x70,0xe0,0xfe,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +}; + +#pragma data-name(pop) + +// +// MUSIC ROUTINES +// + +// Namespace(bias=1.0, freq=111860.8, length=64, maxbits=13, upper=49) +// 440.5 1.79281159771 49 +const int note_table[64] = { +4304, 4062, 3834, 3619, 3416, 3224, 3043, 2872, 2711, 2559, 2415, 2279, 2151, 2031, 1917, 1809, 1707, 1611, 1521, 1436, 1355, 1279, 1207, 1139, 1075, 1015, 958, 904, 853, 805, 760, 717, 677, 639, 603, 569, 537, 507, 478, 451, 426, 402, 379, 358, 338, 319, 301, 284, 268, 253, 239, 225, 213, 201, 189, 179, 168, 159, 150, 142, 134, 126, 119, 112, }; + +byte music_index = 0; +byte cur_duration = 0; + +const byte music1[] = { +0x35,0x8a,0x37,0x8a,0x33,0x3f,0x8a,0x30,0x3c,0x94,0x3e,0x32,0x8a,0x3a,0x2e,0x94,0x35,0x29,0x8a,0x37,0x2b,0x8a,0x33,0x27,0x8a,0x30,0x24,0x94,0x32,0x26,0x8a,0x2e,0x22,0x94,0x29,0x1d,0x8a,0x2b,0x1f,0x8a,0x27,0x1b,0x8a,0x24,0x18,0x94,0x1a,0x26,0x8a,0x18,0x24,0x8a,0x17,0x23,0x8a,0x16,0x22,0xa8,0x3a,0x35,0x32,0x94,0x29,0x26,0x22,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x22,0x1f,0x27,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x39,0x36,0x8a,0x3a,0x37,0x16,0x8a,0x3f,0x37,0x33,0x8a,0x35,0x38,0x22,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x26,0x94,0x3f,0x33,0x37,0x94,0x1f,0x22,0x27,0x94,0x27,0x22,0x1f,0x94,0x29,0x26,0x22,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x1f,0x22,0x27,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x24,0x27,0x94,0x1f,0x13,0x94,0x3c,0x33,0x30,0x8a,0x3a,0x33,0x2e,0x8a,0x39,0x33,0x2d,0x8a,0x3c,0x30,0x8a,0x3f,0x33,0x1d,0x8a,0x37,0x8a,0x1d,0x8a,0x35,0x8a,0x3f,0x33,0x27,0x8a,0x3c,0x30,0x8a,0x35,0x38,0x26,0x94,0x22,0x16,0x94,0x24,0x18,0x94,0x29,0x26,0x1a,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x27,0x22,0x1f,0x8a,0x2b,0x8a,0x33,0x16,0x22,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x13,0x1f,0x8a,0x3f,0x33,0x37,0x8a,0x38,0x35,0x27,0x8a,0x39,0x36,0x8a,0x37,0x3a,0x16,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x20,0x94,0x3f,0x37,0x33,0x94,0x27,0x22,0x1f,0x94,0x2b,0x27,0x22,0x94,0x3f,0x33,0x8a,0x35,0x8a,0x37,0x27,0x1b,0x8a,0x3f,0x33,0x8a,0x35,0x2b,0x22,0x8a,0x37,0x8a,0x25,0x19,0x8a,0x3f,0x33,0x8a,0x35,0x2b,0x27,0x8a,0x3f,0x33,0x8a,0x37,0x24,0x18,0x8a,0x3f,0x33,0x8a,0x35,0x2c,0x27,0x8a,0x37,0x8a,0x23,0x17,0x8a,0x3f,0x33,0x8a,0x35,0x2c,0x27,0x8a,0x3f,0x33,0x8a,0x3a,0x37,0x22,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x2b,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x32,0x35,0x8a,0x35,0x38,0x26,0x94,0x3f,0x33,0x37,0x94,0x22,0x16,0x94,0x24,0x18,0x94,0x29,0x26,0x1a,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x27,0x22,0x1f,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x25,0x22,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x33,0x8a,0x35,0x38,0x27,0x8a,0x39,0x36,0x8a,0x3a,0x37,0x16,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x35,0x38,0x20,0x94,0x37,0x33,0x3f,0x94,0x27,0x22,0x1f,0x94,0x27,0x22,0x1f,0x94,0x29,0x26,0x22,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x22,0x1f,0x27,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x1f,0x13,0x94,0x3c,0x33,0x30,0x8a,0x3a,0x33,0x2e,0x8a,0x2d,0x33,0x39,0x8a,0x3c,0x30,0x8a,0x3f,0x33,0x27,0x8a,0x37,0x8a,0x1d,0x8a,0x35,0x8a,0x33,0x3f,0x27,0x8a,0x3c,0x30,0x8a,0x38,0x35,0x26,0x94,0x22,0x16,0x94,0x24,0x18,0x94,0x29,0x26,0x1a,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x22,0x27,0x1f,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x24,0x27,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x36,0x39,0x8a,0x3a,0x37,0x16,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x37,0x3a,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x22,0x94,0x33,0x37,0x3f,0x94,0x27,0x22,0x1f,0x94,0x22,0x27,0x2b,0x94,0x3f,0x33,0x8a,0x35,0x8a,0x37,0x27,0x1b,0x8a,0x3f,0x33,0x8a,0x35,0x2b,0x27,0x8a,0x37,0x8a,0x25,0x19,0x8a,0x3f,0x33,0x8a,0x35,0x2b,0x22,0x8a,0x3f,0x33,0x8a,0x37,0x24,0x18,0x8a,0x33,0x3f,0x8a,0x35,0x2c,0x27,0x8a,0x37,0x8a,0x23,0x17,0x8a,0x3f,0x33,0x8a,0x35,0x2c,0x27,0x8a,0x3f,0x33,0x8a,0x3a,0x37,0x22,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x2b,0x8a,0x37,0x3a,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x22,0x94,0x33,0x37,0x3f,0x94,0x22,0x16,0x94,0x1b,0x0f,0x8a,0x37,0x2b,0x33,0x8a,0x38,0x2c,0x35,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x37,0x30,0x8a,0x3a,0x2e,0x37,0x8a,0x16,0x8a,0x37,0x33,0x2b,0x8a,0x2c,0x38,0x35,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x37,0x30,0x8a,0x2e,0x37,0x3a,0x8a,0x16,0x8a,0x37,0x8a,0x33,0x27,0x2b,0x8a,0x2e,0x8a,0x30,0x14,0x8a,0x32,0x8a,0x33,0x2c,0x27,0x8a,0x35,0x8a,0x37,0x20,0x8a,0x35,0x8a,0x33,0x2c,0x27,0x8a,0x35,0x8a,0x2e,0x1f,0x8a,0x37,0x8a,0x38,0x2b,0x27,0x8a,0x3a,0x8a,0x3c,0x16,0x8a,0x3a,0x8a,0x37,0x22,0x2b,0x8a,0x38,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x30,0x37,0x8a,0x3a,0x37,0x2e,0x8a,0x16,0x8a,0x37,0x33,0x2b,0x8a,0x38,0x2c,0x35,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x37,0x30,0x8a,0x2e,0x37,0x3a,0x8a,0x1f,0x8a,0x3a,0x8a,0x3c,0x1e,0x8a,0x3d,0x8a,0x3e,0x3a,0x35,0x8a,0x3e,0x35,0x3a,0x8a,0x22,0x29,0x26,0x8a,0x3e,0x33,0x39,0x8a,0x1d,0x8a,0x3c,0x8a,0x39,0x33,0x29,0x8a,0x35,0x8a,0x3a,0x32,0x29,0x94,0x20,0x14,0x94,0x1f,0x13,0x8a,0x37,0x2b,0x33,0x8a,0x38,0x35,0x2c,0x8a,0x39,0x36,0x2d,0x8a,0x2e,0x3a,0x37,0x94,0x3c,0x37,0x30,0x8a,0x3a,0x37,0x2e,0x8a,0x16,0x8a,0x33,0x2b,0x37,0x8a,0x38,0x35,0x2c,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x30,0x37,0x3c,0x8a,0x3a,0x2e,0x37,0x8a,0x16,0x8a,0x37,0x8a,0x33,0x2b,0x27,0x8a,0x2e,0x8a,0x30,0x14,0x8a,0x32,0x8a,0x33,0x2c,0x27,0x8a,0x35,0x8a,0x37,0x20,0x8a,0x35,0x8a,0x33,0x23,0x2c,0x8a,0x35,0x8a,0x33,0x1f,0x94,0x2b,0x22,0x27,0x94,0x1b,0x8a,0x2e,0x8a,0x2d,0x2b,0x27,0x8a,0x2e,0x8a,0x33,0x2c,0x27,0x94,0x30,0x2c,0x27,0x8a,0x33,0x8a,0x21,0x24,0x2a,0x8a,0x30,0x8a,0x33,0x2a,0x27,0x8a,0x30,0x8a,0x2e,0x2b,0x27,0x8a,0x33,0x8a,0x37,0x2b,0x22,0x8a,0x3a,0x8a,0x2b,0x27,0x22,0x8a,0x37,0x8a,0x33,0x2b,0x27,0x8a,0x2e,0x8a,0x30,0x2d,0x1d,0x94,0x33,0x2d,0x24,0x94,0x37,0x2c,0x26,0x8a,0x35,0x2c,0x8a,0x26,0x22,0x8a,0x33,0x2b,0x8a,0x27,0x1b,0x94,0x22,0x16,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x8a,0x38,0x1d,0x11,0x8a,0x39,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x30,0x37,0x8a,0x3a,0x37,0x2e,0x8a,0x16,0x8a,0x37,0x33,0x2b,0x8a,0x38,0x2c,0x35,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x37,0x30,0x8a,0x2e,0x37,0x3a,0x8a,0x16,0x8a,0x37,0x8a,0x33,0x2b,0x27,0x8a,0x2e,0x8a,0x30,0x14,0x8a,0x32,0x8a,0x33,0x2c,0x27,0x8a,0x35,0x8a,0x37,0x20,0x8a,0x35,0x8a,0x33,0x23,0x27,0x8a,0x35,0x8a,0x2e,0x1f,0x8a,0x37,0x8a,0x38,0x27,0x2b,0x8a,0x3a,0x8a,0x3c,0x16,0x8a,0x3a,0x8a,0x37,0x2b,0x27,0x8a,0x38,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x30,0x37,0x8a,0x3a,0x37,0x2e,0x8a,0x16,0x8a,0x37,0x33,0x2b,0x8a,0x38,0x2c,0x35,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x3c,0x37,0x30,0x8a,0x2e,0x37,0x3a,0x8a,0x1f,0x8a,0x3a,0x8a,0x3c,0x1e,0x8a,0x3d,0x8a,0x3e,0x3a,0x35,0x8a,0x3e,0x35,0x3a,0x8a,0x29,0x26,0x22,0x8a,0x3e,0x33,0x39,0x8a,0x1d,0x8a,0x3c,0x8a,0x39,0x33,0x27,0x8a,0x35,0x8a,0x3a,0x32,0x29,0x94,0x20,0x14,0x94,0x1f,0x13,0x8a,0x37,0x2b,0x33,0x8a,0x38,0x35,0x2c,0x8a,0x39,0x36,0x2d,0x8a,0x2e,0x3a,0x37,0x94,0x3c,0x37,0x30,0x8a,0x3a,0x37,0x2e,0x8a,0x16,0x8a,0x33,0x2b,0x37,0x8a,0x38,0x35,0x2c,0x8a,0x39,0x36,0x2d,0x8a,0x3a,0x37,0x2e,0x94,0x30,0x3c,0x37,0x8a,0x37,0x2e,0x3a,0x8a,0x16,0x8a,0x37,0x8a,0x33,0x2b,0x27,0x8a,0x2e,0x8a,0x30,0x14,0x8a,0x32,0x8a,0x33,0x27,0x24,0x8a,0x35,0x8a,0x37,0x20,0x8a,0x35,0x8a,0x33,0x2c,0x27,0x8a,0x35,0x8a,0x33,0x1f,0x94,0x2b,0x27,0x22,0x94,0x1b,0x8a,0x2e,0x8a,0x2d,0x2b,0x27,0x8a,0x2e,0x8a,0x33,0x2c,0x27,0x94,0x30,0x2c,0x20,0x8a,0x33,0x8a,0x2a,0x27,0x24,0x8a,0x30,0x8a,0x33,0x2a,0x27,0x8a,0x30,0x8a,0x2e,0x2b,0x22,0x8a,0x33,0x8a,0x37,0x2b,0x27,0x8a,0x3a,0x8a,0x2b,0x27,0x22,0x8a,0x37,0x8a,0x33,0x2b,0x22,0x8a,0x2e,0x8a,0x30,0x2d,0x27,0x94,0x33,0x2d,0x24,0x94,0x37,0x2c,0x26,0x8a,0x35,0x2c,0x8a,0x26,0x22,0x8a,0x33,0x2b,0x8a,0x27,0x1b,0x94,0x22,0x16,0x94,0x1b,0x0f,0x94,0x29,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x27,0x1f,0x22,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x39,0x36,0x8a,0x3a,0x37,0x16,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x22,0x94,0x3f,0x37,0x33,0x94,0x27,0x22,0x1f,0x94,0x22,0x1f,0x27,0x94,0x29,0x26,0x22,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x27,0x22,0x1f,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x22,0x8a,0x33,0x8a,0x20,0x14,0x94,0x27,0x24,0x94,0x1f,0x13,0x94,0x33,0x3c,0x30,0x8a,0x3a,0x33,0x2e,0x8a,0x39,0x33,0x2d,0x8a,0x3c,0x30,0x8a,0x3f,0x33,0x27,0x8a,0x37,0x8a,0x1d,0x8a,0x35,0x8a,0x3f,0x33,0x27,0x8a,0x3c,0x30,0x8a,0x35,0x38,0x26,0x94,0x22,0x16,0x94,0x24,0x18,0x94,0x29,0x26,0x1a,0x8a,0x2a,0x8a,0x2b,0x1b,0x8a,0x33,0x8a,0x1f,0x22,0x27,0x8a,0x2b,0x8a,0x33,0x22,0x16,0x94,0x2b,0x27,0x25,0x8a,0x33,0x8a,0x20,0x14,0x94,0x24,0x27,0x94,0x1f,0x13,0x8a,0x3f,0x37,0x33,0x8a,0x38,0x35,0x27,0x8a,0x39,0x36,0x8a,0x37,0x3a,0x16,0x8a,0x3f,0x33,0x37,0x8a,0x35,0x38,0x27,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x3e,0x35,0x32,0x8a,0x38,0x35,0x26,0x94,0x3f,0x37,0x33,0x94,0x27,0x22,0x1f,0x94,0x22,0x2b,0x27,0x94,0x3f,0x33,0x8a,0x35,0x8a,0x37,0x27,0x1b,0x8a,0x3f,0x33,0x8a,0x35,0x2b,0x27,0x8a,0x37,0x8a,0x25,0x19,0x8a,0x33,0x3f,0x8a,0x35,0x27,0x22,0x8a,0x3f,0x33,0x8a,0x37,0x24,0x18,0x8a,0x3f,0x33,0x8a,0x35,0x2c,0x27,0x8a,0x37,0x8a,0x23,0x17,0x8a,0x3f,0x33,0x8a,0x35,0x23,0x27,0x8a,0x3f,0x33,0x8a,0x3a,0x37,0x16,0x8a,0x33,0x37,0x3f,0x8a,0x38,0x35,0x2b,0x8a,0x3a,0x37,0x8a,0x16,0x8a,0x32,0x35,0x3e,0x8a,0x38,0x35,0x26,0x94,0x3f,0x37,0x33,0x94,0x22,0x16,0x94,0x3f,0x37,0x33,0xa8,0x38,0x3c,0x14,0x8a,0x3b,0x8a,0x3c,0x38,0x24,0x94,0x1b,0x94,0x3f,0x3c,0x38,0x94,0x38,0x3d,0x19,0x94,0x31,0x2c,0x29,0x8a,0x30,0x8a,0x31,0x20,0x8a,0x33,0x8a,0x35,0x2c,0x25,0x94,0x38,0x35,0x11,0x8a,0x37,0x8a,0x38,0x35,0x2c,0x94,0x18,0x94,0x3c,0x38,0x35,0x94,0x35,0x3a,0x3d,0x94,0x2e,0x25,0x29,0x8a,0x2d,0x8a,0x2e,0x1d,0x8a,0x30,0x8a,0x31,0x29,0x25,0x8a,0x3a,0x8a,0x35,0x25,0x19,0x94,0x3a,0x25,0x29,0x8a,0x35,0x8a,0x22,0x16,0x8a,0x3a,0x8a,0x35,0x23,0x17,0x94,0x33,0x24,0x18,0x94,0x24,0x27,0x2c,0x94,0x38,0x1d,0x94,0x2c,0x29,0x24,0x94,0x37,0x1f,0x8a,0x3b,0x8a,0x3e,0x26,0x29,0x8a,0x8a,0x23,0x8a,0x8a,0x3e,0x2b,0x29,0x8a,0x3f,0x8a,0x3c,0x2b,0x27,0xa8,0x3d,0x22,0x27,0x94,0x1b,0x94,0x3c,0x38,0x14,0x8a,0x3b,0x8a,0x38,0x3c,0x2c,0x94,0x1b,0x94,0x3f,0x3c,0x38,0x94,0x3d,0x38,0x19,0x94,0x31,0x2c,0x25,0x8a,0x30,0x8a,0x31,0x20,0x8a,0x33,0x8a,0x35,0x2c,0x29,0x94,0x38,0x35,0x11,0x8a,0x37,0x8a,0x38,0x35,0x2c,0x94,0x18,0x94,0x35,0x3c,0x38,0x94,0x3d,0x3a,0x35,0x94,0x2e,0x29,0x25,0x8a,0x2d,0x8a,0x2e,0x1d,0x8a,0x30,0x8a,0x31,0x29,0x25,0x8a,0x3a,0x8a,0x35,0x25,0x19,0x94,0x3a,0x29,0x25,0x8a,0x35,0x8a,0x16,0x22,0x8a,0x3a,0x8a,0x35,0x23,0x17,0x94,0x33,0x24,0x18,0x8a,0x20,0x14,0x8a,0x1f,0x13,0x8a,0x11,0x1d,0x8a,0x38,0x32,0x2f,0x9e,0x38,0x8a,0x3c,0x33,0x30,0x8a,0x3f,0x33,0x8a,0x2c,0x27,0x24,0x8a,0x3a,0x31,0x8a,0x27,0x1b,0x8a,0x33,0x8a,0x35,0x31,0x1b,0x8a,0x37,0x8a,0x38,0x30,0x20,0x94,0x32,0x8a,0x33,0x8a,0x35,0x8a,0x37,0x8a,0x38,0x8a,0x3a,0x8a,0x3c,0x38,0x14,0x8a,0x3b,0x8a,0x38,0x3c,0x2c,0x94,0x1b,0x94,0x3f,0x3c,0x38,0x94,0x3d,0x38,0x19,0x94,0x31,0x2c,0x29,0x8a,0x30,0x8a,0x31,0x20,0x8a,0x33,0x8a,0x35,0x29,0x2c,0x94,0x38,0x35,0x11,0x8a,0x37,0x8a,0x38,0x35,0x2c,0x94,0x18,0x94,0x3c,0x35,0x38,0x94,0x35,0x3d,0x3a,0x94,0x2e,0x29,0x25,0x8a,0x2d,0x8a,0x2e,0x1d,0x8a,0x30,0x8a,0x31,0x29,0x25,0x8a,0x3a,0x8a,0x35,0x25,0x19,0x94,0x3a,0x29,0x25,0x8a,0x35,0x8a,0x22,0x16,0x8a,0x3a,0x8a,0x35,0x23,0x17,0x94,0x33,0x24,0x18,0x94,0x2c,0x27,0x24,0x94,0x38,0x1d,0x94,0x2c,0x29,0x24,0x94,0x37,0x1f,0x8a,0x3b,0x8a,0x3e,0x26,0x2b,0x8a,0x8a,0x23,0x8a,0x8a,0x3e,0x2b,0x29,0x8a,0x3f,0x8a,0x3c,0x2b,0x27,0xa8,0x3d,0x2b,0x27,0x94,0x1b,0x94,0x3c,0x38,0x14,0x8a,0x3b,0x8a,0x38,0x3c,0x24,0x94,0x1b,0x94,0x3f,0x3c,0x38,0x94,0x3d,0x38,0x19,0x94,0x31,0x2c,0x29,0x8a,0x30,0x8a,0x31,0x20,0x8a,0x33,0x8a,0x35,0x2c,0x29,0x94,0x35,0x38,0x11,0x8a,0x37,0x8a,0x38,0x35,0x2c,0x94,0x18,0x94,0x3c,0x38,0x35,0x94,0x3d,0x3a,0x35,0x94,0x2e,0x25,0x29,0x8a,0x2d,0x8a,0x2e,0x1d,0x8a,0x30,0x8a,0x31,0x29,0x25,0x8a,0x3a,0x8a,0x35,0x25,0x19,0x94,0x3a,0x29,0x25,0x8a,0x35,0x8a,0x22,0x16,0x8a,0x3a,0x8a,0x35,0x23,0x17,0x94,0x33,0x24,0x18,0x8a,0x20,0x14,0x8a,0x1f,0x13,0x8a,0x1d,0x11,0x8a,0x38,0x32,0x2f,0x9e,0x38,0x8a,0x30,0x33,0x3c,0x8a,0x3f,0x33,0x8a,0x2c,0x27,0x24,0x8a,0x3a,0x31,0x8a,0x27,0x1b,0x8a,0x33,0x8a,0x35,0x31,0x1b,0x8a,0x37,0x8a,0x30,0x38,0x20,0xa8,0x3f,0x3c,0x38,0xa8,0x33,0x20,0x27,0x94,0x30,0x2c,0x27,0x8a,0x33,0x8a,0x2a,0x27,0x24,0x8a,0x30,0x8a,0x33,0x2a,0x21,0x8a,0x30,0x8a,0x2e,0x2b,0x27,0x8a,0x33,0x8a,0x37,0x22,0x27,0x8a,0x3a,0x8a,0x2b,0x27,0x22,0x8a,0x37,0x8a,0x33,0x2b,0x27,0x8a,0x2e,0x8a,0x30,0x2d,0x27,0x94,0x33,0x2d,0x24,0x94,0x37,0x2c,0x26,0x8a,0x35,0x2c,0x8a,0x26,0x22,0x8a,0x33,0x2b,0x8a,0x27,0x1b,0xa8,0x33,0x37,0x3a,0xa8,0x2c,0x29,0x14,0x94,0x2b,0x28,0x20,0x8a,0x2c,0x29,0x8a,0x18,0x8a,0x2b,0x28,0x8a,0x29,0x2c,0x24,0x94,0x14,0x8a,0x30,0x8a,0x2c,0x35,0x24,0x8a,0x30,0x8a,0x33,0x18,0x8a,0x35,0x8a,0x33,0x24,0x20,0x8a,0x30,0x8a,0x2e,0x2b,0x1b,0x94,0x2d,0x2a,0x27,0x8a,0x2e,0x2b,0x8a,0x16,0x8a,0x2d,0x2a,0x8a,0x2e,0x2b,0x1f,0x94,0x1b,0x8a,0x33,0x8a,0x37,0x2e,0x27,0x8a,0x33,0x8a,0x35,0x16,0x8a,0x37,0x8a,0x35,0x1f,0x22,0x8a,0x33,0x8a,0x35,0x32,0x16,0x94,0x34,0x31,0x26,0x8a,0x35,0x32,0x8a,0x1a,0x8a,0x34,0x31,0x8a,0x32,0x35,0x26,0x94,0x16,0x8a,0x38,0x8a,0x3c,0x32,0x22,0x8a,0x38,0x8a,0x3a,0x1d,0x8a,0x3c,0x8a,0x3a,0x26,0x22,0x8a,0x38,0x8a,0x3f,0x33,0x27,0x8a,0x3f,0x33,0x8a,0x3f,0x33,0x27,0xa8,0x3c,0x33,0x27,0x94,0x3a,0x33,0x1f,0x94,0x2e,0x2b,0x8a,0x2e,0x2b,0x8a,0x2e,0x2b,0x94,0x2b,0x2e,0x94,0x2c,0x29,0x14,0x94,0x2b,0x28,0x24,0x8a,0x2c,0x29,0x8a,0x18,0x8a,0x2b,0x28,0x8a,0x2c,0x29,0x24,0x94,0x14,0x8a,0x30,0x8a,0x35,0x2c,0x20,0x8a,0x30,0x8a,0x33,0x18,0x8a,0x35,0x8a,0x33,0x24,0x20,0x8a,0x30,0x8a,0x2e,0x2b,0x1b,0x94,0x2a,0x2d,0x27,0x8a,0x2e,0x2b,0x8a,0x16,0x8a,0x2d,0x2a,0x8a,0x2e,0x2b,0x1f,0x94,0x1b,0x8a,0x33,0x8a,0x37,0x2e,0x27,0x8a,0x33,0x8a,0x35,0x16,0x8a,0x37,0x8a,0x35,0x27,0x22,0x8a,0x33,0x8a,0x30,0x20,0x14,0x8a,0x2f,0x8a,0x30,0x1d,0x11,0x8a,0x3a,0x30,0x8a,0x1f,0x13,0x8a,0x38,0x30,0x8a,0x20,0x14,0x8a,0x33,0x30,0x8a,0x37,0x2e,0x22,0x8a,0x36,0x8a,0x37,0x22,0x2b,0x8a,0x3c,0x8a,0x2a,0x27,0x21,0x8a,0x3f,0x8a,0x3a,0x2b,0x27,0x8a,0x37,0x8a,0x33,0x2d,0x18,0x94,0x33,0x2d,0x1d,0x94,0x37,0x2c,0x32,0x8a,0x35,0x32,0x2c,0x8a,0x26,0x1a,0x8a,0x33,0x2e,0x2b,0x8a,0x27,0x1b,0x94,0x2b,0x2e,0x8a,0x2e,0x2b,0x8a,0x2e,0x2b,0x94,0x2e,0x2b,0x94,0x2c,0x29,0x14,0x94,0x2b,0x28,0x20,0x8a,0x29,0x2c,0x8a,0x18,0x8a,0x2b,0x28,0x8a,0x2c,0x29,0x24,0x94,0x14,0x8a,0x30,0x8a,0x35,0x2c,0x24,0x8a,0x30,0x8a,0x33,0x18,0x8a,0x35,0x8a,0x33,0x24,0x20,0x8a,0x30,0x8a,0x2e,0x2b,0x1b,0x94,0x2d,0x2a,0x27,0x8a,0x2e,0x2b,0x8a,0x16,0x8a,0x2d,0x2a,0x8a,0x2e,0x2b,0x1f,0x94,0x1b,0x8a,0x33,0x8a,0x37,0x2e,0x27,0x8a,0x33,0x8a,0x35,0x16,0x8a,0x37,0x8a,0x35,0x27,0x22,0x8a,0x33,0x8a,0x35,0x32,0x16,0x94,0x31,0x34,0x26,0x8a,0x35,0x32,0x8a,0x1a,0x8a,0x34,0x31,0x8a,0x35,0x32,0x26,0x94,0x16,0x8a,0x38,0x8a,0x3c,0x32,0x20,0x8a,0x38,0x8a,0x3a,0x1d,0x8a,0x3c,0x8a,0x3a,0x26,0x22,0x8a,0x38,0x8a,0x33,0x3f,0x27,0x8a,0x3f,0x33,0x8a,0x3f,0x33,0x1e,0xa8,0x3c,0x33,0x27,0x94,0x3a,0x33,0x27,0x94,0x2b,0x2e,0x8a,0x2e,0x2b,0x8a,0x2e,0x2b,0x94,0x2e,0x2b,0x94,0x2c,0x29,0x14,0x94,0x2b,0x28,0x20,0x8a,0x2c,0x29,0x8a,0x18,0x8a,0x2b,0x28,0x8a,0x2c,0x29,0x24,0x94,0x14,0x8a,0x30,0x8a,0x35,0x2c,0x24,0x8a,0x30,0x8a,0x33,0x18,0x8a,0x35,0x8a,0x33,0x24,0x20,0x8a,0x30,0x8a,0x2e,0x2b,0x1b,0x94,0x2d,0x2a,0x27,0x8a,0x2e,0x2b,0x8a,0x16,0x8a,0x2a,0x2d,0x8a,0x2e,0x2b,0x27,0x94,0x1b,0x8a,0x33,0x8a,0x37,0x2e,0x27,0x8a,0x33,0x8a,0x35,0x16,0x8a,0x37,0x8a,0x35,0x22,0x1f,0x8a,0x33,0x8a,0x30,0x20,0x14,0x8a,0x2f,0x8a,0x30,0x1d,0x11,0x8a,0x3a,0x30,0x8a,0x1f,0x13,0x8a,0x38,0x30,0x8a,0x20,0x14,0x8a,0x33,0x30,0x8a,0x37,0x2e,0x22,0x8a,0x36,0x8a,0x37,0x2b,0x27,0x8a,0x3c,0x8a,0x21,0x27,0x2a,0x8a,0x3f,0x8a,0x3a,0x2b,0x27,0x8a,0x37,0x8a,0x33,0x2d,0x24,0x94,0x33,0x2d,0x1d,0x94,0x37,0x32,0x2c,0x8a,0x35,0x2c,0x32,0x8a,0x26,0x1a,0x8a,0x33,0x2e,0x2b,0x8a,0x27,0x1b,0x94,0x22,0x16,0x94,0x3f,0x3a,0x37,0xff +}; + +static const byte* music_ptr = music1; + +byte next_music_byte() { + return *music_ptr++; +} + +#define DUTY 0x80 + +void play_music() { + static byte ch = 0; + if (music_ptr) { + while (cur_duration == 0) { + byte note = next_music_byte(); + if ((note & 0x80) == 0) { + int period = note_table[note & 63]; + if (ch == 0) { + APU.pulse[0].period_low = period & 0xff; + APU.pulse[0].len_period_high = period >> 8; + APU.pulse[0].control = DUTY | 0xf; + } else { + APU.pulse[1].period_low = period & 0xff; + APU.pulse[1].len_period_high = period >> 8; + APU.pulse[1].control = DUTY | 0xf; + } + ch = ch^1; + } else { + if (note == 0xff) + music_ptr = NULL; + cur_duration = note & 63; + } + } + cur_duration--; + } +} + +void start_music(const byte* music) { + music_ptr = music; + cur_duration = 0; +} + +//put a string into the nametable + +void put_str(unsigned int adr,const char *str) +{ + vram_adr(adr); + while(1) + { + if(!*str) break; + vram_put((*str++)-0x20);//-0x20 because ASCII code 0x20 is placed in tile 0 of the CHR + } +} + +const byte APUINIT[0x13] = { + 0x30,0x08,0x00,0x00, + 0x30,0x08,0x00,0x00, + 0x80,0x00,0x00,0x00, + 0x30,0x00,0x00,0x00, + 0x00,0x00,0x00 +}; + +void init_apu() { + // from https://wiki.nesdev.com/w/index.php/APU_basics + memcpy((void*)0x4000, APUINIT, sizeof(APUINIT)); + APU.status = 0xf; + APU.fcontrol = 0x40; +} + +void main(void) +{ + //copy tileset to RAM + vram_adr(0x0); + vram_write((unsigned char*)TILESET, sizeof(TILESET)); + pal_col(1,0x30);//set while color + put_str(NTADR_A(2,2),"HELLO, WORLD!"); + ppu_on_all();//enable rendering + + init_apu(); + + music_ptr = 0; + while (1) { + if (!music_ptr) start_music(music1); + waitvsync(); + play_music(); + } +} diff --git a/presets/nes/neslib.h b/presets/nes/neslib.h index e9f9355e..e6762296 100644 --- a/presets/nes/neslib.h +++ b/presets/nes/neslib.h @@ -243,6 +243,9 @@ void __fastcall__ oam_clear_fast(void); void __fastcall__ oam_meta_spr_pal(unsigned char x,unsigned char y,unsigned char pal,const unsigned char *metasprite); void __fastcall__ oam_meta_spr_clip(signed int x,unsigned char y,const unsigned char *metasprite); +// set NMI callback +void __fastcall__ nmi_set_callback(void (*callback)(void)); + #define PAD_A 0x01 diff --git a/presets/nes/neslib1.c b/presets/nes/neslib1.c index 740e6815..49c368fb 100644 --- a/presets/nes/neslib1.c +++ b/presets/nes/neslib1.c @@ -3,10 +3,6 @@ #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") const unsigned char TILESET[8*128] = {/*{w:8,h:8,bpp:1,count:128,brev:1}*/ diff --git a/presets/nes/neslib2.c b/presets/nes/neslib2.c index 63180aad..560a6495 100644 --- a/presets/nes/neslib2.c +++ b/presets/nes/neslib2.c @@ -4,10 +4,6 @@ #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") #pragma data-name(pop) diff --git a/presets/nes/neslib3.c b/presets/nes/neslib3.c index e869c72f..8687e43a 100644 --- a/presets/nes/neslib3.c +++ b/presets/nes/neslib3.c @@ -6,10 +6,6 @@ #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") #pragma data-name(pop) diff --git a/presets/nes/neslib4.c b/presets/nes/neslib4.c index 72429f89..91c0690c 100644 --- a/presets/nes/neslib4.c +++ b/presets/nes/neslib4.c @@ -1,10 +1,6 @@ #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") #pragma data-name(pop) diff --git a/presets/nes/neslib5.c b/presets/nes/neslib5.c index 9baabc4d..82523846 100644 --- a/presets/nes/neslib5.c +++ b/presets/nes/neslib5.c @@ -4,10 +4,6 @@ #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") #pragma data-name(pop) diff --git a/presets/nes/shoot2.c b/presets/nes/shoot2.c index fed7441f..2e3c4ec0 100644 --- a/presets/nes/shoot2.c +++ b/presets/nes/shoot2.c @@ -2,22 +2,17 @@ #include #include #include -#include #include "neslib.h" -#pragma bss-name (push,"ZEROPAGE") -unsigned char oam_off; -#pragma bss-name (pop) - #pragma data-name (push,"CHARS") #pragma data-name(pop) -#pragma static-locals (1); - #define COLS 32 #define ROWS 28 +//#define DEBUG_FRAMERATE + typedef unsigned char byte; typedef signed char sbyte; typedef unsigned short word; @@ -47,14 +42,16 @@ const char PALETTE[32] = { #define COLOR_EXPLOSION 3 const char TILESET[128*8*2] = {/*{w:8,h:8,bpp:1,count:128,brev:1,np:2,pofs:8,remap:[0,1,2,4,5,6,7,8,9,10,11,12]}*/ +// font (0..63) 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x7C,0x7C,0x7C,0x38,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6C,0x6C,0x48,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6C,0xFE,0x6C,0xFE,0x6C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0xFE,0xD0,0xFE,0x16,0xFE,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xCE,0xDC,0x38,0x76,0xE6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x6C,0x7C,0xEC,0xEE,0x7E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x38,0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x70,0x70,0x70,0x70,0x70,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x70,0x38,0x38,0x38,0x38,0x38,0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x6C,0x38,0x6C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x38,0xFE,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x30,0x30,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0E,0x1E,0x3C,0x78,0xF0,0xE0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, 0x00,0x7C,0xEE,0xEE,0xEE,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x38,0x78,0x38,0x38,0x38,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0x0E,0x7C,0xE0,0xEE,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0x0E,0x3C,0x0E,0x0E,0xFC,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x3E,0x7E,0xEE,0xEE,0xFE,0x0E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xE0,0xFC,0x0E,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xE0,0xFC,0xEE,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0xEE,0x1C,0x1C,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0x7C,0xEE,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0xEE,0x7E,0x0E,0x3C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x60,0x00,0x00,0x60,0x60,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x1C,0x38,0x70,0x70,0x38,0x1C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0x00,0x00,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x70,0x38,0x1C,0x1C,0x38,0x70,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0x1C,0x38,0x00,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, 0x00,0x7C,0xEE,0xEE,0xEE,0xE0,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0xEE,0xEE,0xFE,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xEE,0xFC,0xEE,0xEE,0xFC,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0xE0,0xE0,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xF8,0xEC,0xEE,0xEE,0xEE,0xFC,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0xE0,0xF0,0xE0,0xE0,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0xE0,0xF8,0xE0,0xE0,0xE0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xE0,0xEE,0xEE,0xEE,0x7E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xEE,0xFE,0xEE,0xEE,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0x38,0x38,0x38,0x38,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0E,0x0E,0x0E,0x0E,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xFC,0xF8,0xEC,0xEE,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xE0,0xE0,0xE0,0xE0,0xEE,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xC6,0xEE,0xFE,0xFE,0xEE,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xCE,0xEE,0xFE,0xFE,0xEE,0xE6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0xEE,0xEE,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, 0x00,0xFC,0xEE,0xEE,0xEE,0xFC,0xE0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xEE,0xEE,0xEE,0xEC,0x7E,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFC,0xEE,0xEE,0xEE,0xFC,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0xE0,0x7C,0x0E,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0x38,0x38,0x38,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xEE,0xEE,0xEE,0xEE,0x7C,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xEE,0xEE,0x6C,0x38,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xEE,0xFE,0xFE,0xEE,0xC6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0x7C,0x38,0x7C,0xEE,0xEE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xEE,0xEE,0xEE,0x7C,0x38,0x38,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0x1C,0x38,0x70,0xE0,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -// formation enemy (66) +// formation enemy (64,66) +0x0F,0x13,0x03,0x03,0x01,0x01,0x00,0x00,0x0C,0x11,0x04,0x08,0x12,0x04,0x08,0x08, +0xF8,0xE4,0xE0,0xE0,0xC0,0xC0,0x80,0x00,0x18,0x44,0x10,0x08,0x24,0x10,0x08,0x08, + 0x0C,0x13,0x03,0x03,0x03,0x01,0x01,0x00,0x0C,0x10,0x01,0x0C,0x30,0x02,0x04,0x18, 0x18,0x64,0xE0,0xE0,0xE0,0xC0,0xC0,0x80,0x18,0x04,0x40,0x18,0x06,0x20,0x10,0x0C, // attackers (68) @@ -68,16 +65,16 @@ const char TILESET[128*8*2] = {/*{w:8,h:8,bpp:1,count:128,brev:1,np:2,pofs:8,rem 0x00,0x00,0x00,0x08,0x08,0x10,0xE0,0xE0,0x00,0x00,0x00,0x08,0x08,0x10,0x00,0x40, 0xE0,0xC0,0xC0,0x00,0x00,0x00,0x00,0x00,0x10,0x0C,0x02,0x20,0x10,0x0C,0x00,0x00, -0x00,0x00,0x0C,0x04,0x02,0x03,0x07,0x27,0x00,0x00,0x0C,0x04,0x00,0x00,0x01,0x20, -0x3F,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x32,0x00,0x04,0x08,0x10,0x01,0x00,0x00, -0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0xE0,0x00,0x00,0x00,0x20,0x40,0x84,0x08,0x10, -0xE0,0xF0,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,0x80,0x00,0x00,0x00, - -0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -0x07,0x03,0x03,0x01,0x00,0x00,0x00,0x00,0x00,0x18,0x21,0x44,0x08,0x08,0x00,0x00, -0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xC0,0x00,0x00,0x20,0x40,0x80,0x98,0x20,0x00, -0xE0,0xFC,0xC4,0x80,0x80,0x80,0xC0,0x00,0x40,0x0C,0x04,0x00,0x00,0x80,0xC0,0x00, +0x00,0x00,0x02,0x04,0x04,0x03,0x03,0x03,0x00,0x00,0x02,0x04,0x04,0x20,0x11,0x0C, +0x03,0x07,0x03,0x03,0x02,0x00,0x00,0x00,0x00,0x20,0x1C,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x08,0x08,0x10,0xE0,0xE0,0x00,0x00,0x00,0x08,0x08,0x10,0x00,0x40, +0xE0,0xC0,0xC0,0x00,0x00,0x00,0x00,0x00,0x10,0x0C,0x02,0x20,0x10,0x0C,0x00,0x00, +0x00,0x00,0x01,0x01,0x01,0x01,0x03,0x03,0x00,0x00,0x01,0x11,0x08,0x04,0x01,0x20, +0x07,0x07,0x03,0x02,0x00,0x00,0x00,0x00,0x10,0x08,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x80,0x00,0x04,0xCC,0xF0,0xE0,0x00,0x00,0x80,0x00,0x04,0x0C,0x00,0x40, +0xC0,0xC0,0x80,0x00,0x00,0x00,0x00,0x00,0x20,0x10,0x08,0x80,0x40,0x20,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x00,0x00,0x00,0x04,0x02,0x11,0x08,0x04, 0x03,0x03,0x07,0x01,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x30,0x20,0x60,0xF0,0xFC,0x00,0x00,0x00,0x30,0x20,0x00,0x40,0x04, @@ -97,15 +94,22 @@ const char TILESET[128*8*2] = {/*{w:8,h:8,bpp:1,count:128,brev:1,np:2,pofs:8,rem 0x11,0x16,0x1E,0x15,0x10,0x10,0x10,0x10,0x3F,0x3F,0x3F,0x3D,0x3B,0x3C,0x28,0x28, 0x40,0x40,0xC0,0x00,0x00,0x40,0x44,0x44,0xC0,0xC0,0x20,0xF0,0xC0,0xC2,0xC2,0xEA, 0x44,0x34,0x3C,0x54,0x04,0x04,0x04,0x04,0xFE,0xFE,0xFE,0xDE,0xEE,0x1E,0x0A,0x0A, - +// player ship (96) 0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18, 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -0x08,0x18,0x08,0x18,0x08,0x18,0x18,0x10,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - -0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -// explosions +// bullet (100) +0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +// stars (102) +0x00,0x00,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +// explosions (112) 0x00,0x00,0x00,0x08,0x04,0x03,0x06,0x05,0x00,0x00,0x00,0x0C,0x06,0x04,0x00,0x18, 0x05,0x06,0x07,0x00,0x00,0x00,0x00,0x00,0x18,0x00,0x08,0x09,0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x08,0x90,0xE0,0x90,0xD0,0x00,0x00,0x00,0x18,0x30,0x10,0x00,0x0C, @@ -132,7 +136,7 @@ const char TILESET[128*8*2] = {/*{w:8,h:8,bpp:1,count:128,brev:1,np:2,pofs:8,rem // VRAM UPDATE BUFFER -#define VBUFSIZE 64 +#define VBUFSIZE 96 byte updbuf[VBUFSIZE]; byte updptr = 0; @@ -226,18 +230,24 @@ word bcd_add(word a, word b) { // GAME CODE -#define NSPRITES 16 -#define NMISSILES 8 -#define YOFFSCREEN 239 +#define NSPRITES 8 // max number of sprites +#define NMISSILES 8 // max number of missiles +#define YOFFSCREEN 240 // offscreen y position (hidden) -#define SPRI_SHIP 96 -#define SPRI_MISSILE 100 -#define SPRI_BOMB 104 -#define SPRI_EXPLODE 112 -#define SPRI_ENEMY 68 +// sprite indexes +#define PLYRMISSILE 7 // player missile +#define PLYRSPRITE 7 // player sprite +#define BOOMSPRITE 6 // explosion sprite -#define SSRC_FORM1 66 -#define SDST_FORM1 128 +// nametable entries +#define NAME_SHIP 96 +#define NAME_MISSILE 100 +#define NAME_BOMB 104 +#define NAME_EXPLODE 112 +#define NAME_ENEMY 68 + +#define SSRC_FORM1 64 // name for formation source sprites +#define SDST_FORM1 128 // start of shifted formation table typedef struct { byte shape; @@ -286,11 +296,10 @@ byte player_exploding; byte enemy_exploding; byte enemies_left; word player_score; -byte framecount; void copy_sprites() { byte i; - byte oamid = 0; + byte oamid = 128; // so we don't clear stars... for (i=0; iy != YOFFSCREEN) { @@ -307,7 +316,7 @@ void copy_sprites() { for (i=0; iypos != YOFFSCREEN) { - oamid = oam_spr(mis->xpos, mis->ypos, SPRI_MISSILE, + oamid = oam_spr(mis->xpos, mis->ypos, NAME_MISSILE, (i==7)?COLOR_MISSILE:COLOR_BOMB, oamid); } @@ -345,12 +354,11 @@ void setup_formation() { void draw_row(byte row) { static char buf[32]; - byte i; - byte x = formation_offset_x / 8; + register byte i; + register byte x = formation_offset_x / 8; byte xd = (formation_offset_x & 7) * 3; byte y = 3 + row * 2; - for (i=0; ifindex) { - byte code = DIR_TO_CODE[(a->dir)&31]; - vsprites[i].name = SPRI_ENEMY + (code&7)*4; // tile - vsprites[i].tag = code & 0xc0; // flip h/v + byte code = DIR_TO_CODE[a->dir & 31]; + vsprites[i].name = NAME_ENEMY + (code & 7)*4; // tile + vsprites[i].tag = code & FLIPXY; // flip h/v vsprites[i].x = a->x >> 8; vsprites[i].y = a->y >> 8; } else { @@ -443,7 +447,7 @@ void draw_attackers() { } } -void return_attacker(AttackingEnemy* a) { +void return_attacker(register AttackingEnemy* a) { byte fi = a->findex-1; byte destx = get_attacker_x(fi); byte desty = get_attacker_y(fi); @@ -460,9 +464,15 @@ void return_attacker(AttackingEnemy* a) { } } -void fly_attacker(AttackingEnemy* a) { - a->x += isin(a->dir) * 2; - a->y += icos(a->dir) * 2; +void fly_attacker(register AttackingEnemy* a) { + byte dir = a->dir; +#if 1 + a->x += SINTBL[dir & 31] * 2; + a->y += SINTBL[(dir+8) & 31] * 2; +#else + a->x += isin(dir) * 2; + a->y += icos(dir) * 2; +#endif if ((a->y >> 8) == 0) { a->returning = 1; } @@ -534,24 +544,24 @@ void formation_to_attacker(byte formation_index) { } void draw_player() { - vsprites[7].x = player_x; - vsprites[7].y = player_y; - vsprites[7].name = SPRI_SHIP; - vsprites[7].tag = COLOR_PLAYER; + vsprites[PLYRSPRITE].x = player_x; + vsprites[PLYRSPRITE].y = player_y; + vsprites[PLYRSPRITE].name = NAME_SHIP; + vsprites[PLYRSPRITE].tag = COLOR_PLAYER; } void move_player() { - byte joy = joy_read(JOY_1); + byte joy = pad_poll(0); // move left/right? - if ((joy & JOY_LEFT_MASK) && player_x > 16) player_x--; - if ((joy & JOY_RIGHT_MASK) && player_x < 224) player_x++; + if ((joy & PAD_LEFT) && player_x > 16) player_x--; + if ((joy & PAD_RIGHT) && player_x < 224) player_x++; // shoot missile? - if ((joy & JOY_BTN_A_MASK) && missiles[7].ypos == YOFFSCREEN) { - missiles[7].ypos = player_y-8; // must be multiple of missile speed - missiles[7].xpos = player_x; // player X position - missiles[7].dy = -4; // player missile speed + if ((joy & PAD_A) && missiles[PLYRMISSILE].ypos == YOFFSCREEN) { + missiles[PLYRMISSILE].ypos = player_y-8; // must be multiple of missile speed + missiles[PLYRMISSILE].xpos = player_x+4; // player X position + missiles[PLYRMISSILE].dy = -4; // player missile speed } - vsprites[7].x = player_x; + vsprites[PLYRMISSILE].x = player_x; } void move_missiles() { @@ -567,10 +577,10 @@ void move_missiles() { } void blowup_at(byte x, byte y) { - vsprites[6].tag = COLOR_EXPLOSION; - vsprites[6].name = SPRI_EXPLODE; // TODO - vsprites[6].x = x; - vsprites[6].y = y; + vsprites[BOOMSPRITE].tag = COLOR_EXPLOSION; + vsprites[BOOMSPRITE].name = NAME_EXPLODE; // TODO + vsprites[BOOMSPRITE].x = x; + vsprites[BOOMSPRITE].y = y; enemy_exploding = 1; } @@ -579,9 +589,9 @@ void animate_enemy_explosion() { // animate next frame if (enemy_exploding >= 8) { enemy_exploding = 0; // hide explosion after 4 frames - vsprites[6].y = YOFFSCREEN; + vsprites[BOOMSPRITE].y = YOFFSCREEN; } else { - vsprites[6].name = SPRI_EXPLODE + (enemy_exploding += 4); // TODO + vsprites[BOOMSPRITE].name = NAME_EXPLODE + (enemy_exploding += 4); // TODO } } } @@ -590,21 +600,23 @@ void animate_player_explosion() { byte z = player_exploding; if (z <= 3) { if (z == 3) { - vsprites[7].y = YOFFSCREEN; + vsprites[PLYRSPRITE].y = YOFFSCREEN; } else { - vsprites[7].name = SPRI_EXPLODE + z*4; + vsprites[PLYRSPRITE].name = NAME_EXPLODE + z*4; } } } void hide_player_missile() { - missiles[7].ypos = YOFFSCREEN; + missiles[PLYRMISSILE].ypos = YOFFSCREEN; } void does_player_shoot_formation() { - byte mx = missiles[7].xpos + 8; - byte my = missiles[7].ypos; + byte mx = missiles[PLYRMISSILE].xpos + 4; + byte my = missiles[PLYRMISSILE].ypos; signed char row = (my - FORMATION_Y0) / FORMATION_YSPACE; + if (missiles[PLYRMISSILE].ypos == YOFFSCREEN) + return; if (row >= 0 && row < ENEMY_ROWS) { // ok if unsigned (in fact, must be due to range) byte xoffset = mx - FORMATION_X0 - formation_offset_x; @@ -624,9 +636,11 @@ void does_player_shoot_formation() { } void does_player_shoot_attacker() { - byte mx = missiles[7].xpos + 8; - byte my = missiles[7].ypos; + byte mx = missiles[PLYRMISSILE].xpos + 4; + byte my = missiles[PLYRMISSILE].ypos; byte i; + if (missiles[PLYRMISSILE].ypos == YOFFSCREEN) + return; for (i=0; ifindex && in_rect(mx, my, a->x >> 8, a->y >> 8, 16, 16)) { @@ -715,13 +729,31 @@ void set_sounds() { */ } -void wait_for_frame() { - ppu_wait_nmi(); +static char starx[32]; +static byte starofs; + +void init_stars() { + byte i; + for (i=0; iDTYEEMx4-15-Ebavd}Hx5t(XlP0EXkB9eyo%-Q`z^yv&;}9Ys8W~Ip@cwSwKs&WVV{=?88in zom5wibw+-k6sc^H${qq{$V@L%)>GM;9%UDJw7URwhHNmAQoMdG@GKcAOHC|GdWf8* z;N;15Q4Z?>+A=Fs zWf-ddfb0V%Nt-DBpbBlMZyDL5`kN6$IH@jeMz!;0p@V!ek^>L&q`)rCF90WB=ECu( zZb%0d=F0M@0)pBvX932@VN|V1x+!jkbdfBEQ$;ci1=o--<0Rcm-N8_N$;NzB%h6!H zX-SUsMO@R6+1FU6iIHM$lC~jcTbSq~^I+5{7RoaCN%^1`EQ6lGvmMu^Xr|>%6$MI9Z3%Gh{aVWmqccP_t2Prd*54 z2|{xXIU{9R&}LfKWghygCF5W?PnHKgMjK-}>W%(!5E{iY0okuB=F1?|Jwqn2zAX1? zM9@klfX9~KhDaqzYE-uj{7O~LV<XOlQiX;2PJ)T?D~IxeW7f%QKd= zmmiX92f03SOt~FVT#oDybOa8Z#o&0#y&g`Tg%fxPH_PPVY4t|w)2!k0JJwinry3Fd zt-Mp++*Nn1vHDImBK%u>r@Fc8?pR~}oodj(js7h5o(*De^sjioV)K$1j$0V6fH*d9 zkPe!cbWc3kayQ8I+>Sd`&E0vY3cK!5A;P&mcc_}X z_f8e|-I)Sz(k}=1NW6gImiIEB%4hM!C`07qun@PH49Vnp2puqx$^+p!O72`1+(3|pTJfcCXsiWwqyz?G%gL8FS=@Gg|m(}un;O3U?#>;Ij;Y29!F3md; z$~%JxK#q*(!xJ9er+MRX(PUfkGFSDEh6dHabLS{u@+4l?La$K%9;oqIZOPxs*%T@T zj}Ndm;n|iW3!``oIi~d_SD!rjKu3U#PCt~FAt_PPDX3_$P~nBtV{#v6X^%6EK7hH@=~l0xu_J3_g>|wnba_;Ipq0kTcqrt^?ogEi+1;V|T-NITC@>R@SAN9G z9>nY0nDWvV;YBTabC`x`7QkMS{LwP|Ptb1yWvHm zEQQWkIgP$HPgV!lw3fIU{$$8nzDuS%sT_A$NKvXnX@M0eQ(RJ>3I*jAYk3nx{s!eu zL`jJ<9wo)2W2q5?`weKe)jD`nLskYu#R}xFgk+A43Ec;RYkdrce@`8ibiFjDL=8Wu zfLBB220<(1z`$GtEk{N~NsT}Y#XcZCHBv*O?ju9gg9EmDrUnjxlOuDZq~@ZB#>U7v zI9(v`@e%;!$l_3-0yh_%LN+U83Ts~nk${+15;nZbon zjM^khp@yJV&<4Ssu$K0)wrGh&S*f*H5V9HMFHoDX#E!TXr!lvsA-W^poR`9Ukz9j7 zkvvD(1fPoJwt6`V^kpF?$`#m+lTP5rNe{)oC@)SfD}ONh`cv^z1XhNOkGd|$!*-5z z4FxQ4s4D{Y)IM1ZT~}^IT~#+=J42R7i7!_VZotr3IRf{GSaQnnc6C!HI&Q*Dz8u99 zhOg?Cn6XPZtFa3j`Lc%Z@OaltL*VjciOrlPu$V6+nS&r)hk-o#fEgcvg9(W_$j_12 zg4g!f`1b84Qd- zpoZa{N!#iGax$cMRQ-EHCsW3hyb?#;4#yy9m=3xM)jT<=6+DRwW=UOIDWnx%medH% z1{K0qo=h{W*ff-tB^OYy4B5^G3d;r$^X)K&mrsYXtD%QTDPfJ_7?$?~WNRN&fj zwk(=y8tmuEzzBy1!Uw#`h8noHI@~ql5!MwI$(Q~ZM6hSXuxFow3q|rMVJWon#tcRc zsj64_WZq+{vg!X7wD7;sXhufEwG7FHYi#vgRKJTHfip(2P;xkV7jE?&7;G;m5UXL9 z>_HicQl9bLg!>d`q7N|^sLePn{UCfUlIt*8Bp2ark?ezdf&7729w1SUQca{g*cnn3 z>MOyRtOyD@ay7&YhBsHiTPFKLx1NBv4@F^O4u#xM%#j_a3-2sDv?*7jex49>q)c#Q zF?w?^gZ6f1ma5-^1J{I@C@1)66Il=K47nM)Rs)}IA}%?S9lApY%L-;O539W+pA$6)}*YH%h)#zkE-<4}`4*%;CA8^Ott1ANwm z%>-3CfC}WxL6lV>ZQ+AaER+sW9WN-d1L~J2*CM7|u7Q&;9bmmcW&n+1q5LMYpg{RI ztn-{GtAPh|H0HN}z5sQ)Astc6kaJPjWf0GE@UcLK08cCC$o}a)BITY$n!3)5lpw+u+ z*61h;qqXiQ(I3hP@iqAi>vJq>ba@Ot^;oeC)cAG}=?A8}^9{ww0IkCM&;=6=?bgFw zyo_=1>Khd=b{?u z90V{r30*>gBa2y=84L9dBMy5 zmOb8&m)1J8Y8oWAp(0&nKg^U|+No+}Ka3Pgy(lA^QI8k=C=_lK3#A7iizUjI&Le=w zhS?HTtu1gKw>Y3tTrTILo##ypJiZnjiHhD4l$ImgqAs&-XcSjw<0ctVwpy5toC4X3 z20W^mC`aH87RN%@c5v;_)FAb@zpvjPn(=Z;FT6{tIX!yqMZ+*1KH)_!T3@5QmjgIU z+CU&rMtv`^qd1>|R!Cxe=S089s^vLo5j?bjcxV9&rCW4Y&{Db~ju;d~#pJ5ie5Yy> zm&-rCU%h{j-yrfH-GG+fh~&J%*shMQo5prEVpAY1P_?6qiIRs1jh4UZDCh!ib7KTA z?x^8?mF4Gp<L^O9nbY(e<<+j1N}7RVQt93te%0`{oy7+e6EWzs`iH##f0+a?Eq_){CxK=EOQ8_Fk0(0bqw(NIgHHIh9GJR#86Q>=w0y@2g6ra=^fbYvq z6XakY1afY|+Ak%=jg(G-Uw!4BfOW5my~8Kfd4!>_+z81A`Zt1kiJH96&4c~7B?lJc z)axS@YS61?P>7dt!L&(p)_fd_j+abFUkkn_ zClfMB(m&M60%!W;8HTD2Kvts6LJ{$DJ_w&0IgiSW#Q=)@GXY;sodG{l)@ki}N7b%3 zY-GyZlG{pzpL0>;MENOeF}Wlg6B>BeBY;Q6zR@|_tNJ3xm8&Ip)IdjbuEGtBY(i}j zylX8&Ti|71qcyzb?h;YXaO7u7R>_?`!dez$F$9A-)GALV;uewaq%s>c$EDpk-m5HU zQRXB$3ZZ+5IybyPRgS}EiOO+s@?|q`h+e$xMga3c=vn(yWGz&>NGD(n(d@r1yHT@ZnF-COi6+*OODLv5 zuEH6-cB6VvU6(xGw5)h(54rZj=lbvDB!@8Ya}&zTli1Q~#L~-s)Ie@0XynQKh``JT zCtt3hkg@U;W*&~nJgk|;G>s~@M+jEQ0`;dcUkw2{k`*;%$)YS=>kp|KaywY?)o|QK z)e>bt?xtM)>=JUQD{Ll8S}2I?;C!NNN2%yw3|aUN#rqgK7-E$v{i1JPniX7l{ZMMW zY{0{@43P8x9iwlG5waaoa8MsuI+5C9JHH6Y!-#Uf~-DU^!Zf*KM>zL8)C} zqd-PN>yqL~860&x4}2dCd&M#m=n*xdM-Y=$a#2gV47?`9L@7jXK)ZcLjVq|LA(}Cc zOhi!`vNdY_u@x#gGBR`p1wCvehxFIw1aw{59VNaS;+Q{;8tkoQ{4K10Xz3TBl_Af5 zKm5-!`t$W7{!ek3550KlCyahSb+jnzNm>LR7GZR=$05`_LmrPTBiQTkILnw7{m|2# zAl9>j2L^gbj%?6d!+-K*1FRRzzj+%5#LF&MZ=oM>E_xU0xLkVa@Zmq{_JZv~xuG|g zaDIdbH_)$Y$nM}yT7wpMquwLs^nd8Dr;$@E*{F9Mk+-HiuyW*h)Y$Vl-0g}j3=yMT z76=Zn&0X3__M&?g2v)VwNr;IuSc5PoH1Oxm)RHlHgBoTDb~Qp^4T>5omqEu%TEy&e z8aS(DCX5tFe>F%o45yU`hxuTaIpIS-@|+9{{Ip1CRc#FG^VRaZYU); z24p(8*aYy5$dBShmSd14-{P2O15&+sBg06oBAj=SoM!-;E|M7ra8>}TskPQd#$F$A zkaClmF^DjX!Yi0N#0NFqkGCb?#Fvqt%st55@jjiy3ljbO7UUMODu}^)YAqRx-dJ6+ zp5lW*tVZA-@fc3Vk~E3+-cI9tSDIr5#Qj$;7Y$%>a;usJ!nEOg$8u2Mm!0Msdj+AFgLIaG(7q0Cc}c;*d|15vG8n^ULVcC| zj1SXXRP35!d$|Tjhs4VixYH4u!(o8~@WXsTsUU+w1HdUzE|TrgE0Az>e3=7FMUsQ? z7hq!-2RJ|uC{H2;@lsodM~@)ZQk&@xzB2IYXn`hYQZRm~N0CV|5HCA1&ldwEeGIe@ z!~jInI1WnlxX{Tyks-%)>F*fmF|ygkBRI(13<0bdV$hQoTB$5VrQ>BZ#)oBraIc0O zh2I&{1p~eG(4Lkq;Ea(eI_j}fv7iWtrl1m70>W!SiC8dLyb1moxnzRJejs~EeR?`V zR82gM;!UQ6dNU&Vq7XitURjfGN#I*yTR-v3_(lKgu z))D>`3%WCwn}BB6O9G=q9*|kcSS9VX8|(mmQ;1nI5rq}VUF;WkVM5fz%RwkSl_L1A z1dh(c5KWinHE?q<$i(>RNjA|O_U4=N7Ntgn2I0YM!3fp7=lgRI_dvrEjGJ^Od;+&j zx$(k&YR5|++`)cVtVP5Ed5gddCvOo?g2bw=Cno41pOW3iiA(q8Ou)gWRLq;&cgdr2 zN`83E6yp1VB7cF`*R(au?3?~Btb>2>TDEh*If?b*)y}_i-5lTiSVkC0bBUIQ04tzdHG(z8=|~ss{4o}Lu#;cex;mCuCfLx3mZUSY>_LySinH#VO$R0H52d# zDDOUHS^LKkxVmG@IMHx*k0$m^#(M|oXM!0W3#OL>U_tBvIAaE!G|R%4_G#1-jB*c^@cmkR9;4DUVZo*flNY zf_sut?y6jD?FP5IBYharF3MZ0JY0IpLkpmVu!9D2`>=3^i@V*9oz_wnPh9so07?glO-F)bnvyrPs!vX487Db zwKv)+VqA6LxX5uj;Bc4UPJ_e_dCgdBG%~^K->=P3uZs=lYGnp*h=WZDca?I3x5$2W z33sJ(gE!5^wrOiGa$q4}x%qmf-3W76D0ilEd%GpF%an^}9h@#_&d6vQSgOoE%DnEB zaF-}IOS$-Djk2vx?T=XL=E{5?@A9opovAAKp|TFRm?{7dqbG=cqP&kW5dqd0*rAL)>-pBkESb+~u zDsKvByTDV$yOq_~F|Uk-_YJhfhm<$aU=psiskTU6#WpIGIo6iOU@cS@h6`ZbwlN0^ z-U8)ex{$7k1TF|*6}-91!{#CI=J=TX1#gb>I7w;A zG20Z`x4qWpVRaa58DM^h34AonY?b5WIUaGI$#l-Z;v*{er7~ywSTum(EEVMJyCvB4 zHO@Z|!N1K^?z_tE>YA?(lZi_lK0dF^%2*=;Yr3)?Q`SY1FIt-qG{!$vPH#Nf5W5dF zcI5+OK33wuQcoOZ9rmyQ*4iYf;%U9Tt@g3536?5i(++$)=U|Z(ELFr?8dz6ttV*^v z9|lc`ePH0t@UfB(o*KjC1z6o}EVZ{bjnvqu$~y020|Z!VEKynGY_r4}hicYS)oRN8 zT0R0}npU!ka_~sZMVa-2GHV3Z@TP-0)zboAQ`R=@34pitrl{((%FA%D_XRvH^ry-i zVcTtG2)2f_HjR~ix3aIg*x}RKB&k71S=(U{l}J+O;*|AQY(N4>^=|0BP~Y8_F|4o{At0w1gGUCJ7WxmrZyW7Xr1F2u}}s;$i@%ITw=LxLT9 ztxcvV?@!9xW@E1-`p{&pWhLchh}i#0CSQuxi=P*6OL)`tj2}Z zHn53p!QifTv9q_esWMR|7c1`t?2v}?1Z8377GfzeW~tqc<&0M@M{a0+gV9@S^KP#4 zunP^mjvn@*LvCEa(=PW3=0G7fR$2d6u~oh~Yp+8<-yNe|ekg_YSQ{Tpfj3%t8G4Jx zCiiKG#Ji)Ehqo`tjd$=-7I-6-_qEDRckt;J3eHg;2b-1*^DyAV?cItPyp@jLtjOV; zl#Ji3hyfhlq(dV(D`E(TH{;M4&WaesITDQGtcYQpE1_|m6)}+W!Xr5=Vkn0TDKwU| zA_j9YQZkyeB8GFZQZk;iA_jDEQZk~mB8GHjBs8Y8A_jG3rDRlRMGWii3Xkioh=E>yIV@ecUHsz@1BSeo)s~~`$2e&XGIM1?v;{J zo)t07`(b#TXGIM3?hB9ftcaoB{Uu{PD`K$sfP_YSR>W}cM-n~Wvmyq34~9p4R>Y9+ zAt@R2SrLQ2hr^>jD`MF9V<{Q;SrG%jN2FxrXGIMC9+i@@pA|9qi_0a_75z$c_+3}{6R0)HZ482DtwIM6B`2>vuY60}N(f5)?4e{@)KnZcJM7OSb87)nX>RHd@pYX z$EsH8Sn}y$F!`ETU-3=*7rgv2Wo3c!B^ms7mlIje1pAnG)_J$J`M2Jt?@^P@@M$wR zTCS&@0Uo{)2TRM{0cG6UjC{#LOGm4}2oF~+j#r-v4_K|z5$m%O8nU)FX}t6Lse{xS zKE>bR+=Uxf3-bCYZ=!?oN}E8cmvZ7T8vvQ+lYS2&{T7zq7FIcI&7 zZZbTGHKAA~W%hI-)+rEsMmeV(%zi=W6AHyED*-ZH1u^$SUrhD)FxN(&`f#@jW!RXL zgI*HFf*pDz97doqhwK~h(rs4|t0C?|p{?cmSUlyLbJ#hGoW#-`eRTZJ9PsBbBcU`y z8+@wmw6i<7zqxIY`9X;}8Ra|UoQ=*k_bBEAt-qBj=`!3-KW2kj?q9QeIgihBZ}@#E z^w&}$PKU_*m?pLUQp(iF@dV?|^xF6X-MwZzc9lco&!rOj)Ewh_o&5}dww-DUovHNd z{Za`Xl3+dw-1kbkTEhXRY?iy-nQZzw9iOiln0~3ENEl&eC)^TrQ zmr@UR7WNL|a%)gh1SgMwHP*@X2AEVC<4!Q|@AOCcQ|;fKa>wJVidAk7Heem|*L!EY zUf5lF&b{SLayt3TosI5ZFWbv9_wP6LdiYzsbLNP<4O`}Bn*R25cdtFl%yGJTSLGiK z-dJs~!^Wzu?rygTE2k*EK1=7xE=5scW6XbDy?fvdidyJXlj&O(AbM3|6bQ-Bc zA?^z0RJz&k6_Z(;Os=|flKt+Bn5C<=0AHFcx5s*E-eM{Ip}9Mq)d@;&ALgQg>46=^V7^6Jev`%JgmN4G|NM8d--p6) zQdqw{#{xw8ZC;Au-*(^oyVfhFcy)^F1%gEjzu38ePx5}W7ax30WGJdJSFaSTYnZZ& z=y_H0*z>vIQD(B+*S%_nds+TO`?!zoH}mboHl*I5l->ofHsZXT=@&US$*)4bULjaG zaW=_9Ns%((S0-P3vV0q}%5-%8e%0CMWt%-%GDr4r(;Y6kU;<{QvjbZUtlunzFjmhW zp7B4{@IQxXqrcFOT##`@KLq%&Om=MQ4rqp^Njf$3A&x5(6MDtX@1RTAsf zdzps;K7KR7Sg-i;NToT?;MZjE`vw0~?+E(K{}jOze!4x&Z@tY)+J-0AI(Mam?J~xC z*<%UCUb%F6eK^)r+SsZ7A-DPhe>e6%b+Ws-*ivMymt0B>^}Pv>d)q(bEc3Cq+gL9; zWaG!2j8(~22|WFgWOmz2)Q|)c>t4;#(Lgj@~r3QN})H` z@8h?(`#ab(V=R2Nh8)}l#Cn#OwiMv*jj68 z{X4m&Mjf)b{p-4^IUtk3Vrqn^~c1LH^qOLryhns3TACkzt*{*;hrUr!6dSl+QZbl zOYRU&kHdH1s6T#$1z#qitm`qvwOZn0Cs!@ZcK^y6Jg`pdm*xMR_8vK?{_pV0z^v6* z6O%o>eju;n5G~_^dsS;S(8X&k*zf(5_|!x6qq|wD*3$i>hUx3}Z7q2iRu56W>ZQ3I z)sHR?UcMnSk-p+Q-2M|!>2`lLQS2>JvFT1PJ@<9+3WI{4uPt^=*==Sg?r;aq5mRJN znPPL^Trti|+_P9WwXAH_Jn7;+3gxe~M{DkM404!0X4hd2hHI^goMU?K z; zu#X+G|E9ovIPM>ea^02$LJ^J5|fYpo*9ffb=MPrrN<BD0>Xu|S?jgj*{bDs^k0B4 zBHvJ^zg?4_{f$xn5#Ca9dgcSVH56;q7T=P=d10K^?~K!wuEs;&vWheWyFHd(>F!@MiXo$H-co88@ynasBNek1o?R%U+}OB&$LbBa{C zr$0~AlbzL?&hS@hdVy1xrQ=Bh{2dKcz`ktIbJWaL=ijXV6?u`TRh&3{=`*HWjdH*fz1wPx;k{-!-NFVsiv*A z#|Zbg(3J9+a>41fpVH1e%~|3uR12qUOyj}Rtt!!Enl@M)@0beha|5$eN<*W`{QL7c8iky+`HxVZcl` zSE^WIks8_QPSuvmbrxzFv+QbOJN8twz^pRan$^{ruWl^%`fBWtIEPhqjr|hcSuI$o zKrsjL&O-AiRcV8R@AHrvtVN%9rz>}YGeukR4-3@NHD`@hG!yH_G}S3sVroKjo$ZOL zGRi5#3vY;CIOF{edLHHvQ12(ZzeHUnZnm1c;^3nSlv#=T!wkM8M&hDo^>r7k&vWd) zjIY&J-8$wLYVfbwzhLo;@nI!ZJ2+!C`?`x|BbZpAWi4~7FmsA&P1*C<^3LX~g$X{K zeue80+*|S*{fWgSD?}&QzbA7qMkq|Kb>HP_3*ITgohFIAik~9%QXdaHD>aa-ycK%R z_f{zXw$mxN(`hQ(#Y`5=%&`ASGneFFEdS}@>hWcFy$ZE)&#KTy`yC4H<~Lew42|eu zrv^hXSdAt#zgULrBc-R}VwIZVyuqv;=({2S`h z5Enamkau2Fymfo+ye3F6-v8$gsN1Z~g+B#>RDlGC|VfI?Vx9`wc zq|9Yrb0&^y0}S*&W)KTB(Zk!R<#qA#%cy+gz#J>iDF(my2FG`*#~a<@TE=i^td@D& zIjZUP4%Uw0Lxwj*dvldswROcitJzzfXK8CGzGGltul+kV*Elo5`dz(t zs*vsMReo1LTiu@E-PUH@fmaWfGtWDu{%m(UXgb$hrMAE?Yw8n9)dM8o^LrAz`*C{2IviAoS&-aLH;bw zzU;hAsSzfbk=z|T%~fK!e^N`^=Z#RwW6pL>7kG!X+|~AUJx{l}P$!S>)7-7zM)j?` z+8E_yVFKpcI!je{9;S-u`Ap@Wv@xZRu(mVXwSJxaUTR~KhqZe;Q*-wU&_Md88y+@AFig4;Qf;(M%pi;TH;((gTwLKM%iDoRP1_J=2iE& zs@$?0FfUizFUP@-I;4)O{9-NXrn6pcF2WNH`e(U-i6Z8BSgt}DzaOc6<1JR4D+*w} zRG&dzrWR*A>$JFT-t*L6E?78)_8Ko;&*Qu%WFN!trjXso$yKM0+7;=)*{?#|yv};D zKS4=Nvoa4^_=>-3EQ`fQ#tvIFTZO2^*8_c=fD2_ZHlB~UsgJ{cHl?4q%Ah9 zwZjKO9q_?THYWW$V@|RwKDX+QpV{h(PtbegTZX>ave_RSb_QaeY%o@6hsrQ)iyVQS zb0cLGCJD!2x@8>pZH~vUMNY)S3SV1c4gu@7sLMfjqMqlu{q#J^#oI3Ug?39;`7~zD znC$2lYW#P4SVl#9rL$YB)Yto*$?o=I&0g-|R~%9AX1pFAzofPA@9)yQjowdCd88h9dkNgh4YO8;5jM*jryXsUi|&ciZX>222#V z*dC?IdH!+ruebj%*7h>D7$EzE-Cx}tTD{VX_xD48mYrGeb+y^xzaMy^WC<{nw6VIHlJgdBS+Ud2EHl?E zGE2=0v&O798x6KlL3pVO&2qY^(iyBX(cTaT+a+<{YwyzHGu^#C_a6}UsF7^*Ydxg7Oo!;b4){a7iyvJy?k15o9;rqC6%Ry;OUI+WPY@RK66fwEO zU9FWmYj@B}c6L&<%w5g|ZN8clH3qlcep==k?-^<@!4DMT&vkWui#=FPO?6kPsbYJu zx?4F***R{p)}f~E%tTI9qi&ea+o@+mllSx$olncwKvh(s9v78hpLxv;A3M* zR${eQ%CC9agdar*Ypohy?T**;9CxJlu1P+&5W-x2e1Huh>>7cSMJ~PwM{1o0WTCxL zxxGBR&%<6vgNbTLt+0ow3&Wg?>Oz{+M)^bSuNckhe7Y`Ii8&4)KG4iIqqWe<{y}wO zo13la5&nZLZh|)UOsvE*#idnijz;CC_c#meYjC56uXR`HDB+66W`KJ_%P4U0e`i?M zP>p$ch+A`&pXdCFx}!}WEpmd3kE|?ftTxz}yfyq3Gsh4ZVn0BKUn4!zJVAHo<0Xa3 zea;aTS!<8b7*`*rUQh6AP->qXP-8z~VgVlTRO#=G(8^5rrfY1D+gaj(Kg?dI`AhK1 z5AhT7JbV@lpRmB;_1ehKlN_VY&TxOl>@xi|m4|h4+TLb=Lfs;4!DF(gyI&YC=J&t(<2yYYY(1q|;H&a{UCVoo;$x&vnMzq;ZZSS*)3|^$wOfP?x)?l@_ zM?GHSVDAuAR=L<2i}OyWqo&8W_?`(KZ&pJeuT|x?K0aOnbEKv&dKjC)rN7`+1gCme zG$a|$*Yxay99E$o{%*Cq+Bu?*cXnT5F~iMK?R@>cOUmx&#?wcxc3BwsKw^RY1QXco zfy6m?pf=HOW7wFT^%+x_^B?=o33JJ$+7q;pkHpop;8v|`jufmy3Ggm9M*zKU_ z(e4=y!T}GzfQ0(I!ZLEqEoC0@u#FVysrJj%T_Z2>v_k$&W~RMZE#$isRd|-ST`k~! z5g}-Vy^A=#`zS?wn_RUs#h#!lbKQ6vnuA}WW%g1JA7`QL4O+pT9`?wynX?;!ceptHXd5o9Hf**d9&x>hhrkP_Fnk8nrS#8#t4Q7Sf zp6gszn{Avo5Lo#EmJiW6HEXG(+nI)HVyLrS&#RoSdhY4eqvUaQbdbkiLB#C32DZJq zt=v%_reI*R(x2g)9Ku@}`)aimEpI3GkI>24UN;pkcJWSxbbTNe? zzV`1Fzq1xN5qmkPxPdP)@c$RxH2b($kK8nSp=wQYUZvS}vPthP-?AaUBIg`lbE)>r zG>z*u{AeQnjMI4CaA&Dc3)~EK{MU@nU1!wbW@n-1EqC!L9tt{z9Sb}!vmd9~d3cMa z*;h`g)E@VJW@gy4)#v$m{z7Q399P}0?p$Rr^g3$#fP>AH5WnWG(XtjfZ?k*NFtg1( zv)C*%`DU#tFq_Q1kisSsnA(Fkb~^qD6SHK5*7AhjNHDmBtr7NR^<=+$Nh6!?oY3=a zyFklc=k?P3@oqOQvzN0&A8xp#y=bXR+HrTTF+N;6OvjtNiLI+P_KTKy7e2>Nl5UU zG;5OFw8@8Vi!WMz@`BT%d5eZFp|zXvS;HpH{BM$4Hvh0ytC&X3TYTNPVRFN}5)$fG zsTt@eB$N%M-uZL&goJWP)UNqLNggFNshJf@%dAnmO0|T9@}-Qr4QeGML` zU9EaTAdZqWrLrYifgmi^tzE53{VE|*^+VGtT$&w-$1zGZtJJAez3yEk>(qTK;f*S_ zeqT>hRo|`~k*fJl-MY2wzEkV1vW!EEh94(A*Q8k^)2fBjs%6s0K8{umzf5vkB)6?@RF1KS&NE(;MWN>=h&)Ef=n^y^fq!E&#^9XY9|4PDwdL!%KVWXra>K)T)k{96hxX;D<4i&uT|xZ8r9=yHjq>D zjkgl&)UR8H+&CR#_|f$0~L2 zDv56b5*0OzL1rqpZk1Y4uU@@cOhWU9pCvT^=%X^VYQ9soVbi7`Hf;2%Q@?u6ItWEI zhQfw-c8%(_{94uDs}FA-`1Ky)eY;-Ws&=({_5Hdv*q8ql!}Htky!Ey+>Q{M78E?E_ zzq*~`#M>zn@3u;A*fLo!OgLvMS2UF?m2K2CsbR}H4Vxwff?bR0IZ#Qh#`0Kj$>&1T6ut{>gubVY`F|Kh^a#EvYwqi^|ixyw7 zhGiQ!Y1N`>!>`ex%^H<2RZsY+VXNf3HT_vqa>ImHEn2b|Q~AXhHqLvs-+WVv_d(nf zE!L=MlNN5}R-ZO$QKnf^E8J_;HcEuYh@~I6{&B#7-GFG+ylHvOVM#&7%7r9DNz|D> zH=_~MIiNrMILwA(tg=6A*y_`O+v@99$w{BZs(q-m4n*aTkUj89BJefV))!k18ksfLZq z1mssOo1hs{oyG|*pjuX`WVGJLNiErYjT6uZl9RlImT0usd_7fsB{rc|QnJ#qftiMl zQA4%e;tMppQXe&G+BC#O3x>-3qFKwPNflIGg}!KkdwJ452_H4ZT|dwZSTPBoC4EK{ zUP9v}bc4GSK1PwOexu};O%uLs*z#_*63K~8K(jV#+Pu-HcPAhon%^jNk=S6wR&Lz9 zffg8}y`T!(yfTVIZ;s(vJF@0L>b~#$M5D2qUn{v)BfCk<&tuqi_(U?5Unmdy4ej^! z8-Ca{sm6EGZ^s5516|v$ToISjOLpZ-70XsejO!rsb(*(K4kv0fZ;p=IxOuZAmvOJC zSV?`Xg=UYVv$dKh*Gu}m49T~fxBLdQ=2wG~GXI#=GAuwP2$WSl(6nzVzx*8!zgvTf z-^s6Jr`Yk|;l22s^h@7Kf47WRzLWpzchaxfDHV9{dCcKM)(ak|_8ax;IecEk{JDDF z+I6bDRo$u8phgYv?dnykRj=!Zh7f+eDmClWs9w+iWA&=_YuBx3&Gj9;0Xi6dIoPV_ z*f<<)V8b}u@o~g}j>CbK5=?Ph4i=l8@;EAhcMpzxaomUW{Wu=L@gt-k!ues_avm*% zU2@Kco+FJs7l((##}N}_`6$!J;LAsOzJtTHEk6cF864$s+>Haa{rhl+P5&VrKL#C- z^W!)_iR0&>pT_YF=;vYM1<;jnei7%F!FvtI>!9&Hv0oYdDxj<4Tn*D zM{OK+aWug39*)1@_y95qkZFjc5z-&wXo90Dj^;R8f}f1zOB}6nd;{LUaQ+rYDl3;x z$RM;Ov?FvNWMfe1cOlh{(1Xy6(1(C8^(}t@0rR1jKbX`|Qo~4%pzbJAV+iAzoIq+4 z0UNC?e=1=*GiDLy5*7fs8`R>*(1^B$Xj_Q3g=kxdwskL#`*A#o1Ch4kaXf+Jr#PO% zfhb$gm&UvVVh_z*`Dj!$rW zilZ5h&v7K<_zDN2X#ERE3LQ=-WD?pDIube)x)FL3`VjgP1`&o57$a*GVJu-hVG>~q zfsw(ds{lsE(#V*Fcp=a^u_XwewT!TWu#&KvZzpR=ts@jLxq;Ls!WP0d!VbbN!XAPy zvtW9}vJNnLh@};hDkAR~;W(2gnQ?~HS@O;?d6CJ>OkN>%jc|h*Shh!SaIIRHA-1eE zLOL5Y6T4EaEJAxiM?xn8x2sy+cy&LG;}?+cPEJokZ))}wVSYqu$Qop8Cak}Yzc=6N60IpE>_Vk3-4_RFyR#8G~o=Pm?Gy0 z_;$&%E>Z0&sq3U}kxH=vX*QA>q}meN5jv39iO`kMgS=j(u-b@llEQz$fN+u;M#y1u z6sfU<@k~x6)ejSY)?`xC2s4>6o76nQLM9iJT1Locauum*R9j1`fUt=fTS#pu>|$~c zsr`gQOdcUsK(!)LCkUsRQB3MQ;S!TqNL?q~VloBuh7eXK@v@)JWG0~<9urmvQk@80 zne0xg7XhEXGztmJ(Jl zxsucx!g?k*keW-i&7`&wb~0l(seJ@|a)Mq$>L}qjlP5`SqguMt6n%rdvxM`6i-gOB ztAy(m#t*F^F1&}P6Ea;Svq*Iyl})M(scxitlIl&WAE^O^L4+X$d|iW(5JnP4Qx5B~ zhzkL8

S|n*wmX5%MTEg)oiD>7-^7W)tQT<`WhY7891z=n4ww6IPP9ny{9D1uJw5 zQX2{QnHg-XBy1<(w`CAN!d}9D3LhYKh;W3Ki%4Oc1$qgoQ{)wsI!E4lQWpuAnQ@K0 z>rCDx+$Lbf7*`n~-GfM`2VNGb4y3XPotcaEBXl!n^dPSnslKH869zJO5P4YELSRYZ zdj?!|gfWD1;ZmeJ^PQu%~cOyVOX1d)Jw9R!gS z)+%r{lG;MpM)TMWg-eovO&Yi^3458lpVR@uLBb)zVZsqYAw`M^#|bA1rwPS`a}>d+ z0l0lJd5Lg^$*U~#29vj#yv<~qk7OH+=d27L$t)(@lgcKAnL$LCR5wBoLN7ueW?(Nq z`Yw|L2!og$Oll}$I3b5HiW#FxjV0tVIiA!+LLQToNlhh8Ctx=-!cLgYFn?YTpx1F396 zXF^v(cLKf&K*R~Xne0pGPZ&rTOu(8mIyI>ggpmX+_@QT$8b=sUm`KRu*lsGR>4cet z*#vA2ME54OfPlSyh%>3B)L6k}K9j2m*Z_>~O$rOf2sWvWgw2Glgzbc#gx!R_g#8pg zKP@O2sR4vROb#VAoYY8Cqe+dU(Of1ckeW!CM93p=3Sk;y24NOq4s+*{ znonv0VIg4=VKFn75|$J439ATen7fwLdcp=4zM0fk!geNik=jFQKdFO+!-PUY5#c!D zB;honm~f78fpCdsTqbpuaGj=ZkxIdfoRvmsL&%InMmtg+2-$?rgsz0{gr0=nguaCS zgn`^QGKesk$)SYdG&PdcXj0=yjVDZGax#UdFgcAdgD{J{*`($Y<`WhY788~dmJ{*` zt7v5{HP(^ZK-f&!M&5Q(yC}DZ$-RVqg@hs|j}eYDd6ICN$up$Rk~&A~ z0^t(j3VByaT_<&e)Gb0v89-VY@Y4Anl}TtvUI#)pGdhvil~gxUJxTRqZXZHFCi{~b zNEl2QN*KEMia&oa+xun)I>rajZP&sof$KjoXzB1Cg(A^kg$ZwrOa4P$S15K ztRbu;6c9ENHdA98HMTRklgT}#_K~-r$wN#YVX}~Ll*wbHjx+ZZsng^Y6V8!$k#L0> zS4rI<+-5SREU0wu!)#L)!kL6D@;Z>pCUhorC9enNdNSFY(3jAkFpw~qBEu*$oXH$g zBT0=Wj3wj}CJ-hOCKIL-rc-woHD)t8moT5aMWmLHT23mTu!^vTu#Ql`+)bpm5VkS7 zlhkg)Uc!FDLBe5{afDFFWD%)jq)re{F?pJBhE~pzI?s%Yq%M`Umy2~(@rL4U#k9M~ z&rr;|tHN5b`Y4W8oT-?vxLvVG@rq(rIh9u&tvHhyYZ?6KAco)oQ1Nn>V?ASeRt3w) LdosS0^sN5}{Qu*n literal 57756 zcmc${2bdjKk@(wny8GVSeeWIHL>UYWaq$w?M1x^LWE;%x0!!F6yNF=GAe5@mp$+C!1H>3&GW{-#q&P@2hW@T0nZDn zJa5~}Ja5+u4=&Jve>u+=2(Nsd=Q-!M?ABxB-Y|66pZL`?kGep zX41?4tdEkP9Tt6_-zo81pZ2`IzIX67;%Z*zxe4`hG3WVR;WIirA^@b>n?+dB(yj}_kDUwHda;q9Y^x0Z#sPZ!>vEWABkc>9;a z+rJjxzEODlX5p<>;q7~cw;vYXeo}b*Md9t&g}2s)x91CQC55;4g}07{w=RXZ9)-6) zg|`8Pw;_eM5rwxgg}3pAw@HP!X@$3$g}1qdw}pkbrG>YZg}3U$+lInhP2p{O;q8UO z+rGlvp~Bm-!dqS8?M&gVzVLRr@OHiMcDvzCT1mgylTsO)kDiovL7UfO;T|DR%H;V- z?&I2M8<6KcH^RyAB2TJhP!P2hpeG&WP)?bY7Qv*EOPkPGl^X5Mywcu;ZAV#|RoZRY zrnD)e-9}86tTetW;ae)Tep4!K#vV9N#>#3Jwe^6SVtgDm=E}S0)|SXglGn@SlqY{@ zuv$uZZy{R|^jV0TvP}eS7kK_q-^nHPQ6;0@eU_uiq*}_zwuNl5^wrJMC&E{2de6yG z3Rxu=)A!R~Ol$i6A@Sm5402S-?k4 z%57clB@6FfOaZqLdIZHJADZIcx51Ti&o zfYQIwV1@J!nsK%~dpFo`TcoOz_2k`9J-n;^O`t`zke$G1Wr=H=OHv0*Tw=cqp{SBo zl&UfPDoRr=?@i3NBML;b7)E3Cax$!zrJ2M!XHk`PG8fCMlimnkC-W#}opi>yo|e;z zb^aX^^RDRzm~cPR*IlrFT9(9Sz(%r!wpb<|(^|6~VcbeKz~)K0iTcWA3GhkTPxb?( zCo(=MgP^aFSq-+?!Zbb$i+GfV5Azz?L2}>V({ea%8TEC@ayU&LI5|ZV>-vh8vIfo- zGAKk#lrn961|e>ZETKrg!KdX=))@R;863)bZj>ioi7u0IYAl6><8tu+xUARFK2HN*36(zhtBg^ZfF zu~@*Q<^OBS75`hxZs}szHM3s1uM)p&W@@UBcIx&vD>Oq;SsKD7jlFNhBqptX$tl*n z)D%tRTl-SePFnYpQ>=ffDVoT)@ujAnwCN?M*!)scsClj?p{l*Ru+BaIBy!ES1+J-D*Ph8tdwH z#z{|`3}LhAmg;2^@H zuT~D|08Ba^xjjOPTdxx%a11Bl)*FvI&2V=ZrPik8CYq^{eJ~0Xs(#KPX{lV(S!032 zH3q|CS(Y;mJWmhJyC*-C?npjfmND%7PD{V~4SSPRwZ(E3kxJ!!vk6{On)66Lf@~>hl}w24PaY;jOdA*l-=lMc4vf*& z@;RpUaEg7M=_%=T^RrG97a8iJtQ4dOgl9tOHM5vKAh_lyV zskD=%W)e2-&{MIjayltqMZ!nlAibE~Rmu*l^l8nAr!ikp4b6mgt#neoP{m1!JE4(Q zQXeAx1G1E+LQxLUD=U2$;_74y)80c&I&Ahc0QT2KVVPWN#^{nU>V#aCG8bhnl7q=K ztQ{?jcdgek4edb30*{bVok-?$tQkDsm1<_=MB2y_E15}yE|u~In@U74M~YT5gqTX% zj#?MV*rcsmj$9JVB&{+cWG%MQ7 zYb&`z4i&PgStqwCAvk9Q`_U$=^oH&`=>==asg)c{8rB5n#S`wytFcMe#w)0nI_ZK~ zbutlStCQ(uUMJV6$QoIOIM)oel23aQ%NDYaWj}?DD_ID2rPL(-)>Q&k zGAgT^7^BFcTIM$_cb34QO0L?L#Z`o>mN^U%y3QYkz*X`^P4Y#>w_{LI9qch)XEGXb zM!B%((AlbBCQ|DP0oP)pO3I9nA_%WHkEj zD79w1TU2G*5owZ!t)49?u1Xf?ly)(UJIYAQvP9cJfi@YcODIg0EHo`FMC3~8iT0|b zXOnenPo!U4B1f@;dg+MT-)yj27L!p6Ig2iym6N*ID=<$M<|lPfL9NqCQzbo`Y_;?t zWwi`Jr!Axh89pmVnk~2!;f}B!t5x+?O@5_`L{}(JwUp~hn;JNaU{!KASplgYc-Q#; z%%pXrrUc#9Nk_7*lY!{2P6pfi1KQGi7g=93S^JvaRCtAaFR9}1+0M)ztM=)1nOg1B zN!>$g$lV#Nm2JA~P^kHB(3DFTDt(kEuhPoyjQ%TSxsJ>AQm0!_lxIIBu9JHZ*U3r~ zZWk=;WITGRk*>U7GuTQt($7o~nPM$$wC=^U3mDI|jHAs~?=*BI$pq#ONmoftCZS7k zHPmXo+#u$*!3ueQ(!;!8@t4q4${_3YhW;fPLRi&?Q|51*npVO)7t)HH_QZ9Tn^`Dbj6HSIat-StI4>-5IQva#dJ?wjo2x zT_x?BOp)4AkZL(ct<}h0@^A)grBAaan56E5B38*ao3c$r_@)+o9jVg_ZF`}uRqh5Y zR6&MBog1KIf=RyT3|7g=CT(aWdDP1(4D3OJ)zSkc*2pOM(d_|irLUStfomcghaZ^a z5O`O};%0NiB-h1ETy)!`8gA=kAhya>j8fk;STE;DxyN8Dse@Ok^lLUz>Sv8$sHH1| zN0BIGj^1pmvYv5iZM|Hl8m37{l$|kHDpwn(C&@Jbs!j;$Zz*f33~$C^IC`m*YK`m&(ot%Sm|e)cG2_=*U|tof?L!BvmJRf?~Ot)s4`L zW^?NshPPy8vL0NyEYPiDktcLKTiPIYl76Yx>G*~QmEguBX@zuXXq?Fy*MWIEo6XZv zVK0moz|~U6^xGS1 zF(Ka$+g5TbspX-F7t1`$b+_eu1;dG@9??qWVl$0hL}L|F*^oiPtP(?f^t`M@VWHGC zBd;+9-)@%oZOi+HF+bC+U}q4aOm@G>B5F6)P%K@F)G)drZmIOqgM-HQ@7aN*R0jjf@gLWoWEcPJ{o;98MEcBd5?ZTe-km z>D7GAsvQkDRnp~VMt>REYNQ>qJAD^|n>n>GNA>*434dcz2cQ>wt zl9C#S-RPB(7THc1Y$dEg(AS8D)|r^l2=XbDIZQm7l+e=8p}`i*F>8XyprQ|KK6lgJ z9-OAHW^8Jb-pXE0*E7PC2^6$SE>Ohgs=bix?nxV1*UI1*sl>sisL8}TQCKT?n~Q1L z+(pa^Y2R#S-kw6&$PY9jV6~iV&fSW467H*IOS5i$3uaIubDEjr9858k>o3CLy2-Z_ zLpUJ{Tgi7Ye_vK3QKg(k{fp#y%BEg#(@mk{&{WDXDxp}aIDg6kb$T{7S^lz!=4^@F zFdK~g0fVnM_%4I3WFPe7Wf84x6l+u+HbgG!M$oHT%02DrJz1nN6q%THy)nJ`e>#ElCX- z4pZo(1}o%>w)MYYd4(3gN_N{ZR`aN2C9oTj>SZrBl`^x+`G{y!=n$WTS+Ozl~RV@XUT$wJ~t`Gg2Wnj5YpmGY`Q@dmrIxCg4 zjXgw@BxjMSl~hxVV!4;>dOWY?zekfUmSM@k7A5m|*HzLB4ZUR|& zHLxaSJnmQ>wxx?Hmf6Xkj&Yi8N?SuLdo~U8f`nfcF=evzMT)kQLbZ~;rj$*MJu zDG~HM$SOIOxL{a8j-jk-snD}j;(Js0Dmla`(Jp9X@rS6+YN521(v8fj=rK;HoRR!l#Iohn&jyBZV46A_csHRkw=+x>j3b6!P%H*Dn_06M_ z3b==O#WEwO6)?j@UDj-Zwv6<}^0>}TAJ;sVH_IdOuvl(+)Y+7>kcUMjdDJES`DeAz zgRGk>P&F}yL8k86bUd*rES9!O^Zc=HkGCb3X=U@_uu1B*sI*p=H6MnX$gm7O;Xsje z*8ip)PowFvGNIW5J~7$}W@tmGlh2m(2V6+YHg#9`h z1Wk>+P7MXX{yEJVKFzj&E+^ZJhe*~+p3!zah1X)4mT*2MGLR5T0CY8F~$p%N3oYqO(Sh}j%m8sn~5sH2U{>{03|fHa0)*%*52 ze(qDk$U;f(jiDs>#!!-bO)8;Ga&HVJxi^NA+;0X6Ws-YiD9QaMR`-DX!~bDWiXA;5 ze>>QNKKTLp+re8{?E~_+f_T?pf@07a^bH0ELxU-UX@ePqkwFe2NSig7Gx)$?!3U); zrvH$^ml=Gy!B-f3rNLJje6_(A1|K%~8iTJj_=rL8ui%4HP9OJ1gKskUW`l1r_*R2& zGx&D~-)`_xgMV-E9R}ZNFyYn|J|-h+;O{Z`UW4y5_f8$ooBhV*3Z9luzO6kz zqgy1MkZ%g6HIY2Z6buI$ptyo!r(kq9&FJRn0=GbsnARLNNk@3{HjfRUX~}ZI z>UkQ*Hch(GEq&8qEYqlKCUP&5%W`ZbmOCh>QZ~>~V_5?R_ua;m7UkGr7i^W^U?WuxrI4QrqEL%FO@YfLcWHWVku8%fz}$zbra%oSw#t| zq_&B**Q(nFDj$zj)pD46tde!i%o>^>@5F~9ODS8mj6x3T>wsDb)-y^EEU}(l$^`2< zq}7V`Tw_X(^&HnA*2DfOrt%vzp6zJ0M&?qGeG2`_G~V9C*GmWTb_T1Z5;>U(LQC6B z)~ZR{RGWTI`z2GVrJSh zj#H*qGLT#M4f@V=d0PBzruKst0a9l5*uA}e%llM*S{cFAORnU)8> zH_%d4B9mcOBdaikP@zRlgVCdZmIDoK^ByH{CAYCLoCjEHG^*W91&nSMT}BrbGMzP9 zAyy3+jK*$IV<69YP(3D{(2FxzBYh~5Z;;h#va|9JOtX2{GCoK$G;;>Ieu_e`Yo|xJ zJykXt75z78^f;2>Mz|kE&S`R;JW>ixi`~fUX}Owc>5}?+U8S$(REk~4v!t1<+JV(h zby0d;P9tuye9&~-A1598pzaC`!Vt0wwHLXeW%(?fk&%AENI$KlUx3rMMCiIkeMovE z1^#TwMyYX{OG$gkL}LYXqj1AR!IM8H@xZ+D;GYMcri-x=|^4AH3)`j+t0X6IB|sr7F=AatTcoOZP+*#-ux%=pplgS%q#? zB%HYWlb;g#oznJ6XpKo9wZ`v=3|2Z%Ug7zR=nAi)@p_q!1%wLy1K`$Ba#qiX@eYOl zB6`;iP?XBbW<#c@|G+^(A3KdAmddbZ-9*y!4MRx_-zhSLBGb;AjA2W#$Oq*(@<#?+ z$W&_axt20rTRu(TJdLJW7La+3tVN)_!5Y~@C8P~jOINC;N_Jw_?UJ#ackREHBhb^b zEKxyDO>!9-(fKfb*(dUn6yU*r%*eUlf?f~rX*%?P*YCPe&v@UJyjx9Ao# zKS%mE8EhflF^ZoCbf8GAlHMk}O4)`alj(COqrmaPmJ<2(PE6D!?XA7XuW9qd3}BDl zB;86OACulNa0*q@DJJQ%WM|4GU8c?aH{_?yTzfE7o~Jbo*G-XMF$&POCx41Ii;n8$ z9+mtigDqqjls`>V9h6BWy=9Vi*OFxz2&`f!VKsl0X-R%2=`_vncW4C59U$Ei3!P4) zZ9OLa$igX9NmpCSio`d?B(2c1i`F79s6_O!*O@6qC9+W&{#N9ks`}G{9V6#ZxVLD4 zETa9N#v=6ik3Jy%$?>TNWHO2wn zO*S~DVnbbj&j^Balj)ELG0BW@{Y9N!{~L8CTm2)cmtt9&%u_hMrY-8^>j4=^g%XjB z%SnW$c)e_}hz*J6EMkN1)4fY3B3H5ONGjhVc4*IrQC-t+*lQ^#w9~|Fx2b5ZrPQgy zFvd+7(Z+9!bf@g~QcIgkDYUuh1vN~+rSwoOQtg9P*+EOb@*s?1wb%GmOKGFp!CdyD z)Q#UocV@uF%BmO&Fq>71bW7Q!y&Ls%My1HKlnOOrD*l3oZcK($~pw<5Jp$sua~Jmrhh|wcv^lmp)DAuYITzO+Pv5wkA;{I!Bv95r@8mpa1@(>vp+ zX!2f4cG#`dmoO@o=W9Bh8QpARoTzIw^@;ld87yLMIhXpYmnjGmD)bM48%Y8$*8(oYjrShew1W9dw$tM28Ow!IxO46Act(B|IL{!US zhJ%Pq>1a~UV67Z^k#Y5i_Q-VPRPST5og_JfpXVGwrv+WW`wIQLl=qf+)MbZh@nZWF+H52`O1 ztd~)weuqN0_G8kUV%N(Fa(chP7Se%=u8@n38~WBPl44(^mwL{Zb6WQg!=1dQ*=^-!KA2`dE`+g!L&UGf=gXi3m|4r zePU0_TrJ&ruR;U&jkul?cKri0Q!=fVZDz77oAm!H(NfpvMflEEXZ*E@T`Y%^ManOA zx^M`Y%B2(RaW|$o&pjZU;8H2Gn9r~S(}&te6a>0#u$62|Hc|#Nybk@d$b2Li`bUvB z^C)5YrhR<}k?kywSeMV!M%ac8IeoSl>8~0t7pX_Xt>h*-#c~PL8ZQG7grn5tTOJdw zH%)soW!nrbA637I;SbfR0Hr&IkfqGi|GM8@O@XVVYm-P}0#L4T=(?3mW4f}4(p^FU^-@VQ$C;3l9{@LrP>rw%lMgEN7m=!$)!a;sna^2( zc-Dd81N3HHT~g_rn20PwlHV%9)E6njk@-fH6XNk!oHg-~H>HzN-V%DJuD83N6V!ZLQ=ni^jI7 zt%wGh)ON-)7qw%1SErdwYU{KuGGXnl`-GYXy(NKMvx}84vp8#KC1fx zg|;}Er-kUqG+HOSOoC79RHc*1Y)#4}cpRnD$!{gA0)!i3rTFz<>*?1dqgi%O)Y%P5 zSIN>B85)<;#q|(AC}*Mpv_!kKk0Fn4^sLlAp9%JK>m$p_a;c2Q@Nlee0^4BD z?-PZ443-)Epuy7yD-3?e;F}GeFgVrV?+rd_@L_{z3@$e~NJb;+Zw!9f;9~|KGI+`0 zE`tjVjyBlEV3LYyJsh4k_=Lf?8+^6FjO?c2+%S0B;C_Q!4B~4>?0kb$4OSQ&Vz9Tt z&Ia2VeBR)14F1gE4`mVc{2hbeH28IcUpDwfgHIX!jKNPB{6~XN82q5Y_ZfW5;JXaI z!yxt^;3jE{{1pcOZ15R_ zA2#@~!CM9o7+hhn(qJ!xe=zucgI_lIaf9zN_=t=}{+z)(2G1EhY;e25YJ+@r2jz5w z;|&fs*w0{BgQW)lWbn5Je<6JFBhMN9uEGB__ziER zAcv+NdkrYa)7Sp@U%4wqv3~~3VF`N&EsEKA_5tG+)Mf!gQ^iiM<$0Tt0jzTbM<^H- z5$urylxplGO))Z0#LNJ&F#{-Z;7$o(O&YLRSxwFs`*OxF&dN+>&`;BLU{}xc_zYI1 zY0c|k-+NHpgP#18R5A{K#^6^Bz6QugY)p2Ju4IsIMbqgD&m z!%S)*_T;Vq3&7mZ8{&JbMI0YLww5`%S$9wRQsaZW3uTm?P-(D3U!W9hr~bQfRnc^l}f%KKi0t3f+X3GE}DyuWl*dAoOwROX9Am z^xxshqYvwd3HYw)kp`R@@w=kOvBX|P<@GV2&oELWH)bRqF+ohb0U zM@Azal-W9mA$4E+XKv5I-fCn%(%m%JQKrGQMrKmdYX-}uKMDJCtj-iomuc6LR6qJ# zsEZ5FmzB2c3*?U)3}vrQfxVPmGqSYQ!HFAtfHg7(SgTOo|Ef_8UY>!iJ0I3MKTrJ> zOULBkhp(zxo00&PCL68)q%^%O)fhfxVk--ipaT53Z3f7|DI;|C+cvFNJ&mADrE)LU zk4EpoW`gWXb3&a&?n`Ur9-MgFN*i4l@UFaC#%=S`67jg`3q9akXii>@_b?pQSu1rs zoQmMMaT{#ena~MayP!?-h4d<_wnFCVq#j(dj3_Xu^zU`JU_4cEwPwW40j?9vs>0Hk=dL@t}4TbcUmXVzN@v7hWr ztHr9Z9biVub3|kO&!HHZ;G(BAFoBo~c}tS;Et>9HvPStT&5(CZ#|lbG$$W(DM1dOE ziHOunlE)WxCDDr#Ot>Q*eO1U$l5!?4*gsLs0Jc1=>`gqy2k0u^lX*0ku3@pv(} zlWLwmcNCGw)6y;-x1}U$?G{*eYPaxKUfI!0iA${F$LLt*7RBw-G9lSs$AZynzDRy2 zU2?%{x7W>yI;Q1~GRlADy?9S%P;fK9GU!*dDSIL}Dtk5f;+f3MqKWbEN2eF(7G}OT zJ-tob8)SG&t~&R6ea=m}*Xi>}+C9S4U3E2qdr*!BZbWWh+C5NsE0XIzmgw^O9Fui9 zeYQ)xEYDQi)WvL%OqZf#na9!Gbw3;&t#VbV+3}2=%P3*X$LETh%qFMT=C|fyxG{@y zf}3QxFHnAJGcVHua1#ypS;LLMb3t*HhWmr1{X6Mf1ZskzK4+*^=>#|4aJXW?E|5NH z$i^9p&x=6aatUs%;U2Pnl(o)Um88OO?=yBc(+O@<9)OL4q4?xV+&GHqebST*`3E z(1VgKH+zm#cNP=gHhu%W&Ms)x9NhWdt{eScgQ#b5>)X0kRA zgf~=wL$T4PC(4UrIQ26OAM1cxn3ge`VPC^>nIE{7VS?*pxH*QK9LP`yU2ns29|3e7 zvI(x2;r?K_zFGMQWIYY_q@jLgm>z~vpIAQpP6s!l4q?}DVg}mo7Q>|s#B_IZLp9aS zaK{Ws%3C40u7=a$*OMh-g6m?qpBZj^D#5YZM9bea92&B;EMvia!f-Wt>6C&WD`IdT zGu+-xg2R%)eaLVX*#yTb8{B&hw-oONP0K3={N8lYYLyhUbG+O&#yq?o;hqFTcOp!W_(Lcqm zmv5T;sUmf>^W^QWV{9_~L~%MMdUDEl=Yxr<5^-tEe{M$RYOz!8=pko10^|JF?sdKC zXuLMhm}6F5hFt=1y$ttp!_D>Cy#UwKaPKhOq^vvws)wN>Lv_xxV*{?c;n?9rf~gt# zD5!3R;wnv0>oaV9fh#ebZYFuMkv+pKI2>n?go6Tbrz09R_bV#Bp5 z;+zFsd&6xpZZ{pLHQ?5p)x6p0{)LkrQ0+BH%2owR_(kqv~V0 zO^$=U)~y{E8u`1Rio;G>m!^a3U4^Q?kp_71%%rcflgQXry#%?L&y`4fic0 zE-&&gguQWOP~!6z@iim5z8SaF`-9?dS4f!@h?qyJ;+B>*2hJ4tNH5_k; ziac#d^?dPUe~kBwB2O9e?+rOWjen0KPa2Z1)+g2uDfkcSP~Bab_iQXV%Xmn1?tJdfKHr9Wmkbw}cRu2k@asrjYZKE~px#c<0e zF;@aSwV*y?ICXTwtvw7rI5+Nw_mlEIY%z%x$9x>Z6nV&yhOH)q3_A@|$Ko$Hgs*PGYFXxNTR{b1fURIr%3=CE2iG1XU8?Kik@EaEU#&Q2G9EH zC*!;=?l%_e)bGc6HSX6MWOjiAk@GgYUup1eR=t0mx5@odgWV%_XL8;~hAM)U8TE^D z-Ujyz4fao|Q5$(D8zyaiUf2Q*L{o4>QS$`xtwpVbG%c`IE`LocLVZ3ZV1=dEyAMGW@Uhs1fyU97=& z?0j>s?JaW|4fagAYXLqe&Rgozia3Nr4C`KRiA!m4K&ZYg&Rgt44X%#NY1&)l0uAmJ zcPC8-_@s21ry?XsnpfzO1@wCfu7;IZ2Mq#*gf7Avpw&;IZQ5~Ul;gC(_MUyg`79r z{aH~f)4_ZWzk203i*ep8_a{Z}$hgY7$rzs<{^OpkMwezy$g5YC(8ey*9c%bRz)H`)D6gTA@Wdz0KxHB=L+r@iwg zy6Rmp-Pts5 zvd$aheyHKLdABgD9!1`0_X9;t3>+?zYGtF`_Z6`wbh}uOgBaGM9sz$ZwY)oVk&1 z6AVxT8^+2I9_P~PfakoSF4W*eoK4lZxm;d@7h-jJblzZ=l>`SBv5V%sK{j8MI~n!p zbKXD~XylGST@jr(z=;Ms<xGa8^&g+)c^v=9IN~o)QN@MAVe@Cc`ds0JpWA)i((&#>?!9yu| zBcXElSq=3pQa@wob#kB4;Bscu&gh4->c zvNz&Y5x(`#yNe?NsZNE#yxgFo$vzHU&bz~|I>_5W&^fx3IhTGPxZ5-|aQpq>VroY) zF~ViqdAHcV0a@+`N8(Po3o$O)O!yMyflO5H@Aq#9r@}S)ySb{OS1`~!?}ofxlWfnW z2WAGiewn?|z;H&;Mzg&xZ`P=KKU^JO%iZ>erEv^#-Zgo>qQ_<2#XMdh&bulPE23@S zx~Q9o^RCD%6j2hV&bv|hxzXt0P7Z$)=UwKQm58OOOwXc2sk`wWw=-YocBLO9?h<>cVa8@dMX&7=@|_*7ZVRp z4(&Oo<>ek5h~9az75_oWT~AFfIvp)dmBej>ahZC5d+r`;H>IDGcN(K?I0T2~k?FGz z|2XHJl{YH7$`4n?(=z>V>irtnGx93Mo{Ymu=?%GIai;*6Ip>|mR~+;@Nmqr}+?uE= zn2}x=<8SA@Q;D1f}UeZ4vy z=3#gwmnq4tBfBd9dUj2|s_0VYLGexqE0Ts!tZZ?4Apg+9cxtYl8=dJE&Q1@`p3fZ& z7H8kox#+v+;(GV%r6H+mo1{Wm#=gvhv)mlMMHq&gW@Y+IM{o;U6`W3Qj_+hkidN%d zL8{|TQjv&;8NG60?n-ufc1&g*J`QX6(qW}rfN$ls)YZ(z=vZopU!OVcF64*$Q+*g5 zE66I7qBq`+PGrWVmZVFwn^V*L+Vr|;2_JzhN$t!n4!6gPg=>KPn(&hA9IiwjPb~Tjx;d)Sd(w>=n|MdGxpPsk3oqvf=7;6BXXiU6bq8(DmV7f? zl64(ZH+A)Mz_7`8wa24I?0&;0-`<`r(C#yA@_p{Clq>OTYzApqd|1hILD-08y~JE` zm0>4Gjo23qJIkx-QyIQ~ zZteQG#YXybL!J%gb&A_zxZfDAU&Qy@iu}DM*6+yqo-4<<aWY=>eEIYZahU6wYD7)(Fpp)BT zsL(i`^SOyaku1|FANM9hcO%7(6^h(!NL*Y&&JDOtLy?;dsaHNQL3M6Mv;dKIiOJ3_ zs$fr%UMq~v4|wWzBy0zTZdi6U^ZwllB~H~~+vmBE15}!% z*9|=(=k^9isEUzpol$?(&}^#qWxX}htu^Gk4cR-i8+g2G92Ma>IqiBy>QnBm!5;|3 zb^)Q@=Nx9)gt00ILjBaeRY?;$obh`_Bg0xjxRu6PFDLS3o6iMBt=(wH3W~D5&9WOA zbF&eI%MGU+qfD*?`8cR$hSHr;l$G*F@_}Z#7I>-Qb$gV{eIvng#wAwrpmAL4%MTP~ zMi(3EOqwg86laR&nj2CsOL6T|Yd1bgdeU%ha@?ts^HrlO1`mkUEy z&m@qfQxhC_x`12HEgj&dB}oq%Zb8Hyp^7uP`F0Pw-C3?qRh;qT6DV-(NA;#!suCP- z$l$uCQAZ?fU+{D^`#93Xj3Pml^nNZv%FwKF8n@*573Jo;0byPYEW(r}FA zap(fl&XEFXJV^4IoFs*fM@e3jvn0+78V-}ZvBtnolhU{xC&xctlk+5wa2pPayfF!_ zR&ykcM@k;uA0pV9QY?*!O5P~L+Nn}j8jqE{k%qN%rCi})$s1uDdblOrat$r;njq~VasYjVo;a%nhb^6sBA zy`u4;$-95j^h%*TcGTqEKWloGG#oa0{Y+FlZF+U#xXEjB-qfOS;N&$qae7!9kDRkEfZUX#g`Pqq`dYY4GPqyAIcC^Jh^?6-5{Jkc|BgX^r2Sq$; zh<^Ftc>Xp&LDic=3O7n;XA_zR4Lreco@hwCZ!f2Ni61>ooq??N~iM>7t$5$Nx&>)qjE6 zRfG=%s9$RQnw)!Xf}XE>_fO{D(|9!3+SRCp={CJg!jjPS&AgVBzffE^!);45q1>8K zl^f>e_-#P*bEWBMm`)KxjPvfF^1ZjoF`sw;obP@25Bj|OCw=d4JnCbLndI|1+z#;(g6KIVDmK(H zf#`r%TDsxaM(C9HF%BI_5KBq@8&*~}U#uTm>tm3|deKuU& zZln2raT~(L8uRV@F*d4w$lcC<6MU=tc(a$0QBWS2XZpClx+?ruBRg4?55kFIyJ#eC z7v6u~Ph<=EQAL?rzOZV2BELMSOD*G;DTw~#K9LziXZ0lWzIh*OlZa_?YFoBC7@A(f z&g_vq6wlnJutEJlQ>8`if-|Wxxh?LbGXD4b1U8|%6Ds3>yN|U3cFX6^r;ld$=3j_Q z!;!(BXi0D{Hz-=`Cg>{r8-;>R%)WML{`v9oXm>Ha+qI9%(#uop{Z;%9+W7RU%!H_? zD~S#S6`W^JlexKGK~KMjyW-zfCSSjwrRi>vgu8QB(!04ubGYs{eXTJQ^{{(lkW9>W z%ijtAb6VWlA62v{KQj8ze(9DSo$JR%*2AMCsZK>p)8m86+=l!LHy|FBx=5oq6Yq}t zM9to z3TH(J!(F*+{$;t6n;tJJy5K|fWhK%}mDQ=x&5vhgL4HY*dTX4z8$NV2RUd2$YV%Wy z=C}@-4sKx7S+=JuQ@7J6{Bd#j+|igM|Ds9s5>6*2&aLELPLThsNWC9a9T?rn>^PYvL~`Qm^S&H%Y#Ly_((` zg8sas?NkXDN;kq^ucdfOk$U*1&Xq-n!WaKOb-gj<+k{pvX`>u>2qo{pVeq<8n}77Sw%Bc$j>NJja?l;vzszg zi%K)?R*!xd?Wpwuc?tho!qxmtZZc*FZ!k}X`D}5?n5iiM&iudF@r>1AW zdNwM_^Ro)h`^Q(eMBqJ)c+UIitMvU~%D)$G3AoYMc^|Q3HYOanpE~aequm{=7peE* zS19q4BK^@p`s#Esp@q>q$GX0$6=owZW+jQ$9Qq$jt`XlhT^)~&7IB^P+T1LEsjP{) z{n2@kr!`3w9OVSVb3Tu4`j=cC@K*^VnRo%g{|$#z7kd3gJ+&U6f_ zBd$t!-UkB3*U=iB_kLgBH}cCax^wzIr=g3P)VBOle^)pl*DuGN?9O|yD1KMU-NfaF z@OwNB&&s8HWrydsq}SzdM*qq+kj~@dSt1t71NS#d|9Z3c01l7dKWJAVw-{K&d-rSf zeRfuZ;=Rk7#UV#XrzUTtCI9ao3i*{_?+vsc^D5K;A8RG9g&KIB7bO0L8h8XJ+6E^> z4L<0l8vP43_<)yg8Z7e6b?_#`g7fk$m(1}{136Ef3>mLAkoEr31yQlFrw)ou{16qH z@yvU%WeIzxX>FY!z{MzWIr7x!=!1#V5ei8*6guX^uIV8`-&}v+jvoVWDM}mS>((pt zF6AJnRr~xe{7QA$HrFoKK3AG6%PlP$&9afbov3?8eBIOJ@R)w4y+Ller8gNBXiQzu zDN@RH*|C;lWyG(=5_?Gb%MaO8NXQD}Jdxcl+Bi%KMv&Ec4lMB;RlKHQBaj z2S$n>n!cJ*P7AXmEw`ze119r{=!Av$X7G_9esPvFcb?s{>>|VF`#N8j*VZ^i-cC=z z-P-eZ;1=t7C8iKQUt>XxHGAfXb|rQ@d#0TrO&F0qq=tP zyybp4bH_@yI~ZV6@5=5q{1#3pmA*^*o2m@bhA?u@qO$B?hEE@^Fqr%EFGCjizeKB~uvihnDH`YqXejMdK8uvBshf>{A zD%RPs)Yz=f))@B{!F;PUu9`r+_C|9ed{#-zeGUQ0>3i%9P$%8g9f0brHRMk^S_yWf zrwjdgKEp{a!PMo)6y#3VOp7B*&fT{YK2&XGKWor6SK5>!gZM+YaXWjykZ~YHNY7+ss~X(`R{% zuME7)GS5&9?y2E7QlLC+l zE7s|FsD&?OPFnh&oZxBh7h?{)Ns4C|pH`z(=Q`;@7 ziwZua)VuX=LIQe|k>{;5t(Js*qYbW;@jV${HPwyf)LO+~6L1R^v1?4~UC{)S;eh2a zKfTk$yq!91X*;B*g-SctQv6<%5A^>-i#gGXH8=A?jh1r$alo%&A#IK0h zy5Qe}NGbbR(b{GETD6~yCt2oS*Qh5U;<7aTH^^eo#&uQ~D^l!_k@NXLW%9Zii@WjT ziW|dHO>WU7jXno19($C~&vGfZqqeKUQ=8qDui zqn9}>B25>6hm~h`y3W+LDbQU2c>q62QVh)WG?@+s9gTCFc#o;`XoQCosi&lSn`K@z zsv#lc9oWUedXsXDb~2^!O5raIRhu+^CFD_?F2)HGQa9tLEGM<~VcnkCFo&C1ekm=>PkH0WHuBFx)&!xdptL9Fr z9B8kDsr_Jl+>o79AJ+n>7a0F*!Jkw)*Z63e$6B2w!M#t+U<1QBKHG~B|HBx|{BV|j z74&$2uc4p4W!AMWeb9K7hu_lJj{ZGkvRjYdF@P~Rm-KNkZk#2W+$1QGP z^m7d`*&y$QY1$ub>QXqv^6Y@`hd$T)?5!eWxofW)@b+p_50_Tb+{n(hG-p!tOaW5^ zMjU8M9N%!EfqD~YL%i0q>xAdNa;yjkTlhkT13$tG{kLnPWqgmKOvl6=?DD)6vC&0z z@AStIQc}mQ_IjK3zfI-l)-EKOYFfS;b72m|E5peq$=HBHWm0{oi&g6jX-=XMh*N2h z-`!;fvpMsyGB|3M^$`_ei~NUTp49ifTqVdq+-qTb*Z-|P`ud;Hs9o}qPWwKhsBx~V zNm~_dGNx-YT>1t6Lij5<$?LCMnYPDVdPsPjNpmdCNg9z~W_n0L@5RHc4CiB-Gf5Ao zhFYTD@om%3E`O{gJDToeTHlu4Zdo3T=3AMUg?zIGpP}&%WBYA3&f)&P?<;(`x9R#! zX1|HmKBfLC-a%8{Mk_g$0NuaU8LvIzOj9#jgyX!-e5-=->7^#ge1E-3a5>x6wA?Eg zZjv2JA2l0VlzzYJXB|I%tJ-Eh1?L|xGn#AZB!u1Y;><(`~9V_dcdL+v>%IBl{H zjjAozsp;8NL1f$Q>x)5qv+|Qm}<0WSPw}KuP?#PY`@p=$}3|$@W|4>iNu&6<) z`+eMmh}F$6Z-wPQD9hn1B$aVbdv=PSQ_8NmZs>D-kkv6|r}fwujP)~$FZDmAj~VV; zI+%YLc7nkx+i|9xBUv2aVY@T>l*VPRnH(oFYfa}zEbB?xEvA$^`2QdjT{|2Hh5W)9 zj0TY_U$mMn98Pft0GAIU03`cDeh7sGWo9r3VvY^SX-Ld$jOX3RcC6Q!7#FjP4LLq8 zGXW|x9jpo9S`DLH{x_7*NA-QYTVMiji7HK~6Ko|Zp0ilhH?=iqn97@drmp1@#qinDf}s{>BScuw`dph@=Y<%AI9Uk{_fnY$+E z3-LV*kI0;|L^VM_)5_6+aTmI_afQVnNv|>Hb5g^tocpp*Dzi$Be&#$|5sNsWF%dK&cszewx) zw#B^=aQI3VPoFkvR;SKex!1=S5Yp`o?wJW34?9~?r$(b~IoQ<%`k0FF9_778Mw(s@ zWZM}1@bIves!PaH57lf<|3umK@cS71&hZLkKQB08Y|lk4#Si>SPT{9H+9{;>Qa$W> zAjO#u;i3K#OEN2%ZqJFqczcf0?4vZ&Tf$7Fx6`rBoJiYz~FL+u_hGohj&*q?qS z>AYE1;ccUZ)&v%1CR$`&`ZH=8`L@P;Z!pJJG(D}17p;q3Z58|VJ64vhDY`R+nCWxY zhY)QXgD1JSu>{wwWF6C2wS{{(Ez~)E+n!z1hs+}1s>zmc<(i7NCFU!4NEaFNnW+zI zK&ttcM z(8ge)v6}5)G_B9ga!U_9nR3IUoKHxV>Wu%8HjsLg`ABAxNpmW-&Ftzxw8@^kqXQPd zJ@YP=X9cHY%41P>kD+TaD@;M-O+l3@79Vh~_i<66q)+}#Lp^KB;Faa z(&jllwMk3mZM24ZH9OgQ^DFUwD^6{+({#`$T4u$qPw|m2sfMI_ndAq3whhQ)Lgq`F zMSo+mGrQ8{nHUccd1T{braG87C2@sKq9z%q z6WM8&vLqU8RdU!bHA`P@z03;J+1GZOuKruaV);uE4~Av-923s8B3}v^V36x_dbWkH z1mD)V0-IzY_eF~>i_&PU2{0(ez+i=k9dt{1H)N_ugB2}b5tmw@+D`?4orMTYySM|}>pJ4@S|_^*=0p=#+v;m|EPsG1Y=Cn&uiYyTjAe@8qq>sV7jaMtT!RrgeUCTJ;bAt9GClB zjd72NPm-XzYwY#}jMk)`lG$zsF)O{r!W%LZt&pD@YmbjzvgzvbG#_)2uae@rp-u8% z6|6E|3j$WTK zuAtTC_V@~uW3^GT%LVGEGc7RHY-3||!3w)9z1T9I8GJ-p`&}${TBI)B-guMkXm+a! zJd<+`&1qhUt@GRwJfS((uyRuktcci};CUr`**LFAw=r{HXV^TJwwP=^bsEg%rCVY!B;@8jN+1^UFFFs+S zEl=$;(&PB^t1wqW?rtW3oNy?}O@0fOf6r(-`VBH@6V+O~=@zntLkC~EW@XtHPqO6o z;TQ`Kh)0{v@L3H^yQNtTlK6Zy)(W@FYP2T&k>+ud-5QN7%QA)FxhfuN1ssD&29(t0j&!P4;x`v6FOZh9o4d@vE%**e*tk-2XFiIOelq!fk^esFWw9ml;HDyw-GhE&P%yV3*s&2d78)NVbj-dh7YB_&VP} z-*tnHN6(l60vsI`lRDY}WBdN0%u1+!JK{VQDu0vr0?@$9o;k@JN&H{yDAuDJbJ{_4L`%j;f~Vq?X=;y z#{UH;d4%OLyzZvP7}XSip^el-4O^Sy7tN7+tXbo%aHSRLPQaWLsaB^Muu0oLylMK! z$Hde)AkBya>;GcsNQE^UTW$<5q@JR&$V1C4L5FCbB^Z}xT?eDn!SD3Z&*w{R`0t4L zbe`vuh%IjL6=|3d9++)sCF~UZT+zM!gXG4jWe__9H$Pl&#aZlggg}PR@f|lQ`(`Ga zNXLxNl(fD-F zZnR9EIb-5pjQHxBlwC8!&1~x9UM5pzILeyF!7OVj;zwj@3q1G4xJjU73PosC=9el9 zdl2L^&YxzaeX=J_(v^6LP=%ZLaXY0wmg!}R8JIp~hFO+6V0!En9yj~F>9b1;-KtC% zE4KdTis#)j+J33UCehzExI?b$KZo1GZzEOeG_d)3;9j+k)Q{HK+6hr^2xPN%Z{ zEZ4bFiDft}Tx#s8T^odUqm475G&Hf%w<#I z1|}KwDlgz>cfcKWwS3Tjj_U_5yBplLaL=i8o`n0%9L8rkm4tCe-Ol5AAj9q^jOY1z zZ3BN&<{d1nF2N4Vq<2(h;mY8=NQmQg{&UntwvK?JtH|B*hr`R~xjP{*VX;+xrnR>B?OE(_nvave0O_*k9TwwceW@I{-goO4r$ z?YSg%%S750T(R-^^Z!p-=K)>Sb*KB=E5&x2ldQ}maq?!KCu3UzCwVFFNd{q<2%(V# zu|2bLpDZp|%R*A5i(4i$G|_u+21M^&RMC6008vdhz4vb5eZT*ekRW%h^X>0nc0K!? zd(J-l?8Cjm64!FqO4mBqM%NbCPR$ytbm^J1;=Z9*>Xp*G&>(AH-GM3h(f-cXzB7XP z)ZjAjX3ObDc!dIoGkv+89Vb`}U1rI2KirgJ?Y0{B4{C@)%3%Qw|4BRCI{3xVD(kbl zJWv)#z4|AR&xk-j3%~aN9M=UlB)G&>*Zi~N7fV*Aq5l3>t0A5_R;#~~$|$$i%26tZ zxe-wKP3V!Oe$x93HH>486{lOUr#bESYp#+a9r0|kI?oE}0#4OwS83Nfoy@7i{}X%$ zyZT!TEC^n;G{yznQ@pROvQN0nmD4Pr?zTXX17Sxz&xG9A{guJ}7XI(FsLJMay z>T96HO_*dAUl%O3L-m~Rgw>_DH%q56&k3!Yao5$!{qHnyk~U}HzWLwRyh#eEr*}$o zysyIY*x{Y5ayguT=x$E4gPO=M^K`e~KT&zd1^z;up8;AcLRHq|E!ijdU*~pfuQ@&S zYXn2eu715sCdccR!**X9xqt69Oe0*MVQEi2E;-ArZAwFHtW8!2^e---nO?mOqa0pW zG`+k}_E-FRD4}q>U(Y?{GR<2|3Rj)8thC#LyRAk3td~aQRS{fmVP#O)^^*GprrIvi zRiUJ-fuWYhEU(r;Q&}#V&wxNj3%~O3wNjV+^iW$lP4S(u9y5c(Td~gvHUC+$w9bjF zkKI2f80pfBzfx*+Mp7r=KT-0H7Jso%XM7d4ziW)eUm4tLxo`1SSXv_FF-2xp&)Mc}boQ4dKdvkZ+ge zcsRJiT<3fAWJ@*J9R3|S4ze6iYC#&DmwN_U4SHFj4*K-GP1B!C`j()QTP|!71MnYmt?{zv1$=6|cm*m24flxKjsfE>9&=5*}~H zvz`HV_NlOvF9_-Jv#gI9_g8u&eKV}YXTmGZ`+-L{da{2T>T2>)&umh5rf39R>a~F) zq@TRZt}JsNG~X#<{pl*L#a>-T$Z1dTr-;L~^agvalVz|j{C|kESF`!?=^D}ii^5sD zs>Nx(ooIX8J{aKX7{6DOgTvXhk5&9@-&`y3Ew66yl=^AkFG+8mQ>O%_vmva7-W1La z4Yf2zdbHGoqHCs+w57pi_AfWU>U7-GntrLrxJqZgdz$UK)9z7L!&w0x@XGdg2Q9s& zp*5D>HD52w{-XD^xg88FwmPr$_ONh@SK~ZNZm4&<)oXLGoOKESxu43$L@Pw(4z`E}^}a&qJREAmzC{ zG{>6uLU^_5ulj7ZKkJ)293yP6X?aVfHQtUGorG11gP}3NxB5?8xXNE@?Wcv)WS!&r%35o!TeqZ=A2Y>6rR?oGV)~6d!;$`wR}(c9cJU0f z0xt~Sv$H^jPlLYFk8^)Yp?=oY3cA}r#&&(r@Dtn1TD3+cSRUMDd6s)Lp-}R{a5~i) zXMO36r^K4?Xh(*$7qK*n)vf}ph>EWjIy*>3Q^&*`S zD8?W4)}vZYkE3K8@4jz2eCfSpzPmlgtSYzNIrx4*gMFuUW+nVl%=sNXdQuj{f~6Mi zoRU^r>N-*`3hU92(p=zS`mW=*@F^};PvKneckQfdU3YV6hV`)vKFy*~qWPbY*H3kd zS1RiQ_ia~f_G=hK^8U~*OMO|m)SB<4|AzUU3TRYEDUWsUGkwRvZxAQDUZb)rH6Mi7 zivuMVP6}v=Cdpj_y__DoO>k>yRll*;*oVW{tU5!y6Kw|%(x?4sqg0YQrjNW5b#=It z?S#X6mjZd3R@@-Rt-hb*wo2c(k=pSKbfdH|4nA{&lgwwjuZNxGwOWyqeUqFg+hL{4 zV!4m^R#>awaCfviKMb~_#osiWtDBX)(yvpOe3w#2g|pootXQMNdSEa4rth~()#=h7 zuQFa2>T6+1=&rTqM*l&Jz1w@-P6`@Lk=KR*U;5Hmn%U-iH7KW)4!ZYR+{K|+sgSN$ zr5xquC+a?!C<8~)w{|XV5xhrb=v>8!Op8Y?Jwf7xt#LqZd3^@2p_i6t_WSBO&n`2 zLe^5av&Ceyjbx}nzKeo-(y!#Zc|NDkw=`0K*wL?9NDBLU8xc%!?K1TP-#PmyzH7$O z-qF^OS3{RA%`Kt*wp+gn=p3xHR|IsTRJc8O!Q`WX(bk~a4bt8Zs9!7XUVe>4f9pkB#!xY)dU{yc*K@#< zUGMH_;TWcEsfH!4iB_2TfpTlK^E=eUF}IE5e$vo{B2G z7}Pud%I{n6QPWQkYYbodlc5K8Dmi0bmxEzaEY?vc+r+S*l`2l9R}+vFexv8aY8{QZ z$~Zir%LyqjdG+W>a_`{hh$GyZ5UN`Ki-xD9T@}(ZZiNd&^DWk8zoxItt*3vp?c9|f z%|Di0;`uA}(yQ#kQT7M>j_TwLjWM?`Jr^yLF+pCV(0UoTsq-l2Wsg?tkaW--w|E+& zEOlk#x5p}VG589RE>mO)8IKOdDRIwe- z->LSgn3QH>l^-Qgg8mpM3h+=U@EwKmYb$|J~8q$=TW2 z#o5(aqInDkp7eNStw zbDVR$v(!03b(-Xy?4079>YV1Bt}g-2)Q50qJLfp(YVy&1=K|+KeY=5@jt!r&iXPI$ z2Ff^K`SA}P@b-dZ3!Iu7>a4N>>Rs^m6YkNvhp5!{u`v-PkC6A{hPVn*x zGCRgpo(G{JcAT6Kt+%Tkjh{&SZ9oGw3YYm=R@wR5ENiv_;Y#!QGdX3GR!{db^Y0SW z@g@17x1W`6ut)t$@)chvCF5}Z;~+cx|AL6St-SZbdR(9!x`vNgrz!Di&_FR3dwxw} zcRK%@;J#KVS8zi^su*v&HFrqz11RRMf#sxmT z{-SWNS8rlT`%_X|pMSAWLEd$CO6Y6_Tp!+UNo@6gjIqC4 z6PFeFaj2_xpNRo|%}*(R0BDsTnN9?DSe4d!nlV6G=344n;acNb@7mMyfWlzWF;ILG@B#9ykf#^ZJ= ztZ`z6vjgwZ-OEjRHLRIdio4UT>na(`gZs>BXJETkp){;>zVuIn_bkm5-h&qJ+weKF z&kZXt*_Q?N->a}JaM!v?SI;hM+-1I<<~Jd%r+u>D@&A^BYfxU9&h}~nXobT(e``!mWq8i5Q3*wQ=>2DEr;nBT zBayU}%t*wSQxtpajpFa-WdG{z2CWm{NceSwe`)Y;ZmdDto5|s(S&=5`jax)oHf>r@ zJhSP0k<6@&l;jqf-bnPb+*mjwIXNS%ReB`i&&|(`<>h|pE$mSI(OaIvg2HSs@R>K# zK07zx|3$Q@;KSnLKu$s7=WViM*>xk4jN}&a_>oARDyjJgDUnD$2`yW^Rc*u5L^Hlr zlV@tn%O=TL$yKga4wKEf z#vFGK(SR+I)6-Kj>O#{q-i^GIoc6~|lNvY6s3o;%o{`Zqqj}o9b!dme>~_&Na`SUs z#f6^YqG&t6w&LthqMpK7Q38+%Gz1!XV(kkPfJC4n&%DoYE42ldp{wVuKq;>kzy4~uc291WvgK8 z|vDvv8E z!IhL)CnqnOU6h`k7mdZDK@(`nfH9G9q%b=#@?lYKyN_Za<7Np(3bNZrj0Qi=&W&Y$ zo}be&)Fv8>=ET@vfk?NQ9H%?hwYxJl~mBw?X!zNj%$lQFOEgq2d#W`?08M(SogUi*E8v(+&0lj zQM5Rwawu`yJkqu(yM457jhx>;*B>d)DJsaz^Qr84xv^k`GeNu_#y)HpihQDIN-Dce zI8Hw;%8f_L>^6}?Wn0Hs zOueODw21D~CZawUi~1r(+4*gLQ(pgc#`hiqQ3;_V*KN|lHRH>{*E1FS=k@vMN?mpn+4-NN{4|vDM80=BX?3_ z!pqfZw%`~`r8`eqE4o=r@PcJBnJrhz33Uq|E(Q)o&rzaRDT9c)zzlLbLw1QY>^eIM6+ zUyy&}?)XxJdTn)V@sc4n!gmP>D*)wo%tY4i7j^n}kSB+r%}Af2V2q zcbZ0jr+K@Urn*KnQ+26oc*95yZ&ZuFZ9Kkz5+bczrfPr1rNrkXwMZ?S+Qg*zo{P5x z_XBY`(P~;F$6KUEj<*Uj-MVqJgsKDOnIiE;MZ+2e7fb9M3dyxwa+7~;m6>HXA}!P2 zjiffu%!;HwFE*oCH4PrI4p&PyJBM0J_4SnWxV@Ha9WpK_H*OqHy+&+CNixYhGhG*R zWS!nBH8VxE%1CMbOjMn!M7w#aDQAsn`Iwl}v}sD?ERM~Vt#q;8sww@R8?9#taJ67% zN2tD{=fqHTOICeiumZ}Z=3IcovtzhguyX-|_Cxi_URj5ebr+DHYMrBQHP8H0N=kaD zT1svCj5cdtMSk~7R=V%!PZthptW*0QgIZHAQuAtU)umH^ytO`lmfy^vU@F2!}qVQ;n2y+C~b+0LsG ztyk5EwzsN9)wXtARq=Vz&X01YHmx~2t9WWHZXHSbs%o;=o=HtT`peC$o5bZ)&PUn# z`O&=MdL~8lKZ)iQ6h@0*jx^0mY|^29`_EIVRL?E}GVPL$s{;Mo<`;4;;8S`E?7~JD zQg!*0RT#0WbNeesDk}K&X2X2<+VIUgnDbcnq~bLny<8o%z!d?$dRIJaH?^OhD> zmcpXwC&W!uTwD`zHBxP9SY>I51=mJW)Fm6;-ozWK9t~C4A+I=^5K)8Ih>3_nv*yNf zJ_^B#th{wGN+C5bd447S4Gjb(V}R6j=G4IrL8w9UzfArsj5$7?jEZ;!L#o2VTZO# zU3UuEIkDVNqQN9Cy}1MQBt;9_TBYKZuc3)n58XIq=eNsK4CR$ykXszpZR<}x49WQ7 zgD>uPGBZ7lE(AVE$!M9L{BDXTtyOBOuUSfRlavg9)qs;fGr2{2YD%WRwN9TcGcq0B zwUDw#C^eGl(YTn$txaD}@%R+_wFSgO+UkgF!ltL5HhrqV^OAJ0X#1`q zjTJUg*i_-W3Y*K8s;#9qEzaz3rR_a!|E}%N@`=bNTU(Cgw%T&FRwR8)+b7yS z)AogQe^dD1+B#{-(BG9Bb_03Y&rlFe&n+?oGTmV}HECyJQ)4v?UN?;AJUcee-4wphTxkF9vP?I~<KrZ&Dg5H8<38*m@GXX?=rjq^;n4hAJ?;Uzuv4|Jz6P{`UO*q9AHV`<4!s`g@cb`rugiZh znxVjOVvd51fsKQe0uzDBz*Jy5FcZ)-L`}Sb&4bN{Ed+KcPp?BaR-J9*lu)t5ceT!TDBfZAZpbmJ;(&~60O6bX*z0P44UVwwgpZDXV9G| zuAW9am^P{g2Ce{C0X@3btXEua0=I#?M0)^x1bYJO=oWN#ODuuulMU*JKyP&YfPuge zbi-gHbyCx(yv4pmHx4!dn2b0THUpTAI2Sg`tu;Rvz{-H77?#6U0&5W0!8QV05Vyg~ zh_(~93#i1f4|WhZjCd4w0yu?u2DXc6=V6zCs~E1sZUJ`@@53GePY^q5wve2ykpHHh zhS&}0ss9N_Z&*KIAmU)yFkmF&XjnIo;*N!t0+TRIflUWyAOCCIFLwDZn)R^jeVG z1<>pjH4dP+HFdlJ^YL2CKXM$)bR#vK(`6l0&GLK9kvsw0CoeF zz&_vrpl=1JBjJ1mb__T{%BNs@F06AI>^!mg%MbdS zfK3LbB2I(N0QAbOS{$a&Td3Ot3(+kC$`F@OpyjY~bXucAZI8GH!+Mw|=d0Nfw<2yw z+<~YUbkyR2-s)1b1CevVLrE;}1Z~~W;uv4(pz!}7IM7xNnwN-RJ0Q9b- z8XK!#j!I0R_&pxPOB3^)ON1DpoVlFft$c>;4W|<(6T0KSfV{a)PfOe*q~S!pakd+^aS*+KK0_DoCm-L!G^+y z10xZ~z{bK#VH06fNOUUVbeLW;&^ZE_g>DWo4_E*!0v2Ok0@I72YED3J@T*OMl^9k7 zYk~E^MnKCgsZC+qfE{FB0ox5!BJPJBgz2+^Ix_&rfs?=~;0$mMxBy%Nt^n778{}~l zb{n`$QV(E{fXBd7pi@YOuDYFbbOU+-y?{PIKVSeb2p9qk14e|D{79I-cctbem2t4~ zu!+EwkSE761Kmtu7S3~kc~}?1%3w=j%Ykyl)i|#~TnB6bHlf=L+X`$4b^;Z^ZlDs_ z2OJ<3eZNRe2RjCw1Wuzn13Qo3MZ`YZvl4@_0=04-G~o>M~M1nxq2e( zDXddi&;=+7OVl{QtiixAbR&RK7)GNT3mXTU0Go()GB6c!8f*qI z3z!4U!!RGV5GVtd0Lw5ehm`}XNOUc1J%$a4n-TR{1@%P4oxm={-54r?eZT?W5O5ec z3LFPc65}*6&LEycya>CD?h4{{#G8n>fZK?7VfU~;ggrv{70JacT1}p*e4Nx7< zz)D~>uohTP+)c#Lw=~p#z;<+B!FItaVf%msz#-r;a1`qa*f+pw#B;Cw78N#!Z5V_g|K^BQfJy6!_xM>oTshJ6hC8xArYTKA{4H>1l9xSjo24905%9V6gC_-3N{8d4wwK;MmH5U z1DK6C7q$Q>LtFwZLo5eY1M7f|7&gPUX}HU=9dRd60qh1UvF?W*gdK(*g`EIS5$!a( zv%qB?*I~C{cYu4q1K<(SzJ)!3Jq0?xB+^I15|=E(6!F-T-bP-i6(VJtCEF5ud=G!aA`S zSZ7AEN?w-O9q5VJ2SZ=j0AMgM3>XQF0mk863Y!E>CB`(^OkfVyd9a1BGGGbfa$qH} z2HiT?M%ZRxE8-5I0@#CYFYEy95O5gr7;qBt6znYQJa7^53UD2`h3*dQKI|dvG3+U< zvxZ|GU0)IF4(kc)1M3G2VC~0&u)!FHAr40z35-S@0~-q)hsy-mMA#JARM-sIO#Eg8 zbI~n;Ey7TSxD;4{SPokaTLW7UY(m^jjIF?SU?+xMKqasrI0PI4j^lEYXx|{70nQ^{ zfL(@Nfn5h~A>Jm&UEn_O5W{1j<97sIfNnrfpwD;Y(vOwp`y&nlh9VAwjf9PYeF=<5 zEG5Q7U@|Zj!wg_HFb~}VSQ)SsaXHaeAg)4O1FQo!pxcaf3*t6l2f7Mi58__f0oWnf z5!f-1Go*`10Dj8@p}sE%usI$&;#fV^aBP0LxABLfOm|9jRD31 z6M)IUG+-t$2bd2m0+s;Fft9QzyNXoSz}CXn!!`gLflc^r#jqXNiMR{42iObj$L|2_ z5Y{7zM-h+1PM|vlJB{uv;swNuh?fzs!EV5A1NVT3z+((gfljPn*BR*YJsG+IJ-;VI zZ&*JJ{SgNu4uK6rHym*k;uzRCbmM_i#7P*Yz^21y0<(d+zh^Mc8H7HJq;_ z-UMzV-htf%9srMk$G}r!bpF0rS3Rt8bcgi>dINod{=h(BFl&hofeiyj0Hc607``Nd z@xVl23WjO0nXuWgdB8$oF|dqi%dwUtu7<6JZNRV*aWmpJ#O;VXfeK(ZhP|-;SPuXP z5x>T86!9413B*&dGqCd*E&vzNU4~tOT?1|)-h|!8`5y2Pcnoy>fef8_z)}MA0D9}O znWGQT7wCs>ATR{yVX%>~(ZH98>Nfu=%h>u*JA6fh|K<4qF9V zi(wt&24EAg1>IJxJ77CuyMRi>y}0ZL4k8|c9flpj;4#qgRY4b^8_*Nz^Q!#%0Rs>R!-fLGfsyFO0ONoOz+_+=FcX-A-#pktU@@=^ zCu}isY(m@$+YammD$wl#_5lZh!+O-|IPxkN-N#?$V)>fkQ^Wp0L^IBCuHkCK z3d7@u*9@N;_WzOj8_qRcZCC;7!zV-BK^Nc=sFi=@@Hqb2;nNp#{EkgdeHq2)`2Re) BBO(9* diff --git a/src/worker/workermain.js b/src/worker/workermain.js index a01935e0..f4eaed0e 100644 --- a/src/worker/workermain.js +++ b/src/worker/workermain.js @@ -267,7 +267,7 @@ function populateExtraFiles(step, fs) { if (xhr.response && xhr.status == 200) { var data = new Uint8Array(xhr.response); fs.writeFile(xfn, data, {encoding:'binary'}); - console.log(":::",xfn); + console.log(":::",xfn,data.length); } else { throw Error("Could not load extra file " + xpath); } @@ -816,6 +816,7 @@ function compileCC65(step) { populateFiles(step, FS); execMain(step, CC65, ['-T', '-g', /*'-Cl',*/ '-Oirs', + '-Cl', // static locals '-I', '/share/include', '-D' + params.define, step.path]);