diff options
author | Denys Vlasenko | 2009-11-29 07:45:33 +0100 |
---|---|---|
committer | Denys Vlasenko | 2009-11-29 07:45:33 +0100 |
commit | f94c9bf288290c9f4e5a7c2745922abd600e88ca (patch) | |
tree | 57289568fb310466798ae6b297fe46d6e3d2bfcf /archival/libunarchive | |
parent | 2ce42e98d799de4c3389d9c4ce0a6b0d42dac7cc (diff) | |
download | busybox-f94c9bf288290c9f4e5a7c2745922abd600e88ca.zip busybox-f94c9bf288290c9f4e5a7c2745922abd600e88ca.tar.gz |
tar: fix bug 673 (misdetection of repeated dir as hardlink). +92 bytes
While at it, remove many superfluous ops on unpack:
mkdir("."), lots of umask() calls. Can remove more
by caching username->uid.
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'archival/libunarchive')
-rw-r--r-- | archival/libunarchive/data_extract_all.c | 17 |
1 files changed, 11 insertions, 6 deletions
diff --git a/archival/libunarchive/data_extract_all.c b/archival/libunarchive/data_extract_all.c index 2fcddc4..1100410 100644 --- a/archival/libunarchive/data_extract_all.c +++ b/archival/libunarchive/data_extract_all.c @@ -13,9 +13,12 @@ void FAST_FUNC data_extract_all(archive_handle_t *archive_handle) int res; if (archive_handle->ah_flags & ARCHIVE_CREATE_LEADING_DIRS) { - char *name = xstrdup(file_header->name); - bb_make_directory(dirname(name), -1, FILEUTILS_RECUR); - free(name); + char *slash = strrchr(file_header->name, '/'); + if (slash) { + *slash = '\0'; + bb_make_directory(file_header->name, -1, FILEUTILS_RECUR); + *slash = '/'; + } } if (archive_handle->ah_flags & ARCHIVE_UNLINK_OLD) { @@ -52,8 +55,9 @@ void FAST_FUNC data_extract_all(archive_handle_t *archive_handle) /* Handle hard links separately * We identified hard links as regular files of size 0 with a symlink */ - if (S_ISREG(file_header->mode) && (file_header->link_target) - && (file_header->size == 0) + if (S_ISREG(file_header->mode) + && file_header->link_target + && file_header->size == 0 ) { /* hard link */ res = link(file_header->link_target, file_header->name); @@ -121,6 +125,7 @@ void FAST_FUNC data_extract_all(archive_handle_t *archive_handle) gid_t gid = file_header->gid; if (file_header->uname) { +//TODO: cache last name/id pair? struct passwd *pwd = getpwnam(file_header->uname); if (pwd) uid = pwd->pw_uid; } @@ -128,7 +133,7 @@ void FAST_FUNC data_extract_all(archive_handle_t *archive_handle) struct group *grp = getgrnam(file_header->gname); if (grp) gid = grp->gr_gid; } - /* GNU tar 1.15.1 use chown, not lchown */ + /* GNU tar 1.15.1 uses chown, not lchown */ chown(file_header->name, uid, gid); } else #endif |