aboutsummaryrefslogtreecommitdiff
blob: b7738c7544974c8de7d1441cb338b0d9a56d4d5a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
GENTOO_PYTHON_PROCESS_NAME environmental variable is set by python-wrapper and wrapper scripts generated by
python_generate_wrapper_scripts() and specifies process name.
GENTOO_PYTHON_WRAPPER_SCRIPT_PATH environmental variable is set by wrapper scripts generated by
python_generate_wrapper_scripts() and specifies sys.argv[0] in target executables.
GENTOO_PYTHON_TARGET_SCRIPT_PATH environmental variable is set by wrapper scripts generated by
python_generate_wrapper_scripts() and specifies paths to actually executed scripts.
GENTOO_PYTHON_TARGET_SCRIPT_PATH_VERIFICATION environmental variable is used by wrapper scripts generated by
python_generate_wrapper_scripts() to check if Python supports GENTOO_PYTHON_TARGET_SCRIPT_PATH environmental variable.

--- Modules/main.c
+++ Modules/main.c
@@ -331,6 +331,7 @@
     int version = 0;
     int saw_unbuffered_flag = 0;
     PyCompilerFlags cf;
+    char *target_script_name = getenv("GENTOO_PYTHON_TARGET_SCRIPT_PATH");
 
     cf.cf_flags = 0;
 
@@ -551,7 +552,17 @@
             filename = argv[_PyOS_optind];
 
 #else
-        filename = argv[_PyOS_optind];
+        if (target_script_name != NULL && *target_script_name != '\0') {
+            size_t length = strlen(target_script_name);
+            wchar_t *wcs_target_script_name = (wchar_t *) calloc(length + 1, sizeof(wchar_t));
+            char *old_locale = setlocale(LC_CTYPE, NULL);
+            setlocale(LC_CTYPE, "");
+            if (mbstowcs(wcs_target_script_name, target_script_name, length) >= 0)
+                filename = wcs_target_script_name;
+            setlocale(LC_CTYPE, old_locale);
+        }
+        if (filename == NULL)
+            filename = argv[_PyOS_optind];
 #endif
     }
 
--- Modules/posixmodule.c
+++ Modules/posixmodule.c
@@ -1157,6 +1157,10 @@
         char *p = strchr(*e, '=');
         if (p == NULL)
             continue;
