Title: [7476] trunk: Task[#5518] Move all bfin serial platform data into board file.

Diff

Modified: trunk/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -81,17 +81,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	0xFFC02000,
-#else
-	0,
-#endif
-};
-

Modified: trunk/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -81,17 +81,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	0xFFC02000,
-#else
-	0,
-#endif
-};
-

Modified: trunk/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -82,12 +82,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-};
-

Modified: trunk/arch/blackfin/mach-bf537/boards/stamp.c (7475 => 7476)


--- trunk/arch/blackfin/mach-bf537/boards/stamp.c	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf537/boards/stamp.c	2009-09-28 02:09:06 UTC (rev 7476)
@@ -1133,11 +1133,18 @@
 #endif
 };
 
+unsigned short bfin_uart0_peripherals[] = {
+	P_UART0_TX, P_UART0_RX, 0
+};
+
 static struct platform_device bfin_uart0_device = {
 	.name = "bfin-uart",
 	.id = 0,
 	.num_resources = ARRAY_SIZE(bfin_uart0_resources),
 	.resource = bfin_uart0_resources,
+	.dev = {
+		.platform_data = &bfin_uart0_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #ifdef CONFIG_SERIAL_BFIN_UART1
@@ -1187,11 +1194,18 @@
 #endif
 };
 
+unsigned short bfin_uart1_peripherals[] = {
+	P_UART1_TX, P_UART1_RX, 0
+};
+
 static struct platform_device bfin_uart1_device = {
 	.name = "bfin-uart",
 	.id = 1,
 	.num_resources = ARRAY_SIZE(bfin_uart1_resources),
 	.resource = bfin_uart1_resources,
+	.dev = {
+		.platform_data = &bfin_uart1_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #endif
@@ -1865,7 +1879,7 @@
 
 
 static struct platform_device *stamp_early_devices[] __initdata = {
-#if defined(CONFIG_SERIAL_BFIN_CONSOLE)
+#if defined(CONFIG_SERIAL_BFIN_CONSOLE) || defined(CONFIG_EARLY_PRINTK)
 #ifdef CONFIG_SERIAL_BFIN_UART0
 	&bfin_uart0_device,
 #endif

Modified: trunk/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -80,18 +80,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	0xFFC02000,
-#else
-	0,
-#endif
-};
-
-#define DRIVER_NAME "bfin-uart"

Modified: trunk/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -81,22 +81,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	0xFFC02000,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-	0xFFC02100,
-#else
-	0,
-#endif
-};
-

Modified: trunk/arch/blackfin/mach-bf548/boards/ezkit.c (7475 => 7476)


--- trunk/arch/blackfin/mach-bf548/boards/ezkit.c	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf548/boards/ezkit.c	2009-09-28 02:09:06 UTC (rev 7476)
@@ -277,11 +277,18 @@
 #endif
 };
 
+unsigned short bfin_uart0_peripherals[] = {
+	P_UART0_TX, P_UART0_RX, 0
+};
+
 static struct platform_device bfin_uart0_device = {
 	.name = "bfin-uart",
 	.id = 0,
 	.num_resources = ARRAY_SIZE(bfin_uart0_resources),
 	.resource = bfin_uart0_resources,
+	.dev = {
+		.platform_data = &bfin_uart0_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #ifdef CONFIG_SERIAL_BFIN_UART1
@@ -331,11 +338,22 @@
 #endif
 };
 
+unsigned short bfin_uart1_peripherals[] = {
+	P_UART1_TX, P_UART1_RX,
+#ifdef CONFIG_SERIAL_BFIN_HARD_CTSRTS
+	P_UART1_RTS, P_UART1_CTS,
+#endif
+	0
+};
+
 static struct platform_device bfin_uart1_device = {
 	.name = "bfin-uart",
 	.id = 1,
 	.num_resources = ARRAY_SIZE(bfin_uart1_resources),
 	.resource = bfin_uart1_resources,
+	.dev = {
+		.platform_data = &bfin_uart1_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #ifdef CONFIG_SERIAL_BFIN_UART2
@@ -385,11 +403,18 @@
 #endif
 };
 
+unsigned short bfin_uart2_peripherals[] = {
+	P_UART2_TX, P_UART2_RX, 0
+};
+
 static struct platform_device bfin_uart2_device = {
 	.name = "bfin-uart",
 	.id = 2,
 	.num_resources = ARRAY_SIZE(bfin_uart2_resources),
 	.resource = bfin_uart2_resources,
+	.dev = {
+		.platform_data = &bfin_uart2_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #ifdef CONFIG_SERIAL_BFIN_UART3
@@ -439,11 +464,22 @@
 #endif
 };
 
+unsigned short bfin_uart3_peripherals[] = {
+	P_UART3_TX, P_UART3_RX,
+#ifdef CONFIG_SERIAL_BFIN_HARD_CTSRTS
+	P_UART3_RTS, P_UART3_CTS,
+#endif
+	0
+};
+
 static struct platform_device bfin_uart3_device = {
 	.name = "bfin-uart",
 	.id = 3,
 	.num_resources = ARRAY_SIZE(bfin_uart3_resources),
 	.resource = bfin_uart3_resources,
+	.dev = {
+		.platform_data = &bfin_uart3_peripherals, /* Passed to driver */
+	},
 };
 #endif
 #endif
@@ -1375,7 +1411,7 @@
 arch_initcall(ezkit_init);
 
 static struct platform_device *ezkit_early_devices[] __initdata = {
-#if defined(CONFIG_SERIAL_BFIN_CONSOLE)
+#if defined(CONFIG_SERIAL_BFIN_CONSOLE) || defined(CONFIG_EARLY_PRINTK)
 #ifdef CONFIG_SERIAL_BFIN_UART0
 	&bfin_uart0_device,
 #endif

Modified: trunk/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -69,27 +69,3 @@
 	int			rts_pin;
 #endif
 };
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	0xFFC02000,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-	0xFFC02100,
-#else
-	0,
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART3
-	0xFFC03100,
-#else
-	0,
-#endif
-};
-

Modified: trunk/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h (7475 => 7476)


--- trunk/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h	2009-09-28 02:09:06 UTC (rev 7476)
@@ -82,12 +82,3 @@
 	uart->lsr = 0;
 	bfin_write16(uart->port.membase + OFFSET_LSR, -1);
 }
-
-unsigned long bfin_serial_console_base_addr[] = {
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	0xFFC00400,
-#else
-	0,
-#endif
-};
-

Modified: trunk/drivers/serial/Kconfig (7475 => 7476)


--- trunk/drivers/serial/Kconfig	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/drivers/serial/Kconfig	2009-09-28 02:09:06 UTC (rev 7476)
@@ -729,8 +729,7 @@
 	bool "Enable UART0 hardware flow control"
 	depends on SERIAL_BFIN_UART0
 	help
-	  Enable hardware flow control in the driver. Using GPIO emulate the CTS/RTS
-	  signal.
+	  Enable hardware flow control in the driver.
 
 config SERIAL_BFIN_UART1
 	bool "Enable UART1"
@@ -742,8 +741,7 @@
 	bool "Enable UART1 hardware flow control"
 	depends on SERIAL_BFIN_UART1
 	help
-	  Enable hardware flow control in the driver. Using GPIO emulate the CTS/RTS
-	  signal.
+	  Enable hardware flow control in the driver.
 
 config SERIAL_BFIN_UART2
 	bool "Enable UART2"
@@ -755,8 +753,7 @@
 	bool "Enable UART2 hardware flow control"
 	depends on SERIAL_BFIN_UART2
 	help
-	  Enable hardware flow control in the driver. Using GPIO emulate the CTS/RTS
-	  signal.
+	  Enable hardware flow control in the driver.
 
 config SERIAL_BFIN_UART3
 	bool "Enable UART3"
@@ -768,8 +765,7 @@
 	bool "Enable UART3 hardware flow control"
 	depends on SERIAL_BFIN_UART3
 	help
-	  Enable hardware flow control in the driver. Using GPIO emulate the CTS/RTS
-	  signal.
+	  Enable hardware flow control in the driver.
 
 config SERIAL_IMX
 	bool "IMX serial port support"

Modified: trunk/drivers/serial/bfin_5xx.c (7475 => 7476)


--- trunk/drivers/serial/bfin_5xx.c	2009-09-27 09:45:12 UTC (rev 7475)
+++ trunk/drivers/serial/bfin_5xx.c	2009-09-28 02:09:06 UTC (rev 7476)
@@ -12,6 +12,8 @@
 #define SUPPORT_SYSRQ
 #endif
 
+#define pr_fmt(fmt) DRIVER_NAME ": " fmt
+
 #include <linux/module.h>
 #include <linux/ioport.h>
 #include <linux/io.h>
@@ -44,13 +46,12 @@
 #endif
 
 /* UART name and device definitions */
-#define BFIN_SERIAL_NAME	"ttyBF"
+#define BFIN_SERIAL_DEV_NAME	"ttyBF"
 #define BFIN_SERIAL_MAJOR	204
 #define BFIN_SERIAL_MINOR	64
 #define DRIVER_NAME		"bfin-uart"
 
-static struct bfin_serial_port bfin_serial_ports[BFIN_UART_NR_PORTS];
-static int nr_ports = ARRAY_SIZE(bfin_serial_console_base_addr);
+static struct bfin_serial_port *bfin_serial_ports[BFIN_UART_NR_PORTS];
 
 #if defined(CONFIG_KGDB_SERIAL_CONSOLE) || \
 	defined(CONFIG_KGDB_SERIAL_CONSOLE_MODULE)
@@ -735,19 +736,10 @@
 		}
 	}
 	if (uart->rts_pin >= 0) {
-		gpio_request(uart->rts_pin, DRIVER_NAME);
 		gpio_direction_output(uart->rts_pin, 0);
 	}
 #endif
 #ifdef CONFIG_SERIAL_BFIN_HARD_CTSRTS
