diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2008-08-08 14:15:23 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2008-08-08 14:15:23 -0400 |
| commit | f2d7499be1b1fe1cd8a5e6a01c1f44173894a241 (patch) | |
| tree | 64d341a90d8cb831a5097e365d303367906f1373 /net | |
| parent | 8d659f5e43c5db2630e85f507b7384365e9e1c1e (diff) | |
| parent | 76aab2c1eae491a5d73ac83deec97dd28ebac584 (diff) | |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-2.6: (99 commits)
pkt_sched: Fix actions referencing
bnx2x: fix logical op
tcp: (whitespace only) fix confusing indentation
pkt_sched: Fix qdisc config when link is down.
[Bluetooth] Add full quirk implementation for btusb driver
[Bluetooth] Removal of unnecessary ignore module parameter
[Bluetooth] Add parameters to control BNEP header compression
ath9k: Revamp wireless mode usage
ath9k: More unused macros
ath9k: Remove a few unused macros and fix indentation
ath9k: Use mac80211's band macros and remove enum hal_freq_band
ath9k: Remove redundant data structure ath9k_txq_info
ath9k: Cleanup data structures related to HW capabilities
ath9k: work around gcc ICEs
ath9k: Add new Atheros IEEE 802.11n driver
ath5k: remove Atheros 11n devices from supported list
list.h: add list_cut_position()
list.h: Add list_splice_tail() and list_splice_tail_init()
p54: swap short slot time dcf values
rt2x00: Block all unsupported modes
...
Diffstat (limited to 'net')
| -rw-r--r-- | net/bluetooth/bnep/core.c | 15 | ||||
| -rw-r--r-- | net/core/dev.c | 35 | ||||
| -rw-r--r-- | net/core/pktgen.c | 37 | ||||
| -rw-r--r-- | net/dccp/dccp.h | 3 | ||||
| -rw-r--r-- | net/dccp/minisocks.c | 3 | ||||
| -rw-r--r-- | net/ipv4/esp4.c | 2 | ||||
| -rw-r--r-- | net/ipv4/route.c | 12 | ||||
| -rw-r--r-- | net/ipv4/tcp_ipv4.c | 4 | ||||
| -rw-r--r-- | net/ipv4/tcp_minisocks.c | 140 | ||||
| -rw-r--r-- | net/ipv4/xfrm4_mode_beet.c | 6 | ||||
| -rw-r--r-- | net/ipv6/esp6.c | 4 | ||||
| -rw-r--r-- | net/ipv6/route.c | 2 | ||||
| -rw-r--r-- | net/ipv6/tcp_ipv6.c | 8 | ||||
| -rw-r--r-- | net/ipv6/xfrm6_mode_beet.c | 29 | ||||
| -rw-r--r-- | net/mac80211/main.c | 8 | ||||
| -rw-r--r-- | net/mac80211/mesh.h | 5 | ||||
| -rw-r--r-- | net/mac80211/mesh_hwmp.c | 19 | ||||
| -rw-r--r-- | net/mac80211/mesh_pathtbl.c | 11 | ||||
| -rw-r--r-- | net/mac80211/rx.c | 116 | ||||
| -rw-r--r-- | net/mac80211/tx.c | 45 | ||||
| -rw-r--r-- | net/netfilter/nf_conntrack_core.c | 6 | ||||
| -rw-r--r-- | net/netfilter/nf_conntrack_standalone.c | 28 | ||||
| -rw-r--r-- | net/sched/act_api.c | 5 | ||||
| -rw-r--r-- | net/sched/sch_api.c | 10 | ||||
| -rw-r--r-- | net/wanrouter/wanmain.c | 27 |
25 files changed, 320 insertions, 260 deletions
diff --git a/net/bluetooth/bnep/core.c b/net/bluetooth/bnep/core.c index 021172c0e666..12bba6207a8d 100644 --- a/net/bluetooth/bnep/core.c +++ b/net/bluetooth/bnep/core.c | |||
| @@ -57,7 +57,10 @@ | |||
| 57 | #define BT_DBG(D...) | 57 | #define BT_DBG(D...) |
| 58 | #endif | 58 | #endif |
| 59 | 59 | ||
| 60 | #define VERSION "1.2" | 60 | #define VERSION "1.3" |
| 61 | |||
| 62 | static int compress_src = 1; | ||
| 63 | static int compress_dst = 1; | ||
| 61 | 64 | ||
| 62 | static LIST_HEAD(bnep_session_list); | 65 | static LIST_HEAD(bnep_session_list); |
| 63 | static DECLARE_RWSEM(bnep_session_sem); | 66 | static DECLARE_RWSEM(bnep_session_sem); |
| @@ -418,10 +421,10 @@ static inline int bnep_tx_frame(struct bnep_session *s, struct sk_buff *skb) | |||
| 418 | iv[il++] = (struct kvec) { &type, 1 }; | 421 | iv[il++] = (struct kvec) { &type, 1 }; |
| 419 | len++; | 422 | len++; |
| 420 | 423 | ||
| 421 | if (!compare_ether_addr(eh->h_dest, s->eh.h_source)) | 424 | if (compress_src && !compare_ether_addr(eh->h_dest, s->eh.h_source)) |
| 422 | type |= 0x01; | 425 | type |= 0x01; |
| 423 | 426 | ||
| 424 | if (!compare_ether_addr(eh->h_source, s->eh.h_dest)) | 427 | if (compress_dst && !compare_ether_addr(eh->h_source, s->eh.h_dest)) |
| 425 | type |= 0x02; | 428 | type |= 0x02; |
| 426 | 429 | ||
| 427 | if (type) | 430 | if (type) |
| @@ -727,6 +730,12 @@ static void __exit bnep_exit(void) | |||
| 727 | module_init(bnep_init); | 730 | module_init(bnep_init); |
| 728 | module_exit(bnep_exit); | 731 | module_exit(bnep_exit); |
| 729 | 732 | ||
| 733 | module_param(compress_src, bool, 0644); | ||
| 734 | MODULE_PARM_DESC(compress_src, "Compress sources headers"); | ||
| 735 | |||
| 736 | module_param(compress_dst, bool, 0644); | ||
| 737 | MODULE_PARM_DESC(compress_dst, "Compress destination headers"); | ||
| 738 | |||
| 730 | MODULE_AUTHOR("David Libault <david.libault@inventel.fr>, Maxim Krasnyansky <maxk@qualcomm.com>"); | 739 | MODULE_AUTHOR("David Libault <david.libault@inventel.fr>, Maxim Krasnyansky <maxk@qualcomm.com>"); |
| 731 | MODULE_DESCRIPTION("Bluetooth BNEP ver " VERSION); | 740 | MODULE_DESCRIPTION("Bluetooth BNEP ver " VERSION); |
| 732 | MODULE_VERSION(VERSION); | 741 | MODULE_VERSION(VERSION); |
diff --git a/net/core/dev.c b/net/core/dev.c index 01993ad74e76..600bb23c4c2e 100644 --- a/net/core/dev.c +++ b/net/core/dev.c | |||
| @@ -1939,22 +1939,6 @@ int netif_rx_ni(struct sk_buff *skb) | |||
| 1939 | 1939 | ||
| 1940 | EXPORT_SYMBOL(netif_rx_ni); | 1940 | EXPORT_SYMBOL(netif_rx_ni); |
| 1941 | 1941 | ||
| 1942 | static inline struct net_device *skb_bond(struct sk_buff *skb) | ||
| 1943 | { | ||
| 1944 | struct net_device *dev = skb->dev; | ||
| 1945 | |||
| 1946 | if (dev->master) { | ||
| 1947 | if (skb_bond_should_drop(skb)) { | ||
| 1948 | kfree_skb(skb); | ||
| 1949 | return NULL; | ||
| 1950 | } | ||
| 1951 | skb->dev = dev->master; | ||
| 1952 | } | ||
| 1953 | |||
| 1954 | return dev; | ||
| 1955 | } | ||
| 1956 | |||
| 1957 | |||
| 1958 | static void net_tx_action(struct softirq_action *h) | 1942 | static void net_tx_action(struct softirq_action *h) |
| 1959 | { | 1943 | { |
| 1960 | struct softnet_data *sd = &__get_cpu_var(softnet_data); | 1944 | struct softnet_data *sd = &__get_cpu_var(softnet_data); |
| @@ -2181,6 +2165,7 @@ int netif_receive_skb(struct sk_buff *skb) | |||
| 2181 | { | 2165 | { |
| 2182 | struct packet_type *ptype, *pt_prev; | 2166 | struct packet_type *ptype, *pt_prev; |
| 2183 | struct net_device *orig_dev; | 2167 | struct net_device *orig_dev; |
| 2168 | struct net_device *null_or_orig; | ||
| 2184 | int ret = NET_RX_DROP; | 2169 | int ret = NET_RX_DROP; |
| 2185 | __be16 type; | 2170 | __be16 type; |
| 2186 | 2171 | ||
| @@ -2194,10 +2179,14 @@ int netif_receive_skb(struct sk_buff *skb) | |||
| 2194 | if (!skb->iif) | 2179 | if (!skb->iif) |
| 2195 | skb->iif = skb->dev->ifindex; | 2180 | skb->iif = skb->dev->ifindex; |
| 2196 | 2181 | ||
| 2197 | orig_dev = skb_bond(skb); | 2182 | null_or_orig = NULL; |
| 2198 | 2183 | orig_dev = skb->dev; | |
| 2199 | if (!orig_dev) | 2184 | if (orig_dev->master) { |
| 2200 | return NET_RX_DROP; | 2185 | if (skb_bond_should_drop(skb)) |
| 2186 | null_or_orig = orig_dev; /* deliver only exact match */ | ||
| 2187 | else | ||
| 2188 | skb->dev = orig_dev->master; | ||
| 2189 | } | ||
| 2201 | 2190 | ||
| 2202 | __get_cpu_var(netdev_rx_stat).total++; | 2191 | __get_cpu_var(netdev_rx_stat).total++; |
| 2203 | 2192 | ||
| @@ -2221,7 +2210,8 @@ int netif_receive_skb(struct sk_buff *skb) | |||
| 2221 | #endif | 2210 | #endif |
| 2222 | 2211 | ||
| 2223 | list_for_each_entry_rcu(ptype, &ptype_all, list) { | 2212 | list_for_each_entry_rcu(ptype, &ptype_all, list) { |
| 2224 | if (!ptype->dev || ptype->dev == skb->dev) { | 2213 | if (ptype->dev == null_or_orig || ptype->dev == skb->dev || |
| 2214 | ptype->dev == orig_dev) { | ||
| 2225 | if (pt_prev) | 2215 | if (pt_prev) |
| 2226 | ret = deliver_skb(skb, pt_prev, orig_dev); | 2216 | ret = deliver_skb(skb, pt_prev, orig_dev); |
| 2227 | pt_prev = ptype; | 2217 | pt_prev = ptype; |
| @@ -2246,7 +2236,8 @@ ncls: | |||
| 2246 | list_for_each_entry_rcu(ptype, | 2236 | list_for_each_entry_rcu(ptype, |
| 2247 | &ptype_base[ntohs(type) & PTYPE_HASH_MASK], list) { | 2237 | &ptype_base[ntohs(type) & PTYPE_HASH_MASK], list) { |
| 2248 | if (ptype->type == type && | 2238 | if (ptype->type == type && |
| 2249 | (!ptype->dev || ptype->dev == skb->dev)) { | 2239 | (ptype->dev == null_or_orig || ptype->dev == skb->dev || |
| 2240 | ptype->dev == orig_dev)) { | ||
| 2250 | if (pt_prev) | 2241 | if (pt_prev) |
| 2251 | ret = deliver_skb(skb, pt_prev, orig_dev); | 2242 | ret = deliver_skb(skb, pt_prev, orig_dev); |
| 2252 | pt_prev = ptype; | 2243 | pt_prev = ptype; |
diff --git a/net/core/pktgen.c b/net/core/pktgen.c index 2498cdaf8cbe..526236453908 100644 --- a/net/core/pktgen.c +++ b/net/core/pktgen.c | |||
| @@ -168,7 +168,7 @@ | |||
| 168 | #include <asm/div64.h> /* do_div */ | 168 | #include <asm/div64.h> /* do_div */ |
| 169 | #include <asm/timex.h> | 169 | #include <asm/timex.h> |
| 170 | 170 | ||
| 171 | #define VERSION "pktgen v2.69: Packet Generator for packet performance testing.\n" | 171 | #define VERSION "pktgen v2.70: Packet Generator for packet performance testing.\n" |
| 172 | 172 | ||
| 173 | #define IP_NAME_SZ 32 | 173 | #define IP_NAME_SZ 32 |
| 174 | #define MAX_MPLS_LABELS 16 /* This is the max label stack depth */ | 174 | #define MAX_MPLS_LABELS 16 /* This is the max label stack depth */ |
| @@ -189,6 +189,7 @@ | |||
| 189 | #define F_FLOW_SEQ (1<<11) /* Sequential flows */ | 189 | #define F_FLOW_SEQ (1<<11) /* Sequential flows */ |
| 190 | #define F_IPSEC_ON (1<<12) /* ipsec on for flows */ | 190 | #define F_IPSEC_ON (1<<12) /* ipsec on for flows */ |
| 191 | #define F_QUEUE_MAP_RND (1<<13) /* queue map Random */ | 191 | #define F_QUEUE_MAP_RND (1<<13) /* queue map Random */ |
| 192 | #define F_QUEUE_MAP_CPU (1<<14) /* queue map mirrors smp_processor_id() */ | ||
| 192 | 193 | ||
| 193 | /* Thread control flag bits */ | 194 | /* Thread control flag bits */ |
| 194 | #define T_TERMINATE (1<<0) | 195 | #define T_TERMINATE (1<<0) |
| @@ -621,6 +622,9 @@ static int pktgen_if_show(struct seq_file *seq, void *v) | |||
| 621 | if (pkt_dev->flags & F_QUEUE_MAP_RND) | 622 | if (pkt_dev->flags & F_QUEUE_MAP_RND) |
| 622 | seq_printf(seq, "QUEUE_MAP_RND "); | 623 | seq_printf(seq, "QUEUE_MAP_RND "); |
| 623 | 624 | ||
| 625 | if (pkt_dev->flags & F_QUEUE_MAP_CPU) | ||
| 626 | seq_printf(seq, "QUEUE_MAP_CPU "); | ||
| 627 | |||
| 624 | if (pkt_dev->cflows) { | 628 | if (pkt_dev->cflows) { |
| 625 | if (pkt_dev->flags & F_FLOW_SEQ) | 629 | if (pkt_dev->flags & F_FLOW_SEQ) |
| 626 | seq_printf(seq, "FLOW_SEQ "); /*in sequence flows*/ | 630 | seq_printf(seq, "FLOW_SEQ "); /*in sequence flows*/ |
| @@ -1134,6 +1138,12 @@ static ssize_t pktgen_if_write(struct file *file, | |||
| 1134 | 1138 | ||
| 1135 | else if (strcmp(f, "!QUEUE_MAP_RND") == 0) | 1139 | else if (strcmp(f, "!QUEUE_MAP_RND") == 0) |
| 1136 | pkt_dev->flags &= ~F_QUEUE_MAP_RND; | 1140 | pkt_dev->flags &= ~F_QUEUE_MAP_RND; |
| 1141 | |||
| 1142 | else if (strcmp(f, "QUEUE_MAP_CPU") == 0) | ||
| 1143 | pkt_dev->flags |= F_QUEUE_MAP_CPU; | ||
| 1144 | |||
| 1145 | else if (strcmp(f, "!QUEUE_MAP_CPU") == 0) | ||
| 1146 | pkt_dev->flags &= ~F_QUEUE_MAP_CPU; | ||
| 1137 | #ifdef CONFIG_XFRM | 1147 | #ifdef CONFIG_XFRM |
| 1138 | else if (strcmp(f, "IPSEC") == 0) | 1148 | else if (strcmp(f, "IPSEC") == 0) |
| 1139 | pkt_dev->flags |= F_IPSEC_ON; | 1149 | pkt_dev->flags |= F_IPSEC_ON; |
| @@ -1895,6 +1905,23 @@ static int pktgen_device_event(struct notifier_block *unused, | |||
| 1895 | return NOTIFY_DONE; | 1905 | return NOTIFY_DONE; |
| 1896 | } | 1906 | } |
| 1897 | 1907 | ||
| 1908 | static struct net_device *pktgen_dev_get_by_name(struct pktgen_dev *pkt_dev, const char *ifname) | ||
| 1909 | { | ||
| 1910 | char b[IFNAMSIZ+5]; | ||
| 1911 | int i = 0; | ||
| 1912 | |||
| 1913 | for(i=0; ifname[i] != '@'; i++) { | ||
| 1914 | if(i == IFNAMSIZ) | ||
| 1915 | break; | ||
| 1916 | |||
| 1917 | b[i] = ifname[i]; | ||
| 1918 | } | ||
| 1919 | b[i] = 0; | ||
| 1920 | |||
| 1921 | return dev_get_by_name(&init_net, b); | ||
| 1922 | } | ||
| 1923 | |||
| 1924 | |||
| 1898 | /* Associate pktgen_dev with a device. */ | 1925 | /* Associate pktgen_dev with a device. */ |
| 1899 | 1926 | ||
| 1900 | static int pktgen_setup_dev(struct pktgen_dev *pkt_dev, const char *ifname) | 1927 | static int pktgen_setup_dev(struct pktgen_dev *pkt_dev, const char *ifname) |
| @@ -1908,7 +1935,7 @@ static int pktgen_setup_dev(struct pktgen_dev *pkt_dev, const char *ifname) | |||
| 1908 | pkt_dev->odev = NULL; | 1935 | pkt_dev->odev = NULL; |
| 1909 | } | 1936 | } |
| 1910 | 1937 | ||
| 1911 | odev = dev_get_by_name(&init_net, ifname); | 1938 | odev = pktgen_dev_get_by_name(pkt_dev, ifname); |
| 1912 | if (!odev) { | 1939 | if (!odev) { |
| 1913 | printk(KERN_ERR "pktgen: no such netdevice: \"%s\"\n", ifname); | 1940 | printk(KERN_ERR "pktgen: no such netdevice: \"%s\"\n", ifname); |
| 1914 | return -ENODEV; | 1941 | return -ENODEV; |
| @@ -2129,7 +2156,11 @@ static void get_ipsec_sa(struct pktgen_dev *pkt_dev, int flow) | |||
| 2129 | #endif | 2156 | #endif |
| 2130 | static void set_cur_queue_map(struct pktgen_dev *pkt_dev) | 2157 | static void set_cur_queue_map(struct pktgen_dev *pkt_dev) |
| 2131 | { | 2158 | { |
| 2132 | if (pkt_dev->queue_map_min < pkt_dev->queue_map_max) { | 2159 | |
| 2160 | if (pkt_dev->flags & F_QUEUE_MAP_CPU) | ||
| 2161 | pkt_dev->cur_queue_map = smp_processor_id(); | ||
| 2162 | |||
| 2163 | else if (pkt_dev->queue_map_min < pkt_dev->queue_map_max) { | ||
| 2133 | __u16 t; | 2164 | __u16 t; |
| 2134 | if (pkt_dev->flags & F_QUEUE_MAP_RND) { | 2165 | if (pkt_dev->flags & F_QUEUE_MAP_RND) { |
| 2135 | t = random32() % | 2166 | t = random32() % |
diff --git a/net/dccp/dccp.h b/net/dccp/dccp.h index 1c2e3ec2eb57..b4bc6e095a0e 100644 --- a/net/dccp/dccp.h +++ b/net/dccp/dccp.h | |||
| @@ -229,7 +229,8 @@ extern void dccp_v4_send_check(struct sock *sk, int len, struct sk_buff *skb); | |||
| 229 | extern int dccp_retransmit_skb(struct sock *sk); | 229 | extern int dccp_retransmit_skb(struct sock *sk); |
| 230 | 230 | ||
| 231 | extern void dccp_send_ack(struct sock *sk); | 231 | extern void dccp_send_ack(struct sock *sk); |
| 232 | extern void dccp_reqsk_send_ack(struct sk_buff *sk, struct request_sock *rsk); | 232 | extern void dccp_reqsk_send_ack(struct sock *sk, struct sk_buff *skb, |
| 233 | struct request_sock *rsk); | ||
| 233 | 234 | ||
| 234 | extern void dccp_send_sync(struct sock *sk, const u64 seq, | 235 | extern void dccp_send_sync(struct sock *sk, const u64 seq, |
| 235 | const enum dccp_pkt_type pkt_type); | 236 | const enum dccp_pkt_type pkt_type); |
diff --git a/net/dccp/minisocks.c b/net/dccp/minisocks.c index 66dca5bba858..b2804e2d1b8c 100644 --- a/net/dccp/minisocks.c +++ b/net/dccp/minisocks.c | |||
| @@ -296,7 +296,8 @@ int dccp_child_process(struct sock *parent, struct sock *child, | |||
| 296 | 296 | ||
| 297 | EXPORT_SYMBOL_GPL(dccp_child_process); | 297 | EXPORT_SYMBOL_GPL(dccp_child_process); |
| 298 | 298 | ||
| 299 | void dccp_reqsk_send_ack(struct sk_buff *skb, struct request_sock *rsk) | 299 | void dccp_reqsk_send_ack(struct sock *sk, struct sk_buff *skb, |
| 300 | struct request_sock *rsk) | ||
| 300 | { | 301 | { |
| 301 | DCCP_BUG("DCCP-ACK packets are never sent in LISTEN/RESPOND state"); | 302 | DCCP_BUG("DCCP-ACK packets are never sent in LISTEN/RESPOND state"); |
| 302 | } | 303 | } |
diff --git a/net/ipv4/esp4.c b/net/ipv4/esp4.c index 4e73e5708e70..21515d4c49eb 100644 --- a/net/ipv4/esp4.c +++ b/net/ipv4/esp4.c | |||
| @@ -575,7 +575,7 @@ static int esp_init_state(struct xfrm_state *x) | |||
| 575 | crypto_aead_ivsize(aead); | 575 | crypto_aead_ivsize(aead); |
| 576 | if (x->props.mode == XFRM_MODE_TUNNEL) | 576 | if (x->props.mode == XFRM_MODE_TUNNEL) |
| 577 | x->props.header_len += sizeof(struct iphdr); | 577 | x->props.header_len += sizeof(struct iphdr); |
| 578 | else if (x->props.mode == XFRM_MODE_BEET) | 578 | else if (x->props.mode == XFRM_MODE_BEET && x->sel.family != AF_INET6) |
| 579 | x->props.header_len += IPV4_BEET_PHMAXLEN; | 579 | x->props.header_len += IPV4_BEET_PHMAXLEN; |
| 580 | if (x->encap) { | 580 | if (x->encap) { |
| 581 | struct xfrm_encap_tmpl *encap = x->encap; | 581 | struct xfrm_encap_tmpl *encap = x->encap; |
diff --git a/net/ipv4/route.c b/net/ipv4/route.c index 1bfa078ddbd0..16fc6f454a31 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c | |||
| @@ -1509,14 +1509,14 @@ unsigned short ip_rt_frag_needed(struct net *net, struct iphdr *iph, | |||
| 1509 | 1509 | ||
| 1510 | /* BSD 4.2 compatibility hack :-( */ | 1510 | /* BSD 4.2 compatibility hack :-( */ |
| 1511 | if (mtu == 0 && | 1511 | if (mtu == 0 && |
| 1512 | old_mtu >= dst_metric(&rth->u.dst, RTAX_MTU) && | 1512 | old_mtu >= dst_mtu(&rth->u.dst) && |
| 1513 | old_mtu >= 68 + (iph->ihl << 2)) | 1513 | old_mtu >= 68 + (iph->ihl << 2)) |
| 1514 | old_mtu -= iph->ihl << 2; | 1514 | old_mtu -= iph->ihl << 2; |
| 1515 | 1515 | ||
| 1516 | mtu = guess_mtu(old_mtu); | 1516 | mtu = guess_mtu(old_mtu); |
| 1517 | } | 1517 | } |
| 1518 | if (mtu <= dst_metric(&rth->u.dst, RTAX_MTU)) { | 1518 | if (mtu <= dst_mtu(&rth->u.dst)) { |
| 1519 | if (mtu < dst_metric(&rth->u.dst, RTAX_MTU)) { | 1519 | if (mtu < dst_mtu(&rth->u.dst)) { |
| 1520 | dst_confirm(&rth->u.dst); | 1520 | dst_confirm(&rth->u.dst); |
| 1521 | if (mtu < ip_rt_min_pmtu) { | 1521 | if (mtu < ip_rt_min_pmtu) { |
| 1522 | mtu = ip_rt_min_pmtu; | 1522 | mtu = ip_rt_min_pmtu; |
| @@ -1538,7 +1538,7 @@ unsigned short ip_rt_frag_needed(struct net *net, struct iphdr *iph, | |||
| 1538 | 1538 | ||
| 1539 | static void ip_rt_update_pmtu(struct dst_entry *dst, u32 mtu) | 1539 | static void ip_rt_update_pmtu(struct dst_entry *dst, u32 mtu) |
| 1540 | { | 1540 | { |
| 1541 | if (dst_metric(dst, RTAX_MTU) > mtu && mtu >= 68 && | 1541 | if (dst_mtu(dst) > mtu && mtu >= 68 && |
| 1542 | !(dst_metric_locked(dst, RTAX_MTU))) { | 1542 | !(dst_metric_locked(dst, RTAX_MTU))) { |
| 1543 | if (mtu < ip_rt_min_pmtu) { | 1543 | if (mtu < ip_rt_min_pmtu) { |
| 1544 | mtu = ip_rt_min_pmtu; | 1544 | mtu = ip_rt_min_pmtu; |
| @@ -1667,7 +1667,7 @@ static void rt_set_nexthop(struct rtable *rt, struct fib_result *res, u32 itag) | |||
| 1667 | 1667 | ||
| 1668 | if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) | 1668 | if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) |
| 1669 | rt->u.dst.metrics[RTAX_HOPLIMIT-1] = sysctl_ip_default_ttl; | 1669 | rt->u.dst.metrics[RTAX_HOPLIMIT-1] = sysctl_ip_default_ttl; |
| 1670 | if (dst_metric(&rt->u.dst, RTAX_MTU) > IP_MAX_MTU) | 1670 | if (dst_mtu(&rt->u.dst) > IP_MAX_MTU) |
| 1671 | rt->u.dst.metrics[RTAX_MTU-1] = IP_MAX_MTU; | 1671 | rt->u.dst.metrics[RTAX_MTU-1] = IP_MAX_MTU; |
| 1672 | if (dst_metric(&rt->u.dst, RTAX_ADVMSS) == 0) | 1672 | if (dst_metric(&rt->u.dst, RTAX_ADVMSS) == 0) |
| 1673 | rt->u.dst.metrics[RTAX_ADVMSS-1] = max_t(unsigned int, rt->u.dst.dev->mtu - 40, | 1673 | rt->u.dst.metrics[RTAX_ADVMSS-1] = max_t(unsigned int, rt->u.dst.dev->mtu - 40, |
| @@ -3223,9 +3223,7 @@ int __init ip_rt_init(void) | |||
| 3223 | */ | 3223 | */ |
| 3224 | void __init ip_static_sysctl_init(void) | 3224 | void __init ip_static_sysctl_init(void) |
| 3225 | { | 3225 | { |
| 3226 | #ifdef CONFIG_SYSCTL | ||
| 3227 | register_sysctl_paths(ipv4_route_path, ipv4_route_table); | 3226 | register_sysctl_paths(ipv4_route_path, ipv4_route_table); |
| 3228 | #endif | ||
| 3229 | } | 3227 | } |
| 3230 | #endif | 3228 | #endif |
| 3231 | 3229 | ||
diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c index 91a8cfddf1c4..44c1e934824b 100644 --- a/net/ipv4/tcp_ipv4.c +++ b/net/ipv4/tcp_ipv4.c | |||
| @@ -687,14 +687,14 @@ static void tcp_v4_timewait_ack(struct sock *sk, struct sk_buff *skb) | |||
| 687 | inet_twsk_put(tw); | 687 | inet_twsk_put(tw); |
| 688 | } | 688 | } |
| 689 | 689 | ||
| 690 | static void tcp_v4_reqsk_send_ack(struct sk_buff *skb, | 690 | static void tcp_v4_reqsk_send_ack(struct sock *sk, struct sk_buff *skb, |
| 691 | struct request_sock *req) | 691 | struct request_sock *req) |
| 692 | { | 692 | { |
| 693 | tcp_v4_send_ack(skb, tcp_rsk(req)->snt_isn + 1, | 693 | tcp_v4_send_ack(skb, tcp_rsk(req)->snt_isn + 1, |
| 694 | tcp_rsk(req)->rcv_isn + 1, req->rcv_wnd, | 694 | tcp_rsk(req)->rcv_isn + 1, req->rcv_wnd, |
| 695 | req->ts_recent, | 695 | req->ts_recent, |
| 696 | 0, | 696 | 0, |
| 697 | tcp_v4_md5_do_lookup(skb->sk, ip_hdr(skb)->daddr)); | 697 | tcp_v4_md5_do_lookup(sk, ip_hdr(skb)->daddr)); |
| 698 | } | 698 | } |
| 699 | 699 | ||
| 700 | /* | 700 | /* |
diff --git a/net/ipv4/tcp_minisocks.c b/net/ipv4/tcp_minisocks.c index 204c42162660..f976fc57892c 100644 --- a/net/ipv4/tcp_minisocks.c +++ b/net/ipv4/tcp_minisocks.c | |||
| @@ -609,7 +609,7 @@ struct sock *tcp_check_req(struct sock *sk,struct sk_buff *skb, | |||
| 609 | tcp_rsk(req)->rcv_isn + 1, tcp_rsk(req)->rcv_isn + 1 + req->rcv_wnd)) { | 609 | tcp_rsk(req)->rcv_isn + 1, tcp_rsk(req)->rcv_isn + 1 + req->rcv_wnd)) { |
| 610 | /* Out of window: send ACK and drop. */ | 610 | /* Out of window: send ACK and drop. */ |
| 611 | if (!(flg & TCP_FLAG_RST)) | 611 | if (!(flg & TCP_FLAG_RST)) |
| 612 | req->rsk_ops->send_ack(skb, req); | 612 | req->rsk_ops->send_ack(sk, skb, req); |
| 613 | if (paws_reject) | 613 | if (paws_reject) |
| 614 | NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_PAWSESTABREJECTED); | 614 | NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_PAWSESTABREJECTED); |
| 615 | return NULL; | 615 | return NULL; |
| @@ -618,89 +618,87 @@ struct sock *tcp_check_req(struct sock *sk,struct sk_buff *skb, | |||
| 618 | /* In sequence, PAWS is OK. */ | 618 | /* In sequence, PAWS is OK. */ |
| 619 | 619 | ||
| 620 | if (tmp_opt.saw_tstamp && !after(TCP_SKB_CB(skb)->seq, tcp_rsk(req)->rcv_isn + 1)) | 620 | if (tmp_opt.saw_tstamp && !after(TCP_SKB_CB(skb)->seq, tcp_rsk(req)->rcv_isn + 1)) |
| 621 | req->ts_recent = tmp_opt.rcv_tsval; | 621 | req->ts_recent = tmp_opt.rcv_tsval; |
| 622 | 622 | ||
| 623 | if (TCP_SKB_CB(skb)->seq == tcp_rsk(req)->rcv_isn) { | 623 | if (TCP_SKB_CB(skb)->seq == tcp_rsk(req)->rcv_isn) { |
| 624 | /* Truncate SYN, it is out of window starting | 624 | /* Truncate SYN, it is out of window starting |
| 625 | at tcp_rsk(req)->rcv_isn + 1. */ | 625 | at tcp_rsk(req)->rcv_isn + 1. */ |
| 626 | flg &= ~TCP_FLAG_SYN; | 626 | flg &= ~TCP_FLAG_SYN; |
| 627 | } | 627 | } |
| 628 | 628 | ||
| 629 | /* RFC793: "second check the RST bit" and | 629 | /* RFC793: "second check the RST bit" and |
| 630 | * "fourth, check the SYN bit" | 630 | * "fourth, check the SYN bit" |
| 631 | */ | 631 | */ |
| 632 | if (flg & (TCP_FLAG_RST|TCP_FLAG_SYN)) { | 632 | if (flg & (TCP_FLAG_RST|TCP_FLAG_SYN)) { |
| 633 | TCP_INC_STATS_BH(sock_net(sk), TCP_MIB_ATTEMPTFAILS); | 633 | TCP_INC_STATS_BH(sock_net(sk), TCP_MIB_ATTEMPTFAILS); |
| 634 | goto embryonic_reset; | 634 | goto embryonic_reset; |
| 635 | } | 635 | } |
| 636 | 636 | ||
| 637 | /* ACK sequence verified above, just make sure ACK is | 637 | /* ACK sequence verified above, just make sure ACK is |
| 638 | * set. If ACK not set, just silently drop the packet. | 638 | * set. If ACK not set, just silently drop the packet. |
| 639 | */ | 639 | */ |
| 640 | if (!(flg & TCP_FLAG_ACK)) | 640 | if (!(flg & TCP_FLAG_ACK)) |
| 641 | return NULL; | 641 | return NULL; |
| 642 | |||
| 643 | /* If TCP_DEFER_ACCEPT is set, drop bare ACK. */ | ||
| 644 | if (inet_csk(sk)->icsk_accept_queue.rskq_defer_accept && | ||
| 645 | TCP_SKB_CB(skb)->end_seq == tcp_rsk(req)->rcv_isn + 1) { | ||
| 646 | inet_rsk(req)->acked = 1; | ||
| 647 | return NULL; | ||
| 648 | } | ||
| 649 | 642 | ||
| 650 | /* OK, ACK is valid, create big socket and | 643 | /* If TCP_DEFER_ACCEPT is set, drop bare ACK. */ |
| 651 | * feed this segment to it. It will repeat all | 644 | if (inet_csk(sk)->icsk_accept_queue.rskq_defer_accept && |
| 652 | * the tests. THIS SEGMENT MUST MOVE SOCKET TO | 645 | TCP_SKB_CB(skb)->end_seq == tcp_rsk(req)->rcv_isn + 1) { |
| 653 | * ESTABLISHED STATE. If it will be dropped after | 646 | inet_rsk(req)->acked = 1; |
| 654 | * socket is created, wait for troubles. | 647 | return NULL; |
| 655 | */ | 648 | } |
| 656 | child = inet_csk(sk)->icsk_af_ops->syn_recv_sock(sk, skb, | 649 | |
| 657 | req, NULL); | 650 | /* OK, ACK is valid, create big socket and |
| 658 | if (child == NULL) | 651 | * feed this segment to it. It will repeat all |
| 659 | goto listen_overflow; | 652 | * the tests. THIS SEGMENT MUST MOVE SOCKET TO |
| 653 | * ESTABLISHED STATE. If it will be dropped after | ||
| 654 | * socket is created, wait for troubles. | ||
| 655 | */ | ||
| 656 | child = inet_csk(sk)->icsk_af_ops->syn_recv_sock(sk, skb, req, NULL); | ||
| 657 | if (child == NULL) | ||
| 658 | goto listen_overflow; | ||
| 660 | #ifdef CONFIG_TCP_MD5SIG | 659 | #ifdef CONFIG_TCP_MD5SIG |
| 661 | else { | 660 | else { |
| 662 | /* Copy over the MD5 key from the original socket */ | 661 | /* Copy over the MD5 key from the original socket */ |
| 663 | struct tcp_md5sig_key *key; | 662 | struct tcp_md5sig_key *key; |
| 664 | struct tcp_sock *tp = tcp_sk(sk); | 663 | struct tcp_sock *tp = tcp_sk(sk); |
| 665 | key = tp->af_specific->md5_lookup(sk, child); | 664 | key = tp->af_specific->md5_lookup(sk, child); |
| 666 | if (key != NULL) { | 665 | if (key != NULL) { |
| 667 | /* | 666 | /* |
| 668 | * We're using one, so create a matching key on the | 667 | * We're using one, so create a matching key on the |
| 669 | * newsk structure. If we fail to get memory then we | 668 | * newsk structure. If we fail to get memory then we |
| 670 | * end up not copying the key across. Shucks. | 669 | * end up not copying the key across. Shucks. |
| 671 | */ | 670 | */ |
| 672 | char *newkey = kmemdup(key->key, key->keylen, | 671 | char *newkey = kmemdup(key->key, key->keylen, |
| 673 | GFP_ATOMIC); | 672 | GFP_ATOMIC); |
| 674 | if (newkey) { | 673 | if (newkey) { |
| 675 | if (!tcp_alloc_md5sig_pool()) | 674 | if (!tcp_alloc_md5sig_pool()) |
| 676 | BUG(); | 675 | BUG(); |
| 677 | tp->af_specific->md5_add(child, child, | 676 | tp->af_specific->md5_add(child, child, newkey, |
| 678 | newkey, | 677 | key->keylen); |
| 679 | key->keylen); | ||
| 680 | } | ||
| 681 | } | 678 | } |
| 682 | } | 679 | } |
| 680 | } | ||
| 683 | #endif | 681 | #endif |
| 684 | 682 | ||
| 685 | inet_csk_reqsk_queue_unlink(sk, req, prev); | 683 | inet_csk_reqsk_queue_unlink(sk, req, prev); |
| 686 | inet_csk_reqsk_queue_removed(sk, req); | 684 | inet_csk_reqsk_queue_removed(sk, req); |
| 687 | 685 | ||
| 688 | inet_csk_reqsk_queue_add(sk, req, child); | 686 | inet_csk_reqsk_queue_add(sk, req, child); |
| 689 | return child; | 687 | return child; |
| 690 | 688 | ||
| 691 | listen_overflow: | 689 | listen_overflow: |
| 692 | if (!sysctl_tcp_abort_on_overflow) { | 690 | if (!sysctl_tcp_abort_on_overflow) { |
| 693 | inet_rsk(req)->acked = 1; | 691 | inet_rsk(req)->acked = 1; |
| 694 | return NULL; | 692 | return NULL; |
| 695 | } | 693 | } |
| 696 | 694 | ||
| 697 | embryonic_reset: | 695 | embryonic_reset: |
| 698 | NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_EMBRYONICRSTS); | 696 | NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_EMBRYONICRSTS); |
| 699 | if (!(flg & TCP_FLAG_RST)) | 697 | if (!(flg & TCP_FLAG_RST)) |
| 700 | req->rsk_ops->send_reset(sk, skb); | 698 | req->rsk_ops->send_reset(sk, skb); |
| 701 | 699 | ||
| 702 | inet_csk_reqsk_queue_drop(sk, req, prev); | 700 | inet_csk_reqsk_queue_drop(sk, req, prev); |
| 703 | return NULL; | 701 | return NULL; |
| 704 | } | 702 | } |
| 705 | 703 | ||
| 706 | /* | 704 | /* |
diff --git a/net/ipv4/xfrm4_mode_beet.c b/net/ipv4/xfrm4_mode_beet.c index 9c798abce736..63418185f524 100644 --- a/net/ipv4/xfrm4_mode_beet.c +++ b/net/ipv4/xfrm4_mode_beet.c | |||
| @@ -47,8 +47,10 @@ static int xfrm4_beet_output(struct xfrm_state *x, struct sk_buff *skb) | |||
| 47 | if (unlikely(optlen)) | 47 | if (unlikely(optlen)) |
| 48 | hdrlen += IPV4_BEET_PHMAXLEN - (optlen & 4); | 48 | hdrlen += IPV4_BEET_PHMAXLEN - (optlen & 4); |
| 49 | 49 | ||
| 50 | skb_set_network_header(skb, IPV4_BEET_PHMAXLEN - x->props.header_len - | 50 | skb_set_network_header(skb, -x->props.header_len - |
| 51 | hdrlen); | 51 | hdrlen + (XFRM_MODE_SKB_CB(skb)->ihl - sizeof(*top_iph))); |
| 52 | if (x->sel.family != AF_INET6) | ||
| 53 | skb->network_header += IPV4_BEET_PHMAXLEN; | ||
| 52 | skb->mac_header = skb->network_header + | 54 | skb->mac_header = skb->network_header + |
| 53 | offsetof(struct iphdr, protocol); | 55 | offsetof(struct iphdr, protocol); |
| 54 | skb->transport_header = skb->network_header + sizeof(*top_iph); | 56 | skb->transport_header = skb->network_header + sizeof(*top_iph); |
diff --git a/net/ipv6/esp6.c b/net/ipv6/esp6.c index c6bb4c6d24b3..b181b08fb761 100644 --- a/net/ipv6/esp6.c +++ b/net/ipv6/esp6.c | |||
| @@ -521,6 +521,10 @@ static int esp6_init_state(struct xfrm_state *x) | |||
| 521 | crypto_aead_ivsize(aead); | 521 | crypto_aead_ivsize(aead); |
| 522 | switch (x->props.mode) { | 522 | switch (x->props.mode) { |
| 523 | case XFRM_MODE_BEET: | 523 | case XFRM_MODE_BEET: |
| 524 | if (x->sel.family != AF_INET6) | ||
| 525 | x->props.header_len += IPV4_BEET_PHMAXLEN + | ||
| 526 | (sizeof(struct ipv6hdr) - sizeof(struct iphdr)); | ||
| 527 | break; | ||
| 524 | case XFRM_MODE_TRANSPORT: | 528 | case XFRM_MODE_TRANSPORT: |
| 525 | break; | 529 | break; |
| 526 | case XFRM_MODE_TUNNEL: | 530 | case XFRM_MODE_TUNNEL: |
diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 86540b24b27c..5a3e87e4b18f 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c | |||
| @@ -1249,7 +1249,7 @@ install_route: | |||
| 1249 | 1249 | ||
| 1250 | if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) | 1250 | if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) |
| 1251 | rt->u.dst.metrics[RTAX_HOPLIMIT-1] = -1; | 1251 | rt->u.dst.metrics[RTAX_HOPLIMIT-1] = -1; |
| 1252 | if (!dst_metric(&rt->u.dst, RTAX_MTU)) | 1252 | if (!dst_mtu(&rt->u.dst)) |
| 1253 | rt->u.dst.metrics[RTAX_MTU-1] = ipv6_get_mtu(dev); | 1253 | rt->u.dst.metrics[RTAX_MTU-1] = ipv6_get_mtu(dev); |
| 1254 | if (!dst_metric(&rt->u.dst, RTAX_ADVMSS)) | 1254 | if (!dst_metric(&rt->u.dst, RTAX_ADVMSS)) |
| 1255 | rt->u.dst.metrics[RTAX_ADVMSS-1] = ipv6_advmss(net, dst_mtu(&rt->u.dst)); | 1255 | rt->u.dst.metrics[RTAX_ADVMSS-1] = ipv6_advmss(net, dst_mtu(&rt->u.dst)); |
diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c index 78185a409212..5b90b369ccb2 100644 --- a/net/ipv6/tcp_ipv6.c +++ b/net/ipv6/tcp_ipv6.c | |||
| @@ -69,7 +69,8 @@ | |||
| 69 | #include <linux/scatterlist.h> | 69 | #include <linux/scatterlist.h> |
| 70 | 70 | ||
| 71 | static void tcp_v6_send_reset(struct sock *sk, struct sk_buff *skb); | 71 | static void tcp_v6_send_reset(struct sock *sk, struct sk_buff *skb); |
| 72 | static void tcp_v6_reqsk_send_ack(struct sk_buff *skb, struct request_sock *req); | 72 | static void tcp_v6_reqsk_send_ack(struct sock *sk, struct sk_buff *skb, |
| 73 | struct request_sock *req); | ||
| 73 | 74 | ||
| 74 | static int tcp_v6_do_rcv(struct sock *sk, struct sk_buff *skb); | 75 | static int tcp_v6_do_rcv(struct sock *sk, struct sk_buff *skb); |
| 75 | 76 | ||
| @@ -1138,10 +1139,11 @@ static void tcp_v6_timewait_ack(struct sock *sk, struct sk_buff *skb) | |||
| 1138 | inet_twsk_put(tw); | 1139 | inet_twsk_put(tw); |
| 1139 | } | 1140 | } |
| 1140 | 1141 | ||
| 1141 | static void tcp_v6_reqsk_send_ack(struct sk_buff *skb, struct request_sock *req) | 1142 | static void tcp_v6_reqsk_send_ack(struct sock *sk, struct sk_buff *skb, |
| 1143 | struct request_sock *req) | ||
| 1142 | { | 1144 | { |
| 1143 | tcp_v6_send_ack(skb, tcp_rsk(req)->snt_isn + 1, tcp_rsk(req)->rcv_isn + 1, req->rcv_wnd, req->ts_recent, | 1145 | tcp_v6_send_ack(skb, tcp_rsk(req)->snt_isn + 1, tcp_rsk(req)->rcv_isn + 1, req->rcv_wnd, req->ts_recent, |
| 1144 | tcp_v6_md5_do_lookup(skb->sk, &ipv6_hdr(skb)->daddr)); | 1146 | tcp_v6_md5_do_lookup(sk, &ipv6_hdr(skb)->daddr)); |
| 1145 | } | 1147 | } |
| 1146 | 1148 | ||
| 1147 | 1149 | ||
diff --git a/net/ipv6/xfrm6_mode_beet.c b/net/ipv6/xfrm6_mode_beet.c index d6ce400f585f..bbd48b101bae 100644 --- a/net/ipv6/xfrm6_mode_beet.c +++ b/net/ipv6/xfrm6_mode_beet.c | |||
| @@ -40,16 +40,39 @@ static void xfrm6_beet_make_header(struct sk_buff *skb) | |||
| 40 | static int xfrm6_beet_output(struct xfrm_state *x, struct sk_buff *skb) | 40 | static int xfrm6_beet_output(struct xfrm_state *x, struct sk_buff *skb) |
| 41 | { | 41 | { |
| 42 | struct ipv6hdr *top_iph; | 42 | struct ipv6hdr *top_iph; |
| 43 | 43 | struct ip_beet_phdr *ph; | |
| 44 | skb_set_network_header(skb, -x->props.header_len); | 44 | struct iphdr *iphv4; |
| 45 | int optlen, hdr_len; | ||
| 46 | |||
| 47 | iphv4 = ip_hdr(skb); | ||
| 48 | hdr_len = 0; | ||
| 49 | optlen = XFRM_MODE_SKB_CB(skb)->optlen; | ||
| 50 | if (unlikely(optlen)) | ||
| 51 | hdr_len += IPV4_BEET_PHMAXLEN - (optlen & 4); | ||
| 52 | |||
| 53 | skb_set_network_header(skb, -x->props.header_len - hdr_len); | ||
| 54 | if (x->sel.family != AF_INET6) | ||
| 55 | skb->network_header += IPV4_BEET_PHMAXLEN; | ||
| 45 | skb->mac_header = skb->network_header + | 56 | skb->mac_header = skb->network_header + |
| 46 | offsetof(struct ipv6hdr, nexthdr); | 57 | offsetof(struct ipv6hdr, nexthdr); |
| 47 | skb->transport_header = skb->network_header + sizeof(*top_iph); | 58 | skb->transport_header = skb->network_header + sizeof(*top_iph); |
| 48 | __skb_pull(skb, XFRM_MODE_SKB_CB(skb)->ihl); | 59 | ph = (struct ip_beet_phdr *)__skb_pull(skb, XFRM_MODE_SKB_CB(skb)->ihl-hdr_len); |
| 49 | 60 | ||
| 50 | xfrm6_beet_make_header(skb); | 61 | xfrm6_beet_make_header(skb); |
| 51 | 62 | ||
| 52 | top_iph = ipv6_hdr(skb); | 63 | top_iph = ipv6_hdr(skb); |
| 64 | if (unlikely(optlen)) { | ||
| 65 | |||
| 66 | BUG_ON(optlen < 0); | ||
| 67 | |||
| 68 | ph->padlen = 4 - (optlen & 4); | ||
| 69 | ph->hdrlen = optlen / 8; | ||
| 70 | ph->nexthdr = top_iph->nexthdr; | ||
| 71 | if (ph->padlen) | ||
| 72 | memset(ph + 1, IPOPT_NOP, ph->padlen); | ||
| 73 | |||
| 74 | top_iph->nexthdr = IPPROTO_BEETPH; | ||
| 75 | } | ||
| 53 | 76 | ||
| 54 | ipv6_addr_copy(&top_iph->saddr, (struct in6_addr *)&x->props.saddr); | 77 | ipv6_addr_copy(&top_iph->saddr, (struct in6_addr *)&x->props.saddr); |
| 55 | ipv6_addr_copy(&top_iph->daddr, (struct in6_addr *)&x->id.daddr); | 78 | ipv6_addr_copy(&top_iph->daddr, (struct in6_addr *)&x->id.daddr); |
diff --git a/net/mac80211/main.c b/net/mac80211/main.c index 0c02c471bca2..aa5a191598c9 100644 --- a/net/mac80211/main.c +++ b/net/mac80211/main.c | |||
| @@ -245,10 +245,13 @@ static int ieee80211_open(struct net_device *dev) | |||
| 245 | case IEEE80211_IF_TYPE_AP: | 245 | case IEEE80211_IF_TYPE_AP: |
| 246 | sdata->bss = &sdata->u.ap; | 246 | sdata->bss = &sdata->u.ap; |
| 247 | break; | 247 | break; |
| 248 | case IEEE80211_IF_TYPE_MESH_POINT: | ||
| 249 | /* mesh ifaces must set allmulti to forward mcast traffic */ | ||
| 250 | atomic_inc(&local->iff_allmultis); | ||
| 251 | break; | ||
| 248 | case IEEE80211_IF_TYPE_STA: | 252 | case IEEE80211_IF_TYPE_STA: |
| 249 | case IEEE80211_IF_TYPE_MNTR: | 253 | case IEEE80211_IF_TYPE_MNTR: |
| 250 | case IEEE80211_IF_TYPE_IBSS: | 254 | case IEEE80211_IF_TYPE_IBSS: |
| 251 | case IEEE80211_IF_TYPE_MESH_POINT: | ||
| 252 | /* no special treatment */ | 255 | /* no special treatment */ |
| 253 | break; | 256 | break; |
| 254 | case IEEE80211_IF_TYPE_INVALID: | 257 | case IEEE80211_IF_TYPE_INVALID: |
| @@ -495,6 +498,9 @@ static int ieee80211_stop(struct net_device *dev) | |||
| 495 | netif_addr_unlock_bh(local->mdev); | 498 | netif_addr_unlock_bh(local->mdev); |
| 496 | break; | 499 | break; |
| 497 | case IEEE80211_IF_TYPE_MESH_POINT: | 500 | case IEEE80211_IF_TYPE_MESH_POINT: |
| 501 | /* allmulti is always set on mesh ifaces */ | ||
| 502 | atomic_dec(&local->iff_allmultis); | ||
| 503 | /* fall through */ | ||
| 498 | case IEEE80211_IF_TYPE_STA: | 504 | case IEEE80211_IF_TYPE_STA: |
| 499 | case IEEE80211_IF_TYPE_IBSS: | 505 | case IEEE80211_IF_TYPE_IBSS: |
| 500 | sdata->u.sta.state = IEEE80211_DISABLED; | 506 | sdata->u.sta.state = IEEE80211_DISABLED; |
diff --git a/net/mac80211/mesh.h b/net/mac80211/mesh.h index 669eafafe497..7495fbb0d211 100644 --- a/net/mac80211/mesh.h +++ b/net/mac80211/mesh.h | |||
| @@ -214,8 +214,7 @@ void ieee80211s_stop(void); | |||
| 214 | void ieee80211_mesh_init_sdata(struct ieee80211_sub_if_data *sdata); | 214 | void ieee80211_mesh_init_sdata(struct ieee80211_sub_if_data *sdata); |
| 215 | 215 | ||
| 216 | /* Mesh paths */ | 216 | /* Mesh paths */ |
| 217 | int mesh_nexthop_lookup(u8 *next_hop, struct sk_buff *skb, | 217 | int mesh_nexthop_lookup(struct sk_buff *skb, struct net_device *dev); |
| 218 | struct net_device *dev); | ||
| 219 | void mesh_path_start_discovery(struct net_device *dev); | 218 | void mesh_path_start_discovery(struct net_device *dev); |
| 220 | struct mesh_path *mesh_path_lookup(u8 *dst, struct net_device *dev); | 219 | struct mesh_path *mesh_path_lookup(u8 *dst, struct net_device *dev); |
| 221 | struct mesh_path *mesh_path_lookup_by_idx(int idx, struct net_device *dev); | 220 | struct mesh_path *mesh_path_lookup_by_idx(int idx, struct net_device *dev); |
| @@ -286,6 +285,4 @@ static inline void mesh_path_activate(struct mesh_path *mpath) | |||
| 286 | #define mesh_allocated 0 | 285 | #define mesh_allocated 0 |
| 287 | #endif | 286 | #endif |
| 288 | 287 | ||
| 289 | #define MESH_PREQ(skb) (skb->cb + 30) | ||
| 290 | |||
| 291 | #endif /* IEEE80211S_H */ | 288 | #endif /* IEEE80211S_H */ |
diff --git a/net/mac80211/mesh_hwmp.c b/net/mac80211/mesh_hwmp.c index 7fa149e230e6..08aca446ca01 100644 --- a/net/mac80211/mesh_hwmp.c +++ b/net/mac80211/mesh_hwmp.c | |||
| @@ -758,29 +758,30 @@ enddiscovery: | |||
| 758 | /** | 758 | /** |
| 759 | * ieee80211s_lookup_nexthop - put the appropriate next hop on a mesh frame | 759 | * ieee80211s_lookup_nexthop - put the appropriate next hop on a mesh frame |
| 760 | * | 760 | * |
| 761 | * @next_hop: output argument for next hop address | 761 | * @skb: 802.11 frame to be sent |
| 762 | * @skb: frame to be sent | ||
| 763 | * @dev: network device the frame will be sent through | 762 | * @dev: network device the frame will be sent through |
| 763 | * @fwd_frame: true if this frame was originally from a different host | ||
| 764 | * | 764 | * |
| 765 | * Returns: 0 if the next hop was found. Nonzero otherwise. If no next hop is | 765 | * Returns: 0 if the next hop was found. Nonzero otherwise. If no next hop is |
| 766 | * found, the function will start a path discovery and queue the frame so it is | 766 | * found, the function will start a path discovery and queue the frame so it is |
| 767 | * sent when the path is resolved. This means the caller must not free the skb | 767 | * sent when the path is resolved. This means the caller must not free the skb |
| 768 | * in this case. | 768 | * in this case. |
| 769 | */ | 769 | */ |
| 770 | int mesh_nexthop_lookup(u8 *next_hop, struct sk_buff *skb, | 770 | int mesh_nexthop_lookup(struct sk_buff *skb, struct net_device *dev) |
| 771 | struct net_device *dev) | ||
| 772 | { | 771 | { |
| 773 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); | 772 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); |
| 774 | struct sk_buff *skb_to_free = NULL; | 773 | struct sk_buff *skb_to_free = NULL; |
| 775 | struct mesh_path *mpath; | 774 | struct mesh_path *mpath; |
| 775 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | ||
| 776 | u8 *dst_addr = hdr->addr3; | ||
| 776 | int err = 0; | 777 | int err = 0; |
| 777 | 778 | ||
| 778 | rcu_read_lock(); | 779 | rcu_read_lock(); |
| 779 | mpath = mesh_path_lookup(skb->data, dev); | 780 | mpath = mesh_path_lookup(dst_addr, dev); |
| 780 | 781 | ||
| 781 | if (!mpath) { | 782 | if (!mpath) { |
| 782 | mesh_path_add(skb->data, dev); | 783 | mesh_path_add(dst_addr, dev); |
| 783 | mpath = mesh_path_lookup(skb->data, dev); | 784 | mpath = mesh_path_lookup(dst_addr, dev); |
| 784 | if (!mpath) { | 785 | if (!mpath) { |
| 785 | dev_kfree_skb(skb); | 786 | dev_kfree_skb(skb); |
| 786 | sdata->u.sta.mshstats.dropped_frames_no_route++; | 787 | sdata->u.sta.mshstats.dropped_frames_no_route++; |
| @@ -792,13 +793,13 @@ int mesh_nexthop_lookup(u8 *next_hop, struct sk_buff *skb, | |||
| 792 | if (mpath->flags & MESH_PATH_ACTIVE) { | 793 | if (mpath->flags & MESH_PATH_ACTIVE) { |
| 793 | if (time_after(jiffies, mpath->exp_time - | 794 | if (time_after(jiffies, mpath->exp_time - |
| 794 | msecs_to_jiffies(sdata->u.sta.mshcfg.path_refresh_time)) | 795 | msecs_to_jiffies(sdata->u.sta.mshcfg.path_refresh_time)) |
| 795 | && skb->pkt_type != PACKET_OTHERHOST | 796 | && !memcmp(dev->dev_addr, hdr->addr4, ETH_ALEN) |
| 796 | && !(mpath->flags & MESH_PATH_RESOLVING) | 797 | && !(mpath->flags & MESH_PATH_RESOLVING) |
| 797 | && !(mpath->flags & MESH_PATH_FIXED)) { | 798 | && !(mpath->flags & MESH_PATH_FIXED)) { |
| 798 | mesh_queue_preq(mpath, | 799 | mesh_queue_preq(mpath, |
| 799 | PREQ_Q_F_START | PREQ_Q_F_REFRESH); | 800 | PREQ_Q_F_START | PREQ_Q_F_REFRESH); |
| 800 | } | 801 | } |
| 801 | memcpy(next_hop, mpath->next_hop->addr, | 802 | memcpy(hdr->addr1, mpath->next_hop->addr, |
| 802 | ETH_ALEN); | 803 | ETH_ALEN); |
| 803 | } else { | 804 | } else { |
| 804 | if (!(mpath->flags & MESH_PATH_RESOLVING)) { | 805 | if (!(mpath->flags & MESH_PATH_RESOLVING)) { |
diff --git a/net/mac80211/mesh_pathtbl.c b/net/mac80211/mesh_pathtbl.c index 5f88a2e6ee50..838ee60492ad 100644 --- a/net/mac80211/mesh_pathtbl.c +++ b/net/mac80211/mesh_pathtbl.c | |||
| @@ -388,18 +388,15 @@ void mesh_path_tx_pending(struct mesh_path *mpath) | |||
| 388 | void mesh_path_discard_frame(struct sk_buff *skb, struct net_device *dev) | 388 | void mesh_path_discard_frame(struct sk_buff *skb, struct net_device *dev) |
| 389 | { | 389 | { |
| 390 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); | 390 | struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); |
| 391 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | ||
| 391 | struct mesh_path *mpath; | 392 | struct mesh_path *mpath; |
| 392 | u32 dsn = 0; | 393 | u32 dsn = 0; |
| 393 | 394 | ||
| 394 | if (skb->pkt_type == PACKET_OTHERHOST) { | 395 | if (memcmp(hdr->addr4, dev->dev_addr, ETH_ALEN) != 0) { |
| 395 | struct ieee80211s_hdr *prev_meshhdr; | ||
| 396 | int mshhdrlen; | ||
| 397 | u8 *ra, *da; | 396 | u8 *ra, *da; |
| 398 | 397 | ||
| 399 | prev_meshhdr = ((struct ieee80211s_hdr *)skb->cb); | 398 | da = hdr->addr3; |
| 400 | mshhdrlen = ieee80211_get_mesh_hdrlen(prev_meshhdr); | 399 | ra = hdr->addr2; |
| 401 | da = skb->data; | ||
| 402 | ra = MESH_PREQ(skb); | ||
| 403 | mpath = mesh_path_lookup(da, dev); | 400 | mpath = mesh_path_lookup(da, dev); |
| 404 | if (mpath) | 401 | if (mpath) |
| 405 | dsn = ++mpath->dsn; | 402 | dsn = ++mpath->dsn; |
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c index 6d9ae67c27ca..6db854505193 100644 --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c | |||
| @@ -1109,20 +1109,9 @@ ieee80211_data_to_8023(struct ieee80211_rx_data *rx) | |||
| 1109 | 1109 | ||
| 1110 | hdrlen = ieee80211_get_hdrlen(fc); | 1110 | hdrlen = ieee80211_get_hdrlen(fc); |
| 1111 | 1111 | ||
| 1112 | if (ieee80211_vif_is_mesh(&sdata->vif)) { | 1112 | if (ieee80211_vif_is_mesh(&sdata->vif)) |
| 1113 | int meshhdrlen = ieee80211_get_mesh_hdrlen( | 1113 | hdrlen += ieee80211_get_mesh_hdrlen( |
| 1114 | (struct ieee80211s_hdr *) (skb->data + hdrlen)); | 1114 | (struct ieee80211s_hdr *) (skb->data + hdrlen)); |
| 1115 | /* Copy on cb: | ||
| 1116 | * - mesh header: to be used for mesh forwarding | ||
| 1117 | * decision. It will also be used as mesh header template at | ||
| 1118 | * tx.c:ieee80211_subif_start_xmit() if interface | ||
| 1119 | * type is mesh and skb->pkt_type == PACKET_OTHERHOST | ||
| 1120 | * - ta: to be used if a RERR needs to be sent. | ||
| 1121 | */ | ||
| 1122 | memcpy(skb->cb, skb->data + hdrlen, meshhdrlen); | ||
| 1123 | memcpy(MESH_PREQ(skb), hdr->addr2, ETH_ALEN); | ||
| 1124 | hdrlen += meshhdrlen; | ||
| 1125 | } | ||
| 1126 | 1115 | ||
| 1127 | /* convert IEEE 802.11 header + possible LLC headers into Ethernet | 1116 | /* convert IEEE 802.11 header + possible LLC headers into Ethernet |
| 1128 | * header | 1117 | * header |
| @@ -1269,38 +1258,6 @@ ieee80211_deliver_skb(struct ieee80211_rx_data *rx) | |||
| 1269 | } | 1258 | } |
| 1270 | } | 1259 | } |
| 1271 | 1260 | ||
| 1272 | /* Mesh forwarding */ | ||
| 1273 | if (ieee80211_vif_is_mesh(&sdata->vif)) { | ||
| 1274 | u8 *mesh_ttl = &((struct ieee80211s_hdr *)skb->cb)->ttl; | ||
| 1275 | (*mesh_ttl)--; | ||
| 1276 | |||
| 1277 | if (is_multicast_ether_addr(skb->data)) { | ||
| 1278 | if (*mesh_ttl > 0) { | ||
| 1279 | xmit_skb = skb_copy(skb, GFP_ATOMIC); | ||
| 1280 | if (xmit_skb) | ||
| 1281 | xmit_skb->pkt_type = PACKET_OTHERHOST; | ||
| 1282 | else if (net_ratelimit()) | ||
| 1283 | printk(KERN_DEBUG "%s: failed to clone " | ||
| 1284 | "multicast frame\n", dev->name); | ||
| 1285 | } else | ||
| 1286 | IEEE80211_IFSTA_MESH_CTR_INC(&sdata->u.sta, | ||
| 1287 | dropped_frames_ttl); | ||
| 1288 | } else if (skb->pkt_type != PACKET_OTHERHOST && | ||
| 1289 | compare_ether_addr(dev->dev_addr, skb->data) != 0) { | ||
| 1290 | if (*mesh_ttl == 0) { | ||
| 1291 | IEEE80211_IFSTA_MESH_CTR_INC(&sdata->u.sta, | ||
| 1292 | dropped_frames_ttl); | ||
| 1293 | dev_kfree_skb(skb); | ||
| 1294 | skb = NULL; | ||
| 1295 | } else { | ||
| 1296 | xmit_skb = skb; | ||
| 1297 | xmit_skb->pkt_type = PACKET_OTHERHOST; | ||
| 1298 | if (!(dev->flags & IFF_PROMISC)) | ||
| 1299 | skb = NULL; | ||
| 1300 | } | ||
| 1301 | } | ||
| 1302 | } | ||
| 1303 | |||
| 1304 | if (skb) { | 1261 | if (skb) { |
| 1305 | /* deliver to local stack */ | 1262 | /* deliver to local stack */ |
| 1306 | skb->protocol = eth_type_trans(skb, dev); | 1263 | skb->protocol = eth_type_trans(skb, dev); |
| @@ -1431,6 +1388,63 @@ ieee80211_rx_h_amsdu(struct ieee80211_rx_data *rx) | |||
| 1431 | } | 1388 | } |
| 1432 | 1389 | ||
| 1433 | static ieee80211_rx_result debug_noinline | 1390 | static ieee80211_rx_result debug_noinline |
| 1391 | ieee80211_rx_h_mesh_fwding(struct ieee80211_rx_data *rx) | ||
| 1392 | { | ||
| 1393 | struct ieee80211_hdr *hdr; | ||
| 1394 | struct ieee80211s_hdr *mesh_hdr; | ||
| 1395 | unsigned int hdrlen; | ||
| 1396 | struct sk_buff *skb = rx->skb, *fwd_skb; | ||
| 1397 | |||
| 1398 | hdr = (struct ieee80211_hdr *) skb->data; | ||
| 1399 | hdrlen = ieee80211_hdrlen(hdr->frame_control); | ||
| 1400 | mesh_hdr = (struct ieee80211s_hdr *) (skb->data + hdrlen); | ||
| 1401 | |||
| 1402 | if (!ieee80211_is_data(hdr->frame_control)) | ||
| 1403 | return RX_CONTINUE; | ||
| 1404 | |||
| 1405 | if (!mesh_hdr->ttl) | ||
| 1406 | /* illegal frame */ | ||
| 1407 | return RX_DROP_MONITOR; | ||
| 1408 | |||
| 1409 | if (compare_ether_addr(rx->dev->dev_addr, hdr->addr3) == 0) | ||
| 1410 | return RX_CONTINUE; | ||
| 1411 | |||
| 1412 | mesh_hdr->ttl--; | ||
| 1413 | |||
| 1414 | if (rx->flags & IEEE80211_RX_RA_MATCH) { | ||
| 1415 | if (!mesh_hdr->ttl) | ||
| 1416 | IEEE80211_IFSTA_MESH_CTR_INC(&rx->sdata->u.sta, | ||
| 1417 | dropped_frames_ttl); | ||
| 1418 | else { | ||
| 1419 | struct ieee80211_hdr *fwd_hdr; | ||
| 1420 | fwd_skb = skb_copy(skb, GFP_ATOMIC); | ||
| 1421 | |||
| 1422 | if (!fwd_skb && net_ratelimit()) | ||
| 1423 | printk(KERN_DEBUG "%s: failed to clone mesh frame\n", | ||
| 1424 | rx->dev->name); | ||
| 1425 | |||
| 1426 | fwd_hdr = (struct ieee80211_hdr *) fwd_skb->data; | ||
| 1427 | /* | ||
| 1428 | * Save TA to addr1 to send TA a path error if a | ||
| 1429 | * suitable next hop is not found | ||
| 1430 | */ | ||
| 1431 | memcpy(fwd_hdr->addr1, fwd_hdr->addr2, ETH_ALEN); | ||
| 1432 | memcpy(fwd_hdr->addr2, rx->dev->dev_addr, ETH_ALEN); | ||
| 1433 | fwd_skb->dev = rx->local->mdev; | ||
| 1434 | fwd_skb->iif = rx->dev->ifindex; | ||
| 1435 | dev_queue_xmit(fwd_skb); | ||
| 1436 | } | ||
| 1437 | } | ||
| 1438 | |||
| 1439 | if (is_multicast_ether_addr(hdr->addr3) || | ||
| 1440 | rx->dev->flags & IFF_PROMISC) | ||
| 1441 | return RX_CONTINUE; | ||
| 1442 | else | ||
| 1443 | return RX_DROP_MONITOR; | ||
| 1444 | } | ||
| 1445 | |||
| 1446 | |||
| 1447 | static ieee80211_rx_result debug_noinline | ||
| 1434 | ieee80211_rx_h_data(struct ieee80211_rx_data *rx) | 1448 | ieee80211_rx_h_data(struct ieee80211_rx_data *rx) |
| 1435 | { | 1449 | { |
| 1436 | struct net_device *dev = rx->dev; | 1450 | struct net_device *dev = rx->dev; |
| @@ -1663,10 +1677,12 @@ static void ieee80211_invoke_rx_handlers(struct ieee80211_sub_if_data *sdata, | |||
| 1663 | rx->sdata = sdata; | 1677 | rx->sdata = sdata; |
| 1664 | rx->dev = sdata->dev; | 1678 | rx->dev = sdata->dev; |
| 1665 | 1679 | ||
| 1666 | #define CALL_RXH(rxh) \ | 1680 | #define CALL_RXH(rxh) \ |
| 1667 | res = rxh(rx); \ | 1681 | do { \ |
| 1668 | if (res != RX_CONTINUE) \ | 1682 | res = rxh(rx); \ |
| 1669 | goto rxh_done; | 1683 | if (res != RX_CONTINUE) \ |
| 1684 | goto rxh_done; \ | ||
| 1685 | } while (0); | ||
| 1670 | 1686 | ||
| 1671 | CALL_RXH(ieee80211_rx_h_passive_scan) | 1687 | CALL_RXH(ieee80211_rx_h_passive_scan) |
| 1672 | CALL_RXH(ieee80211_rx_h_check) | 1688 | CALL_RXH(ieee80211_rx_h_check) |
| @@ -1678,6 +1694,8 @@ static void ieee80211_invoke_rx_handlers(struct ieee80211_sub_if_data *sdata, | |||
| 1678 | /* must be after MMIC verify so header is counted in MPDU mic */ | 1694 | /* must be after MMIC verify so header is counted in MPDU mic */ |
| 1679 | CALL_RXH(ieee80211_rx_h_remove_qos_control) | 1695 | CALL_RXH(ieee80211_rx_h_remove_qos_control) |
| 1680 | CALL_RXH(ieee80211_rx_h_amsdu) | 1696 | CALL_RXH(ieee80211_rx_h_amsdu) |
| 1697 | if (ieee80211_vif_is_mesh(&sdata->vif)) | ||
| 1698 | CALL_RXH(ieee80211_rx_h_mesh_fwding); | ||
| 1681 | CALL_RXH(ieee80211_rx_h_data) | 1699 | CALL_RXH(ieee80211_rx_h_data) |
| 1682 | CALL_RXH(ieee80211_rx_h_ctrl) | 1700 | CALL_RXH(ieee80211_rx_h_ctrl) |
| 1683 | CALL_RXH(ieee80211_rx_h_mgmt) | 1701 | CALL_RXH(ieee80211_rx_h_mgmt) |
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c index 771ec68b848d..4788f7b91f49 100644 --- a/net/mac80211/tx.c +++ b/net/mac80211/tx.c | |||
| @@ -1301,6 +1301,7 @@ int ieee80211_master_start_xmit(struct sk_buff *skb, | |||
| 1301 | struct net_device *dev) | 1301 | struct net_device *dev) |
| 1302 | { | 1302 | { |
| 1303 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | 1303 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); |
| 1304 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | ||
| 1304 | struct net_device *odev = NULL; | 1305 | struct net_device *odev = NULL; |
| 1305 | struct ieee80211_sub_if_data *osdata; | 1306 | struct ieee80211_sub_if_data *osdata; |
| 1306 | int headroom; | 1307 | int headroom; |
| @@ -1328,6 +1329,20 @@ int ieee80211_master_start_xmit(struct sk_buff *skb, | |||
| 1328 | 1329 | ||
| 1329 | osdata = IEEE80211_DEV_TO_SUB_IF(odev); | 1330 | osdata = IEEE80211_DEV_TO_SUB_IF(odev); |
| 1330 | 1331 | ||
| 1332 | if (ieee80211_vif_is_mesh(&osdata->vif) && | ||
| 1333 | ieee80211_is_data(hdr->frame_control)) { | ||
| 1334 | if (ieee80211_is_data(hdr->frame_control)) { | ||
| 1335 | if (is_multicast_ether_addr(hdr->addr3)) | ||
| 1336 | memcpy(hdr->addr1, hdr->addr3, ETH_ALEN); | ||
| 1337 | else | ||
| 1338 | if (mesh_nexthop_lookup(skb, odev)) | ||
| 1339 | return 0; | ||
| 1340 | if (memcmp(odev->dev_addr, hdr->addr4, ETH_ALEN) != 0) | ||
| 1341 | IEEE80211_IFSTA_MESH_CTR_INC(&osdata->u.sta, | ||
| 1342 | fwded_frames); | ||
| 1343 | } | ||
| 1344 | } | ||
| 1345 | |||
| 1331 | may_encrypt = !skb->do_not_encrypt; | 1346 | may_encrypt = !skb->do_not_encrypt; |
| 1332 | 1347 | ||
| 1333 | headroom = osdata->local->tx_headroom; | 1348 | headroom = osdata->local->tx_headroom; |
| @@ -1472,30 +1487,17 @@ int ieee80211_subif_start_xmit(struct sk_buff *skb, | |||
| 1472 | case IEEE80211_IF_TYPE_MESH_POINT: | 1487 | case IEEE80211_IF_TYPE_MESH_POINT: |
| 1473 | fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS); | 1488 | fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS); |
| 1474 | /* RA TA DA SA */ | 1489 | /* RA TA DA SA */ |
| 1475 | if (is_multicast_ether_addr(skb->data)) | 1490 | memset(hdr.addr1, 0, ETH_ALEN); |
| 1476 | memcpy(hdr.addr1, skb->data, ETH_ALEN); | ||
| 1477 | else if (mesh_nexthop_lookup(hdr.addr1, skb, dev)) | ||
| 1478 | return 0; | ||
| 1479 | memcpy(hdr.addr2, dev->dev_addr, ETH_ALEN); | 1491 | memcpy(hdr.addr2, dev->dev_addr, ETH_ALEN); |
| 1480 | memcpy(hdr.addr3, skb->data, ETH_ALEN); | 1492 | memcpy(hdr.addr3, skb->data, ETH_ALEN); |
| 1481 | memcpy(hdr.addr4, skb->data + ETH_ALEN, ETH_ALEN); | 1493 | memcpy(hdr.addr4, skb->data + ETH_ALEN, ETH_ALEN); |
| 1482 | if (skb->pkt_type == PACKET_OTHERHOST) { | 1494 | if (!sdata->u.sta.mshcfg.dot11MeshTTL) { |
| 1483 | /* Forwarded frame, keep mesh ttl and seqnum */ | 1495 | /* Do not send frames with mesh_ttl == 0 */ |
| 1484 | struct ieee80211s_hdr *prev_meshhdr; | 1496 | sdata->u.sta.mshstats.dropped_frames_ttl++; |
| 1485 | prev_meshhdr = ((struct ieee80211s_hdr *)skb->cb); | 1497 | ret = 0; |
| 1486 | meshhdrlen = ieee80211_get_mesh_hdrlen(prev_meshhdr); | 1498 | goto fail; |
| 1487 | memcpy(&mesh_hdr, prev_meshhdr, meshhdrlen); | ||
| 1488 | sdata->u.sta.mshstats.fwded_frames++; | ||
| 1489 | } else { | ||
| 1490 | if (!sdata->u.sta.mshcfg.dot11MeshTTL) { | ||
| 1491 | /* Do not send frames with mesh_ttl == 0 */ | ||
| 1492 | sdata->u.sta.mshstats.dropped_frames_ttl++; | ||
| 1493 | ret = 0; | ||
| 1494 | goto fail; | ||
| 1495 | } | ||
| 1496 | meshhdrlen = ieee80211_new_mesh_header(&mesh_hdr, | ||
| 1497 | sdata); | ||
| 1498 | } | 1499 | } |
| 1500 | meshhdrlen = ieee80211_new_mesh_header(&mesh_hdr, sdata); | ||
| 1499 | hdrlen = 30; | 1501 | hdrlen = 30; |
| 1500 | break; | 1502 | break; |
| 1501 | #endif | 1503 | #endif |
| @@ -1543,7 +1545,8 @@ int ieee80211_subif_start_xmit(struct sk_buff *skb, | |||
| 1543 | * Drop unicast frames to unauthorised stations unless they are | 1545 | * Drop unicast frames to unauthorised stations unless they are |
| 1544 | * EAPOL frames from the local station. | 1546 | * EAPOL frames from the local station. |
| 1545 | */ | 1547 | */ |
| 1546 | if (unlikely(!is_multicast_ether_addr(hdr.addr1) && | 1548 | if (!ieee80211_vif_is_mesh(&sdata->vif) && |
| 1549 | unlikely(!is_multicast_ether_addr(hdr.addr1) && | ||
| 1547 | !(sta_flags & WLAN_STA_AUTHORIZED) && | 1550 | !(sta_flags & WLAN_STA_AUTHORIZED) && |
| 1548 | !(ethertype == ETH_P_PAE && | 1551 | !(ethertype == ETH_P_PAE && |
| 1549 | compare_ether_addr(dev->dev_addr, | 1552 | compare_ether_addr(dev->dev_addr, |
diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c index c519d090bdb9..9d1830da8e84 100644 --- a/net/netfilter/nf_conntrack_core.c +++ b/net/netfilter/nf_conntrack_core.c | |||
| @@ -1032,10 +1032,10 @@ void nf_conntrack_cleanup(void) | |||
| 1032 | nf_ct_free_hashtable(nf_conntrack_hash, nf_conntrack_vmalloc, | 1032 | nf_ct_free_hashtable(nf_conntrack_hash, nf_conntrack_vmalloc, |
| 1033 | nf_conntrack_htable_size); | 1033 | nf_conntrack_htable_size); |
| 1034 | 1034 | ||
| 1035 | nf_conntrack_proto_fini(); | ||
| 1036 | nf_conntrack_helper_fini(); | ||
| 1037 | nf_conntrack_expect_fini(); | ||
| 1038 | nf_conntrack_acct_fini(); | 1035 | nf_conntrack_acct_fini(); |
| 1036 | nf_conntrack_expect_fini(); | ||
| 1037 | nf_conntrack_helper_fini(); | ||
| 1038 | nf_conntrack_proto_fini(); | ||
| 1039 | } | 1039 | } |
| 1040 | 1040 | ||
| 1041 | struct hlist_head *nf_ct_alloc_hashtable(unsigned int *sizep, int *vmalloced) | 1041 | struct hlist_head *nf_ct_alloc_hashtable(unsigned int *sizep, int *vmalloced) |
diff --git a/net/netfilter/nf_conntrack_standalone.c b/net/netfilter/nf_conntrack_standalone.c index 869ef9349d0f..8509db14670b 100644 --- a/net/netfilter/nf_conntrack_standalone.c +++ b/net/netfilter/nf_conntrack_standalone.c | |||
| @@ -324,6 +324,7 @@ static int log_invalid_proto_min = 0; | |||
| 324 | static int log_invalid_proto_max = 255; | 324 | static int log_invalid_proto_max = 255; |
| 325 | 325 | ||
| 326 | static struct ctl_table_header *nf_ct_sysctl_header; | 326 | static struct ctl_table_header *nf_ct_sysctl_header; |
| 327 | static struct ctl_table_header *nf_ct_netfilter_header; | ||
| 327 | 328 | ||
| 328 | static ctl_table nf_ct_sysctl_table[] = { | 329 | static ctl_table nf_ct_sysctl_table[] = { |
| 329 | { | 330 | { |
| @@ -384,12 +385,6 @@ static ctl_table nf_ct_sysctl_table[] = { | |||
| 384 | 385 | ||
| 385 | static ctl_table nf_ct_netfilter_table[] = { | 386 | static ctl_table nf_ct_netfilter_table[] = { |
| 386 | { | 387 | { |
| 387 | .ctl_name = NET_NETFILTER, | ||
| 388 | .procname = "netfilter", | ||
| 389 | .mode = 0555, | ||
| 390 | .child = nf_ct_sysctl_table, | ||
| 391 | }, | ||
| 392 | { | ||
| 393 | .ctl_name = NET_NF_CONNTRACK_MAX, | 388 | .ctl_name = NET_NF_CONNTRACK_MAX, |
| 394 | .procname = "nf_conntrack_max", | 389 | .procname = "nf_conntrack_max", |
| 395 | .data = &nf_conntrack_max, | 390 | .data = &nf_conntrack_max, |
| @@ -409,18 +404,29 @@ EXPORT_SYMBOL_GPL(nf_ct_log_invalid); | |||
| 409 | 404 | ||
| 410 | static int nf_conntrack_standalone_init_sysctl(void) | 405 | static int nf_conntrack_standalone_init_sysctl(void) |
| 411 | { | 406 | { |
| 412 | nf_ct_sysctl_header = | 407 | nf_ct_netfilter_header = |
| 413 | register_sysctl_paths(nf_ct_path, nf_ct_netfilter_table); | 408 | register_sysctl_paths(nf_ct_path, nf_ct_netfilter_table); |
| 414 | if (nf_ct_sysctl_header == NULL) { | 409 | if (!nf_ct_netfilter_header) |
| 415 | printk("nf_conntrack: can't register to sysctl.\n"); | 410 | goto out; |
| 416 | return -ENOMEM; | 411 | |
| 417 | } | 412 | nf_ct_sysctl_header = |
| 413 | register_sysctl_paths(nf_net_netfilter_sysctl_path, | ||
| 414 | nf_ct_sysctl_table); | ||
| 415 | if (!nf_ct_sysctl_header) | ||
| 416 | goto out_unregister_netfilter; | ||
| 417 | |||
| 418 | return 0; | 418 | return 0; |
| 419 | 419 | ||
| 420 | out_unregister_netfilter: | ||
| 421 | unregister_sysctl_table(nf_ct_netfilter_header); | ||
| 422 | out: | ||
| 423 | printk("nf_conntrack: can't register to sysctl.\n"); | ||
| 424 | return -ENOMEM; | ||
| 420 | } | 425 | } |
| 421 | 426 | ||
| 422 | static void nf_conntrack_standalone_fini_sysctl(void) | 427 | static void nf_conntrack_standalone_fini_sysctl(void) |
| 423 | { | 428 | { |
| 429 | unregister_sysctl_table(nf_ct_netfilter_header); | ||
| 424 | unregister_sysctl_table(nf_ct_sysctl_header); | 430 | unregister_sysctl_table(nf_ct_sysctl_header); |
| 425 | } | 431 | } |
| 426 | #else | 432 | #else |
diff --git a/net/sched/act_api.c b/net/sched/act_api.c index d308c19aa3f9..26c7e1f9a350 100644 --- a/net/sched/act_api.c +++ b/net/sched/act_api.c | |||
| @@ -205,10 +205,9 @@ struct tcf_common *tcf_hash_check(u32 index, struct tc_action *a, int bind, | |||
| 205 | { | 205 | { |
| 206 | struct tcf_common *p = NULL; | 206 | struct tcf_common *p = NULL; |
| 207 | if (index && (p = tcf_hash_lookup(index, hinfo)) != NULL) { | 207 | if (index && (p = tcf_hash_lookup(index, hinfo)) != NULL) { |
| 208 | if (bind) { | 208 | if (bind) |
| 209 | p->tcfc_bindcnt++; | 209 | p->tcfc_bindcnt++; |
| 210 | p->tcfc_refcnt++; | 210 | p->tcfc_refcnt++; |
| 211 | } | ||
| 212 | a->priv = p; | 211 | a->priv = p; |
| 213 | } | 212 | } |
| 214 | return p; | 213 | return p; |
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c index 4840aff47256..ba1d121f3127 100644 --- a/net/sched/sch_api.c +++ b/net/sched/sch_api.c | |||
| @@ -189,7 +189,7 @@ struct Qdisc *qdisc_lookup(struct net_device *dev, u32 handle) | |||
| 189 | 189 | ||
| 190 | for (i = 0; i < dev->num_tx_queues; i++) { | 190 | for (i = 0; i < dev->num_tx_queues; i++) { |
| 191 | struct netdev_queue *txq = netdev_get_tx_queue(dev, i); | 191 | struct netdev_queue *txq = netdev_get_tx_queue(dev, i); |
| 192 | struct Qdisc *q, *txq_root = txq->qdisc; | 192 | struct Qdisc *q, *txq_root = txq->qdisc_sleeping; |
| 193 | 193 | ||
| 194 | if (!(txq_root->flags & TCQ_F_BUILTIN) && | 194 | if (!(txq_root->flags & TCQ_F_BUILTIN) && |
| 195 | txq_root->handle == handle) | 195 | txq_root->handle == handle) |
| @@ -792,8 +792,8 @@ qdisc_create(struct net_device *dev, struct netdev_queue *dev_queue, | |||
| 792 | goto err_out3; | 792 | goto err_out3; |
| 793 | } | 793 | } |
| 794 | } | 794 | } |
| 795 | if (parent && !(sch->flags & TCQ_F_INGRESS)) | 795 | if ((parent != TC_H_ROOT) && !(sch->flags & TCQ_F_INGRESS)) |
| 796 | list_add_tail(&sch->list, &dev_queue->qdisc->list); | 796 | list_add_tail(&sch->list, &dev_queue->qdisc_sleeping->list); |
| 797 | 797 | ||
| 798 | return sch; | 798 | return sch; |
| 799 | } | 799 | } |
| @@ -1236,11 +1236,11 @@ static int tc_dump_qdisc(struct sk_buff *skb, struct netlink_callback *cb) | |||
| 1236 | q_idx = 0; | 1236 | q_idx = 0; |
| 1237 | 1237 | ||
| 1238 | dev_queue = netdev_get_tx_queue(dev, 0); | 1238 | dev_queue = netdev_get_tx_queue(dev, 0); |
| 1239 | if (tc_dump_qdisc_root(dev_queue->qdisc, skb, cb, &q_idx, s_q_idx) < 0) | 1239 | if (tc_dump_qdisc_root(dev_queue->qdisc_sleeping, skb, cb, &q_idx, s_q_idx) < 0) |
| 1240 | goto done; | 1240 | goto done; |
| 1241 | 1241 | ||
| 1242 | dev_queue = &dev->rx_queue; | 1242 | dev_queue = &dev->rx_queue; |
| 1243 | if (tc_dump_qdisc_root(dev_queue->qdisc, skb, cb, &q_idx, s_q_idx) < 0) | 1243 | if (tc_dump_qdisc_root(dev_queue->qdisc_sleeping, skb, cb, &q_idx, s_q_idx) < 0) |
| 1244 | goto done; | 1244 | goto done; |
| 1245 | 1245 | ||
| 1246 | cont: | 1246 | cont: |
diff --git a/net/wanrouter/wanmain.c b/net/wanrouter/wanmain.c index b210a88d0960..7f07152bc109 100644 --- a/net/wanrouter/wanmain.c +++ b/net/wanrouter/wanmain.c | |||
| @@ -57,7 +57,6 @@ | |||
| 57 | #include <linux/vmalloc.h> /* vmalloc, vfree */ | 57 | #include <linux/vmalloc.h> /* vmalloc, vfree */ |
| 58 | #include <asm/uaccess.h> /* copy_to/from_user */ | 58 | #include <asm/uaccess.h> /* copy_to/from_user */ |
| 59 | #include <linux/init.h> /* __initfunc et al. */ | 59 | #include <linux/init.h> /* __initfunc et al. */ |
| 60 | #include <net/syncppp.h> | ||
| 61 | 60 | ||
| 62 | #define KMEM_SAFETYZONE 8 | 61 | #define KMEM_SAFETYZONE 8 |
| 63 | 62 | ||
| @@ -567,9 +566,6 @@ static int wanrouter_device_new_if(struct wan_device *wandev, | |||
| 567 | { | 566 | { |
| 568 | wanif_conf_t *cnf; | 567 | wanif_conf_t *cnf; |
| 569 | struct net_device *dev = NULL; | 568 | struct net_device *dev = NULL; |
| 570 | #ifdef CONFIG_WANPIPE_MULTPPP | ||
| 571 | struct ppp_device *pppdev=NULL; | ||
| 572 | #endif | ||
| 573 | int err; | 569 | int err; |
| 574 | 570 | ||
| 575 | if ((wandev->state == WAN_UNCONFIGURED) || (wandev->new_if == NULL)) | 571 | if ((wandev->state == WAN_UNCONFIGURED) || (wandev->new_if == NULL)) |
| @@ -588,25 +584,10 @@ static int wanrouter_device_new_if(struct wan_device *wandev, | |||
| 588 | goto out; | 584 | goto out; |
| 589 | 585 | ||
| 590 | if (cnf->config_id == WANCONFIG_MPPP) { | 586 | if (cnf->config_id == WANCONFIG_MPPP) { |
| 591 | #ifdef CONFIG_WANPIPE_MULTPPP | ||
| 592 | pppdev = kzalloc(sizeof(struct ppp_device), GFP_KERNEL); | ||
| 593 | err = -ENOBUFS; | ||
| 594 | if (pppdev == NULL) | ||
| 595 | goto out; | ||
| 596 | pppdev->dev = kzalloc(sizeof(struct net_device), GFP_KERNEL); | ||
| 597 | if (pppdev->dev == NULL) { | ||
| 598 | kfree(pppdev); | ||
| 599 | err = -ENOBUFS; | ||
| 600 | goto out; | ||
| 601 | } | ||
| 602 | err = wandev->new_if(wandev, (struct net_device *)pppdev, cnf); | ||
| 603 | dev = pppdev->dev; | ||
| 604 | #else | ||
| 605 | printk(KERN_INFO "%s: Wanpipe Mulit-Port PPP support has not been compiled in!\n", | 587 | printk(KERN_INFO "%s: Wanpipe Mulit-Port PPP support has not been compiled in!\n", |
| 606 | wandev->name); | 588 | wandev->name); |
| 607 | err = -EPROTONOSUPPORT; | 589 | err = -EPROTONOSUPPORT; |
| 608 | goto out; | 590 | goto out; |
| 609 | #endif | ||
| 610 | } else { | 591 | } else { |
| 611 | dev = kzalloc(sizeof(struct net_device), GFP_KERNEL); | 592 | dev = kzalloc(sizeof(struct net_device), GFP_KERNEL); |
| 612 | err = -ENOBUFS; | 593 | err = -ENOBUFS; |
| @@ -661,17 +642,9 @@ static int wanrouter_device_new_if(struct wan_device *wandev, | |||
| 661 | kfree(dev->priv); | 642 | kfree(dev->priv); |
| 662 | dev->priv = NULL; | 643 | dev->priv = NULL; |
| 663 | 644 | ||
| 664 | #ifdef CONFIG_WANPIPE_MULTPPP | ||
| 665 | if (cnf->config_id == WANCONFIG_MPPP) | ||
| 666 | kfree(pppdev); | ||
| 667 | else | ||
| 668 | kfree(dev); | ||
| 669 | #else | ||
| 670 | /* Sync PPP is disabled */ | 645 | /* Sync PPP is disabled */ |
| 671 | if (cnf->config_id != WANCONFIG_MPPP) | 646 | if (cnf->config_id != WANCONFIG_MPPP) |
| 672 | kfree(dev); | 647 | kfree(dev); |
| 673 | #endif | ||
| 674 | |||
| 675 | out: | 648 | out: |
| 676 | kfree(cnf); | 649 | kfree(cnf); |
| 677 | return err; | 650 | return err; |
