Netdev List
 help / color / mirror / Atom feed
From: Jakub Kicinski <kuba@kernel.org>
To: michael.dege@renesas.com
Cc: Jakub Kicinski <kuba@kernel.org>,
	yoshihiro.shimoda.uh@renesas.com, andrew+netdev@lunn.ch,
	davem@davemloft.net, edumazet@google.com, pabeni@redhat.com,
	niklas.soderlund@ragnatech.se, paul@pbarker.dev,
	richardcochran@gmail.com, netdev@vger.kernel.org,
	linux-renesas-soc@vger.kernel.org, linux-kernel@vger.kernel.org
Subject: Re: [PATCH net-next v5 05/14] net: renesas: rswitch: add exception path for packets with unknown dst MAC
Date: Mon, 25 May 2026 13:41:10 -0700	[thread overview]
Message-ID: <20260525204110.2471291-1-kuba@kernel.org> (raw)
In-Reply-To: <20260522-rswitch_add_vlans-v5-5-53589d944a9f@renesas.com>

This is an AI-generated review of your patch. The human sending this
email has considered the AI review valid, or at least plausible.
---
net: renesas: rswitch: add exception path for packets with unknown dst MAC

Packets with unknown MAC address cannot be handled by the HW forwarding.
Creates an exception path with a shared queue to forward these packets to
the network driver for MAC learning.

> diff --git a/drivers/net/ethernet/renesas/rswitch_main.c b/drivers/net/ethernet/renesas/rswitch_main.c
> index 9510bcdf9e830..1f4ec65f6f9bd 100644
> --- a/drivers/net/ethernet/renesas/rswitch_main.c
> +++ b/drivers/net/ethernet/renesas/rswitch_main.c
[ ... ]
> @@ -736,6 +772,8 @@ static int rswitch_gwca_hw_deinit(struct rswitch_private *priv)
>  	if (err < 0)
>  		return err;
>  

[Severity: Medium]
Will this leak the shared RX queue memory if rswitch_gwca_change_mode() fails
during teardown and returns early?

> +	rswitch_shared_rx_queue_free(priv);
> +
>  	return rswitch_gwca_change_mode(priv, GWMC_OPC_DISABLE);
>  }
[ ... ]
> @@ -944,10 +982,15 @@ static int rswitch_poll(struct napi_struct *napi, int budget)
>  
>  	if (napi_complete_done(napi, budget - quota)) {
>  		spin_lock_irqsave(&priv->lock, flags);
> +		if (rdev->rx_old_queue) {
> +			rdev->rx_queue = rdev->rx_old_queue;
> +			rdev->rx_old_queue = NULL;
> +		}
>  		if (test_bit(rdev->port, priv->opened_ports)) {
>  			rswitch_enadis_data_irq(priv, rdev->tx_queue->index, true);
>  			rswitch_enadis_data_irq(priv, rdev->rx_queue->index, true);
>  		}
> +		rswitch_enadis_data_irq(priv, priv->gwca.l2_shared_rx_queue->index, true);

[Severity: Critical]
Does unmasking the shared RX queue globally here create a race condition?

If Port A completes NAPI while Port B's NAPI is still actively polling the
shared queue, couldn't another interrupt fire, scheduling another NAPI and
resulting in multiple NAPIs running concurrently on the same shared queue?

This might cause lockless concurrent modifications to gq->cur and gq->dirty,
leading to list corruption.

>  		spin_unlock_irqrestore(&priv->lock, flags);
>  	}
>  
[ ... ]
> @@ -960,15 +1003,41 @@ static int rswitch_poll(struct napi_struct *napi, int budget)
>  	return 0;
>  }
>  
> -static void rswitch_queue_interrupt(struct net_device *ndev)
> +static void rswitch_queue_interrupt(struct rswitch_private *priv, struct rswitch_gwca_queue *gq)
>  {
> -	struct rswitch_device *rdev = netdev_priv(ndev);
> +	struct rswitch_ext_ts_desc *desc;
> +	struct rswitch_device *rdev;
> +	struct net_device *ndev;
> +	unsigned long flags;
> +	u32 spn;
> +
> +	/* If we receive a shared queue through the exception path, it will be missing the ndev
> +	 * pointer. This needs to be added to be able to determine from which port the packet was
> +	 * received. Then we temporarily exchange the rx_queue pointer in rdev. This will be
> +	 * restored after the packet has been processed.
> +	 */
> +
> +	if (gq->index == priv->gwca.l2_shared_rx_queue->index) {
> +		desc = &gq->rx_ring[gq->cur];
> +		spn = FIELD_GET(SPN, le64_to_cpu(desc->info1));

[Severity: Medium]
Could this read stale or garbage data from the descriptor?

It appears to read the DMA descriptor without verifying that the hardware
has handed ownership back to the CPU (e.g., checking DT_FEMPTY) and without
a dma_rmb() barrier before the read.

[Severity: High]
Is it possible for the hardware to provide an out-of-bounds SPN value here?

Since spn is used to index priv->rdev[] on the next line, an unexpected or
corrupted value might cause an out-of-bounds memory access.

> +		ndev = priv->rdev[spn]->ndev;
> +		rdev = netdev_priv(ndev);
> +		gq->ndev = ndev;

[Severity: High]
Since the shared queue collects exception packets from all ports, will this
assign the entire queue to the NAPI of the first packet's port?

When NAPI polls and drains the queue, it seems subsequent packets might be
injected into the network stack under the first packet's ndev, even if they
originated from different physical ports.

> +		/* store original rx_queue */
> +		spin_lock_irqsave(&priv->lock, flags);
> +		rdev->rx_old_queue = rdev->rx_queue;
> +		rdev->rx_queue = gq;

[Severity: High]
Can rdev->rx_old_queue be permanently overwritten with the shared queue
pointer here?

If a second shared queue interrupt fires before NAPI completes and restores
the pointer, the handler will execute this path again and overwrite the
saved normal queue pointer with gq, leaking the normal RX queue.

> +		spin_unlock_irqrestore(&priv->lock, flags);
> +	} else {
> +		rdev = netdev_priv(gq->ndev);
> +	}
>  
>  	if (napi_schedule_prep(&rdev->napi)) {
> -		spin_lock(&rdev->priv->lock);
> -		rswitch_enadis_data_irq(rdev->priv, rdev->tx_queue->index, false);
> -		rswitch_enadis_data_irq(rdev->priv, rdev->rx_queue->index, false);
> -		spin_unlock(&rdev->priv->lock);
> +		spin_lock(&priv->lock);
> +		rswitch_enadis_data_irq(priv, rdev->tx_queue->index, false);
> +		rswitch_enadis_data_irq(priv, rdev->rx_queue->index, false);
> +		rswitch_enadis_data_irq(priv, priv->gwca.l2_shared_rx_queue->index, false);

[Severity: Critical]
If napi_schedule_prep() returns false (because the target NAPI is already
running), hardware interrupts are not disabled. Could this lead to an
immediate interrupt storm for the shared RX queue?

> +		spin_unlock(&priv->lock);
>  		__napi_schedule(&rdev->napi);
>  	}
>  }
[ ... ]
> @@ -1653,6 +1733,11 @@ static int rswitch_stop(struct net_device *ndev)
>  	rswitch_enadis_data_irq(rdev->priv, rdev->tx_queue->index, false);
>  	rswitch_enadis_data_irq(rdev->priv, rdev->rx_queue->index, false);
>  	bitmap_clear(rdev->priv->opened_ports, rdev->port, 1);
> +	if (bitmap_empty(rdev->priv->opened_ports, 1))

