K2: use ClassKind.CLASS for object literals

K1 uses CLASS, and libraries like kotlinx-metadata-jvm and
kotlin-reflect already rely on it.

 #KT-57641 Fixed
This commit is contained in:
Alexander Udalov
2023-06-21 15:51:15 +02:00
committed by Space Team
parent 1be0fcb53a
commit f3a7312ee6
7 changed files with 24 additions and 25 deletions
@@ -9,11 +9,12 @@ import org.jetbrains.kotlin.KtNodeTypes
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.descriptors.Visibilities
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.diagnostics.reportOn
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
import org.jetbrains.kotlin.fir.analysis.checkers.getModifierList
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
import org.jetbrains.kotlin.diagnostics.reportOn
import org.jetbrains.kotlin.fir.declarations.FirAnonymousObject
import org.jetbrains.kotlin.fir.declarations.FirClass
import org.jetbrains.kotlin.fir.declarations.FirConstructor
import org.jetbrains.kotlin.fir.declarations.FirRegularClass
@@ -36,14 +37,17 @@ object FirConstructorAllowedChecker : FirConstructorChecker() {
ClassKind.ENUM_CLASS -> if (declaration.visibility != Visibilities.Private) {
reporter.reportOn(source, FirErrors.NON_PRIVATE_CONSTRUCTOR_IN_ENUM, context)
}
ClassKind.CLASS -> if (containingClass is FirRegularClass && containingClass.modality == Modality.SEALED) {
val modifierList = source.getModifierList() ?: return
val hasIllegalModifier = modifierList.modifiers.any {
val token = it.token
token in KtTokens.VISIBILITY_MODIFIERS && token != KtTokens.PROTECTED_KEYWORD && token != KtTokens.PRIVATE_KEYWORD
}
if (hasIllegalModifier) {
reporter.reportOn(source, FirErrors.NON_PRIVATE_OR_PROTECTED_CONSTRUCTOR_IN_SEALED, context)
ClassKind.CLASS -> when (containingClass) {
is FirAnonymousObject -> reporter.reportOn(source, FirErrors.CONSTRUCTOR_IN_OBJECT, context)
is FirRegularClass -> if (containingClass.modality == Modality.SEALED) {
val modifierList = source.getModifierList() ?: return
val hasIllegalModifier = modifierList.modifiers.any {
val token = it.token
token in KtTokens.VISIBILITY_MODIFIERS && token != KtTokens.PROTECTED_KEYWORD && token != KtTokens.PRIVATE_KEYWORD
}
if (hasIllegalModifier) {
reporter.reportOn(source, FirErrors.NON_PRIVATE_OR_PROTECTED_CONSTRUCTOR_IN_SEALED, context)
}
}
}
ClassKind.ANNOTATION_CLASS -> {
@@ -8,10 +8,10 @@ package org.jetbrains.kotlin.fir.analysis.checkers.declaration
import org.jetbrains.kotlin.KtNodeTypes
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
import org.jetbrains.kotlin.diagnostics.reportOn
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
import org.jetbrains.kotlin.fir.analysis.getChild
import org.jetbrains.kotlin.fir.declarations.FirAnonymousObject
import org.jetbrains.kotlin.fir.declarations.FirClass
@@ -20,15 +20,12 @@ import org.jetbrains.kotlin.fir.languageVersionSettings
object FirTypeParametersInObjectChecker : FirClassChecker() {
override fun check(declaration: FirClass, context: CheckerContext, reporter: DiagnosticReporter) {
if (declaration.classKind != ClassKind.OBJECT) {
return
}
when (declaration) {
is FirRegularClass -> if (declaration.typeParameters.isNotEmpty()) {
if (declaration.classKind == ClassKind.OBJECT && declaration is FirRegularClass) {
if (declaration.typeParameters.isNotEmpty()) {
reporter.reportOn(declaration.source, FirErrors.TYPE_PARAMETERS_IN_OBJECT, context)
}
is FirAnonymousObject -> if (declaration.source?.getChild(KtNodeTypes.TYPE_PARAMETER_LIST, depth = 1) != null) {
} else if (declaration.classKind == ClassKind.CLASS && declaration is FirAnonymousObject) {
if (declaration.source?.getChild(KtNodeTypes.TYPE_PARAMETER_LIST, depth = 1) != null) {
val diagnosticFactory =
if (context.session.languageVersionSettings.supportsFeature(LanguageFeature.ProhibitTypeParametersInAnonymousObjects)) {
FirErrors.TYPE_PARAMETERS_IN_OBJECT
@@ -400,8 +400,7 @@ class Fir2IrClassifierStorage(
name = name,
visibility = components.visibilityConverter.convertToDescriptorVisibility(visibility),
symbol = IrClassSymbolImpl(),
// NB: for unknown reason, IR uses 'CLASS' kind for simple anonymous objects
kind = anonymousObject.classKind.takeIf { it == ClassKind.ENUM_ENTRY } ?: ClassKind.CLASS,
kind = anonymousObject.classKind,
modality = modality,
).apply {
metadata = FirMetadataSource.Class(anonymousObject)
@@ -657,7 +657,7 @@ class DeclarationsConverter(
source = objectDeclaration.toFirSourceElement()
origin = FirDeclarationOrigin.Source
moduleData = baseModuleData
classKind = ClassKind.OBJECT
classKind = ClassKind.CLASS
scopeProvider = baseScopeProvider
symbol = FirAnonymousObjectSymbol()
status = FirDeclarationStatusImpl(Visibilities.Local, Modality.FINAL)
@@ -1399,7 +1399,7 @@ open class RawFirBuilder(
source = objectDeclaration.toFirSourceElement()
moduleData = baseModuleData
origin = FirDeclarationOrigin.Source
classKind = ClassKind.OBJECT
classKind = ClassKind.CLASS
scopeProvider = baseScopeProvider
symbol = FirAnonymousObjectSymbol()
status = FirDeclarationStatusImpl(Visibilities.Local, Modality.FINAL)
@@ -29,6 +29,7 @@ fun box(): String {
assertEquals(null, C::class.objectInstance)
assertEquals(null, String::class.objectInstance)
assertEquals(Unit, Unit::class.objectInstance)
assertEquals(null, object {}::class.objectInstance)
return "OK"
}
@@ -1,5 +1,3 @@
// IGNORE K2
fun test() = object : Runnable {
override fun run() { }
}