From: Daniel Machon <daniel.machon@microchip.com>
To: <netdev-bot+sashiko@kernel.org>
Cc: <andrew+netdev@lunn.ch>, <davem@davemloft.net>,
<edumazet@google.com>, <kuba@kernel.org>, <pabeni@redhat.com>,
<horatiu.vultur@microchip.com>, <steen.hegelund@microchip.com>,
<UNGLinuxDriver@microchip.com>, <ast@kernel.org>,
<daniel@iogearbox.net>, <hawk@kernel.org>,
<john.fastabend@gmail.com>, <sdf@fomichev.me>,
<herve.codina@bootlin.com>, <arnd@arndb.de>,
<gregkh@linuxfoundation.org>, <mohsin.bashr@gmail.com>,
<horms@kernel.org>, <richardcochran@gmail.com>,
<netdev@vger.kernel.org>, <linux-kernel@vger.kernel.org>,
<bpf@vger.kernel.org>, <linux-arm-kernel@lists.infradead.org>
Subject: Re: [PATCH net-next v8 13/15] net: lan966x: add PCIe FDMA XDP support
Date: Mon, 28 Sep 2026 13:02:18 +0200 [thread overview]
Message-ID: <20260928110218.ktlj26jtyakuywio@DEN-DL-M70577> (raw)
In-Reply-To: <179036955220.2160803.7046320782670912992@kernel.org>
> Thank you for your contribution! Sashiko AI review found 3 potential
> issue(s) to consider.
>
> Critical: 1 · High: 0 · Medium: 2 · Low: 0
>
> If you believe none of the issues are legitimate, please reply to each
> issue of Medium severity or higher and explain why the AI is wrong.
> If any of them are legitimate and you plan to respin, please let patchwork
> know by including "pw-bot: cr" as a separate line at the end of your reply
> (one such reply per series is enough).
>
> - [Critical] Use-after-free and double free on the PCIe RX path when an
> XDP program shrinks a frame.
> - [Medium] On the PCIe path the driver accepts XDP but cannot handle
> XDP_REDIRECT, and the bond driver cannot tell.
> - [Medium] In lan966x_fdma_pci_napi_poll(), a poll that consumes all
> FDMA_PCI_DCB_MAX (256) RX descriptors never re-arms any of them.
>
> --
>
> net: lan966x: add PCIe FDMA XDP support
>
> This commit adds basic XDP support (XDP_PASS, XDP_DROP, XDP_TX) to the
> lan966x PCIe FDMA path. The IFH and FCS are stripped before the program
> runs, and the pointer and length from after XDP are passed on to skb
> construction or to a new memcpy-based XDP_TX routine.
> lan966x_xdp_setup() now accepts programs on PCIe and skips the page_pool
> reload there.
>
> > diff --git a/drivers/net/ethernet/microchip/lan966x/lan966x_fdma_pci.c b/drivers/net/ethernet/microchip/lan966x/lan966x_fdma_pci.c
> > index 7185e65dda435..216e9cbcd1580 100644
> > --- a/drivers/net/ethernet/microchip/lan966x/lan966x_fdma_pci.c
> > +++ b/drivers/net/ethernet/microchip/lan966x/lan966x_fdma_pci.c
>
> [ ... ]
>
> > +static int lan966x_xdp_pci_run(struct lan966x_port *port, void *data,
> > + u32 data_len, void **xdp_data, u32 *xdp_len)
> > +{
>
> [ ... ]
>
> > + act = bpf_prog_run_xdp(xdp_prog, &xdp);
> > +
> > + *xdp_data = xdp.data;
> > + *xdp_len = xdp.data_end - xdp.data;
> > +
> > + switch (act) {
> > + case XDP_PASS:
> > + return FDMA_PASS;
> > + case XDP_TX:
> > + return lan966x_fdma_pci_xmit_xdpf(port, *xdp_data, *xdp_len) ?
> > + FDMA_DROP : FDMA_TX;
> > + default:
> > + bpf_warn_invalid_xdp_action(port->dev, xdp_prog, act);
> > + fallthrough;
>
> [Severity: Medium]
> What happens here when the PCIe port is a bond slave?
>
> The PCIe ports use the same lan966x_port_netdev_ops as the platform
> ports, so both .ndo_bpf and .ndo_xdp_xmit are set. bond_xdp_set() looks
> only at those pointers and never reads xdp_features:
>
> drivers/net/bonding/bond_main.c:bond_xdp_set() {
> ...
> if (!slave_dev->netdev_ops->ndo_bpf ||
> !slave_dev->netdev_ops->ndo_xdp_xmit) {
> ...
> }
>
> This patch removes the -EOPNOTSUPP return for PCIe in
> lan966x_xdp_setup(), so a bond with a lan966x PCIe slave can now install
> its program on that slave. For bond slaves, bpf_prog_run_xdp() can then
> turn XDP_TX into XDP_REDIRECT:
>
> net/core/filter.c:xdp_master_redirect() {
> ...
> if (slave && slave != xdp->rxq->dev) {
> ri->tgt_index = slave->ifindex;
> ri->map_id = INT_MAX;
> ri->map_type = BPF_MAP_TYPE_UNSPEC;
> return XDP_REDIRECT;
> ...
> }
>
> It can also return XDP_ABORTED when the master is down.
>
> This switch has no XDP_REDIRECT case. Would those frames go to the
> default branch, log a "Driver unsupported" warning and be dropped?
> Nothing calls xdp_do_redirect(), so the redirect info set by
> xdp_master_redirect() would never be used.
Re-raise of dismissed issue in v7.
>
> [ ... ]
>
> > static struct sk_buff *lan966x_fdma_pci_rx_get_frame(struct lan966x_rx *rx,
> > - u64 src_port)
> > + u64 src_port, void *data,
> > + u32 data_len)
> > {
>
> [ ... ]
>
> > - memcpy(skb->data,
> > - fdma_dataptr_virt_addr_contiguous(fdma,
> > - fdma->dcb_index,
> > - fdma->db_index),
> > - data_len);
> > + memcpy(skb->data, data, data_len);
> >
> > skb_put(skb, data_len);
> >
> > skb->dev = lan966x->ports[src_port]->dev;
> > - skb_pull(skb, IFH_LEN_BYTES);
> > -
> > - skb_trim(skb, skb->len - ETH_FCS_LEN);
> >
> > skb->protocol = eth_type_trans(skb, skb->dev);
>
> [Severity: Critical]
> Can this lead to a use-after-free when an XDP program shrinks the frame?
>
> data_len is now the length from after XDP, returned by
> lan966x_xdp_pci_run(). bpf_xdp_adjust_tail() and bpf_xdp_adjust_head()
> let it shrink to ETH_HLEN. Take a 14-byte frame with h_proto 0x8100
> that returns XDP_PASS. eth_type_trans() then leaves skb->len == 0 and
> skb->protocol == ETH_P_8021Q.
>
> Now suppose src_port is in bridge_mask and IGMP/MLD redirect is enabled
> in ANA_CPU_FWD_CFG. lan966x_port_mc_set() enables it when multicast
> snooping is on, and snooping is on by default. In that case the code
> after this point reaches:
>
> drivers/net/ethernet/microchip/lan966x/lan966x_main.c:lan966x_hw_offload() {
> ...
> if (eth_type_vlan(skb->protocol)) {
> skb = skb_vlan_untag(skb);
> if (unlikely(!skb))
> return false;
> }
> ...
> }
>
> pskb_may_pull(skb, VLAN_HLEN + 2) fails in skb_vlan_untag(), so it
> frees the skb with kfree_skb() and returns NULL. lan966x_hw_offload()
> only returns a bool, so the caller still holds the freed pointer:
>
> if (!lan966x_hw_offload(lan966x, src_port, skb))
> skb->offload_fwd_mark = 0;
> }
>
> skb->dev->stats.rx_bytes += skb->len;
>
> The freed skb is then returned to lan966x_fdma_pci_napi_poll(), which
> passes it to napi_gro_receive(). Would that be a use-after-free followed
> by a double free?
>
> The problem in lan966x_hw_offload() is older. Before this patch it could
> not be reached, because skbs were built from the hardware length and the
> MAC drops runts. The frame contents can also come from the network, for
> example when a decap program uses adjust_head on a minimum-size outer
> frame.
A VLAN-tag frame arrives on a bridged port, with IGMP/MLD snooping enabled. That
same port has an XDP program that shrinks the frame to ETH_HLEN and returns
XDP_PASS. AFAICT, yes, that will result in UAF.
Agree that the problem is lan966x_hw_offload, which can potentially free the
skb, without letting the caller know. This function is pre-existing and used in
the platform path, but the UAF can never happen there, because the frame length
is guarded, and the post-program length is not used at all.
Since there is no live bug in the platform path today, this should, IMO, be a
preparatory commit in this series, that refactors the lan966x_hw_offload()
function to let the caller know the skb was freed.
>
> [ ... ]
>
> > @@ -312,8 +430,17 @@ static int lan966x_fdma_pci_napi_poll(struct napi_struct *napi, int weight)
> > */
> > fdma_dcb_advance(fdma);
> > continue;
> > + case FDMA_TX:
> > + fdma_dcb_advance(fdma);
> > + continue;
> > + case FDMA_DROP:
> > + fdma_dcb_advance(fdma);
> > + continue;
> > }
>
> [Severity: Medium]
> What happens if one poll consumes all 256 (FDMA_PCI_DCB_MAX) RX
> descriptors?
>
> Every result path calls fdma_dcb_advance(), which wraps at n_dcbs. After
> 256 frames, dcb_index is back at the value saved in dcb_reload. The
> re-arm loop at the end of lan966x_fdma_pci_napi_poll() then runs zero
> times:
>
> while (dcb_reload != fdma->dcb_index) {
> old_dcb = dcb_reload;
> dcb_reload++;
> dcb_reload &= fdma->n_dcbs - 1;
>
> So none of the consumed DCBs are re-armed, and they all keep
> FDMA_DCB_STATUS_DONE. With a budget above 256, fdma_has_frames() stays
> true and the same frames are processed again in the same call. With a
> budget of exactly 256, the next poll processes them again.
>
> Would this deliver stale frames twice, run XDP on them again, and resend
> the XDP_TX frames?
>
> Only the budget bounds the loop. __napi_busy_loop() passes the socket's
> SO_BUSY_POLL_BUDGET straight to napi_poll(), and that value can be up to
> U16_MAX with CAP_NET_ADMIN. The ring can fill completely, because the
> hardware fills the last DCB before it stops on the invalid nextptr.
>
> This loop was added by the earlier "net: lan966x: add PCIe FDMA support"
> commit in this series. This patch extends it with the XDP_TX and
> XDP_DROP results, and it does not seem to be fixed later in the series.
> The platform lan966x_fdma_napi_poll() has the same pattern with 512
> DCBs.
Re-raise of dismissed issue in v7.
>
> --
> Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/20260924-lan966x-pci-fdma-v8-0-201c7b707d8b%40microchip.com
pw-bot: cr
next prev parent reply other threads:[~2026-09-28 11:02 UTC|newest]
Thread overview: 25+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-09-24 19:56 [PATCH net-next v8 00/15] net: lan966x: add support for PCIe FDMA Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 01/15] MAINTAINERS: add FDMA library to Sparx5 SoC entry Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 02/15] net: microchip: fdma: rename contiguous dataptr helpers Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 03/15] net: microchip: fdma: add PCIe ATU support Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:56 ` [PATCH net-next v8 04/15] net: microchip: fdma: use little-endian types for descriptor fields Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 05/15] net: lan966x: add FDMA LLP register write helper Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 06/15] net: lan966x: export FDMA helpers for reuse Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 07/15] net: lan966x: use a dedicated device for DMA operations Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 08/15] net: lan966x: add FDMA ops dispatch for PCIe support Daniel Machon
2026-09-24 19:56 ` [PATCH net-next v8 09/15] net: lan966x: clear FDMA interrupt stickies after switch reset Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:56 ` [PATCH net-next v8 10/15] net: lan966x: add shutdown callback to stop the FDMA on reboot Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:56 ` [PATCH net-next v8 11/15] net: lan966x: add PCIe FDMA support Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:57 ` [PATCH net-next v8 12/15] net: lan966x: add PCIe FDMA MTU change support Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:57 ` [PATCH net-next v8 13/15] net: lan966x: add PCIe FDMA XDP support Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-28 11:02 ` Daniel Machon [this message]
2026-09-24 19:57 ` [PATCH net-next v8 14/15] misc: lan966x-pci: dts: extend cpu reg to cover PCIE DBI space Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
2026-09-24 19:57 ` [PATCH net-next v8 15/15] misc: lan966x-pci: dts: add fdma interrupt to overlay Daniel Machon
2026-09-25 20:52 ` netdev-bot+sashiko
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=20260928110218.ktlj26jtyakuywio@DEN-DL-M70577 \
--to=daniel.machon@microchip.com \
--cc=UNGLinuxDriver@microchip.com \
--cc=andrew+netdev@lunn.ch \
--cc=arnd@arndb.de \
--cc=ast@kernel.org \
--cc=bpf@vger.kernel.org \
--cc=daniel@iogearbox.net \
--cc=davem@davemloft.net \
--cc=edumazet@google.com \
--cc=gregkh@linuxfoundation.org \
--cc=hawk@kernel.org \
--cc=herve.codina@bootlin.com \
--cc=horatiu.vultur@microchip.com \
--cc=horms@kernel.org \
--cc=john.fastabend@gmail.com \
--cc=kuba@kernel.org \
--cc=linux-arm-kernel@lists.infradead.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mohsin.bashr@gmail.com \
--cc=netdev-bot+sashiko@kernel.org \
--cc=netdev@vger.kernel.org \
--cc=pabeni@redhat.com \
--cc=richardcochran@gmail.com \
--cc=sdf@fomichev.me \
--cc=steen.hegelund@microchip.com \
/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