001: ;********************************************* Unpackroutine von ICE-PACK
002: ; Eingabe: a0 = Adresse gepackter Daten
003: ; Ausgabe: a1 = Adresse entpackter Daten
004: ice_decrunch:
005: movem.l d0-a6,-(sp)
006: bsr.s getinfo ; ein Langwort holen
007: cmpi.l #'ICE!',d0 ; Kennung gefunden?
008: bne not_packed ; nein: nicht gepackt
009: bsr.s getinfo ; gepackte L�nge holen
010: lea.l -8(a0,d0.l),a5 ; a5 = Ende der gepackten Daten
011: bsr.s getinfo ; ungepackte L�nge holen (original)
012: move.l d0,(sp) ; Originall�nge: sp�ter nach d0
013: move.l a1,a4 ; a4 = Zielpuffer
014: move.l a1,a6
015: adda.l d0,a6 ; a6 = Ende entpackte Daten
016: move.l a6,a3 ; merken f�r Picture decrunch
017: move.b -(a5),d7 ; erstes Informationsbyte
018: bsr normal_bytes
019:
020: bsr get_1_bit ;; Picture decrunch!
021: bcc.s not_packed ;; These marked lines may be
022: move.w #$0f9f,d7 ;; removed in your own sources
023: ice_00: moveq #3,d6 ;; if you do not use the
024: ice_01: move.w -(a3),d4 ;; additional algorithm.
025: moveq #3,d5 ;;
026: ice_02: add.w d4,d4 ;;
027: addx.w d0,d0 ;;
028: add.w d4,d4 ;;
029: addx.w d1,d1 ;;
030: add.w d4,d4 ;;
031: addx.w d2,d2 ;;
032: add.w d4,d4 ;;
033: addx.w d3,d3 ;;
034: dbra d5,ice_02 ;;
035: dbra d6,ice_01 ;;
036: movem.w d0-d3,(a3) ;;
037: dbra d7,ice_00 ;;
038:
039: not_packed:
040: movem.l (sp)+,d0-a6
041: rts
042:
043: getinfo: moveq #3,d1 ; ein Langwort vom Anfang
044: getbytes: lsl.l #8,d0 ; der Daten lesen
045: move.b (a0)+,d0
046: dbf d1,getbytes
047: rts
048:
049: normal_bytes:
050: bsr.s get_1_bit
051: bcc.s test_if_end ; Bit %0: keine Daten
052: moveq.l #0,d1 ; falls zu copy_direkt
053: bsr.s get_1_bit
054: bcc.s copy_direkt ; Bitfolge: %10: 1 Byte direkt kop.
055: lea.l direkt_tab+20(pc),a1
056: moveq.l #4,d3
057: nextgb: move.l -(a1),d0 ; d0.w Bytes lesen
058: bsr.s get_d0_bits
059: swap.w d0
060: cmp.w d0,d1 ; alle gelesenen Bits gesetzt?
061: dbne d3,nextgb ; ja: dann weiter Bits lesen
062: no_more: add.l 20(a1),d1 ; Anzahl der zu �bertragenen Bytes
063: copy_direkt:
064: move.b -(a5),-(a6) ; Daten direkt kopieren
065: dbf d1,copy_direkt ; noch ein Byte
066: test_if_end:
067: cmpa.l a4,a6 ; Fertig?
068: bgt.s strings ; Weiter wenn Ende nicht erreicht
069: rts
070:
071: ;************************** Unterroutinen: wegen Optimierung nicht am Schlu�
072:
073: get_1_bit:add.b d7,d7 ; hole ein bit
074: bne.s bitfound ; quellfeld leer
075: move.b -(a5),d7 ; hole Informationsbyte
076: addx.b d7,d7
077: bitfound: rts
078:
079: get_d0_bits:
080: add.w #$3,$f00402+(32*15)
081:
082: moveq.l #0,d1 ; ergebnisfeld vorbereiten
083: hole_bit_loop:
084: add.b d7,d7 ; hole ein bit
085: bne.s on_d0 ; in d7 steht noch Information
086: move.b -(a5),d7 ; hole Informationsbyte
087: addx.b d7,d7
088: on_d0: addx.w d1,d1 ; und �bernimm es
089: dbf d0,hole_bit_loop ; bis alle Bits geholt wurden
090: rts
091:
092: ;************************************ Ende der Unterroutinen
093:
094:
095: strings: lea.l length_tab(pc),a1 ; a1 = Zeiger auf Tabelle
096: moveq.l #3,d2 ; d2 = Zeiger in Tabelle
097: get_length_bit:
098: bsr.s get_1_bit
099: dbcc d2,get_length_bit ; n�chstes Bit holen
100: no_length_bit:
101: moveq.l #0,d4 ; d4 = �berschu�-L�nge
102: moveq.l #0,d1
103: move.b 1(a1,d2.w),d0 ; d2: zw. -1 und 3; d3+1: Bits lesen
104: ext.w d0 ; als Wort behandeln
105: bmi.s no_ber ; kein �berschu� n�tig
106: get_ber: bsr.s get_d0_bits
107: no_ber: move.b 6(a1,d2.w),d4 ; Standard-L�nge zu �berschu� add.
108: add.w d1,d4 ; d4 = String-L�nge-2
109: beq.s get_offset_2 ; L�nge = 2: Spezielle Offset-Routine
110:
111:
112: lea.l more_offset(pc),a1 ; a1 = Zeiger auf Tabelle
113: moveq.l #1,d2
114: getoffs: bsr.s get_1_bit
115: dbcc d2,getoffs
116: moveq.l #0,d1 ; Offset-�berschu�
117: move.b 1(a1,d2.w),d0 ; request d0 Bits
118: ext.w d0 ; als Wort
119: bsr.s get_d0_bits
120: add.w d2,d2 ; ab jetzt: Pointer auf Worte
121: add.w 6(a1,d2.w),d1 ; Standard-Offset zu �berschu� add.
122: bpl.s depack_bytes ; keine gleiche Bytes: String kop.
123: sub.w d4,d1 ; gleiche Bytes
124: bra.s depack_bytes
125:
126:
127: get_offset_2:
128: moveq.l #0,d1 ; �berschu�-Offset auf 0 setzen
129: moveq.l #5,d0 ; standard: 6 Bits holen
130: moveq.l #-1,d2 ; Standard-Offset auf -1
131: bsr.s get_1_bit
132: bcc.s less_40 ; Bit = %0
133: moveq.l #8,d0 ; quenty fourty: 9 Bits holen
134: moveq.l #$3f,d2 ; Standard-Offset: $3f
135: less_40: bsr.s get_d0_bits
136: add.w d2,d1 ; Standard-Offset + �ber-Offset
137:
138: depack_bytes: ; d1 = Offset, d4 = Anzahl Bytes
139: lea.l 2(a6,d4.w),a1 ; Hier stehen die Originaldaten
140: adda.w d1,a1 ; Dazu der Offset
141: move.b -(a1),-(a6) ; ein Byte auf jeden Fall kopieren
142: dep_b: move.b -(a1),-(a6) ; mehr Bytes kopieren
143: dbf d4,dep_b ; und noch ein Mal
144: bra normal_bytes ; Jetzt kommen wieder normale Bytes
145:
146:
147: direkt_tab:
148: dc.l $7fff000e,$00ff0007,$00070002,$00030001,$00030001 ; Anzahl 1-Bits
149: dc.l 270-1, 15-1, 8-1, 5-1, 2-1 ; Anz. Bytes
150:
151: length_tab:
152: dc.b 9,1,0,-1,-1 ; Bits lesen
153: dc.b 8,4,2,1,0 ; Standard-L�nge - 2 (!!!)
154:
155: more_offset:
156: dc.b 11, 4, 7, 0 ; Bits lesen
157: dc.w $11f, -1, $1f ; Standard Offset
158:
159: ;*************************************************** Ende der Unpackroutine