]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
3.10-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Fri, 27 Jun 2014 23:58:12 +0000 (16:58 -0700)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Fri, 27 Jun 2014 23:58:12 +0000 (16:58 -0700)
added patches:
arm-8037-1-mm-support-big-endian-page-tables.patch
arm-stacktrace-avoid-listing-stacktrace-functions-in-stacktrace.patch
bluetooth-fix-l2cap-deadlock.patch
bluetooth-hci_ldisc-fix-deadlock-condition.patch
media-uvcvideo-fix-clock-param-realtime-setting.patch
target-iser-bail-from-accept_np-if-np_thread-is-trying-to-close.patch
target-iser-fix-hangs-in-connection-teardown.patch

queue-3.10/arm-8037-1-mm-support-big-endian-page-tables.patch [new file with mode: 0644]
queue-3.10/arm-stacktrace-avoid-listing-stacktrace-functions-in-stacktrace.patch [new file with mode: 0644]
queue-3.10/bluetooth-fix-l2cap-deadlock.patch [new file with mode: 0644]
queue-3.10/bluetooth-hci_ldisc-fix-deadlock-condition.patch [new file with mode: 0644]
queue-3.10/media-uvcvideo-fix-clock-param-realtime-setting.patch [new file with mode: 0644]
queue-3.10/series
queue-3.10/target-iser-bail-from-accept_np-if-np_thread-is-trying-to-close.patch [new file with mode: 0644]
queue-3.10/target-iser-fix-hangs-in-connection-teardown.patch [new file with mode: 0644]

diff --git a/queue-3.10/arm-8037-1-mm-support-big-endian-page-tables.patch b/queue-3.10/arm-8037-1-mm-support-big-endian-page-tables.patch
new file mode 100644 (file)
index 0000000..9287506
--- /dev/null
@@ -0,0 +1,107 @@
+From 86f40622af7329375e38f282f6c0aab95f3e5f72 Mon Sep 17 00:00:00 2001
+From: Jianguo Wu <wujianguo@huawei.com>
+Date: Thu, 24 Apr 2014 03:45:56 +0100
+Subject: ARM: 8037/1: mm: support big-endian page tables
+
+From: Jianguo Wu <wujianguo@huawei.com>
+
+commit 86f40622af7329375e38f282f6c0aab95f3e5f72 upstream.
+
+When enable LPAE and big-endian in a hisilicon board, while specify
+mem=384M mem=512M@7680M, will get bad page state:
+
+Freeing unused kernel memory: 180K (c0466000 - c0493000)
+BUG: Bad page state in process init  pfn:fa442
+page:c7749840 count:0 mapcount:-1 mapping:  (null) index:0x0
+page flags: 0x40000400(reserved)
+Modules linked in:
+CPU: 0 PID: 1 Comm: init Not tainted 3.10.27+ #66
+[<c000f5f0>] (unwind_backtrace+0x0/0x11c) from [<c000cbc4>] (show_stack+0x10/0x14)
+[<c000cbc4>] (show_stack+0x10/0x14) from [<c009e448>] (bad_page+0xd4/0x104)
+[<c009e448>] (bad_page+0xd4/0x104) from [<c009e520>] (free_pages_prepare+0xa8/0x14c)
+[<c009e520>] (free_pages_prepare+0xa8/0x14c) from [<c009f8ec>] (free_hot_cold_page+0x18/0xf0)
+[<c009f8ec>] (free_hot_cold_page+0x18/0xf0) from [<c00b5444>] (handle_pte_fault+0xcf4/0xdc8)
+[<c00b5444>] (handle_pte_fault+0xcf4/0xdc8) from [<c00b6458>] (handle_mm_fault+0xf4/0x120)
+[<c00b6458>] (handle_mm_fault+0xf4/0x120) from [<c0013754>] (do_page_fault+0xfc/0x354)
+[<c0013754>] (do_page_fault+0xfc/0x354) from [<c0008400>] (do_DataAbort+0x2c/0x90)
+[<c0008400>] (do_DataAbort+0x2c/0x90) from [<c0008fb4>] (__dabt_usr+0x34/0x40)
+
+The bad pfn:fa442 is not system memory(mem=384M mem=512M@7680M), after debugging,
+I find in page fault handler, will get wrong pfn from pte just after set pte,
+as follow:
+do_anonymous_page()
+{
+       ...
+       set_pte_at(mm, address, page_table, entry);
+
+       //debug code
+       pfn = pte_pfn(entry);
+       pr_info("pfn:0x%lx, pte:0x%llxn", pfn, pte_val(entry));
+
+       //read out the pte just set
+       new_pte = pte_offset_map(pmd, address);
+       new_pfn = pte_pfn(*new_pte);
+       pr_info("new pfn:0x%lx, new pte:0x%llxn", pfn, pte_val(entry));
+       ...
+}
+
+pfn:   0x1fa4f5,     pte:0xc00001fa4f575f
+new_pfn:0xfa4f5, new_pte:0xc00000fa4f5f5f      //new pfn/pte is wrong.
+
+The bug is happened in cpu_v7_set_pte_ext(ptep, pte):
+An LPAE PTE is a 64bit quantity, passed to cpu_v7_set_pte_ext in the r2 and r3 registers.
+On an LE kernel, r2 contains the LSB of the PTE, and r3 the MSB.
+On a BE kernel, the assignment is reversed.
+
+Unfortunately, the current code always assumes the LE case,
+leading to corruption of the PTE when clearing/setting bits.
+
+This patch fixes this issue much like it has been done already in the
+cpu_v7_switch_mm case.
+
+Signed-off-by: Jianguo Wu <wujianguo@huawei.com>
+Acked-by: Marc Zyngier <marc.zyngier@arm.com>
+Acked-by: Will Deacon <will.deacon@arm.com>
+Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm/mm/proc-v7-3level.S |   18 +++++++++++++-----
+ 1 file changed, 13 insertions(+), 5 deletions(-)
+
+--- a/arch/arm/mm/proc-v7-3level.S
++++ b/arch/arm/mm/proc-v7-3level.S
+@@ -56,6 +56,14 @@ ENTRY(cpu_v7_switch_mm)
+       mov     pc, lr
+ ENDPROC(cpu_v7_switch_mm)
++#ifdef __ARMEB__
++#define rl r3
++#define rh r2
++#else
++#define rl r2
++#define rh r3
++#endif
++
+ /*
+  * cpu_v7_set_pte_ext(ptep, pte)
+  *
+@@ -65,13 +73,13 @@ ENDPROC(cpu_v7_switch_mm)
+  */
+ ENTRY(cpu_v7_set_pte_ext)
+ #ifdef CONFIG_MMU
+-      tst     r2, #L_PTE_VALID
++      tst     rl, #L_PTE_VALID
+       beq     1f
+-      tst     r3, #1 << (57 - 32)             @ L_PTE_NONE
+-      bicne   r2, #L_PTE_VALID
++      tst     rh, #1 << (57 - 32)             @ L_PTE_NONE
++      bicne   rl, #L_PTE_VALID
+       bne     1f
+-      tst     r3, #1 << (55 - 32)             @ L_PTE_DIRTY
+-      orreq   r2, #L_PTE_RDONLY
++      tst     rh, #1 << (55 - 32)             @ L_PTE_DIRTY
++      orreq   rl, #L_PTE_RDONLY
+ 1:    strd    r2, r3, [r0]
+       ALT_SMP(W(nop))
+       ALT_UP (mcr     p15, 0, r0, c7, c10, 1)         @ flush_pte
diff --git a/queue-3.10/arm-stacktrace-avoid-listing-stacktrace-functions-in-stacktrace.patch b/queue-3.10/arm-stacktrace-avoid-listing-stacktrace-functions-in-stacktrace.patch
new file mode 100644 (file)
index 0000000..bb7e662
--- /dev/null
@@ -0,0 +1,90 @@
+From 3683f44c42e991d313dc301504ee0fca1aeb8580 Mon Sep 17 00:00:00 2001
+From: Russell King <rmk+kernel@arm.linux.org.uk>
+Date: Sat, 3 May 2014 11:03:28 +0100
+Subject: ARM: stacktrace: avoid listing stacktrace functions in stacktrace
+
+From: Russell King <rmk+kernel@arm.linux.org.uk>
+
+commit 3683f44c42e991d313dc301504ee0fca1aeb8580 upstream.
+
+While debugging the FEC ethernet driver using stacktrace, it was noticed
+that the stacktraces always begin as follows:
+
+ [<c00117b4>] save_stack_trace_tsk+0x0/0x98
+ [<c0011870>] save_stack_trace+0x24/0x28
+ ...
+
+This is because the stack trace code includes the stack frames for itself.
+This is incorrect behaviour, and also leads to "skip" doing the wrong
+thing (which is the number of stack frames to avoid recording.)
+
+Perversely, it does the right thing when passed a non-current thread.  Fix
+this by ensuring that we have a known constant number of frames above the
+main stack trace function, and always skip these.
+
+Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm/kernel/stacktrace.c |   18 +++++++++++++-----
+ 1 file changed, 13 insertions(+), 5 deletions(-)
+
+--- a/arch/arm/kernel/stacktrace.c
++++ b/arch/arm/kernel/stacktrace.c
+@@ -83,13 +83,16 @@ static int save_trace(struct stackframe
+       return trace->nr_entries >= trace->max_entries;
+ }
+-void save_stack_trace_tsk(struct task_struct *tsk, struct stack_trace *trace)
++/* This must be noinline to so that our skip calculation works correctly */
++static noinline void __save_stack_trace(struct task_struct *tsk,
++      struct stack_trace *trace, unsigned int nosched)
+ {
+       struct stack_trace_data data;
+       struct stackframe frame;
+       data.trace = trace;
+       data.skip = trace->skip;
++      data.no_sched_functions = nosched;
+       if (tsk != current) {
+ #ifdef CONFIG_SMP
+@@ -102,7 +105,6 @@ void save_stack_trace_tsk(struct task_st
+                       trace->entries[trace->nr_entries++] = ULONG_MAX;
+               return;
+ #else
+-              data.no_sched_functions = 1;
+               frame.fp = thread_saved_fp(tsk);
+               frame.sp = thread_saved_sp(tsk);
+               frame.lr = 0;           /* recovered from the stack */
+@@ -111,11 +113,12 @@ void save_stack_trace_tsk(struct task_st
+       } else {
+               register unsigned long current_sp asm ("sp");
+-              data.no_sched_functions = 0;
++              /* We don't want this function nor the caller */
++              data.skip += 2;
+               frame.fp = (unsigned long)__builtin_frame_address(0);
+               frame.sp = current_sp;
+               frame.lr = (unsigned long)__builtin_return_address(0);
+-              frame.pc = (unsigned long)save_stack_trace_tsk;
++              frame.pc = (unsigned long)__save_stack_trace;
+       }
+       walk_stackframe(&frame, save_trace, &data);
+@@ -123,9 +126,14 @@ void save_stack_trace_tsk(struct task_st
+               trace->entries[trace->nr_entries++] = ULONG_MAX;
+ }
++void save_stack_trace_tsk(struct task_struct *tsk, struct stack_trace *trace)
++{
++      __save_stack_trace(tsk, trace, 1);
++}
++
+ void save_stack_trace(struct stack_trace *trace)
+ {
+-      save_stack_trace_tsk(current, trace);
++      __save_stack_trace(current, trace, 0);
+ }
+ EXPORT_SYMBOL_GPL(save_stack_trace);
+ #endif
diff --git a/queue-3.10/bluetooth-fix-l2cap-deadlock.patch b/queue-3.10/bluetooth-fix-l2cap-deadlock.patch
new file mode 100644 (file)
index 0000000..497f9ed
--- /dev/null
@@ -0,0 +1,92 @@
+From 8a96f3cd22878fc0bb564a8478a6e17c0b8dca73 Mon Sep 17 00:00:00 2001
+From: Jukka Taimisto <jtt@codenomicon.com>
+Date: Thu, 22 May 2014 10:02:39 +0000
+Subject: Bluetooth: Fix L2CAP deadlock
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Jukka Taimisto <jtt@codenomicon.com>
+
+commit 8a96f3cd22878fc0bb564a8478a6e17c0b8dca73 upstream.
+
+-[0x01 Introduction
+
+We have found a programming error causing a deadlock in Bluetooth subsystem
+of Linux kernel. The problem is caused by missing release_sock() call when
+L2CAP connection creation fails due full accept queue.
+
+The issue can be reproduced with 3.15-rc5 kernel and is also present in
+earlier kernels.
+
+-[0x02 Details
+
+The problem occurs when multiple L2CAP connections are created to a PSM which
+contains listening socket (like SDP) and left pending, for example,
+configuration (the underlying ACL link is not disconnected between
+connections).
+
+When L2CAP connection request is received and listening socket is found the
+l2cap_sock_new_connection_cb() function (net/bluetooth/l2cap_sock.c) is called.
+This function locks the 'parent' socket and then checks if the accept queue
+is full.
+
+1178         lock_sock(parent);
+1179
+1180         /* Check for backlog size */
+1181         if (sk_acceptq_is_full(parent)) {
+1182                 BT_DBG("backlog full %d", parent->sk_ack_backlog);
+1183                 return NULL;
+1184         }
+
+If case the accept queue is full NULL is returned, but the 'parent' socket
+is not released. Thus when next L2CAP connection request is received the code
+blocks on lock_sock() since the parent is still locked.
+
+Also note that for connections already established and waiting for
+configuration to complete a timeout will occur and l2cap_chan_timeout()
+(net/bluetooth/l2cap_core.c) will be called. All threads calling this
+function will also be blocked waiting for the channel mutex since the thread
+which is waiting on lock_sock() alread holds the channel mutex.
+
+We were able to reproduce this by sending continuously L2CAP connection
+request followed by disconnection request containing invalid CID. This left
+the created connections pending configuration.
+
+After the deadlock occurs it is impossible to kill bluetoothd, btmon will not
+get any more data etc. requiring reboot to recover.
+
+-[0x03 Fix
+
+Releasing the 'parent' socket when l2cap_sock_new_connection_cb() returns NULL
+seems to fix the issue.
+
+Signed-off-by: Jukka Taimisto <jtt@codenomicon.com>
+Reported-by: Tommi Mäkilä <tmakila@codenomicon.com>
+Signed-off-by: Johan Hedberg <johan.hedberg@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ net/bluetooth/l2cap_sock.c |    5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+--- a/net/bluetooth/l2cap_sock.c
++++ b/net/bluetooth/l2cap_sock.c
+@@ -949,13 +949,16 @@ static struct l2cap_chan *l2cap_sock_new
+       /* Check for backlog size */
+       if (sk_acceptq_is_full(parent)) {
+               BT_DBG("backlog full %d", parent->sk_ack_backlog);
++              release_sock(parent);
+               return NULL;
+       }
+       sk = l2cap_sock_alloc(sock_net(parent), NULL, BTPROTO_L2CAP,
+                             GFP_ATOMIC);
+-      if (!sk)
++      if (!sk) {
++              release_sock(parent);
+               return NULL;
++        }
+       bt_sock_reclassify_lock(sk, BTPROTO_L2CAP);
diff --git a/queue-3.10/bluetooth-hci_ldisc-fix-deadlock-condition.patch b/queue-3.10/bluetooth-hci_ldisc-fix-deadlock-condition.patch
new file mode 100644 (file)
index 0000000..75a062d
--- /dev/null
@@ -0,0 +1,102 @@
+From da64c27d3c93ee9f89956b9de86c4127eb244494 Mon Sep 17 00:00:00 2001
+From: Felipe Balbi <balbi@ti.com>
+Date: Wed, 23 Apr 2014 09:58:26 -0500
+Subject: bluetooth: hci_ldisc: fix deadlock condition
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Felipe Balbi <balbi@ti.com>
+
+commit da64c27d3c93ee9f89956b9de86c4127eb244494 upstream.
+
+LDISCs shouldn't call tty->ops->write() from within
+->write_wakeup().
+
+->write_wakeup() is called with port lock taken and
+IRQs disabled, tty->ops->write() will try to acquire
+the same port lock and we will deadlock.
+
+Acked-by: Marcel Holtmann <marcel@holtmann.org>
+Reviewed-by: Peter Hurley <peter@hurleysoftware.com>
+Reported-by: Huang Shijie <b32955@freescale.com>
+Signed-off-by: Felipe Balbi <balbi@ti.com>
+Tested-by: Andreas Bießmann <andreas@biessmann.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/bluetooth/hci_ldisc.c |   24 +++++++++++++++++++-----
+ drivers/bluetooth/hci_uart.h  |    1 +
+ 2 files changed, 20 insertions(+), 5 deletions(-)
+
+--- a/drivers/bluetooth/hci_ldisc.c
++++ b/drivers/bluetooth/hci_ldisc.c
+@@ -118,10 +118,6 @@ static inline struct sk_buff *hci_uart_d
+ int hci_uart_tx_wakeup(struct hci_uart *hu)
+ {
+-      struct tty_struct *tty = hu->tty;
+-      struct hci_dev *hdev = hu->hdev;
+-      struct sk_buff *skb;
+-
+       if (test_and_set_bit(HCI_UART_SENDING, &hu->tx_state)) {
+               set_bit(HCI_UART_TX_WAKEUP, &hu->tx_state);
+               return 0;
+@@ -129,6 +125,22 @@ int hci_uart_tx_wakeup(struct hci_uart *
+       BT_DBG("");
++      schedule_work(&hu->write_work);
++
++      return 0;
++}
++
++static void hci_uart_write_work(struct work_struct *work)
++{
++      struct hci_uart *hu = container_of(work, struct hci_uart, write_work);
++      struct tty_struct *tty = hu->tty;
++      struct hci_dev *hdev = hu->hdev;
++      struct sk_buff *skb;
++
++      /* REVISIT: should we cope with bad skbs or ->write() returning
++       * and error value ?
++       */
++
+ restart:
+       clear_bit(HCI_UART_TX_WAKEUP, &hu->tx_state);
+@@ -153,7 +165,6 @@ restart:
+               goto restart;
+       clear_bit(HCI_UART_SENDING, &hu->tx_state);
+-      return 0;
+ }
+ static void hci_uart_init_work(struct work_struct *work)
+@@ -289,6 +300,7 @@ static int hci_uart_tty_open(struct tty_
+       tty->receive_room = 65536;
+       INIT_WORK(&hu->init_ready, hci_uart_init_work);
++      INIT_WORK(&hu->write_work, hci_uart_write_work);
+       spin_lock_init(&hu->rx_lock);
+@@ -326,6 +338,8 @@ static void hci_uart_tty_close(struct tt
+       if (hdev)
+               hci_uart_close(hdev);
++      cancel_work_sync(&hu->write_work);
++
+       if (test_and_clear_bit(HCI_UART_PROTO_SET, &hu->flags)) {
+               if (hdev) {
+                       if (test_bit(HCI_UART_REGISTERED, &hu->flags))
+--- a/drivers/bluetooth/hci_uart.h
++++ b/drivers/bluetooth/hci_uart.h
+@@ -68,6 +68,7 @@ struct hci_uart {
+       unsigned long           hdev_flags;
+       struct work_struct      init_ready;
++      struct work_struct      write_work;
+       struct hci_uart_proto   *proto;
+       void                    *priv;
diff --git a/queue-3.10/media-uvcvideo-fix-clock-param-realtime-setting.patch b/queue-3.10/media-uvcvideo-fix-clock-param-realtime-setting.patch
new file mode 100644 (file)
index 0000000..491946a
--- /dev/null
@@ -0,0 +1,73 @@
+From 3b35fc81e7ec552147a4fd843d0da0bbbe4ef253 Mon Sep 17 00:00:00 2001
+From: Olivier Langlois <olivier@trillion01.com>
+Date: Fri, 28 Mar 2014 02:42:38 -0300
+Subject: media: uvcvideo: Fix clock param realtime setting
+
+From: Olivier Langlois <olivier@trillion01.com>
+
+commit 3b35fc81e7ec552147a4fd843d0da0bbbe4ef253 upstream.
+
+timestamps in v4l2 buffers returned to userspace are updated in
+uvc_video_clock_update() which uses timestamps fetched from
+uvc_video_clock_decode() by calling unconditionally ktime_get_ts().
+
+Hence setting the module clock param to realtime has no effect before
+this patch.
+
+This has been tested with ffmpeg:
+
+ffmpeg -y -f v4l2 -input_format yuyv422 -video_size 640x480 -framerate 30 -i /dev/video0 \
+ -f alsa -acodec pcm_s16le -ar 16000 -ac 1 -i default \
+ -c:v libx264 -preset ultrafast \
+ -c:a libfdk_aac \
+ out.mkv
+
+and inspecting the v4l2 input starting timestamp.
+
+Signed-off-by: Olivier Langlois <olivier@trillion01.com>
+Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
+Signed-off-by: Mauro Carvalho Chehab <m.chehab@samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/media/usb/uvc/uvc_video.c |   15 ++++++++++-----
+ 1 file changed, 10 insertions(+), 5 deletions(-)
+
+--- a/drivers/media/usb/uvc/uvc_video.c
++++ b/drivers/media/usb/uvc/uvc_video.c
+@@ -361,6 +361,14 @@ static int uvc_commit_video(struct uvc_s
+  * Clocks and timestamps
+  */
++static inline void uvc_video_get_ts(struct timespec *ts)
++{
++      if (uvc_clock_param == CLOCK_MONOTONIC)
++              ktime_get_ts(ts);
++      else
++              ktime_get_real_ts(ts);
++}
++
+ static void
+ uvc_video_clock_decode(struct uvc_streaming *stream, struct uvc_buffer *buf,
+                      const __u8 *data, int len)
+@@ -420,7 +428,7 @@ uvc_video_clock_decode(struct uvc_stream
+       stream->clock.last_sof = dev_sof;
+       host_sof = usb_get_current_frame_number(stream->dev->udev);
+-      ktime_get_ts(&ts);
++      uvc_video_get_ts(&ts);
+       /* The UVC specification allows device implementations that can't obtain
+        * the USB frame number to keep their own frame counters as long as they
+@@ -1010,10 +1018,7 @@ static int uvc_video_decode_start(struct
+                       return -ENODATA;
+               }
+-              if (uvc_clock_param == CLOCK_MONOTONIC)
+-                      ktime_get_ts(&ts);
+-              else
+-                      ktime_get_real_ts(&ts);
++              uvc_video_get_ts(&ts);
+               buf->buf.v4l2_buf.sequence = stream->sequence;
+               buf->buf.v4l2_buf.timestamp.tv_sec = ts.tv_sec;
index bb956bae619cce78f1d588092cb7d5094870ca31..db6bbc44db80b7797bbd407fcb324ff6bb423321 100644 (file)
@@ -42,3 +42,10 @@ media-ivtv-fix-oops-when-no-firmware-is-loaded.patch
 media-stk1160-avoid-stack-allocated-buffer-for-control-urbs.patch
 acpica-utstring-check-array-index-bound-before-use.patch
 acpi-fix-conflict-between-customized-dsdt-and-dsdt-local-copy.patch
+media-uvcvideo-fix-clock-param-realtime-setting.patch
+arm-stacktrace-avoid-listing-stacktrace-functions-in-stacktrace.patch
+arm-8037-1-mm-support-big-endian-page-tables.patch
+bluetooth-hci_ldisc-fix-deadlock-condition.patch
+bluetooth-fix-l2cap-deadlock.patch
+target-iser-bail-from-accept_np-if-np_thread-is-trying-to-close.patch
+target-iser-fix-hangs-in-connection-teardown.patch
diff --git a/queue-3.10/target-iser-bail-from-accept_np-if-np_thread-is-trying-to-close.patch b/queue-3.10/target-iser-bail-from-accept_np-if-np_thread-is-trying-to-close.patch
new file mode 100644 (file)
index 0000000..56b6600
--- /dev/null
@@ -0,0 +1,40 @@
+From e346ab343f4f58c12a96725c7b13df9cc2ad56f6 Mon Sep 17 00:00:00 2001
+From: Sagi Grimberg <sagig@mellanox.com>
+Date: Mon, 19 May 2014 17:44:22 +0300
+Subject: Target/iser: Bail from accept_np if np_thread is trying to close
+
+From: Sagi Grimberg <sagig@mellanox.com>
+
+commit e346ab343f4f58c12a96725c7b13df9cc2ad56f6 upstream.
+
+In case np_thread state is in RESET/SHUTDOWN/EXIT states,
+no point for isert to stall there as we may get a hang in
+case no one will wake it up later.
+
+Signed-off-by: Sagi Grimberg <sagig@mellanox.com>
+Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/ulp/isert/ib_isert.c |    9 +++++++--
+ 1 file changed, 7 insertions(+), 2 deletions(-)
+
+--- a/drivers/infiniband/ulp/isert/ib_isert.c
++++ b/drivers/infiniband/ulp/isert/ib_isert.c
+@@ -2190,9 +2190,14 @@ accept_wait:
+               return -ENODEV;
+       spin_lock_bh(&np->np_thread_lock);
+-      if (np->np_thread_state == ISCSI_NP_THREAD_RESET) {
++      if (np->np_thread_state >= ISCSI_NP_THREAD_RESET) {
+               spin_unlock_bh(&np->np_thread_lock);
+-              pr_debug("ISCSI_NP_THREAD_RESET for isert_accept_np\n");
++              pr_debug("np_thread_state %d for isert_accept_np\n",
++                       np->np_thread_state);
++              /**
++               * No point in stalling here when np_thread
++               * is in state RESET/SHUTDOWN/EXIT - bail
++               **/
+               return -ENODEV;
+       }
+       spin_unlock_bh(&np->np_thread_lock);
diff --git a/queue-3.10/target-iser-fix-hangs-in-connection-teardown.patch b/queue-3.10/target-iser-fix-hangs-in-connection-teardown.patch
new file mode 100644 (file)
index 0000000..de6a7af
--- /dev/null
@@ -0,0 +1,109 @@
+From 9d49f5e284e700576f3b65f1e28dea8539da6661 Mon Sep 17 00:00:00 2001
+From: Sagi Grimberg <sagig@mellanox.com>
+Date: Mon, 19 May 2014 17:44:23 +0300
+Subject: Target/iser: Fix hangs in connection teardown
+
+From: Sagi Grimberg <sagig@mellanox.com>
+
+commit 9d49f5e284e700576f3b65f1e28dea8539da6661 upstream.
+
+In ungraceful teardowns isert close flows seem racy such that
+isert_wait_conn hangs as RDMA_CM_EVENT_DISCONNECTED never
+gets invoked (no one called rdma_disconnect).
+
+Both graceful and ungraceful teardowns will have rx flush errors
+(isert posts a batch once connection is established). Once all
+flush errors are consumed we invoke isert_wait_conn and it will
+be responsible for calling rdma_disconnect. This way it can be
+sure that rdma_disconnect was called and it won't wait forever.
+
+This patch also removes the logout_posted indicator. either the
+logout completion was consumed and no problem decrementing the
+post_send_buf_count, or it was consumed as a flush error. no point
+of keeping it for isert_wait_conn as there is no danger that
+isert_conn will be accidentally removed while it is running.
+
+(Drop unnecessary sleep_on_conn_wait_comp check in
+ isert_cq_rx_comp_err - nab)
+
+Signed-off-by: Sagi Grimberg <sagig@mellanox.com>
+Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/ulp/isert/ib_isert.c |   31 ++++++++++---------------------
+ drivers/infiniband/ulp/isert/ib_isert.h |    1 -
+ 2 files changed, 10 insertions(+), 22 deletions(-)
+
+--- a/drivers/infiniband/ulp/isert/ib_isert.c
++++ b/drivers/infiniband/ulp/isert/ib_isert.c
+@@ -572,14 +572,10 @@ isert_disconnect_work(struct work_struct
+               isert_put_conn(isert_conn);
+               return;
+       }
+-      if (!isert_conn->logout_posted) {
+-              pr_debug("Calling rdma_disconnect for !logout_posted from"
+-                       " isert_disconnect_work\n");
+-              rdma_disconnect(isert_conn->conn_cm_id);
+-              mutex_unlock(&isert_conn->conn_mutex);
+-              iscsit_cause_connection_reinstatement(isert_conn->conn, 0);
+-              goto wake_up;
+-      }
++
++      /* Send DREQ/DREP towards our initiator */
++      rdma_disconnect(isert_conn->conn_cm_id);
++
+       mutex_unlock(&isert_conn->conn_mutex);
+ wake_up:
+@@ -1371,11 +1367,8 @@ isert_do_control_comp(struct work_struct
+               break;
+       case ISTATE_SEND_LOGOUTRSP:
+               pr_debug("Calling iscsit_logout_post_handler >>>>>>>>>>>>>>\n");
+-              /*
+-               * Call atomic_dec(&isert_conn->post_send_buf_count)
+-               * from isert_wait_conn()
+-               */
+-              isert_conn->logout_posted = true;
++
++              atomic_dec(&isert_conn->post_send_buf_count);
+               iscsit_logout_post_handler(cmd, cmd->conn);
+               break;
+       default:
+@@ -1483,6 +1476,8 @@ isert_cq_rx_comp_err(struct isert_conn *
+       isert_conn->state = ISER_CONN_DOWN;
+       mutex_unlock(&isert_conn->conn_mutex);
++      iscsit_cause_connection_reinstatement(isert_conn->conn, 0);
++
+       complete(&isert_conn->conn_wait_comp_err);
+ }
+@@ -2247,15 +2242,9 @@ static void isert_wait_conn(struct iscsi
+       struct isert_conn *isert_conn = conn->context;
+       pr_debug("isert_wait_conn: Starting \n");
+-      /*
+-       * Decrement post_send_buf_count for special case when called
+-       * from isert_do_control_comp() -> iscsit_logout_post_handler()
+-       */
+-      mutex_lock(&isert_conn->conn_mutex);
+-      if (isert_conn->logout_posted)
+-              atomic_dec(&isert_conn->post_send_buf_count);
+-      if (isert_conn->conn_cm_id && isert_conn->state != ISER_CONN_DOWN) {
++      mutex_lock(&isert_conn->conn_mutex);
++      if (isert_conn->conn_cm_id) {
+               pr_debug("Calling rdma_disconnect from isert_wait_conn\n");
+               rdma_disconnect(isert_conn->conn_cm_id);
+       }
+--- a/drivers/infiniband/ulp/isert/ib_isert.h
++++ b/drivers/infiniband/ulp/isert/ib_isert.h
+@@ -78,7 +78,6 @@ struct isert_device;
+ struct isert_conn {
+       enum iser_conn_state    state;
+-      bool                    logout_posted;
+       int                     post_recv_buf_count;
+       atomic_t                post_send_buf_count;
+       u32                     responder_resources;