net: Optimize non-gso test checks
authorKrishna Kumar <krkumar2@in.ibm.com>
Thu, 21 Jan 2010 09:26:29 +0000 (01:26 -0800)
committerDavid S. Miller <davem@davemloft.net>
Thu, 21 Jan 2010 09:26:29 +0000 (01:26 -0800)
Avoid checking twice whether skb needs to be linearized, if one
skb_linearize was already done.

Signed-off-by: Krishna Kumar <krkumar2@in.ibm.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
net/core/dev.c

index 5747b9edc1bb03b24075349a293cfaa7bd389e85..4fad9db417b1b3b9657bf97f71d335fb9b771578 100644 (file)
@@ -1982,6 +1982,21 @@ static inline int __dev_xmit_skb(struct sk_buff *skb, struct Qdisc *q,
        return rc;
 }
 
+/*
+ * Returns true if either:
+ *     1. skb has frag_list and the device doesn't support FRAGLIST, or
+ *     2. skb is fragmented and the device does not support SG, or if
+ *        at least one of fragments is in highmem and device does not
+ *        support DMA from it.
+ */
+static inline int skb_needs_linearize(struct sk_buff *skb,
+                                     struct net_device *dev)
+{
+       return (skb_has_frags(skb) && !(dev->features & NETIF_F_FRAGLIST)) ||
+              (skb_shinfo(skb)->nr_frags && (!(dev->features & NETIF_F_SG) ||
+                                             illegal_highdma(dev, skb)));
+}
+
 /**
  *     dev_queue_xmit - transmit a buffer
  *     @skb: buffer to transmit
@@ -2018,18 +2033,8 @@ int dev_queue_xmit(struct sk_buff *skb)
        if (netif_needs_gso(dev, skb))
                goto gso;
 
-       if (skb_has_frags(skb) &&
-           !(dev->features & NETIF_F_FRAGLIST) &&
-           __skb_linearize(skb))
-               goto out_kfree_skb;
-
-       /* Fragmented skb is linearized if device does not support SG,
-        * or if at least one of fragments is in highmem and device
-        * does not support DMA from it.
-        */
-       if (skb_shinfo(skb)->nr_frags &&
-           (!(dev->features & NETIF_F_SG) || illegal_highdma(dev, skb)) &&
-           __skb_linearize(skb))
+       /* Convert a paged skb to linear, if required */
+       if (skb_needs_linearize(skb, dev) && __skb_linearize(skb))
                goto out_kfree_skb;
 
        /* If packet is not checksummed and device does not support