Commit 2a26028d authored by Andrew Lunn's avatar Andrew Lunn Committed by David S. Miller

net: bridge: Send notification when host join/leaves a group

The host can join or leave a multicast group on the brX interface, as
indicated by IGMP snooping.  This is tracked within the bridge
multicast code. Send a notification when this happens, in the same way
a notification is sent when a port of the bridge joins/leaves a group
because of IGMP snooping.
Signed-off-by: default avatarAndrew Lunn <andrew@lunn.ch>
Acked-by: default avatarNikolay Aleksandrov <nikolay@cumulusnetworks.com>
Acked-by: default avatarFlorian Fainelli <f.fainelli@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent ff0fd34e
...@@ -317,7 +317,7 @@ static void __br_mdb_notify(struct net_device *dev, struct net_bridge_port *p, ...@@ -317,7 +317,7 @@ static void __br_mdb_notify(struct net_device *dev, struct net_bridge_port *p,
#endif #endif
mdb.obj.orig_dev = port_dev; mdb.obj.orig_dev = port_dev;
if (port_dev && type == RTM_NEWMDB) { if (p && port_dev && type == RTM_NEWMDB) {
complete_info = kmalloc(sizeof(*complete_info), GFP_ATOMIC); complete_info = kmalloc(sizeof(*complete_info), GFP_ATOMIC);
if (complete_info) { if (complete_info) {
complete_info->port = p; complete_info->port = p;
...@@ -327,7 +327,7 @@ static void __br_mdb_notify(struct net_device *dev, struct net_bridge_port *p, ...@@ -327,7 +327,7 @@ static void __br_mdb_notify(struct net_device *dev, struct net_bridge_port *p,
if (switchdev_port_obj_add(port_dev, &mdb.obj)) if (switchdev_port_obj_add(port_dev, &mdb.obj))
kfree(complete_info); kfree(complete_info);
} }
} else if (port_dev && type == RTM_DELMDB) { } else if (p && port_dev && type == RTM_DELMDB) {
switchdev_port_obj_del(port_dev, &mdb.obj); switchdev_port_obj_del(port_dev, &mdb.obj);
} }
...@@ -353,7 +353,10 @@ void br_mdb_notify(struct net_device *dev, struct net_bridge_port *port, ...@@ -353,7 +353,10 @@ void br_mdb_notify(struct net_device *dev, struct net_bridge_port *port,
struct br_mdb_entry entry; struct br_mdb_entry entry;
memset(&entry, 0, sizeof(entry)); memset(&entry, 0, sizeof(entry));
if (port)
entry.ifindex = port->dev->ifindex; entry.ifindex = port->dev->ifindex;
else
entry.ifindex = dev->ifindex;
entry.addr.proto = group->proto; entry.addr.proto = group->proto;
entry.addr.u.ip4 = group->u.ip4; entry.addr.u.ip4 = group->u.ip4;
#if IS_ENABLED(CONFIG_IPV6) #if IS_ENABLED(CONFIG_IPV6)
......
...@@ -250,6 +250,7 @@ static void br_multicast_group_expired(struct timer_list *t) ...@@ -250,6 +250,7 @@ static void br_multicast_group_expired(struct timer_list *t)
goto out; goto out;
mp->host_joined = false; mp->host_joined = false;
br_mdb_notify(br->dev, NULL, &mp->addr, RTM_DELMDB, 0);
if (mp->ports) if (mp->ports)
goto out; goto out;
...@@ -773,7 +774,10 @@ static int br_multicast_add_group(struct net_bridge *br, ...@@ -773,7 +774,10 @@ static int br_multicast_add_group(struct net_bridge *br,
goto err; goto err;
if (!port) { if (!port) {
if (!mp->host_joined) {
mp->host_joined = true; mp->host_joined = true;
br_mdb_notify(br->dev, NULL, &mp->addr, RTM_NEWMDB, 0);
}
mod_timer(&mp->timer, now + br->multicast_membership_interval); mod_timer(&mp->timer, now + br->multicast_membership_interval);
goto out; goto out;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment