diff options
author | Zbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl> | 2016-04-29 09:16:45 -0400 |
---|---|---|
committer | Zbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl> | 2016-04-29 09:16:45 -0400 |
commit | 3e39355a96f615f2cb1e805c7d74efbc272de1cd (patch) | |
tree | a31b20b819e007d959db412c8d18ee1bf37bed8d /src/journal/journal-file.c | |
parent | 427a28ecbe0eb170e651e0530ab58d6e6f6c498c (diff) | |
parent | 1fcefd8815455e416c1eda3c8c1220831a2f82e9 (diff) |
Merge pull request #3126 from poettering/small-fixes
fsync directory when creating or rotating journal files and other small fixes,
most importantly for the DHCP DUID code.
Diffstat (limited to 'src/journal/journal-file.c')
-rw-r--r-- | src/journal/journal-file.c | 39 |
1 files changed, 39 insertions, 0 deletions
diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c index 35f4abab1d..c9ce5c73be 100644 --- a/src/journal/journal-file.c +++ b/src/journal/journal-file.c @@ -439,6 +439,39 @@ static int journal_file_init_header(JournalFile *f, JournalFile *template) { return 0; } +static int fsync_directory_of_file(int fd) { + _cleanup_free_ char *path = NULL, *dn = NULL; + _cleanup_close_ int dfd = -1; + struct stat st; + int r; + + if (fstat(fd, &st) < 0) + return -errno; + + if (!S_ISREG(st.st_mode)) + return -EBADFD; + + r = fd_get_path(fd, &path); + if (r < 0) + return r; + + if (!path_is_absolute(path)) + return -EINVAL; + + dn = dirname_malloc(path); + if (!dn) + return -ENOMEM; + + dfd = open(dn, O_RDONLY|O_CLOEXEC|O_DIRECTORY); + if (dfd < 0) + return -errno; + + if (fsync(dfd) < 0) + return -errno; + + return 0; +} + static int journal_file_refresh_header(JournalFile *f) { sd_id128_t boot_id; int r; @@ -464,6 +497,9 @@ static int journal_file_refresh_header(JournalFile *f) { /* Sync the online state to disk */ (void) fsync(f->fd); + /* We likely just created a new file, also sync the directory this file is located in. */ + (void) fsync_directory_of_file(f->fd); + return r; } @@ -3177,6 +3213,9 @@ int journal_file_rotate(JournalFile **f, bool compress, bool seal, Set *deferred if (r < 0 && errno != ENOENT) return -errno; + /* Sync the rename to disk */ + (void) fsync_directory_of_file(old_file->fd); + /* Set as archive so offlining commits w/state=STATE_ARCHIVED. * Previously we would set old_file->header->state to STATE_ARCHIVED directly here, * but journal_file_set_offline() short-circuits when state != STATE_ONLINE, which |