On 22.05.2013 16:36, Jim Fehlig wrote: > Marek Marczykowski wrote: >> For now only for PCI devices. Mostly copy-paste from old xen driver. >> > > This one is (or will be) covered by Chanyan's work as well right? Right. > > Regards, > Jim > >> --- >> src/libxl/libxl_driver.c | 193 +++++++++++++++++++++++++++++++++++++++++++++++ >> 1 file changed, 193 insertions(+) >> >> diff --git a/src/libxl/libxl_driver.c b/src/libxl/libxl_driver.c >> index 40a7a6b..011edf8 100644 >> --- a/src/libxl/libxl_driver.c >> +++ b/src/libxl/libxl_driver.c >> @@ -42,6 +42,7 @@ >> #include "libxl.h" >> #include "libxl_driver.h" >> #include "libxl_conf.h" >> +#include "node_device_conf.h" >> #include "xen_xm.h" >> #include "virtypedparam.h" >> #include "viruri.h" >> @@ -3666,6 +3667,195 @@ libxlDomainUpdateDeviceFlags(virDomainPtr dom, const char *xml, >> return libxlDomainModifyDeviceFlags(dom, xml, flags, LIBXL_DEVICE_UPDATE); >> } >> >> +static int >> +libxlNodeDeviceGetPciInfo(virNodeDevicePtr dev, >> + unsigned *domain, >> + unsigned *bus, >> + unsigned *slot, >> + unsigned *function) >> +{ >> + virNodeDeviceDefPtr def = NULL; >> + virNodeDevCapsDefPtr cap; >> + char *xml = NULL; >> + int ret = -1; >> + >> + xml = virNodeDeviceGetXMLDesc(dev, 0); >> + if (!xml) >> + goto out; >> + >> + def = virNodeDeviceDefParseString(xml, EXISTING_DEVICE, NULL); >> + if (!def) >> + goto out; >> + >> + cap = def->caps; >> + while (cap) { >> + if (cap->type == VIR_NODE_DEV_CAP_PCI_DEV) { >> + *domain = cap->data.pci_dev.domain; >> + *bus = cap->data.pci_dev.bus; >> + *slot = cap->data.pci_dev.slot; >> + *function = cap->data.pci_dev.function; >> + break; >> + } >> + >> + cap = cap->next; >> + } >> + >> + if (!cap) { >> + virReportError(VIR_ERR_INVALID_ARG, >> + _("device %s is not a PCI device"), dev->name); >> + goto out; >> + } >> + >> + ret = 0; >> +out: >> + virNodeDeviceDefFree(def); >> + VIR_FREE(xml); >> + return ret; >> +} >> + >> +static int >> +libxlNodeDeviceDettach(virNodeDevicePtr dev) >> +{ >> + virPCIDevicePtr pci; >> + unsigned domain, bus, slot, function; >> + int ret = -1; >> + >> + if (libxlNodeDeviceGetPciInfo(dev, &domain, &bus, &slot, &function) < 0) >> + return -1; >> + >> + pci = virPCIDeviceNew(domain, bus, slot, function); >> + if (!pci) >> + return -1; >> + >> + if (virPCIDeviceDetach(pci, NULL, NULL, "pciback") < 0) >> + goto out; >> + >> + ret = 0; >> +out: >> + virPCIDeviceFree(pci); >> + return ret; >> +} >> + >> +static int >> +libxlNodeDeviceAssignedDomainId(virNodeDevicePtr dev) >> +{ >> + int numdomains; >> + int numpcidevs; >> + int ret = -1, i, j; >> + int *ids = NULL; >> + char *bdf = NULL; >> + char *xref = NULL; >> + unsigned int domain, bus, slot, function; >> + libxl_device_pci *pcidevs = NULL; >> + virConnectPtr conn = dev->conn; >> + libxlDriverPrivatePtr driver = conn->privateData; >> + >> + /* Get active domains */ >> + numdomains = libxlNumDomains(conn); >> + if (numdomains < 0) { >> + return ret; >> + } >> + if (numdomains > 0){ >> + if (VIR_ALLOC_N(ids, numdomains) < 0) { >> + virReportOOMError(); >> + goto out; >> + } >> + if ((numdomains = libxlListDomains(conn, &ids[0], numdomains)) < 0) { >> + goto out; >> + } >> + } >> + >> + /* Get pci bdf */ >> + if (libxlNodeDeviceGetPciInfo(dev, &domain, &bus, &slot, &function) < 0) >> + goto out; >> + >> + if (virAsprintf(&bdf, "%04x:%02x:%02x.%0x", >> + domain, bus, slot, function) < 0) { >> + virReportOOMError(); >> + goto out; >> + } >> + >> + libxlDriverLock(driver); >> + /* Check if bdf is assigned to one of active domains */ >> + for (i = 0; i < numdomains; i++) { >> + pcidevs = libxl_device_pci_list(driver->ctx, ids[i], &numpcidevs); >> + if (pcidevs == NULL) { >> + continue; >> + } else { >> + for (j = 0; j < numpcidevs; j++) { >> + if (pcidevs[j].bus == bus && pcidevs[j].dev == slot && pcidevs[j].func == function) { >> + ret = ids[i]; >> + break; >> + } >> + } >> + VIR_FREE(pcidevs); >> + } >> + } >> + libxlDriverUnlock(driver); >> + >> + VIR_FREE(xref); >> + VIR_FREE(bdf); >> +out: >> + VIR_FREE(ids); >> + >> + return ret; >> +} >> + >> +static int >> +libxlNodeDeviceReAttach(virNodeDevicePtr dev) >> +{ >> + virPCIDevicePtr pci; >> + unsigned domain, bus, slot, function; >> + int ret = -1; >> + int domid; >> + >> + if (libxlNodeDeviceGetPciInfo(dev, &domain, &bus, &slot, &function) < 0) >> + return -1; >> + >> + pci = virPCIDeviceNew(domain, bus, slot, function); >> + if (!pci) >> + return -1; >> + >> + /* Check if device is assigned to an active guest */ >> + if ((domid = libxlNodeDeviceAssignedDomainId(dev)) >= 0) { >> + virReportError(VIR_ERR_INTERNAL_ERROR, >> + _("Device %s has been assigned to guest %d"), >> + dev->name, domid); >> + goto out; >> + } >> + >> + if (virPCIDeviceReattach(pci, NULL, NULL, "pciback") < 0) >> + goto out; >> + >> + ret = 0; >> +out: >> + virPCIDeviceFree(pci); >> + return ret; >> +} >> + >> +static int >> +libxlNodeDeviceReset(virNodeDevicePtr dev) >> +{ >> + virPCIDevicePtr pci; >> + unsigned domain, bus, slot, function; >> + int ret = -1; >> + >> + if (libxlNodeDeviceGetPciInfo(dev, &domain, &bus, &slot, &function) < 0) >> + return -1; >> + >> + pci = virPCIDeviceNew(domain, bus, slot, function); >> + if (!pci) >> + return -1; >> + >> + if (virPCIDeviceReset(pci, NULL, NULL) < 0) >> + goto out; >> + >> + ret = 0; >> +out: >> + virPCIDeviceFree(pci); >> + return ret; >> +} >> + >> static unsigned long long >> libxlNodeGetFreeMemory(virConnectPtr conn) >> { >> @@ -4233,6 +4423,9 @@ static virDriver libxlDriver = { >> .nodeGetFreeMemory = libxlNodeGetFreeMemory, /* 0.9.0 */ >> .domainEventRegister = libxlDomainEventRegister, /* 0.9.0 */ >> .domainEventDeregister = libxlDomainEventDeregister, /* 0.9.0 */ >> + .nodeDeviceDettach = libxlNodeDeviceDettach, /* 1.0.4 */ >> + .nodeDeviceReAttach = libxlNodeDeviceReAttach, /* 1.0.4 */ >> + .nodeDeviceReset = libxlNodeDeviceReset, /* 1.0.4 */ >> .domainManagedSave = libxlDomainManagedSave, /* 0.9.2 */ >> .domainHasManagedSaveImage = libxlDomainHasManagedSaveImage, /* 0.9.2 */ >> .domainManagedSaveRemove = libxlDomainManagedSaveRemove, /* 0.9.2 */ >> -- Best Regards, Marek Marczykowski Invisible Things Lab
Attachment:
signature.asc
Description: OpenPGP digital signature
-- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list