aboutsummaryrefslogtreecommitdiffstats
path: root/kotlinx-coroutines-core/jvm
diff options
context:
space:
mode:
authorVsevolod Tolstopyatov <qwwdfsad@gmail.com>2020-10-20 02:40:38 -0700
committerGitHub <noreply@github.com>2020-10-20 12:40:38 +0300
commit9587590fc003bcd8271a5388075e116c61fb26f5 (patch)
tree923988df8a59adedd763fe254a685b0394159418 /kotlinx-coroutines-core/jvm
parent9eaa9c647c6b10911b34ab2cd10a9aa4bc08b713 (diff)
downloadplatform_external_kotlinx.coroutines-9587590fc003bcd8271a5388075e116c61fb26f5.tar.gz
platform_external_kotlinx.coroutines-9587590fc003bcd8271a5388075e116c61fb26f5.tar.bz2
platform_external_kotlinx.coroutines-9587590fc003bcd8271a5388075e116c61fb26f5.zip
Combine and zip rework (#2308)
* Rework Flow.zip operator: improve its performance by 40%, collect one of the upstreams in the same coroutine as emitter * Rework Flow.combine * Get rid of two code paths * Get rid of accidental O(N^2) where N is the number of flows that caused #2296 * Get rid of select that hits performance hard, improving performance by 50% in the pessimistic case * Get rid of crossinlines in API and implementation to fix Android issues * Make combine fairer and its results less surprising in sequential scenarios * Improve stacktrace recovery and stackwalking for SafeCollector, flowOn and zip operators * Update JMH Fixes #1743 Fixes #1683 Fixes #2296
Diffstat (limited to 'kotlinx-coroutines-core/jvm')
-rw-r--r--kotlinx-coroutines-core/jvm/src/flow/internal/SafeCollector.kt7
-rw-r--r--kotlinx-coroutines-core/jvm/src/internal/LocalAtomics.kt8
2 files changed, 14 insertions, 1 deletions
diff --git a/kotlinx-coroutines-core/jvm/src/flow/internal/SafeCollector.kt b/kotlinx-coroutines-core/jvm/src/flow/internal/SafeCollector.kt
index a8e04f0f..b275a481 100644
--- a/kotlinx-coroutines-core/jvm/src/flow/internal/SafeCollector.kt
+++ b/kotlinx-coroutines-core/jvm/src/flow/internal/SafeCollector.kt
@@ -21,7 +21,11 @@ private val emitFun =
internal actual class SafeCollector<T> actual constructor(
@JvmField internal actual val collector: FlowCollector<T>,
@JvmField internal actual val collectContext: CoroutineContext
-) : FlowCollector<T>, ContinuationImpl(NoOpContinuation, EmptyCoroutineContext) {
+) : FlowCollector<T>, ContinuationImpl(NoOpContinuation, EmptyCoroutineContext), CoroutineStackFrame {
+
+ override val callerFrame: CoroutineStackFrame? get() = completion as? CoroutineStackFrame
+
+ override fun getStackTraceElement(): StackTraceElement? = null
@JvmField // Note, it is non-capturing lambda, so no extra allocation during init of SafeCollector
internal actual val collectContextSize = collectContext.fold(0) { count, _ -> count + 1 }
@@ -51,6 +55,7 @@ internal actual class SafeCollector<T> actual constructor(
*/
override suspend fun emit(value: T) {
return suspendCoroutineUninterceptedOrReturn sc@{ uCont ->
+ // Update information about caller for stackwalking
try {
emit(uCont, value)
} catch (e: Throwable) {
diff --git a/kotlinx-coroutines-core/jvm/src/internal/LocalAtomics.kt b/kotlinx-coroutines-core/jvm/src/internal/LocalAtomics.kt
new file mode 100644
index 00000000..f508749e
--- /dev/null
+++ b/kotlinx-coroutines-core/jvm/src/internal/LocalAtomics.kt
@@ -0,0 +1,8 @@
+/*
+ * Copyright 2016-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.coroutines.internal
+
+@Suppress("ACTUAL_WITHOUT_EXPECT")
+internal actual typealias LocalAtomicInt = java.util.concurrent.atomic.AtomicInteger