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=202608 header.b=YiMyUihP; dkim-atps=neutral Received: from mail.ozlabs.org (mail.ozlabs.org [IPv6:2404:9400:2221:ea00::3]) by passt.top (Postfix) with ESMTPS id 0F4A55A0274 for ; Thu, 13 Aug 2026 07:04:47 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gibson.dropbear.id.au; s=202608; t=1786597482; bh=QJ5nX0ajkuCne0zmu1zJkRmN/iaaejONf2DH4tBWXGQ=; h=Date:From:To:Cc:Subject:References:In-Reply-To:From; b=YiMyUihPyRSH9jMIhkjUGzUakdEJAMiOPP8jWcnm08TBA62Wdw9j6oMTloA3JfYZa msoFmw02xaWk+Z+2xB5iEmGcxHNEOSq5P34UVL7qNz5+NH6NLHiaInmiQUYE/t5vFd cP9U346seM12h0sufjLPwKs0mfkCSHa74DdD6upIVXmVS/TzfdkxIOlVrASKHlYf0E ofnQhXEvyRTs9eXJXcjOqmqRSLlcN0imWhyHmjVYsdi47649gZJSb2Gb36B6bM1NfF Vuwoq4pWbTolVl7clYol74vhsWHaALGB87hngDyhco/fdY/Msidqr8Zfm9HDKRzf1D jCvtTJ3lMhRbg== Received: by gandalf.ozlabs.org (Postfix, from userid 1007) id 4hLCvt3MGWz4w9r; Thu, 13 Aug 2026 15:04:42 +1000 (AEST) Date: Thu, 13 Aug 2026 15:04:33 +1000 From: David Gibson To: Anshu Kumari Subject: Re: [PATCH 3/5] fuzz: Bypass isolation and adapt sockets for AFL++ Message-ID: References: <20260812072630.3235261-1-anskuma@redhat.com> <20260812072630.3235261-4-anskuma@redhat.com> MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha512; protocol="application/pgp-signature"; boundary="peNyB2aGuJasPLhq" Content-Disposition: inline In-Reply-To: <20260812072630.3235261-4-anskuma@redhat.com> Message-ID-Hash: NVIWWA4QZ464JX6ONY7VDMNHQRR6ADV7 X-Message-ID-Hash: NVIWWA4QZ464JX6ONY7VDMNHQRR6ADV7 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: sbrivio@redhat.com, passt-dev@passt.top, aerosound161@gmail.com, abdobngad@gmail.com, lvivier@redhat.com 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: --peNyB2aGuJasPLhq Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Wed, Aug 12, 2026 at 12:56:26PM +0530, Anshu Kumari wrote: > Few components which needs to be disabled to support AFL++ > to work: >=20 > - isolation.c: Skip isolation and seccomp sandboxing that breaks AFL++ > pipes, namespaces, and ASan mmap/mprotect operations. > - util.c / tap.c: Switch UNIX socket to SOCK_SEQPACKET to preserve frame > boundaries, simplifying tap_passt_input() to a single recv() and removi= ng > vnet_len framing. Most of these changes are pretty trivial, but this one is not. I'd suggest moving this into its own patch for clarity, and so it can get a more detailed rationale / explanation in the commit message. Because the test server is using its own SEQPACKET protocol, somewhat similar to, but not identical with the qemu socket protocol, you're essentially adding a new tap backend for fuzzing. That's a reasonable approach, but I think it would be clearer to treat it as that, rather than as a weird special case of the normal passt tap backend. > - passt.h: Use /tmp/passt_fuzz_%i.socket to avoid path collisions with > production instances. > - tcp_buf.c: Include fuzz.h to route recvmsg() through deterministic wrap= pers. >=20 > Signed-off-by: Anshu Kumari > --- > isolation.c | 11 +++++++++++ > passt.h | 4 ++++ > tap.c | 21 +++++++++++++++++++++ > tcp_buf.c | 1 + > util.c | 10 ++++++++++ > 5 files changed, 47 insertions(+) >=20 > diff --git a/isolation.c b/isolation.c > index a30b329..61fc76a 100644 > --- a/isolation.c > +++ b/isolation.c > @@ -208,6 +208,9 @@ static int move_root(void) > */ > void isolate_initial(void) > { > +#ifdef FUZZING > + return; > +#endif Rather than just eliminating the isolate_*() routines entirely, I'd prefer to selectively disable the specific parts that block fuzzing. > uint64_t keep; > =20 > /* We want to keep CAP_NET_BIND_SERVICE in the initial > @@ -389,6 +392,10 @@ void isolate_user(const struct ctx *c, uid_t uid, gi= d_t gid, bool use_userns, > */ > int isolate_prefork(const struct ctx *c) > { > +#ifdef FUZZING > + (void)c; > + return 0; > +#endif > int flags =3D CLONE_NEWIPC | CLONE_NEWNS | CLONE_NEWUTS; > uint64_t ns_caps =3D 0; > =20 > @@ -466,6 +473,10 @@ int isolate_prefork(const struct ctx *c) > */ > void isolate_postfork(const struct ctx *c) > { > +#ifdef FUZZING > + (void)c; > + return; > +#endif > struct sock_fprog prog; > =20 > prctl(PR_SET_DUMPABLE, 0); > diff --git a/passt.h b/passt.h > index 51ccd4f..141c9f8 100644 > --- a/passt.h > +++ b/passt.h > @@ -7,7 +7,11 @@ > #define PASST_H > =20 > #define UNIX_SOCK_MAX 100 > +#ifdef FUZZING > +#define UNIX_SOCK_PATH "/tmp/passt_fuzz_%i.socket" > +#else > #define UNIX_SOCK_PATH "/tmp/passt_%i.socket" > +#endif Good idea. > union epoll_ref; > =20 > diff --git a/tap.c b/tap.c > index dfa66c7..f32c9ad 100644 > --- a/tap.c > +++ b/tap.c > @@ -14,6 +14,7 @@ > */ > =20 > #include > +#include > #include > #include > #include > @@ -61,6 +62,7 @@ > #include "vhost_user.h" > #include "vu_common.h" > #include "epoll_ctl.h" > +#include "fuzz.h" > =20 > /* Maximum allowed frame lengths (including L2 header) */ > =20 > @@ -144,8 +146,10 @@ void tap_send_single(const struct ctx *c, const void= *data, size_t l2len) > =20 > switch (c->mode) { > case MODE_PASST: > +#ifndef FUZZING > iov[iovcnt] =3D IOV_OF_LVALUE(vnet_len); > iovcnt++; > +#endif Right, I think this might be clearer as a new 'case MODE_FUZZ:'. > /* fall through */ > case MODE_PASTA: > iov[iovcnt].iov_base =3D (void *)data; > @@ -1231,6 +1235,22 @@ static void tap_passt_input(struct ctx *c, const s= truct timespec *now) > =20 > tap_flush_pools(); > =20 > +#ifdef FUZZING > + /* SOCK_SEQPACKET: each recv returns exactly one frame */ And I think this would be clearer as a new tap_fuzz_input(). > + do { > + n =3D recv(c->fd_tap, pkt_buf, sizeof(pkt_buf), MSG_DONTWAIT); > + } while ((n < 0) && errno =3D=3D EINTR); > + > + if (n > 0 && n >=3D (ssize_t)sizeof(struct ethhdr)) { I suggest removing the length check: that way the fuzzer can also look for any bugs we might have if we ever get undersized frames from the tap interface. > + struct iov_tail data; > + > + data =3D IOV_TAIL_FROM_BUF(pkt_buf, n, 0); > + tap_add_packet(c, &data, now); > + } else if (n < 0 && errno !=3D EAGAIN && errno !=3D EWOULDBLOCK) { > + tap_sock_reset(c); I don't think we really care about reset and recovery for the fuzzing case, so a die() would probably suffice here. > + return; > + } > +#else > if (partial_len) { > /* We have a partial frame from an earlier pass. Move it to the > * start of the buffer, top up with new data, then process all > @@ -1281,6 +1301,7 @@ static void tap_passt_input(struct ctx *c, const st= ruct timespec *now) > =20 > partial_len =3D n; > partial_frame =3D p; > +#endif Whenever a #if is more than a handful of lines, it's generally helpful to put a comment on the #endif so you can tell what the #if was conditional on without having to scroll up a bunch. > =20 > tap_handler(c, now); > } > diff --git a/tcp_buf.c b/tcp_buf.c > index 72c4541..eb28abe 100644 > --- a/tcp_buf.c > +++ b/tcp_buf.c > @@ -32,6 +32,7 @@ > #include "tcp_conn.h" > #include "tcp_internal.h" > #include "tcp_buf.h" > +#include "fuzz.h" > =20 > #define TCP_FRAMES_MEM 128 > #define TCP_FRAMES \ > diff --git a/util.c b/util.c > index 28c32e4..7f29c3b 100644 > --- a/util.c > +++ b/util.c > @@ -36,6 +36,7 @@ > #include "epoll_ctl.h" > #include "pasta.h" > #include "serialise.h" > +#include "fuzz.h" > #ifdef HAS_GETRANDOM > #include > #endif > @@ -229,7 +230,11 @@ int sock_l4_dualstack_any(const struct ctx *c, enum = epoll_type type, > */ > int sock_unix(char *sock_path) > { > +#ifdef FUZZING > + int fd =3D socket(AF_UNIX, SOCK_SEQPACKET | SOCK_CLOEXEC, 0); > +#else > int fd =3D socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0); > +#endif Special casing what's ostensibly a general helper to open unix sockets is a bit nasty - it's relying on the fact that the only Unix socket that we're really using is the one for tap. Treating fuzz as a different tap backend would address this too. > struct sockaddr_un addr =3D { > .sun_family =3D AF_UNIX, > }; > @@ -248,8 +253,13 @@ int sock_unix(char *sock_path) > UNIX_SOCK_PATH, i)) > die_perror("Can't build UNIX domain socket path"); > =20 > +#ifdef FUZZING > + ex =3D socket(AF_UNIX, SOCK_SEQPACKET | SOCK_NONBLOCK | SOCK_CLOEXEC, > + 0); > +#else > ex =3D socket(AF_UNIX, SOCK_STREAM | SOCK_NONBLOCK | SOCK_CLOEXEC, > 0); > +#endif > if (ex < 0) > die_perror("Failed to check for UNIX domain conflicts"); > =20 > --=20 > 2.55.0 >=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 --peNyB2aGuJasPLhq Content-Type: application/pgp-signature; name=signature.asc -----BEGIN PGP SIGNATURE----- iQIzBAEBCgAdFiEEO+dNsU4E3yXUXRK2zQJF27ox2GcFAmp9UFYACgkQzQJF27ox 2GddGQ/9Ftx8WrwlaBYN46jWcGfI8MAs2QxzshbI2Vy8uh8dG1utXYH3YoA7ImdF RCp8DlcFE657izr8KYgnj4sye6cb6/NJhLIqFzLBqYwGJaLNjHMPhyGgEgkPtuTH KuneCXYt2CzY8+X401SrshqFDsX3rckaDufeeZsRcLd5OINzvliFV2tb/NEAgbHC /odCp/gWl41corClT6HGwpJOPB2n4IDbDhTg6Po4NPnNq2Atq9TvoVHHYX5Xt3J6 rXoytOiOstffOeyKIKCUgsqcCaMi2AGcNxCX1WmUfiXUNHi/B5Ey9LIuLOARy1ik Zj/CD2tEUi/KW4eDDftrLLWpf0EcOLAehv0rtK5FOH9UgcSzogix+BM97ZXAVjyr JoGaijHt8bVKhTWc0ouVQBqHLpLCavvoWqXIKPvkhbxQGurM1gV69E/HysUsjM0/ sTk6V9//ySIPJabkreXkZckKm1M633mBuxAhaaF2ATH9/BMjl86O6+Je+ujZOVGQ VhbOYCVetNekvqXBAevbuDS2QlF02NiGEMOdu5yZC2Tmtkb2mkhE6l/BeeVU4sZO 9Vh4Pfc4O5asZg1vMjW3K/+wCNvNvEn1WBapBZvwz1MxH29KLYNdaV9rWgL3D00W GnBtohGN0ox8I7h60fgBNUpVhmw2iJNeezEjd2p7qoZ+0Kim+Z4= =7KbQ -----END PGP SIGNATURE----- --peNyB2aGuJasPLhq--