Fix initializer lowering crash during deep copy

This commit is contained in:
Roman Artemev
2018-04-29 03:58:42 +03:00
parent 449943da01
commit 131fb642aa
3 changed files with 14 additions and 10 deletions
@@ -93,7 +93,7 @@ class InitializersLowering(
irClass.transformChildrenVoid(object : IrElementTransformerVoid() { irClass.transformChildrenVoid(object : IrElementTransformerVoid() {
override fun visitInstanceInitializerCall(expression: IrInstanceInitializerCall): IrExpression { override fun visitInstanceInitializerCall(expression: IrInstanceInitializerCall): IrExpression {
return IrBlockImpl(irClass.startOffset, irClass.endOffset, context.builtIns.unitType, null, return IrBlockImpl(irClass.startOffset, irClass.endOffset, context.builtIns.unitType, null,
instanceInitializerStatements.map { it.copy() }) instanceInitializerStatements.map { it.copy(irClass) })
} }
}) })
} }
@@ -114,7 +114,7 @@ class InitializersLowering(
irClass.startOffset, irClass.endOffset, declarationOrigin, irClass.startOffset, irClass.endOffset, declarationOrigin,
staticInitializerDescriptor, staticInitializerDescriptor,
IrBlockBodyImpl(irClass.startOffset, irClass.endOffset, IrBlockBodyImpl(irClass.startOffset, irClass.endOffset,
staticInitializerStatements.map { it.copy() }) staticInitializerStatements.map { it.copy(irClass) })
) )
) )
} }
@@ -123,7 +123,7 @@ class InitializersLowering(
companion object { companion object {
val clinitName = Name.special("<clinit>") val clinitName = Name.special("<clinit>")
fun IrStatement.copy() = deepCopyWithSymbols() fun IrStatement.copy(containingDeclaration: IrClass) = deepCopyWithSymbols(containingDeclaration)
fun IrExpression.copy() = deepCopyWithSymbols() fun IrExpression.copy(containingDeclaration: IrClass) = deepCopyWithSymbols(containingDeclaration)
} }
} }
@@ -31,10 +31,10 @@ import org.jetbrains.kotlin.ir.visitors.IrElementTransformerVoid
import org.jetbrains.kotlin.ir.visitors.acceptVoid import org.jetbrains.kotlin.ir.visitors.acceptVoid
import java.util.* import java.util.*
inline fun <reified T : IrElement> T.deepCopyWithSymbols(): T { inline fun <reified T : IrElement> T.deepCopyWithSymbols(initialParent: IrDeclarationParent? = null): T {
val remapper = DeepCopySymbolsRemapper() val remapper = DeepCopySymbolsRemapper()
acceptVoid(remapper) acceptVoid(remapper)
return transform(DeepCopyIrTreeWithSymbols(remapper), null).patchDeclarationParents() as T return transform(DeepCopyIrTreeWithSymbols(remapper), null).patchDeclarationParents(initialParent) as T
} }
@@ -9,18 +9,22 @@ import org.jetbrains.kotlin.ir.IrElement
import org.jetbrains.kotlin.ir.declarations.IrDeclaration import org.jetbrains.kotlin.ir.declarations.IrDeclaration
import org.jetbrains.kotlin.ir.declarations.IrDeclarationParent import org.jetbrains.kotlin.ir.declarations.IrDeclarationParent
import org.jetbrains.kotlin.ir.declarations.IrPackageFragment import org.jetbrains.kotlin.ir.declarations.IrPackageFragment
import org.jetbrains.kotlin.ir.declarations.impl.IrDeclarationBase
import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
import org.jetbrains.kotlin.ir.visitors.acceptVoid import org.jetbrains.kotlin.ir.visitors.acceptVoid
import java.util.* import java.util.*
fun <T : IrElement> T.patchDeclarationParents() = fun <T : IrElement> T.patchDeclarationParents(initialParent: IrDeclarationParent? = null) =
apply { apply {
acceptVoid(PatchDeclarationParentsVisitor()) val visitor = initialParent?.let { PatchDeclarationParentsVisitor(it) } ?: PatchDeclarationParentsVisitor()
acceptVoid(visitor)
} }
class PatchDeclarationParentsVisitor : IrElementVisitorVoid { class PatchDeclarationParentsVisitor() : IrElementVisitorVoid {
constructor(containingDeclaration: IrDeclarationParent) : this() {
declarationParentsStack.push(containingDeclaration)
}
private val declarationParentsStack = ArrayDeque<IrDeclarationParent>() private val declarationParentsStack = ArrayDeque<IrDeclarationParent>()