-# if defined(CONFIG_BFIN_UART1_CTSRTS)
-	peripheral_request(P_UART1_RTS, DRIVER_NAME);
-	peripheral_request(P_UART1_CTS, DRIVER_NAME);
-# endif
-# if defined(CONFIG_BFIN_UART3_CTSRTS)
-	peripheral_request(P_UART3_RTS, DRIVER_NAME);
-	peripheral_request(P_UART3_CTS, DRIVER_NAME);
-# endif
 	if (request_irq(uart->status_irq,
 		bfin_serial_mctrl_cts_int,
 		IRQF_DISABLED, "BFIN_UART_MODEM_STATUS", uart)) {
@@ -797,20 +789,10 @@
 #ifdef CONFIG_SERIAL_BFIN_CTSRTS
 	if (uart->cts_pin >= 0)
 		free_irq(gpio_to_irq(uart->cts_pin), uart);
-	if (uart->rts_pin >= 0)
-		gpio_free(uart->rts_pin);
 #endif
 #ifdef CONFIG_SERIAL_BFIN_HARD_CTSRTS
 	if (UART_GET_IER(uart) && EDSSI)
 		free_irq(uart->status_irq, uart);
-# if defined(CONFIG_BFIN_UART1_CTSRTS)
-	peripheral_free(P_UART1_RTS);
-	peripheral_free(P_UART1_CTS);
-# endif
-# if defined(CONFIG_BFIN_UART3_CTSRTS)
-	peripheral_free(P_UART3_RTS);
-	peripheral_free(P_UART3_CTS);
-# endif
 #endif
 }
 
