~kris/9p

9hist

e30c70c118c598ae21f7b95fe1605d2ec3a0525c — David du Colombier 34 years ago bf48946
Plan 9 from Bell Labs 1992-05-16
9 files changed, 104 insertions(+), 67 deletions(-)

M gnot/main.c
M pc/devhard.c
M pc/main.c
M port/alarm.c
M port/portdat.h
M port/portfns.h
M power/devduart.c
M power/main.c
M ss/main.c
M gnot/main.c => gnot/main.c +4 -2
@@ 135,11 135,13 @@ init0(void)
	u->p->state = Running;
	u->p->mach = m;
	spllo();

	chandevinit();
	
	u->slash = (*devtab[0].attach)(0);
	u->dot = clone(u->slash, 0);

	kproc("alarm", alarmkproc, 0);
	chandevinit();

	if(!waserror()){
		ksetterm("at&t %s");
		ksetenv("cputype", "68020");

M pc/devhard.c => pc/devhard.c +7 -14
@@ 27,9 27,7 @@ enum
	Pstatus=	7,	/* status port (read) */
	 Sbusy=		 (1<<7),
	 Sready=	 (1<<6),
	 Sdwf=		 (1<<5),
	 Sdrq=		 (1<<3),
	 Scorr=		 (1<<2),
	 Serr=		 (1<<0),
	Pcmd=		7,	/* cmd port (write) */



@@ 523,16 521,16 @@ retry:
		len = pp->end - lblk;
	cp->nsecs = len;

	cp->cmd = cmd;
	cp->dp = dp;
	cmdreadywait(cp);

	/*
	 *  start the transfer
	 */
	cp->cmd = cmd;
	cp->dp = dp;
	cp->status = 0;
	cmdreadywait(cp);

	outb(cp->pbase+Pcount, cp->nsecs);
	outb(cp->pbase+Pcount, cp->nsecs-cp->sofar);
	outb(cp->pbase+Psector, sec);
	outb(cp->pbase+Pdh, 0x20 | head);
	outb(cp->pbase+Pcyllsb, cyl);


@@ 545,7 543,6 @@ retry:
			if(++loop > 10000)
				panic("hardxfer");
		outss(cp->pbase+Pdata, cp->buf, dp->bytes/2);
		cp->nsecs--;
	}

	sleep(&cp->r, cmddone, cp);


