-
Notifications
You must be signed in to change notification settings - Fork 32
Consider adding async support #51
Comments
This is a deep topic. I've considered it but so far have not been convinced we should do this. You might be able to change my mind. First, in general you don't want to run anything on the UI thread other than things that are required to process requests from the platform to the app (which are generally synchronous) or submit work to the platform. I believe everything else (including things like network and CPU-heavy async tasks) should be run in a reactor such as that provided by Tokio's runtime. Again, I am open to arguments otherwise. Second, on Windows MsgWaitForMultipleObjects and friends have a fatal flaw, they don't run when resizing the window or in a modal dialog. This is why the run loop is very vanilla and integration with the Rust async world is by injecting user messages. Third, one of the things that might change my mind is the way wgpu implements async. I'm not sure it's in it final form, it seems like there are a number of points where you explicitly poll (for example, to make async map of buffers actually happen). It would be nice to have this become plain Rust async, and expect the runtime to make progress as needed, whether that's on the UI thread or in another runtime. I don't understand all the issues around this (especially the plan for wgpu's end state) but would love to see a detailed design. So I consider this a conversation. Thanks for engaging it. |
Depending on the platform, these synchronous requests may also include some or all accessibility API calls from the platform into the app. On macOS, all such calls run on the UI thread. On Windows, the |
Thank you for the response!
The first thing that comes to mind is what if there isn't any thread other than the UI thread?. The web usecase comes to mind here, since the concurrency story for the web (web workers) is poor at the time of writing. There are also cases where there is an upper limit to the number of threads you can run at once; we've had to adapt to this in the past. Sometimes there isn't much of an option aside from running on the main thread.
Wait, really? I mean, it's possible to just post messages to the thread queue to wake it up anyhow, so this shouldn't be much of an issue.
I'm not entirely familiar with
|
Another idea is that sometimes you have something you want to run on the UI thread. I'm designing a GUI framework where a thread local executor would run on the UI thread and manage widgets.
This scenario can be avoided by using yield points in the |
The web is likely a special case, and deserves careful consideration, especially in conjunction with using wgpu. I know Dioxus has done some stuff with local executor, but haven't tracked down the detail. On web, wgpu ultimately drills down to JS I am unexcited about yield points and consider the need for them a likely sign of an architectural flaw. Again I could have my opinion changed, but it would take persuasive evidence. So, bottom line, I would love to see a design document that analyzed the requirements in different scenarios including better integration with wgpu and the web but would not be inclined to merge a PR without some kind of justification along those lines. Also, this might be a good topic to discuss at office hours. Next one is 2023-01-03. |
I mean, yes, it's a flaw in Rust's async ecosystem as a whole. In my opinion, the potential benefits (e.g. being able to run async tasks using the UI thread as a root thread) outweigh those costs.
Sounds good, I'll see if I can prepare something before then. |
Since the last update, I've created the Still, I think it should be considered whether or not |
Right now, the
Application
structure exposes arun()
method that blocks indefinitely until the application finishes. It would be nice if there were a way to run aFuture
inside of this blocking loop, so that it would be possible to multiplex an asynchronous task with the GUI on one thread.This would require changing the backend such that it can be woken up via a
Waker
. While you could just create aWaker
to send an event to the loop, there is a more elegant way of doing this that can circumvent the normal event loops, based on the platform.MsgWaitForMultipleObjects
.epoll
.kqueue
.I'm willing to implement this behavior into the current system.
The text was updated successfully, but these errors were encountered: