diff options
author | David S. Miller <davem@davemloft.net> | 2011-10-24 18:18:09 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2011-10-24 18:18:09 -0400 |
commit | 1805b2f04855f07afe3a71d620a68f483b0ed74f (patch) | |
tree | b823b90f37f5404fcaef70f785c70112ca74a329 /drivers/net/ppp | |
parent | 78d81d15b74246c7cedf84894434890b33da3907 (diff) | |
parent | f42af6c486aa5ca6ee62800cb45c5b252020509d (diff) |
Merge branch 'master' of ra.kernel.org:/pub/scm/linux/kernel/git/davem/net
Diffstat (limited to 'drivers/net/ppp')
-rw-r--r-- | drivers/net/ppp/pptp.c | 22 |
1 files changed, 14 insertions, 8 deletions
diff --git a/drivers/net/ppp/pptp.c b/drivers/net/ppp/pptp.c index eae542a7e987..89f829f5f725 100644 --- a/drivers/net/ppp/pptp.c +++ b/drivers/net/ppp/pptp.c | |||
@@ -285,8 +285,10 @@ static int pptp_xmit(struct ppp_channel *chan, struct sk_buff *skb) | |||
285 | ip_send_check(iph); | 285 | ip_send_check(iph); |
286 | 286 | ||
287 | ip_local_out(skb); | 287 | ip_local_out(skb); |
288 | return 1; | ||
288 | 289 | ||
289 | tx_error: | 290 | tx_error: |
291 | kfree_skb(skb); | ||
290 | return 1; | 292 | return 1; |
291 | } | 293 | } |
292 | 294 | ||
@@ -305,11 +307,18 @@ static int pptp_rcv_core(struct sock *sk, struct sk_buff *skb) | |||
305 | } | 307 | } |
306 | 308 | ||
307 | header = (struct pptp_gre_header *)(skb->data); | 309 | header = (struct pptp_gre_header *)(skb->data); |
310 | headersize = sizeof(*header); | ||
308 | 311 | ||
309 | /* test if acknowledgement present */ | 312 | /* test if acknowledgement present */ |
310 | if (PPTP_GRE_IS_A(header->ver)) { | 313 | if (PPTP_GRE_IS_A(header->ver)) { |
311 | __u32 ack = (PPTP_GRE_IS_S(header->flags)) ? | 314 | __u32 ack; |
312 | header->ack : header->seq; /* ack in different place if S = 0 */ | 315 | |
316 | if (!pskb_may_pull(skb, headersize)) | ||
317 | goto drop; | ||
318 | header = (struct pptp_gre_header *)(skb->data); | ||
319 | |||
320 | /* ack in different place if S = 0 */ | ||
321 | ack = PPTP_GRE_IS_S(header->flags) ? header->ack : header->seq; | ||
313 | 322 | ||
314 | ack = ntohl(ack); | 323 | ack = ntohl(ack); |
315 | 324 | ||
@@ -318,21 +327,18 @@ static int pptp_rcv_core(struct sock *sk, struct sk_buff *skb) | |||
318 | /* also handle sequence number wrap-around */ | 327 | /* also handle sequence number wrap-around */ |
319 | if (WRAPPED(ack, opt->ack_recv)) | 328 | if (WRAPPED(ack, opt->ack_recv)) |
320 | opt->ack_recv = ack; | 329 | opt->ack_recv = ack; |
330 | } else { | ||
331 | headersize -= sizeof(header->ack); | ||
321 | } | 332 | } |
322 | |||
323 | /* test if payload present */ | 333 | /* test if payload present */ |
324 | if (!PPTP_GRE_IS_S(header->flags)) | 334 | if (!PPTP_GRE_IS_S(header->flags)) |
325 | goto drop; | 335 | goto drop; |
326 | 336 | ||
327 | headersize = sizeof(*header); | ||
328 | payload_len = ntohs(header->payload_len); | 337 | payload_len = ntohs(header->payload_len); |
329 | seq = ntohl(header->seq); | 338 | seq = ntohl(header->seq); |
330 | 339 | ||
331 | /* no ack present? */ | ||
332 | if (!PPTP_GRE_IS_A(header->ver)) | ||
333 | headersize -= sizeof(header->ack); | ||
334 | /* check for incomplete packet (length smaller than expected) */ | 340 | /* check for incomplete packet (length smaller than expected) */ |
335 | if (skb->len - headersize < payload_len) | 341 | if (!pskb_may_pull(skb, headersize + payload_len)) |
336 | goto drop; | 342 | goto drop; |
337 | 343 | ||
338 | payload = skb->data + headersize; | 344 | payload = skb->data + headersize; |