VMware Balloon driver
[safe/jmp/linux-2.6] / drivers / serial / 8250.c
index 83168a6..2b1ea3d 100644 (file)
@@ -38,6 +38,7 @@
 #include <linux/serial_8250.h>
 #include <linux/nmi.h>
 #include <linux/mutex.h>
+#include <linux/slab.h>
 
 #include <asm/io.h>
 #include <asm/irq.h>
@@ -64,6 +65,8 @@ static int serial_index(struct uart_port *port)
        return (serial8250_reg.minor - 64) + port->line;
 }
 
+static unsigned int skip_txen_test; /* force skip of txen test at init time */
+
 /*
  * Debugging.
  */
@@ -81,6 +84,9 @@ static int serial_index(struct uart_port *port)
 
 #define PASS_LIMIT     256
 
+#define BOTH_EMPTY     (UART_LSR_TEMT | UART_LSR_THRE)
+
+
 /*
  * We default to IRQ0 for the "no irq" hack.   Some
  * machine types want others as well - they're free
@@ -1087,7 +1093,7 @@ static void autoconfig(struct uart_8250_port *up, unsigned int probeflags)
        if (!up->port.iobase && !up->port.mapbase && !up->port.membase)
                return;
 
-       DEBUG_AUTOCONF("ttyS%d: autoconf (0x%04x, 0x%p): ",
+       DEBUG_AUTOCONF("ttyS%d: autoconf (0x%04lx, 0x%p): ",
                       serial_index(&up->port), up->port.iobase, up->port.membase);
 
        /*
@@ -1212,12 +1218,6 @@ static void autoconfig(struct uart_8250_port *up, unsigned int probeflags)
        }
 #endif
 
-#ifdef CONFIG_SERIAL_8250_AU1X00
-       /* if access method is AU, it is a 16550 with a quirk */
-       if (up->port.type == PORT_16550A && up->port.iotype == UPIO_AU)
-               up->bugs |= UART_BUG_NOMSR;
-#endif
-
        serial_outp(up, UART_LCR, save_lcr);
 
        if (up->capabilities != uart_config[up->port.type].flags) {
@@ -1337,14 +1337,12 @@ static void serial8250_start_tx(struct uart_port *port)
                serial_out(up, UART_IER, up->ier);
 
                if (up->bugs & UART_BUG_TXEN) {
-                       unsigned char lsr, iir;
+                       unsigned char lsr;
                        lsr = serial_in(up, UART_LSR);
                        up->lsr_saved_flags |= lsr & LSR_SAVE_FLAGS;
-                       iir = serial_in(up, UART_IIR) & 0x0f;
                        if ((up->port.type == PORT_RM9000) ?
-                               (lsr & UART_LSR_THRE &&
-                               (iir == UART_IIR_NO_INT || iir == UART_IIR_THRI)) :
-                               (lsr & UART_LSR_TEMT && iir & UART_IIR_NO_INT))
+                               (lsr & UART_LSR_THRE) :
+                               (lsr & UART_LSR_TEMT))
                                transmit_chars(up);
                }
        }
