You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I want to rewrite our current async stack to be easier to work with, because it currently involves some tedious syntax. I'd like to get some thoughts from the other developers before I plow ahead with a solution. Here's our options for alternatives (or at least, ones that I can think of):
Option 0: 'static futures paired with Loader<'gc> variants
This is the status quo.
Futures only store 'static data, as well as an Arc<Mutex<Player>> that can be locked to gain access to the player instance that spawned this task. 'gc data is referenced inside of a Loader<'gc>, and both it and any 'a' data is accessed by manually locking the player and triggering an update on it.
Pros:
Uses standard tools & code
Cons:
Syntax across yield points is incredibly verbose
References must be manually balanced between future, sync stack, and loader
Option 1: 'static futures via GcPins held by std future
GcPin would "pin" GC data, in the same way that Pin "pins" non-GC data. Pinned data in the GC heap would have the following properties:
It becomes a new GC root, and thus cannot be collected
Pinned data cannot be moved by the GC
GC pinning is not structural - contents of pinned data is free to be moved
Pinned data is 'static and can be mutated without a GC context
Pros:
GcPins can just move into an async block
Cons:
Requires extra reference counting in gc_arena to allow pins to outlive the arena safely
How do we keep people from pulling unpinned GcCells via a pinned one?
No solution for accessing 'a data without locking the player as in Option 0
Option 2: 'a + 'gc futures via special GcFuture trait
GcFuture would work identically to std::Future with an additional parameter on poll for the Ruffle update context. Ruffle would need to become an executor of such futures, providing adapters into std::Future so that they can be spawned by the web backend.
'a or 'gc data would not be able to be held across yield points, and we would be limited to combinator syntax.
Pros:
Does not alter the memory safety or lifetimes we typically work with
Allows access to 'a data
Cons:
No solution for referencing data across yield points
Requires second layer of executors
Combinator syntax is unwieldy
Option 3: GcPin + GcFuture + macro magic
'gc data is pinned and referenced using the GC pinning mechanism mentioned above. 'a data is accessed through an update context provided at poll time via an altered future trait. We then reimplement the entirety of async/await syntax via new procedural macros.
Pros:
'gc data can be referenced and held at any time
'a data can be accessed easier
Syntax identical to existing async syntax
Cons:
Requires a lot of redevelopment of existing Rust features
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
-
I want to rewrite our current async stack to be easier to work with, because it currently involves some tedious syntax. I'd like to get some thoughts from the other developers before I plow ahead with a solution. Here's our options for alternatives (or at least, ones that I can think of):
Option 0:
'static
futures paired withLoader<'gc>
variantsThis is the status quo.
Futures only store
'static
data, as well as anArc<Mutex<Player>>
that can be locked to gain access to the player instance that spawned this task.'gc
data is referenced inside of aLoader<'gc>
, and both it and any'a'
data is accessed by manually locking the player and triggering an update on it.Pros:
Cons:
Option 1:
'static
futures viaGcPin
s held by std futureGcPin
would "pin" GC data, in the same way thatPin
"pins" non-GC data. Pinned data in the GC heap would have the following properties:'static
and can be mutated without a GC contextPros:
GcPin
s can just move into anasync
blockCons:
gc_arena
to allow pins to outlive the arena safelyGcCell
s via a pinned one?'a
data without locking the player as in Option 0Option 2:
'a + 'gc
futures via special GcFuture traitGcFuture
would work identically tostd::Future
with an additional parameter onpoll
for the Ruffle update context. Ruffle would need to become an executor of such futures, providing adapters intostd::Future
so that they can be spawned by the web backend.'a
or'gc
data would not be able to be held across yield points, and we would be limited to combinator syntax.Pros:
'a
dataCons:
Option 3: GcPin + GcFuture + macro magic
'gc
data is pinned and referenced using the GC pinning mechanism mentioned above.'a
data is accessed through an update context provided at poll time via an altered future trait. We then reimplement the entirety ofasync
/await
syntax via new procedural macros.Pros:
'gc
data can be referenced and held at any time'a
data can be accessed easierasync
syntaxCons:
Beta Was this translation helpful? Give feedback.
All reactions