~kris/9p

9hist

26d34b178484d99243173b6ec800cc0ac3d3be69 — David du Colombier 26 years ago 1888d47
Plan 9 from Bell Labs 1999-09-30
7 files changed, 106 insertions(+), 65 deletions(-)

M mpc/clock.c
M mpc/devpcmcia.c
M mpc/etherwavelan.c
M mpc/fns.h
M mpc/main.c
M port/devbridge.c
M port/devsdp.c
M mpc/clock.c => mpc/clock.c +7 -1
@@ 68,7 68,7 @@ enum {
static	ulong	clkreload;

void
clockinit(void)
delayloopinit(void)
{
	long x, est;



@@ 86,6 86,12 @@ clockinit(void)
	m->delayloop = (m->delayloop*est/Timebase)/(x);
	if(m->delayloop == 0)
		m->delayloop = 1;
}

void
clockinit(void)
{
	delayloopinit();

	clkreload = (m->clockgen/Timebase)/HZ-1;
	putdec(clkreload);

M mpc/devpcmcia.c => mpc/devpcmcia.c +1 -0
@@ 601,6 601,7 @@ pcmio(int slotno, ISAConf *isa)
	// setup io space - this could be better
	io->pcmr[1].base = ISAMEM+isa->port;
	x = (0x6<<27) | (2<<16) | (4<<12) | (8<<7) | Rio | Rvalid;
//	x = (0x6<<27) | (8<<16) | (6<<12) | (24<<7) | Rio | Rvalid;
	/* 16-bit data path */
	if(ct->bit16)
		x |= Rport16;

M mpc/etherwavelan.c => mpc/etherwavelan.c +32 -18
@@ 252,6 252,31 @@ mmc_in(int base, uchar o)
	return((uchar) (inb(MMD(base))));	
}

/*
 * a standard insb causes the wavelan card to not be able
 * to simultanisouly receive a packet out of the ether.
 * It appears that the card runs out of bandwidth to it's
 * internal memory
 */
void
slowinsb(int port, void *buf, int len)
{
	int i, j, n;
	uchar *p, *q;

	p = (uchar*)(port + ISAMEM);
	q = buf;
	n = m->delayloop/2000;
	if(n == 0)
		n = 1;
	for(i = 0; i < len; i++){
		*q++ = *p;
		// a small delay of about .5micro seconds
		for(j=0; j<n; j++)
			;
	}
}

static int 
read_ringbuf(Ether *ether, int addr, uchar *buf, int len)
{	Ctlr *ctlr;


@@ 261,7 286,6 @@ read_ringbuf(Ether *ether, int addr, uchar *buf, int len)
	uchar *buf_ptr = buf;
	ctlr = ether->ctlr;
	base = ctlr->port;
print("read_ringbuf\n");

	/* If buf is NULL, just increment the ring buffer pointer */
	if (buf == 0)


@@ 270,16 294,13 @@ print("read_ringbuf\n");
		/* Position the Program I/O Register at the ring buffer pointer */
		outb(PIORL(base), ring_ptr & 0xff);
		outb(PIORH(base), ((ring_ptr >> 8) & PIORH_MASK));
		delay(1);
		/* First, determine how much we can read without wrapping around the
 		ring buffer */
		if ((ring_ptr + len) < (RX_BASE + RX_SIZE))
			chunk_len = len;
		else
			chunk_len = RX_BASE + RX_SIZE - ring_ptr;
		if(chunk_len > 256)
			chunk_len = 256;
		insb(PIOP(base), buf_ptr, chunk_len);
		slowinsb(PIOP(base), buf_ptr, chunk_len);
		buf_ptr += chunk_len;
		len -= chunk_len;
		ring_ptr = (ring_ptr - RX_BASE + chunk_len) % RX_SIZE + RX_BASE;


@@ 296,8 317,6 @@ wavelan_hardware_send_packet(Ether *ether, void *buf, short length)
	ctlr = ether->ctlr;
	base = ctlr->port;

print("%ld: send packet %d\n", m->ticks, length);

	outb(PIORL(base), xmtdata_base & 0xff);
	outb(PIORH(base), ((xmtdata_base >> 8) & PIORH_MASK) | PIORH_SEL_TX);
	outb(PIOP(base), length & 0xff);		/* lsb */


@@ 408,8 427,6 @@ static void wavelan_read(Ether *ether, int fd_p, int sksize)
		ctlr->rx_dropped++;
		return;
	} else {
//print("%d+%d = %d\n", fd_p, sksize, fd_p+sksize);
//delay(100);
		fd_p = read_ringbuf(ether, fd_p, ctlr->rbp->rp, sksize);
		ctlr->rbp->wp = ctlr->rbp->rp + sksize;
		/* read signal level, silence level and signal quality bytes */


@@ 476,8 493,7 @@ if(0) print("before wavelan_cs: i593_rfp %d stop %d newrfp %d ctlr->rfp %d\n", i
		status = c[0] | (c[1] << 8);
		len = c[2] | (c[3] << 8);

print("%ld: len = %d status = %ux %ux %ux\n", m->ticks, len, status, newrfp, rp);
//delay(100);
if(0) print("%ld: len = %d status = %ux %ux %ux\n", m->ticks, len, status, newrfp, rp);

		if(!(status & RX_RCV_OK)) {
			if(status & RX_NO_SFD) ctlr->rx_no_sfd++;


@@ 496,19 512,19 @@ print("%ld: len = %d status = %ux %ux %ux\n", m->ticks, len, status, newrfp, rp)
	* per packet.
	*/
	ctlr->stop = (i593_rfp + RX_SIZE - ((RX_SIZE / 64) * 3)) % RX_SIZE;
//print("ctlr->stop = %ux\n", ctlr->stop);
	outb(LCCR(base), OP0_SWIT_TO_PORT_1 | CR0_CHNL);
	outb(LCCR(base), CR1_STOP_REG_UPDATE | (ctlr->stop >> RX_SIZE_SHIFT));
	outb(LCCR(base), OP1_SWIT_TO_PORT_0);

//delay(100);

if(0){ 
	newrfp = inb(RPLL(base));
	newrfp |= inb(RPLH(base)) << 8;
	newrfp %= RX_SIZE;

if(newrfp != ctlr->rfp)
print("after wavelan_cs: left over = %d\n", (newrfp - ctlr->rfp + RX_SIZE) % RX_SIZE);
	if(newrfp != ctlr->rfp)
		print("after wavelan_cs: left over = %d\n", (newrfp - ctlr->rfp + RX_SIZE) % RX_SIZE);
}

	return 1;
} /* wavelan_receive */



@@ 529,8 545,6 @@ interrupt(Ureg*, void* arg)

	outb(LCCR(base), CR0_STATUS_0 | OP0_NOP);
	interrupt_handler(ether, inb(LCSR(base)));
outb(LCCR(base), CR0_STATUS_0 | OP0_NOP);
print("status = %ux\n", inb(LCSR(base)));
	iunlock(&ctlr->wlock);

}; /* wavelan interrupt */

M mpc/fns.h => mpc/fns.h +1 -0
@@ 19,6 19,7 @@ void	delay(int);
ulong	draminit(ulong*);
void	dtlbmiss(void);
void	dumpregs(Ureg*);
void	delayloopinit(void);
void	eieio(void);
//#define	eieio()
void	evenaddr(ulong);

M mpc/main.c => mpc/main.c +4 -2
@@ 43,6 43,10 @@ main(void)
// turn on pcmcia
*(uchar*)(NVRAMMEM+0x100001) |= 0x60;

print("m->delayloop = %ld\n", m->delayloop);
	delayloopinit();
print("m->delayloop = %ld\n", m->delayloop);

	pageinit();
	procinit0();
	initseg();


@@ 95,8 99,6 @@ init0(void)

	up->nerrlab = 0;

print("spllo = %ux\n", spllo());

	/*
	 * These are o.k. because rootinit is null.
	 * Then early kproc's will have a root and dot.

M port/devbridge.c => port/devbridge.c +1 -2
@@ 981,8 981,7 @@ if(0)print("devbridge: etherread: reading\n");
if(0)print("devbridge: etherread: blocklen = %d\n", blocklen(bp));
		poperror();
		qlock(b);

		if(port->closed)
		if(bp == nil || port->closed)
			break;
		if(waserror()) {
print("etherread bridge error\n");

M port/devsdp.c => port/devsdp.c +60 -42
@@ 489,7 489,6 @@ print("readcontrol asked %ld got %ld\n", n, BLEN(b));
		freeb(b);
		return n;
	case Qdata:
print("readdata\n");
		b = readdata(sdp->conv[CONV(ch->qid)], n);
		if(b == nil)
			return 0;


@@ 916,7 915,6 @@ convstats(Conv *c, int local, char *buf, int n)
	Stats *stats;
	char *p, *ep;

	qlock(c);
	if(local) {
		stats = &c->lstats;
	} else {


@@ 926,6 924,8 @@ convstats(Conv *c, int local, char *buf, int n)
		}
		stats = &c->rstats;
	}

	qlock(c);
	p = buf;
	ep = buf + n;
	p += snprint(p, ep-p, "outPackets: %ld\n", stats->outPackets);


@@ 934,6 934,7 @@ convstats(Conv *c, int local, char *buf, int n)
	p += snprint(p, ep-p, "outCompDataBytes: %ld\n", stats->outCompDataBytes);
	p += snprint(p, ep-p, "inPackets: %ld\n", stats->inPackets);
	p += snprint(p, ep-p, "inDataPackets: %ld\n", stats->inDataPackets);
	p += snprint(p, ep-p, "inDataBytes: %ld\n", stats->inDataBytes);
	p += snprint(p, ep-p, "inCompDataBytes: %ld\n", stats->inCompDataBytes);
	p += snprint(p, ep-p, "inMissing: %ld\n", stats->inMissing);
	p += snprint(p, ep-p, "inDup: %ld\n", stats->inDup);


@@ 953,7 954,7 @@ convack(Conv *c)
	Stats *s;

	b = allocb(sizeof(AckPkt));
	ack = (Ack)b->wp;
	ack = (AckPkt*)b->wp;
	b->wp += sizeof(AckPkt);
	s = &c->lstats;
	hnputl(ack->cseq, c->in.controlseq);


@@ 982,7 983,7 @@ conviput(Conv *c, Block *b, int control)
	ulong seq, cseq;
	AckPkt *ack;

	c->lstat.inPackets++;
	c->lstats.inPackets++;

	if(BLEN(b) < 4) {
		freeb(b);


@@ 999,7 1000,7 @@ conviput(Conv *c, Block *b, int control)
	b->rp += 4;

	USED(seq);
print("coniput seq=%ulx\n", seq);
if(0) print("coniput seq=%ulx\n", seq);
	// auth
	// decrypt



@@ 1029,7 1030,7 @@ print("duplicate control packet: %ulx\n", cseq);
			convack(c);
		} else {
			c->in.controlpkt = b;
print("recv %ld size=%ld\n", cseq, BLEN(b));
if(0) print("recv %ld size=%ld\n", cseq, BLEN(b));
			wakeup(&c->in.controlready);
		}
		return nil;


@@ 1038,22 1039,23 @@ print("recv %ld size=%ld\n", cseq, BLEN(b));
			break;
		ack = (AckPkt*)(b->rp);
		cseq = nhgetl(ack->cseq);
		if(cseq != c->out.controlseq) {
print("ControlAck expected %ulx got %ulx\n", c->out.controlseq, cseq);
		if(cseq != c->out.controlseq)
			break;
		c->rstat.outPackets = nhgetl(ack->outPackets);
		c->rstat.outDataPackets = nhgetl(ack->outDataPackets);
		c->rstat.outDataBytes = nhgetl(ack->outDataBytes);
		c->rstat.outCompDataBytes = nhgetl(ack->outCompDataBytes);
		c->rstat.inPackets = nhgetl(ack->inPackets);
		c->rstat.inDataPackets = nhgetl(ack->inDataPackets);
		c->rstat.inDataBytes = nhgetl(ack->inDataBytes);
		c->rstat.inCompDataBytes = nhgetl(ack->inCompDataBytes);
		c->rstat.inMissing = nhgetl(ack->inMissing);
		c->rstat.inDup = nhgetl(ack->inDup);
		c->rstat.inReorder = nhgetl(ack->inReorder);
		c->rstat.inBadAuth = nhgetl(ack->inBadAuth);
		c->rstat.inBadSeq = nhgetl(ack->inBadSeq);
		}
		c->rstats.outPackets = nhgetl(ack->outPackets);
		c->rstats.outDataPackets = nhgetl(ack->outDataPackets);
		c->rstats.outDataBytes = nhgetl(ack->outDataBytes);
		c->rstats.outCompDataBytes = nhgetl(ack->outCompDataBytes);
		c->rstats.inPackets = nhgetl(ack->inPackets);
		c->rstats.inDataPackets = nhgetl(ack->inDataPackets);
		c->rstats.inDataBytes = nhgetl(ack->inDataBytes);
		c->rstats.inCompDataBytes = nhgetl(ack->inCompDataBytes);
		c->rstats.inMissing = nhgetl(ack->inMissing);
		c->rstats.inDup = nhgetl(ack->inDup);
		c->rstats.inReorder = nhgetl(ack->inReorder);
		c->rstats.inBadAuth = nhgetl(ack->inBadAuth);
		c->rstats.inBadSeq = nhgetl(ack->inBadSeq);
		freeb(b);
		freeb(c->out.controlpkt);
		c->out.controlpkt = nil;


@@ 1182,6 1184,23 @@ print("invalid conviput2 - sending reset\n");
	convoput2(c, ConReset, dialid, acceptid);
}

// c is locked
static void
convwriteblock(Conv *c, Block *b)
{
	// simulated errors
	if(c->drop && c->drop > nrand(c->drop))
		return;

	if(waserror()) {
		convsetstate(c, CClosed);
		nexterror();
	}
	devtab[c->chan->type]->bwrite(c->chan, b, 0);
	poperror();
}


// assume hold conv lock
static void
convoput(Conv *c, int type, Block *b)


@@ 1202,35 1221,31 @@ convoput(Conv *c, int type, Block *b)
	
	// encrypt
	// auth

	// simulated errors
	if(c->drop && c->drop > nrand(c->drop))
		return;
print("convoput\n");
	devtab[c->chan->type]->bwrite(c->chan, b, 0);
	
	convwriteblock(c, b);
}

// assume hold conv lock
static void
convoput2(Conv *c, int op, ulong dialid, ulong acceptid)
{
	ConnectPkt con;
	Block *b;
	ConnectPkt *con;

	c->lstats.outPackets++;
	if(c->chan == nil) {
print("chan = nil\n");
		error("no channel attached");
	}
	memset(&con, 0, sizeof(con));
	con.type = TConnect;
	con.op = op;
	hnputl(con.dialid, dialid);
	hnputl(con.acceptid, acceptid);

	// simulated errors
	if(c->drop && c->drop > nrand(c->drop))
		return;
	devtab[c->chan->type]->write(c->chan, &con, sizeof(con), 0);
	b = allocb(sizeof(ConnectPkt));
	con = (ConnectPkt*)b->wp;
	b->wp += sizeof(ConnectPkt);
	con->type = TConnect;
	con->op = op;
	hnputl(con->dialid, dialid);
	hnputl(con->acceptid, acceptid);

	convwriteblock(c, b);
}

static Block *


@@ 1375,8 1390,10 @@ writecontrol(Conv *c, void *p, int n, int wait)
	convretryinit(c);
print("send %ld size=%ld\n", c->out.controlseq, BLEN(b));	
	convoput(c, TControl, copyblock(b, blocklen(b)));
	if(wait)
	if(wait) {
print("writecontrol wait!\n");
		writewait(c);
	}
	poperror();
	qunlock(c);
	qunlock(&c->out.controllk);


@@ 1389,6 1406,8 @@ readdata(Conv *c, int n)

	for(;;) {
		b = convreadblock(c, n);
		if(b == nil)
			return nil;
		qlock(c);
		if(waserror()) {
			qunlock(c);


@@ 1408,7 1427,6 @@ writedata(Conv *c, Block *b)
	int n;

	qlock(c);
print("writedata %ulx state=%s\n", b, convstatename[c->state]);
	if(waserror()) {
		qunlock(c);
		nexterror();


@@ 1420,9 1438,9 @@ print("writedata %ulx state=%s\n", b, convstatename[c->state]);
	}

	n = BLEN(b);
	c->outDataPackets++;
	c->outDataBytes += n;
	c->outCompDataBytes += n;
	c->lstats.outDataPackets++;
	c->lstats.outDataBytes += n;
	c->lstats.outCompDataBytes += n;
	convoput(c, TData, b);
	poperror();
	qunlock(c);