diff options
| author | Jason Wang <jasowang@redhat.com> | 2013-03-25 20:19:58 +0000 | 
|---|---|---|
| committer | David S. Miller <davem@davemloft.net> | 2013-03-26 12:44:44 -0400 | 
| commit | f9ca8f74399f9195fd8e01f67a8424a8d33efa55 (patch) | |
| tree | 8d46024f2e5c82b0c811c87c8a9924b0efdd28dd /drivers/net/xen-netback/netback.c | |
| parent | c1aad275b0293d2b1905ec95a945422262470684 (diff) | |
| download | olio-linux-3.10-f9ca8f74399f9195fd8e01f67a8424a8d33efa55.tar.xz olio-linux-3.10-f9ca8f74399f9195fd8e01f67a8424a8d33efa55.zip  | |
netback: set transport header before passing it to kernel
Currently, for the packets receives from netback, before doing header check,
kernel just reset the transport header in netif_receive_skb() which pretends non
l4 header. This is suboptimal for precise packet length estimation (introduced
in 1def9238: net_sched: more precise pkt_len computation) which needs correct l4
header for gso packets.
The patch just reuse the header probed by netback for partial checksum packets
and tries to use skb_flow_dissect() for other cases, if both fail, just pretend
no l4 header.
Cc: Eric Dumazet <edumazet@google.com>
Cc: Ian Campbell <ian.campbell@citrix.com>
Signed-off-by: Jason Wang <jasowang@redhat.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/xen-netback/netback.c')
| -rw-r--r-- | drivers/net/xen-netback/netback.c | 12 | 
1 files changed, 12 insertions, 0 deletions
diff --git a/drivers/net/xen-netback/netback.c b/drivers/net/xen-netback/netback.c index aa28550fc9b..fc8faa74b25 100644 --- a/drivers/net/xen-netback/netback.c +++ b/drivers/net/xen-netback/netback.c @@ -39,6 +39,7 @@  #include <linux/udp.h>  #include <net/tcp.h> +#include <net/flow_keys.h>  #include <xen/xen.h>  #include <xen/events.h> @@ -1184,6 +1185,7 @@ static int checksum_setup(struct xenvif *vif, struct sk_buff *skb)  	if (th >= skb_tail_pointer(skb))  		goto out; +	skb_set_transport_header(skb, 4 * iph->ihl);  	skb->csum_start = th - skb->head;  	switch (iph->protocol) {  	case IPPROTO_TCP: @@ -1495,6 +1497,7 @@ static void xen_netbk_tx_submit(struct xen_netbk *netbk)  		skb->dev      = vif->dev;  		skb->protocol = eth_type_trans(skb, skb->dev); +		skb_reset_network_header(skb);  		if (checksum_setup(vif, skb)) {  			netdev_dbg(vif->dev, @@ -1503,6 +1506,15 @@ static void xen_netbk_tx_submit(struct xen_netbk *netbk)  			continue;  		} +		if (!skb_transport_header_was_set(skb)) { +			struct flow_keys keys; + +			if (skb_flow_dissect(skb, &keys)) +				skb_set_transport_header(skb, keys.thoff); +			else +				skb_reset_transport_header(skb); +		} +  		vif->dev->stats.rx_bytes += skb->len;  		vif->dev->stats.rx_packets++;  |