1 title 'LDRBIOS for CP/M 3.0'
8 ; IDE Task File Register Definitions
10 IDEDat equ IDEBASE+0 ; Data Register
11 IDEErr equ IDEBASE+1 ; Error Register
12 IDEFeat equ IDEBASE+1 ; Feature Register
13 IDESCnt equ IDEBASE+2 ; Sector Count
14 IDESNum equ IDEBASE+3 ; Sector Number
15 IDECLo equ IDEBASE+4 ; Cylinder Low
16 IDECHi equ IDEBASE+5 ; Cylinder High
17 IDESDH equ IDEBASE+6 ; Drive and Head
18 IDECmd equ IDEBASE+7 ; Command / Status
20 ; IDE Hard disk commands:
22 CmdHome equ 10h ; Recalibrate
23 CmdRd equ 20h ; Read Sector
24 CmdWr equ 30h ; Write Sector
25 CmdInit equ 91h ; Initialize Drive Params
26 CmdId equ 0ECh ; Read ID
27 CmdSF equ 0EFh ; Set Feature
29 ; Partition Table Structures
36 ; (see http://www.win.tue.nl/~aeb/partitions/partition_types-1.html)
38 PARTID1_FAT16 equ 00EH
39 PARTID2_FAT16 equ 006H
54 ?boot: jp boot ; initial entry on cold start
55 ?wboot: jp wboot ; reentry on program exit, warm start
57 ?const: jp const ; return console input status
58 ?conin: jp conin ; return console input character
59 ?cono: jp conout ; send console output character
60 ?list: jp list ; send list output character
61 ?auxo: jp auxout ; send auxilliary output character
62 ?auxi: jp auxin ; return auxilliary input character
64 ?home: jp home ; set disks to logical home
65 ?sldsk: jp seldsk ; select disk drive, return disk parameter info
66 ?sttrk: jp settrk ; set disk track
67 ?stsec: jp setsec ; set disk sector
68 ?stdma: jp setdma ; set disk I/O memory address
69 ?read: jp read ; read physical block(s)
70 ?write: jp write ; write physical block(s)
72 ?lists: jp listst ; return list device status
73 ?sctrn: jp sectrn ; translate logical to physical sector
75 ?conos: jp conost ; return console output status
76 ?auxis: jp auxist ; return aux input status
77 ?auxos: jp auxost ; return aux output status
78 ?dvtbl: jp devtbl ; return address of device def table
79 ?devin: jp cinit ; change baud rate of device
81 ?drtbl: jp getdrv ; return address of disk drive table
82 ?mltio: jp multio ; set multiple record count for disk I/O
83 ?flush: jp flush ; flush BIOS maintained disk caching
85 ?mov: jp move ; block move memory to memory
86 ?tim: jp time ; Signal Time and Date operation
87 ?bnksl: jp bnksel ; select bank for code execution and default DMA
88 ?stbnk: jp setbnk ; select different bank for disk I/O DMA operations.
89 ?xmov: jp xmove ; set source and destination banks for one operation
91 jp 0 ; reserved for future expansion
92 jp 0 ; reserved for future expansion
93 jp 0 ; reserved for future expansion
95 ;----------------------------------------------------------------------
98 db (hwini0_e-$)/2 ;count
99 db rcr,CREFSH ;configure DRAM refresh
100 db dcntl,CWAITIO ;wait states
101 db ccr,M_NCD ;No Clock Divide
102 db cmr,PHI_X2 ;X2 Clock Multiplier
103 db omcr,~M_IOC ;Operation Mode Control Register
105 db cbr,SYS$CBR ;Common Base Register
106 db cbar,USR$CBAR ;Common Base Area Register
108 db asext1,0 ;disable BRG
109 db stat1,00000000b ;disable RX, TX interrupt, disable CTS1
110 db cntlb1,10000000b;PS:10 DR:16 Rate:1 --> BR = Phi/160
111 db cntla1,01100101b;RE TE RTS:0 8N2
117 db cr,lf,'CPMLDR error: Unable to locate CP/M partition',cr,lf,0
119 ;-------------------------------------------------------------------------------
121 ; CP/M 3 Disk definition macros
123 maclib cpm3slr.lib ; dpb mcaro
125 ; The dph macro from the lib depends on GENCPM
127 dphldr macro ?trans,?dpb,?csize,?asize,?dirbcb,?dtabcb
129 dw ?trans ; translate table address
130 db 0,0,0,0,0,0,0,0,0 ; BDOS Scratch area
132 dw ?dpb ; disk parameter block
134 dw 0 ; permanently mounted, no checksum vector
139 dw ?csv ; checksum vector
143 dw 0 ; no alloc vector
148 dw ?alv ; allocation vector
157 ?csv ds ?csize ; checksum vector
162 ?alv ds ?asize ; allocation vector
167 ;-------------------------------------------------------------------------------
169 ; dphldr translate$table, - disk parameter header
170 ; disk$parameter$block,
171 ; checksum$size, (optional)
172 ; alloc$size (optional)
176 dphldr 0,dpbsimhd512,0,0,bcb,bcb
185 ; dpb physical$sector$size, - disk parameter block
186 ; physical$sectors$per$track,
189 ; number$dir$entries,
191 ; checksum$vec$size (optional)
194 dpb 512,8,2048,4096,1024,6,8000h
196 ;-------------------------------------------------------------------------------
198 wboot: ; jump vector locations not used
220 ;-------------------------------------------------------------------------------
221 ; output bytes to ports
223 ; hl: tables of port,value pairs:
224 ; db n, port1,val1, port2,val2,... portn,valn
226 ; db 0 ; Terminate table
232 ld c,(hl) ;port address
245 ;-------------------------------------------------------------------------------
246 ; print message @<HL> up to a null
259 ;-------------------------------------------------------------------------------
262 ; Init CPU, MMU, ASCI0
267 ; Init disk partition
277 cp (hl) ; Test, if it has a valid MBR
284 ; Find CP/M paartition
285 ; Look for first CP/M partition and save partition offset
287 ld hl,buffer+512-2-64+PART_TYPE ; Point to partition type of first first partition table entry
289 ld b,4 ; Max # of partition table entries
292 sub (HL) ; Test for CP/M Partition
295 add hl,bc ; Point to partition start (lba)
311 ;-------------------------------------------------------------------------------
321 ;-------------------------------------------------------------------------------
324 ex de,hl ; we are passed source in DE and dest in HL
325 ldir ; use Z80 block move instruction
326 ex de,hl ; need next addresses in same regs
329 ;-------------------------------------------------------------------------------
331 ; Return address of disk parameter header in <HL>
337 ; Home selected drive. Treated as SETTRK(0).
340 ld bc,0 ; same as set track zero
342 ; Set Track. Saves track address from <BC> in @trk.
348 ; Set Sector. Saves sector number from <BC> in @sect.
354 ; Set Disk Memory Address. Saves DMA address from <BC> in @dma.
360 ; Translate sector address. Not needed. Return physical=logical.
367 ;-----------------------------------------------------------------
381 ;-------------------------------------------------------------------------------
382 ; Wait for ready signal with time out
393 and 11000000b ; clears carry
403 ;-------------------------------------------------------------------------------
414 ;-------------------------------------------------------------------------------
415 ; Read partition table
430 ;-------------------------------------------------------------------------------
433 ; compute logical block number (lba) --> cf-controller
435 ; TODO: sectors per track from dpb
436 ; lba = track * 8 + sector
453 ld a,(iy+0) ; add partition start
469 ld a,1 ; number of sectors to read
470 out (IdeSCnt),a ; set sector count
473 out (IdeCmd),a ; command: read sector data
474 ld bc,IdeDat ; I/O address
476 in a,(IdeCmd) ; wait for DRQ to become active
479 inir ; read 512 data bytes (2 x 256)
481 wnb: ; wait while busy
485 rrca ; restore status
486 and 10001001b ; Busy, DRQ, or Error?
487 ret z ; return 0, if everything is ok
491 ;-------------------------------------------------------------------------------