diff options
author | Bruno Haible <bruno@clisp.org> | 2008-09-26 16:10:07 +0200 |
---|---|---|
committer | Bruno Haible <bruno@clisp.org> | 2008-09-26 16:10:07 +0200 |
commit | 0215a9d0af452e1851385549d69d4af6a4106183 (patch) | |
tree | 3f0f30d5744fe6fe3a14112925cb3aa5fa91b525 | |
parent | 0600c3a06dc7495a7649234fe6e1ff813abeac02 (diff) | |
download | gnulib-0215a9d0af452e1851385549d69d4af6a4106183.tar.gz |
Ignore error EPIPE when closing a stream.
-rw-r--r-- | ChangeLog | 4 | ||||
-rw-r--r-- | lib/fwriteerror.c | 27 |
2 files changed, 26 insertions, 5 deletions
@@ -1,5 +1,9 @@ 2008-09-26 Bruno Haible <bruno@clisp.org> + * lib/fwriteerror.c (do_fwriteerror): Ignore error EPIPE. + +2008-09-26 Bruno Haible <bruno@clisp.org> + * tests/test-vc-list-files-git.sh: Explain reason for skipping test. * tests/test-vc-list-files-cvs.sh: Likewise. diff --git a/lib/fwriteerror.c b/lib/fwriteerror.c index 3ea3eccd78..21bd09804e 100644 --- a/lib/fwriteerror.c +++ b/lib/fwriteerror.c @@ -1,5 +1,5 @@ /* Detect write error on a stream. - Copyright (C) 2003-2006 Free Software Foundation, Inc. + Copyright (C) 2003-2006, 2008 Free Software Foundation, Inc. Written by Bruno Haible <bruno@clisp.org>, 2003. This program is free software: you can redistribute it and/or modify @@ -38,7 +38,19 @@ do_fwriteerror (FILE *fp, bool ignore_ebadf) stdout_closed = true; } - /* Need to + /* This function returns an error indication if there was a previous failure + or if fclose failed, with two exceptions: + - Ignore an fclose failure if there was no previous error, no data + remains to be flushed, and fclose failed with EBADF. That can + happen when a program like cp is invoked like this `cp a b >&-' + (i.e., with standard output closed) and doesn't generate any + output (hence no previous error and nothing to be flushed). + - Ignore an fclose failure due to EPIPE. That can happen when a + program blocks or ignores SIGPIPE, and the output pipe or socket + has no readers now. The EPIPE tells us that we should stop writing + to this output. That's what we are doing anyway here. + + Need to 1. test the error indicator of the stream, 2. flush the buffers both in userland and in the kernel, through fclose, testing for error again. */ @@ -71,12 +83,12 @@ do_fwriteerror (FILE *fp, bool ignore_ebadf) if (fflush (fp)) goto close_preserving_errno; /* errno is set here */ if (fclose (fp) && errno != EBADF) - return -1; /* errno is set here */ + goto got_errno; /* errno is set here */ } else { if (fclose (fp)) - return -1; /* errno is set here */ + goto got_errno; /* errno is set here */ } return 0; @@ -88,8 +100,13 @@ do_fwriteerror (FILE *fp, bool ignore_ebadf) int saved_errno = errno; fclose (fp); errno = saved_errno; - return -1; } + got_errno: + /* There's an error. Ignore EPIPE. */ + if (errno == EPIPE) + return 0; + else + return -1; } int |