diff --git a/src/conf/node_device_conf.c b/src/conf/node_device_conf.c index 85cfd83961a5af59798915e1800aed0961b64464..7aab2e03c4d89aaf813ea3d9102eceffedd9061b 100644 --- a/src/conf/node_device_conf.c +++ b/src/conf/node_device_conf.c @@ -1286,76 +1286,102 @@ virPCIEDeviceInfoParseXML(xmlXPathContextPtr ctxt, static int -virNodeDevPCICapabilityParseXML(xmlXPathContextPtr ctxt, - xmlNodePtr node, - virNodeDevCapPCIDevPtr pci_dev) +virNodeDevPCICapSRIOVPhysicalParseXML(xmlXPathContextPtr ctxt, + virNodeDevCapPCIDevPtr pci_dev) { - char *maxFuncsStr = virXMLPropString(node, "maxCount"); - char *type = virXMLPropString(node, "type"); - xmlNodePtr *addresses = NULL; - xmlNodePtr orignode = ctxt->node; - int ret = -1; - size_t i = 0; + xmlNodePtr address = virXPathNode("./address[1]", ctxt); - ctxt->node = node; + if (VIR_ALLOC(pci_dev->physical_function) < 0) + return -1; - if (!type) { - virReportError(VIR_ERR_XML_ERROR, "%s", _("Missing capability type")); - goto out; + if (!address) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("Missing address in 'phys_function' capability")); + return -1; } - if (STREQ(type, "phys_function")) { - xmlNodePtr address = virXPathNode("./address[1]", ctxt); + if (virPCIDeviceAddressParseXML(address, + pci_dev->physical_function) < 0) + return -1; - if (VIR_ALLOC(pci_dev->physical_function) < 0) - goto out; + pci_dev->flags |= VIR_NODE_DEV_CAP_FLAG_PCI_PHYSICAL_FUNCTION; - if (!address) { - virReportError(VIR_ERR_XML_ERROR, "%s", - _("Missing address in 'phys_function' capability")); - goto out; - } + return 0; +} - if (virPCIDeviceAddressParseXML(address, - pci_dev->physical_function) < 0) - goto out; - pci_dev->flags |= VIR_NODE_DEV_CAP_FLAG_PCI_PHYSICAL_FUNCTION; - } else if (STREQ(type, "virt_functions")) { - int naddresses; +static int +virNodeDevPCICapSRIOVVirtualParseXML(xmlXPathContextPtr ctxt, + virNodeDevCapPCIDevPtr pci_dev) +{ + int ret = -1; + xmlNodePtr *addresses = NULL; + int naddresses = virXPathNodeSet("./address", ctxt, &addresses); + char *maxFuncsStr = virXPathString("string(./@maxCount)", ctxt); + size_t i; - if ((naddresses = virXPathNodeSet("./address", ctxt, &addresses)) < 0) - goto out; + if (naddresses < 0) + goto cleanup; - if (maxFuncsStr && - virStrToLong_uip(maxFuncsStr, NULL, 10, - &pci_dev->max_virtual_functions) < 0) { - virReportError(VIR_ERR_XML_ERROR, "%s", - _("Malformed 'maxCount' parameter")); - goto out; + if (maxFuncsStr && + virStrToLong_uip(maxFuncsStr, NULL, 10, + &pci_dev->max_virtual_functions) < 0) { + virReportError(VIR_ERR_XML_ERROR, "%s", + _("Malformed 'maxCount' parameter")); + goto cleanup; + } + + if (VIR_ALLOC_N(pci_dev->virtual_functions, naddresses) < 0) + goto cleanup; + + for (i = 0; i < naddresses; i++) { + virPCIDeviceAddressPtr addr = NULL; + + if (VIR_ALLOC(addr) < 0) + goto cleanup; + + if (virPCIDeviceAddressParseXML(addresses[i], addr) < 0) { + VIR_FREE(addr); + goto cleanup; } - if (VIR_ALLOC_N(pci_dev->virtual_functions, naddresses) < 0) - goto out; + if (VIR_APPEND_ELEMENT(pci_dev->virtual_functions, + pci_dev->num_virtual_functions, + addr) < 0) + goto cleanup; + } - for (i = 0; i < naddresses; i++) { - virPCIDeviceAddressPtr addr = NULL; + pci_dev->flags |= VIR_NODE_DEV_CAP_FLAG_PCI_VIRTUAL_FUNCTION; + ret = 0; + cleanup: + VIR_FREE(addresses); + VIR_FREE(maxFuncsStr); + return ret; +} - if (VIR_ALLOC(addr) < 0) - goto out; - if (virPCIDeviceAddressParseXML(addresses[i], addr) < 0) { - VIR_FREE(addr); - goto out; - } +static int +virNodeDevPCICapabilityParseXML(xmlXPathContextPtr ctxt, + xmlNodePtr node, + virNodeDevCapPCIDevPtr pci_dev) +{ + char *type = virXMLPropString(node, "type"); + xmlNodePtr orignode = ctxt->node; + int ret = -1; - if (VIR_APPEND_ELEMENT(pci_dev->virtual_functions, - pci_dev->num_virtual_functions, - addr) < 0) - goto out; - } + ctxt->node = node; + + if (!type) { + virReportError(VIR_ERR_XML_ERROR, "%s", _("Missing capability type")); + goto cleanup; + } - pci_dev->flags |= VIR_NODE_DEV_CAP_FLAG_PCI_VIRTUAL_FUNCTION; + if (STREQ(type, "phys_function") && + virNodeDevPCICapSRIOVPhysicalParseXML(ctxt, pci_dev) < 0) { + goto cleanup; + } else if (STREQ(type, "virt_functions") && + virNodeDevPCICapSRIOVVirtualParseXML(ctxt, pci_dev) < 0) { + goto cleanup; } else { int hdrType = virPCIHeaderTypeFromString(type); @@ -1364,9 +1390,7 @@ virNodeDevPCICapabilityParseXML(xmlXPathContextPtr ctxt, } ret = 0; - out: - VIR_FREE(addresses); - VIR_FREE(maxFuncsStr); + cleanup: VIR_FREE(type); ctxt->node = orignode; return ret;