; Zulu & Grey decruncher by Kyzer/CSG
; look familiar? i'm sure it's a clone of something, but i can't think what...

	include	libraries/xfdmaster.i

ForeMan	dc.l	$70FF4E75,XFDF_ID	; id
	dc.w	XFDF_VERSION		; foreman version
	dcb.w	5,0			; reserved stuff
	dc.l	ZGdata			; first slave

ZGdata	dc.l	0
	dc.w	2,39
	dc.l	ZGdata_name
	dc.w	XFDPFF_DATA!XFDPFF_RECOGLEN!XFDPFF_USERTARGET,0
	dc.l	ZGdata_recog,ZGdata_decrunch,ZGdata_scan,ZGdata_verify
	dc.l	0,18

ZGdata_recog
	cmp.l	#"Z&G!",(a0)+
	bne.s	.fail
	addq.l	#4,a0
	move.l	(a0)+,d0		; d0 = unpacked length
	beq.s	.fail			; fail if unpacked length = 0
	move.l	(a0)+,d1		; d1 = packed length
	beq.s	.fail			; fail if unpacked length = 0
	cmp.l	d0,d1
	bhi.s	.fail			; fail if packed length > unpacked
	move.l	d0,xfdrr_FinalTargetLen(a1)
	move.l	d0,xfdrr_MinTargetLen(a1)
	move.l	d1,xfdrr_MinSourceLen(a1)
	moveq	#1,d0			; return success
	rts
.fail	moveq	#0,d0
	rts

ZGdata_decrunch
	movem.l	d2-d7/a2-a6,-(sp)
	move.l	xfdbi_SourceBuffer(a0),a1
	move.l	xfdbi_UserTargetBuf(a0),a0
	addq.l	#4,a1	; skip ID
	bsr.s	ZGdecrunch
	moveq	#1,d0
	movem.l	(sp)+,d2-d7/a2-a6
	rts

ZGdata_scan
	moveq   #0,d0
	cmp.l   #"Z&G!",(a0)
	bne.s	.fail
	moveq	#1,d0
.fail	rts

ZGdata_verify
	move.l  12(a0),d1		; d1 = packed length
	cmp.l   d0,d1
	bhi.s	.fail			; fail if packed len > remaining len
	cmp.l	8(a0),d1
	bhi.s	.fail			; fail if packed len > unpacked len
	move.l	d1,d0
	rts
.fail	moveq	#0,d0
	rts

; a1 = in, a0 = out
ZGdecrunch
;	movem.l	d3-d7/a2/a3,-(sp)	;48E71F30
;	cmpi.l	#'Z&G!',(a1)+		;0C995A264721
;	beq.b	1$			;6708
;	movem.l	(sp)+,d3-d7/a2/a3	;4CDF0CF8
;	moveq	#0,d0			;7000
;	rts				;4E75

1$	addq.w	#4,a1			;5849
	move.l	a0,d4			;2808
	adda.l	(a1)+,a0		;D1D9
	adda.l	(a1)+,a1		;D3D9
	move.w	(a1),d6			;3C11
	move.w	-(a1),d7		;3E21
	moveq	#$10,d5			;7A10
	lea	(18$,pc),a3		;47FA00EA
2$	subq.w	#1,d6			;5346
	bpl.b	3$			;6A04
	move.w	-(a1),d7		;3E21
	moveq	#15,d6			;7C0F
3$	lsr.w	#1,d7			;E24F
	blo.b	6$			;6538
	moveq	#8,d1			;7208
	move.w	d6,d0			;3006
	sub.w	d1,d6			;9C41
	bpl.b	4$			;6A08
	ror.l	d0,d7			;E0BF
	move.w	-(a1),d7		;3E21
	rol.l	d0,d7			;E1BF
	add.w	d5,d6			;DC45
4$	move.w	d7,d0			;3007
	lsr.l	d1,d7			;E2AF
	add.w	d1,d1			;D241
	and.w	(-4,a3,d1.w),d0		;C07310FC
	move.b	d0,-(a0)		;1100
	cmp.l	a0,d4			;B888
	blo.b	2$			;65D4
