From owner-svn-src-all@FreeBSD.ORG Sun Oct 3 08:57:03 2010 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 489F1106564A; Sun, 3 Oct 2010 08:57:03 +0000 (UTC) (envelope-from kib@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id F3CC28FC18; Sun, 3 Oct 2010 08:57:02 +0000 (UTC) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.3/8.14.3) with ESMTP id o938v2qn069359; Sun, 3 Oct 2010 08:57:02 GMT (envelope-from kib@svn.freebsd.org) Received: (from kib@localhost) by svn.freebsd.org (8.14.3/8.14.3/Submit) id o938v2Hx069355; Sun, 3 Oct 2010 08:57:02 GMT (envelope-from kib@svn.freebsd.org) Message-Id: <201010030857.o938v2Hx069355@svn.freebsd.org> From: Konstantin Belousov Date: Sun, 3 Oct 2010 08:57:02 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-8@freebsd.org X-SVN-Group: stable-8 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r213380 - stable/8/sys/nfsclient X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 03 Oct 2010 08:57:03 -0000 Author: kib Date: Sun Oct 3 08:57:02 2010 New Revision: 213380 URL: http://svn.freebsd.org/changeset/base/213380 Log: MFC r212506: Do not fork nfsiod directly from the vop methods. Schedule the task that performs fork to be executed in the taskqueue context. Modified: stable/8/sys/nfsclient/nfs.h stable/8/sys/nfsclient/nfs_nfsiod.c stable/8/sys/nfsclient/nfs_subs.c Directory Properties: stable/8/sys/ (props changed) stable/8/sys/amd64/include/xen/ (props changed) stable/8/sys/cddl/contrib/opensolaris/ (props changed) stable/8/sys/contrib/dev/acpica/ (props changed) stable/8/sys/contrib/pf/ (props changed) stable/8/sys/dev/xen/xenpci/ (props changed) Modified: stable/8/sys/nfsclient/nfs.h ============================================================================== --- stable/8/sys/nfsclient/nfs.h Sun Oct 3 08:12:17 2010 (r213379) +++ stable/8/sys/nfsclient/nfs.h Sun Oct 3 08:57:02 2010 (r213380) @@ -125,6 +125,7 @@ extern struct uma_zone *nfsmount_zone; extern struct nfsstats nfsstats; extern struct mtx nfs_iod_mtx; +extern struct task nfs_nfsiodnew_task; extern int nfs_numasync; extern unsigned int nfs_iodmax; @@ -253,6 +254,7 @@ int nfs_commit(struct vnode *vp, u_quad_ struct ucred *cred, struct thread *td); int nfs_readdirrpc(struct vnode *, struct uio *, struct ucred *); int nfs_nfsiodnew(int); +void nfs_nfsiodnew_tq(__unused void *, int); int nfs_asyncio(struct nfsmount *, struct buf *, struct ucred *, struct thread *); int nfs_doio(struct vnode *, struct buf *, struct ucred *, struct thread *); void nfs_doio_directwrite (struct buf *); Modified: stable/8/sys/nfsclient/nfs_nfsiod.c ============================================================================== --- stable/8/sys/nfsclient/nfs_nfsiod.c Sun Oct 3 08:12:17 2010 (r213379) +++ stable/8/sys/nfsclient/nfs_nfsiod.c Sun Oct 3 08:57:02 2010 (r213380) @@ -59,6 +59,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include @@ -75,6 +76,16 @@ static MALLOC_DEFINE(M_NFSSVC, "nfsclien static void nfssvc_iod(void *); +struct nfsiod_str { + STAILQ_ENTRY(nfsiod_str) ni_links; + int *ni_inst; + int ni_iod; + int ni_error; + int ni_done; +}; +static STAILQ_HEAD(, nfsiod_str) nfsiodhead = + STAILQ_HEAD_INITIALIZER(nfsiodhead); + static int nfs_asyncdaemon[NFS_MAXASYNCDAEMON]; SYSCTL_DECL(_vfs_nfs); @@ -159,11 +170,30 @@ SYSCTL_PROC(_vfs_nfs, OID_AUTO, iodmax, sizeof (nfs_iodmax), sysctl_iodmax, "IU", "Max number of nfsiod kthreads"); +void +nfs_nfsiodnew_tq(__unused void *arg, int pending) +{ + struct nfsiod_str *nip; + + mtx_lock(&nfs_iod_mtx); + while ((nip = STAILQ_FIRST(&nfsiodhead)) != NULL) { + STAILQ_REMOVE_HEAD(&nfsiodhead, ni_links); + mtx_unlock(&nfs_iod_mtx); + nip->ni_error = kproc_create(nfssvc_iod, nip->ni_inst, NULL, + RFHIGHPID, 0, "nfsiod %d", nip->ni_iod); + nip->ni_done = 1; + mtx_lock(&nfs_iod_mtx); + wakeup(nip); + } + mtx_unlock(&nfs_iod_mtx); +} + int nfs_nfsiodnew(int set_iodwant) { int error, i; int newiod; + struct nfsiod_str *nip; if (nfs_numasync >= nfs_iodmax) return (-1); @@ -179,9 +209,16 @@ nfs_nfsiodnew(int set_iodwant) if (set_iodwant > 0) nfs_iodwant[i] = NFSIOD_CREATED_FOR_NFS_ASYNCIO; mtx_unlock(&nfs_iod_mtx); - error = kproc_create(nfssvc_iod, nfs_asyncdaemon + i, NULL, RFHIGHPID, - 0, "nfsiod %d", newiod); + nip = malloc(sizeof(*nip), M_TEMP, M_WAITOK | M_ZERO); + nip->ni_inst = nfs_asyncdaemon + i; + nip->ni_iod = newiod; mtx_lock(&nfs_iod_mtx); + STAILQ_INSERT_TAIL(&nfsiodhead, nip, ni_links); + taskqueue_enqueue(taskqueue_thread, &nfs_nfsiodnew_task); + while (!nip->ni_done) + mtx_sleep(nip, &nfs_iod_mtx, 0, "niwt", 0); + error = nip->ni_error; + free(nip, M_TEMP); if (error) { if (set_iodwant > 0) nfs_iodwant[i] = NFSIOD_NOT_AVAILABLE; Modified: stable/8/sys/nfsclient/nfs_subs.c ============================================================================== --- stable/8/sys/nfsclient/nfs_subs.c Sun Oct 3 08:12:17 2010 (r213379) +++ stable/8/sys/nfsclient/nfs_subs.c Sun Oct 3 08:57:02 2010 (r213380) @@ -59,6 +59,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include @@ -117,6 +118,7 @@ int nfs_pbuf_freecnt = -1; /* start out struct nfs_bufq nfs_bufq; static struct mtx nfs_xid_mtx; +struct task nfs_nfsiodnew_task; /* * and the reverse mapping from generic to Version 2 procedure numbers @@ -354,6 +356,7 @@ nfs_init(struct vfsconf *vfsp) */ mtx_init(&nfs_iod_mtx, "NFS iod lock", NULL, MTX_DEF); mtx_init(&nfs_xid_mtx, "NFS xid lock", NULL, MTX_DEF); + TASK_INIT(&nfs_nfsiodnew_task, 0, nfs_nfsiodnew_tq, NULL); nfs_pbuf_freecnt = nswbuf / 2 + 1; @@ -368,9 +371,13 @@ nfs_uninit(struct vfsconf *vfsp) /* * Tell all nfsiod processes to exit. Clear nfs_iodmax, and wakeup * any sleeping nfsiods so they check nfs_iodmax and exit. + * Drain nfsiodnew task before we wait for them to finish. */ mtx_lock(&nfs_iod_mtx); nfs_iodmax = 0; + mtx_unlock(&nfs_iod_mtx); + taskqueue_drain(taskqueue_thread, &nfs_nfsiodnew_task); + mtx_lock(&nfs_iod_mtx); for (i = 0; i < nfs_numasync; i++) if (nfs_iodwant[i] == NFSIOD_AVAILABLE) wakeup(&nfs_iodwant[i]);