提交 5785c95b 编写于 作者: A Arjan van de Ven 提交者: Linus Torvalds

[PATCH] tty: make termios_sem a mutex

[akpm@osdl.org: fix]
Cc: Alan Cox <alan@lxorguk.ukuu.org.uk>
Cc: Arjan van de Ven <arjan@infradead.org>
Signed-off-by: NAndrew Morton <akpm@osdl.org>
Signed-off-by: NLinus Torvalds <torvalds@osdl.org>
上级 54306cf0
...@@ -618,9 +618,9 @@ EXPORT_SYMBOL_GPL(tty_prepare_flip_string_flags); ...@@ -618,9 +618,9 @@ EXPORT_SYMBOL_GPL(tty_prepare_flip_string_flags);
static void tty_set_termios_ldisc(struct tty_struct *tty, int num) static void tty_set_termios_ldisc(struct tty_struct *tty, int num)
{ {
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
tty->termios->c_line = num; tty->termios->c_line = num;
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
} }
/* /*
...@@ -1338,9 +1338,9 @@ static void do_tty_hangup(void *data) ...@@ -1338,9 +1338,9 @@ static void do_tty_hangup(void *data)
*/ */
if (tty->driver->flags & TTY_DRIVER_RESET_TERMIOS) if (tty->driver->flags & TTY_DRIVER_RESET_TERMIOS)
{ {
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
*tty->termios = tty->driver->init_termios; *tty->termios = tty->driver->init_termios;
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
} }
/* Defer ldisc switch */ /* Defer ldisc switch */
...@@ -2750,9 +2750,9 @@ static int tiocgwinsz(struct tty_struct *tty, struct winsize __user * arg) ...@@ -2750,9 +2750,9 @@ static int tiocgwinsz(struct tty_struct *tty, struct winsize __user * arg)
{ {
int err; int err;
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
err = copy_to_user(arg, &tty->winsize, sizeof(*arg)); err = copy_to_user(arg, &tty->winsize, sizeof(*arg));
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
return err ? -EFAULT: 0; return err ? -EFAULT: 0;
} }
...@@ -2782,14 +2782,15 @@ static int tiocswinsz(struct tty_struct *tty, struct tty_struct *real_tty, ...@@ -2782,14 +2782,15 @@ static int tiocswinsz(struct tty_struct *tty, struct tty_struct *real_tty,
if (copy_from_user(&tmp_ws, arg, sizeof(*arg))) if (copy_from_user(&tmp_ws, arg, sizeof(*arg)))
return -EFAULT; return -EFAULT;
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
if (!memcmp(&tmp_ws, &tty->winsize, sizeof(*arg))) if (!memcmp(&tmp_ws, &tty->winsize, sizeof(*arg)))
goto done; goto done;
#ifdef CONFIG_VT #ifdef CONFIG_VT
if (tty->driver->type == TTY_DRIVER_TYPE_CONSOLE) { if (tty->driver->type == TTY_DRIVER_TYPE_CONSOLE) {
if (vc_lock_resize(tty->driver_data, tmp_ws.ws_col, tmp_ws.ws_row)) { if (vc_lock_resize(tty->driver_data, tmp_ws.ws_col,
up(&tty->termios_sem); tmp_ws.ws_row)) {
mutex_unlock(&tty->termios_mutex);
return -ENXIO; return -ENXIO;
} }
} }
...@@ -2801,7 +2802,7 @@ static int tiocswinsz(struct tty_struct *tty, struct tty_struct *real_tty, ...@@ -2801,7 +2802,7 @@ static int tiocswinsz(struct tty_struct *tty, struct tty_struct *real_tty,
tty->winsize = tmp_ws; tty->winsize = tmp_ws;
real_tty->winsize = tmp_ws; real_tty->winsize = tmp_ws;
done: done:
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
return 0; return 0;
} }
...@@ -3576,7 +3577,7 @@ static void initialize_tty_struct(struct tty_struct *tty) ...@@ -3576,7 +3577,7 @@ static void initialize_tty_struct(struct tty_struct *tty)
tty_buffer_init(tty); tty_buffer_init(tty);
INIT_WORK(&tty->buf.work, flush_to_ldisc, tty); INIT_WORK(&tty->buf.work, flush_to_ldisc, tty);
init_MUTEX(&tty->buf.pty_sem); init_MUTEX(&tty->buf.pty_sem);
init_MUTEX(&tty->termios_sem); mutex_init(&tty->termios_mutex);
init_waitqueue_head(&tty->write_wait); init_waitqueue_head(&tty->write_wait);
init_waitqueue_head(&tty->read_wait); init_waitqueue_head(&tty->read_wait);
INIT_WORK(&tty->hangup_work, do_tty_hangup, tty); INIT_WORK(&tty->hangup_work, do_tty_hangup, tty);
......
...@@ -20,6 +20,7 @@ ...@@ -20,6 +20,7 @@
#include <linux/mm.h> #include <linux/mm.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/bitops.h> #include <linux/bitops.h>
#include <linux/mutex.h>
#include <asm/io.h> #include <asm/io.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
...@@ -131,7 +132,7 @@ static void change_termios(struct tty_struct * tty, struct termios * new_termios ...@@ -131,7 +132,7 @@ static void change_termios(struct tty_struct * tty, struct termios * new_termios
/* FIXME: we need to decide on some locking/ordering semantics /* FIXME: we need to decide on some locking/ordering semantics
for the set_termios notification eventually */ for the set_termios notification eventually */
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
*tty->termios = *new_termios; *tty->termios = *new_termios;
unset_locked_termios(tty->termios, &old_termios, tty->termios_locked); unset_locked_termios(tty->termios, &old_termios, tty->termios_locked);
...@@ -176,7 +177,7 @@ static void change_termios(struct tty_struct * tty, struct termios * new_termios ...@@ -176,7 +177,7 @@ static void change_termios(struct tty_struct * tty, struct termios * new_termios
(ld->set_termios)(tty, &old_termios); (ld->set_termios)(tty, &old_termios);
tty_ldisc_deref(ld); tty_ldisc_deref(ld);
} }
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
} }
/** /**
...@@ -284,13 +285,13 @@ static int get_sgttyb(struct tty_struct * tty, struct sgttyb __user * sgttyb) ...@@ -284,13 +285,13 @@ static int get_sgttyb(struct tty_struct * tty, struct sgttyb __user * sgttyb)
{ {
struct sgttyb tmp; struct sgttyb tmp;
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
tmp.sg_ispeed = 0; tmp.sg_ispeed = 0;
tmp.sg_ospeed = 0; tmp.sg_ospeed = 0;
tmp.sg_erase = tty->termios->c_cc[VERASE]; tmp.sg_erase = tty->termios->c_cc[VERASE];
tmp.sg_kill = tty->termios->c_cc[VKILL]; tmp.sg_kill = tty->termios->c_cc[VKILL];
tmp.sg_flags = get_sgflags(tty); tmp.sg_flags = get_sgflags(tty);
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
return copy_to_user(sgttyb, &tmp, sizeof(tmp)) ? -EFAULT : 0; return copy_to_user(sgttyb, &tmp, sizeof(tmp)) ? -EFAULT : 0;
} }
...@@ -345,12 +346,12 @@ static int set_sgttyb(struct tty_struct * tty, struct sgttyb __user * sgttyb) ...@@ -345,12 +346,12 @@ static int set_sgttyb(struct tty_struct * tty, struct sgttyb __user * sgttyb)
if (copy_from_user(&tmp, sgttyb, sizeof(tmp))) if (copy_from_user(&tmp, sgttyb, sizeof(tmp)))
return -EFAULT; return -EFAULT;
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
termios = *tty->termios; termios = *tty->termios;
termios.c_cc[VERASE] = tmp.sg_erase; termios.c_cc[VERASE] = tmp.sg_erase;
termios.c_cc[VKILL] = tmp.sg_kill; termios.c_cc[VKILL] = tmp.sg_kill;
set_sgflags(&termios, tmp.sg_flags); set_sgflags(&termios, tmp.sg_flags);
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
change_termios(tty, &termios); change_termios(tty, &termios);
return 0; return 0;
} }
...@@ -592,11 +593,11 @@ int n_tty_ioctl(struct tty_struct * tty, struct file * file, ...@@ -592,11 +593,11 @@ int n_tty_ioctl(struct tty_struct * tty, struct file * file,
case TIOCSSOFTCAR: case TIOCSSOFTCAR:
if (get_user(arg, (unsigned int __user *) arg)) if (get_user(arg, (unsigned int __user *) arg))
return -EFAULT; return -EFAULT;
down(&tty->termios_sem); mutex_lock(&tty->termios_mutex);
tty->termios->c_cflag = tty->termios->c_cflag =
((tty->termios->c_cflag & ~CLOCAL) | ((tty->termios->c_cflag & ~CLOCAL) |
(arg ? CLOCAL : 0)); (arg ? CLOCAL : 0));
up(&tty->termios_sem); mutex_unlock(&tty->termios_mutex);
return 0; return 0;
default: default:
return -ENOIOCTLCMD; return -ENOIOCTLCMD;
......
...@@ -174,7 +174,7 @@ struct tty_struct { ...@@ -174,7 +174,7 @@ struct tty_struct {
struct tty_driver *driver; struct tty_driver *driver;
int index; int index;
struct tty_ldisc ldisc; struct tty_ldisc ldisc;
struct semaphore termios_sem; struct mutex termios_mutex;
struct termios *termios, *termios_locked; struct termios *termios, *termios_locked;
char name[64]; char name[64];
int pgrp; int pgrp;
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册