summaryrefslogtreecommitdiff
path: root/Mac/Tools/pythonw.c
diff options
context:
space:
mode:
Diffstat (limited to 'Mac/Tools/pythonw.c')
-rw-r--r--Mac/Tools/pythonw.c48
1 files changed, 48 insertions, 0 deletions
diff --git a/Mac/Tools/pythonw.c b/Mac/Tools/pythonw.c
index 30c82ac476..1d2db383f9 100644
--- a/Mac/Tools/pythonw.c
+++ b/Mac/Tools/pythonw.c
@@ -28,6 +28,7 @@
#include <dlfcn.h>
#include <stdlib.h>
#include <Python.h>
+#include <mach-o/dyld.h>
extern char** environ;
@@ -150,6 +151,53 @@ setup_spawnattr(posix_spawnattr_t* spawnattr)
int
main(int argc, char **argv) {
char* exec_path = get_python_path();
+ static char path[PATH_MAX * 2];
+ static char real_path[PATH_MAX * 2];
+ int status;
+ uint32_t size = PATH_MAX * 2;
+
+ /* Set the original executable path in the environment. */
+ status = _NSGetExecutablePath(path, &size);
+ if (status == 0) {
+ /*
+ * Note: don't call 'realpath', that will
+ * erase symlink information, and that
+ * breaks "pyvenv --symlink"
+ *
+ * It is nice to have the directory name
+ * as a cleaned up absolute path though,
+ * therefore call realpath on dirname(path)
+ */
+ char* slash = strrchr(path, '/');
+ if (slash) {
+ char replaced;
+ replaced = slash[1];
+ slash[1] = 0;
+ if (realpath(path, real_path) == NULL) {
+ err(1, "realpath: %s", path);
+ }
+ slash[1] = replaced;
+ if (strlcat(real_path, slash, sizeof(real_path)) > sizeof(real_path)) {
+ errno = EINVAL;
+ err(1, "realpath: %s", path);
+ }
+
+ } else {
+ if (realpath(".", real_path) == NULL) {
+ err(1, "realpath: %s", path);
+ }
+ if (strlcat(real_path, "/", sizeof(real_path)) > sizeof(real_path)) {
+ errno = EINVAL;
+ err(1, "realpath: %s", path);
+ }
+ if (strlcat(real_path, path, sizeof(real_path)) > sizeof(real_path)) {
+ errno = EINVAL;
+ err(1, "realpath: %s", path);
+ }
+ }
+
+ setenv("__PYVENV_LAUNCHER__", real_path, 1);
+ }
/*
* Let argv[0] refer to the new interpreter. This is needed to