PERFORCE change 55228 for review

Peter Wemm peter at FreeBSD.org
Fri Jun 18 05:22:07 GMT 2004


http://perforce.freebsd.org/chv.cgi?CH=55228

Change 55228 by peter at peter_daintree on 2004/06/18 05:20:27

	IFC @55227

Affected files ...

.. //depot/projects/hammer/contrib/libpcap/pcap-bpf.c#5 integrate
.. //depot/projects/hammer/lib/libc/sys/clock_gettime.2#4 integrate
.. //depot/projects/hammer/libexec/rtld-elf/rtld.c#21 integrate
.. //depot/projects/hammer/libexec/rtld-elf/sparc64/rtld_machdep.h#6 integrate
.. //depot/projects/hammer/libexec/rtld-elf/sparc64/rtld_start.S#5 integrate
.. //depot/projects/hammer/share/man/man5/rc.conf.5#28 integrate
.. //depot/projects/hammer/sys/amd64/amd64/fpu.c#19 integrate
.. //depot/projects/hammer/sys/dev/ed/if_ed_pci.c#5 integrate
.. //depot/projects/hammer/sys/fs/fifofs/fifo_vnops.c#20 integrate
.. //depot/projects/hammer/sys/fs/portalfs/portal_vnops.c#7 integrate
.. //depot/projects/hammer/sys/i386/isa/npx.c#19 integrate
.. //depot/projects/hammer/sys/kern/kern_time.c#10 integrate
.. //depot/projects/hammer/sys/kern/sys_socket.c#11 integrate
.. //depot/projects/hammer/sys/kern/uipc_socket.c#26 integrate
.. //depot/projects/hammer/sys/kern/uipc_socket2.c#21 integrate
.. //depot/projects/hammer/sys/kern/vfs_aio.c#19 integrate
.. //depot/projects/hammer/sys/netgraph/bluetooth/socket/ng_btsocket_rfcomm.c#9 integrate
.. //depot/projects/hammer/sys/netgraph/ng_ksocket.c#11 integrate
.. //depot/projects/hammer/sys/netinet/in_gif.c#7 integrate
.. //depot/projects/hammer/sys/netinet/tcp_output.c#15 integrate
.. //depot/projects/hammer/sys/netsmb/smb_trantcp.c#7 integrate
.. //depot/projects/hammer/sys/nfsserver/nfs_syscalls.c#13 integrate
.. //depot/projects/hammer/sys/sys/param.h#36 integrate

Differences ...

==== //depot/projects/hammer/contrib/libpcap/pcap-bpf.c#5 (text+ko) ====

@@ -17,8 +17,6 @@
  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
- *
- * $FreeBSD: src/contrib/libpcap/pcap-bpf.c,v 1.2 2004/05/31 21:29:30 dwmalone Exp $
  */
 #ifndef lint
 static const char rcsid[] _U_ =
@@ -469,7 +467,7 @@
 	 */
 	do {
 		(void)snprintf(device, sizeof(device), "/dev/bpf%d", n++);
-		fd = open(device, O_RDWR);
+		fd = open(device, O_RDONLY);
 	} while (fd < 0 && errno == EBUSY);
 
 	/*

==== //depot/projects/hammer/lib/libc/sys/clock_gettime.2#4 (text+ko) ====

@@ -31,9 +31,9 @@
 .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 .\" SUCH DAMAGE.
 .\"
-.\" $FreeBSD: src/lib/libc/sys/clock_gettime.2,v 1.17 2003/09/10 19:24:33 ru Exp $
+.\" $FreeBSD: src/lib/libc/sys/clock_gettime.2,v 1.18 2004/06/17 23:13:38 kbyanc Exp $
 .\"
-.Dd February 5, 2003
+.Dd June 17, 2004
 .Dt CLOCK_GETTIME 2
 .Os
 .Sh NAME
@@ -128,9 +128,3 @@
 .Fn clock_getres
 system calls conform to
 .St -p1003.1b-93 .
-.Sh BUGS
-The
-.Dv CLOCK_VIRTUAL
-and
-.Dv CLOCK_PROF
-timers are not yet implemented.

==== //depot/projects/hammer/libexec/rtld-elf/rtld.c#21 (text+ko) ====

@@ -23,7 +23,7 @@
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/libexec/rtld-elf/rtld.c,v 1.96 2004/05/28 00:05:28 eik Exp $
+ * $FreeBSD: src/libexec/rtld-elf/rtld.c,v 1.97 2004/06/18 02:01:37 tmm Exp $
  */
 
 /*
@@ -162,6 +162,9 @@
 
 extern Elf_Dyn _DYNAMIC;
 #pragma weak _DYNAMIC
+#ifndef RTLD_IS_DYNAMIC
+#define	RTLD_IS_DYNAMIC()	(&_DYNAMIC != NULL)
+#endif
 
 /*
  * These are the functions the dynamic linker exports to application
@@ -1008,7 +1011,7 @@
 #ifdef PIC
     objtmp.relocbase = mapbase;
 #endif
-    if (&_DYNAMIC != 0) {
+    if (RTLD_IS_DYNAMIC()) {
 	objtmp.dynamic = rtld_dynamic(&objtmp);
 	digest_dynamic(&objtmp, 1);
 	assert(objtmp.needed == NULL);

==== //depot/projects/hammer/libexec/rtld-elf/sparc64/rtld_machdep.h#6 (text+ko) ====

@@ -23,7 +23,7 @@
  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  * SUCH DAMAGE.
  *
- * $FreeBSD: src/libexec/rtld-elf/sparc64/rtld_machdep.h,v 1.5 2003/07/04 00:05:15 jake Exp $
+ * $FreeBSD: src/libexec/rtld-elf/sparc64/rtld_machdep.h,v 1.6 2004/06/18 02:01:37 tmm Exp $
  */
 
 #ifndef RTLD_MACHDEP_H
