From nobody Wed May 14 01:05:00 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; envelope-from=libvir-list-bounces@redhat.com; helo=mx1.redhat.com; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass(p=none dis=none) header.from=redhat.com Return-Path: Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by mx.zohomail.com with SMTPS id 152640637693678.21067930225092; Tue, 15 May 2018 10:46:16 -0700 (PDT) Received: from smtp.corp.redhat.com (int-mx07.intmail.prod.int.phx2.redhat.com [10.5.11.22]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 76665C0092DE; Tue, 15 May 2018 17:46:15 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.21]) by smtp.corp.redhat.com (Postfix) with ESMTPS id 3E257100191B; Tue, 15 May 2018 17:46:15 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id E89E84BB79; Tue, 15 May 2018 17:46:14 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id w4FHhkuX004230 for ; Tue, 15 May 2018 13:43:46 -0400 Received: by smtp.corp.redhat.com (Postfix) id 23F5D1002973; Tue, 15 May 2018 17:43:46 +0000 (UTC) Received: from t460.redhat.com (unknown [10.33.36.6]) by smtp.corp.redhat.com (Postfix) with ESMTP id 57B6810A7E3B; Tue, 15 May 2018 17:43:45 +0000 (UTC) From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= To: libvir-list@redhat.com Date: Tue, 15 May 2018 18:43:23 +0100 Message-Id: <20180515174337.11287-8-berrange@redhat.com> In-Reply-To: <20180515174337.11287-1-berrange@redhat.com> References: <20180515174337.11287-1-berrange@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-loop: libvir-list@redhat.com Subject: [libvirt] [PATCH v2 07/21] nwfilter: export port binding concept in the public API X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.84 on 10.5.11.22 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.32]); Tue, 15 May 2018 17:46:16 +0000 (UTC) X-ZohoMail: RSF_0 Z_629925259 SPT_0 When the daemons are split there will need to be a way for the virt drivers and/or network driver to create and delete bindings between network ports and network filters. This defines a set of public APIs that are suitable for managing this facility. Signed-off-by: Daniel P. Berrang=C3=A9 Reviewed-by: John Ferlan --- include/libvirt/libvirt-nwfilter.h | 39 ++++ include/libvirt/virterror.h | 2 + src/datatypes.c | 67 +++++++ src/datatypes.h | 31 +++ src/driver-nwfilter.h | 30 +++ src/libvirt-nwfilter.c | 305 +++++++++++++++++++++++++++++ src/libvirt_private.syms | 1 + src/libvirt_public.syms | 13 ++ src/util/virerror.c | 12 ++ 9 files changed, 500 insertions(+) diff --git a/include/libvirt/libvirt-nwfilter.h b/include/libvirt/libvirt-n= wfilter.h index 9f01c175a9..20e6d1ff9a 100644 --- a/include/libvirt/libvirt-nwfilter.h +++ b/include/libvirt/libvirt-nwfilter.h @@ -43,6 +43,23 @@ typedef struct _virNWFilter virNWFilter; */ typedef virNWFilter *virNWFilterPtr; =20 +/** + * virNWFilterBinding: + * + * a virNWFilterBinding is a private structure representing a network + * filter binding to a port + */ +typedef struct _virNWFilterBinding virNWFilterBinding; + +/** + * virNWFilterBindingPtr: + * + * a virNWFilterBindingPtr is pointer to a virNWFilterBinding private + * structure, this is the type used to reference a network filter + * port binding in the API. + */ +typedef virNWFilterBinding *virNWFilterBindingPtr; + =20 /* * List NWFilters @@ -92,4 +109,26 @@ int virNWFilterGetUUIDString (virNW= FilterPtr nwfilter, char * virNWFilterGetXMLDesc (virNWFilterPtr nwfilter, unsigned int flags); =20 + +virNWFilterBindingPtr virNWFilterBindingLookupByPortDev(virConnectPtr co= nn, + const char *port= dev); + +const char * virNWFilterBindingGetPortDev(virNWFilterBindingPtr= binding); +const char * virNWFilterBindingGetFilterName(virNWFilterBinding= Ptr binding); + +int virConnectListAllNWFilterBindings(virConnectPtr co= nn, + virNWFilterBindi= ngPtr **bindings, + unsigned int fla= gs); + +virNWFilterBindingPtr virNWFilterBindingCreateXML(virConnectPtr conn, + const char *xml, + unsigned int flags); + +char * virNWFilterBindingGetXMLDesc(virNWFilterBindingPtr= binding, + unsigned int flags); + +int virNWFilterBindingDelete(virNWFilterBindingPtr bin= ding); +int virNWFilterBindingRef(virNWFilterBindingPtr bindin= g); +int virNWFilterBindingFree(virNWFilterBindingPtr bindi= ng); + #endif /* __VIR_LIBVIRT_NWFILTER_H__ */ diff --git a/include/libvirt/virterror.h b/include/libvirt/virterror.h index 3e7c7a02c7..02bc141f1c 100644 --- a/include/libvirt/virterror.h +++ b/include/libvirt/virterror.h @@ -321,6 +321,8 @@ typedef enum { to guest-sync command (DEPRECAT= ED)*/ VIR_ERR_LIBSSH =3D 98, /* error in libssh transport dri= ver */ VIR_ERR_DEVICE_MISSING =3D 99, /* fail to find the desired devi= ce */ + VIR_ERR_INVALID_NWFILTER_BINDING =3D 100, /* invalid nwfilter binding= */ + VIR_ERR_NO_NWFILTER_BINDING =3D 101, /* no nwfilter binding */ } virErrorNumber; =20 /** diff --git a/src/datatypes.c b/src/datatypes.c index 09b8eea5a2..878a1c5b5f 100644 --- a/src/datatypes.c +++ b/src/datatypes.c @@ -41,6 +41,7 @@ virClassPtr virInterfaceClass; virClassPtr virNetworkClass; virClassPtr virNodeDeviceClass; virClassPtr virNWFilterClass; +virClassPtr virNWFilterBindingClass; virClassPtr virSecretClass; virClassPtr virStreamClass; virClassPtr virStorageVolClass; @@ -54,6 +55,7 @@ static void virInterfaceDispose(void *obj); static void virNetworkDispose(void *obj); static void virNodeDeviceDispose(void *obj); static void virNWFilterDispose(void *obj); +static void virNWFilterBindingDispose(void *obj); static void virSecretDispose(void *obj); static void virStreamDispose(void *obj); static void virStorageVolDispose(void *obj); @@ -89,6 +91,7 @@ virDataTypesOnceInit(void) DECLARE_CLASS(virNetwork); DECLARE_CLASS(virNodeDevice); DECLARE_CLASS(virNWFilter); + DECLARE_CLASS(virNWFilterBinding); DECLARE_CLASS(virSecret); DECLARE_CLASS(virStream); DECLARE_CLASS(virStorageVol); @@ -830,6 +833,70 @@ virNWFilterDispose(void *obj) } =20 =20 +/** + * virGetNWFilterBinding: + * @conn: the hypervisor connection + * @portdev: pointer to the network filter port device name + * @filtername: name of the network filter + * + * Allocates a new network filter binding object. When the object is no lo= nger + * needed, virObjectUnref() must be called in order to not leak data. + * + * Returns a pointer to the network filter binding object, or NULL on erro= r. + */ +virNWFilterBindingPtr +virGetNWFilterBinding(virConnectPtr conn, const char *portdev, + const char *filtername) +{ + virNWFilterBindingPtr ret =3D NULL; + + if (virDataTypesInitialize() < 0) + return NULL; + + virCheckConnectGoto(conn, error); + virCheckNonNullArgGoto(portdev, error); + + if (!(ret =3D virObjectNew(virNWFilterBindingClass))) + goto error; + + if (VIR_STRDUP(ret->portdev, portdev) < 0) + goto error; + + if (VIR_STRDUP(ret->filtername, filtername) < 0) + goto error; + + ret->conn =3D virObjectRef(conn); + + return ret; + + error: + virObjectUnref(ret); + return NULL; +} + + +/** + * virNWFilterBindingDispose: + * @obj: the network filter binding to release + * + * Unconditionally release all memory associated with a nwfilter binding. + * The nwfilter binding object must not be used once this method returns. + * + * It will also unreference the associated connection object, + * which may also be released if its ref count hits zero. + */ +static void +virNWFilterBindingDispose(void *obj) +{ + virNWFilterBindingPtr binding =3D obj; + + VIR_DEBUG("release binding %p %s", binding, binding->portdev); + + VIR_FREE(binding->portdev); + virObjectUnref(binding->conn); +} + + /** * virGetDomainSnapshot: * @domain: the domain to snapshot diff --git a/src/datatypes.h b/src/datatypes.h index 192c86be80..e1b38706dc 100644 --- a/src/datatypes.h +++ b/src/datatypes.h @@ -36,6 +36,7 @@ extern virClassPtr virInterfaceClass; extern virClassPtr virNetworkClass; extern virClassPtr virNodeDeviceClass; extern virClassPtr virNWFilterClass; +extern virClassPtr virNWFilterBindingClass; extern virClassPtr virSecretClass; extern virClassPtr virStreamClass; extern virClassPtr virStorageVolClass; @@ -277,6 +278,20 @@ extern virClassPtr virAdmClientClass; } \ } while (0) =20 +# define virCheckNWFilterBindingReturn(obj, retval) \ + do { \ + virNWFilterBindingPtr _nw =3D (obj); \ + if (!virObjectIsClass(_nw, virNWFilterBindingClass) || \ + !virObjectIsClass(_nw->conn, virConnectClass)) { \ + virReportErrorHelper(VIR_FROM_NWFILTER, \ + VIR_ERR_INVALID_NWFILTER_BINDING, \ + __FILE__, __FUNCTION__, __LINE__, \ + __FUNCTION__); \ + virDispatchError(NULL); \ + return retval; \ + } \ + } while (0) + # define virCheckDomainSnapshotReturn(obj, retval) \ do { \ virDomainSnapshotPtr _snap =3D (obj); \ @@ -676,6 +691,19 @@ struct _virNWFilter { }; =20 =20 +/** +* _virNWFilterBinding: +* +* Internal structure associated to a network filter port binding +*/ +struct _virNWFilterBinding { + virObject parent; + virConnectPtr conn; /* pointer back to the connection= */ + char *portdev; /* the network filter port device= name */ + char *filtername; /* the network filter name */ +}; + + /* * Helper APIs for allocating new object instances */ @@ -712,6 +740,9 @@ virStreamPtr virGetStream(virConnectPtr conn); virNWFilterPtr virGetNWFilter(virConnectPtr conn, const char *name, const unsigned char *uuid); +virNWFilterBindingPtr virGetNWFilterBinding(virConnectPtr conn, + const char *portdev, + const char *filtername); virDomainSnapshotPtr virGetDomainSnapshot(virDomainPtr domain, const char *name); =20 diff --git a/src/driver-nwfilter.h b/src/driver-nwfilter.h index cb49542f92..2c3e480a32 100644 --- a/src/driver-nwfilter.h +++ b/src/driver-nwfilter.h @@ -57,6 +57,31 @@ typedef char * (*virDrvNWFilterGetXMLDesc)(virNWFilterPtr nwfilter, unsigned int flags); =20 +typedef virNWFilterBindingPtr +(*virDrvNWFilterBindingLookupByPortDev)(virConnectPtr conn, + const char *portdev); + +typedef int +(*virDrvConnectListAllNWFilterBindings)(virConnectPtr conn, + virNWFilterBindingPtr **bindings, + unsigned int flags); + +typedef virNWFilterBindingPtr +(*virDrvNWFilterBindingCreateXML)(virConnectPtr conn, + const char *xml, + unsigned int flags); + +typedef char * +(*virDrvNWFilterBindingGetXMLDesc)(virNWFilterBindingPtr binding, + unsigned int flags); + +typedef int +(*virDrvNWFilterBindingDelete)(virNWFilterBindingPtr binding); +typedef int +(*virDrvNWFilterBindingRef)(virNWFilterBindingPtr binding); +typedef int +(*virDrvNWFilterBindingFree)(virNWFilterBindingPtr binding); + =20 typedef struct _virNWFilterDriver virNWFilterDriver; typedef virNWFilterDriver *virNWFilterDriverPtr; @@ -77,6 +102,11 @@ struct _virNWFilterDriver { virDrvNWFilterDefineXML nwfilterDefineXML; virDrvNWFilterUndefine nwfilterUndefine; virDrvNWFilterGetXMLDesc nwfilterGetXMLDesc; + virDrvConnectListAllNWFilterBindings connectListAllNWFilterBindings; + virDrvNWFilterBindingLookupByPortDev nwfilterBindingLookupByPortDev; + virDrvNWFilterBindingCreateXML nwfilterBindingCreateXML; + virDrvNWFilterBindingDelete nwfilterBindingDelete; + virDrvNWFilterBindingGetXMLDesc nwfilterBindingGetXMLDesc; }; =20 =20 diff --git a/src/libvirt-nwfilter.c b/src/libvirt-nwfilter.c index 948c30deef..e572d46c18 100644 --- a/src/libvirt-nwfilter.c +++ b/src/libvirt-nwfilter.c @@ -513,3 +513,308 @@ virNWFilterRef(virNWFilterPtr nwfilter) virObjectRef(nwfilter); return 0; } + + +/** + * virConnectListAllNWFilterBindings: + * @conn: Pointer to the hypervisor connection. + * @bindings: Pointer to a variable to store the array containing the netw= ork + * filter objects or NULL if the list is not required (just ret= urns + * number of network filters). + * @flags: extra flags; not used yet, so callers should always pass 0 + * + * Collect the list of network filters, and allocate an array to store tho= se + * objects. + * + * Returns the number of network filters found or -1 and sets @filters to = NULL + * in case of error. On success, the array stored into @filters is guaran= teed to + * have an extra allocated element set to NULL but not included in the ret= urn count, + * to make iteration easier. The caller is responsible for calling + * virNWFilterFree() on each array element, then calling free() on @filter= s. + */ +int +virConnectListAllNWFilterBindings(virConnectPtr conn, + virNWFilterBindingPtr **bindings, + unsigned int flags) +{ + VIR_DEBUG("conn=3D%p, bindings=3D%p, flags=3D0x%x", conn, bindings, fl= ags); + + virResetLastError(); + + if (bindings) + *bindings =3D NULL; + + virCheckConnectReturn(conn, -1); + + if (conn->nwfilterDriver && + conn->nwfilterDriver->connectListAllNWFilterBindings) { + int ret; + ret =3D conn->nwfilterDriver->connectListAllNWFilterBindings(conn,= bindings, flags); + if (ret < 0) + goto error; + return ret; + } + + virReportUnsupportedError(); + + error: + virDispatchError(conn); + return -1; +} + + +/** + * virNWFilterBindingLookupByPortDev: + * @conn: pointer to the hypervisor connection + * @portdev: name for the network port device + * + * Try to lookup a network filter binding on the given hypervisor based + * on network port device name. + * + * virNWFilterBindingFree should be used to free the resources after the + * binding object is no longer needed. + * + * Returns a new binding object or NULL in case of failure. If the + * network filter cannot be found, then VIR_ERR_NO_NWFILTER_BINDING + * error is raised. + */ +virNWFilterBindingPtr +virNWFilterBindingLookupByPortDev(virConnectPtr conn, const char *portdev) +{ + VIR_DEBUG("conn=3D%p, name=3D%s", conn, NULLSTR(portdev)); + + virResetLastError(); + + virCheckConnectReturn(conn, NULL); + virCheckNonNullArgGoto(portdev, error); + + if (conn->nwfilterDriver && conn->nwfilterDriver->nwfilterBindingLooku= pByPortDev) { + virNWFilterBindingPtr ret; + ret =3D conn->nwfilterDriver->nwfilterBindingLookupByPortDev(conn,= portdev); + if (!ret) + goto error; + return ret; + } + + virReportUnsupportedError(); + + error: + virDispatchError(conn); + return NULL; +} + + +/** + * virNWFilterBindingFree: + * @binding: a binding object + * + * Free the binding object. The running instance is kept alive. + * The data structure is freed and should not be used thereafter. + * + * Returns 0 in case of success and -1 in case of failure. + */ +int +virNWFilterBindingFree(virNWFilterBindingPtr binding) +{ + VIR_DEBUG("binding=3D%p", binding); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, -1); + + virObjectUnref(binding); + return 0; +} + + +/** + * virNWFilterBindingGetPortDev: + * @binding: a binding object + * + * Get the port dev name for the network filter binding + * + * Returns a pointer to the name or NULL, the string need not be deallocat= ed + * its lifetime will be the same as the binding object. + */ +const char * +virNWFilterBindingGetPortDev(virNWFilterBindingPtr binding) +{ + VIR_DEBUG("binding=3D%p", binding); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, NULL); + + return binding->portdev; +} + + +/** + * virNWFilterBindingGetFilterName: + * @binding: a binding object + * + * Get the filter name for the network filter binding + * + * Returns a pointer to the name or NULL, the string need not be deallocat= ed + * its lifetime will be the same as the binding object. + */ +const char * +virNWFilterBindingGetFilterName(virNWFilterBindingPtr binding) +{ + VIR_DEBUG("binding=3D%p", binding); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, NULL); + + return binding->filtername; +} + + +/** + * virNWFilterBindingCreateXML: + * @conn: pointer to the hypervisor connection + * @xml: an XML description of the binding + * @flags: currently unused, pass 0 + * + * Define a new network filter, based on an XML description + * similar to the one returned by virNWFilterGetXMLDesc() + * + * virNWFilterFree should be used to free the resources after the + * binding object is no longer needed. + * + * Returns a new binding object or NULL in case of failure + */ +virNWFilterBindingPtr +virNWFilterBindingCreateXML(virConnectPtr conn, const char *xml, unsigned = int flags) +{ + VIR_DEBUG("conn=3D%p, xml=3D%s", conn, NULLSTR(xml)); + + virResetLastError(); + + virCheckConnectReturn(conn, NULL); + virCheckNonNullArgGoto(xml, error); + virCheckReadOnlyGoto(conn->flags, error); + + if (conn->nwfilterDriver && conn->nwfilterDriver->nwfilterBindingCreat= eXML) { + virNWFilterBindingPtr ret; + ret =3D conn->nwfilterDriver->nwfilterBindingCreateXML(conn, xml, = flags); + if (!ret) + goto error; + return ret; + } + + virReportUnsupportedError(); + + error: + virDispatchError(conn); + return NULL; +} + + +/** + * virNWFilterBindingDelete: + * @binding: a binding object + * + * Delete the binding object. This does not free the + * associated virNWFilterBindingPtr object. + * + * Returns 0 in case of success and -1 in case of failure. + */ +int +virNWFilterBindingDelete(virNWFilterBindingPtr binding) +{ + virConnectPtr conn; + VIR_DEBUG("binding=3D%p", binding); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, -1); + conn =3D binding->conn; + + virCheckReadOnlyGoto(conn->flags, error); + + if (conn->nwfilterDriver && conn->nwfilterDriver->nwfilterBindingDelet= e) { + int ret; + ret =3D conn->nwfilterDriver->nwfilterBindingDelete(binding); + if (ret < 0) + goto error; + return ret; + } + + virReportUnsupportedError(); + + error: + virDispatchError(binding->conn); + return -1; +} + + +/** + * virNWFilterBindingGetXMLDesc: + * @binding: a binding object + * @flags: extra flags; not used yet, so callers should always pass 0 + * + * Provide an XML description of the network filter. The description may be + * reused later to redefine the network filter with virNWFilterCreateXML(). + * + * Returns a 0 terminated UTF-8 encoded XML instance, or NULL in case of e= rror. + * the caller must free() the returned value. + */ +char * +virNWFilterBindingGetXMLDesc(virNWFilterBindingPtr binding, unsigned int f= lags) +{ + virConnectPtr conn; + VIR_DEBUG("binding=3D%p, flags=3D0x%x", binding, flags); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, NULL); + conn =3D binding->conn; + + if (conn->nwfilterDriver && conn->nwfilterDriver->nwfilterBindingGetXM= LDesc) { + char *ret; + ret =3D conn->nwfilterDriver->nwfilterBindingGetXMLDesc(binding, f= lags); + if (!ret) + goto error; + return ret; + } + + virReportUnsupportedError(); + + error: + virDispatchError(binding->conn); + return NULL; +} + + +/** + * virNWFilterBindingRef: + * @binding: the binding to hold a reference on + * + * Increment the reference count on the binding. For each + * additional call to this method, there shall be a corresponding + * call to virNWFilterFree to release the reference count, once + * the caller no longer needs the reference to this object. + * + * This method is typically useful for applications where multiple + * threads are using a connection, and it is required that the + * connection remain open until all threads have finished using + * it. ie, each new thread using an binding would increment + * the reference count. + * + * Returns 0 in case of success, -1 in case of failure. + */ +int +virNWFilterBindingRef(virNWFilterBindingPtr binding) +{ + VIR_DEBUG("binding=3D%p refs=3D%d", binding, + binding ? binding->parent.u.s.refs : 0); + + virResetLastError(); + + virCheckNWFilterBindingReturn(binding, -1); + + virObjectRef(binding); + return 0; +} diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 03145c70d5..0ce685b6f2 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1193,6 +1193,7 @@ virGetInterface; virGetNetwork; virGetNodeDevice; virGetNWFilter; +virGetNWFilterBinding; virGetSecret; virGetStoragePool; virGetStorageVol; diff --git a/src/libvirt_public.syms b/src/libvirt_public.syms index 95df3a0dbc..cc73fd8528 100644 --- a/src/libvirt_public.syms +++ b/src/libvirt_public.syms @@ -785,4 +785,17 @@ LIBVIRT_4.1.0 { virStoragePoolLookupByTargetPath; } LIBVIRT_3.9.0; =20 +LIBVIRT_4.4.0 { + global: + virNWFilterBindingLookupByPortDev; + virConnectListAllNWFilterBindings; + virNWFilterBindingCreateXML; + virNWFilterBindingGetXMLDesc; + virNWFilterBindingDelete; + virNWFilterBindingRef; + virNWFilterBindingFree; + virNWFilterBindingGetPortDev; + virNWFilterBindingGetFilterName; +} LIBVIRT_4.1.0; + # .... define new API here using predicted next version number .... diff --git a/src/util/virerror.c b/src/util/virerror.c index c000b00436..074e217849 100644 --- a/src/util/virerror.c +++ b/src/util/virerror.c @@ -1459,6 +1459,18 @@ virErrorMsg(virErrorNumber error, const char *info) else errmsg =3D _("device not found: %s"); break; + case VIR_ERR_INVALID_NWFILTER_BINDING: + if (info =3D=3D NULL) + errmsg =3D _("Invalid network filter binding"); + else + errmsg =3D _("Invalid network filter binding: %s"); + break; + case VIR_ERR_NO_NWFILTER_BINDING: + if (info =3D=3D NULL) + errmsg =3D _("Network filter binding not found"); + else + errmsg =3D _("Network filter binding not found: %s"); + break; } return errmsg; } --=20 2.17.0 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list