From c2af86baf6680e54c6e503c7d12957c2e3c283fa Mon Sep 17 00:00:00 2001 From: Bruno Haible Date: Sun, 22 Nov 2009 19:30:39 +0100 Subject: [PATCH] error: account for the possibility of freopen (stdout). --- ChangeLog | 10 ++++++++++ lib/error.c | 42 ++++++++++++++++++++++++++++-------------- m4/error.m4 | 5 +++-- modules/error | 1 + 4 files changed, 42 insertions(+), 16 deletions(-) diff --git a/ChangeLog b/ChangeLog index 5988bcf8e..d7d96f783 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,15 @@ 2009-11-22 Bruno Haible + error: account for the possibility of freopen (stdout). + * lib/error.c: Include . + (flush_stdout): New function, extracted from error and error_at_line. + Determine stdout's fd dynamically. + (error, error_at_line): Invoke flush_stdout. + * m4/error.m4 (gl_PREREQ_ERROR): Require AC_C_INLINE. + * modules/error (Depends-on): Add unistd. + +2009-11-22 Bruno Haible + diffseq: Add comment. * lib/diffseq.h (IF_LINT): Add comment about pitfall. diff --git a/lib/error.c b/lib/error.c index af2287b27..80168a876 100644 --- a/lib/error.c +++ b/lib/error.c @@ -27,6 +27,7 @@ #include #include #include +#include #if !_LIBC && ENABLE_NLS # include "gettext.h" @@ -103,6 +104,31 @@ extern char *program_name; # endif /* HAVE_STRERROR_R || defined strerror_r */ #endif /* not _LIBC */ +static inline void +flush_stdout (void) +{ +#if !_LIBC && defined F_GETFL + int stdout_fd; + +# if GNULIB_FREOPEN_SAFER + /* Use of gnulib's freopen-safer module normally ensures that + fileno (stdout) == 1 + whenever stdout is open. */ + stdout_fd = STDOUT_FILENO; +# else + /* POSIX states that fileno (stdout) after fclose is unspecified. But in + practice it is not a problem, because stdout is statically allocated and + the fd of a FILE stream is stored as a field in its allocated memory. */ + stdout_fd = fileno (stdout); +# endif + /* POSIX states that fflush (stdout) after fclose is unspecified; it + is safe in glibc, but not on all other platforms. fflush (NULL) + is always defined, but too draconian. */ + if (0 <= stdout_fd && 0 <= fcntl (stdout_fd, F_GETFL)) +#endif + fflush (stdout); +} + static void print_errno_message (int errnum) { @@ -238,13 +264,7 @@ error (int status, int errnum, const char *message, ...) 0); #endif -#if !_LIBC && defined F_GETFL - /* POSIX states that fflush (stdout) after fclose is unspecified; it - is safe in glibc, but not on all other platforms. fflush (NULL) - is always defined, but too draconian. */ - if (0 <= fcntl (1, F_GETFL)) -#endif - fflush (stdout); + flush_stdout (); #ifdef _LIBC _IO_flockfile (stderr); #endif @@ -303,13 +323,7 @@ error_at_line (int status, int errnum, const char *file_name, 0); #endif -#if !_LIBC && defined F_GETFL - /* POSIX states that fflush (stdout) after fclose is unspecified; it - is safe in glibc, but not on all other platforms. fflush (NULL) - is always defined, but too draconian. */ - if (0 <= fcntl (1, F_GETFL)) -#endif - fflush (stdout); + flush_stdout (); #ifdef _LIBC _IO_flockfile (stderr); #endif diff --git a/m4/error.m4 b/m4/error.m4 index 7c7746e2c..243dbda44 100644 --- a/m4/error.m4 +++ b/m4/error.m4 @@ -1,6 +1,6 @@ -#serial 11 +#serial 12 -# Copyright (C) 1996, 1997, 1998, 2001, 2002, 2003, 2004 Free Software +# Copyright (C) 1996-1998, 2001-2004, 2009 Free Software # Foundation, Inc. # # This file is free software; the Free Software Foundation @@ -18,5 +18,6 @@ AC_DEFUN([gl_ERROR], AC_DEFUN([gl_PREREQ_ERROR], [ AC_REQUIRE([AC_FUNC_STRERROR_R]) + AC_REQUIRE([AC_C_INLINE]) : ]) diff --git a/modules/error b/modules/error index fbeeb0d93..7d43aba1c 100644 --- a/modules/error +++ b/modules/error @@ -13,6 +13,7 @@ m4/error.m4 Depends-on: strerror +unistd configure.ac: gl_ERROR -- 2.11.0