usbd: improved event file

This commit is contained in:
aiju 2011-07-28 21:26:42 +02:00
parent 4792c6bef9
commit 6f824732a6
2 changed files with 53 additions and 21 deletions

View file

@ -5,7 +5,7 @@
#include "dat.h" #include "dat.h"
#include "fns.h" #include "fns.h"
static Hub *hubs; Hub *hubs;
static int nhubs; static int nhubs;
static int mustdump; static int mustdump;
static int pollms = Pollms; static int pollms = Pollms;

View file

@ -26,10 +26,10 @@ struct Event {
char *data; char *data;
int len; int len;
Event *link; Event *link;
int ref; int ref, prev;
}; };
static Event *evfirst, *evlast; static Event *evlast;
static Req *reqfirst, *reqlast; static Req *reqfirst, *reqlast;
static QLock evlock; static QLock evlock;
@ -59,10 +59,7 @@ fulfill(Req *req, Event *e)
static void static void
initevent(void) initevent(void)
{ {
evfirst = mallocz(sizeof(*evfirst), 1); evlast = mallocz(sizeof(Event), 1);
if(evfirst == nil)
sysfatal("malloc: %r");
evlast = evfirst;
} }
static void static void
@ -80,8 +77,8 @@ readevent(Req *req)
fulfill(req, e); fulfill(req, e);
req->fid->aux = e->link; req->fid->aux = e->link;
e->link->ref++; e->link->ref++;
if(--e->ref == 0 && e == evfirst){ if(--e->ref == 0 && e->prev == 0){
evfirst = e->link; e->link->prev--;
free(e->data); free(e->data);
free(e); free(e);
} }
@ -104,6 +101,7 @@ pushevent(char *data)
e->data = data; e->data = data;
e->len = strlen(data); e->len = strlen(data);
e->link = ee; e->link = ee;
ee->prev++;
for(r = reqfirst; r != nil; r = rr){ for(r = reqfirst; r != nil; r = rr){
rr = r->aux; rr = r->aux;
r->aux = nil; r->aux = nil;
@ -113,8 +111,8 @@ pushevent(char *data)
fulfill(r, e); fulfill(r, e);
respond(r, nil); respond(r, nil);
} }
if(e->ref == 0 && e == evfirst){ if(e->ref == 0 && e->prev == 0){
evfirst = ee; ee->prev--;
free(e->data); free(e->data);
free(e); free(e);
} }
@ -199,13 +197,50 @@ usbdstat(Req *req)
respond(req, nil); respond(req, nil);
} }
static char *
formatdev(Dev *d)
{
Usbdev *u;
u = d->usb;
return smprint("in id %d vid 0x%.4x did 0x%.4x csp 0x%.8lx\n",
d->id, u->vid, u->did, u->csp);
}
static void
enumerate(Event **l)
{
Event *e;
Hub *h;
Port *p;
extern Hub *hubs;
for(h = hubs; h != nil; h = h->next){
for(p = h->port; p < h->port + h->nport; p++){
if(p->dev == nil || p->dev->usb == nil || p->hub != nil)
continue;
e = mallocz(sizeof(Event), 1);
if(e == nil)
sysfatal("malloc: %r");
e->data = formatdev(p->dev);
e->len = strlen(e->data);
e->prev = 1;
*l = e;
l = &e->link;
}
}
*l = evlast;
evlast->prev++;
}
static void static void
usbdopen(Req *req) usbdopen(Req *req)
{ {
if(req->fid->qid.path == Qusbevent){ if(req->fid->qid.path == Qusbevent){
qlock(&evlock); qlock(&evlock);
req->fid->aux = evlast; enumerate(&req->fid->aux);
evlast->ref++; ((Event *)req->fid->aux)->ref++;
((Event *)req->fid->aux)->prev--;
qunlock(&evlock); qunlock(&evlock);
} }
respond(req, nil); respond(req, nil);
@ -219,14 +254,14 @@ usbddestroyfid(Fid *fid)
if(fid->qid.path == Qusbevent){ if(fid->qid.path == Qusbevent){
qlock(&evlock); qlock(&evlock);
e = fid->aux; e = fid->aux;
if(--e->ref == 0 && e == evfirst){ if(--e->ref == 0 && e->prev == 0){
while(e->ref == 0 && e != evlast){ while(e->ref == 0 && e->prev == 0 && e != evlast){
ee = e->link; ee = e->link;
ee->prev--;
free(e->data); free(e->data);
free(e); free(e);
e = ee; e = ee;
} }
evfirst = e;
} }
qunlock(&evlock); qunlock(&evlock);
} }
@ -264,15 +299,12 @@ int
startdev(Port *p) startdev(Port *p)
{ {
Dev *d; Dev *d;
Usbdev *u;
if((d = p->dev) == nil || (u = p->dev->usb) == nil){ if((d = p->dev) == nil || p->dev->usb == nil){
fprint(2, "okay what?\n"); fprint(2, "okay what?\n");
return -1; return -1;
} }
pushevent(smprint("in id %d vid 0x%.4x did 0x%.4x csp 0x%.8x\n", pushevent(formatdev(d));
d->id, u->vid, u->did, u->csp));
closedev(p->dev);
return 0; return 0;
} }