diff options
author | Colin Cross <ccross@android.com> | 2014-04-25 14:28:54 -0700 |
---|---|---|
committer | Colin Cross <ccross@android.com> | 2014-04-25 15:19:18 -0700 |
commit | 0e3f47e4827a067b9b9795a3ae7297b51c9f0776 (patch) | |
tree | 83a1c9a76d708c900155729d92687ac78b59984f | |
parent | 9fdc8156ca8fb3449859bebf080a477fa3bcff5c (diff) | |
download | core-0e3f47e4827a067b9b9795a3ae7297b51c9f0776.tar.gz core-0e3f47e4827a067b9b9795a3ae7297b51c9f0776.tar.bz2 core-0e3f47e4827a067b9b9795a3ae7297b51c9f0776.zip |
append2simg: write to temporary file
append2simg causes libsparse to write mmapped data from a file
back to that same file. On btrfs, this sometimes causes a page
of zeroes to be written instead of the file data. Work around
the issue by writing the output to a temporary file and then
renaming it over the original file.
Change-Id: Ia194b6ba0ddb8548747b63292b523756f544706a
-rw-r--r-- | libsparse/Android.mk | 3 | ||||
-rw-r--r-- | libsparse/append2simg.c | 30 |
2 files changed, 32 insertions, 1 deletions
diff --git a/libsparse/Android.mk b/libsparse/Android.mk index a21e090c4..4aba16873 100644 --- a/libsparse/Android.mk +++ b/libsparse/Android.mk @@ -81,6 +81,8 @@ LOCAL_STATIC_LIBRARIES := \ include $(BUILD_EXECUTABLE) +ifneq ($(HOST_OS),windows) + include $(CLEAR_VARS) LOCAL_SRC_FILES := append2simg.c LOCAL_MODULE := append2simg @@ -89,6 +91,7 @@ LOCAL_STATIC_LIBRARIES := \ libz include $(BUILD_HOST_EXECUTABLE) +endif include $(CLEAR_VARS) LOCAL_MODULE := simg_dump.py diff --git a/libsparse/append2simg.c b/libsparse/append2simg.c index 180584f48..65e6cc29b 100644 --- a/libsparse/append2simg.c +++ b/libsparse/append2simg.c @@ -16,6 +16,7 @@ #define _FILE_OFFSET_BITS 64 #define _LARGEFILE64_SOURCE 1 +#define _GNU_SOURCE #include <errno.h> #include <fcntl.h> @@ -56,6 +57,11 @@ int main(int argc, char *argv[]) char *input_path; off64_t input_len; + int tmp_fd; + char *tmp_path; + + int ret; + if (argc == 3) { output_path = argv[1]; input_path = argv[2]; @@ -64,6 +70,12 @@ int main(int argc, char *argv[]) exit(-1); } + ret = asprintf(&tmp_path, "%s.append2simg", output_path); + if (ret < 0) { + fprintf(stderr, "Couldn't allocate filename\n"); + exit(-1); + } + output = open(output_path, O_RDWR | O_BINARY); if (output < 0) { fprintf(stderr, "Couldn't open output file (%s)\n", strerror(errno)); @@ -99,14 +111,30 @@ int main(int argc, char *argv[]) } sparse_output->len += input_len; + tmp_fd = open(tmp_path, O_WRONLY | O_CREAT | O_BINARY, 0664); + if (tmp_fd < 0) { + fprintf(stderr, "Couldn't open temporary file (%s)\n", strerror(errno)); + exit(-1); + } + lseek64(output, 0, SEEK_SET); - if (sparse_file_write(sparse_output, output, false, true, false) < 0) { + if (sparse_file_write(sparse_output, tmp_fd, false, true, false) < 0) { fprintf(stderr, "Failed to write sparse file\n"); exit(-1); } sparse_file_destroy(sparse_output); + close(tmp_fd); close(output); close(input); + + ret = rename(tmp_path, output_path); + if (ret < 0) { + fprintf(stderr, "Failed to rename temporary file (%s)\n", strerror(errno)); + exit(-1); + } + + free(tmp_path); + exit(0); } |