Do not spill dispatch receiver of suspend functions if it is not used

#KT-20571
This commit is contained in:
Ilmir Usmanov
2020-07-31 14:10:48 +02:00
parent 5db7957230
commit 405c9743ef
12 changed files with 8 additions and 48 deletions
@@ -20,6 +20,7 @@ import org.jetbrains.org.objectweb.asm.Opcodes
import org.jetbrains.org.objectweb.asm.Type
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter
import org.jetbrains.org.objectweb.asm.tree.*
import org.jetbrains.org.objectweb.asm.tree.analysis.BasicValue
import kotlin.math.max
private const val COROUTINES_DEBUG_METADATA_VERSION = 1
@@ -610,14 +611,13 @@ class CoroutineTransformerMethodVisitor(
// k - continuation
// k + 1 - data
// k + 2 - exception
val variablesToSpill =
(0 until localsCount)
.filterNot { it in setOf(continuationIndex, dataIndex, exceptionIndex) }
.map { Pair(it, frame.getLocal(it)) }
.filter { (index, value) ->
(index == 0 && needDispatchReceiver && isForNamedFunction) ||
(value.type != null && livenessFrame.isAlive(index))
}
val variablesToSpill = arrayListOf<Pair<Int, BasicValue>>()
for (slot in 0 until localsCount) {
if (slot == continuationIndex || slot == dataIndex || slot == exceptionIndex) continue
val value = frame.getLocal(slot)
if (value.type == null || !livenessFrame.isAlive(slot)) continue
variablesToSpill += slot to value
}
for ((index, basicValue) in variablesToSpill) {
if (basicValue == StrictBasicValue.NULL_VALUE) {