         .OUTPI ALFRES
         .ENTRY XHUFF
         .VIRT8 AX,BX,I

;This file contains the routines used to expand a file
;which was packed using Huffman squeezing.

ERROR = $FFFF                   -1
SPEOF = 256                     SPECIAL END OF FILE MARKER
NUMVAL = 257                    256 DATA VALUES PLUS SPEOF

;The node/child array is NUMVAL nodes with two child entries
NODE     *=*+2                  BASE NODE ADDRESS
BPOS     *=*+1                  LAST BIT POSITION READ
CURIN    *=*+1                  LAST BYTE VALUE READ
NUMNOD   *=*+2                  NUMBER OF NODES IN TREE

ERR001   .BYTE "MISSING CODE TREE",$9B,0
ERR002   .BYTE "FILE HAS INVALID DECODE TREE",$9B,0
ERR003   .BYTE "TREE LOAD FAILED",$9B,0

XHUFF    LDX #2
         LDY #2
         JSR MALLOC             514 ($0202) BYTES FOR TABLE
         STX NODE
         STY NODE+1             ADDRESS OF TABLE
         JSR FALLOC             ALLOCATE THE BUFFERS
         LDA #0
         STA STATE              RESET PUTNCR
         LDA #99                FORCE INITIAL READ
         STA BPOS
         JSR GETINT             GET NUMBER OF NODES
         BPL XHU002
         LDX #.LO.ERR001
         LDY #.HI.ERR001
XHU001   JSR SCRPRT
         SEC
         RTS
XHU002   STX NUMNOD             GET NUMBER OF NODES
         STY NUMNOD+1
         CPY #.HI.NUMVAL
         BCC XHU005             IS OK
         BEQ XHU004
XHU003   LDX #.LO.ERR002        TOO MANY NODES
         LDY #.HI.ERR002
         JMP XHU001
XHU004   CPX #.LO.NUMVAL
         BCC XHU005
         BEQ XHU005
         BCS XHU003
XHU005   LDA #$FF               -(SPEOF+1)
         STA AX                 INITIALIZE FOR POSSIBLE EMPTY TREE
         LDA #$FE
         STA AX+1
         LDX #0
         LDY #0
         LDA #0                 NODE[0].CHILD[0]=-(SPEOF)+1
         JSR SETNOD
         LDX #0
         LDY #0
         LDA #1                 NODE[0].CHILD[1]=-(SPEOF)+1
         JSR SETNOD
         LDA #0
         STA I
         STA I+1
XHU010   LDA I+1
         CMP NUMNOD+1
         BCC XHU012      KEEP GOING
         LDA I
         CMP NUMNOD
         BCS XHU020
XHU012   JSR GETINT
         BPL XHU015
XHU014   LDX #.LO.ERR003        ERROR DURING TREE LOAD
         LDY #.HI.ERR003
         JMP XHU001
XHU015   STX AX
         STY AX+1
         LDX I
         LDY I+1
         LDA #0
         JSR SETNOD
         JSR GETINT
         BMI XHU014
         STX AX
         STY AX+1
         LDX I
         LDY I+1
         LDA #1
         JSR SETNOD
         INC I
         BNE XHU010
         INC I+1
         JMP XHU010

;UNSQUEEZE BEGINS HERE

XHU020   LDA #0
         STA I                  TREE INDEX
         STA I+1
XHU030   LDA I+1                FOR (I=0; I>=0; )
         BPL XHU031
         JMP XHU040             EXIT LOOP
XHU031   INC BPOS
         LDA BPOS               IF (++BPOS>7)
         CMP #8
         BCS XHU032
         JMP XHU035
XHU032   JSR FGETC
         BPL XHU033
         JMP XHU044    BAD ENDING
XHU033   LDX #0
         STX BPOS
         STA CURIN
         AND #1
         LDX I
         LDY I+1
         JSR GETNOD             I=NODE[I].CHILD[1&CURIN]
         STX I
         STY I+1
         JMP XHU030
XHU035   LSR CURIN
         LDA CURIN
         AND #1
         LDX I
         LDY I+1
         JSR GETNOD
         STX I
         STY I+1
         JMP XHU030
XHU040   INC I                  DECODE FAKE NODE INDEX INTO DATA BYTE
         BNE XHU041
         INC I+1
XHU041   LDA I
         EOR #$FF
         STA I
         LDA I+1
         EOR #$FF
         STA I+1
         INC I
         BNE XHU042
         INC I+1
XHU042   LDA I
         CMP #.LO.SPEOF
         BNE XHU043
         LDA I+1
         CMP #.HI.SPEOF
         BEQ XHU044
XHU043   JSR PUTNCR
         JMP XHU020
XHU044   JSR OFLUSH      ALL DONE
         JSR CHKFIL
         CLC
         RTS


SETNOD   JSR INDEX              4 BYTE ENTRIES
         LDA AX
         STA (BX),Y
         INY
         LDA AX+1
         STA (BX),Y
         RTS
GETNOD   JSR INDEX    4 BYTE ENTRIES
         LDA (BX),Y
         TAX
         INY
         LDA (BX),Y
         TAY
         RTS
INDEX    STX BX      4 BYTE ENTRIES
         STY BX+1
         ASL A       PICK THE CHILD
         TAY
         ASL BX
         ROL BX+1
         ASL BX
         ROL BX+1
         LDA BX
         CLC
         ADC NODE
         STA BX
         LDA BX+1
         ADC NODE+1
         STA BX+1
         RTS

GETINT   JSR FGETC
         PHA
         JSR FGETC
         TAY
         PLA
         TAX
         LDA #1
GETI1    RTS

