; ----------------------------------------------------------------------------- ; ZX0 decoder by Einar Saukas ; "Standard" version (69 bytes only) - BACKWARDS VARIANT ; ----------------------------------------------------------------------------- ; Parameters: ; HL: last source address (compressed data) ; DE: last destination address (decompressing) ; ----------------------------------------------------------------------------- Macro dzx0_standard_back ld bc, 1 ; preserve default offset 1 push bc ld a, $80 @dzx0sb_literals: call @dzx0sb_elias ; obtain length lddr ; copy literals inc c add a, a ; copy from last offset or new offset? jr c, @dzx0sb_new_offset call @dzx0sb_elias ; obtain length @dzx0sb_copy: ex (sp), hl ; preserve source, restore offset push hl ; preserve offset add hl, de ; calculate destination - offset lddr ; copy from offset inc c pop hl ; restore offset ex (sp), hl ; preserve offset, restore source add a, a ; copy from literals or new offset? jr nc, @dzx0sb_literals @dzx0sb_new_offset: inc sp ; discard last offset inc sp call @dzx0sb_elias ; obtain offset MSB dec b ret z ; check end marker dec c ; adjust for positive offset ld b, c ld c, (hl) ; obtain offset LSB dec hl srl b ; last offset bit becomes first length bit rr c inc bc push bc ; preserve new offset ld bc, 1 ; obtain length call c, @dzx0sb_elias_backtrack inc bc jr @dzx0sb_copy @dzx0sb_elias_backtrack: add a, a rl c rl b @dzx0sb_elias: add a, a ; inverted interlaced Elias gamma coding jr nz, @dzx0sb_elias_skip ld a, (hl) ; load another group of 8 bits dec hl rla @dzx0sb_elias_skip: jr c, @dzx0sb_elias_backtrack ret mend ; -----------------------------------------------------------------------------