-
Notifications
You must be signed in to change notification settings - Fork 34
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
Fix ConflatedBroadcastChannelLincheckTest in kotlinx.coroutines #273
Conversation
7ec930a
to
b17c09b
Compare
…s that should be loaded by the system class loader
71eb2f1
to
08f9877
Compare
setResult(iThread, Done) | ||
} | ||
} | ||
|
||
fun waitUntilAllThreadsFinishTheCurrentTasks() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe just awaitAllThreads
or awaitAllTasks
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, we do not need this function at all -- the code always waits for all tasks to be completed. I've checked that we never call Thread.yield()
in the implementation.
@@ -283,8 +284,11 @@ abstract class ManagedStrategy( | |||
* @param codeLocation the byte-code location identifier of the point in code. | |||
*/ | |||
private fun newSwitchPoint(iThread: Int, codeLocation: Int, tracePoint: TracePoint?) { | |||
if (!isTestThread(iThread)) return // can switch only test threads | |||
if (!isTestThread(iThread)) return |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Isn't this check is duplicated by the inIgnoredSection(iThread)
check on the next line?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's fix that under #276 -- there are many such cases.
This issue was quite a journey. Thanks to @eupp for the help with the investigation and the review! |
Fixes failing ConflatedBroadcastChannelLincheckTest; see the build below
https://teamcity.jetbrains.com/buildConfiguration/KotlinTools_KotlinxLincheck_IntegrationTestWithKotlinxCoroutinesDevelopLinuxOnJava17/4485333?hideTestsFromDependencies=false&hideProblemsFromDependencies=false&expandBuildDeploymentsSection=false&expandBuildTestsSection=true&expandBuildProblemsSection=true
Investigation
There were two issues.
Solution: ignore the corresponding classes in
doNotTransform(..)
.suddenInvocationResult
inManagedStrategy
was set to a non-null value. After that, all furtherinIgnoredSection(..)
calls returnedtrue
(it checked forsuddenInvocationResult
being non-null, I don't know why), making it impossible for other threads to notice the spin-lock detection and also finish. This resulted in an infinite spin-lock and deadlock detection. However, the latter was ignored, assuddenInvocationResult
was non-null. Notably, the "hanging" thread was still callingnewSwitchPoint(..)
periodically (there was a veeery long spin-lock). Then, after starting the next interleaving, thesuddenInvocationResult
field was reset tonull
, and the hanging threads, that were callingnewSwitchPoint(..)
periodically, published events related to the previous interleaving. This caused non-deterministic behavior in the model checker.Solution: check whether
suddenInvocationResult
is non-null in the beginning of the analysis, removing the corresponding check frominIgnoredSection(..)
.