From da7efea0e7520f7ce8627acc9f4037a2f875c47e Mon Sep 17 00:00:00 2001 From: Ron Yorston Date: Thu, 12 Aug 2021 11:39:12 +0100 Subject: win32: better handling of nested symlinks Our realpath(3) implementation uses xmalloc_follow_symlinks() to expand symlinks. This detects when symlinks are too deeply nested but didn't set errno, so anything calling realpath(3) was unable to say what had gone wrong. (For example, 'ls -L' or 'stat -L'.) Set errno to ELOOP. This then leads to the problem that Windows doesn't know about ELOOP so reports 'Unknown error'. Add a replacement for strerror(3) which returns a sensible message. Costs 96 bytes. --- include/mingw.h | 3 +++ libbb/xreadlink.c | 3 +++ win32/mingw.c | 8 ++++++++ 3 files changed, 14 insertions(+) diff --git a/include/mingw.h b/include/mingw.h index c4849215b..03ef89029 100644 --- a/include/mingw.h +++ b/include/mingw.h @@ -209,6 +209,9 @@ int unsetenv(const char *env); * string.h */ char *strndup(char const *s, size_t n); +char *mingw_strerror(int errnum); + +#define strerror mingw_strerror /* * strings.h diff --git a/libbb/xreadlink.c b/libbb/xreadlink.c index f0a63fd9b..b64654b33 100644 --- a/libbb/xreadlink.c +++ b/libbb/xreadlink.c @@ -70,6 +70,9 @@ char* FAST_FUNC xmalloc_follow_symlinks(const char *path) } if (!--looping) { +#if ENABLE_PLATFORM_MINGW32 + errno = ELOOP; +#endif free(linkpath); free_buf_ret_null: free(buf); diff --git a/win32/mingw.c b/win32/mingw.c index 49dcd89d8..c592b8d2c 100644 --- a/win32/mingw.c +++ b/win32/mingw.c @@ -161,6 +161,14 @@ int err_win_to_posix(void) return error; } +#undef strerror +char *mingw_strerror(int errnum) +{ + if (errnum == ELOOP) + return (char *)"Too many levels of symbolic links"; + return strerror(errnum); +} + static int zero_fd = -1; static int rand_fd = -1; -- cgit v1.2.3-55-g6feb