From nobody Fri Dec 12 15:16:37 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) client-ip=8.43.85.245; envelope-from=devel-bounces@lists.libvirt.org; helo=lists.libvirt.org; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) smtp.mailfrom=devel-bounces@lists.libvirt.org; dmarc=pass(p=none dis=none) header.from=gmail.com ARC-Seal: i=1; a=rsa-sha256; t=1761913010; cv=none; d=zohomail.com; s=zohoarc; b=CRBM7kMYAzqEN9kC9yGawxmC2y/iPBhbzBSzCGFcfbwNJv5UJApSVvfs8O7IlAqE3qSpIpNM5MgWRd9Y7xbcu0HxG586QT1gd3hqavgwtWyXBycq651Vd6nph6iPOqI/VQMj50OqpWDvsJzmZtv5M7czO7ckuOQ3lGrgV59mPjw= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1761913010; h=Content-Transfer-Encoding:Cc:Cc:Date:Date:From:From:In-Reply-To:List-Subscribe:List-Post:List-Owner:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Subject:Subject:To:To:Message-Id:Reply-To; bh=8bM8zGi2RKInlhnzbjb54ZRYMrjkVtDAtBs1mLAj920=; b=TKNcD9FvO/07p1CuW9JvSpj8H5N+rq7CnZQdoLWhPlYMZ9/tCB1TK1lc26lHR7SYEJjLzCXO1BY4oMfyFUnZ3GVPix09aYjqfkE++/qwMwMTuVtb5Di8s1+lmJac4FsKnTV6YGHqkEXu8GMDD3X3PaPKUhIdjAIRhW49S/Q+bhA= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) smtp.mailfrom=devel-bounces@lists.libvirt.org; dmarc=pass header.from= (p=none dis=none) Return-Path: Received: from lists.libvirt.org (lists.libvirt.org [8.43.85.245]) by mx.zohomail.com with SMTPS id 1761913010096338.0897722661829; Fri, 31 Oct 2025 05:16:50 -0700 (PDT) Received: by lists.libvirt.org (Postfix, from userid 993) id 530A443F3D; Fri, 31 Oct 2025 08:16:49 -0400 (EDT) Received: from [172.19.199.29] (lists.libvirt.org [8.43.85.245]) by lists.libvirt.org (Postfix) with ESMTP id 8D8D2440BE; Fri, 31 Oct 2025 08:08:21 -0400 (EDT) Received: by lists.libvirt.org (Postfix, from userid 993) id 8D55841BAE; Fri, 31 Oct 2025 08:07:53 -0400 (EDT) Received: from mail-ej1-f41.google.com (mail-ej1-f41.google.com [209.85.218.41]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (3072 bits) server-digest SHA256) (No client certificate requested) by lists.libvirt.org (Postfix) with ESMTPS id D088243E51 for ; Fri, 31 Oct 2025 08:07:49 -0400 (EDT) Received: by mail-ej1-f41.google.com with SMTP id a640c23a62f3a-b3b27b50090so375054966b.0 for ; Fri, 31 Oct 2025 05:07:49 -0700 (PDT) Received: from thinkiepadje.home (2a02-a470-a384-0-62ef-bf5-dc71-bd78.fixed6.kpn.net. [2a02:a470:a384:0:62ef:bf5:dc71:bd78]) by smtp.gmail.com with ESMTPSA id a640c23a62f3a-b70779ddf48sm158255866b.32.2025.10.31.05.07.47 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 31 Oct 2025 05:07:47 -0700 (PDT) X-Spam-Checker-Version: SpamAssassin 4.0.1 (2024-03-26) on lists.libvirt.org X-Spam-Level: X-Spam-Status: No, score=-5.3 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,MAILING_LIST_MULTI,RCVD_IN_DNSWL_MED, RCVD_IN_VALIDITY_CERTIFIED_BLOCKED,RCVD_IN_VALIDITY_RPBL_BLOCKED, RCVD_IN_VALIDITY_SAFE_BLOCKED,SPF_PASS autolearn=unavailable autolearn_force=no version=4.0.1 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1761912468; x=1762517268; darn=lists.libvirt.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=8bM8zGi2RKInlhnzbjb54ZRYMrjkVtDAtBs1mLAj920=; b=A4Qit7OimO26T2KLHnPp82sLsMP4ue0lGdoJbUG4YyFUjS5gbMud9tK30WrRwPOM+o vPQ5l4myq0ZukZaFnbsc2YBuxWXzl8FhEQgCUSqZKFMMj2lah3cJl0htrsHIR72n1Uaq AZFJQeHFAZotamtMAcl/kKE4xPIc/uRDbGEIEs7ANRxibuuIwx3yBXWvV5lA7w4qrIcB AJVQo0u2XVdkaxCfhOM3gRRMbTThFr4pteufBv66d8MFM/rdyqXWspsCJdC/LVN8SLlU AVQX4Sl6ZV7Q3vrw42ZYp79yWt1Rxyzu5AjVakl4GQA9HkdO+/nkToA+gLxLG3zuQisv Zr4w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1761912468; x=1762517268; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=8bM8zGi2RKInlhnzbjb54ZRYMrjkVtDAtBs1mLAj920=; b=RHdWriN/LG9SDiO3E1fHi9IScN2FB+N4xmVRqrolQ/hARpV32yHCabVb8A8DN3EDtG EzV0B3Hu9Sgs1zgOkuIJ1gmDALRBwiumMl+2h6dw1i305RLZ7eu1OuFop8Egucv82083 WyqqKlBijjLjzJxixy0KRO3NZeKCibtjVylo7HgdzjF9K4bMMCLItQkJec49YoNq7IjK WZ58wTyw8VqfYwVNE9SJc7ZCYNenLDiYj5+WZO/L7hTSNm20HiJpO1WJffb2APWk9+pw ts2uf+vQWwdUiQswxbBDE2efQWv8UoaNMa3g5FDtwCvO7/slLoZ0YDEE1k7SMXzRbw6H Qcew== X-Gm-Message-State: AOJu0YzjCVy8JM9vKnlKcjlrAPz5EPzOrrZ38LCFTYNNdBrCUv2tj33b lu4EglTQ2Oshyk01vUjjqm/NxDC2VTWyGkCkGrpW4qTdzk2UbJ7Y7oEa7ISuko3QKA== X-Gm-Gg: ASbGncsyXrY4/fwkLIcYwiI4PQ3qaMIvlIuMOCHwset477DEf7IQ2ArEu0c4F9A/w4x F5a8flfmMqWgcJUGpRycyEtoJtj52oeDeFSWY3RJvCam8kNsUw6FJh3lGq4S4CE8lu7LMb6X+nG Yo236NYNxCGtfwQ9b1kXpikD2gkH9mrWqVNN7sZ6bbRnUoQQBVetdH622CQfnPZ4BO6Cjy5r1M4 WETeSS3dSz7YPGrflJBUAX3Cjez5ottEguj/85LD9Xu07irLqBuheIbYUY7CZAhX4Yj8hmcFZ/l 88kmb+JyP1jwCk8JeHIiobttr18vmmB9sjzjsmsHQ9gzJNRbo6W25hr7DOWWrLvQJro9DhcoZ6T 5+BkTA4Pgb5zVSvj+seQIJA1YuyQhHWtlKqNt00iaUVtotPiItmdIXxb4MyAVOjzptlPkpry3eE CNsLbZKljihaR5W9lU7JI0pqp10F5BZBX1GvctEgfKG1P4S8IRBJc7qyXM4u9pVtiFrckPteZox q3LqlhWSg== X-Google-Smtp-Source: AGHT+IFs8bb2DdSXJRvalVGfqlYcT/HN7MWBKMwznTTj+JTY72QxoLUTO2xOhu9jiyP3vDxA04IlCg== X-Received: by 2002:a17:906:7313:b0:b6d:692e:9a84 with SMTP id a640c23a62f3a-b70704b2e87mr294484566b.38.1761912468226; Fri, 31 Oct 2025 05:07:48 -0700 (PDT) From: Dion Bosschieter To: devel@lists.libvirt.org Subject: [PATCH 2/5] nwfilter: move shared nwfilter driver functions into nwfilter_tech_driver.c Date: Fri, 31 Oct 2025 13:05:42 +0100 Message-ID: <20251031120546.942126-3-dionbosschieter@gmail.com> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20251031120546.942126-1-dionbosschieter@gmail.com> References: <20251031120546.942126-1-dionbosschieter@gmail.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Message-ID-Hash: U4VEDMA4PLLUKL5JMVGYIJYT6GUBDAUS X-Message-ID-Hash: U4VEDMA4PLLUKL5JMVGYIJYT6GUBDAUS X-MailFrom: dionbosschieter@gmail.com X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; loop; banned-address; header-match-devel.lists.libvirt.org-0; emergency; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: jean-louis@dupond.be, Dion Bosschieter X-Mailman-Version: 3.3.10 Precedence: list List-Id: Development discussions about the libvirt library & tools Archived-At: List-Archive: List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: X-ZohoMail-DKIM: pass (identity @gmail.com) X-ZM-MESSAGEID: 1761913012143154100 Content-Type: text/plain; charset="utf-8" Introduce nwfilter_tech_driver.c which holds shared non driver specific methods. The following logic can be reused by new nwfilter drivers, which are not ebiptables specific: - data type print logic, used for constructing ascii cli arguments out of nwfilter data; - chain jump proto type l3_proto_idx logic; - virNWFilterRule sorting. Signed-off-by: Dion Bosschieter --- src/nwfilter/meson.build | 1 + src/nwfilter/nwfilter_ebiptables_driver.c | 262 +--------------------- src/nwfilter/nwfilter_tech_driver.c | 250 +++++++++++++++++++++ src/nwfilter/nwfilter_tech_driver.h | 50 ++++- 4 files changed, 299 insertions(+), 264 deletions(-) create mode 100644 src/nwfilter/nwfilter_tech_driver.c diff --git a/src/nwfilter/meson.build b/src/nwfilter/meson.build index de3d202267..9e8a4797c5 100644 --- a/src/nwfilter/meson.build +++ b/src/nwfilter/meson.build @@ -1,6 +1,7 @@ nwfilter_driver_sources =3D [ 'nwfilter_driver.c', 'nwfilter_gentech_driver.c', + 'nwfilter_tech_driver.c', 'nwfilter_dhcpsnoop.c', 'nwfilter_ebiptables_driver.c', 'nwfilter_learnipaddr.c', diff --git a/src/nwfilter/nwfilter_ebiptables_driver.c b/src/nwfilter/nwfil= ter_ebiptables_driver.c index 4578152670..97a90d586e 100644 --- a/src/nwfilter/nwfilter_ebiptables_driver.c +++ b/src/nwfilter/nwfilter_ebiptables_driver.c @@ -25,7 +25,6 @@ #include #include #include -#include =20 #include "internal.h" =20 @@ -35,6 +34,7 @@ #include "virerror.h" #include "nwfilter_conf.h" #include "nwfilter_ebiptables_driver.h" +#include "nwfilter_tech_driver.h" #include "virfile.h" #include "configmake.h" #include "virstring.h" @@ -83,24 +83,6 @@ static void ebiptablesDriverShutdown(void); static int ebtablesCleanAll(const char *ifname); static int ebiptablesAllTeardown(const char *ifname); =20 -struct ushort_map { - unsigned short attr; - const char *val; -}; - - -enum l3_proto_idx { - L3_PROTO_IPV4_IDX =3D 0, - L3_PROTO_IPV6_IDX, - L3_PROTO_ARP_IDX, - L3_PROTO_RARP_IDX, - L2_PROTO_MAC_IDX, - L2_PROTO_VLAN_IDX, - L2_PROTO_STP_IDX, - L3_PROTO_LAST_IDX -}; - -#define USHORTMAP_ENTRY_IDX(IDX, ATT, VAL) [IDX] =3D { .attr =3D ATT, .val= =3D VAL } =20 /* A lookup table for translating ethernet protocol IDs to human readable * strings. None of the human readable strings must be found as a prefix @@ -118,7 +100,6 @@ static const struct ushort_map l3_protocols[] =3D { USHORTMAP_ENTRY_IDX(L3_PROTO_LAST_IDX, 0, NULL), }; =20 - static char chainprefixes_host[3] =3D { CHAINPREFIX_HOST_IN, CHAINPREFIX_HOST_OUT, @@ -137,12 +118,6 @@ typedef struct { const char *targetChain; } iptablesBaseChainFW; =20 -typedef struct { - const char *ifname; - int nrules; - virNWFilterRuleInst **rules; -} chainCreateCallbackData; - static iptablesBaseChainFW fw_base_chains[] =3D { {"FORWARD", "1", VIRT_IN_CHAIN}, {"FORWARD", "2", VIRT_OUT_CHAIN}, @@ -150,206 +125,6 @@ static iptablesBaseChainFW fw_base_chains[] =3D { {"INPUT", "1", HOST_IN_CHAIN}, }; =20 -static int -printVar(virNWFilterVarCombIter *vars, - char *buf, int bufsize, - nwItemDesc *item, - bool *done) -{ - *done =3D false; - - if ((item->flags & NWFILTER_ENTRY_ITEM_FLAG_HAS_VAR)) { - const char *val; - - val =3D virNWFilterVarCombIterGetVarValue(vars, item->varAccess); - if (!val) { - /* error has been reported */ - return -1; - } - - if (virStrcpy(buf, val, bufsize) < 0) { - const char *varName; - - varName =3D virNWFilterVarAccessGetVarName(item->varAccess); - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Buffer too small to print variable '%1$s' in= to"), - varName); - return -1; - } - - *done =3D true; - } - return 0; -} - - -static int -_printDataType(virNWFilterVarCombIter *vars, - char *buf, int bufsize, - nwItemDesc *item, - bool asHex, bool directionIn) -{ - bool done; - g_autofree char *data =3D NULL; - uint8_t ctr; - g_auto(virBuffer) vb =3D VIR_BUFFER_INITIALIZER; - g_autofree char *flags =3D NULL; - - if (printVar(vars, buf, bufsize, item, &done) < 0) - return -1; - - if (done) - return 0; - - switch (item->datatype) { - case DATATYPE_IPADDR: - data =3D virSocketAddrFormat(&item->u.ipaddr); - if (!data) - return -1; - if (g_snprintf(buf, bufsize, "%s", data) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("buffer too small for IP address")); - return -1; - } - break; - - case DATATYPE_IPV6ADDR: - data =3D virSocketAddrFormat(&item->u.ipaddr); - if (!data) - return -1; - - if (g_snprintf(buf, bufsize, "%s", data) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("buffer too small for IPv6 address")); - return -1; - } - break; - - case DATATYPE_MACADDR: - case DATATYPE_MACMASK: - if (bufsize < VIR_MAC_STRING_BUFLEN) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for MAC address")); - return -1; - } - - virMacAddrFormat(&item->u.macaddr, buf); - break; - - case DATATYPE_IPV6MASK: - case DATATYPE_IPMASK: - if (g_snprintf(buf, bufsize, "%d", - item->u.u8) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for uint8 type")); - return -1; - } - break; - - case DATATYPE_UINT32: - case DATATYPE_UINT32_HEX: - if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%u", - item->u.u32) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for uint32 type")); - return -1; - } - break; - - case DATATYPE_UINT16: - case DATATYPE_UINT16_HEX: - if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%d", - item->u.u16) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for uint16 type")); - return -1; - } - break; - - case DATATYPE_UINT8: - case DATATYPE_UINT8_HEX: - if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%d", - item->u.u8) >=3D bufsize) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for uint8 type")); - return -1; - } - break; - - case DATATYPE_IPSETNAME: - if (virStrcpy(buf, item->u.ipset.setname, bufsize) < 0) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer to small for ipset name")); - return -1; - } - break; - - case DATATYPE_IPSETFLAGS: - for (ctr =3D 0; ctr < item->u.ipset.numFlags; ctr++) { - if (ctr !=3D 0) - virBufferAddLit(&vb, ","); - if ((item->u.ipset.flags & (1 << ctr))) { - if (directionIn) - virBufferAddLit(&vb, "dst"); - else - virBufferAddLit(&vb, "src"); - } else { - if (directionIn) - virBufferAddLit(&vb, "src"); - else - virBufferAddLit(&vb, "dst"); - } - } - - flags =3D virBufferContentAndReset(&vb); - - if (virStrcpy(buf, flags, bufsize) < 0) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Buffer too small for IPSETFLAGS type")); - return -1; - } - break; - - case DATATYPE_STRING: - case DATATYPE_STRINGCOPY: - case DATATYPE_BOOLEAN: - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Cannot print data type %1$x"), item->datatype); - return -1; - case DATATYPE_LAST: - default: - virReportEnumRangeError(virNWFilterAttrDataType, item->datatype); - return -1; - } - - return 0; -} - - -static int -printDataType(virNWFilterVarCombIter *vars, - char *buf, int bufsize, - nwItemDesc *item) -{ - return _printDataType(vars, buf, bufsize, item, 0, 0); -} - -static int -printDataTypeDirection(virNWFilterVarCombIter *vars, - char *buf, int bufsize, - nwItemDesc *item, bool directionIn) -{ - return _printDataType(vars, buf, bufsize, item, 0, directionIn); -} - -static int -printDataTypeAsHex(virNWFilterVarCombIter *vars, - char *buf, int bufsize, - nwItemDesc *item) -{ - return _printDataType(vars, buf, bufsize, item, 1, 0); -} - =20 static int ebtablesHandleEthHdr(virFirewall *fw, @@ -3041,41 +2816,6 @@ ebtablesCleanAll(const char *ifname) } =20 =20 -static int -virNWFilterRuleInstSort(const void *a, const void *b) -{ - const virNWFilterRuleInst *insta =3D a; - const virNWFilterRuleInst *instb =3D b; - const char *root =3D virNWFilterChainSuffixTypeToString( - VIR_NWFILTER_CHAINSUFFIX_ROOT); - bool root_a =3D STREQ(insta->chainSuffix, root); - bool root_b =3D STREQ(instb->chainSuffix, root); - - /* ensure root chain commands appear before all others since - we will need them to create the child chains */ - if (root_a) { - if (!root_b) - return -1; /* a before b */ - } else if (root_b) { - return 1; /* b before a */ - } - - /* priorities are limited to range [-1000, 1000] */ - return insta->priority - instb->priority; -} - - -static int -virNWFilterRuleInstSortPtr(const void *a, - const void *b, - void *opaque G_GNUC_UNUSED) -{ - virNWFilterRuleInst * const *insta =3D a; - virNWFilterRuleInst * const *instb =3D b; - return virNWFilterRuleInstSort(*insta, *instb); -} - - static int ebiptablesFilterOrderSort(const void *va, const void *vb, diff --git a/src/nwfilter/nwfilter_tech_driver.c b/src/nwfilter/nwfilter_te= ch_driver.c new file mode 100644 index 0000000000..7b3edff8e6 --- /dev/null +++ b/src/nwfilter/nwfilter_tech_driver.c @@ -0,0 +1,250 @@ +/* + * nwfilter_tech_driver.c: common/shared functions used in nwfilter gentec= h drivers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see + * . + */ + +#include + +#include "nwfilter_tech_driver.h" +#include "nwfilter_conf.h" + +#define VIR_FROM_THIS VIR_FROM_NWFILTER + +int virNWFilterRuleInstSort(const void *a, const void *b) +{ + const virNWFilterRuleInst *insta =3D a; + const virNWFilterRuleInst *instb =3D b; + const char *root =3D virNWFilterChainSuffixTypeToString( + VIR_NWFILTER_CHAINSUFFIX_ROOT); + bool root_a =3D STREQ(insta->chainSuffix, root); + bool root_b =3D STREQ(instb->chainSuffix, root); + + /* ensure root chain commands appear before all others since + we will need them to create the child chains */ + if (root_a) { + if (!root_b) + return -1; /* a before b */ + } else if (root_b) { + return 1; /* b before a */ + } + + /* priorities are limited to range [-1000, 1000] */ + return insta->priority - instb->priority; +} + + +int virNWFilterRuleInstSortPtr(const void *a, + const void *b, + void *opaque G_GNUC_UNUSED) +{ + virNWFilterRuleInst * const *insta =3D a; + virNWFilterRuleInst * const *instb =3D b; + return virNWFilterRuleInstSort(*insta, *instb); +} + +int printVar(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item, + bool *done) +{ + *done =3D false; + + if ((item->flags & NWFILTER_ENTRY_ITEM_FLAG_HAS_VAR)) { + const char *val; + + val =3D virNWFilterVarCombIterGetVarValue(vars, item->varAccess); + if (!val) { + /* error has been reported */ + return -1; + } + + if (virStrcpy(buf, val, bufsize) < 0) { + const char *varName; + + varName =3D virNWFilterVarAccessGetVarName(item->varAccess); + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Buffer too small to print variable '%1$s' in= to"), + varName); + return -1; + } + + *done =3D true; + } + return 0; +} + +static int +_printDataType(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item, + bool asHex, bool directionIn) +{ + bool done; + g_autofree char *data =3D NULL; + uint8_t ctr; + g_auto(virBuffer) vb =3D VIR_BUFFER_INITIALIZER; + g_autofree char *flags =3D NULL; + + if (printVar(vars, buf, bufsize, item, &done) < 0) + return -1; + + if (done) + return 0; + + switch (item->datatype) { + case DATATYPE_IPADDR: + data =3D virSocketAddrFormat(&item->u.ipaddr); + if (!data) + return -1; + if (g_snprintf(buf, bufsize, "%s", data) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("buffer too small for IP address")); + return -1; + } + break; + + case DATATYPE_IPV6ADDR: + data =3D virSocketAddrFormat(&item->u.ipaddr); + if (!data) + return -1; + + if (g_snprintf(buf, bufsize, "%s", data) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("buffer too small for IPv6 address")); + return -1; + } + break; + + case DATATYPE_MACADDR: + case DATATYPE_MACMASK: + if (bufsize < VIR_MAC_STRING_BUFLEN) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for MAC address")); + return -1; + } + + virMacAddrFormat(&item->u.macaddr, buf); + break; + + case DATATYPE_IPV6MASK: + case DATATYPE_IPMASK: + if (g_snprintf(buf, bufsize, "%d", + item->u.u8) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for uint8 type")); + return -1; + } + break; + + case DATATYPE_UINT32: + case DATATYPE_UINT32_HEX: + if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%u", + item->u.u32) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for uint32 type")); + return -1; + } + break; + + case DATATYPE_UINT16: + case DATATYPE_UINT16_HEX: + if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%d", + item->u.u16) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for uint16 type")); + return -1; + } + break; + + case DATATYPE_UINT8: + case DATATYPE_UINT8_HEX: + if (g_snprintf(buf, bufsize, asHex ? "0x%x" : "%d", + item->u.u8) >=3D bufsize) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for uint8 type")); + return -1; + } + break; + + case DATATYPE_IPSETNAME: + if (virStrcpy(buf, item->u.ipset.setname, bufsize) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer to small for ipset name")); + return -1; + } + break; + + case DATATYPE_IPSETFLAGS: + for (ctr =3D 0; ctr < item->u.ipset.numFlags; ctr++) { + if (ctr !=3D 0) + virBufferAddLit(&vb, ","); + if ((item->u.ipset.flags & (1 << ctr))) { + if (directionIn) + virBufferAddLit(&vb, "dst"); + else + virBufferAddLit(&vb, "src"); + } else { + if (directionIn) + virBufferAddLit(&vb, "src"); + else + virBufferAddLit(&vb, "dst"); + } + } + + flags =3D virBufferContentAndReset(&vb); + + if (virStrcpy(buf, flags, bufsize) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Buffer too small for IPSETFLAGS type")); + return -1; + } + break; + + case DATATYPE_STRING: + case DATATYPE_STRINGCOPY: + case DATATYPE_BOOLEAN: + virReportError(VIR_ERR_INTERNAL_ERROR, + _("Cannot print data type %1$x"), item->datatype); + return -1; + case DATATYPE_LAST: + default: + virReportEnumRangeError(virNWFilterAttrDataType, item->datatype); + return -1; + } + + return 0; +} + +int printDataType(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item) +{ + return _printDataType(vars, buf, bufsize, item, 0, 0); +} + +int printDataTypeDirection(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item, bool directionIn) +{ + return _printDataType(vars, buf, bufsize, item, 0, directionIn); +} + +int printDataTypeAsHex(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item) +{ + return _printDataType(vars, buf, bufsize, item, 1, 0); +} diff --git a/src/nwfilter/nwfilter_tech_driver.h b/src/nwfilter/nwfilter_te= ch_driver.h index a4af0bf6d5..7a85c46339 100644 --- a/src/nwfilter/nwfilter_tech_driver.h +++ b/src/nwfilter/nwfilter_tech_driver.h @@ -24,9 +24,7 @@ #pragma once =20 #include "virnwfilterobj.h" - -typedef struct _virNWFilterTechDriver virNWFilterTechDriver; - +#include "virstring.h" =20 typedef struct _virNWFilterRuleInst virNWFilterRuleInst; struct _virNWFilterRuleInst { @@ -38,6 +36,31 @@ struct _virNWFilterRuleInst { }; =20 =20 +typedef struct _chainCreateCallbackData chainCreateCallbackData; +struct _chainCreateCallbackData { + const char *ifname; + int nrules; + virNWFilterRuleInst **rules; +}; + +struct ushort_map { + unsigned short attr; + const char *val; +}; + +#define USHORTMAP_ENTRY_IDX(IDX, ATT, VAL) [IDX] =3D { .attr =3D ATT, .val= =3D VAL } + +enum l3_proto_idx { + L3_PROTO_IPV4_IDX =3D 0, + L3_PROTO_IPV6_IDX, + L3_PROTO_ARP_IDX, + L3_PROTO_RARP_IDX, + L2_PROTO_MAC_IDX, + L2_PROTO_VLAN_IDX, + L2_PROTO_STP_IDX, + L3_PROTO_LAST_IDX +}; + typedef int (*virNWFilterTechDrvInit)(bool privileged); typedef void (*virNWFilterTechDrvShutdown)(void); =20 @@ -69,6 +92,7 @@ enum techDrvFlags { TECHDRV_FLAG_INITIALIZED =3D (1 << 0), }; =20 +typedef struct _virNWFilterTechDriver virNWFilterTechDriver; struct _virNWFilterTechDriver { const char *name; enum techDrvFlags flags; @@ -87,3 +111,23 @@ struct _virNWFilterTechDriver { virNWFilterDropAllRules applyDropAllRules; virNWFilterRemoveBasicRules removeBasicRules; }; + +int virNWFilterRuleInstSort(const void *a, const void *b); +int virNWFilterRuleInstSortPtr(const void *a, + const void *b, + void *opaque); +int printVar(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item, + bool *done); + +int printDataType(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item); + +int printDataTypeDirection(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item, bool directionIn); +int printDataTypeAsHex(virNWFilterVarCombIter *vars, + char *buf, int bufsize, + nwItemDesc *item); --=20 2.43.0