From: Ido Schimmel <idosch@nvidia.com>
To: "Linus Lüssing" <linus.luessing@c0d3.blue>
Cc: bridge@lists.linux.dev, netdev@vger.kernel.org,
linux-kernel@vger.kernel.org,
Nikolay Aleksandrov <razor@blackwall.org>,
Andrew Lunn <andrew+netdev@lunn.ch>,
Simon Horman <horms@kernel.org>, Paolo Abeni <pabeni@redhat.com>,
Jakub Kicinski <kuba@kernel.org>,
Eric Dumazet <edumazet@google.com>,
"David S . Miller" <davem@davemloft.net>,
Kuniyuki Iwashima <kuniyu@google.com>,
Stanislav Fomichev <sdf@fomichev.me>,
Xiao Liang <shaw.leon@gmail.com>
Subject: Re: [PATCH net-next v2 03/14] net: bridge: mcast: avoid sleeping on bridge-down
Date: Sun, 8 Feb 2026 18:01:43 +0200 [thread overview]
Message-ID: <20260208160143.GC154003@shredder> (raw)
In-Reply-To: <20260206030123.5430-4-linus.luessing@c0d3.blue>
On Fri, Feb 06, 2026 at 03:52:09AM +0100, Linus Lüssing wrote:
> We later want to use the multicast lock when setting the bridge
> interface up or down, to be able to atomically both check all conditions
> to toggle the multicast active state and to subsequently toggle it.
> While most variables we check / contexts we check from are serialized
> (toggled variables through netlink/sysfs) the timer_pending() check is
> not and might run in parallel.
>
> However so far we are not allowed to spinlock __br_multicast_stop() as
> its call to timer_delete_sync() might sleep. Therefore replacing the
> sleeping variant with the non-sleeping one. It is sufficient to only
> wait for any timer callback to finish when we are freeing the multicast
> context.
>
> Using the timer_shutdown() instead of the timer_delete() variant also
> allows us to detect that we are stopping from within the according timer
> callbacks, to retain the promise of the previous timer_delete_sync()
> calls that no multicast state is changed after these
> timer_{delete,shutdown}*() calls. And more importantly that we are not
> inadvertently rearming timers.
Can you clarify what you mean by "allows us to detect that we are
stopping from within the according timer callbacks"?
>
> This new check also makes the netif_running() check redundant/obsolete
> in these contexts.
>
> Signed-off-by: Linus Lüssing <linus.luessing@c0d3.blue>
> ---
> net/bridge/br_device.c | 4 ++
> net/bridge/br_multicast.c | 108 ++++++++++++++++++++++++++------------
> net/bridge/br_private.h | 5 ++
> net/bridge/br_vlan.c | 5 ++
> 4 files changed, 87 insertions(+), 35 deletions(-)
>
> diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c
> index a818fdc22da9..d9d1227d5708 100644
> --- a/net/bridge/br_device.c
> +++ b/net/bridge/br_device.c
> @@ -168,7 +168,9 @@ static int br_dev_open(struct net_device *dev)
> netdev_update_features(dev);
> netif_start_queue(dev);
> br_stp_enable_bridge(br);
> + spin_lock_bh(&br->multicast_lock);
> br_multicast_open(br);
Maybe move the spin_lock_bh() / spin_unlock_bh() to br_multicast_open()
and have it call br_multicast_open_locked() that will also be invoked
from br_multicast_toggle()?
> + spin_unlock_bh(&br->multicast_lock);
>
> if (br_opt_get(br, BROPT_MULTICAST_ENABLED))
> br_multicast_join_snoopers(br);
> @@ -191,7 +193,9 @@ static int br_dev_stop(struct net_device *dev)
> struct net_bridge *br = netdev_priv(dev);
>
> br_stp_disable_bridge(br);
> + spin_lock_bh(&br->multicast_lock);
> br_multicast_stop(br);
And like br_multicast_open(), move the locking into br_multicast_stop()?
> + spin_unlock_bh(&br->multicast_lock);
>
> if (br_opt_get(br, BROPT_MULTICAST_ENABLED))
> br_multicast_leave_snoopers(br);
> diff --git a/net/bridge/br_multicast.c b/net/bridge/br_multicast.c
> index dccae08b4f4c..f5a368dd20a3 100644
> --- a/net/bridge/br_multicast.c
> +++ b/net/bridge/br_multicast.c
> @@ -1665,6 +1665,14 @@ static void br_multicast_router_expired(struct net_bridge_mcast_port *pmctx,
> spin_unlock(&br->multicast_lock);
> }
>
> +static bool br_multicast_stopping(struct net_bridge *br,
Nit: br_multicast_is_stopping() ?
> + struct timer_list *timer)
> +{
> + lockdep_assert_held_once(&br->multicast_lock);
> +
> + return !timer->function;
> +}
next prev parent reply other threads:[~2026-02-08 16:01 UTC|newest]
Thread overview: 35+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-02-06 2:52 [PATCH net-next v2 00/14] net: bridge: reduce multicast checks in fast path Linus Lüssing
2026-02-06 2:52 ` [PATCH net-next v2 01/14] net: bridge: mcast: export ip{4,6}_active state to netlink Linus Lüssing
2026-02-08 16:00 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 02/14] net: bridge: mcast: track active state, adding tests Linus Lüssing
2026-02-07 4:58 ` Jakub Kicinski
2026-02-08 16:00 ` Ido Schimmel
2026-02-10 21:06 ` Linus Lüssing
2026-02-11 9:42 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 03/14] net: bridge: mcast: avoid sleeping on bridge-down Linus Lüssing
2026-02-08 11:41 ` Ido Schimmel
2026-02-08 16:01 ` Ido Schimmel [this message]
2026-02-06 2:52 ` [PATCH net-next v2 04/14] net: bridge: mcast: track active state, IGMP/MLD querier appearance Linus Lüssing
2026-02-08 16:07 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 05/14] net: bridge: mcast: track active state, foreign IGMP/MLD querier disappearance Linus Lüssing
2026-02-07 4:56 ` [net-next,v2,05/14] " Jakub Kicinski
2026-02-11 3:05 ` Linus Lüssing
2026-02-08 16:08 ` [PATCH net-next v2 05/14] " Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 06/14] net: bridge: mcast: track active state, IPv6 address availability Linus Lüssing
2026-02-08 16:08 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 07/14] net: bridge: mcast: track active state, own MLD querier disappearance Linus Lüssing
2026-02-08 16:09 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 08/14] net: bridge: mcast: track active state, if snooping is enabled Linus Lüssing
2026-02-08 16:09 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 09/14] net: bridge: mcast: track active state, VLAN snooping Linus Lüssing
2026-02-08 16:10 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 10/14] net: bridge: mcast: track active state, bridge up/down Linus Lüssing
2026-02-08 16:10 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 11/14] net: bridge: mcast: track active state, prepare for outside lock reads Linus Lüssing
2026-02-08 16:11 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 12/14] net: bridge: mcast: use combined active state in netlink Linus Lüssing
2026-02-08 16:11 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 13/14] net: bridge: mcast: use combined active state in fast/data path Linus Lüssing
2026-02-08 16:12 ` Ido Schimmel
2026-02-06 2:52 ` [PATCH net-next v2 14/14] net: bridge: mcast: add inactive state assertions Linus Lüssing
2026-02-08 16:13 ` Ido Schimmel
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=20260208160143.GC154003@shredder \
--to=idosch@nvidia.com \
--cc=andrew+netdev@lunn.ch \
--cc=bridge@lists.linux.dev \
--cc=davem@davemloft.net \
--cc=edumazet@google.com \
--cc=horms@kernel.org \
--cc=kuba@kernel.org \
--cc=kuniyu@google.com \
--cc=linus.luessing@c0d3.blue \
--cc=linux-kernel@vger.kernel.org \
--cc=netdev@vger.kernel.org \
--cc=pabeni@redhat.com \
--cc=razor@blackwall.org \
--cc=sdf@fomichev.me \
--cc=shaw.leon@gmail.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.