diff options
Diffstat (limited to 'sys/kern/kern_proc.c')
| -rw-r--r-- | sys/kern/kern_proc.c | 167 | 
1 files changed, 66 insertions, 101 deletions
diff --git a/sys/kern/kern_proc.c b/sys/kern/kern_proc.c index 4fbb0c489798..79b25b8ecd8a 100644 --- a/sys/kern/kern_proc.c +++ b/sys/kern/kern_proc.c @@ -30,8 +30,8 @@   * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF   * SUCH DAMAGE.   * - *	@(#)kern_proc.c	8.4 (Berkeley) 1/4/94 - * $Id: kern_proc.c,v 1.14 1995/12/14 08:31:30 phk Exp $ + *	@(#)kern_proc.c	8.7 (Berkeley) 2/14/95 + * $Id: kern_proc.c,v 1.15 1996/01/01 17:01:03 peter Exp $   */  #include <sys/param.h> @@ -62,32 +62,43 @@ struct prochd qs[NQS];		/* as good a place as any... */  struct prochd rtqs[NQS];	/* Space for REALTIME queues too */  struct prochd idqs[NQS];	/* Space for IDLE queues too */ -volatile struct proc *allproc;	/* all processes */ -struct proc *zombproc;		/* just zombies */ -  static void pgdelete	__P((struct pgrp *));  /*   * Structure associated with user cacheing.   */ -static struct uidinfo { -	struct	uidinfo *ui_next; -	struct	uidinfo **ui_prev; +struct uidinfo { +	LIST_ENTRY(uidinfo) ui_hash;  	uid_t	ui_uid;  	long	ui_proccnt; -} **uihashtbl; -static u_long	uihash;		/* size of hash table - 1 */ -#define	UIHASH(uid)	((uid) & uihash) +}; +#define	UIHASH(uid)	(&uihashtbl[(uid) & uihash]) +LIST_HEAD(uihashhead, uidinfo) *uihashtbl; +static u_long uihash;		/* size of hash table - 1 */  static void	orphanpg __P((struct pgrp *pg));  /* - * Allocate a hash table. + * Other process lists + */ +struct pidhashhead *pidhashtbl; +u_long pidhash; +struct pgrphashhead *pgrphashtbl; +u_long pgrphash; +struct proclist allproc; +struct proclist zombproc; + +/* + * Initialize global process hashing structures.   */  void -usrinfoinit() +procinit()  { +	LIST_INIT(&allproc); +	LIST_INIT(&zombproc); +	pidhashtbl = hashinit(maxproc / 4, M_PROC, &pidhash); +	pgrphashtbl = hashinit(maxproc / 4, M_PROC, &pgrphash);  	uihashtbl = hashinit(maxproc / 16, M_PROC, &uihash);  } @@ -100,10 +111,11 @@ chgproccnt(uid, diff)  	uid_t	uid;  	int	diff;  { -	register struct uidinfo **uipp, *uip, *uiq; +	register struct uidinfo *uip; +	register struct uihashhead *uipp; -	uipp = &uihashtbl[UIHASH(uid)]; -	for (uip = *uipp; uip; uip = uip->ui_next) +	uipp = UIHASH(uid); +	for (uip = uipp->lh_first; uip != 0; uip = uip->ui_hash.le_next)  		if (uip->ui_uid == uid)  			break;  	if (uip) { @@ -112,9 +124,7 @@ chgproccnt(uid, diff)  			return (uip->ui_proccnt);  		if (uip->ui_proccnt < 0)  			panic("chgproccnt: procs < 0"); -		if ((uiq = uip->ui_next)) -			uiq->ui_prev = uip->ui_prev; -		*uip->ui_prev = uiq; +		LIST_REMOVE(uip, ui_hash);  		FREE(uip, M_PROC);  		return (0);  	} @@ -124,11 +134,7 @@ chgproccnt(uid, diff)  		panic("chgproccnt: lost user");  	}  	MALLOC(uip, struct uidinfo *, sizeof(*uip), M_PROC, M_WAITOK); -	if ((uiq = *uipp)) -		uiq->ui_prev = &uip->ui_next; -	uip->ui_next = uiq; -	uip->ui_prev = uipp; -	*uipp = uip; +	LIST_INSERT_HEAD(uipp, uip, ui_hash);  	uip->ui_uid = uid;  	uip->ui_proccnt = diff;  	return (diff); @@ -157,7 +163,7 @@ pfind(pid)  {  	register struct proc *p; -	for (p = pidhash[PIDHASH(pid)]; p != NULL; p = p->p_hash) +	for (p = PIDHASH(pid)->lh_first; p != 0; p = p->p_hash.le_next)  		if (p->p_pid == pid)  			return (p);  	return (NULL); @@ -172,8 +178,8 @@ pgfind(pgid)  {  	register struct pgrp *pgrp; -	for (pgrp = pgrphash[PIDHASH(pgid)]; -	    pgrp != NULL; pgrp = pgrp->pg_hforw) +	for (pgrp = PGRPHASH(pgid)->lh_first; pgrp != 0; +	     pgrp = pgrp->pg_hash.le_next)  		if (pgrp->pg_id == pgid)  			return (pgrp);  	return (NULL); @@ -189,8 +195,6 @@ enterpgrp(p, pgid, mksess)  	int mksess;  {  	register struct pgrp *pgrp = pgfind(pgid); -	register struct proc **pp; -	int n;  #ifdef DIAGNOSTIC  	if (pgrp != NULL && mksess)	/* firewalls */ @@ -209,7 +213,7 @@ enterpgrp(p, pgid, mksess)  			panic("enterpgrp: new pgrp and pid != pgid");  #endif  		MALLOC(pgrp, struct pgrp *, sizeof(struct pgrp), M_PGRP, -		       M_WAITOK); +		    M_WAITOK);  		if ((np = pfind(savepid)) == NULL || np != p)  			return (ESRCH);  		if (mksess) { @@ -219,7 +223,7 @@ enterpgrp(p, pgid, mksess)  			 * new session  			 */  			MALLOC(sess, struct session *, sizeof(struct session), -				M_SESSION, M_WAITOK); +			    M_SESSION, M_WAITOK);  			sess->s_leader = p;  			sess->s_count = 1;  			sess->s_ttyvp = NULL; @@ -237,10 +241,9 @@ enterpgrp(p, pgid, mksess)  			pgrp->pg_session->s_count++;  		}  		pgrp->pg_id = pgid; -		pgrp->pg_hforw = pgrphash[n = PIDHASH(pgid)]; -		pgrphash[n] = pgrp; +		LIST_INIT(&pgrp->pg_members); +		LIST_INSERT_HEAD(PGRPHASH(pgid), pgrp, pg_hash);  		pgrp->pg_jobc = 0; -		pgrp->pg_mem = NULL;  	} else if (pgrp == p->p_pgrp)  		return (0); @@ -252,30 +255,11 @@ enterpgrp(p, pgid, mksess)  	fixjobc(p, pgrp, 1);  	fixjobc(p, p->p_pgrp, 0); -	/* -	 * unlink p from old process group -	 */ -	for (pp = &p->p_pgrp->pg_mem; *pp; pp = &(*pp)->p_pgrpnxt) { -		if (*pp == p) { -			*pp = p->p_pgrpnxt; -			break; -		} -	} -#ifdef DIAGNOSTIC -	if (pp == NULL) -		panic("enterpgrp: can't find p on old pgrp"); -#endif -	/* -	 * delete old if empty -	 */ -	if (p->p_pgrp->pg_mem == 0) +	LIST_REMOVE(p, p_pglist); +	if (p->p_pgrp->pg_members.lh_first == 0)  		pgdelete(p->p_pgrp); -	/* -	 * link into new one -	 */  	p->p_pgrp = pgrp; -	p->p_pgrpnxt = pgrp->pg_mem; -	pgrp->pg_mem = p; +	LIST_INSERT_HEAD(&pgrp->pg_members, p, p_pglist);  	return (0);  } @@ -286,19 +270,9 @@ int  leavepgrp(p)  	register struct proc *p;  { -	register struct proc **pp = &p->p_pgrp->pg_mem; -	for (; *pp; pp = &(*pp)->p_pgrpnxt) { -		if (*pp == p) { -			*pp = p->p_pgrpnxt; -			break; -		} -	} -#ifdef DIAGNOSTIC -	if (pp == NULL) -		panic("leavepgrp: can't find p in pgrp"); -#endif -	if (!p->p_pgrp->pg_mem) +	LIST_REMOVE(p, p_pglist); +	if (p->p_pgrp->pg_members.lh_first == 0)  		pgdelete(p->p_pgrp);  	p->p_pgrp = 0;  	return (0); @@ -311,21 +285,11 @@ static void  pgdelete(pgrp)  	register struct pgrp *pgrp;  { -	register struct pgrp **pgp = &pgrphash[PIDHASH(pgrp->pg_id)];  	if (pgrp->pg_session->s_ttyp != NULL &&  	    pgrp->pg_session->s_ttyp->t_pgrp == pgrp)  		pgrp->pg_session->s_ttyp->t_pgrp = NULL; -	for (; *pgp; pgp = &(*pgp)->pg_hforw) { -		if (*pgp == pgrp) { -			*pgp = pgrp->pg_hforw; -			break; -		} -	} -#ifdef DIAGNOSTIC -	if (pgp == NULL) -		panic("pgdelete: can't find pgrp on hash chain"); -#endif +	LIST_REMOVE(pgrp, pg_hash);  	if (--pgrp->pg_session->s_count == 0)  		FREE(pgrp->pg_session, M_SESSION);  	FREE(pgrp, M_PGRP); @@ -366,7 +330,7 @@ fixjobc(p, pgrp, entering)  	 * their process groups; if so, adjust counts for children's  	 * process groups.  	 */ -	for (p = p->p_cptr; p; p = p->p_osptr) +	for (p = p->p_children.lh_first; p != 0; p = p->p_sibling.le_next)  		if ((hispgrp = p->p_pgrp) != pgrp &&  		    hispgrp->pg_session == mysession &&  		    p->p_stat != SZOMB) @@ -387,9 +351,10 @@ orphanpg(pg)  {  	register struct proc *p; -	for (p = pg->pg_mem; p; p = p->p_pgrpnxt) { +	for (p = pg->pg_members.lh_first; p != 0; p = p->p_pglist.le_next) {  		if (p->p_stat == SSTOP) { -			for (p = pg->pg_mem; p; p = p->p_pgrpnxt) { +			for (p = pg->pg_members.lh_first; p != 0; +			    p = p->p_pglist.le_next) {  				psignal(p, SIGHUP);  				psignal(p, SIGCONT);  			} @@ -398,31 +363,31 @@ orphanpg(pg)  	}  } -#ifdef debug -/* DEBUG */ +#ifdef DEBUG  pgrpdump()  {  	register struct pgrp *pgrp;  	register struct proc *p;  	register i; -	for (i=0; i<PIDHSZ; i++) { -		if (pgrphash[i]) { -		  printf("\tindx %d\n", i); -		  for (pgrp=pgrphash[i]; pgrp; pgrp=pgrp->pg_hforw) { -		    printf("\tpgrp %x, pgid %d, sess %x, sesscnt %d, mem %x\n", -			pgrp, pgrp->pg_id, pgrp->pg_session, -			pgrp->pg_session->s_count, pgrp->pg_mem); -		    for (p=pgrp->pg_mem; p; p=p->p_pgrpnxt) { -			printf("\t\tpid %d addr %x pgrp %x\n", -				p->p_pid, p, p->p_pgrp); -		    } -		  } - +	for (i = 0; i <= pgrphash; i++) { +		if (pgrp = pgrphashtbl[i].lh_first) { +			printf("\tindx %d\n", i); +			for (; pgrp != 0; pgrp = pgrp->pg_hash.le_next) { +				printf("\tpgrp %x, pgid %d, sess %x, sesscnt %d, mem %x\n", +				    pgrp, pgrp->pg_id, pgrp->pg_session, +				    pgrp->pg_session->s_count, +				    pgrp->pg_members.lh_first); +				for (p = pgrp->pg_members.lh_first; p != 0; +				    p = p->p_pglist.le_next) { +					printf("\t\tpid %d addr %x pgrp %x\n",  +					    p->p_pid, p, p->p_pgrp); +				} +			}  		}  	}  } -#endif /* debug */ +#endif /* DEBUG */  /*   * Fill in an eproc structure for the specified process. @@ -504,10 +469,10 @@ sysctl_kern_proc SYSCTL_HANDLER_ARGS  		if (error)  			return (error);  	} -	p = (struct proc *)allproc; +	p = allproc.lh_first;  	doingzomb = 0;  again: -	for (; p != NULL; p = p->p_next) { +	for (; p != 0; p = p->p_list.le_next) {  		/*  		 * Skip embryonic processes.  		 */ @@ -559,7 +524,7 @@ again:  			return (error);  	}  	if (doingzomb == 0) { -		p = zombproc; +		p = zombproc.lh_first;  		doingzomb++;  		goto again;  	}  | 
