NetBSD Problem Report #24253

Received: (qmail 29979 invoked by uid 605); 26 Jan 2004 18:05:53 -0000
Message-Id: <200401261805.i0QI5pR01466@angel.stchome.com>
Date: Mon, 26 Jan 2004 11:05:51 -0700 (MST)
From: jesse_off@stchome.com
Sender: gnats-bugs-owner@NetBSD.org
Reply-To: jesse_off@stchome.com
To: gnats-bugs@gnats.netbsd.org
Subject: broken pipe race condition in CVS pserver
X-Send-Pr-Version: 3.95

>Number:         24253
>Category:       bin
>Synopsis:       broken pipe race condition in CVS pserver
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    bin-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Mon Jan 26 18:06:00 +0000 2004
>Closed-Date:    
>Last-Modified:  
>Originator:     
>Release:        NetBSD 1.6.2_RC4
>Organization:
	Scientific Technologies Corporation
>Environment:
System: NetBSD angel 1.6.2_RC4 NetBSD 1.6.2_RC4 (DELL600SC) #13: Tue Jan 13 17:33:29 MST 2004 root@angel:/usr/src/sys/arch/i386/compile/DELL600SC i386
Architecture: i386
Machine: i386
>Description:
	There is a race condition in the CVS pserver code that
	causes CVS ops to abort with the "broken pipe" error message.
	What happens is the parent CVS process tries to tell the
	child to stop by writing a "S" to its flow control pipe.
	However, the child may already be dead and its read pipe
	is therefore closed.  This happens when there is enough
	outstanding data in the kernel socket buffers not yet read
	by the parent process when the child exits.  The master
	reads this data in and tries to send a message on its
	flowcontrol pipe to stop, but its flowcontrol pipe is
	already closed and the kernel sends a SIGPIPE to the parent
	PID.
>How-To-Repeat:
	Very difficult, happened to have the right set of conditions for
	this to appear constantly last week.
>Fix:
Don't let child process exit until parent has noticed output is done
and closed the flowcontrol pipe.  Patch below...


Index: server.c
===================================================================
RCS file: /cvsroot/src/gnu/dist/cvs/src/server.c,v
retrieving revision 1.6.2.3
diff -u -r1.6.2.3 server.c
--- server.c	2003/12/17 17:41:02	1.6.2.3
+++ server.c	2004/01/26 17:50:44
@@ -2299,8 +2299,28 @@
 # endif /* SERVER_LO_WATER */

 static int set_nonblock_fd PROTO((int));
+static int unset_nonblock_fd PROTO((int));

 /*
+ * Set fd to blocking I/O.  Returns 0 for success or errno
+ * code.
+ */
+
+static int
+unset_nonblock_fd (fd)
+     int fd;
+{
+    int flags;
+
+    flags = fcntl (fd, F_GETFL, 0);
+    if (flags < 0)
+	return errno;
+    if (fcntl (fd, F_SETFL, flags | ~O_NONBLOCK) < 0)
+	return errno;
+    return 0;
+}
+
+/*
  * Set buffer BUF to non-blocking I/O.  Returns 0 for success or errno
  * code.
  */
@@ -2807,6 +2827,19 @@
 	 * the parent.
 	 */
 	buf_free (protocol);
+
+	close (STDIN_FILENO);
+	close (STDERR_FILENO);
+	close (STDOUT_FILENO);
+	close (protocol_pipe[1]);
+#ifdef SERVER_FLOWCONTROL
+	if (unset_nonblock_fd (flowcontrol_pipe[0]) == 0) 
+	{
+	  char junk;
+	  while (read (flowcontrol_pipe[0], &junk, 1) != 0);
+	}
+#endif
+
 	exit (exitstatus);
     }

>Release-Note:
>Audit-Trail:
>Unformatted:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2007 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.