}
vd->typ = typ;
vd->pci = p;
+ pcienable(p);
/* reset */
outb(vd->port+Status, 0);
static int
vioblkreq(Vdev *vd, int typ, void *a, long count, long secsize, uvlong lba)
{
- int free, head;
+ int need, free, head;
Vqueue *q;
Vdesc *d;
u64int lba;
} req;
- status = 0;
+ need = 2;
+ if(a != nil)
+ need = 3;
+
+ status = -1;
req.typ = typ;
req.prio = 0;
req.lba = lba;
q = vd->queue[0];
ilock(q);
- while(q->nfree < 3){
+ while(q->nfree < need){
iunlock(q);
if(!waserror())
d->len = sizeof(req);
d->flags = Next;
- d = &q->desc[free]; free = d->next;
- d->addr = PADDR(a);
- d->len = secsize*count;
- d->flags = typ ? Next : (Write|Next);
+ if(a != nil){
+ d = &q->desc[free]; free = d->next;
+ d->addr = PADDR(a);
+ d->len = secsize*count;
+ d->flags = typ ? Next : (Write|Next);
+ }
d = &q->desc[free]; free = d->next;
d->addr = PADDR(&status);
d->flags = Write;
q->free = free;
- q->nfree -= 3;
+ q->nfree -= need;
/* queue io, unlock and wait for completion */
vqio(q, head);
SDifc sdvirtioifc;
-static void
-vdevenable(Vdev *vd)
+static int
+vioenable(SDev *sd)
{
- intrenable(vd->pci->intl, viointerrupt, vd, vd->pci->tbdf, "virtio");
+ char name[32];
+ Vdev *vd;
+
+ vd = sd->ctlr;
+ pcisetbme(vd->pci);
+ snprint(name, sizeof(name), "%s (%s)", sd->name, sd->ifc->name);
+ intrenable(vd->pci->intl, viointerrupt, vd, vd->pci->tbdf, name);
outb(vd->port+Status, inb(vd->port+Status) | DriverOk);
+ return 1;
+}
+
+static int
+viodisable(SDev *sd)
+{
+ char name[32];
+ Vdev *vd;
+
+ vd = sd->ctlr;
+ snprint(name, sizeof(name), "%s (%s)", sd->name, sd->ifc->name);
+ intrdisable(vd->pci->intl, viointerrupt, vd, vd->pci->tbdf, name);
+ pciclrbme(vd->pci);
+ return 1;
}
static SDev*
if(vd->nqueue != 1)
continue;
- vdevenable(vd);
-
if((s = malloc(sizeof(*s))) == nil)
break;
s->ctlr = vd;
continue;
}
vd->cfg = cfg;
-
- vdevenable(vd);
if((s = malloc(sizeof(*s))) == nil)
break;
viopnp, /* pnp */
nil, /* legacy */
- nil, /* enable */
- nil, /* disable */
+ vioenable, /* enable */
+ viodisable, /* disable */
vioverify, /* verify */
vioonline, /* online */