;---------------------------------------------------------
; PRO-PACK Unpack Source Code - Nintendo Gameboy, Method 2
;
; Copyright (c) 1992 Rob Northen Computing
;
; File: RNC_2.S
;
; Date: 23.03.92
;---------------------------------------------------------

HDLEN	EQU 18

;---------------------------------------------------------
; PRO-PACK Unpack Routine - Gameboy, Method 2
;
; On entry,
;   HL points to PACKED data in ROM
;   DE points to RAM area for the UNPACKED data
; On exit,
;   all general purpose registers are undefined - A,B,C,D,E,H,L.
;   ROM bank not preserved
;---------------------------------------------------------

UNPACK:
        LD BC,HDLEN
        ADD HL,BC
        SCF
        LD A,(HLI)      ; NOTE: This data fetch requires that the data
        ADC A,A         ; pointed to by HL is in one ROM bank and that the
        ADD A,A         ; fetch will not cross ROM boundaries.
        JP XLOOP

;---------------------------------------------------------

FETCH3:
        LD A,(HLI)
        ADC A,A
        JP BACK3
FETCH4:
        LD A,(HLI)
        ADC A,A
        JP BACK4
FETCH5:
        LD A,(HLI)
        ADC A,A
        JP BACK5
FETCH6:
        LD A,(HLI)
        ADC A,A
        JP BACK6
FETCH7:
        LD A,(HLI)
        ADC A,A
        JP BACK7
RAW:   
        LD C,4
X4BITS:
        ADD A,A
        JR Z,FETCH7
BACK7: 
        RL B
        DEC C
        JR NZ,X4BITS
        PUSH AF
        LD A,3
        ADD A,B
        ADD A,A
        LD C,A
RAWLPB:
        LD A,(HLI)
        LD (DE),A
        INC DE
        LD A,(HLI)
        LD (DE),A
        INC DE
        DEC C
        JR NZ,RAWLPB
        POP AF
        JP XLOOP

;---------------------------------------------------------

FETCH0:
        LD A,(HLI)
        ADC A,A
        JR C,SMALLS
GETLEN:
        ADD A,A
        JR Z,FETCH3
BACK3: 
        RL C
        ADD A,A
        JR Z,FETCH4
BACK4: 
        JR NC,COPY
        ADD A,A
        JR Z,FETCH5
BACK5: 
        DEC C
        PUSH HL
        LD H,A
        LD A,C
        ADC A,A
        LD C,A
        CP 9
        LD A,H
        POP HL
        JR Z,RAW

;---------------------------------------------------------

COPY:  
        ADD A,A
        JR Z,FETCH6
BACK6: 
        JR NC,BYTEDISP
        ADD A,A
        JR NZ,SKIP0
        LD A,(HLI)
        ADC A,A
SKIP0: 
        RL B
        ADD A,A
        JR NZ,SKIP1
        LD A,(HLI)
        ADC A,A
SKIP1: 
        JR C,BIGDISP
        INC B
        DEC B
        JR NZ,BYTEDISP
        INC B
ANOTHER:
        ADD A,A
        JR NZ,DISPX
        LD A,(HLI)
        ADC A,A
DISPX: 
        RL B
BYTEDISP:
        PUSH AF
        LD A,E
        SUB (HL)
        PUSH HL
        LD L,A
        LD A,D
        SBC A,B
        LD H,A
        DEC HL
BYTELP:
        LD A,(HLI)
        LD (DE),A
        INC DE
        DEC C
        JR NZ,BYTELP
        POP HL
        INC HL
        POP AF
        JR XLOOP

;---------------------------------------------------------

GETBITS:
        LD A,(HLI)
        ADC A,A
        JR C,STRING
XBYTE: 
        PUSH AF
        LD A,(HLI)
        LD (DE),A
        INC DE
        POP AF
XLOOP: 
        ADD A,A
        JR C,CHKZ
        PUSH AF
        LD A,(HLI)
        LD (DE),A
        INC DE
        POP AF
        ADD A,A
        JR NC,XBYTE
CHKZ:  
        JR Z,GETBITS

;---------------------------------------------------------

STRING:
        LD BC,2
        ADD A,A
        JR Z,FETCH0
        JR NC,GETLEN
SMALLS:
        ADD A,A
        JR Z,FETCH1
BACK1: 
        JR NC,BYTEDISP
        INC C
        ADD A,A
        JR Z,FETCH2
BACK2: 
        JR NC,COPY
        LD C,(HL)
        INC HL
        INC C
        DEC C
        JR Z,OVERNOUT
        PUSH AF
        LD A,C
        ADD A,8
        LD C,A
        POP AF
        JP COPY

;---------------------------------------------------------

BIGDISP:
        ADD A,A
        JR NZ,SKIP2
        LD A,(HLI)
        ADC A,A
SKIP2: 
        RL B
        SET 2,B
        ADD A,A
        JR NZ,SKIP3
        LD A,(HLI)
        ADC A,A
SKIP3: 
        JR C,BYTEDISP
        JP ANOTHER
FETCH1:
        LD A,(HLI)
        ADC A,A
        JP BACK1
FETCH2:
        LD A,(HLI)
        ADC A,A
        JP BACK2
OVERNOUT:
        ADD A,A
        JR NZ,CHECK4END
        LD A,(HLI)
        ADC A,A
CHECK4END:
        JR C,XLOOP
        RET

