diff --git a/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/ConverterUtil.kt b/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/ConverterUtil.kt index ec0826b237b..4ee7c021005 100644 --- a/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/ConverterUtil.kt +++ b/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/ConverterUtil.kt @@ -90,10 +90,12 @@ inline fun isClassLocal(classNode: LighterASTNode, getParent: LighterASTNode.() parent?.tokenType == KT_FILE -> return true parent?.tokenType == CLASS_BODY && !(grandParent?.tokenType == OBJECT_DECLARATION && grandParent?.getParent()?.tokenType == OBJECT_LITERAL) -> return true parent?.tokenType == BLOCK && grandParent?.tokenType == SCRIPT -> return true - // NB: enum entry nested classes are considered local by FIR design (see discussion in KT-45115) - parent?.tokenType == ENUM_ENTRY -> return true } } + // NB: enum entry nested classes are considered local by FIR design (see discussion in KT-45115) + if (parent?.tokenType == ENUM_ENTRY) { + return true + } if (tokenType == BLOCK) { return true } diff --git a/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt b/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt index cbc1f366afe..4a59b7a55af 100644 --- a/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt +++ b/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt @@ -793,10 +793,11 @@ open class RawFirBuilder( } override fun visitClassOrObject(classOrObject: KtClassOrObject, data: Unit): FirElement { + // NB: enum entry nested classes are considered local by FIR design (see discussion in KT-45115) + val isLocal = classOrObject.isLocal || classOrObject.getStrictParentOfType() != null return withChildClassName( classOrObject.nameAsSafeName, - // NB: enum entry nested classes are considered local by FIR design (see discussion in KT-45115) - isLocal = classOrObject.isLocal || classOrObject.getStrictParentOfType() != null + isLocal = isLocal ) { val classKind = when (classOrObject) { is KtObjectDeclaration -> ClassKind.OBJECT @@ -809,7 +810,7 @@ open class RawFirBuilder( else -> throw AssertionError("Unexpected class or object: ${classOrObject.text}") } val status = FirDeclarationStatusImpl( - if (classOrObject.isLocal) Visibilities.Local else classOrObject.visibility, + if (isLocal) Visibilities.Local else classOrObject.visibility, classOrObject.modality, ).apply { isExpect = classOrObject.hasExpectModifier() diff --git a/compiler/testData/codegen/box/enum/objectInEnum.kt b/compiler/testData/codegen/box/enum/objectInEnum.kt index a177645e9a0..1fc2ffcd2d0 100644 --- a/compiler/testData/codegen/box/enum/objectInEnum.kt +++ b/compiler/testData/codegen/box/enum/objectInEnum.kt @@ -4,6 +4,8 @@ enum class E { ENTRY, SUBCLASS { + // Because of KT-45115 classes/objects inside enum entries are local in FIR + @Suppress("LOCAL_OBJECT_NOT_ALLOWED") object O { fun foo() = 2 } diff --git a/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_after.fir.kt b/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_after.fir.kt index 612ebe7a01f..38e31fea348 100644 --- a/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_after.fir.kt +++ b/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_after.fir.kt @@ -5,7 +5,7 @@ package a enum class C { E1, E2, E3 { - object O_O + object O_O fun b() { O_O diff --git a/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_before.fir.kt b/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_before.fir.kt index eb4e81f4c17..04b28f02060 100644 --- a/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_before.fir.kt +++ b/compiler/testData/diagnostics/tests/classObjects/InnerClassAccessThroughEnum_before.fir.kt @@ -5,7 +5,7 @@ package a enum class C { E1, E2, E3 { - object O_O + object O_O fun b() { O_O diff --git a/compiler/testData/ir/irText/singletons/enumEntry.fir.txt b/compiler/testData/ir/irText/singletons/enumEntry.fir.txt index ba39fe36fb1..d14a72a8ca0 100644 --- a/compiler/testData/ir/irText/singletons/enumEntry.fir.txt +++ b/compiler/testData/ir/irText/singletons/enumEntry.fir.txt @@ -18,13 +18,13 @@ FILE fqName: fileName:/enumEntry.kt FUN name:test visibility:public modality:FINAL <> ($this:.Z.ENTRY) returnType:kotlin.Unit $this: VALUE_PARAMETER name: type:.Z.ENTRY BLOCK_BODY - CLASS CLASS name:A modality:FINAL visibility:public [inner] superTypes:[kotlin.Any] + CLASS CLASS name:A modality:FINAL visibility:local [inner] superTypes:[kotlin.Any] $this: VALUE_PARAMETER INSTANCE_RECEIVER name: type:.Z.ENTRY.A CONSTRUCTOR visibility:public <> ($this:.Z.ENTRY) returnType:.Z.ENTRY.A [primary] $outer: VALUE_PARAMETER name: type:.Z.ENTRY BLOCK_BODY DELEGATING_CONSTRUCTOR_CALL 'public constructor () [primary] declared in kotlin.Any' - INSTANCE_INITIALIZER_CALL classDescriptor='CLASS CLASS name:A modality:FINAL visibility:public [inner] superTypes:[kotlin.Any]' + INSTANCE_INITIALIZER_CALL classDescriptor='CLASS CLASS name:A modality:FINAL visibility:local [inner] superTypes:[kotlin.Any]' FUN name:test2 visibility:public modality:FINAL <> ($this:.Z.ENTRY.A) returnType:kotlin.Unit $this: VALUE_PARAMETER name: type:.Z.ENTRY.A BLOCK_BODY