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 — Disallow multiple initializations of asyncio tasks and futures · Issue #142615 · python/cpython

Disallow multiple initializations of asyncio tasks and futures #142615

New issue
Copy link
New issue
Copy link
Closed
Closed
Disallow multiple initializations of asyncio tasks and futures#142615
Copy link
Labels
3.15bugs and security fixesbugs and security fixestopic-asynciotype-featureA feature request or enhancementA feature request or enhancement

Description

@kumaraditya303
kumaraditya303
opened on Dec 12, 2025
Issue body actions

Problem

This is a long standing issue of the _asyncio accelerator module where _asyncio.Task and _asyncio.Future define tp_init slot instead of tp_new slot for creating the object. This allows malicious code to re-initialize objects while tasks and futures are executing which can crash the interpreter because internally the fields of tasks and futures are accessed using borrowed references for performance.

There have been multiple reports of this where we previously changed the code to use strong references like #126080 but still there are a lot of places where borrowed references to loop is used etc.

IMO changing the code to use strong references is not the solution here, instead we should make tasks and futures immutable at C level so that this issue would not exist in the first place. Avoiding strong references is also important for performance especially in free-threading.

Proposal

Historically _asyncio.Task and _asyncio.Future define tp_init rather than tp_new, so we cannot change it to use tp_new as it would break compatibility with subclasses. To preserve backward compatibility I propose to to instead allow tp_init to be called exactly once and if user tries to initialize it again, raise RuntimeError that task cannot be re-initialized. This would prevent all these issues while preserving backwards compatibility and performance.

Linked PRs

  • gh-142615: disallow multiple initializations of asyncio tasks and futures #142616

Activity

  1. kumaraditya303
    added
    topic-asyncio
    on Dec 12, 2025
  2. github-project-automation
    added this to asyncioon Dec 12, 2025
  3. github-project-automation
    moved this to Todo in asyncioon Dec 12, 2025
  4. kumaraditya303
    added
    3.15bugs and security fixesbugs and security fixes
    on Dec 12, 2025
  5. gvanrossum commented on Dec 12, 2025

    @gvanrossum
    gvanrossum
    on Dec 12, 2025
    Member
    More actions

    I'm a little surprised that we can't change __init__ to __new__, but I trust there's working code that we want to support that relies on it -- somehow. (But would that code perhaps also be broken when we disallow a second __init__ call?)

    Just make sure to make the same change in the pure Python code.

    And I would love to see an example in the wild that would break by switching to __new__.

  6. kumaraditya303 commented on Dec 12, 2025

    @kumaraditya303
    kumaraditya303
    on Dec 12, 2025
    ContributorAuthor
    More actions

    I'm a little surprised that we can't change init to new, but I trust there's working code that we want to support that relies on it -- somehow. (But would that code perhaps also be broken when we disallow a second init call?)

    I did a similar change of changing __init__ to __new__ for struct.Struct a while ago in #78724 but it had to reverted because it broke third party code.

  7. gvanrossum commented on Dec 12, 2025

    @gvanrossum
    gvanrossum
    on Dec 12, 2025
    Member
    More actions

    Bummer. I wonder what people are doing in the wild. For struct.Struct, the only clue in that issue is this:

    reverted, since it broke code for users in the wild who were subclassing struct.Struct.

    And reading through the reverted PR, I find #94532 (comment) which shows the problem. (IIUC, the added builtin __new__ doesn't support all possible signatures, which means subclasses would have to override __new__ to match their __init__ and it should call something like super().__new__(format).

    Okay, so I agree we probably shouldn't change. Sigh. I presume we have this problem with all classes that define both __new__ and __init__.

  8. StanFromIreland
    added
    type-featureA feature request or enhancementA feature request or enhancement
    on Dec 12, 2025
  9. kumaraditya303
    added a commit that references this issue on Jan 3, 2026

    gh-142615: disallow multiple initializations of `asyncio.Task` and `a…

    abdbe0b
  10. kumaraditya303 commented on Jan 3, 2026

    @kumaraditya303
    kumaraditya303
    on Jan 3, 2026
    ContributorAuthor
    More actions

    The PR is merged and multiple initializations of asyncio tasks and futures is disallowed now in both pure python and C implementation.

  11. kumaraditya303
    closed this as completedon Jan 3, 2026
  12. github-project-automation
    moved this from Todo to Done in asyncioon Jan 3, 2026
  13. thunder-coding
    added a commit that references this issue on Feb 15, 2026

    pythongh-142615: disallow multiple initializations of `asyncio.Task` …

    b6beaa3
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

    3.15bugs and security fixesbugs and security fixestopic-asynciotype-featureA feature request or enhancementA feature request or enhancement

    Projects

    • asyncio
      Status
      Done
      Show more project fields

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions

    You are visitor 01402503 — 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.