+2011-01-31 Eric Blake <eblake@redhat.com>
+
+ dup2: work around Haiku bug
+ * m4/dup2.m4 (gl_FUNC_DUP2): Test for bug.
+ * lib/dup2.c (rpl_dup2) [!WIN32]: Add workaround.
+ * doc/posix-functions/dup2.texi (dup2): Document the bug.
+ * tests/test-dup2.c (main): Enhance test.
+
2011-01-31 Simon Josefsson <simon@josefsson.org>
doc: off_t is not available in eglibc 2.11.2 stdio.h.
errno = EBADF;
return -1;
}
+# elif !defined __linux__
+ /* On Haiku, dup2 (fd, fd) mistakenly clears FD_CLOEXEC. */
+ if (fd == desired_fd)
+ return fcntl (fd, F_GETFL) == -1 ? -1 : fd;
# endif
result = dup2 (fd, desired_fd);
# ifdef __linux__
-#serial 11
+#serial 12
dnl Copyright (C) 2002, 2005, 2007, 2009-2011 Free Software Foundation, Inc.
dnl This file is free software; the Free Software Foundation
dnl gives unlimited permission to copy and/or distribute it,
[
AC_REQUIRE([gl_UNISTD_H_DEFAULTS])
AC_REQUIRE([AC_CANONICAL_HOST])
- AC_CHECK_FUNCS_ONCE([dup2])
+ AC_CHECK_FUNCS_ONCE([dup2 fcntl])
if test $ac_cv_func_dup2 = no; then
HAVE_DUP2=0
AC_LIBOBJ([dup2])
AC_CACHE_CHECK([whether dup2 works], [gl_cv_func_dup2_works],
[AC_RUN_IFELSE([
AC_LANG_PROGRAM([[#include <unistd.h>
+#include <fcntl.h>
#include <errno.h>]],
[int result = 0;
- if (dup2 (1, 1) == 0)
+#if HAVE_FCNTL
+ if (fcntl (1, F_SETFD, FD_CLOEXEC) == -1)
result |= 1;
+#endif HAVE_FCNTL
+ if (dup2 (1, 1) == 0)
+ result |= 2;
+#if HAVE_FCNTL
+ if (fcntl (1, F_GETFD) != FD_CLOEXEC)
+ result |= 4;
+#endif
close (0);
if (dup2 (0, 0) != -1)
- result |= 2;
+ result |= 8;
/* Many gnulib modules require POSIX conformance of EBADF. */
- if (dup2 (1, 1000000) == -1 && errno != EBADF)
- result |= 4;
+ if (dup2 (2, 1000000) == -1 && errno != EBADF)
+ result |= 16;
return result;
])
],
gl_cv_func_dup2_works=no;;
freebsd*) # on FreeBSD 6.1, dup2(1,1000000) gives EMFILE, not EBADF.
gl_cv_func_dup2_works=no;;
+ haiku*) # on Haiku alpha 2, dup2(1, 1) resets FD_CLOEXEC.
+ gl_cv_func_dup2_works=no;;
*) gl_cv_func_dup2_works=yes;;
esac])
])
ASSERT (dup2 (fd + 1, fd + 1) == fd + 1);
ASSERT (!is_inheritable (fd + 1));
ASSERT (dup2 (fd + 1, fd + 2) == fd + 2);
+ ASSERT (!is_inheritable (fd + 1));
ASSERT (is_inheritable (fd + 2));
+ errno = 0;
+ ASSERT (dup2 (fd + 1, -1) == -1);
+ ASSERT (errno == EBADF);
+ ASSERT (!is_inheritable (fd + 1));
#endif
/* On systems that distinguish between text and binary mode, dup2