From owner-svn-src-all@FreeBSD.ORG Wed Jun 17 22:50:26 2009 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 6B658106568D; Wed, 17 Jun 2009 22:50:26 +0000 (UTC) (envelope-from rmacklem@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id 589F88FC0C; Wed, 17 Jun 2009 22:50:26 +0000 (UTC) (envelope-from rmacklem@FreeBSD.org) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.3/8.14.3) with ESMTP id n5HMoQSP090667; Wed, 17 Jun 2009 22:50:26 GMT (envelope-from rmacklem@svn.freebsd.org) Received: (from rmacklem@localhost) by svn.freebsd.org (8.14.3/8.14.3/Submit) id n5HMoQZV090661; Wed, 17 Jun 2009 22:50:26 GMT (envelope-from rmacklem@svn.freebsd.org) Message-Id: <200906172250.n5HMoQZV090661@svn.freebsd.org> From: Rick Macklem Date: Wed, 17 Jun 2009 22:50:26 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r194407 - in head/sys: nfsserver nlm rpc 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: Wed, 17 Jun 2009 22:50:26 -0000 Author: rmacklem Date: Wed Jun 17 22:50:26 2009 New Revision: 194407 URL: http://svn.freebsd.org/changeset/base/194407 Log: Since svc_[dg|vc|tli|tp]_create() did not hold a reference count on the SVCXPTR structure returned by them, it was possible for the structure to be free'd before svc_reg() had been completed using the structure. This patch acquires a reference count on the newly created structure that is returned by svc_[dg|vc|tli|tp]_create(). It also adds the appropriate SVC_RELEASE() calls to the callers, except the experimental nfs subsystem. The latter will be committed separately. Submitted by: dfr Tested by: pho Approved by: kib (mentor) Modified: head/sys/nfsserver/nfs_srvkrpc.c head/sys/nlm/nlm_prot_impl.c head/sys/rpc/svc.c head/sys/rpc/svc_generic.c head/sys/rpc/svc_vc.c Modified: head/sys/nfsserver/nfs_srvkrpc.c ============================================================================== --- head/sys/nfsserver/nfs_srvkrpc.c Wed Jun 17 21:58:32 2009 (r194406) +++ head/sys/nfsserver/nfs_srvkrpc.c Wed Jun 17 22:50:26 2009 (r194407) @@ -467,6 +467,7 @@ nfssvc_addsock(struct file *fp, struct t fp->f_data = NULL; svc_reg(xprt, NFS_PROG, NFS_VER2, nfssvc_program, NULL); svc_reg(xprt, NFS_PROG, NFS_VER3, nfssvc_program, NULL); + SVC_RELEASE(xprt); } return (0); Modified: head/sys/nlm/nlm_prot_impl.c ============================================================================== --- head/sys/nlm/nlm_prot_impl.c Wed Jun 17 21:58:32 2009 (r194406) +++ head/sys/nlm/nlm_prot_impl.c Wed Jun 17 22:50:26 2009 (r194407) @@ -1389,7 +1389,7 @@ nlm_register_services(SVCPOOL *pool, int return (EINVAL); } - xprts = malloc(addr_count * sizeof(SVCXPRT *), M_NLM, M_WAITOK); + xprts = malloc(addr_count * sizeof(SVCXPRT *), M_NLM, M_WAITOK|M_ZERO); for (i = 0; i < version_count; i++) { for (j = 0; j < addr_count; j++) { /* @@ -1447,6 +1447,10 @@ nlm_register_services(SVCPOOL *pool, int } error = 0; out: + for (j = 0; j < addr_count; j++) { + if (xprts[j]) + SVC_RELEASE(xprts[j]); + } free(xprts, M_NLM); return (error); } Modified: head/sys/rpc/svc.c ============================================================================== --- head/sys/rpc/svc.c Wed Jun 17 21:58:32 2009 (r194406) +++ head/sys/rpc/svc.c Wed Jun 17 22:50:26 2009 (r194407) @@ -276,6 +276,7 @@ xprt_register(SVCXPRT *xprt) { SVCPOOL *pool = xprt->xp_pool; + SVC_ACQUIRE(xprt); mtx_lock(&pool->sp_lock); xprt->xp_registered = TRUE; xprt->xp_active = FALSE; Modified: head/sys/rpc/svc_generic.c ============================================================================== --- head/sys/rpc/svc_generic.c Wed Jun 17 21:58:32 2009 (r194406) +++ head/sys/rpc/svc_generic.c Wed Jun 17 22:50:26 2009 (r194407) @@ -120,8 +120,10 @@ svc_create( /* It was not found. Now create a new one */ xprt = svc_tp_create(pool, dispatch, prognum, versnum, NULL, nconf); - if (xprt) + if (xprt) { num++; + SVC_RELEASE(xprt); + } } } __rpc_endconf(handle); @@ -179,6 +181,7 @@ svc_tp_create( (unsigned)prognum, (unsigned)versnum, nconf->nc_netid); xprt_unregister(xprt); + SVC_RELEASE(xprt); return (NULL); } return (xprt); Modified: head/sys/rpc/svc_vc.c ============================================================================== --- head/sys/rpc/svc_vc.c Wed Jun 17 21:58:32 2009 (r194406) +++ head/sys/rpc/svc_vc.c Wed Jun 17 22:50:26 2009 (r194407) @@ -324,6 +324,7 @@ svc_vc_rendezvous_recv(SVCXPRT *xprt, st struct socket *so = NULL; struct sockaddr *sa = NULL; int error; + SVCXPRT *new_xprt; /* * The socket upcall calls xprt_active() which will eventually @@ -383,10 +384,14 @@ svc_vc_rendezvous_recv(SVCXPRT *xprt, st /* * svc_vc_create_conn will call xprt_register - we don't need - * to do anything with the new connection. + * to do anything with the new connection except derefence it. */ - if (!svc_vc_create_conn(xprt->xp_pool, so, sa)) + new_xprt = svc_vc_create_conn(xprt->xp_pool, so, sa); + if (!new_xprt) { soclose(so); + } else { + SVC_RELEASE(new_xprt); + } free(sa, M_SONAME);