stable.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
To: linux-kernel@vger.kernel.org, stable@vger.kernel.org
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	alan@lxorguk.ukuu.org.uk,
	Dick Streefland <dick.streefland@altium.nl>,
	Bryan Schumaker <bjschuma@netapp.com>,
	Trond Myklebust <Trond.Myklebust@netapp.com>
Subject: [ 09/42] SUNRPC: Fix a UDP transport regression
Date: Thu, 25 Oct 2012 17:05:17 -0700	[thread overview]
Message-ID: <20121026000125.723898858@linuxfoundation.org> (raw)
In-Reply-To: <20121026000124.790781113@linuxfoundation.org>

3.4-stable review patch.  If anyone has any objections, please let me know.

------------------

From: Trond Myklebust <Trond.Myklebust@netapp.com>

commit f39c1bfb5a03e2d255451bff05be0d7255298fa4 and
commit 84e28a307e376f271505af65a7b7e212dd6f61f4 upstream.

Commit 43cedbf0e8dfb9c5610eb7985d5f21263e313802 (SUNRPC: Ensure that
we grab the XPRT_LOCK before calling xprt_alloc_slot) is causing
hangs in the case of NFS over UDP mounts.

Since neither the UDP or the RDMA transport mechanism use dynamic slot
allocation, we can skip grabbing the socket lock for those transports.
Add a new rpc_xprt_op to allow switching between the TCP and UDP/RDMA
case.

Note that the NFSv4.1 back channel assigns the slot directly
through rpc_run_bc_task, so we can ignore that case.

Reported-by: Dick Streefland <dick.streefland@altium.nl>
Signed-off-by: Bryan Schumaker <bjschuma@netapp.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

---
 include/linux/sunrpc/xprt.h     |    3 +++
 net/sunrpc/xprt.c               |   34 ++++++++++++++++++++--------------
 net/sunrpc/xprtrdma/transport.c |    1 +
 net/sunrpc/xprtsock.c           |    4 ++++
 4 files changed, 28 insertions(+), 14 deletions(-)

