1mod registers;
9
10use bitflags::Flags;
11use rdif_serial::{
12 Config, ConfigError, DataBits, InterfaceRaw, InterruptMask, Parity, SetBackError, StopBits,
13 TIrqHandler, TSender, TransferError,
14};
15use registers::*;
16
17#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
18mod pio;
19mod mmio;
21
22pub use mmio::*;
23#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
24pub use pio::*;
25
26use crate::{RawReciever, RawSender};
27
28pub trait Kind: Clone + Send + Sync + 'static {
29 fn read_reg(&self, reg: u8) -> u8;
30 fn write_reg(&self, reg: u8, val: u8);
31 fn get_base(&self) -> usize;
32
33 fn read_flags<F: Flags<Bits = u8>>(&self, reg: u8) -> F {
35 F::from_bits_retain(self.read_reg(reg))
36 }
37
38 fn write_flags<F: Flags<Bits = u8>>(&self, reg: u8, val: F) {
39 self.write_reg(reg, val.bits());
40 }
41}
42
43pub struct Ns16550<T: Kind> {
44 pub(crate) base: T,
45 pub(crate) clock_freq: u32,
46 pub(crate) irq: Option<Ns16550IrqHandler<T>>,
47 pub(crate) tx: Option<crate::Sender>,
48 pub(crate) rx: Option<crate::Reciever>,
49}
50
51impl<T: Kind> InterfaceRaw for Ns16550<T> {
52 type Sender = crate::Sender;
53 type Reciever = crate::Reciever;
54 type IrqHandler = Ns16550IrqHandler<T>;
55
56 fn name(&self) -> &str {
57 "NS16550 UART"
58 }
59
60 fn base_addr(&self) -> usize {
61 self.base.get_base()
62 }
63
64 fn set_config(&mut self, config: &Config) -> Result<(), ConfigError> {
65 if let Some(baudrate) = config.baudrate {
67 self.set_baudrate_internal(baudrate)?;
68 }
69
70 if let Some(data_bits) = config.data_bits {
72 self.set_data_bits_internal(data_bits)?;
73 }
74
75 if let Some(stop_bits) = config.stop_bits {
77 self.set_stop_bits_internal(stop_bits)?;
78 }
79
80 if let Some(parity) = config.parity {
82 self.set_parity_internal(parity)?;
83 }
84 Ok(())
85 }
86
87 fn baudrate(&self) -> u32 {
88 let dll = self.read_reg_u8(UART_DLL) as u16;
91 let dlh = self.read_reg_u8(UART_DLH) as u16;
92 let divisor = dll | (dlh << 8);
93
94 if divisor == 0 {
95 return 0;
96 }
97
98 self.clock_freq / (16 * divisor as u32)
99 }
100
101 fn data_bits(&self) -> DataBits {
102 let lcr: LineControlFlags = self.read_flags(UART_LCR);
103 let wlen = lcr & LineControlFlags::WORD_LENGTH_MASK;
104 if wlen == LineControlFlags::WORD_LENGTH_5 {
105 DataBits::Five
106 } else if wlen == LineControlFlags::WORD_LENGTH_6 {
107 DataBits::Six
108 } else if wlen == LineControlFlags::WORD_LENGTH_7 {
109 DataBits::Seven
110 } else {
111 DataBits::Eight }
113 }
114
115 fn stop_bits(&self) -> StopBits {
116 let lcr: LineControlFlags = self.read_flags(UART_LCR);
117 if lcr.contains(LineControlFlags::STOP_BITS) {
118 StopBits::Two
119 } else {
120 StopBits::One
121 }
122 }
123
124 fn parity(&self) -> Parity {
125 let lcr: LineControlFlags = self.read_flags(UART_LCR);
126
127 if !lcr.contains(LineControlFlags::PARITY_ENABLE) {
128 Parity::None
129 } else if lcr.contains(LineControlFlags::STICK_PARITY) {
130 if lcr.contains(LineControlFlags::EVEN_PARITY) {
132 Parity::Space
133 } else {
134 Parity::Mark
135 }
136 } else {
137 if lcr.contains(LineControlFlags::EVEN_PARITY) {
139 Parity::Even
140 } else {
141 Parity::Odd
142 }
143 }
144 }
145
146 fn clock_freq(&self) -> Option<core::num::NonZeroU32> {
147 self.clock_freq.try_into().ok()
148 }
149
150 fn open(&mut self) {
151 self.init();
152 }
153
154 fn close(&mut self) {
155 self.write_flags(UART_IER, InterruptEnableFlags::empty());
157
158 let mut mcr: ModemControlFlags = self.read_flags(UART_MCR);
160 mcr.remove(ModemControlFlags::DATA_TERMINAL_READY | ModemControlFlags::REQUEST_TO_SEND);
161 self.write_flags(UART_MCR, mcr);
162 }
163
164 fn enable_loopback(&mut self) {
165 let mut mcr: ModemControlFlags = self.read_flags(UART_MCR);
166 mcr.insert(ModemControlFlags::LOOPBACK_ENABLE);
167 self.write_flags(UART_MCR, mcr);
168 }
169
170 fn disable_loopback(&mut self) {
171 let mut mcr: ModemControlFlags = self.read_flags(UART_MCR);
172 mcr.remove(ModemControlFlags::LOOPBACK_ENABLE);
173 self.write_flags(UART_MCR, mcr);
174 }
175
176 fn is_loopback_enabled(&self) -> bool {
177 let mcr: ModemControlFlags = self.read_flags(UART_MCR);
178 mcr.contains(ModemControlFlags::LOOPBACK_ENABLE)
179 }
180
181 fn set_irq_mask(&mut self, mask: InterruptMask) {
182 let mut ier = InterruptEnableFlags::empty();
183
184 if mask.contains(InterruptMask::RX_AVAILABLE) {
185 ier.insert(InterruptEnableFlags::RECEIVED_DATA_AVAILABLE);
186 ier.insert(InterruptEnableFlags::RECEIVER_LINE_STATUS);
187 }
188 if mask.contains(InterruptMask::TX_EMPTY) {
189 ier.insert(InterruptEnableFlags::TRANSMITTER_HOLDING_EMPTY);
190 }
191
192 self.write_flags(UART_IER, ier);
193 }
194
195 fn get_irq_mask(&self) -> InterruptMask {
196 let ier: InterruptEnableFlags = self.read_flags(UART_IER);
197 let mut mask = InterruptMask::empty();
198
199 if ier.contains(InterruptEnableFlags::RECEIVED_DATA_AVAILABLE) {
200 mask |= InterruptMask::RX_AVAILABLE;
201 }
202 if ier.contains(InterruptEnableFlags::TRANSMITTER_HOLDING_EMPTY) {
203 mask |= InterruptMask::TX_EMPTY;
204 }
205 mask
209 }
210
211 fn irq_handler(&mut self) -> Option<Self::IrqHandler> {
212 self.irq.take()
213 }
214
215 fn take_tx(&mut self) -> Option<Self::Sender> {
216 self.tx.take()
217 }
218
219 fn take_rx(&mut self) -> Option<Self::Reciever> {
220 self.rx.take()
221 }
222
223 fn set_tx(&mut self, tx: Self::Sender) -> Result<(), SetBackError> {
224 let want = self.base.get_base();
225 match tx {
226 #[cfg(target_arch = "x86_64")]
227 crate::Sender::Ns16550Sender(ref sender) => {
228 let actual = sender.base.get_base();
229 if actual != want {
230 return Err(SetBackError::new(want, actual));
231 }
232 }
233 crate::Sender::Ns16550MmioSender(ref sender) => {
234 let actual = sender.base.get_base();
235 if actual != want {
236 return Err(SetBackError::new(want, actual));
237 }
238 }
239 _ => {
240 return Err(SetBackError::new(want, 0)); }
242 }
243 self.tx = Some(tx);
244 Ok(())
245 }
246
247 fn set_rx(&mut self, rx: Self::Reciever) -> Result<(), SetBackError> {
248 let want = self.base.get_base();
249 match rx {
250 #[cfg(target_arch = "x86_64")]
251 crate::Reciever::Ns16550Reciever(ref reciever) => {
252 let actual = reciever.base.get_base();
253 if actual != want {
254 return Err(SetBackError::new(want, actual));
255 }
256 }
257 crate::Reciever::Ns16550MmioReciever(ref reciever) => {
258 let actual = reciever.base.get_base();
259 if actual != want {
260 return Err(SetBackError::new(want, actual));
261 }
262 }
263 _ => {
264 return Err(SetBackError::new(want, 0)); }
266 }
267 self.rx = Some(rx);
268 Ok(())
269 }
270}
271
272impl<T: Kind> Ns16550<T> {
273 fn read_reg_u8(&self, reg: u8) -> u8 {
275 self.base.read_reg(reg)
276 }
277
278 fn write_reg_u8(&mut self, reg: u8, val: u8) {
279 self.base.write_reg(reg, val);
280 }
281
282 fn read_flags<F: Flags<Bits = u8>>(&self, reg: u8) -> F {
284 F::from_bits_retain(self.base.read_reg(reg))
285 }
286
287 fn write_flags<F: Flags<Bits = u8>>(&mut self, reg: u8, val: F) {
288 self.base.write_reg(reg, val.bits());
289 }
290
291 pub fn is_16550_plus(&self) -> bool {
293 let fifo: InterruptIdentificationFlags = self.read_flags(UART_IIR);
296 fifo.contains(InterruptIdentificationFlags::FIFO_ENABLE_MASK)
297 }
298
299 fn set_baudrate_internal(&mut self, baudrate: u32) -> Result<(), ConfigError> {
301 if baudrate == 0 || self.clock_freq == 0 {
302 return Err(ConfigError::InvalidBaudrate);
303 }
304
305 let divisor = self.clock_freq / (16 * baudrate);
306 if divisor == 0 || divisor > 0xFFFF {
307 return Err(ConfigError::InvalidBaudrate);
308 }
309
310 let mut lcr: LineControlFlags = self.read_flags(UART_LCR);
312
313 lcr.insert(LineControlFlags::DIVISOR_LATCH_ACCESS);
315 self.write_flags(UART_LCR, lcr);
316
317 self.write_reg_u8(UART_DLL, (divisor & 0xFF) as u8);
319 self.write_reg_u8(UART_DLH, ((divisor >> 8) & 0xFF) as u8);
320
321 lcr.remove(LineControlFlags::DIVISOR_LATCH_ACCESS);
323 self.write_flags(UART_LCR, lcr);
324
325 Ok(())
326 }
327
328 fn set_data_bits_internal(&mut self, bits: DataBits) -> Result<(), ConfigError> {
330 let wlen = match bits {
331 DataBits::Five => LineControlFlags::WORD_LENGTH_5,
332 DataBits::Six => LineControlFlags::WORD_LENGTH_6,
333 DataBits::Seven => LineControlFlags::WORD_LENGTH_7,
334 DataBits::Eight => LineControlFlags::WORD_LENGTH_8,
335 };
336
337 let mut lcr: LineControlFlags = self.read_flags(UART_LCR);
338 lcr.remove(LineControlFlags::WORD_LENGTH_MASK);
340 lcr.insert(wlen);
341 self.write_flags(UART_LCR, lcr);
342
343 Ok(())
344 }
345
346 fn set_stop_bits_internal(&mut self, bits: StopBits) -> Result<(), ConfigError> {
348 let mut lcr: LineControlFlags = self.read_flags(UART_LCR);
349 match bits {
350 StopBits::One => lcr.remove(LineControlFlags::STOP_BITS),
351 StopBits::Two => lcr.insert(LineControlFlags::STOP_BITS),
352 }
353 self.write_flags(UART_LCR, lcr);
354 Ok(())
355 }
356
357 fn set_parity_internal(&mut self, parity: Parity) -> Result<(), ConfigError> {
359 let mut lcr: LineControlFlags = self.read_flags(UART_LCR);
360
361 lcr.remove(
363 LineControlFlags::PARITY_ENABLE
364 | LineControlFlags::EVEN_PARITY
365 | LineControlFlags::STICK_PARITY,
366 );
367
368 match parity {
370 Parity::None => {
371 }
373 Parity::Odd => {
374 lcr.insert(LineControlFlags::PARITY_ENABLE);
375 }
376 Parity::Even => {
377 lcr.insert(LineControlFlags::PARITY_ENABLE | LineControlFlags::EVEN_PARITY);
378 }
379 Parity::Mark => {
380 lcr.insert(LineControlFlags::PARITY_ENABLE | LineControlFlags::STICK_PARITY);
381 }
382 Parity::Space => {
383 lcr.insert(
384 LineControlFlags::PARITY_ENABLE
385 | LineControlFlags::EVEN_PARITY
386 | LineControlFlags::STICK_PARITY,
387 );
388 }
389 }
390
391 self.write_flags(UART_LCR, lcr);
392 Ok(())
393 }
394
395 pub fn enable_fifo(&mut self, enable: bool) {
397 if enable && self.is_16550_plus() {
398 let mut fcr = FifoControlFlags::ENABLE_FIFO;
399 fcr.insert(FifoControlFlags::CLEAR_RECEIVER_FIFO);
400 fcr.insert(FifoControlFlags::CLEAR_TRANSMITTER_FIFO);
401 fcr.insert(FifoControlFlags::TRIGGER_1_BYTE);
402 self.write_flags(UART_FCR, fcr);
403 } else {
404 self.write_flags(UART_FCR, FifoControlFlags::empty());
405 }
406 }
407
408 pub fn set_fifo_trigger_level(&mut self, level: u8) {
410 if !self.is_16550_plus() {
411 return;
412 }
413
414 let trigger_value = match level {
415 0..=3 => FifoControlFlags::TRIGGER_1_BYTE,
416 4..=7 => FifoControlFlags::TRIGGER_4_BYTES,
417 8..=11 => FifoControlFlags::TRIGGER_8_BYTES,
418 _ => FifoControlFlags::TRIGGER_14_BYTES,
419 };
420
421 let mut fcr: FifoControlFlags = self.read_flags(UART_FCR);
423 fcr.remove(FifoControlFlags::TRIGGER_LEVEL_MASK);
424 fcr.insert(trigger_value);
425 self.write_flags(UART_FCR, fcr);
426 }
427
428 fn init(&mut self) {
430 self.write_flags(UART_IER, InterruptEnableFlags::empty());
432
433 let mut mcr: ModemControlFlags = self.read_flags(UART_MCR);
435 mcr.insert(ModemControlFlags::DATA_TERMINAL_READY | ModemControlFlags::REQUEST_TO_SEND);
436 self.write_flags(UART_MCR, mcr);
437 }
438
439 pub fn is_fifo_enabled(&self) -> bool {
441 if !self.is_16550_plus() {
442 return false;
443 }
444 let iir: InterruptIdentificationFlags = self.read_flags(UART_IIR);
446 iir.contains(InterruptIdentificationFlags::FIFO_ENABLE_MASK)
447 }
448}
449
450pub struct Ns16550Sender<T: Kind> {
451 pub(crate) base: T,
452}
453
454impl<T: Kind> TSender for Ns16550Sender<T> {
455 fn write_byte(&mut self, byte: u8) -> bool {
456 RawSender::write_byte(self, byte)
457 }
458}
459
460pub struct Ns16550Reciever<T: Kind> {
461 pub(crate) base: T,
462}
463
464impl<T: Kind> RawReciever for Ns16550Reciever<T> {
465 fn read_byte(&mut self) -> Option<Result<u8, TransferError>> {
466 let lsr: LineStatusFlags = self.base.read_flags(UART_LSR);
467
468 if lsr.contains(LineStatusFlags::OVERRUN_ERROR) {
470 let b = self.base.read_reg(UART_RBR);
471 return Some(Err(TransferError::Overrun(b)));
472 }
473
474 if lsr.contains(LineStatusFlags::PARITY_ERROR) {
475 let _b = self.base.read_reg(UART_RBR);
476 return Some(Err(TransferError::Parity));
477 }
478
479 if lsr.contains(LineStatusFlags::FRAMING_ERROR) {
480 let _b = self.base.read_reg(UART_RBR);
481 return Some(Err(TransferError::Framing));
482 }
483
484 if lsr.contains(LineStatusFlags::BREAK_INTERRUPT) {
485 let _b = self.base.read_reg(UART_RBR);
486 return Some(Err(TransferError::Break));
487 }
488
489 if lsr.contains(LineStatusFlags::DATA_READY) {
490 let b = self.base.read_reg(UART_RBR);
491 return Some(Ok(b));
492 }
493 None
494 }
495}
496
497pub struct Ns16550IrqHandler<T: Kind> {
498 pub(crate) base: T,
499}
500
501impl<T: Kind> TIrqHandler for Ns16550IrqHandler<T> {
502 fn clean_interrupt_status(&self) -> InterruptMask {
503 let iir: InterruptIdentificationFlags = self.base.read_flags(UART_IIR);
504 let mut mask = InterruptMask::empty();
505
506 if iir.contains(InterruptIdentificationFlags::NO_INTERRUPT_PENDING) {
508 return mask;
509 }
510
511 let interrupt_id = iir & InterruptIdentificationFlags::INTERRUPT_ID_MASK;
513
514 if interrupt_id == InterruptIdentificationFlags::RECEIVER_LINE_STATUS
516 || interrupt_id == InterruptIdentificationFlags::RECEIVED_DATA_AVAILABLE
517 || interrupt_id == InterruptIdentificationFlags::CHARACTER_TIMEOUT
518 {
519 mask |= InterruptMask::RX_AVAILABLE;
521 } else if interrupt_id == InterruptIdentificationFlags::TRANSMITTER_HOLDING_EMPTY {
522 mask |= InterruptMask::TX_EMPTY;
524 } else if interrupt_id == InterruptIdentificationFlags::MODEM_STATUS {
525 }
527
528 mask
529 }
530}
531
532impl<T: Kind> RawSender for Ns16550Sender<T> {
533 fn write_byte(&mut self, byte: u8) -> bool {
534 let lsr: LineStatusFlags = self.base.read_flags(UART_LSR);
535 if lsr.contains(LineStatusFlags::TRANSMITTER_HOLDING_EMPTY) {
536 self.base.write_reg(UART_THR, byte);
537 true
538 } else {
539 false
540 }
541 }
542}