; ;================================================================================================== ; eZ80 UART DRIVER (SERIAL PORT) ;================================================================================================== ; ; ; Supported Line Characteristics are encoded as follows in the DE register pair: ; ; | **Bits** | **Characteristic** | ; |---------:|----------------------------------------| ; | 15-14 | Reserved (set to 0) | ; | 13 | RTS (Not implemented) | ; | 12-8 | Baud Rate* (see below) | ; | 7 | DTR (Not implemented) | ; | 6 | XON/XOFF Flow Control (not implemented)| ; | 5 | Stick Parity (not implemented) | ; | 4 | Even Parity (set for true) | ; | 3 | Parity Enable (set for true) | ; | 2 | Stop Bits (0-> 1 BIT, 1-> 2 BITS) | ; | 1-0 | Data Bits (5-8 encoded as 0-3) | ; ; * The 5-bit Baud Rate value (V) is encoded as V = 75 * 2^X * 3^Y. The ; bits are defined as YXXXX. ; ; STICK & EVEN & PARITY -> MARK PARITY -> NOT SUPPORTED ; STICK & !EVEN & PARITY -> SPACE PARITY -> NOT SUPPORTED ; THEREFORE, MARK PARITY WILL BE INTERPRETED AS EVEN PARITY ; AND SPACE PARITY WILL BE INTERPRETED AS ODD PARITY UART0_LSR .EQU $C5 UART0_THR .EQU $C0 UART0_RBR .EQU $C0 LSR_THRE .EQU $20 LSR_DR .EQU $01 ; ;-------------------------------------------------------------------------------------------------- ; HBIOS MODULE HEADER ;-------------------------------------------------------------------------------------------------- ; ORG_EZ80UART .EQU $ ; .DW SIZ_EZ80UART ; MODULE SIZE .DW EZ80UART_INITPHASE ; ADR OF INIT PHASE HANDLER ; EZ80UART_INITPHASE: ; INIT PHASE HANDLER, A=PHASE CP HB_PHASE_PREINIT ; PREINIT PHASE? JP Z,EZUART_PREINIT ; DO PREINIT CP HB_PHASE_INIT ; INIT PHASE? JP Z,EZUART_INIT ; DO INIT RET ; DONE EZUART_PREINIT: LD BC, EZUART_FNTBL LD DE, EZUART_CFG CALL CIO_ADDENT LD (EZUART_ID), A XOR A RET EZUART_INIT: CALL NEWLINE ; FORMATTING CALL PRTSTRD .TEXT "EZ80 UART: UART0$" XOR A RET ; ; ### Function 0x00 -- Character Input (CIOIN) ; ; Read and return a Character (E). If no character(s) are available in the ; input buffer, this function will wait indefinitely. The returned Status ; (A) is a standard HBIOS result code. ; ; Outputs: ; E: Character ; A: Status (0-OK, else error) ; EZUART_IN: EZ80_UART_IN() ; CHAR RETURNED IN E RET ; ; ### Function 0x01 -- Character Output (CIOOUT) ; ; Send the Character (E). If there is no space available in the unit's output ; buffer, the function will wait indefinitely. The returned Status (A) is a ; standard HBIOS result code. ; ; Inputs: ; E: Character ; ; Outputs: ; A: Status (0-OK, else error) ; EZUART_OUT: EZ80_UART_OUT() RET ; ; ### Function 0x02 -- Character Input Status (CIOIST) ; ; Return the count of Characters Pending (A) in the input buffer. ; ; The value returned in register A is used as both a Status (A) code and ; the return value. Negative values (bit 7 set) indicate a standard HBIOS ; result (error) code. Otherwise, the return value represents the number ; of characters in the input buffer. ; ; Outputs: ; A: Status / Characters Pending ; EZUART_IST: EZ80_UART_IN_STAT() RET ; ; ### Function 0x03 -- Character Output Status (CIOOST) ; ; Return the status of the output FIFO. 0 means the output FIFO is full and ; no more characters can be sent. 1 means the output FIFO is not full and at ; least one character can be sent. Negative values (bit 7 set) indicate a ; standard HBIOS result (error) code. ; ; Outputs ; A: Status (0 -> Full, 1 -> OK to send, < 0 -> HBIOS error code) ; EZUART_OST: EZ80_UART_OUT_STAT() RET BAUD_RATE .EQU 115200 ; ; ### Function 0x04 -- Character I/O Initialization (CIOINIT) ; ; Apply the requested line Characteristics in (DE). The definition of the ; line characteristics value is described above. If DE contains -1 (0xFFFF), ; then the input and output buffers will be flushed and reset. ; The Status (A) is a standard HBIOS result code. ; ; Inputs: ; DE: Line Characteristics ; ; Outputs: ; A: Status (0-OK, else error) ; EZUART_INITDEV: LD A, D CP E JR NZ, NOT_RESET CP $FF JR NZ, NOT_RESET EZ80_UART_RESET() RET NOT_RESET: PUSH DE ; SAVE LINE CHARACTERISTICS LD A, D AND $1F ; ISOLATE ENCODED BAUD RATE LD L, A ; PUT IN L LD H, 0 ; H IS ALWAYS ZERO LD DE, 75 ; BAUD RATE DECODE CONSTANT CALL DECODE ; DE:HL := BAUD RATE EZ80_CPY_EHL_TO_UHL ; HL{23:0} <- E:HL{15:0} POP DE ; RESTORE REQUESTED LINE CHARACTERISTICS LD A, E AND 3 ; MASK FOR DATA BITS RLCA RLCA RLCA ; SHIFT TO BITS 4:3 LD D, A ; SAVE INTO D BIT 2, E ; STOP BITS (1 OR 2) JR Z, ISKIP1 SET 2, D ; APPLY TO D ISKIP1: BIT 3, E ; PARITY ENABLE JR Z, ISKIP2 SET 1, D ; APPLY TO D ISKIP2: BIT 4, E ; EVEN PARITY JR Z, ISKIP3 SET 0, D ; APPLY TO D ISKIP3: ; D NOW CONTAINS THE LINE CONTROL BITS AS PER EZ80 FUNCTION EZ80_UART_CONFIG() RET #DEFINE TRANSLATE(nnn,rrr) \ #defcont \ LDBCMM.LIL(nnn) #defcont \ SBCHLBC.LIL #defcont \ JR NC, $+7 #defcont \ LD D, rrr #defcont \ JP uart_query_end ; ; ### Function 0x05 -- Character I/O Query (CIOQUERY) ; ; Returns the current Line Characteristics (DE). The definition of the line ; characteristics value is described above. The returned status (A) is a ; standard HBIOS result code. ; ; As the eZ80 UART driver supports more than the defined HBIOS baud rates, the ; returned baud rate may be an approximation of the actual baud rate. ; ; Outputs: ; DE: Line Characteristics ; A: Status (0-OK, else error) ; EZUART_QUERY: EZ80_UART_QUERY() ; HL{23:0} := BAUD RATE ; D = LINE CONTROL BITS PUSH DE ; SAVE D OR A ; HL24 bit has the baud rate, we need to convert to the 5 bit representation? TRANSLATE(112, 00000b) ; BAUDRATE=75 (BETWEEN 0 AND 112) TRANSLATE(187-112, 00001b) ; BAUDRATE=150 (BETWEEN 113 AND 187) TRANSLATE(262-187, 10000b) ; BAUDRATE=225 (BETWEEN 188 AND 262) TRANSLATE(375-262, 00010b) ; BAUDRATE=300 (BETWEEN 263 AND 375) TRANSLATE(525-375, 10001b) ; BAUDRATE=450 (BETWEEN 376 AND 525) TRANSLATE(750-525, 00011b) ; BAUDRATE=600 (BETWEEN 526 AND 750) TRANSLATE(1050-750, 10010b) ; BAUDRATE=900 (BETWEEN 751 AND 1050) TRANSLATE(1500-1050, 00100b) ; BAUDRATE=1200 (BETWEEN 1051 AND 1500) TRANSLATE(2100-1500, 10011b) ; BAUDRATE=1800 (BETWEEN 1501 AND 2100) TRANSLATE(3000-2100, 00101b) ; BAUDRATE=2400 (BETWEEN 2101 AND 3000) TRANSLATE(4200-3000, 10100b) ; BAUDRATE=3600 (BETWEEN 3001 AND 4200) TRANSLATE(6000-4200, 00110b) ; BAUDRATE=4800 (BETWEEN 4201 AND 6000) TRANSLATE(8400-6000, 10101b) ; BAUDRATE=7200 (BETWEEN 6001 AND 8400) TRANSLATE(12000-8400, 00111b) ; BAUDRATE=9600 (BETWEEN 8401 AND 12000) TRANSLATE(16800-12000, 10110b) ; BAUDRATE=14400 (BETWEEN 12001 AND 16800) TRANSLATE(24000-16800, 01000b) ; BAUDRATE=19200 (BETWEEN 16801 AND 24000) TRANSLATE(33600-24000, 10111b) ; BAUDRATE=28800 (BETWEEN 24001 AND 33600) TRANSLATE(48000-33600, 01001b) ; BAUDRATE=38400 (BETWEEN 33601 AND 48000) TRANSLATE(67200-48000, 11000b) ; BAUDRATE=57600 (BETWEEN 48001 AND 67200) TRANSLATE(96000-67200, 01010b) ; BAUDRATE=76800 (BETWEEN 67201 AND 96000) TRANSLATE(134400-96000, 11001b) ; BAUDRATE=115200 (BETWEEN 96001 AND 134400) TRANSLATE(192000-134400, 01011b) ; BAUDRATE=153600 (BETWEEN 134401 AND 192000) TRANSLATE(268800-192000, 11010b) ; BAUDRATE=230400 (BETWEEN 192001 AND 268800) TRANSLATE(384000-268800, 01100b) ; BAUDRATE=307200 (BETWEEN 268801 AND 384000) TRANSLATE(537600-384000, 11011b) ; BAUDRATE=460800 (BETWEEN 384001 AND 537600) TRANSLATE(768000-537600, 01101b) ; BAUDRATE=614400 (BETWEEN 537601 AND 768000) TRANSLATE(1075200-768000, 11100b) ; BAUDRATE=921600 (BETWEEN 768001 AND 1075200) TRANSLATE(1536000-1075200, 01110b) ; BAUDRATE=1228800 (BETWEEN 1075201 AND 1536000) TRANSLATE(2150400-1536000, 11101b) ; BAUDRATE=1843200 (BETWEEN 1536001 AND 2150400) TRANSLATE(3072000-2150400, 01111b) ; BAUDRATE=2457600 (BETWEEN 2150401 AND 3072000) TRANSLATE(5529600-3072000, 11110b) ; BAUDRATE=3686400 (BETWEEN 3072001 AND 5529600) LD D, 11111b ; BAUDRATE=7372800 (>=5529601) uart_query_end: POP BC ; B = LINE CONTROL BITS ; Convert from line control settings from: ; ; B{0:1} = Parity (00 -> NONE, 01 -> NONE, 10 -> ODD, 11 -> EVEN) ; B{2} = Stop Bits (0 -> 1, 1 -> 2) ; B{3:4} = Data Bits (00 -> 5, 01 -> 6, 10 -> 7, 11 -> 8) ; B{5:5} = Hardware Flow Control CTS (0 -> OFF, 1 -> ON) ; ; to ; ; E{7} = TODO: DTR ; E{6} = NOT IMPLEMENTED: XON/XOFF Flow Control ; E{5} = NOT SUPPORTED: Stick Parity (set for true) ; E{4} = Even Parity (set for true) ; E{3} = Parity Enable (set for true) ; E{2} = Stop Bits (set for true) ; E{1:0} = Data Bits (5-8 encoded as 0-3) XOR A OR 3 << 3 ; ISOLATE DATA BITS AND B ; MASK IN DATA BITS RRCA ; SHIFT TO BITS 1:0 RRCA RRCA LD H, A ; H{1:0} DATA BITS BIT 2, B ; STOP BITS JR Z, SKIP1 SET 2, H ; APPLY TO H SKIP1: BIT 1, B ; PARITY ENABLE JR Z, SKIP2 SET 3, H ; APPLY TO H SKIP2: BIT 0, B ; EVEN PARITY JR Z, SKIP3 SET 4, H ; APPLY TO H SKIP3: LD E, H XOR A RET ; ; ### Function 0x06 -- Character I/O Device (CIODEVICE) ; ; Returns device information. The status (A) is a standard HBIOS result ; code. ; ; Outputs ; A: Status (0 - OK) ; C: Device Attribute (0 - RS/232) ; D: Device Type (CIODEV_EZ80UART) ; E: Physical Device Number ; H: Device Mode (0) ; L: Device I/O Base Address - Not Supported (0) ; EZUART_DEVICE: LD D, CIODEV_EZ80UART ; D := DEVICE TYPE LD E, (IY) ; E := PHYSICAL UNIT LD C, 0 ; C := DEVICE TYPE, 0x00 IS RS-232 LD HL, 0 ; H := MODE, L := BASE I/O ADDRESS XOR A ; SIGNAL SUCCESS RET EZUART_CFG: EZUART_ID: .DB 0 EZUART_FNTBL: .DW EZUART_IN .DW EZUART_OUT .DW EZUART_IST .DW EZUART_OST .DW EZUART_INITDEV .DW EZUART_QUERY .DW EZUART_DEVICE #IF (($ - EZUART_FNTBL) != (CIO_FNCNT * 2)) .ECHO "*** INVALID EZUART FUNCTION TABLE ***\n" #ENDIF ; ;-------------------------------------------------------------------------------------------------- ; HBIOS MODULE TRAILER ;-------------------------------------------------------------------------------------------------- ; END_EZ80UART .EQU $ SIZ_EZ80UART .EQU END_EZ80UART - ORG_EZ80UART ; MEMECHO "EZ80UART occupies " MEMECHO SIZ_EZ80UART MEMECHO " bytes.\n"