@@ -37,7 +37,9 @@
 struct Struct_Obj_Entry;
 
 /* Return the address of the .dynamic section in the dynamic linker. */
-Elf_Dyn *rtld_dynamic(const struct Struct_Obj_Entry *);
+Elf_Dyn *rtld_dynamic_addr();
+#define	rtld_dynamic(obj)	rtld_dynamic_addr()
+#define	RTLD_IS_DYNAMIC()	(rtld_dynamic_addr() != NULL)
 
 Elf_Addr reloc_jmpslot(Elf_Addr *, Elf_Addr,
 		       const struct Struct_Obj_Entry *,

==== //depot/projects/hammer/libexec/rtld-elf/sparc64/rtld_start.S#5 (text+ko) ====

@@ -37,7 +37,7 @@
  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  * POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/libexec/rtld-elf/sparc64/rtld_start.S,v 1.5 2003/07/04 00:05:15 jake Exp $
+ * $FreeBSD: src/libexec/rtld-elf/sparc64/rtld_start.S,v 1.6 2004/06/18 02:01:37 tmm Exp $
  */
 
 #include <machine/asm.h>
@@ -71,8 +71,9 @@
  * Find the address of _DYNAMIC by disassembling a call instruction to it.
  * Binutils may not fill in the GOT as expected on other architectures.
  */
+.weak	_DYNAMIC
 
-ENTRY(rtld_dynamic)
+ENTRY(rtld_dynamic_addr)
 	save	%sp, -CCFSZ, %sp
 	call	1f
 	 nop
@@ -82,7 +83,7 @@
 	sra	%o0, 0, %o0
 	ret
 	 restore %o0, %o7, %o0
-END(rtld_dynamic)
+END(rtld_dynamic_addr)
 
 	/*
 	 * We have two separate entry points to the runtime linker.

==== //depot/projects/hammer/share/man/man5/rc.conf.5#28 (text+ko) ====

@@ -22,7 +22,7 @@
 .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 .\" SUCH DAMAGE.
 .\"
-.\" $FreeBSD: src/share/man/man5/rc.conf.5,v 1.217 2004/06/16 08:33:56 ru Exp $
+.\" $FreeBSD: src/share/man/man5/rc.conf.5,v 1.218 2004/06/18 01:28:33 bms Exp $
 .\"
 .Dd April 25, 2004
 .Dt RC.CONF 5
@@ -1691,6 +1691,12 @@
 whose contents will later be passed to a
 .Dq Nm route Cm add
 operation.
+For example:
+.Bd -literal
+static_routes="mcast gif0local"
+route_mcast="-net 224.0.0.0/4 -iface gif0"
+route_gif0local="-host 169.254.1.1 -iface lo0"
+.Ed
 .It Va ipv6_static_routes
 .Pq Vt str
 The IPv6 equivalent of

==== //depot/projects/hammer/sys/amd64/amd64/fpu.c#19 (text+ko) ====

@@ -31,7 +31,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/amd64/amd64/fpu.c,v 1.153 2004/06/08 01:35:48 peter Exp $");
+__FBSDID("$FreeBSD: src/sys/amd64/amd64/fpu.c,v 1.154 2004/06/18 04:01:54 peter Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>

==== //depot/projects/hammer/sys/dev/ed/if_ed_pci.c#5 (text+ko) ====

@@ -18,7 +18,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/dev/ed/if_ed_pci.c,v 1.34 2003/10/31 18:31:58 brooks Exp $");
+__FBSDID("$FreeBSD: src/sys/dev/ed/if_ed_pci.c,v 1.36 2004/06/18 01:28:54 imp Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -58,11 +58,11 @@
 	{ 0x00000000,	NULL					}
 };
 
-static int	ed_pci_probe	(device_t);
-static int	ed_pci_attach	(device_t);
+static int	ed_pci_probe(device_t);
+static int	ed_pci_attach(device_t);
 
 static int
-ed_pci_probe (device_t dev)
+ed_pci_probe(device_t dev)
 {
 	u_int32_t	type = pci_get_devid(dev);
 	struct _pcsid	*ep =pci_ids;
@@ -71,10 +71,9 @@
 		++ep;
 	if (ep->desc) {
 		device_set_desc(dev, ep->desc);
-		return 0;
-	} else {
-		return ENXIO;
+		return (0);
 	}
+	return (ENXIO);
 }
 
 static int

==== //depot/projects/hammer/sys/fs/fifofs/fifo_vnops.c#20 (text+ko) ====

@@ -27,7 +27,7 @@
  * SUCH DAMAGE.
  *
  *	@(#)fifo_vnops.c	8.10 (Berkeley) 5/27/95
- * $FreeBSD: src/sys/fs/fifofs/fifo_vnops.c,v 1.97 2004/06/15 03:51:43 rwatson Exp $
+ * $FreeBSD: src/sys/fs/fifofs/fifo_vnops.c,v 1.99 2004/06/18 02:57:54 rwatson Exp $
  */
 
 #include <sys/param.h>
@@ -431,8 +431,10 @@
 
 	ap->a_kn->kn_hook = (caddr_t)so;
 
+	SOCKBUF_LOCK(sb);
 	SLIST_INSERT_HEAD(&sb->sb_sel.si_note, ap->a_kn, kn_selnext);
 	sb->sb_flags |= SB_KNOTE;
+	SOCKBUF_UNLOCK(sb);
 
 	return (0);
 }
