summaryrefslogtreecommitdiffhomepage
path: root/archival/libarchive
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2013-02-20 15:58:42 +0100
committerDenys Vlasenko <vda.linux@googlemail.com>2013-02-20 15:58:42 +0100
commit2aec773688fd64857e9446838187170760acddd4 (patch)
tree4528074a1856b5656b5db6d140026a486c44714d /archival/libarchive
parent10f5f9b10d5bb18aa612e8f340d8454421015b00 (diff)
rpm: use "create+rename" method of replacing existing files
Users were reporting getting errors like "ls: error while loading shared libraries: libc.so.6: ELF load command past end of file" while rpm was unpacking glibc tarball. Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'archival/libarchive')
-rw-r--r--archival/libarchive/data_extract_all.c15
1 files changed, 14 insertions, 1 deletions
diff --git a/archival/libarchive/data_extract_all.c b/archival/libarchive/data_extract_all.c
index 3f67b835f..45776dcbe 100644
--- a/archival/libarchive/data_extract_all.c
+++ b/archival/libarchive/data_extract_all.c
@@ -106,15 +106,28 @@ void FAST_FUNC data_extract_all(archive_handle_t *archive_handle)
switch (file_header->mode & S_IFMT) {
case S_IFREG: {
/* Regular file */
+ char *dst_name;
int flags = O_WRONLY | O_CREAT | O_EXCL;
if (archive_handle->ah_flags & ARCHIVE_O_TRUNC)
flags = O_WRONLY | O_CREAT | O_TRUNC;
- dst_fd = xopen3(file_header->name,
+ dst_name = file_header->name;
+#ifdef ARCHIVE_REPLACE_VIA_RENAME
+ if (archive_handle->ah_flags & ARCHIVE_REPLACE_VIA_RENAME)
+ /* rpm-style temp file name */
+ dst_name = xasprintf("%s;%x", dst_name, (int)getpid());
+#endif
+ dst_fd = xopen3(dst_name,
flags,
file_header->mode
);
bb_copyfd_exact_size(archive_handle->src_fd, dst_fd, file_header->size);
close(dst_fd);
+#ifdef ARCHIVE_REPLACE_VIA_RENAME
+ if (archive_handle->ah_flags & ARCHIVE_REPLACE_VIA_RENAME) {
+ xrename(dst_name, file_header->name);
+ free(dst_name);
+ }
+#endif
break;
}
case S_IFDIR: