M carrera/devether.c => carrera/devether.c +34 -0
@@ 682,6 682,37 @@ isoutbuf(void *arg)
return ctlr->tda[ctlr->th].status == Host;
}
+static int
+etherloop(Etherpkt *p, long n)
+{
+ int s, different;
+ ushort t;
+ Netfile *f, **fp;
+
+ different = memcmp(p->d, p->s, sizeof(p->s));
+ if(different && memcmp(p->d, ether.bcast, sizeof(p->d)))
+ return 0;
+
+ s = splhi();
+ t = (p->type[0]<<8) | p->type[1];
+ for(fp = ether.f; fp < ðer.f[Ntypes]; fp++) {
+ f = *fp;
+ if(f == 0)
+ continue;
+ if(f->type == t || f->type < 0)
+ switch(qproduce(f->in, p->d, n)){
+ case -1:
+ print("etherloop overflow\n");
+ break;
+ case -2:
+ print("etherloop memory\n");
+ break;
+ }
+ }
+ splx(s);
+ return !different;
+}
+
long
etherwrite(Chan *c, void *buf, long n, ulong offset)
{
@@ 699,6 730,9 @@ etherwrite(Chan *c, void *buf, long n, ulong offset)
return netifwrite(ether[0], c, buf, n);
/* we handle data */
+ if(etherloop(buf, n))
+ return n;
+
qlock(&ctlr->tlock);
if(waserror()) {
qunlock(&ctlr->tlock);
M port/devlance.c => port/devlance.c +6 -0
@@ 474,6 474,11 @@ lancewrite(Chan *c, void *buf, long n, ulong offset)
return n;
qlock(&l.tlock);
+ if(waserror()) {
+ qunlock(&ctlr->tlock);
+ nexterror();
+ }
+
m = &(LANCEMEM->tmr[l.tc]);
tsleep(&l.tr, isoutbuf, m, 10000);
if(!isoutbuf(m) || l.wedged)
@@ 496,6 501,7 @@ lancewrite(Chan *c, void *buf, long n, ulong offset)
*l.rdp = INEA|TDMD;
}
qunlock(&l.tlock);
+ poperror();
return n;
}
M port/devproc.c => port/devproc.c +1 -1
@@ 151,7 151,7 @@ int
procwalk(Chan *c, char *name)
{
if(strcmp(name, "..") == 0) {
- c->qid.path = Qdir|CHDIR;
+ c->qid.path = CHDIR;
return 1;
}