; FChain.asm -- asm code for OldScan.bcpl
; Copyright Xerox Corporation 1981, 1982
; Last modified May 2, 1982  10:54 PM by Boggs

.ent FChain

	.srel
FChain:		.FChain

	.nrel

; let FChain(np, vda, lvPN) = valof
; find the end of the wfc (quickly!)
; [
; let i = vda
;    [
;    if np!i eq 0 % (np!i)<<NP.lastPage eq 1 resultis np+i
;    if np!i eq vda resultis 0 //circular chain
;    if np!i eq bad resultis 0 //not a wff
;    if np!i eq good resultis 0 //not a wff
;    if np!i eq free resultis 0 //not a wff
;    if np!i eq incorr resultis 0 //not a wff
;    i = np!i
;    @lvPN = @lvPN +1
;    ] repeat
; ]

; AC0 = np
; AC1 = initial index of np
; AC2 = i or np+i or bad
; AC3 = np!i

.FChain:sta 3 1,2	; save return address
	lda 3 3,2	; third argument
	sta 3 lvPN
	sta 2 save2	; save frame pointer
	mov 1 2		; AC2 ← i
loop:	add 0 2		; AC2 ← np+i
	lda 3 0,2	; AC3 ← np!i
	movl# 3 3 szc	; test lastPage bit (msb)
	 jmp end	; set.  resultis np+i
	snz 3 3		; test np!i
	 jmp end	; zero.  resultis np+i
	lda 2 incorr
	sle 3 2		; skip if np!i le incorr
	 jmp bad	; resultis 0
	mov 3 2		; i ← np!i
	isz @lvPN	; @lvPN ← @lvPN +1
	 nop
	se 1 2		; test np!i eq vda
   	 jmp loop	; not equal
bad:	mkzero 0 0 skp	; resultis 0
end:	 mov 2 0
	lda 2 save2	; recover frame pointer
	lda 3 1,2	; recover return address
	jmp 1,3		; return

save2:	.blk 1
lvPN:	.blk 1
incorr: 77774

	.end