home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.barnyard.co.uk
/
2015.02.ftp.barnyard.co.uk.tar
/
ftp.barnyard.co.uk
/
cpm
/
walnut-creek-CDROM
/
CPM
/
UTILS
/
HDUTL
/
TOHARD.ASM
< prev
next >
Wrap
Assembly Source File
|
2000-06-30
|
8KB
|
385 lines
;
; TOHARD.ASM ver 1.2
; by Keith Petersen, W8SDZ
; (revised 9/26/80)
;
;This program will transfer files from CP/M on floppy disks
;to CP/M on hard disk. (It can also be used for transfers
;from 5-1/4" minifloppy to 8" floppy.)
;
;To do this you must bring up the floppy CP/M as a small
;system (say 24k). The system location isn't important so
;long as it does not overwrite the larger system in use by
;the hard disk. It is assumed that the user's system allows
;both disk controller boards to be used without conflict.
;
;
; USING THIS PROGRAM
;
; 1 - Bring up the hard disk CP/M as a large system (eg. 56k).
; 2 - Log into the drive you will be transferring files to.
; 3 - Cold boot the floppy CP/M, then run this program on it.
;
;COMMANDS:
; TOHARD filename.type ;gets file from default drive
; TOHARD B:filename.type ;gets file from B:
; TOHARD *.* ;gets all files
; TOHARD B:*.* ;gets all files from B:
;
;All normal ambiguous file names are allowed. Files written to
;the hard disk will go to the default drive.
;
FALSE EQU 0
TRUE EQU NOT FALSE
;
;CONDITIONAL ASSEMBLY SWITCHES FOR CPn to
;the hard disk will go to the default drive.
;
FALSE EQU 0
TRUE EQU NOT FALSE
;
;CONDITIONAL ASSEMBLY SWITCHES FOR CP/M VERSION
; (only one should be true)
;
CPM14 EQU FALSE ;CP/M VERSION 1.4
CPM2 EQU TRUE ;CP/M VERSION 2.x
;
;OTHER CONDIT/M VERSION
; (only one should be true)
;
CPM14 EQU FALSE ;CP/M VERSION 1.4
CPM2 EQU TRUE ;CP/M VERSION 2.x
;
;OTHER CONDITIONAL ASSEMBLY SWITCHES
;
DJ2D EQU FALSE ;TRUE IF BIG SYSTEM IS DISCUS 2D FLOPPY
REPORT EQU FALSE ;TRUE TO REPORT READS AND WRITES
;(nice, but slows down transfers)
;
;EQUATES
;
MSIZE EQU 56 ;PUT BIG SYSTEM MEMORY SIZE HERE
;
IF CPM14
BIAS EQU (MSIZE-16)*1024
CCP EQU BIAS+2900H ;BASE OF CCP
ENDIF ;CP/M 1.4
;
IF CPM2 AND (NOT DJ2D)
BIAS EQU (MSIZE-20)*1024
CCP EQU BIAS+3400H ;BASE OF CCP
ENDIF ;STANDARD CP/M 2.x
;
IF CPM2 AND DJ2D
BIAS EQU (MSIZE-20)*1024
CCP EQU BIAS+2D00H ;BASE DISCUS 2D CCP
ENDIF ;CP/M 2.x ON DISCUS 2D
;
DEST$BDOS EQU CCP+806H ;RECEIVING BDOS VECTOR
;
BELL EQU 7 ;BELL CHARACTER
TAB EQU 9 ;TAB CHARACTER
CR EQU 0DH ;CARRIAGE RETURN
LF EQU 0AH ;LINE FEED
;
;BDOS/CBIOS EQUATES
;
WBOOT EQU 0 ;WARM BOOT ENTRY ADRS
WRCON EQU 2 ;WRITE CHARACTER TO CONSOLE
BDOS EQU 0005H ;THE SENDING BDOS VECTOR
PRINT EQU 9 ;PRINT STRING (DE) UNTIL '$'
OPEN EQU 15 ;OPEN FILE
CLOSE EQU 16 ;CLOSE FILE
SRCHF EQU 17 ;SEARCH DIR FOR FIRST OCCUR.
SRCHN EQU 18 ;SEARCH DIR FOR NEXT OCCUR.
DELETE EQU 19 ;ERASE FILE
READ EQU 20 ;READ RECORD
WRITE EQU 21 ;WRITE RECORD
MAKE EQU 22 ;MAKE FILE
STDMA EQU 26 ;SET DMA ADRS
FCB EQU 5CH ;DEFAULT FILE CONTROL BLOCK
FCBEXT EQU FCB+12 ;EXTENT BYTE IN FCB
FCBRNO EQU FCB+32 ;RECORD NUMBER IN FCB
;
NOERR EQU 0 ;NO ERROR
EOF EQU 1 ;END OF FILE
NTFND EQU 255 ;NOT FOUND
NOMAKE EQU 255 ;CAN'T MAKE FILE
BDCLOS EQU 255 ;BAD FILE CLOSE
;
; THIS IS THE START OF THE PROGRAM.
;
ORG 100H
;
START LDA FCB+1
CPI ' ' ;SEE IF FILENAME THERE
JNZ SIGNON
CALL ILPRT ;PRINT:
DB CR,LF,'++NO FILE NAME SPECIFIED++',0
RET ;EXIT TO CP/M
;
SIGNON: LXI SP,STACK ;SET STACK POINTER
CALL ILPRT ;PRINT:
DB CR,LF,'FLOPPY to HARD DISK',CR,LF
DB 'multiple file transfer program',CR,LF,0
MORE: CALL MFNAME ;SEE IF FILE IS IN DIRECTORY
JNC MOVNAM ;ANOTHER FILE FOUND, GET IT
LDA MFFLG1 ;NOTHING FOUND, CHECK...
ORA A ;... FIRST TIME FLAG
JZ DONE ;AT LEAST ONE WAS FOUND
CALL EXIT
DB '++FILE NOT FOUND++$'
;
DONE: CALL EXIT
DB CR,LF,'DONE$'
;
;MOVE FILENAME FROM FCB TO FNAME AND PRINT IT
;
MOVNAM: LXI H,FCB+1
LXI D,FNAME
MVI B,8 ;8 CHARS IN FILE NAME
CALL MOVER
LXI H,FCB+9
LXI D,FNAME+9
MVI B,3 ;3 CHARS IN FILE TYPE
CALL MOVER
CALL ILPRT ;PRINT:
DB CR,LF,'--> FILE: '
FNAME: DB 'XXXXXXXX.XXX'
DB CR,LF,0
;
;SAVE FIRST FCB FOR USE LATER AS DESTINATION FILE NAME
MVI B,11 ;NUMBER OF CHARACTERS TO MOVE
LXI H,FCB+1 ;...FROM FIRST FCB
LXI D,NEWFCB+1 ;...TO NEWFCB (USE DEFAULT DRIVE)
CALL MOVER
;
;OPEN THE SOURCE FILE
LXI D,FCB
MVI C,OPEN
CALL BDOS
CPI NTFND ;NOT FOUND?
JNZ OPENOK
CALL EXIT
DB BELL
DB '++CAN''T OPEN FILE ON SOURCE DISK++$'
;
;OPEN THE DESTINATION FILE
;
OPENOK: CALL ILPRT ;PRINT:
DB 'Opening file on destination disk',0
LXI D,NEWFCB
MVI C,DELETE ;ERASE ANY OLD FILE
CALL DEST$BDOS
LXI D,NEWFCB
MVI C,MAKE ;MAKE THE NEW ONE
CALL DEST$BDOS
CPI NOMAKE
JNZ RDLOOP
CALL EXIT
DB BELL
DB '++CANNOT CREATE FILE ON DESTINATION DISK++$'
;
;READ A SECTOR FROM SMALL DISK
;
RDLOOP: EQU $
;
IF REPORT
CALL ILPRT ;PRINT:
DB TAB,'Reading sector from source disk',0
ENDIF ;REPORT
;
LXI D,80H
MVI C,STDMA ;SET DMA TO 80H
CALL BDOS
LXI D,FCB
MVI C,READ ;READ A RECORD
CALL BDOS
CPI NOERR
JZ WRLOOP ;NO ERROR, GO WRITE SECTOR
CPI EOF
JZ TDONE ;END OF FILE, GO CLOSE IT
CALL EXIT
DB BELL
DB '++READ ERROR ON SOURCE DISK++$'
;
;WRITE A SECTOR TO BIG DISK
;
WRLOOP: EQU $
;
IF REPORT
CALL ILPRT ;PRINT:
DB TAB,'Writing sector to destination disk',0
ENDIF ;REPORT
;
LXI D,80H
MVI C,STDMA ;SET DMA TO 80H
CALL DEST$BDOS
LXI D,NEWFCB
MVI C,WRITE ;WRITE A RECORD
CALL DEST$BDOS
CPI NOERR
JZ RDLOOP
CALL EXIT
DB BELL
DB '++WRITE ERROR ON DESTINATION DISK++$'
;
TDONE: CALL ILPRT ;PRINT:
DB 'Closing file on destination disk now',0
LXI D,NEWFCB
MVI C,CLOSE ;CLOSE DESTINATION FILE
CALL DEST$BDOS
CPI BDCLOS
JNZ MORE ;ANOTHER FILE?
CALL EXIT
DB BELL
DB '++BAD CLOSE ON DESTINATION DISK++$'
;
;PRINT MESSAGE THEN EXIT TO CP/M WARM BOOT
;
EXIT: POP D
MVI C,PRINT
CALL BDOS
JMP WBOOT
;
;INLINE PRINT ROUTINE
;
ILPRT XTHL ;SAVE HL, GET MSG
;
ILPLP MOV A,M ;GET CHAR
CALL TYPE ;OUTPUT IT
INX H ;POINT TO NEXT
MOV A,M ;TEST
ORA A ;..FOR END
JNZ ILPLP
MVI A,CR ;CARRIAGE RETURN
CALL TYPE
MVI A,LF ;LINE FEED
CALL TYPE
XTHL ;RESTORE HL, RET ADDR
RET ;RET PAST MSG
;
TYPE PUSH B
PUSH D
PUSH H
MOV E,A ;CHAR TO E FOR CP/M
MVI C,WRCON ;WRITE TO CONSOLE
CALL BDOS
POP H
POP D
POP B
RET
;
;MULTI-FILE ACCESS SUBROUTINE. ALLOWS PROCESSING
;OF MULTIPLE FILES (I.E. *.ASM) FROM DISK. THIS
;ROUTINE BUILDS THE PROPER NAME IN THE FCB EACH
;TIME IT IS CALLED. CARRY IS SET IF NO MORE NAMES
;CAN BE FOUND. THE ROUTINE IS COMMENTED IN PSEUDO
;CODE, EACH PSEUDO CODE STATEMENT IS IN <<...>>
;
MFNAME: ;<<INIT DMA ADDR, FCB>>
MVI C,STDMA
LXI D,80H
CALL BDOS
XRA A
STA FCBEXT
STA FCBRNO
;<<IF FIRST TIME>>
LDA MFFLG1
ORA A
JZ MFN01
;<<SAVE THE REQUESTED NAME>>
;SAVE ORIG REQ
LXI H,FCB
LXI D,MFREQ
MVI B,12
CALL MOVER
LDA FCB
STA MFCUR ;SAVE DISK IN CURR FCB
;<<SRCHF REQ NAME>>
LXI H,MFREQ
LXI D,FCB
MVI B,12
CALL MOVER
MVI C,SRCHF
LXI D,FCB
CALL BDOS
;<<ELSE>>
JMP MFN02
;
MFN01: ;<<SRCHF CURR NAME>>
LXI H,MFCUR
LXI D,FCB
MVI B,12
CALL MOVER
MVI C,SRCHF
LXI D,FCB
CALL BDOS
;<<SRCHN REQ NAME>>
LXI H,MFREQ
LXI D,FCB
MVI B,12
CALL MOVER
MVI C,SRCHN
LXI D,FCB
CALL BDOS
;<<ENDIF>>
MFN02: ;<<RETURN CARRY IF NOT FOUND>>
INR A
STC
RZ
;<<MOVE NAME FOUND TO CURR>>
DCR A
ANI 3
ADD A
ADD A
ADD A
ADD A
ADD A
ADI 81H
MOV L,A
MVI H,0
PUSH H ;SAVE NAME POINTER
LXI D,MFCUR+1
MVI B,11
CALL MOVER
;<<MOVE NAME FOUND TO FCB>>
POP H
LXI D,FCB+1
MVI B,11
CALL MOVER
;<<SETUP FCB>>
XRA A
STA FCBEXT
STA FCBRNO
STA NEWFCB
STA NEWFCB+12
STA NEWFCB+32
STA MFFLG1 ;TURN OFF 1ST TIME SW
;<<RETURN>>
RET
;------------------------------------------------
;
;MOVE SUBROUTINE MOVE (B) BYTES FROM (HL) TO (DE)
;
MOVER MOV A,M
ANI 7FH ;STRIP CP/M 2.x ATTRIBUTES
STAX D
INX H
INX D
DCR B
JNZ MOVER
RET
;
;MULTI-FILE ACCESS WORK AREA
;
MFFLG1 DB 1 ;1ST TIME SW
MFREQ DS 12 ;REQ NAME
MFCUR DS 12 ;CURR NAME
;
NEWFCB DS 33
STACK EQU $+100
;
END