]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - board/MAI/AmigaOneG3SE/serial.c
* Patch by Thomas Frieden, 13 Nov 2002:
[karo-tx-uboot.git] / board / MAI / AmigaOneG3SE / serial.c
1 #include <common.h>
2 #include <ns16550.h>
3 #include "short_types.h"
4 #include "memio.h"
5 #include "articiaS.h"
6
7 #ifndef CFG_NS16550
8 static uint32 ComPort1;
9
10 uint16 SerialEcho = 1;
11
12
13 #define RECEIVER_HOLDING 0
14 #define TRANSMITTER_HOLDING 0
15 #define INTERRUPT_ENABLE 1
16 #define INTERRUPT_STATUS 2
17 #define FIFO_CONTROL 2
18 #define LINE_CONTROL 3
19 #define MODEM_CONTROL 4
20 #define LINE_STATUS 5
21 #define MODEM_STATUS 6
22 #define SCRATCH_PAD 7
23
24 #define DIVISOR_LATCH_LSB 0
25 #define DIVISOR_LATCH_MSB 1
26 #define PRESCALER_DIVISION 5
27
28 #define COM_WRITE_BYTE(reg, byte) out_byte((ComPort1+reg), byte)
29 #define COM_READ_BYTE(reg) in_byte((ComPort1+reg))
30
31 static int serial_init_done = 0;
32
33 void serial_init (void)
34 {
35 #if 0
36         uint32 clock_divisor = 115200 / baudrate;
37         uint8 cfg;
38         uint8 a;
39         uint16 devfn = 7 << 3;
40
41         if (serial_init_done)
42                 return;
43
44         /*  Enter configuration mode */
45         cfg = pci_read_cfg_byte (0, devfn, 0x85);
46         pci_write_cfg_byte (0, devfn, 0x85, cfg | 0x02);
47
48         /* Set serial port COM1 as 3F8 */
49         out_byte (0x3F0, 0xE7);
50         out_byte (0x3f1, 0xfe);
51
52         /* Set serial port COM2 as 2F8 */
53         out_byte (0x3f0, 0xe8);
54         out_byte (0x3f1, 0xeb);
55
56         /* Enable */
57         out_byte (0x3f0, 0xe2);
58         a = in_byte (0x3f1);
59         a |= 0xc;
60         out_byte (0x3f0, 0xe2);
61         out_byte (0x3f1, a);
62
63         /*  Reset the configuration mode */
64         pci_write_cfg_byte (0, devfn, 0x85, cfg);
65 #endif
66
67         ComPort1 = 0x3F8;
68
69         /*  Disable interrupts */
70         COM_WRITE_BYTE (INTERRUPT_ENABLE, 0x00);
71
72         /*  Set baud rate */
73         /* COM_WRITE_BYTE(LINE_CONTROL, 0x83); */
74         /* COM_WRITE_BYTE(DIVISOR_LATCH_LSB, (uint8)(clock_divisor & 0xFF)); */
75         /* COM_WRITE_BYTE(DIVISOR_LATCH_MSB, (uint8)(clock_divisor >> 8)); */
76         /* __asm("eieio"); */
77
78         /*  Set 8-N-1 */
79         COM_WRITE_BYTE (LINE_CONTROL, 0x03);
80         __asm ("eieio");
81
82         /*  Disable FIFO */
83         COM_WRITE_BYTE (MODEM_CONTROL, 0x03);
84         COM_WRITE_BYTE (FIFO_CONTROL, 0x07);
85
86         __asm ("eieio");
87         serial_init_done = 1;
88 }
89
90 extern int console_changed;
91
92 void serial_putc (const char sendme)
93 {
94         if (sendme == '\n') {
95                 while ((in_byte (0x3FD) & 0x40) == 0);
96                 out_byte (0x3f8, 0x0D);
97         }
98
99         while ((in_byte (0x3FD) & 0x40) == 0);
100         out_byte (0x3f8, sendme);
101 }
102
103 int serial_getc (void)
104 {
105 #if 0
106         uint8 c;
107
108         for (;;) {
109                 uint8 x = in_byte (0x3FD);
110
111                 if (x & 0x01)
112                         break;
113
114                 if (x & 0x0C)
115                         out_byte (0x3fd, 0x0c);
116         }
117
118         c = in_byte (0x3F8);
119
120         return c;
121 #else
122         while ((in_byte (0x3FD) & 0x01) == 0) {
123                 if (console_changed != 0) {
124                         printf ("Console changed\n");
125                         console_changed = 0;
126                         return 0;
127                 }
128         }
129         return in_byte (0x3F8);
130 #endif
131 }
132
133 int serial_tstc (void)
134 {
135         return (in_byte (0x03FD) & 0x01) != 0;
136 }
137
138 void serial_debug_putc (int c)
139 {
140         serial_puts ("DBG");
141         serial_putc (c);
142         serial_putc (0x0d);
143         serial_putc (0x0A);
144 }
145
146 #else
147
148 const NS16550_t Com0 = (NS16550_t) CFG_NS16550_COM1;
149 const NS16550_t Com1 = (NS16550_t) CFG_NS16550_COM2;
150
151 int serial_init (void)
152 {
153         DECLARE_GLOBAL_DATA_PTR;
154
155         uint32 clock_divisor = 115200 / gd->baudrate;
156
157         NS16550_init (Com0, clock_divisor);
158         /* NS16550_reinit(Com1, clock_divisor); */
159         /* serial_puts("COM1: 3F8h initalized"); */
160
161         return (0);
162 }
163
164 #if 0
165 void serial_putc (const char c)
166 {
167         NS16550_putc (Com0, c);
168         if (c == '\n')
169                 NS16550_putc (Com0, 0x0D);
170 }
171
172 int serial_getc (void)
173 {
174         return (int) NS16550_getc (Com0);
175 }
176
177 int serial_tstc (void)
178 {
179         return NS16550_tstc (Com0);
180 }
181 #else
182 void serial_putc (const char sendme)
183 {
184         if (sendme == '\n') {
185                 while ((in_byte (0x3FD) & 0x40) == 0);
186                 out_byte (0x3f8, 0x0D);
187         }
188
189         while ((in_byte (0x3FD) & 0x40) == 0);
190         out_byte (0x3f8, sendme);
191 }
192
193
194 extern int console_changed;
195
196 int serial_getc (void)
197 {
198 #if 0
199         uint8 c;
200
201         for (;;) {
202                 uint8 x = in_byte (0x3FD);
203
204                 if (x & 0x01)
205                         break;
206
207                 if (x & 0x0C)
208                         out_byte (0x3fd, 0x0c);
209         }
210
211         c = in_byte (0x3F8);
212
213         return c;
214 #else
215         while ((in_byte (0x3FD) & 0x01) == 0) {
216                 if (console_changed != 0) {
217                         console_changed = 0;
218                         return 0;
219                 }
220         }
221
222         return in_byte (0x3F8);
223 #endif
224 }
225
226 int serial_tstc (void)
227 {
228         return (in_byte (0x03FD) & 0x01) != 0;
229 }
230 #endif
231
232 #endif
233
234 void serial_puts (const char *string)
235 {
236         while (*string)
237                 serial_putc (*string++);
238 }
239
240 void serial_setbrg (void)
241 {
242         DECLARE_GLOBAL_DATA_PTR;
243
244         uint32 clock_divisor = 115200 / gd->baudrate;
245
246         NS16550_init (Com0, clock_divisor);
247 }