@@ -971,6 +953,7 @@
  */
 static void bfin_serial_set_ldisc(struct uart_port *port)
 {
+	struct bfin_serial_port *uart = (struct bfin_serial_port *)port;
 	int line = port->line;
 	unsigned short val;
 
@@ -979,28 +962,28 @@
 
 	switch (port->info->port.tty->termios->c_line) {
 	case N_IRDA:
-		val = UART_GET_GCTL(&bfin_serial_ports[line]);
+		val = UART_GET_GCTL(uart);
 		val |= (IREN | RPOLC);
-		UART_PUT_GCTL(&bfin_serial_ports[line], val);
+		UART_PUT_GCTL(uart, val);
 		break;
 	default:
-		val = UART_GET_GCTL(&bfin_serial_ports[line]);
+		val = UART_GET_GCTL(uart);
 		val &= ~(IREN | RPOLC);
-		UART_PUT_GCTL(&bfin_serial_ports[line], val);
+		UART_PUT_GCTL(uart, val);
 	}
 }
 
 static void bfin_serial_reset_irda(struct uart_port *port)
 {
-	int line = port->line;
+	struct bfin_serial_port *uart = (struct bfin_serial_port *)port;
 	unsigned short val;
 
-	val = UART_GET_GCTL(&bfin_serial_ports[line]);
+	val = UART_GET_GCTL(uart);
 	val &= ~(IREN | RPOLC);
-	UART_PUT_GCTL(&bfin_serial_ports[line], val);
+	UART_PUT_GCTL(uart, val);
 	SSYNC();
 	val |= (IREN | RPOLC);
-	UART_PUT_GCTL(&bfin_serial_ports[line], val);
+	UART_PUT_GCTL(uart, val);
 	SSYNC();
 }
 
@@ -1082,91 +1065,6 @@
 #endif
 };
 
