aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordec05eba <dec05eba@protonmail.com>2025-03-08 14:03:45 +0100
committerdec05eba <dec05eba@protonmail.com>2025-03-08 14:03:45 +0100
commit616b174b818f26f41a3e114cfe3deb38259398b7 (patch)
tree065cf4b1dcc20c089175ccd5c20aa710f9c5698e
parent8c86bf1c3da587ed8657e2744a6d6e3af21406da (diff)
Fix file copy not working when home drive is encrypted (sendfile fails to some reason with invalid argument)
-rw-r--r--main.c43
1 files changed, 33 insertions, 10 deletions
diff --git a/main.c b/main.c
index 119f681..314d274 100644
--- a/main.c
+++ b/main.c
@@ -6,8 +6,8 @@
#include <errno.h>
#include <fcntl.h>
#include <stdbool.h>
+#include <stdint.h>
#include <sys/stat.h>
-#include <sys/sendfile.h>
#include <sys/capability.h>
#define KMS_SERVER_PROXY_FILEPATH "/var/lib/flatpak/app/com.dec05eba.gpu_screen_recorder/current/active/files/bin/kms-server-proxy"
@@ -88,19 +88,37 @@ static bool copy_file_atomic(const char *source_path, const char *dest_path) {
snprintf(tmp_filepath, sizeof(tmp_filepath), "%s.tmp", dest_path);
in_fd = open(source_path, O_RDONLY);
- if(in_fd == -1)
+ if(in_fd == -1) {
+ fprintf(stderr, "Error: copy_file_atomic: failed to open %s, error: %s\n", source_path, strerror(errno));
goto done;
+ }
- struct stat st;
- if(fstat(in_fd, &st) == -1)
+ out_fd = open(tmp_filepath, O_WRONLY | O_CREAT, 0755);
+ if(out_fd == -1) {
+ fprintf(stderr, "Error: copy_file_atomic: failed to create %s, error: %s\n", tmp_filepath, strerror(errno));
goto done;
+ }
- out_fd = open(tmp_filepath, O_RDWR | O_CREAT | O_TRUNC, 0755);
- if(out_fd == -1)
- goto done;
+ uint8_t buffer[8192];
+ for(;;) {
+ const ssize_t bytes_read = read(in_fd, buffer, sizeof(buffer));
+ if(bytes_read == -1) {
+ fprintf(stderr, "Error: copy_file_atomic: failed to read data from %s, error: %s\n", source_path, strerror(errno));
+ goto done;
+ } else if(bytes_read == 0) {
+ break;
+ }
- if(sendfile(out_fd, in_fd, NULL, st.st_size) != st.st_size)
- goto done;
+ ssize_t bytes_written_total = 0;
+ while(bytes_written_total < bytes_read) {
+ const ssize_t bytes_written = write(out_fd, buffer + bytes_written_total, bytes_read - bytes_written_total);
+ if(bytes_written == -1) {
+ fprintf(stderr, "Error: copy_file_atomic: failed to write data to %s, error: %s\n", tmp_filepath, strerror(errno));
+ goto done;
+ }
+ bytes_written_total += bytes_written;
+ }
+ }
res = true;
@@ -110,8 +128,13 @@ static bool copy_file_atomic(const char *source_path, const char *dest_path) {
if(out_fd)
close(out_fd);
- if(res)
+ if(res) {
res = rename(tmp_filepath, dest_path) == 0;
+ if(!res)
+ fprintf(stderr, "Error: copy_file_atomic: Failed to rename from %s to %s, error: %s\n", strerror(errno), tmp_filepath, dest_path);
+ } else {
+ remove(tmp_filepath);
+ }
return res;
}