History

net: bridge: vlan: add support for mcast router global option

Add support to change and retrieve global vlan multicast router state which is used for the bridge itself. We just need to pass multicast context to br_multicast_set_router instead of bridge device and the rest of the logic remains the same.

Nikolay Aleksandrov committed 5 years ago

Commit a97df081 parent 62938186 files · +25 −10Browse files

Unified · Split

6 files
  1. include/uapi/linux/if_bridge.h +1 −0
  2. net/bridge/br_multicast.c +5 −6
  3. net/bridge/br_netlink.c +2 −1
  4. net/bridge/br_private.h +2 −1
  5. net/bridge/br_sysfs_br.c +1 −1
  6. net/bridge/br_vlan_options.c +14 −1
include/uapi/linux/if_bridge.h+1−0
@@ -561,6 +561,7 @@ enum { · 560 unmodified lines
561 BRIDGE_VLANDB_GOPTS_MCAST_QUERY_RESPONSE_INTVL,561 BRIDGE_VLANDB_GOPTS_MCAST_QUERY_RESPONSE_INTVL,
562 BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_INTVL,562 BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_INTVL,
563 BRIDGE_VLANDB_GOPTS_MCAST_QUERIER,563 BRIDGE_VLANDB_GOPTS_MCAST_QUERIER,
564 BRIDGE_VLANDB_GOPTS_MCAST_ROUTER,
564 __BRIDGE_VLANDB_GOPTS_MAX565 __BRIDGE_VLANDB_GOPTS_MAX
565};566};
566#define BRIDGE_VLANDB_GOPTS_MAX (__BRIDGE_VLANDB_GOPTS_MAX - 1)567#define BRIDGE_VLANDB_GOPTS_MAX (__BRIDGE_VLANDB_GOPTS_MAX - 1)
net/bridge/br_multicast.c+5−6
@@ -4053,17 +4053,16 @@ void br_multicast_dev_del(struct net_bridge *br) · 4052 unmodified lines
4053 rcu_barrier();4053 rcu_barrier();
4054}4054}
4055 4055
4056int br_multicast_set_router(struct net_bridge *br, unsigned long val)4056int br_multicast_set_router(struct net_bridge_mcast *brmctx, unsigned long val)
4057{4057{
4058 struct net_bridge_mcast *brmctx = &br->multicast_ctx;
4059 int err = -EINVAL;4058 int err = -EINVAL;
4060 4059
4061 spin_lock_bh(&br->multicast_lock);4060 spin_lock_bh(&brmctx->br->multicast_lock);
4062 4061
4063 switch (val) {4062 switch (val) {
4064 case MDB_RTR_TYPE_DISABLED:4063 case MDB_RTR_TYPE_DISABLED:
4065 case MDB_RTR_TYPE_PERM:4064 case MDB_RTR_TYPE_PERM:
4066 br_mc_router_state_change(br, val == MDB_RTR_TYPE_PERM);4065 br_mc_router_state_change(brmctx->br, val == MDB_RTR_TYPE_PERM);
4067 del_timer(&brmctx->ip4_mc_router_timer);4066 del_timer(&brmctx->ip4_mc_router_timer);
4068#if IS_ENABLED(CONFIG_IPV6)4067#if IS_ENABLED(CONFIG_IPV6)
4069 del_timer(&brmctx->ip6_mc_router_timer);4068 del_timer(&brmctx->ip6_mc_router_timer);
@@ -4073,13 +4072,13 @@ int br_multicast_set_router(struct net_bridge *br, unsigned long val) · 3 unmodified lines
4073 break;4072 break;
4074 case MDB_RTR_TYPE_TEMP_QUERY:4073 case MDB_RTR_TYPE_TEMP_QUERY:
4075 if (brmctx->multicast_router != MDB_RTR_TYPE_TEMP_QUERY)4074 if (brmctx->multicast_router != MDB_RTR_TYPE_TEMP_QUERY)
4076 br_mc_router_state_change(br, false);4075 br_mc_router_state_change(brmctx->br, false);
4077 brmctx->multicast_router = val;4076 brmctx->multicast_router = val;
4078 err = 0;4077 err = 0;
4079 break;4078 break;
4080 }4079 }
4081 4080
4082 spin_unlock_bh(&br->multicast_lock);4081 spin_unlock_bh(&brmctx->br->multicast_lock);
4083 4082
4084 return err;4083 return err;
4085}4084}
net/bridge/br_netlink.c+2−1
@@ -1286,7 +1286,8 @@ static int br_changelink(struct net_device *brdev, struct nlattr *tb[], · 1285 unmodified lines
1286 if (data[IFLA_BR_MCAST_ROUTER]) {1286 if (data[IFLA_BR_MCAST_ROUTER]) {
1287 u8 multicast_router = nla_get_u8(data[IFLA_BR_MCAST_ROUTER]);1287 u8 multicast_router = nla_get_u8(data[IFLA_BR_MCAST_ROUTER]);
1288 1288
1289 err = br_multicast_set_router(br, multicast_router);1289 err = br_multicast_set_router(&br->multicast_ctx,
1290 multicast_router);
1290 if (err)1291 if (err)
1291 return err;1292 return err;
1292 }1293 }
net/bridge/br_private.h+2−1
@@ -877,7 +877,7 @@ void br_multicast_dev_del(struct net_bridge *br); · 876 unmodified lines
877void br_multicast_flood(struct net_bridge_mdb_entry *mdst, struct sk_buff *skb,877void br_multicast_flood(struct net_bridge_mdb_entry *mdst, struct sk_buff *skb,
878 struct net_bridge_mcast *brmctx,878 struct net_bridge_mcast *brmctx,
879 bool local_rcv, bool local_orig);879 bool local_rcv, bool local_orig);
880int br_multicast_set_router(struct net_bridge *br, unsigned long val);880int br_multicast_set_router(struct net_bridge_mcast *brmctx, unsigned long val);
881int br_multicast_set_port_router(struct net_bridge_port *p, unsigned long val);881int br_multicast_set_port_router(struct net_bridge_port *p, unsigned long val);
882int br_multicast_toggle(struct net_bridge *br, unsigned long val,882int br_multicast_toggle(struct net_bridge *br, unsigned long val,
883 struct netlink_ext_ack *extack);883 struct netlink_ext_ack *extack);
@@ -1191,6 +1191,7 @@ br_multicast_ctx_options_equal(const struct net_bridge_mcast *brmctx1, · 307 unmodified lines
1191 brmctx1->multicast_startup_query_interval ==1191 brmctx1->multicast_startup_query_interval ==
1192 brmctx2->multicast_startup_query_interval &&1192 brmctx2->multicast_startup_query_interval &&
1193 brmctx1->multicast_querier == brmctx2->multicast_querier &&1193 brmctx1->multicast_querier == brmctx2->multicast_querier &&
1194 brmctx1->multicast_router == brmctx2->multicast_router &&
1194#if IS_ENABLED(CONFIG_IPV6)1195#if IS_ENABLED(CONFIG_IPV6)
1195 brmctx1->multicast_mld_version ==1196 brmctx1->multicast_mld_version ==
1196 brmctx2->multicast_mld_version &&1197 brmctx2->multicast_mld_version &&
net/bridge/br_sysfs_br.c+1−1
@@ -390,7 +390,7 @@ static ssize_t multicast_router_show(struct device *d, · 389 unmodified lines
390static int set_multicast_router(struct net_bridge *br, unsigned long val,390static int set_multicast_router(struct net_bridge *br, unsigned long val,
391 struct netlink_ext_ack *extack)391 struct netlink_ext_ack *extack)
392{392{
393 return br_multicast_set_router(br, val);393 return br_multicast_set_router(&br->multicast_ctx, val);
394}394}
395 395
396static ssize_t multicast_router_store(struct device *d,396static ssize_t multicast_router_store(struct device *d,
net/bridge/br_vlan_options.c+14−1
@@ -296,7 +296,9 @@ bool br_vlan_global_opts_fill(struct sk_buff *skb, u16 vid, u16 vid_range, · 295 unmodified lines
296 nla_put_u32(skb, BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_CNT,296 nla_put_u32(skb, BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_CNT,
297 v_opts->br_mcast_ctx.multicast_startup_query_count) ||297 v_opts->br_mcast_ctx.multicast_startup_query_count) ||
298 nla_put_u8(skb, BRIDGE_VLANDB_GOPTS_MCAST_QUERIER,298 nla_put_u8(skb, BRIDGE_VLANDB_GOPTS_MCAST_QUERIER,
299 v_opts->br_mcast_ctx.multicast_querier))299 v_opts->br_mcast_ctx.multicast_querier) ||
300 nla_put_u8(skb, BRIDGE_VLANDB_GOPTS_MCAST_ROUTER,
301 v_opts->br_mcast_ctx.multicast_router))
300 goto out_err;302 goto out_err;
301 303
302 clockval = jiffies_to_clock_t(v_opts->br_mcast_ctx.multicast_last_member_interval);304 clockval = jiffies_to_clock_t(v_opts->br_mcast_ctx.multicast_last_member_interval);
@@ -358,6 +360,7 @@ static size_t rtnl_vlan_global_opts_nlmsg_size(void) · 55 unmodified lines
358 + nla_total_size(sizeof(u64)) /* BRIDGE_VLANDB_GOPTS_MCAST_QUERY_RESPONSE_INTVL */360 + nla_total_size(sizeof(u64)) /* BRIDGE_VLANDB_GOPTS_MCAST_QUERY_RESPONSE_INTVL */
359 + nla_total_size(sizeof(u64)) /* BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_INTVL */361 + nla_total_size(sizeof(u64)) /* BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_INTVL */
360 + nla_total_size(sizeof(u8)) /* BRIDGE_VLANDB_GOPTS_MCAST_QUERIER */362 + nla_total_size(sizeof(u8)) /* BRIDGE_VLANDB_GOPTS_MCAST_QUERIER */
363 + nla_total_size(sizeof(u8)) /* BRIDGE_VLANDB_GOPTS_MCAST_ROUTER */
361#endif364#endif
362 + nla_total_size(sizeof(u16)); /* BRIDGE_VLANDB_GOPTS_RANGE */365 + nla_total_size(sizeof(u16)); /* BRIDGE_VLANDB_GOPTS_RANGE */
363}366}
@@ -497,6 +500,15 @@ static int br_vlan_process_global_one_opts(const struct net_bridge *br, · 133 unmodified lines
497 return err;500 return err;
498 *changed = true;501 *changed = true;
499 }502 }
503 if (tb[BRIDGE_VLANDB_GOPTS_MCAST_ROUTER]) {
504 u8 val;
505
506 val = nla_get_u8(tb[BRIDGE_VLANDB_GOPTS_MCAST_ROUTER]);
507 err = br_multicast_set_router(&v->br_mcast_ctx, val);
508 if (err)
509 return err;
510 *changed = true;
511 }
500#if IS_ENABLED(CONFIG_IPV6)512#if IS_ENABLED(CONFIG_IPV6)
501 if (tb[BRIDGE_VLANDB_GOPTS_MCAST_MLD_VERSION]) {513 if (tb[BRIDGE_VLANDB_GOPTS_MCAST_MLD_VERSION]) {
502 u8 ver;514 u8 ver;
@@ -520,6 +532,7 @@ static const struct nla_policy br_vlan_db_gpol[BRIDGE_VLANDB_GOPTS_MAX + 1] = { · 17 unmodified lines
520 [BRIDGE_VLANDB_GOPTS_MCAST_MLD_VERSION] = { .type = NLA_U8 },532 [BRIDGE_VLANDB_GOPTS_MCAST_MLD_VERSION] = { .type = NLA_U8 },
521 [BRIDGE_VLANDB_GOPTS_MCAST_QUERY_INTVL] = { .type = NLA_U64 },533 [BRIDGE_VLANDB_GOPTS_MCAST_QUERY_INTVL] = { .type = NLA_U64 },
522 [BRIDGE_VLANDB_GOPTS_MCAST_QUERIER] = { .type = NLA_U8 },534 [BRIDGE_VLANDB_GOPTS_MCAST_QUERIER] = { .type = NLA_U8 },
535 [BRIDGE_VLANDB_GOPTS_MCAST_ROUTER] = { .type = NLA_U8 },
523 [BRIDGE_VLANDB_GOPTS_MCAST_IGMP_VERSION] = { .type = NLA_U8 },536 [BRIDGE_VLANDB_GOPTS_MCAST_IGMP_VERSION] = { .type = NLA_U8 },
524 [BRIDGE_VLANDB_GOPTS_MCAST_LAST_MEMBER_CNT] = { .type = NLA_U32 },537 [BRIDGE_VLANDB_GOPTS_MCAST_LAST_MEMBER_CNT] = { .type = NLA_U32 },
525 [BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_CNT] = { .type = NLA_U32 },538 [BRIDGE_VLANDB_GOPTS_MCAST_STARTUP_QUERY_CNT] = { .type = NLA_U32 },