home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
CP/M
/
CPM_CDROM.iso
/
simtel
/
sigm
/
vols000
/
vol018
/
sap.asm
< prev
next >
Wrap
Assembly Source File
|
1984-04-29
|
5KB
|
366 lines
TITLE 'SAP - SORT AND PACK DIRECTORY'
;
; L.E. HUGHES 8080SDC
;
; FIX 1/23/81 W. EARNEST FOR CP/M 2.2 & 1.4
; FIX FOR ANY SIZE SYSTEM TO 256 DIRECT ENTRIES
; FIX FOR ANY DRIVE UP TO 4
;
; OFFSET FROM WARM BOOT VECTOR
;
SELDSK EQU 24
SETTRK EQU 27
SETSEC EQU 30
SETDMA EQU 33
READ EQU 36
WRITE EQU 39
XLT EQU 45
BDOS EQU 5
ORG 100H
SAP: LXI SP,STACK+32
MVI C,12 ;CHECK VERSION
CALL BDOS
MOV A,H
ORA L
STA VERFLG
MVI C,25 ;GET CURR DSK
CALL BDOS
MOV C,A ;SELECT IT ASSUMED
LDA 5CH ;FCB
ORA A ;TEST IF DEFINED
JZ SEDRV ;NO, USE DEFAULT
DCR A ;ADJUST FOR BIOS
MOV C,A
SEDRV: MVI E,SELDSK
CALL XCPM
LDA VERFLG
ORA A
JZ SELSKP ;NOT 2.X
MOV A,H
ORA L
JZ 0 ;ABORT IF ILLEGAL
MOV E,M
INX H
MOV D,M ;XLATE MAP ADDRESS
XCHG
SHLD ADMAP
LXI H,9 ;DPB OFFSET
DAD D
MOV A,M
INX H
MOV H,M ;DPB ADDR
MOV L,A
MOV E,M
INX H
MOV D,M ;SECTORS PER TRK
XCHG
SHLD SPERT
LXI H,6
DAD D
MOV E,M
INX H
MOV D,M ;DIRECT ENTRIES
XCHG
SHLD DIRENT
LXI H,5
DAD D
MOV E,M
INX H
MOV D,M
XCHG
SHLD TKOFFS ;OFFSET TO FIRST DIR TRK
;
SELSKP: LHLD TKOFFS
SHLD CURTRK
CALL DOTRK
XRA A ;SECNO=0 LOGICAL
STA SECNO
STA LSEC
LXI H,BUF ;ADDR = FWA OF BUFFER
SHLD ADDR
;
SAP1: CALL XLATS ;SET TO SECTOR "SECNO"
LHLD ADDR ;SET DMA ADDRESS TO "ADDR"
MOV B,H
MOV C,L
MVI E,SETDMA
CALL XCPM
MVI E,READ
CALL XCPM ;READ SECTOR INTO MEMORY
LHLD ADDR ;ADDR = ADDR + 80H
LXI D,128
DAD D
SHLD ADDR
LDA SECNO ;SECNO = SECNO + 1
INR A
STA SECNO
LXI H,SPERT
CMP M
JC SAMTK1
LHLD CURTRK
INX H
SHLD CURTRK
XRA A
STA SECNO
CALL DOTRK
SAMTK1: LXI H,LSEC
INR M
MOV A,M
ADD A
ADD A ;TIMES 4ENT/TRK
DCR A
LXI H,DIRENT
CMP M
JNZ SAP1
;
CALL CLEAN ;CLEAN THE DIRECTORY
CALL SORT ;SORT THE DIRECTORY
CALL PACK ;PACK THE DIRECTORY
XRA A ;SECNO = 0 LOGICAL
STA SECNO
STA LSEC
LHLD TKOFFS
SHLD CURTRK
CALL DOTRK
LXI H,BUF ;ADDR = FWA OF BUFFER
SHLD ADDR
;
SAP2: CALL XLATS
LHLD ADDR ;SET DMA ADDRESS TO "ADDR"
MOV B,H
MOV C,L
MVI E,SETDMA
CALL XCPM
MVI E,WRITE
CALL XCPM ;WRITE SECTOR TO DISK
LHLD ADDR ;ADDR = ADDR + 80H
LXI D,128
DAD D
SHLD ADDR
LDA SECNO ;SECNO = SECNO + 1
INR A
STA SECNO
LXI H,SPERT
CMP M
JC SAMTK2
LHLD CURTRK
INX H
SHLD CURTRK
XRA A
STA SECNO
CALL DOTRK
SAMTK2: LXI H,LSEC
INR M
MOV A,M
ADD A
ADD A
DCR A
LXI H,DIRENT
CMP M
JNZ SAP2
JMP 0 ;EXIT TO CP/M WARM BOOT
;
DOTRK: MOV B,H
MOV C,L
MVI E,SETTRK
JMP XCPM
;
CLEAN: MVI A,0 ;I = 0
CLEAN1: STA I
CALL INDEX ;HL = BUF + 32 * I
MOV A,M ;JUMP IF THIS IS A DELETED FILE
CPI 0E5H
JZ CLEAN2
LXI D,9 ;OFFSET TO R/O FLG
DAD D
MOV A,M
ANI 80H
JNZ CLEAN4
LXI D,6 ;HL = HL + 6
DAD D
MOV A,M ;CHECK RECORD COUNT FIELD
ORA A
JNZ CLEAN4 ;JUMP IF NON-ZERO
CLEAN2: LDA I ;CLEAR ALL 32 BYTES OF
CALL INDEX ; DIRECTORY ENTRY TO E5
MVI C,32
CLEAN3: MVI M,0E5H
INX H
DCR C
JNZ CLEAN3
CLEAN4: LDA I ;I = I + 1
LXI H,DIRENT
CMP M
RZ
INR A
JMP CLEAN1
;
XLATS: LDA VERFLG
ORA A
LDA SECNO
JNZ XLT2
LXI H,LPMAP
ADD L
MOV L,A
JNC NOCRY
INR H
NOCRY: MOV C,M
XLT3: MVI E,SETSEC
JMP XCPM
;
XLT2: MOV C,A
MVI B,0
LHLD 1
LXI D,XLT
DAD D
LXI D,XRSLT
PUSH D ;FAKE CALL
XCHG
LHLD ADMAP
XCHG
PCHL
;
XRSLT: MOV C,L
JMP XLT3
;
ADMAP: DW LPMAP
;
LPMAP: DB 01,07,13,19,25,05,11,17,23,03,09,15,21
DB 02,08,14,20,26,06,12,18,24,04,10,16,22
COMP: LDA I ;HL = BUF + 32 * I
CALL INDEX
PUSH H
LDA J ;HL = BUF + 32 * J
CALL INDEX
XCHG
POP H
MVI C,13 ;NUMBER OF BYTES TO COMPARE
COMP1: MOV A,M ;GET NEXT BYTE
ANI 7FH ;REMOVE ATTRIBUTE
MOV B,A
LDAX D ;COMPARE NEXT BYTE
ANI 7FH ;REMOVE ATTRIBUTES
CMP B
RNZ ;RETURN IF NOT EQUAL
INX D
INX H
DCR C ;LOOP THRU FIRST 13 BYTES
JNZ COMP1
XRA A ;CLEAR FLAGS AND EXIT
RET
SORT: MVI A,0 ;I = 0
STA I
SORT1: LDA I ;J = I + 1
INR A
STA J
SORT2: CALL COMP ;IF NAME(J)<NAME(I), SWAP
CC SWAP
LDA J ;J = J + 1
INR A
STA J
JZ SORT3
LXI H,DIRENT
CMP M
JNZ SORT2
SORT3: LDA I ;I = I + 1
INR A
STA I
LXI H,DIRENT
RZ
CMP M
JC SORT1
RET
SWAP: LDA I
CALL INDEX
PUSH H
LDA J
CALL INDEX
XCHG
POP H
MVI C,32
SWAP1: LDAX D
MOV B,A
MOV A,M
STAX D
MOV M,B
INX D
INX H
DCR C
JNZ SWAP1
RET
INDEX: MOV L,A
MVI H,0
DAD H
DAD H
DAD H
DAD H
DAD H
LXI D,BUF
DAD D
RET
PACK: MVI A,0 ;I = 0
PACK1: STA I
CALL INDEX ;HL = BUF + 32 * I
MOV A,L ;HL = HL + 9
ADI 9
MOV L,A
JNC $+4
INR H
MOV A,M ;JUMP IF FILETYPE NOT 'X$$'
SUI '0' ; WHERE 0.LE.X.LE.9
JC PACK2
CPI 10
JNC PACK2
STA J
INX H
MOV A,M
CPI '$'
JNZ PACK2
INX H
MOV A,M
CPI '$'
JNZ PACK2
INX H ;SET EXTENT NUMBER TO X
LDA J
MOV M,A
DCX H ;SET FILETYPE TO '$$$'
MVI M,'$'
DCX H
MVI M,'$'
DCX H
MVI M,'$'
PACK2: LDA I ;I = I + 1
LXI H,DIRENT
CMP M
RZ
INR A
JMP PACK1
;
XCPM: MVI D,0 ;CLEAR HI BYTE
LHLD 1 ;WARM BOOT VECT ADDR
DAD D ;CALC VECTOR
PCHL
;
; DATA AREA
CURTRK: DW 2
SPERT DW 26 ;1.4 DEFLT
DIRENT: DW 63 ;1.4
TKOFFS: DW 2 ;1.4
VERFLG: DB 0
LSEC: DB 0
STACK: DS 32
SECNO: DS 1
ADDR: DS 2
I: DS 1
J: DS 1
DS 1 ;MAKE EVEN
BUF: DS 1
;
END