-
-
Notifications
You must be signed in to change notification settings - Fork 676
[work in progress] Coroutines the Third #12168
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: development
Are you sure you want to change the base?
Conversation
I noticed that we were stuck on an outdated hxcpp branch. After updating this we now have green CI for cpp, which is a good baseline. As the next step I'd like to get the JVM tests green. And afterwards we'll have to figure out how to make all this work on non-sys targets, because our coroutine execution currently relies on |
I changed this for reasons I forget from the previous branch
This reverts commit 24cba39.
…12169) * Fix HaxeFoundation#12149 * Add unit test
…undation#12173) * [generics] Ensure type substitution happens for closures too. * Add tests for issue 12171 and PR 11784.
closes #16
Update:
Maybe @yuxiaomao could take a look at that some time. We also don't seem to run these tests on CI yet because HL is green. |
# Conflicts: # src/context/common.ml
* add ILocalContext * use for awaitingChildContinuation
Millisecond Schedulers
…y if Running closes #124
* add Key.fromClass to get rid of explicit .key expressions * we actually don't care about the class itself at all
* split up hx_tmp for result/error * try to get error wrapping under control * add surprisingly simple tests
* add IScheduleObject * use for continuations * use for async * also use for CancellationContinuation * implement suspendCancellable directly closes #138 * avoid some double-scheduling * use AtomicInt instead of simon-mutexes for RacingContinuation too * factor out delayImpl so both delay and yield can call it This avoids the double suspension call from yield to delay, which I noticed in the yield benchmarks.
# Conflicts: # src/typing/typerEntry.ml
* change isCancellationRequested to cancellationException * bring back isCancellationRequested as a convenience method
* start moving some types to continuation api * more * more * don't load exception twice * be lazier * be even lazier * fix * ignore that
* support element deletion in Page * get cpp green even though this seems weird * add some more tests * fix isEmpty but find more problems * fix isEmpty resetting * don't blit with length 0 * use ArraySort for stability * change API to something that might actually be sound * test middle page deletion * move tests to TestPagedDeque
Third times the charm, right?
This is an evolution of #11554, the core state machine transformation has remained pretty much untouched from that branch, but the surrounding scaffolding code has been changed to more closely align with kotlin's coroutine implementation. This should hopefully address the issues surrounding continuation, scheduling, and a few others which were discovered in the other PR.
Changes
Coroutine functions are now transformed to accept a
Continuation<Any>
argument, returnAny
, and contain the state machine transformation. The continuation argument either holds the state of a paused execution of the coroutine function, or what will be invoked once the coroutine completes. The any return will either be the result of the coroutines execution, or a special token indicating that it's execution has been suspended.In addition each coroutine function has a class generated for it. This class implements
IContinuation<Any>
and stores data related to the execution of a coroutine, this includes, the current state, the result or error, variables accessed across states, and a reference to the continuation which will be invoked once this coroutine completes, essentially creating a chain. The continuation interface contains aresume
function which when called resumes execution of the coroutine and is responsible to scheduling the execution of the coroutine into an appropriate thread.Coroutines can be started with the blocking function
Coroutine.run
, which blocks until a coroutine completes. Internally it has its own event loop which all coroutine continuations are scheduled onto.A quick hello world example is provided below. It should work on all sys targets, but some targets might need their generators updated.
Resources
I'm putting a few links below, specifically related to kotlin's coroutines, which helped the puzzle come together a bit for me.
https://kt.academy/article/cc-under-the-hood
That is a good overview of the underlying machinery of kotlin's coroutines. Jumping straight into decompiled kotlin is very daunting as there are many, many layers of abstraction due to optimisations, features, etc. That article cuts through all of it and gets right to the core of whats happening. I pretty much copied that for this coroutine attempt.
https://www.droidcon.com/2022/09/22/design-of-kotlin-coroutines/
This then goes one layer deper, it covers a lot of those layers you see in kotlin's implementation and explains what they're there for.
https://github.com/JetBrains/kotlin/blob/master/compiler/backend/src/org/jetbrains/kotlin/codegen/coroutines/coroutines-codegen.md
Finally, the mega document. Goes in depth into the jvm codegen of kotlin's coroutines.