From patchwork Sun Jul 10 16:04:30 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Nick Carter X-Patchwork-Id: 104063 X-Patchwork-Delegate: davem@davemloft.net Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 959C1B6F98 for ; Mon, 11 Jul 2011 02:04:38 +1000 (EST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753919Ab1GJQEd (ORCPT ); Sun, 10 Jul 2011 12:04:33 -0400 Received: from mail-pv0-f174.google.com ([74.125.83.174]:45604 "EHLO mail-pv0-f174.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1753492Ab1GJQEc convert rfc822-to-8bit (ORCPT ); Sun, 10 Jul 2011 12:04:32 -0400 Received: by pvg12 with SMTP id 12so2167653pvg.19 for ; Sun, 10 Jul 2011 09:04:31 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=mime-version:in-reply-to:references:date:message-id:subject:from:to :cc:content-type:content-transfer-encoding; bh=kx1mbUKBoMtfIfNZCxYPHZX+ZkzJc1yJmTbNplc0BBw=; b=Yvp93JXf+L8pW20jX9pahFIoBKUnUM5PA6U3tFG/UfN1QbAFW9i3dG3RYgkhcRM7+t ll9WftRbwhJHyrWFkvLFEkRufas60B6qbAP0YSNKUoSDbSkSJTLcHXQ0xPi+wW41tZvF fnz1UHGMdgoTWpnVSQCLDXNMCmsKyXjNsvPoI= MIME-Version: 1.0 Received: by 10.68.64.36 with SMTP id l4mr6175835pbs.48.1310313871486; Sun, 10 Jul 2011 09:04:31 -0700 (PDT) Received: by 10.68.49.130 with HTTP; Sun, 10 Jul 2011 09:04:30 -0700 (PDT) In-Reply-To: References: Date: Sun, 10 Jul 2011 17:04:30 +0100 Message-ID: Subject: Re: [PATCH] bridge: mask forwarding of IEEE 802 local multicast groups From: Nick Carter To: netdev@vger.kernel.org, =?ISO-8859-2?Q?Micha=B3_Miros=B3aw?= , David Lamparter , Stephen Hemminger Cc: davem@davemloft.net Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org Updated diffs so they apply to net-next (Original diffs were based off 2.6.38). Any chance of getting these diffs applied? The default behaviour of the bridge code is unchanged. They solve the problem of authenticating a virtual 802.1x supplicant machine against an external 802.1X authenticator. It is also a general solution that allows the forwarding of any combination of the IEEE 802 local multicast groups. Signed-off-by: Nick Carter Reviewed-by: David Lamparter net/bridge/br_device.c | 1 + net/bridge/br_input.c | 3 +++ net/bridge/br_private.h | 8 ++++++++ net/bridge/br_sysfs_br.c | 23 +++++++++++++++++++++++ 4 files changed, 35 insertions(+), 0 deletions(-) On 1 July 2011 22:21, Nick Carter wrote: > Introduce sysfs ../bridge/group_fwd_mask attribute so users can > configure which group mac addresses are forwarded. > > These diffs do not change the default behaviour of bridge.ko.  By > changing the group_fwd_mask value users can select any combination of > the 01-80-C2-00-00-00 - 01-80-C2-00-00-0F addresses to be forwarded. > > Signed-off-by: Nick Carter > > diff --git a/net/bridge/br_if.c b/net/bridge/br_if.c > index d9d1e2b..bb25e49 100644 > --- a/net/bridge/br_if.c > +++ b/net/bridge/br_if.c > @@ -214,6 +214,7 @@ static struct net_device *new_bridge_dev(struct > net *net, const char *name) >        br->topology_change = 0; >        br->topology_change_detected = 0; >        br->ageing_time = 300 * HZ; > +       br->group_fwd_mask = 0; > >        br_netfilter_rtable_init(br); > > diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c > index 90e985b..80b94f4 100644 > --- a/net/bridge/br_input.c > +++ b/net/bridge/br_input.c > @@ -166,6 +166,9 @@ struct sk_buff *br_handle_frame(struct sk_buff *skb) >                if (p->br->stp_enabled == BR_NO_STP && dest[5] == 0) >                        goto forward; > > +               if (p->br->group_fwd_mask & (1 << dest[5])) > +                       goto forward; > + >                if (NF_HOOK(NFPROTO_BRIDGE, NF_BR_LOCAL_IN, skb, skb->dev, >                            NULL, br_handle_local_finish)) >                        return NULL;    /* frame consumed by filter */ > diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h > index 4e1b620..d5aa164 100644 > --- a/net/bridge/br_private.h > +++ b/net/bridge/br_private.h > @@ -244,6 +244,13 @@ struct net_bridge >        struct timer_list               multicast_query_timer; >  #endif > > +       /* Each bit used to match the LSB of the IEEE 802.1D group address > +        * 01-80-C2-00-00-00 bit 0 > +        * .. > +        * 01-80-C2-00-00-0F bit 15 > +        */ > +       u16                             group_fwd_mask; > + >        struct timer_list               hello_timer; >        struct timer_list               tcn_timer; >        struct timer_list               topology_change_timer; > diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c > index 5c1e555..f3cced5 100644 > --- a/net/bridge/br_sysfs_br.c > +++ b/net/bridge/br_sysfs_br.c > @@ -679,6 +679,28 @@ static DEVICE_ATTR(nf_call_arptables, S_IRUGO | S_IWUSR, >                   show_nf_call_arptables, store_nf_call_arptables); >  #endif > > +static ssize_t show_group_fwd_mask(struct device *d, struct > device_attribute *attr, > +                               char *buf) > +{ > +       struct net_bridge *br = to_bridge(d); > +       return sprintf(buf, "%d\n", br->group_fwd_mask); > +} > + > +static int set_group_fwd_mask(struct net_bridge *br, unsigned long val) > +{ > +       br->group_fwd_mask = (u16)val; > +       return 0; > +} > + > +static ssize_t store_group_fwd_mask(struct device *d, > +                                struct device_attribute *attr, const char *buf, > +                                size_t len) > +{ > +       return store_bridge_parm(d, buf, len, set_group_fwd_mask); > +} > +static DEVICE_ATTR(group_fwd_mask, S_IRUGO | S_IWUSR, show_group_fwd_mask, > +                  store_group_fwd_mask); > + >  static struct attribute *bridge_attrs[] = { >        &dev_attr_forward_delay.attr, >        &dev_attr_hello_time.attr, > @@ -698,6 +720,7 @@ static struct attribute *bridge_attrs[] = { >        &dev_attr_gc_timer.attr, >        &dev_attr_group_addr.attr, >        &dev_attr_flush.attr, > +       &dev_attr_group_fwd_mask.attr, >  #ifdef CONFIG_BRIDGE_IGMP_SNOOPING >        &dev_attr_multicast_router.attr, >        &dev_attr_multicast_snooping.attr, > --- To unsubscribe from this list: send the line "unsubscribe netdev" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c index 32b8f9f..573ed8c 100644 --- a/net/bridge/br_device.c +++ b/net/bridge/br_device.c @@ -366,6 +366,7 @@ void br_dev_setup(struct net_device *dev) br->bridge_hello_time = br->hello_time = 2 * HZ; br->bridge_forward_delay = br->forward_delay = 15 * HZ; br->ageing_time = 300 * HZ; + br->group_fwd_mask = 0; br_netfilter_rtable_init(br); br_stp_timer_init(br); diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c index f06ee39..3bee262 100644 --- a/net/bridge/br_input.c +++ b/net/bridge/br_input.c @@ -170,6 +170,9 @@ rx_handler_result_t br_handle_frame(struct sk_buff **pskb) if (p->br->stp_enabled == BR_NO_STP && dest[5] == 0) goto forward; + if (p->br->group_fwd_mask & (1 << dest[5])) + goto forward; + if (NF_HOOK(NFPROTO_BRIDGE, NF_BR_LOCAL_IN, skb, skb->dev, NULL, br_handle_local_finish)) { return RX_HANDLER_CONSUMED; /* consumed by filter */ diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h index 54578f2..413fcec 100644 --- a/net/bridge/br_private.h +++ b/net/bridge/br_private.h @@ -244,6 +244,14 @@ struct net_bridge struct timer_list multicast_query_timer; #endif + /* Each bit used to match the least significant nibble of the + * IEEE 802.1D group address. + * 01-80-C2-00-00-00 bit 0 + * .. + * 01-80-C2-00-00-0F bit 15 + */ + u16 group_fwd_mask; + struct timer_list hello_timer; struct timer_list tcn_timer; struct timer_list topology_change_timer; diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c index 68b893e..d77f681 100644 --- a/net/bridge/br_sysfs_br.c +++ b/net/bridge/br_sysfs_br.c @@ -646,6 +646,28 @@ static DEVICE_ATTR(nf_call_arptables, S_IRUGO | S_IWUSR, show_nf_call_arptables, store_nf_call_arptables); #endif +static ssize_t show_group_fwd_mask(struct device *d, + struct device_attribute *attr, char *buf) +{ + struct net_bridge *br = to_bridge(d); + return sprintf(buf, "%d\n", br->group_fwd_mask); +} + +static int set_group_fwd_mask(struct net_bridge *br, unsigned long val) +{ + br->group_fwd_mask = (u16)val; + return 0; +} + +static ssize_t store_group_fwd_mask(struct device *d, + struct device_attribute *attr, + const char *buf, size_t len) +{ + return store_bridge_parm(d, buf, len, set_group_fwd_mask); +} +static DEVICE_ATTR(group_fwd_mask, S_IRUGO | S_IWUSR, show_group_fwd_mask, + store_group_fwd_mask); + static struct attribute *bridge_attrs[] = { &dev_attr_forward_delay.attr, &dev_attr_hello_time.attr, @@ -665,6 +687,7 @@ static struct attribute *bridge_attrs[] = { &dev_attr_gc_timer.attr, &dev_attr_group_addr.attr, &dev_attr_flush.attr, + &dev_attr_group_fwd_mask.attr, #ifdef CONFIG_BRIDGE_IGMP_SNOOPING &dev_attr_multicast_router.attr, &dev_attr_multicast_snooping.attr,