summaryrefslogtreecommitdiffstats
path: root/Python
diff options
context:
space:
mode:
authorVictor Stinner <vstinner@redhat.com>2018-11-16 10:55:35 (GMT)
committerGitHub <noreply@github.com>2018-11-16 10:55:35 (GMT)
commit37cd982df02795905886ab36a2378ed557cb6f60 (patch)
treeaa750eca7acb660a0d3156fd7820396c2dff2f4c /Python
parentb65413b497a07f521d835b799be7dd0afcedbd65 (diff)
downloadcpython-37cd982df02795905886ab36a2378ed557cb6f60.zip
cpython-37cd982df02795905886ab36a2378ed557cb6f60.tar.gz
cpython-37cd982df02795905886ab36a2378ed557cb6f60.tar.bz2
bpo-35239: _PySys_EndInit() copies module_search_path (GH-10532)
* The _PySys_EndInit() function now copies the config->module_search_path list, so config is longer modified when sys.path is updated. * config->warnoptions list and config->xoptions dict are also copied * test_embed: InitConfigTests now also tests main_config['module_search_path'] * Fix _Py_InitializeMainInterpreter(): don't use config->warnoptions but sys.warnoptions to decide if the warnings module should be imported at startup.
Diffstat (limited to 'Python')
-rw-r--r--Python/pylifecycle.c4
-rw-r--r--Python/sysmodule.c26
2 files changed, 25 insertions, 5 deletions
diff --git a/Python/pylifecycle.c b/Python/pylifecycle.c
index 4ccea2e..58e1647 100644
--- a/Python/pylifecycle.c
+++ b/Python/pylifecycle.c
@@ -836,8 +836,8 @@ _Py_InitializeMainInterpreter(PyInterpreterState *interp,
}
/* Initialize warnings. */
- if (interp->config.warnoptions != NULL &&
- PyList_Size(interp->config.warnoptions) > 0)
+ PyObject *warnoptions = PySys_GetObject("warnoptions");
+ if (warnoptions != NULL && PyList_Size(warnoptions) > 0)
{
PyObject *warnings_module = PyImport_ImportModule("warnings");
if (warnings_module == NULL) {
diff --git a/Python/sysmodule.c b/Python/sysmodule.c
index 99cab2b..2284e88 100644
--- a/Python/sysmodule.c
+++ b/Python/sysmodule.c
@@ -2488,7 +2488,20 @@ _PySys_EndInit(PyObject *sysdict, PyInterpreterState *interp)
assert(config->exec_prefix != NULL);
assert(config->base_exec_prefix != NULL);
- SET_SYS_FROM_STRING_BORROW("path", config->module_search_path);
+#define COPY_LIST(KEY, ATTR) \
+ do { \
+ assert(PyList_Check(config->ATTR)); \
+ PyObject *list = PyList_GetSlice(config->ATTR, \
+ 0, PyList_GET_SIZE(config->ATTR)); \
+ if (list == NULL) { \
+ return -1; \
+ } \
+ SET_SYS_FROM_STRING_BORROW(KEY, list); \
+ Py_DECREF(list); \
+ } while (0)
+
+ COPY_LIST("path", module_search_path);
+
SET_SYS_FROM_STRING_BORROW("executable", config->executable);
SET_SYS_FROM_STRING_BORROW("prefix", config->prefix);
SET_SYS_FROM_STRING_BORROW("base_prefix", config->base_prefix);
@@ -2505,12 +2518,19 @@ _PySys_EndInit(PyObject *sysdict, PyInterpreterState *interp)
SET_SYS_FROM_STRING_BORROW("argv", config->argv);
}
if (config->warnoptions != NULL) {
- SET_SYS_FROM_STRING_BORROW("warnoptions", config->warnoptions);
+ COPY_LIST("warnoptions", warnoptions);
}
if (config->xoptions != NULL) {
- SET_SYS_FROM_STRING_BORROW("_xoptions", config->xoptions);
+ PyObject *dict = PyDict_Copy(config->xoptions);
+ if (dict == NULL) {
+ return -1;
+ }
+ SET_SYS_FROM_STRING_BORROW("_xoptions", dict);
+ Py_DECREF(dict);
}
+#undef COPY_LIST
+
/* Set flags to their final values */
SET_SYS_FROM_STRING_INT_RESULT("flags", make_flags());
/* prevent user from creating new instances */