From 95caa0a9bdaf93607bd0cc8932f53112496f2f22 Mon Sep 17 00:00:00 2001 From: Breno Leitao Date: Fri, 22 May 2009 21:30:39 -0300 Subject: icom: fix rmmod crash Actually the icom driver is crashing when is being removed because the driver is kfreeing the adapter structure before calling pci_release_regions(), which result in the following error: Unable to handle kernel paging request for data at address 0x6b6b6b6b6b6b6d33 Faulting instruction address: 0xc000000000246b80 Oops: Kernel access of bad area, sig: 11 [#1] .... [c000000012d436a0] [c0000000001002d0] .kfree+0x120/0x34c (unreliable) [c000000012d43730] [c000000000246d60] .pci_release_selected_regions+0x3c/0x68 [c000000012d437c0] [d000000002d54700] .icom_kref_release+0xf4/0x118 [icom] [c000000012d43850] [c000000000232e50] .kref_put+0x74/0x94 [c000000012d438d0] [d000000002d56c58] .icom_remove+0x40/0xa4 [icom] [c000000012d43960] [c000000000249e48] .pci_device_remove+0x50/0x90 [c000000012d439e0] [c0000000002d68d8] .__device_release_driver+0x94/0xd4 [c000000012d43a70] [c0000000002d7104] .driver_detach+0xf8/0x12c [c000000012d43b00] [c0000000002d549c] .bus_remove_driver+0xbc/0x11c [c000000012d43b90] [c0000000002d71dc] .driver_unregister+0x60/0x80 [c000000012d43c20] [c00000000024a07c] .pci_unregister_driver+0x44/0xe8 [c000000012d43cb0] [d000000002d56bf4] .icom_exit+0x1c/0x40 [icom] [c000000012d43d30] [c000000000095fa8] .SyS_delete_module+0x214/0x2a8 [c000000012d43e30] [c00000000000852c] syscall_exit+0x0/0x40 Signed-off-by: Breno Leitao Cc: stable@kernel.org Cc: Alan Cox Signed-off-by: Linus Torvalds --- drivers/serial/icom.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/serial') diff --git a/drivers/serial/icom.c b/drivers/serial/icom.c index 6579e2be1dd..a461b3b2c72 100644 --- a/drivers/serial/icom.c +++ b/drivers/serial/icom.c @@ -1472,8 +1472,8 @@ static void icom_remove_adapter(struct icom_adapter *icom_adapter) free_irq(icom_adapter->pci_dev->irq, (void *) icom_adapter); iounmap(icom_adapter->base_addr); - icom_free_adapter(icom_adapter); pci_release_regions(icom_adapter->pci_dev); + icom_free_adapter(icom_adapter); } static void icom_kref_release(struct kref *kref) -- cgit v1.2.3-70-g09d2 From b898f4f869da5b9d41f297fff87aca4cd42d80b3 Mon Sep 17 00:00:00 2001 From: Roel Kluin Date: Thu, 28 May 2009 14:34:29 -0700 Subject: drivers/serial/mpc52xx_uart.c: fix array overindexing check The check for an overindexing of mpc52xx_uart_{ports,nodes} has an off-by-one. Signed-off-by: Roel Kluin Acked-by: Wolfram Sang Acked-by: Grant Likely Cc: Benjamin Herrenschmidt Cc: Alan Cox Cc: Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/serial/mpc52xx_uart.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/serial') diff --git a/drivers/serial/mpc52xx_uart.c b/drivers/serial/mpc52xx_uart.c index 7f72f8ceaa6..b3feb6198d5 100644 --- a/drivers/serial/mpc52xx_uart.c +++ b/drivers/serial/mpc52xx_uart.c @@ -988,7 +988,7 @@ mpc52xx_console_setup(struct console *co, char *options) pr_debug("mpc52xx_console_setup co=%p, co->index=%i, options=%s\n", co, co->index, options); - if ((co->index < 0) || (co->index > MPC52xx_PSC_MAXNUM)) { + if ((co->index < 0) || (co->index >= MPC52xx_PSC_MAXNUM)) { pr_debug("PSC%x out of range\n", co->index); return -EINVAL; } -- cgit v1.2.3-70-g09d2 From 8e8e8267f0a08c2415d5f51bc9a9fde6d5400619 Mon Sep 17 00:00:00 2001 From: Alexander Beregalov Date: Thu, 28 May 2009 14:34:34 -0700 Subject: serial: 8250_gsc: fix printk format error drivers/serial/8250_gsc.c:44: warning: format '%lx' expects type 'long unsigned int', but argument 2 has type 'resource_size_t' [akpm@linux-foundation.org: fix it to handle u64's] Signed-off-by: Alexander Beregalov Cc: Alan Cox Cc: Kyle McMartin Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/serial/8250_gsc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/serial') diff --git a/drivers/serial/8250_gsc.c b/drivers/serial/8250_gsc.c index 418b4fe9a0a..33149d982e8 100644 --- a/drivers/serial/8250_gsc.c +++ b/drivers/serial/8250_gsc.c @@ -39,9 +39,9 @@ static int __init serial_init_chip(struct parisc_device *dev) */ if (parisc_parent(dev)->id.hw_type != HPHW_IOA) printk(KERN_INFO - "Serial: device 0x%lx not configured.\n" + "Serial: device 0x%llx not configured.\n" "Enable support for Wax, Lasi, Asp or Dino.\n", - dev->hpa.start); + (unsigned long long)dev->hpa.start); return -ENODEV; } -- cgit v1.2.3-70-g09d2 From b8e7e40abeac49644fec4a4f52ffe74c7b05eca0 Mon Sep 17 00:00:00 2001 From: Alan Cox Date: Thu, 28 May 2009 14:01:35 +0100 Subject: 8250: Fix oops from setserial If you setserial a port which has never been initialised we change the type but don't update the I/O method pointers. The same problem is true if you change the io type of a port - but nobody ever does that so nobody noticed! Remember the old type and when attaching if the type has changed reload the port accessor pointers. We can't do it blindly as some 8250 drivers load custom accessors and we must not stomp those. Tested-by: Victor Seryodkin Closes-bug: #13367 Signed-off-by: Alan Cox Signed-off-by: Linus Torvalds --- drivers/serial/8250.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'drivers/serial') diff --git a/drivers/serial/8250.c b/drivers/serial/8250.c index b4b39811b44..a0127e93ade 100644 --- a/drivers/serial/8250.c +++ b/drivers/serial/8250.c @@ -137,6 +137,7 @@ struct uart_8250_port { unsigned char mcr; unsigned char mcr_mask; /* mask of user bits */ unsigned char mcr_force; /* mask of forced bits */ + unsigned char cur_iotype; /* Running I/O type */ /* * Some bits in registers are cleared on a read, so they must @@ -471,6 +472,7 @@ static void io_serial_out(struct uart_port *p, int offset, int value) static void set_io_from_upio(struct uart_port *p) { + struct uart_8250_port *up = (struct uart_8250_port *)p; switch (p->iotype) { case UPIO_HUB6: p->serial_in = hub6_serial_in; @@ -509,6 +511,8 @@ static void set_io_from_upio(struct uart_port *p) p->serial_out = io_serial_out; break; } + /* Remember loaded iotype */ + up->cur_iotype = p->iotype; } static void @@ -1937,6 +1941,9 @@ static int serial8250_startup(struct uart_port *port) up->capabilities = uart_config[up->port.type].flags; up->mcr = 0; + if (up->port.iotype != up->cur_iotype) + set_io_from_upio(port); + if (up->port.type == PORT_16C950) { /* Wake up and initialize UART */ up->acr = 0; @@ -2563,6 +2570,9 @@ static void serial8250_config_port(struct uart_port *port, int flags) if (ret < 0) probeflags &= ~PROBE_RSA; + if (up->port.iotype != up->cur_iotype) + set_io_from_upio(port); + if (flags & UART_CONFIG_TYPE) autoconfig(up, probeflags); if (up->port.type != PORT_UNKNOWN && flags & UART_CONFIG_IRQ) @@ -2671,6 +2681,11 @@ serial8250_register_ports(struct uart_driver *drv, struct device *dev) { int i; + for (i = 0; i < nr_uarts; i++) { + struct uart_8250_port *up = &serial8250_ports[i]; + up->cur_iotype = 0xFF; + } + serial8250_isa_init_ports(); for (i = 0; i < nr_uarts; i++) { -- cgit v1.2.3-70-g09d2 From e76afc4e7816a0a5300073098cdac93a994eb5ca Mon Sep 17 00:00:00 2001 From: Eric Lammerts Date: Tue, 19 May 2009 20:53:20 -0400 Subject: fix oops when using console=ttymxcN with N > 0 Signed-off-by: Eric Lammerts Signed-off-by: Sascha Hauer --- drivers/serial/imx.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'drivers/serial') diff --git a/drivers/serial/imx.c b/drivers/serial/imx.c index 9f460b175c5..5f0be40dfda 100644 --- a/drivers/serial/imx.c +++ b/drivers/serial/imx.c @@ -1031,6 +1031,8 @@ imx_console_setup(struct console *co, char *options) if (co->index == -1 || co->index >= ARRAY_SIZE(imx_ports)) co->index = 0; sport = imx_ports[co->index]; + if(sport == NULL) + return -ENODEV; if (options) uart_parse_options(options, &baud, &parity, &bits, &flow); -- cgit v1.2.3-70-g09d2