From rea-fbsd@codelabs.ru  Sat Mar  3 21:12:39 2007
Return-Path: <rea-fbsd@codelabs.ru>
Received: from mx1.freebsd.org (mx1.freebsd.org [69.147.83.52])
	by hub.freebsd.org (Postfix) with ESMTP id 8566616A403;
	Sat,  3 Mar 2007 21:12:39 +0000 (UTC)
	(envelope-from rea-fbsd@codelabs.ru)
Received: from pobox.codelabs.ru (pobox.codelabs.ru [144.206.177.45])
	by mx1.freebsd.org (Postfix) with ESMTP id 3DE5D13C4AA;
	Sat,  3 Mar 2007 21:12:39 +0000 (UTC)
	(envelope-from rea-fbsd@codelabs.ru)
Received: from localdomain
	by pobox.codelabs.ru with local
	id 1HNbWw-000LoF-Bo; Sun, 04 Mar 2007 00:12:38 +0300
Message-Id: <E1HNbWw-000LoF-Bo@pobox.codelabs.ru>
Date: Sun, 04 Mar 2007 00:12:38 +0300
From: Eygene Ryabinkin <rea-fbsd@codelabs.ru>
Sender: rea-fbsd@codelabs.ru
Reply-To: Eygene Ryabinkin <rea-fbsd@codelabs.ru>
To: FreeBSD-gnats-submit@freebsd.org
Cc: rik@freebsd.org, glebius@freebsd.org, thompsa@freebsd.org, andre@freebsd.org
Subject: wrong interface identifier at pfil_hooks for vlans + if_bridge
X-Send-Pr-Version: 3.113
X-GNATS-Notify:

>Number:         109815
>Category:       kern
>Synopsis:       [if_bridge] [patch] wrong interface identifier at pfil_hooks for vlans + if_bridge
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    rik
>State:          closed
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Sat Mar 03 21:20:04 GMT 2007
>Closed-Date:    Mon Apr 09 09:40:38 GMT 2007
>Last-Modified:  Mon Apr 09 09:40:38 GMT 2007
>Originator:     Eygene Ryabinkin
>Release:        FreeBSD 6.2-STABLE i386
>Organization:
Code Labs
>Environment:
System: FreeBSD XXX 6.2-STABLE FreeBSD 6.2-STABLE #13: Mon Feb 12 15:59:07 MSK 2007 root@XXX:/usr/obj/usr/src/sys/XXX i386
>Description:
When if_bridge is used to gather multiple vlan interfaces that have
the same physical parent (I will call such vlan interfaces the 'vlan
group') the interface identifier that will be passed to the
pfil_hooks will be sometimes wrong. For all packets coming from the
'vlan group' and destined to some local interface the incoming interface
passed to the pfil_hooks will be the last interface in that group
regardless of the actual incoming interface. The 'last interface' is
the interface that was added to the if_bridge at the very last 'addm'
command.

The problem is lying in the fact that MAC addresses of the 'vlan group'
are just the same and they are equal to the MAC address of the parent
interface. And the check for the unicat packet that is destined for
'us' in the if_bridge.c:bridge_input() is walking by the list of the
if_bridge-attached interfaces and compares the MAC addresses to the
packet's one. Once match is found the interface in the packet header
will be rewritten to the found list entry's one. Apparently such
code flow will select the last added interface from the 'vlan group'
because FreeBSD list macros are adding list members to the beginning
of the linked list.

BPF will receive the right interface, because it is tapped before
bridge_input (in if_ethersubr.c).

>How-To-Repeat:
Set up three vlan interfaces on the same physical one, and add them
to the same if_bridge. Give one VLAN interface IP address and send
packets from the other VLAN segment to that IP. See that tcpdump
is seeing the correct interface, but ipfw/pf are seeing the same
packet having the last added interface as the rcvif, not the right one.
For the last added interface the result will be correct, but for
others -- not.
>Fix:
Since bridge_input always knows about the incoming interface as
it is passed as the first argument my fix is just to set the
right interface using the passed parameter and not the interface
found by the list traversal. The patch is below. It should not
break the ordinary situation without CARP and I see no troubles
even with the CARP code. But I am not expirienced with CARP, so
I am CCing Gleb, Andrew and Andre. We'd found this bug with rik@
so he gots the CC too.

Shutting up ;))

