[K/N] Implement frontend checkers for usages forward declaration type
Forward declaration type doesn't exist in runtime. This restricts its possible usages. ^KT-59764
This commit is contained in:
committed by
Space Team
parent
27043bd8a6
commit
6da3ecceab
+16
@@ -7,12 +7,14 @@ package org.jetbrains.kotlin.fir.checkers.generator.diagnostics
|
|||||||
|
|
||||||
import com.intellij.psi.PsiElement
|
import com.intellij.psi.PsiElement
|
||||||
import org.jetbrains.kotlin.config.LanguageFeature
|
import org.jetbrains.kotlin.config.LanguageFeature
|
||||||
|
import org.jetbrains.kotlin.diagnostics.Severity
|
||||||
import org.jetbrains.kotlin.fir.PrivateForInline
|
import org.jetbrains.kotlin.fir.PrivateForInline
|
||||||
import org.jetbrains.kotlin.fir.checkers.generator.diagnostics.model.DiagnosticList
|
import org.jetbrains.kotlin.fir.checkers.generator.diagnostics.model.DiagnosticList
|
||||||
import org.jetbrains.kotlin.fir.checkers.generator.diagnostics.model.PositioningStrategy
|
import org.jetbrains.kotlin.fir.checkers.generator.diagnostics.model.PositioningStrategy
|
||||||
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
|
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
||||||
import org.jetbrains.kotlin.name.FqName
|
import org.jetbrains.kotlin.name.FqName
|
||||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||||
import org.jetbrains.kotlin.psi.KtElement
|
import org.jetbrains.kotlin.psi.KtElement
|
||||||
@@ -65,5 +67,19 @@ object NATIVE_DIAGNOSTICS_LIST : DiagnosticList("FirNativeErrors") {
|
|||||||
val INVALID_OBJC_HIDES_TARGETS by error<KtElement>()
|
val INVALID_OBJC_HIDES_TARGETS by error<KtElement>()
|
||||||
val INVALID_REFINES_IN_SWIFT_TARGETS by error<KtElement>()
|
val INVALID_REFINES_IN_SWIFT_TARGETS by error<KtElement>()
|
||||||
val SUBTYPE_OF_HIDDEN_FROM_OBJC by error<KtElement>()
|
val SUBTYPE_OF_HIDDEN_FROM_OBJC by error<KtElement>()
|
||||||
|
|
||||||
|
val CANNOT_CHECK_FOR_FORWARD_DECLARATION by error<KtElement>() {
|
||||||
|
parameter<ConeKotlinType>("type")
|
||||||
|
}
|
||||||
|
val UNCHECKED_CAST_TO_FORWARD_DECLARATION by warning<KtElement> {
|
||||||
|
parameter<ConeKotlinType>("sourceType")
|
||||||
|
parameter<ConeKotlinType>("destinationType")
|
||||||
|
}
|
||||||
|
val FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT by error<KtElement> {
|
||||||
|
parameter<ConeKotlinType>("type")
|
||||||
|
}
|
||||||
|
val FORWARD_DECLARATION_AS_CLASS_LITERAL by error<KtElement> {
|
||||||
|
parameter<ConeKotlinType>("type")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ dependencies {
|
|||||||
implementation(project(":compiler:frontend"))
|
implementation(project(":compiler:frontend"))
|
||||||
implementation(project(":compiler:psi"))
|
implementation(project(":compiler:psi"))
|
||||||
|
|
||||||
|
compileOnly(project(":core:compiler.common.native"))
|
||||||
compileOnly(commonDependency("org.jetbrains.kotlin:kotlin-reflect")) { isTransitive = false }
|
compileOnly(commonDependency("org.jetbrains.kotlin:kotlin-reflect")) { isTransitive = false }
|
||||||
compileOnly(intellijCore())
|
compileOnly(intellijCore())
|
||||||
}
|
}
|
||||||
|
|||||||
+5
@@ -13,6 +13,7 @@ import org.jetbrains.kotlin.diagnostics.rendering.RootDiagnosticRendererFactory
|
|||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.*
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.*
|
||||||
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
|
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
||||||
import org.jetbrains.kotlin.name.FqName
|
import org.jetbrains.kotlin.name.FqName
|
||||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||||
import org.jetbrains.kotlin.psi.KtElement
|
import org.jetbrains.kotlin.psi.KtElement
|
||||||
@@ -47,6 +48,10 @@ object FirNativeErrors {
|
|||||||
val INVALID_OBJC_HIDES_TARGETS by error0<KtElement>()
|
val INVALID_OBJC_HIDES_TARGETS by error0<KtElement>()
|
||||||
val INVALID_REFINES_IN_SWIFT_TARGETS by error0<KtElement>()
|
val INVALID_REFINES_IN_SWIFT_TARGETS by error0<KtElement>()
|
||||||
val SUBTYPE_OF_HIDDEN_FROM_OBJC by error0<KtElement>()
|
val SUBTYPE_OF_HIDDEN_FROM_OBJC by error0<KtElement>()
|
||||||
|
val CANNOT_CHECK_FOR_FORWARD_DECLARATION by error1<KtElement, ConeKotlinType>()
|
||||||
|
val UNCHECKED_CAST_TO_FORWARD_DECLARATION by warning2<KtElement, ConeKotlinType, ConeKotlinType>()
|
||||||
|
val FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT by error1<KtElement, ConeKotlinType>()
|
||||||
|
val FORWARD_DECLARATION_AS_CLASS_LITERAL by error1<KtElement, ConeKotlinType>()
|
||||||
|
|
||||||
init {
|
init {
|
||||||
RootDiagnosticRendererFactory.registerFactory(FirNativeErrorsDefaultMessages)
|
RootDiagnosticRendererFactory.registerFactory(FirNativeErrorsDefaultMessages)
|
||||||
|
|||||||
+29
@@ -8,9 +8,14 @@ package org.jetbrains.kotlin.fir.analysis.diagnostics.native
|
|||||||
import org.jetbrains.kotlin.diagnostics.KtDiagnosticFactoryToRendererMap
|
import org.jetbrains.kotlin.diagnostics.KtDiagnosticFactoryToRendererMap
|
||||||
import org.jetbrains.kotlin.diagnostics.KtDiagnosticRenderers.TO_STRING
|
import org.jetbrains.kotlin.diagnostics.KtDiagnosticRenderers.TO_STRING
|
||||||
import org.jetbrains.kotlin.diagnostics.rendering.BaseDiagnosticRendererFactory
|
import org.jetbrains.kotlin.diagnostics.rendering.BaseDiagnosticRendererFactory
|
||||||
|
import org.jetbrains.kotlin.diagnostics.rendering.Renderers
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticRenderers
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticRenderers.SYMBOL
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticRenderers.SYMBOL
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticRenderers.SYMBOLS
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnosticRenderers.SYMBOLS
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CANNOT_CHECK_FOR_FORWARD_DECLARATION
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.EMPTY_OBJC_NAME
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.EMPTY_OBJC_NAME
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.FORWARD_DECLARATION_AS_CLASS_LITERAL
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_EXACT_OBJC_NAME
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_EXACT_OBJC_NAME
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_OBJC_NAME
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_OBJC_NAME
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_SHARED_IMMUTABLE_PROPERTY
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_SHARED_IMMUTABLE_PROPERTY
|
||||||
@@ -33,6 +38,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.REDU
|
|||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.NON_LITERAL_OBJC_NAME_ARG
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.NON_LITERAL_OBJC_NAME_ARG
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.SUBTYPE_OF_HIDDEN_FROM_OBJC
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.SUBTYPE_OF_HIDDEN_FROM_OBJC
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.THROWS_LIST_EMPTY
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.THROWS_LIST_EMPTY
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.UNCHECKED_CAST_TO_FORWARD_DECLARATION
|
||||||
|
|
||||||
object FirNativeErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
|
object FirNativeErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
|
||||||
override val MAP = KtDiagnosticFactoryToRendererMap("FIR").also { map ->
|
override val MAP = KtDiagnosticFactoryToRendererMap("FIR").also { map ->
|
||||||
@@ -79,5 +85,28 @@ object FirNativeErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
|
|||||||
map.put(MISSING_EXACT_OBJC_NAME, "Exact @ObjCName is required to have an ObjC name")
|
map.put(MISSING_EXACT_OBJC_NAME, "Exact @ObjCName is required to have an ObjC name")
|
||||||
map.put(NON_LITERAL_OBJC_NAME_ARG, "@ObjCName accepts only literal string and boolean values")
|
map.put(NON_LITERAL_OBJC_NAME_ARG, "@ObjCName accepts only literal string and boolean values")
|
||||||
map.put(SUBTYPE_OF_HIDDEN_FROM_OBJC, "Only @HiddenFromObjC declaration can be a subtype of @HiddenFromObjC declaration")
|
map.put(SUBTYPE_OF_HIDDEN_FROM_OBJC, "Only @HiddenFromObjC declaration can be a subtype of @HiddenFromObjC declaration")
|
||||||
|
|
||||||
|
|
||||||
|
map.put(
|
||||||
|
CANNOT_CHECK_FOR_FORWARD_DECLARATION,
|
||||||
|
"Cannot check for forward declaration: ''{0}''",
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
map.put(
|
||||||
|
UNCHECKED_CAST_TO_FORWARD_DECLARATION,
|
||||||
|
"Unchecked cast to forward declaration: ''{0}'' to ''{1}''",
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE,
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
map.put(
|
||||||
|
FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT,
|
||||||
|
"Cannot pass forward declaration ''{0}'' for reified type parameter",
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
map.put(
|
||||||
|
FORWARD_DECLARATION_AS_CLASS_LITERAL,
|
||||||
|
"Can't refer to forward declaration ''{0}'' from class literal",
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+34
@@ -0,0 +1,34 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||||
|
*/
|
||||||
|
|
||||||
|
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.expression.FirGetClassCallChecker
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.toRegularClassSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.native.checkers.forwardDeclarationKindOrNull
|
||||||
|
import org.jetbrains.kotlin.fir.expressions.*
|
||||||
|
import org.jetbrains.kotlin.fir.types.coneType
|
||||||
|
|
||||||
|
|
||||||
|
object FirNativeForwardDeclarationGetClassCallChecker : FirGetClassCallChecker() {
|
||||||
|
override fun check(expression: FirGetClassCall, context: CheckerContext, reporter: DiagnosticReporter) {
|
||||||
|
val declarationToCheck = expression.argument.typeRef.toRegularClassSymbol(context.session) ?: return
|
||||||
|
|
||||||
|
if (expression.arguments.firstOrNull() !is FirResolvedQualifier) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (declarationToCheck.forwardDeclarationKindOrNull() != null) {
|
||||||
|
reporter.reportOn(
|
||||||
|
expression.source,
|
||||||
|
FirNativeErrors.FORWARD_DECLARATION_AS_CLASS_LITERAL,
|
||||||
|
expression.argument.typeRef.coneType,
|
||||||
|
context,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+43
@@ -0,0 +1,43 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* 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.fir.analysis.native.checkers
|
||||||
|
|
||||||
|
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.expression.FirQualifiedAccessExpressionChecker
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors
|
||||||
|
import org.jetbrains.kotlin.fir.expressions.FirQualifiedAccessExpression
|
||||||
|
import org.jetbrains.kotlin.fir.references.toResolvedCallableSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.types.toConeTypeProjection
|
||||||
|
import org.jetbrains.kotlin.fir.types.toRegularClassSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.types.type
|
||||||
|
|
||||||
|
object FirNativeForwardDeclarationReifiedChecker : FirQualifiedAccessExpressionChecker() {
|
||||||
|
override fun check(expression: FirQualifiedAccessExpression, context: CheckerContext, reporter: DiagnosticReporter) {
|
||||||
|
val calleeReference = expression.calleeReference
|
||||||
|
val typeArguments = expression.typeArguments
|
||||||
|
val typeParameters = calleeReference.toResolvedCallableSymbol()?.typeParameterSymbols ?: return
|
||||||
|
|
||||||
|
val count = minOf(typeArguments.size, typeParameters.size)
|
||||||
|
for (index in 0 until count) {
|
||||||
|
val typeArgumentProjection = typeArguments.elementAt(index)
|
||||||
|
val source = typeArgumentProjection.source ?: calleeReference.source ?: continue
|
||||||
|
|
||||||
|
val typeArgument = typeArgumentProjection.toConeTypeProjection().type ?: continue
|
||||||
|
val typeParameter = typeParameters[index]
|
||||||
|
|
||||||
|
if (typeParameter.isReified && typeArgument.toRegularClassSymbol(context.session)?.forwardDeclarationKindOrNull() != null) {
|
||||||
|
reporter.reportOn(
|
||||||
|
source,
|
||||||
|
FirNativeErrors.FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT,
|
||||||
|
typeArgument,
|
||||||
|
context,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+59
@@ -0,0 +1,59 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* 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.fir.analysis.native.checkers
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
|
||||||
|
import org.jetbrains.kotlin.diagnostics.reportOn
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.*
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.expression.FirTypeOperatorCallChecker
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors
|
||||||
|
import org.jetbrains.kotlin.fir.expressions.*
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.lookupSuperTypes
|
||||||
|
import org.jetbrains.kotlin.fir.types.classId
|
||||||
|
import org.jetbrains.kotlin.fir.types.coneType
|
||||||
|
|
||||||
|
object FirNativeForwardDeclarationTypeOperatorChecker : FirTypeOperatorCallChecker() {
|
||||||
|
override fun check(expression: FirTypeOperatorCall, context: CheckerContext, reporter: DiagnosticReporter) {
|
||||||
|
val targetTypeRef = expression.conversionTypeRef
|
||||||
|
val declarationToCheck = targetTypeRef.toRegularClassSymbol(context.session) ?: return
|
||||||
|
val fwdKind = declarationToCheck.forwardDeclarationKindOrNull() ?: return
|
||||||
|
|
||||||
|
when (expression.operation) {
|
||||||
|
FirOperation.AS, FirOperation.SAFE_AS -> {
|
||||||
|
val sourceTypeRef = expression.argument.typeRef
|
||||||
|
val sourceClass = sourceTypeRef.toRegularClassSymbol(context.session)
|
||||||
|
// It can make sense to avoid warning if sourceClass is subclass of class with such property,
|
||||||
|
// but for the sake of simplicity, we don't do it now.
|
||||||
|
if (sourceClass != null && sourceClass.classKind == fwdKind.classKind && sourceClass.name == declarationToCheck.name) {
|
||||||
|
val supers = lookupSuperTypes(
|
||||||
|
symbol = sourceClass,
|
||||||
|
lookupInterfaces = true,
|
||||||
|
deep = true,
|
||||||
|
useSiteSession = context.session,
|
||||||
|
)
|
||||||
|
if (supers.any { it.classId == fwdKind.matchSuperClassId }) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
reporter.reportOn(
|
||||||
|
expression.source,
|
||||||
|
FirNativeErrors.UNCHECKED_CAST_TO_FORWARD_DECLARATION,
|
||||||
|
expression.argument.typeRef.coneType,
|
||||||
|
sourceTypeRef.coneType,
|
||||||
|
context,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
FirOperation.IS, FirOperation.NOT_IS -> reporter.reportOn(
|
||||||
|
expression.source,
|
||||||
|
FirNativeErrors.CANNOT_CHECK_FOR_FORWARD_DECLARATION,
|
||||||
|
targetTypeRef.coneType,
|
||||||
|
context,
|
||||||
|
)
|
||||||
|
else -> {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+5
@@ -11,7 +11,9 @@ import org.jetbrains.kotlin.diagnostics.reportOn
|
|||||||
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
|
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
|
||||||
import org.jetbrains.kotlin.fir.declarations.getAnnotationByClassId
|
import org.jetbrains.kotlin.fir.declarations.getAnnotationByClassId
|
||||||
|
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
||||||
import org.jetbrains.kotlin.name.ClassId
|
import org.jetbrains.kotlin.name.ClassId
|
||||||
|
import org.jetbrains.kotlin.name.NativeForwardDeclarationKind
|
||||||
|
|
||||||
fun DiagnosticReporter.reportIfHasAnnotation(
|
fun DiagnosticReporter.reportIfHasAnnotation(
|
||||||
declaration: FirDeclaration,
|
declaration: FirDeclaration,
|
||||||
@@ -24,3 +26,6 @@ fun DiagnosticReporter.reportIfHasAnnotation(
|
|||||||
reportOn(annotation.source, error, context)
|
reportOn(annotation.source, error, context)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun FirRegularClassSymbol.forwardDeclarationKindOrNull(): NativeForwardDeclarationKind? =
|
||||||
|
NativeForwardDeclarationKind.packageFqNameToKind[classId.packageFqName]
|
||||||
+12
@@ -5,7 +5,19 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.fir.analysis.native.checkers
|
package org.jetbrains.kotlin.fir.analysis.native.checkers
|
||||||
|
|
||||||
|
import FirNativeForwardDeclarationGetClassCallChecker
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.expression.ExpressionCheckers
|
import org.jetbrains.kotlin.fir.analysis.checkers.expression.ExpressionCheckers
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.expression.FirGetClassCallChecker
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.expression.FirQualifiedAccessExpressionChecker
|
||||||
|
|
||||||
object NativeExpressionCheckers : ExpressionCheckers() {
|
object NativeExpressionCheckers : ExpressionCheckers() {
|
||||||
|
override val typeOperatorCallCheckers = setOf(
|
||||||
|
FirNativeForwardDeclarationTypeOperatorChecker,
|
||||||
|
)
|
||||||
|
override val getClassCallCheckers = setOf(
|
||||||
|
FirNativeForwardDeclarationGetClassCallChecker
|
||||||
|
)
|
||||||
|
override val qualifiedAccessExpressionCheckers = setOf(
|
||||||
|
FirNativeForwardDeclarationReifiedChecker
|
||||||
|
)
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,104 @@
|
|||||||
|
// FIR_IDENTICAL
|
||||||
|
// WITH_STDLIB
|
||||||
|
|
||||||
|
// FILE: stdlib.kt
|
||||||
|
|
||||||
|
package kotlinx.cinterop
|
||||||
|
|
||||||
|
abstract class CStructVar
|
||||||
|
interface ObjCObject
|
||||||
|
abstract class ObjCObjectBase : ObjCObject
|
||||||
|
|
||||||
|
// FILE: cnames.kt
|
||||||
|
|
||||||
|
package cnames.structs
|
||||||
|
|
||||||
|
class FwdStruct {}
|
||||||
|
|
||||||
|
// FILE: objcnamesClasses.kt
|
||||||
|
|
||||||
|
package objcnames.classes
|
||||||
|
|
||||||
|
class FwdObjcClass {}
|
||||||
|
|
||||||
|
// FILE: objcnamesProtocols.kt
|
||||||
|
|
||||||
|
package objcnames.protocols
|
||||||
|
|
||||||
|
interface FwdProtocol {}
|
||||||
|
|
||||||
|
// FILE: lib.kt
|
||||||
|
|
||||||
|
package lib
|
||||||
|
|
||||||
|
import kotlinx.cinterop.*
|
||||||
|
|
||||||
|
class FwdStruct : CStructVar()
|
||||||
|
class FwdObjcClass : ObjCObjectBase()
|
||||||
|
interface FwdProtocol : ObjCObject
|
||||||
|
|
||||||
|
// FILE: lib2.kt
|
||||||
|
|
||||||
|
package lib2
|
||||||
|
|
||||||
|
class FwdStruct
|
||||||
|
class FwdObjcClass
|
||||||
|
interface FwdProtocol
|
||||||
|
|
||||||
|
|
||||||
|
// FILE: main.kt
|
||||||
|
|
||||||
|
// this inspections differs in K1/K2, but unrelated to what is tested in this test
|
||||||
|
@file:Suppress("CAST_NEVER_SUCCEEDS", "UNUSED_PARAMETER", "UNUSED_EXPRESSION", "UNUSED_VARIABLE", "INCOMPATIBLE_TYPES")
|
||||||
|
|
||||||
|
fun testUnckeckedAsFromAny(x: Any) {
|
||||||
|
<!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as? cnames.structs.FwdStruct<!>
|
||||||
|
<!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as? objcnames.classes.FwdObjcClass<!>
|
||||||
|
<!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as? objcnames.protocols.FwdProtocol<!>
|
||||||
|
if (1 > 0) { <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as cnames.structs.FwdStruct<!> }
|
||||||
|
if (1 > 0) { <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as objcnames.classes.FwdObjcClass<!> }
|
||||||
|
if (1 > 0) { <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as objcnames.protocols.FwdProtocol<!> }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun testIs(x: Any) : Int {
|
||||||
|
return when {
|
||||||
|
<!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is cnames.structs.FwdStruct<!> -> 1
|
||||||
|
<!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is objcnames.classes.FwdObjcClass<!> -> 2
|
||||||
|
<!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is objcnames.protocols.FwdProtocol<!> -> 3
|
||||||
|
else -> 4
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun testIs2(x: lib.FwdStruct) = <!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is cnames.structs.FwdStruct<!>
|
||||||
|
fun testIs3(x: lib.FwdObjcClass) = <!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is objcnames.classes.FwdObjcClass<!>
|
||||||
|
fun testIs4(x: lib.FwdProtocol) = <!CANNOT_CHECK_FOR_FORWARD_DECLARATION!>x is objcnames.protocols.FwdProtocol<!>
|
||||||
|
|
||||||
|
|
||||||
|
fun testClass1(x : cnames.structs.FwdStruct) = x::class
|
||||||
|
fun testClass2(x : objcnames.classes.FwdObjcClass) = x::class
|
||||||
|
fun testClass3(x : objcnames.protocols.FwdProtocol) = x::class
|
||||||
|
fun testClass4() {
|
||||||
|
<!FORWARD_DECLARATION_AS_CLASS_LITERAL!>cnames.structs.FwdStruct::class<!>
|
||||||
|
<!FORWARD_DECLARATION_AS_CLASS_LITERAL!>objcnames.classes.FwdObjcClass::class<!>
|
||||||
|
<!FORWARD_DECLARATION_AS_CLASS_LITERAL!>objcnames.protocols.FwdProtocol::class<!>
|
||||||
|
}
|
||||||
|
inline fun <reified T> inlineF(x: T) {}
|
||||||
|
|
||||||
|
fun testInline1(x : cnames.structs.FwdStruct) = <!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>(x)
|
||||||
|
fun testInline2(x : objcnames.classes.FwdObjcClass) = <!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>(x)
|
||||||
|
fun testInline3(x : objcnames.protocols.FwdProtocol) = <!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>(x)
|
||||||
|
fun testInline4() {
|
||||||
|
val a : (cnames.structs.FwdStruct) -> Unit = ::<!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>
|
||||||
|
val b : (objcnames.classes.FwdObjcClass) -> Unit = ::<!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>
|
||||||
|
val c : (objcnames.protocols.FwdProtocol) -> Unit = ::<!FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT!>inlineF<!>
|
||||||
|
}
|
||||||
|
|
||||||
|
fun testCheckedAs1(x : lib.FwdStruct) = x as cnames.structs.FwdStruct
|
||||||
|
fun testCheckedAs2(x : lib.FwdObjcClass) = x as objcnames.classes.FwdObjcClass
|
||||||
|
fun testCheckedAs3(x : lib.FwdProtocol) = x as objcnames.protocols.FwdProtocol
|
||||||
|
|
||||||
|
fun testUnCheckedAs1(x : lib2.FwdStruct) = <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as cnames.structs.FwdStruct<!>
|
||||||
|
fun testUnCheckedAs2(x : lib2.FwdObjcClass) = <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as objcnames.classes.FwdObjcClass<!>
|
||||||
|
fun testUnCheckedAs3(x : lib2.FwdProtocol) = <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as objcnames.protocols.FwdProtocol<!>
|
||||||
|
|
||||||
|
fun testUnCheckedAs4(x : lib.FwdStruct) = <!UNCHECKED_CAST_TO_FORWARD_DECLARATION!>x as objcnames.classes.FwdObjcClass<!>
|
||||||
@@ -6,6 +6,7 @@ plugins {
|
|||||||
dependencies {
|
dependencies {
|
||||||
compileOnly(project(":compiler:frontend"))
|
compileOnly(project(":compiler:frontend"))
|
||||||
compileOnly(project(":compiler:frontend.java"))
|
compileOnly(project(":compiler:frontend.java"))
|
||||||
|
compileOnly(project(":core:compiler.common.native"))
|
||||||
compileOnly(intellijCore())
|
compileOnly(intellijCore())
|
||||||
api(project(":native:kotlin-native-utils"))
|
api(project(":native:kotlin-native-utils"))
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,10 +5,15 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.descriptors.konan
|
package org.jetbrains.kotlin.descriptors.konan
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
|
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
|
||||||
|
import org.jetbrains.kotlin.descriptors.PackageFragmentDescriptor
|
||||||
import org.jetbrains.kotlin.konan.library.KONAN_STDLIB_NAME
|
import org.jetbrains.kotlin.konan.library.KONAN_STDLIB_NAME
|
||||||
|
import org.jetbrains.kotlin.name.NativeForwardDeclarationKind
|
||||||
import org.jetbrains.kotlin.name.Name
|
import org.jetbrains.kotlin.name.Name
|
||||||
|
|
||||||
val NATIVE_STDLIB_MODULE_NAME = Name.special("<$KONAN_STDLIB_NAME>")
|
val NATIVE_STDLIB_MODULE_NAME = Name.special("<$KONAN_STDLIB_NAME>")
|
||||||
|
|
||||||
fun ModuleDescriptor.isNativeStdlib() = name == NATIVE_STDLIB_MODULE_NAME
|
fun ModuleDescriptor.isNativeStdlib() = name == NATIVE_STDLIB_MODULE_NAME
|
||||||
|
fun ClassDescriptor.getForwardDeclarationKindOrNull() =
|
||||||
|
NativeForwardDeclarationKind.packageFqNameToKind[(containingDeclaration as? PackageFragmentDescriptor)?.fqName]
|
||||||
+21
@@ -69,6 +69,27 @@ private val DIAGNOSTIC_FACTORY_TO_RENDERER by lazy {
|
|||||||
ErrorsNative.SUBTYPE_OF_HIDDEN_FROM_OBJC,
|
ErrorsNative.SUBTYPE_OF_HIDDEN_FROM_OBJC,
|
||||||
"Only @HiddenFromObjC declaration can be a subtype of @HiddenFromObjC declaration"
|
"Only @HiddenFromObjC declaration can be a subtype of @HiddenFromObjC declaration"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
put(
|
||||||
|
ErrorsNative.CANNOT_CHECK_FOR_FORWARD_DECLARATION,
|
||||||
|
"Cannot check for forward declaration: ''{0}''",
|
||||||
|
Renderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
put(ErrorsNative.UNCHECKED_CAST_TO_FORWARD_DECLARATION,
|
||||||
|
"Unchecked cast to forward declaration: ''{0}'' to ''{1}''",
|
||||||
|
Renderers.RENDER_TYPE,
|
||||||
|
Renderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
put(
|
||||||
|
ErrorsNative.FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT,
|
||||||
|
"Cannot pass forward declaration ''{0}'' for reified type parameter",
|
||||||
|
Renderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
put(
|
||||||
|
ErrorsNative.FORWARD_DECLARATION_AS_CLASS_LITERAL,
|
||||||
|
"Can't refer to forward declaration ''{0}'' from class literal",
|
||||||
|
Renderers.RENDER_TYPE
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import org.jetbrains.kotlin.diagnostics.*
|
|||||||
import org.jetbrains.kotlin.name.FqName
|
import org.jetbrains.kotlin.name.FqName
|
||||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||||
import org.jetbrains.kotlin.psi.KtElement
|
import org.jetbrains.kotlin.psi.KtElement
|
||||||
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
|
||||||
object ErrorsNative {
|
object ErrorsNative {
|
||||||
@JvmField
|
@JvmField
|
||||||
@@ -60,6 +61,14 @@ object ErrorsNative {
|
|||||||
val INVALID_REFINES_IN_SWIFT_TARGETS = DiagnosticFactory0.create<KtElement>(Severity.ERROR)
|
val INVALID_REFINES_IN_SWIFT_TARGETS = DiagnosticFactory0.create<KtElement>(Severity.ERROR)
|
||||||
@JvmField
|
@JvmField
|
||||||
val SUBTYPE_OF_HIDDEN_FROM_OBJC = DiagnosticFactory0.create<KtElement>(Severity.ERROR)
|
val SUBTYPE_OF_HIDDEN_FROM_OBJC = DiagnosticFactory0.create<KtElement>(Severity.ERROR)
|
||||||
|
@JvmField
|
||||||
|
val CANNOT_CHECK_FOR_FORWARD_DECLARATION = DiagnosticFactory1.create<PsiElement, KotlinType>(Severity.ERROR)
|
||||||
|
@JvmField
|
||||||
|
val UNCHECKED_CAST_TO_FORWARD_DECLARATION = DiagnosticFactory2.create<PsiElement, KotlinType, KotlinType>(Severity.WARNING)
|
||||||
|
@JvmField
|
||||||
|
val FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT = DiagnosticFactory1.create<PsiElement, KotlinType>(Severity.ERROR)
|
||||||
|
@JvmField
|
||||||
|
val FORWARD_DECLARATION_AS_CLASS_LITERAL = DiagnosticFactory1.create<PsiElement, KotlinType>(Severity.ERROR)
|
||||||
|
|
||||||
init {
|
init {
|
||||||
Errors.Initializer.initializeFactoryNames(ErrorsNative::class.java)
|
Errors.Initializer.initializeFactoryNames(ErrorsNative::class.java)
|
||||||
|
|||||||
+56
@@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* 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.resolve.konan.diagnostics
|
||||||
|
|
||||||
|
import com.intellij.psi.PsiElement
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
|
import org.jetbrains.kotlin.descriptors.konan.getForwardDeclarationKindOrNull
|
||||||
|
import org.jetbrains.kotlin.psi.KtClassLiteralExpression
|
||||||
|
import org.jetbrains.kotlin.resolve.BindingTrace
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.RttiExpressionChecker
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.RttiExpressionInformation
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.RttiOperation
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.context.ResolutionContext
|
||||||
|
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameSafe
|
||||||
|
import org.jetbrains.kotlin.resolve.descriptorUtil.getAllSuperClassifiers
|
||||||
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
import org.jetbrains.kotlin.types.expressions.ClassLiteralChecker
|
||||||
|
|
||||||
|
class NativeForwardDeclarationRttiChecker : RttiExpressionChecker, ClassLiteralChecker {
|
||||||
|
override fun check(rttiInformation: RttiExpressionInformation, reportOn: PsiElement, trace: BindingTrace) {
|
||||||
|
val sourceType = rttiInformation.sourceType
|
||||||
|
val targetType = rttiInformation.targetType
|
||||||
|
val targetDescriptor = targetType?.constructor?.declarationDescriptor
|
||||||
|
if (sourceType != null && targetDescriptor is ClassDescriptor) {
|
||||||
|
val kind = targetDescriptor.getForwardDeclarationKindOrNull() ?: return
|
||||||
|
when (rttiInformation.operation) {
|
||||||
|
RttiOperation.IS,
|
||||||
|
RttiOperation.NOT_IS -> trace.report(ErrorsNative.CANNOT_CHECK_FOR_FORWARD_DECLARATION.on(reportOn, targetType))
|
||||||
|
|
||||||
|
RttiOperation.AS,
|
||||||
|
RttiOperation.SAFE_AS -> {
|
||||||
|
// It can make sense to avoid warning if sourceClass is subclass of class with such property,
|
||||||
|
// but for the sake of simplicity, we don't do it now.
|
||||||
|
val sourceDescriptor = sourceType.constructor.declarationDescriptor as? ClassDescriptor
|
||||||
|
val isAllowedCast = sourceDescriptor != null &&
|
||||||
|
sourceDescriptor.name == targetDescriptor.name &&
|
||||||
|
sourceDescriptor.kind == kind.classKind &&
|
||||||
|
sourceDescriptor.getAllSuperClassifiers().any { it.fqNameSafe == kind.matchSuperClassFqName }
|
||||||
|
if (!isAllowedCast) {
|
||||||
|
trace.report(ErrorsNative.UNCHECKED_CAST_TO_FORWARD_DECLARATION.on(reportOn, sourceType, targetType))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun check(expression: KtClassLiteralExpression, type: KotlinType, context: ResolutionContext<*>) {
|
||||||
|
val descriptor = type.constructor.declarationDescriptor as? ClassDescriptor
|
||||||
|
if (descriptor?.getForwardDeclarationKindOrNull() != null) {
|
||||||
|
context.trace.report(ErrorsNative.FORWARD_DECLARATION_AS_CLASS_LITERAL.on(expression, type))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+33
@@ -0,0 +1,33 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* 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.resolve.konan.diagnostics
|
||||||
|
|
||||||
|
import com.intellij.psi.PsiElement
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.CallChecker
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.CallCheckerContext
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
|
||||||
|
import org.jetbrains.kotlin.descriptors.konan.*
|
||||||
|
|
||||||
|
class NativeReifiedForwardDeclarationChecker : CallChecker {
|
||||||
|
override fun check(resolvedCall: ResolvedCall<*>, reportOn: PsiElement, context: CallCheckerContext) {
|
||||||
|
val typeArgumentList = resolvedCall.call.typeArgumentList?.arguments
|
||||||
|
for ((typeParam, typeArg) in resolvedCall.typeArguments) {
|
||||||
|
if (!typeParam.isReified) continue
|
||||||
|
|
||||||
|
val typeArgDescriptor = typeArg.constructor.declarationDescriptor
|
||||||
|
if (typeArgDescriptor is ClassDescriptor && typeArgDescriptor.getForwardDeclarationKindOrNull() != null) {
|
||||||
|
val typeArgumentPsi = if (typeArgumentList != null) {
|
||||||
|
typeArgumentList[typeParam.index].typeReference
|
||||||
|
} else {
|
||||||
|
resolvedCall.call.calleeExpression
|
||||||
|
}
|
||||||
|
|
||||||
|
context.trace.report(ErrorsNative.FORWARD_DECLARATION_AS_REIFIED_TYPE_ARGUMENT.on(typeArgumentPsi!!, typeArg))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+4
-2
@@ -21,19 +21,21 @@ import org.jetbrains.kotlin.resolve.konan.diagnostics.*
|
|||||||
object NativePlatformConfigurator : PlatformConfiguratorBase(
|
object NativePlatformConfigurator : PlatformConfiguratorBase(
|
||||||
additionalCallCheckers = listOf(
|
additionalCallCheckers = listOf(
|
||||||
SuperCallWithDefaultArgumentsChecker(),
|
SuperCallWithDefaultArgumentsChecker(),
|
||||||
LateinitIntrinsicApplicabilityChecker(isWarningInPre19 = true)
|
LateinitIntrinsicApplicabilityChecker(isWarningInPre19 = true),
|
||||||
|
NativeReifiedForwardDeclarationChecker(),
|
||||||
),
|
),
|
||||||
additionalDeclarationCheckers = listOf(
|
additionalDeclarationCheckers = listOf(
|
||||||
NativeThrowsChecker, NativeSharedImmutableChecker,
|
NativeThrowsChecker, NativeSharedImmutableChecker,
|
||||||
NativeThreadLocalChecker,
|
NativeThreadLocalChecker,
|
||||||
NativeObjCNameChecker, NativeObjCNameOverridesChecker,
|
NativeObjCNameChecker, NativeObjCNameOverridesChecker,
|
||||||
NativeObjCRefinementChecker, NativeObjCRefinementAnnotationChecker,
|
NativeObjCRefinementChecker, NativeObjCRefinementAnnotationChecker,
|
||||||
NativeObjCRefinementOverridesChecker, NativeHiddenFromObjCInheritanceChecker
|
NativeObjCRefinementOverridesChecker, NativeHiddenFromObjCInheritanceChecker,
|
||||||
)
|
)
|
||||||
) {
|
) {
|
||||||
override fun configureModuleComponents(container: StorageComponentContainer) {
|
override fun configureModuleComponents(container: StorageComponentContainer) {
|
||||||
container.useInstance(NativeInliningRule)
|
container.useInstance(NativeInliningRule)
|
||||||
container.useImpl<NativeIdentifierChecker>()
|
container.useImpl<NativeIdentifierChecker>()
|
||||||
|
container.useImpl<NativeForwardDeclarationRttiChecker>()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun configureModuleDependentCheckers(container: StorageComponentContainer) {
|
override fun configureModuleDependentCheckers(container: StorageComponentContainer) {
|
||||||
|
|||||||
+6
@@ -30,6 +30,12 @@ public class DiagnosticsNativeTestGenerated extends AbstractDiagnosticsNativeTes
|
|||||||
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("forwardDeclarations.kt")
|
||||||
|
public void testForwardDeclarations() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/nativeTests/forwardDeclarations.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("identifiers.kt")
|
@TestMetadata("identifiers.kt")
|
||||||
public void testIdentifiers() throws Exception {
|
public void testIdentifiers() throws Exception {
|
||||||
|
|||||||
+6
@@ -34,6 +34,12 @@ public class FirLightTreeOldFrontendNativeDiagnosticsTestGenerated extends Abstr
|
|||||||
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("forwardDeclarations.kt")
|
||||||
|
public void testForwardDeclarations() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/nativeTests/forwardDeclarations.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("identifiers.kt")
|
@TestMetadata("identifiers.kt")
|
||||||
public void testIdentifiers() throws Exception {
|
public void testIdentifiers() throws Exception {
|
||||||
|
|||||||
+6
@@ -34,6 +34,12 @@ public class FirPsiOldFrontendNativeDiagnosticsTestGenerated extends AbstractFir
|
|||||||
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
runTest("compiler/testData/diagnostics/nativeTests/cloneableInNative.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("forwardDeclarations.kt")
|
||||||
|
public void testForwardDeclarations() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/nativeTests/forwardDeclarations.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("identifiers.kt")
|
@TestMetadata("identifiers.kt")
|
||||||
public void testIdentifiers() throws Exception {
|
public void testIdentifiers() throws Exception {
|
||||||
|
|||||||
Reference in New Issue
Block a user