[PATCH 3/3] bridge: Add support for VLANs
David Ahern
dsa at cumulusnetworks.com
Wed Nov 25 09:11:12 PST 2015
On 11/25/15 8:47 AM, Tobias Jungel wrote:
>> diff --git a/include/netlink/route/link/bridge.h
>> b/include/netlink/route/link/bridge.h
>> index 16a4505f8b74..5dc6a367595c 100644
>> --- a/include/netlink/route/link/bridge.h
>> +++ b/include/netlink/route/link/bridge.h
>> @@ -19,6 +19,22 @@
>> extern "C" {
>> #endif
>>
>> +/* maximum vlan id */
>> +#define VLAN_N_VID 4096
>> +
>> +#define BITS_PER_BYTE 8
>> +#define BITS_PER_LONG (BITS_PER_BYTE *
>> sizeof(unsigned long))
>> +#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
>> +#define BITS_TO_LONGS(nr) DIV_ROUND_UP(nr, BITS_PER_LONG)
>> +#define BR_VLAN_BITMAP_LEN BITS_TO_LONGS(VLAN_N_VID)
>> +
>> +struct bridge_vlan
>> +{
>> + uint16_t pvid;
>> + unsigned long vlan_bitmap[BR_VLAN_BITMAP_LEN];
>> + unsigned long untagged_bitmap[BR_VLAN_BITMAP_LEN];
>> +};
>> +
>
> Fine with me, even if I personnaly would rather opt for the kernels
> compressed data structure, but this is probably just a matter of taste.
A bitmap has better lookup qualities as well as a consistent memory
footprint. No idea why the kernel implementation is a list. Roopa?
-----8<-----
>> @@ -141,6 +185,112 @@ static int bridge_parse_protinfo(struct
>> rtnl_link *link, struct nlattr *attr,
>> return 0;
>> }
>>
>> +static int bridge_parse_af(struct rtnl_link *link, struct nlattr
>> *attr,
>> + void *data)
>> +{
>> + struct bridge_data *bd = data;
>> + struct bridge_vlan_info *vinfo = NULL;
>> +
>> + if (nla_type(attr) != IFLA_BRIDGE_VLAN_INFO)
>> + return 0;
>> +
>> + if (nla_len(attr) != sizeof(struct bridge_vlan_info))
>> + return -EINVAL;
>> +
>> + vinfo = nla_data(attr);
>> + if (!vinfo->vid || vinfo->vid >= VLAN_VID_MASK)
>> + return -EINVAL;
>> +
>> + if (vinfo->flags & BRIDGE_VLAN_INFO_RANGE_BEGIN) {
>> + NL_DBG(1, "Unexpected BRIDGE_VLAN_INFO_RANGE_BEGIN
>> flag; can not handle it.\n");
>> + return -EINVAL;
>
> afaik RTEXT_FILTER_BRVLAN_COMPRESSED is the default for the kernel to
> send notifications, so I see this rather mandatory to have.
sure, can add that one in time. Right now the request below is for
non-compressed, that's why it is marked as unexpected here. The
complication with the compressed version is that it crosses consecutive
attributes: start is in the first, end in the second.
-----8<-----
>> @@ -503,6 +666,44 @@ int rtnl_link_bridge_str2flags(const char *name)
>>
>> /** @} */
>>
>> +int rtnl_link_bridge_pvid(struct rtnl_link *link)
>
> this function seems to be public, so its missing in the .sym file.
>
>> +{
>> + struct bridge_data *bd = link->l_af_data[AF_BRIDGE];
>> +
>> + if (bd->ce_mask & BRIDGE_ATTR_PORT_VLAN)
>> + return (int) bd->vlan_info.pvid;
>> +
>> + return -EINVAL;
>> +}
>> +
>> +int rtnl_link_bridge_has_vlan(struct rtnl_link *link)
>
> same as above
>
>> +{
>> + struct bridge_data *bd = link->l_af_data[AF_BRIDGE];
>> + int i;
>> +
>> + if (bd->ce_mask & BRIDGE_ATTR_PORT_VLAN) {
>> + if (bd->vlan_info.pvid)
>> + return 1;
>> +
>> + for (i = 0; i < BR_VLAN_BITMAP_LEN; ++i) {
>> + if (bd->vlan_info.vlan_bitmap[i] ||
>> + bd->vlan_info.untagged_bitmap[i])
>> + return 1;
>> + }
>> + }
>> + return 0;
>> +}
>> +
>> +struct bridge_vlan *rtnl_bridge_get_port_vlan(struct rtnl_link
>> *link)
>
> same as above and I guess the function should be renamed to
> rtnl_link_bridge_get_port_vlan
>
ack on all 3. Will fix in the next version.
Thanks for the review.
More information about the libnl
mailing list