diff --git a/megademo/Makefile b/megademo/Makefile index e10d182a..369ec536 100644 --- a/megademo/Makefile +++ b/megademo/Makefile @@ -18,12 +18,18 @@ MEGADEMO: megademo.o ld65 -o MEGADEMO megademo.o -C ../linker_scripts/apple2_1000.inc megademo.o: megademo.s \ - c64.img + zp.inc hardware.inc \ + c64.img.lz4 ca65 -o megademo.o megademo.s -l megademo.lst #### +c64.img.lz4: c64.img + lz4 -f -16 c64.img + +#### + c64.img: c64_updated.png ../hgr-utils/png2hgr c64_updated.png > c64.img diff --git a/megademo/lz4_decode.s b/megademo/lz4_decode.s new file mode 100644 index 00000000..1ce7de64 --- /dev/null +++ b/megademo/lz4_decode.s @@ -0,0 +1,207 @@ +; LZ4 data decompressor for Apple II + +; Code by Peter Ferrie (qkumba) (peter.ferrie@gmail.com) +; "LZ4 unpacker in 143 bytes (6502 version) (2013)" +; http://pferrie.host22.com/misc/appleii.htm +; This is that code, but with comments and labels added for clarity. +; I also found a bug when decoding with runs of multiples of 256 +; which has since been fixed upstream. + +; For LZ4 reference see +; https://github.com/lz4/lz4/wiki/lz4_Frame_format.md + +; LZ4 summary: +; +; HEADER: +; Should: check for magic number 04 22 4d 18 +; FLG: 64 in our case (01=version, block.index=1, block.checksum=0 +; size=0, checksum=1, reserved +; MAX Blocksize: 40 (64kB) +; HEADER CHECKSUM: a7 +; BLOCK HEADER: 4 bytes (le) If highest bit set, uncompressed! +; BLOCKS: +; Token byte. High 4-bits literal length, low 4-bits copy length +; + If literal length==15, then following byte gets added to length +; If that byte was 255, then keep adding bytes until not 255 +; + The literal bytes follow. There may be zero of them +; + Next is block copy info. little-endian 2-byte offset to +; be subtracted from current read position indicating source +; + The low 4-bits of the token are the copy length, which needs +; 4 added to it. As with the literal length, if it is 15 then +; you read a byte and add (and if that byte is 255, keep adding) + +;LZ4_SRC EQU $00 +;LZ4_DST EQU $02 +;LZ4_END EQU $04 +;COUNT EQU $06 +;DELTA EQU $08 + +;UNPACK_BUFFER EQU $5E00 ; offset of first unpacked byte + + + ;====================== + ; LZ4 decode + ;====================== + ; input buffer in LZ4_SRC + ; output buffer hardcoded still + ; size in ENDH:ENDL + +lz4_decode: +; lda LZ4_SRC ; packed data offset +; clc +; adc LZ4_END +; sta LZ4_END +; lda LZ4_SRC+1 +; adc LZ4_END+1 +; sta LZ4_END+1 + +; lda #>UNPACK_BUFFER ; original unpacked data offset +; sta LZ4_DST+1 +; lda # - +.include "zp.inc" .include "hardware.inc" @@ -16,6 +16,24 @@ bit HIRES ; hires mode !!! bit SET_GR ; graphics mode + lda #c64 + sta LZ4_SRC+1 + + lda #c64_end + sta LZ4_END+1 + + + lda #<$2000 + sta LZ4_DST + lda #>$2000 + sta LZ4_DST+1 + + jsr lz4_decode + ;=================== ; do nothing @@ -24,6 +42,12 @@ do_nothing: jmp do_nothing -.align $1000 + .include "lz4_decode.s" -.incbin "c64.img" + + ;=================== + ; graphics + ;=================== +c64: +.incbin "c64.img.lz4",11 +c64_end: diff --git a/megademo/zp.inc b/megademo/zp.inc new file mode 100644 index 00000000..959e16b3 --- /dev/null +++ b/megademo/zp.inc @@ -0,0 +1,142 @@ +;; LZ4 addresses + +LZ4_SRC = $00 +LZ4_DST = $02 +LZ4_END = $04 +COUNT = $06 +DELTA = $08 + +;; Zero page monitor routines addresses + +WNDLFT = $20 +WNDWDTH = $21 +WNDTOP = $22 +WNDBTM = $23 +CH = $24 +CV = $25 +GBASL = $26 +GBASH = $27 +BASL = $28 +BASH = $29 +H2 = $2C +V2 = $2D +MASK = $2E +COLOR = $30 + ;INVFLG = $32 + +; dos33 zero page = 26-2f, 35-38, 3e 3f 40-4d +; overlap applesoft 67-6a,6f,70,af,b0,ca-cd,d8 + + +; DOS33: Confirmed kills $68 + +RWTSL = $60 +RWTSH = $61 +DOSBUFL = $62 +DOSBUFH = $63 +FILEML = $64 +FILEMH = $65 + + ;FACTOR_I = $66 + ;FACTOR_F = $67 + ;DX_I = $68 + ;DX_F = $69 + ;SPACEX_I = $6A + ;SPACEX_F = $6B + ;CX_I = $6C + ;CX_F = $6D + ;DY_I = $6E + ;DY_F = $6F + +REGISTER_DUMP = $70 +A_FINE_TONE = $70 +A_COARSE_TONE = $71 +B_FINE_TONE = $72 +B_COARSE_TONE = $73 +C_FINE_TONE = $74 +C_COARSE_TONE = $75 +NOISE = $76 +ENABLE = $77 +A_VOLUME = $78 +B_VOLUME = $79 +C_VOLUME = $7A +ENVELOPE_FINE = $7B +ENVELOPE_COARSE = $7C +ENVELOPE_SHAPE = $7D + + +COPY_OFFSET = $7E +DECODER_STATE = $7F + + +REGISTER_DUMP2 = $80 +A_FINE_TONE2 = $80 +A_COARSE_TONE2 = $81 +B_FINE_TONE2 = $82 +B_COARSE_TONE2 = $83 +C_FINE_TONE2 = $84 +C_COARSE_TONE2 = $85 +NOISE2 = $86 +ENABLE2 = $87 +A_VOLUME2 = $88 +B_VOLUME2 = $89 +C_VOLUME2 = $8A +ENVELOPE_FINE2 = $8B +ENVELOPE_COARS2 = $8C +ENVELOPE_SHAPE2 = $8D +LYRICSL = $8E +LYRICSH = $8F + +FRAME_COUNT = $90 +MB_VALUE = $91 +MB_ADDRL = $91 +MB_ADDRH = $92 +DONE_PLAYING = $93 +MB_CHUNK_OFFSET = $94 +CHUNKSIZE = $95 +LZ4_DONE = $96 +DECODE_ERROR = $97 +COPY_TIME = $98 +DECOMPRESS_TIME = $99 +TIME_TAKEN = $9A +LYRICS_ACTIVE = $9B +;FORTYCOL = $9C +CURSOR = $9D + +; More zero-page addresses +; we try not to conflict with anything DOS, MONITOR or BASIC related + + ;COLOR1 = $E0 + ;COLOR2 = $E1 + ;MATCH = $E2 + ;XX = $E3 +YY = $E4 + ;SHIPY = $E4 + ;YADD = $E5 + ;LOOP = $E6 + ;MEMPTRL = $E7 + ;MEMPTRH = $E8 + ;NAMEL = $E9 + ;NAMEH = $EA + ;NAMEX = $EB + ;CHAR = $EC +DISP_PAGE = $ED +DRAW_PAGE = $EE + + ;FIRST = $F0 + ;LASTKEY = $F1 + ;PADDLE_STATUS = $F2 +SPRITETEMP = $F2 +XPOS = $F3 +YPOS = $F4 +TEMP = $FA +TEMPY = $FB +INL = $FC +INH = $FD +OUTL = $FE +OUTH = $FF + + + + +