From: Greg Kroah-Hartman Date: Thu, 29 May 2014 04:13:30 +0000 (-0700) Subject: 3.14-stable patches X-Git-Tag: v3.10.41~1 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=68f80dc660aa80f499258331aa7233a93b201267;p=thirdparty%2Fkernel%2Fstable-queue.git 3.14-stable patches added patches: batman-adv-always-run-purge_orig_neighbors.patch batman-adv-fix-indirect-hard_iface-null-dereference.patch batman-adv-fix-local-tt-check-for-outgoing-arp.patch batman-adv-fix-neigh_ifinfo-imbalance.patch batman-adv-fix-neigh-reference-imbalance.patch batman-adv-fix-reference-counting-imbalance-while.patch batman-adv-fix-removing-neigh_ifinfo.patch batman-adv-increase-orig-refcount-when-storing-ref-in.patch bonding-fix-out-of-range-parameters-for.patch bonding-remove-debug_fs-files-when-module-init-fails.patch bridge-fix-double-free-and-memory-leak-around-br_allowed_ingress.patch bridge-handle-ifla_address-correctly-when-creating.patch filter-prevent-nla-extensions-to-peek-beyond-the-end-of-the-message.patch gre-don-t-allow-to-add-the-same-tunnel-twice.patch ip6_gre-don-t-allow-to-remove-the-fb_tunnel_dev.patch ip6_tunnel-fix-potential-null-pointer-dereference.patch ip_tunnel-initialize-the-fallback-device-properly.patch ip_tunnel-set-network-header-properly-for.patch ipv4-fib_semantics-increment-fib_info_cnt-after.patch ipv4-initialise-the-itag-variable-in-__mkroute_input.patch ipv4-ip_tunnels-disable-cache-for-nbma-gre-tunnels.patch ipv4-return-valid-rta_iif-on-ip-route-get.patch ipv6-fib-fix-fib-dump-restart.patch ipv6-fix-calculation-of-option-len-in-ip6_append_data.patch ipv6-gro-fix-checksum_complete-support.patch ipv6-limit-mtu-to-65575-bytes.patch l2tp-take-pmtu-from-tunnel-udp-socket.patch mactap-fix-checksum-errors-for-non-gso-packets-in.patch macvlan-don-t-propagate-iff_allmulti-changes-on-down.patch macvlan-fix-lockdep-warnings-with-stacked-macvlan.patch neigh-set-nud_state-to-nud_incomplete-when-probing.patch net-allow-for-more-then-a-single-subclass-for.patch net-avoid-dependency-of-net_get_random_once-on-nop.patch net-cdc_mbim-handle-unaccelerated-vlan-tagged-frames.patch net-cdc_mbim-__vlan_find_dev_deep-need-rcu_read_lock.patch net-cdc_ncm-fix-buffer-overflow.patch net-core-don-t-account-for-udp-header-size-when-computing-seglen.patch net-filter-s390-fix-jit-address-randomization.patch net-filter-x86-fix-jit-address-randomization.patch net-find-the-nesting-level-of-a-given-device-by-type.patch net-fix-ns_capable-check-in-sock_diag_put_filterinfo.patch net-gro-make-sure-skb-cb-initial-content-has-not.patch net-gro-reset-skb-truesize-in-napi_reuse_skb.patch net-ipv4-current-group_info-should-be-put-after-using.patch net-ipv4-ip_forward-fix-inverted-local_df-test.patch net-ipv6-send-pkttoobig-immediately-if-orig-frag.patch net-mlx4_core-don-t-issue-pcie-speed-width-checks-for.patch net-phy-don-t-call-phy_resume-if-phy_init_hw-failed.patch net-qmi_wwan-add-alcatel-l800ma.patch net-qmi_wwan-add-a-number-of-cmotech-devices.patch net-qmi_wwan-add-a-number-of-dell-devices.patch net-qmi_wwan-add-olivetti-olicard-500.patch net-qmi_wwan-add-sierra-wireless-em7355.patch net-qmi_wwan-add-sierra-wireless-mc7305-mc7355.patch net-qmi_wwan-add-sierra-wireless-mc73xx.patch net_sched-fix-an-oops-in-tcindex-filter.patch net-sched-lock-imbalance-in-hhf-qdisc.patch net-sctp-cache-auth_enable-per-endpoint.patch net-sctp-don-t-transition-to-pf-state-when-transport.patch net-sctp-test-if-association-is-dead-in-sctp_wake_up_waiters.patch net-sctp-wake-up-all-assocs-if-sndbuf-policy-is-per-socket.patch net-start-with-correct-mac_len-in-skb_network_protocol.patch revert-macvlan-fix-checksums-error-when-we-are-in.patch revert-net-sctp-fix-a_rwnd-rwnd-management-to-reflect-real-state-of-the-receiver-s-buffer.patch rtnetlink-only-supply-ifla_vf_ports-information-when.patch rtnetlink-wait-for-unregistering-devices-in.patch rtnetlink-warn-when-interface-s-information-won-t-fit.patch sctp-reset-flowi4_oif-parameter-on-route-lookup.patch sfc-fix-calling-of-free_irq-with-already-free-vector.patch slip-fix-spinlock-variant.patch tcp_cubic-fix-the-range-of-delayed_ack.patch tg3-update-rx_jumbo_pending-ring-param-only-when.patch vlan-fix-lockdep-warning-when-vlan-dev-handle-notification.patch vlan-fix-lockdep-warning-with-stacked-vlan-devices.patch vsock-make-transport-the-proto-owner.patch vti-don-t-allow-to-add-the-same-tunnel-twice.patch --- diff --git a/queue-3.14/batman-adv-always-run-purge_orig_neighbors.patch b/queue-3.14/batman-adv-always-run-purge_orig_neighbors.patch new file mode 100644 index 00000000000..1c6387bcc61 --- /dev/null +++ b/queue-3.14/batman-adv-always-run-purge_orig_neighbors.patch @@ -0,0 +1,50 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Simon Wunderlich +Date: Wed, 26 Mar 2014 15:46:23 +0100 +Subject: batman-adv: always run purge_orig_neighbors + +From: Simon Wunderlich + +[ Upstream commit 7b955a9fc164487d7c51acb9787f6d1b01b35ef6 ] + +The current code will not execute batadv_purge_orig_neighbors() when an +orig_ifinfo has already been purged. However we need to run it in any +case. Fix that. + +This is a regression introduced by +7351a4822d42827ba0110677c0cbad88a3d52585 +("batman-adv: split out router from orig_node") + +Signed-off-by: Simon Wunderlich +Signed-off-by: Marek Lindner +Signed-off-by: Antonio Quartulli +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/originator.c | 8 ++++---- + 1 file changed, 4 insertions(+), 4 deletions(-) + +--- a/net/batman-adv/originator.c ++++ b/net/batman-adv/originator.c +@@ -857,7 +857,7 @@ static bool batadv_purge_orig_node(struc + { + struct batadv_neigh_node *best_neigh_node; + struct batadv_hard_iface *hard_iface; +- bool changed; ++ bool changed_ifinfo, changed_neigh; + + if (batadv_has_timed_out(orig_node->last_seen, + 2 * BATADV_PURGE_TIMEOUT)) { +@@ -867,10 +867,10 @@ static bool batadv_purge_orig_node(struc + jiffies_to_msecs(orig_node->last_seen)); + return true; + } +- changed = batadv_purge_orig_ifinfo(bat_priv, orig_node); +- changed = changed || batadv_purge_orig_neighbors(bat_priv, orig_node); ++ changed_ifinfo = batadv_purge_orig_ifinfo(bat_priv, orig_node); ++ changed_neigh = batadv_purge_orig_neighbors(bat_priv, orig_node); + +- if (!changed) ++ if (!changed_ifinfo && !changed_neigh) + return false; + + /* first for NULL ... */ diff --git a/queue-3.14/batman-adv-fix-indirect-hard_iface-null-dereference.patch b/queue-3.14/batman-adv-fix-indirect-hard_iface-null-dereference.patch new file mode 100644 index 00000000000..8f662254e89 --- /dev/null +++ b/queue-3.14/batman-adv-fix-indirect-hard_iface-null-dereference.patch @@ -0,0 +1,36 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Marek Lindner +Date: Thu, 24 Apr 2014 03:44:25 +0800 +Subject: batman-adv: fix indirect hard_iface NULL dereference + +From: Marek Lindner + +[ Upstream commit 16a4142363b11952d3aa76ac78004502c0c2fe6e ] + +If hard_iface is NULL and goto out is made batadv_hardif_free_ref() +doesn't check for NULL before dereferencing it to get to refcount. + +Introduced in cb1c92ec37fb70543d133a1fa7d9b54d6f8a1ecd +("batman-adv: add debugfs support to view multiif tables"). + +Reported-by: Sven Eckelmann +Signed-off-by: Marek Lindner +Acked-by: Antonio Quartulli +Signed-off-by: Antonio Quartulli +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/originator.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/net/batman-adv/originator.c ++++ b/net/batman-adv/originator.c +@@ -1074,7 +1074,8 @@ int batadv_orig_hardif_seq_print_text(st + bat_priv->bat_algo_ops->bat_orig_print(bat_priv, seq, hard_iface); + + out: +- batadv_hardif_free_ref(hard_iface); ++ if (hard_iface) ++ batadv_hardif_free_ref(hard_iface); + return 0; + } + diff --git a/queue-3.14/batman-adv-fix-local-tt-check-for-outgoing-arp.patch b/queue-3.14/batman-adv-fix-local-tt-check-for-outgoing-arp.patch new file mode 100644 index 00000000000..29a0b0f534a --- /dev/null +++ b/queue-3.14/batman-adv-fix-local-tt-check-for-outgoing-arp.patch @@ -0,0 +1,44 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Antonio Quartulli +Date: Sat, 29 Mar 2014 17:27:38 +0100 +Subject: batman-adv: fix local TT check for outgoing arp + requests in DAT + +From: Antonio Quartulli + +[ Upstream commit cc2f33860cea0e48ebec096130bd0f7c4bf6e0bc ] + +Change introduced by 88e48d7b3340ef07b108eb8a8b3813dd093cc7f7 +("batman-adv: make DAT drop ARP requests targeting local clients") +implements a check that prevents DAT from using the caching +mechanism when the client that is supposed to provide a reply +to an arp request is local. + +However change brought by be1db4f6615b5e6156c807ea8985171c215c2d57 +("batman-adv: make the Distributed ARP Table vlan aware") +has not converted the above check into its vlan aware version +thus making it useless when the local client is behind a vlan. + +Fix the behaviour by properly specifying the vlan when +checking for a client being local or not. + +Reported-by: Simon Wunderlich +Signed-off-by: Antonio Quartulli +Signed-off-by: Marek Lindner +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/distributed-arp-table.c | 3 +-- + 1 file changed, 1 insertion(+), 2 deletions(-) + +--- a/net/batman-adv/distributed-arp-table.c ++++ b/net/batman-adv/distributed-arp-table.c +@@ -940,8 +940,7 @@ bool batadv_dat_snoop_outgoing_arp_reque + * additional DAT answer may trigger kernel warnings about + * a packet coming from the wrong port. + */ +- if (batadv_is_my_client(bat_priv, dat_entry->mac_addr, +- BATADV_NO_FLAGS)) { ++ if (batadv_is_my_client(bat_priv, dat_entry->mac_addr, vid)) { + ret = true; + goto out; + } diff --git a/queue-3.14/batman-adv-fix-neigh-reference-imbalance.patch b/queue-3.14/batman-adv-fix-neigh-reference-imbalance.patch new file mode 100644 index 00000000000..2a62e37acf0 --- /dev/null +++ b/queue-3.14/batman-adv-fix-neigh-reference-imbalance.patch @@ -0,0 +1,48 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Simon Wunderlich +Date: Wed, 26 Mar 2014 15:46:22 +0100 +Subject: batman-adv: fix neigh reference imbalance + +From: Simon Wunderlich + +[ Upstream commit 000c8dff97311357535d64539e58990526e4de70 ] + +When an interface is removed from batman-adv, the orig_ifinfo of a +orig_node may be removed without releasing the router first. +This will prevent the reference for the neighbor pointed at by the +orig_ifinfo->router to be released, and this leak may result in +reference leaks for the interface used by this neighbor. Fix that. + +This is a regression introduced by +7351a4822d42827ba0110677c0cbad88a3d52585 +("batman-adv: split out router from orig_node"). + +Reported-by: Antonio Quartulli +Signed-off-by: Simon Wunderlich +Signed-off-by: Marek Lindner +Signed-off-by: Antonio Quartulli +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/originator.c | 5 +++++ + 1 file changed, 5 insertions(+) + +--- a/net/batman-adv/originator.c ++++ b/net/batman-adv/originator.c +@@ -500,12 +500,17 @@ batadv_neigh_node_get(const struct batad + static void batadv_orig_ifinfo_free_rcu(struct rcu_head *rcu) + { + struct batadv_orig_ifinfo *orig_ifinfo; ++ struct batadv_neigh_node *router; + + orig_ifinfo = container_of(rcu, struct batadv_orig_ifinfo, rcu); + + if (orig_ifinfo->if_outgoing != BATADV_IF_DEFAULT) + batadv_hardif_free_ref_now(orig_ifinfo->if_outgoing); + ++ /* this is the last reference to this object */ ++ router = rcu_dereference_protected(orig_ifinfo->router, true); ++ if (router) ++ batadv_neigh_node_free_ref_now(router); + kfree(orig_ifinfo); + } + diff --git a/queue-3.14/batman-adv-fix-neigh_ifinfo-imbalance.patch b/queue-3.14/batman-adv-fix-neigh_ifinfo-imbalance.patch new file mode 100644 index 00000000000..e1d2a36d173 --- /dev/null +++ b/queue-3.14/batman-adv-fix-neigh_ifinfo-imbalance.patch @@ -0,0 +1,36 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Simon Wunderlich +Date: Wed, 26 Mar 2014 15:46:21 +0100 +Subject: batman-adv: fix neigh_ifinfo imbalance + +From: Simon Wunderlich + +[ Upstream commit c1e517fbbcdb13f50662af4edc11c3251fe44f86 ] + +The neigh_ifinfo object must be freed if it has been used in +batadv_iv_ogm_process_per_outif(). + +This is a regression introduced by +89652331c00f43574515059ecbf262d26d885717 +("batman-adv: split tq information in neigh_node struct") + +Reported-by: Antonio Quartulli +Signed-off-by: Simon Wunderlich +Signed-off-by: Marek Lindner +Signed-off-by: Antonio Quartulli +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/bat_iv_ogm.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/net/batman-adv/bat_iv_ogm.c ++++ b/net/batman-adv/bat_iv_ogm.c +@@ -1545,6 +1545,8 @@ out_neigh: + if ((orig_neigh_node) && (!is_single_hop_neigh)) + batadv_orig_node_free_ref(orig_neigh_node); + out: ++ if (router_ifinfo) ++ batadv_neigh_ifinfo_free_ref(router_ifinfo); + if (router) + batadv_neigh_node_free_ref(router); + if (router_router) diff --git a/queue-3.14/batman-adv-fix-reference-counting-imbalance-while.patch b/queue-3.14/batman-adv-fix-reference-counting-imbalance-while.patch new file mode 100644 index 00000000000..8b7dde7662a --- /dev/null +++ b/queue-3.14/batman-adv-fix-reference-counting-imbalance-while.patch @@ -0,0 +1,65 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Antonio Quartulli +Date: Wed, 23 Apr 2014 14:05:16 +0200 +Subject: batman-adv: fix reference counting imbalance while + sending fragment +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Antonio Quartulli + +[ Upstream commit be181015a189cd141398b761ba4e79d33fe69949 ] + +In the new fragmentation code the batadv_frag_send_packet() +function obtains a reference to the primary_if, but it does +not release it upon return. + +This reference imbalance prevents the primary_if (and then +the related netdevice) to be properly released on shut down. + +Fix this by releasing the primary_if in batadv_frag_send_packet(). + +Introduced by ee75ed88879af88558818a5c6609d85f60ff0df4 +("batman-adv: Fragment and send skbs larger than mtu") + +Cc: Martin Hundebøll +Signed-off-by: Antonio Quartulli +Signed-off-by: Marek Lindner +Acked-by: Martin Hundebøll +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/fragmentation.c | 11 ++++++++--- + 1 file changed, 8 insertions(+), 3 deletions(-) + +--- a/net/batman-adv/fragmentation.c ++++ b/net/batman-adv/fragmentation.c +@@ -418,12 +418,13 @@ bool batadv_frag_send_packet(struct sk_b + struct batadv_neigh_node *neigh_node) + { + struct batadv_priv *bat_priv; +- struct batadv_hard_iface *primary_if; ++ struct batadv_hard_iface *primary_if = NULL; + struct batadv_frag_packet frag_header; + struct sk_buff *skb_fragment; + unsigned mtu = neigh_node->if_incoming->net_dev->mtu; + unsigned header_size = sizeof(frag_header); + unsigned max_fragment_size, max_packet_size; ++ bool ret = false; + + /* To avoid merge and refragmentation at next-hops we never send + * fragments larger than BATADV_FRAG_MAX_FRAG_SIZE +@@ -483,7 +484,11 @@ bool batadv_frag_send_packet(struct sk_b + skb->len + ETH_HLEN); + batadv_send_skb_packet(skb, neigh_node->if_incoming, neigh_node->addr); + +- return true; ++ ret = true; ++ + out_err: +- return false; ++ if (primary_if) ++ batadv_hardif_free_ref(primary_if); ++ ++ return ret; + } diff --git a/queue-3.14/batman-adv-fix-removing-neigh_ifinfo.patch b/queue-3.14/batman-adv-fix-removing-neigh_ifinfo.patch new file mode 100644 index 00000000000..b1f7833f3b4 --- /dev/null +++ b/queue-3.14/batman-adv-fix-removing-neigh_ifinfo.patch @@ -0,0 +1,89 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Simon Wunderlich +Date: Wed, 26 Mar 2014 15:46:24 +0100 +Subject: batman-adv: fix removing neigh_ifinfo + +From: Simon Wunderlich + +[ Upstream commit 709de13f0c532fe9c468c094aff069a725ed57fe ] + +When an interface is removed separately, all neighbors need to be +checked if they have a neigh_ifinfo structure for that particular +interface. If that is the case, remove that ifinfo so any references to +a hard interface can be freed. + +This is a regression introduced by +89652331c00f43574515059ecbf262d26d885717 +("batman-adv: split tq information in neigh_node struct") + +Reported-by: Antonio Quartulli +Signed-off-by: Simon Wunderlich +Signed-off-by: Marek Lindner +Signed-off-by: Antonio Quartulli +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/originator.c | 46 ++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 46 insertions(+) + +--- a/net/batman-adv/originator.c ++++ b/net/batman-adv/originator.c +@@ -702,6 +702,47 @@ free_orig_node: + } + + /** ++ * batadv_purge_neigh_ifinfo - purge obsolete ifinfo entries from neighbor ++ * @bat_priv: the bat priv with all the soft interface information ++ * @neigh: orig node which is to be checked ++ */ ++static void ++batadv_purge_neigh_ifinfo(struct batadv_priv *bat_priv, ++ struct batadv_neigh_node *neigh) ++{ ++ struct batadv_neigh_ifinfo *neigh_ifinfo; ++ struct batadv_hard_iface *if_outgoing; ++ struct hlist_node *node_tmp; ++ ++ spin_lock_bh(&neigh->ifinfo_lock); ++ ++ /* for all ifinfo objects for this neighinator */ ++ hlist_for_each_entry_safe(neigh_ifinfo, node_tmp, ++ &neigh->ifinfo_list, list) { ++ if_outgoing = neigh_ifinfo->if_outgoing; ++ ++ /* always keep the default interface */ ++ if (if_outgoing == BATADV_IF_DEFAULT) ++ continue; ++ ++ /* don't purge if the interface is not (going) down */ ++ if ((if_outgoing->if_status != BATADV_IF_INACTIVE) && ++ (if_outgoing->if_status != BATADV_IF_NOT_IN_USE) && ++ (if_outgoing->if_status != BATADV_IF_TO_BE_REMOVED)) ++ continue; ++ ++ batadv_dbg(BATADV_DBG_BATMAN, bat_priv, ++ "neighbor/ifinfo purge: neighbor %pM, iface: %s\n", ++ neigh->addr, if_outgoing->net_dev->name); ++ ++ hlist_del_rcu(&neigh_ifinfo->list); ++ batadv_neigh_ifinfo_free_ref(neigh_ifinfo); ++ } ++ ++ spin_unlock_bh(&neigh->ifinfo_lock); ++} ++ ++/** + * batadv_purge_orig_ifinfo - purge obsolete ifinfo entries from originator + * @bat_priv: the bat priv with all the soft interface information + * @orig_node: orig node which is to be checked +@@ -800,6 +841,11 @@ batadv_purge_orig_neighbors(struct batad + + hlist_del_rcu(&neigh_node->list); + batadv_neigh_node_free_ref(neigh_node); ++ } else { ++ /* only necessary if not the whole neighbor is to be ++ * deleted, but some interface has been removed. ++ */ ++ batadv_purge_neigh_ifinfo(bat_priv, neigh_node); + } + } + diff --git a/queue-3.14/batman-adv-increase-orig-refcount-when-storing-ref-in.patch b/queue-3.14/batman-adv-increase-orig-refcount-when-storing-ref-in.patch new file mode 100644 index 00000000000..386bb5938eb --- /dev/null +++ b/queue-3.14/batman-adv-increase-orig-refcount-when-storing-ref-in.patch @@ -0,0 +1,56 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Antonio Quartulli +Date: Fri, 2 May 2014 01:35:13 +0200 +Subject: batman-adv: increase orig refcount when storing ref in + gw_node + +From: Antonio Quartulli + +[ Upstream commit 377fe0f968b30a1a714fab53a908061914f30e26 ] + +A pointer to the orig_node representing a bat-gateway is +stored in the gw_node->orig_node member, but the refcount +for such orig_node is never increased. +This leads to memory faults when gw_node->orig_node is accessed +and the originator has already been freed. + +Fix this by increasing the refcount on gw_node creation +and decreasing it on gw_node free. + +Signed-off-by: Antonio Quartulli +Signed-off-by: Marek Lindner +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/gateway_client.c | 11 +++++++++-- + 1 file changed, 9 insertions(+), 2 deletions(-) + +--- a/net/batman-adv/gateway_client.c ++++ b/net/batman-adv/gateway_client.c +@@ -42,8 +42,10 @@ + + static void batadv_gw_node_free_ref(struct batadv_gw_node *gw_node) + { +- if (atomic_dec_and_test(&gw_node->refcount)) ++ if (atomic_dec_and_test(&gw_node->refcount)) { ++ batadv_orig_node_free_ref(gw_node->orig_node); + kfree_rcu(gw_node, rcu); ++ } + } + + static struct batadv_gw_node * +@@ -408,9 +410,14 @@ static void batadv_gw_node_add(struct ba + if (gateway->bandwidth_down == 0) + return; + ++ if (!atomic_inc_not_zero(&orig_node->refcount)) ++ return; ++ + gw_node = kzalloc(sizeof(*gw_node), GFP_ATOMIC); +- if (!gw_node) ++ if (!gw_node) { ++ batadv_orig_node_free_ref(orig_node); + return; ++ } + + INIT_HLIST_NODE(&gw_node->list); + gw_node->orig_node = orig_node; diff --git a/queue-3.14/bonding-fix-out-of-range-parameters-for.patch b/queue-3.14/bonding-fix-out-of-range-parameters-for.patch new file mode 100644 index 00000000000..767d9909e77 --- /dev/null +++ b/queue-3.14/bonding-fix-out-of-range-parameters-for.patch @@ -0,0 +1,36 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Nikolay Aleksandrov +Date: Thu, 15 May 2014 13:35:23 +0200 +Subject: bonding: fix out of range parameters for + bond_intmax_tbl + +From: Nikolay Aleksandrov + +[ Upstream commit 81c708068dfedece038e07d818ba68333d8d885d ] + +I've missed to add a NULL entry to the bond_intmax_tbl when I introduced +it with the conversion of arp_interval so add it now. + +CC: Jay Vosburgh +CC: Veaceslav Falico +CC: Andy Gospodarek + +Fixes: 7bdb04ed0dbf ("bonding: convert arp_interval to use the new option API") +Signed-off-by: Nikolay Aleksandrov +Acked-by: Veaceslav Falico +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/bonding/bond_options.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/bonding/bond_options.c ++++ b/drivers/net/bonding/bond_options.c +@@ -70,6 +70,7 @@ static struct bond_opt_value bond_fail_o + static struct bond_opt_value bond_intmax_tbl[] = { + { "off", 0, BOND_VALFLAG_DEFAULT}, + { "maxval", INT_MAX, BOND_VALFLAG_MAX}, ++ { NULL, -1, 0} + }; + + static struct bond_opt_value bond_lacp_rate_tbl[] = { diff --git a/queue-3.14/bonding-remove-debug_fs-files-when-module-init-fails.patch b/queue-3.14/bonding-remove-debug_fs-files-when-module-init-fails.patch new file mode 100644 index 00000000000..0356c6d76ef --- /dev/null +++ b/queue-3.14/bonding-remove-debug_fs-files-when-module-init-fails.patch @@ -0,0 +1,32 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Thomas Richter +Date: Wed, 9 Apr 2014 12:52:59 +0200 +Subject: bonding: Remove debug_fs files when module init fails + +From: Thomas Richter + +[ Upstream commit db29868653394937037d71dc3545768302dda643 ] + +Remove the bonding debug_fs entries when the +module initialization fails. The debug_fs +entries should be removed together with all other +already allocated resources. + +Signed-off-by: Thomas Richter +Signed-off-by: Jay Vosburgh +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/bonding/bond_main.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/bonding/bond_main.c ++++ b/drivers/net/bonding/bond_main.c +@@ -4536,6 +4536,7 @@ static int __init bonding_init(void) + out: + return res; + err: ++ bond_destroy_debugfs(); + bond_netlink_fini(); + err_link: + unregister_pernet_subsys(&bond_net_ops); diff --git a/queue-3.14/bridge-fix-double-free-and-memory-leak-around-br_allowed_ingress.patch b/queue-3.14/bridge-fix-double-free-and-memory-leak-around-br_allowed_ingress.patch new file mode 100644 index 00000000000..953da5cc811 --- /dev/null +++ b/queue-3.14/bridge-fix-double-free-and-memory-leak-around-br_allowed_ingress.patch @@ -0,0 +1,70 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Toshiaki Makita +Date: Wed, 9 Apr 2014 17:00:30 +0900 +Subject: bridge: Fix double free and memory leak around br_allowed_ingress + +From: Toshiaki Makita + +[ Upstream commit eb7076182d1ae4bc4641534134ed707100d76acc ] + +br_allowed_ingress() has two problems. + +1. If br_allowed_ingress() is called by br_handle_frame_finish() and +vlan_untag() in br_allowed_ingress() fails, skb will be freed by both +vlan_untag() and br_handle_frame_finish(). + +2. If br_allowed_ingress() is called by br_dev_xmit() and +br_allowed_ingress() fails, the skb will not be freed. + +Fix these two problems by freeing the skb in br_allowed_ingress() +if it fails. + +Signed-off-by: Toshiaki Makita +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/bridge/br_input.c | 2 +- + net/bridge/br_vlan.c | 7 ++++--- + 2 files changed, 5 insertions(+), 4 deletions(-) + +--- a/net/bridge/br_input.c ++++ b/net/bridge/br_input.c +@@ -73,7 +73,7 @@ int br_handle_frame_finish(struct sk_buf + goto drop; + + if (!br_allowed_ingress(p->br, nbp_get_vlan_info(p), skb, &vid)) +- goto drop; ++ goto out; + + /* insert into forwarding database after filtering to avoid spoofing */ + br = p->br; +--- a/net/bridge/br_vlan.c ++++ b/net/bridge/br_vlan.c +@@ -170,7 +170,7 @@ bool br_allowed_ingress(struct net_bridg + * rejected. + */ + if (!v) +- return false; ++ goto drop; + + /* If vlan tx offload is disabled on bridge device and frame was + * sent from vlan device on the bridge device, it does not have +@@ -193,7 +193,7 @@ bool br_allowed_ingress(struct net_bridg + * vlan untagged or priority-tagged traffic belongs to. + */ + if (pvid == VLAN_N_VID) +- return false; ++ goto drop; + + /* PVID is set on this port. Any untagged or priority-tagged + * ingress frame is considered to belong to this vlan. +@@ -216,7 +216,8 @@ bool br_allowed_ingress(struct net_bridg + /* Frame had a valid vlan tag. See if vlan is allowed */ + if (test_bit(*vid, v->vlan_bitmap)) + return true; +- ++drop: ++ kfree_skb(skb); + return false; + } + diff --git a/queue-3.14/bridge-handle-ifla_address-correctly-when-creating.patch b/queue-3.14/bridge-handle-ifla_address-correctly-when-creating.patch new file mode 100644 index 00000000000..ba196719082 --- /dev/null +++ b/queue-3.14/bridge-handle-ifla_address-correctly-when-creating.patch @@ -0,0 +1,54 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Toshiaki Makita +Date: Fri, 25 Apr 2014 17:01:18 +0900 +Subject: bridge: Handle IFLA_ADDRESS correctly when creating + bridge device + +From: Toshiaki Makita + +[ Upstream commit 30313a3d5794472c3548d7288e306a5492030370 ] + +When bridge device is created with IFLA_ADDRESS, we are not calling +br_stp_change_bridge_id(), which leads to incorrect local fdb +management and bridge id calculation, and prevents us from receiving +frames on the bridge device. + +Reported-by: Tom Gundersen +Signed-off-by: Toshiaki Makita +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/bridge/br_netlink.c | 15 +++++++++++++++ + 1 file changed, 15 insertions(+) + +--- a/net/bridge/br_netlink.c ++++ b/net/bridge/br_netlink.c +@@ -445,6 +445,20 @@ static int br_validate(struct nlattr *tb + return 0; + } + ++static int br_dev_newlink(struct net *src_net, struct net_device *dev, ++ struct nlattr *tb[], struct nlattr *data[]) ++{ ++ struct net_bridge *br = netdev_priv(dev); ++ ++ if (tb[IFLA_ADDRESS]) { ++ spin_lock_bh(&br->lock); ++ br_stp_change_bridge_id(br, nla_data(tb[IFLA_ADDRESS])); ++ spin_unlock_bh(&br->lock); ++ } ++ ++ return register_netdevice(dev); ++} ++ + static size_t br_get_link_af_size(const struct net_device *dev) + { + struct net_port_vlans *pv; +@@ -473,6 +487,7 @@ struct rtnl_link_ops br_link_ops __read_ + .priv_size = sizeof(struct net_bridge), + .setup = br_dev_setup, + .validate = br_validate, ++ .newlink = br_dev_newlink, + .dellink = br_dev_delete, + }; + diff --git a/queue-3.14/filter-prevent-nla-extensions-to-peek-beyond-the-end-of-the-message.patch b/queue-3.14/filter-prevent-nla-extensions-to-peek-beyond-the-end-of-the-message.patch new file mode 100644 index 00000000000..4521e058a4c --- /dev/null +++ b/queue-3.14/filter-prevent-nla-extensions-to-peek-beyond-the-end-of-the-message.patch @@ -0,0 +1,88 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Mathias Krause +Date: Sun, 13 Apr 2014 18:23:33 +0200 +Subject: filter: prevent nla extensions to peek beyond the end of the message + +From: Mathias Krause + +[ Upstream commit 05ab8f2647e4221cbdb3856dd7d32bd5407316b3 ] + +The BPF_S_ANC_NLATTR and BPF_S_ANC_NLATTR_NEST extensions fail to check +for a minimal message length before testing the supplied offset to be +within the bounds of the message. This allows the subtraction of the nla +header to underflow and therefore -- as the data type is unsigned -- +allowing far to big offset and length values for the search of the +netlink attribute. + +The remainder calculation for the BPF_S_ANC_NLATTR_NEST extension is +also wrong. It has the minuend and subtrahend mixed up, therefore +calculates a huge length value, allowing to overrun the end of the +message while looking for the netlink attribute. + +The following three BPF snippets will trigger the bugs when attached to +a UNIX datagram socket and parsing a message with length 1, 2 or 3. + + ,-[ PoC for missing size check in BPF_S_ANC_NLATTR ]-- + | ld #0x87654321 + | ldx #42 + | ld #nla + | ret a + `--- + + ,-[ PoC for the same bug in BPF_S_ANC_NLATTR_NEST ]-- + | ld #0x87654321 + | ldx #42 + | ld #nlan + | ret a + `--- + + ,-[ PoC for wrong remainder calculation in BPF_S_ANC_NLATTR_NEST ]-- + | ; (needs a fake netlink header at offset 0) + | ld #0 + | ldx #42 + | ld #nlan + | ret a + `--- + +Fix the first issue by ensuring the message length fulfills the minimal +size constrains of a nla header. Fix the second bug by getting the math +for the remainder calculation right. + +Fixes: 4738c1db15 ("[SKFILTER]: Add SKF_ADF_NLATTR instruction") +Fixes: d214c7537b ("filter: add SKF_AD_NLATTR_NEST to look for nested..") +Cc: Patrick McHardy +Cc: Pablo Neira Ayuso +Signed-off-by: Mathias Krause +Acked-by: Daniel Borkmann +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/filter.c | 6 +++++- + 1 file changed, 5 insertions(+), 1 deletion(-) + +--- a/net/core/filter.c ++++ b/net/core/filter.c +@@ -355,6 +355,8 @@ load_b: + + if (skb_is_nonlinear(skb)) + return 0; ++ if (skb->len < sizeof(struct nlattr)) ++ return 0; + if (A > skb->len - sizeof(struct nlattr)) + return 0; + +@@ -371,11 +373,13 @@ load_b: + + if (skb_is_nonlinear(skb)) + return 0; ++ if (skb->len < sizeof(struct nlattr)) ++ return 0; + if (A > skb->len - sizeof(struct nlattr)) + return 0; + + nla = (struct nlattr *)&skb->data[A]; +- if (nla->nla_len > A - skb->len) ++ if (nla->nla_len > skb->len - A) + return 0; + + nla = nla_find_nested(nla, X); diff --git a/queue-3.14/gre-don-t-allow-to-add-the-same-tunnel-twice.patch b/queue-3.14/gre-don-t-allow-to-add-the-same-tunnel-twice.patch new file mode 100644 index 00000000000..df4d37a15d6 --- /dev/null +++ b/queue-3.14/gre-don-t-allow-to-add-the-same-tunnel-twice.patch @@ -0,0 +1,46 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Nicolas Dichtel +Date: Fri, 11 Apr 2014 15:51:18 +0200 +Subject: gre: don't allow to add the same tunnel twice + +From: Nicolas Dichtel + +[ Upstream commit 5a4552752d8f7f4cef1d98775ece7adb7616fde2 ] + +Before the patch, it was possible to add two times the same tunnel: +ip l a gre1 type gre remote 10.16.0.121 local 10.16.0.249 +ip l a gre2 type gre remote 10.16.0.121 local 10.16.0.249 + +It was possible, because ip_tunnel_newlink() calls ip_tunnel_find() with the +argument dev->type, which was set only later (when calling ndo_init handler +in register_netdevice()). Let's set this type in the setup handler, which is +called before newlink handler. + +Introduced by commit c54419321455 ("GRE: Refactor GRE tunneling code."). + +CC: Pravin B Shelar +Signed-off-by: Nicolas Dichtel +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_gre.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/ip_gre.c ++++ b/net/ipv4/ip_gre.c +@@ -463,6 +463,7 @@ static const struct net_device_ops ipgre + static void ipgre_tunnel_setup(struct net_device *dev) + { + dev->netdev_ops = &ipgre_netdev_ops; ++ dev->type = ARPHRD_IPGRE; + ip_tunnel_setup(dev, ipgre_net_id); + } + +@@ -501,7 +502,6 @@ static int ipgre_tunnel_init(struct net_ + memcpy(dev->dev_addr, &iph->saddr, 4); + memcpy(dev->broadcast, &iph->daddr, 4); + +- dev->type = ARPHRD_IPGRE; + dev->flags = IFF_NOARP; + dev->priv_flags &= ~IFF_XMIT_DST_RELEASE; + dev->addr_len = 4; diff --git a/queue-3.14/ip6_gre-don-t-allow-to-remove-the-fb_tunnel_dev.patch b/queue-3.14/ip6_gre-don-t-allow-to-remove-the-fb_tunnel_dev.patch new file mode 100644 index 00000000000..baacedc6414 --- /dev/null +++ b/queue-3.14/ip6_gre-don-t-allow-to-remove-the-fb_tunnel_dev.patch @@ -0,0 +1,52 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Nicolas Dichtel +Date: Mon, 14 Apr 2014 17:11:38 +0200 +Subject: ip6_gre: don't allow to remove the fb_tunnel_dev + +From: Nicolas Dichtel + +[ Upstream commit 54d63f787b652755e66eb4dd8892ee6d3f5197fc ] + +It's possible to remove the FB tunnel with the command 'ip link del ip6gre0' but +this is unsafe, the module always supposes that this device exists. For example, +ip6gre_tunnel_lookup() may use it unconditionally. + +Let's add a rtnl handler for dellink, which will never remove the FB tunnel (we +let ip6gre_destroy_tunnels() do the job). + +Introduced by commit c12b395a4664 ("gre: Support GRE over IPv6"). + +CC: Dmitry Kozlov +Signed-off-by: Nicolas Dichtel +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_gre.c | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +--- a/net/ipv6/ip6_gre.c ++++ b/net/ipv6/ip6_gre.c +@@ -1566,6 +1566,15 @@ static int ip6gre_changelink(struct net_ + return 0; + } + ++static void ip6gre_dellink(struct net_device *dev, struct list_head *head) ++{ ++ struct net *net = dev_net(dev); ++ struct ip6gre_net *ign = net_generic(net, ip6gre_net_id); ++ ++ if (dev != ign->fb_tunnel_dev) ++ unregister_netdevice_queue(dev, head); ++} ++ + static size_t ip6gre_get_size(const struct net_device *dev) + { + return +@@ -1643,6 +1652,7 @@ static struct rtnl_link_ops ip6gre_link_ + .validate = ip6gre_tunnel_validate, + .newlink = ip6gre_newlink, + .changelink = ip6gre_changelink, ++ .dellink = ip6gre_dellink, + .get_size = ip6gre_get_size, + .fill_info = ip6gre_fill_info, + }; diff --git a/queue-3.14/ip6_tunnel-fix-potential-null-pointer-dereference.patch b/queue-3.14/ip6_tunnel-fix-potential-null-pointer-dereference.patch new file mode 100644 index 00000000000..d7b205def41 --- /dev/null +++ b/queue-3.14/ip6_tunnel-fix-potential-null-pointer-dereference.patch @@ -0,0 +1,35 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Susant Sahani +Date: Sat, 10 May 2014 00:11:32 +0530 +Subject: ip6_tunnel: fix potential NULL pointer dereference + +From: Susant Sahani + +[ Upstream commit c8965932a2e3b70197ec02c6741c29460279e2a8 ] + +The function ip6_tnl_validate assumes that the rtnl +attribute IFLA_IPTUN_PROTO always be filled . If this +attribute is not filled by the userspace application +kernel get crashed with NULL pointer dereference. This +patch fixes the potential kernel crash when +IFLA_IPTUN_PROTO is missing . + +Signed-off-by: Susant Sahani +Acked-by: Thomas Graf +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_tunnel.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv6/ip6_tunnel.c ++++ b/net/ipv6/ip6_tunnel.c +@@ -1564,7 +1564,7 @@ static int ip6_tnl_validate(struct nlatt + { + u8 proto; + +- if (!data) ++ if (!data || !data[IFLA_IPTUN_PROTO]) + return 0; + + proto = nla_get_u8(data[IFLA_IPTUN_PROTO]); diff --git a/queue-3.14/ip_tunnel-initialize-the-fallback-device-properly.patch b/queue-3.14/ip_tunnel-initialize-the-fallback-device-properly.patch new file mode 100644 index 00000000000..6aa8dc07b5f --- /dev/null +++ b/queue-3.14/ip_tunnel-initialize-the-fallback-device-properly.patch @@ -0,0 +1,32 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Steffen Klassert +Date: Mon, 19 May 2014 11:36:56 +0200 +Subject: ip_tunnel: Initialize the fallback device properly + +From: Steffen Klassert + +[ Upstream commit 78ff4be45a4c51d8fb21ad92e4fabb467c6c3eeb ] + +We need to initialize the fallback device to have a correct mtu +set on this device. Otherwise the mtu is set to null and the device +is unusable. + +Fixes: fd58156e456d ("IPIP: Use ip-tunneling code.") +Cc: Pravin B Shelar +Signed-off-by: Steffen Klassert +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_tunnel.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/net/ipv4/ip_tunnel.c ++++ b/net/ipv4/ip_tunnel.c +@@ -875,6 +875,7 @@ int ip_tunnel_init_net(struct net *net, + */ + if (!IS_ERR(itn->fb_tunnel_dev)) { + itn->fb_tunnel_dev->features |= NETIF_F_NETNS_LOCAL; ++ itn->fb_tunnel_dev->mtu = ip_tunnel_bind_dev(itn->fb_tunnel_dev); + ip_tunnel_add(itn, netdev_priv(itn->fb_tunnel_dev)); + } + rtnl_unlock(); diff --git a/queue-3.14/ip_tunnel-set-network-header-properly-for.patch b/queue-3.14/ip_tunnel-set-network-header-properly-for.patch new file mode 100644 index 00000000000..209645b7368 --- /dev/null +++ b/queue-3.14/ip_tunnel-set-network-header-properly-for.patch @@ -0,0 +1,44 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Ying Cai +Date: Sun, 4 May 2014 15:20:04 -0700 +Subject: ip_tunnel: Set network header properly for + IP_ECN_decapsulate() + +From: Ying Cai + +[ Upstream commit e96f2e7c430014eff52c93cabef1ad4f42ed0db1 ] + +In ip_tunnel_rcv(), set skb->network_header to inner IP header +before IP_ECN_decapsulate(). + +Without the fix, IP_ECN_decapsulate() takes outer IP header as +inner IP header, possibly causing error messages or packet drops. + +Note that this skb_reset_network_header() call was in this spot when +the original feature for checking consistency of ECN bits through +tunnels was added in eccc1bb8d4b4 ("tunnel: drop packet if ECN present +with not-ECT"). It was only removed from this spot in 3d7b46cd20e3 +("ip_tunnel: push generic protocol handling to ip_tunnel module."). + +Fixes: 3d7b46cd20e3 ("ip_tunnel: push generic protocol handling to ip_tunnel module.") +Reported-by: Neal Cardwell +Signed-off-by: Ying Cai +Acked-by: Neal Cardwell +Acked-by: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_tunnel.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/net/ipv4/ip_tunnel.c ++++ b/net/ipv4/ip_tunnel.c +@@ -438,6 +438,8 @@ int ip_tunnel_rcv(struct ip_tunnel *tunn + tunnel->i_seqno = ntohl(tpi->seq) + 1; + } + ++ skb_reset_network_header(skb); ++ + err = IP_ECN_decapsulate(iph, skb); + if (unlikely(err)) { + if (log_ecn_error) diff --git a/queue-3.14/ipv4-fib_semantics-increment-fib_info_cnt-after.patch b/queue-3.14/ipv4-fib_semantics-increment-fib_info_cnt-after.patch new file mode 100644 index 00000000000..d1a845542e2 --- /dev/null +++ b/queue-3.14/ipv4-fib_semantics-increment-fib_info_cnt-after.patch @@ -0,0 +1,39 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Sergey Popovich +Date: Tue, 6 May 2014 18:23:08 +0300 +Subject: ipv4: fib_semantics: increment fib_info_cnt after + fib_info allocation + +From: Sergey Popovich + +[ Upstream commit aeefa1ecfc799b0ea2c4979617f14cecd5cccbfd ] + +Increment fib_info_cnt in fib_create_info() right after successfuly +alllocating fib_info structure, overwise fib_metrics allocation failure +leads to fib_info_cnt incorrectly decremented in free_fib_info(), called +on error path from fib_create_info(). + +Signed-off-by: Sergey Popovich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/fib_semantics.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/fib_semantics.c ++++ b/net/ipv4/fib_semantics.c +@@ -820,13 +820,13 @@ struct fib_info *fib_create_info(struct + fi = kzalloc(sizeof(*fi)+nhs*sizeof(struct fib_nh), GFP_KERNEL); + if (fi == NULL) + goto failure; ++ fib_info_cnt++; + if (cfg->fc_mx) { + fi->fib_metrics = kzalloc(sizeof(u32) * RTAX_MAX, GFP_KERNEL); + if (!fi->fib_metrics) + goto failure; + } else + fi->fib_metrics = (u32 *) dst_default_metrics; +- fib_info_cnt++; + + fi->fib_net = hold_net(net); + fi->fib_protocol = cfg->fc_protocol; diff --git a/queue-3.14/ipv4-initialise-the-itag-variable-in-__mkroute_input.patch b/queue-3.14/ipv4-initialise-the-itag-variable-in-__mkroute_input.patch new file mode 100644 index 00000000000..18b606a955e --- /dev/null +++ b/queue-3.14/ipv4-initialise-the-itag-variable-in-__mkroute_input.patch @@ -0,0 +1,34 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Li RongQing +Date: Thu, 22 May 2014 16:36:55 +0800 +Subject: ipv4: initialise the itag variable in __mkroute_input + +From: Li RongQing + +[ Upstream commit fbdc0ad095c0a299e9abf5d8ac8f58374951149a ] + +the value of itag is a random value from stack, and may not be initiated by +fib_validate_source, which called fib_combine_itag if CONFIG_IP_ROUTE_CLASSID +is not set + +This will make the cached dst uncertainty + +Signed-off-by: Li RongQing +Acked-by: Alexei Starovoitov +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/route.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/route.c ++++ b/net/ipv4/route.c +@@ -1526,7 +1526,7 @@ static int __mkroute_input(struct sk_buf + struct in_device *out_dev; + unsigned int flags = 0; + bool do_cache; +- u32 itag; ++ u32 itag = 0; + + /* get a working reference to the output device */ + out_dev = __in_dev_get_rcu(FIB_RES_DEV(*res)); diff --git a/queue-3.14/ipv4-ip_tunnels-disable-cache-for-nbma-gre-tunnels.patch b/queue-3.14/ipv4-ip_tunnels-disable-cache-for-nbma-gre-tunnels.patch new file mode 100644 index 00000000000..631224e9d72 --- /dev/null +++ b/queue-3.14/ipv4-ip_tunnels-disable-cache-for-nbma-gre-tunnels.patch @@ -0,0 +1,63 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Timo=20Ter=C3=A4s?= +Date: Fri, 16 May 2014 08:34:39 +0300 +Subject: ipv4: ip_tunnels: disable cache for nbma gre tunnels +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Timo=20Ter=C3=A4s?= + +[ Upstream commit 22fb22eaebf4d16987f3fd9c3484c436ee0badf2 ] + +The connected check fails to check for ip_gre nbma mode tunnels +properly. ip_gre creates temporary tnl_params with daddr specified +to pass-in the actual target on per-packet basis from neighbor +layer. Detect these tunnels by inspecting the actual tunnel +configuration. + +Minimal test case: + ip route add 192.168.1.1/32 via 10.0.0.1 + ip route add 192.168.1.2/32 via 10.0.0.2 + ip tunnel add nbma0 mode gre key 1 tos c0 + ip addr add 172.17.0.0/16 dev nbma0 + ip link set nbma0 up + ip neigh add 172.17.0.1 lladdr 192.168.1.1 dev nbma0 + ip neigh add 172.17.0.2 lladdr 192.168.1.2 dev nbma0 + ping 172.17.0.1 + ping 172.17.0.2 + +The second ping should be going to 192.168.1.2 and head 10.0.0.2; +but cached gre tunnel level route is used and it's actually going +to 192.168.1.1 via 10.0.0.1. + +The lladdr's need to go to separate dst for the bug to trigger. +Test case uses separate route entries, but this can also happen +when the route entry is same: if there is a nexthop exception or +the GRE tunnel is IPsec'ed in which case the dst points to xfrm +bundle unique to the gre lladdr. + +Fixes: 7d442fab0a67 ("ipv4: Cache dst in tunnels") +Signed-off-by: Timo Teräs +Cc: Tom Herbert +Cc: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_tunnel.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/net/ipv4/ip_tunnel.c ++++ b/net/ipv4/ip_tunnel.c +@@ -536,9 +536,10 @@ void ip_tunnel_xmit(struct sk_buff *skb, + unsigned int max_headroom; /* The extra header space needed */ + __be32 dst; + int err; +- bool connected = true; ++ bool connected; + + inner_iph = (const struct iphdr *)skb_inner_network_header(skb); ++ connected = (tunnel->parms.iph.daddr != 0); + + dst = tnl_params->daddr; + if (dst == 0) { diff --git a/queue-3.14/ipv4-return-valid-rta_iif-on-ip-route-get.patch b/queue-3.14/ipv4-return-valid-rta_iif-on-ip-route-get.patch new file mode 100644 index 00000000000..8d324a8362c --- /dev/null +++ b/queue-3.14/ipv4-return-valid-rta_iif-on-ip-route-get.patch @@ -0,0 +1,35 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Julian Anastasov +Date: Sun, 13 Apr 2014 18:08:02 +0300 +Subject: ipv4: return valid RTA_IIF on ip route get + +From: Julian Anastasov + +[ Upstream commit 91146153da2feab18efab2e13b0945b6bb704ded ] + +Extend commit 13378cad02afc2adc6c0e07fca03903c7ada0b37 +("ipv4: Change rt->rt_iif encoding.") from 3.6 to return valid +RTA_IIF on 'ip route get ... iif DEVICE' instead of rt_iif 0 +which is displayed as 'iif *'. + +inet_iif is not appropriate to use because skb_iif is not set. +Use the skb->dev->ifindex instead. + +Signed-off-by: Julian Anastasov +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/route.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/route.c ++++ b/net/ipv4/route.c +@@ -2364,7 +2364,7 @@ static int rt_fill_info(struct net *net, + } + } else + #endif +- if (nla_put_u32(skb, RTA_IIF, rt->rt_iif)) ++ if (nla_put_u32(skb, RTA_IIF, skb->dev->ifindex)) + goto nla_put_failure; + } + diff --git a/queue-3.14/ipv6-fib-fix-fib-dump-restart.patch b/queue-3.14/ipv6-fib-fix-fib-dump-restart.patch new file mode 100644 index 00000000000..a513dc2cd03 --- /dev/null +++ b/queue-3.14/ipv6-fib-fix-fib-dump-restart.patch @@ -0,0 +1,45 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Kumar Sundararajan +Date: Thu, 24 Apr 2014 09:48:53 -0400 +Subject: ipv6: fib: fix fib dump restart + +From: Kumar Sundararajan + +[ Upstream commit 1c2658545816088477e91860c3a645053719cb54 ] + +When the ipv6 fib changes during a table dump, the walk is +restarted and the number of nodes dumped are skipped. But the existing +code doesn't advance to the next node after a node is skipped. This can +cause the dump to loop or produce lots of duplicates when the fib +is modified during the dump. + +This change advances the walk to the next node if the current node is +skipped after a restart. + +Signed-off-by: Kumar Sundararajan +Signed-off-by: Chris Mason +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_fib.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/net/ipv6/ip6_fib.c ++++ b/net/ipv6/ip6_fib.c +@@ -1418,7 +1418,7 @@ static int fib6_walk_continue(struct fib + + if (w->skip) { + w->skip--; +- continue; ++ goto skip; + } + + err = w->func(w); +@@ -1428,6 +1428,7 @@ static int fib6_walk_continue(struct fib + w->count++; + continue; + } ++skip: + w->state = FWS_U; + case FWS_U: + if (fn == w->root) diff --git a/queue-3.14/ipv6-fix-calculation-of-option-len-in-ip6_append_data.patch b/queue-3.14/ipv6-fix-calculation-of-option-len-in-ip6_append_data.patch new file mode 100644 index 00000000000..8e9ce659113 --- /dev/null +++ b/queue-3.14/ipv6-fix-calculation-of-option-len-in-ip6_append_data.patch @@ -0,0 +1,37 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Hannes Frederic Sowa +Date: Sun, 11 May 2014 23:01:13 +0200 +Subject: ipv6: fix calculation of option len in ip6_append_data + +From: Hannes Frederic Sowa + +[ Upstream commit 3a1cebe7e05027a1c96f2fc1a8eddf5f19b78f42 ] + +tot_len does specify the size of struct ipv6_txoptions. We need opt_flen + +opt_nflen to calculate the overall length of additional ipv6 extensions. + +I found this while auditing the ipv6 output path for a memory corruption +reported by Alexey Preobrazhensky while he fuzzed an instrumented +AddressSanitizer kernel with trinity. This may or may not be the cause +of the original bug. + +Fixes: 4df98e76cde7c6 ("ipv6: pmtudisc setting not respected with UFO/CORK") +Reported-by: Alexey Preobrazhensky +Signed-off-by: Hannes Frederic Sowa +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_output.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv6/ip6_output.c ++++ b/net/ipv6/ip6_output.c +@@ -1229,7 +1229,7 @@ int ip6_append_data(struct sock *sk, int + unsigned int maxnonfragsize, headersize; + + headersize = sizeof(struct ipv6hdr) + +- (opt ? opt->tot_len : 0) + ++ (opt ? opt->opt_flen + opt->opt_nflen : 0) + + (dst_allfrag(&rt->dst) ? + sizeof(struct frag_hdr) : 0) + + rt->rt6i_nfheader_len; diff --git a/queue-3.14/ipv6-gro-fix-checksum_complete-support.patch b/queue-3.14/ipv6-gro-fix-checksum_complete-support.patch new file mode 100644 index 00000000000..a5aba03f897 --- /dev/null +++ b/queue-3.14/ipv6-gro-fix-checksum_complete-support.patch @@ -0,0 +1,65 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Eric Dumazet +Date: Mon, 19 May 2014 21:56:34 -0700 +Subject: ipv6: gro: fix CHECKSUM_COMPLETE support + +From: Eric Dumazet + +[ Upstream commit 4de462ab63e23953fd05da511aeb460ae10cc726 ] + +When GRE support was added in linux-3.14, CHECKSUM_COMPLETE handling +broke on GRE+IPv6 because we did not update/use the appropriate csum : + +GRO layer is supposed to use/update NAPI_GRO_CB(skb)->csum instead of +skb->csum + +Tested using a GRE tunnel and IPv6 traffic. GRO aggregation now happens +at the first level (ethernet device) instead of being done in gre +tunnel. Native IPv6+TCP is still properly aggregated. + +Fixes: bf5a755f5e918 ("net-gre-gro: Add GRE support to the GRO stack") +Signed-off-by: Eric Dumazet +Cc: Jerry Chu +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_offload.c | 6 +----- + net/ipv6/tcpv6_offload.c | 2 +- + 2 files changed, 2 insertions(+), 6 deletions(-) + +--- a/net/ipv6/ip6_offload.c ++++ b/net/ipv6/ip6_offload.c +@@ -196,7 +196,6 @@ static struct sk_buff **ipv6_gro_receive + unsigned int off; + u16 flush = 1; + int proto; +- __wsum csum; + + off = skb_gro_offset(skb); + hlen = off + sizeof(*iph); +@@ -264,13 +263,10 @@ static struct sk_buff **ipv6_gro_receive + + NAPI_GRO_CB(skb)->flush |= flush; + +- csum = skb->csum; +- skb_postpull_rcsum(skb, iph, skb_network_header_len(skb)); ++ skb_gro_postpull_rcsum(skb, iph, nlen); + + pp = ops->callbacks.gro_receive(head, skb); + +- skb->csum = csum; +- + out_unlock: + rcu_read_unlock(); + +--- a/net/ipv6/tcpv6_offload.c ++++ b/net/ipv6/tcpv6_offload.c +@@ -42,7 +42,7 @@ static struct sk_buff **tcp6_gro_receive + if (NAPI_GRO_CB(skb)->flush) + goto skip_csum; + +- wsum = skb->csum; ++ wsum = NAPI_GRO_CB(skb)->csum; + + switch (skb->ip_summed) { + case CHECKSUM_NONE: diff --git a/queue-3.14/ipv6-limit-mtu-to-65575-bytes.patch b/queue-3.14/ipv6-limit-mtu-to-65575-bytes.patch new file mode 100644 index 00000000000..702c1fe29a6 --- /dev/null +++ b/queue-3.14/ipv6-limit-mtu-to-65575-bytes.patch @@ -0,0 +1,71 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Eric Dumazet +Date: Thu, 10 Apr 2014 21:23:36 -0700 +Subject: ipv6: Limit mtu to 65575 bytes + +From: Eric Dumazet + +[ Upstream commit 30f78d8ebf7f514801e71b88a10c948275168518 ] + +Francois reported that setting big mtu on loopback device could prevent +tcp sessions making progress. + +We do not support (yet ?) IPv6 Jumbograms and cook corrupted packets. + +We must limit the IPv6 MTU to (65535 + 40) bytes in theory. + +Tested: + +ifconfig lo mtu 70000 +netperf -H ::1 + +Before patch : Throughput : 0.05 Mbits + +After patch : Throughput : 35484 Mbits + +Reported-by: Francois WELLENREITER +Signed-off-by: Eric Dumazet +Acked-by: YOSHIFUJI Hideaki +Acked-by: Hannes Frederic Sowa +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/net/ip6_route.h | 5 +++++ + net/ipv6/route.c | 5 +++-- + 2 files changed, 8 insertions(+), 2 deletions(-) + +--- a/include/net/ip6_route.h ++++ b/include/net/ip6_route.h +@@ -32,6 +32,11 @@ struct route_info { + #define RT6_LOOKUP_F_SRCPREF_PUBLIC 0x00000010 + #define RT6_LOOKUP_F_SRCPREF_COA 0x00000020 + ++/* We do not (yet ?) support IPv6 jumbograms (RFC 2675) ++ * Unlike IPv4, hdr->seg_len doesn't include the IPv6 header ++ */ ++#define IP6_MAX_MTU (0xFFFF + sizeof(struct ipv6hdr)) ++ + /* + * rt6_srcprefs2flags() and rt6_flags2srcprefs() translate + * between IPV6_ADDR_PREFERENCES socket option values +--- a/net/ipv6/route.c ++++ b/net/ipv6/route.c +@@ -1342,7 +1342,7 @@ static unsigned int ip6_mtu(const struct + unsigned int mtu = dst_metric_raw(dst, RTAX_MTU); + + if (mtu) +- return mtu; ++ goto out; + + mtu = IPV6_MIN_MTU; + +@@ -1352,7 +1352,8 @@ static unsigned int ip6_mtu(const struct + mtu = idev->cnf.mtu6; + rcu_read_unlock(); + +- return mtu; ++out: ++ return min_t(unsigned int, mtu, IP6_MAX_MTU); + } + + static struct dst_entry *icmp6_dst_gc_list; diff --git a/queue-3.14/l2tp-take-pmtu-from-tunnel-udp-socket.patch b/queue-3.14/l2tp-take-pmtu-from-tunnel-udp-socket.patch new file mode 100644 index 00000000000..4308780c3ef --- /dev/null +++ b/queue-3.14/l2tp-take-pmtu-from-tunnel-udp-socket.patch @@ -0,0 +1,34 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Dmitry Petukhov +Date: Wed, 9 Apr 2014 02:23:20 +0600 +Subject: l2tp: take PMTU from tunnel UDP socket + +From: Dmitry Petukhov + +[ Upstream commit f34c4a35d87949fbb0e0f31eba3c054e9f8199ba ] + +When l2tp driver tries to get PMTU for the tunnel destination, it uses +the pointer to struct sock that represents PPPoX socket, while it +should use the pointer that represents UDP socket of the tunnel. + +Signed-off-by: Dmitry Petukhov +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/l2tp/l2tp_ppp.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/net/l2tp/l2tp_ppp.c ++++ b/net/l2tp/l2tp_ppp.c +@@ -756,9 +756,9 @@ static int pppol2tp_connect(struct socke + session->deref = pppol2tp_session_sock_put; + + /* If PMTU discovery was enabled, use the MTU that was discovered */ +- dst = sk_dst_get(sk); ++ dst = sk_dst_get(tunnel->sock); + if (dst != NULL) { +- u32 pmtu = dst_mtu(__sk_dst_get(sk)); ++ u32 pmtu = dst_mtu(__sk_dst_get(tunnel->sock)); + if (pmtu != 0) + session->mtu = session->mru = pmtu - + PPPOL2TP_HEADER_OVERHEAD; diff --git a/queue-3.14/mactap-fix-checksum-errors-for-non-gso-packets-in.patch b/queue-3.14/mactap-fix-checksum-errors-for-non-gso-packets-in.patch new file mode 100644 index 00000000000..d33dc7c9a4e --- /dev/null +++ b/queue-3.14/mactap-fix-checksum-errors-for-non-gso-packets-in.patch @@ -0,0 +1,63 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Tue, 29 Apr 2014 10:09:50 -0400 +Subject: mactap: Fix checksum errors for non-gso packets in + bridge mode + +From: Vlad Yasevich + +[ Upstream commit cbdb04279ccaefcc702c8757757eea8ed76e50cf ] + +The following is a problematic configuration: + + VM1: virtio-net device connected to macvtap0@eth0 + VM2: e1000 device connect to macvtap1@eth0 + +The problem is is that virtio-net supports checksum offloading +and thus sends the packets to the host with CHECKSUM_PARTIAL set. +On the other hand, e1000 does not support any acceleration. + +For small TCP packets (and this includes the 3-way handshake), +e1000 ends up receiving packets that only have a partial checksum +set. This causes TCP to fail checksum validation and to drop +packets. As a result tcp connections can not be established. + +Commit 3e4f8b787370978733ca6cae452720a4f0c296b8 + macvtap: Perform GSO on forwarding path. +fixes this issue for large packets wthat will end up undergoing GSO. +This commit adds a check for the non-GSO case and attempts to +compute the checksum for partially checksummed packets in the +non-GSO case. + +CC: Daniel Lezcano +CC: Patrick McHardy +CC: Andrian Nord +CC: Eric Dumazet +CC: Michael S. Tsirkin +CC: Jason Wang +Signed-off-by: Vlad Yasevich +Acked-by: Jason Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/macvtap.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +--- a/drivers/net/macvtap.c ++++ b/drivers/net/macvtap.c +@@ -322,6 +322,15 @@ static rx_handler_result_t macvtap_handl + segs = nskb; + } + } else { ++ /* If we receive a partial checksum and the tap side ++ * doesn't support checksum offload, compute the checksum. ++ * Note: it doesn't matter which checksum feature to ++ * check, we either support them all or none. ++ */ ++ if (skb->ip_summed == CHECKSUM_PARTIAL && ++ !(features & NETIF_F_ALL_CSUM) && ++ skb_checksum_help(skb)) ++ goto drop; + skb_queue_tail(&q->sk.sk_receive_queue, skb); + } + diff --git a/queue-3.14/macvlan-don-t-propagate-iff_allmulti-changes-on-down.patch b/queue-3.14/macvlan-don-t-propagate-iff_allmulti-changes-on-down.patch new file mode 100644 index 00000000000..456357da39b --- /dev/null +++ b/queue-3.14/macvlan-don-t-propagate-iff_allmulti-changes-on-down.patch @@ -0,0 +1,40 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Peter Christensen +Date: Thu, 8 May 2014 11:15:37 +0200 +Subject: macvlan: Don't propagate IFF_ALLMULTI changes on down + interfaces. + +From: Peter Christensen + +[ Upstream commit bbeb0eadcf9fe74fb2b9b1a6fea82cd538b1e556 ] + +Clearing the IFF_ALLMULTI flag on a down interface could cause an allmulti +overflow on the underlying interface. + +Attempting the set IFF_ALLMULTI on the underlying interface would cause an +error and the log message: + +"allmulti touches root, set allmulti failed." + +Signed-off-by: Peter Christensen +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/macvlan.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/drivers/net/macvlan.c ++++ b/drivers/net/macvlan.c +@@ -458,8 +458,10 @@ static void macvlan_change_rx_flags(stru + struct macvlan_dev *vlan = netdev_priv(dev); + struct net_device *lowerdev = vlan->lowerdev; + +- if (change & IFF_ALLMULTI) +- dev_set_allmulti(lowerdev, dev->flags & IFF_ALLMULTI ? 1 : -1); ++ if (dev->flags & IFF_UP) { ++ if (change & IFF_ALLMULTI) ++ dev_set_allmulti(lowerdev, dev->flags & IFF_ALLMULTI ? 1 : -1); ++ } + } + + static void macvlan_set_mac_lists(struct net_device *dev) diff --git a/queue-3.14/macvlan-fix-lockdep-warnings-with-stacked-macvlan.patch b/queue-3.14/macvlan-fix-lockdep-warnings-with-stacked-macvlan.patch new file mode 100644 index 00000000000..a8d60387e4d --- /dev/null +++ b/queue-3.14/macvlan-fix-lockdep-warnings-with-stacked-macvlan.patch @@ -0,0 +1,209 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Fri, 16 May 2014 17:04:56 -0400 +Subject: macvlan: Fix lockdep warnings with stacked macvlan + devices + +From: Vlad Yasevich + +[ Upstream commit c674ac30c549596295eb0a5af7f4714c0b905b6f ] + +Macvlan devices try to avoid stacking, but that's not always +successfull or even desired. As an example, the following +configuration is perefectly legal and valid: + +eth0 <--- macvlan0 <---- vlan0.10 <--- macvlan1 + +However, this configuration produces the following lockdep +trace: +[ 115.620418] ====================================================== +[ 115.620477] [ INFO: possible circular locking dependency detected ] +[ 115.620516] 3.15.0-rc1+ #24 Not tainted +[ 115.620540] ------------------------------------------------------- +[ 115.620577] ip/1704 is trying to acquire lock: +[ 115.620604] (&vlan_netdev_addr_lock_key/1){+.....}, at: [] dev_uc_sync+0x3c/0x80 +[ 115.620686] +but task is already holding lock: +[ 115.620723] (&macvlan_netdev_addr_lock_key){+.....}, at: [] dev_set_rx_mode+0x1e/0x40 +[ 115.620795] +which lock already depends on the new lock. + +[ 115.620853] +the existing dependency chain (in reverse order) is: +[ 115.620894] +-> #1 (&macvlan_netdev_addr_lock_key){+.....}: +[ 115.620935] [] lock_acquire+0xa2/0x130 +[ 115.620974] [] _raw_spin_lock_nested+0x37/0x50 +[ 115.621019] [] vlan_dev_set_rx_mode+0x53/0x110 [8021q] +[ 115.621066] [] __dev_set_rx_mode+0x57/0xa0 +[ 115.621105] [] dev_set_rx_mode+0x26/0x40 +[ 115.621143] [] __dev_open+0xde/0x140 +[ 115.621174] [] __dev_change_flags+0x9d/0x170 +[ 115.621174] [] dev_change_flags+0x29/0x60 +[ 115.621174] [] do_setlink+0x321/0x9a0 +[ 115.621174] [] rtnl_newlink+0x51f/0x730 +[ 115.621174] [] rtnetlink_rcv_msg+0x95/0x250 +[ 115.621174] [] netlink_rcv_skb+0xa9/0xc0 +[ 115.621174] [] rtnetlink_rcv+0x2a/0x40 +[ 115.621174] [] netlink_unicast+0xf0/0x1c0 +[ 115.621174] [] netlink_sendmsg+0x2ff/0x740 +[ 115.621174] [] sock_sendmsg+0x8b/0xc0 +[ 115.621174] [] ___sys_sendmsg+0x369/0x380 +[ 115.621174] [] __sys_sendmsg+0x42/0x80 +[ 115.621174] [] SyS_sendmsg+0x12/0x20 +[ 115.621174] [] system_call_fastpath+0x16/0x1b +[ 115.621174] +-> #0 (&vlan_netdev_addr_lock_key/1){+.....}: +[ 115.621174] [] __lock_acquire+0x1773/0x1a60 +[ 115.621174] [] lock_acquire+0xa2/0x130 +[ 115.621174] [] _raw_spin_lock_nested+0x37/0x50 +[ 115.621174] [] dev_uc_sync+0x3c/0x80 +[ 115.621174] [] macvlan_set_mac_lists+0xca/0x110 [macvlan] +[ 115.621174] [] __dev_set_rx_mode+0x57/0xa0 +[ 115.621174] [] dev_set_rx_mode+0x26/0x40 +[ 115.621174] [] __dev_open+0xde/0x140 +[ 115.621174] [] __dev_change_flags+0x9d/0x170 +[ 115.621174] [] dev_change_flags+0x29/0x60 +[ 115.621174] [] do_setlink+0x321/0x9a0 +[ 115.621174] [] rtnl_newlink+0x51f/0x730 +[ 115.621174] [] rtnetlink_rcv_msg+0x95/0x250 +[ 115.621174] [] netlink_rcv_skb+0xa9/0xc0 +[ 115.621174] [] rtnetlink_rcv+0x2a/0x40 +[ 115.621174] [] netlink_unicast+0xf0/0x1c0 +[ 115.621174] [] netlink_sendmsg+0x2ff/0x740 +[ 115.621174] [] sock_sendmsg+0x8b/0xc0 +[ 115.621174] [] ___sys_sendmsg+0x369/0x380 +[ 115.621174] [] __sys_sendmsg+0x42/0x80 +[ 115.621174] [] SyS_sendmsg+0x12/0x20 +[ 115.621174] [] system_call_fastpath+0x16/0x1b +[ 115.621174] +other info that might help us debug this: + +[ 115.621174] Possible unsafe locking scenario: + +[ 115.621174] CPU0 CPU1 +[ 115.621174] ---- ---- +[ 115.621174] lock(&macvlan_netdev_addr_lock_key); +[ 115.621174] lock(&vlan_netdev_addr_lock_key/1); +[ 115.621174] lock(&macvlan_netdev_addr_lock_key); +[ 115.621174] lock(&vlan_netdev_addr_lock_key/1); +[ 115.621174] + *** DEADLOCK *** + +[ 115.621174] 2 locks held by ip/1704: +[ 115.621174] #0: (rtnl_mutex){+.+.+.}, at: [] rtnetlink_rcv+0x1b/0x40 +[ 115.621174] #1: (&macvlan_netdev_addr_lock_key){+.....}, at: [] dev_set_rx_mode+0x1e/0x40 +[ 115.621174] +stack backtrace: +[ 115.621174] CPU: 3 PID: 1704 Comm: ip Not tainted 3.15.0-rc1+ #24 +[ 115.621174] Hardware name: Hewlett-Packard HP xw8400 Workstation/0A08h, BIOS 786D5 v02.38 10/25/2010 +[ 115.621174] ffffffff82339ae0 ffff880465f79568 ffffffff816ee20c ffffffff82339ae0 +[ 115.621174] ffff880465f795a8 ffffffff816e9e1b ffff880465f79600 ffff880465b019c8 +[ 115.621174] 0000000000000001 0000000000000002 ffff880465b019c8 ffff880465b01230 +[ 115.621174] Call Trace: +[ 115.621174] [] dump_stack+0x4d/0x66 +[ 115.621174] [] print_circular_bug+0x200/0x20e +[ 115.621174] [] __lock_acquire+0x1773/0x1a60 +[ 115.621174] [] ? trace_hardirqs_on_caller+0xb2/0x1d0 +[ 115.621174] [] lock_acquire+0xa2/0x130 +[ 115.621174] [] ? dev_uc_sync+0x3c/0x80 +[ 115.621174] [] _raw_spin_lock_nested+0x37/0x50 +[ 115.621174] [] ? dev_uc_sync+0x3c/0x80 +[ 115.621174] [] dev_uc_sync+0x3c/0x80 +[ 115.621174] [] macvlan_set_mac_lists+0xca/0x110 [macvlan] +[ 115.621174] [] __dev_set_rx_mode+0x57/0xa0 +[ 115.621174] [] dev_set_rx_mode+0x26/0x40 +[ 115.621174] [] __dev_open+0xde/0x140 +[ 115.621174] [] __dev_change_flags+0x9d/0x170 +[ 115.621174] [] dev_change_flags+0x29/0x60 +[ 115.621174] [] ? mem_cgroup_bad_page_check+0x21/0x30 +[ 115.621174] [] do_setlink+0x321/0x9a0 +[ 115.621174] [] ? __lock_acquire+0x37c/0x1a60 +[ 115.621174] [] rtnl_newlink+0x51f/0x730 +[ 115.621174] [] ? rtnl_newlink+0xe9/0x730 +[ 115.621174] [] rtnetlink_rcv_msg+0x95/0x250 +[ 115.621174] [] ? trace_hardirqs_on+0xd/0x10 +[ 115.621174] [] ? rtnetlink_rcv+0x1b/0x40 +[ 115.621174] [] ? rtnetlink_rcv+0x40/0x40 +[ 115.621174] [] netlink_rcv_skb+0xa9/0xc0 +[ 115.621174] [] rtnetlink_rcv+0x2a/0x40 +[ 115.621174] [] netlink_unicast+0xf0/0x1c0 +[ 115.621174] [] netlink_sendmsg+0x2ff/0x740 +[ 115.621174] [] sock_sendmsg+0x8b/0xc0 +[ 115.621174] [] ? might_fault+0x5f/0xb0 +[ 115.621174] [] ? might_fault+0xa8/0xb0 +[ 115.621174] [] ? might_fault+0x5f/0xb0 +[ 115.621174] [] ? verify_iovec+0x5e/0xe0 +[ 115.621174] [] ___sys_sendmsg+0x369/0x380 +[ 115.621174] [] ? __do_page_fault+0x11d/0x570 +[ 115.621174] [] ? up_read+0x1f/0x40 +[ 115.621174] [] ? __do_page_fault+0x214/0x570 +[ 115.621174] [] ? mntput_no_expire+0x6b/0x1c0 +[ 115.621174] [] ? mntput_no_expire+0x17/0x1c0 +[ 115.621174] [] ? mntput+0x24/0x40 +[ 115.621174] [] __sys_sendmsg+0x42/0x80 +[ 115.621174] [] SyS_sendmsg+0x12/0x20 +[ 115.621174] [] system_call_fastpath+0x16/0x1b + +Fix this by correctly providing macvlan lockdep class. + +Signed-off-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/macvlan.c | 12 ++++++++++-- + include/linux/if_macvlan.h | 1 + + 2 files changed, 11 insertions(+), 2 deletions(-) + +--- a/drivers/net/macvlan.c ++++ b/drivers/net/macvlan.c +@@ -518,6 +518,11 @@ static struct lock_class_key macvlan_net + #define MACVLAN_STATE_MASK \ + ((1<<__LINK_STATE_NOCARRIER) | (1<<__LINK_STATE_DORMANT)) + ++static int macvlan_get_nest_level(struct net_device *dev) ++{ ++ return ((struct macvlan_dev *)netdev_priv(dev))->nest_level; ++} ++ + static void macvlan_set_lockdep_class_one(struct net_device *dev, + struct netdev_queue *txq, + void *_unused) +@@ -528,8 +533,9 @@ static void macvlan_set_lockdep_class_on + + static void macvlan_set_lockdep_class(struct net_device *dev) + { +- lockdep_set_class(&dev->addr_list_lock, +- &macvlan_netdev_addr_lock_key); ++ lockdep_set_class_and_subclass(&dev->addr_list_lock, ++ &macvlan_netdev_addr_lock_key, ++ macvlan_get_nest_level(dev)); + netdev_for_each_tx_queue(dev, macvlan_set_lockdep_class_one, NULL); + } + +@@ -731,6 +737,7 @@ static const struct net_device_ops macvl + .ndo_fdb_add = macvlan_fdb_add, + .ndo_fdb_del = macvlan_fdb_del, + .ndo_fdb_dump = ndo_dflt_fdb_dump, ++ .ndo_get_lock_subclass = macvlan_get_nest_level, + }; + + void macvlan_common_setup(struct net_device *dev) +@@ -859,6 +866,7 @@ int macvlan_common_newlink(struct net *s + vlan->dev = dev; + vlan->port = port; + vlan->set_features = MACVLAN_FEATURES; ++ vlan->nest_level = dev_get_nest_level(lowerdev, netif_is_macvlan) + 1; + + vlan->mode = MACVLAN_MODE_VEPA; + if (data && data[IFLA_MACVLAN_MODE]) +--- a/include/linux/if_macvlan.h ++++ b/include/linux/if_macvlan.h +@@ -56,6 +56,7 @@ struct macvlan_dev { + int numqueues; + netdev_features_t tap_features; + int minor; ++ int nest_level; + }; + + static inline void macvlan_count_rx(const struct macvlan_dev *vlan, diff --git a/queue-3.14/neigh-set-nud_state-to-nud_incomplete-when-probing.patch b/queue-3.14/neigh-set-nud_state-to-nud_incomplete-when-probing.patch new file mode 100644 index 00000000000..55ef9d7a09e --- /dev/null +++ b/queue-3.14/neigh-set-nud_state-to-nud_incomplete-when-probing.patch @@ -0,0 +1,43 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Duan Jiong +Date: Fri, 9 May 2014 13:16:48 +0800 +Subject: neigh: set nud_state to NUD_INCOMPLETE when probing + router reachability + +From: Duan Jiong + +[ Upstream commit 2176d5d41891753774f648b67470398a5acab584 ] + +Since commit 7e98056964("ipv6: router reachability probing"), a router falls +into NUD_FAILED will be probed. + +Now if function rt6_select() selects a router which neighbour state is NUD_FAILED, +and at the same time function rt6_probe() changes the neighbour state to NUD_PROBE, +then function dst_neigh_output() can directly send packets, but actually the +neighbour still is unreachable. If we set nud_state to NUD_INCOMPLETE instead +NUD_PROBE, packets will not be sent out until the neihbour is reachable. + +In addition, because the route should be probes with a single NS, so we must +set neigh->probes to neigh_max_probes(), then the neigh timer timeout and function +neigh_timer_handler() will not send other NS Messages. + +Signed-off-by: Duan Jiong +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/neighbour.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/net/core/neighbour.c ++++ b/net/core/neighbour.c +@@ -1247,8 +1247,8 @@ void __neigh_set_probe_once(struct neigh + neigh->updated = jiffies; + if (!(neigh->nud_state & NUD_FAILED)) + return; +- neigh->nud_state = NUD_PROBE; +- atomic_set(&neigh->probes, NEIGH_VAR(neigh->parms, UCAST_PROBES)); ++ neigh->nud_state = NUD_INCOMPLETE; ++ atomic_set(&neigh->probes, neigh_max_probes(neigh)); + neigh_add_timer(neigh, + jiffies + NEIGH_VAR(neigh->parms, RETRANS_TIME)); + } diff --git a/queue-3.14/net-allow-for-more-then-a-single-subclass-for.patch b/queue-3.14/net-allow-for-more-then-a-single-subclass-for.patch new file mode 100644 index 00000000000..047db3c3d79 --- /dev/null +++ b/queue-3.14/net-allow-for-more-then-a-single-subclass-for.patch @@ -0,0 +1,56 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Fri, 16 May 2014 17:04:54 -0400 +Subject: net: Allow for more then a single subclass for + netif_addr_lock + +From: Vlad Yasevich + +[ Upstream commit 25175ba5c9bff9aaf0229df34bb5d54c81633ec3 ] + +Currently netif_addr_lock_nested assumes that there can be only +a single nesting level between 2 devices. However, if we +have multiple devices of the same type stacked, this fails. +For example: + eth0 <-- vlan0.10 <-- vlan0.10.20 + +A more complicated configuration may stack more then one type of +device in different order. +Ex: + eth0 <-- vlan0.10 <-- macvlan0 <-- vlan1.10.20 <-- macvlan1 + +This patch adds an ndo_* function that allows each stackable +device to report its nesting level. If the device doesn't +provide this function default subclass of 1 is used. + +Signed-off-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/netdevice.h | 8 +++++++- + 1 file changed, 7 insertions(+), 1 deletion(-) + +--- a/include/linux/netdevice.h ++++ b/include/linux/netdevice.h +@@ -1145,6 +1145,7 @@ struct net_device_ops { + netdev_tx_t (*ndo_dfwd_start_xmit) (struct sk_buff *skb, + struct net_device *dev, + void *priv); ++ int (*ndo_get_lock_subclass)(struct net_device *dev); + }; + + /* +@@ -2861,7 +2862,12 @@ static inline void netif_addr_lock(struc + + static inline void netif_addr_lock_nested(struct net_device *dev) + { +- spin_lock_nested(&dev->addr_list_lock, SINGLE_DEPTH_NESTING); ++ int subclass = SINGLE_DEPTH_NESTING; ++ ++ if (dev->netdev_ops->ndo_get_lock_subclass) ++ subclass = dev->netdev_ops->ndo_get_lock_subclass(dev); ++ ++ spin_lock_nested(&dev->addr_list_lock, subclass); + } + + static inline void netif_addr_lock_bh(struct net_device *dev) diff --git a/queue-3.14/net-avoid-dependency-of-net_get_random_once-on-nop.patch b/queue-3.14/net-avoid-dependency-of-net_get_random_once-on-nop.patch new file mode 100644 index 00000000000..bba2388fae1 --- /dev/null +++ b/queue-3.14/net-avoid-dependency-of-net_get_random_once-on-nop.patch @@ -0,0 +1,105 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Hannes Frederic Sowa +Date: Sun, 11 May 2014 22:59:30 +0200 +Subject: net: avoid dependency of net_get_random_once on nop + patching +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Hannes Frederic Sowa + +[ Upstream commit 3d4405226d27b3a215e4d03cfa51f536244e5de7 ] + +net_get_random_once depends on the static keys infrastructure to patch up +the branch to the slow path during boot. This was realized by abusing the +static keys api and defining a new initializer to not enable the call +site while still indicating that the branch point should get patched +up. This was needed to have the fast path considered likely by gcc. + +The static key initialization during boot up normally walks through all +the registered keys and either patches in ideal nops or enables the jump +site but omitted that step on x86 if ideal nops where already placed at +static_key branch points. Thus net_get_random_once branches not always +became active. + +This patch switches net_get_random_once to the ordinary static_key +api and thus places the kernel fast path in the - by gcc considered - +unlikely path. Microbenchmarks on Intel and AMD x86-64 showed that +the unlikely path actually beats the likely path in terms of cycle cost +and that different nop patterns did not make much difference, thus this +switch should not be noticeable. + +Fixes: a48e42920ff38b ("net: introduce new macro net_get_random_once") +Reported-by: Tuomas Räsänen +Cc: Linus Torvalds +Signed-off-by: Hannes Frederic Sowa +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/net.h | 15 ++++----------- + net/core/utils.c | 8 ++++---- + 2 files changed, 8 insertions(+), 15 deletions(-) + +--- a/include/linux/net.h ++++ b/include/linux/net.h +@@ -248,24 +248,17 @@ do { \ + bool __net_get_random_once(void *buf, int nbytes, bool *done, + struct static_key *done_key); + +-#ifdef HAVE_JUMP_LABEL +-#define ___NET_RANDOM_STATIC_KEY_INIT ((struct static_key) \ +- { .enabled = ATOMIC_INIT(0), .entries = (void *)1 }) +-#else /* !HAVE_JUMP_LABEL */ +-#define ___NET_RANDOM_STATIC_KEY_INIT STATIC_KEY_INIT_FALSE +-#endif /* HAVE_JUMP_LABEL */ +- + #define net_get_random_once(buf, nbytes) \ + ({ \ + bool ___ret = false; \ + static bool ___done = false; \ +- static struct static_key ___done_key = \ +- ___NET_RANDOM_STATIC_KEY_INIT; \ +- if (!static_key_true(&___done_key)) \ ++ static struct static_key ___once_key = \ ++ STATIC_KEY_INIT_TRUE; \ ++ if (static_key_true(&___once_key)) \ + ___ret = __net_get_random_once(buf, \ + nbytes, \ + &___done, \ +- &___done_key); \ ++ &___once_key); \ + ___ret; \ + }) + +--- a/net/core/utils.c ++++ b/net/core/utils.c +@@ -348,8 +348,8 @@ static void __net_random_once_deferred(s + { + struct __net_random_once_work *work = + container_of(w, struct __net_random_once_work, work); +- if (!static_key_enabled(work->key)) +- static_key_slow_inc(work->key); ++ BUG_ON(!static_key_enabled(work->key)); ++ static_key_slow_dec(work->key); + kfree(work); + } + +@@ -367,7 +367,7 @@ static void __net_random_once_disable_ju + } + + bool __net_get_random_once(void *buf, int nbytes, bool *done, +- struct static_key *done_key) ++ struct static_key *once_key) + { + static DEFINE_SPINLOCK(lock); + unsigned long flags; +@@ -382,7 +382,7 @@ bool __net_get_random_once(void *buf, in + *done = true; + spin_unlock_irqrestore(&lock, flags); + +- __net_random_once_disable_jump(done_key); ++ __net_random_once_disable_jump(once_key); + + return true; + } diff --git a/queue-3.14/net-cdc_mbim-__vlan_find_dev_deep-need-rcu_read_lock.patch b/queue-3.14/net-cdc_mbim-__vlan_find_dev_deep-need-rcu_read_lock.patch new file mode 100644 index 00000000000..4143fbfcba4 --- /dev/null +++ b/queue-3.14/net-cdc_mbim-__vlan_find_dev_deep-need-rcu_read_lock.patch @@ -0,0 +1,99 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Sat, 3 May 2014 16:12:47 +0200 +Subject: net: cdc_mbim: __vlan_find_dev_deep need rcu_read_lock +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 4f4178f3bb1f470d7fb863ec531e08e20a0fd51c ] + +Fixes this warning introduced by commit 5b8f15f78e6f +("net: cdc_mbim: handle IPv6 Neigbor Solicitations"): + +=============================== +[ INFO: suspicious RCU usage. ] +3.15.0-rc3 #213 Tainted: G W O +------------------------------- +net/8021q/vlan_core.c:69 suspicious rcu_dereference_check() usage! + +other info that might help us debug this: + +rcu_scheduler_active = 1, debug_locks = 1 +no locks held by ksoftirqd/0/3. + +stack backtrace: +CPU: 0 PID: 3 Comm: ksoftirqd/0 Tainted: G W O 3.15.0-rc3 #213 +Hardware name: LENOVO 2776LEG/2776LEG, BIOS 6EET55WW (3.15 ) 12/19/2011 + 0000000000000001 ffff880232533bf0 ffffffff813a5ee6 0000000000000006 + ffff880232530090 ffff880232533c20 ffffffff81076b94 0000000000000081 + 0000000000000000 ffff8802085ac000 ffff88007fc8ea00 ffff880232533c50 +Call Trace: + [] dump_stack+0x4e/0x68 + [] lockdep_rcu_suspicious+0xfa/0x103 + [] __vlan_find_dev_deep+0x54/0x94 + [] cdc_mbim_rx_fixup+0x379/0x66a [cdc_mbim] + [] ? _raw_spin_unlock_irqrestore+0x3a/0x49 + [] ? trace_hardirqs_on_caller+0x192/0x1a1 + [] usbnet_bh+0x59/0x287 [usbnet] + [] tasklet_action+0xbb/0xcd + [] __do_softirq+0x14c/0x30d + [] run_ksoftirqd+0x1f/0x50 + [] smpboot_thread_fn+0x172/0x18e + [] ? SyS_setgroups+0xdf/0xdf + [] kthread+0xb5/0xbd + [] ? __wait_for_common+0x13b/0x170 + [] ? __kthread_parkme+0x5c/0x5c + [] ret_from_fork+0x7c/0xb0 + [] ? __kthread_parkme+0x5c/0x5c + +Fixes: 5b8f15f78e6f ("net: cdc_mbim: handle IPv6 Neigbor Solicitations") +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/cdc_mbim.c | 18 +++++++++++++----- + 1 file changed, 13 insertions(+), 5 deletions(-) + +--- a/drivers/net/usb/cdc_mbim.c ++++ b/drivers/net/usb/cdc_mbim.c +@@ -204,17 +204,23 @@ static void do_neigh_solicit(struct usbn + return; + + /* need to send the NA on the VLAN dev, if any */ +- if (tci) ++ rcu_read_lock(); ++ if (tci) { + netdev = __vlan_find_dev_deep(dev->net, htons(ETH_P_8021Q), + tci); +- else ++ if (!netdev) { ++ rcu_read_unlock(); ++ return; ++ } ++ } else { + netdev = dev->net; +- if (!netdev) +- return; ++ } ++ dev_hold(netdev); ++ rcu_read_unlock(); + + in6_dev = in6_dev_get(netdev); + if (!in6_dev) +- return; ++ goto out; + is_router = !!in6_dev->cnf.forwarding; + in6_dev_put(in6_dev); + +@@ -224,6 +230,8 @@ static void do_neigh_solicit(struct usbn + true /* solicited */, + false /* override */, + true /* inc_opt */); ++out: ++ dev_put(netdev); + } + + static bool is_neigh_solicit(u8 *buf, size_t len) diff --git a/queue-3.14/net-cdc_mbim-handle-unaccelerated-vlan-tagged-frames.patch b/queue-3.14/net-cdc_mbim-handle-unaccelerated-vlan-tagged-frames.patch new file mode 100644 index 00000000000..dbcd1be5a7d --- /dev/null +++ b/queue-3.14/net-cdc_mbim-handle-unaccelerated-vlan-tagged-frames.patch @@ -0,0 +1,108 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 9 May 2014 14:45:00 +0200 +Subject: net: cdc_mbim: handle unaccelerated VLAN tagged frames +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 6b5eeb7f874b689403e52a646e485d0191ab9507 ] + +This driver maps 802.1q VLANs to MBIM sessions. The mapping is based on +a bogus assumption that all tagged frames will use the acceleration API +because we enable NETIF_F_HW_VLAN_CTAG_TX. This fails for e.g. frames +tagged in userspace using packet sockets. Such frames will erroneously +be considered as untagged and silently dropped based on not being IP. + +Fix by falling back to looking into the ethernet header for a tag if no +accelerated tag was found. + +Fixes: a82c7ce5bc5b ("net: cdc_ncm: map MBIM IPS SessionID to VLAN ID") +Cc: Greg Suarez +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/cdc_mbim.c | 39 ++++++++++++++++++++++++++++----------- + 1 file changed, 28 insertions(+), 11 deletions(-) + +--- a/drivers/net/usb/cdc_mbim.c ++++ b/drivers/net/usb/cdc_mbim.c +@@ -120,6 +120,16 @@ static void cdc_mbim_unbind(struct usbne + cdc_ncm_unbind(dev, intf); + } + ++/* verify that the ethernet protocol is IPv4 or IPv6 */ ++static bool is_ip_proto(__be16 proto) ++{ ++ switch (proto) { ++ case htons(ETH_P_IP): ++ case htons(ETH_P_IPV6): ++ return true; ++ } ++ return false; ++} + + static struct sk_buff *cdc_mbim_tx_fixup(struct usbnet *dev, struct sk_buff *skb, gfp_t flags) + { +@@ -128,6 +138,7 @@ static struct sk_buff *cdc_mbim_tx_fixup + struct cdc_ncm_ctx *ctx = info->ctx; + __le32 sign = cpu_to_le32(USB_CDC_MBIM_NDP16_IPS_SIGN); + u16 tci = 0; ++ bool is_ip; + u8 *c; + + if (!ctx) +@@ -137,25 +148,32 @@ static struct sk_buff *cdc_mbim_tx_fixup + if (skb->len <= ETH_HLEN) + goto error; + ++ /* Some applications using e.g. packet sockets will ++ * bypass the VLAN acceleration and create tagged ++ * ethernet frames directly. We primarily look for ++ * the accelerated out-of-band tag, but fall back if ++ * required ++ */ ++ skb_reset_mac_header(skb); ++ if (vlan_get_tag(skb, &tci) < 0 && skb->len > VLAN_ETH_HLEN && ++ __vlan_get_tag(skb, &tci) == 0) { ++ is_ip = is_ip_proto(vlan_eth_hdr(skb)->h_vlan_encapsulated_proto); ++ skb_pull(skb, VLAN_ETH_HLEN); ++ } else { ++ is_ip = is_ip_proto(eth_hdr(skb)->h_proto); ++ skb_pull(skb, ETH_HLEN); ++ } ++ + /* mapping VLANs to MBIM sessions: + * no tag => IPS session <0> + * 1 - 255 => IPS session + * 256 - 511 => DSS session + * 512 - 4095 => unsupported, drop + */ +- vlan_get_tag(skb, &tci); +- + switch (tci & 0x0f00) { + case 0x0000: /* VLAN ID 0 - 255 */ +- /* verify that datagram is IPv4 or IPv6 */ +- skb_reset_mac_header(skb); +- switch (eth_hdr(skb)->h_proto) { +- case htons(ETH_P_IP): +- case htons(ETH_P_IPV6): +- break; +- default: ++ if (!is_ip) + goto error; +- } + c = (u8 *)&sign; + c[3] = tci; + break; +@@ -169,7 +187,6 @@ static struct sk_buff *cdc_mbim_tx_fixup + "unsupported tci=0x%04x\n", tci); + goto error; + } +- skb_pull(skb, ETH_HLEN); + } + + spin_lock_bh(&ctx->mtx); diff --git a/queue-3.14/net-cdc_ncm-fix-buffer-overflow.patch b/queue-3.14/net-cdc_ncm-fix-buffer-overflow.patch new file mode 100644 index 00000000000..bf607924f39 --- /dev/null +++ b/queue-3.14/net-cdc_ncm-fix-buffer-overflow.patch @@ -0,0 +1,44 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 2 May 2014 23:27:00 +0200 +Subject: net: cdc_ncm: fix buffer overflow +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 9becd707841207652449a8dfd90fe9c476d88546 ] + +Commit 4d619f625a60 ("net: cdc_ncm: no point in filling up the NTBs +if we send ZLPs") changed the padding logic for devices with the ZLP +flag set. This meant that frames of any size will be sent without +additional padding, except for the single byte added if the size is +a multiple of the USB packet size. But if the unpadded size is +identical to the maximum frame size, and the maximum size is a +multiplum of the USB packet size, then this one-byte padding will +overflow the buffer. + +Prevent padding if already at maximum frame size, letting usbnet +transmit a ZLP instead in this case. + +Fixes: 4d619f625a60 ("net: cdc_ncm: no point in filling up the NTBs if we send ZLPs") +Reported by: Yu-an Shih +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/cdc_ncm.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/net/usb/cdc_ncm.c ++++ b/drivers/net/usb/cdc_ncm.c +@@ -768,7 +768,7 @@ cdc_ncm_fill_tx_frame(struct usbnet *dev + skb_out->len > CDC_NCM_MIN_TX_PKT) + memset(skb_put(skb_out, ctx->tx_max - skb_out->len), 0, + ctx->tx_max - skb_out->len); +- else if ((skb_out->len % dev->maxpacket) == 0) ++ else if (skb_out->len < ctx->tx_max && (skb_out->len % dev->maxpacket) == 0) + *skb_put(skb_out, 1) = 0; /* force short packet */ + + /* set final frame length */ diff --git a/queue-3.14/net-core-don-t-account-for-udp-header-size-when-computing-seglen.patch b/queue-3.14/net-core-don-t-account-for-udp-header-size-when-computing-seglen.patch new file mode 100644 index 00000000000..7b9861f5e90 --- /dev/null +++ b/queue-3.14/net-core-don-t-account-for-udp-header-size-when-computing-seglen.patch @@ -0,0 +1,50 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Florian Westphal +Date: Wed, 9 Apr 2014 10:28:50 +0200 +Subject: net: core: don't account for udp header size when computing seglen + +From: Florian Westphal + +[ Upstream commit 6d39d589bb76ee8a1c6cde6822006ae0053decff ] + +In case of tcp, gso_size contains the tcpmss. + +For UFO (udp fragmentation offloading) skbs, gso_size is the fragment +payload size, i.e. we must not account for udp header size. + +Otherwise, when using virtio drivers, a to-be-forwarded UFO GSO packet +will be needlessly fragmented in the forward path, because we think its +individual segments are too large for the outgoing link. + +Fixes: fe6cc55f3a9a053 ("net: ip, ipv6: handle gso skbs in forwarding path") +Cc: Eric Dumazet +Reported-by: Tobias Brunner +Signed-off-by: Florian Westphal +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/skbuff.c | 12 +++++++----- + 1 file changed, 7 insertions(+), 5 deletions(-) + +--- a/net/core/skbuff.c ++++ b/net/core/skbuff.c +@@ -3951,12 +3951,14 @@ EXPORT_SYMBOL_GPL(skb_scrub_packet); + unsigned int skb_gso_transport_seglen(const struct sk_buff *skb) + { + const struct skb_shared_info *shinfo = skb_shinfo(skb); +- unsigned int hdr_len; + + if (likely(shinfo->gso_type & (SKB_GSO_TCPV4 | SKB_GSO_TCPV6))) +- hdr_len = tcp_hdrlen(skb); +- else +- hdr_len = sizeof(struct udphdr); +- return hdr_len + shinfo->gso_size; ++ return tcp_hdrlen(skb) + shinfo->gso_size; ++ ++ /* UFO sets gso_size to the size of the fragmentation ++ * payload, i.e. the size of the L4 (UDP) header is already ++ * accounted for. ++ */ ++ return shinfo->gso_size; + } + EXPORT_SYMBOL_GPL(skb_gso_transport_seglen); diff --git a/queue-3.14/net-filter-s390-fix-jit-address-randomization.patch b/queue-3.14/net-filter-s390-fix-jit-address-randomization.patch new file mode 100644 index 00000000000..e924126a082 --- /dev/null +++ b/queue-3.14/net-filter-s390-fix-jit-address-randomization.patch @@ -0,0 +1,62 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Heiko Carstens +Date: Wed, 14 May 2014 09:48:21 +0200 +Subject: net: filter: s390: fix JIT address randomization + +From: Heiko Carstens + +[ Upstream commit e84d2f8d2ae33c8215429824e1ecf24cbca9645e ] + +This is the s390 variant of Alexei's JIT bug fix. +(patch description below stolen from Alexei's patch) + +bpf_alloc_binary() adds 128 bytes of room to JITed program image +and rounds it up to the nearest page size. If image size is close +to page size (like 4000), it is rounded to two pages: +round_up(4000 + 4 + 128) == 8192 +then 'hole' is computed as 8192 - (4000 + 4) = 4188 +If prandom_u32() % hole selects a number >= PAGE_SIZE - sizeof(*header) +then kernel will crash during bpf_jit_free(): + +kernel BUG at arch/x86/mm/pageattr.c:887! +Call Trace: + [] change_page_attr_set_clr+0x135/0x460 + [] ? _raw_spin_unlock_irq+0x30/0x50 + [] set_memory_rw+0x2f/0x40 + [] bpf_jit_free_deferred+0x2d/0x60 + [] process_one_work+0x1d8/0x6a0 + [] ? process_one_work+0x178/0x6a0 + [] worker_thread+0x11c/0x370 + +since bpf_jit_free() does: + unsigned long addr = (unsigned long)fp->bpf_func & PAGE_MASK; + struct bpf_binary_header *header = (void *)addr; +to compute start address of 'bpf_binary_header' +and header->pages will pass junk to: + set_memory_rw(addr, header->pages); + +Fix it by making sure that &header->image[prandom_u32() % hole] and &header +are in the same page. + +Fixes: aa2d2c73c21f2 ("s390/bpf,jit: address randomize and write protect jit code") + +Reported-by: Alexei Starovoitov +Cc: # v3.11+ +Signed-off-by: Heiko Carstens +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + arch/s390/net/bpf_jit_comp.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/arch/s390/net/bpf_jit_comp.c ++++ b/arch/s390/net/bpf_jit_comp.c +@@ -811,7 +811,7 @@ static struct bpf_binary_header *bpf_all + return NULL; + memset(header, 0, sz); + header->pages = sz / PAGE_SIZE; +- hole = sz - (bpfsize + sizeof(*header)); ++ hole = min(sz - (bpfsize + sizeof(*header)), PAGE_SIZE - sizeof(*header)); + /* Insert random number of illegal instructions before BPF code + * and make sure the first instruction starts at an even address. + */ diff --git a/queue-3.14/net-filter-x86-fix-jit-address-randomization.patch b/queue-3.14/net-filter-x86-fix-jit-address-randomization.patch new file mode 100644 index 00000000000..9240b8f4844 --- /dev/null +++ b/queue-3.14/net-filter-x86-fix-jit-address-randomization.patch @@ -0,0 +1,57 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Alexei Starovoitov +Date: Tue, 13 May 2014 15:05:55 -0700 +Subject: net: filter: x86: fix JIT address randomization + +From: Alexei Starovoitov + +[ Upstream commit 773cd38f40b8834be991dbfed36683acc1dd41ee ] + +bpf_alloc_binary() adds 128 bytes of room to JITed program image +and rounds it up to the nearest page size. If image size is close +to page size (like 4000), it is rounded to two pages: +round_up(4000 + 4 + 128) == 8192 +then 'hole' is computed as 8192 - (4000 + 4) = 4188 +If prandom_u32() % hole selects a number >= PAGE_SIZE - sizeof(*header) +then kernel will crash during bpf_jit_free(): + +kernel BUG at arch/x86/mm/pageattr.c:887! +Call Trace: + [] change_page_attr_set_clr+0x135/0x460 + [] ? _raw_spin_unlock_irq+0x30/0x50 + [] set_memory_rw+0x2f/0x40 + [] bpf_jit_free_deferred+0x2d/0x60 + [] process_one_work+0x1d8/0x6a0 + [] ? process_one_work+0x178/0x6a0 + [] worker_thread+0x11c/0x370 + +since bpf_jit_free() does: + unsigned long addr = (unsigned long)fp->bpf_func & PAGE_MASK; + struct bpf_binary_header *header = (void *)addr; +to compute start address of 'bpf_binary_header' +and header->pages will pass junk to: + set_memory_rw(addr, header->pages); + +Fix it by making sure that &header->image[prandom_u32() % hole] and &header +are in the same page + +Fixes: 314beb9bcabfd ("x86: bpf_jit_comp: secure bpf jit against spraying attacks") +Signed-off-by: Alexei Starovoitov +Acked-by: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + arch/x86/net/bpf_jit_comp.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/arch/x86/net/bpf_jit_comp.c ++++ b/arch/x86/net/bpf_jit_comp.c +@@ -171,7 +171,7 @@ static struct bpf_binary_header *bpf_all + memset(header, 0xcc, sz); /* fill whole space with int3 instructions */ + + header->pages = sz / PAGE_SIZE; +- hole = sz - (proglen + sizeof(*header)); ++ hole = min(sz - (proglen + sizeof(*header)), PAGE_SIZE - sizeof(*header)); + + /* insert a random number of int3 instructions before BPF code */ + *image_ptr = &header->image[prandom_u32() % hole]; diff --git a/queue-3.14/net-find-the-nesting-level-of-a-given-device-by-type.patch b/queue-3.14/net-find-the-nesting-level-of-a-given-device-by-type.patch new file mode 100644 index 00000000000..02164f4a00e --- /dev/null +++ b/queue-3.14/net-find-the-nesting-level-of-a-given-device-by-type.patch @@ -0,0 +1,121 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Fri, 16 May 2014 17:04:53 -0400 +Subject: net: Find the nesting level of a given device by type. + +From: Vlad Yasevich + +[ Upstream commit 4085ebe8c31face855fd01ee40372cb4aab1df3a ] + +Multiple devices in the kernel can be stacked/nested and they +need to know their nesting level for the purposes of lockdep. +This patch provides a generic function that determines a nesting +level of a particular device by its type (ex: vlan, macvlan, etc). +We only care about nesting of the same type of devices. + +For example: + eth0 <- vlan0.10 <- macvlan0 <- vlan1.20 + +The nesting level of vlan1.20 would be 1, since there is another vlan +in the stack under it. + +Signed-off-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/netdevice.h | 10 +++++++++ + net/core/dev.c | 50 ++++++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 60 insertions(+) + +--- a/include/linux/netdevice.h ++++ b/include/linux/netdevice.h +@@ -2988,6 +2988,14 @@ void *netdev_lower_get_next_private_rcu( + priv; \ + priv = netdev_lower_get_next_private_rcu(dev, &(iter))) + ++void *netdev_lower_get_next(struct net_device *dev, ++ struct list_head **iter); ++#define netdev_for_each_lower_dev(dev, ldev, iter) \ ++ for (iter = &(dev)->adj_list.lower, \ ++ ldev = netdev_lower_get_next(dev, &(iter)); \ ++ ldev; \ ++ ldev = netdev_lower_get_next(dev, &(iter))) ++ + void *netdev_adjacent_get_private(struct list_head *adj_list); + void *netdev_lower_get_first_private_rcu(struct net_device *dev); + struct net_device *netdev_master_upper_dev_get(struct net_device *dev); +@@ -3003,6 +3011,8 @@ void netdev_upper_dev_unlink(struct net_ + void netdev_adjacent_rename_links(struct net_device *dev, char *oldname); + void *netdev_lower_dev_get_private(struct net_device *dev, + struct net_device *lower_dev); ++int dev_get_nest_level(struct net_device *dev, ++ bool (*type_check)(struct net_device *dev)); + int skb_checksum_help(struct sk_buff *skb); + struct sk_buff *__skb_gso_segment(struct sk_buff *skb, + netdev_features_t features, bool tx_path); +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -4605,6 +4605,32 @@ void *netdev_lower_get_next_private_rcu( + EXPORT_SYMBOL(netdev_lower_get_next_private_rcu); + + /** ++ * netdev_lower_get_next - Get the next device from the lower neighbour ++ * list ++ * @dev: device ++ * @iter: list_head ** of the current position ++ * ++ * Gets the next netdev_adjacent from the dev's lower neighbour ++ * list, starting from iter position. The caller must hold RTNL lock or ++ * its own locking that guarantees that the neighbour lower ++ * list will remain unchainged. ++ */ ++void *netdev_lower_get_next(struct net_device *dev, struct list_head **iter) ++{ ++ struct netdev_adjacent *lower; ++ ++ lower = list_entry((*iter)->next, struct netdev_adjacent, list); ++ ++ if (&lower->list == &dev->adj_list.lower) ++ return NULL; ++ ++ *iter = &lower->list; ++ ++ return lower->dev; ++} ++EXPORT_SYMBOL(netdev_lower_get_next); ++ ++/** + * netdev_lower_get_first_private_rcu - Get the first ->private from the + * lower neighbour list, RCU + * variant +@@ -5054,6 +5080,30 @@ void *netdev_lower_dev_get_private(struc + } + EXPORT_SYMBOL(netdev_lower_dev_get_private); + ++ ++int dev_get_nest_level(struct net_device *dev, ++ bool (*type_check)(struct net_device *dev)) ++{ ++ struct net_device *lower = NULL; ++ struct list_head *iter; ++ int max_nest = -1; ++ int nest; ++ ++ ASSERT_RTNL(); ++ ++ netdev_for_each_lower_dev(dev, lower, iter) { ++ nest = dev_get_nest_level(lower, type_check); ++ if (max_nest < nest) ++ max_nest = nest; ++ } ++ ++ if (type_check(dev)) ++ max_nest++; ++ ++ return max_nest; ++} ++EXPORT_SYMBOL(dev_get_nest_level); ++ + static void dev_change_rx_flags(struct net_device *dev, int flags) + { + const struct net_device_ops *ops = dev->netdev_ops; diff --git a/queue-3.14/net-fix-ns_capable-check-in-sock_diag_put_filterinfo.patch b/queue-3.14/net-fix-ns_capable-check-in-sock_diag_put_filterinfo.patch new file mode 100644 index 00000000000..b84a5573236 --- /dev/null +++ b/queue-3.14/net-fix-ns_capable-check-in-sock_diag_put_filterinfo.patch @@ -0,0 +1,66 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Andrew Lutomirski +Date: Wed, 16 Apr 2014 21:41:34 -0700 +Subject: net: Fix ns_capable check in sock_diag_put_filterinfo + +From: Andrew Lutomirski + +[ Upstream commit 78541c1dc60b65ecfce5a6a096fc260219d6784e ] + +The caller needs capabilities on the namespace being queried, not on +their own namespace. This is a security bug, although it likely has +only a minor impact. + +Cc: stable@vger.kernel.org +Signed-off-by: Andy Lutomirski +Acked-by: Nicolas Dichtel +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/sock_diag.h | 2 +- + net/core/sock_diag.c | 4 ++-- + net/packet/diag.c | 2 +- + 3 files changed, 4 insertions(+), 4 deletions(-) + +--- a/include/linux/sock_diag.h ++++ b/include/linux/sock_diag.h +@@ -23,7 +23,7 @@ int sock_diag_check_cookie(void *sk, __u + void sock_diag_save_cookie(void *sk, __u32 *cookie); + + int sock_diag_put_meminfo(struct sock *sk, struct sk_buff *skb, int attr); +-int sock_diag_put_filterinfo(struct user_namespace *user_ns, struct sock *sk, ++int sock_diag_put_filterinfo(struct sock *sk, + struct sk_buff *skb, int attrtype); + + #endif +--- a/net/core/sock_diag.c ++++ b/net/core/sock_diag.c +@@ -49,7 +49,7 @@ int sock_diag_put_meminfo(struct sock *s + } + EXPORT_SYMBOL_GPL(sock_diag_put_meminfo); + +-int sock_diag_put_filterinfo(struct user_namespace *user_ns, struct sock *sk, ++int sock_diag_put_filterinfo(struct sock *sk, + struct sk_buff *skb, int attrtype) + { + struct nlattr *attr; +@@ -57,7 +57,7 @@ int sock_diag_put_filterinfo(struct user + unsigned int len; + int err = 0; + +- if (!ns_capable(user_ns, CAP_NET_ADMIN)) { ++ if (!ns_capable(sock_net(sk)->user_ns, CAP_NET_ADMIN)) { + nla_reserve(skb, attrtype, 0); + return 0; + } +--- a/net/packet/diag.c ++++ b/net/packet/diag.c +@@ -172,7 +172,7 @@ static int sk_diag_fill(struct sock *sk, + goto out_nlmsg_trim; + + if ((req->pdiag_show & PACKET_SHOW_FILTER) && +- sock_diag_put_filterinfo(user_ns, sk, skb, PACKET_DIAG_FILTER)) ++ sock_diag_put_filterinfo(sk, skb, PACKET_DIAG_FILTER)) + goto out_nlmsg_trim; + + return nlmsg_end(skb, nlh); diff --git a/queue-3.14/net-gro-make-sure-skb-cb-initial-content-has-not.patch b/queue-3.14/net-gro-make-sure-skb-cb-initial-content-has-not.patch new file mode 100644 index 00000000000..3d020d6d360 --- /dev/null +++ b/queue-3.14/net-gro-make-sure-skb-cb-initial-content-has-not.patch @@ -0,0 +1,67 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Eric Dumazet +Date: Fri, 16 May 2014 11:34:37 -0700 +Subject: net: gro: make sure skb->cb[] initial content has not + to be zero +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Eric Dumazet + +[ Upstream commit 29e98242783ed3ba569797846a606ba66f781625 ] + +Starting from linux-3.13, GRO attempts to build full size skbs. + +Problem is the commit assumed one particular field in skb->cb[] +was clean, but it is not the case on some stacked devices. + +Timo reported a crash in case traffic is decrypted before +reaching a GRE device. + +Fix this by initializing NAPI_GRO_CB(skb)->last at the right place, +this also removes one conditional. + +Thanks a lot to Timo for providing full reports and bisecting this. + +Fixes: 8a29111c7ca6 ("net: gro: allow to build full sized skb") +Bisected-by: Timo Teras +Signed-off-by: Eric Dumazet +Tested-by: Timo Teräs +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/dev.c | 1 + + net/core/skbuff.c | 4 ++-- + 2 files changed, 3 insertions(+), 2 deletions(-) + +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -3944,6 +3944,7 @@ static enum gro_result dev_gro_receive(s + } + NAPI_GRO_CB(skb)->count = 1; + NAPI_GRO_CB(skb)->age = jiffies; ++ NAPI_GRO_CB(skb)->last = skb; + skb_shinfo(skb)->gso_size = skb_gro_len(skb); + skb->next = napi->gro_list; + napi->gro_list = skb; +--- a/net/core/skbuff.c ++++ b/net/core/skbuff.c +@@ -3076,7 +3076,7 @@ int skb_gro_receive(struct sk_buff **hea + if (unlikely(p->len + len >= 65536)) + return -E2BIG; + +- lp = NAPI_GRO_CB(p)->last ?: p; ++ lp = NAPI_GRO_CB(p)->last; + pinfo = skb_shinfo(lp); + + if (headlen <= offset) { +@@ -3192,7 +3192,7 @@ merge: + + __skb_pull(skb, offset); + +- if (!NAPI_GRO_CB(p)->last) ++ if (NAPI_GRO_CB(p)->last == p) + skb_shinfo(p)->frag_list = skb; + else + NAPI_GRO_CB(p)->last->next = skb; diff --git a/queue-3.14/net-gro-reset-skb-truesize-in-napi_reuse_skb.patch b/queue-3.14/net-gro-reset-skb-truesize-in-napi_reuse_skb.patch new file mode 100644 index 00000000000..7b756450d3d --- /dev/null +++ b/queue-3.14/net-gro-reset-skb-truesize-in-napi_reuse_skb.patch @@ -0,0 +1,39 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Eric Dumazet +Date: Thu, 3 Apr 2014 09:28:10 -0700 +Subject: net-gro: reset skb->truesize in napi_reuse_skb() + +From: Eric Dumazet + +[ Upstream commit e33d0ba8047b049c9262fdb1fcafb93cb52ceceb ] + +Recycling skb always had been very tough... + +This time it appears GRO layer can accumulate skb->truesize +adjustments made by drivers when they attach a fragment to skb. + +skb_gro_receive() can only subtract from skb->truesize the used part +of a fragment. + +I spotted this problem seeing TcpExtPruneCalled and +TcpExtTCPRcvCollapsed that were unexpected with a recent kernel, where +TCP receive window should be sized properly to accept traffic coming +from a driver not overshooting skb->truesize. + +Signed-off-by: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/dev.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -4051,6 +4051,7 @@ static void napi_reuse_skb(struct napi_s + skb->vlan_tci = 0; + skb->dev = napi->dev; + skb->skb_iif = 0; ++ skb->truesize = SKB_TRUESIZE(skb_end_offset(skb)); + + napi->skb = skb; + } diff --git a/queue-3.14/net-ipv4-current-group_info-should-be-put-after-using.patch b/queue-3.14/net-ipv4-current-group_info-should-be-put-after-using.patch new file mode 100644 index 00000000000..e6a73cc329a --- /dev/null +++ b/queue-3.14/net-ipv4-current-group_info-should-be-put-after-using.patch @@ -0,0 +1,64 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: "Wang, Xiaoming" +Date: Mon, 14 Apr 2014 12:30:45 -0400 +Subject: net: ipv4: current group_info should be put after using. + +From: "Wang, Xiaoming" + +[ Upstream commit b04c46190219a4f845e46a459e3102137b7f6cac ] + +Plug a group_info refcount leak in ping_init. +group_info is only needed during initialization and +the code failed to release the reference on exit. +While here move grabbing the reference to a place +where it is actually needed. + +Signed-off-by: Chuansheng Liu +Signed-off-by: Zhang Dongxing +Signed-off-by: xiaoming wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ping.c | 15 +++++++++++---- + 1 file changed, 11 insertions(+), 4 deletions(-) + +--- a/net/ipv4/ping.c ++++ b/net/ipv4/ping.c +@@ -252,26 +252,33 @@ int ping_init_sock(struct sock *sk) + { + struct net *net = sock_net(sk); + kgid_t group = current_egid(); +- struct group_info *group_info = get_current_groups(); +- int i, j, count = group_info->ngroups; ++ struct group_info *group_info; ++ int i, j, count; + kgid_t low, high; ++ int ret = 0; + + inet_get_ping_group_range_net(net, &low, &high); + if (gid_lte(low, group) && gid_lte(group, high)) + return 0; + ++ group_info = get_current_groups(); ++ count = group_info->ngroups; + for (i = 0; i < group_info->nblocks; i++) { + int cp_count = min_t(int, NGROUPS_PER_BLOCK, count); + for (j = 0; j < cp_count; j++) { + kgid_t gid = group_info->blocks[i][j]; + if (gid_lte(low, gid) && gid_lte(gid, high)) +- return 0; ++ goto out_release_group; + } + + count -= cp_count; + } + +- return -EACCES; ++ ret = -EACCES; ++ ++out_release_group: ++ put_group_info(group_info); ++ return ret; + } + EXPORT_SYMBOL_GPL(ping_init_sock); + diff --git a/queue-3.14/net-ipv4-ip_forward-fix-inverted-local_df-test.patch b/queue-3.14/net-ipv4-ip_forward-fix-inverted-local_df-test.patch new file mode 100644 index 00000000000..d53bc0b99a8 --- /dev/null +++ b/queue-3.14/net-ipv4-ip_forward-fix-inverted-local_df-test.patch @@ -0,0 +1,47 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Florian Westphal +Date: Sun, 4 May 2014 23:24:31 +0200 +Subject: net: ipv4: ip_forward: fix inverted local_df test + +From: Florian Westphal + +[ Upstream commit ca6c5d4ad216d5942ae544bbf02503041bd802aa ] + +local_df means 'ignore DF bit if set', so if its set we're +allowed to perform ip fragmentation. + +This wasn't noticed earlier because the output path also drops such skbs +(and emits needed icmp error) and because netfilter ip defrag did not +set local_df until couple of days ago. + +Only difference is that DF-packets-larger-than MTU now discarded +earlier (f.e. we avoid pointless netfilter postrouting trip). + +While at it, drop the repeated test ip_exceeds_mtu, checking it once +is enough... + +Fixes: fe6cc55f3a9 ("net: ip, ipv6: handle gso skbs in forwarding path") +Signed-off-by: Florian Westphal +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_forward.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/net/ipv4/ip_forward.c ++++ b/net/ipv4/ip_forward.c +@@ -42,12 +42,12 @@ + static bool ip_may_fragment(const struct sk_buff *skb) + { + return unlikely((ip_hdr(skb)->frag_off & htons(IP_DF)) == 0) || +- !skb->local_df; ++ skb->local_df; + } + + static bool ip_exceeds_mtu(const struct sk_buff *skb, unsigned int mtu) + { +- if (skb->len <= mtu || skb->local_df) ++ if (skb->len <= mtu) + return false; + + if (skb_is_gso(skb) && skb_gso_network_seglen(skb) <= mtu) diff --git a/queue-3.14/net-ipv6-send-pkttoobig-immediately-if-orig-frag.patch b/queue-3.14/net-ipv6-send-pkttoobig-immediately-if-orig-frag.patch new file mode 100644 index 00000000000..de9f8610bf5 --- /dev/null +++ b/queue-3.14/net-ipv6-send-pkttoobig-immediately-if-orig-frag.patch @@ -0,0 +1,50 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Florian Westphal +Date: Mon, 5 May 2014 00:03:34 +0200 +Subject: net: ipv6: send pkttoobig immediately if orig frag + size > mtu + +From: Florian Westphal + +[ Upstream commit 418a31561d594a2b636c1e2fa94ecd9e1245abb1 ] + +If conntrack defragments incoming ipv6 frags it stores largest original +frag size in ip6cb and sets ->local_df. + +We must thus first test the largest original frag size vs. mtu, and not +vice versa. + +Without this patch PKTTOOBIG is still generated in ip6_fragment() later +in the stack, but + +1) IPSTATS_MIB_INTOOBIGERRORS won't increment +2) packet did (needlessly) traverse netfilter postrouting hook. + +Fixes: fe6cc55f3a9 ("net: ip, ipv6: handle gso skbs in forwarding path") +Signed-off-by: Florian Westphal +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv6/ip6_output.c | 6 +++++- + 1 file changed, 5 insertions(+), 1 deletion(-) + +--- a/net/ipv6/ip6_output.c ++++ b/net/ipv6/ip6_output.c +@@ -344,12 +344,16 @@ static unsigned int ip6_dst_mtu_forward( + + static bool ip6_pkt_too_big(const struct sk_buff *skb, unsigned int mtu) + { +- if (skb->len <= mtu || skb->local_df) ++ if (skb->len <= mtu) + return false; + ++ /* ipv6 conntrack defrag sets max_frag_size + local_df */ + if (IP6CB(skb)->frag_max_size && IP6CB(skb)->frag_max_size > mtu) + return true; + ++ if (skb->local_df) ++ return false; ++ + if (skb_is_gso(skb) && skb_gso_network_seglen(skb) <= mtu) + return false; + diff --git a/queue-3.14/net-mlx4_core-don-t-issue-pcie-speed-width-checks-for.patch b/queue-3.14/net-mlx4_core-don-t-issue-pcie-speed-width-checks-for.patch new file mode 100644 index 00000000000..d2fc2115f99 --- /dev/null +++ b/queue-3.14/net-mlx4_core-don-t-issue-pcie-speed-width-checks-for.patch @@ -0,0 +1,34 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Eyal Perry +Date: Sun, 4 May 2014 17:07:25 +0300 +Subject: net/mlx4_core: Don't issue PCIe speed/width checks for + VFs + +From: Eyal Perry + +[ Upstream commit 83d3459a5928f18c9344683e31bc2a7c3c25562a ] + +Carrying out PCI speed/width checks through pcie_get_minimum_link() +on VFs yield wrong results, so remove them. + +Fixes: b912b2f ('net/mlx4_core: Warn if device doesn't have enough PCI bandwidth') +Signed-off-by: Eyal Perry +Signed-off-by: Or Gerlitz +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/ethernet/mellanox/mlx4/main.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/drivers/net/ethernet/mellanox/mlx4/main.c ++++ b/drivers/net/ethernet/mellanox/mlx4/main.c +@@ -2399,7 +2399,8 @@ slave_start: + * No return code for this call, just warn the user in case of PCI + * express device capabilities are under-satisfied by the bus. + */ +- mlx4_check_pcie_caps(dev); ++ if (!mlx4_is_slave(dev)) ++ mlx4_check_pcie_caps(dev); + + /* In master functions, the communication channel must be initialized + * after obtaining its address from fw */ diff --git a/queue-3.14/net-phy-don-t-call-phy_resume-if-phy_init_hw-failed.patch b/queue-3.14/net-phy-don-t-call-phy_resume-if-phy_init_hw-failed.patch new file mode 100644 index 00000000000..aa53721cfae --- /dev/null +++ b/queue-3.14/net-phy-don-t-call-phy_resume-if-phy_init_hw-failed.patch @@ -0,0 +1,49 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Guenter Roeck +Date: Wed, 14 May 2014 13:12:49 -0700 +Subject: net: phy: Don't call phy_resume if phy_init_hw failed + +From: Guenter Roeck + +[ Upstream commit b394745df2d9d4c30bf1bcc55773bec6f3bc7c67 ] + +After the call to phy_init_hw failed in phy_attach_direct, phy_detach is called +to detach the phy device from its network device. If the attached driver is a +generic phy driver, this also detaches the driver. Subsequently phy_resume +is called, which assumes without checking that a driver is attached to the +device. This will result in a crash such as + +Unable to handle kernel paging request for data at address 0xffffffffffffff90 +Faulting instruction address: 0xc0000000003a0e18 +Oops: Kernel access of bad area, sig: 11 [#1] +... +NIP [c0000000003a0e18] .phy_attach_direct+0x68/0x17c +LR [c0000000003a0e6c] .phy_attach_direct+0xbc/0x17c +Call Trace: +[c0000003fc0475d0] [c0000000003a0e6c] .phy_attach_direct+0xbc/0x17c (unreliable) +[c0000003fc047670] [c0000000003a0ff8] .phy_connect_direct+0x28/0x98 +[c0000003fc047700] [c0000000003f0074] .of_phy_connect+0x4c/0xa4 + +Only call phy_resume if phy_init_hw was successful. + +Signed-off-by: Guenter Roeck +Acked-by: Florian Fainelli +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/phy/phy_device.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/drivers/net/phy/phy_device.c ++++ b/drivers/net/phy/phy_device.c +@@ -613,8 +613,8 @@ int phy_attach_direct(struct net_device + err = phy_init_hw(phydev); + if (err) + phy_detach(phydev); +- +- phy_resume(phydev); ++ else ++ phy_resume(phydev); + + return err; + } diff --git a/queue-3.14/net-qmi_wwan-add-a-number-of-cmotech-devices.patch b/queue-3.14/net-qmi_wwan-add-a-number-of-cmotech-devices.patch new file mode 100644 index 00000000000..df8479dad90 --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-a-number-of-cmotech-devices.patch @@ -0,0 +1,48 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:33 +0200 +Subject: net: qmi_wwan: add a number of CMOTech devices +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 41be7d90993b1502d445bfc59e58348c258ce66a ] + +A number of older CMOTech modems are based on Qualcomm +chips and exporting a QMI/wwan function. + +Reported-by: Lars Melin +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 16 ++++++++++++++++ + 1 file changed, 16 insertions(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -662,6 +662,22 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x05c6, 0x920d, 5)}, + {QMI_FIXED_INTF(0x12d1, 0x140c, 1)}, /* Huawei E173 */ + {QMI_FIXED_INTF(0x12d1, 0x14ac, 1)}, /* Huawei E1820 */ ++ {QMI_FIXED_INTF(0x16d8, 0x6003, 0)}, /* CMOTech 6003 */ ++ {QMI_FIXED_INTF(0x16d8, 0x6007, 0)}, /* CMOTech CHE-628S */ ++ {QMI_FIXED_INTF(0x16d8, 0x6008, 0)}, /* CMOTech CMU-301 */ ++ {QMI_FIXED_INTF(0x16d8, 0x6280, 0)}, /* CMOTech CHU-628 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7001, 0)}, /* CMOTech CHU-720S */ ++ {QMI_FIXED_INTF(0x16d8, 0x7002, 0)}, /* CMOTech 7002 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7003, 4)}, /* CMOTech CHU-629K */ ++ {QMI_FIXED_INTF(0x16d8, 0x7004, 3)}, /* CMOTech 7004 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7006, 5)}, /* CMOTech CGU-629 */ ++ {QMI_FIXED_INTF(0x16d8, 0x700a, 4)}, /* CMOTech CHU-629S */ ++ {QMI_FIXED_INTF(0x16d8, 0x7211, 0)}, /* CMOTech CHU-720I */ ++ {QMI_FIXED_INTF(0x16d8, 0x7212, 0)}, /* CMOTech 7212 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7213, 0)}, /* CMOTech 7213 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7251, 1)}, /* CMOTech 7251 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7252, 1)}, /* CMOTech 7252 */ ++ {QMI_FIXED_INTF(0x16d8, 0x7253, 1)}, /* CMOTech 7253 */ + {QMI_FIXED_INTF(0x19d2, 0x0002, 1)}, + {QMI_FIXED_INTF(0x19d2, 0x0012, 1)}, + {QMI_FIXED_INTF(0x19d2, 0x0017, 3)}, diff --git a/queue-3.14/net-qmi_wwan-add-a-number-of-dell-devices.patch b/queue-3.14/net-qmi_wwan-add-a-number-of-dell-devices.patch new file mode 100644 index 00000000000..b3cb257ac58 --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-a-number-of-dell-devices.patch @@ -0,0 +1,55 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:34 +0200 +Subject: net: qmi_wwan: add a number of Dell devices +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 6f10c5d1b1aeddb63d33070abb8bc5a177beeb1f ] + +Dan writes: + +"The Dell drivers use the same configuration for PIDs: + +81A2: Dell Wireless 5806 Gobi(TM) 4G LTE Mobile Broadband Card +81A3: Dell Wireless 5570 HSPA+ (42Mbps) Mobile Broadband Card +81A4: Dell Wireless 5570e HSPA+ (42Mbps) Mobile Broadband Card +81A8: Dell Wireless 5808 Gobi(TM) 4G LTE Mobile Broadband Card +81A9: Dell Wireless 5808e Gobi(TM) 4G LTE Mobile Broadband Card + +These devices are all clearly Sierra devices, but are also definitely +Gobi-based. The A8 might be the MC7700/7710 and A9 is likely a MC7750. + +>From DellGobi5kSetup.exe from the Dell drivers: + +usbif0: serial/firmware loader? +usbif2: nmea +usbif3: modem/ppp +usbif8: net/QMI" + +Reported-by: AceLan Kao +Reported-by: Dan Williams +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 5 +++++ + 1 file changed, 5 insertions(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -756,6 +756,11 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x0b3c, 0xc00b, 4)}, /* Olivetti Olicard 500 */ + {QMI_FIXED_INTF(0x1e2d, 0x0060, 4)}, /* Cinterion PLxx */ + {QMI_FIXED_INTF(0x1e2d, 0x0053, 4)}, /* Cinterion PHxx,PXxx */ ++ {QMI_FIXED_INTF(0x413c, 0x81a2, 8)}, /* Dell Wireless 5806 Gobi(TM) 4G LTE Mobile Broadband Card */ ++ {QMI_FIXED_INTF(0x413c, 0x81a3, 8)}, /* Dell Wireless 5570 HSPA+ (42Mbps) Mobile Broadband Card */ ++ {QMI_FIXED_INTF(0x413c, 0x81a4, 8)}, /* Dell Wireless 5570e HSPA+ (42Mbps) Mobile Broadband Card */ ++ {QMI_FIXED_INTF(0x413c, 0x81a8, 8)}, /* Dell Wireless 5808 Gobi(TM) 4G LTE Mobile Broadband Card */ ++ {QMI_FIXED_INTF(0x413c, 0x81a9, 8)}, /* Dell Wireless 5808e Gobi(TM) 4G LTE Mobile Broadband Card */ + + /* 4. Gobi 1000 devices */ + {QMI_GOBI1K_DEVICE(0x05c6, 0x9212)}, /* Acer Gobi Modem Device */ diff --git a/queue-3.14/net-qmi_wwan-add-alcatel-l800ma.patch b/queue-3.14/net-qmi_wwan-add-alcatel-l800ma.patch new file mode 100644 index 00000000000..c9fd8c0e2e6 --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-alcatel-l800ma.patch @@ -0,0 +1,35 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:32 +0200 +Subject: net: qmi_wwan: add Alcatel L800MA +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 75573660c47a0db7cc931dcf154945610e02130a ] + +Device interface layout: +0: ff/ff/ff - serial +1: ff/00/00 - serial AT+PPP +2: ff/ff/ff - QMI/wwan +3: 08/06/50 - storage + +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -731,6 +731,7 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x1199, 0x9041, 8)}, /* Sierra Wireless MC7305/MC7355 */ + {QMI_FIXED_INTF(0x1199, 0x9051, 8)}, /* Netgear AirCard 340U */ + {QMI_FIXED_INTF(0x1bbb, 0x011e, 4)}, /* Telekom Speedstick LTE II (Alcatel One Touch L100V LTE) */ ++ {QMI_FIXED_INTF(0x1bbb, 0x0203, 2)}, /* Alcatel L800MA */ + {QMI_FIXED_INTF(0x2357, 0x0201, 4)}, /* TP-LINK HSUPA Modem MA180 */ + {QMI_FIXED_INTF(0x2357, 0x9000, 4)}, /* TP-LINK MA260 */ + {QMI_FIXED_INTF(0x1bc7, 0x1200, 5)}, /* Telit LE920 */ diff --git a/queue-3.14/net-qmi_wwan-add-olivetti-olicard-500.patch b/queue-3.14/net-qmi_wwan-add-olivetti-olicard-500.patch new file mode 100644 index 00000000000..7fcac42fd1a --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-olivetti-olicard-500.patch @@ -0,0 +1,37 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:31 +0200 +Subject: net: qmi_wwan: add Olivetti Olicard 500 +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit efc0b25c3add97717ece57bf5319792ca98f348e ] + +Device interface layout: +0: ff/ff/ff - serial +1: ff/ff/ff - serial AT+PPP +2: 08/06/50 - storage +3: ff/ff/ff - serial +4: ff/ff/ff - QMI/wwan + +Reported-by: Julio Araujo +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -736,6 +736,7 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x1bc7, 0x1200, 5)}, /* Telit LE920 */ + {QMI_FIXED_INTF(0x1bc7, 0x1201, 2)}, /* Telit LE920 */ + {QMI_FIXED_INTF(0x0b3c, 0xc005, 6)}, /* Olivetti Olicard 200 */ ++ {QMI_FIXED_INTF(0x0b3c, 0xc00b, 4)}, /* Olivetti Olicard 500 */ + {QMI_FIXED_INTF(0x1e2d, 0x0060, 4)}, /* Cinterion PLxx */ + {QMI_FIXED_INTF(0x1e2d, 0x0053, 4)}, /* Cinterion PHxx,PXxx */ + diff --git a/queue-3.14/net-qmi_wwan-add-sierra-wireless-em7355.patch b/queue-3.14/net-qmi_wwan-add-sierra-wireless-em7355.patch new file mode 100644 index 00000000000..93ff7583b24 --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-sierra-wireless-em7355.patch @@ -0,0 +1,29 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:28 +0200 +Subject: net: qmi_wwan: add Sierra Wireless EM7355 +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit b85f5deaf052340021d025e120a9858f084a1d79 ] + +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -724,6 +724,7 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x1199, 0x68a2, 8)}, /* Sierra Wireless MC7710 in QMI mode */ + {QMI_FIXED_INTF(0x1199, 0x68a2, 19)}, /* Sierra Wireless MC7710 in QMI mode */ + {QMI_FIXED_INTF(0x1199, 0x901c, 8)}, /* Sierra Wireless EM7700 */ ++ {QMI_FIXED_INTF(0x1199, 0x901f, 8)}, /* Sierra Wireless EM7355 */ + {QMI_FIXED_INTF(0x1199, 0x9051, 8)}, /* Netgear AirCard 340U */ + {QMI_FIXED_INTF(0x1bbb, 0x011e, 4)}, /* Telekom Speedstick LTE II (Alcatel One Touch L100V LTE) */ + {QMI_FIXED_INTF(0x2357, 0x0201, 4)}, /* TP-LINK HSUPA Modem MA180 */ diff --git a/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc7305-mc7355.patch b/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc7305-mc7355.patch new file mode 100644 index 00000000000..068ca460307 --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc7305-mc7355.patch @@ -0,0 +1,29 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:30 +0200 +Subject: net: qmi_wwan: add Sierra Wireless MC7305/MC7355 +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 9214224e43e4264b02686ea8b455f310935607b5 ] + +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -728,6 +728,7 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x1199, 0x68c0, 11)}, /* Sierra Wireless MC73xx */ + {QMI_FIXED_INTF(0x1199, 0x901c, 8)}, /* Sierra Wireless EM7700 */ + {QMI_FIXED_INTF(0x1199, 0x901f, 8)}, /* Sierra Wireless EM7355 */ ++ {QMI_FIXED_INTF(0x1199, 0x9041, 8)}, /* Sierra Wireless MC7305/MC7355 */ + {QMI_FIXED_INTF(0x1199, 0x9051, 8)}, /* Netgear AirCard 340U */ + {QMI_FIXED_INTF(0x1bbb, 0x011e, 4)}, /* Telekom Speedstick LTE II (Alcatel One Touch L100V LTE) */ + {QMI_FIXED_INTF(0x2357, 0x0201, 4)}, /* TP-LINK HSUPA Modem MA180 */ diff --git a/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc73xx.patch b/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc73xx.patch new file mode 100644 index 00000000000..750db77d1cf --- /dev/null +++ b/queue-3.14/net-qmi_wwan-add-sierra-wireless-mc73xx.patch @@ -0,0 +1,31 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= +Date: Fri, 25 Apr 2014 19:00:29 +0200 +Subject: net: qmi_wwan: add Sierra Wireless MC73xx +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= + +[ Upstream commit 1c138607a7be64074d7fba68d0d533ec38f9d17b ] + +Signed-off-by: Bjørn Mork +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/usb/qmi_wwan.c | 3 +++ + 1 file changed, 3 insertions(+) + +--- a/drivers/net/usb/qmi_wwan.c ++++ b/drivers/net/usb/qmi_wwan.c +@@ -723,6 +723,9 @@ static const struct usb_device_id produc + {QMI_FIXED_INTF(0x114f, 0x68a2, 8)}, /* Sierra Wireless MC7750 */ + {QMI_FIXED_INTF(0x1199, 0x68a2, 8)}, /* Sierra Wireless MC7710 in QMI mode */ + {QMI_FIXED_INTF(0x1199, 0x68a2, 19)}, /* Sierra Wireless MC7710 in QMI mode */ ++ {QMI_FIXED_INTF(0x1199, 0x68c0, 8)}, /* Sierra Wireless MC73xx */ ++ {QMI_FIXED_INTF(0x1199, 0x68c0, 10)}, /* Sierra Wireless MC73xx */ ++ {QMI_FIXED_INTF(0x1199, 0x68c0, 11)}, /* Sierra Wireless MC73xx */ + {QMI_FIXED_INTF(0x1199, 0x901c, 8)}, /* Sierra Wireless EM7700 */ + {QMI_FIXED_INTF(0x1199, 0x901f, 8)}, /* Sierra Wireless EM7355 */ + {QMI_FIXED_INTF(0x1199, 0x9051, 8)}, /* Netgear AirCard 340U */ diff --git a/queue-3.14/net-sched-lock-imbalance-in-hhf-qdisc.patch b/queue-3.14/net-sched-lock-imbalance-in-hhf-qdisc.patch new file mode 100644 index 00000000000..66abe47ec30 --- /dev/null +++ b/queue-3.14/net-sched-lock-imbalance-in-hhf-qdisc.patch @@ -0,0 +1,51 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: John Fastabend +Date: Thu, 1 May 2014 09:23:06 -0700 +Subject: net: sched: lock imbalance in hhf qdisc + +From: John Fastabend + +[ Upstream commit f6a082fed1e6407c2f4437d0d963b1bcbe5f9f58 ] + +hhf_change() takes the sch_tree_lock and releases it but misses the +error cases. Fix the missed case here. + +To reproduce try a command like this, + +# tc qdisc change dev p3p2 root hhf quantum 40960 non_hh_weight 300000 + +Signed-off-by: John Fastabend +Signed-off-by: Eric Dumazet +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sched/sch_hhf.c | 11 ++++++----- + 1 file changed, 6 insertions(+), 5 deletions(-) + +--- a/net/sched/sch_hhf.c ++++ b/net/sched/sch_hhf.c +@@ -553,11 +553,6 @@ static int hhf_change(struct Qdisc *sch, + if (err < 0) + return err; + +- sch_tree_lock(sch); +- +- if (tb[TCA_HHF_BACKLOG_LIMIT]) +- sch->limit = nla_get_u32(tb[TCA_HHF_BACKLOG_LIMIT]); +- + if (tb[TCA_HHF_QUANTUM]) + new_quantum = nla_get_u32(tb[TCA_HHF_QUANTUM]); + +@@ -567,6 +562,12 @@ static int hhf_change(struct Qdisc *sch, + non_hh_quantum = (u64)new_quantum * new_hhf_non_hh_weight; + if (non_hh_quantum > INT_MAX) + return -EINVAL; ++ ++ sch_tree_lock(sch); ++ ++ if (tb[TCA_HHF_BACKLOG_LIMIT]) ++ sch->limit = nla_get_u32(tb[TCA_HHF_BACKLOG_LIMIT]); ++ + q->quantum = new_quantum; + q->hhf_non_hh_weight = new_hhf_non_hh_weight; + diff --git a/queue-3.14/net-sctp-cache-auth_enable-per-endpoint.patch b/queue-3.14/net-sctp-cache-auth_enable-per-endpoint.patch new file mode 100644 index 00000000000..fe6d157667a --- /dev/null +++ b/queue-3.14/net-sctp-cache-auth_enable-per-endpoint.patch @@ -0,0 +1,604 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Thu, 17 Apr 2014 17:26:50 +0200 +Subject: net: sctp: cache auth_enable per endpoint + +From: Vlad Yasevich + +[ Upstream commit b14878ccb7fac0242db82720b784ab62c467c0dc ] + +Currently, it is possible to create an SCTP socket, then switch +auth_enable via sysctl setting to 1 and crash the system on connect: + +Oops[#1]: +CPU: 0 PID: 0 Comm: swapper Not tainted 3.14.1-mipsgit-20140415 #1 +task: ffffffff8056ce80 ti: ffffffff8055c000 task.ti: ffffffff8055c000 +[...] +Call Trace: +[] sctp_auth_asoc_set_default_hmac+0x68/0x80 +[] sctp_process_init+0x5e0/0x8a4 +[] sctp_sf_do_5_1B_init+0x234/0x34c +[] sctp_do_sm+0xb4/0x1e8 +[] sctp_endpoint_bh_rcv+0x1c4/0x214 +[] sctp_rcv+0x588/0x630 +[] sctp6_rcv+0x10/0x24 +[] ip6_input+0x2c0/0x440 +[] __netif_receive_skb_core+0x4a8/0x564 +[] process_backlog+0xb4/0x18c +[] net_rx_action+0x12c/0x210 +[] __do_softirq+0x17c/0x2ac +[] irq_exit+0x54/0xb0 +[] ret_from_irq+0x0/0x4 +[] rm7k_wait_irqoff+0x24/0x48 +[] cpu_startup_entry+0xc0/0x148 +[] start_kernel+0x37c/0x398 +Code: dd0900b8 000330f8 0126302d 50c0fff1 0047182a a48306a0 +03e00008 00000000 +---[ end trace b530b0551467f2fd ]--- +Kernel panic - not syncing: Fatal exception in interrupt + +What happens while auth_enable=0 in that case is, that +ep->auth_hmacs is initialized to NULL in sctp_auth_init_hmacs() +when endpoint is being created. + +After that point, if an admin switches over to auth_enable=1, +the machine can crash due to NULL pointer dereference during +reception of an INIT chunk. When we enter sctp_process_init() +via sctp_sf_do_5_1B_init() in order to respond to an INIT chunk, +the INIT verification succeeds and while we walk and process +all INIT params via sctp_process_param() we find that +net->sctp.auth_enable is set, therefore do not fall through, +but invoke sctp_auth_asoc_set_default_hmac() instead, and thus, +dereference what we have set to NULL during endpoint +initialization phase. + +The fix is to make auth_enable immutable by caching its value +during endpoint initialization, so that its original value is +being carried along until destruction. The bug seems to originate +from the very first days. + +Fix in joint work with Daniel Borkmann. + +Reported-by: Joshua Kinard +Signed-off-by: Vlad Yasevich +Signed-off-by: Daniel Borkmann +Acked-by: Neil Horman +Tested-by: Joshua Kinard +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/net/sctp/structs.h | 4 ++- + net/sctp/auth.c | 17 +++++--------- + net/sctp/endpointola.c | 3 +- + net/sctp/sm_make_chunk.c | 32 ++++++++++++++------------ + net/sctp/sm_statefuns.c | 6 ++--- + net/sctp/socket.c | 54 +++++++++++++++++++++------------------------ + net/sctp/sysctl.c | 36 +++++++++++++++++++++++++++++- + 7 files changed, 92 insertions(+), 60 deletions(-) + +--- a/include/net/sctp/structs.h ++++ b/include/net/sctp/structs.h +@@ -1241,6 +1241,7 @@ struct sctp_endpoint { + /* SCTP-AUTH: endpoint shared keys */ + struct list_head endpoint_shared_keys; + __u16 active_key_id; ++ __u8 auth_enable; + }; + + /* Recover the outter endpoint structure. */ +@@ -1269,7 +1270,8 @@ struct sctp_endpoint *sctp_endpoint_is_m + int sctp_has_association(struct net *net, const union sctp_addr *laddr, + const union sctp_addr *paddr); + +-int sctp_verify_init(struct net *net, const struct sctp_association *asoc, ++int sctp_verify_init(struct net *net, const struct sctp_endpoint *ep, ++ const struct sctp_association *asoc, + sctp_cid_t, sctp_init_chunk_t *peer_init, + struct sctp_chunk *chunk, struct sctp_chunk **err_chunk); + int sctp_process_init(struct sctp_association *, struct sctp_chunk *chunk, +--- a/net/sctp/auth.c ++++ b/net/sctp/auth.c +@@ -386,14 +386,13 @@ nomem: + */ + int sctp_auth_asoc_init_active_key(struct sctp_association *asoc, gfp_t gfp) + { +- struct net *net = sock_net(asoc->base.sk); + struct sctp_auth_bytes *secret; + struct sctp_shared_key *ep_key; + + /* If we don't support AUTH, or peer is not capable + * we don't need to do anything. + */ +- if (!net->sctp.auth_enable || !asoc->peer.auth_capable) ++ if (!asoc->ep->auth_enable || !asoc->peer.auth_capable) + return 0; + + /* If the key_id is non-zero and we couldn't find an +@@ -440,16 +439,16 @@ struct sctp_shared_key *sctp_auth_get_sh + */ + int sctp_auth_init_hmacs(struct sctp_endpoint *ep, gfp_t gfp) + { +- struct net *net = sock_net(ep->base.sk); + struct crypto_hash *tfm = NULL; + __u16 id; + +- /* if the transforms are already allocted, we are done */ +- if (!net->sctp.auth_enable) { ++ /* If AUTH extension is disabled, we are done */ ++ if (!ep->auth_enable) { + ep->auth_hmacs = NULL; + return 0; + } + ++ /* If the transforms are already allocated, we are done */ + if (ep->auth_hmacs) + return 0; + +@@ -665,12 +664,10 @@ static int __sctp_auth_cid(sctp_cid_t ch + /* Check if peer requested that this chunk is authenticated */ + int sctp_auth_send_cid(sctp_cid_t chunk, const struct sctp_association *asoc) + { +- struct net *net; + if (!asoc) + return 0; + +- net = sock_net(asoc->base.sk); +- if (!net->sctp.auth_enable || !asoc->peer.auth_capable) ++ if (!asoc->ep->auth_enable || !asoc->peer.auth_capable) + return 0; + + return __sctp_auth_cid(chunk, asoc->peer.peer_chunks); +@@ -679,12 +676,10 @@ int sctp_auth_send_cid(sctp_cid_t chunk, + /* Check if we requested that peer authenticate this chunk. */ + int sctp_auth_recv_cid(sctp_cid_t chunk, const struct sctp_association *asoc) + { +- struct net *net; + if (!asoc) + return 0; + +- net = sock_net(asoc->base.sk); +- if (!net->sctp.auth_enable) ++ if (!asoc->ep->auth_enable) + return 0; + + return __sctp_auth_cid(chunk, +--- a/net/sctp/endpointola.c ++++ b/net/sctp/endpointola.c +@@ -68,7 +68,8 @@ static struct sctp_endpoint *sctp_endpoi + if (!ep->digest) + return NULL; + +- if (net->sctp.auth_enable) { ++ ep->auth_enable = net->sctp.auth_enable; ++ if (ep->auth_enable) { + /* Allocate space for HMACS and CHUNKS authentication + * variables. There are arrays that we encode directly + * into parameters to make the rest of the operations easier. +--- a/net/sctp/sm_make_chunk.c ++++ b/net/sctp/sm_make_chunk.c +@@ -219,6 +219,7 @@ struct sctp_chunk *sctp_make_init(const + gfp_t gfp, int vparam_len) + { + struct net *net = sock_net(asoc->base.sk); ++ struct sctp_endpoint *ep = asoc->ep; + sctp_inithdr_t init; + union sctp_params addrs; + size_t chunksize; +@@ -278,7 +279,7 @@ struct sctp_chunk *sctp_make_init(const + chunksize += vparam_len; + + /* Account for AUTH related parameters */ +- if (net->sctp.auth_enable) { ++ if (ep->auth_enable) { + /* Add random parameter length*/ + chunksize += sizeof(asoc->c.auth_random); + +@@ -363,7 +364,7 @@ struct sctp_chunk *sctp_make_init(const + } + + /* Add SCTP-AUTH chunks to the parameter list */ +- if (net->sctp.auth_enable) { ++ if (ep->auth_enable) { + sctp_addto_chunk(retval, sizeof(asoc->c.auth_random), + asoc->c.auth_random); + if (auth_hmacs) +@@ -2010,7 +2011,7 @@ static void sctp_process_ext_param(struc + /* if the peer reports AUTH, assume that he + * supports AUTH. + */ +- if (net->sctp.auth_enable) ++ if (asoc->ep->auth_enable) + asoc->peer.auth_capable = 1; + break; + case SCTP_CID_ASCONF: +@@ -2102,6 +2103,7 @@ static sctp_ierror_t sctp_process_unk_pa + * SCTP_IERROR_NO_ERROR - continue with the chunk + */ + static sctp_ierror_t sctp_verify_param(struct net *net, ++ const struct sctp_endpoint *ep, + const struct sctp_association *asoc, + union sctp_params param, + sctp_cid_t cid, +@@ -2152,7 +2154,7 @@ static sctp_ierror_t sctp_verify_param(s + goto fallthrough; + + case SCTP_PARAM_RANDOM: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fallthrough; + + /* SCTP-AUTH: Secion 6.1 +@@ -2169,7 +2171,7 @@ static sctp_ierror_t sctp_verify_param(s + break; + + case SCTP_PARAM_CHUNKS: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fallthrough; + + /* SCTP-AUTH: Section 3.2 +@@ -2185,7 +2187,7 @@ static sctp_ierror_t sctp_verify_param(s + break; + + case SCTP_PARAM_HMAC_ALGO: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fallthrough; + + hmacs = (struct sctp_hmac_algo_param *)param.p; +@@ -2220,10 +2222,9 @@ fallthrough: + } + + /* Verify the INIT packet before we process it. */ +-int sctp_verify_init(struct net *net, const struct sctp_association *asoc, +- sctp_cid_t cid, +- sctp_init_chunk_t *peer_init, +- struct sctp_chunk *chunk, ++int sctp_verify_init(struct net *net, const struct sctp_endpoint *ep, ++ const struct sctp_association *asoc, sctp_cid_t cid, ++ sctp_init_chunk_t *peer_init, struct sctp_chunk *chunk, + struct sctp_chunk **errp) + { + union sctp_params param; +@@ -2264,8 +2265,8 @@ int sctp_verify_init(struct net *net, co + + /* Verify all the variable length parameters */ + sctp_walk_params(param, peer_init, init_hdr.params) { +- +- result = sctp_verify_param(net, asoc, param, cid, chunk, errp); ++ result = sctp_verify_param(net, ep, asoc, param, cid, ++ chunk, errp); + switch (result) { + case SCTP_IERROR_ABORT: + case SCTP_IERROR_NOMEM: +@@ -2497,6 +2498,7 @@ static int sctp_process_param(struct sct + struct sctp_af *af; + union sctp_addr_param *addr_param; + struct sctp_transport *t; ++ struct sctp_endpoint *ep = asoc->ep; + + /* We maintain all INIT parameters in network byte order all the + * time. This allows us to not worry about whether the parameters +@@ -2636,7 +2638,7 @@ do_addr_param: + goto fall_through; + + case SCTP_PARAM_RANDOM: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fall_through; + + /* Save peer's random parameter */ +@@ -2649,7 +2651,7 @@ do_addr_param: + break; + + case SCTP_PARAM_HMAC_ALGO: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fall_through; + + /* Save peer's HMAC list */ +@@ -2665,7 +2667,7 @@ do_addr_param: + break; + + case SCTP_PARAM_CHUNKS: +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + goto fall_through; + + asoc->peer.peer_chunks = kmemdup(param.p, +--- a/net/sctp/sm_statefuns.c ++++ b/net/sctp/sm_statefuns.c +@@ -357,7 +357,7 @@ sctp_disposition_t sctp_sf_do_5_1B_init( + + /* Verify the INIT chunk before processing it. */ + err_chunk = NULL; +- if (!sctp_verify_init(net, asoc, chunk->chunk_hdr->type, ++ if (!sctp_verify_init(net, ep, asoc, chunk->chunk_hdr->type, + (sctp_init_chunk_t *)chunk->chunk_hdr, chunk, + &err_chunk)) { + /* This chunk contains fatal error. It is to be discarded. +@@ -524,7 +524,7 @@ sctp_disposition_t sctp_sf_do_5_1C_ack(s + + /* Verify the INIT chunk before processing it. */ + err_chunk = NULL; +- if (!sctp_verify_init(net, asoc, chunk->chunk_hdr->type, ++ if (!sctp_verify_init(net, ep, asoc, chunk->chunk_hdr->type, + (sctp_init_chunk_t *)chunk->chunk_hdr, chunk, + &err_chunk)) { + +@@ -1430,7 +1430,7 @@ static sctp_disposition_t sctp_sf_do_une + + /* Verify the INIT chunk before processing it. */ + err_chunk = NULL; +- if (!sctp_verify_init(net, asoc, chunk->chunk_hdr->type, ++ if (!sctp_verify_init(net, ep, asoc, chunk->chunk_hdr->type, + (sctp_init_chunk_t *)chunk->chunk_hdr, chunk, + &err_chunk)) { + /* This chunk contains fatal error. It is to be discarded. +--- a/net/sctp/socket.c ++++ b/net/sctp/socket.c +@@ -3321,10 +3321,10 @@ static int sctp_setsockopt_auth_chunk(st + char __user *optval, + unsigned int optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authchunk val; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (optlen != sizeof(struct sctp_authchunk)) +@@ -3341,7 +3341,7 @@ static int sctp_setsockopt_auth_chunk(st + } + + /* add this chunk id to the endpoint */ +- return sctp_auth_ep_add_chunkid(sctp_sk(sk)->ep, val.sauth_chunk); ++ return sctp_auth_ep_add_chunkid(ep, val.sauth_chunk); + } + + /* +@@ -3354,12 +3354,12 @@ static int sctp_setsockopt_hmac_ident(st + char __user *optval, + unsigned int optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_hmacalgo *hmacs; + u32 idents; + int err; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (optlen < sizeof(struct sctp_hmacalgo)) +@@ -3376,7 +3376,7 @@ static int sctp_setsockopt_hmac_ident(st + goto out; + } + +- err = sctp_auth_ep_set_hmacs(sctp_sk(sk)->ep, hmacs); ++ err = sctp_auth_ep_set_hmacs(ep, hmacs); + out: + kfree(hmacs); + return err; +@@ -3392,12 +3392,12 @@ static int sctp_setsockopt_auth_key(stru + char __user *optval, + unsigned int optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authkey *authkey; + struct sctp_association *asoc; + int ret; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (optlen <= sizeof(struct sctp_authkey)) +@@ -3418,7 +3418,7 @@ static int sctp_setsockopt_auth_key(stru + goto out; + } + +- ret = sctp_auth_set_key(sctp_sk(sk)->ep, asoc, authkey); ++ ret = sctp_auth_set_key(ep, asoc, authkey); + out: + kzfree(authkey); + return ret; +@@ -3434,11 +3434,11 @@ static int sctp_setsockopt_active_key(st + char __user *optval, + unsigned int optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authkeyid val; + struct sctp_association *asoc; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (optlen != sizeof(struct sctp_authkeyid)) +@@ -3450,8 +3450,7 @@ static int sctp_setsockopt_active_key(st + if (!asoc && val.scact_assoc_id && sctp_style(sk, UDP)) + return -EINVAL; + +- return sctp_auth_set_active_key(sctp_sk(sk)->ep, asoc, +- val.scact_keynumber); ++ return sctp_auth_set_active_key(ep, asoc, val.scact_keynumber); + } + + /* +@@ -3463,11 +3462,11 @@ static int sctp_setsockopt_del_key(struc + char __user *optval, + unsigned int optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authkeyid val; + struct sctp_association *asoc; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (optlen != sizeof(struct sctp_authkeyid)) +@@ -3479,8 +3478,7 @@ static int sctp_setsockopt_del_key(struc + if (!asoc && val.scact_assoc_id && sctp_style(sk, UDP)) + return -EINVAL; + +- return sctp_auth_del_key_id(sctp_sk(sk)->ep, asoc, +- val.scact_keynumber); ++ return sctp_auth_del_key_id(ep, asoc, val.scact_keynumber); + + } + +@@ -5387,16 +5385,16 @@ static int sctp_getsockopt_maxburst(stru + static int sctp_getsockopt_hmac_ident(struct sock *sk, int len, + char __user *optval, int __user *optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_hmacalgo __user *p = (void __user *)optval; + struct sctp_hmac_algo_param *hmacs; + __u16 data_len = 0; + u32 num_idents; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + +- hmacs = sctp_sk(sk)->ep->auth_hmacs_list; ++ hmacs = ep->auth_hmacs_list; + data_len = ntohs(hmacs->param_hdr.length) - sizeof(sctp_paramhdr_t); + + if (len < sizeof(struct sctp_hmacalgo) + data_len) +@@ -5417,11 +5415,11 @@ static int sctp_getsockopt_hmac_ident(st + static int sctp_getsockopt_active_key(struct sock *sk, int len, + char __user *optval, int __user *optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authkeyid val; + struct sctp_association *asoc; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (len < sizeof(struct sctp_authkeyid)) +@@ -5436,7 +5434,7 @@ static int sctp_getsockopt_active_key(st + if (asoc) + val.scact_keynumber = asoc->active_key_id; + else +- val.scact_keynumber = sctp_sk(sk)->ep->active_key_id; ++ val.scact_keynumber = ep->active_key_id; + + len = sizeof(struct sctp_authkeyid); + if (put_user(len, optlen)) +@@ -5450,7 +5448,7 @@ static int sctp_getsockopt_active_key(st + static int sctp_getsockopt_peer_auth_chunks(struct sock *sk, int len, + char __user *optval, int __user *optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authchunks __user *p = (void __user *)optval; + struct sctp_authchunks val; + struct sctp_association *asoc; +@@ -5458,7 +5456,7 @@ static int sctp_getsockopt_peer_auth_chu + u32 num_chunks = 0; + char __user *to; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (len < sizeof(struct sctp_authchunks)) +@@ -5495,7 +5493,7 @@ num: + static int sctp_getsockopt_local_auth_chunks(struct sock *sk, int len, + char __user *optval, int __user *optlen) + { +- struct net *net = sock_net(sk); ++ struct sctp_endpoint *ep = sctp_sk(sk)->ep; + struct sctp_authchunks __user *p = (void __user *)optval; + struct sctp_authchunks val; + struct sctp_association *asoc; +@@ -5503,7 +5501,7 @@ static int sctp_getsockopt_local_auth_ch + u32 num_chunks = 0; + char __user *to; + +- if (!net->sctp.auth_enable) ++ if (!ep->auth_enable) + return -EACCES; + + if (len < sizeof(struct sctp_authchunks)) +@@ -5520,7 +5518,7 @@ static int sctp_getsockopt_local_auth_ch + if (asoc) + ch = (struct sctp_chunks_param *)asoc->c.auth_chunks; + else +- ch = sctp_sk(sk)->ep->auth_chunk_list; ++ ch = ep->auth_chunk_list; + + if (!ch) + goto num; +--- a/net/sctp/sysctl.c ++++ b/net/sctp/sysctl.c +@@ -64,6 +64,9 @@ static int proc_sctp_do_rto_min(struct c + static int proc_sctp_do_rto_max(struct ctl_table *ctl, int write, + void __user *buffer, size_t *lenp, + loff_t *ppos); ++static int proc_sctp_do_auth(struct ctl_table *ctl, int write, ++ void __user *buffer, size_t *lenp, ++ loff_t *ppos); + + static struct ctl_table sctp_table[] = { + { +@@ -266,7 +269,7 @@ static struct ctl_table sctp_net_table[] + .data = &init_net.sctp.auth_enable, + .maxlen = sizeof(int), + .mode = 0644, +- .proc_handler = proc_dointvec, ++ .proc_handler = proc_sctp_do_auth, + }, + { + .procname = "addr_scope_policy", +@@ -400,6 +403,37 @@ static int proc_sctp_do_rto_max(struct c + return ret; + } + ++static int proc_sctp_do_auth(struct ctl_table *ctl, int write, ++ void __user *buffer, size_t *lenp, ++ loff_t *ppos) ++{ ++ struct net *net = current->nsproxy->net_ns; ++ struct ctl_table tbl; ++ int new_value, ret; ++ ++ memset(&tbl, 0, sizeof(struct ctl_table)); ++ tbl.maxlen = sizeof(unsigned int); ++ ++ if (write) ++ tbl.data = &new_value; ++ else ++ tbl.data = &net->sctp.auth_enable; ++ ++ ret = proc_dointvec(&tbl, write, buffer, lenp, ppos); ++ ++ if (write) { ++ struct sock *sk = net->sctp.ctl_sock; ++ ++ net->sctp.auth_enable = new_value; ++ /* Update the value in the control socket */ ++ lock_sock(sk); ++ sctp_sk(sk)->ep->auth_enable = new_value; ++ release_sock(sk); ++ } ++ ++ return ret; ++} ++ + int sctp_sysctl_net_register(struct net *net) + { + struct ctl_table *table = sctp_net_table; diff --git a/queue-3.14/net-sctp-don-t-transition-to-pf-state-when-transport.patch b/queue-3.14/net-sctp-don-t-transition-to-pf-state-when-transport.patch new file mode 100644 index 00000000000..f46c3e19a84 --- /dev/null +++ b/queue-3.14/net-sctp-don-t-transition-to-pf-state-when-transport.patch @@ -0,0 +1,48 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Karl Heiss +Date: Fri, 25 Apr 2014 14:26:30 -0400 +Subject: net: sctp: Don't transition to PF state when transport + has exhausted 'Path.Max.Retrans'. + +From: Karl Heiss + +[ Upstream commit 8c2eab9097dba50bcd73ed4632baccc3f34857f9 ] + +Don't transition to the PF state on every strike after 'Path.Max.Retrans'. +Per draft-ietf-tsvwg-sctp-failover-03 Section 5.1.6: + + Additional (PMR - PFMR) consecutive timeouts on a PF destination + confirm the path failure, upon which the destination transitions to the + Inactive state. As described in [RFC4960], the sender (i) SHOULD notify + ULP about this state transition, and (ii) transmit heartbeats to the + Inactive destination at a lower frequency as described in Section 8.3 of + [RFC4960]. + +This also prevents sending SCTP_ADDR_UNREACHABLE to the user as the state +bounces between SCTP_INACTIVE and SCTP_PF for each subsequent strike. + +Signed-off-by: Karl Heiss +Acked-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sctp/sm_sideeffect.c | 7 +++---- + 1 file changed, 3 insertions(+), 4 deletions(-) + +--- a/net/sctp/sm_sideeffect.c ++++ b/net/sctp/sm_sideeffect.c +@@ -496,11 +496,10 @@ static void sctp_do_8_2_transport_strike + + /* If the transport error count is greater than the pf_retrans + * threshold, and less than pathmaxrtx, and if the current state +- * is not SCTP_UNCONFIRMED, then mark this transport as Partially +- * Failed, see SCTP Quick Failover Draft, section 5.1 ++ * is SCTP_ACTIVE, then mark this transport as Partially Failed, ++ * see SCTP Quick Failover Draft, section 5.1 + */ +- if ((transport->state != SCTP_PF) && +- (transport->state != SCTP_UNCONFIRMED) && ++ if ((transport->state == SCTP_ACTIVE) && + (asoc->pf_retrans < transport->pathmaxrxt) && + (transport->error_count > asoc->pf_retrans)) { + diff --git a/queue-3.14/net-sctp-test-if-association-is-dead-in-sctp_wake_up_waiters.patch b/queue-3.14/net-sctp-test-if-association-is-dead-in-sctp_wake_up_waiters.patch new file mode 100644 index 00000000000..a16e64f124d --- /dev/null +++ b/queue-3.14/net-sctp-test-if-association-is-dead-in-sctp_wake_up_waiters.patch @@ -0,0 +1,81 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Daniel Borkmann +Date: Wed, 9 Apr 2014 16:10:20 +0200 +Subject: net: sctp: test if association is dead in sctp_wake_up_waiters + +From: Daniel Borkmann + +[ Upstream commit 1e1cdf8ac78793e0875465e98a648df64694a8d0 ] + +In function sctp_wake_up_waiters(), we need to involve a test +if the association is declared dead. If so, we don't have any +reference to a possible sibling association anymore and need +to invoke sctp_write_space() instead, and normally walk the +socket's associations and notify them of new wmem space. The +reason for special casing is that otherwise, we could run +into the following issue when a sctp_primitive_SEND() call +from sctp_sendmsg() fails, and tries to flush an association's +outq, i.e. in the following way: + +sctp_association_free() +`-> list_del(&asoc->asocs) <-- poisons list pointer + asoc->base.dead = true + sctp_outq_free(&asoc->outqueue) + `-> __sctp_outq_teardown() + `-> sctp_chunk_free() + `-> consume_skb() + `-> sctp_wfree() + `-> sctp_wake_up_waiters() <-- dereferences poisoned pointers + if asoc->ep->sndbuf_policy=0 + +Therefore, only walk the list in an 'optimized' way if we find +that the current association is still active. We could also use +list_del_init() in addition when we call sctp_association_free(), +but as Vlad suggests, we want to trap such bugs and thus leave +it poisoned as is. + +Why is it safe to resolve the issue by testing for asoc->base.dead? +Parallel calls to sctp_sendmsg() are protected under socket lock, +that is lock_sock()/release_sock(). Only within that path under +lock held, we're setting skb/chunk owner via sctp_set_owner_w(). +Eventually, chunks are freed directly by an association still +under that lock. So when traversing association list on destruction +time from sctp_wake_up_waiters() via sctp_wfree(), a different +CPU can't be running sctp_wfree() while another one calls +sctp_association_free() as both happens under the same lock. +Therefore, this can also not race with setting/testing against +asoc->base.dead as we are guaranteed for this to happen in order, +under lock. Further, Vlad says: the times we check asoc->base.dead +is when we've cached an association pointer for later processing. +In between cache and processing, the association may have been +freed and is simply still around due to reference counts. We check +asoc->base.dead under a lock, so it should always be safe to check +and not race against sctp_association_free(). Stress-testing seems +fine now, too. + +Fixes: cd253f9f357d ("net: sctp: wake up all assocs if sndbuf policy is per socket") +Signed-off-by: Daniel Borkmann +Cc: Vlad Yasevich +Acked-by: Neil Horman +Acked-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sctp/socket.c | 6 ++++++ + 1 file changed, 6 insertions(+) + +--- a/net/sctp/socket.c ++++ b/net/sctp/socket.c +@@ -6604,6 +6604,12 @@ static void sctp_wake_up_waiters(struct + if (asoc->ep->sndbuf_policy) + return __sctp_write_space(asoc); + ++ /* If association goes down and is just flushing its ++ * outq, then just normally notify others. ++ */ ++ if (asoc->base.dead) ++ return sctp_write_space(sk); ++ + /* Accounting for the sndbuf space is per socket, so we + * need to wake up others, try to be fair and in case of + * other associations, let them have a go first instead diff --git a/queue-3.14/net-sctp-wake-up-all-assocs-if-sndbuf-policy-is-per-socket.patch b/queue-3.14/net-sctp-wake-up-all-assocs-if-sndbuf-policy-is-per-socket.patch new file mode 100644 index 00000000000..96e20ee2968 --- /dev/null +++ b/queue-3.14/net-sctp-wake-up-all-assocs-if-sndbuf-policy-is-per-socket.patch @@ -0,0 +1,116 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Daniel Borkmann +Date: Tue, 8 Apr 2014 17:26:13 +0200 +Subject: net: sctp: wake up all assocs if sndbuf policy is per socket + +From: Daniel Borkmann + +[ Upstream commit 52c35befb69b005c3fc5afdaae3a5717ad013411 ] + +SCTP charges chunks for wmem accounting via skb->truesize in +sctp_set_owner_w(), and sctp_wfree() respectively as the +reverse operation. If a sender runs out of wmem, it needs to +wait via sctp_wait_for_sndbuf(), and gets woken up by a call +to __sctp_write_space() mostly via sctp_wfree(). + +__sctp_write_space() is being called per association. Although +we assign sk->sk_write_space() to sctp_write_space(), which +is then being done per socket, it is only used if send space +is increased per socket option (SO_SNDBUF), as SOCK_USE_WRITE_QUEUE +is set and therefore not invoked in sock_wfree(). + +Commit 4c3a5bdae293 ("sctp: Don't charge for data in sndbuf +again when transmitting packet") fixed an issue where in case +sctp_packet_transmit() manages to queue up more than sndbuf +bytes, sctp_wait_for_sndbuf() will never be woken up again +unless it is interrupted by a signal. However, a still +remaining issue is that if net.sctp.sndbuf_policy=0, that is +accounting per socket, and one-to-many sockets are in use, +the reclaimed write space from sctp_wfree() is 'unfairly' +handed back on the server to the association that is the lucky +one to be woken up again via __sctp_write_space(), while +the remaining associations are never be woken up again +(unless by a signal). + +The effect disappears with net.sctp.sndbuf_policy=1, that +is wmem accounting per association, as it guarantees a fair +share of wmem among associations. + +Therefore, if we have reclaimed memory in case of per socket +accounting, wake all related associations to a socket in a +fair manner, that is, traverse the socket association list +starting from the current neighbour of the association and +issue a __sctp_write_space() to everyone until we end up +waking ourselves. This guarantees that no association is +preferred over another and even if more associations are +taken into the one-to-many session, all receivers will get +messages from the server and are not stalled forever on +high load. This setting still leaves the advantage of per +socket accounting in touch as an association can still use +up global limits if unused by others. + +Fixes: 4eb701dfc618 ("[SCTP] Fix SCTP sendbuffer accouting.") +Signed-off-by: Daniel Borkmann +Cc: Thomas Graf +Cc: Neil Horman +Cc: Vlad Yasevich +Acked-by: Vlad Yasevich +Acked-by: Neil Horman +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sctp/socket.c | 36 +++++++++++++++++++++++++++++++++++- + 1 file changed, 35 insertions(+), 1 deletion(-) + +--- a/net/sctp/socket.c ++++ b/net/sctp/socket.c +@@ -6593,6 +6593,40 @@ static void __sctp_write_space(struct sc + } + } + ++static void sctp_wake_up_waiters(struct sock *sk, ++ struct sctp_association *asoc) ++{ ++ struct sctp_association *tmp = asoc; ++ ++ /* We do accounting for the sndbuf space per association, ++ * so we only need to wake our own association. ++ */ ++ if (asoc->ep->sndbuf_policy) ++ return __sctp_write_space(asoc); ++ ++ /* Accounting for the sndbuf space is per socket, so we ++ * need to wake up others, try to be fair and in case of ++ * other associations, let them have a go first instead ++ * of just doing a sctp_write_space() call. ++ * ++ * Note that we reach sctp_wake_up_waiters() only when ++ * associations free up queued chunks, thus we are under ++ * lock and the list of associations on a socket is ++ * guaranteed not to change. ++ */ ++ for (tmp = list_next_entry(tmp, asocs); 1; ++ tmp = list_next_entry(tmp, asocs)) { ++ /* Manually skip the head element. */ ++ if (&tmp->asocs == &((sctp_sk(sk))->ep->asocs)) ++ continue; ++ /* Wake up association. */ ++ __sctp_write_space(tmp); ++ /* We've reached the end. */ ++ if (tmp == asoc) ++ break; ++ } ++} ++ + /* Do accounting for the sndbuf space. + * Decrement the used sndbuf space of the corresponding association by the + * data size which was just transmitted(freed). +@@ -6620,7 +6654,7 @@ static void sctp_wfree(struct sk_buff *s + sk_mem_uncharge(sk, skb->truesize); + + sock_wfree(skb); +- __sctp_write_space(asoc); ++ sctp_wake_up_waiters(sk, asoc); + + sctp_association_put(asoc); + } diff --git a/queue-3.14/net-start-with-correct-mac_len-in-skb_network_protocol.patch b/queue-3.14/net-start-with-correct-mac_len-in-skb_network_protocol.patch new file mode 100644 index 00000000000..eedfaa4c638 --- /dev/null +++ b/queue-3.14/net-start-with-correct-mac_len-in-skb_network_protocol.patch @@ -0,0 +1,45 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Mon, 14 Apr 2014 17:37:26 -0400 +Subject: net: Start with correct mac_len in skb_network_protocol + +From: Vlad Yasevich + +[ Upstream commit 1e785f48d29a09b6cf96db7b49b6320dada332e1 ] + +Sometimes, when the packet arrives at skb_mac_gso_segment() +its skb->mac_len already accounts for some of the mac lenght +headers in the packet. This seems to happen when forwarding +through and OpenSSL tunnel. + +When we start looking for any vlan headers in skb_network_protocol() +we seem to ignore any of the already known mac headers and start +with an ETH_HLEN. This results in an incorrect offset, dropped +TSO frames and general slowness of the connection. + +We can start counting from the known skb->mac_len +and return at least that much if all mac level headers +are known and accounted for. + +Fixes: 53d6471cef17262d3ad1c7ce8982a234244f68ec (net: Account for all vlan headers in skb_mac_gso_segment) +CC: Eric Dumazet +CC: Daniel Borkman +Tested-by: Martin Filip +Signed-off-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/dev.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -2289,7 +2289,7 @@ EXPORT_SYMBOL(skb_checksum_help); + __be16 skb_network_protocol(struct sk_buff *skb, int *depth) + { + __be16 type = skb->protocol; +- int vlan_depth = ETH_HLEN; ++ int vlan_depth = skb->mac_len; + + /* Tunnel gso handlers can set protocol to ethernet. */ + if (type == htons(ETH_P_TEB)) { diff --git a/queue-3.14/net_sched-fix-an-oops-in-tcindex-filter.patch b/queue-3.14/net_sched-fix-an-oops-in-tcindex-filter.patch new file mode 100644 index 00000000000..fbe54c98d81 --- /dev/null +++ b/queue-3.14/net_sched-fix-an-oops-in-tcindex-filter.patch @@ -0,0 +1,164 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Cong Wang +Date: Mon, 19 May 2014 12:15:49 -0700 +Subject: net_sched: fix an oops in tcindex filter + +From: Cong Wang + +[ Upstream commit bf63ac73b3e132e6bf0c8798aba7b277c3316e19 ] + +Kelly reported the following crash: + + IP: [] tcf_action_exec+0x46/0x90 + PGD 3009067 PUD 300c067 PMD 11ff30067 PTE 800000011634b060 + Oops: 0000 [#1] SMP DEBUG_PAGEALLOC + CPU: 1 PID: 639 Comm: dhclient Not tainted 3.15.0-rc4+ #342 + Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011 + task: ffff8801169ecd00 ti: ffff8800d21b8000 task.ti: ffff8800d21b8000 + RIP: 0010:[] [] tcf_action_exec+0x46/0x90 + RSP: 0018:ffff8800d21b9b90 EFLAGS: 00010283 + RAX: 00000000ffffffff RBX: ffff88011634b8e8 RCX: ffff8800cf7133d8 + RDX: ffff88011634b900 RSI: ffff8800cf7133e0 RDI: ffff8800d210f840 + RBP: ffff8800d21b9bb0 R08: ffffffff8287bf60 R09: 0000000000000001 + R10: ffff8800d2b22b24 R11: 0000000000000001 R12: ffff8800d210f840 + R13: ffff8800d21b9c50 R14: ffff8800cf7133e0 R15: ffff8800cad433d8 + FS: 00007f49723e1840(0000) GS:ffff88011a800000(0000) knlGS:0000000000000000 + CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 + CR2: ffff88011634b8f0 CR3: 00000000ce469000 CR4: 00000000000006e0 + Stack: + ffff8800d2170188 ffff8800d210f840 ffff8800d2171b90 0000000000000000 + ffff8800d21b9be8 ffffffff817c55bb ffff8800d21b9c50 ffff8800d2171b90 + ffff8800d210f840 ffff8800d21b0300 ffff8800d21b9c50 ffff8800d21b9c18 + Call Trace: + [] tcindex_classify+0x88/0x9b + [] tc_classify_compat+0x3e/0x7b + [] tc_classify+0x25/0x9f + [] htb_enqueue+0x55/0x27a + [] dsmark_enqueue+0x165/0x1a4 + [] __dev_queue_xmit+0x35e/0x536 + [] dev_queue_xmit+0x10/0x12 + [] packet_sendmsg+0xb26/0xb9a + [] ? __lock_acquire+0x3ae/0xdf3 + [] __sock_sendmsg_nosec+0x25/0x27 + [] sock_aio_write+0xd0/0xe7 + [] do_sync_write+0x59/0x78 + [] vfs_write+0xb5/0x10a + [] SyS_write+0x49/0x7f + [] system_call_fastpath+0x16/0x1b + +This is because we memcpy struct tcindex_filter_result which contains +struct tcf_exts, obviously struct list_head can not be simply copied. +This is a regression introduced by commit 33be627159913b094bb578 +(net_sched: act: use standard struct list_head). + +It's not very easy to fix it as the code is a mess: + + if (old_r) + memcpy(&cr, r, sizeof(cr)); + else { + memset(&cr, 0, sizeof(cr)); + tcf_exts_init(&cr.exts, TCA_TCINDEX_ACT, TCA_TCINDEX_POLICE); + } + ... + tcf_exts_change(tp, &cr.exts, &e); + ... + memcpy(r, &cr, sizeof(cr)); + +the above code should equal to: + + tcindex_filter_result_init(&cr); + if (old_r) + cr.res = r->res; + ... + if (old_r) + tcf_exts_change(tp, &r->exts, &e); + else + tcf_exts_change(tp, &cr.exts, &e); + ... + r->res = cr.res; + +after this change, since there is no need to copy struct tcf_exts. + +And it also fixes other places zero'ing struct's contains struct tcf_exts. + +Fixes: commit 33be627159913b0 (net_sched: act: use standard struct list_head) +Reported-by: Kelly Anderson +Tested-by: Kelly Anderson +Cc: David S. Miller +Signed-off-by: Cong Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sched/cls_tcindex.c | 30 ++++++++++++++++++++---------- + 1 file changed, 20 insertions(+), 10 deletions(-) + +--- a/net/sched/cls_tcindex.c ++++ b/net/sched/cls_tcindex.c +@@ -188,6 +188,12 @@ static const struct nla_policy tcindex_p + [TCA_TCINDEX_CLASSID] = { .type = NLA_U32 }, + }; + ++static void tcindex_filter_result_init(struct tcindex_filter_result *r) ++{ ++ memset(r, 0, sizeof(*r)); ++ tcf_exts_init(&r->exts, TCA_TCINDEX_ACT, TCA_TCINDEX_POLICE); ++} ++ + static int + tcindex_set_parms(struct net *net, struct tcf_proto *tp, unsigned long base, + u32 handle, struct tcindex_data *p, +@@ -207,15 +213,11 @@ tcindex_set_parms(struct net *net, struc + return err; + + memcpy(&cp, p, sizeof(cp)); +- memset(&new_filter_result, 0, sizeof(new_filter_result)); +- tcf_exts_init(&new_filter_result.exts, TCA_TCINDEX_ACT, TCA_TCINDEX_POLICE); ++ tcindex_filter_result_init(&new_filter_result); + ++ tcindex_filter_result_init(&cr); + if (old_r) +- memcpy(&cr, r, sizeof(cr)); +- else { +- memset(&cr, 0, sizeof(cr)); +- tcf_exts_init(&cr.exts, TCA_TCINDEX_ACT, TCA_TCINDEX_POLICE); +- } ++ cr.res = r->res; + + if (tb[TCA_TCINDEX_HASH]) + cp.hash = nla_get_u32(tb[TCA_TCINDEX_HASH]); +@@ -267,9 +269,14 @@ tcindex_set_parms(struct net *net, struc + err = -ENOMEM; + if (!cp.perfect && !cp.h) { + if (valid_perfect_hash(&cp)) { ++ int i; ++ + cp.perfect = kcalloc(cp.hash, sizeof(*r), GFP_KERNEL); + if (!cp.perfect) + goto errout; ++ for (i = 0; i < cp.hash; i++) ++ tcf_exts_init(&cp.perfect[i].exts, TCA_TCINDEX_ACT, ++ TCA_TCINDEX_POLICE); + balloc = 1; + } else { + cp.h = kcalloc(cp.hash, sizeof(f), GFP_KERNEL); +@@ -295,14 +302,17 @@ tcindex_set_parms(struct net *net, struc + tcf_bind_filter(tp, &cr.res, base); + } + +- tcf_exts_change(tp, &cr.exts, &e); ++ if (old_r) ++ tcf_exts_change(tp, &r->exts, &e); ++ else ++ tcf_exts_change(tp, &cr.exts, &e); + + tcf_tree_lock(tp); + if (old_r && old_r != r) +- memset(old_r, 0, sizeof(*old_r)); ++ tcindex_filter_result_init(old_r); + + memcpy(p, &cp, sizeof(cp)); +- memcpy(r, &cr, sizeof(cr)); ++ r->res = cr.res; + + if (r == &new_filter_result) { + struct tcindex_filter **fp; diff --git a/queue-3.14/revert-macvlan-fix-checksums-error-when-we-are-in.patch b/queue-3.14/revert-macvlan-fix-checksums-error-when-we-are-in.patch new file mode 100644 index 00000000000..870c85dcf3b --- /dev/null +++ b/queue-3.14/revert-macvlan-fix-checksums-error-when-we-are-in.patch @@ -0,0 +1,60 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Tue, 29 Apr 2014 10:09:51 -0400 +Subject: Revert "macvlan : fix checksums error when we are in + bridge mode" + +From: Vlad Yasevich + +[ Upstream commit f114890cdf84d753f6b41cd0cc44ba51d16313da ] + +This reverts commit 12a2856b604476c27d85a5f9a57ae1661fc46019. +The commit above doesn't appear to be necessary any more as the +checksums appear to be correctly computed/validated. + +Additionally the above commit breaks kvm configurations where +one VM is using a device that support checksum offload (virtio) and +the other VM does not. +In this case, packets leaving virtio device will have CHECKSUM_PARTIAL +set. The packets is forwarded to a macvtap that has offload features +turned off. Since we use CHECKSUM_UNNECESSARY, the host does does not +update the checksum and thus a bad checksum is passed up to +the guest. + +CC: Daniel Lezcano +CC: Patrick McHardy +CC: Andrian Nord +CC: Eric Dumazet +CC: Michael S. Tsirkin +CC: Jason Wang +Signed-off-by: Vlad Yasevich +Acked-by: Michael S. Tsirkin +Acked-by: Jason Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/macvlan.c | 3 --- + 1 file changed, 3 deletions(-) + +--- a/drivers/net/macvlan.c ++++ b/drivers/net/macvlan.c +@@ -263,11 +263,9 @@ static int macvlan_queue_xmit(struct sk_ + const struct macvlan_dev *vlan = netdev_priv(dev); + const struct macvlan_port *port = vlan->port; + const struct macvlan_dev *dest; +- __u8 ip_summed = skb->ip_summed; + + if (vlan->mode == MACVLAN_MODE_BRIDGE) { + const struct ethhdr *eth = (void *)skb->data; +- skb->ip_summed = CHECKSUM_UNNECESSARY; + + /* send to other bridge ports directly */ + if (is_multicast_ether_addr(eth->h_dest)) { +@@ -285,7 +283,6 @@ static int macvlan_queue_xmit(struct sk_ + } + + xmit_world: +- skb->ip_summed = ip_summed; + skb->dev = vlan->lowerdev; + return dev_queue_xmit(skb); + } diff --git a/queue-3.14/revert-net-sctp-fix-a_rwnd-rwnd-management-to-reflect-real-state-of-the-receiver-s-buffer.patch b/queue-3.14/revert-net-sctp-fix-a_rwnd-rwnd-management-to-reflect-real-state-of-the-receiver-s-buffer.patch new file mode 100644 index 00000000000..3000fe16275 --- /dev/null +++ b/queue-3.14/revert-net-sctp-fix-a_rwnd-rwnd-management-to-reflect-real-state-of-the-receiver-s-buffer.patch @@ -0,0 +1,311 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Daniel Borkmann +Date: Mon, 14 Apr 2014 21:45:17 +0200 +Subject: Revert "net: sctp: Fix a_rwnd/rwnd management to reflect real state of the receiver's buffer" + +From: Daniel Borkmann + +[ Upstream commit 362d52040c71f6e8d8158be48c812d7729cb8df1 ] + +This reverts commit ef2820a735f7 ("net: sctp: Fix a_rwnd/rwnd management +to reflect real state of the receiver's buffer") as it introduced a +serious performance regression on SCTP over IPv4 and IPv6, though a not +as dramatic on the latter. Measurements are on 10Gbit/s with ixgbe NICs. + +Current state: + +[root@Lab200slot2 ~]# iperf3 --sctp -4 -c 192.168.241.3 -V -l 1452 -t 60 +iperf version 3.0.1 (10 January 2014) +Linux Lab200slot2 3.14.0 #1 SMP Thu Apr 3 23:18:29 EDT 2014 x86_64 +Time: Fri, 11 Apr 2014 17:56:21 GMT +Connecting to host 192.168.241.3, port 5201 + Cookie: Lab200slot2.1397238981.812898.548918 +[ 4] local 192.168.241.2 port 38616 connected to 192.168.241.3 port 5201 +Starting Test: protocol: SCTP, 1 streams, 1452 byte blocks, omitting 0 seconds, 60 second test +[ ID] Interval Transfer Bandwidth +[ 4] 0.00-1.09 sec 20.8 MBytes 161 Mbits/sec +[ 4] 1.09-2.13 sec 10.8 MBytes 86.8 Mbits/sec +[ 4] 2.13-3.15 sec 3.57 MBytes 29.5 Mbits/sec +[ 4] 3.15-4.16 sec 4.33 MBytes 35.7 Mbits/sec +[ 4] 4.16-6.21 sec 10.4 MBytes 42.7 Mbits/sec +[ 4] 6.21-6.21 sec 0.00 Bytes 0.00 bits/sec +[ 4] 6.21-7.35 sec 34.6 MBytes 253 Mbits/sec +[ 4] 7.35-11.45 sec 22.0 MBytes 45.0 Mbits/sec +[ 4] 11.45-11.45 sec 0.00 Bytes 0.00 bits/sec +[ 4] 11.45-11.45 sec 0.00 Bytes 0.00 bits/sec +[ 4] 11.45-11.45 sec 0.00 Bytes 0.00 bits/sec +[ 4] 11.45-12.51 sec 16.0 MBytes 126 Mbits/sec +[ 4] 12.51-13.59 sec 20.3 MBytes 158 Mbits/sec +[ 4] 13.59-14.65 sec 13.4 MBytes 107 Mbits/sec +[ 4] 14.65-16.79 sec 33.3 MBytes 130 Mbits/sec +[ 4] 16.79-16.79 sec 0.00 Bytes 0.00 bits/sec +[ 4] 16.79-17.82 sec 5.94 MBytes 48.7 Mbits/sec +(etc) + +[root@Lab200slot2 ~]# iperf3 --sctp -6 -c 2001:db8:0:f101::1 -V -l 1400 -t 60 +iperf version 3.0.1 (10 January 2014) +Linux Lab200slot2 3.14.0 #1 SMP Thu Apr 3 23:18:29 EDT 2014 x86_64 +Time: Fri, 11 Apr 2014 19:08:41 GMT +Connecting to host 2001:db8:0:f101::1, port 5201 + Cookie: Lab200slot2.1397243321.714295.2b3f7c +[ 4] local 2001:db8:0:f101::2 port 55804 connected to 2001:db8:0:f101::1 port 5201 +Starting Test: protocol: SCTP, 1 streams, 1400 byte blocks, omitting 0 seconds, 60 second test +[ ID] Interval Transfer Bandwidth +[ 4] 0.00-1.00 sec 169 MBytes 1.42 Gbits/sec +[ 4] 1.00-2.00 sec 201 MBytes 1.69 Gbits/sec +[ 4] 2.00-3.00 sec 188 MBytes 1.58 Gbits/sec +[ 4] 3.00-4.00 sec 174 MBytes 1.46 Gbits/sec +[ 4] 4.00-5.00 sec 165 MBytes 1.39 Gbits/sec +[ 4] 5.00-6.00 sec 199 MBytes 1.67 Gbits/sec +[ 4] 6.00-7.00 sec 163 MBytes 1.36 Gbits/sec +[ 4] 7.00-8.00 sec 174 MBytes 1.46 Gbits/sec +[ 4] 8.00-9.00 sec 193 MBytes 1.62 Gbits/sec +[ 4] 9.00-10.00 sec 196 MBytes 1.65 Gbits/sec +[ 4] 10.00-11.00 sec 157 MBytes 1.31 Gbits/sec +[ 4] 11.00-12.00 sec 175 MBytes 1.47 Gbits/sec +[ 4] 12.00-13.00 sec 192 MBytes 1.61 Gbits/sec +[ 4] 13.00-14.00 sec 199 MBytes 1.67 Gbits/sec +(etc) + +After patch: + +[root@Lab200slot2 ~]# iperf3 --sctp -4 -c 192.168.240.3 -V -l 1452 -t 60 +iperf version 3.0.1 (10 January 2014) +Linux Lab200slot2 3.14.0+ #1 SMP Mon Apr 14 12:06:40 EDT 2014 x86_64 +Time: Mon, 14 Apr 2014 16:40:48 GMT +Connecting to host 192.168.240.3, port 5201 + Cookie: Lab200slot2.1397493648.413274.65e131 +[ 4] local 192.168.240.2 port 50548 connected to 192.168.240.3 port 5201 +Starting Test: protocol: SCTP, 1 streams, 1452 byte blocks, omitting 0 seconds, 60 second test +[ ID] Interval Transfer Bandwidth +[ 4] 0.00-1.00 sec 240 MBytes 2.02 Gbits/sec +[ 4] 1.00-2.00 sec 239 MBytes 2.01 Gbits/sec +[ 4] 2.00-3.00 sec 240 MBytes 2.01 Gbits/sec +[ 4] 3.00-4.00 sec 239 MBytes 2.00 Gbits/sec +[ 4] 4.00-5.00 sec 245 MBytes 2.05 Gbits/sec +[ 4] 5.00-6.00 sec 240 MBytes 2.01 Gbits/sec +[ 4] 6.00-7.00 sec 240 MBytes 2.02 Gbits/sec +[ 4] 7.00-8.00 sec 239 MBytes 2.01 Gbits/sec + +With the reverted patch applied, the SCTP/IPv4 performance is back +to normal on latest upstream for IPv4 and IPv6 and has same throughput +as 3.4.2 test kernel, steady and interval reports are smooth again. + +Fixes: ef2820a735f7 ("net: sctp: Fix a_rwnd/rwnd management to reflect real state of the receiver's buffer") +Reported-by: Peter Butler +Reported-by: Dongsheng Song +Reported-by: Fengguang Wu +Tested-by: Peter Butler +Signed-off-by: Daniel Borkmann +Cc: Matija Glavinic Pecotic +Cc: Alexander Sverdlin +Cc: Vlad Yasevich +Acked-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/net/sctp/structs.h | 14 +++++++ + net/sctp/associola.c | 82 +++++++++++++++++++++++++++++++++++---------- + net/sctp/sm_statefuns.c | 2 - + net/sctp/socket.c | 6 +++ + net/sctp/ulpevent.c | 8 +--- + 5 files changed, 87 insertions(+), 25 deletions(-) + +--- a/include/net/sctp/structs.h ++++ b/include/net/sctp/structs.h +@@ -1653,6 +1653,17 @@ struct sctp_association { + /* This is the last advertised value of rwnd over a SACK chunk. */ + __u32 a_rwnd; + ++ /* Number of bytes by which the rwnd has slopped. The rwnd is allowed ++ * to slop over a maximum of the association's frag_point. ++ */ ++ __u32 rwnd_over; ++ ++ /* Keeps treack of rwnd pressure. This happens when we have ++ * a window, but not recevie buffer (i.e small packets). This one ++ * is releases slowly (1 PMTU at a time ). ++ */ ++ __u32 rwnd_press; ++ + /* This is the sndbuf size in use for the association. + * This corresponds to the sndbuf size for the association, + * as specified in the sk->sndbuf. +@@ -1881,7 +1892,8 @@ void sctp_assoc_update(struct sctp_assoc + __u32 sctp_association_get_next_tsn(struct sctp_association *); + + void sctp_assoc_sync_pmtu(struct sock *, struct sctp_association *); +-void sctp_assoc_rwnd_update(struct sctp_association *, bool); ++void sctp_assoc_rwnd_increase(struct sctp_association *, unsigned int); ++void sctp_assoc_rwnd_decrease(struct sctp_association *, unsigned int); + void sctp_assoc_set_primary(struct sctp_association *, + struct sctp_transport *); + void sctp_assoc_del_nonprimary_peers(struct sctp_association *, +--- a/net/sctp/associola.c ++++ b/net/sctp/associola.c +@@ -1396,35 +1396,44 @@ static inline bool sctp_peer_needs_updat + return false; + } + +-/* Update asoc's rwnd for the approximated state in the buffer, +- * and check whether SACK needs to be sent. +- */ +-void sctp_assoc_rwnd_update(struct sctp_association *asoc, bool update_peer) ++/* Increase asoc's rwnd by len and send any window update SACK if needed. */ ++void sctp_assoc_rwnd_increase(struct sctp_association *asoc, unsigned int len) + { +- int rx_count; + struct sctp_chunk *sack; + struct timer_list *timer; + +- if (asoc->ep->rcvbuf_policy) +- rx_count = atomic_read(&asoc->rmem_alloc); +- else +- rx_count = atomic_read(&asoc->base.sk->sk_rmem_alloc); ++ if (asoc->rwnd_over) { ++ if (asoc->rwnd_over >= len) { ++ asoc->rwnd_over -= len; ++ } else { ++ asoc->rwnd += (len - asoc->rwnd_over); ++ asoc->rwnd_over = 0; ++ } ++ } else { ++ asoc->rwnd += len; ++ } + +- if ((asoc->base.sk->sk_rcvbuf - rx_count) > 0) +- asoc->rwnd = (asoc->base.sk->sk_rcvbuf - rx_count) >> 1; +- else +- asoc->rwnd = 0; ++ /* If we had window pressure, start recovering it ++ * once our rwnd had reached the accumulated pressure ++ * threshold. The idea is to recover slowly, but up ++ * to the initial advertised window. ++ */ ++ if (asoc->rwnd_press && asoc->rwnd >= asoc->rwnd_press) { ++ int change = min(asoc->pathmtu, asoc->rwnd_press); ++ asoc->rwnd += change; ++ asoc->rwnd_press -= change; ++ } + +- pr_debug("%s: asoc:%p rwnd=%u, rx_count=%d, sk_rcvbuf=%d\n", +- __func__, asoc, asoc->rwnd, rx_count, +- asoc->base.sk->sk_rcvbuf); ++ pr_debug("%s: asoc:%p rwnd increased by %d to (%u, %u) - %u\n", ++ __func__, asoc, len, asoc->rwnd, asoc->rwnd_over, ++ asoc->a_rwnd); + + /* Send a window update SACK if the rwnd has increased by at least the + * minimum of the association's PMTU and half of the receive buffer. + * The algorithm used is similar to the one described in + * Section 4.2.3.3 of RFC 1122. + */ +- if (update_peer && sctp_peer_needs_update(asoc)) { ++ if (sctp_peer_needs_update(asoc)) { + asoc->a_rwnd = asoc->rwnd; + + pr_debug("%s: sending window update SACK- asoc:%p rwnd:%u " +@@ -1446,6 +1455,45 @@ void sctp_assoc_rwnd_update(struct sctp_ + } + } + ++/* Decrease asoc's rwnd by len. */ ++void sctp_assoc_rwnd_decrease(struct sctp_association *asoc, unsigned int len) ++{ ++ int rx_count; ++ int over = 0; ++ ++ if (unlikely(!asoc->rwnd || asoc->rwnd_over)) ++ pr_debug("%s: association:%p has asoc->rwnd:%u, " ++ "asoc->rwnd_over:%u!\n", __func__, asoc, ++ asoc->rwnd, asoc->rwnd_over); ++ ++ if (asoc->ep->rcvbuf_policy) ++ rx_count = atomic_read(&asoc->rmem_alloc); ++ else ++ rx_count = atomic_read(&asoc->base.sk->sk_rmem_alloc); ++ ++ /* If we've reached or overflowed our receive buffer, announce ++ * a 0 rwnd if rwnd would still be positive. Store the ++ * the potential pressure overflow so that the window can be restored ++ * back to original value. ++ */ ++ if (rx_count >= asoc->base.sk->sk_rcvbuf) ++ over = 1; ++ ++ if (asoc->rwnd >= len) { ++ asoc->rwnd -= len; ++ if (over) { ++ asoc->rwnd_press += asoc->rwnd; ++ asoc->rwnd = 0; ++ } ++ } else { ++ asoc->rwnd_over = len - asoc->rwnd; ++ asoc->rwnd = 0; ++ } ++ ++ pr_debug("%s: asoc:%p rwnd decreased by %d to (%u, %u, %u)\n", ++ __func__, asoc, len, asoc->rwnd, asoc->rwnd_over, ++ asoc->rwnd_press); ++} + + /* Build the bind address list for the association based on info from the + * local endpoint and the remote peer. +--- a/net/sctp/sm_statefuns.c ++++ b/net/sctp/sm_statefuns.c +@@ -6178,7 +6178,7 @@ static int sctp_eat_data(const struct sc + * PMTU. In cases, such as loopback, this might be a rather + * large spill over. + */ +- if ((!chunk->data_accepted) && (!asoc->rwnd || ++ if ((!chunk->data_accepted) && (!asoc->rwnd || asoc->rwnd_over || + (datalen > asoc->rwnd + asoc->frag_point))) { + + /* If this is the next TSN, consider reneging to make +--- a/net/sctp/socket.c ++++ b/net/sctp/socket.c +@@ -2115,6 +2115,12 @@ static int sctp_recvmsg(struct kiocb *io + sctp_skb_pull(skb, copied); + skb_queue_head(&sk->sk_receive_queue, skb); + ++ /* When only partial message is copied to the user, increase ++ * rwnd by that amount. If all the data in the skb is read, ++ * rwnd is updated when the event is freed. ++ */ ++ if (!sctp_ulpevent_is_notification(event)) ++ sctp_assoc_rwnd_increase(event->asoc, copied); + goto out; + } else if ((event->msg_flags & MSG_NOTIFICATION) || + (event->msg_flags & MSG_EOR)) +--- a/net/sctp/ulpevent.c ++++ b/net/sctp/ulpevent.c +@@ -989,7 +989,7 @@ static void sctp_ulpevent_receive_data(s + skb = sctp_event2skb(event); + /* Set the owner and charge rwnd for bytes received. */ + sctp_ulpevent_set_owner(event, asoc); +- sctp_assoc_rwnd_update(asoc, false); ++ sctp_assoc_rwnd_decrease(asoc, skb_headlen(skb)); + + if (!skb->data_len) + return; +@@ -1011,7 +1011,6 @@ static void sctp_ulpevent_release_data(s + { + struct sk_buff *skb, *frag; + unsigned int len; +- struct sctp_association *asoc; + + /* Current stack structures assume that the rcv buffer is + * per socket. For UDP style sockets this is not true as +@@ -1036,11 +1035,8 @@ static void sctp_ulpevent_release_data(s + } + + done: +- asoc = event->asoc; +- sctp_association_hold(asoc); ++ sctp_assoc_rwnd_increase(event->asoc, len); + sctp_ulpevent_release_owner(event); +- sctp_assoc_rwnd_update(asoc, true); +- sctp_association_put(asoc); + } + + static void sctp_ulpevent_release_frag_data(struct sctp_ulpevent *event) diff --git a/queue-3.14/rtnetlink-only-supply-ifla_vf_ports-information-when.patch b/queue-3.14/rtnetlink-only-supply-ifla_vf_ports-information-when.patch new file mode 100644 index 00000000000..69761b22d88 --- /dev/null +++ b/queue-3.14/rtnetlink-only-supply-ifla_vf_ports-information-when.patch @@ -0,0 +1,99 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: David Gibson +Date: Thu, 24 Apr 2014 10:22:36 +1000 +Subject: rtnetlink: Only supply IFLA_VF_PORTS information when + RTEXT_FILTER_VF is set + +From: David Gibson + +[ Upstream commit c53864fd60227de025cb79e05493b13f69843971 ] + +Since 115c9b81928360d769a76c632bae62d15206a94a (rtnetlink: Fix problem with +buffer allocation), RTM_NEWLINK messages only contain the IFLA_VFINFO_LIST +attribute if they were solicited by a GETLINK message containing an +IFLA_EXT_MASK attribute with the RTEXT_FILTER_VF flag. + +That was done because some user programs broke when they received more data +than expected - because IFLA_VFINFO_LIST contains information for each VF +it can become large if there are many VFs. + +However, the IFLA_VF_PORTS attribute, supplied for devices which implement +ndo_get_vf_port (currently the 'enic' driver only), has the same problem. +It supplies per-VF information and can therefore become large, but it is +not currently conditional on the IFLA_EXT_MASK value. + +Worse, it interacts badly with the existing EXT_MASK handling. When +IFLA_EXT_MASK is not supplied, the buffer for netlink replies is fixed at +NLMSG_GOODSIZE. If the information for IFLA_VF_PORTS exceeds this, then +rtnl_fill_ifinfo() returns -EMSGSIZE on the first message in a packet. +netlink_dump() will misinterpret this as having finished the listing and +omit data for this interface and all subsequent ones. That can cause +getifaddrs(3) to enter an infinite loop. + +This patch addresses the problem by only supplying IFLA_VF_PORTS when +IFLA_EXT_MASK is supplied with the RTEXT_FILTER_VF flag set. + +Signed-off-by: David Gibson +Reviewed-by: Jiri Pirko +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/rtnetlink.c | 16 ++++++++++------ + 1 file changed, 10 insertions(+), 6 deletions(-) + +--- a/net/core/rtnetlink.c ++++ b/net/core/rtnetlink.c +@@ -774,7 +774,8 @@ static inline int rtnl_vfinfo_size(const + return 0; + } + +-static size_t rtnl_port_size(const struct net_device *dev) ++static size_t rtnl_port_size(const struct net_device *dev, ++ u32 ext_filter_mask) + { + size_t port_size = nla_total_size(4) /* PORT_VF */ + + nla_total_size(PORT_PROFILE_MAX) /* PORT_PROFILE */ +@@ -790,7 +791,8 @@ static size_t rtnl_port_size(const struc + size_t port_self_size = nla_total_size(sizeof(struct nlattr)) + + port_size; + +- if (!dev->netdev_ops->ndo_get_vf_port || !dev->dev.parent) ++ if (!dev->netdev_ops->ndo_get_vf_port || !dev->dev.parent || ++ !(ext_filter_mask & RTEXT_FILTER_VF)) + return 0; + if (dev_num_vf(dev->dev.parent)) + return port_self_size + vf_ports_size + +@@ -825,7 +827,7 @@ static noinline size_t if_nlmsg_size(con + + nla_total_size(ext_filter_mask + & RTEXT_FILTER_VF ? 4 : 0) /* IFLA_NUM_VF */ + + rtnl_vfinfo_size(dev, ext_filter_mask) /* IFLA_VFINFO_LIST */ +- + rtnl_port_size(dev) /* IFLA_VF_PORTS + IFLA_PORT_SELF */ ++ + rtnl_port_size(dev, ext_filter_mask) /* IFLA_VF_PORTS + IFLA_PORT_SELF */ + + rtnl_link_get_size(dev) /* IFLA_LINKINFO */ + + rtnl_link_get_af_size(dev) /* IFLA_AF_SPEC */ + + nla_total_size(MAX_PHYS_PORT_ID_LEN); /* IFLA_PHYS_PORT_ID */ +@@ -887,11 +889,13 @@ static int rtnl_port_self_fill(struct sk + return 0; + } + +-static int rtnl_port_fill(struct sk_buff *skb, struct net_device *dev) ++static int rtnl_port_fill(struct sk_buff *skb, struct net_device *dev, ++ u32 ext_filter_mask) + { + int err; + +- if (!dev->netdev_ops->ndo_get_vf_port || !dev->dev.parent) ++ if (!dev->netdev_ops->ndo_get_vf_port || !dev->dev.parent || ++ !(ext_filter_mask & RTEXT_FILTER_VF)) + return 0; + + err = rtnl_port_self_fill(skb, dev); +@@ -1076,7 +1080,7 @@ static int rtnl_fill_ifinfo(struct sk_bu + nla_nest_end(skb, vfinfo); + } + +- if (rtnl_port_fill(skb, dev)) ++ if (rtnl_port_fill(skb, dev, ext_filter_mask)) + goto nla_put_failure; + + if (dev->rtnl_link_ops || rtnl_have_link_slave_info(dev)) { diff --git a/queue-3.14/rtnetlink-wait-for-unregistering-devices-in.patch b/queue-3.14/rtnetlink-wait-for-unregistering-devices-in.patch new file mode 100644 index 00000000000..2d3b7614d67 --- /dev/null +++ b/queue-3.14/rtnetlink-wait-for-unregistering-devices-in.patch @@ -0,0 +1,127 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Cong Wang +Date: Mon, 12 May 2014 15:11:20 -0700 +Subject: rtnetlink: wait for unregistering devices in + rtnl_link_unregister() + +From: Cong Wang + +[ Upstream commit 200b916f3575bdf11609cb447661b8d5957b0bbf ] + +From: Cong Wang + +commit 50624c934db18ab90 (net: Delay default_device_exit_batch until no +devices are unregistering) introduced rtnl_lock_unregistering() for +default_device_exit_batch(). Same race could happen we when rmmod a driver +which calls rtnl_link_unregister() as we call dev->destructor without rtnl +lock. + +For long term, I think we should clean up the mess of netdev_run_todo() +and net namespce exit code. + +Cc: Eric W. Biederman +Cc: David S. Miller +Signed-off-by: Cong Wang +Signed-off-by: Cong Wang +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/rtnetlink.h | 5 +++++ + net/core/dev.c | 2 +- + net/core/net_namespace.c | 2 +- + net/core/rtnetlink.c | 33 ++++++++++++++++++++++++++++++++- + 4 files changed, 39 insertions(+), 3 deletions(-) + +--- a/include/linux/rtnetlink.h ++++ b/include/linux/rtnetlink.h +@@ -4,6 +4,7 @@ + + #include + #include ++#include + #include + + extern int rtnetlink_send(struct sk_buff *skb, struct net *net, u32 pid, u32 group, int echo); +@@ -22,6 +23,10 @@ extern void rtnl_lock(void); + extern void rtnl_unlock(void); + extern int rtnl_trylock(void); + extern int rtnl_is_locked(void); ++ ++extern wait_queue_head_t netdev_unregistering_wq; ++extern struct mutex net_mutex; ++ + #ifdef CONFIG_PROVE_LOCKING + extern int lockdep_rtnl_is_held(void); + #else +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -5573,7 +5573,7 @@ static int dev_new_index(struct net *net + + /* Delayed registration/unregisteration */ + static LIST_HEAD(net_todo_list); +-static DECLARE_WAIT_QUEUE_HEAD(netdev_unregistering_wq); ++DECLARE_WAIT_QUEUE_HEAD(netdev_unregistering_wq); + + static void net_set_todo(struct net_device *dev) + { +--- a/net/core/net_namespace.c ++++ b/net/core/net_namespace.c +@@ -24,7 +24,7 @@ + + static LIST_HEAD(pernet_list); + static struct list_head *first_device = &pernet_list; +-static DEFINE_MUTEX(net_mutex); ++DEFINE_MUTEX(net_mutex); + + LIST_HEAD(net_namespace_list); + EXPORT_SYMBOL_GPL(net_namespace_list); +--- a/net/core/rtnetlink.c ++++ b/net/core/rtnetlink.c +@@ -353,15 +353,46 @@ void __rtnl_link_unregister(struct rtnl_ + } + EXPORT_SYMBOL_GPL(__rtnl_link_unregister); + ++/* Return with the rtnl_lock held when there are no network ++ * devices unregistering in any network namespace. ++ */ ++static void rtnl_lock_unregistering_all(void) ++{ ++ struct net *net; ++ bool unregistering; ++ DEFINE_WAIT(wait); ++ ++ for (;;) { ++ prepare_to_wait(&netdev_unregistering_wq, &wait, ++ TASK_UNINTERRUPTIBLE); ++ unregistering = false; ++ rtnl_lock(); ++ for_each_net(net) { ++ if (net->dev_unreg_count > 0) { ++ unregistering = true; ++ break; ++ } ++ } ++ if (!unregistering) ++ break; ++ __rtnl_unlock(); ++ schedule(); ++ } ++ finish_wait(&netdev_unregistering_wq, &wait); ++} ++ + /** + * rtnl_link_unregister - Unregister rtnl_link_ops from rtnetlink. + * @ops: struct rtnl_link_ops * to unregister + */ + void rtnl_link_unregister(struct rtnl_link_ops *ops) + { +- rtnl_lock(); ++ /* Close the race with cleanup_net() */ ++ mutex_lock(&net_mutex); ++ rtnl_lock_unregistering_all(); + __rtnl_link_unregister(ops); + rtnl_unlock(); ++ mutex_unlock(&net_mutex); + } + EXPORT_SYMBOL_GPL(rtnl_link_unregister); + diff --git a/queue-3.14/rtnetlink-warn-when-interface-s-information-won-t-fit.patch b/queue-3.14/rtnetlink-warn-when-interface-s-information-won-t-fit.patch new file mode 100644 index 00000000000..7a1ee8e3f9c --- /dev/null +++ b/queue-3.14/rtnetlink-warn-when-interface-s-information-won-t-fit.patch @@ -0,0 +1,64 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: David Gibson +Date: Thu, 24 Apr 2014 10:22:35 +1000 +Subject: rtnetlink: Warn when interface's information won't fit + in our packet + +From: David Gibson + +[ Upstream commit 973462bbde79bb827824c73b59027a0aed5c9ca6 ] + +Without IFLA_EXT_MASK specified, the information reported for a single +interface in response to RTM_GETLINK is expected to fit within a netlink +packet of NLMSG_GOODSIZE. + +If it doesn't, however, things will go badly wrong, When listing all +interfaces, netlink_dump() will incorrectly treat -EMSGSIZE on the first +message in a packet as the end of the listing and omit information for +that interface and all subsequent ones. This can cause getifaddrs(3) to +enter an infinite loop. + +This patch won't fix the problem, but it will WARN_ON() making it easier to +track down what's going wrong. + +Signed-off-by: David Gibson +Reviewed-by: Jiri Pirko +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/core/rtnetlink.c | 17 ++++++++++++----- + 1 file changed, 12 insertions(+), 5 deletions(-) + +--- a/net/core/rtnetlink.c ++++ b/net/core/rtnetlink.c +@@ -1130,6 +1130,7 @@ static int rtnl_dump_ifinfo(struct sk_bu + struct hlist_head *head; + struct nlattr *tb[IFLA_MAX+1]; + u32 ext_filter_mask = 0; ++ int err; + + s_h = cb->args[0]; + s_idx = cb->args[1]; +@@ -1150,11 +1151,17 @@ static int rtnl_dump_ifinfo(struct sk_bu + hlist_for_each_entry_rcu(dev, head, index_hlist) { + if (idx < s_idx) + goto cont; +- if (rtnl_fill_ifinfo(skb, dev, RTM_NEWLINK, +- NETLINK_CB(cb->skb).portid, +- cb->nlh->nlmsg_seq, 0, +- NLM_F_MULTI, +- ext_filter_mask) <= 0) ++ err = rtnl_fill_ifinfo(skb, dev, RTM_NEWLINK, ++ NETLINK_CB(cb->skb).portid, ++ cb->nlh->nlmsg_seq, 0, ++ NLM_F_MULTI, ++ ext_filter_mask); ++ /* If we ran out of room on the first message, ++ * we're in trouble ++ */ ++ WARN_ON((err == -EMSGSIZE) && (skb->len == 0)); ++ ++ if (err <= 0) + goto out; + + nl_dump_check_consistent(cb, nlmsg_hdr(skb)); diff --git a/queue-3.14/sctp-reset-flowi4_oif-parameter-on-route-lookup.patch b/queue-3.14/sctp-reset-flowi4_oif-parameter-on-route-lookup.patch new file mode 100644 index 00000000000..4b01e79a6e9 --- /dev/null +++ b/queue-3.14/sctp-reset-flowi4_oif-parameter-on-route-lookup.patch @@ -0,0 +1,63 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Xufeng Zhang +Date: Fri, 25 Apr 2014 16:55:41 +0800 +Subject: sctp: reset flowi4_oif parameter on route lookup + +From: Xufeng Zhang + +[ Upstream commit 85350871317a5adb35519d9dc6fc9e80809d42ad ] + +commit 813b3b5db83 (ipv4: Use caller's on-stack flowi as-is +in output route lookups.) introduces another regression which +is very similar to the problem of commit e6b45241c (ipv4: reset +flowi parameters on route connect) wants to fix: +Before we call ip_route_output_key() in sctp_v4_get_dst() to +get a dst that matches a bind address as the source address, +we have already called this function previously and the flowi +parameters have been initialized including flowi4_oif, so when +we call this function again, the process in __ip_route_output_key() +will be different because of the setting of flowi4_oif, and we'll +get a networking device which corresponds to the inputted flowi4_oif +as the output device, this is wrong because we'll never hit this +place if the previously returned source address of dst match one +of the bound addresses. + +To reproduce this problem, a vlan setting is enough: + # ifconfig eth0 up + # route del default + # vconfig add eth0 2 + # vconfig add eth0 3 + # ifconfig eth0.2 10.0.1.14 netmask 255.255.255.0 + # route add default gw 10.0.1.254 dev eth0.2 + # ifconfig eth0.3 10.0.0.14 netmask 255.255.255.0 + # ip rule add from 10.0.0.14 table 4 + # ip route add table 4 default via 10.0.0.254 src 10.0.0.14 dev eth0.3 + # sctp_darn -H 10.0.0.14 -P 36422 -h 10.1.4.134 -p 36422 -s -I +You'll detect that all the flow are routed to eth0.2(10.0.1.254). + +Signed-off-by: Xufeng Zhang +Signed-off-by: Julian Anastasov +Acked-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/sctp/protocol.c | 7 ++++++- + 1 file changed, 6 insertions(+), 1 deletion(-) + +--- a/net/sctp/protocol.c ++++ b/net/sctp/protocol.c +@@ -491,8 +491,13 @@ static void sctp_v4_get_dst(struct sctp_ + continue; + if ((laddr->state == SCTP_ADDR_SRC) && + (AF_INET == laddr->a.sa.sa_family)) { +- fl4->saddr = laddr->a.v4.sin_addr.s_addr; + fl4->fl4_sport = laddr->a.v4.sin_port; ++ flowi4_update_output(fl4, ++ asoc->base.sk->sk_bound_dev_if, ++ RT_CONN_FLAGS(asoc->base.sk), ++ daddr->v4.sin_addr.s_addr, ++ laddr->a.v4.sin_addr.s_addr); ++ + rt = ip_route_output_key(sock_net(sk), fl4); + if (!IS_ERR(rt)) { + dst = &rt->dst; diff --git a/queue-3.14/series b/queue-3.14/series index 6d54c09e6cd..28b6f1b4bcd 100644 --- a/queue-3.14/series +++ b/queue-3.14/series @@ -62,3 +62,79 @@ drm-radeon-fix-endian-swap-on-hawaii-clear-state-buffer-setup.patch drm-radeon-fix-typo-in-spectre_golden_registers.patch drm-i915-tv-fix-gen4-composite-s-video-tv-out.patch drm-i915-do-not-dereference-pointers-from-ring-buffer-in-evict-event.patch +net-sctp-wake-up-all-assocs-if-sndbuf-policy-is-per-socket.patch +net-sctp-test-if-association-is-dead-in-sctp_wake_up_waiters.patch +l2tp-take-pmtu-from-tunnel-udp-socket.patch +net-core-don-t-account-for-udp-header-size-when-computing-seglen.patch +bonding-remove-debug_fs-files-when-module-init-fails.patch +bridge-fix-double-free-and-memory-leak-around-br_allowed_ingress.patch +ipv6-limit-mtu-to-65575-bytes.patch +gre-don-t-allow-to-add-the-same-tunnel-twice.patch +vti-don-t-allow-to-add-the-same-tunnel-twice.patch +net-ipv4-current-group_info-should-be-put-after-using.patch +ipv4-return-valid-rta_iif-on-ip-route-get.patch +filter-prevent-nla-extensions-to-peek-beyond-the-end-of-the-message.patch +revert-net-sctp-fix-a_rwnd-rwnd-management-to-reflect-real-state-of-the-receiver-s-buffer.patch +net-start-with-correct-mac_len-in-skb_network_protocol.patch +ip6_gre-don-t-allow-to-remove-the-fb_tunnel_dev.patch +vlan-fix-lockdep-warning-when-vlan-dev-handle-notification.patch +net-find-the-nesting-level-of-a-given-device-by-type.patch +net-allow-for-more-then-a-single-subclass-for.patch +vlan-fix-lockdep-warning-with-stacked-vlan-devices.patch +macvlan-fix-lockdep-warnings-with-stacked-macvlan.patch +tg3-update-rx_jumbo_pending-ring-param-only-when.patch +net-sctp-cache-auth_enable-per-endpoint.patch +net-fix-ns_capable-check-in-sock_diag_put_filterinfo.patch +rtnetlink-warn-when-interface-s-information-won-t-fit.patch +rtnetlink-only-supply-ifla_vf_ports-information-when.patch +ipv6-fib-fix-fib-dump-restart.patch +bridge-handle-ifla_address-correctly-when-creating.patch +sctp-reset-flowi4_oif-parameter-on-route-lookup.patch +net-qmi_wwan-add-sierra-wireless-em7355.patch +net-qmi_wwan-add-sierra-wireless-mc73xx.patch +net-qmi_wwan-add-sierra-wireless-mc7305-mc7355.patch +net-qmi_wwan-add-olivetti-olicard-500.patch +net-qmi_wwan-add-alcatel-l800ma.patch +net-qmi_wwan-add-a-number-of-cmotech-devices.patch +net-qmi_wwan-add-a-number-of-dell-devices.patch +slip-fix-spinlock-variant.patch +net-sctp-don-t-transition-to-pf-state-when-transport.patch +mactap-fix-checksum-errors-for-non-gso-packets-in.patch +revert-macvlan-fix-checksums-error-when-we-are-in.patch +tcp_cubic-fix-the-range-of-delayed_ack.patch +net-sched-lock-imbalance-in-hhf-qdisc.patch +vsock-make-transport-the-proto-owner.patch +net-cdc_ncm-fix-buffer-overflow.patch +net-mlx4_core-don-t-issue-pcie-speed-width-checks-for.patch +ip_tunnel-set-network-header-properly-for.patch +ipv4-ip_tunnels-disable-cache-for-nbma-gre-tunnels.patch +net-cdc_mbim-__vlan_find_dev_deep-need-rcu_read_lock.patch +net-ipv4-ip_forward-fix-inverted-local_df-test.patch +net-ipv6-send-pkttoobig-immediately-if-orig-frag.patch +ipv4-fib_semantics-increment-fib_info_cnt-after.patch +net-cdc_mbim-handle-unaccelerated-vlan-tagged-frames.patch +macvlan-don-t-propagate-iff_allmulti-changes-on-down.patch +sfc-fix-calling-of-free_irq-with-already-free-vector.patch +ip6_tunnel-fix-potential-null-pointer-dereference.patch +neigh-set-nud_state-to-nud_incomplete-when-probing.patch +batman-adv-fix-neigh_ifinfo-imbalance.patch +batman-adv-fix-neigh-reference-imbalance.patch +batman-adv-always-run-purge_orig_neighbors.patch +batman-adv-fix-removing-neigh_ifinfo.patch +net-filter-x86-fix-jit-address-randomization.patch +net-filter-s390-fix-jit-address-randomization.patch +net-avoid-dependency-of-net_get_random_once-on-nop.patch +ipv6-fix-calculation-of-option-len-in-ip6_append_data.patch +rtnetlink-wait-for-unregistering-devices-in.patch +net-phy-don-t-call-phy_resume-if-phy_init_hw-failed.patch +bonding-fix-out-of-range-parameters-for.patch +net-gro-make-sure-skb-cb-initial-content-has-not.patch +batman-adv-fix-indirect-hard_iface-null-dereference.patch +batman-adv-fix-reference-counting-imbalance-while.patch +batman-adv-increase-orig-refcount-when-storing-ref-in.patch +batman-adv-fix-local-tt-check-for-outgoing-arp.patch +ip_tunnel-initialize-the-fallback-device-properly.patch +net_sched-fix-an-oops-in-tcindex-filter.patch +ipv6-gro-fix-checksum_complete-support.patch +ipv4-initialise-the-itag-variable-in-__mkroute_input.patch +net-gro-reset-skb-truesize-in-napi_reuse_skb.patch diff --git a/queue-3.14/sfc-fix-calling-of-free_irq-with-already-free-vector.patch b/queue-3.14/sfc-fix-calling-of-free_irq-with-already-free-vector.patch new file mode 100644 index 00000000000..f23b44c18ce --- /dev/null +++ b/queue-3.14/sfc-fix-calling-of-free_irq-with-already-free-vector.patch @@ -0,0 +1,56 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Nikolay Aleksandrov +Date: Fri, 9 May 2014 11:11:39 +0200 +Subject: sfc: fix calling of free_irq with already free vector + +From: Nikolay Aleksandrov + +[ Upstream commit 1c3639005f48492e5f2d965779efd814e80f8b15 ] + +If the sfc driver is in legacy interrupt mode (either explicitly by +using interrupt_mode module param or by falling back to it) it will +hit a warning at kernel/irq/manage.c because it will try to free an irq +which wasn't allocated by it in the first place because the MSI(X) irqs are +zero and it'll try to free them unconditionally. So fix it by checking if +we're in legacy mode and freeing the appropriate irqs. + +CC: Zenghui Shi +CC: Ben Hutchings +CC: +CC: Shradha Shah +CC: David S. Miller + +Fixes: 1899c111a535 ("sfc: Fix IRQ cleanup in case of a probe failure") +Reported-by: Zenghui Shi +Signed-off-by: Nikolay Aleksandrov +Acked-by: Shradha Shah +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/ethernet/sfc/nic.c | 14 ++++++++------ + 1 file changed, 8 insertions(+), 6 deletions(-) + +--- a/drivers/net/ethernet/sfc/nic.c ++++ b/drivers/net/ethernet/sfc/nic.c +@@ -156,13 +156,15 @@ void efx_nic_fini_interrupt(struct efx_n + efx->net_dev->rx_cpu_rmap = NULL; + #endif + +- /* Disable MSI/MSI-X interrupts */ +- efx_for_each_channel(channel, efx) +- free_irq(channel->irq, &efx->msi_context[channel->channel]); +- +- /* Disable legacy interrupt */ +- if (efx->legacy_irq) ++ if (EFX_INT_MODE_USE_MSI(efx)) { ++ /* Disable MSI/MSI-X interrupts */ ++ efx_for_each_channel(channel, efx) ++ free_irq(channel->irq, ++ &efx->msi_context[channel->channel]); ++ } else { ++ /* Disable legacy interrupt */ + free_irq(efx->legacy_irq, efx); ++ } + } + + /* Register dump */ diff --git a/queue-3.14/slip-fix-spinlock-variant.patch b/queue-3.14/slip-fix-spinlock-variant.patch new file mode 100644 index 00000000000..ae01f68270b --- /dev/null +++ b/queue-3.14/slip-fix-spinlock-variant.patch @@ -0,0 +1,53 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Oliver Hartkopp +Date: Sat, 26 Apr 2014 21:18:32 +0200 +Subject: slip: fix spinlock variant + +From: Oliver Hartkopp + +[ Upstream commit ddcde142bed44490e338ed1124cb149976d355bb ] + +With commit cc9fa74e2a ("slip/slcan: added locking in wakeup function") a +formerly missing locking was added to slip.c and slcan.c by Andre Naujoks. + +Alexander Stein contributed the fix 367525c8c2 ("can: slcan: Fix spinlock +variant") as the kernel lock debugging advised to use spin_lock_bh() instead +of just using spin_lock(). + +This fix has to be applied to the same code section in slip.c for the same +reason too. + +Signed-off-by: Oliver Hartkopp +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/slip/slip.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +--- a/drivers/net/slip/slip.c ++++ b/drivers/net/slip/slip.c +@@ -429,13 +429,13 @@ static void slip_write_wakeup(struct tty + if (!sl || sl->magic != SLIP_MAGIC || !netif_running(sl->dev)) + return; + +- spin_lock(&sl->lock); ++ spin_lock_bh(&sl->lock); + if (sl->xleft <= 0) { + /* Now serial buffer is almost free & we can start + * transmission of another packet */ + sl->dev->stats.tx_packets++; + clear_bit(TTY_DO_WRITE_WAKEUP, &tty->flags); +- spin_unlock(&sl->lock); ++ spin_unlock_bh(&sl->lock); + sl_unlock(sl); + return; + } +@@ -443,7 +443,7 @@ static void slip_write_wakeup(struct tty + actual = tty->ops->write(tty, sl->xhead, sl->xleft); + sl->xleft -= actual; + sl->xhead += actual; +- spin_unlock(&sl->lock); ++ spin_unlock_bh(&sl->lock); + } + + static void sl_tx_timeout(struct net_device *dev) diff --git a/queue-3.14/tcp_cubic-fix-the-range-of-delayed_ack.patch b/queue-3.14/tcp_cubic-fix-the-range-of-delayed_ack.patch new file mode 100644 index 00000000000..5ae91eaa578 --- /dev/null +++ b/queue-3.14/tcp_cubic-fix-the-range-of-delayed_ack.patch @@ -0,0 +1,44 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Liu Yu +Date: Wed, 30 Apr 2014 17:34:09 +0800 +Subject: tcp_cubic: fix the range of delayed_ack + +From: Liu Yu + +[ Upstream commit 0cda345d1b2201dd15591b163e3c92bad5191745 ] + +commit b9f47a3aaeab (tcp_cubic: limit delayed_ack ratio to prevent +divide error) try to prevent divide error, but there is still a little +chance that delayed_ack can reach zero. In case the param cnt get +negative value, then ratio+cnt would overflow and may happen to be zero. +As a result, min(ratio, ACK_RATIO_LIMIT) will calculate to be zero. + +In some old kernels, such as 2.6.32, there is a bug that would +pass negative param, which then ultimately leads to this divide error. + +commit 5b35e1e6e9c (tcp: fix tcp_trim_head() to adjust segment count +with skb MSS) fixed the negative param issue. However, +it's safe that we fix the range of delayed_ack as well, +to make sure we do not hit a divide by zero. + +CC: Stephen Hemminger +Signed-off-by: Liu Yu +Signed-off-by: Eric Dumazet +Acked-by: Neal Cardwell +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/tcp_cubic.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/tcp_cubic.c ++++ b/net/ipv4/tcp_cubic.c +@@ -409,7 +409,7 @@ static void bictcp_acked(struct sock *sk + ratio -= ca->delayed_ack >> ACK_RATIO_SHIFT; + ratio += cnt; + +- ca->delayed_ack = min(ratio, ACK_RATIO_LIMIT); ++ ca->delayed_ack = clamp(ratio, 1U, ACK_RATIO_LIMIT); + } + + /* Some calls are for duplicates without timetamps */ diff --git a/queue-3.14/tg3-update-rx_jumbo_pending-ring-param-only-when.patch b/queue-3.14/tg3-update-rx_jumbo_pending-ring-param-only-when.patch new file mode 100644 index 00000000000..ef4cebc9e49 --- /dev/null +++ b/queue-3.14/tg3-update-rx_jumbo_pending-ring-param-only-when.patch @@ -0,0 +1,43 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Ivan Vecera +Date: Thu, 17 Apr 2014 14:51:08 +0200 +Subject: tg3: update rx_jumbo_pending ring param only when + jumbo frames are enabled + +From: Ivan Vecera + +The patch fixes a problem with dropped jumbo frames after usage of +'ethtool -G ... rx'. + +Scenario: +1. ip link set eth0 up +2. ethtool -G eth0 rx N # <- This zeroes rx-jumbo +3. ip link set mtu 9000 dev eth0 + +The ethtool command set rx_jumbo_pending to zero so any received jumbo +packets are dropped and you need to use 'ethtool -G eth0 rx-jumbo N' +to workaround the issue. +The patch changes the logic so rx_jumbo_pending value is changed only if +jumbo frames are enabled (MTU > 1500). + +Signed-off-by: Ivan Vecera +Acked-by: Michael Chan +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/ethernet/broadcom/tg3.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/net/ethernet/broadcom/tg3.c ++++ b/drivers/net/ethernet/broadcom/tg3.c +@@ -12294,7 +12294,9 @@ static int tg3_set_ringparam(struct net_ + if (tg3_flag(tp, MAX_RXPEND_64) && + tp->rx_pending > 63) + tp->rx_pending = 63; +- tp->rx_jumbo_pending = ering->rx_jumbo_pending; ++ ++ if (tg3_flag(tp, JUMBO_RING_ENABLE)) ++ tp->rx_jumbo_pending = ering->rx_jumbo_pending; + + for (i = 0; i < tp->irq_max; i++) + tp->napi[i].tx_pending = ering->tx_pending; diff --git a/queue-3.14/vlan-fix-lockdep-warning-when-vlan-dev-handle-notification.patch b/queue-3.14/vlan-fix-lockdep-warning-when-vlan-dev-handle-notification.patch new file mode 100644 index 00000000000..cb6d8dd1d8b --- /dev/null +++ b/queue-3.14/vlan-fix-lockdep-warning-when-vlan-dev-handle-notification.patch @@ -0,0 +1,185 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: dingtianhong +Date: Thu, 17 Apr 2014 18:40:36 +0800 +Subject: vlan: Fix lockdep warning when vlan dev handle notification + +From: dingtianhong + +[ Upstream commit dc8eaaa006350d24030502a4521542e74b5cb39f ] + +When I open the LOCKDEP config and run these steps: + +modprobe 8021q +vconfig add eth2 20 +vconfig add eth2.20 30 +ifconfig eth2 xx.xx.xx.xx + +then the Call Trace happened: + +[32524.386288] ============================================= +[32524.386293] [ INFO: possible recursive locking detected ] +[32524.386298] 3.14.0-rc2-0.7-default+ #35 Tainted: G O +[32524.386302] --------------------------------------------- +[32524.386306] ifconfig/3103 is trying to acquire lock: +[32524.386310] (&vlan_netdev_addr_lock_key/1){+.....}, at: [] dev_mc_sync+0x64/0xb0 +[32524.386326] +[32524.386326] but task is already holding lock: +[32524.386330] (&vlan_netdev_addr_lock_key/1){+.....}, at: [] dev_set_rx_mode+0x23/0x40 +[32524.386341] +[32524.386341] other info that might help us debug this: +[32524.386345] Possible unsafe locking scenario: +[32524.386345] +[32524.386350] CPU0 +[32524.386352] ---- +[32524.386354] lock(&vlan_netdev_addr_lock_key/1); +[32524.386359] lock(&vlan_netdev_addr_lock_key/1); +[32524.386364] +[32524.386364] *** DEADLOCK *** +[32524.386364] +[32524.386368] May be due to missing lock nesting notation +[32524.386368] +[32524.386373] 2 locks held by ifconfig/3103: +[32524.386376] #0: (rtnl_mutex){+.+.+.}, at: [] rtnl_lock+0x12/0x20 +[32524.386387] #1: (&vlan_netdev_addr_lock_key/1){+.....}, at: [] dev_set_rx_mode+0x23/0x40 +[32524.386398] +[32524.386398] stack backtrace: +[32524.386403] CPU: 1 PID: 3103 Comm: ifconfig Tainted: G O 3.14.0-rc2-0.7-default+ #35 +[32524.386409] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2007 +[32524.386414] ffffffff81ffae40 ffff8800d9625ae8 ffffffff814f68a2 ffff8800d9625bc8 +[32524.386421] ffffffff810a35fb ffff8800d8a8d9d0 00000000d9625b28 ffff8800d8a8e5d0 +[32524.386428] 000003cc00000000 0000000000000002 ffff8800d8a8e5f8 0000000000000000 +[32524.386435] Call Trace: +[32524.386441] [] dump_stack+0x6a/0x78 +[32524.386448] [] __lock_acquire+0x7ab/0x1940 +[32524.386454] [] ? __lock_acquire+0x3ea/0x1940 +[32524.386459] [] lock_acquire+0xe4/0x110 +[32524.386464] [] ? dev_mc_sync+0x64/0xb0 +[32524.386471] [] _raw_spin_lock_nested+0x2a/0x40 +[32524.386476] [] ? dev_mc_sync+0x64/0xb0 +[32524.386481] [] dev_mc_sync+0x64/0xb0 +[32524.386489] [] vlan_dev_set_rx_mode+0x2b/0x50 [8021q] +[32524.386495] [] __dev_set_rx_mode+0x5f/0xb0 +[32524.386500] [] dev_set_rx_mode+0x2b/0x40 +[32524.386506] [] __dev_open+0xef/0x150 +[32524.386511] [] __dev_change_flags+0xa7/0x190 +[32524.386516] [] dev_change_flags+0x32/0x80 +[32524.386524] [] devinet_ioctl+0x7d6/0x830 +[32524.386532] [] ? dev_ioctl+0x34b/0x660 +[32524.386540] [] inet_ioctl+0x80/0xa0 +[32524.386550] [] sock_do_ioctl+0x2d/0x60 +[32524.386558] [] sock_ioctl+0x82/0x2a0 +[32524.386568] [] do_vfs_ioctl+0x93/0x590 +[32524.386578] [] ? rcu_read_lock_held+0x45/0x50 +[32524.386586] [] ? __fget_light+0x105/0x110 +[32524.386594] [] SyS_ioctl+0x91/0xb0 +[32524.386604] [] system_call_fastpath+0x16/0x1b + +======================================================================== + +The reason is that all of the addr_lock_key for vlan dev have the same class, +so if we change the status for vlan dev, the vlan dev and its real dev will +hold the same class of addr_lock_key together, so the warning happened. + +we should distinguish the lock depth for vlan dev and its real dev. + +v1->v2: Convert the vlan_netdev_addr_lock_key to an array of eight elements, which + could support to add 8 vlan id on a same vlan dev, I think it is enough for current + scene, because a netdev's name is limited to IFNAMSIZ which could not hold 8 vlan id, + and the vlan dev would not meet the same class key with its real dev. + + The new function vlan_dev_get_lockdep_subkey() will return the subkey and make the vlan + dev could get a suitable class key. + +v2->v3: According David's suggestion, I use the subclass to distinguish the lock key for vlan dev + and its real dev, but it make no sense, because the difference for subclass in the + lock_class_key doesn't mean that the difference class for lock_key, so I use lock_depth + to distinguish the different depth for every vlan dev, the same depth of the vlan dev + could have the same lock_class_key, I import the MAX_LOCK_DEPTH from the include/linux/sched.h, + I think it is enough here, the lockdep should never exceed that value. + +v3->v4: Add a huge array of locking keys will waste static kernel memory and is not a appropriate method, + we could use _nested() variants to fix the problem, calculate the depth for every vlan dev, + and use the depth as the subclass for addr_lock_key. + +Signed-off-by: Ding Tianhong +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/8021q/vlan_dev.c | 46 +++++++++++++++++++++++++++++++++++++++++----- + net/core/dev.c | 1 + + 2 files changed, 42 insertions(+), 5 deletions(-) + +--- a/net/8021q/vlan_dev.c ++++ b/net/8021q/vlan_dev.c +@@ -493,10 +493,48 @@ static void vlan_dev_change_rx_flags(str + } + } + ++static int vlan_calculate_locking_subclass(struct net_device *real_dev) ++{ ++ int subclass = 0; ++ ++ while (is_vlan_dev(real_dev)) { ++ subclass++; ++ real_dev = vlan_dev_priv(real_dev)->real_dev; ++ } ++ ++ return subclass; ++} ++ ++static void vlan_dev_mc_sync(struct net_device *to, struct net_device *from) ++{ ++ int err = 0, subclass; ++ ++ subclass = vlan_calculate_locking_subclass(to); ++ ++ spin_lock_nested(&to->addr_list_lock, subclass); ++ err = __hw_addr_sync(&to->mc, &from->mc, to->addr_len); ++ if (!err) ++ __dev_set_rx_mode(to); ++ spin_unlock(&to->addr_list_lock); ++} ++ ++static void vlan_dev_uc_sync(struct net_device *to, struct net_device *from) ++{ ++ int err = 0, subclass; ++ ++ subclass = vlan_calculate_locking_subclass(to); ++ ++ spin_lock_nested(&to->addr_list_lock, subclass); ++ err = __hw_addr_sync(&to->uc, &from->uc, to->addr_len); ++ if (!err) ++ __dev_set_rx_mode(to); ++ spin_unlock(&to->addr_list_lock); ++} ++ + static void vlan_dev_set_rx_mode(struct net_device *vlan_dev) + { +- dev_mc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); +- dev_uc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); ++ vlan_dev_mc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); ++ vlan_dev_uc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); + } + + /* +@@ -608,9 +646,7 @@ static int vlan_dev_init(struct net_devi + + SET_NETDEV_DEVTYPE(dev, &vlan_type); + +- if (is_vlan_dev(real_dev)) +- subclass = 1; +- ++ subclass = vlan_calculate_locking_subclass(dev); + vlan_dev_set_lockdep_class(dev, subclass); + + vlan_dev_priv(dev)->vlan_pcpu_stats = alloc_percpu(struct vlan_pcpu_stats); +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -5219,6 +5219,7 @@ void __dev_set_rx_mode(struct net_device + if (ops->ndo_set_rx_mode) + ops->ndo_set_rx_mode(dev); + } ++EXPORT_SYMBOL(__dev_set_rx_mode); + + void dev_set_rx_mode(struct net_device *dev) + { diff --git a/queue-3.14/vlan-fix-lockdep-warning-with-stacked-vlan-devices.patch b/queue-3.14/vlan-fix-lockdep-warning-with-stacked-vlan-devices.patch new file mode 100644 index 00000000000..414b3fd7283 --- /dev/null +++ b/queue-3.14/vlan-fix-lockdep-warning-with-stacked-vlan-devices.patch @@ -0,0 +1,158 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Vlad Yasevich +Date: Fri, 16 May 2014 17:04:55 -0400 +Subject: vlan: Fix lockdep warning with stacked vlan devices. + +From: Vlad Yasevich + +[ Upstream commit d38569ab2bba6e6b3233acfc3a84cdbcfbd1f79f ] + +This reverts commit dc8eaaa006350d24030502a4521542e74b5cb39f. + vlan: Fix lockdep warning when vlan dev handle notification + +Instead we use the new new API to find the lock subclass of +our vlan device. This way we can support configurations where +vlans are interspersed with other devices: + bond -> vlan -> macvlan -> vlan + +Signed-off-by: Vlad Yasevich +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/if_vlan.h | 3 +- + net/8021q/vlan.c | 1 + net/8021q/vlan_dev.c | 53 +++++++++--------------------------------------- + net/core/dev.c | 1 + 4 files changed, 13 insertions(+), 45 deletions(-) + +--- a/include/linux/if_vlan.h ++++ b/include/linux/if_vlan.h +@@ -73,7 +73,7 @@ static inline struct vlan_ethhdr *vlan_e + /* found in socket.c */ + extern void vlan_ioctl_set(int (*hook)(struct net *, void __user *)); + +-static inline int is_vlan_dev(struct net_device *dev) ++static inline bool is_vlan_dev(struct net_device *dev) + { + return dev->priv_flags & IFF_802_1Q_VLAN; + } +@@ -158,6 +158,7 @@ struct vlan_dev_priv { + #ifdef CONFIG_NET_POLL_CONTROLLER + struct netpoll *netpoll; + #endif ++ unsigned int nest_level; + }; + + static inline struct vlan_dev_priv *vlan_dev_priv(const struct net_device *dev) +--- a/net/8021q/vlan.c ++++ b/net/8021q/vlan.c +@@ -169,6 +169,7 @@ int register_vlan_dev(struct net_device + if (err < 0) + goto out_uninit_mvrp; + ++ vlan->nest_level = dev_get_nest_level(real_dev, is_vlan_dev) + 1; + err = register_netdevice(dev); + if (err < 0) + goto out_uninit_mvrp; +--- a/net/8021q/vlan_dev.c ++++ b/net/8021q/vlan_dev.c +@@ -493,48 +493,10 @@ static void vlan_dev_change_rx_flags(str + } + } + +-static int vlan_calculate_locking_subclass(struct net_device *real_dev) +-{ +- int subclass = 0; +- +- while (is_vlan_dev(real_dev)) { +- subclass++; +- real_dev = vlan_dev_priv(real_dev)->real_dev; +- } +- +- return subclass; +-} +- +-static void vlan_dev_mc_sync(struct net_device *to, struct net_device *from) +-{ +- int err = 0, subclass; +- +- subclass = vlan_calculate_locking_subclass(to); +- +- spin_lock_nested(&to->addr_list_lock, subclass); +- err = __hw_addr_sync(&to->mc, &from->mc, to->addr_len); +- if (!err) +- __dev_set_rx_mode(to); +- spin_unlock(&to->addr_list_lock); +-} +- +-static void vlan_dev_uc_sync(struct net_device *to, struct net_device *from) +-{ +- int err = 0, subclass; +- +- subclass = vlan_calculate_locking_subclass(to); +- +- spin_lock_nested(&to->addr_list_lock, subclass); +- err = __hw_addr_sync(&to->uc, &from->uc, to->addr_len); +- if (!err) +- __dev_set_rx_mode(to); +- spin_unlock(&to->addr_list_lock); +-} +- + static void vlan_dev_set_rx_mode(struct net_device *vlan_dev) + { +- vlan_dev_mc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); +- vlan_dev_uc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); ++ dev_mc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); ++ dev_uc_sync(vlan_dev_priv(vlan_dev)->real_dev, vlan_dev); + } + + /* +@@ -562,6 +524,11 @@ static void vlan_dev_set_lockdep_class(s + netdev_for_each_tx_queue(dev, vlan_dev_set_lockdep_one, &subclass); + } + ++static int vlan_dev_get_lock_subclass(struct net_device *dev) ++{ ++ return vlan_dev_priv(dev)->nest_level; ++} ++ + static const struct header_ops vlan_header_ops = { + .create = vlan_dev_hard_header, + .rebuild = vlan_dev_rebuild_header, +@@ -597,7 +564,7 @@ static const struct net_device_ops vlan_ + static int vlan_dev_init(struct net_device *dev) + { + struct net_device *real_dev = vlan_dev_priv(dev)->real_dev; +- int subclass = 0, i; ++ int i; + + netif_carrier_off(dev); + +@@ -646,8 +613,7 @@ static int vlan_dev_init(struct net_devi + + SET_NETDEV_DEVTYPE(dev, &vlan_type); + +- subclass = vlan_calculate_locking_subclass(dev); +- vlan_dev_set_lockdep_class(dev, subclass); ++ vlan_dev_set_lockdep_class(dev, vlan_dev_get_lock_subclass(dev)); + + vlan_dev_priv(dev)->vlan_pcpu_stats = alloc_percpu(struct vlan_pcpu_stats); + if (!vlan_dev_priv(dev)->vlan_pcpu_stats) +@@ -827,6 +793,7 @@ static const struct net_device_ops vlan_ + .ndo_netpoll_cleanup = vlan_dev_netpoll_cleanup, + #endif + .ndo_fix_features = vlan_dev_fix_features, ++ .ndo_get_lock_subclass = vlan_dev_get_lock_subclass, + }; + + void vlan_setup(struct net_device *dev) +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -5269,7 +5269,6 @@ void __dev_set_rx_mode(struct net_device + if (ops->ndo_set_rx_mode) + ops->ndo_set_rx_mode(dev); + } +-EXPORT_SYMBOL(__dev_set_rx_mode); + + void dev_set_rx_mode(struct net_device *dev) + { diff --git a/queue-3.14/vsock-make-transport-the-proto-owner.patch b/queue-3.14/vsock-make-transport-the-proto-owner.patch new file mode 100644 index 00000000000..ff0f6ba73e0 --- /dev/null +++ b/queue-3.14/vsock-make-transport-the-proto-owner.patch @@ -0,0 +1,119 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Andy King +Date: Thu, 1 May 2014 15:20:43 -0700 +Subject: vsock: Make transport the proto owner + +From: Andy King + +[ Upstream commit 2c4a336e0a3e203fab6aa8d8f7bb70a0ad968a6b ] + +Right now the core vsock module is the owner of the proto family. This +means there's nothing preventing the transport module from unloading if +there are open sockets, which results in a panic. Fix that by allowing +the transport to be the owner, which will refcount it properly. + +Includes version bump to 1.0.1.0-k + +Passes checkpatch this time, I swear... + +Acked-by: Dmitry Torokhov +Signed-off-by: Andy King +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + include/net/af_vsock.h | 6 +++++- + net/vmw_vsock/af_vsock.c | 47 ++++++++++++++++++++++------------------------- + 2 files changed, 27 insertions(+), 26 deletions(-) + +--- a/include/net/af_vsock.h ++++ b/include/net/af_vsock.h +@@ -155,7 +155,11 @@ struct vsock_transport { + + /**** CORE ****/ + +-int vsock_core_init(const struct vsock_transport *t); ++int __vsock_core_init(const struct vsock_transport *t, struct module *owner); ++static inline int vsock_core_init(const struct vsock_transport *t) ++{ ++ return __vsock_core_init(t, THIS_MODULE); ++} + void vsock_core_exit(void); + + /**** UTILS ****/ +--- a/net/vmw_vsock/af_vsock.c ++++ b/net/vmw_vsock/af_vsock.c +@@ -1925,9 +1925,23 @@ static struct miscdevice vsock_device = + .fops = &vsock_device_ops, + }; + +-static int __vsock_core_init(void) ++int __vsock_core_init(const struct vsock_transport *t, struct module *owner) + { +- int err; ++ int err = mutex_lock_interruptible(&vsock_register_mutex); ++ ++ if (err) ++ return err; ++ ++ if (transport) { ++ err = -EBUSY; ++ goto err_busy; ++ } ++ ++ /* Transport must be the owner of the protocol so that it can't ++ * unload while there are open sockets. ++ */ ++ vsock_proto.owner = owner; ++ transport = t; + + vsock_init_tables(); + +@@ -1951,36 +1965,19 @@ static int __vsock_core_init(void) + goto err_unregister_proto; + } + ++ mutex_unlock(&vsock_register_mutex); + return 0; + + err_unregister_proto: + proto_unregister(&vsock_proto); + err_misc_deregister: + misc_deregister(&vsock_device); +- return err; +-} +- +-int vsock_core_init(const struct vsock_transport *t) +-{ +- int retval = mutex_lock_interruptible(&vsock_register_mutex); +- if (retval) +- return retval; +- +- if (transport) { +- retval = -EBUSY; +- goto out; +- } +- +- transport = t; +- retval = __vsock_core_init(); +- if (retval) +- transport = NULL; +- +-out: ++ transport = NULL; ++err_busy: + mutex_unlock(&vsock_register_mutex); +- return retval; ++ return err; + } +-EXPORT_SYMBOL_GPL(vsock_core_init); ++EXPORT_SYMBOL_GPL(__vsock_core_init); + + void vsock_core_exit(void) + { +@@ -2000,5 +1997,5 @@ EXPORT_SYMBOL_GPL(vsock_core_exit); + + MODULE_AUTHOR("VMware, Inc."); + MODULE_DESCRIPTION("VMware Virtual Socket Family"); +-MODULE_VERSION("1.0.0.0-k"); ++MODULE_VERSION("1.0.1.0-k"); + MODULE_LICENSE("GPL v2"); diff --git a/queue-3.14/vti-don-t-allow-to-add-the-same-tunnel-twice.patch b/queue-3.14/vti-don-t-allow-to-add-the-same-tunnel-twice.patch new file mode 100644 index 00000000000..7f58b34d18f --- /dev/null +++ b/queue-3.14/vti-don-t-allow-to-add-the-same-tunnel-twice.patch @@ -0,0 +1,47 @@ +From foo@baz Wed May 28 21:03:54 PDT 2014 +From: Nicolas Dichtel +Date: Fri, 11 Apr 2014 15:51:19 +0200 +Subject: vti: don't allow to add the same tunnel twice + +From: Nicolas Dichtel + +[ Upstream commit 8d89dcdf80d88007647945a753821a06eb6cc5a5 ] + +Before the patch, it was possible to add two times the same tunnel: +ip l a vti1 type vti remote 10.16.0.121 local 10.16.0.249 key 41 +ip l a vti2 type vti remote 10.16.0.121 local 10.16.0.249 key 41 + +It was possible, because ip_tunnel_newlink() calls ip_tunnel_find() with the +argument dev->type, which was set only later (when calling ndo_init handler +in register_netdevice()). Let's set this type in the setup handler, which is +called before newlink handler. + +Introduced by commit b9959fd3b0fa ("vti: switch to new ip tunnel code"). + +CC: Cong Wang +CC: Steffen Klassert +Signed-off-by: Nicolas Dichtel +Signed-off-by: David S. Miller +Signed-off-by: Greg Kroah-Hartman +--- + net/ipv4/ip_vti.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/net/ipv4/ip_vti.c ++++ b/net/ipv4/ip_vti.c +@@ -207,6 +207,7 @@ static const struct net_device_ops vti_n + static void vti_tunnel_setup(struct net_device *dev) + { + dev->netdev_ops = &vti_netdev_ops; ++ dev->type = ARPHRD_TUNNEL; + ip_tunnel_setup(dev, vti_net_id); + } + +@@ -218,7 +219,6 @@ static int vti_tunnel_init(struct net_de + memcpy(dev->dev_addr, &iph->saddr, 4); + memcpy(dev->broadcast, &iph->daddr, 4); + +- dev->type = ARPHRD_TUNNEL; + dev->hard_header_len = LL_MAX_HEADER + sizeof(struct iphdr); + dev->mtu = ETH_DATA_LEN; + dev->flags = IFF_NOARP;