From e2d16d50969d8894059636049a50c84a8913dd1d Mon Sep 17 00:00:00 2001 From: Anton Bannykh Date: Tue, 24 Dec 2019 22:39:22 +0300 Subject: [PATCH] FunctionInlining --- .../IrElementTransformerVoidWithContext.kt | 46 +++++++++++++++++++ .../common/lower/inline/FunctionInlining.kt | 18 +++++++- .../kotlin/ir/backend/js/JsLoweringPhases.kt | 7 +-- .../RenameAnonymousParametersLowering.kt | 4 +- 4 files changed, 66 insertions(+), 9 deletions(-) diff --git a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/IrElementTransformerVoidWithContext.kt b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/IrElementTransformerVoidWithContext.kt index ea51853a355..8996c8668ec 100644 --- a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/IrElementTransformerVoidWithContext.kt +++ b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/IrElementTransformerVoidWithContext.kt @@ -68,6 +68,20 @@ abstract class IrElementTransformerVoidWithContext : IrElementTransformerVoid() return result } + final override fun visitAnonymousInitializer(declaration: IrAnonymousInitializer): IrStatement { + scopeStack.push(createScope(declaration)) + val result = visitAnonymousInitializerNew(declaration) + scopeStack.pop() + return result + } + + final override fun visitValueParameter(declaration: IrValueParameter): IrStatement { + scopeStack.push(createScope(declaration)) + val result = visitValueParameterNew(declaration) + scopeStack.pop() + return result + } + final override fun visitScript(declaration: IrScript): IrStatement { scopeStack.push(createScope(declaration)) val result = visitScriptNew(declaration) @@ -80,6 +94,8 @@ abstract class IrElementTransformerVoidWithContext : IrElementTransformerVoid() protected val currentClass get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrClassSymbol } protected val currentFunction get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrFunctionSymbol } protected val currentProperty get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrPropertySymbol } + protected val currentAnonymousInitializer get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrAnonymousInitializer } + protected val currentValueParameter get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrValueParameter } protected val currentScope get() = scopeStack.peek() protected val parentScope get() = if (scopeStack.size < 2) null else scopeStack[scopeStack.size - 2] protected val allScopes get() = scopeStack @@ -109,6 +125,14 @@ abstract class IrElementTransformerVoidWithContext : IrElementTransformerVoid() return super.visitField(declaration) } + open fun visitAnonymousInitializerNew(declaration: IrAnonymousInitializer): IrStatement { + return super.visitAnonymousInitializer(declaration) + } + + open fun visitValueParameterNew(declaration: IrValueParameter): IrStatement { + return super.visitValueParameter(declaration) + } + open fun visitScriptNew(declaration: IrScript): IrStatement { return super.visitScript(declaration) } @@ -152,10 +176,24 @@ abstract class IrElementVisitorVoidWithContext : IrElementVisitorVoid { scopeStack.pop() } + final override fun visitAnonymousInitializer(declaration: IrAnonymousInitializer) { + scopeStack.push(createScope(declaration)) + visitAnonymousInitializerNew(declaration) + scopeStack.pop() + } + + final override fun visitValueParameter(declaration: IrValueParameter) { + scopeStack.push(createScope(declaration)) + visitValueParameterNew(declaration) + scopeStack.pop() + } + protected val currentFile get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrFileSymbol } protected val currentClass get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrClassSymbol } protected val currentFunction get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrFunctionSymbol } protected val currentProperty get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrPropertySymbol } + protected val currentAnonymousInitializer get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrAnonymousInitializer } + protected val currentValueParameter get() = scopeStack.lastOrNull { it.scope.scopeOwnerSymbol is IrValueParameter } protected val currentScope get() = scopeStack.peek() protected val parentScope get() = if (scopeStack.size < 2) null else scopeStack[scopeStack.size - 2] protected val allScopes get() = scopeStack @@ -183,4 +221,12 @@ abstract class IrElementVisitorVoidWithContext : IrElementVisitorVoid { open fun visitFieldNew(declaration: IrField) { super.visitField(declaration) } + + open fun visitAnonymousInitializerNew(declaration: IrAnonymousInitializer) { + super.visitAnonymousInitializer(declaration) + } + + open fun visitValueParameterNew(declaration: IrValueParameter) { + super.visitValueParameter(declaration) + } } \ No newline at end of file diff --git a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/inline/FunctionInlining.kt b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/inline/FunctionInlining.kt index 43f1a362686..952fb7cdff2 100644 --- a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/inline/FunctionInlining.kt +++ b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/inline/FunctionInlining.kt @@ -31,7 +31,18 @@ import org.jetbrains.kotlin.ir.visitors.IrElementVisitor import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid import org.jetbrains.kotlin.util.OperatorNameConventions -class FunctionInlining(val context: CommonBackendContext) : IrElementTransformerVoidWithContext() { +class FunctionInlining(val context: CommonBackendContext) : IrElementTransformerVoidWithContext(), BodyLoweringPass { + + private var containerScope: ScopeWithIr? = null + + override fun lower(irBody: IrBody, container: IrDeclaration) { + // TODO container: IrSymbolDeclaration + containerScope = createScope(container as IrSymbolOwner) + irBody.accept(this, null) + containerScope = null + + irBody.patchDeclarationParents(container as? IrDeclarationParent ?: container.parent) + } fun inline(irModule: IrModuleFragment) = irModule.accept(this, data = null) @@ -52,8 +63,11 @@ class FunctionInlining(val context: CommonBackendContext) : IrElementTransformer val actualCallee = getFunctionDeclaration(callee.symbol) val parent = allScopes.map { it.irElement }.filterIsInstance().lastOrNull() + ?: allScopes.map { it.irElement }.filterIsInstance().lastOrNull()?.parent + ?: containerScope?.irElement as? IrDeclarationParent + ?: (containerScope?.irElement as? IrDeclaration)?.parent - val inliner = Inliner(expression, actualCallee, currentScope!!, parent, context) + val inliner = Inliner(expression, actualCallee, currentScope ?: containerScope!!, parent, context) return inliner.inline() } diff --git a/compiler/ir/backend.js/src/org/jetbrains/kotlin/ir/backend/js/JsLoweringPhases.kt b/compiler/ir/backend.js/src/org/jetbrains/kotlin/ir/backend/js/JsLoweringPhases.kt index 58343580bc1..10afbca21ac 100644 --- a/compiler/ir/backend.js/src/org/jetbrains/kotlin/ir/backend/js/JsLoweringPhases.kt +++ b/compiler/ir/backend.js/src/org/jetbrains/kotlin/ir/backend/js/JsLoweringPhases.kt @@ -111,11 +111,8 @@ private val arrayConstructorPhase = makeJsModulePhase( description = "Transform `Array(size) { index -> value }` into a loop" ) -private val functionInliningPhase = makeCustomJsModulePhase( - { context, module -> - FunctionInlining(context).inline(module) - module.patchDeclarationParents() - }, +private val functionInliningPhase = makeJsModulePhase( + ::FunctionInlining, name = "FunctionInliningPhase", description = "Perform function inlining", prerequisite = setOf(expectDeclarationsRemovingPhase) diff --git a/compiler/ir/backend.jvm/src/org/jetbrains/kotlin/backend/jvm/lower/RenameAnonymousParametersLowering.kt b/compiler/ir/backend.jvm/src/org/jetbrains/kotlin/backend/jvm/lower/RenameAnonymousParametersLowering.kt index ad6426570b2..222690647e3 100644 --- a/compiler/ir/backend.jvm/src/org/jetbrains/kotlin/backend/jvm/lower/RenameAnonymousParametersLowering.kt +++ b/compiler/ir/backend.jvm/src/org/jetbrains/kotlin/backend/jvm/lower/RenameAnonymousParametersLowering.kt @@ -39,7 +39,7 @@ private class RenameAnonymousParametersLowering(val context: JvmBackendContext) override fun lower(irFile: IrFile) = irFile.transformChildrenVoid() - override fun visitValueParameter(declaration: IrValueParameter) = + override fun visitValueParameterNew(declaration: IrValueParameter) = declaration.computeNewParameterName()?.let { name -> val descriptor = if (declaration.descriptor is ReceiverParameterDescriptor) { WrappedReceiverParameterDescriptor(declaration.descriptor.annotations) @@ -63,7 +63,7 @@ private class RenameAnonymousParametersLowering(val context: JvmBackendContext) annotations += declaration.annotations oldParameterToNew[declaration] = this } - } ?: super.visitValueParameter(declaration) + } ?: super.visitValueParameterNew(declaration) override fun visitGetValue(expression: IrGetValue): IrExpression { val oldParameter = expression.symbol.owner