Remove redundant continuation classes and INNERCLASS nodes
#KT-31339 Fixed
This commit is contained in:
+7
-1
@@ -141,7 +141,7 @@ class AnonymousObjectTransformer(
|
||||
superClassName,
|
||||
allCapturedParamBuilder.listCaptured()
|
||||
)
|
||||
loop@for (next in methodsToTransform) {
|
||||
loop@ for (next in methodsToTransform) {
|
||||
val deferringVisitor =
|
||||
when {
|
||||
coroutineTransformer.shouldSkip(next) -> continue@loop
|
||||
@@ -162,9 +162,15 @@ class AnonymousObjectTransformer(
|
||||
}
|
||||
|
||||
deferringMethods.forEach { method ->
|
||||
val continuationToRemove = CoroutineTransformer.findFakeContinuationConstructorClassName(method.intermediate)
|
||||
val oldContinuationName = coroutineTransformer.oldContinuationFrom(method.intermediate)
|
||||
coroutineTransformer.replaceFakesWithReals(method.intermediate)
|
||||
removeFinallyMarkers(method.intermediate)
|
||||
method.visitEnd()
|
||||
if (continuationToRemove != null && coroutineTransformer.safeToRemoveContinuationClass(method.intermediate)) {
|
||||
transformationResult.addClassToRemove(continuationToRemove)
|
||||
innerClassNodes.removeIf { it.name == oldContinuationName }
|
||||
}
|
||||
}
|
||||
|
||||
SourceMapper.flushToClassBuilder(sourceMapper, classBuilder)
|
||||
|
||||
+7
@@ -215,6 +215,13 @@ class CoroutineTransformer(
|
||||
fun unregisterClassBuilder(continuationClassName: String) =
|
||||
(inliningContext as RegeneratedClassContext).continuationBuilders.remove(continuationClassName)
|
||||
|
||||
// If tail-call optimization took place, we do not need continuation class anymore, unless it is used by $$forInline method
|
||||
fun safeToRemoveContinuationClass(method: MethodNode): Boolean = !generateForInline && !isStateMachine(method)
|
||||
|
||||
fun oldContinuationFrom(method: MethodNode): String? =
|
||||
methods.find { it.name == method.name + FOR_INLINE_SUFFIX && it.desc == method.desc }
|
||||
?.let { findFakeContinuationConstructorClassName(it) }
|
||||
|
||||
companion object {
|
||||
fun findFakeContinuationConstructorClassName(node: MethodNode): String? {
|
||||
val marker = node.instructions.asSequence().firstOrNull(::isBeforeFakeContinuationConstructorCallMarker) ?: return null
|
||||
|
||||
Reference in New Issue
Block a user