-#ifdef CONFIG_SERIAL_BFIN_UART0
-unsigned short bfin_uart0_pin_req[] = {P_UART0_TX, P_UART0_RX, 0};
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-unsigned short bfin_uart1_pin_req[] = {P_UART1_TX, P_UART1_RX, 0};
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-unsigned short bfin_uart2_pin_req[] = {P_UART2_TX, P_UART2_RX, 0};
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART3
-unsigned short bfin_uart3_pin_req[] = {P_UART3_TX, P_UART3_RX, 0};
-#endif
-
-static int __init bfin_serial_init_ports(void)
-{
-	static int first = 1;
-	int i;
-	int ret;
-
-	if (!first)
-		return 0;
-
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	ret = peripheral_request_list(bfin_uart0_pin_req, DRIVER_NAME);
-	if (ret) {
-		pr_err("requesting UART0 peripherals failed\n");
-		goto err_out0;
-	}
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	ret = peripheral_request_list(bfin_uart1_pin_req, DRIVER_NAME);
-	if (ret) {
-		pr_err("requesting UART1 peripherals failed\n");
-		goto err_out1;
-	}
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-	ret = peripheral_request_list(bfin_uart2_pin_req, DRIVER_NAME);
-	if (ret) {
-		pr_err("requesting UART2 peripherals failed\n");
-		goto err_out2;
-	}
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART3
-	ret = peripheral_request_list(bfin_uart3_pin_req, DRIVER_NAME);
-	if (ret) {
-		pr_err("requesting UART3 peripherals failed\n");
-		goto err_out3;
-	}
-#endif
-
-	for (i = 0; i < nr_ports; i++) {
-		spin_lock_init(&bfin_serial_ports[i].port.lock);
-		bfin_serial_ports[i].port.uartclk   = get_sclk();
-		bfin_serial_ports[i].port.fifosize  = BFIN_UART_TX_FIFO_SIZE;
-		bfin_serial_ports[i].port.ops       = &bfin_serial_pops;
-		bfin_serial_ports[i].port.line      = i;
-		bfin_serial_ports[i].port.iotype    = UPIO_MEM;
-		bfin_serial_ports[i].port.flags     = UPF_BOOT_AUTOCONF;
-		bfin_serial_ports[i].port.membase   =
-			(void __iomem *)bfin_serial_console_base_addr[i];
-	}
-
-	first = 0;
-
-	return 0;
-#ifdef CONFIG_SERIAL_BFIN_UART3
-err_out3:
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-	peripheral_free_list(bfin_uart2_pin_req);
-err_out2:
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-err_out1:
-	peripheral_free_list(bfin_uart1_pin_req);
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART0
-err_out0:
-	peripheral_free_list(bfin_uart0_pin_req);
-#endif
-
-	return ret;
-}
-
 #if defined(CONFIG_SERIAL_BFIN_CONSOLE) || defined(CONFIG_EARLY_PRINTK)
 /*
  * If the port was already initialised (eg, by a boot loader),
@@ -1214,6 +1112,35 @@
 
 static struct uart_driver bfin_serial_reg;
 
+static void bfin_serial_console_putchar(struct uart_port *port, int ch)
+{
+	struct bfin_serial_port *uart = (struct bfin_serial_port *)port;
+	while (!(UART_GET_LSR(uart) & THRE))
+		barrier();
+	UART_PUT_CHAR(uart, ch);
+	SSYNC();
+}
+
+#endif /* defined (CONFIG_SERIAL_BFIN_CONSOLE) ||
+		 defined (CONFIG_EARLY_PRINTK) */
+
+#ifdef CONFIG_SERIAL_BFIN_CONSOLE
+#define CLASS_BFIN_CONSOLE	"bfin-console"
+/*
+ * Interrupts are disabled on entering
+ */
+static void
+bfin_serial_console_write(struct console *co, const char *s, unsigned int count)
+{
+	struct bfin_serial_port *uart = bfin_serial_ports[co->index];
+	unsigned long flags;
+
+	spin_lock_irqsave(&uart->port.lock, flags);
+	uart_console_write(&uart->port, s, count, bfin_serial_console_putchar);
+	spin_unlock_irqrestore(&uart->port.lock, flags);
+
+}
+
 static int __init
 bfin_serial_console_setup(struct console *co, char *options)
 {
@@ -1233,10 +1160,13 @@
 	 * if so, search for the first available port that does have
 	 * console support.
 	 */
-	if (co->index == -1 || co->index >= nr_ports)
+	if (co->index < 0 || co->index >= BFIN_UART_NR_PORTS)
 		return -ENODEV;
-	uart = &bfin_serial_ports[co->index];
 
+	uart = bfin_serial_ports[co->index];
+	if (!uart)
+		return -ENODEV;
+
 	if (options)
 		uart_parse_options(options, &baud, &parity, &bits, &flow);
 	else
@@ -1245,35 +1175,8 @@
 	return uart_set_options(&uart->port, co, baud, parity, bits, flow);
 }
 
-static void bfin_serial_console_putchar(struct uart_port *port, int ch)
-{
-	struct bfin_serial_port *uart = (struct bfin_serial_port *)port;
-	while (!(UART_GET_LSR(uart) & THRE))
-		barrier();
-	UART_PUT_CHAR(uart, ch);
-	SSYNC();
-}
-
-/*
- * Interrupts are disabled on entering
- */
-static void
-bfin_serial_console_write(struct console *co, const char *s, unsigned int count)
-{
-	struct bfin_serial_port *uart = &bfin_serial_ports[co->index];
-	unsigned long flags;
-
-	spin_lock_irqsave(&uart->port.lock, flags);
-	uart_console_write(&uart->port, s, count, bfin_serial_console_putchar);
-	spin_unlock_irqrestore(&uart->port.lock, flags);
-
-}
-#endif /* defined (CONFIG_SERIAL_BFIN_CONSOLE) ||
-				 defined (CONFIG_EARLY_PRINTK) */
-
-#ifdef CONFIG_SERIAL_BFIN_CONSOLE
 static struct console bfin_serial_console = {
-	.name		= BFIN_SERIAL_NAME,
+	.name		= BFIN_SERIAL_DEV_NAME,
 	.write		= bfin_serial_console_write,
 	.device		= uart_console_device,
 	.setup		= bfin_serial_console_setup,
@@ -1281,28 +1184,29 @@
 	.index		= -1,
 	.data		= ""
 };
-
-static int __init bfin_serial_rs_console_init(void)
-{
-	int ret;
-
-	ret = bfin_serial_init_ports();
-	if (ret)
-		return ret;
-	register_console(&bfin_serial_console);
-
-	return 0;
-}
-console_initcall(bfin_serial_rs_console_init);
-
 #define BFIN_SERIAL_CONSOLE	&bfin_serial_console
 #else
 #define BFIN_SERIAL_CONSOLE	NULL
 #endif /* CONFIG_SERIAL_BFIN_CONSOLE */
 
