~kris/9p

9hist

46130bfdcb395318ba2bf306366b248624ba8483 — David du Colombier 33 years ago cce53a3
Plan 9 from Bell Labs 1992-12-06
7 files changed, 89 insertions(+), 67 deletions(-)

M port/devip.c
M port/devproc.c
M port/ipdat.h
M port/portfns.h
M port/proc.c
M port/segment.c
M port/sysproc.c
M port/devip.c => port/devip.c +1 -1
@@ 1063,7 1063,7 @@ nextport(Ipifc *ifc, int priv)

	if(priv){
		base = PRIVPORTALLOC;
		max = PORTALLOC;
		max = UNPRIVPORTALLOC;
		p = &lastport[1];
	} else {
		base = PORTALLOC;

M port/devproc.c => port/devproc.c +9 -4
@@ 571,11 571,16 @@ procctlreq(Proc *p, char *va, int n)
	if(strncmp(buf, "stop", 4) == 0)
		procstopwait(p, Proc_stopme);
	else if(strncmp(buf, "kill", 4) == 0) {
		if(p->state == Broken)
		switch(p->state) {
		case Broken:
			unbreak(p);
			break;
		case Stopped:
			postnote(p, 0, "sys: killed", NExit);
			p->procctl = Proc_exitme;
			ready(p);
		else {
			if(p->state == Stopped)
				ready(p);
			break;
		default:
			postnote(p, 0, "sys: killed", NExit);
			p->procctl = Proc_exitme;
		}

M port/ipdat.h => port/ipdat.h +1 -0
@@ 422,6 422,7 @@ enum {
	/* Protocol port numbers */
	PORTALLOC	= 5000,			/* First automatic allocated port */
	PRIVPORTALLOC	= 600,			/* First priveleged port allocated */
	UNPRIVPORTALLOC	= 1024,			/* First unpriveleged port allocated */
	PORTMAX		= 30000,		/* Last port to allocte */
};


M port/portfns.h => port/portfns.h +1 -0
@@ 254,6 254,7 @@ void		naildownstream(Stream*);
void		swapinit(void);
long		syscall(Ureg*);
void		tsleep(Rendez*, int (*)(void*), void*, int);
void		unbreak(Proc*);
void		uncachepage(Page*);
long		unicode(uchar*);
long		unionread(Chan*, void*, long);

M port/proc.c => port/proc.c +55 -43
@@ 440,23 440,24 @@ postnote(Proc *p, int dolock, char *n, int flag)
		splx(s);
	}

	if(p->state != Rendezvous)
		return ret;

	/* Try and pull out of a rendezvous */
	lock(p->pgrp);
	if(p->state == Rendezvous) {
		lock(p->pgrp);
		if(p->state == Rendezvous) {
			p->rendval = ~0;
			l = &REND(p->pgrp, p->rendtag);
			for(d = *l; d; d = d->rendhash) {
				if(d == p) {
					*l = p->rendhash;
					break;
				}
				l = &d->rendhash;
		p->rendval = ~0;
		l = &REND(p->pgrp, p->rendtag);
		for(d = *l; d; d = d->rendhash) {
			if(d == p) {
				*l = p->rendhash;
				break;
			}
			ready(p);
			l = &d->rendhash;
		}
		unlock(p->pgrp);
		ready(p);
	}

	unlock(p->pgrp);
	return ret;
}



@@ 464,36 465,45 @@ postnote(Proc *p, int dolock, char *n, int flag)
 * weird thing: keep at most NBROKEN around
 */
#define	NBROKEN 4
struct{
	Lock;
struct
{
	QLock;
	int	n;
	Proc	*p[NBROKEN];
}broken;

void
addbroken(Proc *c)
addbroken(Proc *p)
{
	int b;

	lock(&broken);
	if(broken.n == NBROKEN){
	qlock(&broken);
	if(broken.n == NBROKEN) {
		ready(broken.p[0]);
		memmove(&broken.p[0], &broken.p[1], sizeof(Proc*)*(NBROKEN-1));
		--broken.n;
	}
	broken.p[broken.n++] = c;
	unlock(&broken);
	c->state = Broken;
	c->psstate = 0;
	sched();		/* until someone lets us go */
	lock(&broken);
	for(b=0; b<NBROKEN; b++)
		if(broken.p[b] == c){
			broken.n--;
			memmove(&broken.p[b], &broken.p[b+1], sizeof(Proc*)*(NBROKEN-(b+1)));
			break;
		}
	unlock(&broken);
	broken.p[broken.n++] = p;
	qunlock(&broken);

	p->state = Broken;
	p->psstate = 0;
	sched();
}

void
unbreak(Proc *p)
{
	int b;

	qlock(&broken);
	for(b=0; b < NBROKEN; b++) {
		if(broken.p[b] != p)
			continue;

		broken.n--;
		memmove(&broken.p[b], &broken.p[b+1], sizeof(Proc*)*(NBROKEN-(b+1)));
		ready(p);
	}
	qunlock(&broken);
}

int


@@ 501,12 511,14 @@ freebroken(void)
{
	int i, n;

	lock(&broken);
	qlock(&broken);
	n = broken.n;
	for(i=0; i<n; i++)
	for(i=0; i<n; i++) {
		ready(broken.p[i]);
		broken.p[i] = 0;
	}
	broken.n = 0;
	unlock(&broken);
	qunlock(&broken);
	return n;
}



@@ 516,7 528,7 @@ pexit(char *exitstr, int freemem)
	int n;
	long utime, stime;
	Proc *p, *c;
	Segment **s, **es, *os;
	Segment **s, **es;
	Waitq *wq, *f, *next;

	c = u->p;


@@ 534,7 546,8 @@ pexit(char *exitstr, int freemem)
	 * do some housekeeping.
	 */
	if(c->kp == 0) {
		if((p = c->parent) == 0) {
		p = c->parent;
		if(p == 0) {
			if(exitstr == 0)
				exitstr = "unknown";
			panic("boot process died: %s", exitstr);


@@ 557,7 570,8 @@ pexit(char *exitstr, int freemem)
		if(exitstr && exitstr[0]){
			n = sprint(wq->w.msg, "%s %d:", c->text, c->pid);
			strncpy(wq->w.msg+n, exitstr, ERRLEN-n);
		}else
		}
		else
			wq->w.msg[0] = '\0';

		lock(&p->exl);


@@ 587,10 601,8 @@ pexit(char *exitstr, int freemem)

	es = &c->seg[NSEG];
	for(s = c->seg; s < es; s++)
		if(os = *s) {
			*s = 0;
			putseg(os);
		}
		if(*s)
			putseg(*s);

	lock(&c->exl);		/* Prevent my children from leaving waits */
	c->pid = 0;

M port/segment.c => port/segment.c +16 -16
@@ 335,6 335,7 @@ ibrk(ulong addr, int seg)
	if(newtop < s->top) {
		mfreeseg(s, newtop, (s->top-newtop)/BY2PG);
		qunlock(&s->lk);
		flushmmu();
		return 0;
	}



@@ 371,24 372,24 @@ mfreeseg(Segment *s, ulong start, int pages)

	for(i = soff/PTEMAPMEM; i < SEGMAPSIZE; i++) {
		if(pages <= 0) 
			goto done;
		if(s->map[i]) {
			while(j < PTEPERTAB) {
				if(pg = s->map[i]->pages[j]) {
					putpage(pg);
					s->map[i]->pages[j] = 0;	
				}
				if(--pages == 0)
					goto done;
				j++;
			break;
		if(s->map[i] == 0) {
			pages -= PTEPERTAB-j;
			j = 0;
			continue;
		}
		while(j < PTEPERTAB) {
			pg = s->map[i]->pages[j];
			if(pg) {
				putpage(pg);
				s->map[i]->pages[j] = 0;	
			}
			if(--pages == 0)
				return;
			j++;
		}
		else
			pages -= PTEPERTAB-j;
		j = 0;
	}
done:
	flushmmu();
}

ulong


@@ 407,8 408,7 @@ segattach(Proc *p, ulong attr, char *name, ulong va, ulong len)
	vmemchr(name, 0, ~0);

	for(sno = 0; sno < NSEG; sno++)
		if(u->p->seg[sno] == 0)
		if(sno != ESEG)
		if(u->p->seg[sno] == 0 && sno != ESEG)
			break;

	if(sno == NSEG)

M port/sysproc.c => port/sysproc.c +6 -3
@@ 32,7 32,7 @@ sysrfork(ulong *arg)
	 */
	int lastvar;	

		flag = arg[0];
	flag = arg[0];
	p = u->p;
	if((flag&RFPROC) == 0) {
		if(flag & (RFNAMEG|RFCNAMEG)) {


@@ 345,7 345,9 @@ sysexec(ulong *arg)
	memmove(p->text, elem, NAMELEN);

	/*
	 * Committed.  Free old memory. Special segments are maintained accross exec
	 * Committed.
	 * Free old memory.
	 * Special segments are maintained accross exec
	 */
	for(i = SSEG; i <= BSEG; i++) {
		putseg(p->seg[i]);


@@ 616,6 618,7 @@ syssegfree(ulong *arg)

	mfreeseg(s, from, pages);
	qunlock(&s->lk);
	flushmmu();

	return 0;
}


@@ 643,7 646,7 @@ sysrendezvous(ulong *arg)
			*l = p->rendhash;
			val = p->rendval;
			p->rendval = arg[1];

			/* Easy race avoidance */
			while(p->state != Rendezvous)
				;
			ready(p);