;	movem.l	(sp)+,d3-d7/a2/a3	;4CDF0CF8
;	moveq	#1,d0			;7001
	rts				;4E75

5$	dc.w	5,0
	dc.w	8,$20
	dc.w	10,$120
	dc.w	12,$520

6$	moveq	#2,d1			;7202
	move.w	d6,d0			;3006
	sub.w	d1,d6			;9C41
	bpl.b	7$			;6A08
	ror.l	d0,d7			;E0BF
	move.w	-(a1),d7		;3E21
	rol.l	d0,d7			;E1BF
	add.w	d5,d6			;DC45
7$	move.w	d7,d0			;3007
	lsr.l	d1,d7			;E2AF
	add.w	d1,d1			;D241
	and.w	(-4,a3,d1.w),d0		;C07310FC
	add.w	d0,d0			;D040
	add.w	d0,d0			;D040
	movem.w	(5$,pc,d0.w),d1/d3	;4CBB000A00CE
	move.w	d6,d0			;3006
	sub.w	d1,d6			;9C41
	bpl.b	8$			;6A08
	ror.l	d0,d7			;E0BF
	move.w	-(a1),d7		;3E21
	rol.l	d0,d7			;E1BF
	add.w	d5,d6			;DC45
8$	move.w	d7,d0			;3007
	lsr.l	d1,d7			;E2AF
	add.w	d1,d1			;D241
	and.w	(-4,a3,d1.w),d0		;C07310FC
	add.w	d3,d0			;D043
	lea	(1,a0,d0.w),a2		;45F00001
	subq.w	#1,d6			;5346
	bpl.b	9$			;6A04
	move.w	-(a1),d7		;3E21
	moveq	#15,d6			;7C0F
9$	lsr.w	#1,d7			;E24F
	blo.b	17$			;6544
	subq.w	#1,d6			;5346
	bpl.b	10$			;6A04
	move.w	-(a1),d7		;3E21
	moveq	#15,d6			;7C0F
10$	lsr.w	#1,d7			;E24F
	blo.b	16$			;6536
	subq.w	#1,d6			;5346
	bpl.b	11$			;6A04
	move.w	-(a1),d7		;3E21
	moveq	#15,d6			;7C0F
11$	lsr.w	#1,d7			;E24F
	blo.b	15$			;6528
	moveq	#0,d3			;7600
12$	moveq	#3,d1			;7203
	move.w	d6,d0			;3006
	sub.w	d1,d6			;9C41
	bpl.b	13$			;6A08
	ror.l	d0,d7			;E0BF
	move.w	-(a1),d7		;3E21
	rol.l	d0,d7			;E1BF
	add.w	d5,d6			;DC45
13$	move.w	d7,d0			;3007
	lsr.l	d1,d7			;E2AF
	add.w	d1,d1			;D241
	and.w	(-4,a3,d1.w),d0		;C07310FC
	add.w	d0,d3			;D640
	subq.w	#7,d0			;5F40
	beq.b	12$			;67E0
14$	move.b	-(a2),-(a0)		;1122
	dbra	d3,14$			;51CBFFFC
15$	move.b	-(a2),-(a0)		;1122
16$	move.b	-(a2),-(a0)		;1122
17$	move.b	-(a2),-(a0)		;1122
	move.b	-(a2),-(a0)		;1122
	cmp.l	a0,d4			;B888
	blo.w	2$			;6500FF22
;	movem.l	(sp)+,d3-d7/a2/a3	;4CDF0CF8
;	moveq	#1,d0			;7001
	rts				;4E75

18$	dc.w	%0000000000000011
	dc.w	%0000000000000111
	dc.w	%0000000000001111
	dc.w	%0000000000011111
	dc.w	%0000000000111111
	dc.w	%0000000001111111
	dc.w	%0000000011111111
	dc.w	%0000000111111111
	dc.w	%0000001111111111
	dc.w	%0000011111111111
	dc.w	%0000111111111111


ZGdata_name	dc.b	'(Z&G!) Data Cruncher',0
