diff options
author | Theodore Ts'o <tytso@mit.edu> | 2009-04-22 15:12:40 -0400 |
---|---|---|
committer | Theodore Ts'o <tytso@mit.edu> | 2009-04-22 15:12:40 -0400 |
commit | 6e6b71d697c9a66ab19e67ca2cad10168477a107 (patch) | |
tree | 6da3000a4757fc5f45c13a3bd885ed7e4e973f40 | |
parent | fb72556af88bf01459519d1028743c54a71bcca1 (diff) | |
download | e2fsprogs-6e6b71d697c9a66ab19e67ca2cad10168477a107.tar.gz |
logsave: Fix warn_unused_result warnings from gcc
Fixed a potential bug where by partial returns from the write(2)
system call could some bytes to be lost when writing to the log file.
Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
-rw-r--r-- | misc/logsave.c | 29 |
1 files changed, 26 insertions, 3 deletions
diff --git a/misc/logsave.c b/misc/logsave.c index f0011f81..81ac9f6e 100644 --- a/misc/logsave.c +++ b/misc/logsave.c @@ -49,6 +49,29 @@ static void usage(char *progname) #define SEND_CONSOLE 0x02 #define SEND_BOTH 0x03 +/* + * Helper function that does the right thing if write returns a + * partial write, or an EGAIN/EINTR error. + */ +static int write_all(int fd, const char *buf, size_t count) +{ + ssize_t ret; + int c = 0; + + while (count > 0) { + ret = write(fd, buf, count); + if (ret < 0) { + if ((errno == EAGAIN) || (errno == EINTR)) + continue; + return -1; + } + count -= ret; + buf += ret; + c += ret; + } + return c; +} + static void send_output(const char *buffer, int c, int flag) { char *n; @@ -57,11 +80,11 @@ static void send_output(const char *buffer, int c, int flag) c = strlen(buffer); if (flag & SEND_CONSOLE) - write(1, buffer, c); + write_all(1, buffer, c); if (!(flag & SEND_LOG)) return; if (outfd > 0) - write(outfd, buffer, c); + write_all(outfd, buffer, c); else { n = realloc(outbuf, outbufsize + c); if (n) { @@ -280,7 +303,7 @@ int main(int argc, char **argv) outfd = open(outfn, openflags, 0644); sleep(1); } - write(outfd, outbuf, outbufsize); + write_all(outfd, outbuf, outbufsize); free(outbuf); } close(outfd); |