 ;THIS IS A REWRITE OF BDPATCH.ASM TO ELIMINATE SOME
 ;SERIOUS DRAWBACKS. THESE ARE:

 ;IF YOU TYPED ERA *.* YOU WOULD ERASE ALL PUBLIC FILES AND
 ;ALL PUBLIC FILES THAT ARE NOT SYSTEM FILES WOULD BE SHOWN
 ;EACH TIME YOU TYPED DIR OR IN WORDSTAR. EVEN AFTER YOU 
 ;ERASED A FILE DIR WOULD STILL FIND IT AS A PUBLIC FILE.

 ;THIS PROGRAM CONTAINS A PATCH FOR CP/M 2.2 THAT ADDS
 ;A NEW FILE ATTRIBUTE: THE PUBLIC ATTRIBUTE.
 ;WHEN A FILE'S PUBLIC ATTRIBUTE IS SET, IT IS AVAILABLE
 ;TO ALL USERS. THE PUBLIC ATTRIBUTE IS F1' (THE HIGH BIT
 ;OF THE FIRST CHARACTER OF THE FILENAME).
 
 ;I DON'T KNOW WHO WROTE THE ORIGINAL VERSION BUT I ADDED
 ;SOME ADDITIONAL CODE AND NOW THIS WORKS CORRECTLY. I AM 
 ;AFRAID IT IS LONGER THAN THE ORIGINAL PATCH AND YOU WILL 
 ;HAVE TO PUT SOME OF THIS ELSEWHERE. IF ANYONE CAN MAKE
 ;THIS CODE SMALLER, PLEASE DO SO. THIS WILL ALSO LET YOU SEE
 ;THE PUBLIC FILES IF YOU ARE ON THE CORRECT USER.   A.S.A.
 
 MSIZE	EQU	63	;PUT YOUR CP/M SIZE IN K-BYTES
 
 BIAS	EQU	(MSIZE - 20) * 1024
 HI$MEMORY	EQU	0F662H	;WHEREVER YOU WANT THE REST OF CODE
 
 
 ;Z80 MACROS
 
 @GENDD	MACRO	?DD
 	IF (?DD GT 7FH) AND (?DD LT 0FF80H)
 	DB	100H	;RANGE ERROR ON JUMP RELATIVE
 	ELSE
 	DB	?DD
 	ENDIF
 	ENDM
 JR	MACRO	?N	;;JUMP RELATIVE
 	DB	18H
 	@GENDD	?N-$-1
 	ENDM
 JRC	MACRO	?N	;;JUMP RELATIVE ON CARRY
 	DB	38H
 	@GENDD	?N-$-1
 	ENDM
 JRNC	MACRO	?N	;;JUMP RELATIVE ON NO CARRY
 	DB	30H
 	@GENDD	?N-$-1
 	ENDM
 JRZ	MACRO	?N	;;JUMP RELATIVE ON ZERO
 	DB	28H
 	@GENDD	?N-$-1
 	ENDM
 JRNZ	MACRO	?N	;;JUMP RELATIVE ON NO ZERO
 	DB	20H
 	@GENDD	?N-$-1
 	ENDM
 DJNZ	MACRO	?N	;;DECREMENT B, JMP NZ
 	DB	10H
 	@GENDD	?N-$-1
 	ENDM
 
 ;BDOS ENTRY POINTS
 FIND	EQU	432DH + BIAS
 NXTDIR	EQU	4205H + BIAS
 CHKLST	EQU	41F5H + BIAS
 EXITFF	EQU	4394H + BIAS
 FCBPTR	EQU	49D9H + BIAS
 CKNDIR	EQU	417FH + BIAS
 DIRADD	EQU	415EH + BIAS
 CMPCNT	EQU	49D8H + BIAS
 CMPEXT	EQU	4307H + BIAS
 DIRNUM	EQU	49EAH + BIAS
 RESULT	EQU	3F45H + BIAS
 FNDFLG	EQU	49D4H + BIAS
 
 	ORG	FIND  
 
 FIND:
 	LXI	H,0FFFFH	;SET UP CONTROL
 	SHLD	SER$EXIT+1	
 
 	MVI	C,0
 	CALL	NXTDIR	;SET UP NEXT DIR ENTRY
 	CALL	CHKLST	;SET Z IF READ PAST END OF DIR
 	JRZ	EXITFF	;RET NOT FOUND IF SO
 	LHLD	FCBPTR
 	XCHG
 	LDAX	D
 	CPI	0E5H	;LOOKING FOR FREE DIR SLOT?
 	JRZ	FIND1	
 	PUSH	D	;QUIT IF PASSED ALL ACTIVE
 	CALL	CKNDIR	;CALL IF NOT LOOKING FOR FREE SLOT
 	POP	D
 
 FIND1:
 	CALL	DIRADD	;GET ADDR OF NEXT ENTRY
 	LDA	CMPCNT	;NR. OF FCB BYTES TO COMPARE
 	INR	A
 	MOV	C,A
 	MVI	B,-1	;C IS COUNT, B IS INDEX
 
 FIND2:
 	DCR	C	;ALL MATCHED?
 	JZ 	FIND5	;JMP IF SO
 	INR	B	;BUMP INDEX
 	JRNZ	FIND2A	;JMP IF NOT CHECKING USER BYTE
 
 ;FIRST SEE IF FREE DIRECTORY SPACE
 	LDAX	D	;
 	CPI	0E5H	;LOOKING FOR FREE DIR SLOT?
 	JRZ	FIND2A	;SKIP PUBLIC CHECK IF SO
 

 ;SEE IF WE ARE ON THE SAME USER AREA SO WE CAN SEE 
 ;PUBLIC FILES IF WE ARE ON THAT USER AREA
 	SUB	M	;CHECKS USER AREA WE ARE ON
 	JZ 	FIND4	;IF SO WE HAVE A MATCH
 
