mirror of
https://github.com/zlib-ng/minizip-ng
synced 2026-08-25 14:26:08 -04:00
mz_os: skip symlink check at or above destination dir
mz_dir_has_unsafe_symlink walks every component of the destination path and rejects any symlink with an absolute target. That's too strict: when the user-chosen destination dir (or one of its ancestors) happens to be a symlink, extracting into it gets rejected with -107. The check only needs to police symlinks that appear strictly inside the destination, since those could be zip-controlled. Skip the symlink check when check_path is at or above base_path; let the existing logic enforce on components below. Fixes #943.
This commit is contained in:
parent
8ec500fd38
commit
483f0568b0
1 changed files with 11 additions and 0 deletions
11
mz_os.c
11
mz_os.c
|
|
@ -287,6 +287,7 @@ int32_t mz_dir_has_unsafe_symlink(const char *path, const char *base_path) {
|
|||
size_t max_path = 1024;
|
||||
size_t parent_len = 0;
|
||||
size_t pos = 0;
|
||||
size_t cmp_len = 0;
|
||||
int32_t err = MZ_OK;
|
||||
|
||||
if (!path || *path == 0 || !base_path)
|
||||
|
|
@ -322,6 +323,16 @@ int32_t mz_dir_has_unsafe_symlink(const char *path, const char *base_path) {
|
|||
if (mz_os_is_symlink(check_path) != MZ_OK)
|
||||
continue;
|
||||
|
||||
/* Skip components at or above the base dir. */
|
||||
cmp_len = pos;
|
||||
if (mz_path_has_slash(check_path) == MZ_OK)
|
||||
cmp_len--;
|
||||
if (cmp_len <= base_len && strncmp(check_path, base_path, cmp_len) == 0) {
|
||||
/* Verify that the prefix match is on a directory boundary. */
|
||||
if (cmp_len == base_len || mz_os_is_dir_separator(base_path[cmp_len]))
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Allocate symlink buffers on first use */
|
||||
if (!symlink_target) {
|
||||
symlink_target = (char *)calloc(1, max_path);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue