From nobody Mon Feb 9 17:24:49 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of redhat.com designates 170.10.129.124 as permitted sender) client-ip=170.10.129.124; envelope-from=libvir-list-bounces@redhat.com; helo=us-smtp-delivery-124.mimecast.com; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of redhat.com designates 170.10.129.124 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1675351176; cv=none; d=zohomail.com; s=zohoarc; b=Fxt9cQDZUY0S++tXRUUBREFexi8V/ZddIdtUP6FHyef86iAyLGbzM18byMSz7KZGEKfIBzA/CwFqh3jlz2iO4vBgeqP1jnh44ieM61qDiEpjkdfMzPNmwM3u7PTuTUA/Qk4mpuq8OvCVnc2YkO8WHRwYcmYsI8T0+Ko00jCym+g= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1675351176; h=Content-Type:Content-Transfer-Encoding:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=SOIRCMaXIgvLNIogWXGIMAgdCS41IsrLmEcI4BW9SgA=; b=X+lgU4u/5n8MfIwhy5r81yM+TWIAnMcm02pKQfO7sIBpEkGS5zpeUSuHP3MgPFGcj9l7Qu2bmDrQ8nJ43WLloyEGpY/nKpo7Nltdyl3iob3lH+xKBgIAS4ZFcGPDdOnDopT+sSOMwNKV8PLVLSBStTzlBQXVCjRJ08BDCQzY9sM= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of redhat.com designates 170.10.129.124 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass header.from= (p=none dis=none) Return-Path: Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by mx.zohomail.com with SMTPS id 1675351176630866.8167760236989; Thu, 2 Feb 2023 07:19:36 -0800 (PST) Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-495-BVMJU81WMF-VeH_hJBa7_g-1; Thu, 02 Feb 2023 10:19:31 -0500 Received: from smtp.corp.redhat.com (int-mx01.intmail.prod.int.rdu2.redhat.com [10.11.54.1]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 55E898058A5; Thu, 2 Feb 2023 15:19:14 +0000 (UTC) Received: from mm-prod-listman-01.mail-001.prod.us-east-1.aws.redhat.com (mm-prod-listman-01.mail-001.prod.us-east-1.aws.redhat.com [10.30.29.100]) by smtp.corp.redhat.com (Postfix) with ESMTP id 40D81404BEC2; Thu, 2 Feb 2023 15:19:14 +0000 (UTC) Received: from mm-prod-listman-01.mail-001.prod.us-east-1.aws.redhat.com (localhost [IPv6:::1]) by mm-prod-listman-01.mail-001.prod.us-east-1.aws.redhat.com (Postfix) with ESMTP id 36317194737A; Thu, 2 Feb 2023 15:18:20 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) by mm-prod-listman-01.mail-001.prod.us-east-1.aws.redhat.com (Postfix) with ESMTP id A1DD21947364 for ; Thu, 2 Feb 2023 15:18:18 +0000 (UTC) Received: by smtp.corp.redhat.com (Postfix) id 92A0A2026D68; Thu, 2 Feb 2023 15:18:18 +0000 (UTC) Received: from speedmetal.lan (ovpn-208-29.brq.redhat.com [10.40.208.29]) by smtp.corp.redhat.com (Postfix) with ESMTP id EB7FA2026D4B for ; Thu, 2 Feb 2023 15:18:17 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1675351175; h=from:from:sender:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:mime-version:mime-version: content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references:list-id:list-help: list-unsubscribe:list-subscribe:list-post; bh=SOIRCMaXIgvLNIogWXGIMAgdCS41IsrLmEcI4BW9SgA=; b=EaTRw3P69YV3UA1e644dlvIdtcRY4M/AiO9n13DiMjeUwBA/MlX4QMFpGznstwlnV+uZ/H 4bl/XzkKn5F8WbB3NqIDMZgHx0g7jwa00hzDHaRGB+zsWssNgzdy73dQqcFU1p5Mpegzlx WaOEO/OxxQt1P0DwKRvsV06+4u9Yvls= X-MC-Unique: BVMJU81WMF-VeH_hJBa7_g-1 X-Original-To: libvir-list@listman.corp.redhat.com From: Peter Krempa To: libvir-list@redhat.com Subject: [PATCH 7/7] conf: Store 'origstates' of PCI hostdevs in a bitmap Date: Thu, 2 Feb 2023 16:18:10 +0100 Message-Id: In-Reply-To: References: MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.1 on 10.11.54.4 X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: libvir-list-bounces@redhat.com Sender: "libvir-list" X-Scanned-By: MIMEDefang 3.1 on 10.11.54.1 X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable X-ZohoMail-DKIM: pass (identity @redhat.com) X-ZM-MESSAGEID: 1675351178110100003 Content-Type: text/plain; charset="utf-8" Refactor the code to use a bitmap with an enum to avoid ugly XML parser. Signed-off-by: Peter Krempa --- src/conf/domain_conf.c | 97 ++++++++++++++++++------------------- src/conf/domain_conf.h | 31 ++++-------- src/conf/virconftypes.h | 2 - src/hypervisor/virhostdev.c | 25 ++++++---- 4 files changed, 72 insertions(+), 83 deletions(-) diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c index 6e33a4472f..b21efeacf9 100644 --- a/src/conf/domain_conf.c +++ b/src/conf/domain_conf.c @@ -1061,6 +1061,14 @@ VIR_ENUM_IMPL(virDomainHostdevSubsysSCSIProtocol, "iscsi", ); + +VIR_ENUM_IMPL(virDomainHostdevPCIOrigstate, + VIR_DOMAIN_HOSTDEV_PCI_ORIGSTATE_LAST, + "unbind", + "removeslot", + "reprobe", +); + VIR_ENUM_IMPL(virDomainHostdevSubsysUSBGuestReset, VIR_DOMAIN_HOSTDEV_USB_GUEST_RESET_LAST, "default", @@ -3365,8 +3373,10 @@ void virDomainHostdevDefClear(virDomainHostdevDef *d= ef) case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_SCSI_HOST: VIR_FREE(def->source.subsys.u.scsi_host.wwpn); break; - case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB: case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI: + virBitmapFree(def->source.subsys.u.pci.origstates); + break; + case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB: case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_MDEV: case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_LAST: break; @@ -5731,41 +5741,6 @@ virDomainHostdevSubsysUSBDefParseXML(xmlNodePtr node, return 0; } -/* The internal XML for host PCI device's original states: - * - * - * - * - * - * - */ -static int -virDomainHostdevSubsysPCIOrigStatesDefParseXML(xmlNodePtr node, - virDomainHostdevOrigStates = *def) -{ - xmlNodePtr cur; - cur =3D node->children; - - while (cur !=3D NULL) { - if (cur->type =3D=3D XML_ELEMENT_NODE) { - if (virXMLNodeNameEqual(cur, "unbind")) { - def->states.pci.unbind_from_stub =3D true; - } else if (virXMLNodeNameEqual(cur, "removeslot")) { - def->states.pci.remove_slot =3D true; - } else if (virXMLNodeNameEqual(cur, "reprobe")) { - def->states.pci.reprobe =3D true; - } else { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("unsupported element '%s' of 'origstates'= "), - cur->name); - return -1; - } - } - cur =3D cur->next; - } - - return 0; -} static int virDomainHostdevSubsysPCIDefParseXML(xmlNodePtr node, @@ -5774,7 +5749,6 @@ virDomainHostdevSubsysPCIDefParseXML(xmlNodePtr node, unsigned int flags) { xmlNodePtr address =3D NULL; - xmlNodePtr origstates =3D NULL; VIR_XPATH_NODE_AUTORESTORE(ctxt) ctxt->node =3D node; @@ -5788,10 +5762,35 @@ virDomainHostdevSubsysPCIDefParseXML(xmlNodePtr nod= e, virPCIDeviceAddressParseXML(address, &def->source.subsys.u.pci.add= r) < 0) return -1; - if ((flags & VIR_DOMAIN_DEF_PARSE_PCI_ORIG_STATES) && - (origstates =3D virXPathNode("./origstates", ctxt)) && - virDomainHostdevSubsysPCIOrigStatesDefParseXML(origstates, &def->o= rigstates) < 0) - return -1; + if ((flags & VIR_DOMAIN_DEF_PARSE_PCI_ORIG_STATES)) { + virDomainHostdevSubsysPCI *pcisrc =3D &def->source.subsys.u.pci; + g_autofree xmlNodePtr *nodes =3D NULL; + ssize_t nnodes; + size_t i; + + if ((nnodes =3D virXPathNodeSet("./origstates/*", ctxt, &nodes)) <= 0) + return -1; + + if (nnodes > 0) { + if (!pcisrc->origstates) + pcisrc->origstates =3D virBitmapNew(VIR_DOMAIN_HOSTDEV_PCI= _ORIGSTATE_LAST); + else + virBitmapClearAll(pcisrc->origstates); + + for (i =3D 0; i < nnodes; i++) { + int state; + + if ((state =3D virDomainHostdevPCIOrigstateTypeFromString(= (const char *) nodes[i]->name)) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, + _("unsupported element '%s' of 'origsta= tes'"), + (const char *) nodes[i]->name); + return -1; + } + + virBitmapSetBitExpand(pcisrc->origstates, state); + } + } + } return 0; } @@ -23154,7 +23153,6 @@ virDomainHostdevDefFormatSubsysPCI(virBuffer *buf, { g_auto(virBuffer) sourceAttrBuf =3D VIR_BUFFER_INITIALIZER; g_auto(virBuffer) sourceChildBuf =3D VIR_BUFFER_INIT_CHILD(buf); - g_auto(virBuffer) origstatesChildBuf =3D VIR_BUFFER_INIT_CHILD(&source= ChildBuf); virDomainHostdevSubsysPCI *pcisrc =3D &def->source.subsys.u.pci; if (def->writeFiltering !=3D VIR_TRISTATE_BOOL_ABSENT) @@ -23176,15 +23174,14 @@ virDomainHostdevDefFormatSubsysPCI(virBuffer *buf, virPCIDeviceAddressFormat(&sourceChildBuf, pcisrc->addr, includeTypeIn= Addr); - if ((flags & VIR_DOMAIN_DEF_FORMAT_PCI_ORIG_STATES)) { - if (def->origstates.states.pci.unbind_from_stub) - virBufferAddLit(&origstatesChildBuf, "\n"); - - if (def->origstates.states.pci.remove_slot) - virBufferAddLit(&origstatesChildBuf, "\n"); + if (pcisrc->origstates && + (flags & VIR_DOMAIN_DEF_FORMAT_PCI_ORIG_STATES)) { + g_auto(virBuffer) origstatesChildBuf =3D VIR_BUFFER_INIT_CHILD(&so= urceChildBuf); + ssize_t n =3D -1; - if (def->origstates.states.pci.reprobe) - virBufferAddLit(&origstatesChildBuf, "\n"); + while ((n =3D virBitmapNextSetBit(pcisrc->origstates, n)) >=3D 0) + virBufferAsprintf(&origstatesChildBuf, "<%s/>\n", + virDomainHostdevPCIOrigstateTypeToString(n)); virXMLFormatElement(&sourceChildBuf, "origstates", NULL, &origstat= esChildBuf); } diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h index 1a80399c9c..0bec072478 100644 --- a/src/conf/domain_conf.h +++ b/src/conf/domain_conf.h @@ -167,28 +167,14 @@ typedef enum { } virDomainHyperVMode; VIR_ENUM_DECL(virDomainHyperVMode); -struct _virDomainHostdevOrigStates { - union { - struct { - /* Does the device need to unbind from stub when - * reattaching to host? - */ - bool unbind_from_stub; - - /* Does it need to use remove_slot when reattaching - * the device to host? - */ - bool remove_slot; +typedef enum { + VIR_DOMAIN_HOSTDEV_PCI_ORIGSTATE_UNBIND =3D 0, /* device needs to unbi= nd from stub when reattaching */ + VIR_DOMAIN_HOSTDEV_PCI_ORIGSTATE_REMOVESLOT, /* use remove_slot when r= eattaching */ + VIR_DOMAIN_HOSTDEV_PCI_ORIGSTATE_REPROBE, /* reprobe driver for device= when reattaching */ - /* Does it need to reprobe driver for the device when - * reattaching to host? - */ - bool reprobe; - } pci; - - /* Perhaps 'usb' in future */ - } states; -}; + VIR_DOMAIN_HOSTDEV_PCI_ORIGSTATE_LAST +} virDomainHostdevPCIOrigstate; +VIR_ENUM_DECL(virDomainHostdevPCIOrigstate); struct _virDomainLeaseDef { char *lockspace; @@ -262,6 +248,8 @@ struct _virDomainHostdevSubsysUSB { struct _virDomainHostdevSubsysPCI { virPCIDeviceAddress addr; /* host address */ virDomainHostdevSubsysPCIBackendType backend; + + virBitmap *origstates; }; struct _virDomainHostdevSubsysSCSIHost { @@ -394,7 +382,6 @@ struct _virDomainHostdevDef { virDomainHostdevSubsys subsys; virDomainHostdevCaps caps; } source; - virDomainHostdevOrigStates origstates; virDomainNetTeamingInfo *teaming; virDomainDeviceInfo *info; /* Guest address */ }; diff --git a/src/conf/virconftypes.h b/src/conf/virconftypes.h index d03d1d132e..e07f967814 100644 --- a/src/conf/virconftypes.h +++ b/src/conf/virconftypes.h @@ -116,8 +116,6 @@ typedef struct _virDomainHostdevCaps virDomainHostdevCa= ps; typedef struct _virDomainHostdevDef virDomainHostdevDef; -typedef struct _virDomainHostdevOrigStates virDomainHostdevOrigStates; - typedef struct _virDomainHostdevSubsys virDomainHostdevSubsys; typedef struct _virDomainHostdevSubsysMediatedDev virDomainHostdevSubsysMe= diatedDev; diff --git a/src/hypervisor/virhostdev.c b/src/hypervisor/virhostdev.c index c0ce867596..bc5a20d691 100644 --- a/src/hypervisor/virhostdev.c +++ b/src/hypervisor/virhostdev.c @@ -873,12 +873,18 @@ virHostdevPreparePCIDevicesImpl(virHostdevManager *mg= r, if (actual) { VIR_DEBUG("Saving network configuration of PCI device %s", virPCIDeviceGetName(actual)); - hostdev->origstates.states.pci.unbind_from_stub =3D - virPCIDeviceGetUnbindFromStub(actual); - hostdev->origstates.states.pci.remove_slot =3D - virPCIDeviceGetRemoveSlot(actual); - hostdev->origstates.states.pci.reprobe =3D - virPCIDeviceGetReprobe(actual); + + if (!pcisrc->origstates) + pcisrc->origstates =3D virBitmapNew(VIR_DOMAIN_HOSTDEV_PCI= _ORIGSTATE_LAST); + else + virBitmapClearAll(pcisrc->origstates); + + if (virPCIDeviceGetUnbindFromStub(actual)) + virBitmapSetBitExpand(pcisrc->origstates, VIR_DOMAIN_HOSTD= EV_PCI_ORIGSTATE_UNBIND); + if (virPCIDeviceGetRemoveSlot(actual)) + virBitmapSetBitExpand(pcisrc->origstates, VIR_DOMAIN_HOSTD= EV_PCI_ORIGSTATE_REMOVESLOT); + if (virPCIDeviceGetReprobe(actual)) + virBitmapSetBitExpand(pcisrc->origstates, VIR_DOMAIN_HOSTD= EV_PCI_ORIGSTATE_REPROBE); } } @@ -1132,6 +1138,7 @@ virHostdevUpdateActivePCIDevices(virHostdevManager *m= gr, for (i =3D 0; i < nhostdevs; i++) { const virDomainHostdevDef *hostdev =3D hostdevs[i]; g_autoptr(virPCIDevice) actual =3D NULL; + virBitmap *orig =3D hostdev->source.subsys.u.pci.origstates; if (virHostdevGetPCIHostDevice(hostdev, &actual) < 0) goto cleanup; @@ -1143,9 +1150,9 @@ virHostdevUpdateActivePCIDevices(virHostdevManager *m= gr, goto cleanup; /* Setup the original states for the PCI device */ - virPCIDeviceSetUnbindFromStub(actual, hostdev->origstates.states.p= ci.unbind_from_stub); - virPCIDeviceSetRemoveSlot(actual, hostdev->origstates.states.pci.r= emove_slot); - virPCIDeviceSetReprobe(actual, hostdev->origstates.states.pci.repr= obe); + virPCIDeviceSetUnbindFromStub(actual, virBitmapIsBitSet(orig, VIR_= DOMAIN_HOSTDEV_PCI_ORIGSTATE_UNBIND)); + virPCIDeviceSetRemoveSlot(actual, virBitmapIsBitSet(orig, VIR_DOMA= IN_HOSTDEV_PCI_ORIGSTATE_REMOVESLOT)); + virPCIDeviceSetReprobe(actual, virBitmapIsBitSet(orig, VIR_DOMAIN_= HOSTDEV_PCI_ORIGSTATE_REPROBE)); if (virPCIDeviceListAdd(mgr->activePCIHostdevs, actual) < 0) goto cleanup; --=20 2.39.1