;NEXT SEE IF THIS IS A DELETED FILE ELSE THESE WILL   
;SHOW UP AGAIN IF DIR IS TYPED
	MOV	A,M
	RAL		;SET CY FLAG IF E5
	JRC	FIND2A	;SKIP PUBLIC CHECK

 ;SEE IF WE ARE LOOKING AT A PUBLIC FILE
 	INX	H	;->F1 BYTE
 	MOV	A,M
 	DCX	H
 	RAL		;SET CY FLAG ON PUBLIC ATTRIBUTE
 	JRNC	FIND2A  ;IF NOT CORRECT USER OR PUBLIC CHECK 
 			;NEXT FILE
 ;NOW TELL WE HAVE FOUND A PUBLIC FILE
 	XRA	A
 	STA	PUB$FLAG
 	JMP 	FIND4
 
 ;WE ARE HERE IF WE HAVE A CORRECT USER OR IF PUBLIC FILE

 FIND2A:
 ;NEXT CHECK IF ANY WILD CARDS USED IN FILE
 	LDAX	D
 	CPI	'?'	;? MATCHES ANYTHING
 	JRNZ    FIND2B	;NO WILD CARDS SEARCH ON
 
 ;FOUND A WILD CARD TELL ABOUT IT
 	XRA	A
 	STA	WILD$FLAG
 	JMP 	FIND4
 
 ;WE ARE HERE ONLY IF NOT FINDING ANY WILD CARDS
 FIND2B:
 	MOV	A,B
 	CPI	13	;WE ON S1 BYTE?
 	JZ 	FIND4	;S1 BYTE ALWAYS MATCHES
 	CPI	12	;EXTENT BYTE?
 	LDAX	D	;GET BYTE AGAIN
 	JMP	FIND$HI
 
 
 ;THIS MUST BE PUT IN SOMEWHERE OTHER THAN IN BDOS BECAUSE THE 
 ;WHOLE ROUTINE IS LONGER THAN AVAILABLE SPACE. I PUT THIS IN MY 
 ;BIOS FOR NOW
 
 	ORG	HI$MEMORY
 
FIND$HI:
 	JZ 	FIND3	;JMP IF ON EXTENT BYTE
 	SUB	M	;COMPARE
 	ANI	7FH	;MASK OUT ATTRIB BIT
 	JNZ 	FIND	;MISMATCH, TRY NEXT DIR ENTRY
 	JMP	FIND4	;IF MATCHED

 FIND3:
 	PUSH	B
 	MOV	C,M
 	CALL	CMPEXT	;COMPARE EXTENT BYTES
 	POP	B
 	JNZ	FIND	;JMP IF MISMATCH
 FIND4:
 	INX	D	;BUMP TO NEXT BYTES
 	INX	H
 	JMP	FIND2
 
 ;WE ARRIVE HERE ONLY ON MATCHED BYTES
 
 FIND5:
 
 WILD$FLAG	EQU	$+1
 PUB$FLAG	EQU	$+2
 
 SER$EXIT:
 	LXI	H,0000H	;THIS GETS PATCHED IF WE HAVE EITHER A PUBLIC
 			;FILE OR A WILD CARD IS USED
 	MOV	A,H
 	ORA	L
 	JZ	FIND	;WE CAN NOT ALLOW SEARCHING FOR ANY PUBLIC
 			;FILES IF WE USE WILD CARDS
 	LDA	DIRNUM	;MATCHED, FIX UP RESULT
 	ANI	3
 	STA	RESULT
 	LXI	H,FNDFLG
 	MOV	A,M
 	RAL
 	RNC
 	XRA	A
 	MOV	M,A
 	RET
 
 
 	END

