serial: lpc32xx: Move HSU_OFFSET to platform code
[linux-2.6.34-lpc32xx.git] / arch / arm / mach-lpc32xx / serial.c
1 /*
2  * arch/arm/mach-lpc32xx/serial.c
3  *
4  * Author: Kevin Wells <kevin.wells@nxp.com>
5  *
6  * Copyright (C) 2010 NXP Semiconductors
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU General Public License for more details.
17  */
18
19 #include <linux/kernel.h>
20 #include <linux/types.h>
21 #include <linux/serial.h>
22 #include <linux/serial_core.h>
23 #include <linux/serial_reg.h>
24 #include <linux/serial_8250.h>
25 #include <linux/clk.h>
26 #include <linux/io.h>
27
28 #include <mach/hardware.h>
29 #include <mach/platform.h>
30 #include <mach/board.h>
31 #include "common.h"
32
33 #define LPC32XX_SUART_FIFO_SIZE 64
34
35 /* Standard 8250/16550 compatible serial ports */
36 static struct plat_serial8250_port serial_std_platform_data[] = {
37 #ifdef CONFIG_ARCH_LPC32XX_UART5_SELECT
38         {
39                 .membase        = io_p2v(LPC32XX_UART5_BASE),
40                 .mapbase        = LPC32XX_UART5_BASE,
41                 .irq            = IRQ_LPC32XX_UART_IIR5,
42                 .regshift       = 2,
43                 .iotype         = UPIO_MEM32,
44                 .flags          = UPF_BOOT_AUTOCONF | UPF_BUGGY_UART |
45                                         UPF_SKIP_TEST,
46         },
47 #endif
48 #ifdef CONFIG_ARCH_LPC32XX_UART3_SELECT
49         {
50                 .membase        = io_p2v(LPC32XX_UART3_BASE),
51                 .mapbase        = LPC32XX_UART3_BASE,
52                 .irq            = IRQ_LPC32XX_UART_IIR3,
53                 .regshift       = 2,
54                 .iotype         = UPIO_MEM32,
55                 .flags          = UPF_BOOT_AUTOCONF | UPF_BUGGY_UART |
56                                         UPF_SKIP_TEST,
57         },
58 #endif
59 #ifdef CONFIG_ARCH_LPC32XX_UART4_SELECT
60         {
61                 .membase        = io_p2v(LPC32XX_UART4_BASE),
62                 .mapbase        = LPC32XX_UART4_BASE,
63                 .irq            = IRQ_LPC32XX_UART_IIR4,
64                 .regshift       = 2,
65                 .iotype         = UPIO_MEM32,
66                 .flags          = UPF_BOOT_AUTOCONF | UPF_BUGGY_UART |
67                                         UPF_SKIP_TEST,
68         },
69 #endif
70 #ifdef CONFIG_ARCH_LPC32XX_UART6_SELECT
71         {
72                 .membase        = io_p2v(LPC32XX_UART6_BASE),
73                 .mapbase        = LPC32XX_UART6_BASE,
74                 .irq            = IRQ_LPC32XX_UART_IIR6,
75                 .regshift       = 2,
76                 .iotype         = UPIO_MEM32,
77                 .flags          = UPF_BOOT_AUTOCONF | UPF_BUGGY_UART |
78                                         UPF_SKIP_TEST,
79         },
80 #endif
81         { },
82 };
83
84 struct uartinit {
85         char *uart_ck_name;
86         u32 ck_mode_mask;
87         void __iomem *pdiv_clk_reg;
88         resource_size_t mapbase;
89         bool enabled;
90 };
91
92 static struct uartinit uartinit_data[] __initdata = {
93         {
94                 .uart_ck_name = "uart5_ck",
95                 .ck_mode_mask =
96                         LPC32XX_UART_CLKMODE_LOAD(LPC32XX_UART_CLKMODE_ON, 5),
97                 .pdiv_clk_reg = LPC32XX_CLKPWR_UART5_CLK_CTRL,
98                 .mapbase = LPC32XX_UART5_BASE,
99 #ifdef CONFIG_ARCH_LPC32XX_UART5_SELECT
100                 .enabled = true,
101 #endif
102         },
103         {
104                 .uart_ck_name = "uart3_ck",
105                 .ck_mode_mask =
106                         LPC32XX_UART_CLKMODE_LOAD(LPC32XX_UART_CLKMODE_ON, 3),
107                 .pdiv_clk_reg = LPC32XX_CLKPWR_UART3_CLK_CTRL,
108                 .mapbase = LPC32XX_UART3_BASE,
109 #ifdef CONFIG_ARCH_LPC32XX_UART3_SELECT
110                 .enabled = true,
111 #endif
112         },
113         {
114                 .uart_ck_name = "uart4_ck",
115                 .ck_mode_mask =
116                         LPC32XX_UART_CLKMODE_LOAD(LPC32XX_UART_CLKMODE_ON, 4),
117                 .pdiv_clk_reg = LPC32XX_CLKPWR_UART4_CLK_CTRL,
118                 .mapbase = LPC32XX_UART4_BASE,
119 #ifdef CONFIG_ARCH_LPC32XX_UART4_SELECT
120                 .enabled = true,
121 #endif
122         },
123         {
124                 .uart_ck_name = "uart6_ck",
125                 .ck_mode_mask =
126                         LPC32XX_UART_CLKMODE_LOAD(LPC32XX_UART_CLKMODE_ON, 6),
127                 .pdiv_clk_reg = LPC32XX_CLKPWR_UART6_CLK_CTRL,
128                 .mapbase = LPC32XX_UART6_BASE,
129 #ifdef CONFIG_ARCH_LPC32XX_UART6_SELECT
130                 .enabled = true,
131 #endif
132         },
133 };
134
135 static struct platform_device serial_std_platform_device = {
136         .name                   = "serial8250",
137         .id                     = 0,
138         .dev                    = {
139                 .platform_data  = serial_std_platform_data,
140         },
141 };
142
143 /* High speed serial ports */
144 static struct lpc32xx_hsuart_port serial_hspd_platform_data[] = {
145 #ifdef CONFIG_ARCH_LPC32XX_HSUART1_SELECT
146         {
147                 .port                                   = {
148                         .membase        = io_p2v(LPC32XX_HS_UART1_BASE),
149                         .mapbase        = LPC32XX_HS_UART1_BASE,
150                         .irq            = IRQ_LPC32XX_UART_IIR1,
151                         .regshift       = 2,
152                         .iotype         = UPIO_MEM32,
153                         .flags          = UPF_BOOT_AUTOCONF,
154                 },
155                 .fbit_sam       = 20,
156         },
157 #endif
158 #ifdef CONFIG_ARCH_LPC32XX_HSUART2_SELECT
159         {
160                 .port                                   = {
161                         .membase        = io_p2v(LPC32XX_HS_UART2_BASE),
162                         .mapbase        = LPC32XX_HS_UART2_BASE,
163                         .irq            = IRQ_LPC32XX_UART_IIR2,
164                         .regshift       = 2,
165                         .iotype         = UPIO_MEM32,
166                         .flags          = UPF_BOOT_AUTOCONF,
167                 },
168                 .fbit_sam       = 20,
169         },
170 #endif
171 #ifdef CONFIG_ARCH_LPC32XX_HSUART7_SELECT
172         {
173                 .port                                   = {
174                         .membase        = io_p2v(LPC32XX_HS_UART7_BASE),
175                         .mapbase        = LPC32XX_HS_UART7_BASE,
176                         .irq            = IRQ_LPC32XX_UART_IIR7,
177                         .regshift       = 2,
178                         .iotype         = UPIO_MEM32,
179                         .flags          = UPF_BOOT_AUTOCONF,
180                 },
181                 .fbit_sam       = 20,
182         },
183 #endif
184         { },
185 };
186
187 static struct platform_device serial_hspd_platform_device = {
188         .name                   = "lpc32xx_hsuart",
189         .id                     = 0,
190         .dev                    = {
191                 .platform_data  = serial_hspd_platform_data,
192         },
193 };
194
195 static struct platform_device *lpc32xx_serial_devs[] __initdata = {
196         &serial_std_platform_device,
197         &serial_hspd_platform_device,
198 };
199
200 void __init lpc32xx_serial_init(void)
201 {
202         u32 tmp, tmpclk, clkmodes = 0, clkmodesdone = 0;
203         struct clk *clk;
204         resource_size_t puart;
205         int i, j, k = 0;
206
207         /*
208          * For each standard UART, enable the UART clock, and force
209          * FIFO flush. This works around a HW bug with the 8250 where
210          * the FIFOs may not work correctly. This should be done even if
211          * the standard UARTs are not used. The clocks will be disabled
212          * when done.
213          */
214         for (i = 0; i < ARRAY_SIZE(uartinit_data); i++) {
215                 clk = clk_get(NULL, uartinit_data[i].uart_ck_name);
216                 if (!IS_ERR(clk)) {
217                         clk_enable(clk);
218                         tmpclk = clk_get_rate(clk);
219
220                         /*
221                          * Fall back on main osc rate if clock rate return
222                          * fails
223                          */
224                         if (tmpclk == 0)
225                                 tmpclk = LPC32XX_MAIN_OSC_FREQ;
226
227                         /* pre-UART clock divider set to 1 */
228                         __raw_writel(0x0101, uartinit_data[i].pdiv_clk_reg);
229
230                         /* Setup UART clock modes for all UART to always on */
231                         clkmodes = uartinit_data[i].ck_mode_mask;
232                         __raw_writel(clkmodes, LPC32XX_UARTCTL_CLKMODE);
233
234                         /*
235                          * Force a flush of the RX FIFOs to work around a
236                          * HW bug
237                          */
238                         puart = uartinit_data[i].mapbase;
239                         __raw_writel(0xC1, LPC32XX_UART_IIR_FCR(puart));
240                         __raw_writel(0x00, LPC32XX_UART_DLL_FIFO(puart));
241                         j = LPC32XX_SUART_FIFO_SIZE;
242                         while (j--)
243                                 tmp = __raw_readl(
244                                         LPC32XX_UART_DLL_FIFO(puart));
245                         __raw_writel(0, LPC32XX_UART_IIR_FCR(puart));
246
247                         /*
248                          * The 8250 serial drivers do not use any type of
249                          * clock management, so the clocks need to be
250                          * pre-enabled here before the 8250 driver attempts
251                          * to access the peripherals. If a UART is enabled,
252                          * just leave the clock on.
253                          */
254                         if (uartinit_data[i].enabled) {
255                                 clkmodesdone |= clkmodes;
256                                 serial_std_platform_data[k++].uartclk = tmpclk;
257                         } else {
258                                 clk_disable(clk);
259                                 clk_put(clk);
260                         }
261                 }
262         }
263
264         /* Enable clocks only for enabled UARTs */
265         __raw_writel(clkmodesdone, LPC32XX_UARTCTL_CLKMODE);
266
267         /*
268          * Get current PCLK rate and use it for the base clock for all the
269          * high speed UARTS
270          */
271         tmpclk = 0;
272         clk = clk_get(NULL, "pclk_ck");
273         if (!IS_ERR(clk)) {
274                 tmpclk = clk_get_rate(clk);
275                 clk_put(clk);
276         }
277         if (!tmpclk)
278                 tmpclk = LPC32XX_MAIN_OSC_FREQ;
279
280         /* Setup of HSUART devices */
281         for (i = 0; i < ARRAY_SIZE(serial_hspd_platform_data) - 1; i++) {
282                 serial_hspd_platform_data[i].port.line = i;
283                 serial_hspd_platform_data[i].port.uartclk = tmpclk;
284         }
285
286         /* Disable UART5->USB transparent mode or USB won't work */
287         tmp = __raw_readl(LPC32XX_UARTCTL_CTRL);
288         tmp &= ~LPC32XX_UART_U5_ROUTE_TO_USB;
289         __raw_writel(tmp, LPC32XX_UARTCTL_CTRL);
290
291         platform_add_devices(lpc32xx_serial_devs,
292                 ARRAY_SIZE(lpc32xx_serial_devs));
293 }