;Recovery program to reinstate deleted disk files
;Copyright (C) David R Back 1982
;requires CP/M2.2
;SYNTAX: rec22 [ambiguous]filename.ext
;
;REC22A.ASM created 11/15/84 by Keith Petersen, W8SDZ.  No
;changes made other than reformatting file to make reading
;code easier.  The original had only a single space between
;columns and was all lower case.
;
BDOS	EQU	5
CR	EQU	0DH
LF	EQU	0AH
;
	ORG	100H
;
BEGIN:	JMP	START
	DB	'COPYRIGHT (C) DAVID R BACK 1982'
;
START:	LXI	H,0
	DAD	SP
	SHLD	USERSP
	LXI	SP,USERSP
	LDA	5DH		;test for blank filename
	CPI	' '
	LXI	D,BLKFIL
	JZ	BLKER
	MVI	C,9
	LXI	D,SIGNON
	CALL	BDOS		;signon message
	MVI	C,12
	CALL	BDOS		;get version
	MOV	A,L
	CPI	20H
	LXI	D,BDSEL
	JC	BLKER
	MVI	C,25		;get current disk
	CALL	BDOS
	STA	DISK		;save default
	MOV	C,A
	LXI	D,5CH
	LDAX	D		;required drive
	ORA	A
	MOV	E,C
	JZ	SETALL
	DCR	A
	MOV	E,A
;
SETALL:	PUSH	D
	MVI	C,14		;select disk
	CALL	BDOS		;make sure drive has been selected
	POP	B
	LXI	D,1		;already selected
	CALL	SELDSK		;get .dphd
	LXI	D,8
	DAD	D
	MOV	E,M
	INX	H
	MOV	D,M		;DE=.DIRBUF
	MOV	L,E
	MOV	H,D
	SHLD	DBUF		;save .DIRBUF
	MVI	C,26		;setdma
	CALL	BDOS
	MVI	C,32
	MVI	E,0FFH		;get user
	CALL	BDOS
	STA	US		;save current user
	MVI	C,32		;set user
	MVI	E,5		;user 5
	CALL	BDOS
	LXI	D,5CH
	MVI	A,'?'
	STAX	D
	MVI	C,17		;sfirst
;
LOOP:	CALL	BDOS
	CPI	0FFH
	JZ	EXIT
	ADD	A
	ADD	A
	ADD	A
	ADD	A
	ADD	A
	MOV	C,A
	MVI	B,0
	LHLD	DBUF		;dirbuf
	DAD	B
	PUSH	H
	MVI	C,11		;ignore ext
	LXI	D,5CH
	CALL	COMP		;compare with fcb
	POP	H
	RAR
	JC	NXT
	MOV	A,M
	CPI	0E5H		;recover only deleted files
	JNZ	NXT
	PUSH	H
	PUSH	H
	MOV	A,M
	MVI	B,11
	INX	H
;
NAMOUT:	MOV	A,M
	CALL	CNVRT		;convert to printing chars
	CALL	OPCHR		;o/p char to co
	DCR	B
	INX	H
	JNZ	NAMOUT
	CALL	CRLF
	MVI	B,32
	POP	H
;
FCBOUT:	MOV	A,B
	ANI	3
	CZ	WRSPC		;o/p space to co
	MOV	A,M
	CALL	BINASC		;binary to hex ascii
	INX	H
	DCR	B
	JNZ	FCBOUT
	CALL	CRLF
	LXI	D,RECO
	CALL	PSTR		;printstring
	CALL	CI
	POP	H
	CPI	3		;^C exit
	JZ	EXIT
	CPI	'Y'
	JZ	REC
	CPI	'y'
	JNZ	NXT
;
REC:	MVI	M,0		;recover file to user 0
	MVI	C,12
	CALL	RESET		;reset attributes of recovered file
	MVI	C,1		;directory write
	CALL	WRITE		;write dir sector to disk
	ORA	A
	JNZ	WRERR
;
NXT:	LXI	D,5CH
	MVI	A,0E0H
	STAX	D
	MVI	C,18		;snext
	JMP	LOOP
;
BLKER:	MVI	C,9
	CALL	BDOS
	JMP	EXIT1
;
WRERR:	LXI	D,ERMSG
;
WRERR1:	MVI	C,9
	CALL	BDOS
;
EXIT:	MVI	C,13		;reset system
	CALL	BDOS
	LDA	DISK
	MOV	E,A
	MVI	C,14
	CALL	BDOS		;reset original drive
	MVI	C,32		;reselect original user
	LDA	US
	MOV	E,A
	CALL	BDOS
;
EXIT1:	LHLD	USERSP
	SPHL
	RET			;to ccp
;
COMP:	INX	D
	INX	H		;dont compare drives
;
COMPR1:	LDAX	D
	ANI	7FH
	CPI	'?'
	JZ	COMPR2
	MOV	B,A
	MOV	A,M
	ANI	7FH
	CMP	B
	JNZ	COMPF
;
COMPR2:	INX	H
	INX	D
	DCR	C
	JNZ	COMPR1
	XRA	A
	RET
;
COMPF:	XRA	A
	CMA
	RET
;
RESET:	MOV	A,M
	ANI	7FH
	MOV	M,A
	INX	H
	DCR	C
	JNZ	RESET
	RET
;
PSTR:	LDAX	D
	CPI	'$'
	RZ
	CALL	OPCHR
	INX	D
	JMP	PSTR
;
OPCHR:	PUSH	B
	PUSH	D
	PUSH	H
	MOV	C,A
	CALL	CO
	POP	H
	POP	D
	POP	B
	RET
;
CRLF:	MVI	A,CR
	CALL	OPCHR
	MVI	A,LF
	CALL	OPCHR
	RET
;
WRSPC:	MVI	A,' '
	CALL	OPCHR
	RET
;
HASC:	CPI	10
	JC	HASC1
	ADI	'7'
	CALL	OPCHR
	RET
;
HASC1:	ADI	'0'
	CALL	OPCHR
	RET
;
BINASC:	PUSH	PSW
	RAR
	RAR
	RAR
	RAR
	ANI	0FH
	CALL	HASC
	POP	PSW
	ANI	0FH
	CALL	HASC
	RET
;
CNVRT:	CPI	' '
	JC	CNVRT1
	CPI	61H
	JNC	CNVRT1
	RET
;
CNVRT1:	MVI	A,'-'
	RET
;
CI:	LHLD	1
	LXI	D,6		;bios ci
	DAD	D
	PCHL
;
CO:	LHLD	1
	LXI	D,9		;bios co
	DAD	D
	PCHL
;
;req C=drive 0,1...  lsb E=1
SELDSK:	LHLD	1
	LXI	D,24		;bios seldsk
	DAD	D
	PCHL
;
WRITE:	LHLD	1
	LXI	D,39
	DAD	D		;bios write
	PCHL
;
BLKFIL:	DB	CR,LF,'NO FILE SPECIFIED',CR,LF,'$'
BDSEL:	DB	CR,LF,'CP/M 2.0 or later is required.',CR,LF,'$'
RECO:	DB	'RECOVER ?',CR,LF,'$'
ERMSG:	DB	CR,LF,'DIRECTORY WRITE ERROR',CR,LF,'$'
SIGNON:	DB	CR,LF,'Disk File Recover D.R.Back V2.2',CR,LF,'$'
;
	DS	32		;stack
USERSP:	DS	2
DISK:	DS	1		;original default drive
US:	DS	1		;original user
DBUF:	DS	2		;dirbuf
;
END	BEGIN