+#ifdef	CONFIG_EARLY_PRINTK
+static struct bfin_serial_port bfin_earlyprintk_port;
+#define CLASS_BFIN_EARLYPRINTK	"bfin-earlyprintk"
 
-#ifdef CONFIG_EARLY_PRINTK
 /*
+ * Interrupts are disabled on entering
+ */
+static void
+bfin_earlyprintk_console_write(struct console *co, const char *s, unsigned int count)
+{
+	if (bfin_earlyprintk_port.port.line != co->index)
+		return;
+
+	uart_console_write(&bfin_earlyprintk_port.port, s, count,
+		bfin_serial_console_putchar);
+}
+
+/*
  * This should have a .setup or .early_setup in it, but then things get called
  * without the command line options, and the baud rate gets messed up - so
  * don't let the common infrastructure play with things. (see calls to setup
@@ -1310,48 +1214,18 @@
  */
 static struct __initdata console bfin_early_serial_console = {
 	.name = "early_BFuart",
-	.write = bfin_serial_console_write,
+	.write = bfin_earlyprintk_console_write,
 	.device = uart_console_device,
 	.flags = CON_PRINTBUFFER,
 	.index = -1,
 	.data  = ""
 };
-
-struct console __init *bfin_earlyserial_init(unsigned int port,
-						unsigned int cflag)
-{
-	struct bfin_serial_port *uart;
-	struct ktermios t;
-
-#ifdef CONFIG_SERIAL_BFIN_CONSOLE
-	/*
-	 * If we are using early serial, don't let the normal console rewind
-	 * log buffer, since that causes things to be printed multiple times
-	 */
-	bfin_serial_console.flags &= ~CON_PRINTBUFFER;
 #endif
 
-	if (port == -1 || port >= nr_ports)
-		return NULL;
-	if (bfin_serial_init_ports())
-		return NULL;
-
-	bfin_early_serial_console.index = port;
-	uart = &bfin_serial_ports[port];
-	t.c_cflag = cflag;
-	t.c_iflag = 0;
-	t.c_oflag = 0;
-	t.c_lflag = ICANON;
-	t.c_line = port;
-	bfin_serial_set_termios(&uart->port, &t, &t);
-	return &bfin_early_serial_console;
-}
-#endif /* CONFIG_EARLY_PRINTK */
-
 static struct uart_driver bfin_serial_reg = {
 	.owner			= THIS_MODULE,
 	.driver_name		= DRIVER_NAME,
-	.dev_name		= BFIN_SERIAL_NAME,
+	.dev_name		= BFIN_SERIAL_DEV_NAME,
 	.major			= BFIN_SERIAL_MAJOR,
 	.minor			= BFIN_SERIAL_MINOR,
 	.nr			= BFIN_UART_NR_PORTS,
@@ -1360,12 +1234,16 @@
 
 static int bfin_serial_suspend(struct platform_device *pdev, pm_message_t state)
 {
-	return uart_suspend_port(&bfin_serial_reg, &bfin_serial_ports[pdev->id].port);
+	struct bfin_serial_port *uart = platform_get_drvdata(pdev);
+
+	return uart_suspend_port(&bfin_serial_reg, &uart->port);
 }
 
 static int bfin_serial_resume(struct platform_device *pdev)
 {
-	return uart_resume_port(&bfin_serial_reg, &bfin_serial_ports[pdev->id].port);
+	struct bfin_serial_port *uart = platform_get_drvdata(pdev);
+
+	return uart_resume_port(&bfin_serial_reg, &uart->port);
 }
 
 static int bfin_serial_probe(struct platform_device *pdev)
@@ -1373,118 +1251,184 @@
 	struct resource *res;
 	struct bfin_serial_port *uart;
 	int ret;
-	int index;
 
-	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-	if (res == NULL) {
-		dev_err(&pdev->dev, "Cannot get IORESOURCE_MEM\n");
+	if (pdev->id < 0 || pdev->id >= BFIN_UART_NR_PORTS) {
+		dev_err(&pdev->dev, "Wrong bfin uart platform device id.\n");
 		return -ENOENT;
 	}
 
-	for (index = 0; index < nr_ports; index++)
-		if (res->start == bfin_serial_console_base_addr[index])
-			break;
+	if (bfin_serial_ports[pdev->id] == NULL) {
+		bfin_serial_ports[pdev->id] =
+			kmalloc(sizeof(struct bfin_serial_port), GFP_KERNEL);
 
-	if (index == nr_ports) {
-		dev_err(&pdev->dev, "Wrong uart platform device\n");
-		return -ENOENT;
-	}
+		uart = bfin_serial_ports[pdev->id];
+		if (!uart) {
+			dev_err(&pdev->dev,
+				"fail to kmalloc bfin_serial_port\n");
+			return -ENOMEM;
+		}
 
-	uart = &bfin_serial_ports[index];
+#ifdef CONFIG_EARLY_PRINTK
+		if (!(bfin_earlyprintk_port.port.membase
+			&& bfin_earlyprintk_port.port.line == pdev->id)) {
+			/*
+			 * If the peripheral PINs of current port is allocated
+			 * in earlyprintk probe stage, don't do it again.
+			 */
+#endif
+		ret = peripheral_request_list(
+			(unsigned short *)pdev->dev.platform_data, DRIVER_NAME);
+		if (ret) {
+			dev_err(&pdev->dev,
+				"fail to request bfin serial peripherals\n");
+			goto out_error_free_mem;
+		}
+#ifdef CONFIG_EARLY_PRINTK
+		}
+#endif
 
-	uart->port.membase = ioremap(res->start,
-		res->end - res->start + 1);
-	if (!uart->port.membase) {
-		dev_err(&pdev->dev, "Cannot map uart IO\n");
-		return -ENXIO;
-	}
+		spin_lock_init(&uart->port.lock);
+		uart->port.uartclk   = get_sclk();
+		uart->port.fifosize  = BFIN_UART_TX_FIFO_SIZE;
+		uart->port.ops       = &bfin_serial_pops;
+		uart->port.line      = pdev->id;
+		uart->port.iotype    = UPIO_MEM;
+		uart->port.flags     = UPF_BOOT_AUTOCONF;
 
-	uart->port.irq = platform_get_irq(pdev, 0);
-	if (uart->port.irq < 0) {
-		dev_err(&pdev->dev, "No uart RX/TX IRQ specified\n");
-		ret = -ENOENT;
-		goto out_error;
-	}
+		res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+		if (res == NULL) {
+			dev_err(&pdev->dev, "Cannot get IORESOURCE_MEM\n");
+			ret = -ENOENT;
+			goto out_error_free_peripherals;
+		}
 
-	uart->status_irq = platform_get_irq(pdev, 1);
-	if (uart->status_irq < 0) {
-		dev_err(&pdev->dev, "No uart status IRQ specified\n");
-		ret = -ENOENT;
-		goto out_error;
-	}
+		uart->port.membase = ioremap(res->start,
+			res->end - res->start + 1);
+		if (!uart->port.membase) {
+			dev_err(&pdev->dev, "Cannot map uart IO\n");
+			ret = -ENXIO;
+			goto out_error_free_peripherals;
+		}
+		uart->port.mapbase = res->start;
 
+		uart->port.irq = platform_get_irq(pdev, 0);
+		if (uart->port.irq < 0) {
+			dev_err(&pdev->dev, "No uart RX/TX IRQ specified\n");
+			ret = -ENOENT;
+			goto out_error_unmap;
+		}
+
+		uart->status_irq = platform_get_irq(pdev, 1);
+		if (uart->status_irq < 0) {
+			dev_err(&pdev->dev, "No uart status IRQ specified\n");
+			ret = -ENOENT;
+			goto out_error_unmap;
+		}
+
 #ifdef CONFIG_SERIAL_BFIN_DMA
-	uart->tx_done	    = 1;
-	uart->tx_count	    = 0;
+		uart->tx_done	    = 1;
+		uart->tx_count	    = 0;
 
-	res = platform_get_resource(pdev, IORESOURCE_DMA, 0);
-	if (res == NULL) {
-		dev_err(&pdev->dev, "No uart TX DMA channel specified\n");
-		ret = -ENOENT;
-		goto out_error;
-	}
-	uart->tx_dma_channel = res->start;
+		res = platform_get_resource(pdev, IORESOURCE_DMA, 0);
+		if (res == NULL) {
+			dev_err(&pdev->dev, "No uart TX DMA channel specified\n");
+			ret = -ENOENT;
+			goto out_error_unmap;
+		}
+		uart->tx_dma_channel = res->start;
 
-	res = platform_get_resource(pdev, IORESOURCE_DMA, 1);
-	if (res == NULL) {
-		dev_err(&pdev->dev, "No uart RX DMA channel specified\n");
-		ret = -ENOENT;
-		goto out_error;
-	}
-	uart->rx_dma_channel = res->start;
+		res = platform_get_resource(pdev, IORESOURCE_DMA, 1);
+		if (res == NULL) {
+			dev_err(&pdev->dev, "No uart RX DMA channel specified\n");
+			ret = -ENOENT;
+			goto out_error_unmap;
+		}
+		uart->rx_dma_channel = res->start;
 
-	init_timer(&(uart->rx_dma_timer));
+		init_timer(&(uart->rx_dma_timer));
 #endif
 
 #if defined(CONFIG_SERIAL_BFIN_CTSRTS) || \
 	defined(CONFIG_SERIAL_BFIN_HARD_CTSRTS)
-	res = platform_get_resource(pdev, IORESOURCE_IO, 0);
-	if (res == NULL) {
+		res = platform_get_resource(pdev, IORESOURCE_IO, 0);
+		if (res == NULL) {
 # if defined(CONFIG_SERIAL_BFIN_HARD_CTSRTS)
-		uart->cts_pin = 0;
+			uart->cts_pin = 0;
 # else
-		uart->cts_pin = -1;
+			uart->cts_pin = -1;
 # endif
-	} else
-		uart->cts_pin = res->start;
+		} else
+			uart->cts_pin = res->start;
 
-	res = platform_get_resource(pdev, IORESOURCE_IO, 1);
-	if (res == NULL) {
+		res = platform_get_resource(pdev, IORESOURCE_IO, 1);
+		if (res == NULL) {
 # if defined(CONFIG_SERIAL_BFIN_HARD_CTSRTS)
-		uart->rts_pin = 0;
+			uart->rts_pin = 0;
 # else
-		uart->rts_pin = -1;
+			uart->rts_pin = -1;
 # endif
-	} else
-		uart->rts_pin = res->start;
+		} else
+			uart->rts_pin = res->start;
+# if defined(CONFIG_SERIAL_BFIN_CTSRTS)
+		if (uart->rts_pin >= 0) {
+			gpio_request(uart->rts_pin, DRIVER_NAME);
+# endif
 #endif
+	}
 
-	uart->port.dev = &pdev->dev;
-	ret = uart_add_one_port(&bfin_serial_reg, &uart->port);
+#ifdef CONFIG_SERIAL_BFIN_CONSOLE
+	if (!is_early_platform_device(pdev)) {
+#endif
+		uart = bfin_serial_ports[pdev->id];
+		uart->port.dev = &pdev->dev;
+		dev_set_drvdata(&pdev->dev, uart);
+		ret = uart_add_one_port(&bfin_serial_reg, &uart->port);
+#ifdef CONFIG_SERIAL_BFIN_CONSOLE
+	}
+#endif
+
 	if (!ret)
 		return 0;
 
-out_error:
-	iounmap(uart->port.membase);
+	if (uart) {
+out_error_unmap:
+		iounmap(uart->port.membase);
+out_error_free_peripherals:
+		peripheral_free_list(
+			(unsigned short *)pdev->dev.platform_data);
+out_error_free_mem:
+		kfree(uart);
+		bfin_serial_ports[pdev->id] = NULL;
+	}
 
 	return ret;
 }
 
-static int bfin_serial_remove(struct platform_device *pdev)
+static int __devexit bfin_serial_remove(struct platform_device *pdev)
 {
-	struct bfin_serial_port *uart;
+	struct bfin_serial_port *uart = platform_get_drvdata(pdev);
 
-	uart = &bfin_serial_ports[pdev->id];
-	uart_remove_one_port(&bfin_serial_reg, &uart->port);
-	uart->port.dev = NULL;
-	iounmap(uart->port.membase);
+	dev_set_drvdata(&pdev->dev, NULL);
 
+	if (uart) {
+		uart_remove_one_port(&bfin_serial_reg, &uart->port);
+#ifdef CONFIG_SERIAL_BFIN_CTSRTS
+		if (uart->rts_pin >= 0)
+			gpio_free(uart->rts_pin);
+#endif
+		iounmap(uart->port.membase);
+		peripheral_free_list(
+			(unsigned short *)pdev->dev.platform_data);
+		kfree(uart);
+		bfin_serial_ports[pdev->id] = NULL;
+	}
+
 	return 0;
 }
 
 static struct platform_driver bfin_serial_driver = {
 	.probe		= bfin_serial_probe,
-	.remove		= bfin_serial_remove,
+	.remove		= __devexit_p(bfin_serial_remove),
 	.suspend	= bfin_serial_suspend,
 	.resume		= bfin_serial_resume,
 	.driver		= {
@@ -1493,24 +1437,149 @@
 	},
 };
 
+#if defined(CONFIG_SERIAL_BFIN_CONSOLE)
+static __initdata struct early_platform_driver early_bfin_serial_driver = {
+	.class_str = CLASS_BFIN_CONSOLE,
+	.pdrv = &bfin_serial_driver,
+	.requested_id = EARLY_PLATFORM_ID_UNSET,
+};
+
+static int __init bfin_serial_rs_console_init(void)
+{
+	early_platform_driver_register(&early_bfin_serial_driver, DRIVER_NAME);
+
+	early_platform_driver_probe(CLASS_BFIN_CONSOLE, BFIN_UART_NR_PORTS, 0);
+
+	register_console(&bfin_serial_console);
+
+	return 0;
+}
+console_initcall(bfin_serial_rs_console_init);
+#endif
+
+#ifdef CONFIG_EARLY_PRINTK
+/*
+ * Memory can't be allocated dynamically during earlyprink init stage.
+ * So, do individual probe for earlyprink with a static uart port variable.
+ */
+static int bfin_earlyprintk_probe(struct platform_device *pdev)
+{
+	struct resource *res;
+	int ret;
+
+	if (pdev->id < 0 || pdev->id >= BFIN_UART_NR_PORTS) {
+		dev_err(&pdev->dev, "Wrong earlyprintk platform device id.\n");
+		return -ENOENT;
+	}
+
+	ret = peripheral_request_list(
+		(unsigned short *)pdev->dev.platform_data, DRIVER_NAME);
+	if (ret) {
+		dev_err(&pdev->dev,
+				"fail to request bfin serial peripherals\n");
+			return ret;
+	}
+
+	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	if (res == NULL) {
+		dev_err(&pdev->dev, "Cannot get IORESOURCE_MEM\n");
+		ret = -ENOENT;
+		goto out_error_free_peripherals;
+	}
+
+	bfin_earlyprintk_port.port.membase = ioremap(res->start,
+			res->end - res->start + 1);
+	if (!bfin_earlyprintk_port.port.membase) {
+		dev_err(&pdev->dev, "Cannot map uart IO\n");
+		ret = -ENXIO;
+		goto out_error_free_peripherals;
+	}
+	bfin_earlyprintk_port.port.mapbase = res->start;
+	bfin_earlyprintk_port.port.line = pdev->id;
+	bfin_earlyprintk_port.port.uartclk = get_sclk();
+	bfin_earlyprintk_port.port.fifosize  = BFIN_UART_TX_FIFO_SIZE;
+	spin_lock_init(&bfin_earlyprintk_port.port.lock);
+
+	return 0;
+
+out_error_free_peripherals:
+	peripheral_free_list(
+		(unsigned short *)pdev->dev.platform_data);
+
+	return ret;
+}
+
+static struct platform_driver bfin_earlyprintk_driver = {
+	.probe		= bfin_earlyprintk_probe,
+	.driver		= {
+		.name	= DRIVER_NAME,
+		.owner	= THIS_MODULE,
+	},
+};
+
+static __initdata struct early_platform_driver early_bfin_earlyprintk_driver = {
+	.class_str = CLASS_BFIN_EARLYPRINTK,
+	.pdrv = &bfin_earlyprintk_driver,
+	.requested_id = EARLY_PLATFORM_ID_UNSET,
+};
+
+struct console __init *bfin_earlyserial_init(unsigned int port,
+						unsigned int cflag)
+{
+	struct ktermios t;
+
+	if (port < 0 || port >= BFIN_UART_NR_PORTS)
+		return NULL;
+
+	early_bfin_earlyprintk_driver.requested_id = port;
+
+	early_platform_driver_register(&early_bfin_earlyprintk_driver,
+		DRIVER_NAME);
+
+	early_platform_driver_probe(CLASS_BFIN_EARLYPRINTK,
+		BFIN_UART_NR_PORTS, 0);
+
+	if (!bfin_earlyprintk_port.port.membase)
+		return NULL;
+
+#ifdef CONFIG_SERIAL_BFIN_CONSOLE
+	/*
+	 * If we are using early serial, don't let the normal console rewind
+	 * log buffer, since that causes things to be printed multiple times
+	 */
+	bfin_serial_console.flags &= ~CON_PRINTBUFFER;
+#endif
+
+	bfin_early_serial_console.index = port;
+	t.c_cflag = cflag;
+	t.c_iflag = 0;
+	t.c_oflag = 0;
+	t.c_lflag = ICANON;
+	t.c_line = port;
+	bfin_serial_set_termios(&bfin_earlyprintk_port.port, &t, &t);
+
+	return &bfin_early_serial_console;
+}
+#endif /* CONFIG_EARLY_PRINTK */
+
 static int __init bfin_serial_init(void)
 {
 	int ret;
 
-	pr_info("Serial: Blackfin serial driver\n");
+	pr_info("Blackfin serial driver\n");
 
-	ret = bfin_serial_init_ports();
-	if (ret)
-		return ret;
-
 	ret = uart_register_driver(&bfin_serial_reg);
-	if (ret == 0) {
-		ret = platform_driver_register(&bfin_serial_driver);
-		if (ret) {
-			pr_debug("uart register failed\n");
-			uart_unregister_driver(&bfin_serial_reg);
-		}
+	if (ret) {
+		pr_err("failed to register %s:%d\n",
+			bfin_serial_reg.driver_name, ret);
 	}
+
+	ret = platform_driver_register(&bfin_serial_driver);
+	if (ret) {
+		pr_err("fail to register bfin uart\n");
+		uart_unregister_driver(&bfin_serial_reg);
+	}
+
 	return ret;
 }
 
@@ -1518,20 +1587,6 @@
 {
 	platform_driver_unregister(&bfin_serial_driver);
 	uart_unregister_driver(&bfin_serial_reg);
-
-#ifdef CONFIG_SERIAL_BFIN_UART0
-	peripheral_free_list(bfin_uart0_pin_req);
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART1
-	peripheral_free_list(bfin_uart1_pin_req);
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART2
-	peripheral_free_list(bfin_uart2_pin_req);
-#endif
-#ifdef CONFIG_SERIAL_BFIN_UART3
-	peripheral_free_list(bfin_uart3_pin_req);
-#endif
-
 }
 
 
_______________________________________________
Linux-kernel-commits mailing list
[email protected]
https://blackfin.uclinux.org/mailman/listinfo/linux-kernel-commits

Reply via email to