summaryrefslogtreecommitdiffstats
path: root/include/linux/netdevice.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/linux/netdevice.h')
-rw-r--r--include/linux/netdevice.h75
1 files changed, 61 insertions, 14 deletions
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index bc747e5d713..9264139bd8d 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -187,7 +187,7 @@ struct hh_cache
{
struct hh_cache *hh_next; /* Next entry */
atomic_t hh_refcnt; /* number of users */
- unsigned short hh_type; /* protocol identifier, f.e ETH_P_IP
+ __be16 hh_type; /* protocol identifier, f.e ETH_P_IP
* NOTE: For VLANs, this will be the
* encapuslated type. --BLG
*/
@@ -313,8 +313,15 @@ struct net_device
/* Segmentation offload features */
#define NETIF_F_GSO_SHIFT 16
+#define NETIF_F_GSO_MASK 0xffff0000
#define NETIF_F_TSO (SKB_GSO_TCPV4 << NETIF_F_GSO_SHIFT)
-#define NETIF_F_UFO (SKB_GSO_UDPV4 << NETIF_F_GSO_SHIFT)
+#define NETIF_F_UFO (SKB_GSO_UDP << NETIF_F_GSO_SHIFT)
+#define NETIF_F_GSO_ROBUST (SKB_GSO_DODGY << NETIF_F_GSO_SHIFT)
+#define NETIF_F_TSO_ECN (SKB_GSO_TCP_ECN << NETIF_F_GSO_SHIFT)
+#define NETIF_F_TSO6 (SKB_GSO_TCPV6 << NETIF_F_GSO_SHIFT)
+
+ /* List of features with software fallbacks. */
+#define NETIF_F_GSO_SOFTWARE (NETIF_F_TSO | NETIF_F_TSO_ECN | NETIF_F_TSO6)
#define NETIF_F_GEN_CSUM (NETIF_F_NO_CSUM | NETIF_F_HW_CSUM)
#define NETIF_F_ALL_CSUM (NETIF_F_IP_CSUM | NETIF_F_GEN_CSUM)
@@ -327,7 +334,6 @@ struct net_device
struct net_device_stats* (*get_stats)(struct net_device *dev);
- struct iw_statistics* (*get_wireless_stats)(struct net_device *dev);
/* List of functions to handle Wireless Extensions (instead of ioctl).
* See <net/iw_handler.h> for details. Jean II */
@@ -335,7 +341,7 @@ struct net_device
/* Instance data managed by the core of Wireless Extensions. */
struct iw_public_data * wireless_data;
- struct ethtool_ops *ethtool_ops;
+ const struct ethtool_ops *ethtool_ops;
/*
* This marks the end of the "visible" part of the structure. All
@@ -543,7 +549,9 @@ struct packet_type {
struct net_device *,
struct packet_type *,
struct net_device *);
- struct sk_buff *(*gso_segment)(struct sk_buff *skb, int sg);
+ struct sk_buff *(*gso_segment)(struct sk_buff *skb,
+ int features);
+ int (*gso_send_check)(struct sk_buff *skb);
void *af_packet_priv;
struct list_head list;
};
@@ -699,7 +707,6 @@ extern int dev_hard_start_xmit(struct sk_buff *skb,
extern void dev_init(void);
-extern int netdev_nit;
extern int netdev_budget;
/* Called by rtnetlink.c:rtnl_unlock() */
@@ -919,10 +926,10 @@ static inline void netif_tx_lock_bh(struct net_device *dev)
static inline int netif_tx_trylock(struct net_device *dev)
{
- int err = spin_trylock(&dev->_xmit_lock);
- if (!err)
+ int ok = spin_trylock(&dev->_xmit_lock);
+ if (likely(ok))
dev->xmit_lock_owner = smp_processor_id();
- return err;
+ return ok;
}
static inline void netif_tx_unlock(struct net_device *dev)
@@ -968,8 +975,8 @@ extern void dev_mcast_init(void);
extern int netdev_max_backlog;
extern int weight_p;
extern int netdev_set_master(struct net_device *dev, struct net_device *master);
-extern int skb_checksum_help(struct sk_buff *skb, int inward);
-extern struct sk_buff *skb_gso_segment(struct sk_buff *skb, int sg);
+extern int skb_checksum_help(struct sk_buff *skb);
+extern struct sk_buff *skb_gso_segment(struct sk_buff *skb, int features);
#ifdef CONFIG_BUG
extern void netdev_rx_csum_fault(struct net_device *dev);
#else
@@ -989,11 +996,51 @@ extern void dev_seq_stop(struct seq_file *seq, void *v);
extern void linkwatch_run_queue(void);
+static inline int net_gso_ok(int features, int gso_type)
+{
+ int feature = gso_type << NETIF_F_GSO_SHIFT;
+ return (features & feature) == feature;
+}
+
+static inline int skb_gso_ok(struct sk_buff *skb, int features)
+{
+ return net_gso_ok(features, skb_shinfo(skb)->gso_type);
+}
+
static inline int netif_needs_gso(struct net_device *dev, struct sk_buff *skb)
{
- int feature = skb_shinfo(skb)->gso_type << NETIF_F_GSO_SHIFT;
- return skb_shinfo(skb)->gso_size &&
- (dev->features & feature) != feature;
+ return skb_is_gso(skb) &&
+ (!skb_gso_ok(skb, dev->features) ||
+ unlikely(skb->ip_summed != CHECKSUM_PARTIAL));
+}
+
+/* On bonding slaves other than the currently active slave, suppress
+ * duplicates except for 802.3ad ETH_P_SLOW, alb non-mcast/bcast, and
+ * ARP on active-backup slaves with arp_validate enabled.
+ */
+static inline int skb_bond_should_drop(struct sk_buff *skb)
+{
+ struct net_device *dev = skb->dev;
+ struct net_device *master = dev->master;
+
+ if (master &&
+ (dev->priv_flags & IFF_SLAVE_INACTIVE)) {
+ if ((dev->priv_flags & IFF_SLAVE_NEEDARP) &&
+ skb->protocol == __constant_htons(ETH_P_ARP))
+ return 0;
+
+ if (master->priv_flags & IFF_MASTER_ALB) {
+ if (skb->pkt_type != PACKET_BROADCAST &&
+ skb->pkt_type != PACKET_MULTICAST)
+ return 0;
+ }
+ if (master->priv_flags & IFF_MASTER_8023AD &&
+ skb->protocol == __constant_htons(ETH_P_SLOW))
+ return 0;
+
+ return 1;
+ }
+ return 0;
}
#endif /* __KERNEL__ */