[Severity: High]
Does this check use the wrong size argument?

The second argument to bitmap_empty() is nbits. By passing 1, it seems it
only checks if bit 0 is empty. If port 0 is closed while other ports are
open, this would evaluate to true and prematurely disable the shared RX
queue interrupt for the remaining active ports.

> +		rswitch_enadis_data_irq(rdev->priv,
> +					rdev->priv->gwca.l2_shared_rx_queue->index,
> +					false);
> +
>  	spin_unlock_irqrestore(&rdev->priv->lock, flags);
>  
>  	napi_disable(&rdev->napi);

  reply	other threads:[~2026-05-25 20:41 UTC|newest]

Thread overview: 27+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-05-22 12:12 [net-next PATCH v5 00/14] net: renesas: rswitch: R-Car S4 add VLAN aware switching Michael Dege
2026-05-22 12:12 ` [PATCH net-next v5 01/14] net: renesas: rswitch: improve port change mode functions Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 02/14] net: renesas: rswitch: use device instead of net_device Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 03/14] net: renesas: rswitch: fix FWPC2 register access macros Michael Dege
2026-05-22 12:12 ` [PATCH net-next v5 04/14] net: renesas: rswitch: add register definitions for vlan support Michael Dege
2026-05-22 12:12 ` [PATCH net-next v5 05/14] net: renesas: rswitch: add exception path for packets with unknown dst MAC Michael Dege
2026-05-25 20:41   ` Jakub Kicinski [this message]
2026-05-22 12:12 ` [PATCH net-next v5 06/14] net: renesas: rswitch: add forwarding rules for gwca Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 07/14] net: renesas: rswitch: make helper functions available to whole driver Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 08/14] net: renesas: rswitch: add locking for agent clock control Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 09/14] net: renesas: rswitch: add basic vlan init to rswitch_fwd_init Michael Dege
2026-05-22 12:12 ` [PATCH net-next v5 10/14] net: renesas: rswitch: update port HW init Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 11/14] net: renesas: rswitch: clean up is_rdev rswitch_device checking Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 12/14] net: renesas: rswitch: add passing of rswitch_private into notifiers Michael Dege
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 13/14] net: renesas: rswitch: add handler for FDB notification Michael Dege
2026-05-25 20:40   ` Jakub Kicinski
2026-05-25 20:41   ` Jakub Kicinski
2026-05-22 12:12 ` [PATCH net-next v5 14/14] net: renesas: rswitch: add vlan aware switching Michael Dege
2026-05-25 20:41   ` Jakub Kicinski

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=20260525204110.2471291-1-kuba@kernel.org \
    --to=kuba@kernel.org \
    --cc=andrew+netdev@lunn.ch \
    --cc=davem@davemloft.net \
    --cc=edumazet@google.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-renesas-soc@vger.kernel.org \
    --cc=michael.dege@renesas.com \
    --cc=netdev@vger.kernel.org \
    --cc=niklas.soderlund@ragnatech.se \
    --cc=pabeni@redhat.com \
    --cc=paul@pbarker.dev \
    --cc=richardcochran@gmail.com \
    --cc=yoshihiro.shimoda.uh@renesas.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