home *** CD-ROM | disk | FTP | other *** search
- ; 10/12/79: 1140
- ; P.P.H. LEE,
- ; ROYAL MELBOURNE INSTITUTE OF TECHNOLOGY,
- ; APPLIED PHYSICS DEPARTMENT,
- ; 124 LATROBE STREET, MELBOURNE,
- ; VICTORIA 3000, AUSTRALIA.
-
- ; PROGRAM TO TRANSFER AN FDOS II FILE ON DISK DRIVE B:
- ; TO CP/M FILE IN DISK DRIVE A:
- ; TO USE THE PROGRAM, TYPE FDOS-CPM NFN, WHERE NFN IS A
- ; NEW CP/M FILE THAT THE FDOS FILE IS TO BE TRANSFERED
- ; INTO. THE PROGRAM WILL ASK FOR THE FDOS FILENAME,
- ; WHICH MUST BE 5 CHARACTERS LONG MAXIMUM, WITHOUT
- ; DRIVE NUMBER (IT ASSUMES DRIVE #1 ALLWAYS), FOLLOWED
- ; BY A <CR>.
- ; AT THE COMPLETION OF THE TRANSFER, IT WILL REBOOT BACK
- ; TO CP/M.
-
- ; EXTERNAL LINKAGES:
- TFCB EQU 5CH ; CP/M FCB ADDRESS
- BOOT EQU 0 ; CP/M WARM BOOT
- BDOS EQU 5 ; CP/M BDOS JUMP ADDRESS
- PBUF EQU 9 ; CP/M PRINT BUFFER CODE
- RDBUF EQU 10 ; CP/M READ BUFFER CODE
- MAKE EQU 22 ; CP/M MAKE FILE CODE
- CLOSE EQU 16 ; CP/M CLOSE FILE CODE
- STDMA EQU 26 ; CP/M SET DMA ADDRESS
- WRITE EQU 21 ; CP/M WRITE RECORD
- IUNIT EQU 0C433H ; FDOS INPUT FILE DRIVE NO.
- ISIZE EQU 0C434H ; FDOS INPUT FILE SIZE
- ITRK EQU 0C436H ; FDOS INPUT TRAK NUMBER
- ISCTR EQU 0C437H ; FDOS INPUT SECTOR NUMBER
- ICNTR EQU 0C438H ; FDOS INPUT BUFFER COUNTER
- FREAD EQU 0C033H ; FDOS READ SUBROUTINE
-
- ORG 100H
-
- LXI SP,STACK ; SET STACK POINTER
- LXI D,TFCB ; MAKE CP/M FILE
- MVI C,MAKE
- CALL BDOS
- CPI 0FFH ; ERROR?
- JZ MKERR ; BRIF IS
- LXI D,AFLNM ; ASK FOR FDOS FILENAME
- MVI C,PBUF
- CALL BDOS
- LXI H,TBUF ; GET FDOS FILENAME
- LXI B,0620H ; INTO IFLNM
- MOV M,B ; BUT FIRST SET LENGTH
- INX H ; AND CLEAR IT
- FNAME: MOV M,C ; WITH SPACES
- INX H ; POINT NEXT
- DCR B ; DECREMENT COUNTER
- JNZ FNAME ; LOOP UNTIL ALL DONE
- LXI D,TBUF ; NOW GET IT
- MVI C,RDBUF ; USING BDOS
- CALL BDOS ; READ BUFFER
- MVI A,1 ; SET INPUT TO DRIVE #1 (B:)
- STA IUNIT
- CALL FIND ; GET FDOS FILE
- ORA A ; FOUND IT?
- JNZ INERR ; BRIF NOT
- GET: LXI H,TBUF ; POINT TO BUFFER
- LXI D,TBEND ; END OF BUFFER
- GET1: CALL FREAD ; GET BYTE
- JC GET2 ; BRIF E-0-F
- MOV M,A ; PLACE IN BUFFER
- INX H ; POINT NEXT
- CALL CPHL ; CHECK IF END OF BUFFER YET
- JNZ GET1 ; BRIF NOT
- JMP GET3
- GET2: MVI A,0FFH ; SET FLAG
- STA TBFLG
- GET3: SHLD TBEND ; SET END OF BUFFER
- LOAD: LXI H,TBUF ; POINT TO START OF BUFFER
- SHLD TBDMA ; SAVE IT
- XCHG ; AND PLACE IN DE
- LOAD1: MVI C,STDMA ; SET DMA
- CALL BDOS
- LXI D,TFCB ; POINT TO FCB
- MVI C,WRITE ; LOAD TO CP/M FILE
- CALL BDOS ; A SECTOR AT A TIME
- ORA A ; ANY ERROR?
- JNZ MKERR ; BRIF IS
- LHLD TBDMA ; GET LAST DMA ADDRESS
- LXI D,128 ; CALCULATE NEXT
- DAD D ; DMA ADDRESS
- SHLD TBDMA ; SAVE IT
- XCHG ; PLACE IT IN DE
- LHLD TBEND ; GET END OF BUFFER ADDRESS
- CALL CPHL ; ALREADY THERE?
- JNZ LOAD1 ; BRIF NOT
- LDA TBFLG ; GET FLAG
- ORA A ; NO MORE?
- JZ GET ; BRIF STILL SOME MORE
- LXI D,TFCB ; POINT TO FCB
- MVI C,CLOSE ; CLOSE CP/M FILE
- CALL BDOS
- JMP BOOT ; AND REBOOT
-
- INERR: LXI D,NSFL ; PRINT NO SUCH FILE
- MVI C,PBUF
- CALL BDOS
- JMP BOOT
-
- MKERR: LXI D,ERMSG ; PRINT ERROR
- MVI C,PBUF ; MESSAGE
- CALL BDOS
- JMP BOOT ; AND REBOOT
-
- CPHL: MOV A,H ; COMPARE H
- CMP D ; WITH D
- RNZ ; RIF NOT EQUAL
- MOV A,L ; COMPARE L
- CMP E ; WITH E
- RET
-
- ; MESSAGES:
- NSFL: DB '* NO SUCH FDOS II FILE *',0DH,0AH,'$'
- ERMSG: DB '* CP/M DISK FULL *',0DH,0AH,'$'
- AFLNM: DB 'FDOS II FILENAME: $'
-
- ; SUBROUTINE TO SET ITRK, ISCTR, ISIZE & ICNTR READY TO
- ; START READING THE DIRECTORY TRAK OF AN FDOS II
- ; DISKETTE.
-
- INDEX: LXI H,24 ; 23 SECTORS
- SHLD ISIZE ; STORE IN ISIZE
- LXI H,ITRK ; POINT TO ITRK
- MVI M,0 ; TRAK # 0
- INX H
- LDA IUNIT ; GET INPUT DRIVE NO.
- INDX2: RRC ; ROTATE TO 2 MSB
- RRC
- ORI 03H ; INCORPORATE SECTOR # 3
- MOV M,A ; LOAD ISCTR
- INX H ; POINT TO ICNTR
- MVI M,0 ; RESET ICNTR
- RET
-
- ; SUBROUTINE TO SKIP READING N NUMBER OF BYTE,
- ; WHERE N IS IN E REGISTER.
-
- SKIPR: CALL FREAD
- DCR E ; DECREMENT COUNT
- JNZ SKIPR
- RET
-
- ; SUBROUTINE TO OBTAIN THE ADDRESS & SIZE OF THE FILE
- ; FROM THE DISKETTE DIRECTORY AND LOAD THEM INTO ITRK,
- ; ISCTR & ISIZE, ALSO RESETTING ICNTR TO ZERO.
-
- FIND: CALL CLEAR ; CLEAR READ BUFFER
- CALL INDEX
- SECTR: MVI D,11 ; 11 FCB PER SECTOR
- BLOCK: MVI E,11 ; 11 BYTES PER FCB
- LXI H,TBUF+1 ; GET FILE NAME
- MVI B,5 ; SET MATCH COUNTER
- CHECK: CALL FREAD
- JC NONE ; BRIF NO MATCH FOUND
- DCR E ; DECREMENT FCB BYTE COUNT
- INX H ; GET FILE-NAME
- CMP M ; COMPARE IT
- JZ MATCH
- CALL SKIPR ; NO MATCH, GET NEXT FCB
- DCR D ; DEC. BLOCK COUNT
- JNZ BLOCK ; CHECK FOR LAST FCB
- MVI E,7 ; GET NEXT SECTOR
- CALL SKIPR
- JMP SECTR ; LOOP
- MATCH: DCR B ; DEC. MATCH COUNTER
- JNZ CHECK ; BRIF INCOMPLETE MATCH
- CALL FREAD ; COMPLETE MATCH, SKIP ATTRIBUTE
- CALL FREAD ; GET REST OF INFO
- MOV B,A ; SAVE TRAK ADDRESS IN B
- CALL FREAD
- DCR A ; DEC SECTOR ADDRESS
- MOV C,A ; SAVE SECTOR IN C
- CALL FREAD
- MOV H,A ; SAVE SIZE IN H&L
- CALL FREAD
- MOV L,A
- SHLD ISIZE ; STORE SIZE IN ISIZE
- MOV A,B ; MOVE TRAK ADDR TO ACC
- STA ITRK ; LOAD ITRK
- LDA IUNIT ; GET DRIVE NO.
- RRC ; ROTATE TO 2 MSB
- RRC
- ORA C ; INCORPORATE DRIVE NO. & SECTOR
- STA ISCTR ; LOAD ISCTR
- RLC ; RESTORE UNIT # TO 2 LSB
- RLC
- STA IUNIT ; & REPLACE, INCL SECTOR ADDR
-
- ; SUBROUTINE TO CLEAR THE INPUT BUFFER
- CLEAR: LDA ICNTR ; GET ICNTR
- ORA A ; TEST IT
- RZ ; RET IF EMPTY
- CALL FREAD ; DUMMY READ
- JMP CLEAR ; LOOP
-
- NONE: MVI A,0FFH ; SET FLAG
- RET
-
- ; STORAGES:
- TBFLG: DB 0 ; FLAG: 00 - SOME MORE
- ; FF - NO MORE
- TBDMA: DS 2 ; DMA START ADDRESS
- STACK EQU $+64 ; STACK AREA
- TBUF EQU STACK ; START OF BUFFER
- TBEND EQU TBUF+(128*128) ; END OF BUFFER
- END
-