diff options
-rw-r--r-- | include/net/ip.h | 1 | ||||
-rw-r--r-- | net/bridge/br_netfilter.c | 13 | ||||
-rw-r--r-- | net/ipv4/ip_output.c | 6 |
3 files changed, 15 insertions, 5 deletions
diff --git a/include/net/ip.h b/include/net/ip.h index 8fe6156ca9b0..3d2e5ca62a5a 100644 --- a/include/net/ip.h +++ b/include/net/ip.h | |||
@@ -95,6 +95,7 @@ extern int ip_local_deliver(struct sk_buff *skb); | |||
95 | extern int ip_mr_input(struct sk_buff *skb); | 95 | extern int ip_mr_input(struct sk_buff *skb); |
96 | extern int ip_output(struct sk_buff *skb); | 96 | extern int ip_output(struct sk_buff *skb); |
97 | extern int ip_mc_output(struct sk_buff *skb); | 97 | extern int ip_mc_output(struct sk_buff *skb); |
98 | extern int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff *)); | ||
98 | extern int ip_do_nat(struct sk_buff *skb); | 99 | extern int ip_do_nat(struct sk_buff *skb); |
99 | extern void ip_send_check(struct iphdr *ip); | 100 | extern void ip_send_check(struct iphdr *ip); |
100 | extern int ip_queue_xmit(struct sk_buff *skb, int ipfragok); | 101 | extern int ip_queue_xmit(struct sk_buff *skb, int ipfragok); |
diff --git a/net/bridge/br_netfilter.c b/net/bridge/br_netfilter.c index f29450b788be..3da9264449f7 100644 --- a/net/bridge/br_netfilter.c +++ b/net/bridge/br_netfilter.c | |||
@@ -765,6 +765,15 @@ out: | |||
765 | return NF_STOLEN; | 765 | return NF_STOLEN; |
766 | } | 766 | } |
767 | 767 | ||
768 | static int br_nf_dev_queue_xmit(struct sk_buff *skb) | ||
769 | { | ||
770 | if (skb->protocol == htons(ETH_P_IP) && | ||
771 | skb->len > skb->dev->mtu && | ||
772 | !(skb_shinfo(skb)->ufo_size || skb_shinfo(skb)->tso_size)) | ||
773 | return ip_fragment(skb, br_dev_queue_push_xmit); | ||
774 | else | ||
775 | return br_dev_queue_push_xmit(skb); | ||
776 | } | ||
768 | 777 | ||
769 | /* PF_BRIDGE/POST_ROUTING ********************************************/ | 778 | /* PF_BRIDGE/POST_ROUTING ********************************************/ |
770 | static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb, | 779 | static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb, |
@@ -824,7 +833,7 @@ static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb, | |||
824 | realoutdev = nf_bridge->netoutdev; | 833 | realoutdev = nf_bridge->netoutdev; |
825 | #endif | 834 | #endif |
826 | NF_HOOK(pf, NF_IP_POST_ROUTING, skb, NULL, realoutdev, | 835 | NF_HOOK(pf, NF_IP_POST_ROUTING, skb, NULL, realoutdev, |
827 | br_dev_queue_push_xmit); | 836 | br_nf_dev_queue_xmit); |
828 | 837 | ||
829 | return NF_STOLEN; | 838 | return NF_STOLEN; |
830 | 839 | ||
@@ -869,7 +878,7 @@ static unsigned int ip_sabotage_out(unsigned int hook, struct sk_buff **pskb, | |||
869 | 878 | ||
870 | if ((out->hard_start_xmit == br_dev_xmit && | 879 | if ((out->hard_start_xmit == br_dev_xmit && |
871 | okfn != br_nf_forward_finish && | 880 | okfn != br_nf_forward_finish && |
872 | okfn != br_nf_local_out_finish && okfn != br_dev_queue_push_xmit) | 881 | okfn != br_nf_local_out_finish && okfn != br_nf_dev_queue_xmit) |
873 | #if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE) | 882 | #if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE) |
874 | || ((out->priv_flags & IFF_802_1Q_VLAN) && | 883 | || ((out->priv_flags & IFF_802_1Q_VLAN) && |
875 | VLAN_DEV_INFO(out)->real_dev->hard_start_xmit == br_dev_xmit) | 884 | VLAN_DEV_INFO(out)->real_dev->hard_start_xmit == br_dev_xmit) |
diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c index f75ff1d96551..8dcba3887f04 100644 --- a/net/ipv4/ip_output.c +++ b/net/ipv4/ip_output.c | |||
@@ -86,8 +86,6 @@ | |||
86 | 86 | ||
87 | int sysctl_ip_default_ttl = IPDEFTTL; | 87 | int sysctl_ip_default_ttl = IPDEFTTL; |
88 | 88 | ||
89 | static int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*)); | ||
90 | |||
91 | /* Generate a checksum for an outgoing IP datagram. */ | 89 | /* Generate a checksum for an outgoing IP datagram. */ |
92 | __inline__ void ip_send_check(struct iphdr *iph) | 90 | __inline__ void ip_send_check(struct iphdr *iph) |
93 | { | 91 | { |
@@ -421,7 +419,7 @@ static void ip_copy_metadata(struct sk_buff *to, struct sk_buff *from) | |||
421 | * single device frame, and queue such a frame for sending. | 419 | * single device frame, and queue such a frame for sending. |
422 | */ | 420 | */ |
423 | 421 | ||
424 | static int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*)) | 422 | int ip_fragment(struct sk_buff *skb, int (*output)(struct sk_buff*)) |
425 | { | 423 | { |
426 | struct iphdr *iph; | 424 | struct iphdr *iph; |
427 | int raw = 0; | 425 | int raw = 0; |
@@ -673,6 +671,8 @@ fail: | |||
673 | return err; | 671 | return err; |
674 | } | 672 | } |
675 | 673 | ||
674 | EXPORT_SYMBOL(ip_fragment); | ||
675 | |||
676 | int | 676 | int |
677 | ip_generic_getfrag(void *from, char *to, int offset, int len, int odd, struct sk_buff *skb) | 677 | ip_generic_getfrag(void *from, char *to, int offset, int len, int odd, struct sk_buff *skb) |
678 | { | 678 | { |