Module Name:    src
Committed By:   rmind
Date:           Fri Oct 18 02:32:12 UTC 2013

Modified Files:
        src/sys/kern [rmind-smpnet]: uipc_socket.c
        src/sys/sys [rmind-smpnet]: socketvar.h

Log Message:
Add soref() and sounref().


To generate a diff of this commit:
cvs rdiff -u -r1.215.4.2 -r1.215.4.3 src/sys/kern/uipc_socket.c
cvs rdiff -u -r1.130.2.1 -r1.130.2.2 src/sys/sys/socketvar.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/kern/uipc_socket.c
diff -u src/sys/kern/uipc_socket.c:1.215.4.2 src/sys/kern/uipc_socket.c:1.215.4.3
--- src/sys/kern/uipc_socket.c:1.215.4.2	Wed Aug 28 23:59:35 2013
+++ src/sys/kern/uipc_socket.c	Fri Oct 18 02:32:12 2013
@@ -1,4 +1,4 @@
-/*	$NetBSD: uipc_socket.c,v 1.215.4.2 2013/08/28 23:59:35 rmind Exp $	*/
+/*	$NetBSD: uipc_socket.c,v 1.215.4.3 2013/10/18 02:32:12 rmind Exp $	*/
 
 /*-
  * Copyright (c) 2002, 2007, 2008, 2009 The NetBSD Foundation, Inc.
@@ -71,7 +71,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: uipc_socket.c,v 1.215.4.2 2013/08/28 23:59:35 rmind Exp $");
+__KERNEL_RCSID(0, "$NetBSD: uipc_socket.c,v 1.215.4.3 2013/10/18 02:32:12 rmind Exp $");
 
 #include "opt_compat_netbsd.h"
 #include "opt_sock_counters.h"
@@ -528,6 +528,8 @@ socreate(int dom, struct socket **aso, i
 	so = soget(true);
 	so->so_type = type;
 	so->so_proto = prp;
+	so->so_refcnt = 1;
+
 	so->so_send = sosend;
 	so->so_receive = soreceive;
 #ifdef MBUFTRACE
@@ -607,6 +609,21 @@ fsocreate(int domain, struct socket **so
 	return error;
 }
 
+void
+soref(struct socket *so)
+{
+	atomic_inc_uint(&so->so_refcnt);
+}
+
+void
+sounref(struct socket *so)
+{
+	if (atomic_dec_uint_nv(&so->so_refcnt) > 0) {
+		return;
+	}
+	soput(so);
+}
+
 int
 sofamily(const struct socket *so)
 {
@@ -661,7 +678,6 @@ solisten(struct socket *so, int backlog,
 void
 sofree(struct socket *so)
 {
-	u_int refs;
 
 	KASSERT(solocked(so));
 
@@ -691,13 +707,13 @@ sofree(struct socket *so)
 	KASSERT(!cv_has_waiters(&so->so_rcv.sb_cv));
 	KASSERT(!cv_has_waiters(&so->so_snd.sb_cv));
 	sorflush(so);
-	refs = so->so_aborting;	/* XXX */
 	/* Remove acccept filter if one is present. */
 	if (so->so_accf != NULL)
 		(void)accept_filt_clear(so);
 	sounlock(so);
-	if (refs == 0)		/* XXX */
-		soput(so);
+
+	/* Will soput() if the last reference. */
+	sounref(so);
 }
 
 /*
@@ -772,19 +788,23 @@ soabort(struct socket *so)
 {
 	u_int refs;
 	int error;
-	
+
 	KASSERT(solocked(so));
 	KASSERT(so->so_head == NULL);
 
-	so->so_aborting++;		/* XXX */
+	soref(so);
 	error = (*so->so_proto->pr_usrreqs->pr_generic)(so,
 	    PRU_ABORT, NULL, NULL, NULL, NULL);
-	refs = --so->so_aborting;	/* XXX */
-	if (error || (refs == 0)) {
+	refs = so->so_refcnt;
+	sounref(so);
+
+	/* XXX: Fix PRU_ABORT to behave consistently. */
+	if (error || refs == 1) {
 		sofree(so);
 	} else {
 		sounlock(so);
 	}
+	sounref(so);
 	return error;
 }
 

Index: src/sys/sys/socketvar.h
diff -u src/sys/sys/socketvar.h:1.130.2.1 src/sys/sys/socketvar.h:1.130.2.2
--- src/sys/sys/socketvar.h:1.130.2.1	Wed Aug 28 15:21:49 2013
+++ src/sys/sys/socketvar.h	Fri Oct 18 02:32:12 2013
@@ -1,4 +1,4 @@
-/*	$NetBSD: socketvar.h,v 1.130.2.1 2013/08/28 15:21:49 rmind Exp $	*/
+/*	$NetBSD: socketvar.h,v 1.130.2.2 2013/10/18 02:32:12 rmind Exp $	*/
 
 /*-
  * Copyright (c) 2008, 2009 The NetBSD Foundation, Inc.
@@ -128,7 +128,7 @@ struct socket {
 	short		so_options;	/* from socket call, see socket.h */
 	u_short		so_linger;	/* time to linger while closing */
 	short		so_state;	/* internal state flags SS_*, below */
-	int		so_unused;	/* used to be so_nbio */
+	unsigned	so_refcnt;	/* reference count */
 	void		*so_pcb;	/* protocol control block */
 	const struct protosw *so_proto;	/* protocol handle */
 /*
@@ -152,7 +152,7 @@ struct socket {
 	short		so_qlimit;	/* max number queued connections */
 	short		so_timeo;	/* connection timeout */
 	u_short		so_error;	/* error affecting connection */
-	u_short		so_aborting;	/* references from soabort() */
+	u_short		so_unused1;
 	pid_t		so_pgid;	/* pgid for signals */
 	u_long		so_oobmark;	/* chars to oob mark */
 	struct sockbuf	so_snd;		/* send buffer */
@@ -298,6 +298,8 @@ int	socreate(int, struct socket **, int,
 		 struct socket *);
 int	fsocreate(int, struct socket **, int, int, int *);
 int	sodisconnect(struct socket *);
+void	soref(struct socket *);
+void	sounref(struct socket *);
 void	sofree(struct socket *);
 int	sogetopt(struct socket *, struct sockopt *);
 void	sohasoutofband(struct socket *);

Reply via email to