@@ -1382,7 +1380,7 @@ static void serial8250_enable_ms(struct uart_port *port)
 static void
 receive_chars(struct uart_8250_port *up, unsigned int *status)
 {
-       struct tty_struct *tty = up->port.info->port.tty;
+       struct tty_struct *tty = up->port.state->port.tty;
        unsigned char ch, lsr = *status;
        int max_count = 256;
        char flag;
@@ -1457,7 +1455,7 @@ ignore_char:
 
 static void transmit_chars(struct uart_8250_port *up)
 {
-       struct circ_buf *xmit = &up->port.info->xmit;
+       struct circ_buf *xmit = &up->port.state->xmit;
        int count;
 
        if (up->port.x_char) {
@@ -1500,7 +1498,7 @@ static unsigned int check_modem_status(struct uart_8250_port *up)
        status |= up->msr_saved_flags;
        up->msr_saved_flags = 0;
        if (status & UART_MSR_ANY_DELTA && up->ier & UART_IER_MSI &&
-           up->port.info != NULL) {
+           up->port.state != NULL) {
                if (status & UART_MSR_TERI)
                        up->port.icount.rng++;
                if (status & UART_MSR_DDSR)
@@ -1510,7 +1508,7 @@ static unsigned int check_modem_status(struct uart_8250_port *up)
                if (status & UART_MSR_DCTS)
                        uart_handle_cts_change(&up->port, status & UART_MSR_CTS);
 
-               wake_up_interruptible(&up->port.info->delta_msr_wait);
+               wake_up_interruptible(&up->port.state->port.delta_msr_wait);
        }
 
        return status;
@@ -1764,7 +1762,7 @@ static void serial8250_backup_timeout(unsigned long data)
        up->lsr_saved_flags |= lsr & LSR_SAVE_FLAGS;
        spin_unlock_irqrestore(&up->port.lock, flags);
        if ((iir & UART_IIR_NO_INT) && (up->ier & UART_IER_THRI) &&
-           (!uart_circ_empty(&up->port.info->xmit) || up->port.x_char) &&
+           (!uart_circ_empty(&up->port.state->xmit) || up->port.x_char) &&
            (lsr & UART_LSR_THRE)) {
                iir &= ~(UART_IIR_ID | UART_IIR_NO_INT);
                iir |= UART_IIR_THRI;
@@ -1792,7 +1790,7 @@ static unsigned int serial8250_tx_empty(struct uart_port *port)
        up->lsr_saved_flags |= lsr & LSR_SAVE_FLAGS;
        spin_unlock_irqrestore(&up->port.lock, flags);
 
-       return lsr & UART_LSR_TEMT ? TIOCSER_TEMT : 0;
+       return (lsr & BOTH_EMPTY) == BOTH_EMPTY ? TIOCSER_TEMT : 0;
 }
 
 static unsigned int serial8250_get_mctrl(struct uart_port *port)
@@ -1850,8 +1848,6 @@ static void serial8250_break_ctl(struct uart_port *port, int break_state)
        spin_unlock_irqrestore(&up->port.lock, flags);
 }
 
-#define BOTH_EMPTY (UART_LSR_TEMT | UART_LSR_THRE)
-
 /*
  *     Wait for transmitter & holding register to empty
  */
@@ -2108,7 +2104,7 @@ static int serial8250_startup(struct uart_port *port)
           is variable. So, let's just don't test if we receive
           TX irq. This way, we'll never enable UART_BUG_TXEN.
         */
-       if (up->port.flags & UPF_NO_TXEN_TEST)
+       if (skip_txen_test || up->port.flags & UPF_NO_TXEN_TEST)
                goto dont_test_tx_en;
 
        /*
@@ -2272,7 +2268,9 @@ serial8250_set_termios(struct uart_port *port, struct ktermios *termios,
        /*
         * Ask the core to calculate the divisor for us.
         */
-       baud = uart_get_baud_rate(port, termios, old, 0, port->uartclk/16);
+       baud = uart_get_baud_rate(port, termios, old,
+                                 port->uartclk / 16 / 0xffff,
+                                 port->uartclk / 16);
        quot = serial8250_get_divisor(port, baud);
 
        /*
@@ -2411,6 +2409,21 @@ serial8250_set_termios(struct uart_port *port, struct ktermios *termios,
 }
 
 static void
+serial8250_set_ldisc(struct uart_port *port)
+{
+       int line = port->line;
+
+       if (line >= port->state->port.tty->driver->num)
+               return;
+
+       if (port->state->port.tty->ldisc->ops->num == N_PPS) {
+               port->flags |= UPF_HARDPPS_CD;
+               serial8250_enable_ms(port);
+       } else
+               port->flags &= ~UPF_HARDPPS_CD;
+}
+
+static void
 serial8250_pm(struct uart_port *port, unsigned int state,
              unsigned int oldstate)
 {
@@ -2425,7 +2438,7 @@ serial8250_pm(struct uart_port *port, unsigned int state,
 static unsigned int serial8250_port_size(struct uart_8250_port *pt)
 {
        if (pt->port.iotype == UPIO_AU)
-               return 0x100000;
+               return 0x1000;
 #ifdef CONFIG_ARCH_OMAP
        if (is_omap_port(pt))
                return 0x16 << pt->port.regshift;
@@ -2582,6 +2595,13 @@ static void serial8250_config_port(struct uart_port *port, int flags)
 
        if (flags & UART_CONFIG_TYPE)
                autoconfig(up, probeflags);
+
+#ifdef CONFIG_SERIAL_8250_AU1X00
+       /* if access method is AU, it is a 16550 with a quirk */
+       if (up->port.type == PORT_16550A && up->port.iotype == UPIO_AU)
+               up->bugs |= UART_BUG_NOMSR;
+#endif
+
        if (up->port.type != PORT_UNKNOWN && flags & UART_CONFIG_IRQ)
                autoconfig_irq(up);
 
@@ -2624,6 +2644,7 @@ static struct uart_ops serial8250_pops = {
        .startup        = serial8250_startup,
        .shutdown       = serial8250_shutdown,
        .set_termios    = serial8250_set_termios,
+       .set_ldisc      = serial8250_set_ldisc,
        .pm             = serial8250_pm,
        .type           = serial8250_type,
        .release_port   = serial8250_release_port,
@@ -2642,7 +2663,7 @@ static void __init serial8250_isa_init_ports(void)
 {
        struct uart_8250_port *up;
        static int first = 1;
-       int i;
+       int i, irqflag = 0;
 
        if (!first)
                return;
@@ -2666,6 +2687,9 @@ static void __init serial8250_isa_init_ports(void)
                up->port.ops = &serial8250_pops;
        }
 
+       if (share_irqs)
+               irqflag = IRQF_SHARED;
+
        for (i = 0, up = serial8250_ports;
             i < ARRAY_SIZE(old_serial_port) && i < nr_uarts;
             i++, up++) {
@@ -2679,11 +2703,19 @@ static void __init serial8250_isa_init_ports(void)
                up->port.iotype   = old_serial_port[i].io_type;
                up->port.regshift = old_serial_port[i].iomem_reg_shift;
                set_io_from_upio(&up->port);
-               if (share_irqs)
-                       up->port.irqflags |= IRQF_SHARED;
+               up->port.irqflags |= irqflag;
        }
 }
 
+static void
+serial8250_init_fixed_type_port(struct uart_8250_port *up, unsigned int type)
+{
+       up->port.type = type;
+       up->port.fifosize = uart_config[type].fifo_size;
+       up->capabilities = uart_config[type].flags;
+       up->tx_loadsz = uart_config[type].tx_loadsz;
+}
+
 static void __init
 serial8250_register_ports(struct uart_driver *drv, struct device *dev)
 {
@@ -2700,6 +2732,10 @@ serial8250_register_ports(struct uart_driver *drv, struct device *dev)
                struct uart_8250_port *up = &serial8250_ports[i];
 
                up->port.dev = dev;
+
+               if (up->port.flags & UPF_FIXED_TYPE)
+                       serial8250_init_fixed_type_port(up, up->port.type);
+
                uart_add_one_port(drv, &up->port);
        }
 }
@@ -2936,10 +2972,13 @@ static int __devinit serial8250_probe(struct platform_device *dev)
 {
        struct plat_serial8250_port *p = dev->dev.platform_data;
        struct uart_port port;
-       int ret, i;
+       int ret, i, irqflag = 0;
 
        memset(&port, 0, sizeof(struct uart_port));
 
+       if (share_irqs)
+               irqflag = IRQF_SHARED;
+
        for (i = 0; p && p->flags != 0; p++, i++) {
                port.iobase             = p->iobase;
                port.membase            = p->membase;
@@ -2956,8 +2995,7 @@ static int __devinit serial8250_probe(struct platform_device *dev)
                port.serial_in          = p->serial_in;
                port.serial_out         = p->serial_out;
                port.dev                = &dev->dev;
-               if (share_irqs)
-                       port.irqflags |= IRQF_SHARED;
+               port.irqflags           |= irqflag;
                ret = serial8250_register_port(&port);
                if (ret < 0) {
                        dev_err(&dev->dev, "unable to register port at index %d "
@@ -3110,12 +3148,8 @@ int serial8250_register_port(struct uart_port *port)
                if (port->dev)
                        uart->port.dev = port->dev;
 
-               if (port->flags & UPF_FIXED_TYPE) {
-                       uart->port.type = port->type;
-                       uart->port.fifosize = uart_config[port->type].fifo_size;
-                       uart->capabilities = uart_config[port->type].flags;
-                       uart->tx_loadsz = uart_config[port->type].tx_loadsz;
-               }
+               if (port->flags & UPF_FIXED_TYPE)
+                       serial8250_init_fixed_type_port(uart, port->type);
 
                set_io_from_upio(&uart->port);
                /* Possibly override default I/O functions.  */
@@ -3246,6 +3280,9 @@ MODULE_PARM_DESC(share_irqs, "Share IRQs with other non-8250/16x50 devices"
 module_param(nr_uarts, uint, 0644);
 MODULE_PARM_DESC(nr_uarts, "Maximum number of UARTs supported. (1-" __MODULE_STRING(CONFIG_SERIAL_8250_NR_UARTS) ")");
 
+module_param(skip_txen_test, uint, 0644);
+MODULE_PARM_DESC(skip_txen_test, "Skip checking for the TXEN bug at init time");
+
 #ifdef CONFIG_SERIAL_8250_RSA
 module_param_array(probe_rsa, ulong, &probe_rsa_count, 0444);
 MODULE_PARM_DESC(probe_rsa, "Probe I/O ports for RSA");