Subject: Re: Assume at least POSIX.1-1988 for fcntl.h

From: Paul Eggert <[email-masked]>
Date: Wed, 14 Nov 2012 22:32:07 -0800

On 11/14/2012 09:33 AM, Eli Zaretskii wrote:

> In several places, it actually changes the code involved
> in dealing with the related issues.  Here's one example:

As far as I know, that is the only example involving O_NONBLOCK.

> Here, the code that was left is identical to the one used by platforms
> with O_NONBLOCK, but the code used by platforms with O_NDELAY was
> different in non-trivial ways.

Do those differences matter for Microsoft platforms?  If so, it's
simple to keep them just for DOS_NT, with the following further change:

=== modified file 'src/process.c'
--- src/process.c	2012-11-14 07:26:25 +0000
+++ src/process.c	2012-11-15 06:19:46 +0000
@@ -4797,6 +4797,14 @@
 #endif
 	      else if (nread == -1 && errno == EAGAIN)
 		;
+#ifdef DOS_NT
+	      /* Note that we cannot distinguish between no input
+		 available now and a closed pipe.
+		 With luck, a closed pipe will be accompanied by
+		 subprocess termination and SIGCHLD.  */
+	      else if (nread == 0 && !NETCONN_P (proc) && !SERIALCONN_P (proc))
+		;
+#endif
 #ifdef HAVE_PTYS
 	      /* On some OSs with ptys, when the process on one end of
 		 a pty exits, the other end gets an error reading with

> Another potential problem is that the Windows emulation of fcntl only
> works for sockets, whereas O_NONBLOCK is now used in other system
> calls, like in emacs_open etc.

emacs_open is the only other system call where it's used, and there it's
used only in code that is "#ifndef DOS_NT", so it should be OK.

> This patch also modifies code unrelated to O_NONBLOCK, like this one:

That's OK, as this patch is about all symbols defined by fcntl.h
in POSIX.1-1988, not just about O_NONBLOCK.

> Failing that, Someone(TM) will have to do the footwork of making
> sure these changes don't break non-Posix platforms.

The only non-POSIX platform are the Microsoft ones, right?
And if the above analysis is right, we should be OK.

Attached is a revised patch, relative to trunk bzr 110904,
and with the above extra change.

=== modified file 'ChangeLog'
--- ChangeLog	2012-11-14 04:55:41 +0000
+++ ChangeLog	2012-11-15 06:03:45 +0000
@@ -1,3 +1,8 @@
+2012-11-15  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for fcntl.h (Bug#12881).
+	* lib/gnulib.mk: Regenerate.
+
 2012-11-14  Paul Eggert  <[email-masked]>
 
 	Use faccessat, not access, when checking file permissions (Bug#12632).

=== modified file 'admin/CPP-DEFINES'
--- admin/CPP-DEFINES	2012-11-05 03:18:32 +0000
+++ admin/CPP-DEFINES	2012-11-14 07:26:25 +0000
@@ -420,8 +420,6 @@
 NSIG_MINIMUM
 NULL_DEVICE
 ORDINARY_LINK
-O_RDONLY
-O_RDWR
 PAGESIZE
 PREFER_VSUSP
 PTY_ITERATION

=== modified file 'admin/ChangeLog'
--- admin/ChangeLog	2012-11-14 04:55:41 +0000
+++ admin/ChangeLog	2012-11-15 06:03:45 +0000
@@ -1,3 +1,9 @@
+2012-11-15  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for fcntl.h (Bug#12881).
+	* CPP-DEFINES (O_RDONLY, O_RDWR): Remove.
+	* merge-gnulib (GNULIB_MODULES): Add fcntl-h.
+
 2012-11-14  Paul Eggert  <[email-masked]>
 
 	Use faccessat, not access, when checking file permissions (Bug#12632).

=== modified file 'admin/merge-gnulib'
--- admin/merge-gnulib	2012-11-14 04:55:41 +0000
+++ admin/merge-gnulib	2012-11-14 07:26:25 +0000
@@ -29,7 +29,7 @@
   alloca-opt c-ctype c-strcase
   careadlinkat close-stream crypto/md5 crypto/sha1 crypto/sha256 crypto/sha512
   dtoastr dtotimespec dup2 environ execinfo faccessat
-  filemode getloadavg getopt-gnu gettime gettimeofday
+  fcntl-h filemode getloadavg getopt-gnu gettime gettimeofday
   ignore-value intprops largefile lstat
   manywarnings mktime pselect pthread_sigmask readlink
   socklen stat-time stdalign stdarg stdbool stdio

=== modified file 'lib/gnulib.mk'
--- lib/gnulib.mk	2012-11-14 04:55:41 +0000
+++ lib/gnulib.mk	2012-11-14 07:26:25 +0000
@@ -21,7 +21,7 @@
 # the same distribution terms as the rest of that program.
 #
 # Generated by gnulib-tool.
-# Reproduce by: gnulib-tool --import --dir=. --lib=libgnu --source-base=lib --m4-base=m4 --doc-base=doc --tests-base=tests --aux-dir=build-aux --avoid=at-internal --avoid=errno --avoid=fchdir --avoid=fcntl --avoid=fstat --avoid=malloc-posix --avoid=msvc-inval --avoid=msvc-nothrow --avoid=openat-die --avoid=openat-h --avoid=raise --avoid=save-cwd --avoid=select --avoid=sigprocmask --avoid=sys_types --avoid=threadlib --makefile-name=gnulib.mk --conditional-dependencies --no-libtool --macro-prefix=gl --no-vc-files alloca-opt c-ctype c-strcase careadlinkat close-stream crypto/md5 crypto/sha1 crypto/sha256 crypto/sha512 dtoastr dtotimespec dup2 environ execinfo faccessat filemode getloadavg getopt-gnu gettime gettimeofday ignore-value intprops largefile lstat manywarnings mktime pselect pthread_sigmask readlink socklen stat-time stdalign stdarg stdbool stdio strftime strtoimax strtoumax symlink sys_stat sys_time time timer-time timespec-add timespec-sub utimens warnings
+# Reproduce by: gnulib-tool --import --dir=. --lib=libgnu --source-base=lib --m4-base=m4 --doc-base=doc --tests-base=tests --aux-dir=build-aux --avoid=at-internal --avoid=errno --avoid=fchdir --avoid=fcntl --avoid=fstat --avoid=malloc-posix --avoid=msvc-inval --avoid=msvc-nothrow --avoid=openat-die --avoid=openat-h --avoid=raise --avoid=save-cwd --avoid=select --avoid=sigprocmask --avoid=sys_types --avoid=threadlib --makefile-name=gnulib.mk --conditional-dependencies --no-libtool --macro-prefix=gl --no-vc-files alloca-opt c-ctype c-strcase careadlinkat close-stream crypto/md5 crypto/sha1 crypto/sha256 crypto/sha512 dtoastr dtotimespec dup2 environ execinfo faccessat fcntl-h filemode getloadavg getopt-gnu gettime gettimeofday ignore-value intprops largefile lstat manywarnings mktime pselect pthread_sigmask readlink socklen stat-time stdalign stdarg stdbool stdio strftime strtoimax strtoumax symlink sys_stat sys_time time timer-time timespec-add timespec-sub utimens warnings

 MOSTLYCLEANFILES += core *.stackdump

=== modified file 'nt/ChangeLog'
--- nt/ChangeLog	2012-11-14 17:22:55 +0000
+++ nt/ChangeLog	2012-11-15 06:03:45 +0000
@@ -1,3 +1,9 @@
+2012-11-15  Paul Eggert  <[email-masked]>
+
+	Assume POSIX 1003.1-1988 or later for fcntl.h (Bug#12881).
+	* inc/sys/socket.h (O_NONBLOCK): Rename from O_NDELAY, since the
+	POSIX name for this flag is O_NONBLOCK.  All uses changed.
+
 2012-11-14  Eli Zaretskii  <[email-masked]>
 
 	* inc/unistd.h (faccessat): Add prototype.

=== modified file 'nt/inc/sys/socket.h'
--- nt/inc/sys/socket.h	2012-09-30 21:36:42 +0000
+++ nt/inc/sys/socket.h	2012-11-14 07:26:25 +0000
@@ -119,7 +119,7 @@
    an fcntl function, for setting sockets to non-blocking mode.  */
 int fcntl (int s, int cmd, int options);
 #define F_SETFL   4
