Skip to content

Commit fe0d111

Browse files
idoschgregkh
authored andcommitted
mlxsw: spectrum_switchdev: Do not leak RIFs when removing bridge
[ Upstream commit 602b74e ] When a bridge device is removed, the VLANs are flushed from each configured port. This causes the ports to decrement the reference count on the associated FIDs (filtering identifier). If the reference count of a FID is 1 and it has a RIF (router interface), then this RIF is destroyed. However, if no port is member in the VLAN for which a RIF exists, then the RIF will continue to exist after the removal of the bridge. To reproduce: # ip link add name br0 type bridge vlan_filtering 1 # ip link set dev swp1 master br0 # ip link add link br0 name br0.10 type vlan id 10 # ip address add 192.0.2.0/24 dev br0.10 # ip link del dev br0 The RIF associated with br0.10 continues to exist. Fix this by iterating over all the bridge device uppers when it is destroyed and take care of destroying their RIFs. Fixes: 99f44bb ("mlxsw: spectrum: Enable L3 interfaces on top of bridge devices") Signed-off-by: Ido Schimmel <[email protected]> Reviewed-by: Petr Machata <[email protected]> Signed-off-by: David S. Miller <[email protected]> Signed-off-by: Greg Kroah-Hartman <[email protected]>
1 parent 3c035a4 commit fe0d111

File tree

3 files changed

+33
-0
lines changed

3 files changed

+33
-0
lines changed

drivers/net/ethernet/mellanox/mlxsw/spectrum.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -395,6 +395,8 @@ int mlxsw_sp_netdevice_vrf_event(struct net_device *l3_dev, unsigned long event,
395395
void
396396
mlxsw_sp_port_vlan_router_leave(struct mlxsw_sp_port_vlan *mlxsw_sp_port_vlan);
397397
void mlxsw_sp_rif_destroy(struct mlxsw_sp_rif *rif);
398+
void mlxsw_sp_rif_destroy_by_dev(struct mlxsw_sp *mlxsw_sp,
399+
struct net_device *dev);
398400

399401
/* spectrum_kvdl.c */
400402
int mlxsw_sp_kvdl_alloc(struct mlxsw_sp *mlxsw_sp, unsigned int entry_count,

drivers/net/ethernet/mellanox/mlxsw/spectrum_router.c

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5131,6 +5131,17 @@ void mlxsw_sp_rif_destroy(struct mlxsw_sp_rif *rif)
51315131
mlxsw_sp_vr_put(vr);
51325132
}
51335133

5134+
void mlxsw_sp_rif_destroy_by_dev(struct mlxsw_sp *mlxsw_sp,
5135+
struct net_device *dev)
5136+
{
5137+
struct mlxsw_sp_rif *rif;
5138+
5139+
rif = mlxsw_sp_rif_find_by_dev(mlxsw_sp, dev);
5140+
if (!rif)
5141+
return;
5142+
mlxsw_sp_rif_destroy(rif);
5143+
}
5144+
51345145
static void
51355146
mlxsw_sp_rif_subport_params_init(struct mlxsw_sp_rif_params *params,
51365147
struct mlxsw_sp_port_vlan *mlxsw_sp_port_vlan)

drivers/net/ethernet/mellanox/mlxsw/spectrum_switchdev.c

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,24 @@ bool mlxsw_sp_bridge_device_is_offloaded(const struct mlxsw_sp *mlxsw_sp,
140140
return !!mlxsw_sp_bridge_device_find(mlxsw_sp->bridge, br_dev);
141141
}
142142

143+
static int mlxsw_sp_bridge_device_upper_rif_destroy(struct net_device *dev,
144+
void *data)
145+
{
146+
struct mlxsw_sp *mlxsw_sp = data;
147+
148+
mlxsw_sp_rif_destroy_by_dev(mlxsw_sp, dev);
149+
return 0;
150+
}
151+
152+
static void mlxsw_sp_bridge_device_rifs_destroy(struct mlxsw_sp *mlxsw_sp,
153+
struct net_device *dev)
154+
{
155+
mlxsw_sp_rif_destroy_by_dev(mlxsw_sp, dev);
156+
netdev_walk_all_upper_dev_rcu(dev,
157+
mlxsw_sp_bridge_device_upper_rif_destroy,
158+
mlxsw_sp);
159+
}
160+
143161
static struct mlxsw_sp_bridge_device *
144162
mlxsw_sp_bridge_device_create(struct mlxsw_sp_bridge *bridge,
145163
struct net_device *br_dev)
@@ -176,6 +194,8 @@ static void
176194
mlxsw_sp_bridge_device_destroy(struct mlxsw_sp_bridge *bridge,
177195
struct mlxsw_sp_bridge_device *bridge_device)
178196
{
197+
mlxsw_sp_bridge_device_rifs_destroy(bridge->mlxsw_sp,
198+
bridge_device->dev);
179199
list_del(&bridge_device->list);
180200
if (bridge_device->vlan_enabled)
181201
bridge->vlan_enabled_exists = false;

0 commit comments

Comments
 (0)