]> git.ipfire.org Git - thirdparty/util-linux.git/blame - include/closestream.h
libmount: fix comment referring to passno field
[thirdparty/util-linux.git] / include / closestream.h
CommitLineData
302e423d
SK
1#ifndef UTIL_LINUX_CLOSESTREAM_H
2#define UTIL_LINUX_CLOSESTREAM_H
3
4#include <stdio.h>
78288764 5#ifdef HAVE_STDIO_EXT_H
302e423d 6#include <stdio_ext.h>
78288764 7#endif
302e423d
SK
8#include <unistd.h>
9
10#include "c.h"
11#include "nls.h"
12
090d8c76
KZ
13#ifndef CLOSE_EXIT_CODE
14# define CLOSE_EXIT_CODE EXIT_FAILURE
15#endif
16
302e423d
SK
17static inline int
18close_stream(FILE * stream)
19{
b211467f 20#ifdef HAVE___FPENDING
302e423d 21 const int some_pending = (__fpending(stream) != 0);
b211467f 22#endif
302e423d
SK
23 const int prev_fail = (ferror(stream) != 0);
24 const int fclose_fail = (fclose(stream) != 0);
422f93bf 25
b211467f
SK
26 if (prev_fail || (fclose_fail && (
27#ifdef HAVE___FPENDING
28 some_pending ||
29#endif
30 errno != EBADF))) {
422f93bf 31 if (!fclose_fail && !(errno == EPIPE))
302e423d
SK
32 errno = 0;
33 return EOF;
34 }
35 return 0;
36}
37
38/* Meant to be used atexit(close_stdout); */
39static inline void
40close_stdout(void)
41{
52aa1a66 42 if (stdout && close_stream(stdout) != 0 && !(errno == EPIPE)) {
302e423d
SK
43 if (errno)
44 warn(_("write error"));
45 else
46 warnx(_("write error"));
090d8c76 47 _exit(CLOSE_EXIT_CODE);
302e423d
SK
48 }
49
52aa1a66 50 if (stderr && close_stream(stderr) != 0)
090d8c76 51 _exit(CLOSE_EXIT_CODE);
52aa1a66
KZ
52
53 stdout = NULL;
54 stderr = NULL;
302e423d
SK
55}
56
31c66833
KZ
57static inline void
58close_stdout_atexit(void)
59{
60 /*
61 * Note that close stdout at exit disables ASAN to report memory leaks
62 */
084365f1 63#if !defined(__SANITIZE_ADDRESS__)
31c66833
KZ
64 atexit(close_stdout);
65#endif
66}
67
f416563b
SK
68#ifndef HAVE_FSYNC
69static inline int
70fsync(int fd __attribute__((__unused__)))
71{
72 return 0;
73}
74#endif
75
76static inline int
77close_fd(int fd)
78{
79 const int fsync_fail = (fsync(fd) != 0);
80 const int close_fail = (close(fd) != 0);
81
82 if (fsync_fail || close_fail)
83 return EOF;
84 return 0;
85}
86
302e423d 87#endif /* UTIL_LINUX_CLOSESTREAM_H */