kotlinx-lincheck
kotlinx-lincheck copied to clipboard
Support ThreadLocal variables
The following test succeeds if we get the "threadLocal" from the concurrenthashmap (keyed by thread id), but fails if we get it from actually thread local.
class LincheckTest {
val threadLocalCounters = ConcurrentHashMap<Long, AtomicInteger>()
val counter = AtomicInteger(0)
@Test
fun modelCheckingTest(): Unit = ModelCheckingOptions()
.iterations(0) // Change to 300 for exhaustive testing
.addCustomScenario {
parallel {
thread {
actor(::iinc)
actor(::iinc)
}
thread {
actor(::gget)
actor(::gget)
}
thread {
actor(::gget)
actor(::gget)
}
}
}
.invocationsPerIteration(5_000)
.hangingDetectionThreshold(100)
.logLevel(LoggingLevel.INFO)
.check(this::class.java)
@Operation
fun iinc(): Int {
val add = getLocalCounter().getAndIncrement()
return counter.addAndGet(add)
}
@Operation
fun gget() = counter.get()
// This one works
// private fun getLocalCounter() = threadLocalCounters.computeIfAbsent(Thread.currentThread().id) { AtomicInteger(1) }
// This one doesnt
private fun getLocalCounter() = localCounter.get()
}
private val localCounter: ThreadLocal<AtomicInteger> = ThreadLocal.withInitial { AtomicInteger(1) }