[ObjCInterop] Implement @ObjCSignatureOverride

This annotation leads to conflicting overloads error supression,
in case where several function with the same argument types,
but different argument names are inherited from ObjC class.

We need to implement it in both K1 and K2 to make the IDE experience
better.
But the annotation itself wouldn't be available in K1.

    ^KT-61323
This commit is contained in:
Pavel Kunyavskiy
2024-01-18 14:56:57 +01:00
committed by Space Team
parent 77eee0d3fc
commit 6e8a7d4662
30 changed files with 698 additions and 41 deletions
@@ -103,5 +103,9 @@ object NATIVE_DIAGNOSTICS_LIST : DiagnosticList("FirNativeErrors") {
val CONSTRUCTOR_MATCHES_SEVERAL_SUPER_CONSTRUCTORS by error<KtElement>() {
parameter<FqName>("annotation")
}
val CONFLICTING_OBJC_OVERLOADS by error<PsiElement>() {
parameter<Collection<Symbol>>("conflictingOverloads")
}
val INAPPLICABLE_OBJC_OVERRIDE by error<PsiElement>()
}
}
@@ -62,6 +62,8 @@ object FirNativeErrors {
val CONSTRUCTOR_OVERRIDES_ALREADY_OVERRIDDEN_OBJC_INITIALIZER: KtDiagnosticFactory1<FqName> by error1<KtElement, FqName>()
val CONSTRUCTOR_DOES_NOT_OVERRIDE_ANY_SUPER_CONSTRUCTOR: KtDiagnosticFactory1<FqName> by error1<KtElement, FqName>()
val CONSTRUCTOR_MATCHES_SEVERAL_SUPER_CONSTRUCTORS: KtDiagnosticFactory1<FqName> by error1<KtElement, FqName>()
val CONFLICTING_OBJC_OVERLOADS: KtDiagnosticFactory1<Collection<FirBasedSymbol<*>>> by error1<PsiElement, Collection<FirBasedSymbol<*>>>()
val INAPPLICABLE_OBJC_OVERRIDE: KtDiagnosticFactory0 by error0<PsiElement>()
init {
RootDiagnosticRendererFactory.registerFactory(FirNativeErrorsDefaultMessages)
@@ -12,6 +12,7 @@ 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.SYMBOLS
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CANNOT_CHECK_FOR_FORWARD_DECLARATION
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CONFLICTING_OBJC_OVERLOADS
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CONSTRUCTOR_DOES_NOT_OVERRIDE_ANY_SUPER_CONSTRUCTOR
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CONSTRUCTOR_MATCHES_SEVERAL_SUPER_CONSTRUCTORS
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.CONSTRUCTOR_OVERRIDES_ALREADY_OVERRIDDEN_OBJC_INITIALIZER
@@ -20,6 +21,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.FORW
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_OBJC_NAME
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_OBJC_OVERRIDE
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_TOP_LEVEL
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors.INAPPLICABLE_THREAD_LOCAL
@@ -145,5 +147,14 @@ object FirNativeErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
"Constructor with ''@{0}'' matches more than one of super constructors.",
TO_STRING
)
map.put(
CONFLICTING_OBJC_OVERLOADS,
"Conflicting overloads: {0}. Add @ObjCSignatureOverride to allow collision for functions inherited from Objective-C.",
SYMBOLS
)
map.put(
INAPPLICABLE_OBJC_OVERRIDE,
"@ObjCSignatureOverride is only allowed on methods overriding methods from Objective-C.",
)
}
}
@@ -0,0 +1,74 @@
/*
* Copyright 2010-2024 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.config.LanguageFeature
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.diagnostics.KtDiagnosticFactory1
import org.jetbrains.kotlin.diagnostics.reportOn
import org.jetbrains.kotlin.fir.analysis.checkers.MppCheckerKind
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
import org.jetbrains.kotlin.fir.analysis.checkers.declaration.FirFunctionChecker
import org.jetbrains.kotlin.fir.analysis.checkers.declaration.PlatformConflictDeclarationsDiagnosticDispatcher
import org.jetbrains.kotlin.fir.analysis.diagnostics.native.FirNativeErrors
import org.jetbrains.kotlin.fir.backend.native.interop.getObjCMethodInfoFromOverriddenFunctions
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.name.NativeStandardInteropNames.Annotations.objCSignatureOverrideClassId
import org.jetbrains.kotlin.utils.SmartSet
private fun FirFunctionSymbol<*>.isInheritedFromObjc(context: CheckerContext): Boolean {
return getObjCMethodInfoFromOverriddenFunctions(context.session, context.scopeSession) != null
}
/**
* This function basically checks that these two functions have different objective-C signature.
*
* This signature consists of function name and parameter names except first.
*
* So we ignore the first parameter name, but check others
*/
private fun FirFunctionSymbol<*>.hasDifferentParameterNames(other: FirFunctionSymbol<*>) : Boolean {
return valueParameterSymbols.drop(1).map { it.name } != other.valueParameterSymbols.drop(1).map { it.name }
}
object NativeConflictDeclarationsDiagnosticDispatcher : PlatformConflictDeclarationsDiagnosticDispatcher {
override fun getDiagnostic(
conflictingDeclaration: FirBasedSymbol<*>,
symbols: SmartSet<FirBasedSymbol<*>>,
context: CheckerContext
): KtDiagnosticFactory1<Collection<FirBasedSymbol<*>>>? {
if (context.languageVersionSettings.supportsFeature(LanguageFeature.ObjCSignatureOverrideAnnotation)) {
if (conflictingDeclaration is FirFunctionSymbol<*> && symbols.all { it is FirFunctionSymbol<*> }) {
if (conflictingDeclaration.isInheritedFromObjc(context) && symbols.all { (it as FirFunctionSymbol<*>).isInheritedFromObjc(context) }) {
if (symbols.all { (it as FirFunctionSymbol<*>).hasDifferentParameterNames(conflictingDeclaration) }) {
if (conflictingDeclaration.hasAnnotation(objCSignatureOverrideClassId, context.session)) {
return null
} else {
return FirNativeErrors.CONFLICTING_OBJC_OVERLOADS
}
}
}
}
}
return PlatformConflictDeclarationsDiagnosticDispatcher.DEFAULT.getDiagnostic(conflictingDeclaration, symbols, context)
}
}
object FirNativeObjcOverrideApplicabilityChecker : FirFunctionChecker(MppCheckerKind.Platform) {
override fun check(
declaration: FirFunction,
context: CheckerContext,
reporter: DiagnosticReporter,
) {
if (declaration.hasAnnotation(objCSignatureOverrideClassId, context.session)) {
if (!declaration.symbol.isInheritedFromObjc(context)) {
reporter.reportOn(declaration.getAnnotationByClassId(objCSignatureOverrideClassId, context.session)?.source, FirNativeErrors.INAPPLICABLE_OBJC_OVERRIDE, context)
}
}
}
}
@@ -15,7 +15,12 @@ object NativeDeclarationCheckers : DeclarationCheckers() {
FirNativeSharedImmutableChecker,
FirNativeThreadLocalChecker,
FirNativeIdentifierChecker,
FirNativeObjCNameChecker
FirNativeObjCNameChecker,
)
override val functionCheckers: Set<FirFunctionChecker>
get() = setOf(
FirNativeObjcOverrideApplicabilityChecker
)
override val callableDeclarationCheckers: Set<FirCallableDeclarationChecker>
@@ -679,6 +679,8 @@ val FIR_NON_SUPPRESSIBLE_ERROR_NAMES: Set<String> = setOf(
"CONSTRUCTOR_OVERRIDES_ALREADY_OVERRIDDEN_OBJC_INITIALIZER",
"CONSTRUCTOR_DOES_NOT_OVERRIDE_ANY_SUPER_CONSTRUCTOR",
"CONSTRUCTOR_MATCHES_SEVERAL_SUPER_CONSTRUCTORS",
"CONFLICTING_OBJC_OVERLOADS",
"INAPPLICABLE_OBJC_OVERRIDE",
"NESTED_EXTERNAL_DECLARATION",
"WRONG_EXTERNAL_DECLARATION",
"NESTED_CLASS_IN_EXTERNAL_INTERFACE",
@@ -6,9 +6,13 @@
package org.jetbrains.kotlin.fir.analysis.checkers.declaration
import org.jetbrains.kotlin.KtFakeSourceElementKind
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.diagnostics.KtDiagnosticFactory1
import org.jetbrains.kotlin.diagnostics.reportOn
import org.jetbrains.kotlin.fir.FirNameConflictsTrackerComponent
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.FirSessionComponent
import org.jetbrains.kotlin.fir.analysis.checkers.*
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
@@ -18,14 +22,43 @@ import org.jetbrains.kotlin.fir.scopes.impl.FirPackageMemberScope
import org.jetbrains.kotlin.fir.scopes.impl.PACKAGE_MEMBER
import org.jetbrains.kotlin.fir.scopes.impl.typeAliasForConstructor
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirConstructorSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.*
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.SpecialNames
import org.jetbrains.kotlin.utils.SmartSet
interface PlatformConflictDeclarationsDiagnosticDispatcher : FirSessionComponent {
fun getDiagnostic(
conflictingDeclaration: FirBasedSymbol<*>,
symbols: SmartSet<FirBasedSymbol<*>>,
context: CheckerContext
): KtDiagnosticFactory1<Collection<FirBasedSymbol<*>>>?
object DEFAULT : PlatformConflictDeclarationsDiagnosticDispatcher {
override fun getDiagnostic(
conflictingDeclaration: FirBasedSymbol<*>,
symbols: SmartSet<FirBasedSymbol<*>>,
context: CheckerContext
): KtDiagnosticFactory1<Collection<FirBasedSymbol<*>>> {
return when {
conflictingDeclaration is FirNamedFunctionSymbol || conflictingDeclaration is FirConstructorSymbol -> {
FirErrors.CONFLICTING_OVERLOADS
}
conflictingDeclaration is FirClassLikeSymbol<*> &&
conflictingDeclaration.getContainingClassSymbol(context.session) == null &&
symbols.any { it is FirClassLikeSymbol<*> } -> {
FirErrors.PACKAGE_OR_CLASSIFIER_REDECLARATION
}
else -> {
FirErrors.REDECLARATION
}
}
}
}
}
val FirSession.conflictDeclarationsDiagnosticDispatcher: PlatformConflictDeclarationsDiagnosticDispatcher? by FirSession.nullableSessionComponentAccessor()
object FirConflictsDeclarationChecker : FirBasicDeclarationChecker(MppCheckerKind.Platform) {
override fun check(declaration: FirDeclaration, context: CheckerContext, reporter: DiagnosticReporter) {
when (declaration) {
@@ -90,21 +123,16 @@ object FirConflictsDeclarationChecker : FirBasicDeclarationChecker(MppCheckerKin
conflictingDeclaration.isPrimaryConstructor && symbols.all { it.isPrimaryConstructor }
) return@forEach
when {
symbols.singleOrNull()?.let { isExpectAndActual(conflictingDeclaration, it) } == true -> {
reporter.reportOn(source, FirErrors.EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE, conflictingDeclaration, context)
}
conflictingDeclaration is FirNamedFunctionSymbol || conflictingDeclaration is FirConstructorSymbol -> {
reporter.reportOn(source, FirErrors.CONFLICTING_OVERLOADS, symbols, context)
}
conflictingDeclaration is FirClassLikeSymbol<*> &&
conflictingDeclaration.getContainingClassSymbol(context.session) == null &&
symbols.any { it is FirClassLikeSymbol<*> } -> {
reporter.reportOn(source, FirErrors.PACKAGE_OR_CLASSIFIER_REDECLARATION, symbols, context)
}
else -> {
reporter.reportOn(source, FirErrors.REDECLARATION, symbols, context)
}
if (symbols.singleOrNull()?.let { isExpectAndActual(conflictingDeclaration, it) } == true) {
reporter.reportOn(source, FirErrors.EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE, conflictingDeclaration, context)
return@forEach
}
val dispatcher = context.session.conflictDeclarationsDiagnosticDispatcher ?: PlatformConflictDeclarationsDiagnosticDispatcher.DEFAULT
val factory = dispatcher.getDiagnostic(conflictingDeclaration, symbols, context)
if (factory != null) {
reporter.reportOn(source, factory, symbols, context)
}
}
}
@@ -7,23 +7,25 @@ package org.jetbrains.kotlin.fir.session
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.analysis.checkers.declaration.PlatformConflictDeclarationsDiagnosticDispatcher
import org.jetbrains.kotlin.fir.analysis.native.checkers.FirNativeCastChecker
import org.jetbrains.kotlin.fir.analysis.native.checkers.NativeConflictDeclarationsDiagnosticDispatcher
import org.jetbrains.kotlin.fir.backend.native.FirNativeClassMapper
import org.jetbrains.kotlin.fir.backend.native.FirNativeOverrideChecker
import org.jetbrains.kotlin.fir.checkers.registerNativeCheckers
import org.jetbrains.kotlin.fir.deserialization.ModuleDataProvider
import org.jetbrains.kotlin.fir.extensions.FirExtensionRegistrar
import org.jetbrains.kotlin.fir.java.FirProjectSessionProvider
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirBuiltinSyntheticFunctionInterfaceProvider
import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider
import org.jetbrains.kotlin.fir.scopes.FirOverrideChecker
import org.jetbrains.kotlin.fir.scopes.FirPlatformClassMapper
import org.jetbrains.kotlin.fir.session.FirSessionFactoryHelper.registerDefaultComponents
import org.jetbrains.kotlin.library.isNativeStdlib
import org.jetbrains.kotlin.library.metadata.impl.KlibResolvedModuleDescriptorsFactoryImpl.Companion.FORWARD_DECLARATIONS_MODULE_NAME
import org.jetbrains.kotlin.library.metadata.resolver.KotlinResolvedLibrary
import org.jetbrains.kotlin.name.Name
object FirNativeSessionFactory : FirAbstractSessionFactory() {
@OptIn(SessionConfiguration::class)
fun createLibrarySession(
mainModuleName: Name,
resolvedLibraries: List<KotlinResolvedLibrary>,
@@ -63,7 +65,6 @@ object FirNativeSessionFactory : FirAbstractSessionFactory() {
})
}
@OptIn(SessionConfiguration::class)
fun createModuleBasedSession(
moduleData: FirModuleData,
sessionProvider: FirProjectSessionProvider,
@@ -102,5 +103,7 @@ object FirNativeSessionFactory : FirAbstractSessionFactory() {
fun FirSession.registerNativeComponents() {
register(FirPlatformClassMapper::class, FirNativeClassMapper())
register(FirPlatformSpecificCastChecker::class, FirNativeCastChecker)
register(PlatformConflictDeclarationsDiagnosticDispatcher::class, NativeConflictDeclarationsDiagnosticDispatcher)
register(FirOverrideChecker::class, FirNativeOverrideChecker(this))
}
}
@@ -23,7 +23,7 @@ import org.jetbrains.kotlin.name.NativeStandardInteropNames
import org.jetbrains.kotlin.native.interop.ObjCMethodInfo
internal fun FirFunctionSymbol<*>.getObjCMethodInfoFromOverriddenFunctions(session: FirSession, scopeSession: ScopeSession): ObjCMethodInfo? {
fun FirFunctionSymbol<*>.getObjCMethodInfoFromOverriddenFunctions(session: FirSession, scopeSession: ScopeSession): ObjCMethodInfo? {
decodeObjCMethodAnnotation(session)?.let {
return it
}
@@ -16,9 +16,12 @@
package org.jetbrains.kotlin.resolve
import com.intellij.psi.PsiElement
import com.intellij.util.containers.MultiMap
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.container.DefaultImplementation
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.diagnostics.DiagnosticFactory1
import org.jetbrains.kotlin.diagnostics.Errors
import org.jetbrains.kotlin.diagnostics.reportOnDeclaration
import org.jetbrains.kotlin.idea.MainFunctionDetector
@@ -30,11 +33,35 @@ import org.jetbrains.kotlin.resolve.descriptorUtil.platform
import org.jetbrains.kotlin.resolve.scopes.MemberScope
import java.util.*
@DefaultImplementation(impl = ConflictingOverloadsDispatcher.Default::class)
interface ConflictingOverloadsDispatcher {
fun getDiagnostic(
languageVersionSettings: LanguageVersionSettings,
declaration: DeclarationDescriptor,
redeclarations: Collection<DeclarationDescriptor>
): DiagnosticFactory1<PsiElement, Collection<DeclarationDescriptor>>?
object Default : ConflictingOverloadsDispatcher {
override fun getDiagnostic(
languageVersionSettings: LanguageVersionSettings,
declaration: DeclarationDescriptor,
redeclarations: Collection<DeclarationDescriptor>
): DiagnosticFactory1<PsiElement, Collection<DeclarationDescriptor>>? {
return when (declaration) {
is PropertyDescriptor, is ClassifierDescriptor -> Errors.REDECLARATION
is FunctionDescriptor -> Errors.CONFLICTING_OVERLOADS
else -> null
}
}
}
}
class OverloadResolver(
private val trace: BindingTrace,
private val overloadFilter: OverloadFilter,
private val overloadChecker: OverloadChecker,
languageVersionSettings: LanguageVersionSettings,
private val errorDispatcher: ConflictingOverloadsDispatcher,
private val languageVersionSettings: LanguageVersionSettings,
mainFunctionDetectorFactory: MainFunctionDetector.Factory
) {
@@ -299,12 +326,9 @@ class OverloadResolver(
if (redeclarations.isEmpty()) return
for (memberDescriptor in redeclarations) {
when (memberDescriptor) {
is PropertyDescriptor,
is ClassifierDescriptor ->
reportOnDeclaration(trace, memberDescriptor) { Errors.REDECLARATION.on(it, redeclarations) }
is FunctionDescriptor ->
reportOnDeclaration(trace, memberDescriptor) { Errors.CONFLICTING_OVERLOADS.on(it, redeclarations) }
val diagnostic = errorDispatcher.getDiagnostic(languageVersionSettings, memberDescriptor, redeclarations) ?: continue
reportOnDeclaration(trace, memberDescriptor) {
diagnostic.on(it, redeclarations)
}
}
}
@@ -42,28 +42,34 @@ headerFilter = lib.h
// FILE: main.kt
@file:OptIn(kotlinx.cinterop.ExperimentalForeignApi::class)
import lib.ObjCClass
// required for K1
@file:Suppress("CONFLICTING_OVERLOADS", "UNRESOLVED_REFERENCE", "API_NOT_AVAILABLE")
import lib.ObjCClass
import kotlinx.cinterop.ObjCSignatureOverride
@Suppress("CONFLICTING_OVERLOADS")
class OverrideAll : ObjCClass() {
@ObjCSignatureOverride
override fun fooWithArg(arg: Int, arg2: String?) = "D"
@ObjCSignatureOverride
override fun fooWithArg(ohNoOtherName: Int, name2: String?) = "E"
@ObjCSignatureOverride
override fun fooWithArg(arg: Int, name3: String?) = "F"
}
@Suppress("CONFLICTING_OVERLOADS")
class OverrideNone : ObjCClass() {
}
@Suppress("CONFLICTING_OVERLOADS")
class OverrideOne : ObjCClass() {
override fun fooWithArg(arg: Int, arg2: String?) = "G"
}
@Suppress("CONFLICTING_OVERLOADS")
class OverrideWithDifferentFirstArgName : ObjCClass() {
@ObjCSignatureOverride
override fun fooWithArg(a: Int, arg2: String?) = "H"
@ObjCSignatureOverride
override fun fooWithArg(b: Int, name2: String?) = "I"
@ObjCSignatureOverride
override fun fooWithArg(c: Int, name3: String?) = "J"
}
@@ -0,0 +1,131 @@
// !LANGUAGE: -ObjCSignatureOverrideAnnotation
// FIR_IDENTICAL
// WITH_PLATFORM_LIBS
import kotlinx.cinterop.*
import platform.darwin.*
import platform.Foundation.*
import platform.CoreFoundation.*
import platform.CoreBluetooth.*
class Delelegate1 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
}
class Delegate2 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
}
class Delegate3 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
}
class Delegate4 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
}
class Delegate5 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
}
@@ -0,0 +1,140 @@
// !LANGUAGE: +ObjCSignatureOverrideAnnotation
// !API_VERSION: 2.0
// FIR_IDENTICAL
// WITH_PLATFORM_LIBS
import kotlinx.cinterop.*
import platform.darwin.*
import platform.Foundation.*
import platform.CoreFoundation.*
import platform.CoreBluetooth.*
class Delelegate1 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
}
class Delegate2 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OBJC_OVERLOADS!>override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()<!>
<!CONFLICTING_OBJC_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()<!>
}
class Delegate3 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
<!CONFLICTING_OBJC_OVERLOADS!>override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()<!>
}
class Delegate4 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
}
class Delegate5 : CBCentralManagerDelegateProtocol, NSObject() {
override fun centralManager(central: CBCentralManager, willRestoreState: Map<Any?, *>): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDiscoverPeripheral: CBPeripheral,
advertisementData: Map<Any?, *>,
RSSI: NSNumber
): Unit = TODO()
override fun centralManager(central: CBCentralManager, didConnectPeripheral: CBPeripheral): Unit = TODO()
override fun centralManager(
central: CBCentralManager,
didDisconnectPeripheral: CBPeripheral,
timestamp: Double,
isReconnecting: Boolean,
error: NSError?
): Unit = TODO()
override fun centralManagerDidUpdateState(central: CBCentralManager): Unit = TODO()
<!CONFLICTING_OVERLOADS!>@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
<!CONFLICTING_OVERLOADS!>@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didFailToConnectPeripheral: CBPeripheral, error: NSError?): Unit<!> = TODO()
@ObjCSignatureOverride
override fun centralManager(central: CBCentralManager, didDisconnectPeripheral: CBPeripheral, error: NSError?): Unit = TODO()
}
@@ -0,0 +1,22 @@
// !API_VERSION: 2.0
// FIR_IDENTICAL
// WITH_PLATFORM_LIBS
import kotlinx.cinterop.*
import platform.darwin.*
<!INAPPLICABLE_OBJC_OVERRIDE!>@ObjCSignatureOverride<!>
fun foo() = 1
class A {
<!INAPPLICABLE_OBJC_OVERRIDE!>@ObjCSignatureOverride<!>
fun foo() = 1
}
<!WRONG_ANNOTATION_TARGET!>@ObjCSignatureOverride<!>
class B : NSObject() {
<!INAPPLICABLE_OBJC_OVERRIDE!>@ObjCSignatureOverride<!>
fun foo() = 1
<!WRONG_ANNOTATION_TARGET!>@ObjCSignatureOverride<!>
val v = 1
}
@@ -310,6 +310,7 @@ enum class LanguageFeature(
DisableCompatibilityModeForNewInference(KOTLIN_2_0, kind = OTHER), // KT-63558 (umbrella), KT-64306, KT-64307, KT-64308
DfaBooleanVariables(KOTLIN_2_0), // KT-25747
LightweightLambdas(KOTLIN_2_0, kind = OTHER), // KT-45375
ObjCSignatureOverrideAnnotation(KOTLIN_2_0, sinceApiVersion = ApiVersion.KOTLIN_2_0, kind = OTHER), // KT-61323
// 2.1