8248905: [macos] symbolic links not properly resolved

Reviewed-by: herrick, asemenyuk
This commit is contained in:
Alexander Matveev 2020-08-07 19:04:45 -07:00
parent 3c276ce1fe
commit 084e15bca3

@ -23,12 +23,39 @@
* questions.
*/
#include <sys/stat.h>
#include <unistd.h>
#include <mach-o/dyld.h>
#include "FileUtils.h"
#include "ErrorHandling.h"
namespace SysInfo {
tstring getRealPath(const std::vector<char>& in) {
std::vector<char> out(PATH_MAX);
struct stat sb;
if (lstat(in.data(), &sb) == -1) {
JP_THROW(tstrings::any() << "lstat(" << in.data()
<< ") failed. Error: " << lastCRTError());
}
// readlink() will fail if called on real path, so if we have real path, then just
// use it
if (!S_ISLNK(sb.st_mode)) {
return tstring(in.data(), in.size() - 1 /* don't count trailing '0' */);
}
// Get real path, since _NSGetExecutablePath can return symbolic link
ssize_t len = readlink(in.data(), out.data(), PATH_MAX);
if (len < 0) {
JP_THROW(tstrings::any() << "readlink(" << in.data()
<< ") failed. Error: " << lastCRTError());
}
return tstring(out.data(), len);
}
tstring getProcessModulePath() {
std::vector<char> buffer;
uint32_t bufferSize = 0;
@ -44,8 +71,9 @@ tstring getProcessModulePath() {
buffer.resize(bufferSize);
} while (true);
tstring reply = tstring(buffer.data(),
buffer.size() - 1 /* don't count trailing '0' */);
tstring reply = getRealPath(buffer);
return FileUtils::toAbsolutePath(reply);
}