diff options
author | Alan Cox <alan@linux.intel.com> | 2009-11-30 08:17:51 -0500 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-12-11 18:18:07 -0500 |
commit | f176178ba09d27cc33988435e2c9fe078b44998c (patch) | |
tree | d0c74d464e7c1a7b0b191b75ac28790cf5503626 /drivers/char/moxa.c | |
parent | 2493c0c166565e36831196446af594eb07892daf (diff) |
tty: moxa: Use more tty_port ops
Rework a few bits of this into tty_port format
Signed-off-by: Alan Cox <alan@linux.intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/char/moxa.c')
-rw-r--r-- | drivers/char/moxa.c | 137 |
1 files changed, 21 insertions, 116 deletions
diff --git a/drivers/char/moxa.c b/drivers/char/moxa.c index dd0083bbb64a..d8bcbed6d28d 100644 --- a/drivers/char/moxa.c +++ b/drivers/char/moxa.c | |||
@@ -206,8 +206,9 @@ static int moxa_tiocmset(struct tty_struct *tty, struct file *file, | |||
206 | static void moxa_poll(unsigned long); | 206 | static void moxa_poll(unsigned long); |
207 | static void moxa_set_tty_param(struct tty_struct *, struct ktermios *); | 207 | static void moxa_set_tty_param(struct tty_struct *, struct ktermios *); |
208 | static void moxa_setup_empty_event(struct tty_struct *); | 208 | static void moxa_setup_empty_event(struct tty_struct *); |
209 | static void moxa_shut_down(struct tty_struct *); | 209 | static void moxa_shutdown(struct tty_port *); |
210 | static int moxa_carrier_raised(struct tty_port *); | 210 | static int moxa_carrier_raised(struct tty_port *); |
211 | static void moxa_dtr_rts(struct tty_port *, int); | ||
211 | /* | 212 | /* |
212 | * moxa board interface functions: | 213 | * moxa board interface functions: |
213 | */ | 214 | */ |
@@ -409,6 +410,8 @@ static const struct tty_operations moxa_ops = { | |||
409 | 410 | ||
410 | static const struct tty_port_operations moxa_port_ops = { | 411 | static const struct tty_port_operations moxa_port_ops = { |
411 | .carrier_raised = moxa_carrier_raised, | 412 | .carrier_raised = moxa_carrier_raised, |
413 | .dtr_rts = moxa_dtr_rts, | ||
414 | .shutdown = moxa_shutdown, | ||
412 | }; | 415 | }; |
413 | 416 | ||
414 | static struct tty_driver *moxaDriver; | 417 | static struct tty_driver *moxaDriver; |
@@ -1112,14 +1115,12 @@ static void __exit moxa_exit(void) | |||
1112 | module_init(moxa_init); | 1115 | module_init(moxa_init); |
1113 | module_exit(moxa_exit); | 1116 | module_exit(moxa_exit); |
1114 | 1117 | ||
1115 | static void moxa_close_port(struct tty_struct *tty) | 1118 | static void moxa_shutdown(struct tty_port *port) |
1116 | { | 1119 | { |
1117 | struct moxa_port *ch = tty->driver_data; | 1120 | struct moxa_port *ch = container_of(port, struct moxa_port, port); |
1118 | moxa_shut_down(tty); | 1121 | MoxaPortDisable(ch); |
1119 | MoxaPortFlushData(ch, 2); | 1122 | MoxaPortFlushData(ch, 2); |
1120 | ch->port.flags &= ~ASYNC_NORMAL_ACTIVE; | 1123 | clear_bit(ASYNCB_NORMAL_ACTIVE, &port->flags); |
1121 | tty->driver_data = NULL; | ||
1122 | tty_port_tty_set(&ch->port, NULL); | ||
1123 | } | 1124 | } |
1124 | 1125 | ||
1125 | static int moxa_carrier_raised(struct tty_port *port) | 1126 | static int moxa_carrier_raised(struct tty_port *port) |
@@ -1133,39 +1134,13 @@ static int moxa_carrier_raised(struct tty_port *port) | |||
1133 | return dcd; | 1134 | return dcd; |
1134 | } | 1135 | } |
1135 | 1136 | ||
1136 | static int moxa_block_till_ready(struct tty_struct *tty, struct file *filp, | 1137 | static void moxa_dtr_rts(struct tty_port *port, int onoff) |
1137 | struct moxa_port *ch) | ||
1138 | { | 1138 | { |
1139 | struct tty_port *port = &ch->port; | 1139 | struct moxa_port *ch = container_of(port, struct moxa_port, port); |
1140 | DEFINE_WAIT(wait); | 1140 | MoxaPortLineCtrl(ch, onoff, onoff); |
1141 | int retval = 0; | ||
1142 | u8 dcd; | ||
1143 | |||
1144 | while (1) { | ||
1145 | prepare_to_wait(&port->open_wait, &wait, TASK_INTERRUPTIBLE); | ||
1146 | if (tty_hung_up_p(filp)) { | ||
1147 | #ifdef SERIAL_DO_RESTART | ||
1148 | retval = -ERESTARTSYS; | ||
1149 | #else | ||
1150 | retval = -EAGAIN; | ||
1151 | #endif | ||
1152 | break; | ||
1153 | } | ||
1154 | dcd = tty_port_carrier_raised(port); | ||
1155 | if (dcd) | ||
1156 | break; | ||
1157 | |||
1158 | if (signal_pending(current)) { | ||
1159 | retval = -ERESTARTSYS; | ||
1160 | break; | ||
1161 | } | ||
1162 | schedule(); | ||
1163 | } | ||
1164 | finish_wait(&port->open_wait, &wait); | ||
1165 | |||
1166 | return retval; | ||
1167 | } | 1141 | } |
1168 | 1142 | ||
1143 | |||
1169 | static int moxa_open(struct tty_struct *tty, struct file *filp) | 1144 | static int moxa_open(struct tty_struct *tty, struct file *filp) |
1170 | { | 1145 | { |
1171 | struct moxa_board_conf *brd; | 1146 | struct moxa_board_conf *brd; |
@@ -1194,6 +1169,7 @@ static int moxa_open(struct tty_struct *tty, struct file *filp) | |||
1194 | ch->port.count++; | 1169 | ch->port.count++; |
1195 | tty->driver_data = ch; | 1170 | tty->driver_data = ch; |
1196 | tty_port_tty_set(&ch->port, tty); | 1171 | tty_port_tty_set(&ch->port, tty); |
1172 | mutex_lock(&ch->port.mutex); | ||
1197 | if (!(ch->port.flags & ASYNC_INITIALIZED)) { | 1173 | if (!(ch->port.flags & ASYNC_INITIALIZED)) { |
1198 | ch->statusflags = 0; | 1174 | ch->statusflags = 0; |
1199 | moxa_set_tty_param(tty, tty->termios); | 1175 | moxa_set_tty_param(tty, tty->termios); |
@@ -1202,57 +1178,21 @@ static int moxa_open(struct tty_struct *tty, struct file *filp) | |||
1202 | MoxaSetFifo(ch, ch->type == PORT_16550A); | 1178 | MoxaSetFifo(ch, ch->type == PORT_16550A); |
1203 | ch->port.flags |= ASYNC_INITIALIZED; | 1179 | ch->port.flags |= ASYNC_INITIALIZED; |
1204 | } | 1180 | } |
1181 | mutex_unlock(&ch->port.mutex); | ||
1205 | mutex_unlock(&moxa_openlock); | 1182 | mutex_unlock(&moxa_openlock); |
1206 | 1183 | ||
1207 | retval = 0; | 1184 | retval = tty_port_block_til_ready(&ch->port, tty, filp); |
1208 | if (!(filp->f_flags & O_NONBLOCK) && !C_CLOCAL(tty)) | 1185 | if (retval == 0) |
1209 | retval = moxa_block_till_ready(tty, filp, ch); | 1186 | set_bit(ASYNCB_NORMAL_ACTIVE, &ch->port.flags); |
1210 | mutex_lock(&moxa_openlock); | ||
1211 | if (retval) { | ||
1212 | if (ch->port.count) /* 0 means already hung up... */ | ||
1213 | if (--ch->port.count == 0) | ||
1214 | moxa_close_port(tty); | ||
1215 | } else | ||
1216 | ch->port.flags |= ASYNC_NORMAL_ACTIVE; | ||
1217 | mutex_unlock(&moxa_openlock); | ||
1218 | |||
1219 | return retval; | 1187 | return retval; |
1220 | } | 1188 | } |
1221 | 1189 | ||
1222 | static void moxa_close(struct tty_struct *tty, struct file *filp) | 1190 | static void moxa_close(struct tty_struct *tty, struct file *filp) |
1223 | { | 1191 | { |
1224 | struct moxa_port *ch; | 1192 | struct moxa_port *ch = tty->driver_data; |
1225 | int port; | ||
1226 | |||
1227 | port = tty->index; | ||
1228 | if (port == MAX_PORTS || tty_hung_up_p(filp)) | ||
1229 | return; | ||
1230 | |||
1231 | mutex_lock(&moxa_openlock); | ||
1232 | ch = tty->driver_data; | ||
1233 | if (ch == NULL) | ||
1234 | goto unlock; | ||
1235 | if (tty->count == 1 && ch->port.count != 1) { | ||
1236 | printk(KERN_WARNING "moxa_close: bad serial port count; " | ||
1237 | "tty->count is 1, ch->port.count is %d\n", ch->port.count); | ||
1238 | ch->port.count = 1; | ||
1239 | } | ||
1240 | if (--ch->port.count < 0) { | ||
1241 | printk(KERN_WARNING "moxa_close: bad serial port count, " | ||
1242 | "device=%s\n", tty->name); | ||
1243 | ch->port.count = 0; | ||
1244 | } | ||
1245 | if (ch->port.count) | ||
1246 | goto unlock; | ||
1247 | |||
1248 | ch->cflag = tty->termios->c_cflag; | 1193 | ch->cflag = tty->termios->c_cflag; |
1249 | if (ch->port.flags & ASYNC_INITIALIZED) { | 1194 | mutex_lock(&moxa_openlock); |
1250 | moxa_setup_empty_event(tty); | 1195 | tty_port_close(&ch->port, tty, filp); |
1251 | tty_wait_until_sent(tty, 30 * HZ); /* 30 seconds timeout */ | ||
1252 | } | ||
1253 | |||
1254 | moxa_close_port(tty); | ||
1255 | unlock: | ||
1256 | mutex_unlock(&moxa_openlock); | 1196 | mutex_unlock(&moxa_openlock); |
1257 | } | 1197 | } |
1258 | 1198 | ||
@@ -1300,14 +1240,6 @@ static int moxa_chars_in_buffer(struct tty_struct *tty) | |||
1300 | struct moxa_port *ch = tty->driver_data; | 1240 | struct moxa_port *ch = tty->driver_data; |
1301 | int chars; | 1241 | int chars; |
1302 | 1242 | ||
1303 | /* | ||
1304 | * Sigh...I have to check if driver_data is NULL here, because | ||
1305 | * if an open() fails, the TTY subsystem eventually calls | ||
1306 | * tty_wait_until_sent(), which calls the driver's chars_in_buffer() | ||
1307 | * routine. And since the open() failed, we return 0 here. TDJ | ||
1308 | */ | ||
1309 | if (ch == NULL) | ||
1310 | return 0; | ||
1311 | lock_kernel(); | 1243 | lock_kernel(); |
1312 | chars = MoxaPortTxQueue(ch); | 1244 | chars = MoxaPortTxQueue(ch); |
1313 | if (chars) { | 1245 | if (chars) { |
@@ -1436,15 +1368,8 @@ static void moxa_hangup(struct tty_struct *tty) | |||
1436 | 1368 | ||
1437 | mutex_lock(&moxa_openlock); | 1369 | mutex_lock(&moxa_openlock); |
1438 | ch = tty->driver_data; | 1370 | ch = tty->driver_data; |
1439 | if (ch == NULL) { | 1371 | tty_port_hangup(&ch->port); |
1440 | mutex_unlock(&moxa_openlock); | ||
1441 | return; | ||
1442 | } | ||
1443 | ch->port.count = 0; | ||
1444 | moxa_close_port(tty); | ||
1445 | mutex_unlock(&moxa_openlock); | 1372 | mutex_unlock(&moxa_openlock); |
1446 | |||
1447 | wake_up_interruptible(&ch->port.open_wait); | ||
1448 | } | 1373 | } |
1449 | 1374 | ||
1450 | static void moxa_new_dcdstate(struct moxa_port *p, u8 dcd) | 1375 | static void moxa_new_dcdstate(struct moxa_port *p, u8 dcd) |
@@ -1597,26 +1522,6 @@ static void moxa_setup_empty_event(struct tty_struct *tty) | |||
1597 | spin_unlock_bh(&moxa_lock); | 1522 | spin_unlock_bh(&moxa_lock); |
1598 | } | 1523 | } |
1599 | 1524 | ||
1600 | static void moxa_shut_down(struct tty_struct *tty) | ||
1601 | { | ||
1602 | struct moxa_port *ch = tty->driver_data; | ||
1603 | |||
1604 | if (!(ch->port.flags & ASYNC_INITIALIZED)) | ||
1605 | return; | ||
1606 | |||
1607 | MoxaPortDisable(ch); | ||
1608 | |||
1609 | /* | ||
1610 | * If we're a modem control device and HUPCL is on, drop RTS & DTR. | ||
1611 | */ | ||
1612 | if (C_HUPCL(tty)) | ||
1613 | MoxaPortLineCtrl(ch, 0, 0); | ||
1614 | |||
1615 | spin_lock_bh(&moxa_lock); | ||
1616 | ch->port.flags &= ~ASYNC_INITIALIZED; | ||
1617 | spin_unlock_bh(&moxa_lock); | ||
1618 | } | ||
1619 | |||
1620 | /***************************************************************************** | 1525 | /***************************************************************************** |
1621 | * Driver level functions: * | 1526 | * Driver level functions: * |
1622 | *****************************************************************************/ | 1527 | *****************************************************************************/ |