-
-
Notifications
You must be signed in to change notification settings - Fork 20
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
Semaphore cancellation should increment semaphore value #3
Semaphore cancellation should increment semaphore value #3
Conversation
Hello @KaiOelfke, Thanks for the pull request: you found a bug indeed 👍 The pull request contains a lot more than a fix, though. In particular, I don't understand the many added How does the What is the purpose of I appreciate that you feel at ease with the project, because not many people do so, and not many people try to improve it :-) I'm just trying to limit the changes to the useful ones. |
When I started experimenting with the code by default Xcode was running the test scheme on an iOS simulator. The size of the cooperative thread pool seems to be one in this scenario on my machine, in debug and with Xcode 14.1 and because of this some unit tests fail. LIBDISPATCH_COOPERATIVE_POOL_STRICT is an environment variable explained in this WWDC talk: https://developer.apple.com/videos/play/wwdc2021/10254/?time=1611 If you enable this you can run tests also on a macOS destination with a pool size of 1. Without this normally the thread pool size would be bigger. Then the same tests fail. So this is the problem I described under point 3. Why does this problem happen? It's explained in the WWDC talk as forward progress. If you have a cooperative thread pool size of 1 and the one thread can't make forward progress all async code stops to run.
So how can this be fixed? Either don't use the wait API and something different like the helper function I added. Or guarantee that expectations are always fulfilled before calling I recommend you to run unit tests on main with LIBDISPATCH_COOPERATIVE_POOL_STRICT or on an iOS simulator to better understand this PR. |
It's async / non-blocking (just suspending) so it doesn't break the forward progress rule. |
Thank you very much for the learning material, this is very kind of you 🥰 Please stay tuned until I let this sink in. Automated testing on the various platforms and the variable sizes of their thread pools is definitely something this repo should be able to achieve :) |
+1 for this bug & fix. my preferred variation is this:
to ensure we don't mask the error thrown by |
OMG @dannys42, you are my soulmate 😉 edab432 Of course, thank you @KaiOelfke for spotting the issue, and apologies to everyone for my very slow reaction. I won't merge the PR. I agree there are improvements to bring, but I'd don't want this lib to become a showcase of smartness, or that anyone feels 🤯 when reading the code. So, thank you again, but I'd prefer a more humble style. The fix has shipped on the main branch, version |
No worries I also prefer easier to read code. The issue about failing unit tests on devices with a thread pool of size 1 still remains though. I think It's important to support this size as e.g. Apple Watch or iPhone simulators have such a single thread thread pool currently. Just use LIBDISPATCH_COOPERATIVE_POOL_STRICT=1 as environment variable or run tests on a Simulator to reproduce this. A custom helper like my See also the 14.3 release notes on this issue:
Note that this is an issue only with the test code and not the library code. |
Yes, thank you for this kind reminder. That's really where I have to catch up and learn from your techniques. |
I found a few things:
value += 1
line in main or lines with the changes from this PR for incrementing the value the tests still pass.But after experimenting with this I think it's not nice to use wait in async test functions, if test destinations with a cooperative thread pool size of 1 should be supported. Ideally there would be some async version of wait from XCTest that doesn't block. But as far as I know this doesn't exist.