News for hackers. Stuff that matters.
Re:gh-116167: Allow disabling the GIL by protomikron on Monday March 11, 2024 @12:51PM (#39670530)
Although this is nice, the problems with the GIL are often blown out of proportion: people stating that you couldn't do efficient (compute-bounded) multi-processing, which was never the case as the `multiprocessing` module works just fine.
Re:gh-116167: Allow disabling the GIL by ynik on Monday March 11, 2024 @01:11PM (#39670804)
multiprocessing only works fine when you're working on problems that don't require 10+ GB of memory per process. Once you have significant memory usage, you really need to find a way to share that memory across multiple CPU cores. For non-trivial data structures partly implemented in C++ (as optimization, because pure python would be too slow), that means messing with allocators and shared memory. Such GIL-workarounds have easily cost our company several man-years of engineer time, and we still have a bunch of embarrassingly parallel stuff that we still cannot parallelize due to GIL and not yet supporting shared memory allocation for that stuff.

Once the Python ecosystem supports either subinterpreters or nogil, we'll happily migrate to those and get rid of our hacky interprocess code.

Subinterpreters with independent GILs, released with 3.12, theoretically solve our problems but practically are not yet usable, as none of Cython/pybind11/nanobind support them yet. In comparison, nogil feels like it'll be easier to support.

Re:gh-116167: Allow disabling the GIL by ebiester on Monday March 11, 2024 @01:19PM (#39670896)
And I guess what I don't understand is why people choose Python for these use cases. I am not in the "Rustify" everything camp, but Go + C, Java + JNI, Rust, and C++ all seem like more suitable solutions.
Re:gh-116167: Allow disabling the GIL by esafak on Monday March 11, 2024 @01:31PM (#39671048)
Why do people use python for anything beyond glue code? Because it took off, and machine learning and data science now rely on it.

I think Python is a terrible language that exemplifies the maxim "worse is better".

https://en.wikipedia.org/wiki/Worse_is_better

Re:gh-116167: Allow disabling the GIL by rmbyrro on Monday March 11, 2024 @01:58PM (#39671354)
Some speculate that universities adopted it as introductory language for its expressiveness and flat learning curve. Scientific / research projects in those unis started picking Python, since all students already knew it. And now we're here
Re:gh-116167: Allow disabling the GIL by spprashant on Monday March 11, 2024 @03:36PM (#39672383)
I have no idea if this is verifiably true in a broad sense, but I work at the university and this is definitely the case. PhD students are predominantly using Python to develop models across domains - transportation, finance, social sciences etc. They then transition to industry, continuing to use Python for prototyping.
Re:gh-116167: Allow disabling the GIL by nottorp on Monday March 11, 2024 @07:33PM (#39674410)
To quote from Eric Raymond's article about python, ages ago:

"My second [surprise] came a couple of hours into the project, when I noticed (allowing for pauses needed to look up new features in Programming Python) I was generating working code nearly as fast as I could type.

When you're writing working code nearly as fast as you can type and your misstep rate is near zero, it generally means you've achieved mastery of the language. But that didn't make sense, because it was still day one and I was regularly pausing to look up new language and library features!"

Source: https://www.linuxjournal.com/article/3882

It doesn't go for large code bases, but if you need quick results using existing well tested libraries, like in machine learning and data science, I think those statements are still valid.

Obviously not when you're multiprocessing, that is going to bite you in any language.

Re:gh-116167: Allow disabling the GIL by zamadatix on Monday March 11, 2024 @01:30PM (#39671033)
People choose Python the use case, regardless what that is, because it's quick and easy to work with. When Python can't realistically be extended to a use case then it's lamented, when it can it's celebrated. Even Go, while probably the friendliest of that buch when it comes to parallel work, is on a different level.
Re:gh-116167: Allow disabling the GIL by oivey on Monday March 11, 2024 @01:23PM (#39670940)
Notably, all of those are static languages and none of them have array types as nice as PyTorch or NumPy, among many other packages in the Python ecosystem. Those two facts are likely closely related.
Re:gh-116167: Allow disabling the GIL by abdullahkhalids on Monday March 11, 2024 @01:42PM (#39671158)
Python is just the more popular language. Julia array manipulation is mostly better (better syntax, better integration, larger standard library) or as good as python. Julia is also dynamically typed. It is also faster than Python, except for the jit issues.
Re:gh-116167: Allow disabling the GIL by oivey on Monday March 11, 2024 @02:16PM (#39671568)
Preaching to the choir here.

Julia’s threading API is really nice. One deficiency is that it can be tricky to maintain type stability across tasks / fetches.

Re:gh-116167: Allow disabling the GIL by znpy on Monday March 11, 2024 @02:35PM (#39671804)
> It is also faster than Python, except for the jit issues.

I was intrigued by Julia a while ago, but didn't have time to properly learn it.

So just out of curiosity: what's the issues with jit and Julia ?

Re:gh-116167: Allow disabling the GIL by cjalmeida on Monday March 11, 2024 @03:23PM (#39672277)
The "issue" is Julia is not Just-in-Time, but a "Just-Ahead-of-Time" language. This means code is compiled before getting executed, and this can get expensive for interactive use.

The famous "Time To First Plot" problem was about taking several minutes to do something like `using Plots; Plots.plot(sin)`.

But to be fair recent Julia releases improved a lot of it, the code above in Julia 1.10 takes 1.5s on my 3-year old laptop

Re:gh-116167: Allow disabling the GIL by jakobnissen on Monday March 11, 2024 @03:01PM (#39672068)
Julia's JIT compiles code when its first executed, so Julia has a noticable delay from you start the program and until it starts running. This is anywhere from a few hundred milliseconds for small scripts, to tens of seconds or even minutes for large packages.
Re:gh-116167: Allow disabling the GIL by shiroiushi on Tuesday March 12, 2024 @01:15AM (#39676411)
I wonder why they don't just have an optional pre-compilation, so once you have a version you're happy with and want to run in production, you just have a fully compiled version of the code that you run.
Re:gh-116167: Allow disabling the GIL by aoanla on Tuesday March 12, 2024 @04:12AM (#39677227)
Effectively, it does - one of the things recent releases of Julia have done is to add more precompilation caching on package install. Julia 1.10 feels considerably snappier than 1.0 as a result - that "first time to plot" is now only a couple of seconds thanks to this (and subsequent plots are, of course, much faster than that).
Re:gh-116167: Allow disabling the GIL by samatman on Monday March 11, 2024 @01:35PM (#39671090)
If only there were a dynamic language which performs comparably to C and Fortran, and was specifically designed to have excellent array processing facilities.

Unfortunately, the closest thing we have to that is Julia, which fails to meet none of the requirements. Alas.

Re:gh-116167: Allow disabling the GIL by rmbyrro on Monday March 11, 2024 @01:55PM (#39671316)
If only there was a car that could fly, but was still as easy and cheap to buy and maintain :D
Re:gh-116167: Allow disabling the GIL by KaiserPro on Monday March 11, 2024 @05:52PM (#39673643)
> but Go + C, Java + JNI, Rust, and C++ all seem like more suitable solutions.

apart from go (maybe java) those are all "scary" languages that require a bunch of engineering to get to the point that you can prototype.

even then you can normally pybind the bits that are compute bound.

If Microsoft had been better back in the say, then c# should have been the goto language of choice. It has the best tradeoff of speed/handholding/rapid prototyping. Its also statically typed, unless you tell it to not be.

Re:gh-116167: Allow disabling the GIL by snovv_crash on Tuesday March 12, 2024 @02:33AM (#39676746)
#pragma omp parallel for

gets you 90% of the potential performance of a full multithreaded producer/consumer setup in C++. C++ isn't as scary as it used to be.

Re:gh-116167: Allow disabling the GIL by pillusmany on Monday March 11, 2024 @01:18PM (#39670890)
"Ray" can share python objects memory between processes. It's also much easier to use than multi processing.
Re:gh-116167: Allow disabling the GIL by ptx on Monday March 11, 2024 @01:44PM (#39671180)
How does that work? I'm not familiar with Ray, but I'm assuming you might be referring to actors [1]? Isn't that basically the same idea as multiprocessing's Managers [2], which also allow client processes to manipulate a remote object through message-passing? (See also DCOM.)

[1] https://docs.ray.io/en/latest/ray-core/walkthrough.html#call...

[2] https://docs.python.org/3/library/multiprocessing.html#manag...

Re:gh-116167: Allow disabling the GIL by pillusmany on Monday March 11, 2024 @02:04PM (#39671436)
Re:gh-116167: Allow disabling the GIL by ptx on Monday March 11, 2024 @02:15PM (#39671563)
According to the docs, those shared memory objects have significant limitations: they are immutable and only support numpy arrays (or must be deserialized).

Sharing arrays of numbers is supported in multiprocessing as well: https://docs.python.org/3/library/multiprocessing.html#shari...

Re:gh-116167: Allow disabling the GIL by jononor on Monday March 11, 2024 @08:50PM (#39674886)
I think that 90 or maybe even 99% of cases has under 1GB of memory per process? At least it has been the case for me the last 15 years.

Of course, getting threads to be actually useful for concurrency (GIL removed) adds another very useful tool to the performance toolkit, so that is great.

Re:gh-116167: Allow disabling the GIL by vita7777777 on Monday March 11, 2024 @01:06PM (#39670751)
On the other hand, this particular argument also gets overused. Not all compute-bounded parallel workloads are easily solved by dropping into multiprocessing. When you need to share non-trivial data structures between the processes you may quickly run into un/marshalling issues and inefficiency.
Re:gh-116167: Allow disabling the GIL by kroolik on Monday March 11, 2024 @12:56PM (#39670612)
Managing processes is more annoying than threads, though. Incl. data passing and so forth.
Re:gh-116167: Allow disabling the GIL by pillusmany on Monday March 11, 2024 @01:17PM (#39670869)
The "ray" library makes running python code on multi core and clusters very easy.
Re:gh-116167: Allow disabling the GIL by kroolik on Monday March 11, 2024 @02:48PM (#39671931)
Although its great the library helps with multicore Python, the existence of such package shouldnt be an excuse not to improve the state of things in std python
Re:gh-116167: Allow disabling the GIL by smcl on Monday March 11, 2024 @01:24PM (#39670965)
Interesting - looking at their homepage they seem to lean heavily into the idea that it's for optimising AI/ML work, not multi-process generally.
Re:gh-116167: Allow disabling the GIL by pillusmany on Monday March 11, 2024 @02:02PM (#39671410)
You can use just ray.core to do multi process.

You can do whatever you want in the workers, I parse JSONs and write to sqlite files.

Re:gh-116167: Allow disabling the GIL by liuliu on Monday March 11, 2024 @12:55PM (#39670586)
`multiprocessing` works fine for serving HTTP requests or do some other subset of embarrassingly-parallel problems.
Re:gh-116167: Allow disabling the GIL by skrause on Monday March 11, 2024 @01:44PM (#39671185)
> `multiprocessing` works fine for serving HTTP requests

Not if you use Windows, then it's a mess. I have a suspicion that people who say that the multiprocessing works just fine never had to seriously use Python on Windows.

Re:gh-116167: Allow disabling the GIL by rmbyrro on Monday March 11, 2024 @02:03PM (#39671429)
Probably a very small minority of Python codebases run on Windows, no? That's my impression. It would explain why so many people are unaware of multiprocessing issues on Windows. I've never ran any serious Python code on windows...
Re:gh-116167: Allow disabling the GIL by ptx on Monday March 11, 2024 @01:51PM (#39671271)
Why is it a mess? What's wrong with it on Windows?
Re:gh-116167: Allow disabling the GIL by skrause on Monday March 11, 2024 @01:58PM (#39671356)
* A lack of fork() makes starting new processes slow.

* All Python webservers that somewhat support multiprocessing on Windows disable the IOCP asyncio event loop when using more than one process (because it breaks in random ways), so you're left with the slower select() event loop which doesn't support more than 512 connections.

Re:gh-116167: Allow disabling the GIL by colatkinson on Monday March 11, 2024 @05:43PM (#39673570)
Adding on to the other comment, multiprocessing is also kinda broken on Linux/Mac.

1. Because global objects are refcounted, CoW effectively isn't a thing on Linux. They did add a way to avoid this [0], but you have to manually call it once your main imports are done.

2. On Mac, turns out a lot of the system libs aren't actually fork-safe [1]. Since these get imported inadvertently all the time, Python on Mac actually uses `spawn` [2] -- so it's roughly as slow as on Windows.

I haven't worked in Python in a couple years, but handling concurrency while supporting the major OSes was a goddamn mess and a half.

[0]: https://docs.python.org/3.12/library/gc.html#gc.freeze

[1]: https://bugs.python.org/issue33725

[2]: https://docs.python.org/3.12/library/multiprocessing.html#co...

Re:gh-116167: Allow disabling the GIL by fulafel on Monday March 11, 2024 @11:59PM (#39676064)
Re (1), are there publicly documented cases with numbers on observed slowdowns with it?

I see this mentioned from time to time, but intuitively you'd think this wouldn't pose a big slowdown since the system builtin objects would have been allocated at the same time (startup) and densely located on some pages. I guess if you have a lot of global state in your app it could be more significant.

Re:gh-116167: Allow disabling the GIL by fulafel on Tuesday March 12, 2024 @12:02AM (#39676068)
Re (1), are there publicly documented cases with numbers on observed slowdowns with it?

I see this mentioned from time to time, but intuitively you'd think this wouldn't pose a big slowdown since the system builtin objects would have been allocated at the same time (startup) and densely located on smaller nr of pages. I guess if you have a lot of global state in your app it could be more significant.

Would also be interesting to see a benchmark using hugepages, you'd think this could solve remaining perf problems if they were due to large number of independent CoW page faults.

Re:gh-116167: Allow disabling the GIL by fulafel on Tuesday March 12, 2024 @11:19AM (#39680558)
Replying to my self: it seems one poster case was Instagram and their very large Django app: https://bugs.python.org/issue40255#msg366835
Re:gh-116167: Allow disabling the GIL by jcranmer on Monday March 11, 2024 @01:32PM (#39671061)
> as the `multiprocessing` module works just fine.

Something that tripped me up when I last did `multiprocessing` was that communication between the processes requires marshaling all the data into a binary format to be unmarshaled on the other side; if you're dealing with 100s of MB of data or more, that can be quite some significant expense.