On Sun, Mar 9, 2025, 09:05 Edmond Dantes <edmond...@gmail.com> wrote:
> When a *Fiber* from the *Scheduler* decides to create another *Fiber* and > then tries to call blocking functions inside it, control can no longer > return to the *Scheduler* from those functions. > > Of course, it would be possible to track the state and disable the > concurrency mode flag when the user manually creates a *Fiber*. But… this > wouldn't lead to anything good. Not only would it complicate the code, but > it would also result in a mess with different behavior inside and outside > of *Fiber*. > > Thank you for explaining the problem space. Now let's see what solutions we can find. First of all, I think it would be better for the language to assume the Scheduler is always running and not have to be manually started. An idea that I have for now: Have a different method `Fiber::suspendToScheduler(Resume $resume)` that would return the control to the Scheduler. And this one would be used by all internal functions that does blocking operations, and maybe also user land ones if they need to. Of course, the name can be better, like `Fiber::await`. Maybe that is what we need: to be able to return control both to the parent fiber for custom logic that might be needed, and to the Scheduler so that the language would be concurrent. As for userland event loops, like Revolt, I am not so sure they fit with the new language level async model. But I can see how they could implement a different Event loop that would run only one "loop", schedule a deffered callback and pass control to the Scheduler (that would return the control in the next iteration to perform one more loop, and so on. -- Alex >