• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1"""Core implementation of import.
2
3This module is NOT meant to be directly imported! It has been designed such
4that it can be bootstrapped into Python as the implementation of import. As
5such it requires the injection of specific modules and attributes in order to
6work. One should use importlib as the public-facing version of this module.
7
8"""
9#
10# IMPORTANT: Whenever making changes to this module, be sure to run a top-level
11# `make regen-importlib` followed by `make` in order to get the frozen version
12# of the module updated. Not doing so will result in the Makefile to fail for
13# all others who don't have a ./python around to freeze the module
14# in the early stages of compilation.
15#
16
17# See importlib._setup() for what is injected into the global namespace.
18
19# When editing this code be aware that code executed at import time CANNOT
20# reference any injected objects! This includes not only global code but also
21# anything specified at the class level.
22
23def _object_name(obj):
24    try:
25        return obj.__qualname__
26    except AttributeError:
27        return type(obj).__qualname__
28
29# Bootstrap-related code ######################################################
30
31# Modules injected manually by _setup()
32_thread = None
33_warnings = None
34_weakref = None
35
36# Import done by _install_external_importers()
37_bootstrap_external = None
38
39
40def _wrap(new, old):
41    """Simple substitute for functools.update_wrapper."""
42    for replace in ['__module__', '__name__', '__qualname__', '__doc__']:
43        if hasattr(old, replace):
44            setattr(new, replace, getattr(old, replace))
45    new.__dict__.update(old.__dict__)
46
47
48def _new_module(name):
49    return type(sys)(name)
50
51
52# Module-level locking ########################################################
53
54# A dict mapping module names to weakrefs of _ModuleLock instances
55# Dictionary protected by the global import lock
56_module_locks = {}
57# A dict mapping thread ids to _ModuleLock instances
58_blocking_on = {}
59
60
61class _DeadlockError(RuntimeError):
62    pass
63
64
65class _ModuleLock:
66    """A recursive lock implementation which is able to detect deadlocks
67    (e.g. thread 1 trying to take locks A then B, and thread 2 trying to
68    take locks B then A).
69    """
70
71    def __init__(self, name):
72        self.lock = _thread.allocate_lock()
73        self.wakeup = _thread.allocate_lock()
74        self.name = name
75        self.owner = None
76        self.count = 0
77        self.waiters = 0
78
79    def has_deadlock(self):
80        # Deadlock avoidance for concurrent circular imports.
81        me = _thread.get_ident()
82        tid = self.owner
83        seen = set()
84        while True:
85            lock = _blocking_on.get(tid)
86            if lock is None:
87                return False
88            tid = lock.owner
89            if tid == me:
90                return True
91            if tid in seen:
92                # bpo 38091: the chain of tid's we encounter here
93                # eventually leads to a fixpoint or a cycle, but
94                # does not reach 'me'.  This means we would not
95                # actually deadlock.  This can happen if other
96                # threads are at the beginning of acquire() below.
97                return False
98            seen.add(tid)
99
100    def acquire(self):
101        """
102        Acquire the module lock.  If a potential deadlock is detected,
103        a _DeadlockError is raised.
104        Otherwise, the lock is always acquired and True is returned.
105        """
106        tid = _thread.get_ident()
107        _blocking_on[tid] = self
108        try:
109            while True:
110                with self.lock:
111                    if self.count == 0 or self.owner == tid:
112                        self.owner = tid
113                        self.count += 1
114                        return True
115                    if self.has_deadlock():
116                        raise _DeadlockError('deadlock detected by %r' % self)
117                    if self.wakeup.acquire(False):
118                        self.waiters += 1
119                # Wait for a release() call
120                self.wakeup.acquire()
121                self.wakeup.release()
122        finally:
123            del _blocking_on[tid]
124
125    def release(self):
126        tid = _thread.get_ident()
127        with self.lock:
128            if self.owner != tid:
129                raise RuntimeError('cannot release un-acquired lock')
130            assert self.count > 0
131            self.count -= 1
132            if self.count == 0:
133                self.owner = None
134                if self.waiters:
135                    self.waiters -= 1
136                    self.wakeup.release()
137
138    def __repr__(self):
139        return '_ModuleLock({!r}) at {}'.format(self.name, id(self))
140
141
142class _DummyModuleLock:
143    """A simple _ModuleLock equivalent for Python builds without
144    multi-threading support."""
145
146    def __init__(self, name):
147        self.name = name
148        self.count = 0
149
150    def acquire(self):
151        self.count += 1
152        return True
153
154    def release(self):
155        if self.count == 0:
156            raise RuntimeError('cannot release un-acquired lock')
157        self.count -= 1
158
159    def __repr__(self):
160        return '_DummyModuleLock({!r}) at {}'.format(self.name, id(self))
161
162
163class _ModuleLockManager:
164
165    def __init__(self, name):
166        self._name = name
167        self._lock = None
168
169    def __enter__(self):
170        self._lock = _get_module_lock(self._name)
171        self._lock.acquire()
172
173    def __exit__(self, *args, **kwargs):
174        self._lock.release()
175
176
177# The following two functions are for consumption by Python/import.c.
178
179def _get_module_lock(name):
180    """Get or create the module lock for a given module name.
181
182    Acquire/release internally the global import lock to protect
183    _module_locks."""
184
185    _imp.acquire_lock()
186    try:
187        try:
188            lock = _module_locks[name]()
189        except KeyError:
190            lock = None
191
192        if lock is None:
193            if _thread is None:
194                lock = _DummyModuleLock(name)
195            else:
196                lock = _ModuleLock(name)
197
198            def cb(ref, name=name):
199                _imp.acquire_lock()
200                try:
201                    # bpo-31070: Check if another thread created a new lock
202                    # after the previous lock was destroyed
203                    # but before the weakref callback was called.
204                    if _module_locks.get(name) is ref:
205                        del _module_locks[name]
206                finally:
207                    _imp.release_lock()
208
209            _module_locks[name] = _weakref.ref(lock, cb)
210    finally:
211        _imp.release_lock()
212
213    return lock
214
215
216def _lock_unlock_module(name):
217    """Acquires then releases the module lock for a given module name.
218
219    This is used to ensure a module is completely initialized, in the
220    event it is being imported by another thread.
221    """
222    lock = _get_module_lock(name)
223    try:
224        lock.acquire()
225    except _DeadlockError:
226        # Concurrent circular import, we'll accept a partially initialized
227        # module object.
228        pass
229    else:
230        lock.release()
231
232# Frame stripping magic ###############################################
233def _call_with_frames_removed(f, *args, **kwds):
234    """remove_importlib_frames in import.c will always remove sequences
235    of importlib frames that end with a call to this function
236
237    Use it instead of a normal call in places where including the importlib
238    frames introduces unwanted noise into the traceback (e.g. when executing
239    module code)
240    """
241    return f(*args, **kwds)
242
243
244def _verbose_message(message, *args, verbosity=1):
245    """Print the message to stderr if -v/PYTHONVERBOSE is turned on."""
246    if sys.flags.verbose >= verbosity:
247        if not message.startswith(('#', 'import ')):
248            message = '# ' + message
249        print(message.format(*args), file=sys.stderr)
250
251
252def _requires_builtin(fxn):
253    """Decorator to verify the named module is built-in."""
254    def _requires_builtin_wrapper(self, fullname):
255        if fullname not in sys.builtin_module_names:
256            raise ImportError('{!r} is not a built-in module'.format(fullname),
257                              name=fullname)
258        return fxn(self, fullname)
259    _wrap(_requires_builtin_wrapper, fxn)
260    return _requires_builtin_wrapper
261
262
263def _requires_frozen(fxn):
264    """Decorator to verify the named module is frozen."""
265    def _requires_frozen_wrapper(self, fullname):
266        if not _imp.is_frozen(fullname):
267            raise ImportError('{!r} is not a frozen module'.format(fullname),
268                              name=fullname)
269        return fxn(self, fullname)
270    _wrap(_requires_frozen_wrapper, fxn)
271    return _requires_frozen_wrapper
272
273
274# Typically used by loader classes as a method replacement.
275def _load_module_shim(self, fullname):
276    """Load the specified module into sys.modules and return it.
277
278    This method is deprecated.  Use loader.exec_module() instead.
279
280    """
281    msg = ("the load_module() method is deprecated and slated for removal in "
282          "Python 3.12; use exec_module() instead")
283    _warnings.warn(msg, DeprecationWarning)
284    spec = spec_from_loader(fullname, self)
285    if fullname in sys.modules:
286        module = sys.modules[fullname]
287        _exec(spec, module)
288        return sys.modules[fullname]
289    else:
290        return _load(spec)
291
292# Module specifications #######################################################
293
294def _module_repr(module):
295    """The implementation of ModuleType.__repr__()."""
296    loader = getattr(module, '__loader__', None)
297    if spec := getattr(module, "__spec__", None):
298        return _module_repr_from_spec(spec)
299    elif hasattr(loader, 'module_repr'):
300        try:
301            return loader.module_repr(module)
302        except Exception:
303            pass
304    # Fall through to a catch-all which always succeeds.
305    try:
306        name = module.__name__
307    except AttributeError:
308        name = '?'
309    try:
310        filename = module.__file__
311    except AttributeError:
312        if loader is None:
313            return '<module {!r}>'.format(name)
314        else:
315            return '<module {!r} ({!r})>'.format(name, loader)
316    else:
317        return '<module {!r} from {!r}>'.format(name, filename)
318
319
320class ModuleSpec:
321    """The specification for a module, used for loading.
322
323    A module's spec is the source for information about the module.  For
324    data associated with the module, including source, use the spec's
325    loader.
326
327    `name` is the absolute name of the module.  `loader` is the loader
328    to use when loading the module.  `parent` is the name of the
329    package the module is in.  The parent is derived from the name.
330
331    `is_package` determines if the module is considered a package or
332    not.  On modules this is reflected by the `__path__` attribute.
333
334    `origin` is the specific location used by the loader from which to
335    load the module, if that information is available.  When filename is
336    set, origin will match.
337
338    `has_location` indicates that a spec's "origin" reflects a location.
339    When this is True, `__file__` attribute of the module is set.
340
341    `cached` is the location of the cached bytecode file, if any.  It
342    corresponds to the `__cached__` attribute.
343
344    `submodule_search_locations` is the sequence of path entries to
345    search when importing submodules.  If set, is_package should be
346    True--and False otherwise.
347
348    Packages are simply modules that (may) have submodules.  If a spec
349    has a non-None value in `submodule_search_locations`, the import
350    system will consider modules loaded from the spec as packages.
351
352    Only finders (see importlib.abc.MetaPathFinder and
353    importlib.abc.PathEntryFinder) should modify ModuleSpec instances.
354
355    """
356
357    def __init__(self, name, loader, *, origin=None, loader_state=None,
358                 is_package=None):
359        self.name = name
360        self.loader = loader
361        self.origin = origin
362        self.loader_state = loader_state
363        self.submodule_search_locations = [] if is_package else None
364
365        # file-location attributes
366        self._set_fileattr = False
367        self._cached = None
368
369    def __repr__(self):
370        args = ['name={!r}'.format(self.name),
371                'loader={!r}'.format(self.loader)]
372        if self.origin is not None:
373            args.append('origin={!r}'.format(self.origin))
374        if self.submodule_search_locations is not None:
375            args.append('submodule_search_locations={}'
376                        .format(self.submodule_search_locations))
377        return '{}({})'.format(self.__class__.__name__, ', '.join(args))
378
379    def __eq__(self, other):
380        smsl = self.submodule_search_locations
381        try:
382            return (self.name == other.name and
383                    self.loader == other.loader and
384                    self.origin == other.origin and
385                    smsl == other.submodule_search_locations and
386                    self.cached == other.cached and
387                    self.has_location == other.has_location)
388        except AttributeError:
389            return NotImplemented
390
391    @property
392    def cached(self):
393        if self._cached is None:
394            if self.origin is not None and self._set_fileattr:
395                if _bootstrap_external is None:
396                    raise NotImplementedError
397                self._cached = _bootstrap_external._get_cached(self.origin)
398        return self._cached
399
400    @cached.setter
401    def cached(self, cached):
402        self._cached = cached
403
404    @property
405    def parent(self):
406        """The name of the module's parent."""
407        if self.submodule_search_locations is None:
408            return self.name.rpartition('.')[0]
409        else:
410            return self.name
411
412    @property
413    def has_location(self):
414        return self._set_fileattr
415
416    @has_location.setter
417    def has_location(self, value):
418        self._set_fileattr = bool(value)
419
420
421def spec_from_loader(name, loader, *, origin=None, is_package=None):
422    """Return a module spec based on various loader methods."""
423    if hasattr(loader, 'get_filename'):
424        if _bootstrap_external is None:
425            raise NotImplementedError
426        spec_from_file_location = _bootstrap_external.spec_from_file_location
427
428        if is_package is None:
429            return spec_from_file_location(name, loader=loader)
430        search = [] if is_package else None
431        return spec_from_file_location(name, loader=loader,
432                                       submodule_search_locations=search)
433
434    if is_package is None:
435        if hasattr(loader, 'is_package'):
436            try:
437                is_package = loader.is_package(name)
438            except ImportError:
439                is_package = None  # aka, undefined
440        else:
441            # the default
442            is_package = False
443
444    return ModuleSpec(name, loader, origin=origin, is_package=is_package)
445
446
447def _spec_from_module(module, loader=None, origin=None):
448    # This function is meant for use in _setup().
449    try:
450        spec = module.__spec__
451    except AttributeError:
452        pass
453    else:
454        if spec is not None:
455            return spec
456
457    name = module.__name__
458    if loader is None:
459        try:
460            loader = module.__loader__
461        except AttributeError:
462            # loader will stay None.
463            pass
464    try:
465        location = module.__file__
466    except AttributeError:
467        location = None
468    if origin is None:
469        if location is None:
470            try:
471                origin = loader._ORIGIN
472            except AttributeError:
473                origin = None
474        else:
475            origin = location
476    try:
477        cached = module.__cached__
478    except AttributeError:
479        cached = None
480    try:
481        submodule_search_locations = list(module.__path__)
482    except AttributeError:
483        submodule_search_locations = None
484
485    spec = ModuleSpec(name, loader, origin=origin)
486    spec._set_fileattr = False if location is None else True
487    spec.cached = cached
488    spec.submodule_search_locations = submodule_search_locations
489    return spec
490
491
492def _init_module_attrs(spec, module, *, override=False):
493    # The passed-in module may be not support attribute assignment,
494    # in which case we simply don't set the attributes.
495    # __name__
496    if (override or getattr(module, '__name__', None) is None):
497        try:
498            module.__name__ = spec.name
499        except AttributeError:
500            pass
501    # __loader__
502    if override or getattr(module, '__loader__', None) is None:
503        loader = spec.loader
504        if loader is None:
505            # A backward compatibility hack.
506            if spec.submodule_search_locations is not None:
507                if _bootstrap_external is None:
508                    raise NotImplementedError
509                _NamespaceLoader = _bootstrap_external._NamespaceLoader
510
511                loader = _NamespaceLoader.__new__(_NamespaceLoader)
512                loader._path = spec.submodule_search_locations
513                spec.loader = loader
514                # While the docs say that module.__file__ is not set for
515                # built-in modules, and the code below will avoid setting it if
516                # spec.has_location is false, this is incorrect for namespace
517                # packages.  Namespace packages have no location, but their
518                # __spec__.origin is None, and thus their module.__file__
519                # should also be None for consistency.  While a bit of a hack,
520                # this is the best place to ensure this consistency.
521                #
522                # See # https://docs.python.org/3/library/importlib.html#importlib.abc.Loader.load_module
523                # and bpo-32305
524                module.__file__ = None
525        try:
526            module.__loader__ = loader
527        except AttributeError:
528            pass
529    # __package__
530    if override or getattr(module, '__package__', None) is None:
531        try:
532            module.__package__ = spec.parent
533        except AttributeError:
534            pass
535    # __spec__
536    try:
537        module.__spec__ = spec
538    except AttributeError:
539        pass
540    # __path__
541    if override or getattr(module, '__path__', None) is None:
542        if spec.submodule_search_locations is not None:
543            try:
544                module.__path__ = spec.submodule_search_locations
545            except AttributeError:
546                pass
547    # __file__/__cached__
548    if spec.has_location:
549        if override or getattr(module, '__file__', None) is None:
550            try:
551                module.__file__ = spec.origin
552            except AttributeError:
553                pass
554
555        if override or getattr(module, '__cached__', None) is None:
556            if spec.cached is not None:
557                try:
558                    module.__cached__ = spec.cached
559                except AttributeError:
560                    pass
561    return module
562
563
564def module_from_spec(spec):
565    """Create a module based on the provided spec."""
566    # Typically loaders will not implement create_module().
567    module = None
568    if hasattr(spec.loader, 'create_module'):
569        # If create_module() returns `None` then it means default
570        # module creation should be used.
571        module = spec.loader.create_module(spec)
572    elif hasattr(spec.loader, 'exec_module'):
573        raise ImportError('loaders that define exec_module() '
574                          'must also define create_module()')
575    if module is None:
576        module = _new_module(spec.name)
577    _init_module_attrs(spec, module)
578    return module
579
580
581def _module_repr_from_spec(spec):
582    """Return the repr to use for the module."""
583    # We mostly replicate _module_repr() using the spec attributes.
584    name = '?' if spec.name is None else spec.name
585    if spec.origin is None:
586        if spec.loader is None:
587            return '<module {!r}>'.format(name)
588        else:
589            return '<module {!r} ({!r})>'.format(name, spec.loader)
590    else:
591        if spec.has_location:
592            return '<module {!r} from {!r}>'.format(name, spec.origin)
593        else:
594            return '<module {!r} ({})>'.format(spec.name, spec.origin)
595
596
597# Used by importlib.reload() and _load_module_shim().
598def _exec(spec, module):
599    """Execute the spec's specified module in an existing module's namespace."""
600    name = spec.name
601    with _ModuleLockManager(name):
602        if sys.modules.get(name) is not module:
603            msg = 'module {!r} not in sys.modules'.format(name)
604            raise ImportError(msg, name=name)
605        try:
606            if spec.loader is None:
607                if spec.submodule_search_locations is None:
608                    raise ImportError('missing loader', name=spec.name)
609                # Namespace package.
610                _init_module_attrs(spec, module, override=True)
611            else:
612                _init_module_attrs(spec, module, override=True)
613                if not hasattr(spec.loader, 'exec_module'):
614                    msg = (f"{_object_name(spec.loader)}.exec_module() not found; "
615                           "falling back to load_module()")
616                    _warnings.warn(msg, ImportWarning)
617                    spec.loader.load_module(name)
618                else:
619                    spec.loader.exec_module(module)
620        finally:
621            # Update the order of insertion into sys.modules for module
622            # clean-up at shutdown.
623            module = sys.modules.pop(spec.name)
624            sys.modules[spec.name] = module
625    return module
626
627
628def _load_backward_compatible(spec):
629    # It is assumed that all callers have been warned about using load_module()
630    # appropriately before calling this function.
631    try:
632        spec.loader.load_module(spec.name)
633    except:
634        if spec.name in sys.modules:
635            module = sys.modules.pop(spec.name)
636            sys.modules[spec.name] = module
637        raise
638    # The module must be in sys.modules at this point!
639    # Move it to the end of sys.modules.
640    module = sys.modules.pop(spec.name)
641    sys.modules[spec.name] = module
642    if getattr(module, '__loader__', None) is None:
643        try:
644            module.__loader__ = spec.loader
645        except AttributeError:
646            pass
647    if getattr(module, '__package__', None) is None:
648        try:
649            # Since module.__path__ may not line up with
650            # spec.submodule_search_paths, we can't necessarily rely
651            # on spec.parent here.
652            module.__package__ = module.__name__
653            if not hasattr(module, '__path__'):
654                module.__package__ = spec.name.rpartition('.')[0]
655        except AttributeError:
656            pass
657    if getattr(module, '__spec__', None) is None:
658        try:
659            module.__spec__ = spec
660        except AttributeError:
661            pass
662    return module
663
664def _load_unlocked(spec):
665    # A helper for direct use by the import system.
666    if spec.loader is not None:
667        # Not a namespace package.
668        if not hasattr(spec.loader, 'exec_module'):
669            msg = (f"{_object_name(spec.loader)}.exec_module() not found; "
670                    "falling back to load_module()")
671            _warnings.warn(msg, ImportWarning)
672            return _load_backward_compatible(spec)
673
674    module = module_from_spec(spec)
675
676    # This must be done before putting the module in sys.modules
677    # (otherwise an optimization shortcut in import.c becomes
678    # wrong).
679    spec._initializing = True
680    try:
681        sys.modules[spec.name] = module
682        try:
683            if spec.loader is None:
684                if spec.submodule_search_locations is None:
685                    raise ImportError('missing loader', name=spec.name)
686                # A namespace package so do nothing.
687            else:
688                spec.loader.exec_module(module)
689        except:
690            try:
691                del sys.modules[spec.name]
692            except KeyError:
693                pass
694            raise
695        # Move the module to the end of sys.modules.
696        # We don't ensure that the import-related module attributes get
697        # set in the sys.modules replacement case.  Such modules are on
698        # their own.
699        module = sys.modules.pop(spec.name)
700        sys.modules[spec.name] = module
701        _verbose_message('import {!r} # {!r}', spec.name, spec.loader)
702    finally:
703        spec._initializing = False
704
705    return module
706
707# A method used during testing of _load_unlocked() and by
708# _load_module_shim().
709def _load(spec):
710    """Return a new module object, loaded by the spec's loader.
711
712    The module is not added to its parent.
713
714    If a module is already in sys.modules, that existing module gets
715    clobbered.
716
717    """
718    with _ModuleLockManager(spec.name):
719        return _load_unlocked(spec)
720
721
722# Loaders #####################################################################
723
724class BuiltinImporter:
725
726    """Meta path import for built-in modules.
727
728    All methods are either class or static methods to avoid the need to
729    instantiate the class.
730
731    """
732
733    _ORIGIN = "built-in"
734
735    @staticmethod
736    def module_repr(module):
737        """Return repr for the module.
738
739        The method is deprecated.  The import machinery does the job itself.
740
741        """
742        _warnings.warn("BuiltinImporter.module_repr() is deprecated and "
743                       "slated for removal in Python 3.12", DeprecationWarning)
744        return f'<module {module.__name__!r} ({BuiltinImporter._ORIGIN})>'
745
746    @classmethod
747    def find_spec(cls, fullname, path=None, target=None):
748        if path is not None:
749            return None
750        if _imp.is_builtin(fullname):
751            return spec_from_loader(fullname, cls, origin=cls._ORIGIN)
752        else:
753            return None
754
755    @classmethod
756    def find_module(cls, fullname, path=None):
757        """Find the built-in module.
758
759        If 'path' is ever specified then the search is considered a failure.
760
761        This method is deprecated.  Use find_spec() instead.
762
763        """
764        _warnings.warn("BuiltinImporter.find_module() is deprecated and "
765                       "slated for removal in Python 3.12; use find_spec() instead",
766                       DeprecationWarning)
767        spec = cls.find_spec(fullname, path)
768        return spec.loader if spec is not None else None
769
770    @staticmethod
771    def create_module(spec):
772        """Create a built-in module"""
773        if spec.name not in sys.builtin_module_names:
774            raise ImportError('{!r} is not a built-in module'.format(spec.name),
775                              name=spec.name)
776        return _call_with_frames_removed(_imp.create_builtin, spec)
777
778    @staticmethod
779    def exec_module(module):
780        """Exec a built-in module"""
781        _call_with_frames_removed(_imp.exec_builtin, module)
782
783    @classmethod
784    @_requires_builtin
785    def get_code(cls, fullname):
786        """Return None as built-in modules do not have code objects."""
787        return None
788
789    @classmethod
790    @_requires_builtin
791    def get_source(cls, fullname):
792        """Return None as built-in modules do not have source code."""
793        return None
794
795    @classmethod
796    @_requires_builtin
797    def is_package(cls, fullname):
798        """Return False as built-in modules are never packages."""
799        return False
800
801    load_module = classmethod(_load_module_shim)
802
803
804class FrozenImporter:
805
806    """Meta path import for frozen modules.
807
808    All methods are either class or static methods to avoid the need to
809    instantiate the class.
810
811    """
812
813    _ORIGIN = "frozen"
814
815    @staticmethod
816    def module_repr(m):
817        """Return repr for the module.
818
819        The method is deprecated.  The import machinery does the job itself.
820
821        """
822        _warnings.warn("FrozenImporter.module_repr() is deprecated and "
823                       "slated for removal in Python 3.12", DeprecationWarning)
824        return '<module {!r} ({})>'.format(m.__name__, FrozenImporter._ORIGIN)
825
826    @classmethod
827    def find_spec(cls, fullname, path=None, target=None):
828        if _imp.is_frozen(fullname):
829            return spec_from_loader(fullname, cls, origin=cls._ORIGIN)
830        else:
831            return None
832
833    @classmethod
834    def find_module(cls, fullname, path=None):
835        """Find a frozen module.
836
837        This method is deprecated.  Use find_spec() instead.
838
839        """
840        _warnings.warn("FrozenImporter.find_module() is deprecated and "
841                       "slated for removal in Python 3.12; use find_spec() instead",
842                       DeprecationWarning)
843        return cls if _imp.is_frozen(fullname) else None
844
845    @staticmethod
846    def create_module(spec):
847        """Use default semantics for module creation."""
848
849    @staticmethod
850    def exec_module(module):
851        name = module.__spec__.name
852        if not _imp.is_frozen(name):
853            raise ImportError('{!r} is not a frozen module'.format(name),
854                              name=name)
855        code = _call_with_frames_removed(_imp.get_frozen_object, name)
856        exec(code, module.__dict__)
857
858    @classmethod
859    def load_module(cls, fullname):
860        """Load a frozen module.
861
862        This method is deprecated.  Use exec_module() instead.
863
864        """
865        # Warning about deprecation implemented in _load_module_shim().
866        return _load_module_shim(cls, fullname)
867
868    @classmethod
869    @_requires_frozen
870    def get_code(cls, fullname):
871        """Return the code object for the frozen module."""
872        return _imp.get_frozen_object(fullname)
873
874    @classmethod
875    @_requires_frozen
876    def get_source(cls, fullname):
877        """Return None as frozen modules do not have source code."""
878        return None
879
880    @classmethod
881    @_requires_frozen
882    def is_package(cls, fullname):
883        """Return True if the frozen module is a package."""
884        return _imp.is_frozen_package(fullname)
885
886
887# Import itself ###############################################################
888
889class _ImportLockContext:
890
891    """Context manager for the import lock."""
892
893    def __enter__(self):
894        """Acquire the import lock."""
895        _imp.acquire_lock()
896
897    def __exit__(self, exc_type, exc_value, exc_traceback):
898        """Release the import lock regardless of any raised exceptions."""
899        _imp.release_lock()
900
901
902def _resolve_name(name, package, level):
903    """Resolve a relative module name to an absolute one."""
904    bits = package.rsplit('.', level - 1)
905    if len(bits) < level:
906        raise ImportError('attempted relative import beyond top-level package')
907    base = bits[0]
908    return '{}.{}'.format(base, name) if name else base
909
910
911def _find_spec_legacy(finder, name, path):
912    msg = (f"{_object_name(finder)}.find_spec() not found; "
913                           "falling back to find_module()")
914    _warnings.warn(msg, ImportWarning)
915    loader = finder.find_module(name, path)
916    if loader is None:
917        return None
918    return spec_from_loader(name, loader)
919
920
921def _find_spec(name, path, target=None):
922    """Find a module's spec."""
923    meta_path = sys.meta_path
924    if meta_path is None:
925        # PyImport_Cleanup() is running or has been called.
926        raise ImportError("sys.meta_path is None, Python is likely "
927                          "shutting down")
928
929    if not meta_path:
930        _warnings.warn('sys.meta_path is empty', ImportWarning)
931
932    # We check sys.modules here for the reload case.  While a passed-in
933    # target will usually indicate a reload there is no guarantee, whereas
934    # sys.modules provides one.
935    is_reload = name in sys.modules
936    for finder in meta_path:
937        with _ImportLockContext():
938            try:
939                find_spec = finder.find_spec
940            except AttributeError:
941                spec = _find_spec_legacy(finder, name, path)
942                if spec is None:
943                    continue
944            else:
945                spec = find_spec(name, path, target)
946        if spec is not None:
947            # The parent import may have already imported this module.
948            if not is_reload and name in sys.modules:
949                module = sys.modules[name]
950                try:
951                    __spec__ = module.__spec__
952                except AttributeError:
953                    # We use the found spec since that is the one that
954                    # we would have used if the parent module hadn't
955                    # beaten us to the punch.
956                    return spec
957                else:
958                    if __spec__ is None:
959                        return spec
960                    else:
961                        return __spec__
962            else:
963                return spec
964    else:
965        return None
966
967
968def _sanity_check(name, package, level):
969    """Verify arguments are "sane"."""
970    if not isinstance(name, str):
971        raise TypeError('module name must be str, not {}'.format(type(name)))
972    if level < 0:
973        raise ValueError('level must be >= 0')
974    if level > 0:
975        if not isinstance(package, str):
976            raise TypeError('__package__ not set to a string')
977        elif not package:
978            raise ImportError('attempted relative import with no known parent '
979                              'package')
980    if not name and level == 0:
981        raise ValueError('Empty module name')
982
983
984_ERR_MSG_PREFIX = 'No module named '
985_ERR_MSG = _ERR_MSG_PREFIX + '{!r}'
986
987def _find_and_load_unlocked(name, import_):
988    path = None
989    parent = name.rpartition('.')[0]
990    if parent:
991        if parent not in sys.modules:
992            _call_with_frames_removed(import_, parent)
993        # Crazy side-effects!
994        if name in sys.modules:
995            return sys.modules[name]
996        parent_module = sys.modules[parent]
997        try:
998            path = parent_module.__path__
999        except AttributeError:
1000            msg = (_ERR_MSG + '; {!r} is not a package').format(name, parent)
1001            raise ModuleNotFoundError(msg, name=name) from None
1002    spec = _find_spec(name, path)
1003    if spec is None:
1004        raise ModuleNotFoundError(_ERR_MSG.format(name), name=name)
1005    else:
1006        module = _load_unlocked(spec)
1007    if parent:
1008        # Set the module as an attribute on its parent.
1009        parent_module = sys.modules[parent]
1010        child = name.rpartition('.')[2]
1011        try:
1012            setattr(parent_module, child, module)
1013        except AttributeError:
1014            msg = f"Cannot set an attribute on {parent!r} for child module {child!r}"
1015            _warnings.warn(msg, ImportWarning)
1016    return module
1017
1018
1019_NEEDS_LOADING = object()
1020
1021
1022def _find_and_load(name, import_):
1023    """Find and load the module."""
1024    with _ModuleLockManager(name):
1025        module = sys.modules.get(name, _NEEDS_LOADING)
1026        if module is _NEEDS_LOADING:
1027            return _find_and_load_unlocked(name, import_)
1028
1029    if module is None:
1030        message = ('import of {} halted; '
1031                   'None in sys.modules'.format(name))
1032        raise ModuleNotFoundError(message, name=name)
1033
1034    _lock_unlock_module(name)
1035    return module
1036
1037
1038def _gcd_import(name, package=None, level=0):
1039    """Import and return the module based on its name, the package the call is
1040    being made from, and the level adjustment.
1041
1042    This function represents the greatest common denominator of functionality
1043    between import_module and __import__. This includes setting __package__ if
1044    the loader did not.
1045
1046    """
1047    _sanity_check(name, package, level)
1048    if level > 0:
1049        name = _resolve_name(name, package, level)
1050    return _find_and_load(name, _gcd_import)
1051
1052
1053def _handle_fromlist(module, fromlist, import_, *, recursive=False):
1054    """Figure out what __import__ should return.
1055
1056    The import_ parameter is a callable which takes the name of module to
1057    import. It is required to decouple the function from assuming importlib's
1058    import implementation is desired.
1059
1060    """
1061    # The hell that is fromlist ...
1062    # If a package was imported, try to import stuff from fromlist.
1063    for x in fromlist:
1064        if not isinstance(x, str):
1065            if recursive:
1066                where = module.__name__ + '.__all__'
1067            else:
1068                where = "``from list''"
1069            raise TypeError(f"Item in {where} must be str, "
1070                            f"not {type(x).__name__}")
1071        elif x == '*':
1072            if not recursive and hasattr(module, '__all__'):
1073                _handle_fromlist(module, module.__all__, import_,
1074                                 recursive=True)
1075        elif not hasattr(module, x):
1076            from_name = '{}.{}'.format(module.__name__, x)
1077            try:
1078                _call_with_frames_removed(import_, from_name)
1079            except ModuleNotFoundError as exc:
1080                # Backwards-compatibility dictates we ignore failed
1081                # imports triggered by fromlist for modules that don't
1082                # exist.
1083                if (exc.name == from_name and
1084                    sys.modules.get(from_name, _NEEDS_LOADING) is not None):
1085                    continue
1086                raise
1087    return module
1088
1089
1090def _calc___package__(globals):
1091    """Calculate what __package__ should be.
1092
1093    __package__ is not guaranteed to be defined or could be set to None
1094    to represent that its proper value is unknown.
1095
1096    """
1097    package = globals.get('__package__')
1098    spec = globals.get('__spec__')
1099    if package is not None:
1100        if spec is not None and package != spec.parent:
1101            _warnings.warn("__package__ != __spec__.parent "
1102                           f"({package!r} != {spec.parent!r})",
1103                           ImportWarning, stacklevel=3)
1104        return package
1105    elif spec is not None:
1106        return spec.parent
1107    else:
1108        _warnings.warn("can't resolve package from __spec__ or __package__, "
1109                       "falling back on __name__ and __path__",
1110                       ImportWarning, stacklevel=3)
1111        package = globals['__name__']
1112        if '__path__' not in globals:
1113            package = package.rpartition('.')[0]
1114    return package
1115
1116
1117def __import__(name, globals=None, locals=None, fromlist=(), level=0):
1118    """Import a module.
1119
1120    The 'globals' argument is used to infer where the import is occurring from
1121    to handle relative imports. The 'locals' argument is ignored. The
1122    'fromlist' argument specifies what should exist as attributes on the module
1123    being imported (e.g. ``from module import <fromlist>``).  The 'level'
1124    argument represents the package location to import from in a relative
1125    import (e.g. ``from ..pkg import mod`` would have a 'level' of 2).
1126
1127    """
1128    if level == 0:
1129        module = _gcd_import(name)
1130    else:
1131        globals_ = globals if globals is not None else {}
1132        package = _calc___package__(globals_)
1133        module = _gcd_import(name, package, level)
1134    if not fromlist:
1135        # Return up to the first dot in 'name'. This is complicated by the fact
1136        # that 'name' may be relative.
1137        if level == 0:
1138            return _gcd_import(name.partition('.')[0])
1139        elif not name:
1140            return module
1141        else:
1142            # Figure out where to slice the module's name up to the first dot
1143            # in 'name'.
1144            cut_off = len(name) - len(name.partition('.')[0])
1145            # Slice end needs to be positive to alleviate need to special-case
1146            # when ``'.' not in name``.
1147            return sys.modules[module.__name__[:len(module.__name__)-cut_off]]
1148    elif hasattr(module, '__path__'):
1149        return _handle_fromlist(module, fromlist, _gcd_import)
1150    else:
1151        return module
1152
1153
1154def _builtin_from_name(name):
1155    spec = BuiltinImporter.find_spec(name)
1156    if spec is None:
1157        raise ImportError('no built-in module named ' + name)
1158    return _load_unlocked(spec)
1159
1160
1161def _setup(sys_module, _imp_module):
1162    """Setup importlib by importing needed built-in modules and injecting them
1163    into the global namespace.
1164
1165    As sys is needed for sys.modules access and _imp is needed to load built-in
1166    modules, those two modules must be explicitly passed in.
1167
1168    """
1169    global _imp, sys
1170    _imp = _imp_module
1171    sys = sys_module
1172
1173    # Set up the spec for existing builtin/frozen modules.
1174    module_type = type(sys)
1175    for name, module in sys.modules.items():
1176        if isinstance(module, module_type):
1177            if name in sys.builtin_module_names:
1178                loader = BuiltinImporter
1179            elif _imp.is_frozen(name):
1180                loader = FrozenImporter
1181            else:
1182                continue
1183            spec = _spec_from_module(module, loader)
1184            _init_module_attrs(spec, module)
1185
1186    # Directly load built-in modules needed during bootstrap.
1187    self_module = sys.modules[__name__]
1188    for builtin_name in ('_thread', '_warnings', '_weakref'):
1189        if builtin_name not in sys.modules:
1190            builtin_module = _builtin_from_name(builtin_name)
1191        else:
1192            builtin_module = sys.modules[builtin_name]
1193        setattr(self_module, builtin_name, builtin_module)
1194
1195
1196def _install(sys_module, _imp_module):
1197    """Install importers for builtin and frozen modules"""
1198    _setup(sys_module, _imp_module)
1199
1200    sys.meta_path.append(BuiltinImporter)
1201    sys.meta_path.append(FrozenImporter)
1202
1203
1204def _install_external_importers():
1205    """Install importers that require external filesystem access"""
1206    global _bootstrap_external
1207    import _frozen_importlib_external
1208    _bootstrap_external = _frozen_importlib_external
1209    _frozen_importlib_external._install(sys.modules[__name__])
1210