From 9852cb38112a4f8d11e26c3423643ea994d5a14f Mon Sep 17 00:00:00 2001 From: Victor Stinner Date: Mon, 25 Jan 2021 23:12:50 +0100 Subject: bpo-42955: Rename module_names to sys.stdlib_module_names (GH-24332) * Rename _Py_module_names to _Py_stdlib_module_names. * Rename Python/module_names.h to Python/stdlib_module_names.h. --- .github/workflows/build.yml | 2 +- .travis.yml | 2 +- Doc/library/sys.rst | 38 +-- Doc/whatsnew/3.10.rst | 2 +- Lib/test/test_capi.py | 2 +- Lib/test/test_faulthandler.py | 2 +- Lib/test/test_sys.py | 4 +- Makefile.pre.in | 18 +- .../2021-01-18-11-59-46.bpo-42955.CSWLC9.rst | 2 +- PCbuild/pythoncore.vcxproj | 2 +- PCbuild/pythoncore.vcxproj.filters | 2 +- Python/module_names.h | 317 --------------------- Python/pylifecycle.c | 20 +- Python/stdlib_module_names.h | 317 +++++++++++++++++++++ Python/sysmodule.c | 10 +- Tools/scripts/generate_module_names.py | 150 ---------- Tools/scripts/generate_stdlib_module_names.py | 151 ++++++++++ 17 files changed, 521 insertions(+), 520 deletions(-) delete mode 100644 Python/module_names.h create mode 100644 Python/stdlib_module_names.h delete mode 100644 Tools/scripts/generate_module_names.py create mode 100644 Tools/scripts/generate_stdlib_module_names.py diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 6a41b51..48b5825 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -63,7 +63,7 @@ jobs: # Build Python with the libpython dynamic library ./configure --with-pydebug --enable-shared make -j4 regen-all - make regen-module-names + make regen-stdlib-module-names - name: Check for changes run: | changes=$(git status --porcelain) diff --git a/.travis.yml b/.travis.yml index c908891..6a22d20 100644 --- a/.travis.yml +++ b/.travis.yml @@ -172,7 +172,7 @@ before_script: - eval "$(pyenv init -)" - pyenv global 3.8 - PYTHON_FOR_REGEN=python3.8 make -j4 regen-all - - make regen-module-names + - make regen-stdlib-module-names - changes=`git status --porcelain` - | # Check for changes in regenerated files diff --git a/Doc/library/sys.rst b/Doc/library/sys.rst index f187895..0219ae8 100644 --- a/Doc/library/sys.rst +++ b/Doc/library/sys.rst @@ -157,7 +157,7 @@ always available. Python interpreter. (This information is not available in any other way --- ``modules.keys()`` only lists the imported modules.) - See also the :attr:`sys.module_names` list. + See also the :attr:`sys.stdlib_module_names` list. .. function:: call_tracing(func, args) @@ -1062,24 +1062,6 @@ always available. This is still called as a fallback if a :data:`meta_path` entry doesn't have a :meth:`~importlib.abc.MetaPathFinder.find_spec` method. -.. data:: module_names - - A frozenset of strings containing the names of standard library modules. - - It is the same on all platforms. Modules which are not available on - some platforms and modules disabled at Python build are also listed. - All module kinds are listed: pure Python, built-in, frozen and extension - modules. Test modules are excluded. - - For packages, only sub-packages are listed, not sub-modules. For example, - ``concurrent`` package and ``concurrent.futures`` sub-package are listed, - but not ``concurrent.futures.base`` sub-module. - - See also the :attr:`sys.builtin_module_names` list. - - .. versionadded:: 3.10 - - .. data:: modules This is a dictionary that maps module names to modules which have already been @@ -1584,6 +1566,24 @@ always available. to a console and Python apps started with :program:`pythonw`. +.. data:: stdlib_module_names + + A frozenset of strings containing the names of standard library modules. + + It is the same on all platforms. Modules which are not available on + some platforms and modules disabled at Python build are also listed. + All module kinds are listed: pure Python, built-in, frozen and extension + modules. Test modules are excluded. + + For packages, only sub-packages are listed, not sub-modules. For example, + ``concurrent`` package and ``concurrent.futures`` sub-package are listed, + but not ``concurrent.futures.base`` sub-module. + + See also the :attr:`sys.builtin_module_names` list. + + .. versionadded:: 3.10 + + .. data:: thread_info A :term:`named tuple` holding information about the thread diff --git a/Doc/whatsnew/3.10.rst b/Doc/whatsnew/3.10.rst index 3026a1a..30a8281 100644 --- a/Doc/whatsnew/3.10.rst +++ b/Doc/whatsnew/3.10.rst @@ -396,7 +396,7 @@ Add :data:`sys.orig_argv` attribute: the list of the original command line arguments passed to the Python executable. (Contributed by Victor Stinner in :issue:`23427`.) -Add :data:`sys.module_names`, containing the list of the standard library +Add :data:`sys.stdlib_module_names`, containing the list of the standard library module names. (Contributed by Victor Stinner in :issue:`42955`.) diff --git a/Lib/test/test_capi.py b/Lib/test/test_capi.py index 5f5c0d0..8e92a50 100644 --- a/Lib/test/test_capi.py +++ b/Lib/test/test_capi.py @@ -581,7 +581,7 @@ class CAPITest(unittest.TestCase): not_expected = ('_testcapi',) code = textwrap.dedent(''' import _testcapi, sys - sys.module_names = frozenset({"_testcapi"}) + sys.stdlib_module_names = frozenset({"_testcapi"}) _testcapi.fatal_error(b"MESSAGE") ''') self.check_fatal_error(code, expected) diff --git a/Lib/test/test_faulthandler.py b/Lib/test/test_faulthandler.py index 02077a6..6486244 100644 --- a/Lib/test/test_faulthandler.py +++ b/Lib/test/test_faulthandler.py @@ -336,7 +336,7 @@ class FaultHandlerTests(unittest.TestCase): import faulthandler import sys # Don't filter stdlib module names - sys.module_names = frozenset() + sys.stdlib_module_names = frozenset() faulthandler.enable() faulthandler._sigsegv() """ diff --git a/Lib/test/test_sys.py b/Lib/test/test_sys.py index 729b866..c4e0535 100644 --- a/Lib/test/test_sys.py +++ b/Lib/test/test_sys.py @@ -987,8 +987,8 @@ class SysModuleTest(unittest.TestCase): proc) def test_module_names(self): - self.assertIsInstance(sys.module_names, frozenset) - for name in sys.module_names: + self.assertIsInstance(sys.stdlib_module_names, frozenset) + for name in sys.stdlib_module_names: self.assertIsInstance(name, str) diff --git a/Makefile.pre.in b/Makefile.pre.in index ca6b518..0b22bdd 100644 --- a/Makefile.pre.in +++ b/Makefile.pre.in @@ -760,7 +760,7 @@ regen-all: regen-opcode regen-opcode-targets regen-typeslots \ regen-token regen-ast regen-keyword regen-importlib clinic \ regen-pegen-metaparser regen-pegen @echo - @echo "Note: make regen-module-names and autoconf should be run manually" + @echo "Note: make regen-stdlib-module-names and autoconf should be run manually" ############################################################################ # Special rules for object files @@ -900,14 +900,14 @@ regen-keyword: $(srcdir)/Lib/keyword.py.new $(UPDATE_FILE) $(srcdir)/Lib/keyword.py $(srcdir)/Lib/keyword.py.new -.PHONY: regen-module-names -regen-module-names: build_all - # Regenerate Python/module_names.h - # using Tools/scripts/generate_module_names.py +.PHONY: regen-stdlib-module-names +regen-stdlib-module-names: build_all + # Regenerate Python/stdlib_module_names.h + # using Tools/scripts/generate_stdlib_module_names.py $(RUNSHARED) ./$(BUILDPYTHON) \ - $(srcdir)/Tools/scripts/generate_module_names.py \ - > $(srcdir)/Python/module_names.h.new - $(UPDATE_FILE) $(srcdir)/Python/module_names.h $(srcdir)/Python/module_names.h.new + $(srcdir)/Tools/scripts/generate_stdlib_module_names.py \ + > $(srcdir)/Python/stdlib_module_names.h.new + $(UPDATE_FILE) $(srcdir)/Python/stdlib_module_names.h $(srcdir)/Python/stdlib_module_names.h.new Python/compile.o Python/symtable.o Python/ast_unparse.o Python/ast.o Python/future.o: $(srcdir)/Include/Python-ast.h @@ -1160,7 +1160,7 @@ PYTHON_HEADERS= \ $(srcdir)/Include/internal/pycore_warnings.h \ $(DTRACE_HEADERS) \ \ - $(srcdir)/Python/module_names.h + $(srcdir)/Python/stdlib_module_names.h $(LIBRARY_OBJS) $(MODOBJS) Programs/python.o: $(PYTHON_HEADERS) diff --git a/Misc/NEWS.d/next/Library/2021-01-18-11-59-46.bpo-42955.CSWLC9.rst b/Misc/NEWS.d/next/Library/2021-01-18-11-59-46.bpo-42955.CSWLC9.rst index 0631acd..373b829 100644 --- a/Misc/NEWS.d/next/Library/2021-01-18-11-59-46.bpo-42955.CSWLC9.rst +++ b/Misc/NEWS.d/next/Library/2021-01-18-11-59-46.bpo-42955.CSWLC9.rst @@ -1,2 +1,2 @@ -Add :data:`sys.module_names`, containing the list of the standard library +Add :data:`sys.stdlib_module_names`, containing the list of the standard library module names. Patch by Victor Stinner. diff --git a/PCbuild/pythoncore.vcxproj b/PCbuild/pythoncore.vcxproj index 6a260da..f172f2a 100644 --- a/PCbuild/pythoncore.vcxproj +++ b/PCbuild/pythoncore.vcxproj @@ -291,7 +291,7 @@ - + diff --git a/PCbuild/pythoncore.vcxproj.filters b/PCbuild/pythoncore.vcxproj.filters index 98e3ca2..3bafdb8 100644 --- a/PCbuild/pythoncore.vcxproj.filters +++ b/PCbuild/pythoncore.vcxproj.filters @@ -360,7 +360,7 @@ Python - + Python diff --git a/Python/module_names.h b/Python/module_names.h deleted file mode 100644 index 0dc2633..0000000 --- a/Python/module_names.h +++ /dev/null @@ -1,317 +0,0 @@ -// Auto-generated by Tools/scripts/generate_module_names.py. -// List used to create sys.module_names. - -static const char* _Py_module_names[] = { -"__future__", -"_abc", -"_aix_support", -"_ast", -"_asyncio", -"_bisect", -"_blake2", -"_bootsubprocess", -"_bz2", -"_codecs", -"_codecs_cn", -"_codecs_hk", -"_codecs_iso2022", -"_codecs_jp", -"_codecs_kr", -"_codecs_tw", -"_collections", -"_collections_abc", -"_compat_pickle", -"_compression", -"_contextvars", -"_crypt", -"_csv", -"_ctypes", -"_curses", -"_curses_panel", -"_datetime", -"_dbm", -"_decimal", -"_elementtree", -"_functools", -"_gdbm", -"_hashlib", -"_heapq", -"_imp", -"_io", -"_json", -"_locale", -"_lsprof", -"_lzma", -"_markupbase", -"_md5", -"_msi", -"_multibytecodec", -"_multiprocessing", -"_opcode", -"_operator", -"_osx_support", -"_pickle", -"_posixshmem", -"_posixsubprocess", -"_py_abc", -"_pydecimal", -"_pyio", -"_queue", -"_random", -"_sha1", -"_sha256", -"_sha3", -"_sha512", -"_signal", -"_sitebuiltins", -"_socket", -"_sqlite3", -"_sre", -"_ssl", -"_stat", -"_statistics", -"_string", -"_strptime", -"_struct", -"_symtable", -"_thread", -"_threading_local", -"_tkinter", -"_tracemalloc", -"_uuid", -"_warnings", -"_weakref", -"_weakrefset", -"_winapi", -"_xxsubinterpreters", -"_zoneinfo", -"abc", -"aifc", -"antigravity", -"argparse", -"array", -"ast", -"asynchat", -"asyncio", -"asyncore", -"atexit", -"audioop", -"base64", -"bdb", -"binascii", -"binhex", -"bisect", -"builtins", -"bz2", -"cProfile", -"calendar", -"cgi", -"cgitb", -"chunk", -"cmath", -"cmd", -"code", -"codecs", -"codeop", -"collections", -"colorsys", -"compileall", -"concurrent", -"concurrent.futures", -"configparser", -"contextlib", -"contextvars", -"copy", -"copyreg", -"crypt", -"csv", -"ctypes", -"ctypes.macholib", -"curses", -"dataclasses", -"datetime", -"dbm", -"decimal", -"difflib", -"dis", -"distutils", -"distutils.command", -"doctest", -"email", -"email.mime", -"encodings", -"ensurepip", -"ensurepip._bundled", -"enum", -"errno", -"faulthandler", -"fcntl", -"filecmp", -"fileinput", -"fnmatch", -"fractions", -"ftplib", -"functools", -"gc", -"genericpath", -"getopt", -"getpass", -"gettext", -"glob", -"graphlib", -"grp", -"gzip", -"hashlib", -"heapq", -"hmac", -"html", -"http", -"idlelib", -"imaplib", -"imghdr", -"imp", -"importlib", -"inspect", -"io", -"ipaddress", -"itertools", -"json", -"keyword", -"lib2to3", -"lib2to3.fixes", -"lib2to3.pgen2", -"linecache", -"locale", -"logging", -"lzma", -"mailbox", -"mailcap", -"marshal", -"math", -"mimetypes", -"mmap", -"modulefinder", -"msilib", -"msvcrt", -"multiprocessing", -"multiprocessing.dummy", -"netrc", -"nis", -"nntplib", -"nt", -"ntpath", -"nturl2path", -"numbers", -"opcode", -"operator", -"optparse", -"os", -"ossaudiodev", -"pathlib", -"pdb", -"pickle", -"pickletools", -"pipes", -"pkgutil", -"platform", -"plistlib", -"poplib", -"posix", -"posixpath", -"pprint", -"profile", -"pstats", -"pty", -"pwd", -"py_compile", -"pyclbr", -"pydoc", -"pydoc_data", -"pyexpat", -"queue", -"quopri", -"random", -"re", -"readline", -"reprlib", -"resource", -"rlcompleter", -"runpy", -"sched", -"secrets", -"select", -"selectors", -"shelve", -"shlex", -"shutil", -"signal", -"site", -"smtpd", -"smtplib", -"sndhdr", -"socket", -"socketserver", -"spwd", -"sqlite3", -"sre_compile", -"sre_constants", -"sre_parse", -"ssl", -"stat", -"statistics", -"string", -"stringprep", -"struct", -"subprocess", -"sunau", -"symtable", -"sys", -"sysconfig", -"syslog", -"tabnanny", -"tarfile", -"telnetlib", -"tempfile", -"termios", -"textwrap", -"this", -"threading", -"time", -"timeit", -"tkinter", -"token", -"tokenize", -"trace", -"traceback", -"tracemalloc", -"tty", -"turtle", -"turtledemo", -"types", -"typing", -"unicodedata", -"unittest", -"urllib", -"uu", -"uuid", -"venv", -"warnings", -"wave", -"weakref", -"webbrowser", -"winreg", -"winsound", -"wsgiref", -"xdrlib", -"xml", -"xml.dom", -"xml.etree", -"xml.parsers", -"xml.sax", -"xmlrpc", -"zipapp", -"zipfile", -"zipimport", -"zlib", -"zoneinfo", -}; diff --git a/Python/pylifecycle.c b/Python/pylifecycle.c index a97f45d..bf5dcdd 100644 --- a/Python/pylifecycle.c +++ b/Python/pylifecycle.c @@ -2497,7 +2497,7 @@ fatal_error_exit(int status) // Dump the list of extension modules of sys.modules, excluding stdlib modules -// (sys.module_names), into fd file descriptor. +// (sys.stdlib_module_names), into fd file descriptor. // // This function is called by a signal handler in faulthandler: avoid memory // allocations and keep the implementation simple. For example, the list is not @@ -2519,19 +2519,19 @@ _Py_DumpExtensionModules(int fd, PyInterpreterState *interp) // Avoid PyDict_GetItemString() which calls PyUnicode_FromString(), // memory cannot be allocated on the heap in a signal handler. // Iterate on the dict instead. - PyObject *module_names = NULL; + PyObject *stdlib_module_names = NULL; pos = 0; while (PyDict_Next(interp->sysdict, &pos, &key, &value)) { if (PyUnicode_Check(key) - && PyUnicode_CompareWithASCIIString(key, "module_names") == 0) { - module_names = value; + && PyUnicode_CompareWithASCIIString(key, "stdlib_module_names") == 0) { + stdlib_module_names = value; break; } } - // If we failed to get sys.module_names or it's not a frozenset, + // If we failed to get sys.stdlib_module_names or it's not a frozenset, // don't exclude stdlib modules. - if (module_names != NULL && !PyFrozenSet_Check(module_names)) { - module_names = NULL; + if (stdlib_module_names != NULL && !PyFrozenSet_Check(stdlib_module_names)) { + stdlib_module_names = NULL; } // List extensions @@ -2547,13 +2547,13 @@ _Py_DumpExtensionModules(int fd, PyInterpreterState *interp) } // Use the module name from the sys.modules key, // don't attempt to get the module object name. - if (module_names != NULL) { + if (stdlib_module_names != NULL) { int is_stdlib_ext = 0; - Py_ssize_t i; + Py_ssize_t i = 0; PyObject *item; Py_hash_t hash; - for (i=0; _PySet_NextEntry(module_names, &i, &item, &hash); ) { + while (_PySet_NextEntry(stdlib_module_names, &i, &item, &hash)) { if (PyUnicode_Check(item) && PyUnicode_Compare(key, item) == 0) { diff --git a/Python/stdlib_module_names.h b/Python/stdlib_module_names.h new file mode 100644 index 0000000..8c43082 --- /dev/null +++ b/Python/stdlib_module_names.h @@ -0,0 +1,317 @@ +// Auto-generated by Tools/scripts/generate_stdlib_module_names.py. +// List used to create sys.stdlib_module_names. + +static const char* _Py_stdlib_module_names[] = { +"__future__", +"_abc", +"_aix_support", +"_ast", +"_asyncio", +"_bisect", +"_blake2", +"_bootsubprocess", +"_bz2", +"_codecs", +"_codecs_cn", +"_codecs_hk", +"_codecs_iso2022", +"_codecs_jp", +"_codecs_kr", +"_codecs_tw", +"_collections", +"_collections_abc", +"_compat_pickle", +"_compression", +"_contextvars", +"_crypt", +"_csv", +"_ctypes", +"_curses", +"_curses_panel", +"_datetime", +"_dbm", +"_decimal", +"_elementtree", +"_functools", +"_gdbm", +"_hashlib", +"_heapq", +"_imp", +"_io", +"_json", +"_locale", +"_lsprof", +"_lzma", +"_markupbase", +"_md5", +"_msi", +"_multibytecodec", +"_multiprocessing", +"_opcode", +"_operator", +"_osx_support", +"_pickle", +"_posixshmem", +"_posixsubprocess", +"_py_abc", +"_pydecimal", +"_pyio", +"_queue", +"_random", +"_sha1", +"_sha256", +"_sha3", +"_sha512", +"_signal", +"_sitebuiltins", +"_socket", +"_sqlite3", +"_sre", +"_ssl", +"_stat", +"_statistics", +"_string", +"_strptime", +"_struct", +"_symtable", +"_thread", +"_threading_local", +"_tkinter", +"_tracemalloc", +"_uuid", +"_warnings", +"_weakref", +"_weakrefset", +"_winapi", +"_xxsubinterpreters", +"_zoneinfo", +"abc", +"aifc", +"antigravity", +"argparse", +"array", +"ast", +"asynchat", +"asyncio", +"asyncore", +"atexit", +"audioop", +"base64", +"bdb", +"binascii", +"binhex", +"bisect", +"builtins", +"bz2", +"cProfile", +"calendar", +"cgi", +"cgitb", +"chunk", +"cmath", +"cmd", +"code", +"codecs", +"codeop", +"collections", +"colorsys", +"compileall", +"concurrent", +"concurrent.futures", +"configparser", +"contextlib", +"contextvars", +"copy", +"copyreg", +"crypt", +"csv", +"ctypes", +"ctypes.macholib", +"curses", +"dataclasses", +"datetime", +"dbm", +"decimal", +"difflib", +"dis", +"distutils", +"distutils.command", +"doctest", +"email", +"email.mime", +"encodings", +"ensurepip", +"ensurepip._bundled", +"enum", +"errno", +"faulthandler", +"fcntl", +"filecmp", +"fileinput", +"fnmatch", +"fractions", +"ftplib", +"functools", +"gc", +"genericpath", +"getopt", +"getpass", +"gettext", +"glob", +"graphlib", +"grp", +"gzip", +"hashlib", +"heapq", +"hmac", +"html", +"http", +"idlelib", +"imaplib", +"imghdr", +"imp", +"importlib", +"inspect", +"io", +"ipaddress", +"itertools", +"json", +"keyword", +"lib2to3", +"lib2to3.fixes", +"lib2to3.pgen2", +"linecache", +"locale", +"logging", +"lzma", +"mailbox", +"mailcap", +"marshal", +"math", +"mimetypes", +"mmap", +"modulefinder", +"msilib", +"msvcrt", +"multiprocessing", +"multiprocessing.dummy", +"netrc", +"nis", +"nntplib", +"nt", +"ntpath", +"nturl2path", +"numbers", +"opcode", +"operator", +"optparse", +"os", +"ossaudiodev", +"pathlib", +"pdb", +"pickle", +"pickletools", +"pipes", +"pkgutil", +"platform", +"plistlib", +"poplib", +"posix", +"posixpath", +"pprint", +"profile", +"pstats", +"pty", +"pwd", +"py_compile", +"pyclbr", +"pydoc", +"pydoc_data", +"pyexpat", +"queue", +"quopri", +"random", +"re", +"readline", +"reprlib", +"resource", +"rlcompleter", +"runpy", +"sched", +"secrets", +"select", +"selectors", +"shelve", +"shlex", +"shutil", +"signal", +"site", +"smtpd", +"smtplib", +"sndhdr", +"socket", +"socketserver", +"spwd", +"sqlite3", +"sre_compile", +"sre_constants", +"sre_parse", +"ssl", +"stat", +"statistics", +"string", +"stringprep", +"struct", +"subprocess", +"sunau", +"symtable", +"sys", +"sysconfig", +"syslog", +"tabnanny", +"tarfile", +"telnetlib", +"tempfile", +"termios", +"textwrap", +"this", +"threading", +"time", +"timeit", +"tkinter", +"token", +"tokenize", +"trace", +"traceback", +"tracemalloc", +"tty", +"turtle", +"turtledemo", +"types", +"typing", +"unicodedata", +"unittest", +"urllib", +"uu", +"uuid", +"venv", +"warnings", +"wave", +"weakref", +"webbrowser", +"winreg", +"winsound", +"wsgiref", +"xdrlib", +"xml", +"xml.dom", +"xml.etree", +"xml.parsers", +"xml.sax", +"xmlrpc", +"zipapp", +"zipfile", +"zipimport", +"zlib", +"zoneinfo", +}; diff --git a/Python/sysmodule.c b/Python/sysmodule.c index e2f7e39..b9349ef 100644 --- a/Python/sysmodule.c +++ b/Python/sysmodule.c @@ -29,7 +29,7 @@ Data members: #include "frameobject.h" // PyFrame_GetBack() #include "pydtrace.h" #include "osdefs.h" // DELIM -#include "module_names.h" // _Py_module_names +#include "stdlib_module_names.h" // _Py_stdlib_module_names #include #ifdef MS_WINDOWS @@ -2054,16 +2054,16 @@ error: static PyObject * -list_module_names(void) +list_stdlib_module_names(void) { - Py_ssize_t len = Py_ARRAY_LENGTH(_Py_module_names); + Py_ssize_t len = Py_ARRAY_LENGTH(_Py_stdlib_module_names); PyObject *names = PyTuple_New(len); if (names == NULL) { return NULL; } for (Py_ssize_t i = 0; i < len; i++) { - PyObject *name = PyUnicode_FromString(_Py_module_names[i]); + PyObject *name = PyUnicode_FromString(_Py_stdlib_module_names[i]); if (name == NULL) { Py_DECREF(names); return NULL; @@ -2784,7 +2784,7 @@ _PySys_InitCore(PyThreadState *tstate, PyObject *sysdict) SET_SYS("hash_info", get_hash_info(tstate)); SET_SYS("maxunicode", PyLong_FromLong(0x10FFFF)); SET_SYS("builtin_module_names", list_builtin_module_names()); - SET_SYS("module_names", list_module_names()); + SET_SYS("stdlib_module_names", list_stdlib_module_names()); #if PY_BIG_ENDIAN SET_SYS_FROM_STRING("byteorder", "big"); #else diff --git a/Tools/scripts/generate_module_names.py b/Tools/scripts/generate_module_names.py deleted file mode 100644 index 9d363aa..0000000 --- a/Tools/scripts/generate_module_names.py +++ /dev/null @@ -1,150 +0,0 @@ -# This script lists the names of standard library modules -# to update Python/module_names.h -import os.path -import re -import subprocess -import sys -import sysconfig - - -SRC_DIR = os.path.dirname(os.path.dirname(os.path.dirname(__file__))) -STDLIB_PATH = os.path.join(SRC_DIR, 'Lib') -MODULES_SETUP = os.path.join(SRC_DIR, 'Modules', 'Setup') -SETUP_PY = os.path.join(SRC_DIR, 'setup.py') - -IGNORE = { - '__init__', - '__pycache__', - 'site-packages', - - # test modules - '__phello__.foo', - '_ctypes_test', - '_testbuffer', - '_testcapi', - '_testconsole', - '_testimportmultiple', - '_testinternalcapi', - '_testmultiphase', - '_xxtestfuzz', - 'distutils.tests', - 'idlelib.idle_test', - 'lib2to3.tests', - 'test', - 'xxlimited', - 'xxlimited_35', - 'xxsubtype', -} - -# Windows extension modules -WINDOWS_MODULES = ( - '_msi', - '_testconsole', - '_winapi', - 'msvcrt', - 'nt', - 'winreg', - 'winsound' -) - - -# Pure Python modules (Lib/*.py) -def list_python_modules(names): - for filename in os.listdir(STDLIB_PATH): - if not filename.endswith(".py"): - continue - name = filename.removesuffix(".py") - names.add(name) - - -def _list_sub_packages(path, names, parent=None): - for name in os.listdir(path): - if name in IGNORE: - continue - package_path = os.path.join(path, name) - if not os.path.isdir(package_path): - continue - if not any(package_file.endswith(".py") - for package_file in os.listdir(package_path)): - continue - if parent: - qualname = f"{parent}.{name}" - else: - qualname = name - if qualname in IGNORE: - continue - names.add(qualname) - _list_sub_packages(package_path, names, qualname) - - -# Packages and sub-packages -def list_packages(names): - _list_sub_packages(STDLIB_PATH, names) - - -# Extension modules built by setup.py -def list_setup_extensions(names): - cmd = [sys.executable, SETUP_PY, "-q", "build", "--list-module-names"] - output = subprocess.check_output(cmd) - output = output.decode("utf8") - extensions = output.splitlines() - names |= set(extensions) - - -# Built-in and extension modules built by Modules/Setup -def list_modules_setup_extensions(names): - assign_var = re.compile("^[A-Z]+=") - - with open(MODULES_SETUP, encoding="utf-8") as modules_fp: - for line in modules_fp: - # Strip comment - line = line.partition("#")[0] - line = line.rstrip() - if not line: - continue - if assign_var.match(line): - # Ignore "VAR=VALUE" - continue - if line in ("*disabled*", "*shared*"): - continue - parts = line.split() - if len(parts) < 2: - continue - # "errno errnomodule.c" => write "errno" - name = parts[0] - names.add(name) - - -def list_modules(): - names = set(sys.builtin_module_names) | set(WINDOWS_MODULES) - list_modules_setup_extensions(names) - list_setup_extensions(names) - list_packages(names) - list_python_modules(names) - names -= set(IGNORE) - return names - - -def write_modules(fp, names): - print("// Auto-generated by Tools/scripts/generate_module_names.py.", file=fp) - print("// List used to create sys.module_names.", file=fp) - print(file=fp) - print("static const char* _Py_module_names[] = {", file=fp) - for name in sorted(names): - print(f'"{name}",', file=fp) - print("};", file=fp) - - -def main(): - if not sysconfig.is_python_build(): - print(f"ERROR: {sys.executable} is not a Python build", - file=sys.stderr) - sys.exit(1) - - fp = sys.stdout - names = list_modules() - write_modules(fp, names) - - -if __name__ == "__main__": - main() diff --git a/Tools/scripts/generate_stdlib_module_names.py b/Tools/scripts/generate_stdlib_module_names.py new file mode 100644 index 0000000..0264769 --- /dev/null +++ b/Tools/scripts/generate_stdlib_module_names.py @@ -0,0 +1,151 @@ +# This script lists the names of standard library modules +# to update Python/stdlib_mod_names.h +import os.path +import re +import subprocess +import sys +import sysconfig + + +SRC_DIR = os.path.dirname(os.path.dirname(os.path.dirname(__file__))) +STDLIB_PATH = os.path.join(SRC_DIR, 'Lib') +MODULES_SETUP = os.path.join(SRC_DIR, 'Modules', 'Setup') +SETUP_PY = os.path.join(SRC_DIR, 'setup.py') + +IGNORE = { + '__init__', + '__pycache__', + 'site-packages', + + # test modules + '__phello__.foo', + '_ctypes_test', + '_testbuffer', + '_testcapi', + '_testconsole', + '_testimportmultiple', + '_testinternalcapi', + '_testmultiphase', + '_xxtestfuzz', + 'distutils.tests', + 'idlelib.idle_test', + 'lib2to3.tests', + 'test', + 'xxlimited', + 'xxlimited_35', + 'xxsubtype', +} + +# Windows extension modules +WINDOWS_MODULES = ( + '_msi', + '_testconsole', + '_winapi', + 'msvcrt', + 'nt', + 'winreg', + 'winsound' +) + + +# Pure Python modules (Lib/*.py) +def list_python_modules(names): + for filename in os.listdir(STDLIB_PATH): + if not filename.endswith(".py"): + continue + name = filename.removesuffix(".py") + names.add(name) + + +def _list_sub_packages(path, names, parent=None): + for name in os.listdir(path): + if name in IGNORE: + continue + package_path = os.path.join(path, name) + if not os.path.isdir(package_path): + continue + if not any(package_file.endswith(".py") + for package_file in os.listdir(package_path)): + continue + if parent: + qualname = f"{parent}.{name}" + else: + qualname = name + if qualname in IGNORE: + continue + names.add(qualname) + _list_sub_packages(package_path, names, qualname) + + +# Packages and sub-packages +def list_packages(names): + _list_sub_packages(STDLIB_PATH, names) + + +# Extension modules built by setup.py +def list_setup_extensions(names): + cmd = [sys.executable, SETUP_PY, "-q", "build", "--list-module-names"] + output = subprocess.check_output(cmd) + output = output.decode("utf8") + extensions = output.splitlines() + names |= set(extensions) + + +# Built-in and extension modules built by Modules/Setup +def list_modules_setup_extensions(names): + assign_var = re.compile("^[A-Z]+=") + + with open(MODULES_SETUP, encoding="utf-8") as modules_fp: + for line in modules_fp: + # Strip comment + line = line.partition("#")[0] + line = line.rstrip() + if not line: + continue + if assign_var.match(line): + # Ignore "VAR=VALUE" + continue + if line in ("*disabled*", "*shared*"): + continue + parts = line.split() + if len(parts) < 2: + continue + # "errno errnomodule.c" => write "errno" + name = parts[0] + names.add(name) + + +def list_modules(): + names = set(sys.builtin_module_names) | set(WINDOWS_MODULES) + list_modules_setup_extensions(names) + list_setup_extensions(names) + list_packages(names) + list_python_modules(names) + names -= set(IGNORE) + return names + + +def write_modules(fp, names): + print("// Auto-generated by Tools/scripts/generate_stdlib_module_names.py.", + file=fp) + print("// List used to create sys.stdlib_module_names.", file=fp) + print(file=fp) + print("static const char* _Py_stdlib_module_names[] = {", file=fp) + for name in sorted(names): + print(f'"{name}",', file=fp) + print("};", file=fp) + + +def main(): + if not sysconfig.is_python_build(): + print(f"ERROR: {sys.executable} is not a Python build", + file=sys.stderr) + sys.exit(1) + + fp = sys.stdout + names = list_modules() + write_modules(fp, names) + + +if __name__ == "__main__": + main() -- cgit v0.12