GV

GeezerVison

The World Wide Web, restored to 800 pixels of glory.

Home|About|Gaming cabinet|Archives|How it works|Starter sites

On this site

  • Sign in
  • ActionsCI/CD and automation
  • CodespacesCloud development environments
  • All Features
  • Documentation
  • Training
  • Certifications
  • Build with Copilot
  • Customize Copilot
  • Integrations
  • Trending repos
  • GitHub Sponsors
  • Developer articles
  • Enterprises

This view

  • Original page
  • New address

GeezerVison is showing github.com — Infinite Loop in `typing.get_type_hints()` via Circular `__wrapped__` · Issue #146553 · python/cpython

Infinite Loop in typing.get_type_hints() via Circular __wrapped__ #146553

New issue
Copy link
New issue
Copy link
Closed
Closed
Infinite Loop in typing.get_type_hints() via Circular __wrapped__#146553
Copy link
Labels
stdlibStandard Library Python modules in the Lib/ directoryStandard Library Python modules in the Lib/ directorytopic-typingtype-bugAn unexpected behavior, bug, or errorAn unexpected behavior, bug, or error

Description

@raminfp
raminfp
opened on Mar 28, 2026
Issue body actions

Bug report

Bug description:

typing.get_type_hints() traverses the __wrapped__ attribute chain with no cycle detection. A callable whose __wrapped__ refers back to itself (or forms any cycle) causes an infinite loop, hanging the Python process indefinitely.

inspect.unwrap() solves the identical problem correctly by raising ValueError on cycle detection. get_type_hints() does not use that helper and has no equivalent guard.

Minimal Reproducer

import typing

def f(): pass
f.__wrapped__ = f          # direct self-reference

typing.get_type_hints(f)   # hangs forever - process must be killed

Longer cycle:

def a(): pass
def b(): pass
a.__wrapped__ = b
b.__wrapped__ = a          # mutual cycle

typing.get_type_hints(a)   # also hangs forever

Root Cause

File: Lib/typing.py, get_type_hints(), lines 2488-2489 (CPython main):

# Find globalns for the unwrapped object.
while hasattr(nsobj, '__wrapped__'):
    nsobj = nsobj.__wrapped__   # NO cycle detection

The loop walks the __wrapped__ chain to reach the innermost function and obtain
its __globals__. There is no visited-set, no counter, and no recursion limit.


Comparison with inspect.unwrap()

Lib/inspect.py, unwrap() (lines 679-692) solves the identical problem:

memo = {id(f): f}
recursion_limit = sys.getrecursionlimit()
while not isinstance(func, type) and hasattr(func, '__wrapped__'):
    func = func.__wrapped__
    id_func = id(func)
    if (id_func in memo) or (len(memo) >= recursion_limit):
        raise ValueError('wrapper loop when unwrapping {!r}'.format(f))
    memo[id_func] = func
return func

inspect.unwrap() raises ValueError immediately on cycle detection.


Fix

Replace the bare while loop with inspect.unwrap():

import inspect as _inspect

nsobj = obj
try:
    nsobj = _inspect.unwrap(nsobj)
except (TypeError, ValueError):
    pass
globalns = getattr(nsobj, '__globals__', {})

Or inline the visited-set guard:

nsobj = obj
_seen = {id(nsobj)}
while hasattr(nsobj, '__wrapped__'):
    nsobj = nsobj.__wrapped__
    _id = id(nsobj)
    if _id in _seen:
        raise ValueError(f"wrapper loop when unwrapping {obj!r}")
    _seen.add(_id)
globalns = getattr(nsobj, '__globals__', {})

CPython versions tested on:

CPython main branch

Operating systems tested on:

Linux

Linked PRs

  • gh-146553: Fix infinite loop in typing.get_type_hints() on circular __wrapped__ #146554
  • gh-146553: Fix infinite loop in typing.get_type_hints() on circular __wrapped__ #148595
  • [3.14] gh-146553: Fix infinite loop in typing.get_type_hints() on circular __wrapped__ (GH-148595) #148895
  • [3.13] gh-146553: Fix infinite loop in typing.get_type_hints() on circular __wrapped__ (GH-148595) #148896

Activity

  1. raminfp
    added
    type-bugAn unexpected behavior, bug, or errorAn unexpected behavior, bug, or error
    on Mar 28, 2026
  2. StanFromIreland
    added
    stdlibStandard Library Python modules in the Lib/ directoryStandard Library Python modules in the Lib/ directory
    on Mar 28, 2026
  3. picnixz
    added
    topic-typing
    on Mar 28, 2026
  4. ashm-dev
    added a commit that references this issue on Apr 15, 2026

    pythongh-146553: Fix infinite loop in typing.get_type_hints() on circ…

    0515a54
  5. JelleZijlstra
    added 3 commits that reference this issue on Apr 23, 2026

    gh-146553: Fix infinite loop in typing.get_type_hints() on circular _…

    be833e6

    [3.13] gh-146553: Fix infinite loop in typing.get_type_hints() on cir…

    f540bc9

    [3.14] gh-146553: Fix infinite loop in typing.get_type_hints() on cir…

    27cd234
  6. ljfp
    added a commit that references this issue on Apr 25, 2026

    pythongh-146553: Fix infinite loop in typing.get_type_hints() on circ…

    3ae86b4
  7. StanFromIreland
    closed this as completedon May 2, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    stdlibStandard Library Python modules in the Lib/ directoryStandard Library Python modules in the Lib/ directorytopic-typingtype-bugAn unexpected behavior, bug, or errorAn unexpected behavior, bug, or error

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions

      You are visitor 01402520 — GeezerVison does not store the pages you look up.
      Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800×600. No cookies required.