From 2f62ee0698792c06ee698475049c8d8f03e0e73c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christian=20G=C3=B6ttsche?= Date: Tue, 9 Aug 2022 20:59:10 +0200 Subject: Linux: support openat() without readlinkat() linux/LinuxProcessList.c:1094:52: error: format specifies type 'char *' but the argument has type 'openat_arg_t' (aka 'int') [-Werror,-Wformat] xSnprintf(filename, sizeof(filename), "%s/cwd", procFd); ~~ ^~~~~~ %d linux/LinuxProcessList.c:1333:44: error: format specifies type 'char *' but the argument has type 'openat_arg_t' (aka 'int') [-Werror,-Wformat] xSnprintf(path, sizeof(path), "%s/exe", procFd); ~~ ^~~~~~ %d Supersedes: #1025 --- Compat.c | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) (limited to 'Compat.c') diff --git a/Compat.c b/Compat.c index 8c881381..d0ad2cc9 100644 --- a/Compat.c +++ b/Compat.c @@ -11,6 +11,7 @@ in the source distribution for its full text. #include #include // IWYU pragma: keep +#include #include #include #include // IWYU pragma: keep @@ -18,6 +19,12 @@ in the source distribution for its full text. #include "XUtils.h" // IWYU pragma: keep +/* GNU/Hurd does not have PATH_MAX in limits.h */ +#ifndef PATH_MAX +# define PATH_MAX 4096 +#endif + + int Compat_faccessat(int dirfd, const char* pathname, int mode, @@ -117,3 +124,33 @@ ssize_t Compat_readlinkat(int dirfd, #endif } + +ssize_t Compat_readlink(openat_arg_t dirfd, + const char* pathname, + char* buf, + size_t bufsize) { + +#ifdef HAVE_OPENAT + + char fdPath[32]; + xSnprintf(fdPath, sizeof(fdPath), "/proc/self/fd/%d", dirfd); + + char dirPath[PATH_MAX + 1]; + ssize_t r = readlink(fdPath, dirPath, sizeof(dirPath) - 1); + if (r < 0) + return r; + + dirPath[r] = '\0'; + + char linkPath[PATH_MAX + 1]; + xSnprintf(linkPath, sizeof(linkPath), "%s/%s", dirPath, pathname); + +#else + + char linkPath[PATH_MAX + 1]; + xSnprintf(linkPath, sizeof(linkPath), "%s/%s", dirfd, pathname); + +#endif /* HAVE_OPENAT */ + + return readlink(linkPath, buf, bufsize); +} -- cgit v1.2.3