From: Bobby Eshleman <bobbyeshleman@gmail.com>
To: Daniel Borkmann <daniel@iogearbox.net>
Cc: kuba@kernel.org, razor@blackwall.org, bobbyeshleman@meta.com,
dw@davidwei.uk, netdev@vger.kernel.org
Subject: Re: [PATCH net-next 3/4] selftests/net: Add netkit io_uring ZC test for large rx_buf_len
Date: Wed, 10 Jun 2026 16:28:39 -0700 [thread overview]
Message-ID: <ainzJx27MlX3WhLV@devvm29614.prn0.facebook.com> (raw)
In-Reply-To: <20260610080344.701380-4-daniel@iogearbox.net>
On Wed, Jun 10, 2026 at 10:03:43AM +0200, Daniel Borkmann wrote:
> Add test_iou_zcrx_large_buf, which runs iou-zcrx with rx_buf_len >
> page size (-x 2) through a netkit-leased RX queue. The netkit ifindex
> is opaque to io_uring, but rx_page_size is honoured by the leased
> physical qops via netif_mp_open_rxq()'s lease redirect.
>
> Originally, I also added a BIG TCP variant on top, but dropped it
> here as fbnic (and the QEMU fbnic model) has no BIG TCP support
> to exercise it as this point.
>
> Tested against the QEMU fbnic emulation. The new test exercises
> the > page rx_buf_len path only when the leased NIC advertises
> QCFG_RX_PAGE_SIZE; otherwise it skips.
>
> For fbnic, I used Bjorn's patches locally [0]:
>
> # ./nk_qlease.py
> TAP version 13
> 1..5
> ok 1 nk_qlease.test_iou_zcrx
> ok 2 nk_qlease.test_iou_zcrx_large_buf
> ok 3 nk_qlease.test_attrs
> ok 4 nk_qlease.test_attach_xdp_with_mp
> ok 5 nk_qlease.test_destroy
> # Totals: pass:5 fail:0 xfail:0 xpass:0 skip:0 error:0
>
> Without those patches (aka not advertising QCFG_RX_PAGE_SIZE):
>
> # ./nk_qlease.py
> TAP version 13
> 1..5
> ok 1 nk_qlease.test_iou_zcrx
> ok 2 nk_qlease.test_iou_zcrx_large_buf # SKIP Large chunks are not supported -95
> ok 3 nk_qlease.test_attrs
> ok 4 nk_qlease.test_attach_xdp_with_mp
> ok 5 nk_qlease.test_destroy
> # Totals: pass:4 fail:0 xfail:0 xpass:0 skip:1 error:0
>
> Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
> Link: https://lore.kernel.org/netdev/20260522113225.241337-1-bjorn@kernel.org/ [0]
> ---
> .../selftests/drivers/net/hw/nk_qlease.py | 86 ++++++++++++++++++-
> 1 file changed, 85 insertions(+), 1 deletion(-)
>
> diff --git a/tools/testing/selftests/drivers/net/hw/nk_qlease.py b/tools/testing/selftests/drivers/net/hw/nk_qlease.py
> index fee114676fd8..90d688453ddf 100755
> --- a/tools/testing/selftests/drivers/net/hw/nk_qlease.py
> +++ b/tools/testing/selftests/drivers/net/hw/nk_qlease.py
> @@ -32,6 +32,15 @@ from lib.py import (
> )
> from lib.py import KsftSkipEx, CmdExitFailure
>
> +# iou-zcrx exits with 42 from setup_zcrx() when the NIC does not advertise
> +# QCFG_RX_PAGE_SIZE (or otherwise rejects the requested rx_buf_len).
> +SKIP_CODE = 42
> +
> +
> +def _restore_hugepages(count):
> + with open("/proc/sys/vm/nr_hugepages", "w", encoding="utf-8") as f:
> + f.write(str(count))
> +
>
> def _create_netkit_pair(cfg, rxqueues=2):
> if cfg.nk_host_ifname:
> @@ -188,6 +197,75 @@ def test_iou_zcrx(cfg) -> None:
> cmd(tx_cmd, host=cfg.remote)
>
>
> +def test_iou_zcrx_large_buf(cfg) -> None:
> + """iou-zcrx with rx_buf_len > page size, going through a netkit-leased
> + queue. Exercises the queue rx-buf-len path via netif_mp_open_rxq()'s
> + lease redirect: the netkit ifindex is opaque to io_uring, but
> + rx_page_size is honoured by the *physical* qops because the lease
> + pointer rewrites the request from netkit onto the leased physical
> + rxq before supported_params/validate_qcfg are consulted.
> + """
> + cfg.require_ipver("6")
> + src_queue, nk_queue = _setup_lease(cfg)
> + defer(_teardown_netkit, cfg)
> + ethnl = EthtoolFamily()
> +
> + with open("/proc/sys/vm/nr_hugepages", "r+", encoding="utf-8") as f:
> + nr_hugepages = int(f.read().strip())
> + if nr_hugepages < 64:
> + f.seek(0)
> + f.write("64")
> + defer(_restore_hugepages, nr_hugepages)
> +
> + rings = ethnl.rings_get({"header": {"dev-index": cfg.ifindex}})
> + rx_rings = rings["rx"]
> + hds_thresh = rings.get("hds-thresh", 0)
> +
> + ethnl.rings_set(
> + {
> + "header": {"dev-index": cfg.ifindex},
> + "tcp-data-split": "enabled",
> + "hds-thresh": 0,
> + "rx": 64,
> + }
> + )
> + defer(
> + ethnl.rings_set,
> + {
> + "header": {"dev-index": cfg.ifindex},
> + "tcp-data-split": "unknown",
> + "hds-thresh": hds_thresh,
> + "rx": rx_rings,
> + },
> + )
> +
> + ethtool(f"-X {cfg.ifname} equal {src_queue}")
> + defer(ethtool, f"-X {cfg.ifname} default")
> +
> + flow_rule_id = set_flow_rule(cfg, src_queue)
> + defer(ethtool, f"-N {cfg.ifname} delete {flow_rule_id}")
> +
> + # -x 2 asks iou-zcrx for rx_buf_len = 2 * page_size (8 KiB on x86_64),
> + # backed by a 2 MiB hugepage area so the chunks are physically
> + # contiguous, which is what zcrx requires for non-default rx_buf_len.
> + rx_cmd = (
> + f"ip netns exec {cfg.netns.name} {cfg.bin_local} "
> + f"-s -p {cfg.port} -i {cfg.nk_guest_ifname} -q {nk_queue} -x 2"
> + )
Could cmd(..., ns=cfg.netns) be used instead of ip netns exec?
> + tx_cmd = f"{cfg.bin_remote} -c -h {cfg.nk_guest_ipv6} -p {cfg.port} -l 12840"
> +
> + # Probe via -d (dry run): exits with SKIP_CODE if the leased physical
> + # qops doesn't advertise QCFG_RX_PAGE_SIZE (e.g. older bnxt FW/HW).
> + probe = cmd(rx_cmd + " -d", fail=False)
> + if probe.ret == SKIP_CODE:
> + msg = probe.stdout.strip() or "rx_buf_len not supported by leased NIC"
> + raise KsftSkipEx(msg)
Since -d can still install an mp, does this also need mp_clear_wait()?
The rest below looks good to me!
Best,
Bobby
> +
> + with bkg(rx_cmd, exit_wait=True):
> + wait_port_listen(cfg.port, proto="tcp", ns=cfg.netns)
> + cmd(tx_cmd, host=cfg.remote)
> +
> +
> def test_attrs(cfg) -> None:
> cfg.require_ipver("6")
> src_queue, nk_queue = _setup_lease(cfg)
> @@ -350,7 +428,13 @@ def main() -> None:
> cfg.port = rand_port()
>
> ksft_run(
> - [test_iou_zcrx, test_attrs, test_attach_xdp_with_mp, test_destroy],
> + [
> + test_iou_zcrx,
> + test_iou_zcrx_large_buf,
> + test_attrs,
> + test_attach_xdp_with_mp,
> + test_destroy,
> + ],
> args=(cfg,),
> )
> ksft_exit()
> --
> 2.43.0
>
next prev parent reply other threads:[~2026-06-10 23:28 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-06-10 8:03 [PATCH net-next 0/4] Extend netkit io_uring ZC selftests Daniel Borkmann
2026-06-10 8:03 ` [PATCH net-next 1/4] selftests/net: Move netkit lease hw setup into per-test fixtures Daniel Borkmann
2026-06-10 23:50 ` Bobby Eshleman
2026-06-10 8:03 ` [PATCH net-next 2/4] selftests/net: Use public NetDrvContEnv API in nk_qlease fixtures Daniel Borkmann
2026-06-10 23:53 ` Bobby Eshleman
2026-06-10 8:03 ` [PATCH net-next 3/4] selftests/net: Add netkit io_uring ZC test for large rx_buf_len Daniel Borkmann
2026-06-10 23:28 ` Bobby Eshleman [this message]
2026-06-10 8:03 ` [PATCH net-next 4/4] selftests/net: Add hugepage kernel config dependency for zcrx Daniel Borkmann
2026-06-10 23:54 ` Bobby Eshleman
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=ainzJx27MlX3WhLV@devvm29614.prn0.facebook.com \
--to=bobbyeshleman@gmail.com \
--cc=bobbyeshleman@meta.com \
--cc=daniel@iogearbox.net \
--cc=dw@davidwei.uk \
--cc=kuba@kernel.org \
--cc=netdev@vger.kernel.org \
--cc=razor@blackwall.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox