]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
3.10-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sat, 13 Jun 2015 17:01:59 +0000 (10:01 -0700)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sat, 13 Jun 2015 17:01:59 +0000 (10:01 -0700)
added patches:
bridge-fix-parsing-of-mldv2-reports.patch
ipv4-avoid-crashing-in-ip_error.patch
net-dp83640-fix-broken-calibration-routine.patch
net-phy-allow-eee-for-all-rgmii-variants.patch
net_sched-invoke-attach-after-setting-dev-qdisc.patch
udp-fix-behavior-of-wrong-checksums.patch
unix-caif-sk_socket-can-disappear-when-state-is-unlocked.patch
xen-netback-read-hotplug-script-once-at-start-of-day.patch

queue-3.10/bridge-fix-parsing-of-mldv2-reports.patch [new file with mode: 0644]
queue-3.10/ipv4-avoid-crashing-in-ip_error.patch [new file with mode: 0644]
queue-3.10/net-dp83640-fix-broken-calibration-routine.patch [new file with mode: 0644]
queue-3.10/net-phy-allow-eee-for-all-rgmii-variants.patch [new file with mode: 0644]
queue-3.10/net_sched-invoke-attach-after-setting-dev-qdisc.patch [new file with mode: 0644]
queue-3.10/series
queue-3.10/udp-fix-behavior-of-wrong-checksums.patch [new file with mode: 0644]
queue-3.10/unix-caif-sk_socket-can-disappear-when-state-is-unlocked.patch [new file with mode: 0644]
queue-3.10/xen-netback-read-hotplug-script-once-at-start-of-day.patch [new file with mode: 0644]

diff --git a/queue-3.10/bridge-fix-parsing-of-mldv2-reports.patch b/queue-3.10/bridge-fix-parsing-of-mldv2-reports.patch
new file mode 100644 (file)
index 0000000..e7a2555
--- /dev/null
@@ -0,0 +1,63 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Thadeu Lima de Souza Cascardo <cascardo@redhat.com>
+Date: Fri, 22 May 2015 12:18:59 -0300
+Subject: bridge: fix parsing of MLDv2 reports
+
+From: Thadeu Lima de Souza Cascardo <cascardo@redhat.com>
+
+[ Upstream commit 47cc84ce0c2fe75c99ea5963c4b5704dd78ead54 ]
+
+When more than a multicast address is present in a MLDv2 report, all but
+the first address is ignored, because the code breaks out of the loop if
+there has not been an error adding that address.
+
+This has caused failures when two guests connected through the bridge
+tried to communicate using IPv6. Neighbor discoveries would not be
+transmitted to the other guest when both used a link-local address and a
+static address.
+
+This only happens when there is a MLDv2 querier in the network.
+
+The fix will only break out of the loop when there is a failure adding a
+multicast address.
+
+The mdb before the patch:
+
+dev ovirtmgmt port vnet0 grp ff02::1:ff7d:6603 temp
+dev ovirtmgmt port vnet1 grp ff02::1:ff7d:6604 temp
+dev ovirtmgmt port bond0.86 grp ff02::2 temp
+
+After the patch:
+
+dev ovirtmgmt port vnet0 grp ff02::1:ff7d:6603 temp
+dev ovirtmgmt port vnet1 grp ff02::1:ff7d:6604 temp
+dev ovirtmgmt port bond0.86 grp ff02::fb temp
+dev ovirtmgmt port bond0.86 grp ff02::2 temp
+dev ovirtmgmt port bond0.86 grp ff02::d temp
+dev ovirtmgmt port vnet0 grp ff02::1:ff00:76 temp
+dev ovirtmgmt port bond0.86 grp ff02::16 temp
+dev ovirtmgmt port vnet1 grp ff02::1:ff00:77 temp
+dev ovirtmgmt port bond0.86 grp ff02::1:ff00:def temp
+dev ovirtmgmt port bond0.86 grp ff02::1:ffa1:40bf temp
+
+Fixes: 08b202b67264 ("bridge br_multicast: IPv6 MLD support.")
+Reported-by: Rik Theys <Rik.Theys@esat.kuleuven.be>
+Signed-off-by: Thadeu Lima de Souza Cascardo <cascardo@redhat.com>
+Tested-by: Rik Theys <Rik.Theys@esat.kuleuven.be>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/bridge/br_multicast.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/net/bridge/br_multicast.c
++++ b/net/bridge/br_multicast.c
+@@ -1007,7 +1007,7 @@ static int br_ip6_multicast_mld2_report(
+               err = br_ip6_multicast_add_group(br, port, &grec->grec_mca,
+                                                vid);
+-              if (!err)
++              if (err)
+                       break;
+       }
diff --git a/queue-3.10/ipv4-avoid-crashing-in-ip_error.patch b/queue-3.10/ipv4-avoid-crashing-in-ip_error.patch
new file mode 100644 (file)
index 0000000..f579a6f
--- /dev/null
@@ -0,0 +1,60 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: "Eric W. Biederman" <ebiederm@xmission.com>
+Date: Fri, 22 May 2015 04:58:12 -0500
+Subject: ipv4: Avoid crashing in ip_error
+
+From: "Eric W. Biederman" <ebiederm@xmission.com>
+
+[ Upstream commit 381c759d9916c42959515ad34a6d467e24a88e93 ]
+
+ip_error does not check if in_dev is NULL before dereferencing it.
+
+IThe following sequence of calls is possible:
+CPU A                          CPU B
+ip_rcv_finish
+    ip_route_input_noref()
+        ip_route_input_slow()
+                               inetdev_destroy()
+    dst_input()
+
+With the result that a network device can be destroyed while processing
+an input packet.
+
+A crash was triggered with only unicast packets in flight, and
+forwarding enabled on the only network device.   The error condition
+was created by the removal of the network device.
+
+As such it is likely the that error code was -EHOSTUNREACH, and the
+action taken by ip_error (if in_dev had been accessible) would have
+been to not increment any counters and to have tried and likely failed
+to send an icmp error as the network device is going away.
+
+Therefore handle this weird case by just dropping the packet if
+!in_dev.  It will result in dropping the packet sooner, and will not
+result in an actual change of behavior.
+
+Fixes: 251da4130115b ("ipv4: Cache ip_error() routes even when not forwarding.")
+Reported-by: Vittorio Gambaletta <linuxbugs@vittgam.net>
+Tested-by: Vittorio Gambaletta <linuxbugs@vittgam.net>
+Signed-off-by: Vittorio Gambaletta <linuxbugs@vittgam.net>
+Signed-off-by: "Eric W. Biederman" <ebiederm@xmission.com>
+Acked-by: Eric Dumazet <edumazet@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv4/route.c |    4 ++++
+ 1 file changed, 4 insertions(+)
+
+--- a/net/ipv4/route.c
++++ b/net/ipv4/route.c
+@@ -871,6 +871,10 @@ static int ip_error(struct sk_buff *skb)
+       bool send;
+       int code;
++      /* IP on this device is disabled. */
++      if (!in_dev)
++              goto out;
++
+       net = dev_net(rt->dst.dev);
+       if (!IN_DEV_FORWARD(in_dev)) {
+               switch (rt->dst.error) {
diff --git a/queue-3.10/net-dp83640-fix-broken-calibration-routine.patch b/queue-3.10/net-dp83640-fix-broken-calibration-routine.patch
new file mode 100644 (file)
index 0000000..d0532d2
--- /dev/null
@@ -0,0 +1,38 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Richard Cochran <richardcochran@gmail.com>
+Date: Mon, 25 May 2015 11:55:43 +0200
+Subject: net: dp83640: fix broken calibration routine.
+
+From: Richard Cochran <richardcochran@gmail.com>
+
+[ Upstream commit 397a253af5031de4a4612210055935309af4472c ]
+
+Currently, the calibration function that corrects the initial offsets
+among multiple devices only works the first time.  If the function is
+called more than once, the calibration fails and bogus offsets will be
+programmed into the devices.
+
+In a well hidden spot, the device documentation tells that trigger indexes
+0 and 1 are special in allowing the TRIG_IF_LATE flag to actually work.
+
+This patch fixes the issue by using one of the special triggers during the
+recalibration method.
+
+Signed-off-by: Richard Cochran <richardcochran@gmail.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/phy/dp83640.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/net/phy/dp83640.c
++++ b/drivers/net/phy/dp83640.c
+@@ -45,7 +45,7 @@
+ #define PSF_TX                0x1000
+ #define EXT_EVENT     1
+ #define CAL_EVENT     7
+-#define CAL_TRIGGER   7
++#define CAL_TRIGGER   1
+ #define PER_TRIGGER   6
+ #define MII_DP83640_MICR 0x11
diff --git a/queue-3.10/net-phy-allow-eee-for-all-rgmii-variants.patch b/queue-3.10/net-phy-allow-eee-for-all-rgmii-variants.patch
new file mode 100644 (file)
index 0000000..f2f1e34
--- /dev/null
@@ -0,0 +1,44 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Florian Fainelli <f.fainelli@gmail.com>
+Date: Fri, 15 May 2015 16:30:41 -0700
+Subject: net: phy: Allow EEE for all RGMII variants
+
+From: Florian Fainelli <f.fainelli@gmail.com>
+
+[ Upstream commit 7e14069651591c81046ffaec13c3dac8cb70f5fb ]
+
+RGMII interfaces come in multiple flavors: RGMII with transmit or
+receive internal delay, no delays at all, or delays in both direction.
+
+This change extends the initial check for PHY_INTERFACE_MODE_RGMII to
+cover all of these variants since EEE should be allowed for any of these
+modes, since it is a property of the RGMII, hence Gigabit PHY capability
+more than the RGMII electrical interface and its delays.
+
+Fixes: a59a4d192166 ("phy: add the EEE support and the way to access to the MMD registers")
+Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/phy/phy.c |    6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/net/phy/phy.c
++++ b/drivers/net/phy/phy.c
+@@ -1022,12 +1022,14 @@ int phy_init_eee(struct phy_device *phyd
+       /* According to 802.3az,the EEE is supported only in full duplex-mode.
+        * Also EEE feature is active when core is operating with MII, GMII
+-       * or RGMII.
++       * or RGMII (all kinds). Internal PHYs are also allowed to proceed and
++       * should return an error if they do not support EEE.
+        */
+       if ((phydev->duplex == DUPLEX_FULL) &&
+           ((phydev->interface == PHY_INTERFACE_MODE_MII) ||
+           (phydev->interface == PHY_INTERFACE_MODE_GMII) ||
+-          (phydev->interface == PHY_INTERFACE_MODE_RGMII))) {
++           (phydev->interface >= PHY_INTERFACE_MODE_RGMII &&
++            phydev->interface <= PHY_INTERFACE_MODE_RGMII_TXID))) {
+               int eee_lp, eee_cap, eee_adv;
+               u32 lp, cap, adv;
+               int status;
diff --git a/queue-3.10/net_sched-invoke-attach-after-setting-dev-qdisc.patch b/queue-3.10/net_sched-invoke-attach-after-setting-dev-qdisc.patch
new file mode 100644 (file)
index 0000000..c0ecac8
--- /dev/null
@@ -0,0 +1,110 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: WANG Cong <xiyou.wangcong@gmail.com>
+Date: Tue, 26 May 2015 16:08:48 -0700
+Subject: net_sched: invoke ->attach() after setting dev->qdisc
+
+From: WANG Cong <xiyou.wangcong@gmail.com>
+
+[ Upstream commit 86e363dc3b50bfd50a1f315934583fbda673ab8d ]
+
+For mq qdisc, we add per tx queue qdisc to root qdisc
+for display purpose, however, that happens too early,
+before the new dev->qdisc is finally set, this causes
+q->list points to an old root qdisc which is going to be
+freed right before assigning with a new one.
+
+Fix this by moving ->attach() after setting dev->qdisc.
+
+For the record, this fixes the following crash:
+
+ ------------[ cut here ]------------
+ WARNING: CPU: 1 PID: 975 at lib/list_debug.c:59 __list_del_entry+0x5a/0x98()
+ list_del corruption. prev->next should be ffff8800d1998ae8, but was 6b6b6b6b6b6b6b6b
+ CPU: 1 PID: 975 Comm: tc Not tainted 4.1.0-rc4+ #1019
+ Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
+  0000000000000009 ffff8800d73fb928 ffffffff81a44e7f 0000000047574756
+  ffff8800d73fb978 ffff8800d73fb968 ffffffff810790da ffff8800cfc4cd20
+  ffffffff814e725b ffff8800d1998ae8 ffffffff82381250 0000000000000000
+ Call Trace:
+  [<ffffffff81a44e7f>] dump_stack+0x4c/0x65
+  [<ffffffff810790da>] warn_slowpath_common+0x9c/0xb6
+  [<ffffffff814e725b>] ? __list_del_entry+0x5a/0x98
+  [<ffffffff81079162>] warn_slowpath_fmt+0x46/0x48
+  [<ffffffff81820eb0>] ? dev_graft_qdisc+0x5e/0x6a
+  [<ffffffff814e725b>] __list_del_entry+0x5a/0x98
+  [<ffffffff814e72a7>] list_del+0xe/0x2d
+  [<ffffffff81822f05>] qdisc_list_del+0x1e/0x20
+  [<ffffffff81820cd1>] qdisc_destroy+0x30/0xd6
+  [<ffffffff81822676>] qdisc_graft+0x11d/0x243
+  [<ffffffff818233c1>] tc_get_qdisc+0x1a6/0x1d4
+  [<ffffffff810b5eaf>] ? mark_lock+0x2e/0x226
+  [<ffffffff817ff8f5>] rtnetlink_rcv_msg+0x181/0x194
+  [<ffffffff817ff72e>] ? rtnl_lock+0x17/0x19
+  [<ffffffff817ff72e>] ? rtnl_lock+0x17/0x19
+  [<ffffffff817ff774>] ? __rtnl_unlock+0x17/0x17
+  [<ffffffff81855dc6>] netlink_rcv_skb+0x4d/0x93
+  [<ffffffff817ff756>] rtnetlink_rcv+0x26/0x2d
+  [<ffffffff818544b2>] netlink_unicast+0xcb/0x150
+  [<ffffffff81161db9>] ? might_fault+0x59/0xa9
+  [<ffffffff81854f78>] netlink_sendmsg+0x4fa/0x51c
+  [<ffffffff817d6e09>] sock_sendmsg_nosec+0x12/0x1d
+  [<ffffffff817d8967>] sock_sendmsg+0x29/0x2e
+  [<ffffffff817d8cf3>] ___sys_sendmsg+0x1b4/0x23a
+  [<ffffffff8100a1b8>] ? native_sched_clock+0x35/0x37
+  [<ffffffff810a1d83>] ? sched_clock_local+0x12/0x72
+  [<ffffffff810a1fd4>] ? sched_clock_cpu+0x9e/0xb7
+  [<ffffffff810def2a>] ? current_kernel_time+0xe/0x32
+  [<ffffffff810b4bc5>] ? lock_release_holdtime.part.29+0x71/0x7f
+  [<ffffffff810ddebf>] ? read_seqcount_begin.constprop.27+0x5f/0x76
+  [<ffffffff810b6292>] ? trace_hardirqs_on_caller+0x17d/0x199
+  [<ffffffff811b14d5>] ? __fget_light+0x50/0x78
+  [<ffffffff817d9808>] __sys_sendmsg+0x42/0x60
+  [<ffffffff817d9838>] SyS_sendmsg+0x12/0x1c
+  [<ffffffff81a50e97>] system_call_fastpath+0x12/0x6f
+ ---[ end trace ef29d3fb28e97ae7 ]---
+
+For long term, we probably need to clean up the qdisc_graft() code
+in case it hides other bugs like this.
+
+Fixes: 95dc19299f74 ("pkt_sched: give visibility to mq slave qdiscs")
+Cc: Jamal Hadi Salim <jhs@mojatatu.com>
+Signed-off-by: Cong Wang <xiyou.wangcong@gmail.com>
+Acked-by: Eric Dumazet <edumazet@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/sched/sch_api.c |   10 ++++++----
+ 1 file changed, 6 insertions(+), 4 deletions(-)
+
+--- a/net/sched/sch_api.c
++++ b/net/sched/sch_api.c
+@@ -752,10 +752,8 @@ static int qdisc_graft(struct net_device
+               if (dev->flags & IFF_UP)
+                       dev_deactivate(dev);
+-              if (new && new->ops->attach) {
+-                      new->ops->attach(new);
+-                      num_q = 0;
+-              }
++              if (new && new->ops->attach)
++                      goto skip;
+               for (i = 0; i < num_q; i++) {
+                       struct netdev_queue *dev_queue = dev_ingress_queue(dev);
+@@ -771,12 +769,16 @@ static int qdisc_graft(struct net_device
+                               qdisc_destroy(old);
+               }
++skip:
+               if (!ingress) {
+                       notify_and_destroy(net, skb, n, classid,
+                                          dev->qdisc, new);
+                       if (new && !new->ops->attach)
+                               atomic_inc(&new->refcnt);
+                       dev->qdisc = new ? : &noop_qdisc;
++
++                      if (new && new->ops->attach)
++                              new->ops->attach(new);
+               } else {
+                       notify_and_destroy(net, skb, n, classid, old, new);
+               }
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..e02d7a41625b5b8edfc926fd175383ac5d5e0ec8 100644 (file)
@@ -0,0 +1,8 @@
+net-phy-allow-eee-for-all-rgmii-variants.patch
+ipv4-avoid-crashing-in-ip_error.patch
+bridge-fix-parsing-of-mldv2-reports.patch
+net-dp83640-fix-broken-calibration-routine.patch
+unix-caif-sk_socket-can-disappear-when-state-is-unlocked.patch
+net_sched-invoke-attach-after-setting-dev-qdisc.patch
+udp-fix-behavior-of-wrong-checksums.patch
+xen-netback-read-hotplug-script-once-at-start-of-day.patch
diff --git a/queue-3.10/udp-fix-behavior-of-wrong-checksums.patch b/queue-3.10/udp-fix-behavior-of-wrong-checksums.patch
new file mode 100644 (file)
index 0000000..bb8ed91
--- /dev/null
@@ -0,0 +1,63 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Eric Dumazet <edumazet@google.com>
+Date: Sat, 30 May 2015 09:16:53 -0700
+Subject: udp: fix behavior of wrong checksums
+
+From: Eric Dumazet <edumazet@google.com>
+
+[ Upstream commit beb39db59d14990e401e235faf66a6b9b31240b0 ]
+
+We have two problems in UDP stack related to bogus checksums :
+
+1) We return -EAGAIN to application even if receive queue is not empty.
+   This breaks applications using edge trigger epoll()
+
+2) Under UDP flood, we can loop forever without yielding to other
+   processes, potentially hanging the host, especially on non SMP.
+
+This patch is an attempt to make things better.
+
+We might in the future add extra support for rt applications
+wanting to better control time spent doing a recv() in a hostile
+environment. For example we could validate checksums before queuing
+packets in socket receive queue.
+
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Cc: Willem de Bruijn <willemb@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv4/udp.c |    6 ++----
+ net/ipv6/udp.c |    6 ++----
+ 2 files changed, 4 insertions(+), 8 deletions(-)
+
+--- a/net/ipv4/udp.c
++++ b/net/ipv4/udp.c
+@@ -1293,10 +1293,8 @@ csum_copy_err:
+       }
+       unlock_sock_fast(sk, slow);
+-      if (noblock)
+-              return -EAGAIN;
+-
+-      /* starting over for a new packet */
++      /* starting over for a new packet, but check if we need to yield */
++      cond_resched();
+       msg->msg_flags &= ~MSG_TRUNC;
+       goto try_again;
+ }
+--- a/net/ipv6/udp.c
++++ b/net/ipv6/udp.c
+@@ -494,10 +494,8 @@ csum_copy_err:
+       }
+       unlock_sock_fast(sk, slow);
+-      if (noblock)
+-              return -EAGAIN;
+-
+-      /* starting over for a new packet */
++      /* starting over for a new packet, but check if we need to yield */
++      cond_resched();
+       msg->msg_flags &= ~MSG_TRUNC;
+       goto try_again;
+ }
diff --git a/queue-3.10/unix-caif-sk_socket-can-disappear-when-state-is-unlocked.patch b/queue-3.10/unix-caif-sk_socket-can-disappear-when-state-is-unlocked.patch
new file mode 100644 (file)
index 0000000..bdb1e3e
--- /dev/null
@@ -0,0 +1,71 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Mark Salyzyn <salyzyn@android.com>
+Date: Tue, 26 May 2015 08:22:19 -0700
+Subject: unix/caif: sk_socket can disappear when state is unlocked
+
+From: Mark Salyzyn <salyzyn@android.com>
+
+[ Upstream commit b48732e4a48d80ed4a14812f0bab09560846514e ]
+
+got a rare NULL pointer dereference in clear_bit
+
+Signed-off-by: Mark Salyzyn <salyzyn@android.com>
+Acked-by: Hannes Frederic Sowa <hannes@stressinduktion.org>
+----
+v2: switch to sock_flag(sk, SOCK_DEAD) and added net/caif/caif_socket.c
+v3: return -ECONNRESET in upstream caller of wait function for SOCK_DEAD
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/caif/caif_socket.c |    8 ++++++++
+ net/unix/af_unix.c     |    8 ++++++++
+ 2 files changed, 16 insertions(+)
+
+--- a/net/caif/caif_socket.c
++++ b/net/caif/caif_socket.c
+@@ -332,6 +332,10 @@ static long caif_stream_data_wait(struct
+               release_sock(sk);
+               timeo = schedule_timeout(timeo);
+               lock_sock(sk);
++
++              if (sock_flag(sk, SOCK_DEAD))
++                      break;
++
+               clear_bit(SOCK_ASYNC_WAITDATA, &sk->sk_socket->flags);
+       }
+@@ -376,6 +380,10 @@ static int caif_stream_recvmsg(struct ki
+               struct sk_buff *skb;
+               lock_sock(sk);
++              if (sock_flag(sk, SOCK_DEAD)) {
++                      err = -ECONNRESET;
++                      goto unlock;
++              }
+               skb = skb_dequeue(&sk->sk_receive_queue);
+               caif_check_flow_release(sk);
+--- a/net/unix/af_unix.c
++++ b/net/unix/af_unix.c
+@@ -1898,6 +1898,10 @@ static long unix_stream_data_wait(struct
+               unix_state_unlock(sk);
+               timeo = schedule_timeout(timeo);
+               unix_state_lock(sk);
++
++              if (sock_flag(sk, SOCK_DEAD))
++                      break;
++
+               clear_bit(SOCK_ASYNC_WAITDATA, &sk->sk_socket->flags);
+       }
+@@ -1957,6 +1961,10 @@ static int unix_stream_recvmsg(struct ki
+               struct sk_buff *skb, *last;
+               unix_state_lock(sk);
++              if (sock_flag(sk, SOCK_DEAD)) {
++                      err = -ECONNRESET;
++                      goto unlock;
++              }
+               last = skb = skb_peek(&sk->sk_receive_queue);
+ again:
+               if (skb == NULL) {
diff --git a/queue-3.10/xen-netback-read-hotplug-script-once-at-start-of-day.patch b/queue-3.10/xen-netback-read-hotplug-script-once-at-start-of-day.patch
new file mode 100644 (file)
index 0000000..35e8bfc
--- /dev/null
@@ -0,0 +1,117 @@
+From foo@baz Sat Jun 13 09:49:42 PDT 2015
+From: Ian Campbell <Ian.Campbell@citrix.com>
+Date: Mon, 1 Jun 2015 11:30:24 +0100
+Subject: xen: netback: read hotplug script once at start of day.
+
+From: Ian Campbell <Ian.Campbell@citrix.com>
+
+[ Upstream commit 31a418986a5852034d520a5bab546821ff1ccf3d ]
+
+When we come to tear things down in netback_remove() and generate the
+uevent it is possible that the xenstore directory has already been
+removed (details below).
+
+In such cases netback_uevent() won't be able to read the hotplug
+script and will write a xenstore error node.
+
+A recent change to the hypervisor exposed this race such that we now
+sometimes lose it (where apparently we didn't ever before).
+
+Instead read the hotplug script configuration during setup and use it
+for the lifetime of the backend device.
+
+The apparently more obvious fix of moving the transition to
+state=Closed in netback_remove() to after the uevent does not work
+because it is possible that we are already in state=Closed (in
+reaction to the guest having disconnected as it shutdown). Being
+already in Closed means the toolstack is at liberty to start tearing
+down the xenstore directories. In principal it might be possible to
+arrange to unregister the device sooner (e.g on transition to Closing)
+such that xenstore would still be there but this state machine is
+fragile and prone to anger...
+
+A modern Xen system only relies on the hotplug uevent for driver
+domains, when the backend is in the same domain as the toolstack it
+will run the necessary setup/teardown directly in the correct sequence
+wrt xenstore changes.
+
+Signed-off-by: Ian Campbell <ian.campbell@citrix.com>
+Acked-by: Wei Liu <wei.liu2@citrix.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/xen-netback/xenbus.c |   33 +++++++++++++++++++--------------
+ 1 file changed, 19 insertions(+), 14 deletions(-)
+
+--- a/drivers/net/xen-netback/xenbus.c
++++ b/drivers/net/xen-netback/xenbus.c
+@@ -33,6 +33,8 @@ struct backend_info {
+       enum xenbus_state frontend_state;
+       struct xenbus_watch hotplug_status_watch;
+       u8 have_hotplug_status_watch:1;
++
++      const char *hotplug_script;
+ };
+ static int connect_rings(struct backend_info *);
+@@ -55,6 +57,7 @@ static int netback_remove(struct xenbus_
+               xenvif_free(be->vif);
+               be->vif = NULL;
+       }
++      kfree(be->hotplug_script);
+       kfree(be);
+       dev_set_drvdata(&dev->dev, NULL);
+       return 0;
+@@ -72,6 +75,7 @@ static int netback_probe(struct xenbus_d
+       struct xenbus_transaction xbt;
+       int err;
+       int sg;
++      const char *script;
+       struct backend_info *be = kzalloc(sizeof(struct backend_info),
+                                         GFP_KERNEL);
+       if (!be) {
+@@ -132,6 +136,15 @@ static int netback_probe(struct xenbus_d
+               goto fail;
+       }
++      script = xenbus_read(XBT_NIL, dev->nodename, "script", NULL);
++      if (IS_ERR(script)) {
++              err = PTR_ERR(script);
++              xenbus_dev_fatal(dev, err, "reading script");
++              goto fail;
++      }
++
++      be->hotplug_script = script;
++
+       err = xenbus_switch_state(dev, XenbusStateInitWait);
+       if (err)
+               goto fail;
+@@ -162,22 +175,14 @@ static int netback_uevent(struct xenbus_
+                         struct kobj_uevent_env *env)
+ {
+       struct backend_info *be = dev_get_drvdata(&xdev->dev);
+-      char *val;
+-      val = xenbus_read(XBT_NIL, xdev->nodename, "script", NULL);
+-      if (IS_ERR(val)) {
+-              int err = PTR_ERR(val);
+-              xenbus_dev_fatal(xdev, err, "reading script");
+-              return err;
+-      } else {
+-              if (add_uevent_var(env, "script=%s", val)) {
+-                      kfree(val);
+-                      return -ENOMEM;
+-              }
+-              kfree(val);
+-      }
++      if (!be)
++              return 0;
++
++      if (add_uevent_var(env, "script=%s", be->hotplug_script))
++              return -ENOMEM;
+-      if (!be || !be->vif)
++      if (!be->vif)
+               return 0;
+       return add_uevent_var(env, "vif=%s", be->vif->dev->name);