diff options
| author | Dick Hollenbeck <dick@softplc.com> | 2008-09-16 13:30:27 -0400 |
|---|---|---|
| committer | Russell King <rmk+kernel@arm.linux.org.uk> | 2008-10-01 17:41:43 -0400 |
| commit | 457cd4f5e3011da47f2f76e2bdc545ffcc1189db (patch) | |
| tree | 87a79c37683f112708df66c6507e0c65952c490f | |
| parent | b8e6c91c74e9f0279b7c51048779b3d62da60b88 (diff) | |
[ARM] 5250/1: unbalanced enable_irq() for serial_ks8695.c fix
The function ks8695uart_set_termios() would cause an unbalanced
enable_irq() generated message to be printk()ed. This is because
there was no book keeping support to remember if the calls to
enable_irq() and disable_irq() were balanced for the modem
control irq.
Signed-off-by: Dick Hollenbeck <dick@softplc.com>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
| -rw-r--r-- | drivers/serial/serial_ks8695.c | 61 |
1 files changed, 52 insertions, 9 deletions
diff --git a/drivers/serial/serial_ks8695.c b/drivers/serial/serial_ks8695.c index b9cbfc87f616..998e89dc5aaf 100644 --- a/drivers/serial/serial_ks8695.c +++ b/drivers/serial/serial_ks8695.c | |||
| @@ -63,8 +63,44 @@ | |||
| 63 | #define UART_DUMMY_LSR_RX 0x100 | 63 | #define UART_DUMMY_LSR_RX 0x100 |
| 64 | #define UART_PORT_SIZE (KS8695_USR - KS8695_URRB + 4) | 64 | #define UART_PORT_SIZE (KS8695_USR - KS8695_URRB + 4) |
| 65 | 65 | ||
| 66 | #define tx_enabled(port) ((port)->unused[0]) | 66 | static inline int tx_enabled(struct uart_port *port) |
| 67 | #define rx_enabled(port) ((port)->unused[1]) | 67 | { |
| 68 | return port->unused[0] & 1; | ||
| 69 | } | ||
| 70 | |||
| 71 | static inline int rx_enabled(struct uart_port *port) | ||
| 72 | { | ||
| 73 | return port->unused[0] & 2; | ||
| 74 | } | ||
| 75 | |||
| 76 | static inline int ms_enabled(struct uart_port *port) | ||
| 77 | { | ||
| 78 | return port->unused[0] & 4; | ||
| 79 | } | ||
| 80 | |||
| 81 | static inline void ms_enable(struct uart_port *port, int enabled) | ||
| 82 | { | ||
| 83 | if(enabled) | ||
| 84 | port->unused[0] |= 4; | ||
| 85 | else | ||
| 86 | port->unused[0] &= ~4; | ||
| 87 | } | ||
| 88 | |||
| 89 | static inline void rx_enable(struct uart_port *port, int enabled) | ||
| 90 | { | ||
| 91 | if(enabled) | ||
| 92 | port->unused[0] |= 2; | ||
| 93 | else | ||
| 94 | port->unused[0] &= ~2; | ||
| 95 | } | ||
| 96 | |||
| 97 | static inline void tx_enable(struct uart_port *port, int enabled) | ||
| 98 | { | ||
| 99 | if(enabled) | ||
| 100 | port->unused[0] |= 1; | ||
| 101 | else | ||
| 102 | port->unused[0] &= ~1; | ||
| 103 | } | ||
| 68 | 104 | ||
| 69 | 105 | ||
| 70 | #ifdef SUPPORT_SYSRQ | 106 | #ifdef SUPPORT_SYSRQ |
| @@ -75,7 +111,7 @@ static void ks8695uart_stop_tx(struct uart_port *port) | |||
| 75 | { | 111 | { |
| 76 | if (tx_enabled(port)) { | 112 | if (tx_enabled(port)) { |
| 77 | disable_irq(KS8695_IRQ_UART_TX); | 113 | disable_irq(KS8695_IRQ_UART_TX); |
| 78 | tx_enabled(port) = 0; | 114 | tx_enable(port, 0); |
| 79 | } | 115 | } |
| 80 | } | 116 | } |
| 81 | 117 | ||
| @@ -83,7 +119,7 @@ static void ks8695uart_start_tx(struct uart_port *port) | |||
| 83 | { | 119 | { |
| 84 | if (!tx_enabled(port)) { | 120 | if (!tx_enabled(port)) { |
| 85 | enable_irq(KS8695_IRQ_UART_TX); | 121 | enable_irq(KS8695_IRQ_UART_TX); |
| 86 | tx_enabled(port) = 1; | 122 | tx_enable(port, 1); |
| 87 | } | 123 | } |
| 88 | } | 124 | } |
| 89 | 125 | ||
| @@ -91,18 +127,24 @@ static void ks8695uart_stop_rx(struct uart_port *port) | |||
| 91 | { | 127 | { |
| 92 | if (rx_enabled(port)) { | 128 | if (rx_enabled(port)) { |
| 93 | disable_irq(KS8695_IRQ_UART_RX); | 129 | disable_irq(KS8695_IRQ_UART_RX); |
| 94 | rx_enabled(port) = 0; | 130 | rx_enable(port, 0); |
| 95 | } | 131 | } |
| 96 | } | 132 | } |
| 97 | 133 | ||
| 98 | static void ks8695uart_enable_ms(struct uart_port *port) | 134 | static void ks8695uart_enable_ms(struct uart_port *port) |
| 99 | { | 135 | { |
| 100 | enable_irq(KS8695_IRQ_UART_MODEM_STATUS); | 136 | if (!ms_enabled(port)) { |
| 137 | enable_irq(KS8695_IRQ_UART_MODEM_STATUS); | ||
| 138 | ms_enable(port,1); | ||
| 139 | } | ||
| 101 | } | 140 | } |
| 102 | 141 | ||
| 103 | static void ks8695uart_disable_ms(struct uart_port *port) | 142 | static void ks8695uart_disable_ms(struct uart_port *port) |
| 104 | { | 143 | { |
| 105 | disable_irq(KS8695_IRQ_UART_MODEM_STATUS); | 144 | if (ms_enabled(port)) { |
| 145 | disable_irq(KS8695_IRQ_UART_MODEM_STATUS); | ||
| 146 | ms_enable(port,0); | ||
| 147 | } | ||
| 106 | } | 148 | } |
| 107 | 149 | ||
| 108 | static irqreturn_t ks8695uart_rx_chars(int irq, void *dev_id) | 150 | static irqreturn_t ks8695uart_rx_chars(int irq, void *dev_id) |
| @@ -285,8 +327,9 @@ static int ks8695uart_startup(struct uart_port *port) | |||
| 285 | int retval; | 327 | int retval; |
| 286 | 328 | ||
| 287 | set_irq_flags(KS8695_IRQ_UART_TX, IRQF_VALID | IRQF_NOAUTOEN); | 329 | set_irq_flags(KS8695_IRQ_UART_TX, IRQF_VALID | IRQF_NOAUTOEN); |
| 288 | tx_enabled(port) = 0; | 330 | tx_enable(port, 0); |
| 289 | rx_enabled(port) = 1; | 331 | rx_enable(port, 1); |
| 332 | ms_enable(port, 1); | ||
| 290 | 333 | ||
| 291 | /* | 334 | /* |
| 292 | * Allocate the IRQ | 335 | * Allocate the IRQ |