--- if_bridge.c.orig	Fri Mar  2 18:23:56 2007
+++ if_bridge.c	Sat Mar  3 05:04:38 2007
@@ -2122,7 +2122,11 @@
 	LIST_FOREACH(bif2, &sc->sc_iflist, bif_next) {
 		if (bif2->bif_ifp->if_type == IFT_GIF)
 			continue;
-		/* It is destined for us. */
+		/* It is destined for us. We should not rely on the
+		 * found interface's MAC as the interface identifier,
+		 * because vlanX interfaces are sharing their MAC
+		 * with the parent. Moreover, we do know the interface
+		 * the packet is coming from. So we're using it. */
 		if (memcmp(IF_LLADDR(bif2->bif_ifp), eh->ether_dhost,
 		    ETHER_ADDR_LEN) == 0
 #ifdef DEV_CARP
@@ -2133,7 +2137,7 @@
 			if (bif->bif_flags & IFBIF_LEARNING)
 				(void) bridge_rtupdate(sc,
 				    eh->ether_shost, bif, 0, IFBAF_DYNAMIC);
-			m->m_pkthdr.rcvif = bif2->bif_ifp;
+			m->m_pkthdr.rcvif = ifp;
 			BRIDGE_UNLOCK(sc);
 			return (m);
 		}
>Release-Note:
>Audit-Trail:

From: Roman Kurakin <rik@inse.ru>
To: Eygene Ryabinkin <rea-fbsd@codelabs.ru>
Cc: FreeBSD-gnats-submit@FreeBSD.org,  rik@FreeBSD.org, 
 glebius@FreeBSD.org,  andre@FreeBSD.org,  thompsa@FreeBSD.org
Subject: Re: kern/109815: wrong interface identifier at pfil_hooks for vlans
 +	if_bridge
Date: Sun, 04 Mar 2007 01:08:40 +0300

 Just come to my mind.
 
 The idea behind current code could be that in case of bridge the 
 interface for which this
 packet in?nded is much more important than the physical interface it is 
 arrived from.
 If this is the case, than it would be much better do the same logic for 
 ifp and in case
 it is not that interface to check the list. This will fix the problem in 
 case of vlans and
 will leave the old behavior for the other cases.
 
 Any comments?
 
 rik
 
 Eygene Ryabinkin wrote:
 >> Number:         109815
 >> Category:       kern
 >> Synopsis:       wrong interface identifier at pfil_hooks for vlans + if_bridge
 >> Confidential:   no
 >> Severity:       serious
 >> Priority:       medium
 >> Responsible:    freebsd-bugs
 >> State:          open
 >> Quarter:        
 >> Keywords:       
 >> Date-Required:
 >> Class:          sw-bug
 >> Submitter-Id:   current-users
 >> Arrival-Date:   Sat Mar 03 21:20:04 GMT 2007
 >> Closed-Date:
 >> Last-Modified:
 >> Originator:     Eygene Ryabinkin
 >> Release:        FreeBSD 6.2-STABLE i386
 >> Organization:
 >>     
 > Code Labs
 >   
 >> Environment:
 >>     
 > System: FreeBSD XXX 6.2-STABLE FreeBSD 6.2-STABLE #13: Mon Feb 12 15:59:07 MSK 2007 root@XXX:/usr/obj/usr/src/sys/XXX i386
 >   
 >> Description:
 >>     
 > When if_bridge is used to gather multiple vlan interfaces that have
 > the same physical parent (I will call such vlan interfaces the 'vlan
 > group') the interface identifier that will be passed to the
 > pfil_hooks will be sometimes wrong. For all packets coming from the
 > 'vlan group' and destined to some local interface the incoming interface
 > passed to the pfil_hooks will be the last interface in that group
 > regardless of the actual incoming interface. The 'last interface' is
 > the interface that was added to the if_bridge at the very last 'addm'
 > command.
 >
 > The problem is lying in the fact that MAC addresses of the 'vlan group'
 > are just the same and they are equal to the MAC address of the parent
 > interface. And the check for the unicat packet that is destined for
 > 'us' in the if_bridge.c:bridge_input() is walking by the list of the
 > if_bridge-attached interfaces and compares the MAC addresses to the
 > packet's one. Once match is found the interface in the packet header
 > will be rewritten to the found list entry's one. Apparently such
 > code flow will select the last added interface from the 'vlan group'
 > because FreeBSD list macros are adding list members to the beginning
 > of the linked list.
 >
 > BPF will receive the right interface, because it is tapped before
 > bridge_input (in if_ethersubr.c).
 >
 >   
 >> How-To-Repeat:
 >>     
 > Set up three vlan interfaces on the same physical one, and add them
 > to the same if_bridge. Give one VLAN interface IP address and send
 > packets from the other VLAN segment to that IP. See that tcpdump
 > is seeing the correct interface, but ipfw/pf are seeing the same
 > packet having the last added interface as the rcvif, not the right one.
 > For the last added interface the result will be correct, but for
 > others -- not.
 >   
 >> Fix:
 >>     
 > Since bridge_input always knows about the incoming interface as
 > it is passed as the first argument my fix is just to set the
 > right interface using the passed parameter and not the interface
 > found by the list traversal. The patch is below. It should not
 > break the ordinary situation without CARP and I see no troubles
 > even with the CARP code. But I am not expirienced with CARP, so
 > I am CCing Gleb, Andrew and Andre. We'd found this bug with rik@
 > so he gots the CC too.
 >
 > Shutting up ;))
 >
 > --- if_bridge.c.orig	Fri Mar  2 18:23:56 2007
 > +++ if_bridge.c	Sat Mar  3 05:04:38 2007
 > @@ -2122,7 +2122,11 @@
 >  	LIST_FOREACH(bif2, &sc->sc_iflist, bif_next) {
 >  		if (bif2->bif_ifp->if_type == IFT_GIF)
 >  			continue;
 > -		/* It is destined for us. */
 > +		/* It is destined for us. We should not rely on the
 > +		 * found interface's MAC as the interface identifier,
 > +		 * because vlanX interfaces are sharing their MAC
 > +		 * with the parent. Moreover, we do know the interface
 > +		 * the packet is coming from. So we're using it. */
 >  		if (memcmp(IF_LLADDR(bif2->bif_ifp), eh->ether_dhost,
 >  		    ETHER_ADDR_LEN) == 0
 >  #ifdef DEV_CARP
 > @@ -2133,7 +2137,7 @@
 >  			if (bif->bif_flags & IFBIF_LEARNING)
 >  				(void) bridge_rtupdate(sc,
 >  				    eh->ether_shost, bif, 0, IFBAF_DYNAMIC);
 > -			m->m_pkthdr.rcvif = bif2->bif_ifp;
 > +			m->m_pkthdr.rcvif = ifp;
 >  			BRIDGE_UNLOCK(sc);
 >  			return (m);
 >  		}
 >   
 >> Release-Note:
 >> Audit-Trail:
 >> Unformatted:
 >>     
 > _______________________________________________
 > freebsd-bugs@freebsd.org mailing list
 > http://lists.freebsd.org/mailman/listinfo/freebsd-bugs
 > To unsubscribe, send any mail to "freebsd-bugs-unsubscribe@freebsd.org"
 >   
 

From: Eygene Ryabinkin <rea-fbsd@codelabs.ru>
To: Roman Kurakin <rik@inse.ru>
Cc: FreeBSD-gnats-submit@FreeBSD.org, rik@FreeBSD.org, glebius@FreeBSD.org,
	andre@FreeBSD.org, thompsa@FreeBSD.org
Subject: Re: kern/109815: wrong interface identifier at pfil_hooks for vlans +	if_bridge
Date: Sun, 4 Mar 2007 09:22:03 +0300

 Sun, Mar 04, 2007 at 01:08:40AM +0300, Roman Kurakin wrote:
 > The idea behind current code could be that in case of bridge the interface for
 > which this
 > packet in?nded is much more important than the physical interface it is arrived 
 > from.
 
 So, you're saying the following: let us have two interfaces in the
 bridge ifA and ifB with the MAC-A and MAC-B. In the current situation
 packet coming from the physical interface ifA but destined to the
 MAC-B, then the interface seen by the packet filter will be ifB and
 not the ifA. Right?
 
 In principle, this situation can be used for something. But then we
 should at least teah BPF to behave this way, because as you remember
 from spending three hours before the console with me and trying to
 diagnose the problem with tcpdump we were amazed to see the discrepance
 between bpf and pfil. So it should be at least documented.
 
 But as I understand, my patch will let the described situation to
 work as usual -- packets will still be delivered to the ifB, but
 packet filter will see the physical incoming interface. The patch
 should not break the delivery of the packet since all I do is the
 change of the rcvif. Or I am wrong?
 
 > If this is the case, than it would be much better do the same logic for ifp and 
 > in case
 > it is not that interface to check the list. This will fix the problem in case 
 > of vlans and
 > will leave the old behavior for the other cases.
 > 
 > Any comments?
 
 I am eager to listen to the comments on the current behaviour too,
 because as I understand the situation, the offending code in if_bridge
 was just written with the thoughts that the MAC address in a single
 system  uniquely identifies the interface.
 -- 
 Eygene
State-Changed-From-To: open->feedback 
State-Changed-By: rik 
State-Changed-When: Sun Mar 18 22:40:38 UTC 2007 
State-Changed-Why:  
The problem was discussed on freebsd-net@. 
Final patch was provided. 
Feedback actually was already received, but this state 
is much more appropriate before commit. 



Responsible-Changed-From-To: freebsd-bugs->rik  
Responsible-Changed-By: rik 
Responsible-Changed-When: Sun Mar 18 22:40:38 UTC 2007 
Responsible-Changed-Why:  
The problem was discussed on freebsd-net@. 
Final patch was provided. 
Feedback actually was already received, but this state 
is much more appropriate before commit. 


http://www.freebsd.org/cgi/query-pr.cgi?pr=109815 

From: dfilter@FreeBSD.ORG (dfilter service)
To: bug-followup@FreeBSD.org
Cc:  
Subject: Re: kern/109815: commit references a PR
Date: Sun, 18 Mar 2007 23:29:00 +0000 (UTC)

 rik         2007-03-18 23:28:53 UTC
 
   FreeBSD src repository
 
   Modified files:
     sys/net              if_bridge.c 
   Log:
   Give a chance for packet to appear with a correct input interfaces
   in case of multiple interfaces with the same MAC in the same bridge.
   This commit do not solve the entire problem. Only case where packet
   arrived from such interface.
   
   PR:     kern/109815
   MFC after:      7 days
   Submitted by:   Eygene Ryabinkin and rik@
   Discussed with: bms@, thompsa@, yar@
   
   Revision  Changes    Path
   1.96      +50 -30    src/sys/net/if_bridge.c
 _______________________________________________
 cvs-all@freebsd.org mailing list
 http://lists.freebsd.org/mailman/listinfo/cvs-all
 To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
 

From: dfilter@FreeBSD.ORG (dfilter service)
To: bug-followup@FreeBSD.org
Cc:  
Subject: Re: kern/109815: commit references a PR
Date: Sun, 25 Mar 2007 21:33:44 +0000 (UTC)

 rik         2007-03-25 21:33:38 UTC
 
   FreeBSD src repository
 
   Modified files:        (Branch: RELENG_6)
     sys/net              if_bridge.c 
   Log:
   MFC: -j 1.95 -j 1.96
     rik         2007-03-18 23:28:53 UTC
   
     FreeBSD src repository
   
     Modified files:
       sys/net              if_bridge.c
     Log:
     Give a chance for packet to appear with a correct input interfaces
     in case of multiple interfaces with the same MAC in the same bridge.
     This commit do not solve the entire problem. Only case where packet
     arrived from such interface.
   
     PR:     kern/109815
     MFC after:      7 days
     Submitted by:   Eygene Ryabinkin and rik@
     Discussed with: bms@, thompsa@, yar@
   
     Revision  Changes    Path
     1.96      +50 -30    src/sys/net/if_bridge.c
   
   Revision   Changes    Path
   1.11.2.48  +50 -30    src/sys/net/if_bridge.c
 _______________________________________________
 cvs-all@freebsd.org mailing list
 http://lists.freebsd.org/mailman/listinfo/cvs-all
 To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
 

From: dfilter@FreeBSD.ORG (dfilter service)
To: bug-followup@FreeBSD.org
Cc:  
Subject: Re: kern/109815: commit references a PR
Date: Mon,  2 Apr 2007 22:04:29 +0000 (UTC)

 rik         2007-04-02 22:04:21 UTC
 
   FreeBSD src repository
 
   Modified files:
     share/man/man4       if_bridge.4 
   Log:
   Add description how the filter works in case of multiple interfaces
   with the same MAC.
   
   PR:     kern/109815
   MFC after:      7 days
   Submitted by:   Eygene Ryabinkin
   Glanced by:     rik (all pointy hats are mine)
   Discussed with: julian@, rik@
   
   Revision  Changes    Path
   1.27      +92 -3     src/share/man/man4/if_bridge.4
 _______________________________________________
 cvs-all@freebsd.org mailing list
 http://lists.freebsd.org/mailman/listinfo/cvs-all
 To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
 

From: dfilter@FreeBSD.ORG (dfilter service)
To: bug-followup@FreeBSD.org
Cc:  
Subject: Re: kern/109815: commit references a PR
Date: Mon,  9 Apr 2007 00:08:02 +0000 (UTC)

 rik         2007-04-09 00:07:54 UTC
 
   FreeBSD src repository
 
   Modified files:        (Branch: RELENG_6)
     share/man/man4       if_bridge.4 
   Log:
   MFC: -j 1.26 -j 1.28
       Log:
       Add description how the filter works in case of multiple interfaces
       with the same MAC.
   
       PR:     kern/109815
       MFC after:      7 days
       Submitted by:   Eygene Ryabinkin
       Glanced by:     rik (all pointy hats are mine)
       Discussed with: julian@, rik@
   
       Log:
       s/if_vlan/vlan/
   
       Noted by: brueffer
   
   Revision  Changes    Path
   1.5.2.15  +92 -3     src/share/man/man4/if_bridge.4
 _______________________________________________
 cvs-all@freebsd.org mailing list
 http://lists.freebsd.org/mailman/listinfo/cvs-all
 To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
 
State-Changed-From-To: feedback->closed 
State-Changed-By: rik 
State-Changed-When: Mon Apr 9 09:38:12 UTC 2007 
State-Changed-Why:  
The patch has been commited. The case is closed. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=109815 
>Unformatted:
