tmpfiles: stat file in item_do() rather than in its callers
This a slight simplification since all callers of item_do() (glob_item_recursively() and item_do() itself) stat the file descriptor only for passing it to item_do().
This commit is contained in:
parent
1c57fa90be
commit
14f3480af1
|
@ -1295,18 +1295,23 @@ static int write_one_file(Item *i, const char *path) {
|
||||||
typedef int (*action_t)(Item *, const char *);
|
typedef int (*action_t)(Item *, const char *);
|
||||||
typedef int (*fdaction_t)(Item *, int fd, const struct stat *st);
|
typedef int (*fdaction_t)(Item *, int fd, const struct stat *st);
|
||||||
|
|
||||||
static int item_do(Item *i, int fd, const struct stat *st, fdaction_t action) {
|
static int item_do(Item *i, int fd, fdaction_t action) {
|
||||||
|
struct stat st;
|
||||||
int r = 0, q;
|
int r = 0, q;
|
||||||
|
|
||||||
assert(i);
|
assert(i);
|
||||||
assert(fd >= 0);
|
assert(fd >= 0);
|
||||||
assert(st);
|
|
||||||
|
if (fstat(fd, &st) < 0) {
|
||||||
|
r = -errno;
|
||||||
|
goto finish;
|
||||||
|
}
|
||||||
|
|
||||||
/* This returns the first error we run into, but nevertheless
|
/* This returns the first error we run into, but nevertheless
|
||||||
* tries to go on */
|
* tries to go on */
|
||||||
r = action(i, fd, st);
|
r = action(i, fd, &st);
|
||||||
|
|
||||||
if (S_ISDIR(st->st_mode)) {
|
if (S_ISDIR(st.st_mode)) {
|
||||||
char procfs_path[STRLEN("/proc/self/fd/") + DECIMAL_STR_MAX(int)];
|
char procfs_path[STRLEN("/proc/self/fd/") + DECIMAL_STR_MAX(int)];
|
||||||
_cleanup_closedir_ DIR *d = NULL;
|
_cleanup_closedir_ DIR *d = NULL;
|
||||||
struct dirent *de;
|
struct dirent *de;
|
||||||
|
@ -1322,16 +1327,15 @@ static int item_do(Item *i, int fd, const struct stat *st, fdaction_t action) {
|
||||||
}
|
}
|
||||||
|
|
||||||
FOREACH_DIRENT_ALL(de, d, q = -errno; goto finish) {
|
FOREACH_DIRENT_ALL(de, d, q = -errno; goto finish) {
|
||||||
struct stat de_st;
|
|
||||||
int de_fd;
|
int de_fd;
|
||||||
|
|
||||||
if (dot_or_dot_dot(de->d_name))
|
if (dot_or_dot_dot(de->d_name))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
de_fd = openat(fd, de->d_name, O_NOFOLLOW|O_CLOEXEC|O_PATH);
|
de_fd = openat(fd, de->d_name, O_NOFOLLOW|O_CLOEXEC|O_PATH);
|
||||||
if (de_fd >= 0 && fstat(de_fd, &de_st) >= 0)
|
if (de_fd >= 0)
|
||||||
/* pass ownership of dirent fd over */
|
/* pass ownership of dirent fd over */
|
||||||
q = item_do(i, de_fd, &de_st, action);
|
q = item_do(i, de_fd, action);
|
||||||
else
|
else
|
||||||
q = -errno;
|
q = -errno;
|
||||||
|
|
||||||
|
@ -1377,7 +1381,6 @@ static int glob_item_recursively(Item *i, fdaction_t action) {
|
||||||
|
|
||||||
STRV_FOREACH(fn, g.gl_pathv) {
|
STRV_FOREACH(fn, g.gl_pathv) {
|
||||||
_cleanup_close_ int fd = -1;
|
_cleanup_close_ int fd = -1;
|
||||||
struct stat st;
|
|
||||||
|
|
||||||
/* Make sure we won't trigger/follow file object (such as
|
/* Make sure we won't trigger/follow file object (such as
|
||||||
* device nodes, automounts, ...) pointed out by 'fn' with
|
* device nodes, automounts, ...) pointed out by 'fn' with
|
||||||
|
@ -1390,12 +1393,7 @@ static int glob_item_recursively(Item *i, fdaction_t action) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (fstat(fd, &st) < 0) {
|
k = item_do(i, fd, action);
|
||||||
r = r ?: -errno;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
k = item_do(i, fd, &st, action);
|
|
||||||
if (k < 0 && r == 0)
|
if (k < 0 && r == 0)
|
||||||
r = k;
|
r = k;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue