home *** CD-ROM | disk | FTP | other *** search
/ Oakland CPM Archive / oakcpm.iso / sigm / vol236 / loadsys.mac < prev    next >
Encoding:
Text File  |  1986-02-13  |  10.5 KB  |  355 lines

  1. ; program to load boot routines to tracks one & two
  2.  
  3.         title 'loadsys'
  4.         .z80
  5.  
  6. bdos    equ 5             ; cpm entry point
  7. cr      equ 0dh           ; carriage return
  8. lf      equ 0ah           ; line feed
  9. boot    equ 0             ; boot location
  10.  
  11. loadsy:                   ; entry point
  12.  
  13. ; check we have cpm3
  14.         ld c,12           ; to get version number
  15.         call bdos
  16.         ld a,l            ; version number in a
  17.         cp 30h            ; version 30 or later
  18.         jp c,oldver       ; jump if old version
  19.  
  20. ; read cpmldr
  21.         ld c,15           ; open file code
  22.         ld de,fcb         ; fcb address
  23.         call bdos
  24.         and a
  25.         jp nz,operr       ; jump if can't open file
  26.         ld de,cpmldr
  27.         ld c,26           ; set dma address
  28.         call bdos
  29.         ld e,26           ; set to read 26 sectors
  30.         ld c,44           ; multi-record read
  31.         call bdos
  32.         ld de,fcb
  33.         ld c,20           ; read instruction
  34.         call bdos
  35.         inc a
  36.         jp z,rderr        ; jump if read fails
  37.         ld e,1
  38.         ld c,44           ; to reset multi-record count
  39.         call bdos
  40.  
  41. ; message to load target disk
  42. ltd:    ld c,13           ; to reset disk system
  43.         call bdos
  44.         call clear
  45. rp:     ld de,lddm
  46.         ld c,9            ; output string code
  47.         call bdos
  48.         ld de,rbuff       ; read buff location
  49.         ld c,10           ; read buffer
  50.         call bdos
  51.         ld hl,(rbuffc)    ; count to l, char to h
  52.         ld a,l
  53.         and a             ; get flags
  54.         jp z,exit         ; exit if no chars entered
  55.         ld a,h            ; character
  56.         sub 'A'           ; change 'A' to 0
  57.         jr c,rp           ; try again if disk not valid
  58.         ld e,a            ; need result in e
  59.         sub 32            ; in case lowercase
  60.         jr c,uc           ; jump if uppercase
  61.         ld e,a
  62. uc:     ld a,e
  63.         cp 3              ; check disk = A,B or C
  64.         jr nc,rp
  65.  
  66. ; select disk and get disk characteristics
  67.         ld c,14           ; disk select code
  68.         call bdos
  69.         and a             ; get flags
  70.         jp nz,slerr       ; select error
  71.         ld c,31           ; code to get dpb address
  72.         call bdos
  73.         ld bc,13
  74.         add hl,bc         ; now points to offset
  75.         ld c,(hl)         ; c contains offset
  76.         inc hl
  77.         inc hl            ; now points to psh
  78.         ld b,(hl)         ; contains psh
  79.         ld e,b
  80.         ld d,0            ; de contains psh
  81.         ld hl,nsec        ; address of sector table
  82.         add hl,de
  83.         ld a,(hl)         ; number of sectors
  84.         push af           ; number of sectors in a
  85.         ld hl,msec        ; address of sectors per track
  86.                           ;   table
  87.         add hl,de
  88.         ld a,(hl)         ; sectors per track
  89.         ld (msecx),a      ; keep this
  90.         ld hl,cread       ; address of table of primary
  91.                           ;   load routines
  92.         add hl,de
  93.         add hl,de         ; points to address of plr
  94.         ld e,(hl)
  95.         inc hl
  96.         ld d,(hl)         ; de contains address of plr
  97.         ld (creada),de    ; store in creada
  98.         ld hl,128         ; calculate sector length
  99.         ld a,b
  100.         and a
  101.         jr z,zer          ; djnz does not handle b=0
  102. dbbl:   add hl,hl         ; double hl
  103.         djnz dbbl
  104. zer:    ld (seclen),hl    ; sector length
  105.  
  106. ; set track
  107.         ld a,c            ; get directory offset
  108.         srl a             ; dd => offset=4 => a=2 => track=1
  109.                           ; sd => offset=2 => a=1 => track=1
  110.         cp 3              ; make sure track <= 2
  111.         jp nc,it          ; jump if invalid track
  112.         ld l,a            ; track number to hl
  113.         ld h,0
  114.         ld (biosbc),hl    ; track number
  115.         ld a,10
  116.         ld (biospb),a     ; function code
  117.         ld c,50           ; bios code call
  118.         ld de,biospb      ; register image array
  119.         call bdos
  120.  
  121. ; set bank=1 for disk operations
  122.         ld a,1
  123.         ld (biosa),a      ; bank number
  124.         ld a,28
  125.         ld (biospb),a     ; set function = setbnk
  126.         ld c,50           ; bios code call
  127.         ld de,biospb      ; register image array
  128.         call bdos
  129.  
  130. ; load cpmldr to track 1 of disk
  131.         pop bc            ; number of sectors of b
  132.         ld hl,cpmldr      ; address of image of cpmldr
  133.         ld (craddr),hl    ; keep address
  134.         ld c,1            ; initial sector number
  135. wloop:  push bc           ; sector count and number
  136.         ld b,0
  137.         ld (biosbc),bc    ; sector number
  138.  
  139.         ld a,11           ; bios set sector code
  140.         ld (biospb),a     ; bios command
  141.         ld c,50           ; bios call code
  142.         ld de,biospb      ; register image array
  143.         call bdos         ; set sector
  144.  
  145.                           ; set dma for disk ops
  146.         ld bc,(craddr)    ; address of current seg
  147.         ld (biosbc),bc
  148.         ld hl,(seclen)    ; sector length
  149.         add hl,bc         ; form address of next
  150.         ld (craddr),hl    ;   segment of cpmldr
  151.         ld a,12           ; bios set dma code
  152.         ld (biospb),a     ; bios command
  153.         ld c,50           ; bios call mode
  154.         ld de,biospb      ; register image array
  155.         call bdos
  156.  
  157.         ld a,14           ; bios write code
  158.         ld (biospb),a     ; bios command
  159.         ld c,50
  160.         ld de,biospb      ; register image array
  161.         call bdos         ; write
  162.         and a
  163.         jp nz,werr        ; jump if write error
  164.  
  165.         pop bc
  166.         inc c             ; update sector number
  167.         ld a,(msecx)      ; find number of sectors per track
  168.         cp c
  169.         jr nz,cy1
  170.         ld c,1            ; first cycle complete
  171. cy1:    inc c
  172.         djnz wloop        ; read next segment
  173.  
  174. ; set track = 0
  175.         ld hl,0
  176.         ld (biosbc),hl    ; track number
  177.         ld a,10
  178.         ld (biospb),a     ; function code
  179.         ld c,50           ; bios code call
  180.         ld de,biospb      ; register image array
  181.         call bdos
  182.  
  183. ; load primary loader to track 0 of disk
  184.         ld bc,1           ; sector number
  185.         ld (biosbc),bc    ; sector number
  186.         ld a,11           ; bios set sector code
  187.         ld (biospb),a     ; bios command
  188.         ld c,50           ; bios call code
  189.         ld de,biospb      ; register image array
  190.         call bdos         ; set sector
  191.  
  192.                           ; set dma for disk ops
  193.         ld bc,(creada)    ; address of primary ldr
  194.         ld (biosbc),bc
  195.         ld a,12           ; bios set dma code
  196.         ld (biospb),a     ; bios command
  197.         ld c,50           ; bios call mode
  198.         ld de,biospb      ; register image array
  199.         call bdos
  200.  
  201.         ld a,14           ; bios write code
  202.         ld (biospb),a     ; bios command
  203.         ld c,50
  204.         ld de,biospb      ; register image array
  205.         call bdos         ; write
  206.         and a
  207.         jp nz,werr        ; jump if write error
  208.  
  209.         jp ltd            ; function complete
  210.  
  211. oldver: ld de,ovm         ; not cpm3 error exit
  212.         ld c,9            ; output string
  213.         call bdos
  214.         jp boot           ; to exit
  215. ovm:    db 'Need cpm-3',cr,lf,'$'
  216.  
  217. operr:  ld de,oem         ; can't open cpmldr error exit
  218.         ld c,9            ; output string code
  219.         call bdos
  220.         jp boot           ; to exit
  221. oem:    db 'Cannot open cpmldr.com',cr,lf,'$'
  222. rderr:  ld de,rem         ; read error
  223.         ld c,9
  224.         call bdos
  225.         jp boot
  226. rem:    db 'Read fails',cr,lf,'$'
  227.  
  228. ; clear console input
  229. clear:  ld c,11           ; to check console status
  230.         call bdos
  231.         and a             ; to set flags
  232.         ret z             ; return if no character
  233.         ld c,1            ; console input
  234.         call bdos
  235.         jr clear          ; cycle until console clear
  236.  
  237. lddm:   db 'Enter drive name; <ret> to quit: $'
  238.  
  239. exit:   ld c,13           ; reset disk system
  240.         call bdos
  241.         jp boot
  242.  
  243. slerr:  ld de,sem         ; select error
  244.         ld c,9
  245.         call bdos
  246.         jp boot
  247.  
  248. sem:    db 'Disk select fails',cr,lf,'$'
  249.  
  250. it:     ld de,itm         ; invalid track
  251.         ld c,9
  252.         call bdos
  253.         jp boot
  254.  
  255. itm:    db 'Invalid track',cr,lf,'$'
  256.  
  257. werr:   ld de,wem         ; write fails
  258.         ld c,9
  259.         call bdos
  260.         jp boot
  261.  
  262. wem:    db 'Write error',cr,lf,'$'
  263.  
  264. rbuff:  db 1              ; buffer length
  265. rbuffc: ds 2              ; number chars entered
  266.  
  267. ; fcb for cpmldr
  268. fcb:    db 1,'CPMLDR  COM',0,0,0,0
  269.         ds 16
  270.         db 0,0,0
  271.  
  272. ; temporary storage for cpmldr
  273. cpmldr: ds 1000h          ; 4k
  274.  
  275. craddr: ds 2              ; address of next portion
  276.                           ;   of cpmldr to be loaded
  277. seclen: ds 2              ; sector length
  278. creada: ds 2              ; address of primary loader
  279. msecx:  ds 1              ; sectors per track
  280.  
  281. ; parameter block for making calls to bios
  282. biospb: ds 1
  283. biosa:  ds 1
  284. biosbc: ds 2
  285. biosde: ds 2
  286. bioshl: ds 2
  287.  
  288. ; number of sectors
  289. nsec:   db 26             ; 26 128 byte blocks
  290.         db 13             ; 13 256 byte blocks
  291.         db 7              ; 7 512 byte blocks
  292.         db 4              ; 4 1024 byte blocks
  293.  
  294. ;number of sectors per track
  295. msec:   db 26
  296.         db 26
  297.         db 15
  298.         db 8
  299.  
  300. ; code to read track 1 to core
  301.  
  302. rdcpm   macro ?nsec,?blkl,?msec
  303.                           ; ?nsec = number of sectors
  304.                           ; ?blkl = sector length
  305.                           ; ?msec = sectors per track
  306.         local rloop,rloop1,rok,sl1
  307.         .phase 0e700h     ; to executed at 0e700h
  308.         ld c,1
  309.         call 0e00ch       ; track 1
  310.         ld c,0
  311.         call 0e030h       ; side 0
  312.         ld c,0
  313.         call 0e01bh       ; drive A
  314.         ld bc,100h        ; dma
  315.         call 0e012h       ; set dma
  316.         ld bc,?nsec*100h+1; ?nsec sectors & sector number
  317. rloop:  call 0e00fh       ; set sector
  318.         push bc           ; store sector count & no.
  319.         ld b,5            ; 5 tries to read
  320. rloop1: push bc
  321.         call 0e015h       ; do read
  322.         pop bc
  323.         jr nc,rok         ; jump out if ok
  324.         djnz rloop1
  325. rok:    jp c,0e02ah       ; error exit
  326.         call 0e024h       ; get dma to bc
  327.         ld hl,?blkl       ; length of block
  328.         add hl,bc         ; increment dma
  329.         ld b,h
  330.         ld c,l
  331.         call 0e012h       ; and set dma
  332.         pop bc
  333.         ld a,c
  334.         cp ?msec-1        ; check for one cycle
  335.         jr nz,sl1
  336.         ld c,0            ; one cycle of disk complete
  337. sl1:    inc c             ; increment sector no. by 2
  338.         inc c
  339.         djnz rloop        ; loop controlled by reg b
  340.         jp 100h           ; jump to cmpldr
  341.         .dephase
  342.         endm
  343.  
  344. cread0: rdcpm 26,128,26
  345. cread1: rdcpm 13,256,26
  346. cread2: rdcpm 7,512,15
  347. cread3: rdcpm 4,1024,8
  348.  
  349. cread:  dw cread0
  350.         dw cread1
  351.         dw cread2
  352.         dw cread3
  353.  
  354.         end loadsy
  355.