Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 03 Oct 1996 02:11:34 -0700
From:      mccanne@eecs.berkeley.edu (Steven McCanne)
To:        bugs@freebsd.org
Subject:   bpf and multicast don't work in pci/if_vx.c
Message-ID:  <199610030911.CAA13487@durant.cs.berkeley.edu>

next in thread | raw e-mail | index | archive | help
Attached is a patch to the vx driver that fixes a bug
related to bpf and adds multicast support.
(w/o this patch bpf_mtap is never called because the
pointer address passed to bpfattach is not the same
as the pointer tested in the recv/xmit path).

Steve

*** pci/if_vx.c	1996/09/29 21:03:24	1.1
--- pci/if_vx.c	1996/10/03 07:51:32
***************
*** 52,57 ****
--- 52,66 ----
   *          babkin@hq.icb.chel.su
   */
  
+ /*
+  * Sep 29, 1996
+  * Multicast support and bpf bug fixes.
+  *
+  * Steven McCanne
+  * http://www.cs.berkeley.edu/~mccanne/
+  * mccanne@cs.berkeley.edu
+  */
+ 
  #include "vx.h"
  #if NVX > 0
  
***************
*** 254,260 ****
      ifp->if_unit = unit;
      ifp->if_name = "vx";
      ifp->if_mtu = ETHERMTU;
!     ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX /*| IFF_NOTRAILERS*/;
      ifp->if_output = ether_output;
      ifp->if_start = vxstart;
      ifp->if_ioctl = vxioctl;
--- 263,269 ----
      ifp->if_unit = unit;
      ifp->if_name = "vx";
      ifp->if_mtu = ETHERMTU;
!     ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
      ifp->if_output = ether_output;
      ifp->if_start = vxstart;
      ifp->if_ioctl = vxioctl;
***************
*** 356,364 ****
  	if(ifp->if_flags & IFF_PROMISC)
  		outw(BASE + VX_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL |
  		 FIL_GROUP | FIL_BRDCST | FIL_ALL);
  	else
  		outw(BASE + VX_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL |
! 		 FIL_GROUP | FIL_BRDCST);
  
  	 /*
  	  * S.B.
--- 365,377 ----
  	if(ifp->if_flags & IFF_PROMISC)
  		outw(BASE + VX_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL |
  		 FIL_GROUP | FIL_BRDCST | FIL_ALL);
+ 	else if((ifp->if_flags & IFF_ALLMULTI) != 0 ||
+ 		sc->arpcom.ac_multiaddrs != 0)
+     		outw(BASE + VX_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL |
+ 		 FIL_GROUP | FIL_BRDCST | FIL_ALL);
  	else
  		outw(BASE + VX_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL |
! 		 FIL_BRDCST);
  
  	 /*
  	  * S.B.
***************
*** 552,558 ****
  	outb(BASE + VX_W1_TX_PIO_WR_1, 0);	/* Padding */
  
  #if NBPFILTER > 0
!     if (sc->arpcom.ac_if.if_bpf) {
  	bpf_mtap(sc->bpf, top);
      }
  #endif
--- 565,571 ----
  	outb(BASE + VX_W1_TX_PIO_WR_1, 0);	/* Padding */
  
  #if NBPFILTER > 0
!     if (sc->bpf) {
  	bpf_mtap(sc->bpf, top);
      }
  #endif
***************
*** 870,876 ****
      top->m_pkthdr.len = sc->cur_len;
  
  #if NBPFILTER > 0
!     if (sc->arpcom.ac_if.if_bpf) {
  	bpf_mtap(sc->bpf, top);
  
  	/*
--- 883,889 ----
      top->m_pkthdr.len = sc->cur_len;
  
  #if NBPFILTER > 0
!     if (sc->bpf) {
  	bpf_mtap(sc->bpf, top);
  
  	/*
***************
*** 880,889 ****
  	 */
  	eh = mtod(top, struct ether_header *);
  	if ((sc->arpcom.ac_if.if_flags & IFF_PROMISC) &&
  	    (eh->ether_dhost[0] & 1) == 0 &&
  	    bcmp(eh->ether_dhost, sc->arpcom.ac_enaddr,
- 		 sizeof(eh->ether_dhost)) != 0 &&
- 	    bcmp(eh->ether_dhost, etherbroadcastaddr,
  		 sizeof(eh->ether_dhost)) != 0) {
  	    if (sc->top) {
  		m_freem(sc->top);
--- 893,901 ----
  	 */
  	eh = mtod(top, struct ether_header *);
  	if ((sc->arpcom.ac_if.if_flags & IFF_PROMISC) &&
+ 	    /* non-multicast (also non-broadcast) */
  	    (eh->ether_dhost[0] & 1) == 0 &&
  	    bcmp(eh->ether_dhost, sc->arpcom.ac_enaddr,
  		 sizeof(eh->ether_dhost)) != 0) {
  	    if (sc->top) {
  		m_freem(sc->top);
***************
*** 1014,1020 ****
--- 1026,1058 ----
  	    vxinit(ifp->if_unit);
  	    }
  
+ 	if ( (ifp->if_flags & IFF_ALLMULTI) &&  !vx_ftst(F_ALLMULTI) ) {
+ 	    vx_fset(F_ALLMULTI);
+ 	    vxinit(ifp->if_unit);
+ 	    }
+ 	else if( !(ifp->if_flags & IFF_ALLMULTI) && vx_ftst(F_ALLMULTI) ) {
+ 	    vx_frst(F_ALLMULTI);
+ 	    vxinit(ifp->if_unit);
+ 	    }
+ 
  	break;
+ 
+       case SIOCADDMULTI:
+       case SIOCDELMULTI:
+ 	/*
+ 	 * Update multicast listeners
+ 	 */
+ 	error = (cmd == SIOCADDMULTI ?
+ 		 ether_addmulti(ifr, &sc->arpcom) :
+ 		 ether_delmulti(ifr, &sc->arpcom));
+ 
+ 	if(error == ENETRESET) {
+ 	    /* reset multicast filtering */
+ 	    vxinit(ifp->if_unit);
+ 	    error = 0;
+ 	}
+ 	break;
+ 
  #ifdef notdef
        case SIOCGHWADDR:
  	bcopy((caddr_t) sc->sc_addr, (caddr_t) & ifr->ifr_data,
*** pci/if_vxreg.h	1996/09/29 21:12:27	1.1
--- pci/if_vxreg.h	1996/09/29 21:24:17
***************
*** 70,75 ****
--- 70,76 ----
  #define         F_WAIT_TRAIL 0x2
  #define         F_RX_TRAILER 0x4
  #define		F_PROMISC    0x8
+ #define		F_ALLMULTI   0x10
  
  #define         F_ACCESS_32_BITS 0x100
  



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199610030911.CAA13487>