Digital Research
This commit is contained in:
2020-11-06 18:50:37 +01:00
parent 621ed8ccaf
commit 31738079c4
8481 changed files with 1888323 additions and 0 deletions

View File

@@ -0,0 +1,578 @@
; title 'Serialization Program for MP/M-86 09/14/81'
version equ 20 ;version 2.0
system equ 1 ;MP/M 86 system
; Serialization Program for MP/M 86 diskettes
; Note **********************************************************
; This program contains Digital Research proprietary information,
; and must not be reproduced, copied, or transcribed in any form
; whatsoever
; ***************************************************************
; Copyright (C) 1979, 1980, 1981
; Digital Research
; Box 579 Pacific Grove
; California, 93950
; Revised:
; 14 Sept 81 by Thomas Rolander (MP/M II 8080)
; 18 Sept 81 by Danny Horovitz (MP/M-8086)
; '$' signs taken out of identifiers and labels for
; ASM86 compatibility, names of serialized
; programs changed, only one disk to be serialized
tpa equ 100h ;transient program area
org tpa
jmp start
Copyright:
db 'COPYRIGHT (C) 1981,'
db ' DIGITAL RESEARCH '
CoNmLen equ $-Copyright
;
; global equates
boot equ 0000h
bdos equ 0005h
;
; BDOS equates
conin equ 1 ;read console device
conout equ 2 ;write console device
pbuff equ 9 ;print buffer
rdbuff equ 10 ;read buffer
resetds equ 13 ;reset disk system
selectd equ 14 ;select disk
openf equ 15 ;open file
rdseqf equ 20 ;read sequential file
wrseqf equ 21 ;write sequential file
stdmadr equ 26 ;set DMA address
; Hardware dependent equates
begtrk equ 0 ;beginning track #
dirtrk equ 2 ;directory track #
maxtrk equ 76 ;maximum track #
sectrk equ 26 ;sectors per track
srcdsk equ 2 ;source disk
dstdsk equ 3 ;destination disk
secsiz equ 128 ;sector size in # bytes
nsrlsec equ 4 ;# of sectors to search serial #
cr equ 0dh
lf equ 0ah
;
readtrk equ $
writtrk equ $+3
reread equ $+6
; track read/write routines, filled in later
jmp readdisk
jmp writedisk
jmp rereaddisk
track: ds 1 ;set to track to read/write
buffa: ds 2 ;set to buffer address to read/write
iof: ds 1 ;io function 0 = read, 1 = write
;
readdisk:
;read disk drive a, from track 'track'
;into the address given by 'buffa'
mvi a,srcdsk! call sel ;select src drive
jmp readd
;
;
writedisk:
;write to disk drive b, to track 'track'
;from the address given by 'buffa'
mvi a,1! sta iof ;set iofunction to write
mvi a,dstdsk! call sel ;select dst drive
jmp rwdisk
;
rereaddisk:
;read from dstdsk, from track 'track'
;to the address given by 'buffa'
mvi a,dstdsk! call sel ;dst drive selected
readd: xra a! sta iof ;set to read function
rwdisk: ;read or write disk
lxi h,track! mov c,m ;get track number
call trk ;track selected
lhld buffa ;get dma address
lxi d,sectrk ;d = 0, e = sectors per track
rwloop: ;read/write loop
inr d ;to next sector
push d! push h! mov c,d! mvi b,0
lxi h,skewtbl! mov a,m! ora a
jz noskew ;jump if no skew table
dcr c! dad b! mov c,m
noskew:
call sec ;sector set
pop b! push b ;get dma address
call dma ;dma address set
;perform io function
lda iof! ora a ;0=read, 1=write
jnz writefunc
;read disk
call dread
jmp rwcomplete
writefunc:
;write disk
call dwrite
rwcomplete: ;function complete
pop h ;recall dma address
lxi d,secsiz! dad d ;to nxt dma
pop d ;recall sector and count
; check error conditions
ora a! rnz ;rtn with non zero flag set
dcr e ;count = count - 1
jnz rwloop ;for another sector
ret ;with zero flag set for io complete
;
;
; utility subroutines for direct disk io
wboot equ 1 ;warm boot address
seldsk equ 24 ;select disk
settrk equ 27 ;set track
setsec equ 30 ;set sector
setdma equ 33 ;set dma address
readf equ 36 ;read disk
writf equ 39 ;write disk
;
sel: ;select drive given by register a
mov c,a! lhld wboot! lxi d,seldsk! dad d! pchl
;
trk: ;set track given by c
lhld wboot! lxi d,settrk! dad d! pchl
;
sec: ;set sector given by c
lhld wboot! lxi d,setsec! dad d! pchl
;
dma: ;set dma address to value of b,c
lhld wboot! lxi d,setdma! dad d! pchl
;
dread: ;perform read operation
lhld wboot! lxi d,readf! dad d! pchl
;
dwrite: ;perform write operation
lhld wboot! lxi d,writf! dad d! pchl
;
start:
lxi sp,stack
call signonmsg ;display sign on message
call sysdskmsg! call ci ;system disk serialize ?
ani 0dfh! cpi 'Y'! mvi a,dirtrk
jnz sd1
lxi h,sysdsk! inr m! mvi a,begtrk
sd1: sta strtrk
call dskslctmsg! call read ;select 1/2, 2/2, or 1/2 & 2/2
lxi h,disk! mov m,c
call orgmsg! call read ;origin prompt
lxi h,origin! mov m,c ;saved the origin number
inx h! mov m,b ;high order origin number byte
lxi h,comlen! mov b,m! inx h! xchg
lxi h,aorigin ;ascii version of the origin
org2: ldax d! ora a! jz org3
inx d! mov m,a! inx h! dcr b! jnz org2
;ascii version moved to buffer, pad it
org3: mvi m,'-'! inx h! mvi m,'$' ;ready for printing
;
; now read the serial number
call sermsg! call read
lxi h,bserial! mov m,c! inx h! mov m,b ;binary copied
lxi h,comlen! mvi a,5! sub m ;difference in reg-a
lxi h,aserial! jz pad1 ;pad high order positions with 0
pad0: mvi m,'0'! inx h! dcr a! jnz pad0
pad1: lxi d,cbuff ;addressing buffer
pad2: ldax d! ora a! jz pad3 ;looking for binary 0
mov m,a! inx h! inx d! jmp pad2 ;another char
pad3: ;end of ascii fill (right adjusted in aserial)
;
rddsk: ;read disk and copy
lxi sp,stack ;reset stack pointer (entry from errors)
call insmsg! call ci ;wait for response
;
nextdisk:
call curmsg! call asermsg! call newmsg! call ci
;new disk is ready, try the copy operation
lda strtrk ;get start track
lxi h,track! mov m,a ;initialize the track number
lxi h,trcount! mvi m,'0'! inx h! mvi m,'0'
;
rdtrk: ;read the next source track, compare with 0e5h for end
lxi h,ibuff! shld buffa! call readtrk
jz readok! call read0msg! jmp rddsk
readok:
;track is in memory, track 0?
lda track! ora a
;if track 0, do MPMLDR serialization
cz serialize
;
;track in memory, check for last track
lxi h,ibuff! lxi b,trlen
trcomp: mvi a,0e5h! cmp m! jnz wrtrk
inx h! dcx b! mov a,c! ora b
jnz trcomp
;end of copy, all 0e5h's
endcopy:
;write serial # into files in FCB table
lda sysdsk! ora a! lxi h,FCBtabledisk1
jz nonsysdsk! lxi h,FCBtablesysdisk1
nonsysdsk:
;write serial # into disk1
lda disk! ani 01h! cnz srlfile
;write serial # into disk2
lxi h,FCBtabledisk2
lda disk! ani 02h! cnz srlfile
lxi d,trmsg! call prmsg
call incserial! jmp nextdisk
;
;not end of copy, write track to disk from ibuff
wrtrk: call writtrk
jz wrok! call write0msg! jmp nextdisk
wrok:
;written to disk, now read it back and compare
lxi h,obuff! shld buffa! call reread
jz read1ok! call read1msg! jmp nextdisk
read1ok:
lxi h,ibuff! lxi d,obuff! lxi b,trlen
wrcomp: ldax d! cmp m! jnz wrerr
inx h! inx d! dcx b! mov a,c! ora b
jnz wrcomp
;compare ok, increment track count and cycle
lxi h,track! inr m
mvi a,maxtrk+1! cmp m
;jump if last track on disk copied
jz endcopy
lxi h,trcount+1! inr m! mov a,m! cpi '9'+1
jc rdtrk ;overflow to high order track number
mvi m,'0'! dcx h! inr m! jmp rdtrk
;
wrerr: ;verify error
call vererr! jmp nextdisk
;
;
; utility subroutines
ci: mvi c,conin! jmp bdos ;read a character
;
prmsg: mvi c,pbuff! jmp bdos ;print a buffer
;
rderr: call invalid
;
read: ;read constant value to b,c
lxi d,maxlen! mvi c,rdbuff! call bdos ;buffer filled
lxi h,comlen! mov a,m! ora a! jz rderr ;non zero length
inx h! mov e,a! mvi d,0! dad d ;h,l address last pos+1
mvi m,0 ;cleared for end of scan
lxi h,cbuff! lxi b,0
conv: mov a,m! ora a! rz ;return if end of convert
sui '0'! cpi 10! jnc rderr
push h! push b! pop h ;b,c copied to h,l
dad h! dad h! dad h! dad b! dad b
push h! pop b! pop h ;bc=bc*10
inx h! add c! mov c,a! mvi a,0! adc b! mov b,a
jc rderr! jmp conv ;tested for overflow
;
incserial:
;increment the serial number
lhld bserial! inx h! shld bserial ;test for overflow
mov a,l! ora h! jz serover
;
lxi h,aserial+4! mvi b,5 ;length of serial number
inc0: inr m! mov a,m! cpi '9'+1! rc ;return if carry
mvi m,'0' ;clear the number
dcx h! dcr b! jnz inc0
;
serover:
;overflow in serial number
call overmsg
jmp boot
;
serialize:
;match ' DIGITAL RESEARCH ' and update serial #
lxi h,ibuff! lxi b,nsrlsec*secsiz
search: push h! push b
lxi d,Copyright! mvi c,CoNmLen
comp0: ldax d! cmp m
jnz nomatch
inx h! inx d! dcr c! jnz comp0
;match complete, we've found the serial number
pop b! pop d ;clears stack
xchg! lhld origin! xchg! mov m,e ;low byte origin
inx h! mvi m,version ;version number in binary
inx h! mvi m,system ;system number in binary
inx h! mov m,d ;high byte origin number
inx h ;get the serial number
xchg! lhld bserial! xchg
mov m,d! inx h! mov m,e
;MPMLDR serial number is copied
ret
;
nomatch: ;try for next match
pop b! pop h! inx h! dcx b! mov a,c! ora b
jnz search
;not found
call noserial! jmp rddsk
;
rdwrsrlfl:
sta iof ;save rdseqf / wrseqf func code
push d! push h
lxi d,32! dad d! mvi m,0 ;set nr = 0
pop h! pop d! mvi b,nsrlsec ;count = 4 sectors
flrdwr:
push b! push d! push h
mvi c,stdmadr! call bdos
pop d! push d
lda iof! mov c,a! call bdos
pop h! pop d! pop b
inr a! jz srlflerr
dcr b! rz
push h! lxi h,secsiz! dad d
xchg! pop h
jmp flrdwr
srlflerr:
call badMPM! jmp rddsk
;
srlfile:
;update serial # in all files in the FCB table
;HL = FCBTable address
shld FCBtableadr
;reset disk system
push h!mvi c,resetds! call bdos! pop h
srlflopn:
mov a,m! ora a! jz srlflrdwrvr
push h! xchg! mvi c,openf
call bdos ;open next file from FCB Table
pop h! inr a! jz srlflerr
lxi d,33! dad d! jmp srlflopn
srlflrdwrvr:
lhld FCBtableadr
flrdwrvr:
mov a,m! ora a! rz
push h
srlflrd:
lxi d,ibuff ;dma buffer is ibuff
mvi a,rdseqf! call rdwrsrlfl
srlflwr:
call serialize ;patch in serial #
pop h! push h
lxi d,ibuff ;dma buffer is ibuff
mvi a,wrseqf! call rdwrsrlfl
srlflvr:
pop h! push h
lxi d,obuff ;dma buffer is obuff
mvi a,rdseqf! call rdwrsrlfl
lxi h,ibuff! lxi d,obuff! lxi b,nsrlsec*secsiz
flvr:
ldax d! cmp m
jnz srlflerr
inx h! inx d! dcx b
mov a,b! ora c
jnz flvr
pop h! lxi d,33! dad d
jmp flrdwrvr
;
FCBtablesysdisk1:
;
; MPM.SYS
db dstdsk+1 ;drive code
db 'MPM ' ;file name
db 'SYS' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
FCBtabledisk1:
; SUP.MPM
db dstdsk+1 ;drive code
db 'SUP ' ;file name
db 'MPM' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
; RTM.MPM
db dstdsk+1 ;drive code
db 'RTM ' ;file name
db 'MPM' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
; MEM.MPM
db dstdsk+1 ;drive code
db 'MEM ' ;file name
db 'MPM' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
; CIO.MPM
db dstdsk+1 ;drive code
db 'CIO ' ;file name
db 'MPM' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
; BDOS.MPM
db dstdsk+1 ;drive code
db 'BDOS ' ;file name
db 'MPM' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
; GENSYS.CMD
db dstdsk+1 ;drive code
db 'GENSYS ' ;file name
db 'CMD' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
; MPMLDR.CMD
db dstdsk+1 ;drive code
db 'MPMLDR ' ;file name
db 'CMD' ;file type
db 0 ;extent
ds 2
db 0 ;record count
ds 16 ;allocation map
db 0 ;next record
;
db 0 ;end of FCB Table
;
;
FCBtabledisk2:
; if files on second disk are to be serialized
; put their FCBs here
db 0 ;end of FCB Table
; print strings
insmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Insert control diskette in '
db 'A'+srcdsk
db ':, type return$'
;
signonmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'MP/M-86 V'
db version/10+'0','.',version mod 10 +'0'
db ' Serialization',cr,lf,'$'
;
sysdskmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'System disk (Y/N)? $'
;
dskslctmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Select type of disk serialization:'
db cr,lf,' 1 = Disk 1/2'
db cr,lf,' 2 = Disk 2/2'
db cr,lf,' 3 = Disk 1/2 & 2/2'
db cr,lf,'?$'
;
orgmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Origin number? $'
;
sermsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Starting serial number? $'
;
invalid:
lxi d,$+6! jmp prmsg
db cr,lf,'Invalid number, try again $'
;
curmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Serializing disk $'
;
asermsg:
lxi d,aorigin! call prmsg
lxi d,aserial! jmp prmsg
;
newmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Insert new diskette in '
db 'A'+dstdsk
db ':, type return$'
;
noserial:
lxi d,$+6! jmp prmsg
db cr,lf,'Non MP/M-86 diskette, cannot serialize$'
;
badMPM:
lxi d,$+6! jmp prmsg
db cr,lf,'Bad MP/M-86 files on disk$'
;
vererr:
lxi d,$+6! jmp prmsg
db cr,lf,'Verification error, bad disk$'
;
overmsg:
lxi d,$+6! jmp prmsg
db cr,lf,'Serial number overflow$'
read0msg:
lxi d,$+6! jmp prmsg
db cr,lf,'Error on source disk, replace$'
;
write0msg:
lxi d,$+6! jmp prmsg
db cr,lf,'Cannot write new disk, replace$'
;
read1msg:
lxi d,$+6! jmp prmsg
db cr,lf,'Cannot re-read new disk, replace$'
;
;
; miscellaneous data areas
;
disk: ds 1 ;1=1/2, 2=2/2, 3=1/2 & 2/2
sysdsk: db 0 ;0ffh="system disk"
strtrk: ds 1 ;start track, begtrk or dirtrk
FCBtableadr: ds 2 ;FCB table address
origin: ds 2 ;binary origin
aorig: db cr,lf
aorigin:
db '00000-$'
trmsg: db cr,lf
trcount:
db '00 tracks verified$'
bserial:
ds 2 ;binary serial number
aserial:
db '00000$'
; skew table (first byte 0 if no skewing)
skewtbl:
db 0 ;no skew table for MDS-800
; input buffer
maxlen: db 7
comlen: ds 1
cbuff: ds 8
;
ds 32 ;stack
stack:
trlen equ sectrk*secsiz ;buffer size
ibuff: ds trlen
obuff: ds trlen
db 1 ;force hex generation
end