@@ -7,6 +7,7 @@ package kotlinx.coroutines.debug.internal
7
7
import kotlinx.atomicfu.*
8
8
import kotlinx.coroutines.*
9
9
import kotlinx.coroutines.debug.*
10
+ import kotlinx.coroutines.internal.*
10
11
import kotlinx.coroutines.internal.ScopeCoroutine
11
12
import java.io.*
12
13
import java.lang.StackTraceElement
@@ -17,10 +18,10 @@ import kotlin.concurrent.*
17
18
import kotlin.coroutines.*
18
19
import kotlin.coroutines.jvm.internal.CoroutineStackFrame
19
20
import kotlin.synchronized
20
- import _COROUTINE.ArtificialStackFrames
21
+ import kotlinx.coroutines.internal.artificialFrame as createArtificialFrame // IDEA bug workaround
21
22
22
23
internal object DebugProbesImpl {
23
- private val ARTIFICIAL_FRAME = ArtificialStackFrames ().coroutineCreation()
24
+ private const val ARTIFICIAL_FRAME_MESSAGE = " Coroutine creation stacktrace "
24
25
private val dateFormat = SimpleDateFormat (" yyyy/MM/dd HH:mm:ss" )
25
26
26
27
private var weakRefCleanerThread: Thread ? = null
@@ -218,7 +219,7 @@ internal object DebugProbesImpl {
218
219
info.state
219
220
out .print (" \n\n Coroutine ${owner.delegate} , state: $state " )
220
221
if (observedStackTrace.isEmpty()) {
221
- out .print (" \n\t at $ARTIFICIAL_FRAME " )
222
+ out .print (" \n\t at ${createArtificialFrame( ARTIFICIAL_FRAME_MESSAGE )} " )
222
223
printStackTrace(out , info.creationStackTrace)
223
224
} else {
224
225
printStackTrace(out , enhancedStackTrace)
@@ -420,17 +421,15 @@ internal object DebugProbesImpl {
420
421
return createOwner(completion, frame)
421
422
}
422
423
423
- private fun List<StackTraceElement>.toStackTraceFrame (): StackTraceFrame =
424
- StackTraceFrame (
425
- foldRight<StackTraceElement , StackTraceFrame ?>(null ) { frame, acc ->
426
- StackTraceFrame (acc, frame)
427
- }, ARTIFICIAL_FRAME
428
- )
424
+ private fun List<StackTraceElement>.toStackTraceFrame (): StackTraceFrame ? =
425
+ foldRight<StackTraceElement , StackTraceFrame ?>(null ) { frame, acc ->
426
+ StackTraceFrame (acc, frame)
427
+ }
429
428
430
429
private fun <T > createOwner (completion : Continuation <T >, frame : StackTraceFrame ? ): Continuation <T > {
431
430
if (! isInstalled) return completion
432
431
val info = DebugCoroutineInfoImpl (completion.context, frame, sequenceNumber.incrementAndGet())
433
- val owner = CoroutineOwner (completion, info)
432
+ val owner = CoroutineOwner (completion, info, frame )
434
433
capturedCoroutinesMap[owner] = true
435
434
if (! isInstalled) capturedCoroutinesMap.clear()
436
435
return owner
@@ -453,9 +452,9 @@ internal object DebugProbesImpl {
453
452
*/
454
453
private class CoroutineOwner <T >(
455
454
@JvmField val delegate : Continuation <T >,
456
- @JvmField val info : DebugCoroutineInfoImpl
455
+ @JvmField val info : DebugCoroutineInfoImpl ,
456
+ private val frame : CoroutineStackFrame ?
457
457
) : Continuation<T> by delegate, CoroutineStackFrame {
458
- private val frame get() = info.creationStackBottom
459
458
460
459
override val callerFrame: CoroutineStackFrame ?
461
460
get() = frame?.callerFrame
@@ -473,10 +472,12 @@ internal object DebugProbesImpl {
473
472
private fun <T : Throwable > sanitizeStackTrace (throwable : T ): List <StackTraceElement > {
474
473
val stackTrace = throwable.stackTrace
475
474
val size = stackTrace.size
476
- val traceStart = 1 + stackTrace.indexOfLast { it.className == " kotlin.coroutines.jvm.internal.DebugProbesKt" }
475
+ val probeIndex = stackTrace.indexOfLast { it.className == " kotlin.coroutines.jvm.internal.DebugProbesKt" }
477
476
478
477
if (! sanitizeStackTraces) {
479
- return List (size - traceStart) { stackTrace[it + traceStart] }
478
+ return List (size - probeIndex) {
479
+ if (it == 0 ) createArtificialFrame(ARTIFICIAL_FRAME_MESSAGE ) else stackTrace[it + probeIndex]
480
+ }
480
481
}
481
482
482
483
/*
@@ -487,8 +488,9 @@ internal object DebugProbesImpl {
487
488
* If an interval of internal methods ends in a synthetic method, the outermost non-synthetic method in that
488
489
* interval will also be included.
489
490
*/
490
- val result = ArrayList <StackTraceElement >(size - traceStart + 1 )
491
- var i = traceStart
491
+ val result = ArrayList <StackTraceElement >(size - probeIndex + 1 )
492
+ result + = createArtificialFrame(ARTIFICIAL_FRAME_MESSAGE )
493
+ var i = probeIndex + 1
492
494
while (i < size) {
493
495
if (stackTrace[i].isInternalMethod) {
494
496
result + = stackTrace[i] // we include the boundary of the span in any case
0 commit comments