From: James S. <jsi...@us...> - 2002-03-14 20:02:15
|
Update of /cvsroot/linuxconsole/ruby/linux/drivers/serial In directory usw-pr-cvs1:/tmp/cvs-serv5099/linux/drivers/serial Modified Files: serial_21285.c serial_8250.c serial_8250.h serial_8250_pci.c serial_8250_pnp.c serial_amba.c serial_anakin.c serial_clps711x.c serial_core.c serial_sa1100.c serial_uart00.c Log Message: Synced to 2.5.4 Index: serial_21285.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_21285.c,v retrieving revision 1.9 retrieving revision 1.10 diff -u -d -r1.9 -r1.10 --- serial_21285.c 25 Dec 2001 06:50:51 -0000 1.9 +++ serial_21285.c 14 Mar 2002 20:02:07 -0000 1.10 @@ -67,15 +67,16 @@ * int((BAUD_BASE - (baud >> 1)) / baud) */ -static void serial21285_stop_tx(struct uart_port *port, u_int from_tty) +static void +serial21285_stop_tx(struct uart_port *port, unsigned int tty_stop) { disable_irq(IRQ_CONTX); } -static void serial21285_start_tx(struct uart_port *port, u_int nonempty, u_int from_tty) +static void +serial21285_start_tx(struct uart_port *port, unsigned int tty_start) { - if (nonempty) - enable_irq(IRQ_CONTX); + enable_irq(IRQ_CONTX); } static void serial21285_stop_rx(struct uart_port *port) @@ -89,9 +90,8 @@ static void serial21285_rx_chars(int irq, void *dev_id, struct pt_regs *regs) { - struct uart_info *info = dev_id; - struct uart_port *port = info->port; - struct tty_struct *tty = info->tty; + struct uart_port *port = dev_id; + struct tty_struct *tty = port->info->tty; unsigned int status, ch, rxs, max_count = 256; status = *CSR_UARTFLG; @@ -150,8 +150,8 @@ static void serial21285_tx_chars(int irq, void *dev_id, struct pt_regs *regs) { - struct uart_info *info = dev_id; - struct uart_port *port = info->port; + struct uart_port *port = dev_id; + struct circ_buf *xmit = &port->info->xmit; int count = 256; if (port->x_char) { @@ -160,87 +160,96 @@ port->x_char = 0; return; } - if (port->xmit.head == port->xmit.tail - || info->tty->stopped - || info->tty->hw_stopped) { + if (uart_circ_empty(xmit) || uart_tx_stopped(port)) { serial21285_stop_tx(port, 0); return; } do { - *CSR_UARTDR = port->xmit.buf[port->xmit.tail]; - port->xmit.tail = (port->xmit.tail + 1) & (UART_XMIT_SIZE - 1); + *CSR_UARTDR = xmit->buf[xmit->tail]; + xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE - 1); port->icount.tx++; - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) break; } while (--count > 0 && !(*CSR_UARTFLG & 0x20)); - if (CIRC_CNT(port->xmit.head, port->xmit.tail, UART_XMIT_SIZE) < - WAKEUP_CHARS) - uart_event(info, EVT_WRITE_WAKEUP); + if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) + uart_event(port, EVT_WRITE_WAKEUP); - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) serial21285_stop_tx(port, 0); } -static u_int serial21285_tx_empty(struct uart_port *port) +static unsigned int serial21285_tx_empty(struct uart_port *port) { return (*CSR_UARTFLG & 8) ? 0 : TIOCSER_TEMT; } /* no modem control lines */ -static u_int serial21285_get_mctrl(struct uart_port *port) +static unsigned int serial21285_get_mctrl(struct uart_port *port) { return TIOCM_CAR | TIOCM_DSR | TIOCM_CTS; } -static void serial21285_set_mctrl(struct uart_port *port, u_int mctrl) +static void serial21285_set_mctrl(struct uart_port *port, unsigned int mctrl) { } static void serial21285_break_ctl(struct uart_port *port, int break_state) { - u_int h_lcr; + unsigned long flags; + unsigned int h_lcr; + spin_lock_irqsave(&port->lock, flags); h_lcr = *CSR_H_UBRLCR; if (break_state) h_lcr |= H_UBRLCR_BREAK; else h_lcr &= ~H_UBRLCR_BREAK; *CSR_H_UBRLCR = h_lcr; + spin_unlock_irqrestore(&port->lock, flags); } -static int serial21285_startup(struct uart_port *port, struct uart_info *info) +static int serial21285_startup(struct uart_port *port) { int ret; ret = request_irq(IRQ_CONRX, serial21285_rx_chars, 0, - serial21285_name, info); + serial21285_name, port); if (ret == 0) { ret = request_irq(IRQ_CONTX, serial21285_tx_chars, 0, - serial21285_name, info); + serial21285_name, port); if (ret) - free_irq(IRQ_CONRX, info); + free_irq(IRQ_CONRX, port); } return ret; } -static void serial21285_shutdown(struct uart_port *port, struct uart_info *info) +static void serial21285_shutdown(struct uart_port *port) { - free_irq(IRQ_CONTX, info); - free_irq(IRQ_CONRX, info); + free_irq(IRQ_CONTX, port); + free_irq(IRQ_CONRX, port); } static void -serial21285_change_speed(struct uart_port *port, u_int cflag, u_int iflag, u_int quot) +serial21285_change_speed(struct uart_port *port, unsigned int cflag, + unsigned int iflag, unsigned int quot) { - u_int h_lcr; + unsigned int h_lcr; switch (cflag & CSIZE) { - case CS5: h_lcr = 0x00; break; - case CS6: h_lcr = 0x20; break; - case CS7: h_lcr = 0x40; break; - default: /* CS8 */ h_lcr = 0x60; break; + case CS5: + h_lcr = 0x00; + break; + case CS6: + h_lcr = 0x20; + break; + case CS7: + h_lcr = 0x40; + break; + default: /* CS8 */ + h_lcr = 0x60; + break; } if (cflag & CSTOPB) @@ -353,9 +362,10 @@ } #ifdef CONFIG_SERIAL_21285_CONSOLE -/************** console driver *****************/ -static void serial21285_console_write(struct console *co, const char *s, u_int count) +static void +serial21285_console_write(struct console *co, const char *s, + unsigned int count) { int i; @@ -373,22 +383,12 @@ static kdev_t serial21285_console_device(struct console *c) { - return MKDEV(SERIAL_21285_MAJOR, SERIAL_21285_MINOR); -} - -static int serial21285_console_wait_key(struct console *co) -{ - int c; - - disable_irq(IRQ_CONRX); - while (*CSR_UARTFLG & 0x10); - c = *CSR_UARTDR; - enable_irq(IRQ_CONRX); - return c; + return mk_kdev(SERIAL_21285_MAJOR, SERIAL_21285_MINOR); } static void __init -serial21285_get_options(struct uart_port *port, int *baud, int *parity, int *bits) +serial21285_get_options(struct uart_port *port, int *baud, + int *parity, int *bits) { } @@ -419,17 +419,12 @@ #ifdef CONFIG_SERIAL_21285_OLD static struct console serial21285_old_cons = { - SERIAL_21285_OLD_NAME, - serial21285_console_write, - NULL, - serial21285_console_device, - serial21285_console_wait_key, - NULL, - serial21285_console_setup, - CON_PRINTBUFFER, - -1, - 0, - NULL + name: SERIAL_21285_OLD_NAME, + write: serial21285_console_write, + device: serial21285_console_device, + setup: serial21285_console_setup, + flags: CON_PRINTBUFFER, + index: -1, }; #endif @@ -438,7 +433,6 @@ name: SERIAL_21285_NAME, write: serial21285_console_write, device: serial21285_console_device, - wait_key: serial21285_console_wait_key, setup: serial21285_console_setup, flags: CON_PRINTBUFFER, index: -1, @@ -457,6 +451,7 @@ static struct uart_driver serial21285_reg = { owner: THIS_MODULE, + driver_name: "ttyFB", normal_major: SERIAL_21285_MAJOR, #ifdef CONFIG_DEVFS_FS normal_name: "ttyFB%d", Index: serial_8250.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_8250.c,v retrieving revision 1.14 retrieving revision 1.15 diff -u -d -r1.14 -r1.15 --- serial_8250.c 25 Dec 2001 06:50:51 -0000 1.14 +++ serial_8250.c 14 Mar 2002 20:02:07 -0000 1.15 @@ -13,9 +13,19 @@ * (at your option) any later version. * * $Id$ + * + * A note about mapbase / membase + * + * mapbase is the physical address of the IO port. Currently, we don't + * support this very well, and it may well be dropped from this driver + * in future. As such, mapbase should be NULL. + * + * membase is an 'ioremapped' cookie. This is compatible with the old [...2473 lines suppressed...] for (i = 0; i < UART_NR; i++) { - if (serial8250_ports[i].port.type != PORT_UNKNOWN) - clear_bit(serial8250_ports[i].port.irq, map); + if (serial8250_ports[i].port.type != PORT_UNKNOWN && + serial8250_ports[i].port.irq < 16) + *map |= 1 << serial8250_ports[i].port.irq; } } @@ -1968,7 +1872,8 @@ int i; for (i = 0; i < UART_NR; i++) - uart_remove_one_port(&serial8250_reg,&serial8250_ports[i].port); + uart_remove_one_port(&serial8250_reg, &serial8250_ports[i].port); + uart_unregister_driver(&serial8250_reg); } Index: serial_8250.h =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_8250.h,v retrieving revision 1.6 retrieving revision 1.7 diff -u -d -r1.6 -r1.7 --- serial_8250.h 25 Dec 2001 06:50:51 -0000 1.6 +++ serial_8250.h 14 Mar 2002 20:02:07 -0000 1.7 @@ -15,6 +15,8 @@ * $Id$ */ +#include <linux/config.h> + struct serial8250_probe { struct module *owner; int (*pci_init_one)(struct pci_dev *dev); @@ -24,7 +26,7 @@ int serial8250_register_probe(struct serial8250_probe *probe); void serial8250_unregister_probe(struct serial8250_probe *probe); -void serial8250_get_irq_map(int *map); +void serial8250_get_irq_map(unsigned int *map); struct old_serial_port { unsigned int uart; @@ -34,55 +36,7 @@ unsigned int flags; }; -#undef SERIAL_PARANOIA_CHECK -#define CONFIG_SERIAL_NOPAUSE_IO -#define SERIAL_DO_RESTART - -#ifdef CONFIG_PCI -#ifndef CONFIG_SERIAL_SHARE_IRQ -#define CONFIG_SERIAL_SHARE_IRQ -#endif -#ifndef CONFIG_SERIAL_MANY_PORTS -#define CONFIG_SERIAL_MANY_PORTS -#endif -#endif - -#ifdef __ISAPNP__ -#ifndef ENABLE_SERIAL_PNP -#define ENABLE_SERIAL_PNP -#endif -#endif - -/* Set of debugging defines */ - -#undef SERIAL_DEBUG_INTR #undef SERIAL_DEBUG_PCI -#undef SERIAL_DEBUG_AUTOCONF - -/* Sanity checks */ - -#ifdef CONFIG_SERIAL_MULTIPORT -#ifndef CONFIG_SERIAL_SHARE_IRQ -#define CONFIG_SERIAL_SHARE_IRQ -#endif -#endif - -#ifdef CONFIG_HUB6 -#ifndef CONFIG_SERIAL_MANY_PORTS -#define CONFIG_SERIAL_MANY_PORTS -#endif -#ifndef CONFIG_SERIAL_SHARE_IRQ -#define CONFIG_SERIAL_SHARE_IRQ -#endif -#endif - -#ifdef MODULE -#undef CONFIG_SERIAL_CONSOLE -#endif - -#define CONFIG_SERIAL_RSA - -#define RS_ISR_PASS_LIMIT 256 #if defined(__i386__) && (defined(CONFIG_M386) || defined(CONFIG_M486)) #define SERIAL_INLINE @@ -98,5 +52,3 @@ #define PROBE_ANY (~0) #define HIGH_BITS_OFFSET ((sizeof(long)-sizeof(int))*8) - - Index: serial_8250_pci.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_8250_pci.c,v retrieving revision 1.14 retrieving revision 1.15 diff -u -d -r1.14 -r1.15 --- serial_8250_pci.c 25 Dec 2001 06:50:51 -0000 1.14 +++ serial_8250_pci.c 14 Mar 2002 20:02:07 -0000 1.15 @@ -13,7 +13,6 @@ * * $Id$ */ -#include <linux/config.h> #include <linux/module.h> #include <linux/init.h> #include <linux/pci.h> @@ -23,7 +22,7 @@ #include <linux/slab.h> #include <linux/serial.h> -/* 2.4.6 compatibility cruft ;( */ +/* 2.4.6 compatibility cruft - to be removed with the old serial.c code */ #define pci_board __pci_board #include <linux/serialP.h> #undef pci_board @@ -90,24 +89,40 @@ offset = board->first_uart_offset; - /* Timedia/SUNIX uses a mixture of BARs and offsets */ - /* Ugh, this is ugly as all hell --- TYT */ - if(dev->vendor == PCI_VENDOR_ID_TIMEDIA ) /* 0x1409 */ + /* + * Timedia/SUNIX uses a mixture of BARs and offsets + * Ugh, this is ugly as all hell --- TYT + */ + if (dev->vendor == PCI_VENDOR_ID_TIMEDIA) switch(idx) { - case 0: base_idx=0; - break; - case 1: base_idx=0; offset=8; - break; - case 2: base_idx=1; - break; - case 3: base_idx=1; offset=8; - break; - case 4: /* BAR 2*/ - case 5: /* BAR 3 */ - case 6: /* BAR 4*/ - case 7: base_idx=idx-2; /* BAR 5*/ + case 0: + base_idx = 0; + break; + case 1: + base_idx = 0; + offset = 8; + break; + case 2: + base_idx = 1; + break; + case 3: + base_idx = 1; + offset = 8; + break; + case 4: /* BAR 2 */ + case 5: /* BAR 3 */ + case 6: /* BAR 4 */ + case 7: /* BAR 5 */ + base_idx = idx - 2; } + /* AFAVLAB uses a different mixture of BARs and offsets */ + /* Not that ugly ;) -- HW */ + if (dev->vendor == PCI_VENDOR_ID_AFAVLAB && idx >= 4) { + base_idx = 4; + offset = (idx - 4) * 8; + } + /* Some Titan cards are also a little weird */ if (dev->vendor == PCI_VENDOR_ID_TITAN && (dev->device == PCI_DEVICE_ID_TITAN_400L || @@ -138,14 +153,15 @@ } req->io_type = SERIAL_IO_MEM; req->iomem_base = ioremap(port, board->uart_offset); + if (req->iomem_base == NULL) + return -ENOMEM; req->iomem_reg_shift = board->reg_shift; req->port = 0; return 0; } -static _INLINE_ int get_pci_irq(struct pci_dev *dev, - struct pci_board *board, - int idx) +static _INLINE_ int +get_pci_irq(struct pci_dev *dev, struct pci_board *board, int idx) { int base_idx; @@ -168,41 +184,40 @@ static int __devinit pci_plx9050_fn(struct pci_dev *dev, struct pci_board *board, int enable) { - u8 data, *p, irq_config; - int pci_config; + u8 *p, irq_config = 0; - irq_config = 0x41; - pci_config = PCI_COMMAND_MEMORY; - if (dev->vendor == PCI_VENDOR_ID_PANACOM) - irq_config = 0x43; - if ((dev->vendor == PCI_VENDOR_ID_PLX) && - (dev->device == PCI_DEVICE_ID_PLX_ROMULUS)) { - /* - * As the megawolf cards have the int pins active - * high, and have 2 UART chips, both ints must be - * enabled on the 9050. Also, the UARTS are set in - * 16450 mode by default, so we have to enable the - * 16C950 'enhanced' mode so that we can use the deep - * FIFOs - */ - irq_config = 0x5b; - pci_config = PCI_COMMAND_MEMORY | PCI_COMMAND_IO; + if (enable) { + irq_config = 0x41; + if (dev->vendor == PCI_VENDOR_ID_PANACOM) + irq_config = 0x43; + if ((dev->vendor == PCI_VENDOR_ID_PLX) && + (dev->device == PCI_DEVICE_ID_PLX_ROMULUS)) { + /* + * As the megawolf cards have the int pins active + * high, and have 2 UART chips, both ints must be + * enabled on the 9050. Also, the UARTS are set in + * 16450 mode by default, so we have to enable the + * 16C950 'enhanced' mode so that we can use the + * deep FIFOs + */ + irq_config = 0x5b; + } } - - pci_read_config_byte(dev, PCI_COMMAND, &data); - if (enable) - pci_write_config_byte(dev, PCI_COMMAND, - data | pci_config); - - /* enable/disable interrupts */ + /* + * enable/disable interrupts + */ p = ioremap(pci_resource_start(dev, 0), 0x80); - writel(enable ? irq_config : 0x00, (unsigned long)p + 0x4c); + if (p == NULL) + return -ENOMEM; + writel(irq_config, (unsigned long)p + 0x4c); + + /* + * Read the register back to ensure that it took effect. + */ + readl((unsigned long)p + 0x4c); iounmap(p); - if (!enable) - pci_write_config_byte(dev, PCI_COMMAND, - data & ~pci_config); return 0; } @@ -232,27 +247,30 @@ static int __devinit pci_siig10x_fn(struct pci_dev *dev, struct pci_board *board, int enable) { - u16 data, *p; + u16 data, *p; - if (!enable) return 0; + if (!enable) + return 0; - p = ioremap(pci_resource_start(dev, 0), 0x80); + switch (dev->device & 0xfff8) { + case PCI_DEVICE_ID_SIIG_1S_10x: /* 1S */ + data = 0xffdf; + break; + case PCI_DEVICE_ID_SIIG_2S_10x: /* 2S, 2S1P */ + data = 0xf7ff; + break; + default: /* 1S1P, 4S */ + data = 0xfffb; + break; + } - switch (dev->device & 0xfff8) { - case PCI_DEVICE_ID_SIIG_1S_10x: /* 1S */ - data = 0xffdf; - break; - case PCI_DEVICE_ID_SIIG_2S_10x: /* 2S, 2S1P */ - data = 0xf7ff; - break; - default: /* 1S1P, 4S */ - data = 0xfffb; - break; - } + p = ioremap(pci_resource_start(dev, 0), 0x80); + if (p == NULL) + return -ENOMEM; - writew(readw((unsigned long) p + 0x28) & data, (unsigned long) p + 0x28); - iounmap(p); - return 0; + writew(readw((unsigned long) p + 0x28) & data, (unsigned long) p + 0x28); + iounmap(p); + return 0; } #define PCI_DEVICE_ID_SIIG_2S_20x (PCI_DEVICE_ID_SIIG_2S_20x_550 & 0xfffc) @@ -261,44 +279,43 @@ static int __devinit pci_siig20x_fn(struct pci_dev *dev, struct pci_board *board, int enable) { - u8 data; + u8 data; - if (!enable) return 0; + if (!enable) + return 0; - /* Change clock frequency for the first UART. */ - pci_read_config_byte(dev, 0x6f, &data); - pci_write_config_byte(dev, 0x6f, data & 0xef); + /* Change clock frequency for the first UART. */ + pci_read_config_byte(dev, 0x6f, &data); + pci_write_config_byte(dev, 0x6f, data & 0xef); - /* If this card has 2 UART, we have to do the same with second UART. */ - if (((dev->device & 0xfffc) == PCI_DEVICE_ID_SIIG_2S_20x) || - ((dev->device & 0xfffc) == PCI_DEVICE_ID_SIIG_2S1P_20x)) { - pci_read_config_byte(dev, 0x73, &data); - pci_write_config_byte(dev, 0x73, data & 0xef); - } - return 0; + /* If this card has 2 UART, we have to do the same with second UART. */ + if (((dev->device & 0xfffc) == PCI_DEVICE_ID_SIIG_2S_20x) || + ((dev->device & 0xfffc) == PCI_DEVICE_ID_SIIG_2S1P_20x)) { + pci_read_config_byte(dev, 0x73, &data); + pci_write_config_byte(dev, 0x73, data & 0xef); + } + return 0; } /* Added for EKF Intel i960 serial boards */ static int __devinit -pci_inteli960ni_fn(struct pci_dev *dev, - struct pci_board *board, - int enable) +pci_inteli960ni_fn(struct pci_dev *dev, struct pci_board *board, int enable) { unsigned long oldval; - + if (!(pci_get_subdevice(dev) & 0x1000)) - return(-1); + return -ENODEV; if (!enable) /* is there something to deinit? */ - return(0); + return 0; /* is firmware started? */ pci_read_config_dword(dev, 0x44, (void*) &oldval); if (oldval == 0x00001000L) { /* RESET value */ printk(KERN_DEBUG "Local i960 firmware missing"); - return(-1); + return -ENODEV; } - return(0); + return 0; } /* @@ -307,21 +324,29 @@ * in the PCI table into one, for sanity's and compactness's sake. */ static unsigned short timedia_single_port[] = { - 0x4025, 0x4027, 0x4028, 0x5025, 0x5027, 0 }; + 0x4025, 0x4027, 0x4028, 0x5025, 0x5027, 0 +}; + static unsigned short timedia_dual_port[] = { 0x0002, 0x4036, 0x4037, 0x4038, 0x4078, 0x4079, 0x4085, 0x4088, 0x4089, 0x5037, 0x5078, 0x5079, 0x5085, 0x6079, 0x7079, 0x8079, 0x8137, 0x8138, 0x8237, 0x8238, 0x9079, 0x9137, 0x9138, 0x9237, 0x9238, 0xA079, 0xB079, 0xC079, - 0xD079, 0 }; + 0xD079, 0 +}; + static unsigned short timedia_quad_port[] = { 0x4055, 0x4056, 0x4095, 0x4096, 0x5056, 0x8156, 0x8157, 0x8256, 0x8257, 0x9056, 0x9156, 0x9157, 0x9158, 0x9159, 0x9256, 0x9257, 0xA056, 0xA157, 0xA158, 0xA159, 0xB056, - 0xB157, 0 }; + 0xB157, 0 +}; + static unsigned short timedia_eight_port[] = { 0x4065, 0x4066, 0x5065, 0x5066, 0x8166, 0x9066, 0x9166, - 0x9167, 0x9168, 0xA066, 0xA167, 0xA168, 0 }; + 0x9167, 0x9168, 0xA066, 0xA167, 0xA168, 0 +}; + static struct timedia_struct { int num; unsigned short *ids; @@ -342,9 +367,9 @@ if (!enable) return 0; - for (i=0; timedia_data[i].num; i++) { + for (i = 0; timedia_data[i].num; i++) { ids = timedia_data[i].ids; - for (j=0; ids[j]; j++) { + for (j = 0; ids[j]; j++) { if (pci_get_subdevice(dev) == ids[j]) { board->num_ports = timedia_data[i].num; return 0; @@ -381,6 +406,7 @@ pbn_b0_bt_1_115200, pbn_b0_bt_2_115200, + pbn_b0_bt_8_115200, pbn_b0_bt_1_460800, pbn_b0_bt_2_460800, @@ -417,12 +443,11 @@ pbn_timedia, pbn_intel_i960, pbn_sgi_ioc3, -#ifdef CONFIG_DDB5074 pbn_nec_nile4, -#endif -#if 0 + + pbn_dci_pccom4, pbn_dci_pccom8, -#endif + pbn_xircom_combo, pbn_siig10x_0, @@ -459,6 +484,7 @@ { SPCI_FL_BASE0 | SPCI_FL_BASE_TABLE, 1, 115200 }, /* pbn_b0_bt_1_115200 */ { SPCI_FL_BASE0 | SPCI_FL_BASE_TABLE, 2, 115200 }, /* pbn_b0_bt_2_115200 */ + { SPCI_FL_BASE0 | SPCI_FL_BASE_TABLE, 8, 115200 }, /* pbn_b0_bt_8_115200 */ { SPCI_FL_BASE0 | SPCI_FL_BASE_TABLE, 1, 460800 }, /* pbn_b0_bt_1_460800 */ { SPCI_FL_BASE0 | SPCI_FL_BASE_TABLE, 2, 460800 }, /* pbn_b0_bt_2_460800 */ @@ -505,18 +531,17 @@ 8<<2, 2, pci_inteli960ni_fn, 0x10000}, { SPCI_FL_BASE0 | SPCI_FL_IRQRESOURCE, /* pbn_sgi_ioc3 */ 1, 458333, 0, 0, 0, 0x20178 }, -#ifdef CONFIG_DDB5074 + /* * NEC Vrc-5074 (Nile 4) builtin UART. - * Conditionally compiled in since this is a motherboard device. */ { SPCI_FL_BASE0, 1, 520833, /* pbn_nec_nile4 */ 64, 3, NULL, 0x300 }, -#endif -#if 0 /* PCI_DEVICE_ID_DCI_PCCOM8 ? */ /* pbn_dci_pccom8 */ - { SPCI_FL_BASE3, 8, 115200, 8 }, -#endif - { SPCI_FL_BASE0, 1, 115200, /* pbn_xircom_combo */ + + { SPCI_FL_BASE3, 4, 115200, 8 }, /* pbn_dci_pccom4 */ + { SPCI_FL_BASE3, 8, 115200, 8 }, /* pbn_dci_pccom8 */ + + { SPCI_FL_BASE0, 1, 115200, /* pbn_xircom_combo */ 0, 0, pci_xircom_fn }, { SPCI_FL_BASE2, 1, 460800, /* pbn_siig10x_0 */ @@ -547,11 +572,11 @@ * guess what the configuration might be, based on the pitiful PCI * serial specs. Returns 0 on success, 1 on failure. */ -static int __devinit serial_pci_guess_board(struct pci_dev *dev, - struct pci_board *board) +static int __devinit +serial_pci_guess_board(struct pci_dev *dev, struct pci_board *board) { - int num_iomem = 0, num_port = 0, first_port = -1; - int i; + int num_iomem = 0, num_port = 0, first_port = -1; + int i; /* * If it is not a communications device or the programming @@ -565,7 +590,7 @@ (dev->class & 0xff) > 6) return 1; - for (i=0; i < 6; i++) { + for (i = 0; i < 6; i++) { if (IS_PCI_REGION_IOPORT(dev, i)) { num_port++; if (first_port == -1) @@ -587,15 +612,23 @@ } /* - * return -1 to refuse + * return an error code to refuse. + * + * serial_struct is 60 bytes. */ -static int pci_init_one(struct pci_dev *dev, const struct pci_device_id *ent) +static int __devinit pci_init_one(struct pci_dev *dev, const struct pci_device_id *ent) { struct serial_private *priv; struct pci_board *board, tmp; struct serial_struct serial_req; int base_baud, rc, k; + if (ent->driver_data >= ARRAY_SIZE(pci_boards)) { + printk(KERN_ERR "pci_init_one: invalid driver_data: %ld\n", + ent->driver_data); + return -EINVAL; + } + board = &pci_boards[ent->driver_data]; rc = pci_enable_device(dev); @@ -616,7 +649,6 @@ pci_get_subvendor(dev), pci_get_subdevice(dev)); } - priv = kmalloc(sizeof(struct serial_private) + sizeof(unsigned int) * board->num_ports, GFP_KERNEL); @@ -626,16 +658,19 @@ /* * Run the initialization function, if any */ - if (board->init_fn && ((board->init_fn)(dev, board, 1) != 0)) { - kfree(priv); - return -ENODEV; + if (board->init_fn) { + rc = board->init_fn(dev, board, 1); + if (rc != 0) { + kfree(priv); + return rc; + } } base_baud = board->base_baud; if (!base_baud) base_baud = BASE_BAUD; memset(&serial_req, 0, sizeof(serial_req)); - for (k=0; k < board->num_ports; k++) { + for (k = 0; k < board->num_ports; k++) { serial_req.irq = get_pci_irq(dev, board, k); if (get_pci_port(dev, board, &serial_req, k)) break; @@ -645,6 +680,7 @@ #endif serial_req.flags = ASYNC_SKIP_TEST | ASYNC_AUTOPROBE; serial_req.baud_base = base_baud; + priv->line[k] = register_serial(&serial_req); if (priv->line[k] < 0) break; @@ -658,19 +694,23 @@ return 0; } -static void pci_remove_one(struct pci_dev *dev) +static void __devexit pci_remove_one(struct pci_dev *dev) { struct serial_private *priv = pci_get_drvdata(dev); int i; pci_set_drvdata(dev, NULL); - for (i = 0; i < priv->nr; i++) - unregister_serial(priv->line[i]); + if (priv) { + for (i = 0; i < priv->nr; i++) + unregister_serial(priv->line[i]); - priv->board->init_fn(dev, priv->board, 0); + priv->board->init_fn(dev, priv->board, 0); - kfree(priv); + pci_disable_device(dev); + + kfree(priv); + } } static struct pci_device_id serial_pci_tbl[] __devinitdata = { @@ -979,6 +1019,11 @@ { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_DSERIAL, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_b0_bt_2_115200 }, + /* AFAVLAB serial card, from Harald Welte <la...@gn...> */ + { PCI_VENDOR_ID_AFAVLAB, PCI_DEVICE_ID_AFAVLAB_P028, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, + pbn_b0_bt_8_115200 }, + { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_QUATRO_A, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_b0_bt_2_115200 }, @@ -1029,35 +1074,47 @@ 0xFF00, 0, 0, 0, pbn_sgi_ioc3 }, -#ifdef CONFIG_DDB5074 /* * NEC Vrc-5074 (Nile 4) builtin UART. - * Conditionally compiled in since this is a motherboard device. */ { PCI_VENDOR_ID_NEC, PCI_DEVICE_ID_NEC_NILE4, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_nec_nile4 }, -#endif -#if 0 /* PCI_DEVICE_ID_DCI_PCCOM8 ? */ + { PCI_VENDOR_ID_DCI, PCI_DEVICE_ID_DCI_PCCOM4, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, + pbn_dci_pccom4 }, { PCI_VENDOR_ID_DCI, PCI_DEVICE_ID_DCI_PCCOM8, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_dci_pccom8 }, -#endif - { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, - PCI_CLASS_COMMUNICATION_SERIAL << 8, 0xffff00, }, - { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, - PCI_CLASS_COMMUNICATION_MODEM << 8, 0xffff00, }, - { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, - PCI_CLASS_COMMUNICATION_MULTISERIAL << 8, 0xffff00, }, + { PCI_ANY_ID, PCI_ANY_ID, + PCI_ANY_ID, PCI_ANY_ID, + PCI_CLASS_COMMUNICATION_SERIAL << 8, + 0xffff00, }, + { PCI_ANY_ID, PCI_ANY_ID, + PCI_ANY_ID, PCI_ANY_ID, + PCI_CLASS_COMMUNICATION_MODEM << 8, + 0xffff00, }, + { PCI_ANY_ID, PCI_ANY_ID, + PCI_ANY_ID, PCI_ANY_ID, + PCI_CLASS_COMMUNICATION_MULTISERIAL << 8, + 0xffff00, }, { 0, } }; +#ifndef __devexit_p +#if defined(MODULE) || defined(CONFIG_HOTPLUG) +#define __devexit_p(x) x +#else +#define __devexit_p(x) NULL +#endif +#endif + static struct pci_driver serial_pci_driver = { name: "serial", probe: pci_init_one, - remove: pci_remove_one, + remove: __devexit_p(pci_remove_one), id_table: serial_pci_tbl, }; Index: serial_8250_pnp.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_8250_pnp.c,v retrieving revision 1.9 retrieving revision 1.10 diff -u -d -r1.9 -r1.10 --- serial_8250_pnp.c 25 Dec 2001 06:50:51 -0000 1.9 +++ serial_8250_pnp.c 14 Mar 2002 20:02:07 -0000 1.10 @@ -13,7 +13,6 @@ * * $Id$ */ -#include <linux/config.h> #include <linux/module.h> #include <linux/init.h> #include <linux/pci.h> @@ -309,14 +308,14 @@ static void inline avoid_irq_share(struct pci_dev *dev) { + unsigned int map = 0x1FF8; struct isapnp_irq *irq; struct isapnp_resources *res = dev->sysdata; - int map = 0x1FF8; serial8250_get_irq_map(&map); for ( ; res; res = res->alt) - for(irq = res->irq; irq; irq = irq->next) + for (irq = res->irq; irq; irq = irq->next) irq->map = map; } @@ -424,8 +423,8 @@ if (HIGH_BITS_OFFSET) serial_req.port = pci_resource_start(dev, 0) >> HIGH_BITS_OFFSET; -#ifdef SERIAL_DEBUG_PCI - printk("Setup PCI/PNP port: port %x, irq %d, type %d\n", +#ifdef SERIAL_DEBUG_PNP + printk("Setup PNP port: port %x, irq %d, type %d\n", serial_req.port, serial_req.irq, serial_req.io_type); #endif @@ -466,10 +465,11 @@ * This function should vanish when 2.5 comes around and * we have pnpbios_module_init() */ -static void pnp_init(void) +static int pnp_init(void) { const struct pnpbios_device_id *id; struct pci_dev *dev = NULL; + int nr = 0, rc = -ENODEV; #ifdef SERIAL_DEBUG_PNP printk("Entered probe_serial_pnp()\n"); @@ -501,14 +501,19 @@ break; if (id->id[0]) - pnp_init_one(dev, id, slot_name); + rc = pnp_init_one(dev, id, slot_name); else - pnp_init_one(dev, NULL, slot_name); + rc = pnp_init_one(dev, NULL, slot_name); + + if (rc == 0) + nr++; } #ifdef SERIAL_DEBUG_PNP printk("Leaving probe_serial_pnp() (probe finished)\n"); #endif + + return nr == 0 ? rc : 0; } static int __init serial8250_pnp_init(void) @@ -519,8 +524,7 @@ #endif return -ENODEV; } - pnp_init(); - return 0; + return pnp_init(); } static void __exit serial8250_pnp_exit(void) Index: serial_amba.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_amba.c,v retrieving revision 1.12 retrieving revision 1.13 diff -u -d -r1.12 -r1.13 --- serial_amba.c 25 Dec 2001 06:50:51 -0000 1.12 +++ serial_amba.c 14 Mar 2002 20:02:07 -0000 1.13 @@ -111,9 +111,6 @@ * RTS DTR * UART0 7 6 * UART1 5 4 - * - * We encode this bit information into port->driver_priv using the - * following macros. */ #define SC_CTRLC (IO_ADDRESS(INTEGRATOR_SC_BASE) + INTEGRATOR_SC_CTRLC_OFFSET) #define SC_CTRLS (IO_ADDRESS(INTEGRATOR_SC_BASE) + INTEGRATOR_SC_CTRLS_OFFSET) @@ -123,59 +120,65 @@ */ struct uart_amba_port { struct uart_port port; - u_int dtr_mask; - u_int rts_mask; - u_int old_status; + unsigned int dtr_mask; + unsigned int rts_mask; + unsigned int old_status; }; -static void ambauart_stop_tx(struct uart_port *port, u_int from_tty) +static void ambauart_stop_tx(struct uart_port *port, unsigned int tty_stop) { + unsigned long flags; unsigned int cr; + spin_lock_irqsave(&port->lock, flags); cr = UART_GET_CR(port); cr &= ~AMBA_UARTCR_TIE; UART_PUT_CR(port, cr); + spin_unlock_irqrestore(&port->lock, flags); } -static void ambauart_start_tx(struct uart_port *port, u_int nonempty, u_int from_tty) +static void ambauart_start_tx(struct uart_port *port, unsigned int tty_start) { - if (nonempty) { - unsigned int cr; + unsigned int cr; - cr = UART_GET_CR(port); - cr |= AMBA_UARTCR_TIE; - UART_PUT_CR(port, cr); - } + cr = UART_GET_CR(port); + cr |= AMBA_UARTCR_TIE; + UART_PUT_CR(port, cr); } static void ambauart_stop_rx(struct uart_port *port) { + unsigned long flags; unsigned int cr; + spin_lock_irqsave(&port->lock, flags); cr = UART_GET_CR(port); cr &= ~(AMBA_UARTCR_RIE | AMBA_UARTCR_RTIE); UART_PUT_CR(port, cr); + spin_unlock_irqrestore(&port->lock, flags); } static void ambauart_enable_ms(struct uart_port *port) { + unsigned long flags; unsigned int cr; + spin_lock_irqsave(&port->lock, flags); cr = UART_GET_CR(port); cr |= AMBA_UARTCR_MSIE; UART_PUT_CR(port, cr); + spin_unlock_irqrestore(&port->lock, flags); } static void #ifdef SUPPORT_SYSRQ -ambauart_rx_chars(struct uart_info *info, struct pt_regs *regs) +ambauart_rx_chars(struct uart_port *port, struct pt_regs *regs) #else -ambauart_rx_chars(struct uart_info *info) +ambauart_rx_chars(struct uart_port *port) #endif { - struct tty_struct *tty = info->tty; + struct tty_struct *tty = port->info->tty; unsigned int status, ch, rsr, max_count = 256; - struct uart_port *port = info->port; status = UART_GET_FR(port); while (UART_RX_DATA(status) && max_count--) { @@ -202,7 +205,7 @@ if (rsr & AMBA_UARTRSR_BE) { rsr &= ~(AMBA_UARTRSR_FE | AMBA_UARTRSR_PE); port->icount.brk++; - if (uart_handle_break(info, port->cons)) + if (uart_handle_break(port)) goto ignore_char; } else if (rsr & AMBA_UARTRSR_PE) port->icount.parity++; @@ -221,7 +224,7 @@ *tty->flip.flag_buf_ptr = TTY_FRAME; } - if (uart_handle_sysrq_char(info, ch, regs)) + if (uart_handle_sysrq_char(port, ch, regs)) goto ignore_char; if ((rsr & port->ignore_status_mask) == 0) { @@ -247,9 +250,9 @@ return; } -static void ambauart_tx_chars(struct uart_info *info) +static void ambauart_tx_chars(struct uart_port *port) { - struct uart_port *port = info->port; + struct circ_buf *xmit = &port->info->xmit; int count; if (port->x_char) { @@ -258,34 +261,30 @@ port->x_char = 0; return; } - if (port->xmit.head == port->xmit.tail - || info->tty->stopped - || info->tty->hw_stopped) { + if (uart_circ_empty(xmit) || uart_tx_stopped(port)) { ambauart_stop_tx(port, 0); return; } count = port->fifosize >> 1; do { - UART_PUT_CHAR(port, port->xmit.buf[port->xmit.tail]); - port->xmit.tail = (port->xmit.tail + 1) & (UART_XMIT_SIZE - 1); + UART_PUT_CHAR(port, xmit->buf[xmit->tail]); + xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE - 1); port->icount.tx++; - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) break; } while (--count > 0); - if (CIRC_CNT(port->xmit.head, port->xmit.tail, UART_XMIT_SIZE) < - WAKEUP_CHARS) - uart_event(info, EVT_WRITE_WAKEUP); + if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) + uart_event(port, EVT_WRITE_WAKEUP); - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) ambauart_stop_tx(port, 0); } -static void ambauart_modem_status(struct uart_info *info) +static void ambauart_modem_status(struct uart_port *port) { - struct uart_amba_port *uap = (struct uart_amba_port *)info->port; - struct uart_port *port = info->port; + struct uart_amba_port *uap = (struct uart_amba_port *)port; unsigned int status, delta; UART_PUT_ICR(&uap->port, 0); @@ -299,49 +298,49 @@ return; if (delta & AMBA_UARTFR_DCD) - uart_handle_dcd_change(info, status & AMBA_UARTFR_DCD); + uart_handle_dcd_change(&uap->port, status & AMBA_UARTFR_DCD); if (delta & AMBA_UARTFR_DSR) - port->icount.dsr++; + uap->port.icount.dsr++; if (delta & AMBA_UARTFR_CTS) - uart_handle_cts_change(info, status & AMBA_UARTFR_CTS); + uart_handle_cts_change(&uap->port, status & AMBA_UARTFR_CTS); - wake_up_interruptible(&info->delta_msr_wait); + wake_up_interruptible(&uap->port.info->delta_msr_wait); } static void ambauart_int(int irq, void *dev_id, struct pt_regs *regs) { - struct uart_info *info = dev_id; + struct uart_port *port = dev_id; unsigned int status, pass_counter = AMBA_ISR_PASS_LIMIT; - status = UART_GET_INT_STATUS(info->port); + status = UART_GET_INT_STATUS(port); do { if (status & (AMBA_UARTIIR_RTIS | AMBA_UARTIIR_RIS)) #ifdef SUPPORT_SYSRQ - ambauart_rx_chars(info, regs); + ambauart_rx_chars(port, regs); #else - ambauart_rx_chars(info); + ambauart_rx_chars(port); #endif - if (status & AMBA_UARTIIR_TIS) - ambauart_tx_chars(info); if (status & AMBA_UARTIIR_MIS) - ambauart_modem_status(info); + ambauart_modem_status(port); + if (status & AMBA_UARTIIR_TIS) + ambauart_tx_chars(port); if (pass_counter-- == 0) break; - status = UART_GET_INT_STATUS(info->port); + status = UART_GET_INT_STATUS(port); } while (status & (AMBA_UARTIIR_RTIS | AMBA_UARTIIR_RIS | AMBA_UARTIIR_TIS)); } -static u_int ambauart_tx_empty(struct uart_port *port) +static unsigned int ambauart_tx_empty(struct uart_port *port) { return UART_GET_FR(port) & AMBA_UARTFR_BUSY ? 0 : TIOCSER_TEMT; } -static u_int ambauart_get_mctrl(struct uart_port *port) +static unsigned int ambauart_get_mctrl(struct uart_port *port) { unsigned int result = 0; unsigned int status; @@ -357,15 +356,15 @@ return result; } -static void ambauart_set_mctrl(struct uart_port *port, u_int mctrl) +static void ambauart_set_mctrl(struct uart_port *port, unsigned int mctrl) { struct uart_amba_port *uap = (struct uart_amba_port *)port; - u_int ctrls = 0, ctrlc = 0; + unsigned int ctrls = 0, ctrlc = 0; if (mctrl & TIOCM_RTS) ctrlc |= uap->rts_mask; else - ctrls |= uap->rts_mask; + ctrls |= uap->rts_mask; if (mctrl & TIOCM_DTR) ctrlc |= uap->dtr_mask; @@ -378,17 +377,20 @@ static void ambauart_break_ctl(struct uart_port *port, int break_state) { + unsigned long flags; unsigned int lcr_h; + spin_lock_irqsave(&port->lock, flags); lcr_h = UART_GET_LCRH(port); if (break_state == -1) lcr_h |= AMBA_UARTLCR_H_BRK; else lcr_h &= ~AMBA_UARTLCR_H_BRK; UART_PUT_LCRH(port, lcr_h); + spin_unlock_irqrestore(&port->lock, flags); } -static int ambauart_startup(struct uart_port *port, struct uart_info *info) +static int ambauart_startup(struct uart_port *port) { struct uart_amba_port *uap = (struct uart_amba_port *)port; int retval; @@ -396,7 +398,7 @@ /* * Allocate the IRQ */ - retval = request_irq(port->irq, ambauart_int, 0, "amba", info); + retval = request_irq(port->irq, ambauart_int, 0, "amba", port); if (retval) return retval; @@ -414,12 +416,12 @@ return 0; } -static void ambauart_shutdown(struct uart_port *port, struct uart_info *info) +static void ambauart_shutdown(struct uart_port *port) { /* * Free the interrupt */ - free_irq(port->irq, info); + free_irq(port->irq, port); /* * disable all interrupts, disable the port @@ -431,20 +433,27 @@ ~(AMBA_UARTLCR_H_BRK | AMBA_UARTLCR_H_FEN)); } -static void ambauart_change_speed(struct uart_port *port, u_int cflag, u_int iflag, u_int quot) +static void +ambauart_change_speed(struct uart_port *port, unsigned int cflag, + unsigned int iflag, unsigned int quot) { - u_int lcr_h, old_cr; + unsigned int lcr_h, old_cr; unsigned long flags; -#if DEBUG - printk("ambauart_set_cflag(0x%x) called\n", cflag); -#endif /* byte size and parity */ switch (cflag & CSIZE) { - case CS5: lcr_h = AMBA_UARTLCR_H_WLEN_5; break; - case CS6: lcr_h = AMBA_UARTLCR_H_WLEN_6; break; - case CS7: lcr_h = AMBA_UARTLCR_H_WLEN_7; break; - default: lcr_h = AMBA_UARTLCR_H_WLEN_8; break; // CS8 + case CS5: + lcr_h = AMBA_UARTLCR_H_WLEN_5; + break; + case CS6: + lcr_h = AMBA_UARTLCR_H_WLEN_6; + break; + case CS7: + lcr_h = AMBA_UARTLCR_H_WLEN_7; + break; + default: // CS8 + lcr_h = AMBA_UARTLCR_H_WLEN_8; + break; } if (cflag & CSTOPB) lcr_h |= AMBA_UARTLCR_H_STP2; @@ -485,11 +494,10 @@ port->ignore_status_mask |= UART_DUMMY_RSR_RX; /* first, disable everything */ - save_flags(flags); cli(); + spin_lock_irqsave(&port->lock, flags); old_cr = UART_GET_CR(port) & ~AMBA_UARTCR_MSIE; - if ((port->flags & ASYNC_HARDPPS_CD) || - (cflag & CRTSCTS) || !(cflag & CLOCAL)) + if (UART_ENABLE_MS(port, cflag)) old_cr |= AMBA_UARTCR_MSIE; UART_PUT_CR(port, 0); @@ -507,7 +515,7 @@ UART_PUT_LCRH(port, lcr_h); UART_PUT_CR(port, old_cr); - restore_flags(flags); + spin_unlock_irqrestore(&port->lock, flags); } static const char *ambauart_type(struct uart_port *port) @@ -586,9 +594,9 @@ irq: IRQ_UARTINT0, uartclk: 14745600, fifosize: 16, - unused: { 4, 5 }, /*driver_priv: PORT_CTRLS(5, 4), */ ops: &amba_pops, flags: ASYNC_BOOT_AUTOCONF, + line: 0, }, dtr_mask: 1 << 5, rts_mask: 1 << 4, @@ -601,9 +609,9 @@ irq: IRQ_UARTINT1, uartclk: 14745600, fifosize: 16, - unused: { 6, 7 }, /*driver_priv: PORT_CTRLS(7, 6), */ ops: &amba_pops, flags: ASYNC_BOOT_AUTOCONF, + line: 1, }, dtr_mask: 1 << 7, rts_mask: 1 << 6, @@ -611,32 +619,9 @@ }; #ifdef CONFIG_SERIAL_AMBA_CONSOLE -#ifdef used_and_not_const_char_pointer -static int ambauart_console_read(struct uart_port *port, char *s, u_int count) -{ - unsigned int status; - int c; -#if DEBUG - printk("ambauart_console_read() called\n"); -#endif - - c = 0; - while (c < count) { - status = UART_GET_FR(port); - if (UART_RX_DATA(status)) { - *s++ = UART_GET_CHAR(port); - c++; - } else { - // nothing more to get, return - return c; - } - } - // return the count - return c; -} -#endif -static void ambauart_console_write(struct console *co, const char *s, u_int count) +static void +ambauart_console_write(struct console *co, const char *s, unsigned int count) { struct uart_port *port = &amba_ports[co->index].port; unsigned int status, old_cr; @@ -676,25 +661,15 @@ static kdev_t ambauart_console_device(struct console *co) { - return MKDEV(SERIAL_AMBA_MAJOR, SERIAL_AMBA_MINOR + co->index); -} - -static int ambauart_console_wait_key(struct console *co) -{ - struct uart_port *port = &amba_ports[co->index].port; - unsigned int status; - - do { - status = UART_GET_FR(port); - } while (!UART_RX_DATA(status)); - return UART_GET_CHAR(port); + return mk_kdev(SERIAL_AMBA_MAJOR, SERIAL_AMBA_MINOR + co->index); } static void __init -ambauart_console_get_options(struct uart_port *port, int *baud, int *parity, int *bits) +ambauart_console_get_options(struct uart_port *port, int *baud, + int *parity, int *bits) { if (UART_GET_CR(port) & AMBA_UARTCR_UARTEN) { - u_int lcr_h, quot; + unsigned int lcr_h, quot; lcr_h = UART_GET_LCRH(port); *parity = 'n'; @@ -728,14 +703,10 @@ * if so, search for the first available port that does have * console support. */ -#if 0 - port = uart_get_console(amba_ports, UART_NR, co); -#else if (co->index >= UART_NR) co->index = 0; port = &amba_ports[co->index].port; -#endif - + if (options) uart_parse_options(options, &baud, &parity, &bits, &flow); else @@ -747,11 +718,7 @@ static struct console amba_console = { name: "ttyAM", write: ambauart_console_write, -#ifdef used_and_not_const_char_pointer - read: ambauart_console_read, -#endif device: ambauart_console_device, - wait_key: ambauart_console_wait_key, setup: ambauart_console_setup, flags: CON_PRINTBUFFER, index: -1, @@ -769,6 +736,7 @@ static struct uart_driver amba_reg = { owner: THIS_MODULE, + driver_name: "ttyAM", normal_major: SERIAL_AMBA_MAJOR, #ifdef CONFIG_DEVFS_FS normal_name: "ttyAM%d", Index: serial_anakin.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_anakin.c,v retrieving revision 1.5 retrieving revision 1.6 diff -u -d -r1.5 -r1.6 --- serial_anakin.c 25 Dec 2001 06:50:51 -0000 1.5 +++ serial_anakin.c 14 Mar 2002 20:02:07 -0000 1.6 @@ -64,27 +64,22 @@ #define CALLOUT_ANAKIN_MINOR 32 static struct tty_driver normal, callout; -static u_int txenable[NR_IRQS]; /* Software interrupt register */ - -struct uart_anakin_port { - struct uart_port port; - struct uart_info *info; -}; +static unsigned int txenable[NR_IRQS]; /* Software interrupt register */ static inline unsigned int -anakin_in(struct uart_port *port, u_int offset) +anakin_in(struct uart_port *port, unsigned int offset) { return __raw_readl(port->base + offset); } static inline void -anakin_out(struct uart_port *port, u_int offset, unsigned int value) +anakin_out(struct uart_port *port, unsigned int offset, unsigned int value) { __raw_writel(value, port->base + offset); } static void -anakin_stop_tx(struct uart_port *port, u_int from_tty) +anakin_stop_tx(struct uart_port *port, unsigned int tty_stop) { txenable[port->irq] = 0; } @@ -92,13 +87,15 @@ static inline void anakin_transmit_buffer(struct uart_port *port) { + struct circ_buf *xmit = &port->info->xmit; + while (!(anakin_in(port, 0x10) & TXEMPTY)); - anakin_out(port, 0x14, port->xmit.buf[port->xmit.tail]); + anakin_out(port, 0x14, xmit->buf[xmit->tail]); anakin_out(port, 0x18, anakin_in(port, 0x18) | SENDREQUEST); - port->xmit.tail = (port->xmit.tail + 1) & (UART_XMIT_SIZE-1); + xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE-1); port->icount.tx++; - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) anakin_stop_tx(port, 0); } @@ -112,22 +109,22 @@ } static void -anakin_start_tx(struct uart_port *port, u_int nonempty, u_int from_tty) +anakin_start_tx(struct uart_port *port, unsigned int tty_start) { - struct uart_anakin_port *up = (struct uart_anakin_port *)port; unsigned int flags; - save_flags_cli(flags); + spin_lock_irqsave(&port->lock, flags); - // is it this... or below: if (nonempty + // is it this... or below if (!txenable[port->irq]) { txenable[port->irq] = TXENABLE; - if ((anakin_in(port, 0x10) & TXEMPTY) && nonempty) { - anakin_transmit_buffer(up->port); + if ((anakin_in(port, 0x10) & TXEMPTY)) { + anakin_transmit_buffer(port); } } - restore_flags(flags); + + spin_unlock_irqrestore(&port->lock, flags); } static void @@ -135,11 +132,11 @@ { unsigned long flags; - save_flags_cli(flags); + spin_lock_irqsave(&port->lock, flags); while (anakin_in(port, 0x10) & RXRELEASE) anakin_in(port, 0x14); anakin_out(port, 0x18, anakin_in(port, 0x18) | BLOCKRX); - restore_flags(flags); + spin_unlock_irqrestore(&port->lock, flags); } static void @@ -148,20 +145,20 @@ } static inline void -anakin_rx_chars(struct uart_info *info) +anakin_rx_chars(struct uart_port *port) { unsigned int ch; - struct tty_struct *tty = info->tty; + struct tty_struct *tty = port->info->tty; - if (!(anakin_in(info->port, 0x10) & RXRELEASE)) + if (!(anakin_in(port, 0x10) & RXRELEASE)) return; - ch = anakin_in(info->port, 0x14) & 0xff; + ch = anakin_in(port, 0x14) & 0xff; if (tty->flip.count < TTY_FLIPBUF_SIZE) { *tty->flip.char_buf_ptr++ = ch; *tty->flip.flag_buf_ptr++ = TTY_NORMAL; - info->port->icount.rx++; + port->icount.rx++; tty->flip.count++; } tty_flip_buffer_push(tty); @@ -177,55 +174,51 @@ } static inline void -anakin_tx_chars(struct uart_info *info) +anakin_tx_chars(struct uart_port *port) { - struct uart_port *port = info->port; + struct circ_buf *xmit = &port->info->xmit; if (port->x_char) { anakin_transmit_x_char(port); return; } - if (port->xmit.head == port->xmit.tail - || info->tty->stopped - || info->tty->hw_stopped) { + if (uart_circ_empty(xmit) || uart_tx_stopped(port)) { anakin_stop_tx(port, 0); return; } anakin_transmit_buffer(port); - if (CIRC_CNT(port->xmit.head, - port->xmit.tail, - UART_XMIT_SIZE) < WAKEUP_CHARS) - uart_event(info, EVT_WRITE_WAKEUP); + if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) + uart_event(port, EVT_WRITE_WAKEUP); } static void anakin_int(int irq, void *dev_id, struct pt_regs *regs) { unsigned int status; - struct uart_info *info = dev_id; + struct uart_port *port = dev_id; - status = anakin_in(info->port, 0x1c); + status = anakin_in(port, 0x1c); if (status & RX) - anakin_rx_chars(info); + anakin_rx_chars(port); if (status & OVERRUN) - anakin_overrun_chars(info->port); + anakin_overrun_chars(port); - if (txenable[info->port->irq] && (status & TX)) - anakin_tx_chars(info); + if (txenable[port->irq] && (status & TX)) + anakin_tx_chars(port); } -static u_int +static unsigned int anakin_tx_empty(struct uart_port *port) { return anakin_in(port, 0x10) & TXEMPTY ? TIOCSER_TEMT : 0; } -static u_int +static unsigned int anakin_get_mctrl(struct uart_port *port) { unsigned int status = 0; @@ -239,7 +232,7 @@ } static void -anakin_set_mctrl(struct uart_port *port, u_int mctrl) +anakin_set_mctrl(struct uart_port *port, unsigned int mctrl) { unsigned int status; @@ -261,8 +254,10 @@ static void anakin_break_ctl(struct uart_port *port, int break_state) { + unsigned long flags; unsigned int status; + spin_lock_irqsave(&port->lock, flags); status = anakin_in(port, 0x20); if (break_state == -1) @@ -271,24 +266,22 @@ status &= ~SETBREAK; anakin_out(port, 0x20, status); + spin_unlock_irqrestore(&port->lock, flags); } -static int -anakin_startup(struct uart_port *port, struct uart_info *info) +static int anakin_startup(struct uart_port *port) { - struct uart_anakin_port *up = (struct uart_anakin_port *)port; - unsigned int read,write; int retval; + unsigned int read,write; /* * Allocate the IRQ */ - retval = request_irq(port->irq, anakin_int, SA_INTERRUPT, "serial_anakin", info); + retval = request_irq(port->irq, anakin_int, SA_INTERRUPT, + "serial_anakin", port); if (retval) return retval; - port->ops->set_mctrl(port, info->mctrl); - /* * initialise the old status of the modem signals */ @@ -302,19 +295,15 @@ write = (read & ~(RTS | DTR | BLOCKRX)) | IRQENABLE; anakin_out(port, 0x18, write); - /* Store the uart_info pointer so we can reference it in - * anakin_start_tx() */ - up->info = info; return 0; } -static void -anakin_shutdown(struct uart_port *port, struct uart_info *info) +static void anakin_shutdown(struct uart_port *port) { /* * Free the interrupt */ - free_irq(port->irq, info); + free_irq(port->irq, port); /* * disable all interrupts, disable the port @@ -323,18 +312,19 @@ } static void -anakin_change_speed(struct uart_port *port, u_int cflag, u_int iflag, u_int quot) +anakin_change_speed(struct uart_port *port, unsigned int cflag, + unsigned int iflag, unsigned int quot) { unsigned int flags; - save_flags_cli(flags); + spin_lock_irqsave(&port->lock, flags); while (!(anakin_in(port, 0x10) & TXEMPTY)); anakin_out(port, 0x10, (anakin_in(port, 0x10) & ~PRESCALER) | (quot << 3)); //parity always set to none anakin_out(port, 0x18, anakin_in(port, 0x18) & ~PARITY); - restore_flags(flags); + spin_unlock_irqrestore(&port->lock, flags); } static const char *anakin_type(struct port *port) @@ -357,51 +347,51 @@ type: anakin_type, }; -static struct uart_anakin_port anakin_ports[UART_NR] = { +static struct uart_port anakin_ports[UART_NR] = { { - port: { - base: IO_BASE + UART0, - irq: IRQ_UART0, - uartclk: 3686400, - fifosize: 0, - ops: &anakin_pops, - }, + base: IO_BASE + UART0, + irq: IRQ_UART0, + uartclk: 3686400, + fifosize: 0, + ops: &anakin_pops, + flags: ASYNC_BOOT_AUTOCONF, + line: 0, }, { - port: { - base: IO_BASE + UART1, - irq: IRQ_UART1, - uartclk: 3686400, - fifosize: 0, - ops: &anakin_pops, - }, + base: IO_BASE + UART1, + irq: IRQ_UART1, + uartclk: 3686400, + fifosize: 0, + ops: &anakin_pops, + flags: ASYNC_BOOT_AUTOCONF, + line: 1, }, { - port: { - base: IO_BASE + UART2, - irq: IRQ_UART2, - uartclk: 3686400, - fifosize: 0, - ops: &anakin_pops, - }, + base: IO_BASE + UART2, + irq: IRQ_UART2, + uartclk: 3686400, + fifosize: 0, + ops: &anakin_pops, + flags: ASYNC_BOOT_AUTOCONF, + line: 2, }, { - port: { - base: IO_BASE + UART3, - irq: IRQ_UART3, - uartclk: 3686400, - fifosize: 0, - ops: &anakin_pops, - }, + base: IO_BASE + UART3, + irq: IRQ_UART3, + uartclk: 3686400, + fifosize: 0, + ops: &anakin_pops, + flags: ASYNC_BOOT_AUTOCONF, + line: 3, }, { - port: { - base: IO_BASE + UART4, - irq: IRQ_UART4, - uartclk: 3686400, - fifosize: 0, - ops: &anakin_pops, - }, + base: IO_BASE + UART4, + irq: IRQ_UART4, + uartclk: 3686400, + fifosize: 0, + ops: &anakin_pops, + flags: ASYNC_BOOT_AUTOCONF, + line: 4, }, }; @@ -409,18 +399,18 @@ #ifdef CONFIG_SERIAL_ANAKIN_CONSOLE static void -anakin_console_write(struct console *co, const char *s, u_int count) +anakin_console_write(struct console *co, const char *s, unsigned int count) { - struct uart_port *port = &anakin_ports[co->index].port; + struct uart_port *port = &anakin_ports[co->index]; unsigned int flags, status, i; /* * First save the status then disable the interrupts */ - save_flags_cli(flags); + local_irq_save(flags); status = anakin_in(port, 0x18); anakin_out(port, 0x18, status & ~IRQENABLE); - restore_flags(flags); + local_irq_restore(flags); /* * Now, do each character @@ -450,38 +440,16 @@ while (!(anakin_in(port, 0x10) & TXEMPTY)); if (status & IRQENABLE) { - save_flags_cli(flags); + local_irq_save(flags); anakin_out(port, 0x18, anakin_in(port, 0x18) | IRQENABLE); - restore_flags(flags); + local_irq_restore(flags); } } static kdev_t anakin_console_device(struct console *co) { - return MKDEV(SERIAL_ANAKIN_MAJOR, SERIAL_ANAKIN_MINOR + co->index); -} - -static int -anakin_console_wait_key(struct console *co) -{ - struct uart_port *port = &anakin_ports[co->index].port; - unsigned int flags, status, ch; - - save_flags_cli(flags); - status = anakin_in(port, 0x18); - anakin_out(port, 0x18, status & ~IRQENABLE); - restore_flags(flags); - - while (!(anakin_in(port, 0x10) & RXRELEASE)); - ch = anakin_in(port, 0x14); - - if (status & IRQENABLE) { - save_flags_cli(flags); - anakin_out(port, 0x18, anakin_in(port, 0x18) | IRQENABLE); - restore_flags(flags); - } - return ch; + return mk_kdev(SERIAL_ANAKIN_MAJOR, SERIAL_ANAKIN_MINOR + co->index); } /* @@ -515,13 +483,9 @@ * if so, search for the first available port that does have * console support. */ -#if 0 - port = uart_get_console(anakin_ports, UART_NR, co); -#else if (co->index >= UART_NR) co->index = 0; - port = &anakin_ports[co->index].port; -#endif + port = &anakin_ports[co->index]; if (options) uart_parse_options(options, &baud, &parity, &bits); @@ -535,7 +499,6 @@ name: SERIAL_ANAKIN_NAME, write: anakin_console_write, device: anakin_console_device, - wait_key: anakin_console_wait_key, setup: anakin_console_setup, flags: CON_PRINTBUFFER, index: -1, @@ -553,6 +516,7 @@ #endif static struct uart_register anakin_reg = { + driver_name: SERIAL_ANAKIN_NAME, normal_major: SERIAL_ANAKIN_MAJOR, normal_name: SERIAL_ANAKIN_NAME, normal_driver: &normal, @@ -574,7 +538,7 @@ int i; for (i = 0; i < UART_NR; i++) - uart_add_one_port(&anakin_reg, &anakin_ports[i].port); + uart_add_one_port(&anakin_reg, &anakin_ports[i]); } return ret; } Index: serial_clps711x.c =================================================================== RCS file: /cvsroot/linuxconsole/ruby/linux/drivers/serial/serial_clps711x.c,v retrieving revision 1.12 retrieving revision 1.13 diff -u -d -r1.12 -r1.13 --- serial_clps711x.c 25 Dec 2001 06:50:51 -0000 1.12 +++ serial_clps711x.c 14 Mar 2002 20:02:07 -0000 1.13 @@ -53,6 +53,10 @@ #include <asm/system.h> #include <asm/uaccess.h> +#if defined(CONFIG_SERIAL_CLPS711X_CONSOLE) && defined(CONFIG_MAGIC_SYSRQ) +#define SUPPORT_SYSRQ +#endif + #include <linux/serial_core.h> #include <asm/hardware/clps7111.h> @@ -61,12 +65,12 @@ #define SERIAL_CLPS711X_NAME "ttyCL" #define SERIAL_CLPS711X_MAJOR 204 -#define SERIAL_CLPS711X_MINOR 40 +#define SERIAL_CLPS711X_MINOR 40 #define SERIAL_CLPS711X_NR UART_NR #define CALLOUT_CLPS711X_NAME "cuacl" #define CALLOUT_CLPS711X_MAJOR 205 -#define CALLOUT_CLPS711X_MINOR 40 +#define CALLOUT_CLPS711X_MINOR 40 #define CALLOUT_CLPS711X_NR UART_NR static struct tty_driver normal, callout; @@ -84,15 +88,16 @@ #define UART_ANY_ERR (UARTDR_FRMERR | UARTDR_PARERR | UARTDR_OVERR) -static void clps711xuart_stop_tx(struct uart_port *port, u_int from_tty) +static void +clps711xuart_stop_tx(struct uart_port *port, unsigned int tty_stop) { disable_irq(TX_IRQ(port)); } -static void clps711xuart_start_tx(struct uart_port *port, u_int nonempty, u_int from_tty) +static void +clps711xuart_start_tx(struct uart_port *port, unsigned int tty_start) { - if (nonempty) - enable_irq(TX_IRQ(port)); + enable_irq(TX_IRQ(port)); } static void clps711xuart_stop_rx(struct uart_port *port) @@ -104,41 +109,11 @@ { } -#if 0 -static void ambauart_modem_status(struct uart_info *info) -{ - unsigned int status, delta; - struct uart_icount *icount = &info->port->icount; - - UART_PUT_ICR(info->port, 0); - - status = UART_GET_FR(info->port) & AMBA_UARTFR_MODEM_ANY; - - delta = status ^ info->port->old_status; - info->port->old_status = status; - - if (!delta) - return; - - if (delta & AMBA_UARTFR_DCD) - uart_handle_dcd_change(info, status & AMBA_UARTFR_DCD); - - if (delta & AMBA_UARTFR_DSR) - icount->dsr++; - - if (delta & AMBA_UARTFR_CTS) - uart_handle_cts_change(info, status & AMBA_UARTFR_CTS); - - wake_up_interruptible(&info->delta_msr_wait); -} -#endif - static void clps711xuart_int_rx(int irq, void *dev_id, struct pt_regs *regs) { - struct uart_info *info = dev_id; - struct tty_struct *tty = info->tty; + struct uart_port *port = dev_id; + struct tty_struct *tty = port->info->tty; unsigned int status, ch, flg, ignored = 0; - struct uart_port *port = info->port; status = clps_readl(SYSFLG(port)); while (!(status & SYSFLG_URXFE)) { @@ -157,7 +132,7 @@ if (ch & UART_ANY_ERR) goto handle_error; - if (uart_handle_sysrq_char(info, ch, regs)) + if (uart_handle_sysrq_char(port, ch, regs)) goto ignore_char; error_return: @@ -167,11 +142,11 @@ ignore_char: status = clps_readl(SYSFLG(port)); } -out: + out: tty_flip_buffer_push(tty); return; -handle_error: + handle_error: if (ch & UARTDR_PARERR) port->icount.parity++; else if (ch & UARTDR_FRMERR) @@ -205,15 +180,15 @@ flg = TTY_OVERRUN; } #ifdef SUPPORT_SYSRQ - info->sysrq = 0; + port->sysrq = 0; #endif goto error_return; } static void clps711xuart_int_tx(int irq, void *dev_id, struct pt_regs *regs) { - struct uart_info *info = dev_id; - struct uart_port *port = info->port; + struct uart_port *port = dev_id; + struct circ_buf *xmit = &port->info->xmit; int count; if (port->x_char) { @@ -222,38 +197,34 @@ port->x_char = 0; return; } - if (port->xmit.head == port->xmit.tail - || info->tty->stopped - || info->tty->hw_stopped) { + if (uart_circ_empty(xmit) || uart_tx_stopped(port)) { clps711xuart_stop_tx(port, 0); return; } count = port->fifosize >> 1; do { - clps_writel(port->xmit.buf[port->xmit.tail], UARTDR(port)); - port->xmit.tail = (port->xmit.tail + 1) & (UART_XMIT_SIZE - 1); + clps_writel(xmit->buf[xmit->tail], UARTDR(port)); + xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE - 1); port->icount.tx++; - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) break; } while (--count > 0); - if (CIRC_CNT(port->xmit.head, - port->xmit.tail, - UART_XMIT_SIZE) < WAKEUP_CHARS) - uart_event(info, EVT_WRITE_WAKEUP); + if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) + uart_event(port, EVT_WRITE_WAKEUP); - if (port->xmit.head == port->xmit.tail) + if (uart_circ_empty(xmit)) clps711xuart_stop_tx(port, 0); } -static u_int clps711xuart_tx_empty(struct uart_port *port) +static unsigned int clps711xuart_tx_empty(struct uart_port *port) { - u_int status = clps_readl(SYSFLG(port)); + unsigned int status = clps_readl(SYSFLG(port)); return status & SYSFLG_UBUSY ? 0 : TIOCSER_TEMT; } -static u_int clps711xuart_get_mctrl(struct uart_port *port) +static unsigned int clps711xuart_get_mctrl(struct uart_port *port) { unsigned int port_addr; unsigned int result = 0; @@ -273,44 +244,46 @@ return result; } -static void clps711xuart_set_mctrl_null(struct uart_port *port, u_int mctrl) +static void +clps711xuart_set_mctrl_null(struct uart_port *port, unsigned int mctrl) { } static void clps711xuart_break_ctl(struct uart_port *port, int break_state) { + unsigned long flags; unsigned int ubrlcr; + spin_lock_irqsave(&port->lock, flags); ubrlcr = clps_readl(UBRLCR(port)); if (break_state == -1) ubrlcr |= UBRLCR_BREAK; else ubrlcr &= ~UBRLCR_BREAK; clps_writel(ubrlcr, UBRLCR(port)); + spin_unlock_irqrestore(&port->lock, flags); } -static int clps711xuart_startup(struct uart_port *port, struct uart_info *info) +static int clps711xuart_startup(struct uart_port *port) { - u_int syscon; + unsigned int syscon; int retval; /* * Allocate the IRQs */ retval = request_irq(TX_IRQ(port), clps711xuart_int_tx, 0, - "clps711xuart_tx", info); + "clps711xuart_tx", port); if (retval) return retval; retval = request_irq(RX_IRQ(port), clps711xuart_int_rx, 0, - "clps711xuart_rx", info); + "clps711xuart_rx", port); if (retval) { - free_irq(TX_IRQ(port), info); + free_irq(TX_IRQ(port), port); return retval; } - port->ops->set_mctrl(port, info->mctrl); - /* * enable the port */ @@ -321,15 +294,15 @@ return 0; } -static void clps711xuart_shutdown(struct uart_port *port, struct uart_info *info) +static void clps711xuart_shutdown(struct uart_port *port) { - u_int ubrlcr, syscon; + unsigned int ubrlcr, syscon; /* * Free the interrupt */ - free_irq(TX_IRQ(port), info); /* TX interrupt */ - free_irq(RX_IRQ(port), info); /* RX interrupt */ + free_irq(TX_IRQ(port), port); /* TX interrupt */ + free_irq(RX_IRQ(port), port); /* RX interrupt */ /* * disable the port @@ -346,21 +319,27 @@ clps_writel(ubrlcr, UBRLCR(port)); } -static void clps711xuart_change_speed(struct uart_port *port, u_int cflag, u_int iflag, u_int quot) +static void +clps711xuart_change_speed(struct uart_port *port, unsigned int cflag, + unsigned int iflag, unsigned int quot) { - u_int ubrlcr; + unsigned int ubrlcr; unsigned long flags; -#if DEBUG - printk("clps711xuart_change_speed(cflag=0x%x, iflag=0x%x, quot=%d) called\n", - cflag, iflag, quot); -#endif /* byte size and parity */ switch (cflag & CSIZE) { - case CS5: ubrlcr = UBRLCR_WRDLEN5; break; - case CS6: ubrlcr = UBRLCR_... [truncated message content] |