diff Mac/Tools/pythonw.c @ 78160:b79d276041a8

Closes #15307: symlinks now work on OS X with framework Python builds. Patch by Ronald Oussoren.
author Vinay Sajip <vinay_sajip@yahoo.co.uk>
date Tue, 17 Jul 2012 17:33:46 +0100
parents c96dd645825e
children
line wrap: on
line diff
--- a/Mac/Tools/pythonw.c	Tue Jul 17 14:29:33 2012 +0200
+++ b/Mac/Tools/pythonw.c	Tue Jul 17 17:33:46 2012 +0100
@@ -28,6 +28,7 @@
 #include <dlfcn.h>
 #include <stdlib.h>
 #include <Python.h>
+#include <mach-o/dyld.h>
 
 
 extern char** environ;
@@ -158,9 +159,44 @@
     /* Set the original executable path in the environment. */
     status = _NSGetExecutablePath(path, &size);
     if (status == 0) {
-        if (realpath(path, real_path) != NULL) {
-            setenv("__PYVENV_LAUNCHER__", real_path, 1);
+        /*
+         * 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);
     }
 
     /*