From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: passt.top; dmarc=none (p=none dis=none) header.from=gibson.dropbear.id.au Authentication-Results: passt.top; dkim=pass (2048-bit key; secure) header.d=gibson.dropbear.id.au header.i=@gibson.dropbear.id.au header.a=rsa-sha256 header.s=202602 header.b=E44srv3o; dkim-atps=neutral Received: from mail.ozlabs.org (mail.ozlabs.org [IPv6:2404:9400:2221:ea00::3]) by passt.top (Postfix) with ESMTPS id 08E635A0262 for ; Tue, 05 May 2026 11:58:44 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gibson.dropbear.id.au; s=202602; t=1777975120; bh=ZMzCrtYl4+7pNvGZL3U2xJKEGVqj0+s3qhxo230v2ak=; h=Date:From:To:Cc:Subject:References:In-Reply-To:From; b=E44srv3oeD4lFtg9nRoUUNhoQm4B+X/zujQhz+E2+WYm2PcUsB9KXZ2LacRSl7GZc InXfJ1eHdKhfi43vVWCblFQ0T7Dj4RNWpBEF07mcNlqSkUaXVzNAwUzDgczcUPyOT/ bJOy5IycQJxSIxk5j5uhCoP7vaNJDUQ7spheXl18oshLODARljtspJ2ZNQFTwDDrL6 84icb4RI0RBReX1MiH6YESkFGCCb7ZKeGVum22lSGoz8mPzTQOSTQCBQC0+L5T1Gu5 ngse/fJoYaucOp5LEqsZcJecu5Wkh7gxE+i9dhAzz1dIWgomLAsdVbb9I+DgH/0CWn pCIVNofiM1SEQ== Received: by gandalf.ozlabs.org (Postfix, from userid 1007) id 4g8v9D513yz4wJg; Tue, 05 May 2026 19:58:40 +1000 (AEST) Date: Tue, 5 May 2026 19:58:07 +1000 From: David Gibson To: Laurent Vivier Subject: Re: [PATCH v7 16/18] pesto, conf: Send updated rules from pesto back to passt/pasta Message-ID: References: <20260504231142.1118652-1-sbrivio@redhat.com> <20260504231142.1118652-17-sbrivio@redhat.com> MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha512; protocol="application/pgp-signature"; boundary="9SloW1AcALv0aOxD" Content-Disposition: inline In-Reply-To: Message-ID-Hash: O2MG2MQM2FC7NV45FMXUZ4Q7UTC5PLSB X-Message-ID-Hash: O2MG2MQM2FC7NV45FMXUZ4Q7UTC5PLSB X-MailFrom: dgibson@gandalf.ozlabs.org X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; emergency; loop; banned-address; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: Stefano Brivio , passt-dev@passt.top, Jon Maloy X-Mailman-Version: 3.3.8 Precedence: list List-Id: Development discussion and patches for passt Archived-At: Archived-At: List-Archive: List-Archive: List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: --9SloW1AcALv0aOxD Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Tue, May 05, 2026 at 09:53:04AM +0200, Laurent Vivier wrote: > On 5/5/26 01:11, Stefano Brivio wrote: > > From: David Gibson > >=20 > > Extend pesto to send the updated rule configuration back to passt/pasta. > > Extend passt/pasta to read the new configuration and store the new rule= s in > > a "pending" table. We don't yet attempt to activate them. > >=20 > > Signed-off-by: Stefano Brivio > > [dwg: Based on an early draft from Stefano] > > [sbrivio: Add redundant check on interface names being terminated in > > conf_recv_rules(), to make static checkers happy] > > [sbrivio: Make conf_recv_rules() return -1 if fwd_rule_read() fails, > > as suggested by Jon Maloy] > > Signed-off-by: David Gibson >=20 > Reviewed-by: Laurent Vivier >=20 > But one comment below >=20 > > --- > > Makefile | 5 --- > > conf.c | 94 ++++++++++++++++++++++++++++++++++++++++++++++++-------- > > fwd.c | 10 +++++- > > passt.h | 2 ++ > > pesto.c | 35 +++++++++++++++++++++ > > 5 files changed, 127 insertions(+), 19 deletions(-) > >=20 > > diff --git a/Makefile b/Makefile > > index c746b55..ae755a0 100644 > > --- a/Makefile > > +++ b/Makefile > > @@ -224,10 +224,6 @@ cppcheck: passt.cppcheck passt-repair.cppcheck pes= to.cppcheck qrap.cppcheck > > $(CPPCHECK) $(CPPCHECK_FLAGS) $(BASE_CPPFLAGS) $^ > > passt.cppcheck: BASE_CPPFLAGS +=3D -UPESTO > > -passt.cppcheck: CPPCHECK_FLAGS +=3D \ > > - --suppress=3DunusedFunction:fwd_rule.c \ > > - --suppress=3DstaticFunction:fwd_rule.c \ > > - --suppress=3DunusedFunction:serialise.c > > passt.cppcheck: $(PASST_SRCS) $(PASST_HEADERS) seccomp.h > > passt-repair.cppcheck: $(PASST_REPAIR_SRCS) $(PASST_REPAIR_HEADERS) s= eccomp_repair.h > > @@ -238,7 +234,6 @@ pesto.cppcheck: CPPCHECK_FLAGS +=3D \ > > --suppress=3DunusedFunction:inany.h \ > > --suppress=3DunusedFunction:inany.c \ > > --suppress=3DunusedFunction:ip.h \ > > - --suppress=3DunusedFunction:fwd_rule.c \ > > --suppress=3DstaticFunction:fwd_rule.c \ > > --suppress=3DunusedFunction:serialise.c > > pesto.cppcheck: $(PESTO_SRCS) $(PESTO_HEADERS) seccomp_pesto.h > > diff --git a/conf.c b/conf.c > > index 5e4e81e..f035fd3 100644 > > --- a/conf.c > > +++ b/conf.c > > @@ -1971,6 +1971,62 @@ static int conf_send_rules(const struct ctx *c, = int fd) > > return 0; > > } > > +/** > > + * conf_recv_rules() - Receive forwarding rules from configuration cli= ent > > + * @c: Execution context > > + * @fd: Socket to the client > > + * > > + * Return: 0 on success, -1 on failure > > + */ > > +static int conf_recv_rules(const struct ctx *c, int fd) > > +{ > > + while (1) { > > + struct fwd_table *fwd; > > + struct fwd_rule r; > > + uint32_t count; > > + uint8_t pif; > > + unsigned i; > > + > > + if (read_u8(fd, &pif)) > > + return -1; > > + > > + if (pif =3D=3D PIF_NONE) > > + break; > > + > > + if (pif >=3D ARRAY_SIZE(c->fwd_pending) || > > + !(fwd =3D c->fwd_pending[pif])) { > > + err("Received rules for non-existent table"); > > + return -1; > > + } > > + > > + if (read_u32(fd, &count)) > > + return -1; > > + > > + if (count > MAX_FWD_RULES) { > > + err("Received %"PRIu32" rules (maximum %u)", > > + count, MAX_FWD_RULES); > > + return -1; > > + } > > + > > + for (i =3D 0; i < count; i++) { > > + if (fwd_rule_read(fd, &r)) > > + return -1; > > + > > + if (r.ifname[sizeof(r.ifname) - 1]) { > > + err("Interface name was not NULL terminated"); > > + return -1; > > + } > > + /* Redundant, to make static checkers happy */ > > + r.ifname[sizeof(r.ifname) - 1] =3D '\0'; > > + > > + if (fwd_rule_add(fwd, &r) < 0) > > + return -1; > > + } > > + } > > + > > + return 0; > > +} > > + > > /** > > * conf_close() - Close configuration / control socket and clean up > > * @c: Execution context > > @@ -2075,21 +2131,33 @@ fail: > > void conf_handler(struct ctx *c, uint32_t events) > > { > > if (events & EPOLLIN) { > > - char discard[BUFSIZ]; > > - ssize_t n; > > - > > - do { > > - n =3D read(c->fd_control, discard, sizeof(discard)); > > - if (n > 0) > > - debug("Discarded %zd bytes of config data", n); > > - } while (n > 0); > > - if (n =3D=3D 0) { > > - debug("Configuration client EOF"); > > - goto close; > > + unsigned pif; > > + > > + /* Clear pending tables */ > > + for (pif =3D 0; pif < PIF_NUM_TYPES; pif++) { > > + struct fwd_table *fwd =3D c->fwd_pending[pif]; > > + > > + if (!fwd) > > + continue; > > + fwd->count =3D 0; > > + fwd->sock_count =3D 0; > > } > > - if (errno !=3D EAGAIN && errno !=3D EWOULDBLOCK) { > > - err_perror("Error reading config data"); > > + > > + /* FIXME: this could block indefinitely if the client doesn't > > + * write as much as it should > > + */ > > + if (conf_recv_rules(c, c->fd_control) < 0) > > goto close; > > + > > + for (pif =3D 0; pif < PIF_NUM_TYPES; pif++) { > > + struct fwd_table *fwd =3D c->fwd_pending[pif]; > > + > > + if (!fwd) > > + continue; > > + > > + info("New forwarding rules for %s:", pif_name(pif)); > > + fwd_rules_dump(info, fwd->rules, fwd->count, > > + " ", ""); > > } > > } > > diff --git a/fwd.c b/fwd.c > > index 8849cfc..d93d2e5 100644 > > --- a/fwd.c > > +++ b/fwd.c > > @@ -247,6 +247,9 @@ void fwd_neigh_table_init(const struct ctx *c) > > static struct fwd_table fwd_in; > > static struct fwd_table fwd_out; > > +static struct fwd_table fwd_in_pending; > > +static struct fwd_table fwd_out_pending; > > + > > /** > > * fwd_rule_init() - Initialise forwarding tables > > * @c: Execution context > > @@ -269,10 +272,15 @@ void fwd_rule_init(struct ctx *c) > > caps |=3D FWD_CAP_IFNAME; > > fwd_in.caps =3D fwd_out.caps =3D caps; > > + fwd_in_pending.caps =3D fwd_out_pending.caps =3D caps; > > c->fwd[PIF_HOST] =3D &fwd_in; > > - if (c->mode =3D=3D MODE_PASTA) > > + c->fwd_pending[PIF_HOST] =3D &fwd_in_pending; > > + > > + if (c->mode =3D=3D MODE_PASTA) { > > c->fwd[PIF_SPLICE] =3D &fwd_out; > > + c->fwd_pending[PIF_SPLICE] =3D &fwd_out_pending; > > + } > > } > > /** > > diff --git a/passt.h b/passt.h > > index b3f049d..1726965 100644 > > --- a/passt.h > > +++ b/passt.h > > @@ -188,6 +188,7 @@ struct ip6_ctx { > > * @pasta_ifi: Index of namespace interface for pasta > > * @pasta_conf_ns: Configure namespace after creating it > > * @fwd: Forwarding tables > > + * @fwd_pending: Pending forward tables > > * @no_tcp: Disable TCP operation > > * @tcp: Context for TCP protocol handler > > * @no_udp: Disable UDP operation > > @@ -270,6 +271,7 @@ struct ctx { > > int pasta_conf_ns; > > struct fwd_table *fwd[PIF_NUM_TYPES]; > > + struct fwd_table *fwd_pending[PIF_NUM_TYPES]; > > int no_tcp; > > struct tcp_ctx tcp; > > diff --git a/pesto.c b/pesto.c > > index 16b3a5a..73fdc39 100644 > > --- a/pesto.c > > +++ b/pesto.c > > @@ -230,6 +230,39 @@ static bool read_pif_conf(int fd, struct configura= tion *conf) > > return true; > > } > > +/** > > + * send_conf() - Send updated configuration to passt/pasta > > + * @fd: Control socket > > + * @conf: Updated configuration > > + */ > > +static void send_conf(int fd, const struct configuration *conf) > > +{ > > + unsigned i; > > + >=20 > Perhaps it could be interesting to send a magic number (or a type id) if = we > want to be able to update something else than the rules in the future? > We also can send the length of the data if we want to be able to ignore it > if the type id is not supported? > (Something like the chunks in IFF or PNG file format... but perhaps it's > overcomplicated for our purpose...) Undoubtedly, amongst a bunch of other ways we could make the protocol more flexible. However, I'm inclined to leave that v2. >=20 > > + for (i =3D 0; i < conf->npifs; i++) { > > + const struct pif_configuration *pc =3D &conf->pif[i]; > > + unsigned j; > > + > > + if (write_u8(fd, pc->pif) < 0) > > + goto fail; > > + > > + if (write_u32(fd, pc->fwd.count) < 0) > > + goto fail; > > + > > + for (j =3D 0; j < pc->fwd.count; j++) { > > + if (fwd_rule_write(fd, &pc->fwd.rules[j]) < 0) > > + goto fail; > > + } > > + } > > + > > + if (write_u8(fd, PIF_NONE) < 0) > > + goto fail; > > + return; > > + > > +fail: > > + die_perror("Error writing to control socket"); > > +} > > + > > /** > > * show_conf() - Show current configuration obtained from passt/pasta > > * @conf: Configuration description > > @@ -432,6 +465,8 @@ int main(int argc, char **argv) > > show_conf(&conf); > > } > > + send_conf(s, &conf); > > + > > noupdate: > > if (shutdown(s, SHUT_RDWR) < 0 || close(s) < 0) > > die_perror("Error shutting down control socket"); >=20 --=20 David Gibson (he or they) | I'll have my music baroque, and my code david AT gibson.dropbear.id.au | minimalist, thank you, not the other way | around. http://www.ozlabs.org/~dgibson --9SloW1AcALv0aOxD Content-Type: application/pgp-signature; name=signature.asc -----BEGIN PGP SIGNATURE----- iQIzBAEBCgAdFiEEO+dNsU4E3yXUXRK2zQJF27ox2GcFAmn5vyQACgkQzQJF27ox 2GfjVA//UtnQgvHUGPgj1y+BZKSmS5hvn2H9PFP7prwAUXrw3dMFBN7yBbkRWggE p8ghbY0DuUqB9pFlDH63f8iAfsk5A7OnrhUutWfzZmNeOHFKk5uNnIepnFYw63sx XmhvHh0WpGGOqxZ7XQah+mVZ+fjErY8BdlNHaBvZyvJ7Vc4Sjb1IibC+C63SUtEh d5WfKjO3g4n8pHR2aLWjep8CaJ4q4COd1M0OJi77OhIZKKXrrtQl0jGiXi7WfmUU aeYH5Cfnnla6Lnqsv4nHAaaUp06XH3wwljwYmPQx6zmxIqzqGWR2/Yur3nM5P3pq FTD/hMKpRMUetoCOs0vL9a2fW2umXg8XnWBd7tcz3Cz/oLdCbk5gz4OfNf5S9U4+ FYx0HL1YmdDL/kEfdTtQfCm842VjkLkj75vGa4jSXViCWZ4ZrxA0gPgs+fd+qkob pCvYiDmdcYKIbpTGr9fpX0oun+zVkNr/zL5xy9pePfxrMpTcGuVj5PaSkaK1VOVA +7CougtIXY6D1OrsU6vtj8nyzKi04QxUJYmiWS7hoN2e8/2ep63Htducs7LF97P3 K3ycawlybZkwJxzfeWGgh6Qv84Guk9rIHl4M0IaYNReeFgICV6V0i9FDSp6gOWJl NO+irKzDih5b+tV9u/v6bBWYhjlgVwpXlvxkZyc0+v3gXwylOok= =3PKJ -----END PGP SIGNATURE----- --9SloW1AcALv0aOxD--