From b69b9e143e42af9ea924c8077ae16c2904e3e972 Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Mon, 9 Jul 2012 16:18:55 -0700 Subject: [PATCH] 3.0-stable patches added patches: be2net-fix-a-race-in-be_xmit.patch bonding-fix-corrupted-queue_mapping.patch bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch dummy-fix-rcu_sched-self-detected-stalls.patch ethtool-allow-ethtool_gsset_info-for-users.patch ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch netpoll-fix-netpoll_send_udp-bugs.patch net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch sky2-fix-checksum-bit-management-on-some-chips.patch --- queue-3.0/be2net-fix-a-race-in-be_xmit.patch | 42 ++++++ .../bonding-fix-corrupted-queue_mapping.patch | 113 ++++++++++++++++ ...-bridge-devices-created-via-ioctl-v2.patch | 55 ++++++++ ...-correctly-when-netlabel-is-disabled.patch | 77 +++++++++++ ...y-fix-rcu_sched-self-detected-stalls.patch | 39 ++++++ ...l-allow-ethtool_gsset_info-for-users.patch | 31 +++++ ...le-registration-to-end-of-init-order.patch | 123 ++++++++++++++++++ ...h-fix-kernel-panic-on-rmmod-l2tp_eth.patch | 41 ++++++ ...locating-skb-in-sock_alloc_send_pskb.patch | 50 +++++++ .../netpoll-fix-netpoll_send_udp-bugs.patch | 75 +++++++++++ queue-3.0/series | 11 ++ ...hecksum-bit-management-on-some-chips.patch | 45 +++++++ 12 files changed, 702 insertions(+) create mode 100644 queue-3.0/be2net-fix-a-race-in-be_xmit.patch create mode 100644 queue-3.0/bonding-fix-corrupted-queue_mapping.patch create mode 100644 queue-3.0/bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch create mode 100644 queue-3.0/cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch create mode 100644 queue-3.0/dummy-fix-rcu_sched-self-detected-stalls.patch create mode 100644 queue-3.0/ethtool-allow-ethtool_gsset_info-for-users.patch create mode 100644 queue-3.0/ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch create mode 100644 queue-3.0/net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch create mode 100644 queue-3.0/net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch create mode 100644 queue-3.0/netpoll-fix-netpoll_send_udp-bugs.patch create mode 100644 queue-3.0/sky2-fix-checksum-bit-management-on-some-chips.patch diff --git a/queue-3.0/be2net-fix-a-race-in-be_xmit.patch b/queue-3.0/be2net-fix-a-race-in-be_xmit.patch new file mode 100644 index 00000000000..b583dfa6d6c --- /dev/null +++ b/queue-3.0/be2net-fix-a-race-in-be_xmit.patch @@ -0,0 +1,42 @@ +From 8074e5e58716e64f4077862596756c04227b5c57 Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Thu, 7 Jun 2012 22:59:59 +0000 +Subject: be2net: fix a race in be_xmit() + + +From: Eric Dumazet + +[ Upstream commit cd8f76c0a0c6fce0b2cf23c9bd0123f91453f46d ] + +As soon as hardware is notified of a transmit, we no longer can assume +skb can be dereferenced, as TX completion might have freed the packet. + +Signed-off-by: Eric Dumazet +Cc: Sathya Perla +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/benet/be_main.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +--- a/drivers/net/benet/be_main.c ++++ b/drivers/net/benet/be_main.c +@@ -763,6 +763,8 @@ static netdev_tx_t be_xmit(struct sk_buf + + copied = make_tx_wrbs(adapter, skb, wrb_cnt, dummy_wrb); + if (copied) { ++ int gso_segs = skb_shinfo(skb)->gso_segs; ++ + /* record the sent skb in the sent_skb table */ + BUG_ON(tx_obj->sent_skb_list[start]); + tx_obj->sent_skb_list[start] = skb; +@@ -780,8 +782,7 @@ static netdev_tx_t be_xmit(struct sk_buf + + be_txq_notify(adapter, txq->id, wrb_cnt); + +- be_tx_stats_update(adapter, wrb_cnt, copied, +- skb_shinfo(skb)->gso_segs, stopped); ++ be_tx_stats_update(adapter, wrb_cnt, copied, gso_segs, stopped); + } else { + txq->head = start; + dev_kfree_skb_any(skb); diff --git a/queue-3.0/bonding-fix-corrupted-queue_mapping.patch b/queue-3.0/bonding-fix-corrupted-queue_mapping.patch new file mode 100644 index 00000000000..49dba2e0ebc --- /dev/null +++ b/queue-3.0/bonding-fix-corrupted-queue_mapping.patch @@ -0,0 +1,113 @@ +From 572d9c7b6e91b84a2a122a8d30e47b3e834548ce Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Tue, 12 Jun 2012 06:03:51 +0000 +Subject: bonding: Fix corrupted queue_mapping + + +From: Eric Dumazet + +[ Upstream commit 5ee31c6898ea5537fcea160999d60dc63bc0c305 ] + +In the transmit path of the bonding driver, skb->cb is used to +stash the skb->queue_mapping so that the bonding device can set its +own queue mapping. This value becomes corrupted since the skb->cb is +also used in __dev_xmit_skb. + +When transmitting through bonding driver, bond_select_queue is +called from dev_queue_xmit. In bond_select_queue the original +skb->queue_mapping is copied into skb->cb (via bond_queue_mapping) +and skb->queue_mapping is overwritten with the bond driver queue. + +Subsequently in dev_queue_xmit, __dev_xmit_skb is called which writes +the packet length into skb->cb, thereby overwriting the stashed +queue mappping. In bond_dev_queue_xmit (called from hard_start_xmit), +the queue mapping for the skb is set to the stashed value which is now +the skb length and hence is an invalid queue for the slave device. + +If we want to save skb->queue_mapping into skb->cb[], best place is to +add a field in struct qdisc_skb_cb, to make sure it wont conflict with +other layers (eg : Qdiscc, Infiniband...) + +This patchs also makes sure (struct qdisc_skb_cb)->data is aligned on 8 +bytes : + +netem qdisc for example assumes it can store an u64 in it, without +misalignment penalty. + +Note : we only have 20 bytes left in (struct qdisc_skb_cb)->data[]. +The largest user is CHOKe and it fills it. + +Based on a previous patch from Tom Herbert. + +Signed-off-by: Eric Dumazet +Reported-by: Tom Herbert +Cc: John Fastabend +Cc: Roland Dreier +Acked-by: Neil Horman +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/bonding/bond_main.c | 9 +++++---- + include/net/sch_generic.h | 7 +++++-- + 2 files changed, 10 insertions(+), 6 deletions(-) + +--- a/drivers/net/bonding/bond_main.c ++++ b/drivers/net/bonding/bond_main.c +@@ -77,6 +77,7 @@ + #include + #include + #include ++#include + #include "bonding.h" + #include "bond_3ad.h" + #include "bond_alb.h" +@@ -388,8 +389,6 @@ struct vlan_entry *bond_next_vlan(struct + return next; + } + +-#define bond_queue_mapping(skb) (*(u16 *)((skb)->cb)) +- + /** + * bond_dev_queue_xmit - Prepare skb for xmit. + * +@@ -403,7 +402,9 @@ int bond_dev_queue_xmit(struct bonding * + skb->dev = slave_dev; + skb->priority = 1; + +- skb->queue_mapping = bond_queue_mapping(skb); ++ BUILD_BUG_ON(sizeof(skb->queue_mapping) != ++ sizeof(qdisc_skb_cb(skb)->bond_queue_mapping)); ++ skb->queue_mapping = qdisc_skb_cb(skb)->bond_queue_mapping; + + if (unlikely(netpoll_tx_running(slave_dev))) + bond_netpoll_send_skb(bond_get_slave_by_dev(bond, slave_dev), skb); +@@ -4240,7 +4241,7 @@ static u16 bond_select_queue(struct net_ + /* + * Save the original txq to restore before passing to the driver + */ +- bond_queue_mapping(skb) = skb->queue_mapping; ++ qdisc_skb_cb(skb)->bond_queue_mapping = skb->queue_mapping; + + if (unlikely(txq >= dev->real_num_tx_queues)) { + do { +--- a/include/net/sch_generic.h ++++ b/include/net/sch_generic.h +@@ -219,13 +219,16 @@ struct tcf_proto { + + struct qdisc_skb_cb { + unsigned int pkt_len; +- unsigned char data[24]; ++ u16 bond_queue_mapping; ++ u16 _pad; ++ unsigned char data[20]; + }; + + static inline void qdisc_cb_private_validate(const struct sk_buff *skb, int sz) + { + struct qdisc_skb_cb *qcb; +- BUILD_BUG_ON(sizeof(skb->cb) < sizeof(unsigned int) + sz); ++ ++ BUILD_BUG_ON(sizeof(skb->cb) < offsetof(struct qdisc_skb_cb, data) + sz); + BUILD_BUG_ON(sizeof(qcb->data) < sz); + } + diff --git a/queue-3.0/bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch b/queue-3.0/bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch new file mode 100644 index 00000000000..f6c20804e57 --- /dev/null +++ b/queue-3.0/bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch @@ -0,0 +1,55 @@ +From a53a0c1ea8bf9cecf770af137b289fd2cecdb785 Mon Sep 17 00:00:00 2001 +From: stephen hemminger +Date: Tue, 26 Jun 2012 05:48:45 +0000 +Subject: bridge: Assign rtnl_link_ops to bridge devices created via ioctl (v2) + + +From: stephen hemminger + +[ Upstream commit 149ddd83a92b02c658d6c61f3276eb6500d585e8 ] + +This ensures that bridges created with brctl(8) or ioctl(2) directly +also carry IFLA_LINKINFO when dumped over netlink. This also allows +to create a bridge with ioctl(2) and delete it with RTM_DELLINK. + +Signed-off-by: Thomas Graf +Signed-off-by: Stephen Hemminger +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/bridge/br_if.c | 1 + + net/bridge/br_netlink.c | 2 +- + net/bridge/br_private.h | 1 + + 3 files changed, 3 insertions(+), 1 deletion(-) + +--- a/net/bridge/br_if.c ++++ b/net/bridge/br_if.c +@@ -241,6 +241,7 @@ int br_add_bridge(struct net *net, const + return -ENOMEM; + + dev_net_set(dev, net); ++ dev->rtnl_link_ops = &br_link_ops; + + res = register_netdev(dev); + if (res) +--- a/net/bridge/br_netlink.c ++++ b/net/bridge/br_netlink.c +@@ -203,7 +203,7 @@ static int br_validate(struct nlattr *tb + return 0; + } + +-static struct rtnl_link_ops br_link_ops __read_mostly = { ++struct rtnl_link_ops br_link_ops __read_mostly = { + .kind = "bridge", + .priv_size = sizeof(struct net_bridge), + .setup = br_dev_setup, +--- a/net/bridge/br_private.h ++++ b/net/bridge/br_private.h +@@ -529,6 +529,7 @@ extern int (*br_fdb_test_addr_hook)(stru + #endif + + /* br_netlink.c */ ++extern struct rtnl_link_ops br_link_ops; + extern int br_netlink_init(void); + extern void br_netlink_fini(void); + extern void br_ifinfo_notify(int event, struct net_bridge_port *port); diff --git a/queue-3.0/cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch b/queue-3.0/cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch new file mode 100644 index 00000000000..41486f7363b --- /dev/null +++ b/queue-3.0/cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch @@ -0,0 +1,77 @@ +From 8021525230b097019b34cb6a6b29a8944122e09d Mon Sep 17 00:00:00 2001 +From: Paul Moore +Date: Fri, 1 Jun 2012 05:54:56 +0000 +Subject: cipso: handle CIPSO options correctly when NetLabel is disabled + + +From: Paul Moore + +[ Upstream commit 20e2a86485967c385d7c7befc1646e4d1d39362e ] + +When NetLabel is not enabled, e.g. CONFIG_NETLABEL=n, and the system +receives a CIPSO tagged packet it is dropped (cipso_v4_validate() +returns non-zero). In most cases this is the correct and desired +behavior, however, in the case where we are simply forwarding the +traffic, e.g. acting as a network bridge, this becomes a problem. + +This patch fixes the forwarding problem by providing the basic CIPSO +validation code directly in ip_options_compile() without the need for +the NetLabel or CIPSO code. The new validation code can not perform +any of the CIPSO option label/value verification that +cipso_v4_validate() does, but it can verify the basic CIPSO option +format. + +The behavior when NetLabel is enabled is unchanged. + +Signed-off-by: Paul Moore +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/net/cipso_ipv4.h | 29 ++++++++++++++++++++++++++++- + 1 file changed, 28 insertions(+), 1 deletion(-) + +--- a/include/net/cipso_ipv4.h ++++ b/include/net/cipso_ipv4.h +@@ -42,6 +42,7 @@ + #include + #include + #include ++#include + + /* known doi values */ + #define CIPSO_V4_DOI_UNKNOWN 0x00000000 +@@ -285,7 +286,33 @@ static inline int cipso_v4_skbuff_getatt + static inline int cipso_v4_validate(const struct sk_buff *skb, + unsigned char **option) + { +- return -ENOSYS; ++ unsigned char *opt = *option; ++ unsigned char err_offset = 0; ++ u8 opt_len = opt[1]; ++ u8 opt_iter; ++ ++ if (opt_len < 8) { ++ err_offset = 1; ++ goto out; ++ } ++ ++ if (get_unaligned_be32(&opt[2]) == 0) { ++ err_offset = 2; ++ goto out; ++ } ++ ++ for (opt_iter = 6; opt_iter < opt_len;) { ++ if (opt[opt_iter + 1] > (opt_len - opt_iter)) { ++ err_offset = opt_iter + 1; ++ goto out; ++ } ++ opt_iter += opt[opt_iter + 1]; ++ } ++ ++out: ++ *option = opt + err_offset; ++ return err_offset; ++ + } + #endif /* CONFIG_NETLABEL */ + diff --git a/queue-3.0/dummy-fix-rcu_sched-self-detected-stalls.patch b/queue-3.0/dummy-fix-rcu_sched-self-detected-stalls.patch new file mode 100644 index 00000000000..89088a3b76b --- /dev/null +++ b/queue-3.0/dummy-fix-rcu_sched-self-detected-stalls.patch @@ -0,0 +1,39 @@ +From b2bb91bb1007a5923544fe0983180b7b0b124475 Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Sun, 10 Jun 2012 21:11:57 +0000 +Subject: dummy: fix rcu_sched self-detected stalls + + +From: Eric Dumazet + +[ Upstream commit 16b0dc29c1af9df341428f4c49ada4f626258082 ] + +Trying to "modprobe dummy numdummies=30000" triggers : + +INFO: rcu_sched self-detected stall on CPU { 8} (t=60000 jiffies) + +After this splat, RTNL is locked and reboot is needed. + +We must call cond_resched() to avoid this, even holding RTNL. + +Signed-off-by: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/dummy.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/net/dummy.c ++++ b/drivers/net/dummy.c +@@ -186,8 +186,10 @@ static int __init dummy_init_module(void + rtnl_lock(); + err = __rtnl_link_register(&dummy_link_ops); + +- for (i = 0; i < numdummies && !err; i++) ++ for (i = 0; i < numdummies && !err; i++) { + err = dummy_init_one(); ++ cond_resched(); ++ } + if (err < 0) + __rtnl_link_unregister(&dummy_link_ops); + rtnl_unlock(); diff --git a/queue-3.0/ethtool-allow-ethtool_gsset_info-for-users.patch b/queue-3.0/ethtool-allow-ethtool_gsset_info-for-users.patch new file mode 100644 index 00000000000..f7188ca9c5a --- /dev/null +++ b/queue-3.0/ethtool-allow-ethtool_gsset_info-for-users.patch @@ -0,0 +1,31 @@ +From ab9c35abcc470fd1fe4f55723eeb04808c2a3738 Mon Sep 17 00:00:00 2001 +From: Michał Mirosław +Date: Sun, 22 Jan 2012 00:20:40 +0000 +Subject: ethtool: allow ETHTOOL_GSSET_INFO for users + + +From: =?UTF-8?q?Micha=C5=82=20Miros=C5=82aw?= + +[ Upstream commit f80400a26a2e8bff541de12834a1134358bb6642 ] + +Allow ETHTOOL_GSSET_INFO ethtool ioctl() for unprivileged users. +ETHTOOL_GSTRINGS is already allowed, but is unusable without this one. + +Signed-off-by: Micha©© Miros©©aw +Acked-by: Ben Hutchings +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/ethtool.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/net/core/ethtool.c ++++ b/net/core/ethtool.c +@@ -1964,6 +1964,7 @@ int dev_ethtool(struct net *net, struct + case ETHTOOL_GRXCSUM: + case ETHTOOL_GTXCSUM: + case ETHTOOL_GSG: ++ case ETHTOOL_GSSET_INFO: + case ETHTOOL_GSTRINGS: + case ETHTOOL_GTSO: + case ETHTOOL_GPERMADDR: diff --git a/queue-3.0/ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch b/queue-3.0/ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch new file mode 100644 index 00000000000..4eeabe7de5d --- /dev/null +++ b/queue-3.0/ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch @@ -0,0 +1,123 @@ +From dc9e3e535fb323672e4f1604cdfa968fb40bea99 Mon Sep 17 00:00:00 2001 +From: Thomas Graf +Date: Mon, 18 Jun 2012 12:08:33 +0000 +Subject: ipv6: Move ipv6 proc file registration to end of init order + + +From: Thomas Graf + +[ Upstream commit d189634ecab947c10f6f832258b103d0bbfe73cc ] + +/proc/net/ipv6_route reflects the contents of fib_table_hash. The proc +handler is installed in ip6_route_net_init() whereas fib_table_hash is +allocated in fib6_net_init() _after_ the proc handler has been installed. + +This opens up a short time frame to access fib_table_hash with its pants +down. + +Move the registration of the proc files to a later point in the init +order to avoid the race. + +Tested :-) + +Signed-off-by: Thomas Graf +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/route.c | 41 +++++++++++++++++++++++++++++++---------- + 1 file changed, 31 insertions(+), 10 deletions(-) + +--- a/net/ipv6/route.c ++++ b/net/ipv6/route.c +@@ -2846,10 +2846,6 @@ static int __net_init ip6_route_net_init + net->ipv6.sysctl.ip6_rt_mtu_expires = 10*60*HZ; + net->ipv6.sysctl.ip6_rt_min_advmss = IPV6_MIN_MTU - 20 - 40; + +-#ifdef CONFIG_PROC_FS +- proc_net_fops_create(net, "ipv6_route", 0, &ipv6_route_proc_fops); +- proc_net_fops_create(net, "rt6_stats", S_IRUGO, &rt6_stats_seq_fops); +-#endif + net->ipv6.ip6_rt_gc_expire = 30*HZ; + + ret = 0; +@@ -2870,10 +2866,6 @@ out_ip6_dst_ops: + + static void __net_exit ip6_route_net_exit(struct net *net) + { +-#ifdef CONFIG_PROC_FS +- proc_net_remove(net, "ipv6_route"); +- proc_net_remove(net, "rt6_stats"); +-#endif + kfree(net->ipv6.ip6_null_entry); + #ifdef CONFIG_IPV6_MULTIPLE_TABLES + kfree(net->ipv6.ip6_prohibit_entry); +@@ -2882,11 +2874,33 @@ static void __net_exit ip6_route_net_exi + dst_entries_destroy(&net->ipv6.ip6_dst_ops); + } + ++static int __net_init ip6_route_net_init_late(struct net *net) ++{ ++#ifdef CONFIG_PROC_FS ++ proc_net_fops_create(net, "ipv6_route", 0, &ipv6_route_proc_fops); ++ proc_net_fops_create(net, "rt6_stats", S_IRUGO, &rt6_stats_seq_fops); ++#endif ++ return 0; ++} ++ ++static void __net_exit ip6_route_net_exit_late(struct net *net) ++{ ++#ifdef CONFIG_PROC_FS ++ proc_net_remove(net, "ipv6_route"); ++ proc_net_remove(net, "rt6_stats"); ++#endif ++} ++ + static struct pernet_operations ip6_route_net_ops = { + .init = ip6_route_net_init, + .exit = ip6_route_net_exit, + }; + ++static struct pernet_operations ip6_route_net_late_ops = { ++ .init = ip6_route_net_init_late, ++ .exit = ip6_route_net_exit_late, ++}; ++ + static struct notifier_block ip6_route_dev_notifier = { + .notifier_call = ip6_route_dev_notify, + .priority = 0, +@@ -2936,19 +2950,25 @@ int __init ip6_route_init(void) + if (ret) + goto xfrm6_init; + ++ ret = register_pernet_subsys(&ip6_route_net_late_ops); ++ if (ret) ++ goto fib6_rules_init; ++ + ret = -ENOBUFS; + if (__rtnl_register(PF_INET6, RTM_NEWROUTE, inet6_rtm_newroute, NULL) || + __rtnl_register(PF_INET6, RTM_DELROUTE, inet6_rtm_delroute, NULL) || + __rtnl_register(PF_INET6, RTM_GETROUTE, inet6_rtm_getroute, NULL)) +- goto fib6_rules_init; ++ goto out_register_late_subsys; + + ret = register_netdevice_notifier(&ip6_route_dev_notifier); + if (ret) +- goto fib6_rules_init; ++ goto out_register_late_subsys; + + out: + return ret; + ++out_register_late_subsys: ++ unregister_pernet_subsys(&ip6_route_net_late_ops); + fib6_rules_init: + fib6_rules_cleanup(); + xfrm6_init: +@@ -2967,6 +2987,7 @@ out_kmem_cache: + void ip6_route_cleanup(void) + { + unregister_netdevice_notifier(&ip6_route_dev_notifier); ++ unregister_pernet_subsys(&ip6_route_net_late_ops); + fib6_rules_cleanup(); + xfrm6_fini(); + fib6_gc_cleanup(); diff --git a/queue-3.0/net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch b/queue-3.0/net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch new file mode 100644 index 00000000000..c8fae3656a2 --- /dev/null +++ b/queue-3.0/net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch @@ -0,0 +1,41 @@ +From b389c83bcb28fc61400c33a91a8571f5c556bf29 Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Thu, 7 Jun 2012 00:07:20 +0000 +Subject: net: l2tp_eth: fix kernel panic on rmmod l2tp_eth + + +From: Eric Dumazet + +[ Upstream commit a06998b88b1651c5f71c0e35f528bf2057188ead ] + +We must prevent module unloading if some devices are still attached to +l2tp_eth driver. + +Signed-off-by: Eric Dumazet +Reported-by: Denys Fedoryshchenko +Tested-by: Denys Fedoryshchenko +Cc: James Chapman +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/l2tp/l2tp_eth.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/net/l2tp/l2tp_eth.c ++++ b/net/l2tp/l2tp_eth.c +@@ -167,6 +167,7 @@ static void l2tp_eth_delete(struct l2tp_ + if (dev) { + unregister_netdev(dev); + spriv->dev = NULL; ++ module_put(THIS_MODULE); + } + } + } +@@ -254,6 +255,7 @@ static int l2tp_eth_create(struct net *n + if (rc < 0) + goto out_del_dev; + ++ __module_get(THIS_MODULE); + /* Must be done after register_netdev() */ + strlcpy(session->ifname, dev->name, IFNAMSIZ); + diff --git a/queue-3.0/net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch b/queue-3.0/net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch new file mode 100644 index 00000000000..360b8dbde4f --- /dev/null +++ b/queue-3.0/net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch @@ -0,0 +1,50 @@ +From fd2a6fa5a30dc467188e6a847fc1abf820f06e80 Mon Sep 17 00:00:00 2001 +From: Jason Wang +Date: Wed, 30 May 2012 21:18:10 +0000 +Subject: net: sock: validate data_len before allocating skb in sock_alloc_send_pskb() + + +From: Jason Wang + +[ Upstream commit cc9b17ad29ecaa20bfe426a8d4dbfb94b13ff1cc ] + +We need to validate the number of pages consumed by data_len, otherwise frags +array could be overflowed by userspace. So this patch validate data_len and +return -EMSGSIZE when data_len may occupies more frags than MAX_SKB_FRAGS. + +Signed-off-by: Jason Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/sock.c | 7 +++++-- + 1 file changed, 5 insertions(+), 2 deletions(-) + +--- a/net/core/sock.c ++++ b/net/core/sock.c +@@ -1501,6 +1501,11 @@ struct sk_buff *sock_alloc_send_pskb(str + gfp_t gfp_mask; + long timeo; + int err; ++ int npages = (data_len + (PAGE_SIZE - 1)) >> PAGE_SHIFT; ++ ++ err = -EMSGSIZE; ++ if (npages > MAX_SKB_FRAGS) ++ goto failure; + + gfp_mask = sk->sk_allocation; + if (gfp_mask & __GFP_WAIT) +@@ -1519,14 +1524,12 @@ struct sk_buff *sock_alloc_send_pskb(str + if (atomic_read(&sk->sk_wmem_alloc) < sk->sk_sndbuf) { + skb = alloc_skb(header_len, gfp_mask); + if (skb) { +- int npages; + int i; + + /* No pages, we're done... */ + if (!data_len) + break; + +- npages = (data_len + (PAGE_SIZE - 1)) >> PAGE_SHIFT; + skb->truesize += data_len; + skb_shinfo(skb)->nr_frags = npages; + for (i = 0; i < npages; i++) { diff --git a/queue-3.0/netpoll-fix-netpoll_send_udp-bugs.patch b/queue-3.0/netpoll-fix-netpoll_send_udp-bugs.patch new file mode 100644 index 00000000000..882024020fd --- /dev/null +++ b/queue-3.0/netpoll-fix-netpoll_send_udp-bugs.patch @@ -0,0 +1,75 @@ +From 1a961a2cf8be20962318f196a40d75b6dad40cc3 Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Tue, 12 Jun 2012 19:30:21 +0000 +Subject: netpoll: fix netpoll_send_udp() bugs + + +From: Eric Dumazet + +[ Upstream commit 954fba0274058d27c7c07b5ea07c41b3b7477894 ] + +Bogdan Hamciuc diagnosed and fixed following bug in netpoll_send_udp() : + +"skb->len += len;" instead of "skb_put(skb, len);" + +Meaning that _if_ a network driver needs to call skb_realloc_headroom(), +only packet headers would be copied, leaving garbage in the payload. + +However the skb_realloc_headroom() must be avoided as much as possible +since it requires memory and netpoll tries hard to work even if memory +is exhausted (using a pool of preallocated skbs) + +It appears netpoll_send_udp() reserved 16 bytes for the ethernet header, +which happens to work for typicall drivers but not all. + +Right thing is to use LL_RESERVED_SPACE(dev) +(And also add dev->needed_tailroom of tailroom) + +This patch combines both fixes. + +Many thanks to Bogdan for raising this issue. + +Reported-by: Bogdan Hamciuc +Signed-off-by: Eric Dumazet +Tested-by: Bogdan Hamciuc +Cc: Herbert Xu +Cc: Neil Horman +Reviewed-by: Neil Horman +Reviewed-by: Cong Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/netpoll.c | 11 ++++++----- + 1 file changed, 6 insertions(+), 5 deletions(-) + +--- a/net/core/netpoll.c ++++ b/net/core/netpoll.c +@@ -357,22 +357,23 @@ EXPORT_SYMBOL(netpoll_send_skb_on_dev); + + void netpoll_send_udp(struct netpoll *np, const char *msg, int len) + { +- int total_len, eth_len, ip_len, udp_len; ++ int total_len, ip_len, udp_len; + struct sk_buff *skb; + struct udphdr *udph; + struct iphdr *iph; + struct ethhdr *eth; + + udp_len = len + sizeof(*udph); +- ip_len = eth_len = udp_len + sizeof(*iph); +- total_len = eth_len + ETH_HLEN + NET_IP_ALIGN; ++ ip_len = udp_len + sizeof(*iph); ++ total_len = ip_len + LL_RESERVED_SPACE(np->dev); + +- skb = find_skb(np, total_len, total_len - len); ++ skb = find_skb(np, total_len + np->dev->needed_tailroom, ++ total_len - len); + if (!skb) + return; + + skb_copy_to_linear_data(skb, msg, len); +- skb->len += len; ++ skb_put(skb, len); + + skb_push(skb, sizeof(*udph)); + skb_reset_transport_header(skb); diff --git a/queue-3.0/series b/queue-3.0/series index 5e433aa1b85..245f658caa2 100644 --- a/queue-3.0/series +++ b/queue-3.0/series @@ -2,3 +2,14 @@ alsa-hda-add-realtek-alc280-codec-support.patch powerpc-xmon-use-cpumask-iterator-to-avoid-warning.patch media-smsusb-add-autodetection-support-for-usb-id-2040-f5a0.patch arm-fix-rcu-stalls-on-smp-platforms.patch +net-sock-validate-data_len-before-allocating-skb-in-sock_alloc_send_pskb.patch +cipso-handle-cipso-options-correctly-when-netlabel-is-disabled.patch +net-l2tp_eth-fix-kernel-panic-on-rmmod-l2tp_eth.patch +dummy-fix-rcu_sched-self-detected-stalls.patch +ethtool-allow-ethtool_gsset_info-for-users.patch +bridge-assign-rtnl_link_ops-to-bridge-devices-created-via-ioctl-v2.patch +bonding-fix-corrupted-queue_mapping.patch +ipv6-move-ipv6-proc-file-registration-to-end-of-init-order.patch +sky2-fix-checksum-bit-management-on-some-chips.patch +be2net-fix-a-race-in-be_xmit.patch +netpoll-fix-netpoll_send_udp-bugs.patch diff --git a/queue-3.0/sky2-fix-checksum-bit-management-on-some-chips.patch b/queue-3.0/sky2-fix-checksum-bit-management-on-some-chips.patch new file mode 100644 index 00000000000..1f66361a874 --- /dev/null +++ b/queue-3.0/sky2-fix-checksum-bit-management-on-some-chips.patch @@ -0,0 +1,45 @@ +From 48083d72f1f1293f8f9bec73321537377aaebc1b Mon Sep 17 00:00:00 2001 +From: stephen hemminger +Date: Wed, 6 Jun 2012 10:01:30 +0000 +Subject: sky2: fix checksum bit management on some chips + + +From: stephen hemminger + +[ Upstream commit 5ff0feac88ced864f44adb145142269196fa79d9 ] + +The newer flavors of Yukon II use a different method for receive +checksum offload. This is indicated in the driver by the SKY2_HW_NEW_LE +flag. On these newer chips, the BMU_ENA_RX_CHKSUM should not be set. + +The driver would get incorrectly toggle the bit, enabling the old +checksum logic on these chips and cause a BUG_ON() assertion. If +receive checksum was toggled via ethtool. + +Reported-by: Kirill Smelkov +Signed-off-by: Stephen Hemminger +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/sky2.c | 10 ++++++---- + 1 file changed, 6 insertions(+), 4 deletions(-) + +--- a/drivers/net/sky2.c ++++ b/drivers/net/sky2.c +@@ -4206,10 +4206,12 @@ static int sky2_set_features(struct net_ + struct sky2_port *sky2 = netdev_priv(dev); + u32 changed = dev->features ^ features; + +- if (changed & NETIF_F_RXCSUM) { +- u32 on = features & NETIF_F_RXCSUM; +- sky2_write32(sky2->hw, Q_ADDR(rxqaddr[sky2->port], Q_CSR), +- on ? BMU_ENA_RX_CHKSUM : BMU_DIS_RX_CHKSUM); ++ if ((changed & NETIF_F_RXCSUM) && ++ !(sky2->hw->flags & SKY2_HW_NEW_LE)) { ++ sky2_write32(sky2->hw, ++ Q_ADDR(rxqaddr[sky2->port], Q_CSR), ++ (features & NETIF_F_RXCSUM) ++ ? BMU_ENA_RX_CHKSUM : BMU_DIS_RX_CHKSUM); + } + + if (changed & NETIF_F_RXHASH) -- 2.47.3