diff --git a/src/unix/darwin.c b/src/unix/darwin.c index 69117d61..651545f8 100644 --- a/src/unix/darwin.c +++ b/src/unix/darwin.c @@ -65,28 +65,33 @@ uint64_t uv__hrtime(uv_clocktype_t type) { int uv_exepath(char* buffer, size_t* size) { - uint32_t usize; - int result; - char* path; - char* fullpath; + /* realpath(exepath) may be > PATH_MAX so double it to be on the safe side. */ + char abspath[PATH_MAX * 2 + 1]; + char exepath[PATH_MAX + 1]; + uint32_t exepath_size; + size_t abspath_size; if (buffer == NULL || size == NULL || *size == 0) return -EINVAL; - usize = *size; - result = _NSGetExecutablePath(buffer, &usize); - if (result) return result; + exepath_size = sizeof(exepath); + if (_NSGetExecutablePath(exepath, &exepath_size)) + return -EIO; - path = malloc(2 * PATH_MAX); - fullpath = realpath(buffer, path); - if (fullpath == NULL) { - SAVE_ERRNO(free(path)); + if (realpath(exepath, abspath) != abspath) return -errno; - } - strncpy(buffer, fullpath, *size); - free(fullpath); - *size = strlen(buffer); + abspath_size = strlen(abspath); + if (abspath_size == 0) + return -EIO; + + *size -= 1; + if (*size > abspath_size) + *size = abspath_size; + + memcpy(buffer, abspath, *size); + buffer[*size] = '\0'; + return 0; } diff --git a/test/test-get-currentexe.c b/test/test-get-currentexe.c index b2399172..c6091ff7 100644 --- a/test/test-get-currentexe.c +++ b/test/test-get-currentexe.c @@ -65,5 +65,13 @@ TEST_IMPL(get_currentexe) { r = uv_exepath(buffer, &size); ASSERT(r == UV_EINVAL); + memset(buffer, -1, sizeof(buffer)); + + size = 1; + r = uv_exepath(buffer, &size); + ASSERT(r == 0); + ASSERT(size == 0); + ASSERT(buffer[0] == '\0'); + return 0; }