Remove descriptors from EnumClassLowering

This commit is contained in:
Georgy Bronnikov
2018-11-27 20:57:06 +03:00
parent 8f6d73fd32
commit 5f4b8dd0aa
2 changed files with 125 additions and 103 deletions
@@ -8,29 +8,31 @@ package org.jetbrains.kotlin.backend.jvm.lower
import gnu.trove.TObjectIntHashMap import gnu.trove.TObjectIntHashMap
import org.jetbrains.kotlin.backend.common.ClassLoweringPass import org.jetbrains.kotlin.backend.common.ClassLoweringPass
import org.jetbrains.kotlin.backend.common.phaser.makeIrFilePhase import org.jetbrains.kotlin.backend.common.phaser.makeIrFilePhase
import org.jetbrains.kotlin.backend.common.descriptors.WrappedClassConstructorDescriptor
import org.jetbrains.kotlin.backend.common.descriptors.WrappedFieldDescriptor
import org.jetbrains.kotlin.backend.common.descriptors.WrappedValueParameterDescriptor
import org.jetbrains.kotlin.backend.common.ir.copyTo
import org.jetbrains.kotlin.backend.jvm.JvmBackendContext import org.jetbrains.kotlin.backend.jvm.JvmBackendContext
import org.jetbrains.kotlin.backend.jvm.descriptors.JvmPropertyDescriptorImpl
import org.jetbrains.kotlin.backend.jvm.descriptors.createValueParameter
import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.ClassConstructorDescriptorImpl
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
import org.jetbrains.kotlin.ir.IrStatement import org.jetbrains.kotlin.ir.IrStatement
import org.jetbrains.kotlin.ir.UNDEFINED_OFFSET import org.jetbrains.kotlin.ir.UNDEFINED_OFFSET
import org.jetbrains.kotlin.ir.declarations.* import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.declarations.impl.IrConstructorImpl import org.jetbrains.kotlin.ir.declarations.impl.IrConstructorImpl
import org.jetbrains.kotlin.ir.declarations.impl.IrFieldImpl import org.jetbrains.kotlin.ir.declarations.impl.IrFieldImpl
import org.jetbrains.kotlin.ir.declarations.impl.IrValueParameterImpl
import org.jetbrains.kotlin.ir.expressions.* import org.jetbrains.kotlin.ir.expressions.*
import org.jetbrains.kotlin.ir.expressions.impl.* import org.jetbrains.kotlin.ir.expressions.impl.*
import org.jetbrains.kotlin.ir.types.toIrType import org.jetbrains.kotlin.ir.symbols.IrConstructorSymbol
import org.jetbrains.kotlin.ir.types.toKotlinType import org.jetbrains.kotlin.ir.symbols.IrValueParameterSymbol
import org.jetbrains.kotlin.ir.symbols.impl.IrConstructorSymbolImpl
import org.jetbrains.kotlin.ir.symbols.impl.IrFieldSymbolImpl
import org.jetbrains.kotlin.ir.symbols.impl.IrValueParameterSymbolImpl
import org.jetbrains.kotlin.ir.types.*
import org.jetbrains.kotlin.ir.util.* import org.jetbrains.kotlin.ir.util.*
import org.jetbrains.kotlin.ir.visitors.IrElementTransformerVoid import org.jetbrains.kotlin.ir.visitors.IrElementTransformerVoid
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi2ir.findSingleFunction
import org.jetbrains.kotlin.types.* import org.jetbrains.kotlin.types.*
import org.jetbrains.org.objectweb.asm.Opcodes
import java.util.* import java.util.*
internal val enumClassPhase = makeIrFilePhase( internal val enumClassPhase = makeIrFilePhase(
@@ -51,30 +53,30 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
fun transform(delegatingConstructorCall: IrDelegatingConstructorCall): IrExpression fun transform(delegatingConstructorCall: IrDelegatingConstructorCall): IrExpression
} }
private val arrayOfFun = context.ir.symbols.arrayOf.owner private fun createArrayOfExpression(arrayElementType: IrSimpleType, arrayElements: List<IrExpression>): IrExpression {
private val unsubstitutedArrayOfFunDescriptor = arrayOfFun.descriptor val arrayOfFun = context.ir.symbols.arrayOf.owner
private fun createArrayOfExpression(arrayElementType: KotlinType, arrayElements: List<IrExpression>): IrExpression { /* Substituted descriptor is only needed to construct IrCall */
val unsubstitutedArrayOfFunDescriptor = arrayOfFun.descriptor
val typeParameter0 = unsubstitutedArrayOfFunDescriptor.typeParameters[0] val typeParameter0 = unsubstitutedArrayOfFunDescriptor.typeParameters[0]
val typeSubstitutor = TypeSubstitutor.create(mapOf(typeParameter0.typeConstructor to TypeProjectionImpl(arrayElementType))) val typeSubstitutor = TypeSubstitutor.create(
mapOf(typeParameter0.typeConstructor to TypeProjectionImpl(arrayElementType.toKotlinType()))
)
val substitutedArrayOfDescriptor = unsubstitutedArrayOfFunDescriptor.substitute(typeSubstitutor)!! val substitutedArrayOfDescriptor = unsubstitutedArrayOfFunDescriptor.substitute(typeSubstitutor)!!
val arrayType = context.irBuiltIns.arrayClass.typeWith(arrayElementType)
val valueParameter0 = substitutedArrayOfDescriptor.valueParameters[0]
val arg0VarargType = valueParameter0.type
val arg0VarargElementType = valueParameter0.varargElementType!!
val arg0 = val arg0 =
IrVarargImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, arg0VarargType.toIrType()!!, arg0VarargElementType.toIrType()!!, arrayElements) IrVarargImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, arrayType, arrayElementType, arrayElements)
return IrCallImpl( return IrCallImpl(
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
substitutedArrayOfDescriptor.returnType!!.toIrType()!!, arrayType,
arrayOfFun.symbol, arrayOfFun.symbol,
substitutedArrayOfDescriptor, substitutedArrayOfDescriptor,
arrayOfFun.typeParameters.size arrayOfFun.typeParameters.size
).apply { ).apply {
putTypeArgument(0, arrayElementType.toIrType()!!) putTypeArgument(0, arrayElementType)
putValueArgument(0, arg0) putValueArgument(0, arg0)
} }
} }
@@ -82,8 +84,8 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
private inner class EnumClassTransformer(val irClass: IrClass) { private inner class EnumClassTransformer(val irClass: IrClass) {
private val enumEntryOrdinals = TObjectIntHashMap<IrEnumEntry>() private val enumEntryOrdinals = TObjectIntHashMap<IrEnumEntry>()
private val enumEntryClassToEntry = HashMap<IrClass, IrEnumEntry>() private val enumEntryClassToEntry = HashMap<IrClass, IrEnumEntry>()
private val loweredEnumConstructors = HashMap<ClassConstructorDescriptor, IrConstructorImpl>() private val loweredEnumConstructors = HashMap<IrConstructorSymbol, IrConstructorImpl>()
private val loweredEnumConstructorParameters = HashMap<ValueParameterDescriptor, IrValueParameter>() private val loweredEnumConstructorParameters = HashMap<IrValueParameterSymbol, IrValueParameter>()
private val enumEntriesByField = HashMap<IrField, IrEnumEntry>() private val enumEntriesByField = HashMap<IrField, IrEnumEntry>()
private val enumEntryFields = ArrayList<IrField>() private val enumEntryFields = ArrayList<IrField>()
@@ -125,56 +127,73 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
enumConstructor: IrConstructor, enumConstructor: IrConstructor,
enumClass: IrClass enumClass: IrClass
): IrConstructor { ): IrConstructor {
val constructorDescriptor = enumConstructor.descriptor val descriptor = WrappedClassConstructorDescriptor(enumConstructor.descriptor.annotations, enumConstructor.descriptor.source)
val loweredConstructorDescriptor = lowerEnumConstructor(constructorDescriptor)
return IrConstructorImpl( return IrConstructorImpl(
enumConstructor.startOffset, enumConstructor.endOffset, enumConstructor.origin, enumConstructor.startOffset, enumConstructor.endOffset,
loweredConstructorDescriptor, enumConstructor.origin,
loweredConstructorDescriptor.returnType.toIrType()!!, IrConstructorSymbolImpl(descriptor),
enumConstructor.body!! // will be transformed later enumConstructor.name,
Visibilities.PROTECTED,
returnType = enumConstructor.returnType,
isInline = enumConstructor.isInline,
isExternal = enumConstructor.isExternal,
isPrimary = enumConstructor.isPrimary
).apply { ).apply {
val newConstructor = this
descriptor.bind(this)
parent = enumClass parent = enumClass
createParameterDeclarations()
loweredEnumConstructors[constructorDescriptor] = this val nameParameter = makeNameValueParameter(newConstructor)
constructorDescriptor.valueParameters.forEach { val ordinalParameter = makeOrdinalValueParameter(newConstructor)
loweredEnumConstructorParameters[it] = valueParameters[2 + it.index] valueParameters.add(0, nameParameter)
} valueParameters.add(1, ordinalParameter)
valueParameters.addAll(enumConstructor.valueParameters.map { param ->
param.copyTo(newConstructor, index = param.index + 2).also { newParam ->
loweredEnumConstructorParameters[param.symbol] = newParam
}
})
body = enumConstructor.body // will be transformed later
loweredEnumConstructors[enumConstructor.symbol] = this
metadata = enumConstructor.metadata metadata = enumConstructor.metadata
} }
} }
private fun lowerEnumConstructor(constructorDescriptor: ClassConstructorDescriptor): ClassConstructorDescriptor { private fun makeNameValueParameter(constructor: IrConstructor): IrValueParameter {
val loweredConstructorDescriptor = ClassConstructorDescriptorImpl.createSynthesized( val descriptor = WrappedValueParameterDescriptor()
constructorDescriptor.containingDeclaration, return IrValueParameterImpl(
constructorDescriptor.annotations, UNDEFINED_OFFSET, UNDEFINED_OFFSET,
constructorDescriptor.isPrimary, IrDeclarationOrigin.DEFINED,
constructorDescriptor.source IrValueParameterSymbolImpl(descriptor),
) Name.identifier("name"),
index = 0,
val valueParameters = type = context.irBuiltIns.stringType,
listOf( varargElementType = null,
loweredConstructorDescriptor.createValueParameter(0, "name", context.builtIns.stringType), isCrossinline = false,
loweredConstructorDescriptor.createValueParameter(1, "ordinal", context.builtIns.intType) isNoinline = false
) + ).apply {
constructorDescriptor.valueParameters.map { descriptor.bind(this)
lowerConstructorValueParameter(loweredConstructorDescriptor, it) parent = constructor
} }
loweredConstructorDescriptor.initialize(valueParameters, Visibilities.PROTECTED)
loweredConstructorDescriptor.returnType = constructorDescriptor.returnType
return loweredConstructorDescriptor
} }
private fun lowerConstructorValueParameter( private fun makeOrdinalValueParameter(constructor: IrConstructor): IrValueParameter {
loweredConstructorDescriptor: ClassConstructorDescriptor, val descriptor = WrappedValueParameterDescriptor()
valueParameterDescriptor: ValueParameterDescriptor return IrValueParameterImpl(
): ValueParameterDescriptor { UNDEFINED_OFFSET, UNDEFINED_OFFSET,
return valueParameterDescriptor.copy( IrDeclarationOrigin.DEFINED,
loweredConstructorDescriptor, IrValueParameterSymbolImpl(descriptor),
valueParameterDescriptor.name, Name.identifier("ordinal"),
valueParameterDescriptor.index + 2 index = 1,
) type = context.irBuiltIns.intType,
varargElementType = null,
isCrossinline = false,
isNoinline = false
).apply {
descriptor.bind(this)
parent = constructor
}
} }
private fun lowerEnumEntries() { private fun lowerEnumEntries() {
@@ -224,39 +243,37 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
private fun createSyntheticValuesFieldDeclaration(): IrFieldImpl { private fun createSyntheticValuesFieldDeclaration(): IrFieldImpl {
val valuesArrayType = context.builtIns.getArrayType(Variance.INVARIANT, irClass.descriptor.defaultType) val valuesArrayType = context.irBuiltIns.arrayClass.typeWith(irClass.defaultType)
val irValuesInitializer = createSyntheticValuesFieldInitializerExpression() val irValuesInitializer = createSyntheticValuesFieldInitializerExpression()
val descriptor = WrappedFieldDescriptor()
// TODO: mark ACC_SYNTHETIC
return IrFieldImpl( return IrFieldImpl(
UNDEFINED_OFFSET, UNDEFINED_OFFSET, IrDeclarationOrigin.FIELD_FOR_ENUM_VALUES, UNDEFINED_OFFSET, UNDEFINED_OFFSET, IrDeclarationOrigin.FIELD_FOR_ENUM_VALUES,
createSyntheticValuesFieldDescriptor(valuesArrayType), IrFieldSymbolImpl(descriptor),
valuesArrayType.toIrType()!!, Name.identifier("\$VALUES"),
IrExpressionBodyImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, irValuesInitializer) valuesArrayType,
Visibilities.PRIVATE,
isFinal = true,
isExternal = false,
isStatic = true
).also { ).also {
descriptor.bind(it)
it.parent = irClass it.parent = irClass
it.initializer = IrExpressionBodyImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, irValuesInitializer)
valuesField = it valuesField = it
} }
} }
private fun createSyntheticValuesFieldInitializerExpression(): IrExpression = private fun createSyntheticValuesFieldInitializerExpression(): IrExpression =
createArrayOfExpression( createArrayOfExpression(
irClass.defaultType.toKotlinType(), irClass.defaultType,
enumEntryFields.map { irField -> enumEntryFields.map { irField ->
IrGetFieldImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, irField.symbol, irField.symbol.owner.type) IrGetFieldImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, irField.symbol, irField.symbol.owner.type)
}) })
private fun createSyntheticValuesFieldDescriptor(valuesArrayType: SimpleType): PropertyDescriptorImpl {
return JvmPropertyDescriptorImpl.createStaticVal(
Name.identifier("\$VALUES"),
valuesArrayType,
irClass.descriptor,
Annotations.EMPTY,
Modality.FINAL, Visibilities.PRIVATE, Opcodes.ACC_SYNTHETIC,
irClass.descriptor.source
)
}
private fun lowerEnumClassBody() { private fun lowerEnumClassBody() {
irClass.transformChildrenVoid(EnumClassBodyTransformer()) irClass.transformChildrenVoid(EnumClassBodyTransformer())
} }
@@ -277,7 +294,10 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
enumConstructorCall.typeArgumentsCount enumConstructorCall.typeArgumentsCount
) )
assert(result.descriptor.valueParameters.size == 2) { assert(enumConstructorCall.typeArgumentsCount == 1) { "Enum<T> call expected:\n${result.dump()}" }
result.putTypeArgument(0, enumConstructorCall.getTypeArgument(0))
assert(result.symbol.owner.valueParameters.size == 2) {
"Enum(String, Int) constructor call expected:\n${result.dump()}" "Enum(String, Int) constructor call expected:\n${result.dump()}"
} }
@@ -296,12 +316,11 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
} }
override fun transform(delegatingConstructorCall: IrDelegatingConstructorCall): IrExpression { override fun transform(delegatingConstructorCall: IrDelegatingConstructorCall): IrExpression {
val descriptor = delegatingConstructorCall.descriptor
val startOffset = delegatingConstructorCall.startOffset val startOffset = delegatingConstructorCall.startOffset
val endOffset = delegatingConstructorCall.endOffset val endOffset = delegatingConstructorCall.endOffset
val loweredDelegatedConstructor = loweredEnumConstructors.getOrElse(descriptor) { val loweredDelegatedConstructor = loweredEnumConstructors.getOrElse(delegatingConstructorCall.symbol) {
throw AssertionError("Constructor called in enum entry initializer should've been lowered: $descriptor") throw AssertionError("Constructor called in enum entry initializer should've been lowered: ${delegatingConstructorCall.symbol}")
} }
val result = IrDelegatingConstructorCallImpl( val result = IrDelegatingConstructorCallImpl(
@@ -313,10 +332,12 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
loweredDelegatedConstructor.typeParameters.size loweredDelegatedConstructor.typeParameters.size
) )
assert(loweredDelegatedConstructor.typeParameters.size == 0) { "Enum delegating call expected:\n${result.dump()}" }
result.putValueArgument(0, IrGetValueImpl(startOffset, endOffset, irEnumConstructor.valueParameters[0].symbol)) result.putValueArgument(0, IrGetValueImpl(startOffset, endOffset, irEnumConstructor.valueParameters[0].symbol))
result.putValueArgument(1, IrGetValueImpl(startOffset, endOffset, irEnumConstructor.valueParameters[1].symbol)) result.putValueArgument(1, IrGetValueImpl(startOffset, endOffset, irEnumConstructor.valueParameters[1].symbol))
descriptor.valueParameters.forEach { valueParameter -> delegatingConstructorCall.symbol.owner.valueParameters.forEach { valueParameter ->
val i = valueParameter.index val i = valueParameter.index
result.putValueArgument(i + 2, delegatingConstructorCall.getValueArgument(i)) result.putValueArgument(i + 2, delegatingConstructorCall.getValueArgument(i))
} }
@@ -330,12 +351,11 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
val name = enumEntry.name.asString() val name = enumEntry.name.asString()
val ordinal = enumEntryOrdinals[enumEntry] val ordinal = enumEntryOrdinals[enumEntry]
val descriptor = enumConstructorCall.descriptor
val startOffset = enumConstructorCall.startOffset val startOffset = enumConstructorCall.startOffset
val endOffset = enumConstructorCall.endOffset val endOffset = enumConstructorCall.endOffset
val loweredConstructor = loweredEnumConstructors.getOrElse(descriptor) { val loweredConstructor = loweredEnumConstructors.getOrElse(enumConstructorCall.symbol) {
throw AssertionError("Constructor called in enum entry initializer should've been lowered: $descriptor") throw AssertionError("Constructor called in enum entry initializer should've been lowered:\n${enumConstructorCall.dump()}")
} }
val result = createConstructorCall(startOffset, endOffset, loweredConstructor) val result = createConstructorCall(startOffset, endOffset, loweredConstructor)
@@ -343,7 +363,7 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
result.putValueArgument(0, IrConstImpl.string(startOffset, endOffset, context.irBuiltIns.stringType, name)) result.putValueArgument(0, IrConstImpl.string(startOffset, endOffset, context.irBuiltIns.stringType, name))
result.putValueArgument(1, IrConstImpl.int(startOffset, endOffset, context.irBuiltIns.intType, ordinal)) result.putValueArgument(1, IrConstImpl.int(startOffset, endOffset, context.irBuiltIns.intType, ordinal))
descriptor.valueParameters.forEach { valueParameter -> enumConstructorCall.symbol.owner.valueParameters.forEach { valueParameter ->
val i = valueParameter.index val i = valueParameter.index
result.putValueArgument(i + 2, enumConstructorCall.getValueArgument(i)) result.putValueArgument(i + 2, enumConstructorCall.getValueArgument(i))
} }
@@ -440,7 +460,7 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
override fun visitDelegatingConstructorCall(expression: IrDelegatingConstructorCall): IrExpression { override fun visitDelegatingConstructorCall(expression: IrDelegatingConstructorCall): IrExpression {
expression.transformChildrenVoid(this) expression.transformChildrenVoid(this)
if (expression.descriptor.containingDeclaration.kind == ClassKind.ENUM_CLASS) { if (expression.symbol.owner.parentAsClass.kind == ClassKind.ENUM_CLASS) {
val callTransformer = enumConstructorCallTransformer ?: throw AssertionError( val callTransformer = enumConstructorCallTransformer ?: throw AssertionError(
"Enum constructor call outside of enum entry initialization or enum class constructor:\n" + "Enum constructor call outside of enum entry initialization or enum class constructor:\n" +
irClass.dump() irClass.dump()
@@ -453,7 +473,7 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
} }
override fun visitGetValue(expression: IrGetValue): IrExpression { override fun visitGetValue(expression: IrGetValue): IrExpression {
val loweredParameter = loweredEnumConstructorParameters[expression.descriptor] val loweredParameter = loweredEnumConstructorParameters[expression.symbol]
return if (loweredParameter != null) { return if (loweredParameter != null) {
IrGetValueImpl(expression.startOffset, expression.endOffset, loweredParameter.symbol, expression.origin) IrGetValueImpl(expression.startOffset, expression.endOffset, loweredParameter.symbol, expression.origin)
} else { } else {
@@ -473,22 +493,25 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
} }
private fun createEnumValueOfBody(): IrBody { private fun createEnumValueOfBody(): IrBody {
val unsubstitutedValueOfDescriptor = context.irBuiltIns.enumValueOf val enumValueOf = context.irBuiltIns.enumValueOfFun
val valueOfSymbol = context.irBuiltIns.enumValueOfSymbol val returnType = irClass.defaultType
val typeParameterT = unsubstitutedValueOfDescriptor.typeParameters[0]
val unsubstitutedValueOfDescriptor = enumValueOf.descriptor
val typeParameter0 = unsubstitutedValueOfDescriptor.typeParameters[0]
val enumClassType = irClass.descriptor.defaultType val enumClassType = irClass.descriptor.defaultType
val typeSubstitutor = TypeSubstitutor.create(mapOf(typeParameterT.typeConstructor to TypeProjectionImpl(enumClassType))) val typeSubstitutor = TypeSubstitutor.create(mapOf(typeParameter0.typeConstructor to TypeProjectionImpl(enumClassType)))
val substitutedValueOfDescriptor = unsubstitutedValueOfDescriptor.substitute(typeSubstitutor)!! val substitutedValueOfDescriptor = unsubstitutedValueOfDescriptor.substitute(typeSubstitutor)!!
val irValueOfCall = val irValueOfCall =
IrCallImpl( IrCallImpl(
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
substitutedValueOfDescriptor.returnType!!.toIrType()!!, returnType,
valueOfSymbol, enumValueOf.symbol,
substitutedValueOfDescriptor, substitutedValueOfDescriptor,
substitutedValueOfDescriptor.typeParametersCount enumValueOf.typeParameters.size
) )
irValueOfCall.putTypeArgument(0, irClass.defaultType)
irValueOfCall.putValueArgument( irValueOfCall.putValueArgument(
0, IrGetValueImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, valueOfFunction.valueParameters[0].symbol) 0, IrGetValueImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, valueOfFunction.valueParameters[0].symbol)
) )
@@ -499,7 +522,7 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
IrReturnImpl( IrReturnImpl(
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
valueOfFunction.returnType, returnType,
valueOfFunction.symbol, valueOfFunction.symbol,
irValueOfCall irValueOfCall
) )
@@ -508,11 +531,10 @@ private class EnumClassLowering(val context: JvmBackendContext) : ClassLoweringP
} }
private fun createEnumValuesBody(valuesField: IrField): IrBody { private fun createEnumValuesBody(valuesField: IrField): IrBody {
val cloneFunDescriptor = valuesField.type.toKotlinType().memberScope.findSingleFunction(Name.identifier("clone")).original val cloneFun = context.irBuiltIns.arrayClass.owner.functions.find { it.name.asString() == "clone" }!!
val cloneFun = context.ir.symbols.externalSymbolTable.referenceSimpleFunction(cloneFunDescriptor).owner
val irCloneValues = val irCloneValues =
IrCallImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, cloneFun.returnType, cloneFun.symbol, cloneFunDescriptor, 0).apply { IrCallImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, cloneFun.returnType, cloneFun.symbol, cloneFun.descriptor, 0).apply {
dispatchReceiver = dispatchReceiver =
IrGetFieldImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, valuesField.symbol, valuesField.symbol.owner.type) IrGetFieldImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, valuesField.symbol, valuesField.symbol.owner.type)
} }
@@ -286,8 +286,8 @@ val IrDeclarationContainer.properties: Sequence<IrProperty>
val IrFunction.explicitParameters: List<IrValueParameter> val IrFunction.explicitParameters: List<IrValueParameter>
get() = (listOfNotNull(dispatchReceiverParameter, extensionReceiverParameter) + valueParameters) get() = (listOfNotNull(dispatchReceiverParameter, extensionReceiverParameter) + valueParameters)
val IrClass.defaultType: IrType val IrClass.defaultType: IrSimpleType
get() = this.thisReceiver!!.type get() = this.thisReceiver!!.type as IrSimpleType
val IrSimpleFunction.isReal: Boolean get() = descriptor.kind.isReal val IrSimpleFunction.isReal: Boolean get() = descriptor.kind.isReal