@@ -442,23 +444,33 @@
 {
 	struct socket *so = (struct socket *)kn->kn_hook;
 
+	SOCKBUF_LOCK(&so->so_rcv);
 	SLIST_REMOVE(&so->so_rcv.sb_sel.si_note, kn, knote, kn_selnext);
 	if (SLIST_EMPTY(&so->so_rcv.sb_sel.si_note))
 		so->so_rcv.sb_flags &= ~SB_KNOTE;
+	SOCKBUF_UNLOCK(&so->so_rcv);
 }
 
 static int
 filt_fiforead(struct knote *kn, long hint)
 {
 	struct socket *so = (struct socket *)kn->kn_hook;
+	int need_lock, result;
 
+	need_lock = !SOCKBUF_OWNED(&so->so_rcv);
+	if (need_lock)
+		SOCKBUF_LOCK(&so->so_rcv);
 	kn->kn_data = so->so_rcv.sb_cc;
 	if (so->so_rcv.sb_state & SBS_CANTRCVMORE) {
 		kn->kn_flags |= EV_EOF;
-		return (1);
+		result = 1;
+	} else {
+		kn->kn_flags &= ~EV_EOF;
+		result = (kn->kn_data > 0);
 	}
-	kn->kn_flags &= ~EV_EOF;
-	return (kn->kn_data > 0);
+	if (need_lock)
+		SOCKBUF_UNLOCK(&so->so_rcv);
+	return (result);
 }
 
 static void
@@ -466,23 +478,34 @@
 {
 	struct socket *so = (struct socket *)kn->kn_hook;
 
+	SOCKBUF_LOCK(&so->so_snd);
 	SLIST_REMOVE(&so->so_snd.sb_sel.si_note, kn, knote, kn_selnext);
 	if (SLIST_EMPTY(&so->so_snd.sb_sel.si_note))
 		so->so_snd.sb_flags &= ~SB_KNOTE;
+	SOCKBUF_UNLOCK(&so->so_snd);
 }
 
 static int
 filt_fifowrite(struct knote *kn, long hint)
 {
 	struct socket *so = (struct socket *)kn->kn_hook;
+	int need_lock, result;
 
+	need_lock = !SOCKBUF_OWNED(&so->so_snd);
+	if (need_lock)
+		SOCKBUF_LOCK(&so->so_snd);
 	kn->kn_data = sbspace(&so->so_snd);
+	/* Unlocked read. */
 	if (so->so_snd.sb_state & SBS_CANTSENDMORE) {
 		kn->kn_flags |= EV_EOF;
-		return (1);
+		result = 1;
+	} else {
+		kn->kn_flags &= ~EV_EOF;
+	        result = (kn->kn_data >= so->so_snd.sb_lowat);
 	}
-	kn->kn_flags &= ~EV_EOF;
-	return (kn->kn_data >= so->so_snd.sb_lowat);
+	if (need_lock)
+		SOCKBUF_UNLOCK(&so->so_snd);
+	return (result);
 }
 
 /* ARGSUSED */

==== //depot/projects/hammer/sys/fs/portalfs/portal_vnops.c#7 (text+ko) ====

