]> code.delx.au - gnu-emacs/blobdiff - lib/fdopendir.c
Merge from origin/emacs-24
[gnu-emacs] / lib / fdopendir.c
index 9dc1e7b26dcf4f49b3838ffc1300b583fe9daea8..837a8219b3399f7431c70169e0694ee7cb523f1d 100644 (file)
@@ -93,7 +93,7 @@ fdopendir (int fd)
    That way, barring race conditions, fd_clone_opendir returns a
    stream whose file descriptor is FD.
 
-   If REPLACE_CHDIR or CWD is null, use opendir ("/proc/self/fd/...",
+   If REPLACE_FCHDIR or CWD is null, use opendir ("/proc/self/fd/...",
    falling back on fchdir metadata.  Otherwise, CWD is a saved version
    of the working directory; use fchdir/opendir(".")/restore_cwd(CWD).  */
 static DIR *
@@ -156,7 +156,16 @@ fd_clone_opendir (int fd, struct saved_cwd const *cwd)
       if (! dir && EXPECTED_ERRNO (saved_errno))
         {
           char const *name = _gl_directory_name (fd);
-          return (name ? opendir (name) : NULL);
+          DIR *dp = name ? opendir (name) : NULL;
+
+          /* The caller has done an elaborate dance to arrange for opendir to
+             consume just the right file descriptor.  If dirfd returns -1,
+             though, we're on a system like mingw where opendir does not
+             consume a file descriptor.  Consume it via 'dup' instead.  */
+          if (dp && dirfd (dp) < 0)
+            dup (fd);
+
+          return dp;
         }
 # endif
       errno = saved_errno;