diff options
author | Bart De Schuymer <bdschuym@pandora.be> | 2005-12-19 17:00:08 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2005-12-19 17:00:08 -0500 |
commit | b03664869aa6f84c3c98a06ac9d6905b195909bc (patch) | |
tree | 222958ab671d7a0493f530bfe3243c119f7c01fe /net/bridge | |
parent | 6b80ebedbee87c5b2213fc3635bf0bd7450bce30 (diff) |
[BRIDGE-NF]: Fix bridge-nf ipv6 length check
A typo caused some bridged IPv6 packets to get dropped randomly,
as reported by Sebastien Chaumontet. The patch below fixes this
(using skb->nh.raw instead of raw) and also makes the jumbo packet
length checking up-to-date with the code in
net/ipv6/exthdrs.c::ipv6_hop_jumbo.
Signed-off-by: Bart De Schuymer <bdschuym@pandora.be>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/bridge')
-rw-r--r-- | net/bridge/br_netfilter.c | 17 |
1 files changed, 7 insertions, 10 deletions
diff --git a/net/bridge/br_netfilter.c b/net/bridge/br_netfilter.c index d8e36b775125..43a0b35dfe6f 100644 --- a/net/bridge/br_netfilter.c +++ b/net/bridge/br_netfilter.c | |||
@@ -295,7 +295,7 @@ static int check_hbh_len(struct sk_buff *skb) | |||
295 | len -= 2; | 295 | len -= 2; |
296 | 296 | ||
297 | while (len > 0) { | 297 | while (len > 0) { |
298 | int optlen = raw[off+1]+2; | 298 | int optlen = skb->nh.raw[off+1]+2; |
299 | 299 | ||
300 | switch (skb->nh.raw[off]) { | 300 | switch (skb->nh.raw[off]) { |
301 | case IPV6_TLV_PAD0: | 301 | case IPV6_TLV_PAD0: |
@@ -308,18 +308,15 @@ static int check_hbh_len(struct sk_buff *skb) | |||
308 | case IPV6_TLV_JUMBO: | 308 | case IPV6_TLV_JUMBO: |
309 | if (skb->nh.raw[off+1] != 4 || (off&3) != 2) | 309 | if (skb->nh.raw[off+1] != 4 || (off&3) != 2) |
310 | goto bad; | 310 | goto bad; |
311 | |||
312 | pkt_len = ntohl(*(u32*)(skb->nh.raw+off+2)); | 311 | pkt_len = ntohl(*(u32*)(skb->nh.raw+off+2)); |
313 | 312 | if (pkt_len <= IPV6_MAXPLEN || | |
313 | skb->nh.ipv6h->payload_len) | ||
314 | goto bad; | ||
314 | if (pkt_len > skb->len - sizeof(struct ipv6hdr)) | 315 | if (pkt_len > skb->len - sizeof(struct ipv6hdr)) |
315 | goto bad; | 316 | goto bad; |
316 | if (pkt_len + sizeof(struct ipv6hdr) < skb->len) { | 317 | if (pskb_trim_rcsum(skb, |
317 | if (__pskb_trim(skb, | 318 | pkt_len+sizeof(struct ipv6hdr))) |
318 | pkt_len + sizeof(struct ipv6hdr))) | 319 | goto bad; |
319 | goto bad; | ||
320 | if (skb->ip_summed == CHECKSUM_HW) | ||
321 | skb->ip_summed = CHECKSUM_NONE; | ||
322 | } | ||
323 | break; | 320 | break; |
324 | default: | 321 | default: |
325 | if (optlen > len) | 322 | if (optlen > len) |