@@ -31,7 +31,7 @@
  *
  *	@(#)portal_vnops.c	8.14 (Berkeley) 5/21/95
  *
- * $FreeBSD: src/sys/fs/portalfs/portal_vnops.c,v 1.62 2004/04/07 20:46:01 imp Exp $
+ * $FreeBSD: src/sys/fs/portalfs/portal_vnops.c,v 1.63 2004/06/17 22:48:09 rwatson Exp $
  */
 
 /*
@@ -304,8 +304,12 @@
 	 */
 	so->so_rcv.sb_timeo = 0;
 	so->so_snd.sb_timeo = 0;
+	SOCKBUF_LOCK(&so->so_rcv);
 	so->so_rcv.sb_flags |= SB_NOINTR;
+	SOCKBUF_UNLOCK(&so->so_rcv);
+	SOCKBUF_LOCK(&so->so_snd);
 	so->so_snd.sb_flags |= SB_NOINTR;
+	SOCKBUF_UNLOCK(&so->so_snd);
 
 
 	pcred.pcr_flag = ap->a_mode;

==== //depot/projects/hammer/sys/i386/isa/npx.c#19 (text+ko) ====

@@ -31,7 +31,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/i386/isa/npx.c,v 1.149 2004/06/06 15:17:44 bde Exp $");
+__FBSDID("$FreeBSD: src/sys/i386/isa/npx.c,v 1.151 2004/06/18 02:10:55 bde Exp $");
 
 #include "opt_cpu.h"
 #include "opt_debug_npx.h"
@@ -872,6 +872,15 @@
 {
 	struct thread *td;
 
+	/*
+	 * Discard pending exceptions in the !cpu_fxsr case so that unmasked
+	 * ones don't cause a panic on the next frstor.
+	 */
+#ifdef CPU_ENABLE_SSE
+	if (!cpu_fxsr)
+#endif
+		fnclex();
+
 	td = PCPU_GET(fpcurthread);
 	PCPU_SET(fpcurthread, NULL);
 	td->td_pcb->pcb_flags &= ~PCB_NPXINITDONE;

==== //depot/projects/hammer/sys/kern/kern_time.c#10 (text+ko) ====

@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/kern/kern_time.c,v 1.106 2004/04/05 21:03:35 imp Exp $");
+__FBSDID("$FreeBSD: src/sys/kern/kern_time.c,v 1.107 2004/06/17 23:12:12 kbyanc Exp $");
 
 #include "opt_mac.h"
 
@@ -156,13 +156,31 @@
 clock_gettime(struct thread *td, struct clock_gettime_args *uap)
 {
 	struct timespec ats;
+	struct timeval user, sys;
 
-	if (uap->clock_id == CLOCK_REALTIME)
+	switch (uap->clock_id) {
+	case CLOCK_REALTIME:
 		nanotime(&ats);
-	else if (uap->clock_id == CLOCK_MONOTONIC)
+		break;
+	case CLOCK_MONOTONIC:
 		nanouptime(&ats);
-	else
+		break;
+	case CLOCK_VIRTUAL:
+		calcru(td->td_proc, &user, &sys, NULL);
+		TIMEVAL_TO_TIMESPEC(&user, &ats);
+		break;
+	case CLOCK_PROF:
+		calcru(td->td_proc, &user, &sys, NULL);
+		ats.tv_sec = user.tv_sec + sys.tv_sec;
+		ats.tv_nsec = (user.tv_usec + sys.tv_usec) * 1000;
+		if (ats.tv_nsec > 1000000000) {
+			ats.tv_sec++;
+			ats.tv_nsec -= 1000000000;
+		}
+		break;
+	default:
 		return (EINVAL);
+	}
 	return (copyout(&ats, uap->tp, sizeof(ats)));
 }
 
@@ -216,19 +234,31 @@
 	struct timespec ts;
 	int error;
 
-	if (uap->clock_id != CLOCK_REALTIME)
-		return (EINVAL);
-	error = 0;
-	if (uap->tp) {
-		ts.tv_sec = 0;
+	ts.tv_sec = 0;
+
+	switch (uap->clock_id) {
+	case CLOCK_REALTIME:
+	case CLOCK_MONOTONIC:
 		/*
 		 * Round up the result of the division cheaply by adding 1.
 		 * Rounding up is especially important if rounding down
 		 * would give 0.  Perfect rounding is unimportant.
 		 */
 		ts.tv_nsec = 1000000000 / tc_getfrequency() + 1;
+		break;
+	case CLOCK_VIRTUAL:
+	case CLOCK_PROF:
+		/* Accurately round up here because we can do so cheaply. */
+		ts.tv_nsec = (1000000000 + hz - 1) / hz;
+		break;
+	default:
+		return (EINVAL);
+	}
+
+	error = 0;
+	if (uap->tp)
 		error = copyout(&ts, uap->tp, sizeof(ts));
-	}
+
 	return (error);
 }
 

==== //depot/projects/hammer/sys/kern/sys_socket.c#11 (text+ko) ====

@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/kern/sys_socket.c,v 1.59 2004/06/14 18:16:19 rwatson Exp $");
+__FBSDID("$FreeBSD: src/sys/kern/sys_socket.c,v 1.60 2004/06/17 22:48:09 rwatson Exp $");
 
 #include "opt_mac.h"
 
@@ -131,21 +131,41 @@
 	switch (cmd) {
 
 	case FIONBIO:
+		SOCK_LOCK(so);
 		if (*(int *)data)
 			so->so_state |= SS_NBIO;
 		else
 			so->so_state &= ~SS_NBIO;
+		SOCK_UNLOCK(so);
 		return (0);
 
 	case FIOASYNC:
+		/*
+		 * XXXRW: This code separately acquires SOCK_LOCK(so)
+		 * and SOCKBUF_LOCK(&so->so_rcv) even though they are
+		 * the same mutex to avoid introducing the assumption
+		 * that they are the same.
+		 */
 		if (*(int *)data) {
+			SOCK_LOCK(so);
 			so->so_state |= SS_ASYNC;
+			SOCK_UNLOCK(so);
+			SOCKBUF_LOCK(&so->so_rcv);
 			so->so_rcv.sb_flags |= SB_ASYNC;
+			SOCKBUF_UNLOCK(&so->so_rcv);
+			SOCKBUF_LOCK(&so->so_snd);
 			so->so_snd.sb_flags |= SB_ASYNC;
+			SOCKBUF_UNLOCK(&so->so_snd);
 		} else {
+			SOCK_LOCK(so);
 			so->so_state &= ~SS_ASYNC;
+			SOCK_UNLOCK(so);
+			SOCKBUF_LOCK(&so->so_rcv);
 			so->so_rcv.sb_flags &= ~SB_ASYNC;
+			SOCKBUF_UNLOCK(&so->so_rcv);
+			SOCKBUF_LOCK(&so->so_snd);
 			so->so_snd.sb_flags &= ~SB_ASYNC;
+			SOCKBUF_UNLOCK(&so->so_snd);
 		}
 		return (0);
 

==== //depot/projects/hammer/sys/kern/uipc_socket.c#26 (text+ko) ====

@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/kern/uipc_socket.c,v 1.178 2004/06/14 18:16:19 rwatson Exp $");
+__FBSDID("$FreeBSD: src/sys/kern/uipc_socket.c,v 1.181 2004/06/18 04:02:56 rwatson Exp $");
 
 #include "opt_inet.h"
 #include "opt_mac.h"
@@ -277,8 +277,11 @@
 		return (error);
 	}
 	ACCEPT_LOCK();
-	if (TAILQ_EMPTY(&so->so_comp))
+	if (TAILQ_EMPTY(&so->so_comp)) {
+		SOCK_LOCK(so);
 		so->so_options |= SO_ACCEPTCONN;
+		SOCK_UNLOCK(so);
+	}
 	if (backlog < 0 || backlog > somaxconn)
 		backlog = somaxconn;
 	so->so_qlimit = backlog;
@@ -448,14 +451,13 @@
 	struct socket *so;
 	struct sockaddr **nam;
 {
-	int s = splnet();
 	int error;
 
-	if ((so->so_state & SS_NOFDREF) == 0)
-		panic("soaccept: !NOFDREF");
+	SOCK_LOCK(so);
+	KASSERT((so->so_state & SS_NOFDREF) != 0, ("soaccept: !NOFDREF"));
 	so->so_state &= ~SS_NOFDREF;
+	SOCK_UNLOCK(so);
 	error = (*so->so_proto->pr_usrreqs->pru_accept)(so, nam);
-	splx(s);
 	return (error);
 }
 
@@ -504,20 +506,13 @@
 sodisconnect(so)
 	struct socket *so;
 {
-	int s = splnet();
 	int error;
 
-	if ((so->so_state & SS_ISCONNECTED) == 0) {
-		error = ENOTCONN;
-		goto bad;
-	}
-	if (so->so_state & SS_ISDISCONNECTING) {
-		error = EALREADY;
-		goto bad;
-	}
+	if ((so->so_state & SS_ISCONNECTED) == 0)
+		return (ENOTCONN);
+	if (so->so_state & SS_ISDISCONNECTING)
+		return (EALREADY);
 	error = (*so->so_proto->pr_usrreqs->pru_disconnect)(so);
-bad:
-	splx(s);
 	return (error);
 }
 
@@ -754,9 +749,11 @@
 				break;
 			}
 		    } while (space > 0 && atomic);
-		    if (dontroute)
+		    if (dontroute) {
+			    SOCK_LOCK(so);
 			    so->so_options |= SO_DONTROUTE;
-		    s = splnet();				/* XXX */
+			    SOCK_UNLOCK(so);
+		    }
 		    /*
 		     * XXX all the SBS_CANTSENDMORE checks previously
 		     * done could be out of date.  We could have recieved
@@ -781,8 +778,11 @@
 			(resid > 0 && space > 0) ? PRUS_MORETOCOME : 0,
 			top, addr, control, td);
 		    splx(s);
-		    if (dontroute)
+		    if (dontroute) {
+			    SOCK_LOCK(so);
 			    so->so_options &= ~SO_DONTROUTE;
+			    SOCK_UNLOCK(so);
+		    }
 		    clen = 0;
 		    control = NULL;
 		    top = NULL;
@@ -1396,11 +1396,13 @@
 			if (error)
 				goto bad;
 
+			SOCK_LOCK(so);
 			so->so_linger = l.l_linger;
 			if (l.l_onoff)
 				so->so_options |= SO_LINGER;
 			else
 				so->so_options &= ~SO_LINGER;
+			SOCK_UNLOCK(so);
 			break;
 
 		case SO_DEBUG:
@@ -1418,10 +1420,12 @@
 					    sizeof optval);
 			if (error)
 				goto bad;
+			SOCK_LOCK(so);
 			if (optval)
 				so->so_options |= sopt->sopt_name;
 			else
 				so->so_options &= ~sopt->sopt_name;
+			SOCK_UNLOCK(so);
 			break;
 
 		case SO_SNDBUF:
@@ -1842,12 +1846,16 @@
 		    (POLLIN | POLLINIGNEOF | POLLPRI | POLLRDNORM |
 		     POLLRDBAND)) {
 			selrecord(td, &so->so_rcv.sb_sel);
+			SOCKBUF_LOCK(&so->so_rcv);
 			so->so_rcv.sb_flags |= SB_SEL;
+			SOCKBUF_UNLOCK(&so->so_rcv);
 		}
 
 		if (events & (POLLOUT | POLLWRNORM)) {
 			selrecord(td, &so->so_snd.sb_sel);
+			SOCKBUF_LOCK(&so->so_snd);
 			so->so_snd.sb_flags |= SB_SEL;
+			SOCKBUF_UNLOCK(&so->so_snd);
 		}
 	}
 
@@ -1860,7 +1868,6 @@
 {
 	struct socket *so = kn->kn_fp->f_data;
 	struct sockbuf *sb;
-	int s;
 
 	switch (kn->kn_filter) {
 	case EVFILT_READ:
@@ -1878,10 +1885,10 @@
 		return (1);
 	}
 
-	s = splnet();
+	SOCKBUF_LOCK(sb);
 	SLIST_INSERT_HEAD(&sb->sb_sel.si_note, kn, kn_selnext);
 	sb->sb_flags |= SB_KNOTE;
-	splx(s);
+	SOCKBUF_UNLOCK(sb);
 	return (0);
 }
 
@@ -1889,12 +1896,12 @@
 filt_sordetach(struct knote *kn)
 {
 	struct socket *so = kn->kn_fp->f_data;
-	int s = splnet();
 
+	SOCKBUF_LOCK(&so->so_rcv);
 	SLIST_REMOVE(&so->so_rcv.sb_sel.si_note, kn, knote, kn_selnext);
 	if (SLIST_EMPTY(&so->so_rcv.sb_sel.si_note))
 		so->so_rcv.sb_flags &= ~SB_KNOTE;
-	splx(s);
+	SOCKBUF_UNLOCK(&so->so_rcv);
 }
 
 /*ARGSUSED*/
