1 /*
2  * PROJECT:     NEC PC-98 series onboard hardware
3  * LICENSE:     GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4  * PURPOSE:     UART header file
5  * COPYRIGHT:   Copyright 2020 Dmitry Borisov (di.sean@protonmail.com)
6  */
7 
8 #pragma once
9 
10 /* COM1 (Intel 8251A-based UART) **********************************************/
11 
12 /*
13  * UART registers and definitions
14  */
15 #define SER1_IO_i_DATA               0x030
16 #define SER1_IO_i_STATUS             0x032
17     #define SER1_STATUS_TxRDY             0x01 /* Transmitter ready */
18     #define SER1_STATUS_RxRDY             0x02 /* Receiver ready */
19     #define SER1_STATUS_TxEMPTY           0x04 /* Transmitter empty */
20     #define SER1_STATUS_PE                0x08 /* Parity error */
21     #define SER1_STATUS_OE                0x10 /* Overrun error */
22     #define SER1_STATUS_FE                0x20 /* Framing error */
23     #define SER1_STATUS_SYNDET            0x40 /* Sync detect / Break detect */
24     #define SER1_STATUS_DSR               0x80 /* Data set ready */
25 #define SER1_IO_i_RECEIVER_BUFFER    0x130
26 #define SER1_IO_i_LINE_STATUS        0x132
27     #define SER1_LSR_TxEMPTY              0x01 /* Transmitter empty */
28     #define SER1_LSR_TxRDY                0x02 /* Transmitter ready */
29     #define SER1_LSR_RxRDY                0x04 /* Receiver ready */
30     #define SER1_LSR_OE                   0x10 /* Overrun error */
31     #define SER1_LSR_PE                   0x20 /* Parity error */
32     #define SER1_LSR_BI                   0x80 /* Break detect */
33 #define SER1_IO_i_MODEM_STATUS       0x134
34     #define SER_MSR_CTS_CHANGED           0x01 /* Change in clear to send */
35     #define SER_MSR_DSR_CHANGED           0x02 /* Change in data set ready */
36     #define SER_MSR_RI_CHANGED            0x04 /* Trailing edge ring indicator */
37     #define SER_MSR_DCD_CHANGED           0x08 /* Change in carrier detect */
38     #define SER_MSR_CTS                   0x10 /* Clear to send */
39     #define SER_MSR_DSR                   0x20 /* Data set ready */
40     #define SER_MSR_RI                    0x40 /* Ring indicator */
41     #define SER_MSR_DCD                   0x80 /* Data carrier detect */
42 #define SER1_IO_i_INTERRUPT_ID       0x136
43     #define SER_IIR_MS                    0x00 /* Modem status change */
44     #define SER_IIR_THR                   0x02 /* Transmitter holding register empty */
45     #define SER_IIR_RDA                   0x04 /* Received data acailable */
46     #define SER_IIR_RLS                   0x06 /* Receiver line status change */
47     #define SER_IIR_CTI                   0x0C /* Character timeout */
48     #define SER_IIR_ID_MASK               0x0F
49     #define SER_IIR_SELF                  0x01 /* No interrupt pending */
50     #define SER1_IIR_MUST_BE_ZERO         0x20
51     #define SER1_IIR_FIFOS_ENABLED        0x40 /* Toggles for each read */
52 #define SER1_IO_i_FIFO_CONTROL       0x138
53 #define SER1_IO_i_DIVISOR_LATCH      0x13A
54 
55 #define SER1_IO_o_DATA               0x030
56 #define SER1_IO_o_MODE_COMMAND       0x032
57     /* Parity generate/check */
58     #define SER1_MODE_PEN                 0x10 /* Parity enable */
59     #define SER1_MODE_EP                  0x20 /* Even parity generation/check */
60     #define SER1_MODE_ESD                 0x40 /* External sync detect */
61     #define SER1_MODE_SCS                 0x80 /* Single character sync */
62     /* Character length */
63     #define SER1_MODE_LENGTH_5            0x00
64     #define SER1_MODE_LENGTH_6            0x04
65     #define SER1_MODE_LENGTH_7            0x08
66     #define SER1_MODE_LENGTH_8            0x0C
67     /* Baud rate factor */
68     #define SER1_MODE_SYNC                0x00
69     #define SER1_MODE_CLOCKx1             0x01
70     #define SER1_MODE_CLOCKx16            0x02
71     #define SER1_MODE_CLOCKx64            0x03
72     /* Number of stop bits */
73     #define SER1_MODE_1_STOP              0x40
74     #define SER1_MODE_1_5_STOP            0x80
75     #define SER1_MODE_2_STOP              0xC0
76     /* Command bits */
77     #define SER1_COMMMAND_TxEN            0x01 /* Transmit enable */
78     #define SER1_COMMMAND_DTR             0x02 /* Data terminal ready */
79     #define SER1_COMMMAND_RxEN            0x04 /* Receive enable */
80     #define SER1_COMMMAND_SBRK            0x08 /* Send break character */
81     #define SER1_COMMMAND_ER              0x10 /* Error reset */
82     #define SER1_COMMMAND_RTS             0x20 /* Request to send */
83     #define SER1_COMMMAND_IR              0x40 /* Internal reset */
84     #define SER1_COMMMAND_EH              0x80 /* Enter hunt mode */
85 #define SER1_IO_o_TRANSMITTER_BUFFER 0x130
86 #define SER1_IO_o_FIFO_CONTROL       0x138
87     #define SER_FCR_DISABLE               0x00 /* Disable FIFO */
88     #define SER_FCR_ENABLE                0x01 /* Enable FIFO */
89     #define SER_FCR_RCVR_RESET            0x02 /* Clear receive FIFO */
90     #define SER_FCR_TXMT_RESET            0x04 /* Clear transmit FIFO */
91     /* Receive FIFO interrupt trigger level */
92     #define SER_FCR_1_BYTE_HIGH_WATER     0x00
93     #define SER_FCR_4_BYTE_HIGH_WATER     0x40
94     #define SER_FCR_8_BYTE_HIGH_WATER     0x80
95     #define SER_FCR_14_BYTE_HIGH_WATER    0xC0
96 #define SER1_IO_o_DIVISOR_LATCH      0x13A
97     #define SER1_DLR_BAUD_115200          0x01
98     #define SER1_DLR_BAUD_57600           0x02
99     #define SER1_DLR_BAUD_38400           0x03
100     #define SER1_DLR_BAUD_28800           0x04
101     #define SER1_DLR_BAUD_19200           0x06
102     #define SER1_DLR_BAUD_14400           0x08
103     #define SER1_DLR_BAUD_9600            0x0C
104     #define SER1_DLR_MODE_VFAST           0x80
105     #define SER1_DLR_MODE_LEGACY          0x00
106 
107 /* COM2 (National Semiconductor 16550 UART) ***********************************/
108 
109 /*
110  * UART registers and definitions
111  */
112 #define SER2_IO_i_RECEIVER_BUFFER    0x238 /* If DLAB = 0 */
113 #define SER2_IO_i_DIVISOR_LATCH_LSB  0x238 /* If DLAB = 1 */
114 #define SER2_IO_i_INTERRUPT_EN       0x239 /* If DLAB = 0 */
115 #define SER2_IO_i_DIVISOR_LATCH_MSB  0x239 /* If DLAB = 1 */
116 #define SER2_IO_i_INTERRUPT_ID       0x23A
117     /* Bits 0-3 same as for COM1 */
118     #define SER2_IIR_MUST_BE_ZERO         0x30
119     #define SER2_IIR_NO_FIFO              0x00
120     #define SER2_IIR_HAS_FIFO             0x40
121     #define SER2_IIR_FIFOS_ENABLED        0xC0
122 #define SER2_IO_i_LINE_CONTROL       0x23B
123 #define SER2_IO_i_MODEM_CONTROL      0x23C
124 #define SER2_IO_i_LINE_STATUS        0x23D
125     #define SER2_LSR_DR                   0x01 /* Data ready */
126     #define SER2_LSR_OE                   0x02 /* Overrun error */
127     #define SER2_LSR_PE                   0x04 /* Parity error */
128     #define SER2_LSR_FE                   0x80 /* Framing error */
129     #define SER2_LSR_BI                   0x80 /* Break interrupt */
130     #define SER2_LSR_THR_EMPTY            0x20 /* Transmit holding register empty */
131     #define SER2_LSR_TSR_EMPTY            0x40 /* Transmitter FIFO empty */
132     #define SER2_LSR_ERROR_IN_FIFO        0x80 /* FIFO error */
133 #define SER2_IO_i_MODEM_STATUS       0x23E
134     /* Bits 0-7 same as for COM1 */
135 #define SER2_IO_i_SCRATCH            0x23F
136 
137 #define SER2_IO_o_TRANSMITTER_BUFFER 0x238 /* If DLAB = 0 */
138 #define SER2_IO_o_DIVISOR_LATCH_LSB  0x238 /* If DLAB = 1 */
139     #define SER2_DLR_BAUD_115200          0x0001
140     #define SER2_DLR_BAUD_57600           0x0002
141     #define SER2_DLR_BAUD_38400           0x0003
142     #define SER2_DLR_BAUD_19200           0x0006
143     #define SER2_DLR_BAUD_9600            0x000C
144     #define SER2_DLR_BAUD_4800            0x0018
145     #define SER2_DLR_BAUD_2400            0x0030
146     #define SER2_DLR_BAUD_1200            0x0060
147     #define SER2_DLR_BAUD_600             0x00C0
148     #define SER2_DLR_BAUD_300             0x0180
149 #define SER2_IO_o_DIVISOR_LATCH_MSB  0x239 /* If DLAB = 1 */
150 #define SER2_IO_o_INTERRUPT_EN       0x239 /* If DLAB = 0 */
151     #define SER2_IER_DATA_RECEIVED        0x01 /* Received data available */
152     #define SER2_IER_THR_EMPTY            0x02 /* Transmitter holding register empty */
153     #define SER2_IER_LSR_CHANGE           0x04 /* Receiver line register status change */
154     #define SER2_IER_MSR_CHANGE           0x08 /* Modem status register change */
155 #define SER2_IO_o_FIFO_CONTROL       0x23A
156     /* Bits 0-2, 6-7 same as for COM1 */
157     #define SER2_FCR_DMA_SELECT           0x04
158 #define SER2_IO_o_LINE_CONTROL       0x23B
159     /* Character length */
160     #define SER2_LCR_LENGTH_5             0x00
161     #define SER2_LCR_LENGTH_6             0x01
162     #define SER2_LCR_LENGTH_7             0x02
163     #define SER2_LCR_LENGTH_8             0x03
164     /* Number of stop bits */
165     #define SER2_LCR_ST1                  0x00 /* 1 */
166     #define SER2_LCR_ST2                  0x04 /* 1.5 - 2 */
167     /* Parity generate/check */
168     #define SER2_LCR_NO_PARITY            0x00
169     #define SER2_LCR_ODD_PARITY           0x08
170     #define SER2_LCR_EVEN_PARITY          0x18
171     #define SER2_LCR_MARK_PARITY          0x28
172     #define SER2_LCR_SPACE_PARITY         0x38
173     #define SER2_LCR_BREAK                0x40
174     #define SER2_LCR_DLAB                 0x80 /* Divisor latch access bit */
175 #define SER2_IO_o_MODEM_CONTROL      0x23C
176     #define SER2_MCR_DTR_STATE            0x01 /* Data terminal ready */
177     #define SER2_MCR_RTS_STATE            0x02 /* Request to send */
178     #define SER2_MCR_OUT_1                0x04
179     #define SER2_MCR_OUT_2                0x08
180     #define SER2_MCR_LOOPBACK             0x10
181 #define SER2_IO_o_LINE_STATUS        0x23D
182 #define SER2_IO_o_SCRATCH            0x23F
183 
184 #define SER2_CLOCK_RATE    115200
185