-
Notifications
You must be signed in to change notification settings - Fork 106
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
Installing PyQt6 on macOS #100
Comments
PS: @colesbury - thanks for all your work on nogil and I'm very excited to see PEP 703! |
Hi @jimkring, I'll look into build a PyQT6 wheel for macOS. |
I noticed that I get similar issues when I try to install numpy:
|
Update: Using the
(note the "=" after "--confirm-license=" is required)] |
Hi @jimkring, I think something strange is going on. You should be able to just run "pip install numpy" and get the pre-built binary wheel for NumPy 1.24.0 on macOS. You should not need to install it from source. Can you provide details about your installation:
|
Hi @colesbury. I'm on an Intel mac. I installed nogil via I then created a virtual environment via Then, after activating the venv, I think I probably updated pip (out of habit):
Here's the output of
|
I should also mention: I've been able to successfull build+install pyqt6. That's good news. However, I then realized that PyQt6 does not include the Here's how I did that (and let me know if you'd like me to open a different issue for the pyside/libshiboken build issue). Pull a copy of the pyside sources Switch to the version/branch we want to build Start the build
We can see this error Thanks for looking into this. I'm excited to start testing out nogil (and encouraging others to do so). |
Great! I got it to build locally too after some challenges with homebrew. I'll see if it's not too much work to build binary wheels once we figure out the other issues.
This looks like it needs to use It also sounds like there is a similar issue in nuitka. Is nuitka a dependency of pyside6?
Let's wait until we figure out any issues on the nogil side. |
Hi @colesbury some answers and updates...
No, nuitka is not related to pyside6 -- nuitka is a python compiler for building stand-alone executables. Regarding the pyside/libshiboken build issue, I did a search in the code for use of before: for (int index : std::as_const(invalidateArgs)) {
s << "bool invalidateArg" << index << " = PyTuple_GET_ITEM(" << PYTHON_ARGS
<< ", " << index - 1 << ")->ob_refcnt == 1;\n";
} after: for (int index : std::as_const(invalidateArgs)) {
s << "bool invalidateArg" << index << " = Py_REFCNT(PyTuple_GET_ITEM(" << PYTHON_ARGS
<< ", " << index - 1 << ")) == 1;\n";
} Also, I looked at what it would take to upstream such fixes to PySide6 and the process described on the Qt Contribution Guidelines is a little daunting to me. I have a pyside6 build in progress and it takes a long time... we'll see how it goes. |
I've gotten farther -- I can now build/install pyside6. This runs to completion:
However, I get a segfault, even with a simple hello world example :(
|
@jimkring I will have a deeper look into nogil on PySide. |
Thanks @ctismer! |
@ctismer -- I just noticed you're on the Qt team. I'm sure you can figure this all out much faster than I could ever, and... I figured I'd share with you the changes I made to the pyside6 code to get it to build. Here is a PR with the changes in a fork I made of pyside-setup -> jimkring/pyside-nogil#1 (I'm working in the nogil branch) |
Yes folks, I've been hacking away at PySide for 7 years now and even managed to get a PyPy build working. So I thought it would be a good thing to jump on the NoGil wagon as the next big thing for PySide. PyPy really pushed me to my limit and beyond in that regard, although the response to it was pretty unsatisfactory. I think the effort-to-benefit ratio should be much better with NoGil. Thanks for your patch @jimkring , I'll get right on it :-) |
FYI: The equivalent to Signal and Slot in PyQt are pyqtSignal and pyqtSlot.
But now warming up the VS-Code debugger, quite helpful to look at a debug build. |
@ctismer it’s nice to learn more of the history of pyside. Thanks for that info (and tips). I am certain NoGil is going to be a huge benefit to all, so thanks in advance for supporting that. It’s a fun place to explore, for sure. Cheers. |
@colesbury I see quite different opcodes - even the convention of 2 byte per opcode was not used. |
@ctismer Does PyQt depend on the byte code format? The byte code changes will probably not be ported to 3.12. In C code, you can use the |
@colesbury Ah, fine! Thanks for your help! |
Hi @colesbury and @ctismer, Here's a nice update -> I've been able to get my application to run on NoGIL with PyQt6! (Christian, your the tip about where to find pyqtSignal and pyqtSlot was very helpful, so thanks again. I'm still VERY interested in getting PyQt6 running in NoGIL, so I'm still very eager to help test PySide6 on NoGIL and don't want my my "good news" to slow us down :) For what it's worth, Sam, my application seems to be much snappier running in NoGIL. It uses trio for concurrency -- I used the asyncio examples on doc.qt.io/qtforpython as a starting point, which has worked well (Christian, perhaps you helped write those? Thanks!). I'm now going to look into how best to move from asyncio over to threads for concurrency+parallelism and see how that goes. |
Your app is running? But there must be lots of bugs in the test suite, at least I get quite a lot in PySide. |
@colesbury We have some unit tests which check the refcounts. Some of them fail, they are off by one. The tests use no threads. Is that to be expected? Also, about 1/5th of unit tests segfault at the end. How can that be without threading? I still have to test with setting the environment flag, tomorrow. |
@ctismer my unit tests probably aren't as extensive as yours and perhaps I have bugs in the form of race conditions that are yet to be observed :) I'm a parallel programmer by trade, and I'm excited to help Python become more parallel. |
Yes. Some objects are "immortal", including small integers. For what it's worth, "immortal objects" is probably going to land in Python 3.12 completely independently of the nogil changes (and with a different implementation.)
I don't know without more information. If you can get a stack trace from gdb, that would help. |
@colesbury Hi Sam, just tried it: |
python3.9-2023-02-09-113333.txt |
Hi @ctismer, I think the problem is that signalmanager.cpp is calling into Python without trying to acquire the GIL: Although, the whole point of the project is to remove the GIL, it's still important to call those same functions to attach/detach the thread from the VM. The functions are still important, they just don't prevent multiple threads from running concurrently. (Here's the section of the PEP that explains it a bit more.) I don't think calling the |
@colesbury Whow, thank you! How could you find that with that dump? For some reason, it was quite unreadable for me. Repeated this now and got a better readable one, which in fact tells me what you said. Yeah, it works for this example. Running all tests now. Yes, only 7 out of 616 tests fail - that is great! |
@ctismer Great! A lot of the same issues crop up repeatedly both during development of the "nogil" fork and in extensions. This one, where I'll start maintaining a list of common issues and how they appear. Maybe that will help with future extensions. EDIT: Started documenting common issues on the wiki: https://github.com/colesbury/nogil/wiki/Common-issues-with-extensions |
BTW.: Do you know the GIL-carousal effect? The reason to use no GIL with signals? |
@ctismer I hadn't heard of the GIL carousel effect, but the linked bug report explains it well. I've encountered performance issues due to releasing the GIL, mostly due to the overhead of Both those issues should be greatly reduced with the nogil fork: the overhead of |
@colesbury Your hint was great.
The python_thread test is flaky. It seems that something needs to be locked, now. I might stop this now, since the basic functionality is there. |
@ctismer Do you have a fork with changes? Can you point me at it? I'd like to take a look at the threading issues. |
@colesbury Yes, I will create a branch on github, tomorrow. |
@colesbury Hi Sam, This repo needs the Qt 6.4.2 branch. I am building with the following setting:
This should work with all but the two mentioned tests:
Oh, and I saw the |
@ctismer - thanks! I'm able to reproduce the issues. The sources/shiboken6/tests/samplebinding/python_thread_test.py The bucket list was previously protected from concurrent access by the GIL. Without the GIL, it needs protection by a mutex (e.g., colesbury/pyside6-dev@d71fb16) sources/shiboken6/tests/samplebinding/cyclic_test.py This isn't related to the GIL, at least not directly (there aren't any threads in this test). It has to do with the order of destruction of cyclic trash in the garbage collector. The immediate cause is that the child C++ For context, the order of destruction of cyclic trash is sometimes different than in upstream. In upstream CPython, it's mostly deterministic (usually in older objects are destroyed first). In nogil Python, objects are found scanning the GC heap, and a lot of things can affect the order. (I think this is why the test only crashes sometimes.) Mostly for my own future reference, here's the steps I took to build pyside6 (on macOS 13.1, ARM64):
|
@ctismer - here's a possible patch to address the cyclic_test.py issue: For context, you can trigger a similar crash in upstream CPython if you change the order in which |
@colesbury Great, I will continue tomorrw. |
@ctismer - I forget exactly when the 3.12 feature freeze is, but at this point I don't expect any major GIL-related changes to make it in to 3.12. |
Freeze is May 8th |
@colesbury Hi Sam, The fix for the |
@colesbury Ok, I checked the patches also with normal Python, all great. In a sense, we can claim now
modulo the many missing NoGIL tests 😆 |
@ctismer It'll be great to get these changes merged into the main repo. In general, I'd like to preserve the behavior of CPython, but in this case, I don't how to, at least not without substantial performance penalties. It might be possible to do something narrow that would avoid the issue in PyPy has a pretty different GC implementation than CPython, and at least in some simple tests, can finalize objects in a different order than CPython. I'm not sure why the |
@colesbury Ok, nice that I may merge this into the main repo (hope the'll take it). Ok, I take it that it was a bug in our code that just worked, but needed to be made more stable against changes in the calling sequence. On That it segfaulted during build is probably an overlap since you built two versions of Python 3.9 (maybe). You should try a clean build, then things should work. You can run the tests also with a build, only. The overlap comes from a site-packages entry that is not unique. |
Hi @colesbury and @ctismer. I'm still getting a it appears to be happening in the constructor of an object which is a subclass of Note: I'm testing with nogil 3.9.10-1 and qt 6.4.2. I was able to pinpoint the crash location using a combination of |
Hi @jimkring can you please give me some code? Simply creating an $ /Users/tismer/.pyenv/versions/nogil-3.9.10-1-debug/bin/python3
Python 3.9.10 (main, Feb 6 2023, 15:50:18)
[nogil, Clang 14.0.0 (clang-1400.0.29.202)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> from PySide6.QtWidgets import *
>>> self = QGraphicsRectItem()
>>> crash = QGraphicsTextItem(parent=self)
>>> Quite apart from that, please do not get your hopes up too high: However, I will try to craft a NoGIL version of the PySide-Mandelbrot example shortly. |
Hi @jimkring @colesbury As promised, I have adapted a PySide Mandelbrot program for use with NoGil. My version takes the display I tried different thread pool sizes. Funnily, So, this result is partly nice, partially disappointing, because of the worse performance with increased core number. |
Hi again,
@colesbury Can you imagine what that behavior means? Do I have a glaring bug, or is the function I am uploading the source files now. The machine used was a |
EDIT: Oops I swapped the results from 4 and 8 threads. |
Nevermind - I swapped the results from 4 and 8 threads. Really strange that higher number of iterations scale worse with more threads... |
@ctismer, the scaling issue is due to reference count contention, especially on
You can do the same thing for the other shared numbers (e.g., |
@colesbury Arrrgh yes now I see it 😀 many thanks! |
Hi. I'm trying to install PyQt6 on nogil. I have no idea if it should work or not.
It gets stuck at
Preparing metadata (pyproject.toml) ...
I installed qt6 with homebrew and it appears to accessible in the PATH -- I can run
qmake
just fine.Thanks for any ideas. Looking forward to exploring nogil!
Update
The text was updated successfully, but these errors were encountered: