diff options
author | Lennart Poettering <lennart@poettering.net> | 2020-11-18 15:10:52 +0100 |
---|---|---|
committer | Lennart Poettering <lennart@poettering.net> | 2020-12-02 10:32:17 +0100 |
commit | b1b657c48fad087d6451ae022a2f246a07b05c59 (patch) | |
tree | aa5d21de486d79d5b9fae58977530154bd12dd88 | |
parent | pager: stop disabling urlification under a pager (diff) | |
download | systemd-b1b657c48fad087d6451ae022a2f246a07b05c59.tar.xz systemd-b1b657c48fad087d6451ae022a2f246a07b05c59.zip |
copy: teach copy_file() that a mode=-1 call means "take mode from original file"
-rw-r--r-- | src/basic/copy.c | 18 |
1 files changed, 16 insertions, 2 deletions
diff --git a/src/basic/copy.c b/src/basic/copy.c index 6a9c3a396f..aa805bb8e2 100644 --- a/src/basic/copy.c +++ b/src/basic/copy.c @@ -1047,18 +1047,29 @@ int copy_file_full( copy_progress_bytes_t progress_bytes, void *userdata) { + _cleanup_close_ int fdf = -1; + struct stat st; int fdt = -1, r; assert(from); assert(to); + fdf = open(from, O_RDONLY|O_CLOEXEC|O_NOCTTY); + if (fdf < 0) + return -errno; + + if (mode == (mode_t) -1) + if (fstat(fdf, &st) < 0) + return -errno; + RUN_WITH_UMASK(0000) { if (copy_flags & COPY_MAC_CREATE) { r = mac_selinux_create_file_prepare(to, S_IFREG); if (r < 0) return r; } - fdt = open(to, flags|O_WRONLY|O_CREAT|O_CLOEXEC|O_NOCTTY, mode); + fdt = open(to, flags|O_WRONLY|O_CREAT|O_CLOEXEC|O_NOCTTY, + mode != (mode_t) -1 ? mode : st.st_mode); if (copy_flags & COPY_MAC_CREATE) mac_selinux_create_file_clear(); if (fdt < 0) @@ -1068,13 +1079,16 @@ int copy_file_full( if (chattr_mask != 0) (void) chattr_fd(fdt, chattr_flags, chattr_mask & CHATTR_EARLY_FL, NULL); - r = copy_file_fd_full(from, fdt, copy_flags, progress_bytes, userdata); + r = copy_bytes_full(fdf, fdt, (uint64_t) -1, copy_flags, NULL, NULL, progress_bytes, userdata); if (r < 0) { close(fdt); (void) unlink(to); return r; } + (void) copy_times(fdf, fdt, copy_flags); + (void) copy_xattr(fdf, fdt); + if (chattr_mask != 0) (void) chattr_fd(fdt, chattr_flags, chattr_mask & ~CHATTR_EARLY_FL, NULL); |