-#define O_NDELAY  04000
+#define O_NONBLOCK  04000
 
 /* we are providing a real h_errno variable */
 #undef h_errno

=== modified file 'src/ChangeLog'
--- src/ChangeLog	2012-11-15 00:41:32 +0000
+++ src/ChangeLog	2012-11-15 06:19:46 +0000
@@ -1,5 +1,27 @@
 2012-11-15  Paul Eggert  <[email-masked]>
 
+	Assume POSIX 1003.1-1988 or later for fcntl.h (Bug#12881).
+	* callproc.c (relocate_fd): Assume F_DUPFD.
+	* emacs.c, term.c (O_RDWR): Remove.
+	* keyboard.c (tty_read_avail_input): Use O_NONBLOCK rather than
+	O_NDELAY, since O_NONBLOCK is the standard name for this flag.
+	* process.c (NON_BLOCKING_CONNECT, allocate_pty, create_process)
+	(create_pty, Fmake_network_process, server_accept_connection)
+	(wait_reading_process_output, init_process_emacs):
+	Assume O_NONBLOCK.
+	(wait_reading_process_output): Put in a special case for DOS_NT,
+	to mimick the older behavior where it had O_NDELAY but not O_NONBLOCK.
+	It's not clear this is needed, but it's a more-conservative change.
+	(create_process): Assume FD_CLOEXEC.
+	(create_process, create_pty): Assume O_NOCTTY.
+	* sysdep.c (init_sys_modes, reset_sys_modes): Assume F_SETFL.
+	(reset_sys_modes): Use O_NONBLOCK rather than O_NDELAY.
+	(serial_open): Assume O_NONBLOCK and O_NOCTTY.
+	* term.c (O_NOCTTY): Remove.
+	(init_tty): Assume O_IGNORE_CTTY is defined to 0 on platforms that
+	lack it, since gnulib guarantees this.
+	* w32.c (fcntl): Test for O_NONBLOCK rather than O_NDELAY.
+
 	* eval.c (mark_backtrace) [BYTE_MARK_STACK]: Remove stray '*'.
 	This follows up on the 2012-09-29 patch that removed indirection
 	for the 'function' field.  Reported by Sergey Vinokurov in

=== modified file 'src/callproc.c'
--- src/callproc.c	2012-11-14 04:55:41 +0000
+++ src/callproc.c	2012-11-14 07:26:25 +0000
@@ -1317,16 +1317,7 @@
     return fd;
   else
     {
-      int new;
-#ifdef F_DUPFD
-      new = fcntl (fd, F_DUPFD, minfd);
-#else
-      new = dup (fd);
-      if (new != -1)
-	/* Note that we hold the original FD open while we recurse,
-	   to guarantee we'll get a new FD if we need it.  */
-	new = relocate_fd (new, minfd);
-#endif
+      int new = fcntl (fd, F_DUPFD, minfd);
       if (new == -1)
 	{
 	  const char *message_1 = "Error while setting up child: ";

=== modified file 'src/emacs.c'
--- src/emacs.c	2012-11-08 19:12:23 +0000
+++ src/emacs.c	2012-11-14 07:26:25 +0000
@@ -95,10 +95,6 @@
 #include <sys/personality.h>
 #endif
 
-#ifndef O_RDWR
-#define O_RDWR 2
-#endif
-
 static const char emacs_version[] = VERSION;
 static const char emacs_copyright[] = COPYRIGHT;

=== modified file 'src/keyboard.c'
--- src/keyboard.c	2012-11-08 09:26:40 +0000
+++ src/keyboard.c	2012-11-14 07:26:25 +0000
@@ -6948,7 +6948,7 @@
 #elif defined USG || defined CYGWIN
   /* Read some input if available, but don't wait.  */
   n_to_read = sizeof cbuf;
-  fcntl (fileno (tty->input), F_SETFL, O_NDELAY);
+  fcntl (fileno (tty->input), F_SETFL, O_NONBLOCK);
 #else
 # error "Cannot read without possibly delaying"
 #endif
@@ -6982,7 +6982,7 @@
     }
   while (
          /* We used to retry the read if it was interrupted.
-            But this does the wrong thing when O_NDELAY causes
+            But this does the wrong thing when O_NONBLOCK causes
             an EAGAIN error.  Does anybody know of a situation
             where a retry is actually needed?  */
 #if 0

=== modified file 'src/process.c'
--- src/process.c	2012-11-14 04:55:41 +0000
+++ src/process.c	2012-11-15 06:19:46 +0000
@@ -208,11 +208,9 @@
 #ifndef NON_BLOCKING_CONNECT
 #ifdef HAVE_SELECT
 #if defined (HAVE_GETPEERNAME) || defined (GNU_LINUX)
-#if O_NONBLOCK || O_NDELAY
 #if defined (EWOULDBLOCK) || defined (EINPROGRESS)
 #define NON_BLOCKING_CONNECT
 #endif /* EWOULDBLOCK || EINPROGRESS */
-#endif /* O_NONBLOCK || O_NDELAY */
 #endif /* HAVE_GETPEERNAME || GNU_LINUX */
 #endif /* HAVE_SELECT */
 #endif /* NON_BLOCKING_CONNECT */
@@ -654,13 +652,7 @@
 #ifdef PTY_OPEN
 	PTY_OPEN;
 #else /* no PTY_OPEN */
-	{
-#  if O_NONBLOCK
-	  fd = emacs_open (pty_name, O_RDWR | O_NONBLOCK, 0);
-#  else
-	  fd = emacs_open (pty_name, O_RDWR | O_NDELAY, 0);
-#  endif
-	}
+	fd = emacs_open (pty_name, O_RDWR | O_NONBLOCK, 0);
 #endif /* no PTY_OPEN */
 
 	if (fd >= 0)
@@ -1598,7 +1590,7 @@
   int inchannel, outchannel;
   pid_t pid;
   int sv[2];
-#if !defined (WINDOWSNT) && defined (FD_CLOEXEC)
+#ifndef WINDOWSNT
   int wait_child_setup[2];
 #endif
 #ifdef SIGCHLD
@@ -1624,13 +1616,9 @@
 #if ! defined (USG) || defined (USG_SUBTTY_WORKS)
       /* On most USG systems it does not work to open the pty's tty here,
 	 then close it and reopen it in the child.  */
-#if O_NOCTTY
       /* Don't let this terminal become our controlling terminal
 	 (in case we don't have one).  */
       forkout = forkin = emacs_open (pty_name, O_RDWR | O_NOCTTY, 0);
-#else
-      forkout = forkin = emacs_open (pty_name, O_RDWR, 0);
-#endif
       if (forkin < 0)
 	report_file_error ("Opening pty", Qnil);
 #else
@@ -1659,7 +1647,7 @@
       forkin = sv[0];
     }
 
-#if !defined (WINDOWSNT) && defined (FD_CLOEXEC)
+#ifndef WINDOWSNT
     {
       int tem;
 
@@ -1678,15 +1666,8 @@
     }
 #endif
 
-#if O_NONBLOCK
   fcntl (inchannel, F_SETFL, O_NONBLOCK);
   fcntl (outchannel, F_SETFL, O_NONBLOCK);
-#else
-#if O_NDELAY
-  fcntl (inchannel, F_SETFL, O_NDELAY);
-  fcntl (outchannel, F_SETFL, O_NDELAY);
-#endif
-#endif
 
   /* Record this as an active process, with its channels.
      As a result, child_setup will close Emacs's side of the pipes.  */
@@ -1845,9 +1826,7 @@
       pid = child_setup (xforkin, xforkout, xforkout,
 			 new_argv, 1, encoded_current_dir);
 #else  /* not WINDOWSNT */
-#ifdef FD_CLOEXEC
       emacs_close (wait_child_setup[0]);
-#endif
       child_setup (xforkin, xforkout, xforkout,
 		   new_argv, 1, encoded_current_dir);
 #endif /* not WINDOWSNT */
@@ -1906,7 +1885,7 @@
 
       pset_tty_name (XPROCESS (process), lisp_pty_name);
 
-#if !defined (WINDOWSNT) && defined (FD_CLOEXEC)
+#ifndef WINDOWSNT
       /* Wait for child_setup to complete in case that vfork is
 	 actually defined as fork.  The descriptor wait_child_setup[1]
 	 of a pipe is closed at the child side either by close-on-exec
@@ -1943,13 +1922,9 @@
 #if ! defined (USG) || defined (USG_SUBTTY_WORKS)
       /* On most USG systems it does not work to open the pty's tty here,
 	 then close it and reopen it in the child.  */
-#if O_NOCTTY
       /* Don't let this terminal become our controlling terminal
 	 (in case we don't have one).  */
       int forkout = emacs_open (pty_name, O_RDWR | O_NOCTTY, 0);
-#else
-      int forkout = emacs_open (pty_name, O_RDWR, 0);
-#endif
       if (forkout < 0)
 	report_file_error ("Opening pty", Qnil);
 #if defined (DONT_REOPEN_PTY)
@@ -1963,15 +1938,8 @@
     }
 #endif /* HAVE_PTYS */
 
-#if O_NONBLOCK
   fcntl (inchannel, F_SETFL, O_NONBLOCK);
   fcntl (outchannel, F_SETFL, O_NONBLOCK);
-#else
-#if O_NDELAY
-  fcntl (inchannel, F_SETFL, O_NDELAY);
-  fcntl (outchannel, F_SETFL, O_NDELAY);
-#endif
-#endif
 
   /* Record this as an active process, with its channels.
      As a result, child_setup will close Emacs's side of the pipes.  */
@@ -2927,13 +2895,9 @@
     {
       /* Don't support network sockets when non-blocking mode is
 	 not available, since a blocked Emacs is not useful.  */
-#if !O_NONBLOCK && !O_NDELAY
-      error ("Network servers not supported");
-#else
       is_server = 1;
       if (TYPE_RANGED_INTEGERP (int, tem))
 	backlog = XINT (tem);
-#endif
     }
 
   /* Make QCaddress an alias for :local (server) or :remote (client).  */
@@ -3193,11 +3157,7 @@
 #ifdef NON_BLOCKING_CONNECT
       if (is_non_blocking_client)
 	{
-#if O_NONBLOCK
 	  ret = fcntl (s, F_SETFL, O_NONBLOCK);
-#else
-	  ret = fcntl (s, F_SETFL, O_NDELAY);
-#endif
 	  if (ret < 0)
 	    {
 	      xerrno = errno;
@@ -3410,13 +3370,7 @@
 
   chan_process[inch] = proc;
 
-#if O_NONBLOCK
   fcntl (inch, F_SETFL, O_NONBLOCK);
-#else
-#if O_NDELAY
-  fcntl (inch, F_SETFL, O_NDELAY);
-#endif
-#endif
 
   p = XPROCESS (proc);
 
@@ -4145,13 +4099,7 @@
 
   chan_process[s] = proc;
 
-#if O_NONBLOCK
   fcntl (s, F_SETFL, O_NONBLOCK);
-#else
-#if O_NDELAY
-  fcntl (s, F_SETFL, O_NDELAY);
-#endif
-#endif
 
   p = XPROCESS (proc);
 
@@ -4847,23 +4795,16 @@
 	      else if (nread == -1 && errno == EWOULDBLOCK)
 		;
 #endif
-	      /* ISC 4.1 defines both EWOULDBLOCK and O_NONBLOCK,
-		 and Emacs uses O_NONBLOCK, so what we get is EAGAIN.  */
-#if O_NONBLOCK
-	      else if (nread == -1 && errno == EAGAIN)
-		;
-#else
-#if O_NDELAY
-	      else if (nread == -1 && errno == EAGAIN)
-		;
+	      else if (nread == -1 && errno == EAGAIN)
+		;
+#ifdef DOS_NT
 	      /* Note that we cannot distinguish between no input
 		 available now and a closed pipe.
 		 With luck, a closed pipe will be accompanied by
 		 subprocess termination and SIGCHLD.  */
 	      else if (nread == 0 && !NETCONN_P (proc) && !SERIALCONN_P (proc))
 		;
-#endif /* O_NDELAY */
-#endif /* O_NONBLOCK */
+#endif
 #ifdef HAVE_PTYS
 	      /* On some OSs with ptys, when the process on one end of
 		 a pty exits, the other end gets an error reading with
@@ -7348,9 +7289,7 @@
 #ifdef HAVE_GETSOCKNAME
    ADD_SUBFEATURE (QCservice, Qt);
 #endif
-#if O_NONBLOCK || O_NDELAY
    ADD_SUBFEATURE (QCserver, Qt);
-#endif
 
    for (sopt = socket_options; sopt->name; sopt++)
      subfeatures = pure_cons (intern_c_string (sopt->name), subfeatures);

=== modified file 'src/sysdep.c'
--- src/sysdep.c	2012-11-14 04:55:41 +0000
+++ src/sysdep.c	2012-11-14 07:26:25 +0000
@@ -1039,8 +1039,7 @@
 #endif
 #endif
 
-#ifdef F_SETFL
-#ifdef F_GETOWN		/* F_SETFL does not imply existence of F_GETOWN */
+#ifdef F_GETOWN
   if (interrupt_input)
     {
       old_fcntl_owner[fileno (tty_out->input)] =
@@ -1058,7 +1057,6 @@
 #endif /* HAVE_GPM */
     }
 #endif /* F_GETOWN */
-#endif /* F_SETFL */
 
 #ifdef _IOFBF
   /* This symbol is defined on recent USG systems.
@@ -1278,8 +1276,7 @@
   fsync (fileno (tty_out->output));
 #endif
 
-#ifdef F_SETFL
-#ifdef F_SETOWN		/* F_SETFL does not imply existence of F_SETOWN */
+#ifdef F_SETOWN
   if (interrupt_input)
     {
       reset_sigio (fileno (tty_out->input));
@@ -1287,11 +1284,8 @@
              old_fcntl_owner[fileno (tty_out->input)]);
     }
 #endif /* F_SETOWN */
-#if O_NDELAY
   fcntl (fileno (tty_out->input), F_SETFL,
-         fcntl (fileno (tty_out->input), F_GETFL, 0) & ~O_NDELAY);
-#endif
-#endif /* F_SETFL */
+         fcntl (fileno (tty_out->input), F_GETFL, 0) & ~O_NONBLOCK);
 
   if (tty_out->old_tty)
     while (emacs_set_tty (fileno (tty_out->input),
@@ -2380,19 +2374,7 @@
 int
 serial_open (char *port)
 {
-  int fd = -1;
-
-  fd = emacs_open ((char*) port,
-		   O_RDWR
-#if O_NONBLOCK
-		   | O_NONBLOCK
-#else
-		   | O_NDELAY
-#endif
-#if O_NOCTTY
-		   | O_NOCTTY
-#endif
-		   , 0);
+  int fd = emacs_open (port, O_RDWR | O_NOCTTY | O_NONBLOCK, 0);
   if (fd < 0)
     {
       error ("Could not open %s: %s",

=== modified file 'src/term.c'
--- src/term.c	2012-11-14 04:55:41 +0000
+++ src/term.c	2012-11-14 07:26:25 +0000
@@ -55,14 +55,6 @@
 #include "xterm.h"
 #endif
 
-#ifndef O_RDWR
-#define O_RDWR 2
-#endif
-
-#ifndef O_NOCTTY
-#define O_NOCTTY 0
-#endif
-
 /* The name of the default console device.  */
 #ifdef WINDOWSNT
 #define DEV_TTY  "CONOUT$"
@@ -2989,22 +2981,18 @@
   set_tty_hooks (terminal);
 
   {
-    int fd;
+    /* Open the terminal device.  */
     FILE *file;
 
-#if O_IGNORE_CTTY
-    if (!ctty)
-      /* Open the terminal device.  Don't recognize it as our
-         controlling terminal, and don't make it the controlling tty
-         if we don't have one at the moment.  */
-      fd = emacs_open (name, O_RDWR | O_IGNORE_CTTY | O_NOCTTY, 0);
-    else
-#endif /* O_IGNORE_CTTY */
-      /* Alas, O_IGNORE_CTTY is a GNU extension that seems to be only
-         defined on Hurd.  On other systems, we need to explicitly
-         dissociate ourselves from the controlling tty when we want to
-         open a frame on the same terminal.  */
-      fd = emacs_open (name, O_RDWR | O_NOCTTY, 0);
+    /* If !ctty, don't recognize it as our controlling terminal, and
+       don't make it the controlling tty if we don't have one now.
+
+       Alas, O_IGNORE_CTTY is a GNU extension that seems to be only
+       defined on Hurd.  On other systems, we need to explicitly
+       dissociate ourselves from the controlling tty when we want to
+       open a frame on the same terminal.  */
+    int flags = O_RDWR | O_NOCTTY | (ctty ? 0 : O_IGNORE_CTTY);
+    int fd = emacs_open (name, flags, 0);
 
     tty->name = xstrdup (name);
     terminal->name = xstrdup (name);
@@ -3023,10 +3011,8 @@
                      name);
       }
 
-#if !O_IGNORE_CTTY
-    if (!ctty)
+    if (!O_IGNORE_CTTY && !ctty)
       dissociate_if_controlling_tty (fd);
-#endif
 
     file = fdopen (fd, "w+");
     tty->input = file;

=== modified file 'src/w32.c'
--- src/w32.c	2012-11-14 17:22:55 +0000
+++ src/w32.c	2012-11-15 05:41:09 +0000
@@ -5853,7 +5853,7 @@
   check_errno ();
   if (fd_info[s].flags & FILE_SOCKET)
     {
-      if (cmd == F_SETFL && options == O_NDELAY)
+      if (cmd == F_SETFL && options == O_NONBLOCK)
 	{
 	  unsigned long nblock = 1;
 	  int rc = pfn_ioctlsocket (SOCK_HANDLE (s), FIONBIO, &nblock);