blob: e51bf9424a308390b86361471672b1955e034334 [file] [log] [blame]
Victor Stinner6c785c02018-08-01 17:56:14 +02001#include "Python.h"
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002#include "osdefs.h" /* DELIM */
Victor Stinnerf684d832019-03-01 03:44:13 +01003#include "pycore_coreconfig.h"
Victor Stinner9fc57a32018-11-07 00:44:03 +01004#include "pycore_fileutils.h"
Victor Stinner95e2cbf2019-03-01 16:25:19 +01005#include "pycore_getopt.h"
Victor Stinner621cebe2018-11-12 16:53:38 +01006#include "pycore_pylifecycle.h"
7#include "pycore_pymem.h"
Victor Stinner6d5ee972019-03-23 12:05:43 +01008#include "pycore_pystate.h" /* _PyRuntime */
Victor Stinnera1c249c2018-11-01 03:15:58 +01009#include "pycore_pathconfig.h"
Victor Stinner95e2cbf2019-03-01 16:25:19 +010010#include <locale.h> /* setlocale() */
Victor Stinnerdfe0dc72018-08-29 11:47:29 +020011#ifdef HAVE_LANGINFO_H
Victor Stinner95e2cbf2019-03-01 16:25:19 +010012# include <langinfo.h> /* nl_langinfo(CODESET) */
Victor Stinnerdfe0dc72018-08-29 11:47:29 +020013#endif
Victor Stinner95e2cbf2019-03-01 16:25:19 +010014#if defined(MS_WINDOWS) || defined(__CYGWIN__)
15# include <windows.h> /* GetACP() */
16# ifdef HAVE_IO_H
17# include <io.h>
18# endif
19# ifdef HAVE_FCNTL_H
20# include <fcntl.h> /* O_BINARY */
21# endif
Victor Stinnerb2457ef2018-08-29 13:25:36 +020022#endif
23
Victor Stinner6c785c02018-08-01 17:56:14 +020024
Victor Stinner95e2cbf2019-03-01 16:25:19 +010025/* --- Command line options --------------------------------------- */
26
Victor Stinner95e2cbf2019-03-01 16:25:19 +010027/* Short usage message (with %s for argv0) */
28static const char usage_line[] =
29"usage: %ls [option] ... [-c cmd | -m mod | file | -] [arg] ...\n";
30
31/* Long usage message, split into parts < 512 bytes */
32static const char usage_1[] = "\
33Options and arguments (and corresponding environment variables):\n\
34-b : issue warnings about str(bytes_instance), str(bytearray_instance)\n\
35 and comparing bytes/bytearray with str. (-bb: issue errors)\n\
36-B : don't write .pyc files on import; also PYTHONDONTWRITEBYTECODE=x\n\
37-c cmd : program passed in as string (terminates option list)\n\
38-d : debug output from parser; also PYTHONDEBUG=x\n\
39-E : ignore PYTHON* environment variables (such as PYTHONPATH)\n\
40-h : print this help message and exit (also --help)\n\
41";
42static const char usage_2[] = "\
43-i : inspect interactively after running script; forces a prompt even\n\
44 if stdin does not appear to be a terminal; also PYTHONINSPECT=x\n\
45-I : isolate Python from the user's environment (implies -E and -s)\n\
46-m mod : run library module as a script (terminates option list)\n\
47-O : remove assert and __debug__-dependent statements; add .opt-1 before\n\
48 .pyc extension; also PYTHONOPTIMIZE=x\n\
49-OO : do -O changes and also discard docstrings; add .opt-2 before\n\
50 .pyc extension\n\
51-q : don't print version and copyright messages on interactive startup\n\
52-s : don't add user site directory to sys.path; also PYTHONNOUSERSITE\n\
53-S : don't imply 'import site' on initialization\n\
54";
55static const char usage_3[] = "\
56-u : force the stdout and stderr streams to be unbuffered;\n\
57 this option has no effect on stdin; also PYTHONUNBUFFERED=x\n\
58-v : verbose (trace import statements); also PYTHONVERBOSE=x\n\
59 can be supplied multiple times to increase verbosity\n\
60-V : print the Python version number and exit (also --version)\n\
61 when given twice, print more information about the build\n\
62-W arg : warning control; arg is action:message:category:module:lineno\n\
63 also PYTHONWARNINGS=arg\n\
64-x : skip first line of source, allowing use of non-Unix forms of #!cmd\n\
65-X opt : set implementation-specific option\n\
66--check-hash-based-pycs always|default|never:\n\
67 control how Python invalidates hash-based .pyc files\n\
68";
69static const char usage_4[] = "\
70file : program read from script file\n\
71- : program read from stdin (default; interactive mode if a tty)\n\
72arg ...: arguments passed to program in sys.argv[1:]\n\n\
73Other environment variables:\n\
74PYTHONSTARTUP: file executed on interactive startup (no default)\n\
75PYTHONPATH : '%lc'-separated list of directories prefixed to the\n\
76 default module search path. The result is sys.path.\n\
77";
78static const char usage_5[] =
79"PYTHONHOME : alternate <prefix> directory (or <prefix>%lc<exec_prefix>).\n"
80" The default module search path uses %s.\n"
81"PYTHONCASEOK : ignore case in 'import' statements (Windows).\n"
82"PYTHONIOENCODING: Encoding[:errors] used for stdin/stdout/stderr.\n"
83"PYTHONFAULTHANDLER: dump the Python traceback on fatal errors.\n";
84static const char usage_6[] =
85"PYTHONHASHSEED: if this variable is set to 'random', a random value is used\n"
86" to seed the hashes of str, bytes and datetime objects. It can also be\n"
87" set to an integer in the range [0,4294967295] to get hash values with a\n"
88" predictable seed.\n"
89"PYTHONMALLOC: set the Python memory allocators and/or install debug hooks\n"
90" on Python memory allocators. Use PYTHONMALLOC=debug to install debug\n"
91" hooks.\n"
92"PYTHONCOERCECLOCALE: if this variable is set to 0, it disables the locale\n"
93" coercion behavior. Use PYTHONCOERCECLOCALE=warn to request display of\n"
94" locale coercion and locale compatibility warnings on stderr.\n"
95"PYTHONBREAKPOINT: if this variable is set to 0, it disables the default\n"
96" debugger. It can be set to the callable of your debugger of choice.\n"
97"PYTHONDEVMODE: enable the development mode.\n"
98"PYTHONPYCACHEPREFIX: root directory for bytecode cache (pyc) files.\n";
99
100#if defined(MS_WINDOWS)
101# define PYTHONHOMEHELP "<prefix>\\python{major}{minor}"
102#else
103# define PYTHONHOMEHELP "<prefix>/lib/pythonX.X"
104#endif
Victor Stinner6c785c02018-08-01 17:56:14 +0200105
106
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100107/* --- Global configuration variables ----------------------------- */
Victor Stinnerb2457ef2018-08-29 13:25:36 +0200108
Victor Stinner6c785c02018-08-01 17:56:14 +0200109/* UTF-8 mode (PEP 540): if equals to 1, use the UTF-8 encoding, and change
110 stdin and stdout error handler to "surrogateescape". It is equal to
111 -1 by default: unknown, will be set by Py_Main() */
112int Py_UTF8Mode = -1;
113int Py_DebugFlag = 0; /* Needed by parser.c */
114int Py_VerboseFlag = 0; /* Needed by import.c */
115int Py_QuietFlag = 0; /* Needed by sysmodule.c */
116int Py_InteractiveFlag = 0; /* Needed by Py_FdIsInteractive() below */
117int Py_InspectFlag = 0; /* Needed to determine whether to exit at SystemExit */
118int Py_OptimizeFlag = 0; /* Needed by compile.c */
119int Py_NoSiteFlag = 0; /* Suppress 'import site' */
120int Py_BytesWarningFlag = 0; /* Warn on str(bytes) and str(buffer) */
121int Py_FrozenFlag = 0; /* Needed by getpath.c */
122int Py_IgnoreEnvironmentFlag = 0; /* e.g. PYTHONPATH, PYTHONHOME */
123int Py_DontWriteBytecodeFlag = 0; /* Suppress writing bytecode files (*.pyc) */
124int Py_NoUserSiteDirectory = 0; /* for -s and site.py */
125int Py_UnbufferedStdioFlag = 0; /* Unbuffered binary std{in,out,err} */
126int Py_HashRandomizationFlag = 0; /* for -R and PYTHONHASHSEED */
127int Py_IsolatedFlag = 0; /* for -I, isolate from user's env */
128#ifdef MS_WINDOWS
129int Py_LegacyWindowsFSEncodingFlag = 0; /* Uses mbcs instead of utf-8 */
130int Py_LegacyWindowsStdioFlag = 0; /* Uses FileIO instead of WindowsConsoleIO */
131#endif
Victor Stinner6c785c02018-08-01 17:56:14 +0200132
133
Victor Stinner1075d162019-03-25 23:19:57 +0100134static PyObject *
Victor Stinner7ddd56f2018-11-14 00:24:28 +0100135_Py_GetGlobalVariablesAsDict(void)
136{
137 PyObject *dict, *obj;
138
139 dict = PyDict_New();
140 if (dict == NULL) {
141 return NULL;
142 }
143
144#define SET_ITEM(KEY, EXPR) \
145 do { \
146 obj = (EXPR); \
147 if (obj == NULL) { \
148 return NULL; \
149 } \
150 int res = PyDict_SetItemString(dict, (KEY), obj); \
151 Py_DECREF(obj); \
152 if (res < 0) { \
153 goto fail; \
154 } \
155 } while (0)
156#define SET_ITEM_INT(VAR) \
157 SET_ITEM(#VAR, PyLong_FromLong(VAR))
158#define FROM_STRING(STR) \
159 ((STR != NULL) ? \
160 PyUnicode_FromString(STR) \
161 : (Py_INCREF(Py_None), Py_None))
162#define SET_ITEM_STR(VAR) \
163 SET_ITEM(#VAR, FROM_STRING(VAR))
164
165 SET_ITEM_STR(Py_FileSystemDefaultEncoding);
166 SET_ITEM_INT(Py_HasFileSystemDefaultEncoding);
167 SET_ITEM_STR(Py_FileSystemDefaultEncodeErrors);
168 SET_ITEM_INT(_Py_HasFileSystemDefaultEncodeErrors);
169
170 SET_ITEM_INT(Py_UTF8Mode);
171 SET_ITEM_INT(Py_DebugFlag);
172 SET_ITEM_INT(Py_VerboseFlag);
173 SET_ITEM_INT(Py_QuietFlag);
174 SET_ITEM_INT(Py_InteractiveFlag);
175 SET_ITEM_INT(Py_InspectFlag);
176
177 SET_ITEM_INT(Py_OptimizeFlag);
178 SET_ITEM_INT(Py_NoSiteFlag);
179 SET_ITEM_INT(Py_BytesWarningFlag);
180 SET_ITEM_INT(Py_FrozenFlag);
181 SET_ITEM_INT(Py_IgnoreEnvironmentFlag);
182 SET_ITEM_INT(Py_DontWriteBytecodeFlag);
183 SET_ITEM_INT(Py_NoUserSiteDirectory);
184 SET_ITEM_INT(Py_UnbufferedStdioFlag);
185 SET_ITEM_INT(Py_HashRandomizationFlag);
186 SET_ITEM_INT(Py_IsolatedFlag);
187
188#ifdef MS_WINDOWS
189 SET_ITEM_INT(Py_LegacyWindowsFSEncodingFlag);
190 SET_ITEM_INT(Py_LegacyWindowsStdioFlag);
191#endif
192
193 return dict;
194
195fail:
196 Py_DECREF(dict);
197 return NULL;
198
199#undef FROM_STRING
200#undef SET_ITEM
201#undef SET_ITEM_INT
202#undef SET_ITEM_STR
203}
204
205
Victor Stinner74f65682019-03-15 15:08:05 +0100206/* --- _PyWstrList ------------------------------------------------ */
207
208#ifndef NDEBUG
209int
210_PyWstrList_CheckConsistency(const _PyWstrList *list)
211{
212 assert(list->length >= 0);
213 if (list->length != 0) {
214 assert(list->items != NULL);
215 }
216 for (Py_ssize_t i = 0; i < list->length; i++) {
217 assert(list->items[i] != NULL);
218 }
219 return 1;
220}
221#endif /* Py_DEBUG */
222
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100223
Victor Stinner6c785c02018-08-01 17:56:14 +0200224void
Victor Stinner74f65682019-03-15 15:08:05 +0100225_PyWstrList_Clear(_PyWstrList *list)
Victor Stinner6c785c02018-08-01 17:56:14 +0200226{
Victor Stinner74f65682019-03-15 15:08:05 +0100227 assert(_PyWstrList_CheckConsistency(list));
228 for (Py_ssize_t i=0; i < list->length; i++) {
229 PyMem_RawFree(list->items[i]);
Victor Stinner6c785c02018-08-01 17:56:14 +0200230 }
Victor Stinner74f65682019-03-15 15:08:05 +0100231 PyMem_RawFree(list->items);
232 list->length = 0;
233 list->items = NULL;
Victor Stinner6c785c02018-08-01 17:56:14 +0200234}
235
236
Victor Stinner74f65682019-03-15 15:08:05 +0100237int
238_PyWstrList_Copy(_PyWstrList *list, const _PyWstrList *list2)
Victor Stinner6c785c02018-08-01 17:56:14 +0200239{
Victor Stinner74f65682019-03-15 15:08:05 +0100240 assert(_PyWstrList_CheckConsistency(list));
241 assert(_PyWstrList_CheckConsistency(list2));
242
243 if (list2->length == 0) {
244 _PyWstrList_Clear(list);
245 return 0;
Alexey Izbysheveb746db2018-08-25 02:34:56 +0300246 }
Victor Stinner74f65682019-03-15 15:08:05 +0100247
248 _PyWstrList copy = _PyWstrList_INIT;
249
250 size_t size = list2->length * sizeof(list2->items[0]);
251 copy.items = PyMem_RawMalloc(size);
252 if (copy.items == NULL) {
253 return -1;
254 }
255
256 for (Py_ssize_t i=0; i < list2->length; i++) {
257 wchar_t *item = _PyMem_RawWcsdup(list2->items[i]);
258 if (item == NULL) {
259 _PyWstrList_Clear(&copy);
260 return -1;
Victor Stinner6c785c02018-08-01 17:56:14 +0200261 }
Victor Stinner74f65682019-03-15 15:08:05 +0100262 copy.items[i] = item;
263 copy.length = i + 1;
Victor Stinner6c785c02018-08-01 17:56:14 +0200264 }
Victor Stinner74f65682019-03-15 15:08:05 +0100265
266 _PyWstrList_Clear(list);
267 *list = copy;
268 return 0;
Victor Stinner6c785c02018-08-01 17:56:14 +0200269}
270
271
Victor Stinner74f65682019-03-15 15:08:05 +0100272int
273_PyWstrList_Append(_PyWstrList *list, const wchar_t *item)
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100274{
Victor Stinner74f65682019-03-15 15:08:05 +0100275 if (list->length == PY_SSIZE_T_MAX) {
276 /* lenght+1 would overflow */
277 return -1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100278 }
279
Victor Stinner74f65682019-03-15 15:08:05 +0100280 wchar_t *item2 = _PyMem_RawWcsdup(item);
281 if (item2 == NULL) {
282 return -1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100283 }
Victor Stinner74f65682019-03-15 15:08:05 +0100284
285 size_t size = (list->length + 1) * sizeof(list->items[0]);
286 wchar_t **items2 = (wchar_t **)PyMem_RawRealloc(list->items, size);
287 if (items2 == NULL) {
288 PyMem_RawFree(item2);
289 return -1;
290 }
291
292 items2[list->length] = item2;
293 list->items = items2;
294 list->length++;
295 return 0;
296}
297
298
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100299int
Victor Stinner74f65682019-03-15 15:08:05 +0100300_PyWstrList_Extend(_PyWstrList *list, const _PyWstrList *list2)
301{
302 for (Py_ssize_t i = 0; i < list2->length; i++) {
303 if (_PyWstrList_Append(list, list2->items[i])) {
304 return -1;
305 }
306 }
307 return 0;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100308}
309
310
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100311static int
312_PyWstrList_Find(_PyWstrList *list, const wchar_t *item)
313{
314 for (Py_ssize_t i = 0; i < list->length; i++) {
315 if (wcscmp(list->items[i], item) == 0) {
316 return 1;
317 }
318 }
319 return 0;
320}
321
322
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100323PyObject*
Victor Stinner74f65682019-03-15 15:08:05 +0100324_PyWstrList_AsList(const _PyWstrList *list)
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100325{
Victor Stinner74f65682019-03-15 15:08:05 +0100326 assert(_PyWstrList_CheckConsistency(list));
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100327
Victor Stinner74f65682019-03-15 15:08:05 +0100328 PyObject *pylist = PyList_New(list->length);
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100329 if (pylist == NULL) {
330 return NULL;
331 }
332
Victor Stinner74f65682019-03-15 15:08:05 +0100333 for (Py_ssize_t i = 0; i < list->length; i++) {
334 PyObject *item = PyUnicode_FromWideChar(list->items[i], -1);
335 if (item == NULL) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100336 Py_DECREF(pylist);
337 return NULL;
338 }
Victor Stinner74f65682019-03-15 15:08:05 +0100339 PyList_SET_ITEM(pylist, i, item);
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100340 }
341 return pylist;
342}
343
344
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100345/* --- Py_SetStandardStreamEncoding() ----------------------------- */
346
Victor Stinner124b9eb2018-08-29 01:29:06 +0200347/* Helper to allow an embedding application to override the normal
348 * mechanism that attempts to figure out an appropriate IO encoding
349 */
350
Victor Stinnerdfe0dc72018-08-29 11:47:29 +0200351static char *_Py_StandardStreamEncoding = NULL;
352static char *_Py_StandardStreamErrors = NULL;
Victor Stinner124b9eb2018-08-29 01:29:06 +0200353
354int
355Py_SetStandardStreamEncoding(const char *encoding, const char *errors)
356{
357 if (Py_IsInitialized()) {
358 /* This is too late to have any effect */
359 return -1;
360 }
361
362 int res = 0;
363
364 /* Py_SetStandardStreamEncoding() can be called before Py_Initialize(),
365 but Py_Initialize() can change the allocator. Use a known allocator
366 to be able to release the memory later. */
367 PyMemAllocatorEx old_alloc;
368 _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
369
370 /* Can't call PyErr_NoMemory() on errors, as Python hasn't been
371 * initialised yet.
372 *
373 * However, the raw memory allocators are initialised appropriately
374 * as C static variables, so _PyMem_RawStrdup is OK even though
375 * Py_Initialize hasn't been called yet.
376 */
377 if (encoding) {
Victor Stinner463b82a2019-05-01 01:36:13 +0200378 PyMem_RawFree(_Py_StandardStreamEncoding);
Victor Stinner124b9eb2018-08-29 01:29:06 +0200379 _Py_StandardStreamEncoding = _PyMem_RawStrdup(encoding);
380 if (!_Py_StandardStreamEncoding) {
381 res = -2;
382 goto done;
383 }
384 }
385 if (errors) {
Victor Stinner463b82a2019-05-01 01:36:13 +0200386 PyMem_RawFree(_Py_StandardStreamErrors);
Victor Stinner124b9eb2018-08-29 01:29:06 +0200387 _Py_StandardStreamErrors = _PyMem_RawStrdup(errors);
388 if (!_Py_StandardStreamErrors) {
Victor Stinner463b82a2019-05-01 01:36:13 +0200389 PyMem_RawFree(_Py_StandardStreamEncoding);
390 _Py_StandardStreamEncoding = NULL;
Victor Stinner124b9eb2018-08-29 01:29:06 +0200391 res = -3;
392 goto done;
393 }
394 }
395#ifdef MS_WINDOWS
396 if (_Py_StandardStreamEncoding) {
397 /* Overriding the stream encoding implies legacy streams */
398 Py_LegacyWindowsStdioFlag = 1;
399 }
400#endif
401
402done:
403 PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
404
405 return res;
406}
407
408
409void
410_Py_ClearStandardStreamEncoding(void)
411{
412 /* Use the same allocator than Py_SetStandardStreamEncoding() */
413 PyMemAllocatorEx old_alloc;
414 _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
415
416 /* We won't need them anymore. */
417 if (_Py_StandardStreamEncoding) {
418 PyMem_RawFree(_Py_StandardStreamEncoding);
419 _Py_StandardStreamEncoding = NULL;
420 }
421 if (_Py_StandardStreamErrors) {
422 PyMem_RawFree(_Py_StandardStreamErrors);
423 _Py_StandardStreamErrors = NULL;
424 }
425
426 PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
427}
428
429
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100430/* --- Py_GetArgcArgv() ------------------------------------------- */
431
432/* For Py_GetArgcArgv(); set by _Py_SetArgcArgv() */
Victor Stinner74f65682019-03-15 15:08:05 +0100433static _PyWstrList orig_argv = {.length = 0, .items = NULL};
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100434
435
436void
437_Py_ClearArgcArgv(void)
438{
439 PyMemAllocatorEx old_alloc;
440 _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
441
Victor Stinner74f65682019-03-15 15:08:05 +0100442 _PyWstrList_Clear(&orig_argv);
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100443
444 PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
445}
446
447
Victor Stinner4fffd382019-03-06 01:44:31 +0100448static int
Victor Stinner74f65682019-03-15 15:08:05 +0100449_Py_SetArgcArgv(Py_ssize_t argc, wchar_t * const *argv)
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100450{
Victor Stinner74f65682019-03-15 15:08:05 +0100451 const _PyWstrList argv_list = {.length = argc, .items = (wchar_t **)argv};
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100452 int res;
453
454 PyMemAllocatorEx old_alloc;
455 _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
456
Victor Stinner74f65682019-03-15 15:08:05 +0100457 res = _PyWstrList_Copy(&orig_argv, &argv_list);
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100458
459 PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
460 return res;
461}
462
463
464/* Make the *original* argc/argv available to other modules.
465 This is rare, but it is needed by the secureware extension. */
466void
467Py_GetArgcArgv(int *argc, wchar_t ***argv)
468{
Victor Stinner74f65682019-03-15 15:08:05 +0100469 *argc = (int)orig_argv.length;
470 *argv = orig_argv.items;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100471}
472
473
474/* --- _PyCoreConfig ---------------------------------------------- */
475
476#define DECODE_LOCALE_ERR(NAME, LEN) \
477 (((LEN) == -2) \
Victor Stinnerdb719752019-05-01 05:35:33 +0200478 ? _Py_INIT_ERR("cannot decode " NAME) \
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100479 : _Py_INIT_NO_MEMORY())
480
Victor Stinner6c785c02018-08-01 17:56:14 +0200481/* Free memory allocated in config, but don't clear all attributes */
482void
483_PyCoreConfig_Clear(_PyCoreConfig *config)
484{
485#define CLEAR(ATTR) \
486 do { \
487 PyMem_RawFree(ATTR); \
488 ATTR = NULL; \
489 } while (0)
Victor Stinner6c785c02018-08-01 17:56:14 +0200490
491 CLEAR(config->pycache_prefix);
492 CLEAR(config->module_search_path_env);
493 CLEAR(config->home);
494 CLEAR(config->program_name);
495 CLEAR(config->program);
496
Victor Stinner74f65682019-03-15 15:08:05 +0100497 _PyWstrList_Clear(&config->argv);
498 _PyWstrList_Clear(&config->warnoptions);
499 _PyWstrList_Clear(&config->xoptions);
500 _PyWstrList_Clear(&config->module_search_paths);
501 config->use_module_search_paths = 0;
Victor Stinner6c785c02018-08-01 17:56:14 +0200502
503 CLEAR(config->executable);
504 CLEAR(config->prefix);
505 CLEAR(config->base_prefix);
506 CLEAR(config->exec_prefix);
507#ifdef MS_WINDOWS
508 CLEAR(config->dll_path);
509#endif
510 CLEAR(config->base_exec_prefix);
Victor Stinnerdfe0dc72018-08-29 11:47:29 +0200511
Victor Stinnerb2457ef2018-08-29 13:25:36 +0200512 CLEAR(config->filesystem_encoding);
513 CLEAR(config->filesystem_errors);
Victor Stinnerdfe0dc72018-08-29 11:47:29 +0200514 CLEAR(config->stdio_encoding);
515 CLEAR(config->stdio_errors);
Victor Stinner4fffd382019-03-06 01:44:31 +0100516 CLEAR(config->run_command);
517 CLEAR(config->run_module);
518 CLEAR(config->run_filename);
Victor Stinnercb9fbd32019-05-01 23:51:56 -0400519 CLEAR(config->check_hash_pycs_mode);
Victor Stinner6c785c02018-08-01 17:56:14 +0200520#undef CLEAR
Victor Stinner6c785c02018-08-01 17:56:14 +0200521}
522
523
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200524/* Copy str into *config_str (duplicate the string) */
525_PyInitError
Victor Stinner709d23d2019-05-02 14:56:30 -0400526_PyCoreConfig_SetString(wchar_t **config_str, const wchar_t *str)
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200527{
528 wchar_t *str2;
529 if (str != NULL) {
530 str2 = _PyMem_RawWcsdup(str);
531 if (str2 == NULL) {
532 return _Py_INIT_NO_MEMORY();
533 }
534 }
535 else {
536 str2 = NULL;
537 }
538 PyMem_RawFree(*config_str);
539 *config_str = str2;
540 return _Py_INIT_OK();
541}
542
543
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200544static _PyInitError
Victor Stinner709d23d2019-05-02 14:56:30 -0400545_PyCoreConfig_DecodeLocaleErr(wchar_t **config_str, const char *str,
546 const char *decode_err_msg)
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200547{
Victor Stinner70005ac2019-05-02 15:25:34 -0400548 _PyInitError err = _Py_PreInitialize(NULL);
549 if (_Py_INIT_FAILED(err)) {
550 return err;
551 }
552
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200553 wchar_t *str2;
554 if (str != NULL) {
555 size_t len;
556 str2 = Py_DecodeLocale(str, &len);
557 if (str2 == NULL) {
558 if (len == (size_t)-2) {
559 return _Py_INIT_ERR(decode_err_msg);
560 }
561 else {
562 return _Py_INIT_NO_MEMORY();
563 }
564 }
565 }
566 else {
567 str2 = NULL;
568 }
569 PyMem_RawFree(*config_str);
570 *config_str = str2;
571 return _Py_INIT_OK();
572}
573
574
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200575#define CONFIG_DECODE_LOCALE(config_str, str, NAME) \
Victor Stinner709d23d2019-05-02 14:56:30 -0400576 _PyCoreConfig_DecodeLocaleErr(config_str, str, "cannot decode " NAME)
577
578
Victor Stinner70005ac2019-05-02 15:25:34 -0400579/* Decode str using Py_DecodeLocale() and set the result into *config_str.
580 Pre-initialize Python if needed to ensure that encodings are properly
581 configured. */
Victor Stinner709d23d2019-05-02 14:56:30 -0400582_PyInitError
583_PyCoreConfig_DecodeLocale(wchar_t **config_str, const char *str)
584{
585 return CONFIG_DECODE_LOCALE(config_str, str, "string");
586}
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200587
588
589_PyInitError
Victor Stinner6c785c02018-08-01 17:56:14 +0200590_PyCoreConfig_Copy(_PyCoreConfig *config, const _PyCoreConfig *config2)
591{
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200592 _PyInitError err;
Victor Stinner6c785c02018-08-01 17:56:14 +0200593 _PyCoreConfig_Clear(config);
594
595#define COPY_ATTR(ATTR) config->ATTR = config2->ATTR
Victor Stinner124b9eb2018-08-29 01:29:06 +0200596#define COPY_WSTR_ATTR(ATTR) \
Victor Stinner6c785c02018-08-01 17:56:14 +0200597 do { \
Victor Stinner709d23d2019-05-02 14:56:30 -0400598 err = _PyCoreConfig_SetString(&config->ATTR, config2->ATTR); \
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200599 if (_Py_INIT_FAILED(err)) { \
600 return err; \
Victor Stinner6c785c02018-08-01 17:56:14 +0200601 } \
602 } while (0)
Victor Stinner74f65682019-03-15 15:08:05 +0100603#define COPY_WSTRLIST(LIST) \
Victor Stinner6c785c02018-08-01 17:56:14 +0200604 do { \
Victor Stinner74f65682019-03-15 15:08:05 +0100605 if (_PyWstrList_Copy(&config->LIST, &config2->LIST) < 0 ) { \
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200606 return _Py_INIT_NO_MEMORY(); \
Victor Stinner6c785c02018-08-01 17:56:14 +0200607 } \
Victor Stinner6c785c02018-08-01 17:56:14 +0200608 } while (0)
609
Victor Stinner20004952019-03-26 02:31:11 +0100610 COPY_ATTR(isolated);
611 COPY_ATTR(use_environment);
612 COPY_ATTR(dev_mode);
Victor Stinner6c785c02018-08-01 17:56:14 +0200613 COPY_ATTR(install_signal_handlers);
Victor Stinner6c785c02018-08-01 17:56:14 +0200614 COPY_ATTR(use_hash_seed);
615 COPY_ATTR(hash_seed);
616 COPY_ATTR(_install_importlib);
Victor Stinner6c785c02018-08-01 17:56:14 +0200617 COPY_ATTR(faulthandler);
618 COPY_ATTR(tracemalloc);
619 COPY_ATTR(import_time);
620 COPY_ATTR(show_ref_count);
621 COPY_ATTR(show_alloc_count);
622 COPY_ATTR(dump_refs);
623 COPY_ATTR(malloc_stats);
624
Victor Stinner124b9eb2018-08-29 01:29:06 +0200625 COPY_WSTR_ATTR(pycache_prefix);
626 COPY_WSTR_ATTR(module_search_path_env);
627 COPY_WSTR_ATTR(home);
628 COPY_WSTR_ATTR(program_name);
629 COPY_WSTR_ATTR(program);
Victor Stinner6c785c02018-08-01 17:56:14 +0200630
Victor Stinnerae239f62019-05-16 17:02:56 +0200631 COPY_ATTR(parse_argv);
Victor Stinner74f65682019-03-15 15:08:05 +0100632 COPY_WSTRLIST(argv);
633 COPY_WSTRLIST(warnoptions);
634 COPY_WSTRLIST(xoptions);
635 COPY_WSTRLIST(module_search_paths);
636 COPY_ATTR(use_module_search_paths);
Victor Stinner6c785c02018-08-01 17:56:14 +0200637
Victor Stinner124b9eb2018-08-29 01:29:06 +0200638 COPY_WSTR_ATTR(executable);
639 COPY_WSTR_ATTR(prefix);
640 COPY_WSTR_ATTR(base_prefix);
641 COPY_WSTR_ATTR(exec_prefix);
Victor Stinner6c785c02018-08-01 17:56:14 +0200642#ifdef MS_WINDOWS
Victor Stinner124b9eb2018-08-29 01:29:06 +0200643 COPY_WSTR_ATTR(dll_path);
Victor Stinner6c785c02018-08-01 17:56:14 +0200644#endif
Victor Stinner124b9eb2018-08-29 01:29:06 +0200645 COPY_WSTR_ATTR(base_exec_prefix);
Victor Stinner6c785c02018-08-01 17:56:14 +0200646
Victor Stinner6c785c02018-08-01 17:56:14 +0200647 COPY_ATTR(site_import);
648 COPY_ATTR(bytes_warning);
649 COPY_ATTR(inspect);
650 COPY_ATTR(interactive);
651 COPY_ATTR(optimization_level);
652 COPY_ATTR(parser_debug);
653 COPY_ATTR(write_bytecode);
654 COPY_ATTR(verbose);
655 COPY_ATTR(quiet);
656 COPY_ATTR(user_site_directory);
Victor Stinner54b43bb2019-05-16 18:30:15 +0200657 COPY_ATTR(configure_c_stdio);
Victor Stinner6c785c02018-08-01 17:56:14 +0200658 COPY_ATTR(buffered_stdio);
Victor Stinner709d23d2019-05-02 14:56:30 -0400659 COPY_WSTR_ATTR(filesystem_encoding);
660 COPY_WSTR_ATTR(filesystem_errors);
661 COPY_WSTR_ATTR(stdio_encoding);
662 COPY_WSTR_ATTR(stdio_errors);
Victor Stinner6c785c02018-08-01 17:56:14 +0200663#ifdef MS_WINDOWS
Victor Stinner6c785c02018-08-01 17:56:14 +0200664 COPY_ATTR(legacy_windows_stdio);
665#endif
Victor Stinner62be7632019-03-01 13:10:14 +0100666 COPY_ATTR(skip_source_first_line);
667 COPY_WSTR_ATTR(run_command);
668 COPY_WSTR_ATTR(run_module);
669 COPY_WSTR_ATTR(run_filename);
Victor Stinnercb9fbd32019-05-01 23:51:56 -0400670 COPY_WSTR_ATTR(check_hash_pycs_mode);
Victor Stinner9ef5dca2019-05-16 17:38:16 +0200671 COPY_ATTR(pathconfig_warnings);
672 COPY_ATTR(_init_main);
Victor Stinner6c785c02018-08-01 17:56:14 +0200673
674#undef COPY_ATTR
Victor Stinner124b9eb2018-08-29 01:29:06 +0200675#undef COPY_WSTR_ATTR
Victor Stinner6c785c02018-08-01 17:56:14 +0200676#undef COPY_WSTRLIST
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200677 return _Py_INIT_OK();
Victor Stinner6c785c02018-08-01 17:56:14 +0200678}
679
680
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100681static PyObject *
682_PyCoreConfig_AsDict(const _PyCoreConfig *config)
683{
684 PyObject *dict;
685
686 dict = PyDict_New();
687 if (dict == NULL) {
688 return NULL;
689 }
690
691#define SET_ITEM(KEY, EXPR) \
692 do { \
693 PyObject *obj = (EXPR); \
694 if (obj == NULL) { \
695 goto fail; \
696 } \
697 int res = PyDict_SetItemString(dict, (KEY), obj); \
698 Py_DECREF(obj); \
699 if (res < 0) { \
700 goto fail; \
701 } \
702 } while (0)
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100703#define SET_ITEM_INT(ATTR) \
704 SET_ITEM(#ATTR, PyLong_FromLong(config->ATTR))
705#define SET_ITEM_UINT(ATTR) \
706 SET_ITEM(#ATTR, PyLong_FromUnsignedLong(config->ATTR))
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100707#define FROM_WSTRING(STR) \
708 ((STR != NULL) ? \
709 PyUnicode_FromWideChar(STR, -1) \
710 : (Py_INCREF(Py_None), Py_None))
711#define SET_ITEM_WSTR(ATTR) \
712 SET_ITEM(#ATTR, FROM_WSTRING(config->ATTR))
713#define SET_ITEM_WSTRLIST(LIST) \
714 SET_ITEM(#LIST, _PyWstrList_AsList(&config->LIST))
715
716 SET_ITEM_INT(isolated);
717 SET_ITEM_INT(use_environment);
718 SET_ITEM_INT(dev_mode);
719 SET_ITEM_INT(install_signal_handlers);
720 SET_ITEM_INT(use_hash_seed);
721 SET_ITEM_UINT(hash_seed);
722 SET_ITEM_INT(faulthandler);
723 SET_ITEM_INT(tracemalloc);
724 SET_ITEM_INT(import_time);
725 SET_ITEM_INT(show_ref_count);
726 SET_ITEM_INT(show_alloc_count);
727 SET_ITEM_INT(dump_refs);
728 SET_ITEM_INT(malloc_stats);
Victor Stinner709d23d2019-05-02 14:56:30 -0400729 SET_ITEM_WSTR(filesystem_encoding);
730 SET_ITEM_WSTR(filesystem_errors);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100731 SET_ITEM_WSTR(pycache_prefix);
732 SET_ITEM_WSTR(program_name);
Victor Stinnerae239f62019-05-16 17:02:56 +0200733 SET_ITEM_INT(parse_argv);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100734 SET_ITEM_WSTRLIST(argv);
735 SET_ITEM_WSTR(program);
736 SET_ITEM_WSTRLIST(xoptions);
737 SET_ITEM_WSTRLIST(warnoptions);
738 SET_ITEM_WSTR(module_search_path_env);
739 SET_ITEM_WSTR(home);
740 SET_ITEM_WSTRLIST(module_search_paths);
741 SET_ITEM_WSTR(executable);
742 SET_ITEM_WSTR(prefix);
743 SET_ITEM_WSTR(base_prefix);
744 SET_ITEM_WSTR(exec_prefix);
745 SET_ITEM_WSTR(base_exec_prefix);
746#ifdef MS_WINDOWS
747 SET_ITEM_WSTR(dll_path);
748#endif
749 SET_ITEM_INT(site_import);
750 SET_ITEM_INT(bytes_warning);
751 SET_ITEM_INT(inspect);
752 SET_ITEM_INT(interactive);
753 SET_ITEM_INT(optimization_level);
754 SET_ITEM_INT(parser_debug);
755 SET_ITEM_INT(write_bytecode);
756 SET_ITEM_INT(verbose);
757 SET_ITEM_INT(quiet);
758 SET_ITEM_INT(user_site_directory);
Victor Stinner54b43bb2019-05-16 18:30:15 +0200759 SET_ITEM_INT(configure_c_stdio);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100760 SET_ITEM_INT(buffered_stdio);
Victor Stinner709d23d2019-05-02 14:56:30 -0400761 SET_ITEM_WSTR(stdio_encoding);
762 SET_ITEM_WSTR(stdio_errors);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100763#ifdef MS_WINDOWS
764 SET_ITEM_INT(legacy_windows_stdio);
765#endif
766 SET_ITEM_INT(skip_source_first_line);
767 SET_ITEM_WSTR(run_command);
768 SET_ITEM_WSTR(run_module);
769 SET_ITEM_WSTR(run_filename);
770 SET_ITEM_INT(_install_importlib);
Victor Stinnercb9fbd32019-05-01 23:51:56 -0400771 SET_ITEM_WSTR(check_hash_pycs_mode);
Victor Stinner9ef5dca2019-05-16 17:38:16 +0200772 SET_ITEM_INT(pathconfig_warnings);
773 SET_ITEM_INT(_init_main);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100774
775 return dict;
776
777fail:
778 Py_DECREF(dict);
779 return NULL;
780
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100781#undef FROM_WSTRING
782#undef SET_ITEM
783#undef SET_ITEM_INT
784#undef SET_ITEM_UINT
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100785#undef SET_ITEM_WSTR
786#undef SET_ITEM_WSTRLIST
787}
788
789
Victor Stinnerf78a5e92019-03-26 00:03:15 +0100790static const char*
Victor Stinner6c785c02018-08-01 17:56:14 +0200791_PyCoreConfig_GetEnv(const _PyCoreConfig *config, const char *name)
792{
Victor Stinner20004952019-03-26 02:31:11 +0100793 return _Py_GetEnv(config->use_environment, name);
Victor Stinner6c785c02018-08-01 17:56:14 +0200794}
795
796
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100797/* Get a copy of the environment variable as wchar_t*.
798 Return 0 on success, but *dest can be NULL.
799 Return -1 on memory allocation failure. Return -2 on decoding error. */
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200800static _PyInitError
Victor Stinner6c785c02018-08-01 17:56:14 +0200801_PyCoreConfig_GetEnvDup(const _PyCoreConfig *config,
802 wchar_t **dest,
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200803 wchar_t *wname, char *name,
804 const char *decode_err_msg)
Victor Stinner6c785c02018-08-01 17:56:14 +0200805{
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200806 assert(*dest == NULL);
Victor Stinner20004952019-03-26 02:31:11 +0100807 assert(config->use_environment >= 0);
Victor Stinner6c785c02018-08-01 17:56:14 +0200808
Victor Stinner20004952019-03-26 02:31:11 +0100809 if (!config->use_environment) {
Victor Stinner6c785c02018-08-01 17:56:14 +0200810 *dest = NULL;
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200811 return _Py_INIT_OK();
Victor Stinner6c785c02018-08-01 17:56:14 +0200812 }
813
814#ifdef MS_WINDOWS
815 const wchar_t *var = _wgetenv(wname);
816 if (!var || var[0] == '\0') {
817 *dest = NULL;
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200818 return _Py_INIT_OK();
Victor Stinner6c785c02018-08-01 17:56:14 +0200819 }
820
Victor Stinner709d23d2019-05-02 14:56:30 -0400821 return _PyCoreConfig_SetString(dest, var);
Victor Stinner6c785c02018-08-01 17:56:14 +0200822#else
823 const char *var = getenv(name);
824 if (!var || var[0] == '\0') {
825 *dest = NULL;
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200826 return _Py_INIT_OK();
Victor Stinner6c785c02018-08-01 17:56:14 +0200827 }
828
Victor Stinner709d23d2019-05-02 14:56:30 -0400829 return _PyCoreConfig_DecodeLocaleErr(dest, var, decode_err_msg);
Victor Stinner6c785c02018-08-01 17:56:14 +0200830#endif
Victor Stinner6c785c02018-08-01 17:56:14 +0200831}
832
833
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200834#define CONFIG_GET_ENV_DUP(CONFIG, DEST, WNAME, NAME) \
835 _PyCoreConfig_GetEnvDup(CONFIG, DEST, WNAME, NAME, "cannot decode " NAME)
836
837
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100838static void
Victor Stinner6c785c02018-08-01 17:56:14 +0200839_PyCoreConfig_GetGlobalConfig(_PyCoreConfig *config)
840{
841#define COPY_FLAG(ATTR, VALUE) \
842 if (config->ATTR == -1) { \
843 config->ATTR = VALUE; \
844 }
845#define COPY_NOT_FLAG(ATTR, VALUE) \
846 if (config->ATTR == -1) { \
847 config->ATTR = !(VALUE); \
848 }
849
Victor Stinner20004952019-03-26 02:31:11 +0100850 COPY_FLAG(isolated, Py_IsolatedFlag);
851 COPY_NOT_FLAG(use_environment, Py_IgnoreEnvironmentFlag);
Victor Stinner6c785c02018-08-01 17:56:14 +0200852 COPY_FLAG(bytes_warning, Py_BytesWarningFlag);
853 COPY_FLAG(inspect, Py_InspectFlag);
854 COPY_FLAG(interactive, Py_InteractiveFlag);
855 COPY_FLAG(optimization_level, Py_OptimizeFlag);
856 COPY_FLAG(parser_debug, Py_DebugFlag);
857 COPY_FLAG(verbose, Py_VerboseFlag);
858 COPY_FLAG(quiet, Py_QuietFlag);
859#ifdef MS_WINDOWS
Victor Stinner6c785c02018-08-01 17:56:14 +0200860 COPY_FLAG(legacy_windows_stdio, Py_LegacyWindowsStdioFlag);
861#endif
Victor Stinner9ef5dca2019-05-16 17:38:16 +0200862 COPY_NOT_FLAG(pathconfig_warnings, Py_FrozenFlag);
Victor Stinner6c785c02018-08-01 17:56:14 +0200863
Victor Stinner6c785c02018-08-01 17:56:14 +0200864 COPY_NOT_FLAG(buffered_stdio, Py_UnbufferedStdioFlag);
865 COPY_NOT_FLAG(site_import, Py_NoSiteFlag);
866 COPY_NOT_FLAG(write_bytecode, Py_DontWriteBytecodeFlag);
867 COPY_NOT_FLAG(user_site_directory, Py_NoUserSiteDirectory);
868
Victor Stinner6c785c02018-08-01 17:56:14 +0200869#undef COPY_FLAG
870#undef COPY_NOT_FLAG
871}
872
873
874/* Set Py_xxx global configuration variables from 'config' configuration. */
Victor Stinnerf8ba6f52019-03-26 16:58:50 +0100875static void
Victor Stinner6c785c02018-08-01 17:56:14 +0200876_PyCoreConfig_SetGlobalConfig(const _PyCoreConfig *config)
877{
878#define COPY_FLAG(ATTR, VAR) \
879 if (config->ATTR != -1) { \
880 VAR = config->ATTR; \
881 }
882#define COPY_NOT_FLAG(ATTR, VAR) \
883 if (config->ATTR != -1) { \
884 VAR = !config->ATTR; \
885 }
886
Victor Stinner20004952019-03-26 02:31:11 +0100887 COPY_FLAG(isolated, Py_IsolatedFlag);
888 COPY_NOT_FLAG(use_environment, Py_IgnoreEnvironmentFlag);
Victor Stinner6c785c02018-08-01 17:56:14 +0200889 COPY_FLAG(bytes_warning, Py_BytesWarningFlag);
890 COPY_FLAG(inspect, Py_InspectFlag);
891 COPY_FLAG(interactive, Py_InteractiveFlag);
892 COPY_FLAG(optimization_level, Py_OptimizeFlag);
893 COPY_FLAG(parser_debug, Py_DebugFlag);
894 COPY_FLAG(verbose, Py_VerboseFlag);
895 COPY_FLAG(quiet, Py_QuietFlag);
896#ifdef MS_WINDOWS
Victor Stinner6c785c02018-08-01 17:56:14 +0200897 COPY_FLAG(legacy_windows_stdio, Py_LegacyWindowsStdioFlag);
898#endif
Victor Stinner9ef5dca2019-05-16 17:38:16 +0200899 COPY_NOT_FLAG(pathconfig_warnings, Py_FrozenFlag);
Victor Stinner6c785c02018-08-01 17:56:14 +0200900
Victor Stinner6c785c02018-08-01 17:56:14 +0200901 COPY_NOT_FLAG(buffered_stdio, Py_UnbufferedStdioFlag);
902 COPY_NOT_FLAG(site_import, Py_NoSiteFlag);
903 COPY_NOT_FLAG(write_bytecode, Py_DontWriteBytecodeFlag);
904 COPY_NOT_FLAG(user_site_directory, Py_NoUserSiteDirectory);
905
Victor Stinner6c785c02018-08-01 17:56:14 +0200906 /* Random or non-zero hash seed */
907 Py_HashRandomizationFlag = (config->use_hash_seed == 0 ||
908 config->hash_seed != 0);
909
910#undef COPY_FLAG
911#undef COPY_NOT_FLAG
912}
913
914
915/* Get the program name: use PYTHONEXECUTABLE and __PYVENV_LAUNCHER__
916 environment variables on macOS if available. */
917static _PyInitError
918config_init_program_name(_PyCoreConfig *config)
919{
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200920 _PyInitError err;
Victor Stinner5a953fd2018-08-03 22:49:07 +0200921 assert(config->program_name == NULL);
922
Victor Stinner6c785c02018-08-01 17:56:14 +0200923 /* If Py_SetProgramName() was called, use its value */
924 const wchar_t *program_name = _Py_path_config.program_name;
925 if (program_name != NULL) {
926 config->program_name = _PyMem_RawWcsdup(program_name);
927 if (config->program_name == NULL) {
928 return _Py_INIT_NO_MEMORY();
929 }
930 return _Py_INIT_OK();
931 }
932
933#ifdef __APPLE__
934 /* On MacOS X, when the Python interpreter is embedded in an
935 application bundle, it gets executed by a bootstrapping script
936 that does os.execve() with an argv[0] that's different from the
937 actual Python executable. This is needed to keep the Finder happy,
938 or rather, to work around Apple's overly strict requirements of
939 the process name. However, we still need a usable sys.executable,
940 so the actual executable path is passed in an environment variable.
941 See Lib/plat-mac/bundlebuiler.py for details about the bootstrap
942 script. */
943 const char *p = _PyCoreConfig_GetEnv(config, "PYTHONEXECUTABLE");
944 if (p != NULL) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200945 err = CONFIG_DECODE_LOCALE(&config->program_name, p,
946 "PYTHONEXECUTABLE environment variable");
947 if (_Py_INIT_FAILED(err)) {
948 return err;
Victor Stinner6c785c02018-08-01 17:56:14 +0200949 }
Victor Stinner6c785c02018-08-01 17:56:14 +0200950 return _Py_INIT_OK();
951 }
952#ifdef WITH_NEXT_FRAMEWORK
953 else {
954 const char* pyvenv_launcher = getenv("__PYVENV_LAUNCHER__");
955 if (pyvenv_launcher && *pyvenv_launcher) {
956 /* Used by Mac/Tools/pythonw.c to forward
957 * the argv0 of the stub executable
958 */
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200959 err = CONFIG_DECODE_LOCALE(&config->program_name, pyvenv_launcher,
960 "__PYVENV_LAUNCHER__ environment variable");
961 if (_Py_INIT_FAILED(err)) {
962 return err;
Victor Stinner6c785c02018-08-01 17:56:14 +0200963 }
Victor Stinner6c785c02018-08-01 17:56:14 +0200964 return _Py_INIT_OK();
965 }
966 }
967#endif /* WITH_NEXT_FRAMEWORK */
968#endif /* __APPLE__ */
969
970 /* Use argv[0] by default, if available */
971 if (config->program != NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -0400972 err = _PyCoreConfig_SetString(&config->program_name, config->program);
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200973 if (_Py_INIT_FAILED(err)) {
974 return err;
Victor Stinner6c785c02018-08-01 17:56:14 +0200975 }
976 return _Py_INIT_OK();
977 }
978
979 /* Last fall back: hardcoded string */
980#ifdef MS_WINDOWS
981 const wchar_t *default_program_name = L"python";
982#else
983 const wchar_t *default_program_name = L"python3";
984#endif
Victor Stinner709d23d2019-05-02 14:56:30 -0400985 err = _PyCoreConfig_SetString(&config->program_name, default_program_name);
Victor Stinner1a9f0d82019-05-01 15:22:52 +0200986 if (_Py_INIT_FAILED(err)) {
987 return err;
Victor Stinner6c785c02018-08-01 17:56:14 +0200988 }
989 return _Py_INIT_OK();
990}
991
Steve Dower177a41a2018-11-17 20:41:48 -0800992static _PyInitError
993config_init_executable(_PyCoreConfig *config)
994{
995 assert(config->executable == NULL);
996
997 /* If Py_SetProgramFullPath() was called, use its value */
998 const wchar_t *program_full_path = _Py_path_config.program_full_path;
999 if (program_full_path != NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001000 _PyInitError err = _PyCoreConfig_SetString(&config->executable,
1001 program_full_path);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001002 if (_Py_INIT_FAILED(err)) {
1003 return err;
Steve Dower177a41a2018-11-17 20:41:48 -08001004 }
1005 return _Py_INIT_OK();
1006 }
Steve Dower177a41a2018-11-17 20:41:48 -08001007 return _Py_INIT_OK();
1008}
Victor Stinner6c785c02018-08-01 17:56:14 +02001009
Victor Stinner4fffd382019-03-06 01:44:31 +01001010
Victor Stinner6c785c02018-08-01 17:56:14 +02001011static const wchar_t*
1012config_get_xoption(const _PyCoreConfig *config, wchar_t *name)
1013{
Victor Stinner74f65682019-03-15 15:08:05 +01001014 return _Py_get_xoption(&config->xoptions, name);
Victor Stinner6c785c02018-08-01 17:56:14 +02001015}
1016
1017
1018static _PyInitError
1019config_init_home(_PyCoreConfig *config)
1020{
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001021 assert(config->home == NULL);
Victor Stinner6c785c02018-08-01 17:56:14 +02001022
1023 /* If Py_SetPythonHome() was called, use its value */
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001024 wchar_t *home = _Py_path_config.home;
Victor Stinner6c785c02018-08-01 17:56:14 +02001025 if (home) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001026 _PyInitError err = _PyCoreConfig_SetString(&config->home, home);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001027 if (_Py_INIT_FAILED(err)) {
1028 return err;
Victor Stinner6c785c02018-08-01 17:56:14 +02001029 }
1030 return _Py_INIT_OK();
1031 }
1032
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001033 return CONFIG_GET_ENV_DUP(config, &config->home,
1034 L"PYTHONHOME", "PYTHONHOME");
Victor Stinner6c785c02018-08-01 17:56:14 +02001035}
1036
1037
1038static _PyInitError
1039config_init_hash_seed(_PyCoreConfig *config)
1040{
1041 const char *seed_text = _PyCoreConfig_GetEnv(config, "PYTHONHASHSEED");
1042
1043 Py_BUILD_ASSERT(sizeof(_Py_HashSecret_t) == sizeof(_Py_HashSecret.uc));
1044 /* Convert a text seed to a numeric one */
1045 if (seed_text && strcmp(seed_text, "random") != 0) {
1046 const char *endptr = seed_text;
1047 unsigned long seed;
1048 errno = 0;
1049 seed = strtoul(seed_text, (char **)&endptr, 10);
1050 if (*endptr != '\0'
1051 || seed > 4294967295UL
1052 || (errno == ERANGE && seed == ULONG_MAX))
1053 {
Victor Stinnerdb719752019-05-01 05:35:33 +02001054 return _Py_INIT_ERR("PYTHONHASHSEED must be \"random\" "
1055 "or an integer in range [0; 4294967295]");
Victor Stinner6c785c02018-08-01 17:56:14 +02001056 }
1057 /* Use a specific hash */
1058 config->use_hash_seed = 1;
1059 config->hash_seed = seed;
1060 }
1061 else {
1062 /* Use a random hash */
1063 config->use_hash_seed = 0;
1064 config->hash_seed = 0;
1065 }
1066 return _Py_INIT_OK();
1067}
1068
1069
Victor Stinner6c785c02018-08-01 17:56:14 +02001070static int
1071config_wstr_to_int(const wchar_t *wstr, int *result)
1072{
1073 const wchar_t *endptr = wstr;
1074 errno = 0;
1075 long value = wcstol(wstr, (wchar_t **)&endptr, 10);
1076 if (*endptr != '\0' || errno == ERANGE) {
1077 return -1;
1078 }
1079 if (value < INT_MIN || value > INT_MAX) {
1080 return -1;
1081 }
1082
1083 *result = (int)value;
1084 return 0;
1085}
1086
1087
Victor Stinner6c785c02018-08-01 17:56:14 +02001088static _PyInitError
1089config_read_env_vars(_PyCoreConfig *config)
1090{
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001091 _PyInitError err;
Victor Stinner20004952019-03-26 02:31:11 +01001092 int use_env = config->use_environment;
Victor Stinner5a02e0d2019-03-05 12:32:09 +01001093
Victor Stinner6c785c02018-08-01 17:56:14 +02001094 /* Get environment variables */
Victor Stinnerf78a5e92019-03-26 00:03:15 +01001095 _Py_get_env_flag(use_env, &config->parser_debug, "PYTHONDEBUG");
1096 _Py_get_env_flag(use_env, &config->verbose, "PYTHONVERBOSE");
1097 _Py_get_env_flag(use_env, &config->optimization_level, "PYTHONOPTIMIZE");
1098 _Py_get_env_flag(use_env, &config->inspect, "PYTHONINSPECT");
Victor Stinner6c785c02018-08-01 17:56:14 +02001099
1100 int dont_write_bytecode = 0;
Victor Stinnerf78a5e92019-03-26 00:03:15 +01001101 _Py_get_env_flag(use_env, &dont_write_bytecode, "PYTHONDONTWRITEBYTECODE");
Victor Stinner6c785c02018-08-01 17:56:14 +02001102 if (dont_write_bytecode) {
1103 config->write_bytecode = 0;
1104 }
1105
1106 int no_user_site_directory = 0;
Victor Stinnerf78a5e92019-03-26 00:03:15 +01001107 _Py_get_env_flag(use_env, &no_user_site_directory, "PYTHONNOUSERSITE");
Victor Stinner6c785c02018-08-01 17:56:14 +02001108 if (no_user_site_directory) {
1109 config->user_site_directory = 0;
1110 }
1111
1112 int unbuffered_stdio = 0;
Victor Stinnerf78a5e92019-03-26 00:03:15 +01001113 _Py_get_env_flag(use_env, &unbuffered_stdio, "PYTHONUNBUFFERED");
Victor Stinner6c785c02018-08-01 17:56:14 +02001114 if (unbuffered_stdio) {
1115 config->buffered_stdio = 0;
1116 }
1117
1118#ifdef MS_WINDOWS
Victor Stinnerf78a5e92019-03-26 00:03:15 +01001119 _Py_get_env_flag(use_env, &config->legacy_windows_stdio,
Victor Stinner6c785c02018-08-01 17:56:14 +02001120 "PYTHONLEGACYWINDOWSSTDIO");
1121#endif
1122
Victor Stinner6c785c02018-08-01 17:56:14 +02001123 if (_PyCoreConfig_GetEnv(config, "PYTHONDUMPREFS")) {
1124 config->dump_refs = 1;
1125 }
1126 if (_PyCoreConfig_GetEnv(config, "PYTHONMALLOCSTATS")) {
1127 config->malloc_stats = 1;
1128 }
1129
Victor Stinner4a1468e2019-03-20 03:11:38 +01001130 if (config->module_search_path_env == NULL) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001131 err = CONFIG_GET_ENV_DUP(config, &config->module_search_path_env,
1132 L"PYTHONPATH", "PYTHONPATH");
1133 if (_Py_INIT_FAILED(err)) {
1134 return err;
Victor Stinner4a1468e2019-03-20 03:11:38 +01001135 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001136 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001137
1138 if (config->use_hash_seed < 0) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001139 err = config_init_hash_seed(config);
Victor Stinner6c785c02018-08-01 17:56:14 +02001140 if (_Py_INIT_FAILED(err)) {
1141 return err;
1142 }
1143 }
1144
1145 return _Py_INIT_OK();
1146}
1147
1148
1149static _PyInitError
1150config_init_tracemalloc(_PyCoreConfig *config)
1151{
1152 int nframe;
1153 int valid;
1154
1155 const char *env = _PyCoreConfig_GetEnv(config, "PYTHONTRACEMALLOC");
1156 if (env) {
Victor Stinner5a02e0d2019-03-05 12:32:09 +01001157 if (!_Py_str_to_int(env, &nframe)) {
Victor Stinner6c785c02018-08-01 17:56:14 +02001158 valid = (nframe >= 0);
1159 }
1160 else {
1161 valid = 0;
1162 }
1163 if (!valid) {
Victor Stinnerdb719752019-05-01 05:35:33 +02001164 return _Py_INIT_ERR("PYTHONTRACEMALLOC: invalid number of frames");
Victor Stinner6c785c02018-08-01 17:56:14 +02001165 }
1166 config->tracemalloc = nframe;
1167 }
1168
1169 const wchar_t *xoption = config_get_xoption(config, L"tracemalloc");
1170 if (xoption) {
1171 const wchar_t *sep = wcschr(xoption, L'=');
1172 if (sep) {
1173 if (!config_wstr_to_int(sep + 1, &nframe)) {
1174 valid = (nframe >= 0);
1175 }
1176 else {
1177 valid = 0;
1178 }
1179 if (!valid) {
Victor Stinnerdb719752019-05-01 05:35:33 +02001180 return _Py_INIT_ERR("-X tracemalloc=NFRAME: "
1181 "invalid number of frames");
Victor Stinner6c785c02018-08-01 17:56:14 +02001182 }
1183 }
1184 else {
1185 /* -X tracemalloc behaves as -X tracemalloc=1 */
1186 nframe = 1;
1187 }
1188 config->tracemalloc = nframe;
1189 }
1190 return _Py_INIT_OK();
1191}
1192
1193
1194static _PyInitError
1195config_init_pycache_prefix(_PyCoreConfig *config)
1196{
1197 assert(config->pycache_prefix == NULL);
1198
1199 const wchar_t *xoption = config_get_xoption(config, L"pycache_prefix");
1200 if (xoption) {
1201 const wchar_t *sep = wcschr(xoption, L'=');
1202 if (sep && wcslen(sep) > 1) {
1203 config->pycache_prefix = _PyMem_RawWcsdup(sep + 1);
1204 if (config->pycache_prefix == NULL) {
1205 return _Py_INIT_NO_MEMORY();
1206 }
1207 }
1208 else {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001209 // PYTHONPYCACHEPREFIX env var ignored
1210 // if "-X pycache_prefix=" option is used
Victor Stinner6c785c02018-08-01 17:56:14 +02001211 config->pycache_prefix = NULL;
1212 }
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001213 return _Py_INIT_OK();
Victor Stinner6c785c02018-08-01 17:56:14 +02001214 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001215
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001216 return CONFIG_GET_ENV_DUP(config, &config->pycache_prefix,
1217 L"PYTHONPYCACHEPREFIX",
1218 "PYTHONPYCACHEPREFIX");
Victor Stinner6c785c02018-08-01 17:56:14 +02001219}
1220
1221
1222static _PyInitError
1223config_read_complex_options(_PyCoreConfig *config)
1224{
1225 /* More complex options configured by env var and -X option */
1226 if (config->faulthandler < 0) {
1227 if (_PyCoreConfig_GetEnv(config, "PYTHONFAULTHANDLER")
1228 || config_get_xoption(config, L"faulthandler")) {
1229 config->faulthandler = 1;
1230 }
1231 }
1232 if (_PyCoreConfig_GetEnv(config, "PYTHONPROFILEIMPORTTIME")
1233 || config_get_xoption(config, L"importtime")) {
1234 config->import_time = 1;
1235 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001236
1237 _PyInitError err;
1238 if (config->tracemalloc < 0) {
1239 err = config_init_tracemalloc(config);
1240 if (_Py_INIT_FAILED(err)) {
1241 return err;
1242 }
1243 }
1244
1245 if (config->pycache_prefix == NULL) {
1246 err = config_init_pycache_prefix(config);
1247 if (_Py_INIT_FAILED(err)) {
1248 return err;
1249 }
1250 }
1251 return _Py_INIT_OK();
1252}
1253
1254
Victor Stinner709d23d2019-05-02 14:56:30 -04001255static const wchar_t *
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001256config_get_stdio_errors(const _PyCoreConfig *config)
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001257{
1258#ifndef MS_WINDOWS
1259 const char *loc = setlocale(LC_CTYPE, NULL);
1260 if (loc != NULL) {
1261 /* surrogateescape is the default in the legacy C and POSIX locales */
1262 if (strcmp(loc, "C") == 0 || strcmp(loc, "POSIX") == 0) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001263 return L"surrogateescape";
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001264 }
1265
1266#ifdef PY_COERCE_C_LOCALE
1267 /* surrogateescape is the default in locale coercion target locales */
1268 if (_Py_IsLocaleCoercionTarget(loc)) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001269 return L"surrogateescape";
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001270 }
1271#endif
1272 }
1273
Victor Stinner709d23d2019-05-02 14:56:30 -04001274 return L"strict";
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001275#else
1276 /* On Windows, always use surrogateescape by default */
Victor Stinner709d23d2019-05-02 14:56:30 -04001277 return L"surrogateescape";
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001278#endif
1279}
1280
1281
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001282static _PyInitError
Victor Stinner709d23d2019-05-02 14:56:30 -04001283config_get_locale_encoding(wchar_t **locale_encoding)
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001284{
1285#ifdef MS_WINDOWS
1286 char encoding[20];
Serhiy Storchakad53fe5f2019-03-13 22:59:55 +02001287 PyOS_snprintf(encoding, sizeof(encoding), "cp%u", GetACP());
Victor Stinner709d23d2019-05-02 14:56:30 -04001288 return _PyCoreConfig_DecodeLocale(locale_encoding, encoding);
Victor Stinnere2510952019-05-02 11:28:57 -04001289#elif defined(_Py_FORCE_UTF8_LOCALE)
Victor Stinner709d23d2019-05-02 14:56:30 -04001290 return _PyCoreConfig_SetString(locale_encoding, L"utf-8");
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001291#else
1292 const char *encoding = nl_langinfo(CODESET);
1293 if (!encoding || encoding[0] == '\0') {
Victor Stinnerdb719752019-05-01 05:35:33 +02001294 return _Py_INIT_ERR("failed to get the locale encoding: "
1295 "nl_langinfo(CODESET) failed");
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001296 }
Victor Stinner709d23d2019-05-02 14:56:30 -04001297 /* nl_langinfo(CODESET) is decoded by Py_DecodeLocale() */
1298 return CONFIG_DECODE_LOCALE(locale_encoding, encoding,
1299 "nl_langinfo(CODESET)");
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001300#endif
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001301}
1302
1303
1304static _PyInitError
Victor Stinner20004952019-03-26 02:31:11 +01001305config_init_stdio_encoding(_PyCoreConfig *config,
1306 const _PyPreConfig *preconfig)
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001307{
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001308 _PyInitError err;
1309
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001310 /* If Py_SetStandardStreamEncoding() have been called, use these
1311 parameters. */
1312 if (config->stdio_encoding == NULL && _Py_StandardStreamEncoding != NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001313 err = CONFIG_DECODE_LOCALE(&config->stdio_encoding,
1314 _Py_StandardStreamEncoding,
1315 "_Py_StandardStreamEncoding");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001316 if (_Py_INIT_FAILED(err)) {
1317 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001318 }
1319 }
1320
1321 if (config->stdio_errors == NULL && _Py_StandardStreamErrors != NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001322 err = CONFIG_DECODE_LOCALE(&config->stdio_errors,
1323 _Py_StandardStreamErrors,
1324 "_Py_StandardStreamErrors");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001325 if (_Py_INIT_FAILED(err)) {
1326 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001327 }
1328 }
1329
1330 if (config->stdio_encoding != NULL && config->stdio_errors != NULL) {
1331 return _Py_INIT_OK();
1332 }
1333
1334 /* PYTHONIOENCODING environment variable */
1335 const char *opt = _PyCoreConfig_GetEnv(config, "PYTHONIOENCODING");
1336 if (opt) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001337 char *pythonioencoding = _PyMem_RawStrdup(opt);
1338 if (pythonioencoding == NULL) {
1339 return _Py_INIT_NO_MEMORY();
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001340 }
1341
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001342 char *errors = strchr(pythonioencoding, ':');
1343 if (errors) {
1344 *errors = '\0';
1345 errors++;
1346 if (!errors[0]) {
1347 errors = NULL;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001348 }
1349 }
1350
1351 /* Does PYTHONIOENCODING contain an encoding? */
1352 if (pythonioencoding[0]) {
1353 if (config->stdio_encoding == NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001354 err = CONFIG_DECODE_LOCALE(&config->stdio_encoding,
1355 pythonioencoding,
1356 "PYTHONIOENCODING environment variable");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001357 if (_Py_INIT_FAILED(err)) {
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001358 PyMem_RawFree(pythonioencoding);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001359 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001360 }
1361 }
1362
1363 /* If the encoding is set but not the error handler,
1364 use "strict" error handler by default.
1365 PYTHONIOENCODING=latin1 behaves as
1366 PYTHONIOENCODING=latin1:strict. */
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001367 if (!errors) {
1368 errors = "strict";
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001369 }
1370 }
1371
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001372 if (config->stdio_errors == NULL && errors != NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001373 err = CONFIG_DECODE_LOCALE(&config->stdio_errors,
1374 errors,
1375 "PYTHONIOENCODING environment variable");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001376 if (_Py_INIT_FAILED(err)) {
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001377 PyMem_RawFree(pythonioencoding);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001378 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001379 }
1380 }
1381
1382 PyMem_RawFree(pythonioencoding);
1383 }
1384
1385 /* UTF-8 Mode uses UTF-8/surrogateescape */
Victor Stinner20004952019-03-26 02:31:11 +01001386 if (preconfig->utf8_mode) {
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001387 if (config->stdio_encoding == NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001388 err = _PyCoreConfig_SetString(&config->stdio_encoding, L"utf-8");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001389 if (_Py_INIT_FAILED(err)) {
1390 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001391 }
1392 }
1393 if (config->stdio_errors == NULL) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001394 err = _PyCoreConfig_SetString(&config->stdio_errors,
Victor Stinner709d23d2019-05-02 14:56:30 -04001395 L"surrogateescape");
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001396 if (_Py_INIT_FAILED(err)) {
1397 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001398 }
1399 }
1400 }
1401
1402 /* Choose the default error handler based on the current locale. */
1403 if (config->stdio_encoding == NULL) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001404 err = config_get_locale_encoding(&config->stdio_encoding);
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001405 if (_Py_INIT_FAILED(err)) {
1406 return err;
1407 }
1408 }
1409 if (config->stdio_errors == NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001410 const wchar_t *errors = config_get_stdio_errors(config);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001411 assert(errors != NULL);
1412
1413 err = _PyCoreConfig_SetString(&config->stdio_errors, errors);
1414 if (_Py_INIT_FAILED(err)) {
1415 return err;
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001416 }
1417 }
1418
1419 return _Py_INIT_OK();
1420}
1421
1422
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001423static _PyInitError
Victor Stinner20004952019-03-26 02:31:11 +01001424config_init_fs_encoding(_PyCoreConfig *config, const _PyPreConfig *preconfig)
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001425{
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001426 _PyInitError err;
1427
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001428 if (config->filesystem_encoding == NULL) {
Victor Stinnere2510952019-05-02 11:28:57 -04001429#ifdef _Py_FORCE_UTF8_FS_ENCODING
Victor Stinner709d23d2019-05-02 14:56:30 -04001430 err = _PyCoreConfig_SetString(&config->filesystem_encoding, L"utf-8");
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001431#else
Victor Stinnere2510952019-05-02 11:28:57 -04001432
1433#ifdef MS_WINDOWS
1434 if (preconfig->legacy_windows_fs_encoding) {
1435 /* Legacy Windows filesystem encoding: mbcs/replace */
1436 err = _PyCoreConfig_SetString(&config->filesystem_encoding,
Victor Stinner709d23d2019-05-02 14:56:30 -04001437 L"mbcs");
Victor Stinnere2510952019-05-02 11:28:57 -04001438 }
1439 else
1440#endif
Victor Stinner20004952019-03-26 02:31:11 +01001441 if (preconfig->utf8_mode) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001442 err = _PyCoreConfig_SetString(&config->filesystem_encoding,
Victor Stinner709d23d2019-05-02 14:56:30 -04001443 L"utf-8");
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001444 }
Victor Stinnere2510952019-05-02 11:28:57 -04001445#ifndef MS_WINDOWS
Victor Stinner905f1ac2018-10-30 12:58:10 +01001446 else if (_Py_GetForceASCII()) {
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001447 err = _PyCoreConfig_SetString(&config->filesystem_encoding,
Victor Stinner709d23d2019-05-02 14:56:30 -04001448 L"ascii");
Victor Stinner905f1ac2018-10-30 12:58:10 +01001449 }
Victor Stinnere2510952019-05-02 11:28:57 -04001450#endif
Victor Stinner905f1ac2018-10-30 12:58:10 +01001451 else {
Victor Stinnere2510952019-05-02 11:28:57 -04001452#ifdef MS_WINDOWS
1453 /* Windows defaults to utf-8/surrogatepass (PEP 529). */
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001454 err = _PyCoreConfig_SetString(&config->filesystem_encoding,
Victor Stinner709d23d2019-05-02 14:56:30 -04001455 L"utf-8");
Victor Stinner905f1ac2018-10-30 12:58:10 +01001456#else
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001457 err = config_get_locale_encoding(&config->filesystem_encoding);
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001458#endif
Victor Stinner905f1ac2018-10-30 12:58:10 +01001459 }
Victor Stinnere2510952019-05-02 11:28:57 -04001460#endif /* !_Py_FORCE_UTF8_FS_ENCODING */
Victor Stinner905f1ac2018-10-30 12:58:10 +01001461
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001462 if (_Py_INIT_FAILED(err)) {
1463 return err;
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001464 }
1465 }
1466
1467 if (config->filesystem_errors == NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001468 const wchar_t *errors;
Victor Stinnere2510952019-05-02 11:28:57 -04001469#ifdef MS_WINDOWS
1470 if (preconfig->legacy_windows_fs_encoding) {
Victor Stinner709d23d2019-05-02 14:56:30 -04001471 errors = L"replace";
Victor Stinnere2510952019-05-02 11:28:57 -04001472 }
1473 else {
Victor Stinner709d23d2019-05-02 14:56:30 -04001474 errors = L"surrogatepass";
Victor Stinnere2510952019-05-02 11:28:57 -04001475 }
1476#else
Victor Stinner709d23d2019-05-02 14:56:30 -04001477 errors = L"surrogateescape";
Victor Stinnere2510952019-05-02 11:28:57 -04001478#endif
1479 err = _PyCoreConfig_SetString(&config->filesystem_errors, errors);
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001480 if (_Py_INIT_FAILED(err)) {
1481 return err;
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001482 }
1483 }
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001484 return _Py_INIT_OK();
1485}
1486
1487
Victor Stinnera6fbc4e2019-03-25 18:37:10 +01001488static _PyInitError
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001489config_read(_PyCoreConfig *config, _PyPreCmdline *cmdline)
Victor Stinner6c785c02018-08-01 17:56:14 +02001490{
1491 _PyInitError err;
Victor Stinner20004952019-03-26 02:31:11 +01001492 const _PyPreConfig *preconfig = &_PyRuntime.preconfig;
Victor Stinnera6fbc4e2019-03-25 18:37:10 +01001493
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001494 if (_PyPreCmdline_SetCoreConfig(cmdline, config) < 0) {
Victor Stinnera6fbc4e2019-03-25 18:37:10 +01001495 return _Py_INIT_NO_MEMORY();
1496 }
1497
Victor Stinner20004952019-03-26 02:31:11 +01001498 if (config->isolated > 0) {
Victor Stinnerae239f62019-05-16 17:02:56 +02001499 /* _PyPreCmdline_Read() sets use_environment to 0 if isolated is set,
1500 _PyPreCmdline_SetCoreConfig() overrides config->use_environment. */
Victor Stinner6c785c02018-08-01 17:56:14 +02001501 config->user_site_directory = 0;
1502 }
1503
Victor Stinner20004952019-03-26 02:31:11 +01001504 if (config->use_environment) {
Victor Stinner6c785c02018-08-01 17:56:14 +02001505 err = config_read_env_vars(config);
1506 if (_Py_INIT_FAILED(err)) {
1507 return err;
1508 }
1509 }
1510
1511 /* -X options */
1512 if (config_get_xoption(config, L"showrefcount")) {
1513 config->show_ref_count = 1;
1514 }
1515 if (config_get_xoption(config, L"showalloccount")) {
1516 config->show_alloc_count = 1;
1517 }
1518
1519 err = config_read_complex_options(config);
1520 if (_Py_INIT_FAILED(err)) {
1521 return err;
1522 }
1523
Victor Stinner6c785c02018-08-01 17:56:14 +02001524 if (config->home == NULL) {
1525 err = config_init_home(config);
1526 if (_Py_INIT_FAILED(err)) {
1527 return err;
1528 }
1529 }
1530
1531 if (config->program_name == NULL) {
1532 err = config_init_program_name(config);
1533 if (_Py_INIT_FAILED(err)) {
1534 return err;
1535 }
1536 }
1537
Steve Dower177a41a2018-11-17 20:41:48 -08001538 if (config->executable == NULL) {
1539 err = config_init_executable(config);
1540 if (_Py_INIT_FAILED(err)) {
1541 return err;
1542 }
1543 }
1544
Victor Stinner6c785c02018-08-01 17:56:14 +02001545 if (config->_install_importlib) {
1546 err = _PyCoreConfig_InitPathConfig(config);
1547 if (_Py_INIT_FAILED(err)) {
1548 return err;
1549 }
1550 }
1551
1552 /* default values */
Victor Stinner20004952019-03-26 02:31:11 +01001553 if (config->dev_mode) {
Victor Stinner6c785c02018-08-01 17:56:14 +02001554 if (config->faulthandler < 0) {
1555 config->faulthandler = 1;
1556 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001557 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001558 if (config->faulthandler < 0) {
1559 config->faulthandler = 0;
1560 }
1561 if (config->tracemalloc < 0) {
1562 config->tracemalloc = 0;
1563 }
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001564 if (config->use_hash_seed < 0) {
1565 config->use_hash_seed = 0;
1566 config->hash_seed = 0;
1567 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001568
Victor Stinner70fead22018-08-29 13:45:34 +02001569 if (config->filesystem_encoding == NULL || config->filesystem_errors == NULL) {
Victor Stinner20004952019-03-26 02:31:11 +01001570 err = config_init_fs_encoding(config, preconfig);
Victor Stinnerb2457ef2018-08-29 13:25:36 +02001571 if (_Py_INIT_FAILED(err)) {
1572 return err;
1573 }
1574 }
1575
Victor Stinner20004952019-03-26 02:31:11 +01001576 err = config_init_stdio_encoding(config, preconfig);
Victor Stinnerdfe0dc72018-08-29 11:47:29 +02001577 if (_Py_INIT_FAILED(err)) {
1578 return err;
1579 }
1580
Victor Stinner62599762019-03-15 16:03:23 +01001581 if (config->argv.length < 1) {
1582 /* Ensure at least one (empty) argument is seen */
1583 if (_PyWstrList_Append(&config->argv, L"") < 0) {
1584 return _Py_INIT_NO_MEMORY();
1585 }
1586 }
Victor Stinner6c785c02018-08-01 17:56:14 +02001587 return _Py_INIT_OK();
1588}
Victor Stinner5ed69952018-11-06 15:59:52 +01001589
1590
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001591static void
1592config_init_stdio(const _PyCoreConfig *config)
1593{
1594#if defined(MS_WINDOWS) || defined(__CYGWIN__)
1595 /* don't translate newlines (\r\n <=> \n) */
1596 _setmode(fileno(stdin), O_BINARY);
1597 _setmode(fileno(stdout), O_BINARY);
1598 _setmode(fileno(stderr), O_BINARY);
1599#endif
1600
1601 if (!config->buffered_stdio) {
1602#ifdef HAVE_SETVBUF
1603 setvbuf(stdin, (char *)NULL, _IONBF, BUFSIZ);
1604 setvbuf(stdout, (char *)NULL, _IONBF, BUFSIZ);
1605 setvbuf(stderr, (char *)NULL, _IONBF, BUFSIZ);
1606#else /* !HAVE_SETVBUF */
1607 setbuf(stdin, (char *)NULL);
1608 setbuf(stdout, (char *)NULL);
1609 setbuf(stderr, (char *)NULL);
1610#endif /* !HAVE_SETVBUF */
1611 }
1612 else if (config->interactive) {
1613#ifdef MS_WINDOWS
1614 /* Doesn't have to have line-buffered -- use unbuffered */
1615 /* Any set[v]buf(stdin, ...) screws up Tkinter :-( */
1616 setvbuf(stdout, (char *)NULL, _IONBF, BUFSIZ);
1617#else /* !MS_WINDOWS */
1618#ifdef HAVE_SETVBUF
1619 setvbuf(stdin, (char *)NULL, _IOLBF, BUFSIZ);
1620 setvbuf(stdout, (char *)NULL, _IOLBF, BUFSIZ);
1621#endif /* HAVE_SETVBUF */
1622#endif /* !MS_WINDOWS */
1623 /* Leave stderr alone - it should be unbuffered anyway. */
1624 }
1625}
1626
1627
1628/* Write the configuration:
1629
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001630 - set Py_xxx global configuration variables
1631 - initialize C standard streams (stdin, stdout, stderr) */
Victor Stinner20004952019-03-26 02:31:11 +01001632void
Victor Stinner43125222019-04-24 18:23:53 +02001633_PyCoreConfig_Write(const _PyCoreConfig *config, _PyRuntimeState *runtime)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001634{
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001635 _PyCoreConfig_SetGlobalConfig(config);
Victor Stinner54b43bb2019-05-16 18:30:15 +02001636
1637 if (config->configure_c_stdio) {
1638 config_init_stdio(config);
1639 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001640
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001641 /* Write the new pre-configuration into _PyRuntime */
Victor Stinner43125222019-04-24 18:23:53 +02001642 _PyPreConfig *preconfig = &runtime->preconfig;
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001643 preconfig->isolated = config->isolated;
1644 preconfig->use_environment = config->use_environment;
1645 preconfig->dev_mode = config->dev_mode;
Victor Stinner5ed69952018-11-06 15:59:52 +01001646}
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001647
1648
Victor Stinner2f549082019-03-29 15:13:46 +01001649/* --- _PyCoreConfig command line parser -------------------------- */
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001650
1651static void
Victor Stinner2f549082019-03-29 15:13:46 +01001652config_usage(int error, const wchar_t* program)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001653{
Victor Stinner2f549082019-03-29 15:13:46 +01001654 FILE *f = error ? stderr : stdout;
1655
1656 fprintf(f, usage_line, program);
1657 if (error)
1658 fprintf(f, "Try `python -h' for more information.\n");
1659 else {
1660 fputs(usage_1, f);
1661 fputs(usage_2, f);
1662 fputs(usage_3, f);
1663 fprintf(f, usage_4, (wint_t)DELIM);
1664 fprintf(f, usage_5, (wint_t)DELIM, PYTHONHOMEHELP);
1665 fputs(usage_6, f);
1666 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001667}
1668
1669
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001670/* Parse the command line arguments */
1671static _PyInitError
Victor Stinner2f549082019-03-29 15:13:46 +01001672config_parse_cmdline(_PyCoreConfig *config, _PyPreCmdline *precmdline,
Victor Stinnerae239f62019-05-16 17:02:56 +02001673 _PyWstrList *warnoptions, int *opt_index)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001674{
Victor Stinnercb9fbd32019-05-01 23:51:56 -04001675 _PyInitError err;
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001676 const _PyWstrList *argv = &precmdline->argv;
Victor Stinner2f549082019-03-29 15:13:46 +01001677 int print_version = 0;
Victor Stinnerfa153762019-03-20 04:25:38 +01001678
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001679 _PyOS_ResetGetOpt();
1680 do {
1681 int longindex = -1;
Victor Stinnerfa153762019-03-20 04:25:38 +01001682 int c = _PyOS_GetOpt(argv->length, argv->items, &longindex);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001683 if (c == EOF) {
1684 break;
1685 }
1686
1687 if (c == 'c') {
Victor Stinner4a1468e2019-03-20 03:11:38 +01001688 if (config->run_command == NULL) {
1689 /* -c is the last option; following arguments
1690 that look like options are left for the
1691 command to interpret. */
1692 size_t len = wcslen(_PyOS_optarg) + 1 + 1;
1693 wchar_t *command = PyMem_RawMalloc(sizeof(wchar_t) * len);
1694 if (command == NULL) {
1695 return _Py_INIT_NO_MEMORY();
1696 }
1697 memcpy(command, _PyOS_optarg, (len - 2) * sizeof(wchar_t));
1698 command[len - 2] = '\n';
1699 command[len - 1] = 0;
1700 config->run_command = command;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001701 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001702 break;
1703 }
1704
1705 if (c == 'm') {
1706 /* -m is the last option; following arguments
1707 that look like options are left for the
1708 module to interpret. */
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001709 if (config->run_module == NULL) {
Victor Stinner4a1468e2019-03-20 03:11:38 +01001710 config->run_module = _PyMem_RawWcsdup(_PyOS_optarg);
1711 if (config->run_module == NULL) {
1712 return _Py_INIT_NO_MEMORY();
1713 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001714 }
1715 break;
1716 }
1717
1718 switch (c) {
1719 case 0:
1720 // Handle long option.
1721 assert(longindex == 0); // Only one long option now.
Victor Stinnercb9fbd32019-05-01 23:51:56 -04001722 if (wcscmp(_PyOS_optarg, L"always") == 0
1723 || wcscmp(_PyOS_optarg, L"never") == 0
1724 || wcscmp(_PyOS_optarg, L"default") == 0)
1725 {
Victor Stinner709d23d2019-05-02 14:56:30 -04001726 err = _PyCoreConfig_SetString(&config->check_hash_pycs_mode,
1727 _PyOS_optarg);
Victor Stinnercb9fbd32019-05-01 23:51:56 -04001728 if (_Py_INIT_FAILED(err)) {
1729 return err;
1730 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001731 } else {
1732 fprintf(stderr, "--check-hash-based-pycs must be one of "
1733 "'default', 'always', or 'never'\n");
Victor Stinner2f549082019-03-29 15:13:46 +01001734 config_usage(1, config->program);
1735 return _Py_INIT_EXIT(2);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001736 }
1737 break;
1738
1739 case 'b':
1740 config->bytes_warning++;
1741 break;
1742
1743 case 'd':
1744 config->parser_debug++;
1745 break;
1746
1747 case 'i':
1748 config->inspect++;
1749 config->interactive++;
1750 break;
1751
Victor Stinner6dcb5422019-03-05 02:44:12 +01001752 case 'E':
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001753 case 'I':
Victor Stinnerfa153762019-03-20 04:25:38 +01001754 case 'X':
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001755 /* option handled by _PyPreCmdline_Read() */
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001756 break;
1757
1758 /* case 'J': reserved for Jython */
1759
1760 case 'O':
1761 config->optimization_level++;
1762 break;
1763
1764 case 'B':
1765 config->write_bytecode = 0;
1766 break;
1767
1768 case 's':
1769 config->user_site_directory = 0;
1770 break;
1771
1772 case 'S':
1773 config->site_import = 0;
1774 break;
1775
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001776 case 't':
1777 /* ignored for backwards compatibility */
1778 break;
1779
1780 case 'u':
1781 config->buffered_stdio = 0;
1782 break;
1783
1784 case 'v':
1785 config->verbose++;
1786 break;
1787
1788 case 'x':
1789 config->skip_source_first_line = 1;
1790 break;
1791
1792 case 'h':
1793 case '?':
Victor Stinner2f549082019-03-29 15:13:46 +01001794 config_usage(0, config->program);
1795 return _Py_INIT_EXIT(0);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001796
1797 case 'V':
Victor Stinner2f549082019-03-29 15:13:46 +01001798 print_version++;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001799 break;
1800
1801 case 'W':
Victor Stinner2f549082019-03-29 15:13:46 +01001802 if (_PyWstrList_Append(warnoptions, _PyOS_optarg) < 0) {
Victor Stinner74f65682019-03-15 15:08:05 +01001803 return _Py_INIT_NO_MEMORY();
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001804 }
1805 break;
1806
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001807 case 'q':
1808 config->quiet++;
1809 break;
1810
1811 case 'R':
1812 config->use_hash_seed = 0;
1813 break;
1814
1815 /* This space reserved for other options */
1816
1817 default:
1818 /* unknown argument: parsing failed */
Victor Stinner2f549082019-03-29 15:13:46 +01001819 config_usage(1, config->program);
1820 return _Py_INIT_EXIT(2);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001821 }
1822 } while (1);
1823
Victor Stinner2f549082019-03-29 15:13:46 +01001824 if (print_version) {
1825 printf("Python %s\n",
1826 (print_version >= 2) ? Py_GetVersion() : PY_VERSION);
1827 return _Py_INIT_EXIT(0);
1828 }
1829
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001830 if (config->run_command == NULL && config->run_module == NULL
Victor Stinnerfa153762019-03-20 04:25:38 +01001831 && _PyOS_optind < argv->length
1832 && wcscmp(argv->items[_PyOS_optind], L"-") != 0
Victor Stinner4a1468e2019-03-20 03:11:38 +01001833 && config->run_filename == NULL)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001834 {
Victor Stinnerfa153762019-03-20 04:25:38 +01001835 config->run_filename = _PyMem_RawWcsdup(argv->items[_PyOS_optind]);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001836 if (config->run_filename == NULL) {
1837 return _Py_INIT_NO_MEMORY();
1838 }
1839 }
1840
1841 if (config->run_command != NULL || config->run_module != NULL) {
1842 /* Backup _PyOS_optind */
1843 _PyOS_optind--;
1844 }
1845
Victor Stinnerae239f62019-05-16 17:02:56 +02001846 *opt_index = _PyOS_optind;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001847
1848 return _Py_INIT_OK();
1849}
1850
1851
1852#ifdef MS_WINDOWS
1853# define WCSTOK wcstok_s
1854#else
1855# define WCSTOK wcstok
1856#endif
1857
1858/* Get warning options from PYTHONWARNINGS environment variable. */
1859static _PyInitError
Victor Stinner2f549082019-03-29 15:13:46 +01001860config_init_env_warnoptions(const _PyCoreConfig *config, _PyWstrList *warnoptions)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001861{
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001862 _PyInitError err;
1863 /* CONFIG_GET_ENV_DUP requires dest to be initialized to NULL */
1864 wchar_t *env = NULL;
1865 err = CONFIG_GET_ENV_DUP(config, &env,
1866 L"PYTHONWARNINGS", "PYTHONWARNINGS");
1867 if (_Py_INIT_FAILED(err)) {
1868 return err;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001869 }
1870
Victor Stinner1a9f0d82019-05-01 15:22:52 +02001871 /* env var is not set or is empty */
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001872 if (env == NULL) {
1873 return _Py_INIT_OK();
1874 }
1875
1876
1877 wchar_t *warning, *context = NULL;
1878 for (warning = WCSTOK(env, L",", &context);
1879 warning != NULL;
1880 warning = WCSTOK(NULL, L",", &context))
1881 {
Victor Stinner2f549082019-03-29 15:13:46 +01001882 if (_PyWstrList_Append(warnoptions, warning) < 0) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001883 PyMem_RawFree(env);
Victor Stinner74f65682019-03-15 15:08:05 +01001884 return _Py_INIT_NO_MEMORY();
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001885 }
1886 }
1887 PyMem_RawFree(env);
1888 return _Py_INIT_OK();
1889}
1890
1891
1892static _PyInitError
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001893config_init_program(_PyCoreConfig *config, const _PyPreCmdline *cmdline)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001894{
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001895 const _PyWstrList *argv = &cmdline->argv;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001896 wchar_t *program;
Victor Stinnerfa153762019-03-20 04:25:38 +01001897 if (argv->length >= 1) {
1898 program = argv->items[0];
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001899 }
1900 else {
1901 program = L"";
1902 }
1903 config->program = _PyMem_RawWcsdup(program);
1904 if (config->program == NULL) {
1905 return _Py_INIT_NO_MEMORY();
1906 }
1907
1908 return _Py_INIT_OK();
1909}
1910
1911
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001912static int
1913config_add_warnoption(_PyCoreConfig *config, const wchar_t *option)
1914{
1915 if (_PyWstrList_Find(&config->warnoptions, option)) {
1916 /* Already present: do nothing */
1917 return 0;
1918 }
1919 if (_PyWstrList_Append(&config->warnoptions, option)) {
1920 return -1;
1921 }
1922 return 0;
1923}
1924
1925
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001926static _PyInitError
Victor Stinner2f549082019-03-29 15:13:46 +01001927config_init_warnoptions(_PyCoreConfig *config,
1928 const _PyWstrList *cmdline_warnoptions,
1929 const _PyWstrList *env_warnoptions)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001930{
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001931 /* The priority order for warnings configuration is (highest precedence
1932 * first):
1933 *
1934 * - the BytesWarning filter, if needed ('-b', '-bb')
1935 * - any '-W' command line options; then
1936 * - the 'PYTHONWARNINGS' environment variable; then
1937 * - the dev mode filter ('-X dev', 'PYTHONDEVMODE'); then
1938 * - any implicit filters added by _warnings.c/warnings.py
1939 *
1940 * All settings except the last are passed to the warnings module via
1941 * the `sys.warnoptions` list. Since the warnings module works on the basis
1942 * of "the most recently added filter will be checked first", we add
1943 * the lowest precedence entries first so that later entries override them.
1944 */
1945
Victor Stinner20004952019-03-26 02:31:11 +01001946 if (config->dev_mode) {
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001947 if (config_add_warnoption(config, L"default") < 0) {
Victor Stinner74f65682019-03-15 15:08:05 +01001948 return _Py_INIT_NO_MEMORY();
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001949 }
1950 }
1951
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001952 Py_ssize_t i;
1953 const _PyWstrList *options;
1954
Victor Stinner2f549082019-03-29 15:13:46 +01001955 options = env_warnoptions;
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001956 for (i = 0; i < options->length; i++) {
1957 if (config_add_warnoption(config, options->items[i]) < 0) {
1958 return _Py_INIT_NO_MEMORY();
1959 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001960 }
1961
Victor Stinner2f549082019-03-29 15:13:46 +01001962 options = cmdline_warnoptions;
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001963 for (i = 0; i < options->length; i++) {
1964 if (config_add_warnoption(config, options->items[i]) < 0) {
1965 return _Py_INIT_NO_MEMORY();
1966 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001967 }
1968
1969 /* If the bytes_warning_flag isn't set, bytesobject.c and bytearrayobject.c
1970 * don't even try to emit a warning, so we skip setting the filter in that
1971 * case.
1972 */
1973 if (config->bytes_warning) {
Victor Stinner74f65682019-03-15 15:08:05 +01001974 const wchar_t *filter;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001975 if (config->bytes_warning> 1) {
1976 filter = L"error::BytesWarning";
1977 }
1978 else {
1979 filter = L"default::BytesWarning";
1980 }
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001981 if (config_add_warnoption(config, filter) < 0) {
Victor Stinner74f65682019-03-15 15:08:05 +01001982 return _Py_INIT_NO_MEMORY();
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001983 }
1984 }
1985 return _Py_INIT_OK();
1986}
1987
1988
1989static _PyInitError
Victor Stinnerae239f62019-05-16 17:02:56 +02001990config_update_argv(_PyCoreConfig *config, const _PyPreCmdline *cmdline,
1991 int opt_index)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001992{
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01001993 const _PyWstrList *cmdline_argv = &cmdline->argv;
Victor Stinnerfa153762019-03-20 04:25:38 +01001994 _PyWstrList config_argv = _PyWstrList_INIT;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001995
Victor Stinner74f65682019-03-15 15:08:05 +01001996 /* Copy argv to be able to modify it (to force -c/-m) */
Victor Stinnerae239f62019-05-16 17:02:56 +02001997 if (cmdline_argv->length <= opt_index) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +01001998 /* Ensure at least one (empty) argument is seen */
Victor Stinnerfa153762019-03-20 04:25:38 +01001999 if (_PyWstrList_Append(&config_argv, L"") < 0) {
Victor Stinner74f65682019-03-15 15:08:05 +01002000 return _Py_INIT_NO_MEMORY();
2001 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002002 }
2003 else {
Victor Stinner74f65682019-03-15 15:08:05 +01002004 _PyWstrList slice;
Victor Stinnerae239f62019-05-16 17:02:56 +02002005 slice.length = cmdline_argv->length - opt_index;
2006 slice.items = &cmdline_argv->items[opt_index];
Victor Stinnerfa153762019-03-20 04:25:38 +01002007 if (_PyWstrList_Copy(&config_argv, &slice) < 0) {
Victor Stinner74f65682019-03-15 15:08:05 +01002008 return _Py_INIT_NO_MEMORY();
2009 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002010 }
Victor Stinnerfa153762019-03-20 04:25:38 +01002011 assert(config_argv.length >= 1);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002012
2013 wchar_t *arg0 = NULL;
2014 if (config->run_command != NULL) {
2015 /* Force sys.argv[0] = '-c' */
2016 arg0 = L"-c";
2017 }
2018 else if (config->run_module != NULL) {
2019 /* Force sys.argv[0] = '-m'*/
2020 arg0 = L"-m";
2021 }
2022 if (arg0 != NULL) {
2023 arg0 = _PyMem_RawWcsdup(arg0);
2024 if (arg0 == NULL) {
Victor Stinnerfa153762019-03-20 04:25:38 +01002025 _PyWstrList_Clear(&config_argv);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002026 return _Py_INIT_NO_MEMORY();
2027 }
2028
Victor Stinnerfa153762019-03-20 04:25:38 +01002029 PyMem_RawFree(config_argv.items[0]);
2030 config_argv.items[0] = arg0;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002031 }
2032
Victor Stinner74f65682019-03-15 15:08:05 +01002033 _PyWstrList_Clear(&config->argv);
Victor Stinnerfa153762019-03-20 04:25:38 +01002034 config->argv = config_argv;
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002035 return _Py_INIT_OK();
2036}
2037
2038
Victor Stinner5ac27a52019-03-27 13:40:14 +01002039static _PyInitError
Victor Stinner5f38b842019-05-01 02:30:12 +02002040core_read_precmdline(_PyCoreConfig *config, _PyPreCmdline *precmdline)
Victor Stinner5ac27a52019-03-27 13:40:14 +01002041{
2042 _PyInitError err;
2043
Victor Stinner2f549082019-03-29 15:13:46 +01002044 if (_PyWstrList_Copy(&precmdline->argv, &config->argv) < 0) {
2045 return _Py_INIT_NO_MEMORY();
Victor Stinner5ac27a52019-03-27 13:40:14 +01002046 }
2047
2048 _PyPreConfig preconfig = _PyPreConfig_INIT;
2049 if (_PyPreConfig_Copy(&preconfig, &_PyRuntime.preconfig) < 0) {
2050 err = _Py_INIT_NO_MEMORY();
2051 goto done;
2052 }
2053
2054 _PyCoreConfig_GetCoreConfig(&preconfig, config);
2055
2056 err = _PyPreCmdline_Read(precmdline, &preconfig);
2057
2058done:
2059 _PyPreConfig_Clear(&preconfig);
2060 return err;
2061}
2062
2063
Victor Stinner2f549082019-03-29 15:13:46 +01002064static _PyInitError
2065config_read_cmdline(_PyCoreConfig *config, _PyPreCmdline *precmdline)
2066{
2067 _PyInitError err;
2068 _PyWstrList cmdline_warnoptions = _PyWstrList_INIT;
2069 _PyWstrList env_warnoptions = _PyWstrList_INIT;
2070
Victor Stinnerae239f62019-05-16 17:02:56 +02002071 if (config->parse_argv < 0) {
2072 config->parse_argv = 1;
Victor Stinner2f549082019-03-29 15:13:46 +01002073 }
Victor Stinner54b43bb2019-05-16 18:30:15 +02002074 if (config->configure_c_stdio < 0) {
2075 config->configure_c_stdio = 1;
2076 }
Victor Stinner2f549082019-03-29 15:13:46 +01002077
Victor Stinnerae239f62019-05-16 17:02:56 +02002078 if (config->parse_argv) {
2079 int opt_index;
2080 err = config_parse_cmdline(config, precmdline, &cmdline_warnoptions,
2081 &opt_index);
2082 if (_Py_INIT_FAILED(err)) {
2083 goto done;
2084 }
2085
2086 err = config_update_argv(config, precmdline, opt_index);
2087 if (_Py_INIT_FAILED(err)) {
2088 goto done;
2089 }
Victor Stinner2f549082019-03-29 15:13:46 +01002090 }
2091
2092 err = config_read(config, precmdline);
2093 if (_Py_INIT_FAILED(err)) {
2094 goto done;
2095 }
2096
2097 if (config->use_environment) {
2098 err = config_init_env_warnoptions(config, &env_warnoptions);
2099 if (_Py_INIT_FAILED(err)) {
2100 goto done;
2101 }
2102 }
2103
2104 err = config_init_warnoptions(config,
2105 &cmdline_warnoptions, &env_warnoptions);
2106 if (_Py_INIT_FAILED(err)) {
2107 goto done;
2108 }
2109
Victor Stinnercb9fbd32019-05-01 23:51:56 -04002110 if (config->check_hash_pycs_mode == NULL) {
Victor Stinner709d23d2019-05-02 14:56:30 -04002111 err = _PyCoreConfig_SetString(&config->check_hash_pycs_mode, L"default");
Victor Stinnercb9fbd32019-05-01 23:51:56 -04002112 if (_Py_INIT_FAILED(err)) {
2113 goto done;
2114 }
2115 }
2116
Victor Stinner2f549082019-03-29 15:13:46 +01002117 err = _Py_INIT_OK();
2118
2119done:
2120 _PyWstrList_Clear(&cmdline_warnoptions);
2121 _PyWstrList_Clear(&env_warnoptions);
2122 return err;
2123}
2124
2125
Victor Stinner5f38b842019-05-01 02:30:12 +02002126_PyInitError
2127_PyCoreConfig_SetPyArgv(_PyCoreConfig *config, const _PyArgv *args)
2128{
Victor Stinner70005ac2019-05-02 15:25:34 -04002129 if (args->use_bytes_argv) {
2130 _PyInitError err;
2131
2132 err = _PyRuntime_Initialize();
2133 if (_Py_INIT_FAILED(err)) {
2134 return err;
2135 }
2136 _PyRuntimeState *runtime = &_PyRuntime;
2137
2138 /* do nothing if Python is already pre-initialized:
2139 _PyCoreConfig_Write() will update _PyRuntime.preconfig later */
2140 if (!runtime->pre_initialized) {
2141 err = _Py_PreInitializeFromCoreConfig(config, args);
2142 if (_Py_INIT_FAILED(err)) {
2143 return err;
2144 }
2145 }
2146 }
Victor Stinner5f38b842019-05-01 02:30:12 +02002147 return _PyArgv_AsWstrList(args, &config->argv);
2148}
2149
2150
Victor Stinner70005ac2019-05-02 15:25:34 -04002151/* Set config.argv: decode argv using Py_DecodeLocale(). Pre-initialize Python
2152 if needed to ensure that encodings are properly configured. */
Victor Stinner5f38b842019-05-01 02:30:12 +02002153_PyInitError
2154_PyCoreConfig_SetArgv(_PyCoreConfig *config, int argc, char **argv)
2155{
2156 _PyArgv args = {
2157 .argc = argc,
2158 .use_bytes_argv = 1,
2159 .bytes_argv = argv,
2160 .wchar_argv = NULL};
2161 return _PyCoreConfig_SetPyArgv(config, &args);
2162}
2163
2164
2165_PyInitError
2166_PyCoreConfig_SetWideArgv(_PyCoreConfig *config, int argc, wchar_t **argv)
2167{
2168 _PyArgv args = {
2169 .argc = argc,
2170 .use_bytes_argv = 0,
2171 .bytes_argv = NULL,
2172 .wchar_argv = argv};
2173 return _PyCoreConfig_SetPyArgv(config, &args);
2174}
2175
2176
Victor Stinner4fffd382019-03-06 01:44:31 +01002177/* Read the configuration into _PyCoreConfig from:
Victor Stinner5a02e0d2019-03-05 12:32:09 +01002178
2179 * Command line arguments
2180 * Environment variables
Victor Stinner54b43bb2019-05-16 18:30:15 +02002181 * Py_xxx global configuration variables
2182
2183 The only side effects are to modify config and to call _Py_SetArgcArgv(). */
Victor Stinner5a02e0d2019-03-05 12:32:09 +01002184_PyInitError
Victor Stinner5f38b842019-05-01 02:30:12 +02002185_PyCoreConfig_Read(_PyCoreConfig *config)
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002186{
2187 _PyInitError err;
2188
Victor Stinner70005ac2019-05-02 15:25:34 -04002189 err = _Py_PreInitializeFromCoreConfig(config, NULL);
Victor Stinner6d5ee972019-03-23 12:05:43 +01002190 if (_Py_INIT_FAILED(err)) {
2191 return err;
2192 }
2193
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002194 _PyCoreConfig_GetGlobalConfig(config);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002195
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002196 _PyPreCmdline precmdline = _PyPreCmdline_INIT;
Victor Stinner5f38b842019-05-01 02:30:12 +02002197 err = core_read_precmdline(config, &precmdline);
Victor Stinner5ac27a52019-03-27 13:40:14 +01002198 if (_Py_INIT_FAILED(err)) {
2199 goto done;
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002200 }
2201
2202 if (config->program == NULL) {
2203 err = config_init_program(config, &precmdline);
2204 if (_Py_INIT_FAILED(err)) {
2205 goto done;
2206 }
2207 }
2208
Victor Stinner2f549082019-03-29 15:13:46 +01002209 err = config_read_cmdline(config, &precmdline);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002210 if (_Py_INIT_FAILED(err)) {
2211 goto done;
2212 }
2213
2214 const _PyWstrList *argv = &precmdline.argv;
2215 if (_Py_SetArgcArgv(argv->length, argv->items) < 0) {
2216 err = _Py_INIT_NO_MEMORY();
2217 goto done;
2218 }
2219
2220 /* Check config consistency */
2221 assert(config->isolated >= 0);
2222 assert(config->use_environment >= 0);
2223 assert(config->dev_mode >= 0);
2224 assert(config->install_signal_handlers >= 0);
2225 assert(config->use_hash_seed >= 0);
2226 assert(config->faulthandler >= 0);
2227 assert(config->tracemalloc >= 0);
2228 assert(config->site_import >= 0);
2229 assert(config->bytes_warning >= 0);
2230 assert(config->inspect >= 0);
2231 assert(config->interactive >= 0);
2232 assert(config->optimization_level >= 0);
2233 assert(config->parser_debug >= 0);
2234 assert(config->write_bytecode >= 0);
2235 assert(config->verbose >= 0);
2236 assert(config->quiet >= 0);
2237 assert(config->user_site_directory >= 0);
Victor Stinnerae239f62019-05-16 17:02:56 +02002238 assert(config->parse_argv >= 0);
Victor Stinner54b43bb2019-05-16 18:30:15 +02002239 assert(config->configure_c_stdio >= 0);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002240 assert(config->buffered_stdio >= 0);
2241 assert(config->program_name != NULL);
2242 assert(config->program != NULL);
2243 assert(_PyWstrList_CheckConsistency(&config->argv));
Victor Stinner54b43bb2019-05-16 18:30:15 +02002244 /* sys.argv must be non-empty: empty argv is replaced with [''] */
2245 assert(config->argv.length >= 1);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002246 assert(_PyWstrList_CheckConsistency(&config->xoptions));
2247 assert(_PyWstrList_CheckConsistency(&config->warnoptions));
2248 assert(_PyWstrList_CheckConsistency(&config->module_search_paths));
2249 if (config->_install_importlib) {
Victor Stinner54b43bb2019-05-16 18:30:15 +02002250 assert(config->use_module_search_paths != 0);
2251 /* don't check config->module_search_paths */
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002252 assert(config->executable != NULL);
2253 assert(config->prefix != NULL);
2254 assert(config->base_prefix != NULL);
2255 assert(config->exec_prefix != NULL);
2256 assert(config->base_exec_prefix != NULL);
2257#ifdef MS_WINDOWS
2258 assert(config->dll_path != NULL);
2259#endif
2260 }
2261 assert(config->filesystem_encoding != NULL);
2262 assert(config->filesystem_errors != NULL);
2263 assert(config->stdio_encoding != NULL);
2264 assert(config->stdio_errors != NULL);
2265#ifdef MS_WINDOWS
2266 assert(config->legacy_windows_stdio >= 0);
2267#endif
Victor Stinnerae239f62019-05-16 17:02:56 +02002268 /* -c and -m options are exclusive */
2269 assert(!(config->run_command != NULL && config->run_module != NULL));
Victor Stinnercb9fbd32019-05-01 23:51:56 -04002270 assert(config->check_hash_pycs_mode != NULL);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002271 assert(config->_install_importlib >= 0);
Victor Stinner9ef5dca2019-05-16 17:38:16 +02002272 assert(config->pathconfig_warnings >= 0);
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002273
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002274 err = _Py_INIT_OK();
2275
2276done:
Victor Stinnerf8ba6f52019-03-26 16:58:50 +01002277 _PyPreCmdline_Clear(&precmdline);
Victor Stinner95e2cbf2019-03-01 16:25:19 +01002278 return err;
2279}
Victor Stinner1075d162019-03-25 23:19:57 +01002280
2281
2282PyObject*
2283_Py_GetConfigsAsDict(void)
2284{
2285 PyObject *config = NULL;
2286 PyObject *dict = NULL;
2287
2288 config = PyDict_New();
2289 if (config == NULL) {
2290 goto error;
2291 }
2292
2293 /* global config */
2294 dict = _Py_GetGlobalVariablesAsDict();
2295 if (dict == NULL) {
2296 goto error;
2297 }
2298 if (PyDict_SetItemString(config, "global_config", dict) < 0) {
2299 goto error;
2300 }
2301 Py_CLEAR(dict);
2302
2303 /* pre config */
2304 PyInterpreterState *interp = _PyInterpreterState_Get();
Victor Stinner20004952019-03-26 02:31:11 +01002305 const _PyPreConfig *pre_config = &_PyRuntime.preconfig;
Victor Stinner1075d162019-03-25 23:19:57 +01002306 dict = _PyPreConfig_AsDict(pre_config);
2307 if (dict == NULL) {
2308 goto error;
2309 }
2310 if (PyDict_SetItemString(config, "pre_config", dict) < 0) {
2311 goto error;
2312 }
2313 Py_CLEAR(dict);
2314
2315 /* core config */
Victor Stinner20004952019-03-26 02:31:11 +01002316 const _PyCoreConfig *core_config = _PyInterpreterState_GetCoreConfig(interp);
Victor Stinner1075d162019-03-25 23:19:57 +01002317 dict = _PyCoreConfig_AsDict(core_config);
2318 if (dict == NULL) {
2319 goto error;
2320 }
2321 if (PyDict_SetItemString(config, "core_config", dict) < 0) {
2322 goto error;
2323 }
2324 Py_CLEAR(dict);
2325
Victor Stinner1075d162019-03-25 23:19:57 +01002326 return config;
2327
2328error:
2329 Py_XDECREF(config);
2330 Py_XDECREF(dict);
2331 return NULL;
2332}