summaryrefslogtreecommitdiffstats
path: root/sys/dev/e1000
diff options
context:
space:
mode:
authorjfv <jfv@FreeBSD.org>2010-01-30 00:11:44 +0000
committerjfv <jfv@FreeBSD.org>2010-01-30 00:11:44 +0000
commit248442cb37a7afa0c71a61294afe194b8f72e0d9 (patch)
treee38b0c8200c8aa116999fa10570a2cb7fa4c9311 /sys/dev/e1000
parent70c89bf0f60c00809fd90f6374c58d2eade5e5fe (diff)
downloadFreeBSD-src-248442cb37a7afa0c71a61294afe194b8f72e0d9.zip
FreeBSD-src-248442cb37a7afa0c71a61294afe194b8f72e0d9.tar.gz
Fix for kern/141646: when stacking pseudo drivers like
lagg and vlan the vlan attach/detach event is not being handed down to em, this caused some init code not to run, and thus VLANs did not work. Ultimately having the event get propagated would be nice, but for now the solution is to have HWFILTER off by default, when this is the case VLANs will work, ifconfig can be used to turn it on and then get HW tag filtering.
Diffstat (limited to 'sys/dev/e1000')
-rw-r--r--sys/dev/e1000/if_em.c44
1 files changed, 30 insertions, 14 deletions
diff --git a/sys/dev/e1000/if_em.c b/sys/dev/e1000/if_em.c
index 5f2a4f6..ca1b0a7 100644
--- a/sys/dev/e1000/if_em.c
+++ b/sys/dev/e1000/if_em.c
@@ -94,7 +94,7 @@ int em_display_debug_stats = 0;
/*********************************************************************
* Driver version:
*********************************************************************/
-char em_driver_version[] = "6.9.24";
+char em_driver_version[] = "6.9.25";
/*********************************************************************
@@ -1287,6 +1287,12 @@ em_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
ifp->if_capenable ^= IFCAP_VLAN_HWTAGGING;
reinit = 1;
}
+
+ if (mask & IFCAP_VLAN_HWFILTER) {
+ ifp->if_capenable ^= IFCAP_VLAN_HWFILTER;
+ reinit = 1;
+ }
+
if ((mask & IFCAP_WOL) &&
(ifp->if_capabilities & IFCAP_WOL) != 0) {
if (mask & IFCAP_WOL_MCAST)
@@ -1294,6 +1300,7 @@ em_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
if (mask & IFCAP_WOL_MAGIC)
ifp->if_capenable ^= IFCAP_WOL_MAGIC;
}
+
if (reinit && (ifp->if_drv_flags & IFF_DRV_RUNNING))
em_init(adapter);
#if __FreeBSD_version >= 700000
@@ -1420,18 +1427,17 @@ em_init_locked(struct adapter *adapter)
/* Setup VLAN support, basic and offload if available */
E1000_WRITE_REG(&adapter->hw, E1000_VET, ETHERTYPE_VLAN);
-
-#if __FreeBSD_version < 700029
if (ifp->if_capenable & IFCAP_VLAN_HWTAGGING) {
- u32 ctrl;
- ctrl = E1000_READ_REG(&adapter->hw, E1000_CTRL);
- ctrl |= E1000_CTRL_VME;
- E1000_WRITE_REG(&adapter->hw, E1000_CTRL, ctrl);
+ if (ifp->if_capenable & IFCAP_VLAN_HWFILTER)
+ /* Use real VLAN Filter support */
+ em_setup_vlan_hw_support(adapter);
+ else {
+ u32 ctrl;
+ ctrl = E1000_READ_REG(&adapter->hw, E1000_CTRL);
+ ctrl |= E1000_CTRL_VME;
+ E1000_WRITE_REG(&adapter->hw, E1000_CTRL, ctrl);
+ }
}
-#else
- /* Use real VLAN Filter support */
- em_setup_vlan_hw_support(adapter);
-#endif
/* Set hardware offload abilities */
ifp->if_hwassist = 0;
@@ -3123,13 +3129,23 @@ em_setup_interface(device_t dev, struct adapter *adapter)
if (adapter->hw.mac.type >= e1000_82571)
ifp->if_capenable |= IFCAP_TSO4;
#endif
-
/*
- * Tell the upper layer(s) we support long frames.
+ * Tell the upper layer(s) we
+ * support full VLAN capability
*/
ifp->if_data.ifi_hdrlen = sizeof(struct ether_vlan_header);
ifp->if_capabilities |= IFCAP_VLAN_HWTAGGING | IFCAP_VLAN_MTU;
- ifp->if_capenable |= IFCAP_VLAN_HWTAGGING | IFCAP_VLAN_MTU;
+ ifp->if_capenable |= (IFCAP_VLAN_MTU | IFCAP_VLAN_HWTAGGING);
+
+ /*
+ ** Dont turn this on by default, if vlans are
+ ** created on another pseudo device (eg. lagg)
+ ** then vlan events are not passed thru, breaking
+ ** operation, but with HW FILTER off it works. If
+ ** using vlans directly on the em driver you can
+ ** enable this and get full hardware tag filtering.
+ */
+ ifp->if_capabilities |= IFCAP_VLAN_HWFILTER;
#ifdef DEVICE_POLLING
ifp->if_capabilities |= IFCAP_POLLING;
OpenPOWER on IntegriCloud