1#include <stdbool.h>
2#include <stdio.h>
3
4#include "mystuff.h"
5#include "file.h"
6#include "io.h"
7
8enum {
9 THR = 0,
10 RBR = 0,
11 DLL = 0,
12 DLM = 1,
13 IER = 1,
14 IIR = 2,
15 FCR = 2,
16 LCR = 3,
17 MCR = 4,
18 LSR = 5,
19 MSR = 6,
20 SCR = 7,
21};
22
23int serial_init(struct serial_if *sif)
24{
25 uint16_t port = sif->port;
26 uint8_t dll, dlm, lcr;
27
28
29 outb(0x83, port + LCR);
30 outb(0x01, port + DLL);
31 outb(0x00, port + DLM);
32 (void)inb(port + IER);
33 dll = inb(port + DLL);
34 dlm = inb(port + DLM);
35 lcr = inb(port + LCR);
36 outb(0x03, port + LCR);
37 (void)inb(port + IER);
38
39 if (dll != 0x01 || dlm != 0x00 || lcr != 0x83)
40 return -1;
41
42
43 outb(port + IER, 0);
44
45
46 outb(port + FCR, 0x01);
47 (void)inb(port + IER);
48 if (inb(port + IIR) < 0xc0)
49 outb(port + FCR, 0x00);
50 (void)inb(port + IER);
51
52 return 0;
53}
54
55void serial_write(struct serial_if *sif, const void *data, size_t n)
56{
57 uint16_t port = sif->port;
58 const char *p = data;
59 uint8_t lsr;
60
61 while (n--) {
62 do {
63 lsr = inb(port + LSR);
64 } while (!(lsr & 0x20));
65
66 outb(*p++, port + THR);
67 }
68}
69
70void serial_read(struct serial_if *sif, void *data, size_t n)
71{
72 uint16_t port = sif->port;
73 char *p = data;
74 uint8_t lsr;
75
76 while (n--) {
77 do {
78 lsr = inb(port + LSR);
79 } while (!(lsr & 0x01));
80
81 *p++ = inb(port + RBR);
82 }
83}
84