aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/char
diff options
context:
space:
mode:
authorJiri Kosina <jkosina@suse.cz>2010-08-11 03:36:51 -0400
committerJiri Kosina <jkosina@suse.cz>2010-08-11 03:36:51 -0400
commit6396fc3b3ff3f6b942992b653a62df11dcef9bea (patch)
treedb3c7cbe833b43c653adc99f70941431c5ff7c4e /drivers/char
parent4785879e4d340e24e54f6de2ccfc42728b912808 (diff)
parent3d30701b58970425e1d45994d6cb82f828924fdd (diff)
Merge branch 'master' into for-next
Conflicts: fs/exofs/inode.c
Diffstat (limited to 'drivers/char')
-rw-r--r--drivers/char/Makefile1
-rw-r--r--drivers/char/amiserial.c25
-rw-r--r--drivers/char/briq_panel.c6
-rw-r--r--drivers/char/cyclades.c22
-rw-r--r--drivers/char/epca.c4
-rw-r--r--drivers/char/ip2/ip2main.c4
-rw-r--r--drivers/char/isicom.c13
-rw-r--r--drivers/char/istallion.c68
-rw-r--r--drivers/char/keyboard.c10
-rw-r--r--drivers/char/mxser.c2
-rw-r--r--drivers/char/n_gsm.c1
-rw-r--r--drivers/char/n_hdlc.c16
-rw-r--r--drivers/char/n_r3964.c10
-rw-r--r--drivers/char/n_tty.c17
-rw-r--r--drivers/char/nozomi.c4
-rw-r--r--drivers/char/pty.c47
-rw-r--r--drivers/char/riscom8.c14
-rw-r--r--drivers/char/rocket.c28
-rw-r--r--drivers/char/selection.c13
-rw-r--r--drivers/char/serial167.c8
-rw-r--r--drivers/char/specialix.c13
-rw-r--r--drivers/char/stallion.c20
-rw-r--r--drivers/char/sx.c12
-rw-r--r--drivers/char/synclink.c21
-rw-r--r--drivers/char/synclink_gt.c92
-rw-r--r--drivers/char/synclinkmp.c43
-rw-r--r--drivers/char/tty_io.c150
-rw-r--r--drivers/char/tty_ioctl.c18
-rw-r--r--drivers/char/tty_ldisc.c43
-rw-r--r--drivers/char/tty_mutex.c47
-rw-r--r--drivers/char/tty_port.c4
-rw-r--r--drivers/char/vc_screen.c4
-rw-r--r--drivers/char/vt.c37
-rw-r--r--drivers/char/vt_ioctl.c17
34 files changed, 506 insertions, 328 deletions
diff --git a/drivers/char/Makefile b/drivers/char/Makefile
index 273cee1cc77b..dc9641660605 100644
--- a/drivers/char/Makefile
+++ b/drivers/char/Makefile
@@ -9,6 +9,7 @@ FONTMAPFILE = cp437.uni
9 9
10obj-y += mem.o random.o tty_io.o n_tty.o tty_ioctl.o tty_ldisc.o tty_buffer.o tty_port.o 10obj-y += mem.o random.o tty_io.o n_tty.o tty_ioctl.o tty_ldisc.o tty_buffer.o tty_port.o
11 11
12obj-y += tty_mutex.o
12obj-$(CONFIG_LEGACY_PTYS) += pty.o 13obj-$(CONFIG_LEGACY_PTYS) += pty.o
13obj-$(CONFIG_UNIX98_PTYS) += pty.o 14obj-$(CONFIG_UNIX98_PTYS) += pty.o
14obj-y += misc.o 15obj-y += misc.o
diff --git a/drivers/char/amiserial.c b/drivers/char/amiserial.c
index 4f8d60c25a98..a11c8c9ca3d4 100644
--- a/drivers/char/amiserial.c
+++ b/drivers/char/amiserial.c
@@ -1072,7 +1072,7 @@ static int get_serial_info(struct async_struct * info,
1072 if (!retinfo) 1072 if (!retinfo)
1073 return -EFAULT; 1073 return -EFAULT;
1074 memset(&tmp, 0, sizeof(tmp)); 1074 memset(&tmp, 0, sizeof(tmp));
1075 lock_kernel(); 1075 tty_lock();
1076 tmp.type = state->type; 1076 tmp.type = state->type;
1077 tmp.line = state->line; 1077 tmp.line = state->line;
1078 tmp.port = state->port; 1078 tmp.port = state->port;
@@ -1083,7 +1083,7 @@ static int get_serial_info(struct async_struct * info,
1083 tmp.close_delay = state->close_delay; 1083 tmp.close_delay = state->close_delay;
1084 tmp.closing_wait = state->closing_wait; 1084 tmp.closing_wait = state->closing_wait;
1085 tmp.custom_divisor = state->custom_divisor; 1085 tmp.custom_divisor = state->custom_divisor;
1086 unlock_kernel(); 1086 tty_unlock();
1087 if (copy_to_user(retinfo,&tmp,sizeof(*retinfo))) 1087 if (copy_to_user(retinfo,&tmp,sizeof(*retinfo)))
1088 return -EFAULT; 1088 return -EFAULT;
1089 return 0; 1089 return 0;
@@ -1100,14 +1100,14 @@ static int set_serial_info(struct async_struct * info,
1100 if (copy_from_user(&new_serial,new_info,sizeof(new_serial))) 1100 if (copy_from_user(&new_serial,new_info,sizeof(new_serial)))
1101 return -EFAULT; 1101 return -EFAULT;
1102 1102
1103 lock_kernel(); 1103 tty_lock();
1104 state = info->state; 1104 state = info->state;
1105 old_state = *state; 1105 old_state = *state;
1106 1106
1107 change_irq = new_serial.irq != state->irq; 1107 change_irq = new_serial.irq != state->irq;
1108 change_port = (new_serial.port != state->port); 1108 change_port = (new_serial.port != state->port);
1109 if(change_irq || change_port || (new_serial.xmit_fifo_size != state->xmit_fifo_size)) { 1109 if(change_irq || change_port || (new_serial.xmit_fifo_size != state->xmit_fifo_size)) {
1110 unlock_kernel(); 1110 tty_unlock();
1111 return -EINVAL; 1111 return -EINVAL;
1112 } 1112 }
1113 1113
@@ -1127,7 +1127,7 @@ static int set_serial_info(struct async_struct * info,
1127 } 1127 }
1128 1128
1129 if (new_serial.baud_base < 9600) { 1129 if (new_serial.baud_base < 9600) {
1130 unlock_kernel(); 1130 tty_unlock();
1131 return -EINVAL; 1131 return -EINVAL;
1132 } 1132 }
1133 1133
@@ -1163,7 +1163,7 @@ check_and_exit:
1163 } 1163 }
1164 } else 1164 } else
1165 retval = startup(info); 1165 retval = startup(info);
1166 unlock_kernel(); 1166 tty_unlock();
1167 return retval; 1167 return retval;
1168} 1168}
1169 1169
@@ -1528,6 +1528,7 @@ static void rs_wait_until_sent(struct tty_struct *tty, int timeout)
1528{ 1528{
1529 struct async_struct * info = tty->driver_data; 1529 struct async_struct * info = tty->driver_data;
1530 unsigned long orig_jiffies, char_time; 1530 unsigned long orig_jiffies, char_time;
1531 int tty_was_locked = tty_locked();
1531 int lsr; 1532 int lsr;
1532 1533
1533 if (serial_paranoia_check(info, tty->name, "rs_wait_until_sent")) 1534 if (serial_paranoia_check(info, tty->name, "rs_wait_until_sent"))
@@ -1538,7 +1539,12 @@ static void rs_wait_until_sent(struct tty_struct *tty, int timeout)
1538 1539
1539 orig_jiffies = jiffies; 1540 orig_jiffies = jiffies;
1540 1541
1541 lock_kernel(); 1542 /*
1543 * tty_wait_until_sent is called from lots of places,
1544 * with or without the BTM.
1545 */
1546 if (!tty_was_locked)
1547 tty_lock();
1542 /* 1548 /*
1543 * Set the check interval to be 1/5 of the estimated time to 1549 * Set the check interval to be 1/5 of the estimated time to
1544 * send a single character, and make it at least 1. The check 1550 * send a single character, and make it at least 1. The check
@@ -1579,7 +1585,8 @@ static void rs_wait_until_sent(struct tty_struct *tty, int timeout)
1579 break; 1585 break;
1580 } 1586 }
1581 __set_current_state(TASK_RUNNING); 1587 __set_current_state(TASK_RUNNING);
1582 unlock_kernel(); 1588 if (!tty_was_locked)
1589 tty_unlock();
1583#ifdef SERIAL_DEBUG_RS_WAIT_UNTIL_SENT 1590#ifdef SERIAL_DEBUG_RS_WAIT_UNTIL_SENT
1584 printk("lsr = %d (jiff=%lu)...done\n", lsr, jiffies); 1591 printk("lsr = %d (jiff=%lu)...done\n", lsr, jiffies);
1585#endif 1592#endif
@@ -1703,7 +1710,9 @@ static int block_til_ready(struct tty_struct *tty, struct file * filp,
1703 printk("block_til_ready blocking: ttys%d, count = %d\n", 1710 printk("block_til_ready blocking: ttys%d, count = %d\n",
1704 info->line, state->count); 1711 info->line, state->count);
1705#endif 1712#endif
1713 tty_unlock();
1706 schedule(); 1714 schedule();
1715 tty_lock();
1707 } 1716 }
1708 __set_current_state(TASK_RUNNING); 1717 __set_current_state(TASK_RUNNING);
1709 remove_wait_queue(&info->open_wait, &wait); 1718 remove_wait_queue(&info->open_wait, &wait);
diff --git a/drivers/char/briq_panel.c b/drivers/char/briq_panel.c
index 555cd93c2ee5..d5fa113afe37 100644
--- a/drivers/char/briq_panel.c
+++ b/drivers/char/briq_panel.c
@@ -67,15 +67,15 @@ static void set_led(char state)
67 67
68static int briq_panel_open(struct inode *ino, struct file *filep) 68static int briq_panel_open(struct inode *ino, struct file *filep)
69{ 69{
70 lock_kernel(); 70 tty_lock();
71 /* enforce single access, vfd_is_open is protected by BKL */ 71 /* enforce single access, vfd_is_open is protected by BKL */
72 if (vfd_is_open) { 72 if (vfd_is_open) {
73 unlock_kernel(); 73 tty_unlock();
74 return -EBUSY; 74 return -EBUSY;
75 } 75 }
76 vfd_is_open = 1; 76 vfd_is_open = 1;
77 77
78 unlock_kernel(); 78 tty_unlock();
79 return 0; 79 return 0;
80} 80}
81 81
diff --git a/drivers/char/cyclades.c b/drivers/char/cyclades.c
index 9824b4162904..27aad9422332 100644
--- a/drivers/char/cyclades.c
+++ b/drivers/char/cyclades.c
@@ -65,7 +65,6 @@
65#include <linux/tty.h> 65#include <linux/tty.h>
66#include <linux/tty_flip.h> 66#include <linux/tty_flip.h>
67#include <linux/serial.h> 67#include <linux/serial.h>
68#include <linux/smp_lock.h>
69#include <linux/major.h> 68#include <linux/major.h>
70#include <linux/string.h> 69#include <linux/string.h>
71#include <linux/fcntl.h> 70#include <linux/fcntl.h>
@@ -1608,7 +1607,7 @@ static int cy_open(struct tty_struct *tty, struct file *filp)
1608 * If the port is the middle of closing, bail out now 1607 * If the port is the middle of closing, bail out now
1609 */ 1608 */
1610 if (tty_hung_up_p(filp) || (info->port.flags & ASYNC_CLOSING)) { 1609 if (tty_hung_up_p(filp) || (info->port.flags & ASYNC_CLOSING)) {
1611 wait_event_interruptible(info->port.close_wait, 1610 wait_event_interruptible_tty(info->port.close_wait,
1612 !(info->port.flags & ASYNC_CLOSING)); 1611 !(info->port.flags & ASYNC_CLOSING));
1613 return (info->port.flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS; 1612 return (info->port.flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS;
1614 } 1613 }
@@ -1655,7 +1654,6 @@ static void cy_wait_until_sent(struct tty_struct *tty, int timeout)
1655 return; /* Just in case.... */ 1654 return; /* Just in case.... */
1656 1655
1657 orig_jiffies = jiffies; 1656 orig_jiffies = jiffies;
1658 lock_kernel();
1659 /* 1657 /*
1660 * Set the check interval to be 1/5 of the estimated time to 1658 * Set the check interval to be 1/5 of the estimated time to
1661 * send a single character, and make it at least 1. The check 1659 * send a single character, and make it at least 1. The check
@@ -1702,7 +1700,6 @@ static void cy_wait_until_sent(struct tty_struct *tty, int timeout)
1702 } 1700 }
1703 /* Run one more char cycle */ 1701 /* Run one more char cycle */
1704 msleep_interruptible(jiffies_to_msecs(char_time * 5)); 1702 msleep_interruptible(jiffies_to_msecs(char_time * 5));
1705 unlock_kernel();
1706#ifdef CY_DEBUG_WAIT_UNTIL_SENT 1703#ifdef CY_DEBUG_WAIT_UNTIL_SENT
1707 printk(KERN_DEBUG "Clean (jiff=%lu)...done\n", jiffies); 1704 printk(KERN_DEBUG "Clean (jiff=%lu)...done\n", jiffies);
1708#endif 1705#endif
@@ -1959,7 +1956,6 @@ static int cy_chars_in_buffer(struct tty_struct *tty)
1959 int char_count; 1956 int char_count;
1960 __u32 tx_put, tx_get, tx_bufsize; 1957 __u32 tx_put, tx_get, tx_bufsize;
1961 1958
1962 lock_kernel();
1963 tx_get = readl(&buf_ctrl->tx_get); 1959 tx_get = readl(&buf_ctrl->tx_get);
1964 tx_put = readl(&buf_ctrl->tx_put); 1960 tx_put = readl(&buf_ctrl->tx_put);
1965 tx_bufsize = readl(&buf_ctrl->tx_bufsize); 1961 tx_bufsize = readl(&buf_ctrl->tx_bufsize);
@@ -1971,7 +1967,6 @@ static int cy_chars_in_buffer(struct tty_struct *tty)
1971 printk(KERN_DEBUG "cyc:cy_chars_in_buffer ttyC%d %d\n", 1967 printk(KERN_DEBUG "cyc:cy_chars_in_buffer ttyC%d %d\n",
1972 info->line, info->xmit_cnt + char_count); 1968 info->line, info->xmit_cnt + char_count);
1973#endif 1969#endif
1974 unlock_kernel();
1975 return info->xmit_cnt + char_count; 1970 return info->xmit_cnt + char_count;
1976 } 1971 }
1977#endif /* Z_EXT_CHARS_IN_BUFFER */ 1972#endif /* Z_EXT_CHARS_IN_BUFFER */
@@ -2359,17 +2354,22 @@ cy_set_serial_info(struct cyclades_port *info, struct tty_struct *tty,
2359 struct serial_struct __user *new_info) 2354 struct serial_struct __user *new_info)
2360{ 2355{
2361 struct serial_struct new_serial; 2356 struct serial_struct new_serial;
2357 int ret;
2362 2358
2363 if (copy_from_user(&new_serial, new_info, sizeof(new_serial))) 2359 if (copy_from_user(&new_serial, new_info, sizeof(new_serial)))
2364 return -EFAULT; 2360 return -EFAULT;
2365 2361
2362 mutex_lock(&info->port.mutex);
2366 if (!capable(CAP_SYS_ADMIN)) { 2363 if (!capable(CAP_SYS_ADMIN)) {
2367 if (new_serial.close_delay != info->port.close_delay || 2364 if (new_serial.close_delay != info->port.close_delay ||
2368 new_serial.baud_base != info->baud || 2365 new_serial.baud_base != info->baud ||
2369 (new_serial.flags & ASYNC_FLAGS & 2366 (new_serial.flags & ASYNC_FLAGS &
2370 ~ASYNC_USR_MASK) != 2367 ~ASYNC_USR_MASK) !=
2371 (info->port.flags & ASYNC_FLAGS & ~ASYNC_USR_MASK)) 2368 (info->port.flags & ASYNC_FLAGS & ~ASYNC_USR_MASK))
2369 {
2370 mutex_unlock(&info->port.mutex);
2372 return -EPERM; 2371 return -EPERM;
2372 }
2373 info->port.flags = (info->port.flags & ~ASYNC_USR_MASK) | 2373 info->port.flags = (info->port.flags & ~ASYNC_USR_MASK) |
2374 (new_serial.flags & ASYNC_USR_MASK); 2374 (new_serial.flags & ASYNC_USR_MASK);
2375 info->baud = new_serial.baud_base; 2375 info->baud = new_serial.baud_base;
@@ -2392,10 +2392,12 @@ cy_set_serial_info(struct cyclades_port *info, struct tty_struct *tty,
2392check_and_exit: 2392check_and_exit:
2393 if (info->port.flags & ASYNC_INITIALIZED) { 2393 if (info->port.flags & ASYNC_INITIALIZED) {
2394 cy_set_line_char(info, tty); 2394 cy_set_line_char(info, tty);
2395 return 0; 2395 ret = 0;
2396 } else { 2396 } else {
2397 return cy_startup(info, tty); 2397 ret = cy_startup(info, tty);
2398 } 2398 }
2399 mutex_unlock(&info->port.mutex);
2400 return ret;
2399} /* set_serial_info */ 2401} /* set_serial_info */
2400 2402
2401/* 2403/*
@@ -2438,7 +2440,6 @@ static int cy_tiocmget(struct tty_struct *tty, struct file *file)
2438 2440
2439 card = info->card; 2441 card = info->card;
2440 2442
2441 lock_kernel();
2442 if (!cy_is_Z(card)) { 2443 if (!cy_is_Z(card)) {
2443 unsigned long flags; 2444 unsigned long flags;
2444 int channel = info->line - card->first_line; 2445 int channel = info->line - card->first_line;
@@ -2478,7 +2479,6 @@ static int cy_tiocmget(struct tty_struct *tty, struct file *file)
2478 ((lstatus & C_RS_CTS) ? TIOCM_CTS : 0); 2479 ((lstatus & C_RS_CTS) ? TIOCM_CTS : 0);
2479 } 2480 }
2480end: 2481end:
2481 unlock_kernel();
2482 return result; 2482 return result;
2483} /* cy_tiomget */ 2483} /* cy_tiomget */
2484 2484
@@ -2696,7 +2696,6 @@ cy_ioctl(struct tty_struct *tty, struct file *file,
2696 printk(KERN_DEBUG "cyc:cy_ioctl ttyC%d, cmd = %x arg = %lx\n", 2696 printk(KERN_DEBUG "cyc:cy_ioctl ttyC%d, cmd = %x arg = %lx\n",
2697 info->line, cmd, arg); 2697 info->line, cmd, arg);
2698#endif 2698#endif
2699 lock_kernel();
2700 2699
2701 switch (cmd) { 2700 switch (cmd) {
2702 case CYGETMON: 2701 case CYGETMON:
@@ -2817,7 +2816,6 @@ cy_ioctl(struct tty_struct *tty, struct file *file,
2817 default: 2816 default:
2818 ret_val = -ENOIOCTLCMD; 2817 ret_val = -ENOIOCTLCMD;
2819 } 2818 }
2820 unlock_kernel();
2821 2819
2822#ifdef CY_DEBUG_OTHER 2820#ifdef CY_DEBUG_OTHER
2823 printk(KERN_DEBUG "cyc:cy_ioctl done\n"); 2821 printk(KERN_DEBUG "cyc:cy_ioctl done\n");
diff --git a/drivers/char/epca.c b/drivers/char/epca.c
index 6f5ffe1320f7..d9df46aa0fba 100644
--- a/drivers/char/epca.c
+++ b/drivers/char/epca.c
@@ -36,7 +36,7 @@
36#include <linux/ctype.h> 36#include <linux/ctype.h>
37#include <linux/tty.h> 37#include <linux/tty.h>
38#include <linux/tty_flip.h> 38#include <linux/tty_flip.h>
39#include <linux/smp_lock.h> 39#include <linux/slab.h>
40#include <linux/ioport.h> 40#include <linux/ioport.h>
41#include <linux/interrupt.h> 41#include <linux/interrupt.h>
42#include <linux/uaccess.h> 42#include <linux/uaccess.h>
@@ -2105,7 +2105,6 @@ static int pc_ioctl(struct tty_struct *tty, struct file *file,
2105 break; 2105 break;
2106 case DIGI_SETAW: 2106 case DIGI_SETAW:
2107 case DIGI_SETAF: 2107 case DIGI_SETAF:
2108 lock_kernel();
2109 if (cmd == DIGI_SETAW) { 2108 if (cmd == DIGI_SETAW) {
2110 /* Setup an event to indicate when the transmit 2109 /* Setup an event to indicate when the transmit
2111 buffer empties */ 2110 buffer empties */
@@ -2118,7 +2117,6 @@ static int pc_ioctl(struct tty_struct *tty, struct file *file,
2118 if (tty->ldisc->ops->flush_buffer) 2117 if (tty->ldisc->ops->flush_buffer)
2119 tty->ldisc->ops->flush_buffer(tty); 2118 tty->ldisc->ops->flush_buffer(tty);
2120 } 2119 }
2121 unlock_kernel();
2122 /* Fall Thru */ 2120 /* Fall Thru */
2123 case DIGI_SETA: 2121 case DIGI_SETA:
2124 if (copy_from_user(&ch->digiext, argp, sizeof(digi_t))) 2122 if (copy_from_user(&ch->digiext, argp, sizeof(digi_t)))
diff --git a/drivers/char/ip2/ip2main.c b/drivers/char/ip2/ip2main.c
index 911e1da6def2..07f3ea38b582 100644
--- a/drivers/char/ip2/ip2main.c
+++ b/drivers/char/ip2/ip2main.c
@@ -1486,7 +1486,9 @@ ip2_open( PTTY tty, struct file *pFile )
1486 1486
1487 if ( tty_hung_up_p(pFile) || ( pCh->flags & ASYNC_CLOSING )) { 1487 if ( tty_hung_up_p(pFile) || ( pCh->flags & ASYNC_CLOSING )) {
1488 if ( pCh->flags & ASYNC_CLOSING ) { 1488 if ( pCh->flags & ASYNC_CLOSING ) {
1489 tty_unlock();
1489 schedule(); 1490 schedule();
1491 tty_lock();
1490 } 1492 }
1491 if ( tty_hung_up_p(pFile) ) { 1493 if ( tty_hung_up_p(pFile) ) {
1492 set_current_state( TASK_RUNNING ); 1494 set_current_state( TASK_RUNNING );
@@ -1548,7 +1550,9 @@ ip2_open( PTTY tty, struct file *pFile )
1548 rc = (( pCh->flags & ASYNC_HUP_NOTIFY ) ? -EAGAIN : -ERESTARTSYS); 1550 rc = (( pCh->flags & ASYNC_HUP_NOTIFY ) ? -EAGAIN : -ERESTARTSYS);
1549 break; 1551 break;
1550 } 1552 }
1553 tty_unlock();
1551 schedule(); 1554 schedule();
1555 tty_lock();
1552 } 1556 }
1553 set_current_state( TASK_RUNNING ); 1557 set_current_state( TASK_RUNNING );
1554 remove_wait_queue(&pCh->open_wait, &wait); 1558 remove_wait_queue(&pCh->open_wait, &wait);
diff --git a/drivers/char/isicom.c b/drivers/char/isicom.c
index 98310e1aae30..c27e9d21fea9 100644
--- a/drivers/char/isicom.c
+++ b/drivers/char/isicom.c
@@ -124,7 +124,6 @@
124#include <linux/fs.h> 124#include <linux/fs.h>
125#include <linux/sched.h> 125#include <linux/sched.h>
126#include <linux/serial.h> 126#include <linux/serial.h>
127#include <linux/smp_lock.h>
128#include <linux/mm.h> 127#include <linux/mm.h>
129#include <linux/interrupt.h> 128#include <linux/interrupt.h>
130#include <linux/timer.h> 129#include <linux/timer.h>
@@ -872,7 +871,6 @@ static struct tty_port *isicom_find_port(struct tty_struct *tty)
872static int isicom_open(struct tty_struct *tty, struct file *filp) 871static int isicom_open(struct tty_struct *tty, struct file *filp)
873{ 872{
874 struct isi_port *port; 873 struct isi_port *port;
875 struct isi_board *card;
876 struct tty_port *tport; 874 struct tty_port *tport;
877 875
878 tport = isicom_find_port(tty); 876 tport = isicom_find_port(tty);
@@ -1118,8 +1116,7 @@ static int isicom_set_serial_info(struct tty_struct *tty,
1118 if (copy_from_user(&newinfo, info, sizeof(newinfo))) 1116 if (copy_from_user(&newinfo, info, sizeof(newinfo)))
1119 return -EFAULT; 1117 return -EFAULT;
1120 1118
1121 lock_kernel(); 1119 mutex_lock(&port->port.mutex);
1122
1123 reconfig_port = ((port->port.flags & ASYNC_SPD_MASK) != 1120 reconfig_port = ((port->port.flags & ASYNC_SPD_MASK) !=
1124 (newinfo.flags & ASYNC_SPD_MASK)); 1121 (newinfo.flags & ASYNC_SPD_MASK));
1125 1122
@@ -1128,7 +1125,7 @@ static int isicom_set_serial_info(struct tty_struct *tty,
1128 (newinfo.closing_wait != port->port.closing_wait) || 1125 (newinfo.closing_wait != port->port.closing_wait) ||
1129 ((newinfo.flags & ~ASYNC_USR_MASK) != 1126 ((newinfo.flags & ~ASYNC_USR_MASK) !=
1130 (port->port.flags & ~ASYNC_USR_MASK))) { 1127 (port->port.flags & ~ASYNC_USR_MASK))) {
1131 unlock_kernel(); 1128 mutex_unlock(&port->port.mutex);
1132 return -EPERM; 1129 return -EPERM;
1133 } 1130 }
1134 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) | 1131 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) |
@@ -1145,7 +1142,7 @@ static int isicom_set_serial_info(struct tty_struct *tty,
1145 isicom_config_port(tty); 1142 isicom_config_port(tty);
1146 spin_unlock_irqrestore(&port->card->card_lock, flags); 1143 spin_unlock_irqrestore(&port->card->card_lock, flags);
1147 } 1144 }
1148 unlock_kernel(); 1145 mutex_unlock(&port->port.mutex);
1149 return 0; 1146 return 0;
1150} 1147}
1151 1148
@@ -1154,7 +1151,7 @@ static int isicom_get_serial_info(struct isi_port *port,
1154{ 1151{
1155 struct serial_struct out_info; 1152 struct serial_struct out_info;
1156 1153
1157 lock_kernel(); 1154 mutex_lock(&port->port.mutex);
1158 memset(&out_info, 0, sizeof(out_info)); 1155 memset(&out_info, 0, sizeof(out_info));
1159/* out_info.type = ? */ 1156/* out_info.type = ? */
1160 out_info.line = port - isi_ports; 1157 out_info.line = port - isi_ports;
@@ -1164,7 +1161,7 @@ static int isicom_get_serial_info(struct isi_port *port,
1164/* out_info.baud_base = ? */ 1161/* out_info.baud_base = ? */
1165 out_info.close_delay = port->port.close_delay; 1162 out_info.close_delay = port->port.close_delay;
1166 out_info.closing_wait = port->port.closing_wait; 1163 out_info.closing_wait = port->port.closing_wait;
1167 unlock_kernel(); 1164 mutex_unlock(&port->port.mutex);
1168 if (copy_to_user(info, &out_info, sizeof(out_info))) 1165 if (copy_to_user(info, &out_info, sizeof(out_info)))
1169 return -EFAULT; 1166 return -EFAULT;
1170 return 0; 1167 return 0;
diff --git a/drivers/char/istallion.c b/drivers/char/istallion.c
index 4e395c956a09..be28391adb79 100644
--- a/drivers/char/istallion.c
+++ b/drivers/char/istallion.c
@@ -203,9 +203,9 @@ static int stli_shared;
203 * the board has been detected, and whether it is actually running a slave 203 * the board has been detected, and whether it is actually running a slave
204 * or not. 204 * or not.
205 */ 205 */
206#define BST_FOUND 0x1 206#define BST_FOUND 0
207#define BST_STARTED 0x2 207#define BST_STARTED 1
208#define BST_PROBED 0x4 208#define BST_PROBED 2
209 209
210/* 210/*
211 * Define the set of port state flags. These are marked for internal 211 * Define the set of port state flags. These are marked for internal
@@ -816,7 +816,7 @@ static int stli_open(struct tty_struct *tty, struct file *filp)
816 brdp = stli_brds[brdnr]; 816 brdp = stli_brds[brdnr];
817 if (brdp == NULL) 817 if (brdp == NULL)
818 return -ENODEV; 818 return -ENODEV;
819 if ((brdp->state & BST_STARTED) == 0) 819 if (!test_bit(BST_STARTED, &brdp->state))
820 return -ENODEV; 820 return -ENODEV;
821 portnr = MINOR2PORT(minordev); 821 portnr = MINOR2PORT(minordev);
822 if (portnr > brdp->nrports) 822 if (portnr > brdp->nrports)
@@ -954,7 +954,7 @@ static int stli_rawopen(struct stlibrd *brdp, struct stliport *portp, unsigned l
954 * order of opens and closes may not be preserved across shared 954 * order of opens and closes may not be preserved across shared
955 * memory, so we must wait until it is complete. 955 * memory, so we must wait until it is complete.
956 */ 956 */
957 wait_event_interruptible(portp->raw_wait, 957 wait_event_interruptible_tty(portp->raw_wait,
958 !test_bit(ST_CLOSING, &portp->state)); 958 !test_bit(ST_CLOSING, &portp->state));
959 if (signal_pending(current)) { 959 if (signal_pending(current)) {
960 return -ERESTARTSYS; 960 return -ERESTARTSYS;
@@ -989,7 +989,7 @@ static int stli_rawopen(struct stlibrd *brdp, struct stliport *portp, unsigned l
989 set_bit(ST_OPENING, &portp->state); 989 set_bit(ST_OPENING, &portp->state);
990 spin_unlock_irqrestore(&brd_lock, flags); 990 spin_unlock_irqrestore(&brd_lock, flags);
991 991
992 wait_event_interruptible(portp->raw_wait, 992 wait_event_interruptible_tty(portp->raw_wait,
993 !test_bit(ST_OPENING, &portp->state)); 993 !test_bit(ST_OPENING, &portp->state));
994 if (signal_pending(current)) 994 if (signal_pending(current))
995 rc = -ERESTARTSYS; 995 rc = -ERESTARTSYS;
@@ -1020,7 +1020,7 @@ static int stli_rawclose(struct stlibrd *brdp, struct stliport *portp, unsigned
1020 * occurs on this port. 1020 * occurs on this port.
1021 */ 1021 */
1022 if (wait) { 1022 if (wait) {
1023 wait_event_interruptible(portp->raw_wait, 1023 wait_event_interruptible_tty(portp->raw_wait,
1024 !test_bit(ST_CLOSING, &portp->state)); 1024 !test_bit(ST_CLOSING, &portp->state));
1025 if (signal_pending(current)) { 1025 if (signal_pending(current)) {
1026 return -ERESTARTSYS; 1026 return -ERESTARTSYS;
@@ -1052,7 +1052,7 @@ static int stli_rawclose(struct stlibrd *brdp, struct stliport *portp, unsigned
1052 * to come back. 1052 * to come back.
1053 */ 1053 */
1054 rc = 0; 1054 rc = 0;
1055 wait_event_interruptible(portp->raw_wait, 1055 wait_event_interruptible_tty(portp->raw_wait,
1056 !test_bit(ST_CLOSING, &portp->state)); 1056 !test_bit(ST_CLOSING, &portp->state));
1057 if (signal_pending(current)) 1057 if (signal_pending(current))
1058 rc = -ERESTARTSYS; 1058 rc = -ERESTARTSYS;
@@ -1073,6 +1073,10 @@ static int stli_rawclose(struct stlibrd *brdp, struct stliport *portp, unsigned
1073 1073
1074static int stli_cmdwait(struct stlibrd *brdp, struct stliport *portp, unsigned long cmd, void *arg, int size, int copyback) 1074static int stli_cmdwait(struct stlibrd *brdp, struct stliport *portp, unsigned long cmd, void *arg, int size, int copyback)
1075{ 1075{
1076 /*
1077 * no need for wait_event_tty because clearing ST_CMDING cannot block
1078 * on BTM
1079 */
1076 wait_event_interruptible(portp->raw_wait, 1080 wait_event_interruptible(portp->raw_wait,
1077 !test_bit(ST_CMDING, &portp->state)); 1081 !test_bit(ST_CMDING, &portp->state));
1078 if (signal_pending(current)) 1082 if (signal_pending(current))
@@ -1846,7 +1850,7 @@ static void stli_portinfo(struct seq_file *m, struct stlibrd *brdp, struct stlip
1846 rc = stli_portcmdstats(NULL, portp); 1850 rc = stli_portcmdstats(NULL, portp);
1847 1851
1848 uart = "UNKNOWN"; 1852 uart = "UNKNOWN";
1849 if (brdp->state & BST_STARTED) { 1853 if (test_bit(BST_STARTED, &brdp->state)) {
1850 switch (stli_comstats.hwid) { 1854 switch (stli_comstats.hwid) {
1851 case 0: uart = "2681"; break; 1855 case 0: uart = "2681"; break;
1852 case 1: uart = "SC26198"; break; 1856 case 1: uart = "SC26198"; break;
@@ -1855,7 +1859,7 @@ static void stli_portinfo(struct seq_file *m, struct stlibrd *brdp, struct stlip
1855 } 1859 }
1856 seq_printf(m, "%d: uart:%s ", portnr, uart); 1860 seq_printf(m, "%d: uart:%s ", portnr, uart);
1857 1861
1858 if ((brdp->state & BST_STARTED) && (rc >= 0)) { 1862 if (test_bit(BST_STARTED, &brdp->state) && rc >= 0) {
1859 char sep; 1863 char sep;
1860 1864
1861 seq_printf(m, "tx:%d rx:%d", (int) stli_comstats.txtotal, 1865 seq_printf(m, "tx:%d rx:%d", (int) stli_comstats.txtotal,
@@ -2355,7 +2359,7 @@ static void stli_poll(unsigned long arg)
2355 brdp = stli_brds[brdnr]; 2359 brdp = stli_brds[brdnr];
2356 if (brdp == NULL) 2360 if (brdp == NULL)
2357 continue; 2361 continue;
2358 if ((brdp->state & BST_STARTED) == 0) 2362 if (!test_bit(BST_STARTED, &brdp->state))
2359 continue; 2363 continue;
2360 2364
2361 spin_lock(&brd_lock); 2365 spin_lock(&brd_lock);
@@ -3140,7 +3144,7 @@ static int stli_initecp(struct stlibrd *brdp)
3140 } 3144 }
3141 3145
3142 3146
3143 brdp->state |= BST_FOUND; 3147 set_bit(BST_FOUND, &brdp->state);
3144 return 0; 3148 return 0;
3145err_unmap: 3149err_unmap:
3146 iounmap(brdp->membase); 3150 iounmap(brdp->membase);
@@ -3297,7 +3301,7 @@ static int stli_initonb(struct stlibrd *brdp)
3297 brdp->panels[0] = brdp->nrports; 3301 brdp->panels[0] = brdp->nrports;
3298 3302
3299 3303
3300 brdp->state |= BST_FOUND; 3304 set_bit(BST_FOUND, &brdp->state);
3301 return 0; 3305 return 0;
3302err_unmap: 3306err_unmap:
3303 iounmap(brdp->membase); 3307 iounmap(brdp->membase);
@@ -3407,7 +3411,7 @@ stli_donestartup:
3407 spin_unlock_irqrestore(&brd_lock, flags); 3411 spin_unlock_irqrestore(&brd_lock, flags);
3408 3412
3409 if (rc == 0) 3413 if (rc == 0)
3410 brdp->state |= BST_STARTED; 3414 set_bit(BST_STARTED, &brdp->state);
3411 3415
3412 if (! stli_timeron) { 3416 if (! stli_timeron) {
3413 stli_timeron++; 3417 stli_timeron++;
@@ -3710,7 +3714,7 @@ static int __devinit stli_pciprobe(struct pci_dev *pdev,
3710 if (retval) 3714 if (retval)
3711 goto err_null; 3715 goto err_null;
3712 3716
3713 brdp->state |= BST_PROBED; 3717 set_bit(BST_PROBED, &brdp->state);
3714 pci_set_drvdata(pdev, brdp); 3718 pci_set_drvdata(pdev, brdp);
3715 3719
3716 EBRDENABLE(brdp); 3720 EBRDENABLE(brdp);
@@ -3841,7 +3845,7 @@ static int __init stli_initbrds(void)
3841 brdp = stli_brds[i]; 3845 brdp = stli_brds[i];
3842 if (brdp == NULL) 3846 if (brdp == NULL)
3843 continue; 3847 continue;
3844 if (brdp->state & BST_FOUND) { 3848 if (test_bit(BST_FOUND, &brdp->state)) {
3845 EBRDENABLE(brdp); 3849 EBRDENABLE(brdp);
3846 brdp->enable = NULL; 3850 brdp->enable = NULL;
3847 brdp->disable = NULL; 3851 brdp->disable = NULL;
@@ -4011,6 +4015,7 @@ static int stli_getbrdstats(combrd_t __user *bp)
4011 return -ENODEV; 4015 return -ENODEV;
4012 4016
4013 memset(&stli_brdstats, 0, sizeof(combrd_t)); 4017 memset(&stli_brdstats, 0, sizeof(combrd_t));
4018
4014 stli_brdstats.brd = brdp->brdnr; 4019 stli_brdstats.brd = brdp->brdnr;
4015 stli_brdstats.type = brdp->brdtype; 4020 stli_brdstats.type = brdp->brdtype;
4016 stli_brdstats.hwid = 0; 4021 stli_brdstats.hwid = 0;
@@ -4076,10 +4081,13 @@ static int stli_portcmdstats(struct tty_struct *tty, struct stliport *portp)
4076 if (brdp == NULL) 4081 if (brdp == NULL)
4077 return -ENODEV; 4082 return -ENODEV;
4078 4083
4079 if (brdp->state & BST_STARTED) { 4084 mutex_lock(&portp->port.mutex);
4085 if (test_bit(BST_STARTED, &brdp->state)) {
4080 if ((rc = stli_cmdwait(brdp, portp, A_GETSTATS, 4086 if ((rc = stli_cmdwait(brdp, portp, A_GETSTATS,
4081 &stli_cdkstats, sizeof(asystats_t), 1)) < 0) 4087 &stli_cdkstats, sizeof(asystats_t), 1)) < 0) {
4088 mutex_unlock(&portp->port.mutex);
4082 return rc; 4089 return rc;
4090 }
4083 } else { 4091 } else {
4084 memset(&stli_cdkstats, 0, sizeof(asystats_t)); 4092 memset(&stli_cdkstats, 0, sizeof(asystats_t));
4085 } 4093 }
@@ -4124,6 +4132,7 @@ static int stli_portcmdstats(struct tty_struct *tty, struct stliport *portp)
4124 stli_comstats.modem = stli_cdkstats.dcdcnt; 4132 stli_comstats.modem = stli_cdkstats.dcdcnt;
4125 stli_comstats.hwid = stli_cdkstats.hwid; 4133 stli_comstats.hwid = stli_cdkstats.hwid;
4126 stli_comstats.signals = stli_mktiocm(stli_cdkstats.signals); 4134 stli_comstats.signals = stli_mktiocm(stli_cdkstats.signals);
4135 mutex_unlock(&portp->port.mutex);
4127 4136
4128 return 0; 4137 return 0;
4129} 4138}
@@ -4186,15 +4195,20 @@ static int stli_clrportstats(struct stliport *portp, comstats_t __user *cp)
4186 if (!brdp) 4195 if (!brdp)
4187 return -ENODEV; 4196 return -ENODEV;
4188 4197
4189 if (brdp->state & BST_STARTED) { 4198 mutex_lock(&portp->port.mutex);
4190 if ((rc = stli_cmdwait(brdp, portp, A_CLEARSTATS, NULL, 0, 0)) < 0) 4199
4200 if (test_bit(BST_STARTED, &brdp->state)) {
4201 if ((rc = stli_cmdwait(brdp, portp, A_CLEARSTATS, NULL, 0, 0)) < 0) {
4202 mutex_unlock(&portp->port.mutex);
4191 return rc; 4203 return rc;
4204 }
4192 } 4205 }
4193 4206
4194 memset(&stli_comstats, 0, sizeof(comstats_t)); 4207 memset(&stli_comstats, 0, sizeof(comstats_t));
4195 stli_comstats.brd = portp->brdnr; 4208 stli_comstats.brd = portp->brdnr;
4196 stli_comstats.panel = portp->panelnr; 4209 stli_comstats.panel = portp->panelnr;
4197 stli_comstats.port = portp->portnr; 4210 stli_comstats.port = portp->portnr;
4211 mutex_unlock(&portp->port.mutex);
4198 4212
4199 if (copy_to_user(cp, &stli_comstats, sizeof(comstats_t))) 4213 if (copy_to_user(cp, &stli_comstats, sizeof(comstats_t)))
4200 return -EFAULT; 4214 return -EFAULT;
@@ -4266,8 +4280,6 @@ static long stli_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
4266 done = 0; 4280 done = 0;
4267 rc = 0; 4281 rc = 0;
4268 4282
4269 lock_kernel();
4270
4271 switch (cmd) { 4283 switch (cmd) {
4272 case COM_GETPORTSTATS: 4284 case COM_GETPORTSTATS:
4273 rc = stli_getportstats(NULL, NULL, argp); 4285 rc = stli_getportstats(NULL, NULL, argp);
@@ -4290,8 +4302,6 @@ static long stli_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
4290 done++; 4302 done++;
4291 break; 4303 break;
4292 } 4304 }
4293 unlock_kernel();
4294
4295 if (done) 4305 if (done)
4296 return rc; 4306 return rc;
4297 4307
@@ -4308,8 +4318,6 @@ static long stli_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
4308 if (brdp->state == 0) 4318 if (brdp->state == 0)
4309 return -ENODEV; 4319 return -ENODEV;
4310 4320
4311 lock_kernel();
4312
4313 switch (cmd) { 4321 switch (cmd) {
4314 case STL_BINTR: 4322 case STL_BINTR:
4315 EBRDINTR(brdp); 4323 EBRDINTR(brdp);
@@ -4318,10 +4326,10 @@ static long stli_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
4318 rc = stli_startbrd(brdp); 4326 rc = stli_startbrd(brdp);
4319 break; 4327 break;
4320 case STL_BSTOP: 4328 case STL_BSTOP:
4321 brdp->state &= ~BST_STARTED; 4329 clear_bit(BST_STARTED, &brdp->state);
4322 break; 4330 break;
4323 case STL_BRESET: 4331 case STL_BRESET:
4324 brdp->state &= ~BST_STARTED; 4332 clear_bit(BST_STARTED, &brdp->state);
4325 EBRDRESET(brdp); 4333 EBRDRESET(brdp);
4326 if (stli_shared == 0) { 4334 if (stli_shared == 0) {
4327 if (brdp->reenable != NULL) 4335 if (brdp->reenable != NULL)
@@ -4332,7 +4340,6 @@ static long stli_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
4332 rc = -ENOIOCTLCMD; 4340 rc = -ENOIOCTLCMD;
4333 break; 4341 break;
4334 } 4342 }
4335 unlock_kernel();
4336 return rc; 4343 return rc;
4337} 4344}
4338 4345
@@ -4378,7 +4385,8 @@ static void istallion_cleanup_isa(void)
4378 unsigned int j; 4385 unsigned int j;
4379 4386
4380 for (j = 0; (j < stli_nrbrds); j++) { 4387 for (j = 0; (j < stli_nrbrds); j++) {
4381 if ((brdp = stli_brds[j]) == NULL || (brdp->state & BST_PROBED)) 4388 if ((brdp = stli_brds[j]) == NULL ||
4389 test_bit(BST_PROBED, &brdp->state))
4382 continue; 4390 continue;
4383 4391
4384 stli_cleanup_ports(brdp); 4392 stli_cleanup_ports(brdp);
diff --git a/drivers/char/keyboard.c b/drivers/char/keyboard.c
index 25be2102a60a..a7ca75212bfe 100644
--- a/drivers/char/keyboard.c
+++ b/drivers/char/keyboard.c
@@ -299,7 +299,7 @@ int kbd_rate(struct kbd_repeat *rep)
299 */ 299 */
300static void put_queue(struct vc_data *vc, int ch) 300static void put_queue(struct vc_data *vc, int ch)
301{ 301{
302 struct tty_struct *tty = vc->vc_tty; 302 struct tty_struct *tty = vc->port.tty;
303 303
304 if (tty) { 304 if (tty) {
305 tty_insert_flip_char(tty, ch, 0); 305 tty_insert_flip_char(tty, ch, 0);
@@ -309,7 +309,7 @@ static void put_queue(struct vc_data *vc, int ch)
309 309
310static void puts_queue(struct vc_data *vc, char *cp) 310static void puts_queue(struct vc_data *vc, char *cp)
311{ 311{
312 struct tty_struct *tty = vc->vc_tty; 312 struct tty_struct *tty = vc->port.tty;
313 313
314 if (!tty) 314 if (!tty)
315 return; 315 return;
@@ -485,7 +485,7 @@ static void fn_show_ptregs(struct vc_data *vc)
485 485
486static void fn_hold(struct vc_data *vc) 486static void fn_hold(struct vc_data *vc)
487{ 487{
488 struct tty_struct *tty = vc->vc_tty; 488 struct tty_struct *tty = vc->port.tty;
489 489
490 if (rep || !tty) 490 if (rep || !tty)
491 return; 491 return;
@@ -563,7 +563,7 @@ static void fn_inc_console(struct vc_data *vc)
563 563
564static void fn_send_intr(struct vc_data *vc) 564static void fn_send_intr(struct vc_data *vc)
565{ 565{
566 struct tty_struct *tty = vc->vc_tty; 566 struct tty_struct *tty = vc->port.tty;
567 567
568 if (!tty) 568 if (!tty)
569 return; 569 return;
@@ -1162,7 +1162,7 @@ static void kbd_keycode(unsigned int keycode, int down, int hw_raw)
1162 struct keyboard_notifier_param param = { .vc = vc, .value = keycode, .down = down }; 1162 struct keyboard_notifier_param param = { .vc = vc, .value = keycode, .down = down };
1163 int rc; 1163 int rc;
1164 1164
1165 tty = vc->vc_tty; 1165 tty = vc->port.tty;
1166 1166
1167 if (tty && (!tty->driver_data)) { 1167 if (tty && (!tty->driver_data)) {
1168 /* No driver data? Strange. Okay we fix it then. */ 1168 /* No driver data? Strange. Okay we fix it then. */
diff --git a/drivers/char/mxser.c b/drivers/char/mxser.c
index d2692d443f7b..3fc89da856ae 100644
--- a/drivers/char/mxser.c
+++ b/drivers/char/mxser.c
@@ -2193,7 +2193,7 @@ static void mxser_transmit_chars(struct tty_struct *tty, struct mxser_port *port
2193 port->mon_data.up_txcnt += (cnt - port->xmit_cnt); 2193 port->mon_data.up_txcnt += (cnt - port->xmit_cnt);
2194 port->icount.tx += (cnt - port->xmit_cnt); 2194 port->icount.tx += (cnt - port->xmit_cnt);
2195 2195
2196 if (port->xmit_cnt < WAKEUP_CHARS && tty) 2196 if (port->xmit_cnt < WAKEUP_CHARS)
2197 tty_wakeup(tty); 2197 tty_wakeup(tty);
2198 2198
2199 if (port->xmit_cnt <= 0) { 2199 if (port->xmit_cnt <= 0) {
diff --git a/drivers/char/n_gsm.c b/drivers/char/n_gsm.c
index e4089c432f15..099105e0894e 100644
--- a/drivers/char/n_gsm.c
+++ b/drivers/char/n_gsm.c
@@ -43,7 +43,6 @@
43#include <linux/sched.h> 43#include <linux/sched.h>
44#include <linux/interrupt.h> 44#include <linux/interrupt.h>
45#include <linux/tty.h> 45#include <linux/tty.h>
46#include <linux/timer.h>
47#include <linux/ctype.h> 46#include <linux/ctype.h>
48#include <linux/mm.h> 47#include <linux/mm.h>
49#include <linux/string.h> 48#include <linux/string.h>
diff --git a/drivers/char/n_hdlc.c b/drivers/char/n_hdlc.c
index c68118efad84..47d32281032c 100644
--- a/drivers/char/n_hdlc.c
+++ b/drivers/char/n_hdlc.c
@@ -598,18 +598,18 @@ static ssize_t n_hdlc_tty_read(struct tty_struct *tty, struct file *file,
598 return -EFAULT; 598 return -EFAULT;
599 } 599 }
600 600
601 lock_kernel(); 601 tty_lock();
602 602
603 for (;;) { 603 for (;;) {
604 if (test_bit(TTY_OTHER_CLOSED, &tty->flags)) { 604 if (test_bit(TTY_OTHER_CLOSED, &tty->flags)) {
605 unlock_kernel(); 605 tty_unlock();
606 return -EIO; 606 return -EIO;
607 } 607 }
608 608
609 n_hdlc = tty2n_hdlc (tty); 609 n_hdlc = tty2n_hdlc (tty);
610 if (!n_hdlc || n_hdlc->magic != HDLC_MAGIC || 610 if (!n_hdlc || n_hdlc->magic != HDLC_MAGIC ||
611 tty != n_hdlc->tty) { 611 tty != n_hdlc->tty) {
612 unlock_kernel(); 612 tty_unlock();
613 return 0; 613 return 0;
614 } 614 }
615 615
@@ -619,13 +619,13 @@ static ssize_t n_hdlc_tty_read(struct tty_struct *tty, struct file *file,
619 619
620 /* no data */ 620 /* no data */
621 if (file->f_flags & O_NONBLOCK) { 621 if (file->f_flags & O_NONBLOCK) {
622 unlock_kernel(); 622 tty_unlock();
623 return -EAGAIN; 623 return -EAGAIN;
624 } 624 }
625 625
626 interruptible_sleep_on (&tty->read_wait); 626 interruptible_sleep_on (&tty->read_wait);
627 if (signal_pending(current)) { 627 if (signal_pending(current)) {
628 unlock_kernel(); 628 tty_unlock();
629 return -EINTR; 629 return -EINTR;
630 } 630 }
631 } 631 }
@@ -648,7 +648,7 @@ static ssize_t n_hdlc_tty_read(struct tty_struct *tty, struct file *file,
648 kfree(rbuf); 648 kfree(rbuf);
649 else 649 else
650 n_hdlc_buf_put(&n_hdlc->rx_free_buf_list,rbuf); 650 n_hdlc_buf_put(&n_hdlc->rx_free_buf_list,rbuf);
651 unlock_kernel(); 651 tty_unlock();
652 return ret; 652 return ret;
653 653
654} /* end of n_hdlc_tty_read() */ 654} /* end of n_hdlc_tty_read() */
@@ -691,7 +691,7 @@ static ssize_t n_hdlc_tty_write(struct tty_struct *tty, struct file *file,
691 count = maxframe; 691 count = maxframe;
692 } 692 }
693 693
694 lock_kernel(); 694 tty_lock();
695 695
696 add_wait_queue(&tty->write_wait, &wait); 696 add_wait_queue(&tty->write_wait, &wait);
697 set_current_state(TASK_INTERRUPTIBLE); 697 set_current_state(TASK_INTERRUPTIBLE);
@@ -731,7 +731,7 @@ static ssize_t n_hdlc_tty_write(struct tty_struct *tty, struct file *file,
731 n_hdlc_buf_put(&n_hdlc->tx_buf_list,tbuf); 731 n_hdlc_buf_put(&n_hdlc->tx_buf_list,tbuf);
732 n_hdlc_send_frames(n_hdlc,tty); 732 n_hdlc_send_frames(n_hdlc,tty);
733 } 733 }
734 unlock_kernel(); 734 tty_unlock();
735 return error; 735 return error;
736 736
737} /* end of n_hdlc_tty_write() */ 737} /* end of n_hdlc_tty_write() */
diff --git a/drivers/char/n_r3964.c b/drivers/char/n_r3964.c
index c1d8b54c816d..a98290d7a2c5 100644
--- a/drivers/char/n_r3964.c
+++ b/drivers/char/n_r3964.c
@@ -1067,7 +1067,7 @@ static ssize_t r3964_read(struct tty_struct *tty, struct file *file,
1067 1067
1068 TRACE_L("read()"); 1068 TRACE_L("read()");
1069 1069
1070 lock_kernel(); 1070 tty_lock();
1071 1071
1072 pClient = findClient(pInfo, task_pid(current)); 1072 pClient = findClient(pInfo, task_pid(current));
1073 if (pClient) { 1073 if (pClient) {
@@ -1079,7 +1079,7 @@ static ssize_t r3964_read(struct tty_struct *tty, struct file *file,
1079 goto unlock; 1079 goto unlock;
1080 } 1080 }
1081 /* block until there is a message: */ 1081 /* block until there is a message: */
1082 wait_event_interruptible(pInfo->read_wait, 1082 wait_event_interruptible_tty(pInfo->read_wait,
1083 (pMsg = remove_msg(pInfo, pClient))); 1083 (pMsg = remove_msg(pInfo, pClient)));
1084 } 1084 }
1085 1085
@@ -1109,7 +1109,7 @@ static ssize_t r3964_read(struct tty_struct *tty, struct file *file,
1109 } 1109 }
1110 ret = -EPERM; 1110 ret = -EPERM;
1111unlock: 1111unlock:
1112 unlock_kernel(); 1112 tty_unlock();
1113 return ret; 1113 return ret;
1114} 1114}
1115 1115
@@ -1158,7 +1158,7 @@ static ssize_t r3964_write(struct tty_struct *tty, struct file *file,
1158 pHeader->locks = 0; 1158 pHeader->locks = 0;
1159 pHeader->owner = NULL; 1159 pHeader->owner = NULL;
1160 1160
1161 lock_kernel(); 1161 tty_lock();
1162 1162
1163 pClient = findClient(pInfo, task_pid(current)); 1163 pClient = findClient(pInfo, task_pid(current));
1164 if (pClient) { 1164 if (pClient) {
@@ -1177,7 +1177,7 @@ static ssize_t r3964_write(struct tty_struct *tty, struct file *file,
1177 add_tx_queue(pInfo, pHeader); 1177 add_tx_queue(pInfo, pHeader);
1178 trigger_transmit(pInfo); 1178 trigger_transmit(pInfo);
1179 1179
1180 unlock_kernel(); 1180 tty_unlock();
1181 1181
1182 return 0; 1182 return 0;
1183} 1183}
diff --git a/drivers/char/n_tty.c b/drivers/char/n_tty.c
index bdae8327143c..428f4fe0b5f7 100644
--- a/drivers/char/n_tty.c
+++ b/drivers/char/n_tty.c
@@ -1102,6 +1102,11 @@ static inline void n_tty_receive_char(struct tty_struct *tty, unsigned char c)
1102 if (I_IUCLC(tty) && L_IEXTEN(tty)) 1102 if (I_IUCLC(tty) && L_IEXTEN(tty))
1103 c = tolower(c); 1103 c = tolower(c);
1104 1104
1105 if (L_EXTPROC(tty)) {
1106 put_tty_queue(c, tty);
1107 return;
1108 }
1109
1105 if (tty->stopped && !tty->flow_stopped && I_IXON(tty) && 1110 if (tty->stopped && !tty->flow_stopped && I_IXON(tty) &&
1106 I_IXANY(tty) && c != START_CHAR(tty) && c != STOP_CHAR(tty) && 1111 I_IXANY(tty) && c != START_CHAR(tty) && c != STOP_CHAR(tty) &&
1107 c != INTR_CHAR(tty) && c != QUIT_CHAR(tty) && c != SUSP_CHAR(tty)) { 1112 c != INTR_CHAR(tty) && c != QUIT_CHAR(tty) && c != SUSP_CHAR(tty)) {
@@ -1409,7 +1414,8 @@ static void n_tty_receive_buf(struct tty_struct *tty, const unsigned char *cp,
1409 1414
1410 n_tty_set_room(tty); 1415 n_tty_set_room(tty);
1411 1416
1412 if (!tty->icanon && (tty->read_cnt >= tty->minimum_to_wake)) { 1417 if ((!tty->icanon && (tty->read_cnt >= tty->minimum_to_wake)) ||
1418 L_EXTPROC(tty)) {
1413 kill_fasync(&tty->fasync, SIGIO, POLL_IN); 1419 kill_fasync(&tty->fasync, SIGIO, POLL_IN);
1414 if (waitqueue_active(&tty->read_wait)) 1420 if (waitqueue_active(&tty->read_wait))
1415 wake_up_interruptible(&tty->read_wait); 1421 wake_up_interruptible(&tty->read_wait);
@@ -1585,7 +1591,7 @@ static int n_tty_open(struct tty_struct *tty)
1585static inline int input_available_p(struct tty_struct *tty, int amt) 1591static inline int input_available_p(struct tty_struct *tty, int amt)
1586{ 1592{
1587 tty_flush_to_ldisc(tty); 1593 tty_flush_to_ldisc(tty);
1588 if (tty->icanon) { 1594 if (tty->icanon && !L_EXTPROC(tty)) {
1589 if (tty->canon_data) 1595 if (tty->canon_data)
1590 return 1; 1596 return 1;
1591 } else if (tty->read_cnt >= (amt ? amt : 1)) 1597 } else if (tty->read_cnt >= (amt ? amt : 1))
@@ -1632,6 +1638,11 @@ static int copy_from_read_buf(struct tty_struct *tty,
1632 spin_lock_irqsave(&tty->read_lock, flags); 1638 spin_lock_irqsave(&tty->read_lock, flags);
1633 tty->read_tail = (tty->read_tail + n) & (N_TTY_BUF_SIZE-1); 1639 tty->read_tail = (tty->read_tail + n) & (N_TTY_BUF_SIZE-1);
1634 tty->read_cnt -= n; 1640 tty->read_cnt -= n;
1641 /* Turn single EOF into zero-length read */
1642 if (L_EXTPROC(tty) && tty->icanon && n == 1) {
1643 if (!tty->read_cnt && (*b)[n-1] == EOF_CHAR(tty))
1644 n--;
1645 }
1635 spin_unlock_irqrestore(&tty->read_lock, flags); 1646 spin_unlock_irqrestore(&tty->read_lock, flags);
1636 *b += n; 1647 *b += n;
1637 *nr -= n; 1648 *nr -= n;
@@ -1812,7 +1823,7 @@ do_it_again:
1812 nr--; 1823 nr--;
1813 } 1824 }
1814 1825
1815 if (tty->icanon) { 1826 if (tty->icanon && !L_EXTPROC(tty)) {
1816 /* N.B. avoid overrun if nr == 0 */ 1827 /* N.B. avoid overrun if nr == 0 */
1817 while (nr && tty->read_cnt) { 1828 while (nr && tty->read_cnt) {
1818 int eol; 1829 int eol;
diff --git a/drivers/char/nozomi.c b/drivers/char/nozomi.c
index a6638003f530..18af923093c3 100644
--- a/drivers/char/nozomi.c
+++ b/drivers/char/nozomi.c
@@ -1611,6 +1611,8 @@ static int ntty_install(struct tty_driver *driver, struct tty_struct *tty)
1611 ret = tty_init_termios(tty); 1611 ret = tty_init_termios(tty);
1612 if (ret == 0) { 1612 if (ret == 0) {
1613 tty_driver_kref_get(driver); 1613 tty_driver_kref_get(driver);
1614 tty->count++;
1615 tty->driver_data = port;
1614 driver->ttys[tty->index] = tty; 1616 driver->ttys[tty->index] = tty;
1615 } 1617 }
1616 return ret; 1618 return ret;
@@ -1639,7 +1641,7 @@ static int ntty_activate(struct tty_port *tport, struct tty_struct *tty)
1639 1641
1640static int ntty_open(struct tty_struct *tty, struct file *filp) 1642static int ntty_open(struct tty_struct *tty, struct file *filp)
1641{ 1643{
1642 struct port *port = get_port_by_tty(tty); 1644 struct port *port = tty->driver_data;
1643 return tty_port_open(&port->port, tty, filp); 1645 return tty_port_open(&port->port, tty, filp);
1644} 1646}
1645 1647
diff --git a/drivers/char/pty.c b/drivers/char/pty.c
index d83a43130df4..ad46eae1f9bb 100644
--- a/drivers/char/pty.c
+++ b/drivers/char/pty.c
@@ -62,7 +62,9 @@ static void pty_close(struct tty_struct *tty, struct file *filp)
62 if (tty->driver == ptm_driver) 62 if (tty->driver == ptm_driver)
63 devpts_pty_kill(tty->link); 63 devpts_pty_kill(tty->link);
64#endif 64#endif
65 tty_unlock();
65 tty_vhangup(tty->link); 66 tty_vhangup(tty->link);
67 tty_lock();
66 } 68 }
67} 69}
68 70
@@ -171,6 +173,23 @@ static int pty_set_lock(struct tty_struct *tty, int __user *arg)
171 return 0; 173 return 0;
172} 174}
173 175
176/* Send a signal to the slave */
177static int pty_signal(struct tty_struct *tty, int sig)
178{
179 unsigned long flags;
180 struct pid *pgrp;
181
182 if (tty->link) {
183 spin_lock_irqsave(&tty->link->ctrl_lock, flags);
184 pgrp = get_pid(tty->link->pgrp);
185 spin_unlock_irqrestore(&tty->link->ctrl_lock, flags);
186
187 kill_pgrp(pgrp, sig, 1);
188 put_pid(pgrp);
189 }
190 return 0;
191}
192
174static void pty_flush_buffer(struct tty_struct *tty) 193static void pty_flush_buffer(struct tty_struct *tty)
175{ 194{
176 struct tty_struct *to = tty->link; 195 struct tty_struct *to = tty->link;
@@ -321,6 +340,8 @@ static int pty_bsd_ioctl(struct tty_struct *tty, struct file *file,
321 switch (cmd) { 340 switch (cmd) {
322 case TIOCSPTLCK: /* Set PT Lock (disallow slave open) */ 341 case TIOCSPTLCK: /* Set PT Lock (disallow slave open) */
323 return pty_set_lock(tty, (int __user *) arg); 342 return pty_set_lock(tty, (int __user *) arg);
343 case TIOCSIG: /* Send signal to other side of pty */
344 return pty_signal(tty, (int) arg);
324 } 345 }
325 return -ENOIOCTLCMD; 346 return -ENOIOCTLCMD;
326} 347}
@@ -476,6 +497,8 @@ static int pty_unix98_ioctl(struct tty_struct *tty, struct file *file,
476 return pty_set_lock(tty, (int __user *)arg); 497 return pty_set_lock(tty, (int __user *)arg);
477 case TIOCGPTN: /* Get PT Number */ 498 case TIOCGPTN: /* Get PT Number */
478 return put_user(tty->index, (unsigned int __user *)arg); 499 return put_user(tty->index, (unsigned int __user *)arg);
500 case TIOCSIG: /* Send signal to other side of pty */
501 return pty_signal(tty, (int) arg);
479 } 502 }
480 503
481 return -ENOIOCTLCMD; 504 return -ENOIOCTLCMD;
@@ -626,7 +649,7 @@ static const struct tty_operations pty_unix98_ops = {
626 * allocated_ptys_lock handles the list of free pty numbers 649 * allocated_ptys_lock handles the list of free pty numbers
627 */ 650 */
628 651
629static int __ptmx_open(struct inode *inode, struct file *filp) 652static int ptmx_open(struct inode *inode, struct file *filp)
630{ 653{
631 struct tty_struct *tty; 654 struct tty_struct *tty;
632 int retval; 655 int retval;
@@ -635,11 +658,14 @@ static int __ptmx_open(struct inode *inode, struct file *filp)
635 nonseekable_open(inode, filp); 658 nonseekable_open(inode, filp);
636 659
637 /* find a device that is not in use. */ 660 /* find a device that is not in use. */
661 tty_lock();
638 index = devpts_new_index(inode); 662 index = devpts_new_index(inode);
663 tty_unlock();
639 if (index < 0) 664 if (index < 0)
640 return index; 665 return index;
641 666
642 mutex_lock(&tty_mutex); 667 mutex_lock(&tty_mutex);
668 tty_lock();
643 tty = tty_init_dev(ptm_driver, index, 1); 669 tty = tty_init_dev(ptm_driver, index, 1);
644 mutex_unlock(&tty_mutex); 670 mutex_unlock(&tty_mutex);
645 671
@@ -657,26 +683,21 @@ static int __ptmx_open(struct inode *inode, struct file *filp)
657 goto out1; 683 goto out1;
658 684
659 retval = ptm_driver->ops->open(tty, filp); 685 retval = ptm_driver->ops->open(tty, filp);
660 if (!retval) 686 if (retval)
661 return 0; 687 goto out2;
662out1: 688out1:
689 tty_unlock();
690 return retval;
691out2:
692 tty_unlock();
663 tty_release(inode, filp); 693 tty_release(inode, filp);
664 return retval; 694 return retval;
665out: 695out:
666 devpts_kill_index(inode, index); 696 devpts_kill_index(inode, index);
697 tty_unlock();
667 return retval; 698 return retval;
668} 699}
669 700
670static int ptmx_open(struct inode *inode, struct file *filp)
671{
672 int ret;
673
674 lock_kernel();
675 ret = __ptmx_open(inode, filp);
676 unlock_kernel();
677 return ret;
678}
679
680static struct file_operations ptmx_fops; 701static struct file_operations ptmx_fops;
681 702
682static void __init unix98_pty_init(void) 703static void __init unix98_pty_init(void)
diff --git a/drivers/char/riscom8.c b/drivers/char/riscom8.c
index b02332a5412f..af4de1fe8445 100644
--- a/drivers/char/riscom8.c
+++ b/drivers/char/riscom8.c
@@ -47,7 +47,6 @@
47#include <linux/init.h> 47#include <linux/init.h>
48#include <linux/delay.h> 48#include <linux/delay.h>
49#include <linux/tty_flip.h> 49#include <linux/tty_flip.h>
50#include <linux/smp_lock.h>
51#include <linux/spinlock.h> 50#include <linux/spinlock.h>
52#include <linux/device.h> 51#include <linux/device.h>
53 52
@@ -1184,6 +1183,7 @@ static int rc_set_serial_info(struct tty_struct *tty, struct riscom_port *port,
1184 if (copy_from_user(&tmp, newinfo, sizeof(tmp))) 1183 if (copy_from_user(&tmp, newinfo, sizeof(tmp)))
1185 return -EFAULT; 1184 return -EFAULT;
1186 1185
1186 mutex_lock(&port->port.mutex);
1187 change_speed = ((port->port.flags & ASYNC_SPD_MASK) != 1187 change_speed = ((port->port.flags & ASYNC_SPD_MASK) !=
1188 (tmp.flags & ASYNC_SPD_MASK)); 1188 (tmp.flags & ASYNC_SPD_MASK));
1189 1189
@@ -1191,8 +1191,10 @@ static int rc_set_serial_info(struct tty_struct *tty, struct riscom_port *port,
1191 if ((tmp.close_delay != port->port.close_delay) || 1191 if ((tmp.close_delay != port->port.close_delay) ||
1192 (tmp.closing_wait != port->port.closing_wait) || 1192 (tmp.closing_wait != port->port.closing_wait) ||
1193 ((tmp.flags & ~ASYNC_USR_MASK) != 1193 ((tmp.flags & ~ASYNC_USR_MASK) !=
1194 (port->port.flags & ~ASYNC_USR_MASK))) 1194 (port->port.flags & ~ASYNC_USR_MASK))) {
1195 mutex_unlock(&port->port.mutex);
1195 return -EPERM; 1196 return -EPERM;
1197 }
1196 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) | 1198 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) |
1197 (tmp.flags & ASYNC_USR_MASK)); 1199 (tmp.flags & ASYNC_USR_MASK));
1198 } else { 1200 } else {
@@ -1208,6 +1210,7 @@ static int rc_set_serial_info(struct tty_struct *tty, struct riscom_port *port,
1208 rc_change_speed(tty, bp, port); 1210 rc_change_speed(tty, bp, port);
1209 spin_unlock_irqrestore(&riscom_lock, flags); 1211 spin_unlock_irqrestore(&riscom_lock, flags);
1210 } 1212 }
1213 mutex_unlock(&port->port.mutex);
1211 return 0; 1214 return 0;
1212} 1215}
1213 1216
@@ -1220,12 +1223,15 @@ static int rc_get_serial_info(struct riscom_port *port,
1220 memset(&tmp, 0, sizeof(tmp)); 1223 memset(&tmp, 0, sizeof(tmp));
1221 tmp.type = PORT_CIRRUS; 1224 tmp.type = PORT_CIRRUS;
1222 tmp.line = port - rc_port; 1225 tmp.line = port - rc_port;
1226
1227 mutex_lock(&port->port.mutex);
1223 tmp.port = bp->base; 1228 tmp.port = bp->base;
1224 tmp.irq = bp->irq; 1229 tmp.irq = bp->irq;
1225 tmp.flags = port->port.flags; 1230 tmp.flags = port->port.flags;
1226 tmp.baud_base = (RC_OSCFREQ + CD180_TPC/2) / CD180_TPC; 1231 tmp.baud_base = (RC_OSCFREQ + CD180_TPC/2) / CD180_TPC;
1227 tmp.close_delay = port->port.close_delay * HZ/100; 1232 tmp.close_delay = port->port.close_delay * HZ/100;
1228 tmp.closing_wait = port->port.closing_wait * HZ/100; 1233 tmp.closing_wait = port->port.closing_wait * HZ/100;
1234 mutex_unlock(&port->port.mutex);
1229 tmp.xmit_fifo_size = CD180_NFIFO; 1235 tmp.xmit_fifo_size = CD180_NFIFO;
1230 return copy_to_user(retinfo, &tmp, sizeof(tmp)) ? -EFAULT : 0; 1236 return copy_to_user(retinfo, &tmp, sizeof(tmp)) ? -EFAULT : 0;
1231} 1237}
@@ -1242,14 +1248,10 @@ static int rc_ioctl(struct tty_struct *tty, struct file *filp,
1242 1248
1243 switch (cmd) { 1249 switch (cmd) {
1244 case TIOCGSERIAL: 1250 case TIOCGSERIAL:
1245 lock_kernel();
1246 retval = rc_get_serial_info(port, argp); 1251 retval = rc_get_serial_info(port, argp);
1247 unlock_kernel();
1248 break; 1252 break;
1249 case TIOCSSERIAL: 1253 case TIOCSSERIAL:
1250 lock_kernel();
1251 retval = rc_set_serial_info(tty, port, argp); 1254 retval = rc_set_serial_info(tty, port, argp);
1252 unlock_kernel();
1253 break; 1255 break;
1254 default: 1256 default:
1255 retval = -ENOIOCTLCMD; 1257 retval = -ENOIOCTLCMD;
diff --git a/drivers/char/rocket.c b/drivers/char/rocket.c
index 0e29a23ec4c5..79c3bc69165a 100644
--- a/drivers/char/rocket.c
+++ b/drivers/char/rocket.c
@@ -73,7 +73,6 @@
73#include <linux/tty_driver.h> 73#include <linux/tty_driver.h>
74#include <linux/tty_flip.h> 74#include <linux/tty_flip.h>
75#include <linux/serial.h> 75#include <linux/serial.h>
76#include <linux/smp_lock.h>
77#include <linux/string.h> 76#include <linux/string.h>
78#include <linux/fcntl.h> 77#include <linux/fcntl.h>
79#include <linux/ptrace.h> 78#include <linux/ptrace.h>
@@ -1017,6 +1016,7 @@ static void rp_close(struct tty_struct *tty, struct file *filp)
1017 if (tty_port_close_start(port, tty, filp) == 0) 1016 if (tty_port_close_start(port, tty, filp) == 0)
1018 return; 1017 return;
1019 1018
1019 mutex_lock(&port->mutex);
1020 cp = &info->channel; 1020 cp = &info->channel;
1021 /* 1021 /*
1022 * Before we drop DTR, make sure the UART transmitter 1022 * Before we drop DTR, make sure the UART transmitter
@@ -1060,9 +1060,13 @@ static void rp_close(struct tty_struct *tty, struct file *filp)
1060 info->xmit_buf = NULL; 1060 info->xmit_buf = NULL;
1061 } 1061 }
1062 } 1062 }
1063 spin_lock_irq(&port->lock);
1063 info->port.flags &= ~(ASYNC_INITIALIZED | ASYNC_CLOSING | ASYNC_NORMAL_ACTIVE); 1064 info->port.flags &= ~(ASYNC_INITIALIZED | ASYNC_CLOSING | ASYNC_NORMAL_ACTIVE);
1064 tty->closing = 0; 1065 tty->closing = 0;
1066 spin_unlock_irq(&port->lock);
1067 mutex_unlock(&port->mutex);
1065 tty_port_tty_set(port, NULL); 1068 tty_port_tty_set(port, NULL);
1069
1066 wake_up_interruptible(&port->close_wait); 1070 wake_up_interruptible(&port->close_wait);
1067 complete_all(&info->close_wait); 1071 complete_all(&info->close_wait);
1068 atomic_dec(&rp_num_ports_open); 1072 atomic_dec(&rp_num_ports_open);
@@ -1210,11 +1214,13 @@ static int get_config(struct r_port *info, struct rocket_config __user *retinfo)
1210 if (!retinfo) 1214 if (!retinfo)
1211 return -EFAULT; 1215 return -EFAULT;
1212 memset(&tmp, 0, sizeof (tmp)); 1216 memset(&tmp, 0, sizeof (tmp));
1217 mutex_lock(&info->port.mutex);
1213 tmp.line = info->line; 1218 tmp.line = info->line;
1214 tmp.flags = info->flags; 1219 tmp.flags = info->flags;
1215 tmp.close_delay = info->port.close_delay; 1220 tmp.close_delay = info->port.close_delay;
1216 tmp.closing_wait = info->port.closing_wait; 1221 tmp.closing_wait = info->port.closing_wait;
1217 tmp.port = rcktpt_io_addr[(info->line >> 5) & 3]; 1222 tmp.port = rcktpt_io_addr[(info->line >> 5) & 3];
1223 mutex_unlock(&info->port.mutex);
1218 1224
1219 if (copy_to_user(retinfo, &tmp, sizeof (*retinfo))) 1225 if (copy_to_user(retinfo, &tmp, sizeof (*retinfo)))
1220 return -EFAULT; 1226 return -EFAULT;
@@ -1229,10 +1235,13 @@ static int set_config(struct tty_struct *tty, struct r_port *info,
1229 if (copy_from_user(&new_serial, new_info, sizeof (new_serial))) 1235 if (copy_from_user(&new_serial, new_info, sizeof (new_serial)))
1230 return -EFAULT; 1236 return -EFAULT;
1231 1237
1238 mutex_lock(&info->port.mutex);
1232 if (!capable(CAP_SYS_ADMIN)) 1239 if (!capable(CAP_SYS_ADMIN))
1233 { 1240 {
1234 if ((new_serial.flags & ~ROCKET_USR_MASK) != (info->flags & ~ROCKET_USR_MASK)) 1241 if ((new_serial.flags & ~ROCKET_USR_MASK) != (info->flags & ~ROCKET_USR_MASK)) {
1242 mutex_unlock(&info->port.mutex);
1235 return -EPERM; 1243 return -EPERM;
1244 }
1236 info->flags = ((info->flags & ~ROCKET_USR_MASK) | (new_serial.flags & ROCKET_USR_MASK)); 1245 info->flags = ((info->flags & ~ROCKET_USR_MASK) | (new_serial.flags & ROCKET_USR_MASK));
1237 configure_r_port(tty, info, NULL); 1246 configure_r_port(tty, info, NULL);
1238 return 0; 1247 return 0;
@@ -1250,6 +1259,7 @@ static int set_config(struct tty_struct *tty, struct r_port *info,
1250 tty->alt_speed = 230400; 1259 tty->alt_speed = 230400;
1251 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP) 1260 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP)
1252 tty->alt_speed = 460800; 1261 tty->alt_speed = 460800;
1262 mutex_unlock(&info->port.mutex);
1253 1263
1254 configure_r_port(tty, info, NULL); 1264 configure_r_port(tty, info, NULL);
1255 return 0; 1265 return 0;
@@ -1325,8 +1335,6 @@ static int rp_ioctl(struct tty_struct *tty, struct file *file,
1325 if (cmd != RCKP_GET_PORTS && rocket_paranoia_check(info, "rp_ioctl")) 1335 if (cmd != RCKP_GET_PORTS && rocket_paranoia_check(info, "rp_ioctl"))
1326 return -ENXIO; 1336 return -ENXIO;
1327 1337
1328 lock_kernel();
1329
1330 switch (cmd) { 1338 switch (cmd) {
1331 case RCKP_GET_STRUCT: 1339 case RCKP_GET_STRUCT:
1332 if (copy_to_user(argp, info, sizeof (struct r_port))) 1340 if (copy_to_user(argp, info, sizeof (struct r_port)))
@@ -1350,7 +1358,6 @@ static int rp_ioctl(struct tty_struct *tty, struct file *file,
1350 default: 1358 default:
1351 ret = -ENOIOCTLCMD; 1359 ret = -ENOIOCTLCMD;
1352 } 1360 }
1353 unlock_kernel();
1354 return ret; 1361 return ret;
1355} 1362}
1356 1363
@@ -1471,7 +1478,6 @@ static void rp_wait_until_sent(struct tty_struct *tty, int timeout)
1471 jiffies); 1478 jiffies);
1472 printk(KERN_INFO "cps=%d...\n", info->cps); 1479 printk(KERN_INFO "cps=%d...\n", info->cps);
1473#endif 1480#endif
1474 lock_kernel();
1475 while (1) { 1481 while (1) {
1476 txcnt = sGetTxCnt(cp); 1482 txcnt = sGetTxCnt(cp);
1477 if (!txcnt) { 1483 if (!txcnt) {
@@ -1499,7 +1505,6 @@ static void rp_wait_until_sent(struct tty_struct *tty, int timeout)
1499 break; 1505 break;
1500 } 1506 }
1501 __set_current_state(TASK_RUNNING); 1507 __set_current_state(TASK_RUNNING);
1502 unlock_kernel();
1503#ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT 1508#ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT
1504 printk(KERN_INFO "txcnt = %d (jiff=%lu)...done\n", txcnt, jiffies); 1509 printk(KERN_INFO "txcnt = %d (jiff=%lu)...done\n", txcnt, jiffies);
1505#endif 1510#endif
@@ -1512,6 +1517,7 @@ static void rp_hangup(struct tty_struct *tty)
1512{ 1517{
1513 CHANNEL_t *cp; 1518 CHANNEL_t *cp;
1514 struct r_port *info = tty->driver_data; 1519 struct r_port *info = tty->driver_data;
1520 unsigned long flags;
1515 1521
1516 if (rocket_paranoia_check(info, "rp_hangup")) 1522 if (rocket_paranoia_check(info, "rp_hangup"))
1517 return; 1523 return;
@@ -1520,11 +1526,15 @@ static void rp_hangup(struct tty_struct *tty)
1520 printk(KERN_INFO "rp_hangup of ttyR%d...\n", info->line); 1526 printk(KERN_INFO "rp_hangup of ttyR%d...\n", info->line);
1521#endif 1527#endif
1522 rp_flush_buffer(tty); 1528 rp_flush_buffer(tty);
1523 if (info->port.flags & ASYNC_CLOSING) 1529 spin_lock_irqsave(&info->port.lock, flags);
1530 if (info->port.flags & ASYNC_CLOSING) {
1531 spin_unlock_irqrestore(&info->port.lock, flags);
1524 return; 1532 return;
1533 }
1525 if (info->port.count) 1534 if (info->port.count)
1526 atomic_dec(&rp_num_ports_open); 1535 atomic_dec(&rp_num_ports_open);
1527 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1536 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1537 spin_unlock_irqrestore(&info->port.lock, flags);
1528 1538
1529 tty_port_hangup(&info->port); 1539 tty_port_hangup(&info->port);
1530 1540
@@ -1535,7 +1545,7 @@ static void rp_hangup(struct tty_struct *tty)
1535 sDisCTSFlowCtl(cp); 1545 sDisCTSFlowCtl(cp);
1536 sDisTxSoftFlowCtl(cp); 1546 sDisTxSoftFlowCtl(cp);
1537 sClrTxXOFF(cp); 1547 sClrTxXOFF(cp);
1538 info->port.flags &= ~ASYNC_INITIALIZED; 1548 clear_bit(ASYNCB_INITIALIZED, &info->port.flags);
1539 1549
1540 wake_up_interruptible(&info->port.open_wait); 1550 wake_up_interruptible(&info->port.open_wait);
1541} 1551}
diff --git a/drivers/char/selection.c b/drivers/char/selection.c
index f97b9e848064..ebae344ce910 100644
--- a/drivers/char/selection.c
+++ b/drivers/char/selection.c
@@ -26,6 +26,7 @@
26#include <linux/selection.h> 26#include <linux/selection.h>
27#include <linux/tiocl.h> 27#include <linux/tiocl.h>
28#include <linux/console.h> 28#include <linux/console.h>
29#include <linux/smp_lock.h>
29 30
30/* Don't take this from <ctype.h>: 011-015 on the screen aren't spaces */ 31/* Don't take this from <ctype.h>: 011-015 on the screen aren't spaces */
31#define isspace(c) ((c) == ' ') 32#define isspace(c) ((c) == ' ')
@@ -312,12 +313,20 @@ int paste_selection(struct tty_struct *tty)
312 struct tty_ldisc *ld; 313 struct tty_ldisc *ld;
313 DECLARE_WAITQUEUE(wait, current); 314 DECLARE_WAITQUEUE(wait, current);
314 315
316 /* always called with BTM from vt_ioctl */
317 WARN_ON(!tty_locked());
318
315 acquire_console_sem(); 319 acquire_console_sem();
316 poke_blanked_console(); 320 poke_blanked_console();
317 release_console_sem(); 321 release_console_sem();
318 322
319 ld = tty_ldisc_ref_wait(tty); 323 ld = tty_ldisc_ref(tty);
320 324 if (!ld) {
325 tty_unlock();
326 ld = tty_ldisc_ref_wait(tty);
327 tty_lock();
328 }
329
321 add_wait_queue(&vc->paste_wait, &wait); 330 add_wait_queue(&vc->paste_wait, &wait);
322 while (sel_buffer && sel_buffer_lth > pasted) { 331 while (sel_buffer && sel_buffer_lth > pasted) {
323 set_current_state(TASK_INTERRUPTIBLE); 332 set_current_state(TASK_INTERRUPTIBLE);
diff --git a/drivers/char/serial167.c b/drivers/char/serial167.c
index ecbe479c7d68..f646725bd567 100644
--- a/drivers/char/serial167.c
+++ b/drivers/char/serial167.c
@@ -1505,7 +1505,7 @@ cy_ioctl(struct tty_struct *tty, struct file *file,
1505 printk("cy_ioctl %s, cmd = %x arg = %lx\n", tty->name, cmd, arg); /* */ 1505 printk("cy_ioctl %s, cmd = %x arg = %lx\n", tty->name, cmd, arg); /* */
1506#endif 1506#endif
1507 1507
1508 lock_kernel(); 1508 tty_lock();
1509 1509
1510 switch (cmd) { 1510 switch (cmd) {
1511 case CYGETMON: 1511 case CYGETMON:
@@ -1561,7 +1561,7 @@ cy_ioctl(struct tty_struct *tty, struct file *file,
1561 default: 1561 default:
1562 ret_val = -ENOIOCTLCMD; 1562 ret_val = -ENOIOCTLCMD;
1563 } 1563 }
1564 unlock_kernel(); 1564 tty_unlock();
1565 1565
1566#ifdef SERIAL_DEBUG_OTHER 1566#ifdef SERIAL_DEBUG_OTHER
1567 printk("cy_ioctl done\n"); 1567 printk("cy_ioctl done\n");
@@ -1786,7 +1786,9 @@ block_til_ready(struct tty_struct *tty, struct file *filp,
1786 tty->name, info->count); 1786 tty->name, info->count);
1787 /**/ 1787 /**/
1788#endif 1788#endif
1789 schedule(); 1789 tty_unlock();
1790 schedule();
1791 tty_lock();
1790 } 1792 }
1791 __set_current_state(TASK_RUNNING); 1793 __set_current_state(TASK_RUNNING);
1792 remove_wait_queue(&info->open_wait, &wait); 1794 remove_wait_queue(&info->open_wait, &wait);
diff --git a/drivers/char/specialix.c b/drivers/char/specialix.c
index 2c24fcdc722a..9f8495b4fc8f 100644
--- a/drivers/char/specialix.c
+++ b/drivers/char/specialix.c
@@ -1365,7 +1365,9 @@ static int block_til_ready(struct tty_struct *tty, struct file *filp,
1365 retval = -ERESTARTSYS; 1365 retval = -ERESTARTSYS;
1366 break; 1366 break;
1367 } 1367 }
1368 tty_unlock();
1368 schedule(); 1369 schedule();
1370 tty_lock();
1369 } 1371 }
1370 1372
1371 set_current_state(TASK_RUNNING); 1373 set_current_state(TASK_RUNNING);
@@ -1863,8 +1865,7 @@ static int sx_set_serial_info(struct specialix_port *port,
1863 return -EFAULT; 1865 return -EFAULT;
1864 } 1866 }
1865 1867
1866 lock_kernel(); 1868 mutex_lock(&port->port.mutex);
1867
1868 change_speed = ((port->port.flags & ASYNC_SPD_MASK) != 1869 change_speed = ((port->port.flags & ASYNC_SPD_MASK) !=
1869 (tmp.flags & ASYNC_SPD_MASK)); 1870 (tmp.flags & ASYNC_SPD_MASK));
1870 change_speed |= (tmp.custom_divisor != port->custom_divisor); 1871 change_speed |= (tmp.custom_divisor != port->custom_divisor);
@@ -1875,7 +1876,7 @@ static int sx_set_serial_info(struct specialix_port *port,
1875 ((tmp.flags & ~ASYNC_USR_MASK) != 1876 ((tmp.flags & ~ASYNC_USR_MASK) !=
1876 (port->port.flags & ~ASYNC_USR_MASK))) { 1877 (port->port.flags & ~ASYNC_USR_MASK))) {
1877 func_exit(); 1878 func_exit();
1878 unlock_kernel(); 1879 mutex_unlock(&port->port.mutex);
1879 return -EPERM; 1880 return -EPERM;
1880 } 1881 }
1881 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) | 1882 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) |
@@ -1892,7 +1893,7 @@ static int sx_set_serial_info(struct specialix_port *port,
1892 sx_change_speed(bp, port); 1893 sx_change_speed(bp, port);
1893 1894
1894 func_exit(); 1895 func_exit();
1895 unlock_kernel(); 1896 mutex_unlock(&port->port.mutex);
1896 return 0; 1897 return 0;
1897} 1898}
1898 1899
@@ -1906,7 +1907,7 @@ static int sx_get_serial_info(struct specialix_port *port,
1906 func_enter(); 1907 func_enter();
1907 1908
1908 memset(&tmp, 0, sizeof(tmp)); 1909 memset(&tmp, 0, sizeof(tmp));
1909 lock_kernel(); 1910 mutex_lock(&port->port.mutex);
1910 tmp.type = PORT_CIRRUS; 1911 tmp.type = PORT_CIRRUS;
1911 tmp.line = port - sx_port; 1912 tmp.line = port - sx_port;
1912 tmp.port = bp->base; 1913 tmp.port = bp->base;
@@ -1917,7 +1918,7 @@ static int sx_get_serial_info(struct specialix_port *port,
1917 tmp.closing_wait = port->port.closing_wait * HZ/100; 1918 tmp.closing_wait = port->port.closing_wait * HZ/100;
1918 tmp.custom_divisor = port->custom_divisor; 1919 tmp.custom_divisor = port->custom_divisor;
1919 tmp.xmit_fifo_size = CD186x_NFIFO; 1920 tmp.xmit_fifo_size = CD186x_NFIFO;
1920 unlock_kernel(); 1921 mutex_unlock(&port->port.mutex);
1921 if (copy_to_user(retinfo, &tmp, sizeof(tmp))) { 1922 if (copy_to_user(retinfo, &tmp, sizeof(tmp))) {
1922 func_exit(); 1923 func_exit();
1923 return -EFAULT; 1924 return -EFAULT;
diff --git a/drivers/char/stallion.c b/drivers/char/stallion.c
index 6049fd731924..f2167f8e5aab 100644
--- a/drivers/char/stallion.c
+++ b/drivers/char/stallion.c
@@ -807,7 +807,6 @@ static void stl_waituntilsent(struct tty_struct *tty, int timeout)
807 timeout = HZ; 807 timeout = HZ;
808 tend = jiffies + timeout; 808 tend = jiffies + timeout;
809 809
810 lock_kernel();
811 while (stl_datastate(portp)) { 810 while (stl_datastate(portp)) {
812 if (signal_pending(current)) 811 if (signal_pending(current))
813 break; 812 break;
@@ -815,7 +814,6 @@ static void stl_waituntilsent(struct tty_struct *tty, int timeout)
815 if (time_after_eq(jiffies, tend)) 814 if (time_after_eq(jiffies, tend))
816 break; 815 break;
817 } 816 }
818 unlock_kernel();
819} 817}
820 818
821/*****************************************************************************/ 819/*****************************************************************************/
@@ -1029,6 +1027,8 @@ static int stl_getserial(struct stlport *portp, struct serial_struct __user *sp)
1029 pr_debug("stl_getserial(portp=%p,sp=%p)\n", portp, sp); 1027 pr_debug("stl_getserial(portp=%p,sp=%p)\n", portp, sp);
1030 1028
1031 memset(&sio, 0, sizeof(struct serial_struct)); 1029 memset(&sio, 0, sizeof(struct serial_struct));
1030
1031 mutex_lock(&portp->port.mutex);
1032 sio.line = portp->portnr; 1032 sio.line = portp->portnr;
1033 sio.port = portp->ioaddr; 1033 sio.port = portp->ioaddr;
1034 sio.flags = portp->port.flags; 1034 sio.flags = portp->port.flags;
@@ -1048,6 +1048,7 @@ static int stl_getserial(struct stlport *portp, struct serial_struct __user *sp)
1048 brdp = stl_brds[portp->brdnr]; 1048 brdp = stl_brds[portp->brdnr];
1049 if (brdp != NULL) 1049 if (brdp != NULL)
1050 sio.irq = brdp->irq; 1050 sio.irq = brdp->irq;
1051 mutex_unlock(&portp->port.mutex);
1051 1052
1052 return copy_to_user(sp, &sio, sizeof(struct serial_struct)) ? -EFAULT : 0; 1053 return copy_to_user(sp, &sio, sizeof(struct serial_struct)) ? -EFAULT : 0;
1053} 1054}
@@ -1069,12 +1070,15 @@ static int stl_setserial(struct tty_struct *tty, struct serial_struct __user *sp
1069 1070
1070 if (copy_from_user(&sio, sp, sizeof(struct serial_struct))) 1071 if (copy_from_user(&sio, sp, sizeof(struct serial_struct)))
1071 return -EFAULT; 1072 return -EFAULT;
1073 mutex_lock(&portp->port.mutex);
1072 if (!capable(CAP_SYS_ADMIN)) { 1074 if (!capable(CAP_SYS_ADMIN)) {
1073 if ((sio.baud_base != portp->baud_base) || 1075 if ((sio.baud_base != portp->baud_base) ||
1074 (sio.close_delay != portp->close_delay) || 1076 (sio.close_delay != portp->close_delay) ||
1075 ((sio.flags & ~ASYNC_USR_MASK) != 1077 ((sio.flags & ~ASYNC_USR_MASK) !=
1076 (portp->port.flags & ~ASYNC_USR_MASK))) 1078 (portp->port.flags & ~ASYNC_USR_MASK))) {
1079 mutex_unlock(&portp->port.mutex);
1077 return -EPERM; 1080 return -EPERM;
1081 }
1078 } 1082 }
1079 1083
1080 portp->port.flags = (portp->port.flags & ~ASYNC_USR_MASK) | 1084 portp->port.flags = (portp->port.flags & ~ASYNC_USR_MASK) |
@@ -1083,6 +1087,7 @@ static int stl_setserial(struct tty_struct *tty, struct serial_struct __user *sp
1083 portp->close_delay = sio.close_delay; 1087 portp->close_delay = sio.close_delay;
1084 portp->closing_wait = sio.closing_wait; 1088 portp->closing_wait = sio.closing_wait;
1085 portp->custom_divisor = sio.custom_divisor; 1089 portp->custom_divisor = sio.custom_divisor;
1090 mutex_unlock(&portp->port.mutex);
1086 stl_setport(portp, tty->termios); 1091 stl_setport(portp, tty->termios);
1087 return 0; 1092 return 0;
1088} 1093}
@@ -1147,8 +1152,6 @@ static int stl_ioctl(struct tty_struct *tty, struct file *file, unsigned int cmd
1147 1152
1148 rc = 0; 1153 rc = 0;
1149 1154
1150 lock_kernel();
1151
1152 switch (cmd) { 1155 switch (cmd) {
1153 case TIOCGSERIAL: 1156 case TIOCGSERIAL:
1154 rc = stl_getserial(portp, argp); 1157 rc = stl_getserial(portp, argp);
@@ -1173,7 +1176,6 @@ static int stl_ioctl(struct tty_struct *tty, struct file *file, unsigned int cmd
1173 rc = -ENOIOCTLCMD; 1176 rc = -ENOIOCTLCMD;
1174 break; 1177 break;
1175 } 1178 }
1176 unlock_kernel();
1177 return rc; 1179 return rc;
1178} 1180}
1179 1181
@@ -2327,6 +2329,7 @@ static int stl_getportstats(struct tty_struct *tty, struct stlport *portp, comst
2327 return -ENODEV; 2329 return -ENODEV;
2328 } 2330 }
2329 2331
2332 mutex_lock(&portp->port.mutex);
2330 portp->stats.state = portp->istate; 2333 portp->stats.state = portp->istate;
2331 portp->stats.flags = portp->port.flags; 2334 portp->stats.flags = portp->port.flags;
2332 portp->stats.hwid = portp->hwid; 2335 portp->stats.hwid = portp->hwid;
@@ -2358,6 +2361,7 @@ static int stl_getportstats(struct tty_struct *tty, struct stlport *portp, comst
2358 (STL_TXBUFSIZE - (tail - head)); 2361 (STL_TXBUFSIZE - (tail - head));
2359 2362
2360 portp->stats.signals = (unsigned long) stl_getsignals(portp); 2363 portp->stats.signals = (unsigned long) stl_getsignals(portp);
2364 mutex_unlock(&portp->port.mutex);
2361 2365
2362 return copy_to_user(cp, &portp->stats, 2366 return copy_to_user(cp, &portp->stats,
2363 sizeof(comstats_t)) ? -EFAULT : 0; 2367 sizeof(comstats_t)) ? -EFAULT : 0;
@@ -2382,10 +2386,12 @@ static int stl_clrportstats(struct stlport *portp, comstats_t __user *cp)
2382 return -ENODEV; 2386 return -ENODEV;
2383 } 2387 }
2384 2388
2389 mutex_lock(&portp->port.mutex);
2385 memset(&portp->stats, 0, sizeof(comstats_t)); 2390 memset(&portp->stats, 0, sizeof(comstats_t));
2386 portp->stats.brd = portp->brdnr; 2391 portp->stats.brd = portp->brdnr;
2387 portp->stats.panel = portp->panelnr; 2392 portp->stats.panel = portp->panelnr;
2388 portp->stats.port = portp->portnr; 2393 portp->stats.port = portp->portnr;
2394 mutex_unlock(&portp->port.mutex);
2389 return copy_to_user(cp, &portp->stats, 2395 return copy_to_user(cp, &portp->stats,
2390 sizeof(comstats_t)) ? -EFAULT : 0; 2396 sizeof(comstats_t)) ? -EFAULT : 0;
2391} 2397}
@@ -2451,7 +2457,6 @@ static long stl_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
2451 return -ENODEV; 2457 return -ENODEV;
2452 rc = 0; 2458 rc = 0;
2453 2459
2454 lock_kernel();
2455 switch (cmd) { 2460 switch (cmd) {
2456 case COM_GETPORTSTATS: 2461 case COM_GETPORTSTATS:
2457 rc = stl_getportstats(NULL, NULL, argp); 2462 rc = stl_getportstats(NULL, NULL, argp);
@@ -2472,7 +2477,6 @@ static long stl_memioctl(struct file *fp, unsigned int cmd, unsigned long arg)
2472 rc = -ENOIOCTLCMD; 2477 rc = -ENOIOCTLCMD;
2473 break; 2478 break;
2474 } 2479 }
2475 unlock_kernel();
2476 return rc; 2480 return rc;
2477} 2481}
2478 2482
diff --git a/drivers/char/sx.c b/drivers/char/sx.c
index a81ec4fcf6ff..5b24db4ff7f1 100644
--- a/drivers/char/sx.c
+++ b/drivers/char/sx.c
@@ -1699,7 +1699,7 @@ static long sx_fw_ioctl(struct file *filp, unsigned int cmd,
1699 if (!capable(CAP_SYS_RAWIO)) 1699 if (!capable(CAP_SYS_RAWIO))
1700 return -EPERM; 1700 return -EPERM;
1701 1701
1702 lock_kernel(); 1702 tty_lock();
1703 1703
1704 sx_dprintk(SX_DEBUG_FIRMWARE, "IOCTL %x: %lx\n", cmd, arg); 1704 sx_dprintk(SX_DEBUG_FIRMWARE, "IOCTL %x: %lx\n", cmd, arg);
1705 1705
@@ -1848,7 +1848,7 @@ static long sx_fw_ioctl(struct file *filp, unsigned int cmd,
1848 break; 1848 break;
1849 } 1849 }
1850out: 1850out:
1851 unlock_kernel(); 1851 tty_unlock();
1852 func_exit(); 1852 func_exit();
1853 return rc; 1853 return rc;
1854} 1854}
@@ -1859,7 +1859,7 @@ static int sx_break(struct tty_struct *tty, int flag)
1859 int rv; 1859 int rv;
1860 1860
1861 func_enter(); 1861 func_enter();
1862 lock_kernel(); 1862 tty_lock();
1863 1863
1864 if (flag) 1864 if (flag)
1865 rv = sx_send_command(port, HS_START, -1, HS_IDLE_BREAK); 1865 rv = sx_send_command(port, HS_START, -1, HS_IDLE_BREAK);
@@ -1868,7 +1868,7 @@ static int sx_break(struct tty_struct *tty, int flag)
1868 if (rv != 1) 1868 if (rv != 1)
1869 printk(KERN_ERR "sx: couldn't send break (%x).\n", 1869 printk(KERN_ERR "sx: couldn't send break (%x).\n",
1870 read_sx_byte(port->board, CHAN_OFFSET(port, hi_hstat))); 1870 read_sx_byte(port->board, CHAN_OFFSET(port, hi_hstat)));
1871 unlock_kernel(); 1871 tty_unlock();
1872 func_exit(); 1872 func_exit();
1873 return 0; 1873 return 0;
1874} 1874}
@@ -1909,7 +1909,7 @@ static int sx_ioctl(struct tty_struct *tty, struct file *filp,
1909 /* func_enter2(); */ 1909 /* func_enter2(); */
1910 1910
1911 rc = 0; 1911 rc = 0;
1912 lock_kernel(); 1912 tty_lock();
1913 switch (cmd) { 1913 switch (cmd) {
1914 case TIOCGSERIAL: 1914 case TIOCGSERIAL:
1915 rc = gs_getserial(&port->gs, argp); 1915 rc = gs_getserial(&port->gs, argp);
@@ -1921,7 +1921,7 @@ static int sx_ioctl(struct tty_struct *tty, struct file *filp,
1921 rc = -ENOIOCTLCMD; 1921 rc = -ENOIOCTLCMD;
1922 break; 1922 break;
1923 } 1923 }
1924 unlock_kernel(); 1924 tty_unlock();
1925 1925
1926 /* func_exit(); */ 1926 /* func_exit(); */
1927 return rc; 1927 return rc;
diff --git a/drivers/char/synclink.c b/drivers/char/synclink.c
index 0658fc548222..a2a58004e188 100644
--- a/drivers/char/synclink.c
+++ b/drivers/char/synclink.c
@@ -81,7 +81,6 @@
81#include <linux/mm.h> 81#include <linux/mm.h>
82#include <linux/seq_file.h> 82#include <linux/seq_file.h>
83#include <linux/slab.h> 83#include <linux/slab.h>
84#include <linux/smp_lock.h>
85#include <linux/delay.h> 84#include <linux/delay.h>
86#include <linux/netdevice.h> 85#include <linux/netdevice.h>
87#include <linux/vmalloc.h> 86#include <linux/vmalloc.h>
@@ -2436,7 +2435,9 @@ static int mgsl_get_stats(struct mgsl_struct * info, struct mgsl_icount __user *
2436 if (!user_icount) { 2435 if (!user_icount) {
2437 memset(&info->icount, 0, sizeof(info->icount)); 2436 memset(&info->icount, 0, sizeof(info->icount));
2438 } else { 2437 } else {
2438 mutex_lock(&info->port.mutex);
2439 COPY_TO_USER(err, user_icount, &info->icount, sizeof(struct mgsl_icount)); 2439 COPY_TO_USER(err, user_icount, &info->icount, sizeof(struct mgsl_icount));
2440 mutex_unlock(&info->port.mutex);
2440 if (err) 2441 if (err)
2441 return -EFAULT; 2442 return -EFAULT;
2442 } 2443 }
@@ -2461,7 +2462,9 @@ static int mgsl_get_params(struct mgsl_struct * info, MGSL_PARAMS __user *user_p
2461 printk("%s(%d):mgsl_get_params(%s)\n", 2462 printk("%s(%d):mgsl_get_params(%s)\n",
2462 __FILE__,__LINE__, info->device_name); 2463 __FILE__,__LINE__, info->device_name);
2463 2464
2465 mutex_lock(&info->port.mutex);
2464 COPY_TO_USER(err,user_params, &info->params, sizeof(MGSL_PARAMS)); 2466 COPY_TO_USER(err,user_params, &info->params, sizeof(MGSL_PARAMS));
2467 mutex_unlock(&info->port.mutex);
2465 if (err) { 2468 if (err) {
2466 if ( debug_level >= DEBUG_LEVEL_INFO ) 2469 if ( debug_level >= DEBUG_LEVEL_INFO )
2467 printk( "%s(%d):mgsl_get_params(%s) user buffer copy failed\n", 2470 printk( "%s(%d):mgsl_get_params(%s) user buffer copy failed\n",
@@ -2501,11 +2504,13 @@ static int mgsl_set_params(struct mgsl_struct * info, MGSL_PARAMS __user *new_pa
2501 return -EFAULT; 2504 return -EFAULT;
2502 } 2505 }
2503 2506
2507 mutex_lock(&info->port.mutex);
2504 spin_lock_irqsave(&info->irq_spinlock,flags); 2508 spin_lock_irqsave(&info->irq_spinlock,flags);
2505 memcpy(&info->params,&tmp_params,sizeof(MGSL_PARAMS)); 2509 memcpy(&info->params,&tmp_params,sizeof(MGSL_PARAMS));
2506 spin_unlock_irqrestore(&info->irq_spinlock,flags); 2510 spin_unlock_irqrestore(&info->irq_spinlock,flags);
2507 2511
2508 mgsl_change_params(info); 2512 mgsl_change_params(info);
2513 mutex_unlock(&info->port.mutex);
2509 2514
2510 return 0; 2515 return 0;
2511 2516
@@ -2935,7 +2940,6 @@ static int mgsl_ioctl(struct tty_struct *tty, struct file * file,
2935 unsigned int cmd, unsigned long arg) 2940 unsigned int cmd, unsigned long arg)
2936{ 2941{
2937 struct mgsl_struct * info = tty->driver_data; 2942 struct mgsl_struct * info = tty->driver_data;
2938 int ret;
2939 2943
2940 if (debug_level >= DEBUG_LEVEL_INFO) 2944 if (debug_level >= DEBUG_LEVEL_INFO)
2941 printk("%s(%d):mgsl_ioctl %s cmd=%08X\n", __FILE__,__LINE__, 2945 printk("%s(%d):mgsl_ioctl %s cmd=%08X\n", __FILE__,__LINE__,
@@ -2950,10 +2954,7 @@ static int mgsl_ioctl(struct tty_struct *tty, struct file * file,
2950 return -EIO; 2954 return -EIO;
2951 } 2955 }
2952 2956
2953 lock_kernel(); 2957 return mgsl_ioctl_common(info, cmd, arg);
2954 ret = mgsl_ioctl_common(info, cmd, arg);
2955 unlock_kernel();
2956 return ret;
2957} 2958}
2958 2959
2959static int mgsl_ioctl_common(struct mgsl_struct *info, unsigned int cmd, unsigned long arg) 2960static int mgsl_ioctl_common(struct mgsl_struct *info, unsigned int cmd, unsigned long arg)
@@ -3109,12 +3110,14 @@ static void mgsl_close(struct tty_struct *tty, struct file * filp)
3109 3110
3110 if (tty_port_close_start(&info->port, tty, filp) == 0) 3111 if (tty_port_close_start(&info->port, tty, filp) == 0)
3111 goto cleanup; 3112 goto cleanup;
3112 3113
3114 mutex_lock(&info->port.mutex);
3113 if (info->port.flags & ASYNC_INITIALIZED) 3115 if (info->port.flags & ASYNC_INITIALIZED)
3114 mgsl_wait_until_sent(tty, info->timeout); 3116 mgsl_wait_until_sent(tty, info->timeout);
3115 mgsl_flush_buffer(tty); 3117 mgsl_flush_buffer(tty);
3116 tty_ldisc_flush(tty); 3118 tty_ldisc_flush(tty);
3117 shutdown(info); 3119 shutdown(info);
3120 mutex_unlock(&info->port.mutex);
3118 3121
3119 tty_port_close_end(&info->port, tty); 3122 tty_port_close_end(&info->port, tty);
3120 info->port.tty = NULL; 3123 info->port.tty = NULL;
@@ -3162,7 +3165,6 @@ static void mgsl_wait_until_sent(struct tty_struct *tty, int timeout)
3162 * Note: use tight timings here to satisfy the NIST-PCTS. 3165 * Note: use tight timings here to satisfy the NIST-PCTS.
3163 */ 3166 */
3164 3167
3165 lock_kernel();
3166 if ( info->params.data_rate ) { 3168 if ( info->params.data_rate ) {
3167 char_time = info->timeout/(32 * 5); 3169 char_time = info->timeout/(32 * 5);
3168 if (!char_time) 3170 if (!char_time)
@@ -3192,7 +3194,6 @@ static void mgsl_wait_until_sent(struct tty_struct *tty, int timeout)
3192 break; 3194 break;
3193 } 3195 }
3194 } 3196 }
3195 unlock_kernel();
3196 3197
3197exit: 3198exit:
3198 if (debug_level >= DEBUG_LEVEL_INFO) 3199 if (debug_level >= DEBUG_LEVEL_INFO)
@@ -3348,7 +3349,9 @@ static int block_til_ready(struct tty_struct *tty, struct file * filp,
3348 printk("%s(%d):block_til_ready blocking on %s count=%d\n", 3349 printk("%s(%d):block_til_ready blocking on %s count=%d\n",
3349 __FILE__,__LINE__, tty->driver->name, port->count ); 3350 __FILE__,__LINE__, tty->driver->name, port->count );
3350 3351
3352 tty_unlock();
3351 schedule(); 3353 schedule();
3354 tty_lock();
3352 } 3355 }
3353 3356
3354 set_current_state(TASK_RUNNING); 3357 set_current_state(TASK_RUNNING);
diff --git a/drivers/char/synclink_gt.c b/drivers/char/synclink_gt.c
index 334cf5c8c8b6..fef80cfcab5c 100644
--- a/drivers/char/synclink_gt.c
+++ b/drivers/char/synclink_gt.c
@@ -40,8 +40,8 @@
40#define DBGBH(fmt) if (debug_level >= DEBUG_LEVEL_BH) printk fmt 40#define DBGBH(fmt) if (debug_level >= DEBUG_LEVEL_BH) printk fmt
41#define DBGISR(fmt) if (debug_level >= DEBUG_LEVEL_ISR) printk fmt 41#define DBGISR(fmt) if (debug_level >= DEBUG_LEVEL_ISR) printk fmt
42#define DBGDATA(info, buf, size, label) if (debug_level >= DEBUG_LEVEL_DATA) trace_block((info), (buf), (size), (label)) 42#define DBGDATA(info, buf, size, label) if (debug_level >= DEBUG_LEVEL_DATA) trace_block((info), (buf), (size), (label))
43//#define DBGTBUF(info) dump_tbufs(info) 43/*#define DBGTBUF(info) dump_tbufs(info)*/
44//#define DBGRBUF(info) dump_rbufs(info) 44/*#define DBGRBUF(info) dump_rbufs(info)*/
45 45
46 46
47#include <linux/module.h> 47#include <linux/module.h>
@@ -62,7 +62,6 @@
62#include <linux/mm.h> 62#include <linux/mm.h>
63#include <linux/seq_file.h> 63#include <linux/seq_file.h>
64#include <linux/slab.h> 64#include <linux/slab.h>
65#include <linux/smp_lock.h>
66#include <linux/netdevice.h> 65#include <linux/netdevice.h>
67#include <linux/vmalloc.h> 66#include <linux/vmalloc.h>
68#include <linux/init.h> 67#include <linux/init.h>
@@ -676,12 +675,14 @@ static int open(struct tty_struct *tty, struct file *filp)
676 goto cleanup; 675 goto cleanup;
677 } 676 }
678 677
678 mutex_lock(&info->port.mutex);
679 info->port.tty->low_latency = (info->port.flags & ASYNC_LOW_LATENCY) ? 1 : 0; 679 info->port.tty->low_latency = (info->port.flags & ASYNC_LOW_LATENCY) ? 1 : 0;
680 680
681 spin_lock_irqsave(&info->netlock, flags); 681 spin_lock_irqsave(&info->netlock, flags);
682 if (info->netcount) { 682 if (info->netcount) {
683 retval = -EBUSY; 683 retval = -EBUSY;
684 spin_unlock_irqrestore(&info->netlock, flags); 684 spin_unlock_irqrestore(&info->netlock, flags);
685 mutex_unlock(&info->port.mutex);
685 goto cleanup; 686 goto cleanup;
686 } 687 }
687 info->port.count++; 688 info->port.count++;
@@ -693,7 +694,7 @@ static int open(struct tty_struct *tty, struct file *filp)
693 if (retval < 0) 694 if (retval < 0)
694 goto cleanup; 695 goto cleanup;
695 } 696 }
696 697 mutex_unlock(&info->port.mutex);
697 retval = block_til_ready(tty, filp, info); 698 retval = block_til_ready(tty, filp, info);
698 if (retval) { 699 if (retval) {
699 DBGINFO(("%s block_til_ready rc=%d\n", info->device_name, retval)); 700 DBGINFO(("%s block_til_ready rc=%d\n", info->device_name, retval));
@@ -725,12 +726,14 @@ static void close(struct tty_struct *tty, struct file *filp)
725 if (tty_port_close_start(&info->port, tty, filp) == 0) 726 if (tty_port_close_start(&info->port, tty, filp) == 0)
726 goto cleanup; 727 goto cleanup;
727 728
729 mutex_lock(&info->port.mutex);
728 if (info->port.flags & ASYNC_INITIALIZED) 730 if (info->port.flags & ASYNC_INITIALIZED)
729 wait_until_sent(tty, info->timeout); 731 wait_until_sent(tty, info->timeout);
730 flush_buffer(tty); 732 flush_buffer(tty);
731 tty_ldisc_flush(tty); 733 tty_ldisc_flush(tty);
732 734
733 shutdown(info); 735 shutdown(info);
736 mutex_unlock(&info->port.mutex);
734 737
735 tty_port_close_end(&info->port, tty); 738 tty_port_close_end(&info->port, tty);
736 info->port.tty = NULL; 739 info->port.tty = NULL;
@@ -741,17 +744,23 @@ cleanup:
741static void hangup(struct tty_struct *tty) 744static void hangup(struct tty_struct *tty)
742{ 745{
743 struct slgt_info *info = tty->driver_data; 746 struct slgt_info *info = tty->driver_data;
747 unsigned long flags;
744 748
745 if (sanity_check(info, tty->name, "hangup")) 749 if (sanity_check(info, tty->name, "hangup"))
746 return; 750 return;
747 DBGINFO(("%s hangup\n", info->device_name)); 751 DBGINFO(("%s hangup\n", info->device_name));
748 752
749 flush_buffer(tty); 753 flush_buffer(tty);
754
755 mutex_lock(&info->port.mutex);
750 shutdown(info); 756 shutdown(info);
751 757
758 spin_lock_irqsave(&info->port.lock, flags);
752 info->port.count = 0; 759 info->port.count = 0;
753 info->port.flags &= ~ASYNC_NORMAL_ACTIVE; 760 info->port.flags &= ~ASYNC_NORMAL_ACTIVE;
754 info->port.tty = NULL; 761 info->port.tty = NULL;
762 spin_unlock_irqrestore(&info->port.lock, flags);
763 mutex_unlock(&info->port.mutex);
755 764
756 wake_up_interruptible(&info->port.open_wait); 765 wake_up_interruptible(&info->port.open_wait);
757} 766}
@@ -901,8 +910,6 @@ static void wait_until_sent(struct tty_struct *tty, int timeout)
901 * Note: use tight timings here to satisfy the NIST-PCTS. 910 * Note: use tight timings here to satisfy the NIST-PCTS.
902 */ 911 */
903 912
904 lock_kernel();
905
906 if (info->params.data_rate) { 913 if (info->params.data_rate) {
907 char_time = info->timeout/(32 * 5); 914 char_time = info->timeout/(32 * 5);
908 if (!char_time) 915 if (!char_time)
@@ -920,8 +927,6 @@ static void wait_until_sent(struct tty_struct *tty, int timeout)
920 if (timeout && time_after(jiffies, orig_jiffies + timeout)) 927 if (timeout && time_after(jiffies, orig_jiffies + timeout))
921 break; 928 break;
922 } 929 }
923 unlock_kernel();
924
925exit: 930exit:
926 DBGINFO(("%s wait_until_sent exit\n", info->device_name)); 931 DBGINFO(("%s wait_until_sent exit\n", info->device_name));
927} 932}
@@ -1041,8 +1046,37 @@ static int ioctl(struct tty_struct *tty, struct file *file,
1041 return -EIO; 1046 return -EIO;
1042 } 1047 }
1043 1048
1044 lock_kernel(); 1049 switch (cmd) {
1045 1050 case MGSL_IOCWAITEVENT:
1051 return wait_mgsl_event(info, argp);
1052 case TIOCMIWAIT:
1053 return modem_input_wait(info,(int)arg);
1054 case TIOCGICOUNT:
1055 spin_lock_irqsave(&info->lock,flags);
1056 cnow = info->icount;
1057 spin_unlock_irqrestore(&info->lock,flags);
1058 p_cuser = argp;
1059 if (put_user(cnow.cts, &p_cuser->cts) ||
1060 put_user(cnow.dsr, &p_cuser->dsr) ||
1061 put_user(cnow.rng, &p_cuser->rng) ||
1062 put_user(cnow.dcd, &p_cuser->dcd) ||
1063 put_user(cnow.rx, &p_cuser->rx) ||
1064 put_user(cnow.tx, &p_cuser->tx) ||
1065 put_user(cnow.frame, &p_cuser->frame) ||
1066 put_user(cnow.overrun, &p_cuser->overrun) ||
1067 put_user(cnow.parity, &p_cuser->parity) ||
1068 put_user(cnow.brk, &p_cuser->brk) ||
1069 put_user(cnow.buf_overrun, &p_cuser->buf_overrun))
1070 return -EFAULT;
1071 return 0;
1072 case MGSL_IOCSGPIO:
1073 return set_gpio(info, argp);
1074 case MGSL_IOCGGPIO:
1075 return get_gpio(info, argp);
1076 case MGSL_IOCWAITGPIO:
1077 return wait_gpio(info, argp);
1078 }
1079 mutex_lock(&info->port.mutex);
1046 switch (cmd) { 1080 switch (cmd) {
1047 case MGSL_IOCGPARAMS: 1081 case MGSL_IOCGPARAMS:
1048 ret = get_params(info, argp); 1082 ret = get_params(info, argp);
@@ -1068,50 +1102,16 @@ static int ioctl(struct tty_struct *tty, struct file *file,
1068 case MGSL_IOCGSTATS: 1102 case MGSL_IOCGSTATS:
1069 ret = get_stats(info, argp); 1103 ret = get_stats(info, argp);
1070 break; 1104 break;
1071 case MGSL_IOCWAITEVENT:
1072 ret = wait_mgsl_event(info, argp);
1073 break;
1074 case TIOCMIWAIT:
1075 ret = modem_input_wait(info,(int)arg);
1076 break;
1077 case MGSL_IOCGIF: 1105 case MGSL_IOCGIF:
1078 ret = get_interface(info, argp); 1106 ret = get_interface(info, argp);
1079 break; 1107 break;
1080 case MGSL_IOCSIF: 1108 case MGSL_IOCSIF:
1081 ret = set_interface(info,(int)arg); 1109 ret = set_interface(info,(int)arg);
1082 break; 1110 break;
1083 case MGSL_IOCSGPIO:
1084 ret = set_gpio(info, argp);
1085 break;
1086 case MGSL_IOCGGPIO:
1087 ret = get_gpio(info, argp);
1088 break;
1089 case MGSL_IOCWAITGPIO:
1090 ret = wait_gpio(info, argp);
1091 break;
1092 case TIOCGICOUNT:
1093 spin_lock_irqsave(&info->lock,flags);
1094 cnow = info->icount;
1095 spin_unlock_irqrestore(&info->lock,flags);
1096 p_cuser = argp;
1097 if (put_user(cnow.cts, &p_cuser->cts) ||
1098 put_user(cnow.dsr, &p_cuser->dsr) ||
1099 put_user(cnow.rng, &p_cuser->rng) ||
1100 put_user(cnow.dcd, &p_cuser->dcd) ||
1101 put_user(cnow.rx, &p_cuser->rx) ||
1102 put_user(cnow.tx, &p_cuser->tx) ||
1103 put_user(cnow.frame, &p_cuser->frame) ||
1104 put_user(cnow.overrun, &p_cuser->overrun) ||
1105 put_user(cnow.parity, &p_cuser->parity) ||
1106 put_user(cnow.brk, &p_cuser->brk) ||
1107 put_user(cnow.buf_overrun, &p_cuser->buf_overrun))
1108 ret = -EFAULT;
1109 ret = 0;
1110 break;
1111 default: 1111 default:
1112 ret = -ENOIOCTLCMD; 1112 ret = -ENOIOCTLCMD;
1113 } 1113 }
1114 unlock_kernel(); 1114 mutex_unlock(&info->port.mutex);
1115 return ret; 1115 return ret;
1116} 1116}
1117 1117
@@ -3244,7 +3244,9 @@ static int block_til_ready(struct tty_struct *tty, struct file *filp,
3244 } 3244 }
3245 3245
3246 DBGINFO(("%s block_til_ready wait\n", tty->driver->name)); 3246 DBGINFO(("%s block_til_ready wait\n", tty->driver->name));
3247 tty_unlock();
3247 schedule(); 3248 schedule();
3249 tty_lock();
3248 } 3250 }
3249 3251
3250 set_current_state(TASK_RUNNING); 3252 set_current_state(TASK_RUNNING);
diff --git a/drivers/char/synclinkmp.c b/drivers/char/synclinkmp.c
index 2b18adc4ee19..e56caf7d82aa 100644
--- a/drivers/char/synclinkmp.c
+++ b/drivers/char/synclinkmp.c
@@ -52,7 +52,6 @@
52#include <linux/mm.h> 52#include <linux/mm.h>
53#include <linux/seq_file.h> 53#include <linux/seq_file.h>
54#include <linux/slab.h> 54#include <linux/slab.h>
55#include <linux/smp_lock.h>
56#include <linux/netdevice.h> 55#include <linux/netdevice.h>
57#include <linux/vmalloc.h> 56#include <linux/vmalloc.h>
58#include <linux/init.h> 57#include <linux/init.h>
@@ -813,13 +812,15 @@ static void close(struct tty_struct *tty, struct file *filp)
813 812
814 if (tty_port_close_start(&info->port, tty, filp) == 0) 813 if (tty_port_close_start(&info->port, tty, filp) == 0)
815 goto cleanup; 814 goto cleanup;
816 815
816 mutex_lock(&info->port.mutex);
817 if (info->port.flags & ASYNC_INITIALIZED) 817 if (info->port.flags & ASYNC_INITIALIZED)
818 wait_until_sent(tty, info->timeout); 818 wait_until_sent(tty, info->timeout);
819 819
820 flush_buffer(tty); 820 flush_buffer(tty);
821 tty_ldisc_flush(tty); 821 tty_ldisc_flush(tty);
822 shutdown(info); 822 shutdown(info);
823 mutex_unlock(&info->port.mutex);
823 824
824 tty_port_close_end(&info->port, tty); 825 tty_port_close_end(&info->port, tty);
825 info->port.tty = NULL; 826 info->port.tty = NULL;
@@ -835,6 +836,7 @@ cleanup:
835static void hangup(struct tty_struct *tty) 836static void hangup(struct tty_struct *tty)
836{ 837{
837 SLMP_INFO *info = tty->driver_data; 838 SLMP_INFO *info = tty->driver_data;
839 unsigned long flags;
838 840
839 if (debug_level >= DEBUG_LEVEL_INFO) 841 if (debug_level >= DEBUG_LEVEL_INFO)
840 printk("%s(%d):%s hangup()\n", 842 printk("%s(%d):%s hangup()\n",
@@ -843,12 +845,16 @@ static void hangup(struct tty_struct *tty)
843 if (sanity_check(info, tty->name, "hangup")) 845 if (sanity_check(info, tty->name, "hangup"))
844 return; 846 return;
845 847
848 mutex_lock(&info->port.mutex);
846 flush_buffer(tty); 849 flush_buffer(tty);
847 shutdown(info); 850 shutdown(info);
848 851
852 spin_lock_irqsave(&info->port.lock, flags);
849 info->port.count = 0; 853 info->port.count = 0;
850 info->port.flags &= ~ASYNC_NORMAL_ACTIVE; 854 info->port.flags &= ~ASYNC_NORMAL_ACTIVE;
851 info->port.tty = NULL; 855 info->port.tty = NULL;
856 spin_unlock_irqrestore(&info->port.lock, flags);
857 mutex_unlock(&info->port.mutex);
852 858
853 wake_up_interruptible(&info->port.open_wait); 859 wake_up_interruptible(&info->port.open_wait);
854} 860}
@@ -1062,9 +1068,7 @@ static void wait_until_sent(struct tty_struct *tty, int timeout)
1062 if (sanity_check(info, tty->name, "wait_until_sent")) 1068 if (sanity_check(info, tty->name, "wait_until_sent"))
1063 return; 1069 return;
1064 1070
1065 lock_kernel(); 1071 if (!test_bit(ASYNCB_INITIALIZED, &info->port.flags))
1066
1067 if (!(info->port.flags & ASYNC_INITIALIZED))
1068 goto exit; 1072 goto exit;
1069 1073
1070 orig_jiffies = jiffies; 1074 orig_jiffies = jiffies;
@@ -1094,8 +1098,10 @@ static void wait_until_sent(struct tty_struct *tty, int timeout)
1094 break; 1098 break;
1095 } 1099 }
1096 } else { 1100 } else {
1097 //TODO: determine if there is something similar to USC16C32 1101 /*
1098 // TXSTATUS_ALL_SENT status 1102 * TODO: determine if there is something similar to USC16C32
1103 * TXSTATUS_ALL_SENT status
1104 */
1099 while ( info->tx_active && info->tx_enabled) { 1105 while ( info->tx_active && info->tx_enabled) {
1100 msleep_interruptible(jiffies_to_msecs(char_time)); 1106 msleep_interruptible(jiffies_to_msecs(char_time));
1101 if (signal_pending(current)) 1107 if (signal_pending(current))
@@ -1106,7 +1112,6 @@ static void wait_until_sent(struct tty_struct *tty, int timeout)
1106 } 1112 }
1107 1113
1108exit: 1114exit:
1109 unlock_kernel();
1110 if (debug_level >= DEBUG_LEVEL_INFO) 1115 if (debug_level >= DEBUG_LEVEL_INFO)
1111 printk("%s(%d):%s wait_until_sent() exit\n", 1116 printk("%s(%d):%s wait_until_sent() exit\n",
1112 __FILE__,__LINE__, info->device_name ); 1117 __FILE__,__LINE__, info->device_name );
@@ -1122,7 +1127,6 @@ static int write_room(struct tty_struct *tty)
1122 if (sanity_check(info, tty->name, "write_room")) 1127 if (sanity_check(info, tty->name, "write_room"))
1123 return 0; 1128 return 0;
1124 1129
1125 lock_kernel();
1126 if (info->params.mode == MGSL_MODE_HDLC) { 1130 if (info->params.mode == MGSL_MODE_HDLC) {
1127 ret = (info->tx_active) ? 0 : HDLC_MAX_FRAME_SIZE; 1131 ret = (info->tx_active) ? 0 : HDLC_MAX_FRAME_SIZE;
1128 } else { 1132 } else {
@@ -1130,7 +1134,6 @@ static int write_room(struct tty_struct *tty)
1130 if (ret < 0) 1134 if (ret < 0)
1131 ret = 0; 1135 ret = 0;
1132 } 1136 }
1133 unlock_kernel();
1134 1137
1135 if (debug_level >= DEBUG_LEVEL_INFO) 1138 if (debug_level >= DEBUG_LEVEL_INFO)
1136 printk("%s(%d):%s write_room()=%d\n", 1139 printk("%s(%d):%s write_room()=%d\n",
@@ -1251,7 +1254,7 @@ static void tx_release(struct tty_struct *tty)
1251 * 1254 *
1252 * Return Value: 0 if success, otherwise error code 1255 * Return Value: 0 if success, otherwise error code
1253 */ 1256 */
1254static int do_ioctl(struct tty_struct *tty, struct file *file, 1257static int ioctl(struct tty_struct *tty, struct file *file,
1255 unsigned int cmd, unsigned long arg) 1258 unsigned int cmd, unsigned long arg)
1256{ 1259{
1257 SLMP_INFO *info = tty->driver_data; 1260 SLMP_INFO *info = tty->driver_data;
@@ -1341,16 +1344,6 @@ static int do_ioctl(struct tty_struct *tty, struct file *file,
1341 return 0; 1344 return 0;
1342} 1345}
1343 1346
1344static int ioctl(struct tty_struct *tty, struct file *file,
1345 unsigned int cmd, unsigned long arg)
1346{
1347 int ret;
1348 lock_kernel();
1349 ret = do_ioctl(tty, file, cmd, arg);
1350 unlock_kernel();
1351 return ret;
1352}
1353
1354/* 1347/*
1355 * /proc fs routines.... 1348 * /proc fs routines....
1356 */ 1349 */
@@ -2883,7 +2876,9 @@ static int get_stats(SLMP_INFO * info, struct mgsl_icount __user *user_icount)
2883 if (!user_icount) { 2876 if (!user_icount) {
2884 memset(&info->icount, 0, sizeof(info->icount)); 2877 memset(&info->icount, 0, sizeof(info->icount));
2885 } else { 2878 } else {
2879 mutex_lock(&info->port.mutex);
2886 COPY_TO_USER(err, user_icount, &info->icount, sizeof(struct mgsl_icount)); 2880 COPY_TO_USER(err, user_icount, &info->icount, sizeof(struct mgsl_icount));
2881 mutex_unlock(&info->port.mutex);
2887 if (err) 2882 if (err)
2888 return -EFAULT; 2883 return -EFAULT;
2889 } 2884 }
@@ -2898,7 +2893,9 @@ static int get_params(SLMP_INFO * info, MGSL_PARAMS __user *user_params)
2898 printk("%s(%d):%s get_params()\n", 2893 printk("%s(%d):%s get_params()\n",
2899 __FILE__,__LINE__, info->device_name); 2894 __FILE__,__LINE__, info->device_name);
2900 2895
2896 mutex_lock(&info->port.mutex);
2901 COPY_TO_USER(err,user_params, &info->params, sizeof(MGSL_PARAMS)); 2897 COPY_TO_USER(err,user_params, &info->params, sizeof(MGSL_PARAMS));
2898 mutex_unlock(&info->port.mutex);
2902 if (err) { 2899 if (err) {
2903 if ( debug_level >= DEBUG_LEVEL_INFO ) 2900 if ( debug_level >= DEBUG_LEVEL_INFO )
2904 printk( "%s(%d):%s get_params() user buffer copy failed\n", 2901 printk( "%s(%d):%s get_params() user buffer copy failed\n",
@@ -2926,11 +2923,13 @@ static int set_params(SLMP_INFO * info, MGSL_PARAMS __user *new_params)
2926 return -EFAULT; 2923 return -EFAULT;
2927 } 2924 }
2928 2925
2926 mutex_lock(&info->port.mutex);
2929 spin_lock_irqsave(&info->lock,flags); 2927 spin_lock_irqsave(&info->lock,flags);
2930 memcpy(&info->params,&tmp_params,sizeof(MGSL_PARAMS)); 2928 memcpy(&info->params,&tmp_params,sizeof(MGSL_PARAMS));
2931 spin_unlock_irqrestore(&info->lock,flags); 2929 spin_unlock_irqrestore(&info->lock,flags);
2932 2930
2933 change_params(info); 2931 change_params(info);
2932 mutex_unlock(&info->port.mutex);
2934 2933
2935 return 0; 2934 return 0;
2936} 2935}
@@ -3366,7 +3365,9 @@ static int block_til_ready(struct tty_struct *tty, struct file *filp,
3366 printk("%s(%d):%s block_til_ready() count=%d\n", 3365 printk("%s(%d):%s block_til_ready() count=%d\n",
3367 __FILE__,__LINE__, tty->driver->name, port->count ); 3366 __FILE__,__LINE__, tty->driver->name, port->count );
3368 3367
3368 tty_unlock();
3369 schedule(); 3369 schedule();
3370 tty_lock();
3370 } 3371 }
3371 3372
3372 set_current_state(TASK_RUNNING); 3373 set_current_state(TASK_RUNNING);
diff --git a/drivers/char/tty_io.c b/drivers/char/tty_io.c
index 507441ac6edb..0350c42375a2 100644
--- a/drivers/char/tty_io.c
+++ b/drivers/char/tty_io.c
@@ -149,6 +149,7 @@ static long tty_compat_ioctl(struct file *file, unsigned int cmd,
149#else 149#else
150#define tty_compat_ioctl NULL 150#define tty_compat_ioctl NULL
151#endif 151#endif
152static int __tty_fasync(int fd, struct file *filp, int on);
152static int tty_fasync(int fd, struct file *filp, int on); 153static int tty_fasync(int fd, struct file *filp, int on);
153static void release_tty(struct tty_struct *tty, int idx); 154static void release_tty(struct tty_struct *tty, int idx);
154static void __proc_set_tty(struct task_struct *tsk, struct tty_struct *tty); 155static void __proc_set_tty(struct task_struct *tsk, struct tty_struct *tty);
@@ -470,7 +471,7 @@ void tty_wakeup(struct tty_struct *tty)
470EXPORT_SYMBOL_GPL(tty_wakeup); 471EXPORT_SYMBOL_GPL(tty_wakeup);
471 472
472/** 473/**
473 * do_tty_hangup - actual handler for hangup events 474 * __tty_hangup - actual handler for hangup events
474 * @work: tty device 475 * @work: tty device
475 * 476 *
476 * This can be called by the "eventd" kernel thread. That is process 477 * This can be called by the "eventd" kernel thread. That is process
@@ -483,7 +484,7 @@ EXPORT_SYMBOL_GPL(tty_wakeup);
483 * remains intact. 484 * remains intact.
484 * 485 *
485 * Locking: 486 * Locking:
486 * BKL 487 * BTM
487 * redirect lock for undoing redirection 488 * redirect lock for undoing redirection
488 * file list lock for manipulating list of ttys 489 * file list lock for manipulating list of ttys
489 * tty_ldisc_lock from called functions 490 * tty_ldisc_lock from called functions
@@ -491,10 +492,8 @@ EXPORT_SYMBOL_GPL(tty_wakeup);
491 * tasklist_lock to walk task list for hangup event 492 * tasklist_lock to walk task list for hangup event
492 * ->siglock to protect ->signal/->sighand 493 * ->siglock to protect ->signal/->sighand
493 */ 494 */
494static void do_tty_hangup(struct work_struct *work) 495void __tty_hangup(struct tty_struct *tty)
495{ 496{
496 struct tty_struct *tty =
497 container_of(work, struct tty_struct, hangup_work);
498 struct file *cons_filp = NULL; 497 struct file *cons_filp = NULL;
499 struct file *filp, *f = NULL; 498 struct file *filp, *f = NULL;
500 struct task_struct *p; 499 struct task_struct *p;
@@ -513,9 +512,12 @@ static void do_tty_hangup(struct work_struct *work)
513 } 512 }
514 spin_unlock(&redirect_lock); 513 spin_unlock(&redirect_lock);
515 514
516 /* inuse_filps is protected by the single kernel lock */ 515 tty_lock();
517 lock_kernel(); 516
518 check_tty_count(tty, "do_tty_hangup"); 517 /* inuse_filps is protected by the single tty lock,
518 this really needs to change if we want to flush the
519 workqueue with the lock held */
520 check_tty_count(tty, "tty_hangup");
519 521
520 file_list_lock(); 522 file_list_lock();
521 /* This breaks for file handles being sent over AF_UNIX sockets ? */ 523 /* This breaks for file handles being sent over AF_UNIX sockets ? */
@@ -525,7 +527,7 @@ static void do_tty_hangup(struct work_struct *work)
525 if (filp->f_op->write != tty_write) 527 if (filp->f_op->write != tty_write)
526 continue; 528 continue;
527 closecount++; 529 closecount++;
528 tty_fasync(-1, filp, 0); /* can't block */ 530 __tty_fasync(-1, filp, 0); /* can't block */
529 filp->f_op = &hung_up_tty_fops; 531 filp->f_op = &hung_up_tty_fops;
530 } 532 }
531 file_list_unlock(); 533 file_list_unlock();
@@ -594,11 +596,21 @@ static void do_tty_hangup(struct work_struct *work)
594 */ 596 */
595 set_bit(TTY_HUPPED, &tty->flags); 597 set_bit(TTY_HUPPED, &tty->flags);
596 tty_ldisc_enable(tty); 598 tty_ldisc_enable(tty);
597 unlock_kernel(); 599
600 tty_unlock();
601
598 if (f) 602 if (f)
599 fput(f); 603 fput(f);
600} 604}
601 605
606static void do_tty_hangup(struct work_struct *work)
607{
608 struct tty_struct *tty =
609 container_of(work, struct tty_struct, hangup_work);
610
611 __tty_hangup(tty);
612}
613
602/** 614/**
603 * tty_hangup - trigger a hangup event 615 * tty_hangup - trigger a hangup event
604 * @tty: tty to hangup 616 * @tty: tty to hangup
@@ -634,11 +646,12 @@ void tty_vhangup(struct tty_struct *tty)
634 646
635 printk(KERN_DEBUG "%s vhangup...\n", tty_name(tty, buf)); 647 printk(KERN_DEBUG "%s vhangup...\n", tty_name(tty, buf));
636#endif 648#endif
637 do_tty_hangup(&tty->hangup_work); 649 __tty_hangup(tty);
638} 650}
639 651
640EXPORT_SYMBOL(tty_vhangup); 652EXPORT_SYMBOL(tty_vhangup);
641 653
654
642/** 655/**
643 * tty_vhangup_self - process vhangup for own ctty 656 * tty_vhangup_self - process vhangup for own ctty
644 * 657 *
@@ -696,7 +709,8 @@ static void session_clear_tty(struct pid *session)
696 * exiting; it is 0 if called by the ioctl TIOCNOTTY. 709 * exiting; it is 0 if called by the ioctl TIOCNOTTY.
697 * 710 *
698 * Locking: 711 * Locking:
699 * BKL is taken for hysterical raisins 712 * BTM is taken for hysterical raisins, and held when
713 * called from no_tty().
700 * tty_mutex is taken to protect tty 714 * tty_mutex is taken to protect tty
701 * ->siglock is taken to protect ->signal/->sighand 715 * ->siglock is taken to protect ->signal/->sighand
702 * tasklist_lock is taken to walk process list for sessions 716 * tasklist_lock is taken to walk process list for sessions
@@ -714,10 +728,10 @@ void disassociate_ctty(int on_exit)
714 tty = get_current_tty(); 728 tty = get_current_tty();
715 if (tty) { 729 if (tty) {
716 tty_pgrp = get_pid(tty->pgrp); 730 tty_pgrp = get_pid(tty->pgrp);
717 lock_kernel(); 731 if (on_exit) {
718 if (on_exit && tty->driver->type != TTY_DRIVER_TYPE_PTY) 732 if (tty->driver->type != TTY_DRIVER_TYPE_PTY)
719 tty_vhangup(tty); 733 tty_vhangup(tty);
720 unlock_kernel(); 734 }
721 tty_kref_put(tty); 735 tty_kref_put(tty);
722 } else if (on_exit) { 736 } else if (on_exit) {
723 struct pid *old_pgrp; 737 struct pid *old_pgrp;
@@ -774,9 +788,9 @@ void disassociate_ctty(int on_exit)
774void no_tty(void) 788void no_tty(void)
775{ 789{
776 struct task_struct *tsk = current; 790 struct task_struct *tsk = current;
777 lock_kernel(); 791 tty_lock();
778 disassociate_ctty(0); 792 disassociate_ctty(0);
779 unlock_kernel(); 793 tty_unlock();
780 proc_clear_tty(tsk); 794 proc_clear_tty(tsk);
781} 795}
782 796
@@ -879,7 +893,7 @@ static ssize_t tty_read(struct file *file, char __user *buf, size_t count,
879 struct inode *inode; 893 struct inode *inode;
880 struct tty_ldisc *ld; 894 struct tty_ldisc *ld;
881 895
882 tty = (struct tty_struct *)file->private_data; 896 tty = file->private_data;
883 inode = file->f_path.dentry->d_inode; 897 inode = file->f_path.dentry->d_inode;
884 if (tty_paranoia_check(tty, inode, "tty_read")) 898 if (tty_paranoia_check(tty, inode, "tty_read"))
885 return -EIO; 899 return -EIO;
@@ -1013,19 +1027,19 @@ out:
1013 * We don't put it into the syslog queue right now maybe in the future if 1027 * We don't put it into the syslog queue right now maybe in the future if
1014 * really needed. 1028 * really needed.
1015 * 1029 *
1016 * We must still hold the BKL and test the CLOSING flag for the moment. 1030 * We must still hold the BTM and test the CLOSING flag for the moment.
1017 */ 1031 */
1018 1032
1019void tty_write_message(struct tty_struct *tty, char *msg) 1033void tty_write_message(struct tty_struct *tty, char *msg)
1020{ 1034{
1021 if (tty) { 1035 if (tty) {
1022 mutex_lock(&tty->atomic_write_lock); 1036 mutex_lock(&tty->atomic_write_lock);
1023 lock_kernel(); 1037 tty_lock();
1024 if (tty->ops->write && !test_bit(TTY_CLOSING, &tty->flags)) { 1038 if (tty->ops->write && !test_bit(TTY_CLOSING, &tty->flags)) {
1025 unlock_kernel(); 1039 tty_unlock();
1026 tty->ops->write(tty, msg, strlen(msg)); 1040 tty->ops->write(tty, msg, strlen(msg));
1027 } else 1041 } else
1028 unlock_kernel(); 1042 tty_unlock();
1029 tty_write_unlock(tty); 1043 tty_write_unlock(tty);
1030 } 1044 }
1031 return; 1045 return;
@@ -1056,7 +1070,7 @@ static ssize_t tty_write(struct file *file, const char __user *buf,
1056 ssize_t ret; 1070 ssize_t ret;
1057 struct tty_ldisc *ld; 1071 struct tty_ldisc *ld;
1058 1072
1059 tty = (struct tty_struct *)file->private_data; 1073 tty = file->private_data;
1060 if (tty_paranoia_check(tty, inode, "tty_write")) 1074 if (tty_paranoia_check(tty, inode, "tty_write"))
1061 return -EIO; 1075 return -EIO;
1062 if (!tty || !tty->ops->write || 1076 if (!tty || !tty->ops->write ||
@@ -1208,18 +1222,14 @@ static int tty_driver_install_tty(struct tty_driver *driver,
1208 int ret; 1222 int ret;
1209 1223
1210 if (driver->ops->install) { 1224 if (driver->ops->install) {
1211 lock_kernel();
1212 ret = driver->ops->install(driver, tty); 1225 ret = driver->ops->install(driver, tty);
1213 unlock_kernel();
1214 return ret; 1226 return ret;
1215 } 1227 }
1216 1228
1217 if (tty_init_termios(tty) == 0) { 1229 if (tty_init_termios(tty) == 0) {
1218 lock_kernel();
1219 tty_driver_kref_get(driver); 1230 tty_driver_kref_get(driver);
1220 tty->count++; 1231 tty->count++;
1221 driver->ttys[idx] = tty; 1232 driver->ttys[idx] = tty;
1222 unlock_kernel();
1223 return 0; 1233 return 0;
1224 } 1234 }
1225 return -ENOMEM; 1235 return -ENOMEM;
@@ -1312,14 +1322,11 @@ struct tty_struct *tty_init_dev(struct tty_driver *driver, int idx,
1312 struct tty_struct *tty; 1322 struct tty_struct *tty;
1313 int retval; 1323 int retval;
1314 1324
1315 lock_kernel();
1316 /* Check if pty master is being opened multiple times */ 1325 /* Check if pty master is being opened multiple times */
1317 if (driver->subtype == PTY_TYPE_MASTER && 1326 if (driver->subtype == PTY_TYPE_MASTER &&
1318 (driver->flags & TTY_DRIVER_DEVPTS_MEM) && !first_ok) { 1327 (driver->flags & TTY_DRIVER_DEVPTS_MEM) && !first_ok) {
1319 unlock_kernel();
1320 return ERR_PTR(-EIO); 1328 return ERR_PTR(-EIO);
1321 } 1329 }
1322 unlock_kernel();
1323 1330
1324 /* 1331 /*
1325 * First time open is complex, especially for PTY devices. 1332 * First time open is complex, especially for PTY devices.
@@ -1363,9 +1370,7 @@ release_mem_out:
1363 if (printk_ratelimit()) 1370 if (printk_ratelimit())
1364 printk(KERN_INFO "tty_init_dev: ldisc open failed, " 1371 printk(KERN_INFO "tty_init_dev: ldisc open failed, "
1365 "clearing slot %d\n", idx); 1372 "clearing slot %d\n", idx);
1366 lock_kernel();
1367 release_tty(tty, idx); 1373 release_tty(tty, idx);
1368 unlock_kernel();
1369 return ERR_PTR(retval); 1374 return ERR_PTR(retval);
1370} 1375}
1371 1376
@@ -1508,14 +1513,14 @@ int tty_release(struct inode *inode, struct file *filp)
1508 int idx; 1513 int idx;
1509 char buf[64]; 1514 char buf[64];
1510 1515
1511 tty = (struct tty_struct *)filp->private_data; 1516 tty = filp->private_data;
1512 if (tty_paranoia_check(tty, inode, "tty_release_dev")) 1517 if (tty_paranoia_check(tty, inode, "tty_release_dev"))
1513 return 0; 1518 return 0;
1514 1519
1515 lock_kernel(); 1520 tty_lock();
1516 check_tty_count(tty, "tty_release_dev"); 1521 check_tty_count(tty, "tty_release_dev");
1517 1522
1518 tty_fasync(-1, filp, 0); 1523 __tty_fasync(-1, filp, 0);
1519 1524
1520 idx = tty->index; 1525 idx = tty->index;
1521 pty_master = (tty->driver->type == TTY_DRIVER_TYPE_PTY && 1526 pty_master = (tty->driver->type == TTY_DRIVER_TYPE_PTY &&
@@ -1527,18 +1532,18 @@ int tty_release(struct inode *inode, struct file *filp)
1527 if (idx < 0 || idx >= tty->driver->num) { 1532 if (idx < 0 || idx >= tty->driver->num) {
1528 printk(KERN_DEBUG "tty_release_dev: bad idx when trying to " 1533 printk(KERN_DEBUG "tty_release_dev: bad idx when trying to "
1529 "free (%s)\n", tty->name); 1534 "free (%s)\n", tty->name);
1530 unlock_kernel(); 1535 tty_unlock();
1531 return 0; 1536 return 0;
1532 } 1537 }
1533 if (!devpts) { 1538 if (!devpts) {
1534 if (tty != tty->driver->ttys[idx]) { 1539 if (tty != tty->driver->ttys[idx]) {
1535 unlock_kernel(); 1540 tty_unlock();
1536 printk(KERN_DEBUG "tty_release_dev: driver.table[%d] not tty " 1541 printk(KERN_DEBUG "tty_release_dev: driver.table[%d] not tty "
1537 "for (%s)\n", idx, tty->name); 1542 "for (%s)\n", idx, tty->name);
1538 return 0; 1543 return 0;
1539 } 1544 }
1540 if (tty->termios != tty->driver->termios[idx]) { 1545 if (tty->termios != tty->driver->termios[idx]) {
1541 unlock_kernel(); 1546 tty_unlock();
1542 printk(KERN_DEBUG "tty_release_dev: driver.termios[%d] not termios " 1547 printk(KERN_DEBUG "tty_release_dev: driver.termios[%d] not termios "
1543 "for (%s)\n", 1548 "for (%s)\n",
1544 idx, tty->name); 1549 idx, tty->name);
@@ -1556,21 +1561,21 @@ int tty_release(struct inode *inode, struct file *filp)
1556 if (tty->driver->other && 1561 if (tty->driver->other &&
1557 !(tty->driver->flags & TTY_DRIVER_DEVPTS_MEM)) { 1562 !(tty->driver->flags & TTY_DRIVER_DEVPTS_MEM)) {
1558 if (o_tty != tty->driver->other->ttys[idx]) { 1563 if (o_tty != tty->driver->other->ttys[idx]) {
1559 unlock_kernel(); 1564 tty_unlock();
1560 printk(KERN_DEBUG "tty_release_dev: other->table[%d] " 1565 printk(KERN_DEBUG "tty_release_dev: other->table[%d] "
1561 "not o_tty for (%s)\n", 1566 "not o_tty for (%s)\n",
1562 idx, tty->name); 1567 idx, tty->name);
1563 return 0 ; 1568 return 0 ;
1564 } 1569 }
1565 if (o_tty->termios != tty->driver->other->termios[idx]) { 1570 if (o_tty->termios != tty->driver->other->termios[idx]) {
1566 unlock_kernel(); 1571 tty_unlock();
1567 printk(KERN_DEBUG "tty_release_dev: other->termios[%d] " 1572 printk(KERN_DEBUG "tty_release_dev: other->termios[%d] "
1568 "not o_termios for (%s)\n", 1573 "not o_termios for (%s)\n",
1569 idx, tty->name); 1574 idx, tty->name);
1570 return 0; 1575 return 0;
1571 } 1576 }
1572 if (o_tty->link != tty) { 1577 if (o_tty->link != tty) {
1573 unlock_kernel(); 1578 tty_unlock();
1574 printk(KERN_DEBUG "tty_release_dev: bad pty pointers\n"); 1579 printk(KERN_DEBUG "tty_release_dev: bad pty pointers\n");
1575 return 0; 1580 return 0;
1576 } 1581 }
@@ -1579,7 +1584,7 @@ int tty_release(struct inode *inode, struct file *filp)
1579 if (tty->ops->close) 1584 if (tty->ops->close)
1580 tty->ops->close(tty, filp); 1585 tty->ops->close(tty, filp);
1581 1586
1582 unlock_kernel(); 1587 tty_unlock();
1583 /* 1588 /*
1584 * Sanity check: if tty->count is going to zero, there shouldn't be 1589 * Sanity check: if tty->count is going to zero, there shouldn't be
1585 * any waiters on tty->read_wait or tty->write_wait. We test the 1590 * any waiters on tty->read_wait or tty->write_wait. We test the
@@ -1602,7 +1607,7 @@ int tty_release(struct inode *inode, struct file *filp)
1602 opens on /dev/tty */ 1607 opens on /dev/tty */
1603 1608
1604 mutex_lock(&tty_mutex); 1609 mutex_lock(&tty_mutex);
1605 lock_kernel(); 1610 tty_lock();
1606 tty_closing = tty->count <= 1; 1611 tty_closing = tty->count <= 1;
1607 o_tty_closing = o_tty && 1612 o_tty_closing = o_tty &&
1608 (o_tty->count <= (pty_master ? 1 : 0)); 1613 (o_tty->count <= (pty_master ? 1 : 0));
@@ -1633,7 +1638,7 @@ int tty_release(struct inode *inode, struct file *filp)
1633 1638
1634 printk(KERN_WARNING "tty_release_dev: %s: read/write wait queue " 1639 printk(KERN_WARNING "tty_release_dev: %s: read/write wait queue "
1635 "active!\n", tty_name(tty, buf)); 1640 "active!\n", tty_name(tty, buf));
1636 unlock_kernel(); 1641 tty_unlock();
1637 mutex_unlock(&tty_mutex); 1642 mutex_unlock(&tty_mutex);
1638 schedule(); 1643 schedule();
1639 } 1644 }
@@ -1698,7 +1703,7 @@ int tty_release(struct inode *inode, struct file *filp)
1698 1703
1699 /* check whether both sides are closing ... */ 1704 /* check whether both sides are closing ... */
1700 if (!tty_closing || (o_tty && !o_tty_closing)) { 1705 if (!tty_closing || (o_tty && !o_tty_closing)) {
1701 unlock_kernel(); 1706 tty_unlock();
1702 return 0; 1707 return 0;
1703 } 1708 }
1704 1709
@@ -1718,7 +1723,7 @@ int tty_release(struct inode *inode, struct file *filp)
1718 /* Make this pty number available for reallocation */ 1723 /* Make this pty number available for reallocation */
1719 if (devpts) 1724 if (devpts)
1720 devpts_kill_index(inode, idx); 1725 devpts_kill_index(inode, idx);
1721 unlock_kernel(); 1726 tty_unlock();
1722 return 0; 1727 return 0;
1723} 1728}
1724 1729
@@ -1760,12 +1765,12 @@ retry_open:
1760 retval = 0; 1765 retval = 0;
1761 1766
1762 mutex_lock(&tty_mutex); 1767 mutex_lock(&tty_mutex);
1763 lock_kernel(); 1768 tty_lock();
1764 1769
1765 if (device == MKDEV(TTYAUX_MAJOR, 0)) { 1770 if (device == MKDEV(TTYAUX_MAJOR, 0)) {
1766 tty = get_current_tty(); 1771 tty = get_current_tty();
1767 if (!tty) { 1772 if (!tty) {
1768 unlock_kernel(); 1773 tty_unlock();
1769 mutex_unlock(&tty_mutex); 1774 mutex_unlock(&tty_mutex);
1770 return -ENXIO; 1775 return -ENXIO;
1771 } 1776 }
@@ -1797,14 +1802,14 @@ retry_open:
1797 goto got_driver; 1802 goto got_driver;
1798 } 1803 }
1799 } 1804 }
1800 unlock_kernel(); 1805 tty_unlock();
1801 mutex_unlock(&tty_mutex); 1806 mutex_unlock(&tty_mutex);
1802 return -ENODEV; 1807 return -ENODEV;
1803 } 1808 }
1804 1809
1805 driver = get_tty_driver(device, &index); 1810 driver = get_tty_driver(device, &index);
1806 if (!driver) { 1811 if (!driver) {
1807 unlock_kernel(); 1812 tty_unlock();
1808 mutex_unlock(&tty_mutex); 1813 mutex_unlock(&tty_mutex);
1809 return -ENODEV; 1814 return -ENODEV;
1810 } 1815 }
@@ -1814,7 +1819,7 @@ got_driver:
1814 tty = tty_driver_lookup_tty(driver, inode, index); 1819 tty = tty_driver_lookup_tty(driver, inode, index);
1815 1820
1816 if (IS_ERR(tty)) { 1821 if (IS_ERR(tty)) {
1817 unlock_kernel(); 1822 tty_unlock();
1818 mutex_unlock(&tty_mutex); 1823 mutex_unlock(&tty_mutex);
1819 return PTR_ERR(tty); 1824 return PTR_ERR(tty);
1820 } 1825 }
@@ -1830,7 +1835,7 @@ got_driver:
1830 mutex_unlock(&tty_mutex); 1835 mutex_unlock(&tty_mutex);
1831 tty_driver_kref_put(driver); 1836 tty_driver_kref_put(driver);
1832 if (IS_ERR(tty)) { 1837 if (IS_ERR(tty)) {
1833 unlock_kernel(); 1838 tty_unlock();
1834 return PTR_ERR(tty); 1839 return PTR_ERR(tty);
1835 } 1840 }
1836 1841
@@ -1860,29 +1865,29 @@ got_driver:
1860 printk(KERN_DEBUG "error %d in opening %s...", retval, 1865 printk(KERN_DEBUG "error %d in opening %s...", retval,
1861 tty->name); 1866 tty->name);
1862#endif 1867#endif
1868 tty_unlock(); /* need to call tty_release without BTM */
1863 tty_release(inode, filp); 1869 tty_release(inode, filp);
1864 if (retval != -ERESTARTSYS) { 1870 if (retval != -ERESTARTSYS)
1865 unlock_kernel();
1866 return retval; 1871 return retval;
1867 } 1872
1868 if (signal_pending(current)) { 1873 if (signal_pending(current))
1869 unlock_kernel();
1870 return retval; 1874 return retval;
1871 } 1875
1872 schedule(); 1876 schedule();
1873 /* 1877 /*
1874 * Need to reset f_op in case a hangup happened. 1878 * Need to reset f_op in case a hangup happened.
1875 */ 1879 */
1880 tty_lock();
1876 if (filp->f_op == &hung_up_tty_fops) 1881 if (filp->f_op == &hung_up_tty_fops)
1877 filp->f_op = &tty_fops; 1882 filp->f_op = &tty_fops;
1878 unlock_kernel(); 1883 tty_unlock();
1879 goto retry_open; 1884 goto retry_open;
1880 } 1885 }
1881 unlock_kernel(); 1886 tty_unlock();
1882 1887
1883 1888
1884 mutex_lock(&tty_mutex); 1889 mutex_lock(&tty_mutex);
1885 lock_kernel(); 1890 tty_lock();
1886 spin_lock_irq(&current->sighand->siglock); 1891 spin_lock_irq(&current->sighand->siglock);
1887 if (!noctty && 1892 if (!noctty &&
1888 current->signal->leader && 1893 current->signal->leader &&
@@ -1890,7 +1895,7 @@ got_driver:
1890 tty->session == NULL) 1895 tty->session == NULL)
1891 __proc_set_tty(current, tty); 1896 __proc_set_tty(current, tty);
1892 spin_unlock_irq(&current->sighand->siglock); 1897 spin_unlock_irq(&current->sighand->siglock);
1893 unlock_kernel(); 1898 tty_unlock();
1894 mutex_unlock(&tty_mutex); 1899 mutex_unlock(&tty_mutex);
1895 return 0; 1900 return 0;
1896} 1901}
@@ -1915,7 +1920,7 @@ static unsigned int tty_poll(struct file *filp, poll_table *wait)
1915 struct tty_ldisc *ld; 1920 struct tty_ldisc *ld;
1916 int ret = 0; 1921 int ret = 0;
1917 1922
1918 tty = (struct tty_struct *)filp->private_data; 1923 tty = filp->private_data;
1919 if (tty_paranoia_check(tty, filp->f_path.dentry->d_inode, "tty_poll")) 1924 if (tty_paranoia_check(tty, filp->f_path.dentry->d_inode, "tty_poll"))
1920 return 0; 1925 return 0;
1921 1926
@@ -1926,14 +1931,13 @@ static unsigned int tty_poll(struct file *filp, poll_table *wait)
1926 return ret; 1931 return ret;
1927} 1932}
1928 1933
1929static int tty_fasync(int fd, struct file *filp, int on) 1934static int __tty_fasync(int fd, struct file *filp, int on)
1930{ 1935{
1931 struct tty_struct *tty; 1936 struct tty_struct *tty;
1932 unsigned long flags; 1937 unsigned long flags;
1933 int retval = 0; 1938 int retval = 0;
1934 1939
1935 lock_kernel(); 1940 tty = filp->private_data;
1936 tty = (struct tty_struct *)filp->private_data;
1937 if (tty_paranoia_check(tty, filp->f_path.dentry->d_inode, "tty_fasync")) 1941 if (tty_paranoia_check(tty, filp->f_path.dentry->d_inode, "tty_fasync"))
1938 goto out; 1942 goto out;
1939 1943
@@ -1966,7 +1970,15 @@ static int tty_fasync(int fd, struct file *filp, int on)
1966 } 1970 }
1967 retval = 0; 1971 retval = 0;
1968out: 1972out:
1969 unlock_kernel(); 1973 return retval;
1974}
1975
1976static int tty_fasync(int fd, struct file *filp, int on)
1977{
1978 int retval;
1979 tty_lock();
1980 retval = __tty_fasync(fd, filp, on);
1981 tty_unlock();
1970 return retval; 1982 return retval;
1971} 1983}
1972 1984
@@ -2485,7 +2497,7 @@ long tty_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
2485 struct tty_ldisc *ld; 2497 struct tty_ldisc *ld;
2486 struct inode *inode = file->f_dentry->d_inode; 2498 struct inode *inode = file->f_dentry->d_inode;
2487 2499
2488 tty = (struct tty_struct *)file->private_data; 2500 tty = file->private_data;
2489 if (tty_paranoia_check(tty, inode, "tty_ioctl")) 2501 if (tty_paranoia_check(tty, inode, "tty_ioctl"))
2490 return -EINVAL; 2502 return -EINVAL;
2491 2503
diff --git a/drivers/char/tty_ioctl.c b/drivers/char/tty_ioctl.c
index 6bd5f8866c74..0c1889971459 100644
--- a/drivers/char/tty_ioctl.c
+++ b/drivers/char/tty_ioctl.c
@@ -517,19 +517,25 @@ static void change_termios(struct tty_struct *tty, struct ktermios *new_termios)
517 517
518 /* See if packet mode change of state. */ 518 /* See if packet mode change of state. */
519 if (tty->link && tty->link->packet) { 519 if (tty->link && tty->link->packet) {
520 int extproc = (old_termios.c_lflag & EXTPROC) |
521 (tty->termios->c_lflag & EXTPROC);
520 int old_flow = ((old_termios.c_iflag & IXON) && 522 int old_flow = ((old_termios.c_iflag & IXON) &&
521 (old_termios.c_cc[VSTOP] == '\023') && 523 (old_termios.c_cc[VSTOP] == '\023') &&
522 (old_termios.c_cc[VSTART] == '\021')); 524 (old_termios.c_cc[VSTART] == '\021'));
523 int new_flow = (I_IXON(tty) && 525 int new_flow = (I_IXON(tty) &&
524 STOP_CHAR(tty) == '\023' && 526 STOP_CHAR(tty) == '\023' &&
525 START_CHAR(tty) == '\021'); 527 START_CHAR(tty) == '\021');
526 if (old_flow != new_flow) { 528 if ((old_flow != new_flow) || extproc) {
527 spin_lock_irqsave(&tty->ctrl_lock, flags); 529 spin_lock_irqsave(&tty->ctrl_lock, flags);
528 tty->ctrl_status &= ~(TIOCPKT_DOSTOP | TIOCPKT_NOSTOP); 530 if (old_flow != new_flow) {
529 if (new_flow) 531 tty->ctrl_status &= ~(TIOCPKT_DOSTOP | TIOCPKT_NOSTOP);
530 tty->ctrl_status |= TIOCPKT_DOSTOP; 532 if (new_flow)
531 else 533 tty->ctrl_status |= TIOCPKT_DOSTOP;
532 tty->ctrl_status |= TIOCPKT_NOSTOP; 534 else
535 tty->ctrl_status |= TIOCPKT_NOSTOP;
536 }
537 if (extproc)
538 tty->ctrl_status |= TIOCPKT_IOCTL;
533 spin_unlock_irqrestore(&tty->ctrl_lock, flags); 539 spin_unlock_irqrestore(&tty->ctrl_lock, flags);
534 wake_up_interruptible(&tty->link->read_wait); 540 wake_up_interruptible(&tty->link->read_wait);
535 } 541 }
diff --git a/drivers/char/tty_ldisc.c b/drivers/char/tty_ldisc.c
index 500e740ec5e4..412f9775d19c 100644
--- a/drivers/char/tty_ldisc.c
+++ b/drivers/char/tty_ldisc.c
@@ -440,6 +440,8 @@ static void tty_set_termios_ldisc(struct tty_struct *tty, int num)
440 * 440 *
441 * A helper opening method. Also a convenient debugging and check 441 * A helper opening method. Also a convenient debugging and check
442 * point. 442 * point.
443 *
444 * Locking: always called with BTM already held.
443 */ 445 */
444 446
445static int tty_ldisc_open(struct tty_struct *tty, struct tty_ldisc *ld) 447static int tty_ldisc_open(struct tty_struct *tty, struct tty_ldisc *ld)
@@ -447,10 +449,9 @@ static int tty_ldisc_open(struct tty_struct *tty, struct tty_ldisc *ld)
447 WARN_ON(test_and_set_bit(TTY_LDISC_OPEN, &tty->flags)); 449 WARN_ON(test_and_set_bit(TTY_LDISC_OPEN, &tty->flags));
448 if (ld->ops->open) { 450 if (ld->ops->open) {
449 int ret; 451 int ret;
450 /* BKL here locks verus a hangup event */ 452 /* BTM here locks versus a hangup event */
451 lock_kernel(); 453 WARN_ON(!tty_locked());
452 ret = ld->ops->open(tty); 454 ret = ld->ops->open(tty);
453 unlock_kernel();
454 return ret; 455 return ret;
455 } 456 }
456 return 0; 457 return 0;
@@ -553,7 +554,7 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
553 if (IS_ERR(new_ldisc)) 554 if (IS_ERR(new_ldisc))
554 return PTR_ERR(new_ldisc); 555 return PTR_ERR(new_ldisc);
555 556
556 lock_kernel(); 557 tty_lock();
557 /* 558 /*
558 * We need to look at the tty locking here for pty/tty pairs 559 * We need to look at the tty locking here for pty/tty pairs
559 * when both sides try to change in parallel. 560 * when both sides try to change in parallel.
@@ -567,12 +568,12 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
567 */ 568 */
568 569
569 if (tty->ldisc->ops->num == ldisc) { 570 if (tty->ldisc->ops->num == ldisc) {
570 unlock_kernel(); 571 tty_unlock();
571 tty_ldisc_put(new_ldisc); 572 tty_ldisc_put(new_ldisc);
572 return 0; 573 return 0;
573 } 574 }
574 575
575 unlock_kernel(); 576 tty_unlock();
576 /* 577 /*
577 * Problem: What do we do if this blocks ? 578 * Problem: What do we do if this blocks ?
578 * We could deadlock here 579 * We could deadlock here
@@ -580,6 +581,7 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
580 581
581 tty_wait_until_sent(tty, 0); 582 tty_wait_until_sent(tty, 0);
582 583
584 tty_lock();
583 mutex_lock(&tty->ldisc_mutex); 585 mutex_lock(&tty->ldisc_mutex);
584 586
585 /* 587 /*
@@ -589,13 +591,13 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
589 591
590 while (test_bit(TTY_LDISC_CHANGING, &tty->flags)) { 592 while (test_bit(TTY_LDISC_CHANGING, &tty->flags)) {
591 mutex_unlock(&tty->ldisc_mutex); 593 mutex_unlock(&tty->ldisc_mutex);
594 tty_unlock();
592 wait_event(tty_ldisc_wait, 595 wait_event(tty_ldisc_wait,
593 test_bit(TTY_LDISC_CHANGING, &tty->flags) == 0); 596 test_bit(TTY_LDISC_CHANGING, &tty->flags) == 0);
597 tty_lock();
594 mutex_lock(&tty->ldisc_mutex); 598 mutex_lock(&tty->ldisc_mutex);
595 } 599 }
596 600
597 lock_kernel();
598
599 set_bit(TTY_LDISC_CHANGING, &tty->flags); 601 set_bit(TTY_LDISC_CHANGING, &tty->flags);
600 602
601 /* 603 /*
@@ -607,7 +609,7 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
607 609
608 o_ldisc = tty->ldisc; 610 o_ldisc = tty->ldisc;
609 611
610 unlock_kernel(); 612 tty_unlock();
611 /* 613 /*
612 * Make sure we don't change while someone holds a 614 * Make sure we don't change while someone holds a
613 * reference to the line discipline. The TTY_LDISC bit 615 * reference to the line discipline. The TTY_LDISC bit
@@ -632,15 +634,15 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
632 634
633 flush_scheduled_work(); 635 flush_scheduled_work();
634 636
637 tty_lock();
635 mutex_lock(&tty->ldisc_mutex); 638 mutex_lock(&tty->ldisc_mutex);
636 lock_kernel();
637 if (test_bit(TTY_HUPPED, &tty->flags)) { 639 if (test_bit(TTY_HUPPED, &tty->flags)) {
638 /* We were raced by the hangup method. It will have stomped 640 /* We were raced by the hangup method. It will have stomped
639 the ldisc data and closed the ldisc down */ 641 the ldisc data and closed the ldisc down */
640 clear_bit(TTY_LDISC_CHANGING, &tty->flags); 642 clear_bit(TTY_LDISC_CHANGING, &tty->flags);
641 mutex_unlock(&tty->ldisc_mutex); 643 mutex_unlock(&tty->ldisc_mutex);
642 tty_ldisc_put(new_ldisc); 644 tty_ldisc_put(new_ldisc);
643 unlock_kernel(); 645 tty_unlock();
644 return -EIO; 646 return -EIO;
645 } 647 }
646 648
@@ -682,7 +684,7 @@ int tty_set_ldisc(struct tty_struct *tty, int ldisc)
682 if (o_work) 684 if (o_work)
683 schedule_delayed_work(&o_tty->buf.work, 1); 685 schedule_delayed_work(&o_tty->buf.work, 1);
684 mutex_unlock(&tty->ldisc_mutex); 686 mutex_unlock(&tty->ldisc_mutex);
685 unlock_kernel(); 687 tty_unlock();
686 return retval; 688 return retval;
687} 689}
688 690
@@ -780,7 +782,20 @@ void tty_ldisc_hangup(struct tty_struct *tty)
780 * Avoid racing set_ldisc or tty_ldisc_release 782 * Avoid racing set_ldisc or tty_ldisc_release
781 */ 783 */
782 mutex_lock(&tty->ldisc_mutex); 784 mutex_lock(&tty->ldisc_mutex);
783 tty_ldisc_halt(tty); 785
786 /*
787 * this is like tty_ldisc_halt, but we need to give up
788 * the BTM before calling cancel_delayed_work_sync,
789 * which may need to wait for another function taking the BTM
790 */
791 clear_bit(TTY_LDISC, &tty->flags);
792 tty_unlock();
793 cancel_delayed_work_sync(&tty->buf.work);
794 mutex_unlock(&tty->ldisc_mutex);
795
796 tty_lock();
797 mutex_lock(&tty->ldisc_mutex);
798
784 /* At this point we have a closed ldisc and we want to 799 /* At this point we have a closed ldisc and we want to
785 reopen it. We could defer this to the next open but 800 reopen it. We could defer this to the next open but
786 it means auditing a lot of other paths so this is 801 it means auditing a lot of other paths so this is
@@ -851,8 +866,10 @@ void tty_ldisc_release(struct tty_struct *tty, struct tty_struct *o_tty)
851 * race with the set_ldisc code path. 866 * race with the set_ldisc code path.
852 */ 867 */
853 868
869 tty_unlock();
854 tty_ldisc_halt(tty); 870 tty_ldisc_halt(tty);
855 flush_scheduled_work(); 871 flush_scheduled_work();
872 tty_lock();
856 873
857 mutex_lock(&tty->ldisc_mutex); 874 mutex_lock(&tty->ldisc_mutex);
858 /* 875 /*
diff --git a/drivers/char/tty_mutex.c b/drivers/char/tty_mutex.c
new file mode 100644
index 000000000000..133697540c73
--- /dev/null
+++ b/drivers/char/tty_mutex.c
@@ -0,0 +1,47 @@
1/*
2 * drivers/char/tty_lock.c
3 */
4#include <linux/tty.h>
5#include <linux/module.h>
6#include <linux/kallsyms.h>
7#include <linux/semaphore.h>
8#include <linux/sched.h>
9
10/*
11 * The 'big tty mutex'
12 *
13 * This mutex is taken and released by tty_lock() and tty_unlock(),
14 * replacing the older big kernel lock.
15 * It can no longer be taken recursively, and does not get
16 * released implicitly while sleeping.
17 *
18 * Don't use in new code.
19 */
20static DEFINE_MUTEX(big_tty_mutex);
21struct task_struct *__big_tty_mutex_owner;
22EXPORT_SYMBOL_GPL(__big_tty_mutex_owner);
23
24/*
25 * Getting the big tty mutex.
26 */
27void __lockfunc tty_lock(void)
28{
29 struct task_struct *task = current;
30
31 WARN_ON(__big_tty_mutex_owner == task);
32
33 mutex_lock(&big_tty_mutex);
34 __big_tty_mutex_owner = task;
35}
36EXPORT_SYMBOL(tty_lock);
37
38void __lockfunc tty_unlock(void)
39{
40 struct task_struct *task = current;
41
42 WARN_ON(__big_tty_mutex_owner != task);
43 __big_tty_mutex_owner = NULL;
44
45 mutex_unlock(&big_tty_mutex);
46}
47EXPORT_SYMBOL(tty_unlock);
diff --git a/drivers/char/tty_port.c b/drivers/char/tty_port.c
index a3bd1d0b66cf..33d37d230f8f 100644
--- a/drivers/char/tty_port.c
+++ b/drivers/char/tty_port.c
@@ -231,7 +231,7 @@ int tty_port_block_til_ready(struct tty_port *port,
231 231
232 /* block if port is in the process of being closed */ 232 /* block if port is in the process of being closed */
233 if (tty_hung_up_p(filp) || port->flags & ASYNC_CLOSING) { 233 if (tty_hung_up_p(filp) || port->flags & ASYNC_CLOSING) {
234 wait_event_interruptible(port->close_wait, 234 wait_event_interruptible_tty(port->close_wait,
235 !(port->flags & ASYNC_CLOSING)); 235 !(port->flags & ASYNC_CLOSING));
236 if (port->flags & ASYNC_HUP_NOTIFY) 236 if (port->flags & ASYNC_HUP_NOTIFY)
237 return -EAGAIN; 237 return -EAGAIN;
@@ -294,7 +294,9 @@ int tty_port_block_til_ready(struct tty_port *port,
294 retval = -ERESTARTSYS; 294 retval = -ERESTARTSYS;
295 break; 295 break;
296 } 296 }
297 tty_unlock();
297 schedule(); 298 schedule();
299 tty_lock();
298 } 300 }
299 finish_wait(&port->open_wait, &wait); 301 finish_wait(&port->open_wait, &wait);
300 302
diff --git a/drivers/char/vc_screen.c b/drivers/char/vc_screen.c
index c1791a63d99d..bcce46c96b88 100644
--- a/drivers/char/vc_screen.c
+++ b/drivers/char/vc_screen.c
@@ -463,10 +463,10 @@ vcs_open(struct inode *inode, struct file *filp)
463 unsigned int currcons = iminor(inode) & 127; 463 unsigned int currcons = iminor(inode) & 127;
464 int ret = 0; 464 int ret = 0;
465 465
466 lock_kernel(); 466 tty_lock();
467 if(currcons && !vc_cons_allocated(currcons-1)) 467 if(currcons && !vc_cons_allocated(currcons-1))
468 ret = -ENXIO; 468 ret = -ENXIO;
469 unlock_kernel(); 469 tty_unlock();
470 return ret; 470 return ret;
471} 471}
472 472
diff --git a/drivers/char/vt.c b/drivers/char/vt.c
index 44f03ddd8871..c734f9b1263a 100644
--- a/drivers/char/vt.c
+++ b/drivers/char/vt.c
@@ -105,6 +105,7 @@
105#include <asm/system.h> 105#include <asm/system.h>
106#include <linux/uaccess.h> 106#include <linux/uaccess.h>
107#include <linux/kdb.h> 107#include <linux/kdb.h>
108#include <linux/ctype.h>
108 109
109#define MAX_NR_CON_DRIVER 16 110#define MAX_NR_CON_DRIVER 16
110 111
@@ -286,8 +287,12 @@ static inline unsigned short *screenpos(struct vc_data *vc, int offset, int view
286 return p; 287 return p;
287} 288}
288 289
290/* Called from the keyboard irq path.. */
289static inline void scrolldelta(int lines) 291static inline void scrolldelta(int lines)
290{ 292{
293 /* FIXME */
294 /* scrolldelta needs some kind of consistency lock, but the BKL was
295 and still is not protecting versus the scheduled back end */
291 scrollback_delta += lines; 296 scrollback_delta += lines;
292 schedule_console_callback(); 297 schedule_console_callback();
293} 298}
@@ -704,7 +709,10 @@ void redraw_screen(struct vc_data *vc, int is_switch)
704 update_attr(vc); 709 update_attr(vc);
705 clear_buffer_attributes(vc); 710 clear_buffer_attributes(vc);
706 } 711 }
707 if (update && vc->vc_mode != KD_GRAPHICS) 712
713 /* Forcibly update if we're panicing */
714 if ((update && vc->vc_mode != KD_GRAPHICS) ||
715 vt_force_oops_output(vc))
708 do_update_region(vc, vc->vc_origin, vc->vc_screenbuf_size / 2); 716 do_update_region(vc, vc->vc_origin, vc->vc_screenbuf_size / 2);
709 } 717 }
710 set_cursor(vc); 718 set_cursor(vc);
@@ -742,6 +750,7 @@ static void visual_init(struct vc_data *vc, int num, int init)
742 vc->vc_hi_font_mask = 0; 750 vc->vc_hi_font_mask = 0;
743 vc->vc_complement_mask = 0; 751 vc->vc_complement_mask = 0;
744 vc->vc_can_do_color = 0; 752 vc->vc_can_do_color = 0;
753 vc->vc_panic_force_write = false;
745 vc->vc_sw->con_init(vc, init); 754 vc->vc_sw->con_init(vc, init);
746 if (!vc->vc_complement_mask) 755 if (!vc->vc_complement_mask)
747 vc->vc_complement_mask = vc->vc_can_do_color ? 0x7700 : 0x0800; 756 vc->vc_complement_mask = vc->vc_can_do_color ? 0x7700 : 0x0800;
@@ -774,6 +783,7 @@ int vc_allocate(unsigned int currcons) /* return 0 on success */
774 if (!vc) 783 if (!vc)
775 return -ENOMEM; 784 return -ENOMEM;
776 vc_cons[currcons].d = vc; 785 vc_cons[currcons].d = vc;
786 tty_port_init(&vc->port);
777 INIT_WORK(&vc_cons[currcons].SAK_work, vc_SAK); 787 INIT_WORK(&vc_cons[currcons].SAK_work, vc_SAK);
778 visual_init(vc, currcons, 1); 788 visual_init(vc, currcons, 1);
779 if (!*vc->vc_uni_pagedir_loc) 789 if (!*vc->vc_uni_pagedir_loc)
@@ -963,12 +973,12 @@ static int vc_do_resize(struct tty_struct *tty, struct vc_data *vc,
963 * Resize a virtual console as seen from the console end of things. We 973 * Resize a virtual console as seen from the console end of things. We
964 * use the common vc_do_resize methods to update the structures. The 974 * use the common vc_do_resize methods to update the structures. The
965 * caller must hold the console sem to protect console internals and 975 * caller must hold the console sem to protect console internals and
966 * vc->vc_tty 976 * vc->port.tty
967 */ 977 */
968 978
969int vc_resize(struct vc_data *vc, unsigned int cols, unsigned int rows) 979int vc_resize(struct vc_data *vc, unsigned int cols, unsigned int rows)
970{ 980{
971 return vc_do_resize(vc->vc_tty, vc, cols, rows); 981 return vc_do_resize(vc->port.tty, vc, cols, rows);
972} 982}
973 983
974/** 984/**
@@ -1796,8 +1806,8 @@ static void do_con_trol(struct tty_struct *tty, struct vc_data *vc, int c)
1796 vc->vc_state = ESnormal; 1806 vc->vc_state = ESnormal;
1797 return; 1807 return;
1798 case ESpalette: 1808 case ESpalette:
1799 if ( (c>='0'&&c<='9') || (c>='A'&&c<='F') || (c>='a'&&c<='f') ) { 1809 if (isxdigit(c)) {
1800 vc->vc_par[vc->vc_npar++] = (c > '9' ? (c & 0xDF) - 'A' + 10 : c - '0'); 1810 vc->vc_par[vc->vc_npar++] = hex_to_bin(c);
1801 if (vc->vc_npar == 7) { 1811 if (vc->vc_npar == 7) {
1802 int i = vc->vc_par[0] * 3, j = 1; 1812 int i = vc->vc_par[0] * 3, j = 1;
1803 vc->vc_palette[i] = 16 * vc->vc_par[j++]; 1813 vc->vc_palette[i] = 16 * vc->vc_par[j++];
@@ -2505,7 +2515,7 @@ static void vt_console_print(struct console *co, const char *b, unsigned count)
2505 goto quit; 2515 goto quit;
2506 } 2516 }
2507 2517
2508 if (vc->vc_mode != KD_TEXT) 2518 if (vc->vc_mode != KD_TEXT && !vt_force_oops_output(vc))
2509 goto quit; 2519 goto quit;
2510 2520
2511 /* undraw cursor first */ 2521 /* undraw cursor first */
@@ -2611,8 +2621,6 @@ int tioclinux(struct tty_struct *tty, unsigned long arg)
2611 return -EFAULT; 2621 return -EFAULT;
2612 ret = 0; 2622 ret = 0;
2613 2623
2614 lock_kernel();
2615
2616 switch (type) 2624 switch (type)
2617 { 2625 {
2618 case TIOCL_SETSEL: 2626 case TIOCL_SETSEL:
@@ -2687,7 +2695,6 @@ int tioclinux(struct tty_struct *tty, unsigned long arg)
2687 ret = -EINVAL; 2695 ret = -EINVAL;
2688 break; 2696 break;
2689 } 2697 }
2690 unlock_kernel();
2691 return ret; 2698 return ret;
2692} 2699}
2693 2700
@@ -2800,12 +2807,12 @@ static int con_open(struct tty_struct *tty, struct file *filp)
2800 struct vc_data *vc = vc_cons[currcons].d; 2807 struct vc_data *vc = vc_cons[currcons].d;
2801 2808
2802 /* Still being freed */ 2809 /* Still being freed */
2803 if (vc->vc_tty) { 2810 if (vc->port.tty) {
2804 release_console_sem(); 2811 release_console_sem();
2805 return -ERESTARTSYS; 2812 return -ERESTARTSYS;
2806 } 2813 }
2807 tty->driver_data = vc; 2814 tty->driver_data = vc;
2808 vc->vc_tty = tty; 2815 vc->port.tty = tty;
2809 2816
2810 if (!tty->winsize.ws_row && !tty->winsize.ws_col) { 2817 if (!tty->winsize.ws_row && !tty->winsize.ws_col) {
2811 tty->winsize.ws_row = vc_cons[currcons].d->vc_rows; 2818 tty->winsize.ws_row = vc_cons[currcons].d->vc_rows;
@@ -2833,7 +2840,7 @@ static void con_shutdown(struct tty_struct *tty)
2833 struct vc_data *vc = tty->driver_data; 2840 struct vc_data *vc = tty->driver_data;
2834 BUG_ON(vc == NULL); 2841 BUG_ON(vc == NULL);
2835 acquire_console_sem(); 2842 acquire_console_sem();
2836 vc->vc_tty = NULL; 2843 vc->port.tty = NULL;
2837 release_console_sem(); 2844 release_console_sem();
2838 tty_shutdown(tty); 2845 tty_shutdown(tty);
2839} 2846}
@@ -2915,6 +2922,7 @@ static int __init con_init(void)
2915 for (currcons = 0; currcons < MIN_NR_CONSOLES; currcons++) { 2922 for (currcons = 0; currcons < MIN_NR_CONSOLES; currcons++) {
2916 vc_cons[currcons].d = vc = kzalloc(sizeof(struct vc_data), GFP_NOWAIT); 2923 vc_cons[currcons].d = vc = kzalloc(sizeof(struct vc_data), GFP_NOWAIT);
2917 INIT_WORK(&vc_cons[currcons].SAK_work, vc_SAK); 2924 INIT_WORK(&vc_cons[currcons].SAK_work, vc_SAK);
2925 tty_port_init(&vc->port);
2918 visual_init(vc, currcons, 1); 2926 visual_init(vc, currcons, 1);
2919 vc->vc_screenbuf = kzalloc(vc->vc_screenbuf_size, GFP_NOWAIT); 2927 vc->vc_screenbuf = kzalloc(vc->vc_screenbuf_size, GFP_NOWAIT);
2920 vc_init(vc, vc->vc_rows, vc->vc_cols, 2928 vc_init(vc, vc->vc_rows, vc->vc_cols,
@@ -3783,7 +3791,8 @@ void do_unblank_screen(int leaving_gfx)
3783 return; 3791 return;
3784 } 3792 }
3785 vc = vc_cons[fg_console].d; 3793 vc = vc_cons[fg_console].d;
3786 if (vc->vc_mode != KD_TEXT) 3794 /* Try to unblank in oops case too */
3795 if (vc->vc_mode != KD_TEXT && !vt_force_oops_output(vc))
3787 return; /* but leave console_blanked != 0 */ 3796 return; /* but leave console_blanked != 0 */
3788 3797
3789 if (blankinterval) { 3798 if (blankinterval) {
@@ -3792,7 +3801,7 @@ void do_unblank_screen(int leaving_gfx)
3792 } 3801 }
3793 3802
3794 console_blanked = 0; 3803 console_blanked = 0;
3795 if (vc->vc_sw->con_blank(vc, 0, leaving_gfx)) 3804 if (vc->vc_sw->con_blank(vc, 0, leaving_gfx) || vt_force_oops_output(vc))
3796 /* Low-level driver cannot restore -> do it ourselves */ 3805 /* Low-level driver cannot restore -> do it ourselves */
3797 update_screen(vc); 3806 update_screen(vc);
3798 if (console_blank_hook) 3807 if (console_blank_hook)
diff --git a/drivers/char/vt_ioctl.c b/drivers/char/vt_ioctl.c
index cb19dbc52136..2bbeaaea46e9 100644
--- a/drivers/char/vt_ioctl.c
+++ b/drivers/char/vt_ioctl.c
@@ -133,7 +133,7 @@ static void vt_event_wait(struct vt_event_wait *vw)
133 list_add(&vw->list, &vt_events); 133 list_add(&vw->list, &vt_events);
134 spin_unlock_irqrestore(&vt_event_lock, flags); 134 spin_unlock_irqrestore(&vt_event_lock, flags);
135 /* Wait for it to pass */ 135 /* Wait for it to pass */
136 wait_event_interruptible(vt_event_waitqueue, vw->done); 136 wait_event_interruptible_tty(vt_event_waitqueue, vw->done);
137 /* Dequeue it */ 137 /* Dequeue it */
138 spin_lock_irqsave(&vt_event_lock, flags); 138 spin_lock_irqsave(&vt_event_lock, flags);
139 list_del(&vw->list); 139 list_del(&vw->list);
@@ -509,7 +509,7 @@ int vt_ioctl(struct tty_struct *tty, struct file * file,
509 509
510 console = vc->vc_num; 510 console = vc->vc_num;
511 511
512 lock_kernel(); 512 tty_lock();
513 513
514 if (!vc_cons_allocated(console)) { /* impossible? */ 514 if (!vc_cons_allocated(console)) { /* impossible? */
515 ret = -ENOIOCTLCMD; 515 ret = -ENOIOCTLCMD;
@@ -1336,7 +1336,7 @@ int vt_ioctl(struct tty_struct *tty, struct file * file,
1336 ret = -ENOIOCTLCMD; 1336 ret = -ENOIOCTLCMD;
1337 } 1337 }
1338out: 1338out:
1339 unlock_kernel(); 1339 tty_unlock();
1340 return ret; 1340 return ret;
1341eperm: 1341eperm:
1342 ret = -EPERM; 1342 ret = -EPERM;
@@ -1369,7 +1369,7 @@ void vc_SAK(struct work_struct *work)
1369 acquire_console_sem(); 1369 acquire_console_sem();
1370 vc = vc_con->d; 1370 vc = vc_con->d;
1371 if (vc) { 1371 if (vc) {
1372 tty = vc->vc_tty; 1372 tty = vc->port.tty;
1373 /* 1373 /*
1374 * SAK should also work in all raw modes and reset 1374 * SAK should also work in all raw modes and reset
1375 * them properly. 1375 * them properly.
@@ -1503,7 +1503,7 @@ long vt_compat_ioctl(struct tty_struct *tty, struct file * file,
1503 1503
1504 console = vc->vc_num; 1504 console = vc->vc_num;
1505 1505
1506 lock_kernel(); 1506 tty_lock();
1507 1507
1508 if (!vc_cons_allocated(console)) { /* impossible? */ 1508 if (!vc_cons_allocated(console)) { /* impossible? */
1509 ret = -ENOIOCTLCMD; 1509 ret = -ENOIOCTLCMD;
@@ -1571,11 +1571,11 @@ long vt_compat_ioctl(struct tty_struct *tty, struct file * file,
1571 goto fallback; 1571 goto fallback;
1572 } 1572 }
1573out: 1573out:
1574 unlock_kernel(); 1574 tty_unlock();
1575 return ret; 1575 return ret;
1576 1576
1577fallback: 1577fallback:
1578 unlock_kernel(); 1578 tty_unlock();
1579 return vt_ioctl(tty, file, cmd, arg); 1579 return vt_ioctl(tty, file, cmd, arg);
1580} 1580}
1581 1581
@@ -1761,10 +1761,13 @@ int vt_move_to_console(unsigned int vt, int alloc)
1761 return -EIO; 1761 return -EIO;
1762 } 1762 }
1763 release_console_sem(); 1763 release_console_sem();
1764 tty_lock();
1764 if (vt_waitactive(vt + 1)) { 1765 if (vt_waitactive(vt + 1)) {
1765 pr_debug("Suspend: Can't switch VCs."); 1766 pr_debug("Suspend: Can't switch VCs.");
1767 tty_unlock();
1766 return -EINTR; 1768 return -EINTR;
1767 } 1769 }
1770 tty_unlock();
1768 return prev; 1771 return prev;
1769} 1772}
1770 1773