aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv4/ip_output.c
diff options
context:
space:
mode:
authorSteffen Klassert <steffen.klassert@secunet.com>2011-06-05 16:48:47 -0400
committerDavid S. Miller <davem@davemloft.net>2011-06-09 17:49:59 -0400
commit96d7303e9cfb6a9bc664174a4dfdb6fa689284fe (patch)
tree5478498eaa5f23f2548930d83b06b3ee1280856d /net/ipv4/ip_output.c
parente23535ca11525945bd7fca05ac5941efba232498 (diff)
ipv4: Fix packet size calculation for raw IPsec packets in __ip_append_data
We assume that transhdrlen is positive on the first fragment which is wrong for raw packets. So we don't add exthdrlen to the packet size for raw packets. This leads to a reallocation on IPsec because we have not enough headroom on the skb to place the IPsec headers. This patch fixes this by adding exthdrlen to the packet size whenever the send queue of the socket is empty. This issue was introduced with git commit 1470ddf7 (inet: Remove explicit write references to sk/inet in ip_append_data) Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv4/ip_output.c')
-rw-r--r--net/ipv4/ip_output.c6
1 files changed, 3 insertions, 3 deletions
diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c
index 98af3697c718..a8024eaa0e87 100644
--- a/net/ipv4/ip_output.c
+++ b/net/ipv4/ip_output.c
@@ -799,7 +799,9 @@ static int __ip_append_data(struct sock *sk,
799 int csummode = CHECKSUM_NONE; 799 int csummode = CHECKSUM_NONE;
800 struct rtable *rt = (struct rtable *)cork->dst; 800 struct rtable *rt = (struct rtable *)cork->dst;
801 801
802 exthdrlen = transhdrlen ? rt->dst.header_len : 0; 802 skb = skb_peek_tail(queue);
803
804 exthdrlen = !skb ? rt->dst.header_len : 0;
803 length += exthdrlen; 805 length += exthdrlen;
804 transhdrlen += exthdrlen; 806 transhdrlen += exthdrlen;
805 mtu = cork->fragsize; 807 mtu = cork->fragsize;
@@ -825,8 +827,6 @@ static int __ip_append_data(struct sock *sk,
825 !exthdrlen) 827 !exthdrlen)
826 csummode = CHECKSUM_PARTIAL; 828 csummode = CHECKSUM_PARTIAL;
827 829
828 skb = skb_peek_tail(queue);
829
830 cork->length += length; 830 cork->length += length;
831 if (((length > mtu) || (skb && skb_is_gso(skb))) && 831 if (((length > mtu) || (skb && skb_is_gso(skb))) &&
832 (sk->sk_protocol == IPPROTO_UDP) && 832 (sk->sk_protocol == IPPROTO_UDP) &&