Something’s wrong with your explanation here. In those two scenarios, you say “main thread” and cooperative thread" but the first scenario is “cooperative” and the other scenario is “preemptive”
From my experience, I’m guessing that in a preemptive thread, Sleep is a no-op. Why would you want that to sleep anyway? The whole reason to use a different core is to do it as fast as possible anyway, right?
If it is, it is wrong. Sleep must work as the designer of the process requested. Why he wants some process sleeping is something no one would guess or judge, he wants or NEEDs “for some reason”, just do it.
I can think of tons of use cases where I don’t want a thread to be in a tight loop burning 100% CPU, so I think that would not be a good design if true.
But regardless, in this scenario the bug appears to be that the Main thread can’t sleep, and the preemptive thread is sleeping too long.
Sure thing - I’m just bummed that I wasn’t able to do more testing when 2024R3 was in beta (I’m on an academic schedule and Xojo beta releases always seem to come at the wrong time of the year for me)
What about using threads on different cores to talk to different sockets? Where you might be using Sleep() to implement a timeout - that is, while waiting for data, sleep for a while and if you get data set a flag and resume the thread, whereas if the sleep finishes with the flag unset then you have a timeout (not that I’d do it that way but it seems a plasuible way to do it).
What you describe is a good use case for a cooperative thread. Don’t use preemptive threads as if they were equivalent. I agree with @Greg_O, preemptive threads are for when you want to burn hot and get as much done as quickly as possible.
Fine with me. I’m often getting data from many sockets simultaneously and cooperative works just fine for that, for me, because the data rates don’t need to be high. I was just suggesting a scenario for whch someone might feel they want to use pre-emptive for and want much higher performance.
Not in my case. I am exploring preemptive threads instead of helper console apps (my custom worker replacement) which are mostly interfaces to measurement and signal generator devices, which means they sometimes are in idle state, waiting for the operator to choose another task. I wouldn’t want them to use 100% CPU on their core, but that was the same when I ran them as helpers (on macOS, not on Windows where a console main loop using DoEvents will not cause this extreme hunger).
In the console apps, I had to use DelayMBS inside the Mac version. In the preemptive thread version, a Sleep(100) if idle will bring consumption down to a few percent.
EDIT: I am unsure if threads still have an issue with sometimes ending before all UserUpdate dictionaries have been processed, so I use a counter in my thread subclass that will keep the thread running while having dictionaries in its queue. And that will not cause any sleep during this time. I am really pleased about the performance UserUpdates are showing in preemptive mode. It feels a lot snappier.
What you’re describing would be Suspending the thread, not Sleep. Sleep (the method) is used “to give other threads a chance to do some processing,” and as I said is better tuned for cooperative threads.
Now I’m going to repeat what Norman and I have been saying all along… Planning, coding, debugging and testing preemptive threads is hard, even for seasoned developers. I’m impressed that Xojo took the time to make their framework thread-safe and they’re doing an admirable job of trying to make preemptive threads easy for their audience, but there’s a limit to what they can do about race-conditions and all around crashing caused by developers writing their own non-thread-safe code. It’s going to take some time for Xojo to work out the remaining kinks and for people to get their sea legs in these uncharted waters.
Certainly in my app the method asking for data suspends the thread when data is needed and then the DataAvailable event resumes it. The method then does a ReadAll and passes data back to its caller. But I have a timer going around this so that the thread (which is expecting data and should be getting it) does not wait indefinitely.
All I was saying was that someone might code it to use a Sleep call to effect the timeout aspect instead of suspend and a timer.