]> cloudbase.mooo.com Git - z180-stamp-cpm3.git/blob - cbios/bioskrnl.180
Add TCGETA, TCSETA
[z180-stamp-cpm3.git] / cbios / bioskrnl.180
1 title 'Root module of relocatable BIOS for CP/M 3.0'
2
3 ; version 1.0 15 Sept 82
4
5 include config.inc
6 include z180reg.inc
7
8
9 ; Copyright (C), 1982
10 ; Digital Research, Inc
11 ; P.O. Box 579
12 ; Pacific Grove, CA 93950
13
14
15 ; This is the invariant portion of the modular BIOS and is
16 ; distributed as source for informational purposes only.
17 ; All desired modifications should be performed by
18 ; adding or changing externally defined modules.
19 ; This allows producing "standard" I/O modules that
20 ; can be combined to support a particular system
21 ; configuration.
22
23 ctlQ equ 'Q'-'@'
24 ctlS equ 'S'-'@'
25
26 ccp equ 0100h ; Console Command Processor gets loaded
27 ; into the TPA
28
29 cseg ; GENCPM puts CSEG stuff in common memory
30
31
32 ; variables in system data page
33
34 extrn @covec,@civec,@aovec,@aivec,@lovec ; I/O redirection vectors
35 extrn @mxtpa ; addr of system entry point
36 extrn @bnkbf ; 128 byte scratch buffer
37
38 ; initialization
39
40 extrn hwinit,?init ; general initialization and signon
41 extrn ?ldccp,?rlccp ; load & reload CCP for BOOT & WBOOT
42
43 ; user defined character I/O routines
44
45 extrn ?ci,?co,?cist,?cost ; each take device in <B>
46 extrn ?cinit ; (re)initialize device in <C>
47 extrn ioctl
48 extrn @ctbl ; physical character device table
49
50 ; disk communication data items
51
52 extrn @dtbl ; table of pointers to XDPHs
53 public @adrv,@rdrv,@trk,@sect ; parameters for disk I/O
54 public @dma,@dbnk,@cnt ; '' '' '' ''
55 public @xdph,@op
56
57 ; memory control
58
59 public @cbnk ; current bank
60 extrn ?xmove,?move ; select move bank, and block move
61 extrn ?bank ; select CPU bank
62
63 ; clock support
64
65 extrn ?time ; signal time operation
66
67 extrn ijphl ; vectored call
68
69 maclib modebaud.inc ; define mode bits
70
71
72 ; External names for BIOS entry points
73
74 public ?boot,?wboot,boot,?const,?conin,?cono,?list,?auxo,?auxi
75 public ?home,?sldsk,?sttrk,?stsec,?stdma,?read,?write
76 public ?lists,?sctrn
77 public ?conos,?auxis,?auxos,?dvtbl,?devin,?drtbl
78 public ?mltio,?flush,?mov,?tim,?bnksl,?stbnk,?xmov
79
80 public bs$stack
81
82
83 ; BIOS Jump vector.
84
85 ; All BIOS routines are invoked by calling these
86 ; entry points.
87
88 ?boot: jp boot ; initial entry on cold start
89 ?wboot: jp wboot ; reentry on program exit, warm start
90
91 ?const: jp const ; return console input status
92 ?conin: jp conin ; return console input character
93 ?cono: jp conout ; send console output character
94 ?list: jp list ; send list output character
95 ?auxo: jp auxout ; send auxiliary output character
96 ?auxi: jp auxin ; return auxiliary input character
97
98 ?home: jp home ; set disks to logical home
99 ?sldsk: jp seldsk ; select disk drive, return disk parameter info
100 ?sttrk: jp settrk ; set disk track
101 ?stsec: jp setsec ; set disk sector
102 ?stdma: jp setdma ; set disk I/O memory address
103 ?read: jp read ; read physical block(s)
104 ?write: jp write ; write physical block(s)
105
106 ?lists: jp listst ; return list device status
107 ?sctrn: jp sectrn ; translate logical to physical sector
108
109 ?conos: jp conost ; return console output status
110 ?auxis: jp auxist ; return aux input status
111 ?auxos: jp auxost ; return aux output status
112 ?dvtbl: jp devtbl ; return address of device def table
113 ?devin: jp ?cinit ; change baud rate of device
114
115 ?drtbl: jp getdrv ; return address of disk drive table
116 ?mltio: jp multio ; set multiple record count for disk I/O
117 ?flush: jp flush ; flush BIOS maintained disk caching
118
119 ?mov: jp ?move ; block move memory to memory
120 ?tim: jp ?time ; Signal Time and Date operation
121 ?bnksl: jp bnksel ; select bank for code execution and default DMA
122 ?stbnk: jp setbnk ; select different bank for disk I/O DMA operations
123 ?xmov: jp ?xmove ; set source and destination banks for one operation
124
125 jp 0 ; reserved for system implementor
126 jp 0 ; reserved for future expansion
127 jp 0 ; reserved for future expansion
128 ?ioctl jp ioctl ;
129
130
131 ; BOOT
132 ; Initial entry point for system startup.
133
134 dseg ; this part can be banked
135
136 boot:
137 ld a,SYS$CBR
138 out0 (cbr),a
139 ld a,USR$CBAR
140 out0 (cbar),a
141 ld sp,bs$stack
142
143 call hwinit ; first time hardware initialisation
144
145 ld bc,16*256 + 0 ; initialize all 16 character devices
146 c$init$loop:
147 push bc
148 call ?cinit
149 pop bc
150 inc c
151 djnz c$init$loop
152
153 call ?init ; perform any additional system initialization
154 ; and print signon message
155
156 ld bc,16*256+0
157 ld hl,@dtbl ; init all 16 logical disk drives
158 d$init$loop:
159 push bc ; save remaining count and abs drive
160 ld e,(hl)
161 inc hl
162 ld d,(hl)
163 inc hl ; grab @drv entry
164 ld a,e
165 or d
166 jr z,d$init$next ; if null, no drive
167 push hl ; save @drv pointer
168 push de
169 pop ix ; XDPH address in <DE>
170 ld b,(ix-2)
171 ld (@ADRV),bc ; save absolute and relative drive code
172 ld l,(ix-4)
173 ld h,(ix-3) ; get init pointer
174 call ijphl ; call init routine
175 pop hl ; recover @drv pointer
176 d$init$next:
177 pop bc ; recover counter and drive #
178 inc c
179 djnz d$init$loop ; and loop for each drive
180 jp boot$1
181
182 cseg ; following in resident memory
183
184 boot$1:
185 call set$jumps
186 call ?ldccp ; fetch CCP for first time
187 jp ccp
188
189
190 ; WBOOT
191 ; Entry for system restarts.
192
193 wboot:
194 ld sp,bs$stack
195 call set$jumps ; initialize page zero
196 call ?rlccp ; reload CCP
197 jp ccp ; then reset jmp vectors and exit to ccp
198
199
200 set$jumps:
201
202 if banked
203 ld a,1
204 call ?bnksl
205 endif
206
207 ld a,0C3h ; jp opcode
208 ld (0),a
209 ld (5),a ; set up jumps in page zero
210 ld hl,?wboot
211 ld (1),hl ; BIOS warm start entry
212 ld hl,(@MXTPA)
213 ld (6),hl ; BDOS system call entry
214 ret
215
216
217 ds bs$stack$size
218 bs$stack equ $
219
220
221 ; DEVTBL
222 ; Return address of character device table
223
224 devtbl:
225 ld hl,@ctbl
226 ret
227
228
229 ; GETDRV
230 ; Return address of drive table
231
232 getdrv:
233 ld hl,@dtbl
234 ret
235
236
237
238 ; LIST
239 ; List Output. Send character in <C>
240 ; to all selected devices.
241
242 list:
243 ld hl,(@lovec) ; fetch list output bit vector
244 jr out$scan
245
246
247 ; AUXOUT
248 ; Auxiliary Output. Send character in <C>
249 ; to all selected devices
250
251 auxout:
252 ld hl,(@aovec) ; fetch aux output bit vector
253 jr out$scan
254
255
256 ; CONOUT
257 ; Console Output. Send character in <C>
258 ; to all selected devices
259
260 conout:
261
262 ld hl,(@covec) ; fetch console output bit vector
263
264 out$scan:
265 ld b,0 ; start with device 0
266 co$next:
267 add hl,hl ; shift out next bit
268 jr nc,not$out$device
269 push hl ; save the vector
270 push bc ; save device num and the character
271 call ?co ; if device selected, print it
272 pop bc ; recover count and character
273 pop hl ; recover the rest of the vector
274 not$out$device:
275 inc b ; next device number
276 ld a,h
277 or l ; see if any devices left
278 jr nz,co$next ; and go find them...
279 ret
280
281
282 ; LISTST
283 ; List Output Status. Return true if
284 ; all selected list output devices
285 ; are ready.
286
287 listst:
288 ld hl,(@lovec) ; get list output bit vector
289 jr ost$scan
290
291
292 ; AUXOST
293 ; Auxiliary Output Status. Return true if
294 ; all selected auxiliary output devices
295 ; are ready.
296
297 auxost:
298 ld hl,(@aovec) ; get aux output bit vector
299 jr ost$scan
300
301
302 ; CONOST
303 ; Console Output Status. Return true if
304 ; all selected console output devices
305 ; are ready.
306
307 conost:
308 ld hl,(@covec) ; get console output bit vector
309
310 ost$scan:
311 ld b,0 ; start with device 0
312 cos$next:
313 add hl,hl ; check next bit
314 push hl ; save the vector
315 push bc ; save the count
316 ld a,0FFh ; assume device ready
317 call c,?cost ; check status for this device
318 pop bc ; recover count
319 pop hl ; recover bit vector
320 or a ; see if device ready
321 ret z ; if any not ready, return false
322 inc b ; drop device number
323 ld a,h
324 or l ; see if any more selected devices
325 jr nz,cos$next
326 or 0FFh ; all selected were ready, return true
327 ret
328
329
330 cist1: ; get input status with <BC> and <HL> saved
331 push bc
332 push hl
333 call ?cist
334 pop hl
335 pop bc
336 or a
337 ret
338
339
340 ; AUXIST
341 ; Auxiliary Input Status. Return true if
342 ; any selected auxiliary input device
343 ; has an available character.
344
345 auxist:
346 ld hl,(@aivec) ; get aux input bit vector
347 jr ist$scan
348
349
350 ; CONST
351 ; Console Input Status. Return true if
352 ; any selected console input device
353 ; has an available character.
354
355 const:
356 ld hl,(@civec) ; get console input bit vector
357
358 ist$scan:
359 ld b,0 ; start with device 0
360 cis$next:
361 xor a ; assume next device not ready
362 add hl,hl ; check next bit (lets z flag unaffected)
363 call c,cist1 ; check status for this device
364 ret nz ; if any ready, return true
365 inc b ; next device number
366 ld a,h
367 or l ; see if any more selected devices
368 ret z ; all selected were not ready, return false
369 jr cis$next
370
371
372 ; AUXIN
373 ; Auxiliary Input. Return character from first
374 ; ready auxiliary input device.
375
376 auxin:
377 ld hl,(@aivec)
378 jr in$scan
379
380
381 ; CONIN
382 ; Console Input. Return character from first
383 ; ready console input device.
384
385 conin:
386 ld hl,(@civec)
387
388 ;check if only one device assigned
389
390 push hl ; save bit vector
391 ld b,0
392 insc_0:
393 or a ; clear carry
394 adc hl,hl ; shift out next bit
395 jr nc,insc_1 ;
396 jr z,ci$rdy ; single device
397 jr ci$check ;
398
399 insc_1:
400 inc b ; else, next device
401 ld a,h
402 or l ; see if any more devices
403 jr nz,insc_0 ; no,
404 pop hl
405
406 in$scan:
407 push hl ; save bit vector
408 ld b,0
409 ci$next:
410 xor a ; assume next device not ready
411 add hl,hl ; shift out next bit
412 ci$check:
413 call c,cist1 ; see if the device has a character
414 jr nz,ci$rdy ; this device has a character
415 inc b ; else, next device
416 ld a,h
417 or l ; see if any more devices
418 jr nz,ci$next ; go look at them
419 pop hl ; recover bit vector
420 jr in$scan ; loop til we find a character
421
422 ci$rdy:
423 pop hl ; discard extra stack
424 jp ?ci
425
426
427 ;-------------------------------------------------------------------------------
428 ; Utility Subroutines
429
430 ; BNKSEL
431 ; Bank Select. Select CPU bank for further execution.
432
433 bnksel:
434 ld (@cbnk),a ; remember current bank
435 jp ?bank ; and go exit through users
436 ; physical bank select routine
437
438 dseg ; following resides in banked memory
439
440 ; Disk I/O interface routines
441
442
443 ; SELDSK
444 ; Select Disk Drive. Drive code in <C>.
445 ; Invoke login procedure for drive
446 ; if this is first select. Return
447 ; address of disk parameter header
448 ; in <HL>
449
450 seldsk:
451 ld a,c ; save drive select code
452 ld (@adrv),a
453 xor a
454 ld (@op),a
455 ld (@cnt),a
456 ld b,a ; create index from drive code
457 ld hl,@dtbl
458 add hl,bc ; get pointer to dispatch table
459 add hl,bc
460 ld a,(hl)
461 inc hl
462 ld h,(hl)
463 ld l,a ; point at disk descriptor
464 ld (@xdph),hl ; save descriptor pointer
465 or h
466 ret z ; if no entry in table, no disk
467
468 bit 0,e ; login bit to zero flag
469 ex de,hl
470 ld hl,-2 ; get relative drive
471 add hl,de
472 ld a,(hl)
473 ld (@RDRV),a
474 jr nz,notfirst ; examine login bit
475 ld hl,-6
476 add hl,de
477 ld a,(hl)
478 inc hl
479 ld h,(hl)
480 ld l,a
481 call ijphl ; call LOGIN
482 ld hl,(@xdph) ; recover DPH pointer
483 ret
484
485
486 ; HOME
487 ; Home selected drive. Treated as SETTRK(0).
488
489 home:
490 ld bc,0 ; same as set track zero
491
492
493 ; SETTRK
494 ; Set Track. Saves track address from <BC>
495 ; in @TRK for further operations.
496
497 settrk:
498 ld (@trk),bc
499 ret
500
501
502 ; SETSEC
503 ; Set Sector. Saves sector number from <BC>
504 ; in @sect for further operations.
505
506 setsec:
507 ld (@sect),bc
508 ret
509
510
511 ; SETDMA
512 ; Set Disk Memory Address. Saves DMA address
513 ; from <BC> in @DMA and sets @DBNK to @CBNK
514 ; so that further disk operations take place
515 ; in current bank.
516
517 setdma:
518 ld (@dma),bc
519
520 ld a,(@cbnk) ; default DMA bank is current bank
521 ; fall through to set DMA bank
522
523 ; SETBNK
524 ; Set Disk Memory Bank. Saves bank number
525 ; in @DBNK for future disk data
526 ; transfers.
527
528 setbnk:
529 ld (@dbnk),a
530 ret
531
532
533 ; SECTRN
534 ; Sector Translate. Indexes skew table in <DE>
535 ; with sector in <BC>. Returns physical sector
536 ; in <HL>. If no skew table (<DE>=0) then
537 ; returns physical=logical.
538
539 sectrn:
540 ld l,c
541 ld h,b
542 ld a,d
543 or e
544 ret z
545 ex de,hl
546 add hl,bc
547 ld l,(hl)
548 ld h,0
549 ret
550
551
552 ; READ
553 ; Read physical record from currently selected drive.
554 ; Finds address of proper read routine from
555 ; extended disk parameter header (XDPH).
556
557 read:
558 ld a,1
559 ld (@op),a
560 ld ix,(@xdph) ; get drive descriptor pointer
561 ld l,(ix-8) ; get read routine entry
562 ld h,(ix-7)
563 jp (hl)
564
565
566 ; WRITE
567 ; Write physical sector from currently selected drive.
568 ; Finds address of proper write routine from
569 ; extended disk parameter header (XDPH).
570
571 write:
572 ld a,2
573 ld (@op),a
574 ld ix,(@xdph) ; get drive descriptor pointer
575 ld l,(ix-10) ; get write routine entry
576 ld h,(ix- 9)
577 jp (hl)
578
579
580
581 ; MULTIO
582 ; Set multiple sector count. Saves passed count in
583 ; @CNT
584
585 multio:
586 ld (@cnt),a
587 ret
588
589
590 ; FLUSH
591 ; BIOS deblocking buffer flush. Not implemented.
592
593 flush:
594 xor a
595 ret ; return with no error
596
597
598 ; disk communication data items
599 ; do not change order. sd driver depends on this
600
601 @xdph: ds 2 ; pointer to currently selected drives dph
602 @op ds 1 ; current disk operation 0:select, 1:read, 2 write
603 @adrv: ds 1 ; currently selected disk drive
604 @rdrv: ds 1 ; controller relative disk drive
605 @trk: ds 2 ; current track number
606 @sect: ds 2 ; current sector number
607 @dma: ds 2 ; current DMA address
608 @dbnk: db 0 ; bank for DMA operations
609 @cnt: db 0 ; record count for multisector transfer
610
611
612 cseg ; common memory
613
614 @cbnk: db 0 ; bank for processor operations
615
616
617 end