34c34
< * $FreeBSD: head/sys/kern/kern_proc.c 91066 2002-02-22 13:32:01Z phk $
---
> * $FreeBSD: head/sys/kern/kern_proc.c 91140 2002-02-23 11:12:57Z tanimura $
58c58
< static MALLOC_DEFINE(M_PGRP, "pgrp", "process group header");
---
> MALLOC_DEFINE(M_PGRP, "pgrp", "process group header");
62a63,66
> static struct proc *dopfind __P((register pid_t));
>
> static void doenterpgrp __P((struct proc *, struct pgrp *));
>
65c69
< static void orphanpg __P((struct pgrp *pg));
---
> static void orphanpg __P((struct pgrp *pg));
77a82
> struct sx pgrpsess_lock;
90a96
> sx_init(&pgrpsess_lock, "pgrpsess");
267a274,286
> p = dopfind(pid);
> sx_sunlock(&allproc_lock);
> return (p);
> }
>
> static struct proc *
> dopfind(pid)
> register pid_t pid;
> {
> register struct proc *p;
>
> sx_assert(&allproc_lock, SX_LOCKED);
>
273d291
< sx_sunlock(&allproc_lock);
278c296,297
< * Locate a process group by number
---
> * Locate a process group by number.
> * The caller must hold pgrpsess_lock.
286,287c305,309
< LIST_FOREACH(pgrp, PGRPHASH(pgid), pg_hash)
< if (pgrp->pg_id == pgid)
---
> PGRPSESS_LOCK_ASSERT(SX_LOCKED);
>
> LIST_FOREACH(pgrp, PGRPHASH(pgid), pg_hash) {
> if (pgrp->pg_id == pgid) {
> PGRP_LOCK(pgrp);
288a311,312
> }
> }
293c317,319
< * Move p to a new or existing process group (and session)
---
> * Create a new process group.
> * pgid must be equal to the pid of p.
> * Begin a new session if required.
296c322
< enterpgrp(p, pgid, mksess)
---
> enterpgrp(p, pgid, pgrp, sess)
299c325,326
< int mksess;
---
> struct pgrp *pgrp;
> struct session *sess;
301,302c328
< register struct pgrp *pgrp = pgfind(pgid);
< struct pgrp *savegrp;
---
> struct pgrp *pgrp2;
304,305c330,339
< KASSERT(pgrp == NULL || !mksess,
< ("enterpgrp: setsid into non-empty pgrp"));
---
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
>
> KASSERT(pgrp != NULL, ("enterpgrp: pgrp == NULL"));
> KASSERT(p->p_pid == pgid,
> ("enterpgrp: new pgrp and pid != pgid"));
>
> pgrp2 = pgfind(pgid);
>
> KASSERT(pgrp2 == NULL,
> ("enterpgrp: pgrp with pgid exists"));
309,311c343,345
< if (pgrp == NULL) {
< pid_t savepid = p->p_pid;
< struct proc *np;
---
> mtx_init(&pgrp->pg_mtx, "process group", MTX_DEF);
>
> if (sess != NULL) {
313c347
< * new process group
---
> * new session
315,338c349,359
< KASSERT(p->p_pid == pgid,
< ("enterpgrp: new pgrp and pid != pgid"));
< if ((np = pfind(savepid)) == NULL || np != p) {
< if (np != NULL)
< PROC_UNLOCK(np);
< return (ESRCH);
< }
< PROC_UNLOCK(np);
< MALLOC(pgrp, struct pgrp *, sizeof(struct pgrp), M_PGRP,
< M_WAITOK);
< if (mksess) {
< register struct session *sess;
<
< /*
< * new session
< */
< MALLOC(sess, struct session *, sizeof(struct session),
< M_SESSION, M_WAITOK);
< sess->s_leader = p;
< sess->s_sid = p->p_pid;
< sess->s_count = 1;
< sess->s_ttyvp = NULL;
< sess->s_ttyp = NULL;
< bcopy(p->p_session->s_login, sess->s_login,
---
> mtx_init(&sess->s_mtx, "session", MTX_DEF);
> PROC_LOCK(p);
> p->p_flag &= ~P_CONTROLT;
> PROC_UNLOCK(p);
> PGRP_LOCK(pgrp);
> sess->s_leader = p;
> sess->s_sid = p->p_pid;
> sess->s_count = 1;
> sess->s_ttyvp = NULL;
> sess->s_ttyp = NULL;
> bcopy(p->p_session->s_login, sess->s_login,
340,356c361,372
< PROC_LOCK(p);
< p->p_flag &= ~P_CONTROLT;
< PROC_UNLOCK(p);
< pgrp->pg_session = sess;
< KASSERT(p == curproc,
< ("enterpgrp: mksession and p != curproc"));
< } else {
< pgrp->pg_session = p->p_session;
< pgrp->pg_session->s_count++;
< }
< pgrp->pg_id = pgid;
< LIST_INIT(&pgrp->pg_members);
< LIST_INSERT_HEAD(PGRPHASH(pgid), pgrp, pg_hash);
< pgrp->pg_jobc = 0;
< SLIST_INIT(&pgrp->pg_sigiolst);
< } else if (pgrp == p->p_pgrp)
< return (0);
---
> pgrp->pg_session = sess;
> KASSERT(p == curproc,
> ("enterpgrp: mksession and p != curproc"));
> } else {
> pgrp->pg_session = p->p_session;
> SESS_LOCK(pgrp->pg_session);
> pgrp->pg_session->s_count++;
> SESS_UNLOCK(pgrp->pg_session);
> PGRP_LOCK(pgrp);
> }
> pgrp->pg_id = pgid;
> LIST_INIT(&pgrp->pg_members);
358a375,432
> * As we have an exclusive lock of pgrpsess_lock,
> * this should not deadlock.
> */
> LIST_INSERT_HEAD(PGRPHASH(pgid), pgrp, pg_hash);
> pgrp->pg_jobc = 0;
> SLIST_INIT(&pgrp->pg_sigiolst);
> PGRP_UNLOCK(pgrp);
>
> doenterpgrp(p, pgrp);
>
> return (0);
> }
>
> /*
> * Move p to an existing process group
> */
> int
> enterthispgrp(p, pgrp)
> register struct proc *p;
> struct pgrp *pgrp;
> {
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(p->p_pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(p->p_session, MA_NOTOWNED);
> KASSERT(pgrp->pg_session == p->p_session,
> ("%s: pgrp's session %p, p->p_session %p.\n",
> __func__,
> pgrp->pg_session,
> p->p_session));
> KASSERT(pgrp != p->p_pgrp,
> ("%s: p belongs to pgrp.", __func__));
>
> doenterpgrp(p, pgrp);
>
> return (0);
> }
>
> /*
> * Move p to a process group
> */
> static void
> doenterpgrp(p, pgrp)
> struct proc *p;
> struct pgrp *pgrp;
> {
> struct pgrp *savepgrp;
>
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(p->p_pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(p->p_session, MA_NOTOWNED);
>
> savepgrp = p->p_pgrp;
>
> /*
365a440,441
> PGRP_LOCK(pgrp);
> PGRP_LOCK(savepgrp);
368d443
< savegrp = p->p_pgrp;
370d444
< LIST_INSERT_HEAD(&pgrp->pg_members, p, p_pglist);
372,374c446,450
< if (LIST_EMPTY(&savegrp->pg_members))
< pgdelete(savegrp);
< return (0);
---
> LIST_INSERT_HEAD(&pgrp->pg_members, p, p_pglist);
> PGRP_UNLOCK(savepgrp);
> PGRP_UNLOCK(pgrp);
> if (LIST_EMPTY(&savepgrp->pg_members))
> pgdelete(savepgrp);
384c460
< struct pgrp *savegrp;
---
> struct pgrp *savepgrp;
385a462,464
> PGRPSESS_XLOCK();
> savepgrp = p->p_pgrp;
> PGRP_LOCK(savepgrp);
388d466
< savegrp = p->p_pgrp;
391,392c469,472
< if (LIST_EMPTY(&savegrp->pg_members))
< pgdelete(savegrp);
---
> PGRP_UNLOCK(savepgrp);
> if (LIST_EMPTY(&savepgrp->pg_members))
> pgdelete(savepgrp);
> PGRPSESS_XUNLOCK();
402a483
> struct session *savesess;
403a485,490
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(pgrp->pg_session, MA_NOTOWNED);
>
> PGRP_LOCK(pgrp);
>
414c501,507
< if (--pgrp->pg_session->s_count == 0)
---
> savesess = pgrp->pg_session;
> SESS_LOCK(savesess);
> savesess->s_count--;
> SESS_UNLOCK(savesess);
> PGRP_UNLOCK(pgrp);
> if (savesess->s_count == 0) {
> mtx_destroy(&savesess->s_mtx);
415a509,510
> }
> mtx_destroy(&pgrp->pg_mtx);
436c531
< register struct session *mysession = pgrp->pg_session;
---
> register struct session *mysession;
437a533,537
> PGRPSESS_LOCK_ASSERT(SX_LOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(pgrp->pg_session, MA_NOTOWNED);
>
441a542
> mysession = pgrp->pg_session;
444a546
> PGRP_LOCK(pgrp);
447,448c549,554
< else if (--pgrp->pg_jobc == 0)
< orphanpg(pgrp);
---
> else {
> --pgrp->pg_jobc;
> if (pgrp->pg_jobc == 0)
> orphanpg(pgrp);
> }
> PGRP_UNLOCK(pgrp);
456c562
< LIST_FOREACH(p, &p->p_children, p_sibling)
---
> LIST_FOREACH(p, &p->p_children, p_sibling) {
459a566
> PGRP_LOCK(hispgrp);
462,463c569,574
< else if (--hispgrp->pg_jobc == 0)
< orphanpg(hispgrp);
---
> else {
> --hispgrp->pg_jobc;
> if (hispgrp->pg_jobc == 0)
> orphanpg(hispgrp);
> }
> PGRP_UNLOCK(hispgrp);
464a576
> }
478a591,592
> PGRP_LOCK_ASSERT(pg, MA_OWNED);
>
621a736
> tp = NULL;
628a744
> SESS_LOCK(sp);
634a751,752
> tp = sp->s_ttyp;
> SESS_UNLOCK(sp);
637c755
< if ((p->p_flag & P_CONTROLT) && sp && ((tp = sp->s_ttyp) != NULL)) {
---
> if ((p->p_flag & P_CONTROLT) && tp != NULL) {
770a889
> PROC_LOCK(p);
772c891,892
< p->p_pgrp->pg_id != (pid_t)name[0])
---
> p->p_pgrp->pg_id != (pid_t)name[0]) {
> PROC_UNLOCK(p);
773a894,895
> }
> PROC_UNLOCK(p);
776a899
> PROC_LOCK(p);
778,779c901,906
< p->p_session == NULL ||
< p->p_session->s_ttyp == NULL ||
---
> p->p_session == NULL) {
> PROC_UNLOCK(p);
> continue;
> }
> SESS_LOCK(p->p_session);
> if (p->p_session->s_ttyp == NULL ||
781c908,910
< (udev_t)name[0])
---
> (udev_t)name[0]) {
> SESS_UNLOCK(p->p_session);
> PROC_UNLOCK(p);
782a912,914
> }
> SESS_UNLOCK(p->p_session);
> PROC_UNLOCK(p);
< * $FreeBSD: head/sys/kern/kern_proc.c 91066 2002-02-22 13:32:01Z phk $
---
> * $FreeBSD: head/sys/kern/kern_proc.c 91140 2002-02-23 11:12:57Z tanimura $
58c58
< static MALLOC_DEFINE(M_PGRP, "pgrp", "process group header");
---
> MALLOC_DEFINE(M_PGRP, "pgrp", "process group header");
62a63,66
> static struct proc *dopfind __P((register pid_t));
>
> static void doenterpgrp __P((struct proc *, struct pgrp *));
>
65c69
< static void orphanpg __P((struct pgrp *pg));
---
> static void orphanpg __P((struct pgrp *pg));
77a82
> struct sx pgrpsess_lock;
90a96
> sx_init(&pgrpsess_lock, "pgrpsess");
267a274,286
> p = dopfind(pid);
> sx_sunlock(&allproc_lock);
> return (p);
> }
>
> static struct proc *
> dopfind(pid)
> register pid_t pid;
> {
> register struct proc *p;
>
> sx_assert(&allproc_lock, SX_LOCKED);
>
273d291
< sx_sunlock(&allproc_lock);
278c296,297
< * Locate a process group by number
---
> * Locate a process group by number.
> * The caller must hold pgrpsess_lock.
286,287c305,309
< LIST_FOREACH(pgrp, PGRPHASH(pgid), pg_hash)
< if (pgrp->pg_id == pgid)
---
> PGRPSESS_LOCK_ASSERT(SX_LOCKED);
>
> LIST_FOREACH(pgrp, PGRPHASH(pgid), pg_hash) {
> if (pgrp->pg_id == pgid) {
> PGRP_LOCK(pgrp);
288a311,312
> }
> }
293c317,319
< * Move p to a new or existing process group (and session)
---
> * Create a new process group.
> * pgid must be equal to the pid of p.
> * Begin a new session if required.
296c322
< enterpgrp(p, pgid, mksess)
---
> enterpgrp(p, pgid, pgrp, sess)
299c325,326
< int mksess;
---
> struct pgrp *pgrp;
> struct session *sess;
301,302c328
< register struct pgrp *pgrp = pgfind(pgid);
< struct pgrp *savegrp;
---
> struct pgrp *pgrp2;
304,305c330,339
< KASSERT(pgrp == NULL || !mksess,
< ("enterpgrp: setsid into non-empty pgrp"));
---
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
>
> KASSERT(pgrp != NULL, ("enterpgrp: pgrp == NULL"));
> KASSERT(p->p_pid == pgid,
> ("enterpgrp: new pgrp and pid != pgid"));
>
> pgrp2 = pgfind(pgid);
>
> KASSERT(pgrp2 == NULL,
> ("enterpgrp: pgrp with pgid exists"));
309,311c343,345
< if (pgrp == NULL) {
< pid_t savepid = p->p_pid;
< struct proc *np;
---
> mtx_init(&pgrp->pg_mtx, "process group", MTX_DEF);
>
> if (sess != NULL) {
313c347
< * new process group
---
> * new session
315,338c349,359
< KASSERT(p->p_pid == pgid,
< ("enterpgrp: new pgrp and pid != pgid"));
< if ((np = pfind(savepid)) == NULL || np != p) {
< if (np != NULL)
< PROC_UNLOCK(np);
< return (ESRCH);
< }
< PROC_UNLOCK(np);
< MALLOC(pgrp, struct pgrp *, sizeof(struct pgrp), M_PGRP,
< M_WAITOK);
< if (mksess) {
< register struct session *sess;
<
< /*
< * new session
< */
< MALLOC(sess, struct session *, sizeof(struct session),
< M_SESSION, M_WAITOK);
< sess->s_leader = p;
< sess->s_sid = p->p_pid;
< sess->s_count = 1;
< sess->s_ttyvp = NULL;
< sess->s_ttyp = NULL;
< bcopy(p->p_session->s_login, sess->s_login,
---
> mtx_init(&sess->s_mtx, "session", MTX_DEF);
> PROC_LOCK(p);
> p->p_flag &= ~P_CONTROLT;
> PROC_UNLOCK(p);
> PGRP_LOCK(pgrp);
> sess->s_leader = p;
> sess->s_sid = p->p_pid;
> sess->s_count = 1;
> sess->s_ttyvp = NULL;
> sess->s_ttyp = NULL;
> bcopy(p->p_session->s_login, sess->s_login,
340,356c361,372
< PROC_LOCK(p);
< p->p_flag &= ~P_CONTROLT;
< PROC_UNLOCK(p);
< pgrp->pg_session = sess;
< KASSERT(p == curproc,
< ("enterpgrp: mksession and p != curproc"));
< } else {
< pgrp->pg_session = p->p_session;
< pgrp->pg_session->s_count++;
< }
< pgrp->pg_id = pgid;
< LIST_INIT(&pgrp->pg_members);
< LIST_INSERT_HEAD(PGRPHASH(pgid), pgrp, pg_hash);
< pgrp->pg_jobc = 0;
< SLIST_INIT(&pgrp->pg_sigiolst);
< } else if (pgrp == p->p_pgrp)
< return (0);
---
> pgrp->pg_session = sess;
> KASSERT(p == curproc,
> ("enterpgrp: mksession and p != curproc"));
> } else {
> pgrp->pg_session = p->p_session;
> SESS_LOCK(pgrp->pg_session);
> pgrp->pg_session->s_count++;
> SESS_UNLOCK(pgrp->pg_session);
> PGRP_LOCK(pgrp);
> }
> pgrp->pg_id = pgid;
> LIST_INIT(&pgrp->pg_members);
358a375,432
> * As we have an exclusive lock of pgrpsess_lock,
> * this should not deadlock.
> */
> LIST_INSERT_HEAD(PGRPHASH(pgid), pgrp, pg_hash);
> pgrp->pg_jobc = 0;
> SLIST_INIT(&pgrp->pg_sigiolst);
> PGRP_UNLOCK(pgrp);
>
> doenterpgrp(p, pgrp);
>
> return (0);
> }
>
> /*
> * Move p to an existing process group
> */
> int
> enterthispgrp(p, pgrp)
> register struct proc *p;
> struct pgrp *pgrp;
> {
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(p->p_pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(p->p_session, MA_NOTOWNED);
> KASSERT(pgrp->pg_session == p->p_session,
> ("%s: pgrp's session %p, p->p_session %p.\n",
> __func__,
> pgrp->pg_session,
> p->p_session));
> KASSERT(pgrp != p->p_pgrp,
> ("%s: p belongs to pgrp.", __func__));
>
> doenterpgrp(p, pgrp);
>
> return (0);
> }
>
> /*
> * Move p to a process group
> */
> static void
> doenterpgrp(p, pgrp)
> struct proc *p;
> struct pgrp *pgrp;
> {
> struct pgrp *savepgrp;
>
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(p->p_pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(p->p_session, MA_NOTOWNED);
>
> savepgrp = p->p_pgrp;
>
> /*
365a440,441
> PGRP_LOCK(pgrp);
> PGRP_LOCK(savepgrp);
368d443
< savegrp = p->p_pgrp;
370d444
< LIST_INSERT_HEAD(&pgrp->pg_members, p, p_pglist);
372,374c446,450
< if (LIST_EMPTY(&savegrp->pg_members))
< pgdelete(savegrp);
< return (0);
---
> LIST_INSERT_HEAD(&pgrp->pg_members, p, p_pglist);
> PGRP_UNLOCK(savepgrp);
> PGRP_UNLOCK(pgrp);
> if (LIST_EMPTY(&savepgrp->pg_members))
> pgdelete(savepgrp);
384c460
< struct pgrp *savegrp;
---
> struct pgrp *savepgrp;
385a462,464
> PGRPSESS_XLOCK();
> savepgrp = p->p_pgrp;
> PGRP_LOCK(savepgrp);
388d466
< savegrp = p->p_pgrp;
391,392c469,472
< if (LIST_EMPTY(&savegrp->pg_members))
< pgdelete(savegrp);
---
> PGRP_UNLOCK(savepgrp);
> if (LIST_EMPTY(&savepgrp->pg_members))
> pgdelete(savepgrp);
> PGRPSESS_XUNLOCK();
402a483
> struct session *savesess;
403a485,490
> PGRPSESS_LOCK_ASSERT(SX_XLOCKED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(pgrp->pg_session, MA_NOTOWNED);
>
> PGRP_LOCK(pgrp);
>
414c501,507
< if (--pgrp->pg_session->s_count == 0)
---
> savesess = pgrp->pg_session;
> SESS_LOCK(savesess);
> savesess->s_count--;
> SESS_UNLOCK(savesess);
> PGRP_UNLOCK(pgrp);
> if (savesess->s_count == 0) {
> mtx_destroy(&savesess->s_mtx);
415a509,510
> }
> mtx_destroy(&pgrp->pg_mtx);
436c531
< register struct session *mysession = pgrp->pg_session;
---
> register struct session *mysession;
437a533,537
> PGRPSESS_LOCK_ASSERT(SX_LOCKED);
> PROC_LOCK_ASSERT(p, MA_NOTOWNED);
> PGRP_LOCK_ASSERT(pgrp, MA_NOTOWNED);
> SESS_LOCK_ASSERT(pgrp->pg_session, MA_NOTOWNED);
>
441a542
> mysession = pgrp->pg_session;
444a546
> PGRP_LOCK(pgrp);
447,448c549,554
< else if (--pgrp->pg_jobc == 0)
< orphanpg(pgrp);
---
> else {
> --pgrp->pg_jobc;
> if (pgrp->pg_jobc == 0)
> orphanpg(pgrp);
> }
> PGRP_UNLOCK(pgrp);
456c562
< LIST_FOREACH(p, &p->p_children, p_sibling)
---
> LIST_FOREACH(p, &p->p_children, p_sibling) {
459a566
> PGRP_LOCK(hispgrp);
462,463c569,574
< else if (--hispgrp->pg_jobc == 0)
< orphanpg(hispgrp);
---
> else {
> --hispgrp->pg_jobc;
> if (hispgrp->pg_jobc == 0)
> orphanpg(hispgrp);
> }
> PGRP_UNLOCK(hispgrp);
464a576
> }
478a591,592
> PGRP_LOCK_ASSERT(pg, MA_OWNED);
>
621a736
> tp = NULL;
628a744
> SESS_LOCK(sp);
634a751,752
> tp = sp->s_ttyp;
> SESS_UNLOCK(sp);
637c755
< if ((p->p_flag & P_CONTROLT) && sp && ((tp = sp->s_ttyp) != NULL)) {
---
> if ((p->p_flag & P_CONTROLT) && tp != NULL) {
770a889
> PROC_LOCK(p);
772c891,892
< p->p_pgrp->pg_id != (pid_t)name[0])
---
> p->p_pgrp->pg_id != (pid_t)name[0]) {
> PROC_UNLOCK(p);
773a894,895
> }
> PROC_UNLOCK(p);
776a899
> PROC_LOCK(p);
778,779c901,906
< p->p_session == NULL ||
< p->p_session->s_ttyp == NULL ||
---
> p->p_session == NULL) {
> PROC_UNLOCK(p);
> continue;
> }
> SESS_LOCK(p->p_session);
> if (p->p_session->s_ttyp == NULL ||
781c908,910
< (udev_t)name[0])
---
> (udev_t)name[0]) {
> SESS_UNLOCK(p->p_session);
> PROC_UNLOCK(p);
782a912,914
> }
> SESS_UNLOCK(p->p_session);
> PROC_UNLOCK(p);