--- a/include/linux/sunrpc/xprt.h
+++ b/include/linux/sunrpc/xprt.h
@@ -114,6 +114,7 @@ struct rpc_xprt_ops {
 	void		(*set_buffer_size)(struct rpc_xprt *xprt, size_t sndsize, size_t rcvsize);
 	int		(*reserve_xprt)(struct rpc_xprt *xprt, struct rpc_task *task);
 	void		(*release_xprt)(struct rpc_xprt *xprt, struct rpc_task *task);
+	void		(*alloc_slot)(struct rpc_xprt *xprt, struct rpc_task *task);
 	void		(*rpcbind)(struct rpc_task *task);
 	void		(*set_port)(struct rpc_xprt *xprt, unsigned short port);
 	void		(*connect)(struct rpc_task *task);
@@ -279,6 +280,8 @@ void			xprt_connect(struct rpc_task *tas
 void			xprt_reserve(struct rpc_task *task);
 int			xprt_reserve_xprt(struct rpc_xprt *xprt, struct rpc_task *task);
 int			xprt_reserve_xprt_cong(struct rpc_xprt *xprt, struct rpc_task *task);
+void			xprt_alloc_slot(struct rpc_xprt *xprt, struct rpc_task *task);
+void			xprt_lock_and_alloc_slot(struct rpc_xprt *xprt, struct rpc_task *task);
 int			xprt_prepare_transmit(struct rpc_task *task);
 void			xprt_transmit(struct rpc_task *task);
 void			xprt_end_transmit(struct rpc_task *task);
--- a/net/sunrpc/xprt.c
+++ b/net/sunrpc/xprt.c
@@ -969,11 +969,11 @@ static bool xprt_dynamic_free_slot(struc
 	return false;
 }
 
-static void xprt_alloc_slot(struct rpc_task *task)
+void xprt_alloc_slot(struct rpc_xprt *xprt, struct rpc_task *task)
 {
-	struct rpc_xprt	*xprt = task->tk_xprt;
 	struct rpc_rqst *req;
 
+	spin_lock(&xprt->reserve_lock);
 	if (!list_empty(&xprt->free)) {
 		req = list_entry(xprt->free.next, struct rpc_rqst, rq_list);
 		list_del(&req->rq_list);
@@ -994,12 +994,29 @@ static void xprt_alloc_slot(struct rpc_t
 	default:
 		task->tk_status = -EAGAIN;
 	}
+	spin_unlock(&xprt->reserve_lock);
 	return;
 out_init_req:
 	task->tk_status = 0;
 	task->tk_rqstp = req;
 	xprt_request_init(task, xprt);
+	spin_unlock(&xprt->reserve_lock);
+}
+EXPORT_SYMBOL_GPL(xprt_alloc_slot);
+
+void xprt_lock_and_alloc_slot(struct rpc_xprt *xprt, struct rpc_task *task)
+{
+	/* Note: grabbing the xprt_lock_write() ensures that we throttle
+	 * new slot allocation if the transport is congested (i.e. when
+	 * reconnecting a stream transport or when out of socket write
+	 * buffer space).
+	 */
+	if (xprt_lock_write(xprt, task)) {
+		xprt_alloc_slot(xprt, task);
+		xprt_release_write(xprt, task);
+	}
 }
+EXPORT_SYMBOL_GPL(xprt_lock_and_alloc_slot);
 
 static void xprt_free_slot(struct rpc_xprt *xprt, struct rpc_rqst *req)
 {
@@ -1083,20 +1100,9 @@ void xprt_reserve(struct rpc_task *task)
 	if (task->tk_rqstp != NULL)
 		return;
 
-	/* Note: grabbing the xprt_lock_write() here is not strictly needed,
-	 * but ensures that we throttle new slot allocation if the transport
-	 * is congested (e.g. if reconnecting or if we're out of socket
-	 * write buffer space).
-	 */
 	task->tk_timeout = 0;
 	task->tk_status = -EAGAIN;
-	if (!xprt_lock_write(xprt, task))
-		return;
-
-	spin_lock(&xprt->reserve_lock);
-	xprt_alloc_slot(task);
-	spin_unlock(&xprt->reserve_lock);
-	xprt_release_write(xprt, task);
+	xprt->ops->alloc_slot(xprt, task);
 }
 
 static inline __be32 xprt_alloc_xid(struct rpc_xprt *xprt)
--- a/net/sunrpc/xprtrdma/transport.c
+++ b/net/sunrpc/xprtrdma/transport.c
@@ -713,6 +713,7 @@ static void xprt_rdma_print_stats(struct
 static struct rpc_xprt_ops xprt_rdma_procs = {
 	.reserve_xprt		= xprt_rdma_reserve_xprt,
 	.release_xprt		= xprt_release_xprt_cong, /* sunrpc/xprt.c */
+	.alloc_slot		= xprt_alloc_slot,
 	.release_request	= xprt_release_rqst_cong,       /* ditto */
 	.set_retrans_timeout	= xprt_set_retrans_timeout_def, /* ditto */
 	.rpcbind		= rpcb_getport_async,	/* sunrpc/rpcb_clnt.c */
--- a/net/sunrpc/xprtsock.c
+++ b/net/sunrpc/xprtsock.c
@@ -2444,6 +2444,7 @@ static void bc_destroy(struct rpc_xprt *
 static struct rpc_xprt_ops xs_local_ops = {
 	.reserve_xprt		= xprt_reserve_xprt,
 	.release_xprt		= xs_tcp_release_xprt,
+	.alloc_slot		= xprt_alloc_slot,
 	.rpcbind		= xs_local_rpcbind,
 	.set_port		= xs_local_set_port,
 	.connect		= xs_connect,
@@ -2460,6 +2461,7 @@ static struct rpc_xprt_ops xs_udp_ops =
 	.set_buffer_size	= xs_udp_set_buffer_size,
 	.reserve_xprt		= xprt_reserve_xprt_cong,
 	.release_xprt		= xprt_release_xprt_cong,
+	.alloc_slot		= xprt_alloc_slot,
 	.rpcbind		= rpcb_getport_async,
 	.set_port		= xs_set_port,
 	.connect		= xs_connect,
@@ -2477,6 +2479,7 @@ static struct rpc_xprt_ops xs_udp_ops =
 static struct rpc_xprt_ops xs_tcp_ops = {
 	.reserve_xprt		= xprt_reserve_xprt,
 	.release_xprt		= xs_tcp_release_xprt,
+	.alloc_slot		= xprt_lock_and_alloc_slot,
 	.rpcbind		= rpcb_getport_async,
 	.set_port		= xs_set_port,
 	.connect		= xs_connect,
@@ -2496,6 +2499,7 @@ static struct rpc_xprt_ops xs_tcp_ops =
 static struct rpc_xprt_ops bc_tcp_ops = {
 	.reserve_xprt		= xprt_reserve_xprt,
 	.release_xprt		= xprt_release_xprt,
+	.alloc_slot		= xprt_alloc_slot,
 	.rpcbind		= xs_local_rpcbind,
 	.buf_alloc		= bc_malloc,
 	.buf_free		= bc_free,



  parent reply	other threads:[~2012-10-26  0:05 UTC|newest]

Thread overview: 42+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-10-26  0:05 [ 00/42] 3.4.16-stable review Greg Kroah-Hartman
2012-10-26  0:05 ` [ 01/42] ext4: race-condition protection for ext4_convert_unwritten_extents_endio Greg Kroah-Hartman
2012-10-26  0:05 ` [ 02/42] ext4: Avoid underflow in ext4_trim_fs() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 03/42] nohz: Fix idle ticks in cpu summary line of /proc/stat Greg Kroah-Hartman
2012-10-26  0:05 ` [ 04/42] arch/tile: avoid generating .eh_frame information in modules Greg Kroah-Hartman
2012-10-26  0:05 ` [ 05/42] NLM: nlm_lookup_file() may return NLMv4-specific error codes Greg Kroah-Hartman
2012-10-26  0:05 ` [ 06/42] oprofile, x86: Fix wrapping bug in op_x86_get_ctrl() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 07/42] s390: fix linker script for 31 bit builds Greg Kroah-Hartman
2012-10-26  0:05 ` [ 08/42] SUNRPC: Prevent kernel stack corruption on long values of flush Greg Kroah-Hartman
2012-10-26  0:05 ` Greg Kroah-Hartman [this message]
2012-10-26  0:05 ` [ 10/42] pcmcia: sharpsl: dont discard sharpsl_pcmcia_ops Greg Kroah-Hartman
2012-10-26  0:05 ` [ 11/42] kernel/sys.c: fix stack memory content leak via UNAME26 Greg Kroah-Hartman
2012-10-26  0:05 ` [ 13/42] x86: Exclude E820_RESERVED regions and memory holes above 4 GB from direct mapping Greg Kroah-Hartman
2012-10-26  0:05 ` [ 14/42] xen/x86: dont corrupt %eip when returning from a signal handler Greg Kroah-Hartman
2012-10-26  0:05 ` [ 15/42] USB: cdc-acm: fix pipe type of write endpoint Greg Kroah-Hartman
2012-10-26  0:05 ` [ 16/42] usb: acm: fix the computation of the number of data bits Greg Kroah-Hartman
2012-10-26  0:05 ` [ 17/42] usb: host: xhci: New system added for Compliance Mode Patch on SN65LVPE502CP Greg Kroah-Hartman
2012-10-26  0:05 ` [ 18/42] USB: option: blacklist net interface on ZTE devices Greg Kroah-Hartman
2012-10-26  0:05 ` [ 19/42] USB: option: add more " Greg Kroah-Hartman
2012-10-26  0:05 ` [ 20/42] cgroup: notify_on_release may not be triggered in some cases Greg Kroah-Hartman
2012-10-26  0:05 ` [ 21/42] Revert "cgroup: Remove task_lock() from cgroup_post_fork()" Greg Kroah-Hartman
2012-10-26  0:05 ` [ 22/42] Revert "cgroup: Drop task_lock(parent) on cgroup_fork()" Greg Kroah-Hartman
2012-10-26  0:05 ` [ 23/42] pinctrl: tegra: correct bank for pingroup and drv pingroup Greg Kroah-Hartman
2012-10-26  0:05 ` [ 24/42] pinctrl: tegra: set low power mode bank width to 2 Greg Kroah-Hartman
2012-10-26  0:05 ` [ 25/42] iommu/tegra: smmu: Fix deadly typo Greg Kroah-Hartman
2012-10-26  0:05 ` [ 26/42] amd64_edac:__amd64_set_scrub_rate(): avoid overindexing scrubrates[] Greg Kroah-Hartman
2012-10-26  0:05 ` [ 27/42] usb: dwc3: gadget: fix endpoint always busy bug Greg Kroah-Hartman
2012-10-26  0:05 ` [ 28/42] media: au0828: fix case where STREAMOFF being called on stopped stream causes BUG() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 29/42] netlink: add reference of module in netlink_dump_start Greg Kroah-Hartman
2012-10-26  0:05 ` [ 30/42] infiniband: pass rdma_cm module to netlink_dump_start Greg Kroah-Hartman
2012-10-26  0:05 ` [ 31/42] net: Fix skb_under_panic oops in neigh_resolve_output Greg Kroah-Hartman
2012-10-26  0:05 ` [ 32/42] skge: Add DMA mask quirk for Marvell 88E8001 on ASUS P5NSLI motherboard Greg Kroah-Hartman
2012-10-26  0:05 ` [ 33/42] vlan: dont deliver frames for unknown vlans to protocols Greg Kroah-Hartman
2012-10-26  0:05 ` [ 34/42] RDS: fix rds-ping spinlock recursion Greg Kroah-Hartman
2012-10-26  0:05 ` [ 35/42] tcp: resets are misrouted Greg Kroah-Hartman
2012-10-26  0:05 ` [ 36/42] ipv6: addrconf: fix /proc/net/if_inet6 Greg Kroah-Hartman
2012-10-26  0:05 ` [ 37/42] sparc64: fix ptrace interaction with force_successful_syscall_return() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 38/42] sparc64: Like x86 we should check current->mm during perf backtrace generation Greg Kroah-Hartman
2012-10-26  0:05 ` [ 39/42] sparc64: Fix bit twiddling in sparc_pmu_enable_event() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 40/42] sparc64: do not clobber personality flags in sys_sparc64_personality() Greg Kroah-Hartman
2012-10-26  0:05 ` [ 41/42] sparc64: Be less verbose during vmemmap population Greg Kroah-Hartman
2012-10-26  0:05 ` [ 42/42] mtd: nand: allow NAND_NO_SUBPAGE_WRITE to be set from driver Greg Kroah-Hartman

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20121026000125.723898858@linuxfoundation.org \
    --to=gregkh@linuxfoundation.org \
    --cc=Trond.Myklebust@netapp.com \
    --cc=alan@lxorguk.ukuu.org.uk \
    --cc=bjschuma@netapp.com \
    --cc=dick.streefland@altium.nl \
    --cc=linux-kernel@vger.kernel.org \
    --cc=stable@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).