Codereview

This commit is contained in:
Igor Yakovlev
2023-05-27 14:28:38 +02:00
committed by Space Team
parent c71a2c6dd3
commit 39c8d5759b
3 changed files with 63 additions and 50 deletions
@@ -186,6 +186,7 @@ internal class WasmUsefulDeclarationProcessor(
processIrFunction(irConstructor)
}
// Primitive constructors has no body, since that such constructors implicitly initialize all fields, so we have to preserve them
if (irConstructor.hasWasmPrimitiveConstructorAnnotation()) {
constructedClass.declarations.forEach { declaration ->
if (declaration is IrField) {
@@ -11,41 +11,32 @@ import org.jetbrains.kotlin.backend.common.lower.createIrBuilder
import org.jetbrains.kotlin.backend.wasm.WasmBackendContext
import org.jetbrains.kotlin.ir.builders.irBlock
import org.jetbrains.kotlin.ir.builders.irCall
import org.jetbrains.kotlin.ir.declarations.IrConstructor
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
import org.jetbrains.kotlin.ir.declarations.IrSymbolOwner
import org.jetbrains.kotlin.ir.expressions.IrBody
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.IrFunctionReference
import org.jetbrains.kotlin.ir.expressions.impl.IrFunctionReferenceImpl
import org.jetbrains.kotlin.ir.symbols.IrFunctionSymbol
import org.jetbrains.kotlin.ir.util.constructedClass
import org.jetbrains.kotlin.ir.visitors.IrElementTransformerVoid
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
class WasmArrayConstructorLowering(val context: WasmBackendContext) : BodyLoweringPass {
override fun lower(irBody: IrBody, container: IrDeclaration) {
irBody.transformChildrenVoid(ArrayConstructorTransformer(context, container as IrSymbolOwner))
irBody.transformChildrenVoid(WasmArrayConstructorTransformer(context, container as IrSymbolOwner))
}
}
private class ArrayConstructorTransformer(
private class WasmArrayConstructorTransformer(
val context: WasmBackendContext,
val container: IrSymbolOwner
) : IrElementTransformerVoidWithContext() {
// Array(size, init) -> create###Array(size, init)
companion object {
internal fun arrayInlineToSizeCreator(context: WasmBackendContext, irConstructor: IrConstructor): IrFunctionSymbol? =
when (irConstructor.valueParameters.size) {
2 -> context.wasmSymbols.primitiveTypeToCreateTypedArray[irConstructor.constructedClass.symbol]
else -> null
}
}
override fun visitConstructorCall(expression: IrConstructorCall): IrExpression {
val creator = arrayInlineToSizeCreator(context, expression.symbol.owner)
?: return super.visitConstructorCall(expression)
val target = expression.symbol.owner
// Array(size, init) -> create###Array(size, init)
val creator = when (target.valueParameters.size) {
2 -> context.wasmSymbols.primitiveTypeToCreateTypedArray[target.constructedClass.symbol]
else -> null
} ?: return super.visitConstructorCall(expression)
expression.transformChildrenVoid()
@@ -57,36 +48,4 @@ private class ArrayConstructorTransformer(
}
}
}
}
class WasmArrayConstructorReferenceLowering(val context: WasmBackendContext) : BodyLoweringPass {
override fun lower(irBody: IrBody, container: IrDeclaration) {
irBody.transformChildrenVoid(ArrayConstructorReferenceTransformer(context))
}
private class ArrayConstructorReferenceTransformer(val context: WasmBackendContext) : IrElementTransformerVoid() {
override fun visitFunctionReference(expression: IrFunctionReference): IrExpression {
expression.transformChildrenVoid()
val target = expression.symbol.owner
if (target !is IrConstructor) return expression
val creator = ArrayConstructorTransformer.arrayInlineToSizeCreator(context, target)
?: return super.visitFunctionReference(expression)
return IrFunctionReferenceImpl(
startOffset = expression.startOffset,
endOffset = expression.endOffset,
type = expression.type,
symbol = creator,
typeArgumentsCount = expression.typeArgumentsCount,
valueArgumentsCount = expression.valueArgumentsCount,
reflectionTarget = creator,
origin = expression.origin
).also { reference ->
repeat(expression.typeArgumentsCount) { reference.putTypeArgument(it, expression.getTypeArgument(it)) }
repeat(expression.valueArgumentsCount) { reference.putValueArgument(it, expression.getValueArgument(it)) }
}
}
}
}
@@ -0,0 +1,53 @@
/*
* Copyright 2010-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
* that can be found in the license/LICENSE.txt file.
*/
package org.jetbrains.kotlin.backend.wasm.lower
import org.jetbrains.kotlin.backend.common.BodyLoweringPass
import org.jetbrains.kotlin.backend.wasm.WasmBackendContext
import org.jetbrains.kotlin.ir.declarations.IrConstructor
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
import org.jetbrains.kotlin.ir.expressions.IrBody
import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.IrFunctionReference
import org.jetbrains.kotlin.ir.expressions.impl.IrFunctionReferenceImpl
import org.jetbrains.kotlin.ir.util.constructedClass
import org.jetbrains.kotlin.ir.visitors.IrElementTransformerVoid
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
class WasmArrayConstructorReferenceLowering(val context: WasmBackendContext) : BodyLoweringPass {
override fun lower(irBody: IrBody, container: IrDeclaration) {
irBody.transformChildrenVoid(WasmArrayConstructorReferenceTransformer(context))
}
}
private class WasmArrayConstructorReferenceTransformer(val context: WasmBackendContext) : IrElementTransformerVoid() {
override fun visitFunctionReference(expression: IrFunctionReference): IrExpression {
expression.transformChildrenVoid()
val target = expression.symbol.owner
if (target !is IrConstructor) return expression
// Array(size, init) -> create###Array(size, init)
val creator = when (target.valueParameters.size) {
2 -> context.wasmSymbols.primitiveTypeToCreateTypedArray[target.constructedClass.symbol]
else -> null
} ?: return super.visitFunctionReference(expression)
return IrFunctionReferenceImpl(
startOffset = expression.startOffset,
endOffset = expression.endOffset,
type = expression.type,
symbol = creator,
typeArgumentsCount = expression.typeArgumentsCount,
valueArgumentsCount = expression.valueArgumentsCount,
reflectionTarget = creator,
origin = expression.origin
).also { reference ->
repeat(expression.typeArgumentsCount) { reference.putTypeArgument(it, expression.getTypeArgument(it)) }
repeat(expression.valueArgumentsCount) { reference.putValueArgument(it, expression.getValueArgument(it)) }
}
}
}