diff options
author | tanimura <tanimura@FreeBSD.org> | 2002-02-23 11:12:57 +0000 |
---|---|---|
committer | tanimura <tanimura@FreeBSD.org> | 2002-02-23 11:12:57 +0000 |
commit | a09da298590e8c11ebafa37f79e0046814665237 (patch) | |
tree | 2289c653c0f7aa23498f82b603c33107952652ec /sys/kern/tty_tty.c | |
parent | 33e8ee5265ca2838260ab581a9cebdedb1e1e29b (diff) | |
download | FreeBSD-src-a09da298590e8c11ebafa37f79e0046814665237.zip FreeBSD-src-a09da298590e8c11ebafa37f79e0046814665237.tar.gz |
Lock struct pgrp, session and sigio.
New locks are:
- pgrpsess_lock which locks the whole pgrps and sessions,
- pg_mtx which protects the pgrp members, and
- s_mtx which protects the session members.
Please refer to sys/proc.h for the coverage of these locks.
Changes on the pgrp/session interface:
- pgfind() needs the pgrpsess_lock held.
- The caller of enterpgrp() is responsible to allocate a new pgrp and
session.
- Call enterthispgrp() in order to enter an existing pgrp.
- pgsignal() requires a pgrp lock held.
Reviewed by: jhb, alfred
Tested on: cvsup.jp.FreeBSD.org
(which is a quad-CPU machine running -current)
Diffstat (limited to 'sys/kern/tty_tty.c')
-rw-r--r-- | sys/kern/tty_tty.c | 56 |
1 files changed, 47 insertions, 9 deletions
diff --git a/sys/kern/tty_tty.c b/sys/kern/tty_tty.c index 1c6635c..931da01 100644 --- a/sys/kern/tty_tty.c +++ b/sys/kern/tty_tty.c @@ -43,6 +43,8 @@ #include <sys/conf.h> #include <sys/kernel.h> #include <sys/lock.h> +#include <sys/mutex.h> +#include <sys/sx.h> #include <sys/proc.h> #include <sys/ttycom.h> #include <sys/vnode.h> @@ -80,9 +82,15 @@ cttyopen(dev, flag, mode, td) int flag, mode; struct thread *td; { - struct vnode *ttyvp = cttyvp(td); + struct vnode *ttyvp; int error; + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + ttyvp = cttyvp(td); + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); + if (ttyvp == NULL) return (ENXIO); vn_lock(ttyvp, LK_EXCLUSIVE | LK_RETRY, td); @@ -99,9 +107,15 @@ cttyread(dev, uio, flag) int flag; { struct thread *td = uio->uio_td; - register struct vnode *ttyvp = cttyvp(td); + register struct vnode *ttyvp; int error; + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + ttyvp = cttyvp(td); + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); + if (ttyvp == NULL) return (EIO); vn_lock(ttyvp, LK_EXCLUSIVE | LK_RETRY, td); @@ -118,10 +132,16 @@ cttywrite(dev, uio, flag) int flag; { struct thread *td = uio->uio_td; - struct vnode *ttyvp = cttyvp(uio->uio_td); + struct vnode *ttyvp; struct mount *mp; int error; + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + ttyvp = cttyvp(td); + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); + if (ttyvp == NULL) return (EIO); mp = NULL; @@ -144,18 +164,30 @@ cttyioctl(dev, cmd, addr, flag, td) int flag; struct thread *td; { - struct vnode *ttyvp = cttyvp(td); + struct vnode *ttyvp; + int error; + + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + ttyvp = cttyvp(td); + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); if (ttyvp == NULL) return (EIO); if (cmd == TIOCSCTTY) /* don't allow controlling tty to be set */ return EINVAL; /* to controlling tty -- infinite recursion */ if (cmd == TIOCNOTTY) { - if (!SESS_LEADER(td->td_proc)) { + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + error = 0; + if (!SESS_LEADER(td->td_proc)) td->td_proc->p_flag &= ~P_CONTROLT; - return (0); - } else - return (EINVAL); + else + error = EINVAL; + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); + return (error); } return (VOP_IOCTL(ttyvp, cmd, addr, flag, NOCRED, td)); } @@ -167,7 +199,13 @@ cttypoll(dev, events, td) int events; struct thread *td; { - struct vnode *ttyvp = cttyvp(td); + struct vnode *ttyvp; + + PROC_LOCK(td->td_proc); + SESS_LOCK(td->td_proc->p_session); + ttyvp = cttyvp(td); + SESS_UNLOCK(td->td_proc->p_session); + PROC_UNLOCK(td->td_proc); if (ttyvp == NULL) /* try operation to get EOF/failure */ |