]>
Commit | Line | Data |
---|---|---|
5da627a4 WD |
1 | /* |
2 | * AU1X00 UART support | |
3 | * | |
4 | * Hardcoded to UART 0 for now | |
5 | * Speed and options also hardcoded to 115200 8N1 | |
6 | * | |
7 | * Copyright (c) 2003 Thomas.Lange@corelatus.se | |
8 | * | |
9 | * See file CREDITS for list of people who contributed to this | |
10 | * project. | |
11 | * | |
12 | * This program is free software; you can redistribute it and/or | |
13 | * modify it under the terms of the GNU General Public License as | |
14 | * published by the Free Software Foundation; either version 2 of | |
15 | * the License, or (at your option) any later version. | |
16 | * | |
17 | * This program is distributed in the hope that it will be useful, | |
18 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
20 | * GNU General Public License for more details. | |
21 | * | |
22 | * You should have received a copy of the GNU General Public License | |
23 | * along with this program; if not, write to the Free Software | |
24 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, | |
25 | * MA 02111-1307 USA | |
26 | */ | |
27 | ||
28 | #include <config.h> | |
5da627a4 WD |
29 | #include <common.h> |
30 | #include <asm/au1x00.h> | |
31 | ||
32 | /****************************************************************************** | |
33 | * | |
34 | * serial_init - initialize a channel | |
35 | * | |
36 | * This routine initializes the number of data bits, parity | |
37 | * and set the selected baud rate. Interrupts are disabled. | |
38 | * Set the modem control signals if the option is selected. | |
39 | * | |
40 | * RETURNS: N/A | |
41 | */ | |
42 | ||
43 | int serial_init (void) | |
44 | { | |
45 | volatile u32 *uart_fifoctl = (volatile u32*)(UART0_ADDR+UART_FCR); | |
46 | volatile u32 *uart_enable = (volatile u32*)(UART0_ADDR+UART_ENABLE); | |
47 | ||
48 | /* Enable clocks first */ | |
49 | *uart_enable = UART_EN_CE; | |
50 | ||
51 | /* Then release reset */ | |
52 | /* Must release reset before setting other regs */ | |
53 | *uart_enable = UART_EN_CE|UART_EN_E; | |
54 | ||
55 | /* Activate fifos, reset tx and rx */ | |
56 | /* Set tx trigger level to 12 */ | |
57 | *uart_fifoctl = UART_FCR_ENABLE_FIFO|UART_FCR_CLEAR_RCVR| | |
58 | UART_FCR_CLEAR_XMIT|UART_FCR_T_TRIGGER_12; | |
59 | ||
60 | serial_setbrg(); | |
61 | ||
62 | return 0; | |
63 | } | |
64 | ||
65 | ||
66 | void serial_setbrg (void) | |
67 | { | |
68 | volatile u32 *uart_clk = (volatile u32*)(UART0_ADDR+UART_CLK); | |
69 | volatile u32 *uart_lcr = (volatile u32*)(UART0_ADDR+UART_LCR); | |
7a22cd53 WD |
70 | volatile u32 *sys_powerctrl = (u32 *)SYS_POWERCTRL; |
71 | int sd; | |
72 | int divisorx2; | |
5da627a4 | 73 | |
7a22cd53 WD |
74 | /* sd is system clock divisor */ |
75 | /* see section 10.4.5 in au1550 datasheet */ | |
76 | sd = (*sys_powerctrl & 0x03) + 2; | |
77 | ||
78 | /* calulate 2x baudrate and round */ | |
f2302d44 | 79 | divisorx2 = ((CFG_MIPS_TIMER_FREQ/(sd * 16 * CONFIG_BAUDRATE))); |
7a22cd53 WD |
80 | |
81 | if (divisorx2 & 0x01) | |
82 | divisorx2 = divisorx2 + 1; | |
83 | ||
84 | *uart_clk = divisorx2 / 2; | |
5da627a4 WD |
85 | |
86 | /* Set parity, stop bits and word length to 8N1 */ | |
87 | *uart_lcr = UART_LCR_WLEN8; | |
88 | } | |
89 | ||
90 | void serial_putc (const char c) | |
91 | { | |
92 | volatile u32 *uart_lsr = (volatile u32*)(UART0_ADDR+UART_LSR); | |
93 | volatile u32 *uart_tx = (volatile u32*)(UART0_ADDR+UART_TX); | |
94 | ||
95 | if (c == '\n') serial_putc ('\r'); | |
96 | ||
97 | /* Wait for fifo to shift out some bytes */ | |
98 | while((*uart_lsr&UART_LSR_THRE)==0); | |
99 | ||
100 | *uart_tx = (u32)c; | |
101 | } | |
102 | ||
103 | void serial_puts (const char *s) | |
104 | { | |
105 | while (*s) | |
106 | { | |
107 | serial_putc (*s++); | |
108 | } | |
109 | } | |
110 | ||
111 | int serial_getc (void) | |
112 | { | |
113 | volatile u32 *uart_rx = (volatile u32*)(UART0_ADDR+UART_RX); | |
114 | char c; | |
115 | ||
116 | while (!serial_tstc()); | |
117 | ||
118 | c = (*uart_rx&0xFF); | |
119 | return c; | |
120 | } | |
121 | ||
122 | int serial_tstc (void) | |
123 | { | |
124 | volatile u32 *uart_lsr = (volatile u32*)(UART0_ADDR+UART_LSR); | |
125 | ||
126 | if(*uart_lsr&UART_LSR_DR){ | |
127 | /* Data in rfifo */ | |
128 | return(1); | |
129 | } | |
130 | return 0; | |
131 | } |