mirror of
https://github.com/systemd/systemd
synced 2024-10-06 16:21:34 +00:00
Add fopen_unlocked() wrapper
This commit is contained in:
parent
03abeb0baf
commit
fdeea3f4f1
37
coccinelle/fopen-unlocked.cocci
Normal file
37
coccinelle/fopen-unlocked.cocci
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
@@
|
||||||
|
expression f, path, options;
|
||||||
|
@@
|
||||||
|
- f = fopen(path, options);
|
||||||
|
- if (!f)
|
||||||
|
- return -errno;
|
||||||
|
- (void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
||||||
|
+ r = fopen_unlocked(path, options, &f);
|
||||||
|
+ if (r < 0)
|
||||||
|
+ return r;
|
||||||
|
@@
|
||||||
|
expression f, path, options;
|
||||||
|
@@
|
||||||
|
- f = fopen(path, options);
|
||||||
|
- if (!f) {
|
||||||
|
- if (errno == ENOENT)
|
||||||
|
- return -ESRCH;
|
||||||
|
- return -errno;
|
||||||
|
- }
|
||||||
|
- (void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
||||||
|
+ r = fopen_unlocked(path, options, &f);
|
||||||
|
+ if (r == -ENOENT)
|
||||||
|
+ return -ESRCH;
|
||||||
|
+ if (r < 0)
|
||||||
|
+ return r;
|
||||||
|
@@
|
||||||
|
expression f, path, options;
|
||||||
|
@@
|
||||||
|
- f = fopen(path, options);
|
||||||
|
- if (!f)
|
||||||
|
- return errno == ENOENT ? -ESRCH : -errno;
|
||||||
|
- (void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
||||||
|
+ r = fopen_unlocked(path, options, &f);
|
||||||
|
+ if (r == -ENOENT)
|
||||||
|
+ return -ESRCH;
|
||||||
|
+ if (r < 0)
|
||||||
|
+ return r;
|
|
@ -1016,11 +1016,11 @@ int cg_pid_get_path(const char *controller, pid_t pid, char **path) {
|
||||||
}
|
}
|
||||||
|
|
||||||
fs = procfs_file_alloca(pid, "cgroup");
|
fs = procfs_file_alloca(pid, "cgroup");
|
||||||
f = fopen(fs, "re");
|
r = fopen_unlocked(fs, "re", &f);
|
||||||
if (!f)
|
if (r == -ENOENT)
|
||||||
return errno == ENOENT ? -ESRCH : -errno;
|
return -ESRCH;
|
||||||
|
if (r < 0)
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
return r;
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
_cleanup_free_ char *line = NULL;
|
_cleanup_free_ char *line = NULL;
|
||||||
|
@ -2442,17 +2442,13 @@ int cg_kernel_controllers(Set **ret) {
|
||||||
if (!controllers)
|
if (!controllers)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
f = fopen("/proc/cgroups", "re");
|
r = fopen_unlocked("/proc/cgroups", "re", &f);
|
||||||
if (!f) {
|
if (r == -ENOENT) {
|
||||||
if (errno == ENOENT) {
|
|
||||||
*ret = NULL;
|
*ret = NULL;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
}
|
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
/* Ignore the header line */
|
/* Ignore the header line */
|
||||||
(void) read_line(f, (size_t) -1, NULL);
|
(void) read_line(f, (size_t) -1, NULL);
|
||||||
|
|
|
@ -29,6 +29,19 @@
|
||||||
|
|
||||||
#define READ_FULL_BYTES_MAX (4U*1024U*1024U)
|
#define READ_FULL_BYTES_MAX (4U*1024U*1024U)
|
||||||
|
|
||||||
|
int fopen_unlocked(const char *path, const char *options, FILE **ret) {
|
||||||
|
assert(ret);
|
||||||
|
|
||||||
|
FILE *f = fopen(path, options);
|
||||||
|
if (!f)
|
||||||
|
return -errno;
|
||||||
|
|
||||||
|
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
||||||
|
|
||||||
|
*ret = f;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
int write_string_stream_ts(
|
int write_string_stream_ts(
|
||||||
FILE *f,
|
FILE *f,
|
||||||
const char *line,
|
const char *line,
|
||||||
|
@ -213,15 +226,14 @@ int write_string_filef(
|
||||||
|
|
||||||
int read_one_line_file(const char *fn, char **line) {
|
int read_one_line_file(const char *fn, char **line) {
|
||||||
_cleanup_fclose_ FILE *f = NULL;
|
_cleanup_fclose_ FILE *f = NULL;
|
||||||
|
int r;
|
||||||
|
|
||||||
assert(fn);
|
assert(fn);
|
||||||
assert(line);
|
assert(line);
|
||||||
|
|
||||||
f = fopen(fn, "re");
|
r = fopen_unlocked(fn, "re", &f);
|
||||||
if (!f)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
return read_line(f, LONG_LINE_MAX, line);
|
return read_line(f, LONG_LINE_MAX, line);
|
||||||
}
|
}
|
||||||
|
@ -230,6 +242,7 @@ int verify_file(const char *fn, const char *blob, bool accept_extra_nl) {
|
||||||
_cleanup_fclose_ FILE *f = NULL;
|
_cleanup_fclose_ FILE *f = NULL;
|
||||||
_cleanup_free_ char *buf = NULL;
|
_cleanup_free_ char *buf = NULL;
|
||||||
size_t l, k;
|
size_t l, k;
|
||||||
|
int r;
|
||||||
|
|
||||||
assert(fn);
|
assert(fn);
|
||||||
assert(blob);
|
assert(blob);
|
||||||
|
@ -243,11 +256,9 @@ int verify_file(const char *fn, const char *blob, bool accept_extra_nl) {
|
||||||
if (!buf)
|
if (!buf)
|
||||||
return -ENOMEM;
|
return -ENOMEM;
|
||||||
|
|
||||||
f = fopen(fn, "re");
|
r = fopen_unlocked(fn, "re", &f);
|
||||||
if (!f)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
/* We try to read one byte more than we need, so that we know whether we hit eof */
|
/* We try to read one byte more than we need, so that we know whether we hit eof */
|
||||||
errno = 0;
|
errno = 0;
|
||||||
|
@ -390,15 +401,14 @@ finalize:
|
||||||
|
|
||||||
int read_full_file_full(const char *filename, ReadFullFileFlags flags, char **contents, size_t *size) {
|
int read_full_file_full(const char *filename, ReadFullFileFlags flags, char **contents, size_t *size) {
|
||||||
_cleanup_fclose_ FILE *f = NULL;
|
_cleanup_fclose_ FILE *f = NULL;
|
||||||
|
int r;
|
||||||
|
|
||||||
assert(filename);
|
assert(filename);
|
||||||
assert(contents);
|
assert(contents);
|
||||||
|
|
||||||
f = fopen(filename, "re");
|
r = fopen_unlocked(filename, "re", &f);
|
||||||
if (!f)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
return read_full_stream_full(f, filename, flags, contents, size);
|
return read_full_stream_full(f, filename, flags, contents, size);
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,6 +33,8 @@ typedef enum {
|
||||||
READ_FULL_FILE_UNBASE64 = 1 << 1,
|
READ_FULL_FILE_UNBASE64 = 1 << 1,
|
||||||
} ReadFullFileFlags;
|
} ReadFullFileFlags;
|
||||||
|
|
||||||
|
int fopen_unlocked(const char *path, const char *options, FILE **ret);
|
||||||
|
|
||||||
int write_string_stream_ts(FILE *f, const char *line, WriteStringFileFlags flags, struct timespec *ts);
|
int write_string_stream_ts(FILE *f, const char *line, WriteStringFileFlags flags, struct timespec *ts);
|
||||||
static inline int write_string_stream(FILE *f, const char *line, WriteStringFileFlags flags) {
|
static inline int write_string_stream(FILE *f, const char *line, WriteStringFileFlags flags) {
|
||||||
return write_string_stream_ts(f, line, flags, NULL);
|
return write_string_stream_ts(f, line, flags, NULL);
|
||||||
|
|
|
@ -378,11 +378,9 @@ int dev_is_devtmpfs(void) {
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return r;
|
return r;
|
||||||
|
|
||||||
proc_self_mountinfo = fopen("/proc/self/mountinfo", "re");
|
r = fopen_unlocked("/proc/self/mountinfo", "re", &proc_self_mountinfo);
|
||||||
if (!proc_self_mountinfo)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(proc_self_mountinfo, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
_cleanup_free_ char *line = NULL;
|
_cleanup_free_ char *line = NULL;
|
||||||
|
|
|
@ -106,7 +106,7 @@ int get_process_cmdline(pid_t pid, size_t max_length, bool comm_fallback, char *
|
||||||
char *k;
|
char *k;
|
||||||
_cleanup_free_ char *ans = NULL;
|
_cleanup_free_ char *ans = NULL;
|
||||||
const char *p;
|
const char *p;
|
||||||
int c;
|
int c, r;
|
||||||
|
|
||||||
assert(line);
|
assert(line);
|
||||||
assert(pid >= 0);
|
assert(pid >= 0);
|
||||||
|
@ -121,15 +121,11 @@ int get_process_cmdline(pid_t pid, size_t max_length, bool comm_fallback, char *
|
||||||
* comm_fallback is false). Returns 0 and sets *line otherwise. */
|
* comm_fallback is false). Returns 0 and sets *line otherwise. */
|
||||||
|
|
||||||
p = procfs_file_alloca(pid, "cmdline");
|
p = procfs_file_alloca(pid, "cmdline");
|
||||||
|
r = fopen_unlocked(p, "re", &f);
|
||||||
f = fopen(p, "re");
|
if (r == -ENOENT)
|
||||||
if (!f) {
|
|
||||||
if (errno == ENOENT)
|
|
||||||
return -ESRCH;
|
return -ESRCH;
|
||||||
return -errno;
|
if (r < 0)
|
||||||
}
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
if (max_length == 0) {
|
if (max_length == 0) {
|
||||||
/* This is supposed to be a safety guard against runaway command lines. */
|
/* This is supposed to be a safety guard against runaway command lines. */
|
||||||
|
@ -513,14 +509,11 @@ static int get_process_id(pid_t pid, const char *field, uid_t *uid) {
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
p = procfs_file_alloca(pid, "status");
|
p = procfs_file_alloca(pid, "status");
|
||||||
f = fopen(p, "re");
|
r = fopen_unlocked(p, "re", &f);
|
||||||
if (!f) {
|
if (r == -ENOENT)
|
||||||
if (errno == ENOENT)
|
|
||||||
return -ESRCH;
|
return -ESRCH;
|
||||||
return -errno;
|
if (r < 0)
|
||||||
}
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
_cleanup_free_ char *line = NULL;
|
_cleanup_free_ char *line = NULL;
|
||||||
|
@ -602,14 +595,11 @@ int get_process_environ(pid_t pid, char **env) {
|
||||||
|
|
||||||
p = procfs_file_alloca(pid, "environ");
|
p = procfs_file_alloca(pid, "environ");
|
||||||
|
|
||||||
f = fopen(p, "re");
|
r = fopen_unlocked(p, "re", &f);
|
||||||
if (!f) {
|
if (r == -ENOENT)
|
||||||
if (errno == ENOENT)
|
|
||||||
return -ESRCH;
|
return -ESRCH;
|
||||||
return -errno;
|
if (r < 0)
|
||||||
}
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
char c;
|
char c;
|
||||||
|
@ -895,15 +885,11 @@ int getenv_for_pid(pid_t pid, const char *field, char **ret) {
|
||||||
|
|
||||||
path = procfs_file_alloca(pid, "environ");
|
path = procfs_file_alloca(pid, "environ");
|
||||||
|
|
||||||
f = fopen(path, "re");
|
r = fopen_unlocked(path, "re", &f);
|
||||||
if (!f) {
|
if (r == -ENOENT)
|
||||||
if (errno == ENOENT)
|
|
||||||
return -ESRCH;
|
return -ESRCH;
|
||||||
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
}
|
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
l = strlen(field);
|
l = strlen(field);
|
||||||
for (;;) {
|
for (;;) {
|
||||||
|
|
|
@ -2,7 +2,6 @@
|
||||||
|
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
#include <stdio_ext.h>
|
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
@ -479,15 +478,13 @@ static int add_crypttab_devices(void) {
|
||||||
if (!arg_read_crypttab)
|
if (!arg_read_crypttab)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
f = fopen("/etc/crypttab", "re");
|
r = fopen_unlocked("/etc/crypttab", "re", &f);
|
||||||
if (!f) {
|
if (r < 0) {
|
||||||
if (errno != ENOENT)
|
if (errno != ENOENT)
|
||||||
log_error_errno(errno, "Failed to open /etc/crypttab: %m");
|
log_error_errno(errno, "Failed to open /etc/crypttab: %m");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
(void) __fsetlocking(f, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
if (fstat(fileno(f), &st) < 0) {
|
if (fstat(fileno(f), &st) < 0) {
|
||||||
log_error_errno(errno, "Failed to stat /etc/crypttab: %m");
|
log_error_errno(errno, "Failed to stat /etc/crypttab: %m");
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -40,13 +40,10 @@ int umount_recursive(const char *prefix, int flags) {
|
||||||
_cleanup_fclose_ FILE *proc_self_mountinfo = NULL;
|
_cleanup_fclose_ FILE *proc_self_mountinfo = NULL;
|
||||||
|
|
||||||
again = false;
|
again = false;
|
||||||
r = 0;
|
|
||||||
|
|
||||||
proc_self_mountinfo = fopen("/proc/self/mountinfo", "re");
|
r = fopen_unlocked("/proc/self/mountinfo", "re", &proc_self_mountinfo);
|
||||||
if (!proc_self_mountinfo)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(proc_self_mountinfo, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
_cleanup_free_ char *path = NULL, *p = NULL;
|
_cleanup_free_ char *path = NULL, *p = NULL;
|
||||||
|
@ -302,12 +299,11 @@ int bind_remount_recursive_with_mountinfo(
|
||||||
|
|
||||||
int bind_remount_recursive(const char *prefix, unsigned long new_flags, unsigned long flags_mask, char **blacklist) {
|
int bind_remount_recursive(const char *prefix, unsigned long new_flags, unsigned long flags_mask, char **blacklist) {
|
||||||
_cleanup_fclose_ FILE *proc_self_mountinfo = NULL;
|
_cleanup_fclose_ FILE *proc_self_mountinfo = NULL;
|
||||||
|
int r;
|
||||||
|
|
||||||
proc_self_mountinfo = fopen("/proc/self/mountinfo", "re");
|
r = fopen_unlocked("/proc/self/mountinfo", "re", &proc_self_mountinfo);
|
||||||
if (!proc_self_mountinfo)
|
if (r < 0)
|
||||||
return -errno;
|
return r;
|
||||||
|
|
||||||
(void) __fsetlocking(proc_self_mountinfo, FSETLOCKING_BYCALLER);
|
|
||||||
|
|
||||||
return bind_remount_recursive_with_mountinfo(prefix, new_flags, flags_mask, blacklist, proc_self_mountinfo);
|
return bind_remount_recursive_with_mountinfo(prefix, new_flags, flags_mask, blacklist, proc_self_mountinfo);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue