Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New PEP: A Per-Interpreter GIL #2212

Closed

Conversation

ericsnowcurrently
Copy link
Member

This is an informational PEP explaining the issues and work around making the GIL per-interpreter.

(I hope to publish/post later this week, but figured I'd get the meat of it up now so I can point people at it.)

@brettcannon
Copy link
Member

Does this really need to be a PEP if it is just basically going to be a white paper trying to justify a per-interpreter GIL (which has not been approved to occur)?

@gvanrossum
Copy link
Member

gvanrossum commented Jan 6, 2022 via email

https://bugs.python.org/issue40077 Convert static types to heap types: use PyType_FromSpec()
https://bugs.python.org/issue42972 [C API] Heap types (PyType_FromSpec) must fully implement the GC protocol
https://bugs.python.org/issue15870 PyType_FromSpec should take metaclass as an argument
https://bugs.python.org/issue45113 [subinterpreters][C API] Add a new function to create PyStructSequence from Heap.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe we can add this issue too.
https://bugs.python.org/issue1635741

@warsaw
Copy link
Member

warsaw commented Jan 7, 2022

Does this really need to be a PEP if it is just basically going to be a white paper trying to justify a per-interpreter GIL (which has not been approved to occur)?

On this narrow question, given that we don't have any other good repository for these types of documents, it doesn't bother me for things like this to be information PEPs. And even so, if they weren't PEPs, how would they be discoverable?

@encukou
Copy link
Member

encukou commented Jan 7, 2022

I'm under the impression that an informational PEP is essentially a whitepaper. What PEP 1 says looks like a definition of a whitepaper. (Or is my English failing me and we're talking about a different meaning of the term?)
Of course, an informational PEP cannot be approved, so it's not the only PEP you'll need to make big changes to the language. The "proposal" section would be better named "plan" or "goals".

@vstinner
Copy link
Member

vstinner commented Jan 7, 2022

IMO this topic is too wide to fit everything into a single PEP. I suggest to split it into multiple (smaller) PEPs:

  • Rationale for running multiple interpreters in parallel: focus on use cases, performance
  • Guideline to make things per-interpreter. Note: I don't think that a PEP should track the progress of such work.
  • Address the complex problem of static types
  • Address the complex problem of singletons
  • Make the GIL per interpreter: elaborate the impact on C extensions, explain how to migrate existing C extensions to that, propose a solution to continue supporting C extensions which are "compatible"

For static types and singletons, it seems like you are supporter of immortal objects. Well, I dislike immortal objects and there are other solutions to these problems. For example, make singletons per interpreter, and keep static types in the main interpreter, but modify C extensions to call functions to get types, in C extensions which needs to be compatible with sub-interpreters (all stdlib extensions must be modified this way).

IMO the key is the migration plan. How to introduce this feature without requiring all C extensions to be written on a flag day? It has been discussed multiple times to add a flag to a C extension to opt in for sub-interpreters support.

Moreover, IMO we should also consider to support multiple interpreters sharing the same GIL ("shared GIL", current behavior) and interprereters having their own GIL ("isolated"). Again, it's to have a more smooth migration plan, to avoid having to rewrite all C extensions on a flag day.

@ericsnowcurrently
Copy link
Member Author

Does this really need to be a PEP if it is just basically going to be a white paper trying to justify a per-interpreter GIL (which has not been approved to occur)?

Yeah, after the conversation here it makes sense to me to split the PEP into the decidable parts (and maybe not even do an informational PEP).

@gvanrossum
Copy link
Member

  • Rationale for running multiple interpreters in parallel: focus on use cases, performance

This could be split into two parts:

  • Rationale for multiple interpreters while GIL remains shared
  • Rationale for multiple interpreters with separate GILs

And we should probably address the downsides of separate GILs:

  • Can only share immutable immortal objects
  • Issues for ABI and API compatibility

@ericsnowcurrently
Copy link
Member Author

  • Rationale for running multiple interpreters in parallel: focus on use cases, performance

This would be good and would benefit PEP 554 as well. However, I'm worried that I don't have enough time to do all these PEPs at once and still get anything else done. This PEP doesn't seem like it would add enough value to make it worth it. (The general points would just go into other PEPs, with not as much detail.)

  • Guideline to make things per-interpreter. Note: I don't think that a PEP should track the progress of such work.

To me, the devguide would be a better place for this.

Aside from guidelines for the transition to per-interpreter, we would also need to cover any constraints core devs need to keep in mind relative to subinterpreters. We would also document any related tooling, e.g. c-analyzer (if that survives). This information would be valuable well after the GIL becomes per-interpreter.

  • Address the complex problem of static types
  • Address the complex problem of singletons

Why would these be separate PEPs?

  • Make the GIL per interpreter: elaborate the impact on C extensions, explain how to migrate existing C extensions to that, propose a solution to continue supporting C extensions which are "compatible"

This is basically already covered by PEP 630.

For static types and singletons, it seems like you are supporter of immortal objects. Well, I dislike immortal objects and there are other solutions to these problems. For example, make singletons per interpreter, and keep static types in the main interpreter, but modify C extensions to call functions to get types, in C extensions which needs to be compatible with sub-interpreters (all stdlib extensions must be modified this way).

That's pretty much exactly what I was planning on until recently. 🙂 At first I looked into immortal objects because they solve the problem so much more simply. However, there didn't seem to be a good way to work around the performance penalty. So I focused on per-interpreter objects (and successfully prototyped most of it).

However, now immortal objects may be possible without the penalty. I'm going to do some benchmarking on the current branch. If they work out then I'd rather go with that because it is so much simpler.

Either way we should consider deprecating all the objects in the C-API, and provide lookup functions as a replacement.

IMO the key is the migration plan. How to introduce this feature without requiring all C extensions to be written on a flag day?

No extensions will need to be rewritten. In subinterpreters created via Py_NewInterpreter(), extensions that currently work will keep working. Those that don't currently work there will still not work.

If an extension wants to be used in subinterpreters that do not share a GIL, they would have to be isolated (PEPs 489/630) first. However, that would be new in 3.11, so there is not compatibility issue. Existing code will keep working.

It has been discussed multiple times to add a flag to a C extension to opt in for sub-interpreters support.

PEP 489 says that if an extension implements multi-phase init then it must support subinterpreters (and reloading, etc.).

Moreover, IMO we should also consider to support multiple interpreters sharing the same GIL ("shared GIL", current behavior) and interprereters having their own GIL ("isolated").

That is exactly the plan. Py_NewInterpreter() will continue creating subinterpreters that do share a GIL.

@JelleZijlstra
Copy link
Member

FYI, PEP 679 is now taken.

@brettcannon
Copy link
Member

The SC talked about this and if you want to move forward with an informational PEP that outlines plans, @ericsnowcurrently , then that's fine. We do want to be very clear, though, that it doesn't give tacit approval for the idea, just a place for you to collect and write down what you want to accomplish and how you plan to pull it off.

We may also to move/copy it somewhere else in the future as we are now talking about how to handle communication of these large projects.

@CAM-Gerlach CAM-Gerlach changed the title Add PEP 679, "A Per-Interpreter GIL". Add PEP 679, "A Per-Interpreter GIL" Jan 24, 2022
@CAM-Gerlach CAM-Gerlach changed the title Add PEP 679, "A Per-Interpreter GIL" New PEP: A Per-Interpreter GIL Jan 24, 2022
@ericsnowcurrently
Copy link
Member Author

I'll be posting a PEP just about immortal objects soon, as well a more focused one about per-interpreter GIL. Both will be leaner this this one.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

9 participants