diff options
Diffstat (limited to 'net/bridge/br_netfilter.c')
-rw-r--r-- | net/bridge/br_netfilter.c | 17 |
1 files changed, 9 insertions, 8 deletions
diff --git a/net/bridge/br_netfilter.c b/net/bridge/br_netfilter.c index 4b5b66d07bb..008ff6c4eec 100644 --- a/net/bridge/br_netfilter.c +++ b/net/bridge/br_netfilter.c | |||
@@ -412,10 +412,6 @@ static int br_nf_pre_routing_finish(struct sk_buff *skb) | |||
412 | nf_bridge->mask ^= BRNF_NF_BRIDGE_PREROUTING; | 412 | nf_bridge->mask ^= BRNF_NF_BRIDGE_PREROUTING; |
413 | if (dnat_took_place(skb)) { | 413 | if (dnat_took_place(skb)) { |
414 | if ((err = ip_route_input(skb, iph->daddr, iph->saddr, iph->tos, dev))) { | 414 | if ((err = ip_route_input(skb, iph->daddr, iph->saddr, iph->tos, dev))) { |
415 | struct flowi fl = { | ||
416 | .fl4_dst = iph->daddr, | ||
417 | .fl4_tos = RT_TOS(iph->tos), | ||
418 | }; | ||
419 | struct in_device *in_dev = __in_dev_get_rcu(dev); | 415 | struct in_device *in_dev = __in_dev_get_rcu(dev); |
420 | 416 | ||
421 | /* If err equals -EHOSTUNREACH the error is due to a | 417 | /* If err equals -EHOSTUNREACH the error is due to a |
@@ -428,14 +424,16 @@ static int br_nf_pre_routing_finish(struct sk_buff *skb) | |||
428 | if (err != -EHOSTUNREACH || !in_dev || IN_DEV_FORWARD(in_dev)) | 424 | if (err != -EHOSTUNREACH || !in_dev || IN_DEV_FORWARD(in_dev)) |
429 | goto free_skb; | 425 | goto free_skb; |
430 | 426 | ||
431 | if (!ip_route_output_key(dev_net(dev), &rt, &fl)) { | 427 | rt = ip_route_output(dev_net(dev), iph->daddr, 0, |
428 | RT_TOS(iph->tos), 0); | ||
429 | if (!IS_ERR(rt)) { | ||
432 | /* - Bridged-and-DNAT'ed traffic doesn't | 430 | /* - Bridged-and-DNAT'ed traffic doesn't |
433 | * require ip_forwarding. */ | 431 | * require ip_forwarding. */ |
434 | if (((struct dst_entry *)rt)->dev == dev) { | 432 | if (rt->dst.dev == dev) { |
435 | skb_dst_set(skb, (struct dst_entry *)rt); | 433 | skb_dst_set(skb, &rt->dst); |
436 | goto bridged_dnat; | 434 | goto bridged_dnat; |
437 | } | 435 | } |
438 | dst_release((struct dst_entry *)rt); | 436 | ip_rt_put(rt); |
439 | } | 437 | } |
440 | free_skb: | 438 | free_skb: |
441 | kfree_skb(skb); | 439 | kfree_skb(skb); |
@@ -741,6 +739,9 @@ static unsigned int br_nf_forward_ip(unsigned int hook, struct sk_buff *skb, | |||
741 | nf_bridge->mask |= BRNF_PKT_TYPE; | 739 | nf_bridge->mask |= BRNF_PKT_TYPE; |
742 | } | 740 | } |
743 | 741 | ||
742 | if (br_parse_ip_options(skb)) | ||
743 | return NF_DROP; | ||
744 | |||
744 | /* The physdev module checks on this */ | 745 | /* The physdev module checks on this */ |
745 | nf_bridge->mask |= BRNF_BRIDGED; | 746 | nf_bridge->mask |= BRNF_BRIDGED; |
746 | nf_bridge->physoutdev = skb->dev; | 747 | nf_bridge->physoutdev = skb->dev; |