Skip to content

Commit 170afa7

Browse files
idoschkuba-moo
authored andcommitted
bridge: mcast: Move validation to a policy
Future patches are going to move parts of the bridge MDB code to the common rtnetlink code in preparation for VXLAN MDB support. To facilitate code sharing between both drivers, move the validation of the top level attributes in RTM_{NEW,DEL}MDB messages to a policy that will eventually be moved to the rtnetlink code. Use 'NLA_NESTED' for 'MDBA_SET_ENTRY_ATTRS' instead of NLA_POLICY_NESTED() as this attribute is going to be validated using different policies in the underlying drivers. Signed-off-by: Ido Schimmel <idosch@nvidia.com> Acked-by: Nikolay Aleksandrov <razor@blackwall.org> Signed-off-by: Jakub Kicinski <kuba@kernel.org>
1 parent 7ea8296 commit 170afa7

File tree

1 file changed

+27
-18
lines changed

1 file changed

+27
-18
lines changed

net/bridge/br_mdb.c

Lines changed: 27 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -683,51 +683,58 @@ static const struct nla_policy br_mdbe_attrs_pol[MDBE_ATTR_MAX + 1] = {
683683
[MDBE_ATTR_RTPROT] = NLA_POLICY_MIN(NLA_U8, RTPROT_STATIC),
684684
};
685685

686-
static bool is_valid_mdb_entry(struct br_mdb_entry *entry,
687-
struct netlink_ext_ack *extack)
686+
static int validate_mdb_entry(const struct nlattr *attr,
687+
struct netlink_ext_ack *extack)
688688
{
689+
struct br_mdb_entry *entry = nla_data(attr);
690+
691+
if (nla_len(attr) != sizeof(struct br_mdb_entry)) {
692+
NL_SET_ERR_MSG_MOD(extack, "Invalid MDBA_SET_ENTRY attribute length");
693+
return -EINVAL;
694+
}
695+
689696
if (entry->ifindex == 0) {
690697
NL_SET_ERR_MSG_MOD(extack, "Zero entry ifindex is not allowed");
691-
return false;
698+
return -EINVAL;
692699
}
693700

694701
if (entry->addr.proto == htons(ETH_P_IP)) {
695702
if (!ipv4_is_multicast(entry->addr.u.ip4)) {
696703
NL_SET_ERR_MSG_MOD(extack, "IPv4 entry group address is not multicast");
697-
return false;
704+
return -EINVAL;
698705
}
699706
if (ipv4_is_local_multicast(entry->addr.u.ip4)) {
700707
NL_SET_ERR_MSG_MOD(extack, "IPv4 entry group address is local multicast");
701-
return false;
708+
return -EINVAL;
702709
}
703710
#if IS_ENABLED(CONFIG_IPV6)
704711
} else if (entry->addr.proto == htons(ETH_P_IPV6)) {
705712
if (ipv6_addr_is_ll_all_nodes(&entry->addr.u.ip6)) {
706713
NL_SET_ERR_MSG_MOD(extack, "IPv6 entry group address is link-local all nodes");
707-
return false;
714+
return -EINVAL;
708715
}
709716
#endif
710717
} else if (entry->addr.proto == 0) {
711718
/* L2 mdb */
712719
if (!is_multicast_ether_addr(entry->addr.u.mac_addr)) {
713720
NL_SET_ERR_MSG_MOD(extack, "L2 entry group is not multicast");
714-
return false;
721+
return -EINVAL;
715722
}
716723
} else {
717724
NL_SET_ERR_MSG_MOD(extack, "Unknown entry protocol");
718-
return false;
725+
return -EINVAL;
719726
}
720727

721728
if (entry->state != MDB_PERMANENT && entry->state != MDB_TEMPORARY) {
722729
NL_SET_ERR_MSG_MOD(extack, "Unknown entry state");
723-
return false;
730+
return -EINVAL;
724731
}
725732
if (entry->vid >= VLAN_VID_MASK) {
726733
NL_SET_ERR_MSG_MOD(extack, "Invalid entry VLAN id");
727-
return false;
734+
return -EINVAL;
728735
}
729736

730-
return true;
737+
return 0;
731738
}
732739

733740
static bool is_valid_mdb_source(struct nlattr *attr, __be16 proto,
@@ -1292,6 +1299,14 @@ static int br_mdb_config_attrs_init(struct nlattr *set_attrs,
12921299
return 0;
12931300
}
12941301

1302+
static const struct nla_policy mdba_policy[MDBA_SET_ENTRY_MAX + 1] = {
1303+
[MDBA_SET_ENTRY_UNSPEC] = { .strict_start_type = MDBA_SET_ENTRY_ATTRS + 1 },
1304+
[MDBA_SET_ENTRY] = NLA_POLICY_VALIDATE_FN(NLA_BINARY,
1305+
validate_mdb_entry,
1306+
sizeof(struct br_mdb_entry)),
1307+
[MDBA_SET_ENTRY_ATTRS] = { .type = NLA_NESTED },
1308+
};
1309+
12951310
static int br_mdb_config_init(struct net *net, const struct nlmsghdr *nlh,
12961311
struct br_mdb_config *cfg,
12971312
struct netlink_ext_ack *extack)
@@ -1302,7 +1317,7 @@ static int br_mdb_config_init(struct net *net, const struct nlmsghdr *nlh,
13021317
int err;
13031318

13041319
err = nlmsg_parse_deprecated(nlh, sizeof(*bpm), tb,
1305-
MDBA_SET_ENTRY_MAX, NULL, extack);
1320+
MDBA_SET_ENTRY_MAX, mdba_policy, extack);
13061321
if (err)
13071322
return err;
13081323

@@ -1344,14 +1359,8 @@ static int br_mdb_config_init(struct net *net, const struct nlmsghdr *nlh,
13441359
NL_SET_ERR_MSG_MOD(extack, "Missing MDBA_SET_ENTRY attribute");
13451360
return -EINVAL;
13461361
}
1347-
if (nla_len(tb[MDBA_SET_ENTRY]) != sizeof(struct br_mdb_entry)) {
1348-
NL_SET_ERR_MSG_MOD(extack, "Invalid MDBA_SET_ENTRY attribute length");
1349-
return -EINVAL;
1350-
}
13511362

13521363
cfg->entry = nla_data(tb[MDBA_SET_ENTRY]);
1353-
if (!is_valid_mdb_entry(cfg->entry, extack))
1354-
return -EINVAL;
13551364

13561365
if (cfg->entry->ifindex != cfg->br->dev->ifindex) {
13571366
struct net_device *pdev;

0 commit comments

Comments
 (0)