-
In our usage scenario (a game framework), we have the functionality for a user to change the game's execution mode from single-thread to multi-threaded at runtime. This stops all running threads (managed by us) and reallocates how the game's subsystems are run. An example of what happens is: Start in multi-threaded:Input (managed thread 0, startup thread / window loop) runFrames()
{
while(true) { runInputFrame(); }
} Draw (managed thread 1) runFrames()
{
while(true) { runDrawFrame(); }
} Update (managed thread 2, realm "main" context) runFrames()
{
while(true) {
realm.Refresh();
runUpdateFrame();
}
} Audio (managed thread 3) runFrames()
{
while(true) { runAudioFrame(); }
} User switches to single-thread:Input (managed thread 0, startup thread / window loop) runFrames()
{
while(true) {
runInputFrame();
// input thread additionally gains responsibility for other task areas
realm.Refresh(); // exception due to managed thread changing.
runUpdateFrame();
runDrawFrame();
runAudioFrame();
}
} Each time the mode switches, the update thread exposed to the game code changes its underlying managed thread ID, which causes realm to fall over due to the check: Note that the same applies switching in the other direction, as we spin up new threads each time and the OS generally doesn't give us matching thread IDs. I'm currently working on a local solution which pins the managed thread for the update thread (where we intend to keep realm), with a proof-of-concept implementation confirmed to fix the realm-side issue but also reducing the flexibility at our disposal (we can no longer run the update thread on the OS entry thread, which may be desirable on some platforms to get more correct window redraw timings) From the linked realm code, there doesn't look like any room for play at our end, and I don't necessarily expect realm to be exposing this kind of low level functionality - our use case is likely a very edge case in that most applications aren't managing threads at the level of complexity we are - but I thought I would open this issue to document what we are working through. |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 9 replies
-
The way I see it, you have two options:
If you're going with option 2., you may also want to considering installing a synchronization context only on the main thread in single-thread mode and then reinstalling it on the |
Beta Was this translation helpful? Give feedback.
The way I see it, you have two options:
IsOnContext
check. There are two considerations when rolling that out:2.1. It may affect where your async continuations are dispatched. You will probably want to do something clever and capture the original thread to make sure you dispatch continuations from the
draw
thread back to thedraw
thread.2.2. You need to ensure no paralle…