2 ; Interrupt drivers for ASCI0 and ASCI1
7 extrn ff_empty,ff_get,ff_full,ff_put
8 extrn ff_puth,ff_cnt,ff_gech
10 extrn isv_sw,ijphl,add_hla,div32_r
21 m2b mbxon_bit,mb$xon$xoff
23 ;-----------------------------------------------------
33 db 0 ;absolute device #
36 db M_CREAD+M_CRTS_IFLOW+M_CCTS_OFLOW ;fflags
51 oint.iflags equ as0_dev+o.iflags-s0.inbuf
52 oint.fflags equ as0_dev+o.fflags-s0.inbuf
53 oint.stat equ as0_dev+o.stat-s0.inbuf
54 mkbuf s0.rx_id, s0.inbuf, s0.rx_len
55 mkbuf s0.tx_id, s0.outbuf,s0.tx_len
64 db 0 ;absolute device #
67 db M_CREAD+M_IXOFF ;fflags
72 mkbuf s1.rx_id, s1.inbuf, s1.rx_len
73 mkbuf s1.tx_id, s1.outbuf,s1.tx_len
81 dw func_tcinit ;(00h) CP/M 3 DEVINI function
82 dw func_tcgeta ;(01h) Get the current serial port settings.
83 dw func_tcseta ;(02h) Set the current serial port settings.
84 dw func_tcsetaw ;(03h) Allow the output buffer to drain
85 dw func_tcsetaf ;(04h) Allow the output buffer to drain, discard pending input
86 dw func_tcsbrk ;(05h) Sending a break (250ms .. 500ms)
87 dw func_tcsbrkp ;(06h) arg is timeinterval in 0.1sec
88 dw func_tiocsbrk ;(07h) Turn break on
89 dw func_tioccbrk ;(08h) Turn break off
90 dw func_tcxonc ;(09h) Software flow control (TCOOFF, TCOON, TCIOFF, TCION)
91 dw func_tcflsh ;(0Ah) Flush input/output buffer (TCIFLUSH, TCOFLUSH, TCIOFLUSH)
92 dw func_fionread ;(0Bh) Get the number of bytes in the input buffer.
93 dw func_tiocoutq ;(0Ch) Get the number of bytes in the output buffer.
94 dw func_tiocmget ;(0Dh) get the status of modem bits.
95 dw func_tiocmbis ;(0Eh) set the indicated modem bits.
96 dw func_tiocmbic ;(0Fh) clear the indicated modem bits.
97 dw func_tiocmset ;(10h) set the status of modem bits.
98 dw func_tiocgsoftcar ;(11h) Get the status of the CLOCAL flag in the c_cflag field
99 dw func_tiocssoftcar ;(12h) Set the CLOCAL flag when *argp is nonzero, and clear it otherwise.
101 IOCTL_MAX equ ($-ioctl_ftab)/2
105 ;--------------------------------------------------------------
109 ; de: ioctl arg pointer
110 ; hl: ptr to driver local data
141 ;--------------------------------------------------------------
142 ; CP/M 3 DEVINI function
143 ; Init Serial I/O for input and output (ASCI 0/1)
149 ld c,asext0 ;Enable baud rate generator
150 ld a,M_BRGMOD+M_DCD0DIS ; +M_CTS0DIS +M_BREAKEN
151 bit CCTS_OFLOW,(ix+o.fflags)
161 res IXON,(ix+o.fflags)
162 bit mbxon_bit,(hl) ;get cpm3 xon flag
164 set IXON,(ix+o.fflags)
166 ld a,(hl) ;get baudrate index
172 ld a,M_MPBT ;No MP Mode, X16
173 bit PARODD,(ix+o.iflags)
184 or a,M_RE+M_TE+M_RTS0+M_EFR ;Rx/Tx enable
190 ld hl,rtxisvjmp0 ;rx/tx int vector
191 ld (ivtab + IV$ASCI0),hl ;
197 ld hl,rtxisvjmp1 ;rx/tx int vector
198 ld (ivtab + IV$ASCI1),hl ;
208 ;--------------------------------------------------------------
221 ;--------------------------------------------------------------
222 ; Get the current serial port settings.
232 res IXON,(ix+o.fflags)
233 bit mbxon_bit,(hl) ;get cpm3 xon flag
235 set IXON,(ix+o.fflags)
243 ld a,(hl) ;get baudrate index
255 ;--------------------------------------------------------------
256 ; Set the current serial port settings.
283 ld (hl),a ;set baudrate index
292 ;--------------------------------------------------------------
293 ; Allow the output buffer to drain
297 ;--------------------------------------------------------------
298 ; Allow the output buffer to drain, discard pending input
302 ;--------------------------------------------------------------
303 ; Sending a break (250ms .. 500ms)
307 ;--------------------------------------------------------------
308 ; arg is timeinterval in 0.1sec
312 ;--------------------------------------------------------------
317 ;--------------------------------------------------------------
322 ;--------------------------------------------------------------
323 ; Software flow control (TCOOFF, TCOON, TCIOFF, TCION)
327 ;--------------------------------------------------------------
328 ; Flush input/output buffer (TCIFLUSH, TCOFLUSH, TCIOFLUSH)
332 ;--------------------------------------------------------------
333 ; Get the number of bytes in the input buffer.
337 ;--------------------------------------------------------------
338 ; Get the number of bytes in the output buffer.
342 ;--------------------------------------------------------------
343 ; get the status of modem bits.
347 ;--------------------------------------------------------------
348 ; set the indicated modem bits.
352 ;--------------------------------------------------------------
353 ; clear the indicated modem bits.
357 ;--------------------------------------------------------------
358 ; set the status of modem bits.
362 ;--------------------------------------------------------------
363 ; Get the status of the CLOCAL flag in the c_cflag field
367 ;--------------------------------------------------------------
368 ; Set the CLOCAL flag when *argp is nonzero, and clear it otherwise.
375 ;--------------------------------------------------------------
385 ;--------------------------------------------------------------
388 ld c,stat0 ;Disable rx/tx interrupts
392 ld c,cntla0 ;Disable receiver and transmitter
393 ld a,M_RTS0+M_EFR ;RTS/CKA1
396 ;--------------------------------------------------------------
402 and ~M_RTS0 ;Activate RTS
410 ;--------------------------------------------------------------
411 ; output to asci0/1 register
413 ; c: register address
427 ;--------------------------------------------------------------
428 ; output 16 bit value to asci0/1 register
430 ; c: register address
447 ;--------------------------------------------------------------
479 ; factor index baudrate orig. cp/m
480 dw 19200/150 ; 0 19200 -
481 dw 28800/150 ; 1 28800 50
482 dw 38400/150 ; 2 38400 75
483 dw 57600/150 ; 3 57600 110
484 dw 11520/15 ; 4 115200 134.5
495 dw 19200/150 ;15 19200
498 ;--------------------------------------------------------------
503 db 1,stat0,0 ;Disable rx/tx interrupts
504 ;Enable baud rate generator
505 db 1,asext0,M_BRGMOD+M_DCD0DIS ; +M_CTS0DIS
507 init_br_off equ $ - initab0
509 db 1,cntlb0,M_MPBT ;No MP Mode, X16
510 db 1,cntla0,M_RE+M_TE+M_MOD2 ;Rx/Tx enable, 8N1
514 db 1,stat1,0 ;Disable rx/tx ints, disable CTS1
515 db 1,asext1,M_BRGMOD ;Enable baud rate generator
516 db 2,astc1l,low 3, high 3
517 db 1,cntlb1,M_MPBT ;No MP Mode, X16
518 db 1,cntla1,M_RE+M_TE+M_MOD2 ;Rx/Tx enable, 8N1
522 ;--------------------------------------------------------------
532 ;--------------------------------------------------------------
541 ;--------------------------------------------------------------
542 ; Get an input character
568 ld a,b ;remaining chrs in buffer
569 cp s0.rx_len/4 ; < 32?
570 jr nc,a0i_2 ; no, just get char
571 ld b,(ix+oint.fflags) ; yes, enable RTS if needed
572 bit CRTS_IFLOW,b ; yes, enable RTS if needed
573 jr z,a0i_1 ; no needed
576 and ~M_RTS0 ;assert RTS
577 or M_EFR ;don't reset error flags
581 bit IXOFF,b ; XON/XOFF on input?
584 set TDC1,(ix+oint.stat) ;
594 ;--------------------------------------------------------------
595 ; Get an input character
601 ld a,b ; remaining chars in buffer
602 cp s0.rx_len/4 ; == 25% full?
603 jr nz,a1i_2 ; no, just get char
604 bit IXOFF,(ix+oint.fflags) ; XON/XOFF on input?
607 set TDC1,(ix+oint.stat) ;
613 ld a,c ; get back the char
617 ;--------------------------------------------------------------
627 ;--------------------------------------------------------------
637 ;--------------------------------------------------------------
638 ; put character in c in buffer
646 ld a,(as0_dev+o.stat) ;Transmitter stopped?
656 ;--------------------------------------------------------------
657 ; put character in c in buffer
665 ld a,(as1_dev+o.stat) ;Transmitter stopped?
676 ;--------------------------------------------------------------
687 ;--------------------------------------------------------------
688 ; ASCI 0/1 Transmit/Receive interupt routines
694 ld d,(ix+oint.fflags)
696 in0 e,(stat&dev) ;get asci status
697 jp p,txi&dev ;RDRF == Bit 7
702 in0 a,(asext&dev) ;get break status
704 or e ;merge to other error flags
707 in0 a,(cntla&dev) ;reset all error flags
711 ld c,(ix+o.in_idx) ;get input index
713 ld hl,s&dev&.inbuf ; + base = input buffer pointer
716 in0 b,(rdr&dev) ;get char
717 ;todo: break detection
718 ;todo: parity, framing, overrun error
726 set TOFF,(ix+oint.stat) ;Stop transmitter
732 res TOFF,(ix+oint.stat) ;Enable transmitter
737 res TOFF,(ix+oint.stat) ;Enable transmitter
740 ld a,c ;increment input index
746 sub (ix+o.out_idx) ;number of free places in buffer
747 jr z,rxtxi&dev&_lp1 ;buffer full?
749 ld (ix+o.in_idx),c ; no, update input index
751 cp s&dev&.tx_len*3/4 ;buffer now 75% full?
754 if dev=0 ;only channel 0 has rts line
758 or M_RTS0+M_EFR ;RTS inactive
766 set TDC3,(ix+oint.stat)
778 ld a,(ix+oint.stat) ;check whether xon/xoff should be sent
780 jr z,txi&dev&_char ; no
782 ld l,DC3 ;prepare for xoff
783 bit TDC1,a ;request for xon (also) set?
788 and ~(M_TDC1+M_TDC3) ;reset request flags
789 ld (ix+oint.stat),a ;
793 bit TOFF,(ix+oint.stat)
794 jr nz,txi&dev&_empty ;
796 ld hl,s&dev&.outbuf+o.in_idx ;[in]
801 jr z,txi&dev&_empty ;
808 ld a,(s&dev&.outbuf+o.mask);
810 ld (s&dev&.outbuf+o.out_idx),a ;
815 res TIE,e ;disable tx-int
824 ;--------------------------------------------------------------
825 ; ASCI 0 Transmit/Receive interupt routines
830 ;--------------------------------------------------------------
831 ; ASCI 1 Transmit/Receive interupt routines