	TTL	RoutinesA
	OPT	!
	MACHINE	68020

	XDEF	_BuildLines
	XDEF	_BuildHash
	XDEF	_CheckLine

; hash index -> hash store
;		0000 next store
;		0004 data line (+2)

_BuildLines:	; Strip extra information from lines
		; INPUT	A0.L: source lines
		;	D0.L: source size
		;	A1.L: target area
		;	D1.L: target size
		;	A2.L: ret struct
		;	D2.W: TRUE = no suffix
		movem.l	a2-a5/d2-d7,-(sp)
		moveq	#$a,d4
		moveq	#' ',d5
		moveq	#'.',d6
		move.l	a2,a5

		lea	(a0,d0.l),a2
		lea	(a1,d1.l),a3
.next:		move.l	a0,a4
		move.l	a1,d7

.skip:		cmp.l	a0,a2			; skip spaces (+ empty lines)
		bls	.done
		move.b	(a0)+,d3
		cmp.b	d5,d3
		beq	.skip
		cmp.b	d4,d3
		beq	.next
		subq.w	#1,a0

.copy:		cmp.l	a0,a2			; skip spaces (+ empty lines)
		bls	.done
		move.b	(a0)+,d3
		cmp.l	a1,a3			; Copy line (word actually)
		bls	.done
		move.b	d3,(a1)+
		tst.w	d2
		beq	.getsuffix
		cmp.b	d6,d3
		beq	.copied
.getsuffix:	cmp.b	d5,d3
		beq	.copied
		cmp.b	d4,d3
		bne	.copy
.copied:	cmp.b	d4,d3			; skip rest of the line
		beq	.skipped
.stillspace:	cmp.l	a0,a2
		bls	.done
		cmp.b	(a0)+,d4
		bne	.stillspace
.skipped:	move.b	d4,-1(a1)
		addq.l	#1,(a5)
		bra	.next

.done:		sub.l	a4,a2			; leftover bytes
		sub.l	d7,a3
		move.l	a2,4(a5)
		move.l	a3,8(a5)

		movem.l	(sp)+,a2-a5/d2-d7
		rts

_BuildHash:	; Make cmp index table from memory
		; (expects cleaned lines / no empty)
		; INPUT	A0.L: cmp data (pointers to data blocks)
		;	A1.L: hash index
		;	A2.L: hash store
		;	D0.L: method (bits)
		;	      0 = case
		;	      1 = _ and - are equivalent
		;	      2 = strip
		movem.l	d2-d4/a2-a4,-(sp)
		moveq	#0,d1
		moveq	#$a,d2
		moveq	#'-',d3
		moveq	#'_',d4
.cont:		move.l	4(a0),a3
		lea	([8,a0],a3.l),a4

.loop:		btst	#1,d0
		beq	.noequ
		move.b	(a3)+,d1
		cmp.b	d3,d1
		bne	.nohit1
		move.b	d4,d1
.nohit1:	lsl.w	#8,d1
		move.b	(a3)+,d1
		cmp.b	d3,d1
		bne	.testcase
		move.b	d4,d1
		bra	.testcase
.noequ:		move.w	(a3)+,d1
.testcase:	btst	#0,d0
		bne	.case
		and.w	#%1101111111011111,d1
.case:		move.l	(a1,d1.l*4),(a2)	; next store
		move.l	a2,(a1,d1.l*4)
		addq.w	#4,a2
		move.l	a3,(a2)+
		cmp.b	d2,d1
		beq	.next
.skiprest:	cmp.b	(a3)+,d2
		bne	.skiprest
.next:		cmp.l	a3,a4
		bhi	.loop
		move.l	(a0),a0
		tst.l	a0
		bne	.cont
		movem.l	(sp)+,d2-d4/a2-a4
		rts

_CheckLine:	; Check line against hash
		; INPUT	A0.L: line
		;	A1.L: hash index
		;	D0.L: method (bits)
		;	      0 = case
		;	      1 = _ and - are equivalent
		;	      2 = strip
		; OUPUT	D0.W: TRUE/FALSE
		movem.l	a2-a4/d2-d7,-(sp)
		moveq	#0,d1
		moveq	#$a,d2
		moveq	#'_',d4
		moveq	#'-',d5
		moveq	#' ',d6
		moveq	#'.',d7

.skip		move.b	(a0)+,d1		; skip possible spaces in start
		cmp.b	d2,d1
		beq	.false
		cmp.b	d6,d1
		beq	.skip
		subq.w	#1,a0

		btst	#1,d0
		beq	.noequ1
		move.b	(a0)+,d1
		cmp.b	d5,d1
		bne	.nohit1
		move.b	d4,d1
.nohit1:	lsl.w	#8,d1
		move.b	(a0)+,d1
		cmp.b	d5,d1
		bne	.testcase
		move.b	d4,d1
		bra	.testcase
.noequ1:	move.w	(a0)+,d1
.testcase:	btst	#0,d0
		bne	.case1
		and.w	#%1101111111011111,d1
.case1:		move.l	(a1,d1.l*4),d3		; hash store
		beq	.false
		cmp.b	d2,d1
		beq	.true
		move.l	d3,a2
		move.l	a0,a4

.nextstore:	move.l	a4,a0
		move.l	4(a2),a3		; line in hash
.next:		move.b	(a3)+,d3
		move.b	(a0)+,d1
		cmp.b	d2,d3
		bne	.contline

		btst	#2,d0			; strip suffix
		beq	.nodot
		cmp.b	d7,d1
		beq	.true
.nodot:		cmp.b	d6,d1
		beq	.true
		cmp.b	d2,d1
		beq	.true
		bra	.noequline

.contline:	cmp.b	d2,d1
		beq	.noequline

		cmp.b	d1,d3			; matching char?
		beq	.next
		btst	#1,d0			; _ == -
		beq	.noequ2
		cmp.b	d4,d1
		beq	.pass1
		cmp.b	d5,d1
		bne	.noequ2
.pass1:		cmp.b	d4,d3
		beq	.next
		cmp.b	d5,d3
		beq	.next
.noequ2:	btst	#0,d0			; case == CASE
		bne	.noequline
		bclr	#5,d1
		bclr	#5,d3
		cmp.b	d1,d3
		beq	.next
.noequline:	move.l	(a2),a2
		tst.l	a2
		bne	.nextstore

.false:		movem.l	(sp)+,a2-a4/d2-d7
		moveq	#0,d0
		rts
.true:		movem.l	(sp)+,a2-a4/d2-d7
		moveq	#1,d0
		rts