@@ 776,8 773,6 @@ hardintr(Ureg *ur)
				cp->cmd, inb(cp->pbase+Pstatus));
			panic("hardintr: wait busy");
		}
	if(cp->status & (Sdwf|Scorr))
		print("hardintr: cmd=#%lux, status=#%lux\n", cp->cmd, cp->status);
	switch(cp->cmd){
	case Cwrite:
		if(cp->status & Serr){


@@ 788,7 783,7 @@ hardintr(Ureg *ur)
			return;
		}
		cp->sofar++;
		if(cp->nsecs){
		if(cp->sofar < cp->nsecs){
			loop = 0;
			while((inb(cp->pbase+Pstatus) & Sdrq) == 0)
				if(++loop > 10000) {


@@ 798,8 793,7 @@ hardintr(Ureg *ur)
				}
			outss(cp->pbase+Pdata, &cp->buf[cp->sofar*dp->bytes],
				dp->bytes/2);
			cp->nsecs--;
		} else {
		} else{
			cp->lastcmd = cp->cmd;
			cp->cmd = 0;
			wakeup(&cp->r);


@@ 831,8 825,7 @@ hardintr(Ureg *ur)
		inss(cp->pbase+Pdata, &cp->buf[cp->sofar*dp->bytes],
			dp->bytes/2);
		cp->sofar++;
		cp->nsecs--;
		if(cp->nsecs == 0){
		if(cp->sofar >= cp->nsecs){
			cp->lastcmd = cp->cmd;
			if (cp->cmd == Cread)
				cp->cmd = 0;

M pc/main.c => pc/main.c +1 -0
@@ 86,6 86,7 @@ init0(void)
	u->slash = (*devtab[0].attach)(0);
	u->dot = clone(u->slash, 0);

	kproc("alarm", alarmkproc, 0);
	chandevinit();

	if(!waserror()){

M port/alarm.c => port/alarm.c +84 -46
@@ 5,34 5,34 @@
#include	"fns.h"
#include	"io.h"

Alarm	*alarmtab;
struct {
	QLock;
	Alarm	*tab;	/* table of all alarm structures */
	void	*list;	/* busy alarms */
	Rendez	r;
} alarmalloc;

Alarms	alarms;

Alarm*
alarm(int ms, void (*f)(Alarm*), void *arg)
{
	Alarm *a, *w, *pw;
	ulong s;

	if(ms < 0)
		ms = 0;
	a = newalarm();
	a->dt = MS2TK(ms);
	a->when = MACHP(0)->ticks+MS2TK(ms);
	a->f = f;
	a->arg = arg;
	s = splhi();
	lock(&m->alarmlock);
	qlock(&alarmalloc);
	pw = 0;
	for(w=m->alarm; w; pw=w, w=w->next){
		if(w->dt <= a->dt){
			a->dt -= w->dt;
			continue;
		}
		w->dt -= a->dt;
		break;
	for(w=alarmalloc.list; w; pw=w, w=w->next){
		if(w->when > a->when)
			break;
	}
	insert(&m->alarm, pw, a);
	unlock(&m->alarmlock);
	splx(s);
	insert(&alarmalloc.list, pw, a);
	qunlock(&alarmalloc);
	return a;
}



@@ 48,7 48,7 @@ newalarm(void)
	int i;
	Alarm *a;

	for(i=0,a=alarmtab; i<conf.nalarm; i++,a++)
	for(i=0,a=alarmalloc.tab; i<conf.nalarm; i++,a++)
		if(a->busy==0 && a->f==0 && canlock(a)){
			if(a->busy){
				unlock(a);


@@ 61,6 61,7 @@ newalarm(void)
			return a;
		}
	panic("newalarm");
	return 0;	/* not reached */
}

/* allocate locks here since you can't allocate them at interrupt time (on the SGI) */


@@ 69,18 70,20 @@ alarminit(void)
{
	int i;

	alarmtab = ialloc(conf.nalarm*sizeof(Alarm), 0);
	alarmalloc.tab = ialloc(conf.nalarm*sizeof(Alarm), 0);
	for(i=0; i<conf.nalarm; i++){
		lock(&alarmtab[i]);
		unlock(&alarmtab[i]);
		lock(&alarmalloc.tab[i]);
		unlock(&alarmalloc.tab[i]);
	}
	lock(&alarms);
	unlock(&alarms);
	qlock(&alarmalloc);
	qunlock(&alarmalloc);
	qlock(&alarms);
	qunlock(&alarms);
}

#define NA 10		/* alarms per clock tick */
#define NA 10		/* alarms per wakeup */
void
checkalarms(void)
alarmkproc(void *arg)
{
	int i, n;
	Alarm *a;


@@ 89,35 92,48 @@ checkalarms(void)
	ulong now;
	Proc *rp;

	if(canlock(&m->alarmlock)){
		a = m->alarm;
	USED(arg);

	for(;;){
		now = MACHP(0)->ticks;

		qlock(&alarmalloc);
		a = alarmalloc.list;
		if(a){
			for(n=0; a && a->dt<=0 && n<NA; n++){
			for(n=0; a && a->when<=now && n<NA; n++){
				alist[n] = a;
				delete(&m->alarm, 0, a);
				a = m->alarm;
				delete(&alarmalloc.list, 0, a);
				a = alarmalloc.list;
			}
			if(a)
				a->dt--;
			unlock(&m->alarmlock);

			/*  execute alarm functions outside the lock */
			for(i = 0; i < n; i++){
				f = alist[i]->f;	/* avoid race with cancel */
				if(f)
					(*f)(alist[i]);
				alist[i]->busy = 0;
			qunlock(&alarmalloc);

			/*
			 *  execute alarm functions outside the lock since they
			 *  might call alarm().
			 */
			f = 0;
			if(waserror()){
				print("alarm func %lux caused error %s\n", f, u->error);
			} else {
				for(i = 0; i < n; i++){
					f = alist[i]->f; /* avoid race with cancel */
					if(f)
						(*f)(alist[i]);
					alist[i]->busy = 0;
				}
				poperror();
			}
		}else
			unlock(&m->alarmlock);
	}
			qunlock(&alarmalloc);

	if(m == MACHP(0) && canlock(&alarms)){
		now = MACHP(0)->ticks;
		qlock(&alarms);
		while((rp = alarms.head) && rp->alarm <= now){
			if(rp->alarm != 0L){
				if(canqlock(&rp->debug)){
					postnote(rp, 0, "alarm", NUser);
					if(!waserror()){
						postnote(rp, 0, "alarm", NUser);
						poperror();
					}
					qunlock(&rp->debug);
					rp->alarm = 0L;
				}else


@@ 125,10 141,32 @@ checkalarms(void)
			}
			alarms.head = rp->palarm;
		}
		unlock(&alarms);
		qunlock(&alarms);

		sleep(&alarmalloc.r, return0, 0);
	}
}

/*
 *  called every clock tick
 */
void
checkalarms(void)
{
	ulong now;
	Proc *p;
	Alarm *a;

	if(m != MACHP(0))
		return;
	a = alarmalloc.list;
	p = alarms.head;
	now = MACHP(0)->ticks;

	if((a && a->when <= now) || (p && p->alarm <= now))
		wakeup(&alarmalloc.r);
}

ulong
procalarm(ulong time)
{


@@ 143,7 181,7 @@ procalarm(ulong time)
	when = MS2TK(time);
	when += MACHP(0)->ticks;

	lock(&alarms);
	qlock(&alarms);
	l = &alarms.head;
	for(f = *l; f; f = f->palarm){
		if(u->p == f){


@@ 170,7 208,7 @@ procalarm(ulong time)
		alarms.head = u->p;
done:
	u->p->alarm = when;
	unlock(&alarms);
	qunlock(&alarms);

	return old;			
}

M port/portdat.h => port/portdat.h +2 -2
@@ 76,14 76,14 @@ struct Alarm
	List;
	Lock;
	int	busy;
	long	dt;			/* may underflow in clock(); must be signed */
	ulong	when;			/* may underflow in clock(); must be signed */
	void	(*f)(void*);
	void	*arg;
};

struct Alarms
{
	Lock;
	QLock;
	Proc	*head;
};


M port/portfns.h => port/portfns.h +1 -0
@@ 1,5 1,6 @@
Alarm*	alarm(int, void (*)(Alarm*), void*);
void	alarminit(void);
void	alarmkproc(void*);
Block*	allocb(ulong);
int	anyready(void);
void	append(List**, List*);

M power/devduart.c => power/devduart.c +1 -1
@@ 232,7 232,7 @@ duartbaud(Duartport *dp, int b)
		x = BD300;
		break;
	default:
		error(Ebadarg);
		return;
	}
	if(x & 0x0100)
		dp->duart->ipc_acr = duartacr |= 0x80;

M power/main.c => power/main.c +1 -0
@@ 218,6 218,7 @@ init0(void)
	 */
	u->slash = (*devtab[0].attach)(0);
	u->dot = clone(u->slash, 0);
	kproc("alarm", alarmkproc, 0);
	chandevinit();

	if(!waserror()){

M ss/main.c => ss/main.c +3 -2
@@ 103,12 103,13 @@ init0(void)
	u->p->state = Running;
	u->p->mach = m;
	spllo();

	chandevinit();
	
	u->slash = (*devtab[0].attach)(0);
	u->dot = clone(u->slash, 0);

	kproc("alarm", alarmkproc, 0);
	chandevinit();

	if(!waserror()){
		ksetterm("sun %s");
		ksetenv("cputype", "sparc");