| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
1 parent ae239f6 commit 9ef5dca
10 files changed
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -398,10 +398,14 @@ typedef struct { | |||
| 398 | 398 | See PEP 552 "Deterministic pycs" for more details. */ | |
| 399 | 399 | wchar_t *check_hash_pycs_mode; | |
| 400 | 400 | ||
| 401 | - /* If greater than 0, suppress _PyPathConfig_Calculate() warnings. | ||
| 401 | + /* If greater than 0, suppress _PyPathConfig_Calculate() warnings on Unix. | ||
| 402 | + The parameter has no effect on Windows. | ||
| 402 | 403 | ||
| 403 | - If set to -1 (default), inherit Py_FrozenFlag value. */ | ||
| 404 | - int _frozen; | ||
| 404 | + If set to -1 (default), inherit !Py_FrozenFlag value. */ | ||
| 405 | + int pathconfig_warnings; | ||
| 406 | + | ||
| 407 | + /* If equal to 0, stop Python initialization before the "main" phase */ | ||
| 408 | + int _init_main; | ||
| 405 | 409 | ||
| 406 | 410 | } _PyCoreConfig; | |
| 407 | 411 | ||
@@ -438,7 +442,8 @@ typedef struct { | |||
| 438 | 442 | .buffered_stdio = -1, \ | |
| 439 | 443 | ._install_importlib = 1, \ | |
| 440 | 444 | .check_hash_pycs_mode = NULL, \ | |
| 441 | - ._frozen = -1} | ||
| 445 | + .pathconfig_warnings = -1, \ | ||
| 446 | + ._init_main = 1} | ||
| 442 | 447 | /* Note: _PyCoreConfig_INIT sets other fields to 0/NULL */ | |
| 443 | 448 | ||
| 444 | 449 | #ifdef __cplusplus | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -40,6 +40,7 @@ PyAPI_FUNC(_PyInitError) _Py_InitializeFromWideArgs( | |||
| 40 | 40 | const _PyCoreConfig *config, | |
| 41 | 41 | int argc, | |
| 42 | 42 | wchar_t **argv); | |
| 43 | + PyAPI_FUNC(_PyInitError) _Py_InitializeMain(void); | ||
| 43 | 44 | ||
| 44 | 45 | PyAPI_FUNC(int) _Py_RunMain(void); | |
| 45 | 46 | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -343,7 +343,8 @@ class InitConfigTests(EmbeddingTestsMixin, unittest.TestCase): | |||
| 343 | 343 | ||
| 344 | 344 | '_install_importlib': 1, | |
| 345 | 345 | 'check_hash_pycs_mode': 'default', | |
| 346 | - '_frozen': 0, | ||
| 346 | + 'pathconfig_warnings': 1, | ||
| 347 | + '_init_main': 1, | ||
| 347 | 348 | } | |
| 348 | 349 | if MS_WINDOWS: | |
| 349 | 350 | DEFAULT_PRE_CONFIG.update({ | |
@@ -371,7 +372,7 @@ class InitConfigTests(EmbeddingTestsMixin, unittest.TestCase): | |||
| 371 | 372 | ('Py_DontWriteBytecodeFlag', 'write_bytecode', True), | |
| 372 | 373 | ('Py_FileSystemDefaultEncodeErrors', 'filesystem_errors'), | |
| 373 | 374 | ('Py_FileSystemDefaultEncoding', 'filesystem_encoding'), | |
| 374 | - ('Py_FrozenFlag', '_frozen'), | ||
| 375 | + ('Py_FrozenFlag', 'pathconfig_warnings', True), | ||
| 375 | 376 | ('Py_IgnoreEnvironmentFlag', 'use_environment', True), | |
| 376 | 377 | ('Py_InspectFlag', 'inspect'), | |
| 377 | 378 | ('Py_InteractiveFlag', 'interactive'), | |
@@ -500,7 +501,8 @@ def check_global_config(self, config): | |||
| 500 | 501 | ||
| 501 | 502 | self.assertEqual(config['global_config'], expected) | |
| 502 | 503 | ||
| 503 | - def check_config(self, testname, expected_config, expected_preconfig, add_path=None): | ||
| 504 | + def check_config(self, testname, expected_config, expected_preconfig, | ||
| 505 | + add_path=None, stderr=None): | ||
| 504 | 506 | env = dict(os.environ) | |
| 505 | 507 | # Remove PYTHON* environment variables to get deterministic environment | |
| 506 | 508 | for key in list(env): | |
@@ -511,19 +513,22 @@ def check_config(self, testname, expected_config, expected_preconfig, add_path=N | |||
| 511 | 513 | env['PYTHONCOERCECLOCALE'] = '0' | |
| 512 | 514 | env['PYTHONUTF8'] = '0' | |
| 513 | 515 | ||
| 514 | - out, err = self.run_embedded_interpreter(testname, env=env) | ||
| 515 | - # Ignore err | ||
| 516 | - try: | ||
| 517 | - config = json.loads(out) | ||
| 518 | - except json.JSONDecodeError: | ||
| 519 | - self.fail(f"fail to decode stdout: {out!r}") | ||
| 520 | - | ||
| 521 | 516 | expected_preconfig = dict(self.DEFAULT_PRE_CONFIG, **expected_preconfig) | |
| 522 | 517 | expected_config = self.get_expected_config(expected_config, env, add_path) | |
| 523 | 518 | for key in self.COPY_PRE_CONFIG: | |
| 524 | 519 | if key not in expected_preconfig: | |
| 525 | 520 | expected_preconfig[key] = expected_config[key] | |
| 526 | 521 | ||
| 522 | + out, err = self.run_embedded_interpreter(testname, env=env) | ||
| 523 | + if stderr is None and not expected_config['verbose']: | ||
| 524 | + stderr = "" | ||
| 525 | + if stderr is not None: | ||
| 526 | + self.assertEqual(err.rstrip(), stderr) | ||
| 527 | + try: | ||
| 528 | + config = json.loads(out) | ||
| 529 | + except json.JSONDecodeError: | ||
| 530 | + self.fail(f"fail to decode stdout: {out!r}") | ||
| 531 | + | ||
| 527 | 532 | self.check_pre_config(config, expected_preconfig) | |
| 528 | 533 | self.check_core_config(config, expected_config) | |
| 529 | 534 | self.check_global_config(config) | |
@@ -689,7 +694,19 @@ def test_init_read_set(self): | |||
| 689 | 694 | self.check_config("init_read_set", core_config, preconfig, | |
| 690 | 695 | add_path="init_read_set_path") | |
| 691 | 696 | ||
| 692 | - def test_run_main_config(self): | ||
| 697 | + def test_init_run_main(self): | ||
| 698 | + preconfig = {} | ||
| 699 | + code = ('import _testinternalcapi, json; ' | ||
| 700 | + 'print(json.dumps(_testinternalcapi.get_configs()))') | ||
| 701 | + core_config = { | ||
| 702 | + 'argv': ['-c', 'arg2'], | ||
| 703 | + 'program': 'python3', | ||
| 704 | + 'program_name': './python3', | ||
| 705 | + 'run_command': code + '\n', | ||
| 706 | + } | ||
| 707 | + self.check_config("init_run_main", core_config, preconfig) | ||
| 708 | + | ||
| 709 | + def test_init_main(self): | ||
| 693 | 710 | preconfig = {} | |
| 694 | 711 | code = ('import _testinternalcapi, json; ' | |
| 695 | 712 | 'print(json.dumps(_testinternalcapi.get_configs()))') | |
@@ -698,8 +715,10 @@ def test_run_main_config(self): | |||
| 698 | 715 | 'program': 'python3', | |
| 699 | 716 | 'program_name': './python3', | |
| 700 | 717 | 'run_command': code + '\n', | |
| 718 | + '_init_main': 0, | ||
| 701 | 719 | } | |
| 702 | - self.check_config("run_main_config", core_config, preconfig) | ||
| 720 | + self.check_config("init_main", core_config, preconfig, | ||
| 721 | + stderr="Run Python code before _Py_InitializeMain") | ||
| 703 | 722 | ||
| 704 | 723 | def test_init_dont_parse_argv(self): | |
| 705 | 724 | core_config = { | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -493,7 +493,7 @@ calculate_prefix(const _PyCoreConfig *core_config, | |||
| 493 | 493 | } | |
| 494 | 494 | ||
| 495 | 495 | if (!calculate->prefix_found) { | |
| 496 | - if (!core_config->_frozen) { | ||
| 496 | + if (core_config->pathconfig_warnings) { | ||
| 497 | 497 | fprintf(stderr, | |
| 498 | 498 | "Could not find platform independent libraries <prefix>\n"); | |
| 499 | 499 | } | |
@@ -681,7 +681,7 @@ calculate_exec_prefix(const _PyCoreConfig *core_config, | |||
| 681 | 681 | } | |
| 682 | 682 | ||
| 683 | 683 | if (!calculate->exec_prefix_found) { | |
| 684 | - if (!core_config->_frozen) { | ||
| 684 | + if (core_config->pathconfig_warnings) { | ||
| 685 | 685 | fprintf(stderr, | |
| 686 | 686 | "Could not find platform dependent libraries <exec_prefix>\n"); | |
| 687 | 687 | } | |
@@ -1206,7 +1206,7 @@ calculate_path_impl(const _PyCoreConfig *core_config, | |||
| 1206 | 1206 | } | |
| 1207 | 1207 | ||
| 1208 | 1208 | if ((!calculate->prefix_found || !calculate->exec_prefix_found) && | |
| 1209 | - !core_config->_frozen) | ||
| 1209 | + core_config->pathconfig_warnings) | ||
| 1210 | 1210 | { | |
| 1211 | 1211 | fprintf(stderr, | |
| 1212 | 1212 | "Consider setting $PYTHONHOME to <prefix>[:<exec_prefix>]\n"); | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -83,7 +83,8 @@ main(int argc, char *argv[]) | |||
| 83 | 83 | config.program_name = L"./_freeze_importlib"; | |
| 84 | 84 | /* Don't install importlib, since it could execute outdated bytecode. */ | |
| 85 | 85 | config._install_importlib = 0; | |
| 86 | - config._frozen = 1; | ||
| 86 | + config.pathconfig_warnings = 0; | ||
| 87 | + config._init_main = 0; | ||
| 87 | 88 | ||
| 88 | 89 | _PyInitError err = _Py_InitializeFromConfig(&config); | |
| 89 | 90 | /* No need to call _PyCoreConfig_Clear() since we didn't allocate any | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -757,34 +757,71 @@ static int test_init_read_set(void) | |||
| 757 | 757 | } | |
| 758 | 758 | ||
| 759 | 759 | ||
| 760 | - static int test_run_main(void) | ||
| 760 | + wchar_t *init_main_argv[] = { | ||
| 761 | + L"python3", L"-c", | ||
| 762 | + (L"import _testinternalcapi, json; " | ||
| 763 | + L"print(json.dumps(_testinternalcapi.get_configs()))"), | ||
| 764 | + L"arg2"}; | ||
| 765 | + | ||
| 766 | + | ||
| 767 | + static void configure_init_main(_PyCoreConfig *config) | ||
| 768 | + { | ||
| 769 | + config->argv.length = Py_ARRAY_LENGTH(init_main_argv); | ||
| 770 | + config->argv.items = init_main_argv; | ||
| 771 | + config->program_name = L"./python3"; | ||
| 772 | + } | ||
| 773 | + | ||
| 774 | + | ||
| 775 | + static int test_init_run_main(void) | ||
| 761 | 776 | { | |
| 762 | 777 | _PyCoreConfig config = _PyCoreConfig_INIT; | |
| 778 | + configure_init_main(&config); | ||
| 779 | + | ||
| 780 | + _PyInitError err = _Py_InitializeFromConfig(&config); | ||
| 781 | + if (_Py_INIT_FAILED(err)) { | ||
| 782 | + _Py_ExitInitError(err); | ||
| 783 | + } | ||
| 784 | + | ||
| 785 | + return _Py_RunMain(); | ||
| 786 | + } | ||
| 763 | 787 | ||
| 764 | - wchar_t *argv[] = {L"python3", L"-c", | ||
| 765 | - (L"import sys; " | ||
| 766 | - L"print(f'_Py_RunMain(): sys.argv={sys.argv}')"), | ||
| 767 | - L"arg2"}; | ||
| 768 | - config.argv.length = Py_ARRAY_LENGTH(argv); | ||
| 769 | - config.argv.items = argv; | ||
| 770 | - config.program_name = L"./python3"; | ||
| 788 | + | ||
| 789 | + static int test_init_main(void) | ||
| 790 | + { | ||
| 791 | + _PyCoreConfig config = _PyCoreConfig_INIT; | ||
| 792 | + configure_init_main(&config); | ||
| 793 | + config._init_main = 0; | ||
| 771 | 794 | ||
| 772 | 795 | _PyInitError err = _Py_InitializeFromConfig(&config); | |
| 773 | 796 | if (_Py_INIT_FAILED(err)) { | |
| 774 | 797 | _Py_ExitInitError(err); | |
| 775 | 798 | } | |
| 776 | 799 | ||
| 800 | + /* sys.stdout don't exist yet: it is created by _Py_InitializeMain() */ | ||
| 801 | + int res = PyRun_SimpleString( | ||
| 802 | + "import sys; " | ||
| 803 | + "print('Run Python code before _Py_InitializeMain', " | ||
| 804 | + "file=sys.stderr)"); | ||
| 805 | + if (res < 0) { | ||
| 806 | + exit(1); | ||
| 807 | + } | ||
| 808 | + | ||
| 809 | + err = _Py_InitializeMain(); | ||
| 810 | + if (_Py_INIT_FAILED(err)) { | ||
| 811 | + _Py_ExitInitError(err); | ||
| 812 | + } | ||
| 813 | + | ||
| 777 | 814 | return _Py_RunMain(); | |
| 778 | 815 | } | |
| 779 | 816 | ||
| 780 | 817 | ||
| 781 | - static int test_run_main_config(void) | ||
| 818 | + static int test_run_main(void) | ||
| 782 | 819 | { | |
| 783 | 820 | _PyCoreConfig config = _PyCoreConfig_INIT; | |
| 784 | 821 | ||
| 785 | 822 | wchar_t *argv[] = {L"python3", L"-c", | |
| 786 | - (L"import _testinternalcapi, json; " | ||
| 787 | - L"print(json.dumps(_testinternalcapi.get_configs()))"), | ||
| 823 | + (L"import sys; " | ||
| 824 | + L"print(f'_Py_RunMain(): sys.argv={sys.argv}')"), | ||
| 788 | 825 | L"arg2"}; | |
| 789 | 826 | config.argv.length = Py_ARRAY_LENGTH(argv); | |
| 790 | 827 | config.argv.items = argv; | |
@@ -837,8 +874,9 @@ static struct TestCase TestCases[] = { | |||
| 837 | 874 | { "preinit_isolated1", test_preinit_isolated1 }, | |
| 838 | 875 | { "preinit_isolated2", test_preinit_isolated2 }, | |
| 839 | 876 | { "init_read_set", test_init_read_set }, | |
| 877 | + { "init_run_main", test_init_run_main }, | ||
| 878 | + { "init_main", test_init_main }, | ||
| 840 | 879 | { "run_main", test_run_main }, | |
| 841 | - { "run_main_config", test_run_main_config }, | ||
| 842 | 880 | { NULL, NULL } | |
| 843 | 881 | }; | |
| 844 | 882 | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -667,7 +667,8 @@ _PyCoreConfig_Copy(_PyCoreConfig *config, const _PyCoreConfig *config2) | |||
| 667 | 667 | COPY_WSTR_ATTR(run_module); | |
| 668 | 668 | COPY_WSTR_ATTR(run_filename); | |
| 669 | 669 | COPY_WSTR_ATTR(check_hash_pycs_mode); | |
| 670 | - COPY_ATTR(_frozen); | ||
| 670 | + COPY_ATTR(pathconfig_warnings); | ||
| 671 | + COPY_ATTR(_init_main); | ||
| 671 | 672 | ||
| 672 | 673 | #undef COPY_ATTR | |
| 673 | 674 | #undef COPY_WSTR_ATTR | |
@@ -766,7 +767,8 @@ _PyCoreConfig_AsDict(const _PyCoreConfig *config) | |||
| 766 | 767 | SET_ITEM_WSTR(run_filename); | |
| 767 | 768 | SET_ITEM_INT(_install_importlib); | |
| 768 | 769 | SET_ITEM_WSTR(check_hash_pycs_mode); | |
| 769 | - SET_ITEM_INT(_frozen); | ||
| 770 | + SET_ITEM_INT(pathconfig_warnings); | ||
| 771 | + SET_ITEM_INT(_init_main); | ||
| 770 | 772 | ||
| 771 | 773 | return dict; | |
| 772 | 774 | ||
@@ -855,7 +857,7 @@ _PyCoreConfig_GetGlobalConfig(_PyCoreConfig *config) | |||
| 855 | 857 | #ifdef MS_WINDOWS | |
| 856 | 858 | COPY_FLAG(legacy_windows_stdio, Py_LegacyWindowsStdioFlag); | |
| 857 | 859 | #endif | |
| 858 | - COPY_FLAG(_frozen, Py_FrozenFlag); | ||
| 860 | + COPY_NOT_FLAG(pathconfig_warnings, Py_FrozenFlag); | ||
| 859 | 861 | ||
| 860 | 862 | COPY_NOT_FLAG(buffered_stdio, Py_UnbufferedStdioFlag); | |
| 861 | 863 | COPY_NOT_FLAG(site_import, Py_NoSiteFlag); | |
@@ -892,7 +894,7 @@ _PyCoreConfig_SetGlobalConfig(const _PyCoreConfig *config) | |||
| 892 | 894 | #ifdef MS_WINDOWS | |
| 893 | 895 | COPY_FLAG(legacy_windows_stdio, Py_LegacyWindowsStdioFlag); | |
| 894 | 896 | #endif | |
| 895 | - COPY_FLAG(_frozen, Py_FrozenFlag); | ||
| 897 | + COPY_NOT_FLAG(pathconfig_warnings, Py_FrozenFlag); | ||
| 896 | 898 | ||
| 897 | 899 | COPY_NOT_FLAG(buffered_stdio, Py_UnbufferedStdioFlag); | |
| 898 | 900 | COPY_NOT_FLAG(site_import, Py_NoSiteFlag); | |
@@ -2253,7 +2255,7 @@ _PyCoreConfig_Read(_PyCoreConfig *config) | |||
| 2253 | 2255 | assert(!(config->run_command != NULL && config->run_module != NULL)); | |
| 2254 | 2256 | assert(config->check_hash_pycs_mode != NULL); | |
| 2255 | 2257 | assert(config->_install_importlib >= 0); | |
| 2256 | - assert(config->_frozen >= 0); | ||
| 2258 | + assert(config->pathconfig_warnings >= 0); | ||
| 2257 | 2259 | ||
| 2258 | 2260 | err = _Py_INIT_OK(); | |
| 2259 | 2261 | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -40,7 +40,7 @@ Py_FrozenMain(int argc, char **argv) | |||
| 40 | 40 | } | |
| 41 | 41 | ||
| 42 | 42 | _PyCoreConfig config = _PyCoreConfig_INIT; | |
| 43 | - config._frozen = 1; /* Suppress errors from getpath.c */ | ||
| 43 | + config.pathconfig_warnings = 0; /* Suppress errors from getpath.c */ | ||
| 44 | 44 | ||
| 45 | 45 | if ((p = Py_GETENV("PYTHONINSPECT")) && *p != '\0') | |
| 46 | 46 | inspect = 1; | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -970,6 +970,21 @@ _Py_InitializeMainInterpreter(_PyRuntimeState *runtime, | |||
| 970 | 970 | return _Py_INIT_OK(); | |
| 971 | 971 | } | |
| 972 | 972 | ||
| 973 | + | ||
| 974 | + _PyInitError | ||
| 975 | + _Py_InitializeMain(void) | ||
| 976 | + { | ||
| 977 | + _PyInitError err = _PyRuntime_Initialize(); | ||
| 978 | + if (_Py_INIT_FAILED(err)) { | ||
| 979 | + return err; | ||
| 980 | + } | ||
| 981 | + _PyRuntimeState *runtime = &_PyRuntime; | ||
| 982 | + PyInterpreterState *interp = _PyRuntimeState_GetThreadState(runtime)->interp; | ||
| 983 | + | ||
| 984 | + return _Py_InitializeMainInterpreter(runtime, interp); | ||
| 985 | + } | ||
| 986 | + | ||
| 987 | + | ||
| 973 | 988 | #undef _INIT_DEBUG_PRINT | |
| 974 | 989 | ||
| 975 | 990 | static _PyInitError | |
@@ -990,7 +1005,7 @@ init_python(const _PyCoreConfig *config, const _PyArgv *args) | |||
| 990 | 1005 | } | |
| 991 | 1006 | config = &interp->core_config; | |
| 992 | 1007 | ||
| 993 | - if (!config->_frozen) { | ||
| 1008 | + if (config->_init_main) { | ||
| 994 | 1009 | err = _Py_InitializeMainInterpreter(runtime, interp); | |
| 995 | 1010 | if (_Py_INIT_FAILED(err)) { | |
| 996 | 1011 | return err; | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1046,6 +1046,15 @@ run_eval_code_obj(PyCodeObject *co, PyObject *globals, PyObject *locals) | |||
| 1046 | 1046 | * Py_Main() based one. | |
| 1047 | 1047 | */ | |
| 1048 | 1048 | _Py_UnhandledKeyboardInterrupt = 0; | |
| 1049 | + | ||
| 1050 | + /* Set globals['__builtins__'] if it doesn't exist */ | ||
| 1051 | + if (globals != NULL && PyDict_GetItemString(globals, "__builtins__") == NULL) { | ||
| 1052 | + PyInterpreterState *interp = _PyInterpreterState_Get(); | ||
| 1053 | + if (PyDict_SetItemString(globals, "__builtins__", interp->builtins) < 0) { | ||
| 1054 | + return NULL; | ||
| 1055 | + } | ||
| 1056 | + } | ||
| 1057 | + | ||
| 1049 | 1058 | v = PyEval_EvalCode((PyObject*)co, globals, locals); | |
| 1050 | 1059 | if (!v && PyErr_Occurred() == PyExc_KeyboardInterrupt) { | |
| 1051 | 1060 | _Py_UnhandledKeyboardInterrupt = 1; | |
| Back | FazBrowse Home | New Git URL |
0 commit comments