blob: bb103c28a3e2a1a2dae11f9d7c1e785c02f94b88 [file] [log] [blame]
Guido van Rossum667d7041995-08-04 04:20:48 +00001/* Python interpreter main program */
2
3#include "Python.h"
Victor Stinnerf684d832019-03-01 03:44:13 +01004#include "pycore_coreconfig.h"
Victor Stinner621cebe2018-11-12 16:53:38 +01005#include "pycore_pylifecycle.h"
6#include "pycore_pymem.h"
7#include "pycore_pystate.h"
Guido van Rossum667d7041995-08-04 04:20:48 +00008
Victor Stinner6efcb6d2017-12-18 23:42:55 +01009#ifdef __FreeBSD__
Victor Stinner95e2cbf2019-03-01 16:25:19 +010010# include <fenv.h> /* fedisableexcept() */
Martin v. Löwis945362c2007-08-30 14:57:25 +000011#endif
12
Victor Stinner95e2cbf2019-03-01 16:25:19 +010013/* Includes for exit_sigint() */
14#include <stdio.h> /* perror() */
15#ifdef HAVE_SIGNAL_H
16# include <signal.h> /* SIGINT */
Guido van Rossuma075ce11997-12-05 21:56:45 +000017#endif
Victor Stinner95e2cbf2019-03-01 16:25:19 +010018#if defined(HAVE_GETPID) && defined(HAVE_UNISTD_H)
19# include <unistd.h> /* getpid() */
20#endif
21#ifdef _MSC_VER
22# include <crtdbg.h> /* STATUS_CONTROL_C_EXIT */
23#endif
24/* End of includes for exit_sigint() */
Guido van Rossuma075ce11997-12-05 21:56:45 +000025
Guido van Rossuma22865e2000-09-05 04:41:18 +000026#define COPYRIGHT \
Guido van Rossum36002d72001-07-18 16:59:46 +000027 "Type \"help\", \"copyright\", \"credits\" or \"license\" " \
28 "for more information."
Guido van Rossuma22865e2000-09-05 04:41:18 +000029
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000030#ifdef __cplusplus
31extern "C" {
32#endif
33
Victor Stinner95e2cbf2019-03-01 16:25:19 +010034/* --- pymain_init() ---------------------------------------------- */
35
Victor Stinner6dcb5422019-03-05 02:44:12 +010036static _PyInitError
Victor Stinner5ac27a52019-03-27 13:40:14 +010037pymain_init(const _PyArgv *args)
Victor Stinner95e2cbf2019-03-01 16:25:19 +010038{
39 _PyInitError err;
40
41 err = _PyRuntime_Initialize();
42 if (_Py_INIT_FAILED(err)) {
43 return err;
44 }
45
46 /* 754 requires that FP exceptions run in "no stop" mode by default,
47 * and until C vendors implement C99's ways to control FP exceptions,
48 * Python requires non-stop mode. Alas, some platforms enable FP
49 * exceptions by default. Here we disable them.
50 */
51#ifdef __FreeBSD__
52 fedisableexcept(FE_OVERFLOW);
53#endif
54
Victor Stinnerd929f182019-03-27 18:28:46 +010055 _PyPreConfig preconfig = _PyPreConfig_INIT;
56 /* Set to -1 to enable them depending on the LC_CTYPE locale and the
57 environment variables (PYTHONUTF8 and PYTHONCOERCECLOCALE) */
58 preconfig.coerce_c_locale = -1;
59 preconfig.utf8_mode = -1;
Victor Stinner70005ac2019-05-02 15:25:34 -040060 err = _Py_PreInitializeFromPyArgv(&preconfig, args);
Victor Stinner6dcb5422019-03-05 02:44:12 +010061 if (_Py_INIT_FAILED(err)) {
Victor Stinnerf72346c2019-03-25 17:54:58 +010062 return err;
Victor Stinner6dcb5422019-03-05 02:44:12 +010063 }
64
Victor Stinnerd929f182019-03-27 18:28:46 +010065 /* pass NULL as the config: config is read from command line arguments,
66 environment variables, configuration files */
Victor Stinner5ac27a52019-03-27 13:40:14 +010067 if (args->use_bytes_argv) {
Victor Stinnerd929f182019-03-27 18:28:46 +010068 return _Py_InitializeFromArgs(NULL, args->argc, args->bytes_argv);
Victor Stinner484f20d2019-03-27 02:04:16 +010069 }
Victor Stinner5ac27a52019-03-27 13:40:14 +010070 else {
Victor Stinnerd929f182019-03-27 18:28:46 +010071 return _Py_InitializeFromWideArgs(NULL, args->argc, args->wchar_argv);
Victor Stinner484f20d2019-03-27 02:04:16 +010072 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +010073}
74
75
76/* --- pymain_run_python() ---------------------------------------- */
77
78/* Non-zero if filename, command (-c) or module (-m) is set
79 on the command line */
80#define RUN_CODE(config) \
81 (config->run_command != NULL || config->run_filename != NULL \
82 || config->run_module != NULL)
83
84/* Return non-zero is stdin is a TTY or if -i command line option is used */
85static int
86stdin_is_interactive(const _PyCoreConfig *config)
87{
88 return (isatty(fileno(stdin)) || config->interactive);
89}
90
91
92static PyObject *
93pymain_get_importer(const wchar_t *filename)
94{
95 PyObject *sys_path0 = NULL, *importer;
96
97 sys_path0 = PyUnicode_FromWideChar(filename, wcslen(filename));
98 if (sys_path0 == NULL) {
99 goto error;
100 }
101
102 importer = PyImport_GetImporter(sys_path0);
103 if (importer == NULL) {
104 goto error;
105 }
106
107 if (importer == Py_None) {
108 Py_DECREF(sys_path0);
109 Py_DECREF(importer);
110 return NULL;
111 }
112
113 Py_DECREF(importer);
114 return sys_path0;
115
116error:
117 Py_XDECREF(sys_path0);
118 PySys_WriteStderr("Failed checking if argv[0] is an import path entry\n");
119 PyErr_Print();
120 return NULL;
121}
122
123
124static int
125pymain_sys_path_add_path0(PyInterpreterState *interp, PyObject *path0)
126{
127 _Py_IDENTIFIER(path);
128 PyObject *sys_path;
129 PyObject *sysdict = interp->sysdict;
130 if (sysdict != NULL) {
131 sys_path = _PyDict_GetItemIdWithError(sysdict, &PyId_path);
132 if (sys_path == NULL && PyErr_Occurred()) {
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200133 return -1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100134 }
135 }
136 else {
137 sys_path = NULL;
138 }
139 if (sys_path == NULL) {
140 PyErr_SetString(PyExc_RuntimeError, "unable to get sys.path");
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200141 return -1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100142 }
143
144 if (PyList_Insert(sys_path, 0, path0)) {
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200145 return -1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100146 }
147 return 0;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100148}
149
150
151static void
152pymain_header(const _PyCoreConfig *config)
153{
154 if (config->quiet) {
155 return;
156 }
157
158 if (!config->verbose && (RUN_CODE(config) || !stdin_is_interactive(config))) {
159 return;
160 }
161
162 fprintf(stderr, "Python %s on %s\n", Py_GetVersion(), Py_GetPlatform());
163 if (config->site_import) {
164 fprintf(stderr, "%s\n", COPYRIGHT);
165 }
166}
167
168
169static void
170pymain_import_readline(const _PyCoreConfig *config)
171{
Victor Stinner20004952019-03-26 02:31:11 +0100172 if (config->isolated) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100173 return;
174 }
175 if (!config->inspect && RUN_CODE(config)) {
176 return;
177 }
178 if (!isatty(fileno(stdin))) {
179 return;
180 }
181
182 PyObject *mod = PyImport_ImportModule("readline");
183 if (mod == NULL) {
184 PyErr_Clear();
185 }
186 else {
187 Py_DECREF(mod);
188 }
189}
190
191
192static int
193pymain_run_command(wchar_t *command, PyCompilerFlags *cf)
194{
195 PyObject *unicode, *bytes;
196 int ret;
197
198 unicode = PyUnicode_FromWideChar(command, -1);
199 if (unicode == NULL) {
200 goto error;
201 }
202
203 bytes = PyUnicode_AsUTF8String(unicode);
204 Py_DECREF(unicode);
205 if (bytes == NULL) {
206 goto error;
207 }
208
209 ret = PyRun_SimpleStringFlags(PyBytes_AsString(bytes), cf);
210 Py_DECREF(bytes);
211 return (ret != 0);
212
213error:
214 PySys_WriteStderr("Unable to decode the command from the command line:\n");
215 PyErr_Print();
216 return 1;
217}
218
219
220static int
221pymain_run_module(const wchar_t *modname, int set_argv0)
222{
223 PyObject *module, *runpy, *runmodule, *runargs, *result;
224 runpy = PyImport_ImportModule("runpy");
225 if (runpy == NULL) {
226 fprintf(stderr, "Could not import runpy module\n");
227 PyErr_Print();
228 return -1;
229 }
230 runmodule = PyObject_GetAttrString(runpy, "_run_module_as_main");
231 if (runmodule == NULL) {
232 fprintf(stderr, "Could not access runpy._run_module_as_main\n");
233 PyErr_Print();
234 Py_DECREF(runpy);
235 return -1;
236 }
237 module = PyUnicode_FromWideChar(modname, wcslen(modname));
238 if (module == NULL) {
239 fprintf(stderr, "Could not convert module name to unicode\n");
240 PyErr_Print();
241 Py_DECREF(runpy);
242 Py_DECREF(runmodule);
243 return -1;
244 }
245 runargs = Py_BuildValue("(Oi)", module, set_argv0);
246 if (runargs == NULL) {
247 fprintf(stderr,
248 "Could not create arguments for runpy._run_module_as_main\n");
249 PyErr_Print();
250 Py_DECREF(runpy);
251 Py_DECREF(runmodule);
252 Py_DECREF(module);
253 return -1;
254 }
255 result = PyObject_Call(runmodule, runargs, NULL);
256 if (result == NULL) {
257 PyErr_Print();
258 }
259 Py_DECREF(runpy);
260 Py_DECREF(runmodule);
261 Py_DECREF(module);
262 Py_DECREF(runargs);
263 if (result == NULL) {
264 return -1;
265 }
266 Py_DECREF(result);
267 return 0;
268}
269
270
271static int
272pymain_run_file(_PyCoreConfig *config, PyCompilerFlags *cf)
273{
274 const wchar_t *filename = config->run_filename;
Inada Naoki10654c12019-04-01 18:35:20 +0900275 FILE *fp = _Py_wfopen(filename, L"rb");
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100276 if (fp == NULL) {
277 char *cfilename_buffer;
278 const char *cfilename;
279 int err = errno;
280 cfilename_buffer = _Py_EncodeLocaleRaw(filename, NULL);
281 if (cfilename_buffer != NULL)
282 cfilename = cfilename_buffer;
283 else
284 cfilename = "<unprintable file name>";
285 fprintf(stderr, "%ls: can't open file '%s': [Errno %d] %s\n",
Victor Stinnerfed02e12019-05-17 11:12:09 +0200286 config->program_name, cfilename, err, strerror(err));
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100287 PyMem_RawFree(cfilename_buffer);
288 return 2;
289 }
290
291 if (config->skip_source_first_line) {
292 int ch;
293 /* Push back first newline so line numbers remain the same */
294 while ((ch = getc(fp)) != EOF) {
295 if (ch == '\n') {
296 (void)ungetc(ch, fp);
297 break;
298 }
299 }
300 }
301
302 struct _Py_stat_struct sb;
303 if (_Py_fstat_noraise(fileno(fp), &sb) == 0 && S_ISDIR(sb.st_mode)) {
304 fprintf(stderr,
305 "%ls: '%ls' is a directory, cannot continue\n",
Victor Stinnerfed02e12019-05-17 11:12:09 +0200306 config->program_name, filename);
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100307 fclose(fp);
308 return 1;
309 }
310
311 /* call pending calls like signal handlers (SIGINT) */
312 if (Py_MakePendingCalls() == -1) {
313 PyErr_Print();
314 fclose(fp);
315 return 1;
316 }
317
318 PyObject *unicode, *bytes = NULL;
319 const char *filename_str;
320
321 unicode = PyUnicode_FromWideChar(filename, wcslen(filename));
322 if (unicode != NULL) {
323 bytes = PyUnicode_EncodeFSDefault(unicode);
324 Py_DECREF(unicode);
325 }
326 if (bytes != NULL) {
327 filename_str = PyBytes_AsString(bytes);
328 }
329 else {
330 PyErr_Clear();
331 filename_str = "<filename encoding error>";
332 }
333
334 /* PyRun_AnyFileExFlags(closeit=1) calls fclose(fp) before running code */
335 int run = PyRun_AnyFileExFlags(fp, filename_str, 1, cf);
336 Py_XDECREF(bytes);
337 return (run != 0);
338}
339
340
341static void
342pymain_run_startup(_PyCoreConfig *config, PyCompilerFlags *cf)
343{
Victor Stinner20004952019-03-26 02:31:11 +0100344 const char *startup = _Py_GetEnv(config->use_environment, "PYTHONSTARTUP");
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100345 if (startup == NULL) {
346 return;
347 }
348
349 FILE *fp = _Py_fopen(startup, "r");
350 if (fp == NULL) {
351 int save_errno = errno;
352 PySys_WriteStderr("Could not open PYTHONSTARTUP\n");
353 errno = save_errno;
354
355 PyErr_SetFromErrnoWithFilename(PyExc_OSError,
356 startup);
357 PyErr_Print();
358 return;
359 }
360
361 (void) PyRun_SimpleFileExFlags(fp, startup, 0, cf);
362 PyErr_Clear();
363 fclose(fp);
364}
365
366
367static void
368pymain_run_interactive_hook(void)
369{
370 PyObject *sys, *hook, *result;
371 sys = PyImport_ImportModule("sys");
372 if (sys == NULL) {
373 goto error;
374 }
375
376 hook = PyObject_GetAttrString(sys, "__interactivehook__");
377 Py_DECREF(sys);
378 if (hook == NULL) {
379 PyErr_Clear();
380 return;
381 }
382
383 result = _PyObject_CallNoArg(hook);
384 Py_DECREF(hook);
385 if (result == NULL) {
386 goto error;
387 }
388 Py_DECREF(result);
389
390 return;
391
392error:
393 PySys_WriteStderr("Failed calling sys.__interactivehook__\n");
394 PyErr_Print();
395}
396
397
398static int
399pymain_run_stdin(_PyCoreConfig *config, PyCompilerFlags *cf)
400{
401 if (stdin_is_interactive(config)) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100402 config->inspect = 0;
Victor Stinnerc96be812019-05-14 17:34:56 +0200403 Py_InspectFlag = 0; /* do exit on SystemExit */
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100404 pymain_run_startup(config, cf);
405 pymain_run_interactive_hook();
406 }
407
408 /* call pending calls like signal handlers (SIGINT) */
409 if (Py_MakePendingCalls() == -1) {
410 PyErr_Print();
411 return 1;
412 }
413
414 int run = PyRun_AnyFileExFlags(stdin, "<stdin>", 0, cf);
415 return (run != 0);
416}
417
418
419static void
420pymain_repl(_PyCoreConfig *config, PyCompilerFlags *cf, int *exitcode)
421{
422 /* Check this environment variable at the end, to give programs the
423 opportunity to set it from Python. */
Victor Stinnerc96be812019-05-14 17:34:56 +0200424 if (!config->inspect && _Py_GetEnv(config->use_environment, "PYTHONINSPECT")) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100425 config->inspect = 1;
Victor Stinnerc96be812019-05-14 17:34:56 +0200426 Py_InspectFlag = 1;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100427 }
428
Victor Stinnerc96be812019-05-14 17:34:56 +0200429 if (!(config->inspect && stdin_is_interactive(config) && RUN_CODE(config))) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100430 return;
431 }
432
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100433 config->inspect = 0;
Victor Stinnerc96be812019-05-14 17:34:56 +0200434 Py_InspectFlag = 0;
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100435 pymain_run_interactive_hook();
436
437 int res = PyRun_AnyFileFlags(stdin, "<stdin>", cf);
438 *exitcode = (res != 0);
439}
440
441
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200442static void
Victor Stinner5ac27a52019-03-27 13:40:14 +0100443pymain_run_python(int *exitcode)
Victor Stinnerb5fd9ad2017-12-14 02:20:52 +0100444{
Victor Stinner5ac27a52019-03-27 13:40:14 +0100445 PyInterpreterState *interp = _PyInterpreterState_GET_UNSAFE();
446 /* pymain_run_stdin() modify the config */
Victor Stinnerd3b19192018-07-25 10:21:03 +0200447 _PyCoreConfig *config = &interp->core_config;
448
449 PyObject *main_importer_path = NULL;
Victor Stinner62be7632019-03-01 13:10:14 +0100450 if (config->run_filename != NULL) {
Victor Stinnerd5dda982017-12-13 17:31:16 +0100451 /* If filename is a package (ex: directory or ZIP file) which contains
452 __main__.py, main_importer_path is set to filename and will be
Victor Stinnerd3b19192018-07-25 10:21:03 +0200453 prepended to sys.path.
454
455 Otherwise, main_importer_path is set to NULL. */
Victor Stinner62be7632019-03-01 13:10:14 +0100456 main_importer_path = pymain_get_importer(config->run_filename);
Victor Stinnerd5dda982017-12-13 17:31:16 +0100457 }
458
Victor Stinnerd3b19192018-07-25 10:21:03 +0200459 if (main_importer_path != NULL) {
460 if (pymain_sys_path_add_path0(interp, main_importer_path) < 0) {
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200461 goto error;
Victor Stinnerd3b19192018-07-25 10:21:03 +0200462 }
Victor Stinnerd5dda982017-12-13 17:31:16 +0100463 }
Victor Stinner20004952019-03-26 02:31:11 +0100464 else if (!config->isolated) {
Victor Stinnerdcf61712019-03-19 16:09:27 +0100465 PyObject *path0 = NULL;
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200466 int res = _PyPathConfig_ComputeSysPath0(&config->argv, &path0);
467 if (res < 0) {
468 goto error;
469 }
Victor Stinner19760862017-12-20 01:41:59 +0100470
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200471 if (res > 0) {
Victor Stinnerdcf61712019-03-19 16:09:27 +0100472 if (pymain_sys_path_add_path0(interp, path0) < 0) {
473 Py_DECREF(path0);
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200474 goto error;
Victor Stinnerdcf61712019-03-19 16:09:27 +0100475 }
Victor Stinner19760862017-12-20 01:41:59 +0100476 Py_DECREF(path0);
Victor Stinner19760862017-12-20 01:41:59 +0100477 }
Victor Stinner19760862017-12-20 01:41:59 +0100478 }
Victor Stinnera7368ac2017-11-15 18:11:45 -0800479
Guido van Rossum495da292019-03-07 12:38:08 -0800480 PyCompilerFlags cf = {.cf_flags = 0, .cf_feature_version = PY_MINOR_VERSION};
Victor Stinnera7368ac2017-11-15 18:11:45 -0800481
Victor Stinner62be7632019-03-01 13:10:14 +0100482 pymain_header(config);
483 pymain_import_readline(config);
Victor Stinnera7368ac2017-11-15 18:11:45 -0800484
Victor Stinner62be7632019-03-01 13:10:14 +0100485 if (config->run_command) {
486 *exitcode = pymain_run_command(config->run_command, &cf);
Victor Stinnera7368ac2017-11-15 18:11:45 -0800487 }
Victor Stinner62be7632019-03-01 13:10:14 +0100488 else if (config->run_module) {
489 *exitcode = (pymain_run_module(config->run_module, 1) != 0);
Victor Stinnera7368ac2017-11-15 18:11:45 -0800490 }
Victor Stinnerd3b19192018-07-25 10:21:03 +0200491 else if (main_importer_path != NULL) {
492 int sts = pymain_run_module(L"__main__", 0);
Victor Stinnerdfe88472019-03-01 12:14:41 +0100493 *exitcode = (sts != 0);
Victor Stinnerd3b19192018-07-25 10:21:03 +0200494 }
Victor Stinner62be7632019-03-01 13:10:14 +0100495 else if (config->run_filename != NULL) {
496 *exitcode = pymain_run_file(config, &cf);
Victor Stinner72ec3192018-08-02 19:34:20 +0200497 }
Victor Stinnera7368ac2017-11-15 18:11:45 -0800498 else {
Victor Stinner62be7632019-03-01 13:10:14 +0100499 *exitcode = pymain_run_stdin(config, &cf);
Victor Stinnera7368ac2017-11-15 18:11:45 -0800500 }
Victor Stinner9cfc0022017-12-20 19:36:46 +0100501
Victor Stinner62be7632019-03-01 13:10:14 +0100502 pymain_repl(config, &cf, exitcode);
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200503 goto done;
504
505error:
506 PyErr_Print();
507 *exitcode = 1;
Victor Stinnerd3b19192018-07-25 10:21:03 +0200508
509done:
510 Py_XDECREF(main_importer_path);
Victor Stinnerf7e5b562017-11-15 15:48:08 -0800511}
512
Victor Stinnera7368ac2017-11-15 18:11:45 -0800513
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100514/* --- pymain_main() ---------------------------------------------- */
515
516static void
517pymain_free(void)
Victor Stinnerf7e5b562017-11-15 15:48:08 -0800518{
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100519 _PyImport_Fini2();
Victor Stinner99fcc612019-04-29 13:04:07 +0200520
521 /* Free global variables which cannot be freed in Py_Finalize():
522 configuration options set before Py_Initialize() which should
523 remain valid after Py_Finalize(), since
524 Py_Initialize()-Py_Finalize() can be called multiple times. */
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100525 _PyPathConfig_ClearGlobal();
526 _Py_ClearStandardStreamEncoding();
527 _Py_ClearArgcArgv();
Victor Stinnerf5f336a2019-03-19 14:53:58 +0100528 _PyRuntime_Finalize();
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100529}
Victor Stinner94540602017-12-16 04:54:22 +0100530
Victor Stinner53b7d4e2018-07-25 01:37:05 +0200531
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100532static int
533exit_sigint(void)
534{
535 /* bpo-1054041: We need to exit via the
536 * SIG_DFL handler for SIGINT if KeyboardInterrupt went unhandled.
537 * If we don't, a calling process such as a shell may not know
538 * about the user's ^C. https://www.cons.org/cracauer/sigint.html */
539#if defined(HAVE_GETPID) && !defined(MS_WINDOWS)
540 if (PyOS_setsig(SIGINT, SIG_DFL) == SIG_ERR) {
541 perror("signal"); /* Impossible in normal environments. */
542 } else {
543 kill(getpid(), SIGINT);
Victor Stinner19760862017-12-20 01:41:59 +0100544 }
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100545 /* If setting SIG_DFL failed, or kill failed to terminate us,
546 * there isn't much else we can do aside from an error code. */
547#endif /* HAVE_GETPID && !MS_WINDOWS */
548#ifdef MS_WINDOWS
549 /* cmd.exe detects this, prints ^C, and offers to terminate. */
550 /* https://msdn.microsoft.com/en-us/library/cc704588.aspx */
551 return STATUS_CONTROL_C_EXIT;
552#else
553 return SIGINT + 128;
554#endif /* !MS_WINDOWS */
Victor Stinner1dc6e392018-07-25 02:49:17 +0200555}
556
557
Victor Stinner2f549082019-03-29 15:13:46 +0100558static void _Py_NO_RETURN
559pymain_exit_error(_PyInitError err)
Victor Stinner1dc6e392018-07-25 02:49:17 +0200560{
Victor Stinnerdb719752019-05-01 05:35:33 +0200561 if (_Py_INIT_IS_EXIT(err)) {
Victor Stinner4cb525a2019-04-26 13:05:47 +0200562 /* If it's an error rather than a regular exit, leave Python runtime
563 alive: _Py_ExitInitError() uses the current exception and use
564 sys.stdout in this case. */
565 pymain_free();
566 }
Victor Stinner2f549082019-03-29 15:13:46 +0100567 _Py_ExitInitError(err);
568}
Victor Stinner1dc6e392018-07-25 02:49:17 +0200569
Victor Stinnerdfe88472019-03-01 12:14:41 +0100570
Victor Stinner2f549082019-03-29 15:13:46 +0100571int
572_Py_RunMain(void)
573{
Victor Stinnerdfe88472019-03-01 12:14:41 +0100574 int exitcode = 0;
Victor Stinner2f549082019-03-29 15:13:46 +0100575
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200576 pymain_run_python(&exitcode);
Victor Stinnerae239f62019-05-16 17:02:56 +0200577
Victor Stinnerdfe88472019-03-01 12:14:41 +0100578 if (Py_FinalizeEx() < 0) {
579 /* Value unlikely to be confused with a non-error exit status or
580 other special meaning */
581 exitcode = 120;
Victor Stinner19760862017-12-20 01:41:59 +0100582 }
583
Victor Stinner62be7632019-03-01 13:10:14 +0100584 pymain_free();
Victor Stinner94540602017-12-16 04:54:22 +0100585
Gregory P. Smith38f11cc2019-02-16 12:57:40 -0800586 if (_Py_UnhandledKeyboardInterrupt) {
Victor Stinner95e2cbf2019-03-01 16:25:19 +0100587 exitcode = exit_sigint();
Gregory P. Smith38f11cc2019-02-16 12:57:40 -0800588 }
589
Victor Stinnerdfe88472019-03-01 12:14:41 +0100590 return exitcode;
Victor Stinner2f549082019-03-29 15:13:46 +0100591}
Victor Stinnerc1834442019-03-18 22:24:28 +0100592
Victor Stinner2f549082019-03-29 15:13:46 +0100593
594static int
595pymain_main(_PyArgv *args)
596{
597 _PyInitError err = pymain_init(args);
Victor Stinnerdbacfc22019-05-16 16:39:26 +0200598 if (_Py_INIT_IS_EXIT(err)) {
599 pymain_free();
600 return err.exitcode;
601 }
Victor Stinner2f549082019-03-29 15:13:46 +0100602 if (_Py_INIT_FAILED(err)) {
603 pymain_exit_error(err);
604 }
605
606 return _Py_RunMain();
Victor Stinner94540602017-12-16 04:54:22 +0100607}
608
609
Victor Stinnerf7e5b562017-11-15 15:48:08 -0800610int
611Py_Main(int argc, wchar_t **argv)
612{
Victor Stinner62be7632019-03-01 13:10:14 +0100613 _PyArgv args = {
614 .argc = argc,
615 .use_bytes_argv = 0,
616 .bytes_argv = NULL,
617 .wchar_argv = argv};
618 return pymain_main(&args);
Guido van Rossum667d7041995-08-04 04:20:48 +0000619}
620
Victor Stinner94540602017-12-16 04:54:22 +0100621
622int
623_Py_UnixMain(int argc, char **argv)
624{
Victor Stinner62be7632019-03-01 13:10:14 +0100625 _PyArgv args = {
626 .argc = argc,
627 .use_bytes_argv = 1,
628 .bytes_argv = argv,
629 .wchar_argv = NULL};
630 return pymain_main(&args);
Victor Stinner94540602017-12-16 04:54:22 +0100631}
632
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000633#ifdef __cplusplus
634}
635#endif