@@ -1902,8 +1909,16 @@
 filt_soread(struct knote *kn, long hint)
 {
 	struct socket *so = kn->kn_fp->f_data;
-	int result;
+	int need_lock, result;
 
+	/*
+	 * XXXRW: Conditional locking because filt_soread() can be called
+	 * either from KNOTE() in the socket context where the socket buffer
+	 * lock is already held, or from kqueue() itself.
+	 */
+	need_lock = !SOCKBUF_OWNED(&so->so_rcv);
+	if (need_lock)
+		SOCKBUF_LOCK(&so->so_rcv);
 	kn->kn_data = so->so_rcv.sb_cc - so->so_rcv.sb_ctl;
 	if (so->so_rcv.sb_state & SBS_CANTRCVMORE) {
 		kn->kn_flags |= EV_EOF;
@@ -1915,6 +1930,8 @@
 		result = (kn->kn_data >= kn->kn_sdata);
 	else
 		result = (so->so_rcv.sb_cc >= so->so_rcv.sb_lowat);
+	if (need_lock)
+		SOCKBUF_UNLOCK(&so->so_rcv);
 	return (result);
 }
 
@@ -1922,12 +1939,12 @@
 filt_sowdetach(struct knote *kn)
 {
 	struct socket *so = kn->kn_fp->f_data;
-	int s = splnet();
 
+	SOCKBUF_LOCK(&so->so_snd);
 	SLIST_REMOVE(&so->so_snd.sb_sel.si_note, kn, knote, kn_selnext);
 	if (SLIST_EMPTY(&so->so_snd.sb_sel.si_note))
 		so->so_snd.sb_flags &= ~SB_KNOTE;
-	splx(s);
+	SOCKBUF_UNLOCK(&so->so_snd);
 }
 
 /*ARGSUSED*/
@@ -1935,8 +1952,16 @@
 filt_sowrite(struct knote *kn, long hint)
 {
 	struct socket *so = kn->kn_fp->f_data;
-	int result;
+	int need_lock, result;
 
+	/*
+	 * XXXRW: Conditional locking because filt_soread() can be called
+	 * either from KNOTE() in the socket context where the socket buffer
+	 * lock is already held, or from kqueue() itself.
+	 */
+	need_lock = !SOCKBUF_OWNED(&so->so_snd);
+	if (need_lock)
+		SOCKBUF_LOCK(&so->so_snd);
 	kn->kn_data = sbspace(&so->so_snd);
 	if (so->so_snd.sb_state & SBS_CANTSENDMORE) {
 		kn->kn_flags |= EV_EOF;
@@ -1951,6 +1976,8 @@
 		result = (kn->kn_data >= kn->kn_sdata);
 	else
 		result = (kn->kn_data >= so->so_snd.sb_lowat);
+	if (need_lock)
+		SOCKBUF_UNLOCK(&so->so_snd);
 	return (result);
 }
 

==== //depot/projects/hammer/sys/kern/uipc_socket2.c#21 (text+ko) ====

@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/kern/uipc_socket2.c,v 1.131 2004/06/15 03:51:44 rwatson Exp $");
+__FBSDID("$FreeBSD: src/sys/kern/uipc_socket2.c,v 1.132 2004/06/17 22:48:09 rwatson Exp $");
 
 #include "opt_mac.h"
 #include "opt_param.h"
@@ -105,8 +105,10 @@
 	register struct socket *so;
 {
 
+	SOCK_LOCK(so);
 	so->so_state &= ~(SS_ISCONNECTED|SS_ISDISCONNECTING);
 	so->so_state |= SS_ISCONNECTING;
+	SOCK_UNLOCK(so);
 }
 
 void
@@ -115,8 +117,10 @@
 {
 	struct socket *head;
 
+	SOCK_LOCK(so);
 	so->so_state &= ~(SS_ISCONNECTING|SS_ISDISCONNECTING|SS_ISCONFIRMING);
 	so->so_state |= SS_ISCONNECTED;
+	SOCK_UNLOCK(so);
 	ACCEPT_LOCK();
 	head = so->so_head;
 	if (head != NULL && (so->so_qstate & SQ_INCOMP)) {
@@ -132,11 +136,13 @@
 			wakeup_one(&head->so_timeo);
 		} else {
 			ACCEPT_UNLOCK();
+			SOCK_LOCK(so);
 			so->so_upcall =
 			    head->so_accf->so_accept_filter->accf_callback;
 			so->so_upcallarg = head->so_accf->so_accept_filter_arg;
 			so->so_rcv.sb_flags |= SB_UPCALL;
 			so->so_options &= ~SO_ACCEPTFILTER;
+			SOCK_UNLOCK(so);
 			so->so_upcall(so, so->so_upcallarg, M_TRYWAIT);
 		}
 		return;
@@ -152,8 +158,15 @@
 	register struct socket *so;
 {
 
+	/*
+	 * XXXRW: This code separately acquires SOCK_LOCK(so) and
+	 * SOCKBUF_LOCK(&so->so_rcv) even though they are the same mutex to
+	 * avoid introducing the assumption  that they are the same.
+	 */
+	SOCK_LOCK(so);
 	so->so_state &= ~SS_ISCONNECTING;
 	so->so_state |= SS_ISDISCONNECTING;
+	SOCK_UNLOCK(so);
 	SOCKBUF_LOCK(&so->so_rcv);
 	so->so_rcv.sb_state |= SBS_CANTRCVMORE;
 	SOCKBUF_UNLOCK(&so->so_rcv);
@@ -170,8 +183,15 @@
 	register struct socket *so;
 {
 
+	/*
+	 * XXXRW: This code separately acquires SOCK_LOCK(so) and
+	 * SOCKBUF_LOCK(&so->so_rcv) even though they are the same mutex to
+	 * avoid introducing the assumption  that they are the same.
+	 */
+	SOCK_LOCK(so);
 	so->so_state &= ~(SS_ISCONNECTING|SS_ISCONNECTED|SS_ISDISCONNECTING);
 	so->so_state |= SS_ISDISCONNECTED;
+	SOCK_UNLOCK(so);
 	SOCKBUF_LOCK(&so->so_rcv);
 	so->so_rcv.sb_state |= SBS_CANTRCVMORE;
 	SOCKBUF_UNLOCK(&so->so_rcv);
@@ -400,12 +420,16 @@
 		goto bad;
 	if (sbreserve(&so->so_rcv, rcvcc, so, td) == 0)
 		goto bad2;
+	SOCKBUF_LOCK(&so->so_rcv);
 	if (so->so_rcv.sb_lowat == 0)
 		so->so_rcv.sb_lowat = 1;
+	SOCKBUF_UNLOCK(&so->so_rcv);
+	SOCKBUF_LOCK(&so->so_snd);
 	if (so->so_snd.sb_lowat == 0)
 		so->so_snd.sb_lowat = MCLBYTES;
 	if (so->so_snd.sb_lowat > so->so_snd.sb_hiwat)
 		so->so_snd.sb_lowat = so->so_snd.sb_hiwat;
+	SOCKBUF_UNLOCK(&so->so_snd);
 	return (0);
 bad2:
 	sbrelease(&so->so_snd, so);

==== //depot/projects/hammer/sys/kern/vfs_aio.c#19 (text+ko) ====

@@ -19,7 +19,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/kern/vfs_aio.c,v 1.170 2004/05/30 20:34:58 phk Exp $");
+__FBSDID("$FreeBSD: src/sys/kern/vfs_aio.c,v 1.171 2004/06/17 22:48:09 rwatson Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -566,8 +566,12 @@
 			so = fp->f_data;
 			TAILQ_REMOVE(&so->so_aiojobq, aiocbe, list);
 			if (TAILQ_EMPTY(&so->so_aiojobq)) {
+				SOCKBUF_LOCK(&so->so_snd);
 				so->so_snd.sb_flags &= ~SB_AIO;
+				SOCKBUF_UNLOCK(&so->so_snd);
+				SOCKBUF_LOCK(&so->so_rcv);
 				so->so_rcv.sb_flags &= ~SB_AIO;
+				SOCKBUF_UNLOCK(&so->so_rcv);
 			}
 		}
 		TAILQ_REMOVE(&ki->kaio_sockqueue, aiocbe, plist);
@@ -1231,10 +1235,14 @@
 
 	if (sb == &so->so_snd) {
 		opcode = LIO_WRITE;
+		SOCKBUF_LOCK(&so->so_snd);
 		so->so_snd.sb_flags &= ~SB_AIO;
+		SOCKBUF_UNLOCK(&so->so_snd);
 	} else {
 		opcode = LIO_READ;
+		SOCKBUF_LOCK(&so->so_rcv);
 		so->so_rcv.sb_flags &= ~SB_AIO;
+		SOCKBUF_UNLOCK(&so->so_rcv);
 	}
 
 	for (cb = TAILQ_FIRST(&so->so_aiojobq); cb; cb = cbn) {
@@ -1443,10 +1451,15 @@
 		    LIO_WRITE) && (!sowriteable(so)))) {
 			TAILQ_INSERT_TAIL(&so->so_aiojobq, aiocbe, list);
 			TAILQ_INSERT_TAIL(&ki->kaio_sockqueue, aiocbe, plist);
-			if (opcode == LIO_READ)
+			if (opcode == LIO_READ) {
+				SOCKBUF_LOCK(&so->so_rcv);
 				so->so_rcv.sb_flags |= SB_AIO;
-			else
+				SOCKBUF_UNLOCK(&so->so_rcv);
+			} else {
+				SOCKBUF_LOCK(&so->so_snd);
 				so->so_snd.sb_flags |= SB_AIO;
+				SOCKBUF_UNLOCK(&so->so_snd);
+			}
 			aiocbe->jobstate = JOBST_JOBQGLOBAL; /* XXX */
 			ki->kaio_queue_count++;
 			num_queue_count++;

==== //depot/projects/hammer/sys/netgraph/bluetooth/socket/ng_btsocket_rfcomm.c#9 (text+ko) ====

@@ -26,7 +26,7 @@
  * SUCH DAMAGE.
  *
  * $Id: ng_btsocket_rfcomm.c,v 1.28 2003/09/14 23:29:06 max Exp $
- * $FreeBSD: src/sys/netgraph/bluetooth/socket/ng_btsocket_rfcomm.c,v 1.10 2004/06/14 18:16:21 rwatson Exp $
+ * $FreeBSD: src/sys/netgraph/bluetooth/socket/ng_btsocket_rfcomm.c,v 1.12 2004/06/18 05:09:42 rwatson Exp $
  */
 
 #include <sys/param.h>
@@ -997,8 +997,12 @@
 			/* Close L2CAP socket */
 			s->l2so->so_upcallarg = NULL;
 			s->l2so->so_upcall = NULL;
+			SOCKBUF_LOCK(&s->l2so->so_rcv);
 			s->l2so->so_rcv.sb_flags &= ~SB_UPCALL;
+			SOCKBUF_UNLOCK(&s->l2so->so_rcv);
+			SOCKBUF_LOCK(&s->l2so->so_snd);
 			s->l2so->so_snd.sb_flags &= ~SB_UPCALL;
+			SOCKBUF_UNLOCK(&s->l2so->so_snd);
 			soclose(s->l2so);
 
 			mtx_unlock(&s->session_mtx);
@@ -1237,8 +1241,12 @@
 	/* Prepare L2CAP socket */
 	l2so->so_upcallarg = NULL;
 	l2so->so_upcall = ng_btsocket_rfcomm_upcall;
+	SOCKBUF_LOCK(&l2so->so_rcv);
 	l2so->so_rcv.sb_flags |= SB_UPCALL;
+	SOCKBUF_UNLOCK(&l2so->so_rcv);
+	SOCKBUF_LOCK(&l2so->so_snd);
 	l2so->so_snd.sb_flags |= SB_UPCALL;
+	SOCKBUF_UNLOCK(&l2so->so_snd);
 	l2so->so_state |= SS_NBIO;
 	s->l2so = l2so;
 
@@ -1317,8 +1325,12 @@
 	/* Return L2CAP socket back to its original state */
 	l2so->so_upcallarg = NULL;
 	l2so->so_upcall = NULL;
+	SOCKBUF_LOCK(&l2so->so_rcv);
 	l2so->so_rcv.sb_flags &= ~SB_UPCALL;
+	SOCKBUF_UNLOCK(&l2so->so_rcv);
+	SOCKBUF_LOCK(&l2so->so_snd);
 	l2so->so_snd.sb_flags &= ~SB_UPCALL;
+	SOCKBUF_UNLOCK(&l2so->so_snd);
 	l2so->so_state &= ~SS_NBIO;
 
 	mtx_destroy(&s->session_mtx);

==== //depot/projects/hammer/sys/netgraph/ng_ksocket.c#11 (text+ko) ====

@@ -36,7 +36,7 @@
  *
  * Author: Archie Cobbs <archie at freebsd.org>
  *
- * $FreeBSD: src/sys/netgraph/ng_ksocket.c,v 1.44 2004/06/14 18:16:20 rwatson Exp $
+ * $FreeBSD: src/sys/netgraph/ng_ksocket.c,v 1.45 2004/06/17 22:48:10 rwatson Exp $
  * $Whistle: ng_ksocket.c,v 1.1 1999/11/16 20:04:40 archie Exp $
  */
 
@@ -609,9 +609,15 @@
 	/* Add our hook for incoming data and other events */
 	priv->so->so_upcallarg = (caddr_t)node;
 	priv->so->so_upcall = ng_ksocket_incoming;
+	SOCKBUF_LOCK(&priv->so->so_rcv);
 	priv->so->so_rcv.sb_flags |= SB_UPCALL;
+	SOCKBUF_UNLOCK(&priv->so->so_rcv);
+	SOCKBUF_LOCK(&priv->so->so_snd);

>>> TRUNCATED FOR MAIL (1000 lines) <<<


More information about the p4-projects mailing list