diff options
author | Jesse Gross <jesse@nicira.com> | 2011-06-23 09:04:39 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2011-06-27 23:56:51 -0400 |
commit | 72e85c45b9541e1f3d233e775da1dc6f68b85867 (patch) | |
tree | f5cb5ae4166282031c77fc8dc3a324a43304679e /drivers/net/vmxnet3/vmxnet3_drv.c | |
parent | cfbf7586bc07cd6d14cd93ca56d8a3f90e248625 (diff) |
vmxnet3: Convert to new vlan model.
This converts the vmxnet3 driver to use the new vlan model. In doing so
it fixes missing tags in tcpdump and failure to do checksum offload when
tx vlan offload is disabled.
CC: Shreyas Bhatewara <sbhatewara@vmware.com>
CC: VMware PV-Drivers <pv-drivers@vmware.com>
Signed-off-by: Jesse Gross <jesse@nicira.com>
Signed-off-by: Scott J. Goldman <scottjg@vmware.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/vmxnet3/vmxnet3_drv.c')
-rw-r--r-- | drivers/net/vmxnet3/vmxnet3_drv.c | 111 |
1 files changed, 30 insertions, 81 deletions
diff --git a/drivers/net/vmxnet3/vmxnet3_drv.c b/drivers/net/vmxnet3/vmxnet3_drv.c index 33097ec1c514..c84b1dd02a78 100644 --- a/drivers/net/vmxnet3/vmxnet3_drv.c +++ b/drivers/net/vmxnet3/vmxnet3_drv.c | |||
@@ -918,7 +918,7 @@ vmxnet3_tq_xmit(struct sk_buff *skb, struct vmxnet3_tx_queue *tq, | |||
918 | count = VMXNET3_TXD_NEEDED(skb_headlen(skb)) + | 918 | count = VMXNET3_TXD_NEEDED(skb_headlen(skb)) + |
919 | skb_shinfo(skb)->nr_frags + 1; | 919 | skb_shinfo(skb)->nr_frags + 1; |
920 | 920 | ||
921 | ctx.ipv4 = (skb->protocol == cpu_to_be16(ETH_P_IP)); | 921 | ctx.ipv4 = (vlan_get_protocol(skb) == cpu_to_be16(ETH_P_IP)); |
922 | 922 | ||
923 | ctx.mss = skb_shinfo(skb)->gso_size; | 923 | ctx.mss = skb_shinfo(skb)->gso_size; |
924 | if (ctx.mss) { | 924 | if (ctx.mss) { |
@@ -1231,12 +1231,10 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq, | |||
1231 | (union Vmxnet3_GenericDesc *)rcd); | 1231 | (union Vmxnet3_GenericDesc *)rcd); |
1232 | skb->protocol = eth_type_trans(skb, adapter->netdev); | 1232 | skb->protocol = eth_type_trans(skb, adapter->netdev); |
1233 | 1233 | ||
1234 | if (unlikely(adapter->vlan_grp && rcd->ts)) { | 1234 | if (unlikely(rcd->ts)) |
1235 | vlan_hwaccel_receive_skb(skb, | 1235 | __vlan_hwaccel_put_tag(skb, rcd->tci); |
1236 | adapter->vlan_grp, rcd->tci); | 1236 | |
1237 | } else { | 1237 | netif_receive_skb(skb); |
1238 | netif_receive_skb(skb); | ||
1239 | } | ||
1240 | 1238 | ||
1241 | ctx->skb = NULL; | 1239 | ctx->skb = NULL; |
1242 | } | 1240 | } |
@@ -1856,79 +1854,18 @@ vmxnet3_free_irqs(struct vmxnet3_adapter *adapter) | |||
1856 | } | 1854 | } |
1857 | } | 1855 | } |
1858 | 1856 | ||
1859 | static void | ||
1860 | vmxnet3_vlan_rx_register(struct net_device *netdev, struct vlan_group *grp) | ||
1861 | { | ||
1862 | struct vmxnet3_adapter *adapter = netdev_priv(netdev); | ||
1863 | struct Vmxnet3_DriverShared *shared = adapter->shared; | ||
1864 | u32 *vfTable = adapter->shared->devRead.rxFilterConf.vfTable; | ||
1865 | unsigned long flags; | ||
1866 | |||
1867 | if (grp) { | ||
1868 | /* add vlan rx stripping. */ | ||
1869 | if (adapter->netdev->features & NETIF_F_HW_VLAN_RX) { | ||
1870 | int i; | ||
1871 | adapter->vlan_grp = grp; | ||
1872 | |||
1873 | /* | ||
1874 | * Clear entire vfTable; then enable untagged pkts. | ||
1875 | * Note: setting one entry in vfTable to non-zero turns | ||
1876 | * on VLAN rx filtering. | ||
1877 | */ | ||
1878 | for (i = 0; i < VMXNET3_VFT_SIZE; i++) | ||
1879 | vfTable[i] = 0; | ||
1880 | |||
1881 | VMXNET3_SET_VFTABLE_ENTRY(vfTable, 0); | ||
1882 | spin_lock_irqsave(&adapter->cmd_lock, flags); | ||
1883 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | ||
1884 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); | ||
1885 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); | ||
1886 | } else { | ||
1887 | printk(KERN_ERR "%s: vlan_rx_register when device has " | ||
1888 | "no NETIF_F_HW_VLAN_RX\n", netdev->name); | ||
1889 | } | ||
1890 | } else { | ||
1891 | /* remove vlan rx stripping. */ | ||
1892 | struct Vmxnet3_DSDevRead *devRead = &shared->devRead; | ||
1893 | adapter->vlan_grp = NULL; | ||
1894 | |||
1895 | if (devRead->misc.uptFeatures & UPT1_F_RXVLAN) { | ||
1896 | int i; | ||
1897 | |||
1898 | for (i = 0; i < VMXNET3_VFT_SIZE; i++) { | ||
1899 | /* clear entire vfTable; this also disables | ||
1900 | * VLAN rx filtering | ||
1901 | */ | ||
1902 | vfTable[i] = 0; | ||
1903 | } | ||
1904 | spin_lock_irqsave(&adapter->cmd_lock, flags); | ||
1905 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | ||
1906 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); | ||
1907 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); | ||
1908 | } | ||
1909 | } | ||
1910 | } | ||
1911 | |||
1912 | 1857 | ||
1913 | static void | 1858 | static void |
1914 | vmxnet3_restore_vlan(struct vmxnet3_adapter *adapter) | 1859 | vmxnet3_restore_vlan(struct vmxnet3_adapter *adapter) |
1915 | { | 1860 | { |
1916 | if (adapter->vlan_grp) { | 1861 | u32 *vfTable = adapter->shared->devRead.rxFilterConf.vfTable; |
1917 | u16 vid; | 1862 | u16 vid; |
1918 | u32 *vfTable = adapter->shared->devRead.rxFilterConf.vfTable; | ||
1919 | bool activeVlan = false; | ||
1920 | 1863 | ||
1921 | for (vid = 0; vid < VLAN_N_VID; vid++) { | 1864 | /* allow untagged pkts */ |
1922 | if (vlan_group_get_device(adapter->vlan_grp, vid)) { | 1865 | VMXNET3_SET_VFTABLE_ENTRY(vfTable, 0); |
1923 | VMXNET3_SET_VFTABLE_ENTRY(vfTable, vid); | 1866 | |
1924 | activeVlan = true; | 1867 | for_each_set_bit(vid, adapter->active_vlans, VLAN_N_VID) |
1925 | } | 1868 | VMXNET3_SET_VFTABLE_ENTRY(vfTable, vid); |
1926 | } | ||
1927 | if (activeVlan) { | ||
1928 | /* continue to allow untagged pkts */ | ||
1929 | VMXNET3_SET_VFTABLE_ENTRY(vfTable, 0); | ||
1930 | } | ||
1931 | } | ||
1932 | } | 1869 | } |
1933 | 1870 | ||
1934 | 1871 | ||
@@ -1944,6 +1881,8 @@ vmxnet3_vlan_rx_add_vid(struct net_device *netdev, u16 vid) | |||
1944 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | 1881 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, |
1945 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); | 1882 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); |
1946 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); | 1883 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); |
1884 | |||
1885 | set_bit(vid, adapter->active_vlans); | ||
1947 | } | 1886 | } |
1948 | 1887 | ||
1949 | 1888 | ||
@@ -1959,6 +1898,8 @@ vmxnet3_vlan_rx_kill_vid(struct net_device *netdev, u16 vid) | |||
1959 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | 1898 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, |
1960 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); | 1899 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); |
1961 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); | 1900 | spin_unlock_irqrestore(&adapter->cmd_lock, flags); |
1901 | |||
1902 | clear_bit(vid, adapter->active_vlans); | ||
1962 | } | 1903 | } |
1963 | 1904 | ||
1964 | 1905 | ||
@@ -1995,8 +1936,14 @@ vmxnet3_set_mc(struct net_device *netdev) | |||
1995 | u8 *new_table = NULL; | 1936 | u8 *new_table = NULL; |
1996 | u32 new_mode = VMXNET3_RXM_UCAST; | 1937 | u32 new_mode = VMXNET3_RXM_UCAST; |
1997 | 1938 | ||
1998 | if (netdev->flags & IFF_PROMISC) | 1939 | if (netdev->flags & IFF_PROMISC) { |
1940 | u32 *vfTable = adapter->shared->devRead.rxFilterConf.vfTable; | ||
1941 | memset(vfTable, 0, VMXNET3_VFT_SIZE * sizeof(*vfTable)); | ||
1942 | |||
1999 | new_mode |= VMXNET3_RXM_PROMISC; | 1943 | new_mode |= VMXNET3_RXM_PROMISC; |
1944 | } else { | ||
1945 | vmxnet3_restore_vlan(adapter); | ||
1946 | } | ||
2000 | 1947 | ||
2001 | if (netdev->flags & IFF_BROADCAST) | 1948 | if (netdev->flags & IFF_BROADCAST) |
2002 | new_mode |= VMXNET3_RXM_BCAST; | 1949 | new_mode |= VMXNET3_RXM_BCAST; |
@@ -2030,6 +1977,8 @@ vmxnet3_set_mc(struct net_device *netdev) | |||
2030 | rxConf->rxMode = cpu_to_le32(new_mode); | 1977 | rxConf->rxMode = cpu_to_le32(new_mode); |
2031 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | 1978 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, |
2032 | VMXNET3_CMD_UPDATE_RX_MODE); | 1979 | VMXNET3_CMD_UPDATE_RX_MODE); |
1980 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | ||
1981 | VMXNET3_CMD_UPDATE_VLAN_FILTERS); | ||
2033 | } | 1982 | } |
2034 | 1983 | ||
2035 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, | 1984 | VMXNET3_WRITE_BAR1_REG(adapter, VMXNET3_REG_CMD, |
@@ -2639,12 +2588,13 @@ vmxnet3_declare_features(struct vmxnet3_adapter *adapter, bool dma64) | |||
2639 | 2588 | ||
2640 | netdev->hw_features = NETIF_F_SG | NETIF_F_RXCSUM | | 2589 | netdev->hw_features = NETIF_F_SG | NETIF_F_RXCSUM | |
2641 | NETIF_F_HW_CSUM | NETIF_F_HW_VLAN_TX | | 2590 | NETIF_F_HW_CSUM | NETIF_F_HW_VLAN_TX | |
2642 | NETIF_F_TSO | NETIF_F_TSO6 | NETIF_F_LRO; | 2591 | NETIF_F_HW_VLAN_RX | NETIF_F_TSO | NETIF_F_TSO6 | |
2592 | NETIF_F_LRO; | ||
2643 | if (dma64) | 2593 | if (dma64) |
2644 | netdev->features |= NETIF_F_HIGHDMA; | 2594 | netdev->features |= NETIF_F_HIGHDMA; |
2645 | netdev->vlan_features = netdev->hw_features & ~NETIF_F_HW_VLAN_TX; | 2595 | netdev->vlan_features = netdev->hw_features & |
2646 | netdev->features = netdev->hw_features | | 2596 | ~(NETIF_F_HW_VLAN_TX | NETIF_F_HW_VLAN_RX); |
2647 | NETIF_F_HW_VLAN_RX | NETIF_F_HW_VLAN_FILTER; | 2597 | netdev->features = netdev->hw_features | NETIF_F_HW_VLAN_FILTER; |
2648 | 2598 | ||
2649 | netdev_info(adapter->netdev, | 2599 | netdev_info(adapter->netdev, |
2650 | "features: sg csum vlan jf tso tsoIPv6 lro%s\n", | 2600 | "features: sg csum vlan jf tso tsoIPv6 lro%s\n", |
@@ -2865,7 +2815,6 @@ vmxnet3_probe_device(struct pci_dev *pdev, | |||
2865 | .ndo_get_stats64 = vmxnet3_get_stats64, | 2815 | .ndo_get_stats64 = vmxnet3_get_stats64, |
2866 | .ndo_tx_timeout = vmxnet3_tx_timeout, | 2816 | .ndo_tx_timeout = vmxnet3_tx_timeout, |
2867 | .ndo_set_multicast_list = vmxnet3_set_mc, | 2817 | .ndo_set_multicast_list = vmxnet3_set_mc, |
2868 | .ndo_vlan_rx_register = vmxnet3_vlan_rx_register, | ||
2869 | .ndo_vlan_rx_add_vid = vmxnet3_vlan_rx_add_vid, | 2818 | .ndo_vlan_rx_add_vid = vmxnet3_vlan_rx_add_vid, |
2870 | .ndo_vlan_rx_kill_vid = vmxnet3_vlan_rx_kill_vid, | 2819 | .ndo_vlan_rx_kill_vid = vmxnet3_vlan_rx_kill_vid, |
2871 | #ifdef CONFIG_NET_POLL_CONTROLLER | 2820 | #ifdef CONFIG_NET_POLL_CONTROLLER |