diff --git a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrConverter.kt b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrConverter.kt index 0d38c47d9ab..81eb6a18303 100644 --- a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrConverter.kt +++ b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrConverter.kt @@ -103,6 +103,7 @@ class Fir2IrConverter( // 5. Body processing // If we encounter local class / anonymous object here, then we perform all (1)-(5) stages immediately + delegatedMemberGenerator.generateBodies() for (firFile in allFirFiles) { firFile.accept(fir2irVisitor, null) } diff --git a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrDeclarationStorage.kt b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrDeclarationStorage.kt index 3d900cbe4f5..0d640d73806 100644 --- a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrDeclarationStorage.kt +++ b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/Fir2IrDeclarationStorage.kt @@ -30,6 +30,7 @@ import org.jetbrains.kotlin.fir.lazy.Fir2IrLazyConstructor import org.jetbrains.kotlin.fir.lazy.Fir2IrLazyProperty import org.jetbrains.kotlin.fir.lazy.Fir2IrLazySimpleFunction import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference +import org.jetbrains.kotlin.fir.resolve.dfa.cfg.isLocalClassOrAnonymousObject import org.jetbrains.kotlin.fir.types.isSuspendFunctionType import org.jetbrains.kotlin.fir.resolve.isKFunctionInvoke import org.jetbrains.kotlin.fir.resolve.providers.firProvider @@ -949,7 +950,10 @@ class Fir2IrDeclarationStorage( fun createIrFieldAndDelegatedMembers(field: FirField, owner: FirClass, irClass: IrClass): IrField { val irField = createIrField(field, origin = IrDeclarationOrigin.DELEGATE) irField.setAndModifyParent(irClass) - components.delegatedMemberGenerator.generate(irField, field, owner, irClass) + delegatedMemberGenerator.generate(irField, field, owner, irClass) + if (owner.isLocalClassOrAnonymousObject()) { + delegatedMemberGenerator.generateBodies() + } return irField } diff --git a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/generators/DelegatedMemberGenerator.kt b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/generators/DelegatedMemberGenerator.kt index eef290d7361..629e711d04f 100644 --- a/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/generators/DelegatedMemberGenerator.kt +++ b/compiler/fir/fir2ir/src/org/jetbrains/kotlin/fir/backend/generators/DelegatedMemberGenerator.kt @@ -50,6 +50,40 @@ class DelegatedMemberGenerator( private val baseFunctionSymbols = mutableMapOf>() private val basePropertySymbols = mutableMapOf>() + private data class DeclarationBodyInfo( + val declaration: IrDeclaration, + val field: IrField, + val delegateToSymbol: FirCallableSymbol<*> + ) + + private val bodiesInfo = mutableListOf() + + fun generateBodies() { + for ((declaration, irField, delegateToSymbol) in bodiesInfo) { + when (declaration) { + is IrSimpleFunction -> { + val member = declarationStorage.getIrFunctionSymbol( + delegateToSymbol as FirNamedFunctionSymbol + ).owner as? IrSimpleFunction ?: continue + val body = createDelegateBody(irField, declaration, member) + declaration.body = body + } + is IrProperty -> { + val member = declarationStorage.getIrPropertySymbol( + delegateToSymbol as FirPropertySymbol + ).owner as? IrProperty ?: continue + val getter = declaration.getter!! + getter.body = createDelegateBody(irField, getter, member.getter!!) + if (declaration.isVar) { + val setter = declaration.setter!! + setter.body = createDelegateBody(irField, setter, member.setter!!) + } + } + } + } + bodiesInfo.clear() + } + // Generate delegated members for [subClass]. The synthetic field [irField] has the super interface type. fun generate(irField: IrField, firField: FirField, firSubClass: FirClass, subClass: IrClass) { val subClassLookupTag = firSubClass.symbol.toLookupTag() @@ -61,18 +95,14 @@ class DelegatedMemberGenerator( .unwrapDelegateTarget(subClassLookupTag, firField) ?: return@processAllFunctions - val member = - declarationStorage.getIrFunctionSymbol(unwrapped.symbol).owner as? IrSimpleFunction - ?: return@processAllFunctions - if (shouldSkipDelegationFor(unwrapped)) { return@processAllFunctions } val irSubFunction = generateDelegatedFunction( - subClass, firSubClass, irField, member, functionSymbol.fir + subClass, firSubClass, functionSymbol.fir ) - + bodiesInfo += DeclarationBodyInfo(irSubFunction, irField, unwrapped.symbol) declarationStorage.cacheDelegationFunction(functionSymbol.fir, irSubFunction) subClass.addMember(irSubFunction) } @@ -85,17 +115,14 @@ class DelegatedMemberGenerator( .unwrapDelegateTarget(subClassLookupTag, firField) ?: return@processAllProperties - val member = declarationStorage.getIrPropertySymbol(unwrapped.symbol).owner as? IrProperty - ?: return@processAllProperties - if (shouldSkipDelegationFor(unwrapped)) { return@processAllProperties } val irSubProperty = generateDelegatedProperty( - subClass, firSubClass, irField, member, propertySymbol.fir + subClass, firSubClass, propertySymbol.fir ) - + bodiesInfo += DeclarationBodyInfo(irSubProperty, irField, unwrapped.symbol) declarationStorage.cacheDelegatedProperty(propertySymbol.fir, irSubProperty) subClass.addMember(irSubProperty) } @@ -146,8 +173,6 @@ class DelegatedMemberGenerator( private fun generateDelegatedFunction( subClass: IrClass, firSubClass: FirClass, - irField: IrField, - superFunction: IrSimpleFunction, delegateOverride: FirSimpleFunction ): IrSimpleFunction { val delegateFunction = @@ -164,8 +189,6 @@ class DelegatedMemberGenerator( baseFunctionSymbols[delegateFunction] = baseSymbols annotationGenerator.generate(delegateFunction, delegateOverride) - val body = createDelegateBody(irField, delegateFunction, superFunction) - delegateFunction.body = body return delegateFunction } @@ -226,8 +249,6 @@ class DelegatedMemberGenerator( private fun generateDelegatedProperty( subClass: IrClass, firSubClass: FirClass, - irField: IrField, - superProperty: IrProperty, firDelegateProperty: FirProperty ): IrProperty { val delegateProperty = @@ -244,8 +265,8 @@ class DelegatedMemberGenerator( basePropertySymbols[delegateProperty] = baseSymbols annotationGenerator.generate(delegateProperty, firDelegateProperty) - delegateProperty.getter!!.body = createDelegateBody(irField, delegateProperty.getter!!, superProperty.getter!!) - delegateProperty.getter!!.overriddenSymbols = + val getter = delegateProperty.getter!! + getter.overriddenSymbols = firDelegateProperty.generateOverriddenAccessorSymbols( firSubClass, isGetter = true, @@ -256,8 +277,8 @@ class DelegatedMemberGenerator( ) annotationGenerator.generate(delegateProperty.getter!!, firDelegateProperty) if (delegateProperty.isVar) { - delegateProperty.setter!!.body = createDelegateBody(irField, delegateProperty.setter!!, superProperty.setter!!) - delegateProperty.setter!!.overriddenSymbols = + val setter = delegateProperty.setter!! + setter.overriddenSymbols = firDelegateProperty.generateOverriddenAccessorSymbols( firSubClass, isGetter = false, session, scopeSession, declarationStorage, fakeOverrideGenerator )