+        if ((strlen("GENTOO_PYTHON_PROCESS_NAME") == (int)(p-*e) && strncmp("GENTOO_PYTHON_PROCESS_NAME", *e, (int)(p-*e)) == 0) ||
+            (strlen("GENTOO_PYTHON_TARGET_SCRIPT_PATH") == (int)(p-*e) && strncmp("GENTOO_PYTHON_TARGET_SCRIPT_PATH", *e, (int)(p-*e)) == 0) ||
+            (strlen("GENTOO_PYTHON_WRAPPER_SCRIPT_PATH") == (int)(p-*e) && strncmp("GENTOO_PYTHON_WRAPPER_SCRIPT_PATH", *e, (int)(p-*e)) == 0))
+            continue;
         k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
         if (k == NULL) {
             PyErr_Clear();
--- Modules/python.c
+++ Modules/python.c
@@ -7,6 +7,14 @@
 #include <floatingpoint.h>
 #endif
 
+#ifdef __linux__
+#include <linux/prctl.h>
+#include <sys/prctl.h>
+#ifndef PR_SET_NAME
+#define PR_SET_NAME 15
+#endif
+#endif
+
 #ifdef MS_WINDOWS
 int
 wmain(int argc, wchar_t **argv)
@@ -18,6 +26,11 @@
 int
 main(int argc, char **argv)
 {
+    if (getenv("GENTOO_PYTHON_TARGET_SCRIPT_PATH_VERIFICATION")) {
+        printf("GENTOO_PYTHON_TARGET_SCRIPT_PATH supported\n");
+        return 0;
+    }
+
     wchar_t **argv_copy;
     /* We need a second copy, as Python might modify the first one. */
     wchar_t **argv_copy2;
@@ -59,6 +72,16 @@
 
     setlocale(LC_ALL, oldloc);
     free(oldloc);
+
+#ifdef __linux__
+    char *process_name = getenv("GENTOO_PYTHON_PROCESS_NAME");
+#ifdef HAVE_UNSETENV
+    unsetenv("GENTOO_PYTHON_PROCESS_NAME");
+#endif
+    if (process_name != NULL && *process_name != '\0')
+        prctl(PR_SET_NAME, process_name);
+#endif
+
     res = Py_Main(argc, argv_copy);
     for (i = 0; i < argc; i++) {
         PyMem_Free(argv_copy2[i]);
--- Python/sysmodule.c
+++ Python/sysmodule.c
@@ -1778,6 +1778,10 @@
 makeargvobject(int argc, wchar_t **argv)
 {
     PyObject *av;
+    char *wrapper_script_name = getenv("GENTOO_PYTHON_WRAPPER_SCRIPT_PATH");
+#ifdef HAVE_UNSETENV
+    unsetenv("GENTOO_PYTHON_WRAPPER_SCRIPT_PATH");
+#endif
     if (argc <= 0 || argv == NULL) {
         /* Ensure at least one (empty) argument is seen */
         static wchar_t *empty_argv[1] = {L""};
@@ -1802,7 +1806,16 @@
             } else
                 v = PyUnicode_FromString(argv[i]);
 #else
-            PyObject *v = PyUnicode_FromWideChar(argv[i], -1);
+            PyObject *v = NULL;
+            if (i == 0 && wrapper_script_name != NULL && *wrapper_script_name != '\0') {
+                size_t length = strlen(wrapper_script_name);
+                wchar_t *wcs_wrapper_script_name = (wchar_t *) calloc(length + 1, sizeof(wchar_t));
+                if (mbstowcs(wcs_wrapper_script_name, wrapper_script_name, length) >= 0)
+                    v = PyUnicode_FromWideChar(wcs_wrapper_script_name, -1);
+                free(wcs_wrapper_script_name);
+            }
+            if (v == NULL)
+                v = PyUnicode_FromWideChar(argv[i], -1);
 #endif
             if (v == NULL) {
                 Py_DECREF(av);
@@ -1822,7 +1835,12 @@
 static void
 sys_update_path(int argc, wchar_t **argv)
 {
-    wchar_t *argv0;
+    char *target_script_name = getenv("GENTOO_PYTHON_TARGET_SCRIPT_PATH");
+#ifdef HAVE_UNSETENV
+    unsetenv("GENTOO_PYTHON_TARGET_SCRIPT_PATH");
+#endif
+    wchar_t *wcs_target_script_name = NULL;
+    wchar_t *argv0 = NULL;
     wchar_t *p = NULL;
     Py_ssize_t n = 0;
     PyObject *a;
@@ -1842,7 +1860,14 @@
     if (path == NULL)
         return;
 
-    argv0 = argv[0];
+    if (target_script_name != NULL && *target_script_name != '\0') {
+        size_t length = strlen(target_script_name);
+        wcs_target_script_name = (wchar_t *) calloc(length + 1, sizeof(wchar_t));
+        if (mbstowcs(wcs_target_script_name, target_script_name, length) >= 0)
+            argv0 = wcs_target_script_name;
+    }
+    if (argv0 == NULL)
+        argv0 = argv[0];
 
 #ifdef HAVE_READLINK
     if (_HAVE_SCRIPT_ARGUMENT(argc, argv))
@@ -1919,6 +1944,7 @@
     if (PyList_Insert(path, 0, a) < 0)
         Py_FatalError("sys.path.insert(0) failed");
     Py_DECREF(a);
+    free(wcs_target_script_name);
 }
 
 void