[FIR] Consistently use _function_ instead of _functional_ in names of classes and functions

This commit is contained in:
Dmitriy Novozhilov
2023-01-26 13:35:07 +02:00
committed by Space Team
parent f268ab8858
commit 89c42e20c9
102 changed files with 573 additions and 574 deletions
@@ -12,8 +12,8 @@ import org.jetbrains.kotlin.analysis.api.descriptors.types.base.KtFe10Type
import org.jetbrains.kotlin.analysis.api.lifetime.KtLifetimeToken import org.jetbrains.kotlin.analysis.api.lifetime.KtLifetimeToken
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.builtins.KotlinBuiltIns import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.getFunctionalClassKind import org.jetbrains.kotlin.builtins.getFunctionTypeKind
import org.jetbrains.kotlin.load.java.sam.JavaSingleAbstractMethodUtils import org.jetbrains.kotlin.load.java.sam.JavaSingleAbstractMethodUtils
import org.jetbrains.kotlin.name.SpecialNames import org.jetbrains.kotlin.name.SpecialNames
import org.jetbrains.kotlin.types.DefinitelyNotNullType import org.jetbrains.kotlin.types.DefinitelyNotNullType
@@ -31,9 +31,9 @@ internal class KtFe10TypeInfoProvider(
return JavaSingleAbstractMethodUtils.isSamType(type.fe10Type) return JavaSingleAbstractMethodUtils.isSamType(type.fe10Type)
} }
override fun getFunctionClassKind(type: KtType): FunctionalTypeKind? { override fun getFunctionClassKind(type: KtType): FunctionTypeKind? {
require(type is KtFe10Type) require(type is KtFe10Type)
return type.fe10Type.constructor.declarationDescriptor?.getFunctionalClassKind() return type.fe10Type.constructor.declarationDescriptor?.getFunctionTypeKind()
} }
override fun canBeNull(type: KtType): Boolean { override fun canBeNull(type: KtType): Boolean {
@@ -26,8 +26,7 @@ import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability
import org.jetbrains.kotlin.builtins.* import org.jetbrains.kotlin.builtins.*
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.isSuspendOrKSuspendFunction
import org.jetbrains.kotlin.builtins.functions.isSuspendType
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.types.SimpleType import org.jetbrains.kotlin.types.SimpleType
@@ -53,7 +52,7 @@ internal class KtFe10FunctionalType(
} }
override val isSuspend: Boolean override val isSuspend: Boolean
get() = withValidityAssertion { descriptor.functionKind.isSuspendType } get() = withValidityAssertion { descriptor.functionKind.isSuspendOrKSuspendFunction }
override val isReflectType: Boolean override val isReflectType: Boolean
get() = withValidityAssertion { descriptor.functionKind.isReflectType } get() = withValidityAssertion { descriptor.functionKind.isReflectType }
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.analysis.api.descriptors.utils
import org.jetbrains.kotlin.builtins.FAKE_CONTINUATION_CLASS_DESCRIPTOR import org.jetbrains.kotlin.builtins.FAKE_CONTINUATION_CLASS_DESCRIPTOR
import org.jetbrains.kotlin.builtins.KotlinBuiltIns import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
import org.jetbrains.kotlin.builtins.functions.isSuspendType import org.jetbrains.kotlin.builtins.functions.isSuspendOrKSuspendFunction
import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.incremental.components.NoLookupLocation import org.jetbrains.kotlin.incremental.components.NoLookupLocation
import org.jetbrains.kotlin.name.StandardClassIds import org.jetbrains.kotlin.name.StandardClassIds
@@ -61,7 +61,7 @@ internal class KtFe10TypeSystemCommonBackendContextForTypeMapping(
override fun SimpleTypeMarker.isSuspendFunction(): Boolean { override fun SimpleTypeMarker.isSuspendFunction(): Boolean {
require(this is SimpleType) require(this is SimpleType)
val declaration = constructor.declarationDescriptor val declaration = constructor.declarationDescriptor
return declaration is FunctionClassDescriptor && declaration.functionKind.isSuspendType return declaration is FunctionClassDescriptor && declaration.functionKind.isSuspendOrKSuspendFunction
} }
override fun SimpleTypeMarker.isKClass(): Boolean { override fun SimpleTypeMarker.isKClass(): Boolean {
@@ -9,7 +9,7 @@ import com.intellij.psi.PsiElement
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.analysis.api.symbols.* import org.jetbrains.kotlin.analysis.api.symbols.*
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.ApiVersion import org.jetbrains.kotlin.config.ApiVersion
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
@@ -366,7 +366,7 @@ internal object FirToKtConversionCreator {
ApiVersion::class, ApiVersion::class,
CallableId::class, CallableId::class,
ClassKind::class, ClassKind::class,
FunctionalTypeKind::class, FunctionTypeKind::class,
) )
private val KType.kClass: KClass<*> private val KType.kClass: KClass<*>
@@ -487,7 +487,7 @@ internal class KtSymbolByFirBuilder constructor(
} }
private fun hasFunctionalClassId(coneType: ConeClassLikeTypeImpl): Boolean { private fun hasFunctionalClassId(coneType: ConeClassLikeTypeImpl): Boolean {
return coneType.isSomeFunctionalType(analysisSession.firResolveSession.useSiteFirSession) return coneType.isSomeFunctionType(analysisSession.firResolveSession.useSiteFirSession)
} }
fun buildKtType(coneType: FirTypeRef): KtType { fun buildKtType(coneType: FirTypeRef): KtType {
@@ -22,7 +22,7 @@ import org.jetbrains.kotlin.fir.expressions.*
import org.jetbrains.kotlin.fir.references.FirNamedReference import org.jetbrains.kotlin.fir.references.FirNamedReference
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
import org.jetbrains.kotlin.fir.references.FirSuperReference import org.jetbrains.kotlin.fir.references.FirSuperReference
import org.jetbrains.kotlin.fir.resolve.constructFunctionalType import org.jetbrains.kotlin.fir.resolve.constructFunctionType
import org.jetbrains.kotlin.fir.symbols.impl.FirClassSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirClassSymbol
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.lexer.KtTokens import org.jetbrains.kotlin.lexer.KtTokens
@@ -113,7 +113,7 @@ internal class KtFirExpressionTypeProvider(
declaration.toFirAnonymousFunction() declaration.toFirAnonymousFunction()
else else
declaration.getOrBuildFirOfType<FirFunction>(firResolveSession) declaration.getOrBuildFirOfType<FirFunction>(firResolveSession)
return firFunction.constructFunctionalType(firFunction.specialFunctionalTypeKind(firResolveSession.useSiteFirSession)).asKtType() return firFunction.constructFunctionType(firFunction.specialFunctionTypeKind(firResolveSession.useSiteFirSession)).asKtType()
} }
@OptIn(ExperimentalContracts::class) @OptIn(ExperimentalContracts::class)
@@ -11,7 +11,7 @@ import org.jetbrains.kotlin.analysis.api.fir.types.KtFirType
import org.jetbrains.kotlin.analysis.api.fir.types.PublicTypeApproximator import org.jetbrains.kotlin.analysis.api.fir.types.PublicTypeApproximator
import org.jetbrains.kotlin.analysis.api.lifetime.KtLifetimeToken import org.jetbrains.kotlin.analysis.api.lifetime.KtLifetimeToken
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.resolve.FirSamResolver import org.jetbrains.kotlin.fir.resolve.FirSamResolver
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
@@ -31,9 +31,10 @@ internal class KtFirTypeInfoProvider(
return samResolver.isSamType(coneType) return samResolver.isSamType(coneType)
} }
override fun getFunctionClassKind(type: KtType): FunctionalTypeKind? { override fun getFunctionClassKind(type: KtType): FunctionTypeKind? {
return (type as KtFirType).coneType.functionalTypeKind(analysisSession.useSiteSession) return (type as KtFirType).coneType.functionTypeKind(analysisSession.useSiteSession)
} }
override fun canBeNull(type: KtType): Boolean = (type as KtFirType).coneType.canBeNull override fun canBeNull(type: KtType): Boolean = (type as KtFirType).coneType.canBeNull
override fun isDenotable(type: KtType): Boolean { override fun isDenotable(type: KtType): Boolean {
@@ -1814,10 +1814,10 @@ internal val KT_DIAGNOSTIC_CONVERTER = KtDiagnosticConverterBuilder.buildConvert
token, token,
) )
} }
add(FirErrors.AMBIGUOUS_FUNCTIONAL_TYPE_KIND) { firDiagnostic -> add(FirErrors.AMBIGUOUS_FUNCTION_TYPE_KIND) { firDiagnostic ->
AmbiguousFunctionalTypeKindImpl( AmbiguousFunctionTypeKindImpl(
firDiagnostic.a.map { functionalTypeKind -> firDiagnostic.a.map { functionTypeKind ->
functionalTypeKind functionTypeKind
}, },
firDiagnostic as KtPsiDiagnostic, firDiagnostic as KtPsiDiagnostic,
token, token,
@@ -16,7 +16,7 @@ import org.jetbrains.kotlin.analysis.api.symbols.KtTypeParameterSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtVariableLikeSymbol import org.jetbrains.kotlin.analysis.api.symbols.KtVariableLikeSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtVariableSymbol import org.jetbrains.kotlin.analysis.api.symbols.KtVariableSymbol
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.ApiVersion import org.jetbrains.kotlin.config.ApiVersion
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
@@ -1293,9 +1293,9 @@ sealed class KtFirDiagnostic<PSI : PsiElement> : KtDiagnosticWithPsi<PSI> {
abstract val candidates: List<KtSymbol> abstract val candidates: List<KtSymbol>
} }
abstract class AmbiguousFunctionalTypeKind : KtFirDiagnostic<PsiElement>() { abstract class AmbiguousFunctionTypeKind : KtFirDiagnostic<PsiElement>() {
override val diagnosticClass get() = AmbiguousFunctionalTypeKind::class override val diagnosticClass get() = AmbiguousFunctionTypeKind::class
abstract val kinds: List<FunctionalTypeKind> abstract val kinds: List<FunctionTypeKind>
} }
abstract class NoContextReceiver : KtFirDiagnostic<KtElement>() { abstract class NoContextReceiver : KtFirDiagnostic<KtElement>() {
@@ -16,7 +16,7 @@ import org.jetbrains.kotlin.analysis.api.symbols.KtTypeParameterSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtVariableLikeSymbol import org.jetbrains.kotlin.analysis.api.symbols.KtVariableLikeSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtVariableSymbol import org.jetbrains.kotlin.analysis.api.symbols.KtVariableSymbol
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.ApiVersion import org.jetbrains.kotlin.config.ApiVersion
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
@@ -1553,11 +1553,11 @@ internal class NextAmbiguityImpl(
override val token: KtLifetimeToken, override val token: KtLifetimeToken,
) : KtFirDiagnostic.NextAmbiguity(), KtAbstractFirDiagnostic<PsiElement> ) : KtFirDiagnostic.NextAmbiguity(), KtAbstractFirDiagnostic<PsiElement>
internal class AmbiguousFunctionalTypeKindImpl( internal class AmbiguousFunctionTypeKindImpl(
override val kinds: List<FunctionalTypeKind>, override val kinds: List<FunctionTypeKind>,
override val firDiagnostic: KtPsiDiagnostic, override val firDiagnostic: KtPsiDiagnostic,
override val token: KtLifetimeToken, override val token: KtLifetimeToken,
) : KtFirDiagnostic.AmbiguousFunctionalTypeKind(), KtAbstractFirDiagnostic<PsiElement> ) : KtFirDiagnostic.AmbiguousFunctionTypeKind(), KtAbstractFirDiagnostic<PsiElement>
internal class NoContextReceiverImpl( internal class NoContextReceiverImpl(
override val contextReceiverRepresentation: KtType, override val contextReceiverRepresentation: KtType,
@@ -23,6 +23,7 @@ import org.jetbrains.kotlin.analysis.api.types.KtFunctionalType
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability
import org.jetbrains.kotlin.analysis.low.level.api.fir.util.errorWithFirSpecificEntries import org.jetbrains.kotlin.analysis.low.level.api.fir.util.errorWithFirSpecificEntries
import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
@@ -49,10 +50,10 @@ internal class KtFirFunctionalType(
override val nullability: KtTypeNullability get() = withValidityAssertion { coneType.nullability.asKtNullability() } override val nullability: KtTypeNullability get() = withValidityAssertion { coneType.nullability.asKtNullability() }
override val isSuspend: Boolean get() = withValidityAssertion { coneType.isSuspendFunctionType(builder.rootSession) } override val isSuspend: Boolean get() = withValidityAssertion { coneType.isSuspendOrKSuspendFunctionType(builder.rootSession) }
override val isReflectType: Boolean override val isReflectType: Boolean
get() = withValidityAssertion { coneType.functionalTypeKind(builder.rootSession)?.isReflectType == true } get() = withValidityAssertion { coneType.functionTypeKind(builder.rootSession)?.isReflectType == true }
override val arity: Int override val arity: Int
get() = withValidityAssertion { get() = withValidityAssertion {
@@ -23,7 +23,7 @@ abstract class AbstractFunctionClassKindTest : AbstractAnalysisApiSingleFileTes
val (type, functionClassKind) = executeOnPooledThreadInReadAction { val (type, functionClassKind) = executeOnPooledThreadInReadAction {
analyseForTest(expressionAtCaret) { analyseForTest(expressionAtCaret) {
val functionType = expressionAtCaret.getExpectedType() val functionType = expressionAtCaret.getExpectedType()
functionType?.render(position = Variance.INVARIANT) to functionType?.functionalTypeKind functionType?.render(position = Variance.INVARIANT) to functionType?.functionTypeKind
} }
} }
val actual = buildString { val actual = buildString {
@@ -13,12 +13,12 @@ import org.jetbrains.kotlin.analysis.api.types.KtNonErrorClassType
import org.jetbrains.kotlin.analysis.api.types.KtType import org.jetbrains.kotlin.analysis.api.types.KtType
import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability import org.jetbrains.kotlin.analysis.api.types.KtTypeNullability
import org.jetbrains.kotlin.builtins.StandardNames import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
public abstract class KtTypeInfoProvider : KtAnalysisSessionComponent() { public abstract class KtTypeInfoProvider : KtAnalysisSessionComponent() {
public abstract fun isFunctionalInterfaceType(type: KtType): Boolean public abstract fun isFunctionalInterfaceType(type: KtType): Boolean
public abstract fun getFunctionClassKind(type: KtType): FunctionalTypeKind? public abstract fun getFunctionClassKind(type: KtType): FunctionTypeKind?
public abstract fun canBeNull(type: KtType): Boolean public abstract fun canBeNull(type: KtType): Boolean
public abstract fun isDenotable(type: KtType): Boolean public abstract fun isDenotable(type: KtType): Boolean
public abstract fun isArrayOrPrimitiveArray(type: KtType): Boolean public abstract fun isArrayOrPrimitiveArray(type: KtType): Boolean
@@ -41,22 +41,22 @@ public interface KtTypeInfoProviderMixIn : KtAnalysisSessionMixIn {
get() = withValidityAssertion { analysisSession.typeInfoProvider.isFunctionalInterfaceType(this) } get() = withValidityAssertion { analysisSession.typeInfoProvider.isFunctionalInterfaceType(this) }
/** /**
* Returns [FunctionalTypeKind] of the given [KtType] * Returns [FunctionTypeKind] of the given [KtType]
*/ */
public val KtType.functionalTypeKind: FunctionalTypeKind? public val KtType.functionTypeKind: FunctionTypeKind?
get() = withValidityAssertion { analysisSession.typeInfoProvider.getFunctionClassKind(this) } get() = withValidityAssertion { analysisSession.typeInfoProvider.getFunctionClassKind(this) }
public val KtType.isFunctionType: Boolean public val KtType.isFunctionType: Boolean
get() = withValidityAssertion { functionalTypeKind == FunctionalTypeKind.Function } get() = withValidityAssertion { functionTypeKind == FunctionTypeKind.Function }
public val KtType.isKFunctionType: Boolean public val KtType.isKFunctionType: Boolean
get() = withValidityAssertion { functionalTypeKind == FunctionalTypeKind.KFunction } get() = withValidityAssertion { functionTypeKind == FunctionTypeKind.KFunction }
public val KtType.isSuspendFunctionType: Boolean public val KtType.isSuspendFunctionType: Boolean
get() = withValidityAssertion { functionalTypeKind == FunctionalTypeKind.SuspendFunction } get() = withValidityAssertion { functionTypeKind == FunctionTypeKind.SuspendFunction }
public val KtType.isKSuspendFunctionType: Boolean public val KtType.isKSuspendFunctionType: Boolean
get() = withValidityAssertion { functionalTypeKind == FunctionalTypeKind.KSuspendFunction } get() = withValidityAssertion { functionTypeKind == FunctionTypeKind.KSuspendFunction }
/** /**
* Returns true if a public value of this type can potentially be null. This means this type is not a subtype of [Any]. However, it does not * Returns true if a public value of this type can potentially be null. This means this type is not a subtype of [Any]. However, it does not
@@ -19,7 +19,7 @@ import org.jetbrains.kotlin.fir.backend.jvm.FirJvmTypeMapper
import org.jetbrains.kotlin.fir.resolve.providers.FirProvider import org.jetbrains.kotlin.fir.resolve.providers.FirProvider
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirCloneableSymbolProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirCloneableSymbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionalInterfaceProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionInterfaceProvider
import org.jetbrains.kotlin.fir.resolve.scopes.wrapScopeWithJvmMapped import org.jetbrains.kotlin.fir.resolve.scopes.wrapScopeWithJvmMapped
import org.jetbrains.kotlin.fir.resolve.transformers.FirDummyCompilerLazyDeclarationResolver import org.jetbrains.kotlin.fir.resolve.transformers.FirDummyCompilerLazyDeclarationResolver
import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider
@@ -64,7 +64,7 @@ class LLFirBuiltinsSessionFactory(
register(FirKotlinScopeProvider::class, kotlinScopeProvider) register(FirKotlinScopeProvider::class, kotlinScopeProvider)
val symbolProvider = createCompositeSymbolProvider(this) { val symbolProvider = createCompositeSymbolProvider(this) {
add(LLFirBuiltinSymbolProvider(this@session, moduleData, kotlinScopeProvider)) add(LLFirBuiltinSymbolProvider(this@session, moduleData, kotlinScopeProvider))
add(FirExtensionSyntheticFunctionalInterfaceProvider(this@session, moduleData, kotlinScopeProvider)) add(FirExtensionSyntheticFunctionInterfaceProvider(this@session, moduleData, kotlinScopeProvider))
add(FirCloneableSymbolProvider(this@session, moduleData, kotlinScopeProvider)) add(FirCloneableSymbolProvider(this@session, moduleData, kotlinScopeProvider))
} }
@@ -31,7 +31,7 @@ import org.jetbrains.kotlin.fir.backend.jvm.FirJvmTypeMapper
import org.jetbrains.kotlin.fir.extensions.* import org.jetbrains.kotlin.fir.extensions.*
import org.jetbrains.kotlin.fir.java.JavaSymbolProvider import org.jetbrains.kotlin.fir.java.JavaSymbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.* import org.jetbrains.kotlin.fir.resolve.providers.*
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionalInterfaceProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionInterfaceProvider
import org.jetbrains.kotlin.fir.resolve.scopes.wrapScopeWithJvmMapped import org.jetbrains.kotlin.fir.resolve.scopes.wrapScopeWithJvmMapped
import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider
import org.jetbrains.kotlin.fir.session.* import org.jetbrains.kotlin.fir.session.*
@@ -149,7 +149,7 @@ internal object LLFirSessionFactory {
} }
val javaSymbolProvider = createJavaSymbolProvider(this, moduleData, project, contentScope) val javaSymbolProvider = createJavaSymbolProvider(this, moduleData, project, contentScope)
val syntheticFunctionalInterfaceProvider = FirExtensionSyntheticFunctionalInterfaceProvider(this, moduleData, scopeProvider) val syntheticFunctionalInterfaceProvider = FirExtensionSyntheticFunctionInterfaceProvider(this, moduleData, scopeProvider)
register( register(
FirSymbolProvider::class, FirSymbolProvider::class,
LLFirModuleWithDependenciesSymbolProvider( LLFirModuleWithDependenciesSymbolProvider(
@@ -9,7 +9,7 @@ import com.intellij.openapi.util.text.StringUtil
import org.jetbrains.kotlin.builtins.BuiltInsPackageFragment import org.jetbrains.kotlin.builtins.BuiltInsPackageFragment
import org.jetbrains.kotlin.builtins.KotlinBuiltIns import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.jvm.JavaToKotlinClassMap import org.jetbrains.kotlin.builtins.jvm.JavaToKotlinClassMap
import org.jetbrains.kotlin.codegen.* import org.jetbrains.kotlin.codegen.*
import org.jetbrains.kotlin.codegen.DescriptorAsmUtil.isStaticMethod import org.jetbrains.kotlin.codegen.DescriptorAsmUtil.isStaticMethod
@@ -342,8 +342,8 @@ class KotlinTypeMapper @JvmOverloads constructor(
if (classDescriptor is FunctionClassDescriptor) { if (classDescriptor is FunctionClassDescriptor) {
if (classDescriptor.hasBigArity || if (classDescriptor.hasBigArity ||
classDescriptor.functionKind == FunctionalTypeKind.KFunction || classDescriptor.functionKind == FunctionTypeKind.KFunction ||
classDescriptor.functionKind == FunctionalTypeKind.KSuspendFunction classDescriptor.functionKind == FunctionTypeKind.KSuspendFunction
) { ) {
// kotlin.reflect.KFunction{n}<P1, ..., Pn, R> is mapped to kotlin.reflect.KFunction<R> (for all n), and // kotlin.reflect.KFunction{n}<P1, ..., Pn, R> is mapped to kotlin.reflect.KFunction<R> (for all n), and
// kotlin.Function{n}<P1, ..., Pn, R> is mapped to kotlin.jvm.functions.FunctionN<R> (for n > 22). // kotlin.Function{n}<P1, ..., Pn, R> is mapped to kotlin.jvm.functions.FunctionN<R> (for n > 22).
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.fir.checkers.generator.diagnostics
import com.intellij.psi.PsiElement import com.intellij.psi.PsiElement
import com.intellij.psi.impl.source.tree.LeafPsiElement import com.intellij.psi.impl.source.tree.LeafPsiElement
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.ApiVersion import org.jetbrains.kotlin.config.ApiVersion
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
@@ -568,8 +568,8 @@ object DIAGNOSTICS_LIST : DiagnosticList("FirErrors") {
val NEXT_AMBIGUITY by error<PsiElement>(PositioningStrategy.REFERENCE_BY_QUALIFIED) { val NEXT_AMBIGUITY by error<PsiElement>(PositioningStrategy.REFERENCE_BY_QUALIFIED) {
parameter<Collection<FirBasedSymbol<*>>>("candidates") parameter<Collection<FirBasedSymbol<*>>>("candidates")
} }
val AMBIGUOUS_FUNCTIONAL_TYPE_KIND by error<PsiElement> { val AMBIGUOUS_FUNCTION_TYPE_KIND by error<PsiElement> {
parameter<Collection<FunctionalTypeKind>>("kinds") parameter<Collection<FunctionTypeKind>>("kinds")
} }
} }
@@ -22,7 +22,7 @@ import org.jetbrains.kotlin.fir.scopes.collectAllFunctions
import org.jetbrains.kotlin.fir.symbols.impl.FirIntersectionOverrideFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirIntersectionOverrideFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.fir.types.ConeClassLikeType import org.jetbrains.kotlin.fir.types.ConeClassLikeType
import org.jetbrains.kotlin.fir.types.isSuspendFunctionType import org.jetbrains.kotlin.fir.types.isSuspendOrKSuspendFunctionType
import org.jetbrains.kotlin.fir.types.typeContext import org.jetbrains.kotlin.fir.types.typeContext
object FirJsInheritanceClassChecker : FirClassChecker() { object FirJsInheritanceClassChecker : FirClassChecker() {
@@ -49,11 +49,11 @@ object FirJsInheritanceClassChecker : FirClassChecker() {
} }
private fun ConeClassLikeType.isBuiltinFunctionalTypeOrSubtype(session: FirSession): Boolean { private fun ConeClassLikeType.isBuiltinFunctionalTypeOrSubtype(session: FirSession): Boolean {
return with(session.typeContext) { isBuiltinFunctionalTypeOrSubtype() } return with(session.typeContext) { isBuiltinFunctionTypeOrSubtype() }
} }
private fun ConeClassLikeType.isSuspendFunctionTypeOrSubtype(session: FirSession): Boolean { private fun ConeClassLikeType.isSuspendFunctionTypeOrSubtype(session: FirSession): Boolean {
return with(session.typeContext) { isTypeOrSubtypeOf { it.isSuspendFunctionType(session) } } return with(session.typeContext) { isTypeOrSubtypeOf { it.isSuspendOrKSuspendFunctionType(session) } }
} }
private fun FirClass.findFakeMethodOverridingExternalWithOptionalParams(context: CheckerContext): FirNamedFunctionSymbol? { private fun FirClass.findFakeMethodOverridingExternalWithOptionalParams(context: CheckerContext): FirNamedFunctionSymbol? {
@@ -20,7 +20,7 @@ import org.jetbrains.kotlin.fir.declarations.utils.isAbstract
import org.jetbrains.kotlin.fir.declarations.utils.isInline import org.jetbrains.kotlin.fir.declarations.utils.isInline
import org.jetbrains.kotlin.fir.declarations.utils.isSuspend import org.jetbrains.kotlin.fir.declarations.utils.isSuspend
import org.jetbrains.kotlin.fir.types.coneType import org.jetbrains.kotlin.fir.types.coneType
import org.jetbrains.kotlin.fir.types.isSuspendFunctionType import org.jetbrains.kotlin.fir.types.isSuspendOrKSuspendFunctionType
import org.jetbrains.kotlin.name.JvmNames.SYNCHRONIZED_ANNOTATION_CLASS_ID import org.jetbrains.kotlin.name.JvmNames.SYNCHRONIZED_ANNOTATION_CLASS_ID
object FirSynchronizedAnnotationChecker : FirFunctionChecker() { object FirSynchronizedAnnotationChecker : FirFunctionChecker() {
@@ -33,7 +33,7 @@ object FirSynchronizedAnnotationChecker : FirFunctionChecker() {
return return
} }
if (declaration.isSuspend || if (declaration.isSuspend ||
(declaration as? FirAnonymousFunction)?.typeRef?.coneType?.isSuspendFunctionType(session) == true (declaration as? FirAnonymousFunction)?.typeRef?.coneType?.isSuspendOrKSuspendFunctionType(session) == true
) { ) {
reporter.reportOn(annotation.source, FirJvmErrors.SYNCHRONIZED_ON_SUSPEND, context) reporter.reportOn(annotation.source, FirJvmErrors.SYNCHRONIZED_ON_SUSPEND, context)
return return
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.fir.analysis.diagnostics
import com.intellij.psi.PsiElement import com.intellij.psi.PsiElement
import com.intellij.psi.impl.source.tree.LeafPsiElement import com.intellij.psi.impl.source.tree.LeafPsiElement
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.ApiVersion import org.jetbrains.kotlin.config.ApiVersion
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageFeature.ForbidExposingTypesInPrimaryConstructorProperties import org.jetbrains.kotlin.config.LanguageFeature.ForbidExposingTypesInPrimaryConstructorProperties
@@ -370,7 +370,7 @@ object FirErrors {
val ITERATOR_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED) val ITERATOR_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED)
val HAS_NEXT_FUNCTION_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED) val HAS_NEXT_FUNCTION_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED)
val NEXT_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED) val NEXT_AMBIGUITY by error1<PsiElement, Collection<FirBasedSymbol<*>>>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED)
val AMBIGUOUS_FUNCTIONAL_TYPE_KIND by error1<PsiElement, Collection<FunctionalTypeKind>>() val AMBIGUOUS_FUNCTION_TYPE_KIND by error1<PsiElement, Collection<FunctionTypeKind>>()
// Context receivers resolution // Context receivers resolution
val NO_CONTEXT_RECEIVER by error1<KtElement, ConeKotlinType>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED) val NO_CONTEXT_RECEIVER by error1<KtElement, ConeKotlinType>(SourceElementPositioningStrategies.REFERENCE_BY_QUALIFIED)
@@ -52,13 +52,13 @@ object FirCallsEffectAnalyzer : FirControlFlowChecker() {
val functionalTypeEffects = mutableMapOf<FirBasedSymbol<*>, ConeCallsEffectDeclaration>() val functionalTypeEffects = mutableMapOf<FirBasedSymbol<*>, ConeCallsEffectDeclaration>()
function.valueParameters.forEachIndexed { index, parameter -> function.valueParameters.forEachIndexed { index, parameter ->
if (parameter.returnTypeRef.isFunctionalTypeRef(session)) { if (parameter.returnTypeRef.isFunctionTypeRef(session)) {
val effectDeclaration = function.contractDescription.getParameterCallsEffectDeclaration(index) val effectDeclaration = function.contractDescription.getParameterCallsEffectDeclaration(index)
if (effectDeclaration != null) functionalTypeEffects[parameter.symbol] = effectDeclaration if (effectDeclaration != null) functionalTypeEffects[parameter.symbol] = effectDeclaration
} }
} }
if (function.receiverParameter?.typeRef.isFunctionalTypeRef(session)) { if (function.receiverParameter?.typeRef.isFunctionTypeRef(session)) {
val effectDeclaration = function.contractDescription.getParameterCallsEffectDeclaration(-1) val effectDeclaration = function.contractDescription.getParameterCallsEffectDeclaration(-1)
if (effectDeclaration != null) functionalTypeEffects[function.symbol] = effectDeclaration if (effectDeclaration != null) functionalTypeEffects[function.symbol] = effectDeclaration
} }
@@ -277,8 +277,8 @@ object FirCallsEffectAnalyzer : FirControlFlowChecker() {
} }
} }
private fun FirTypeRef?.isFunctionalTypeRef(session: FirSession): Boolean { private fun FirTypeRef?.isFunctionTypeRef(session: FirSession): Boolean {
return this?.coneType?.isSomeFunctionalType(session) == true return this?.coneType?.isSomeFunctionType(session) == true
} }
private fun FirContractDescription?.getParameterCallsEffectDeclaration(index: Int): ConeCallsEffectDeclaration? { private fun FirContractDescription?.getParameterCallsEffectDeclaration(index: Int): ConeCallsEffectDeclaration? {
@@ -303,10 +303,10 @@ private fun isUpcast(context: CheckerContext, candidateType: ConeKotlinType, tar
if (!AbstractTypeChecker.isSubtypeOf(context.session.typeContext, candidateType, targetType, stubTypesEqualToAnything = false)) if (!AbstractTypeChecker.isSubtypeOf(context.session.typeContext, candidateType, targetType, stubTypesEqualToAnything = false))
return false return false
// E.g., foo(p1: (X) -> Y), where p1 has a functional type whose receiver type is X and return type is Y. // E.g., foo(p1: (X) -> Y), where p1 has a function type whose receiver type is X and return type is Y.
// For bar(p2: X.() -> Y), p2 has the same functional type (with same receiver and return types). // For bar(p2: X.() -> Y), p2 has the same function type (with same receiver and return types).
// The only difference is the existence of type annotation, @ExtensionFunctionType, // The only difference is the existence of type annotation, @ExtensionFunctionType,
// which indicates that the annotated type represents an extension function. // which indicates that the annotated type represents an extension function.
// If one casts p1 to p2 (or vice versa), it is _not_ up cast, i.e., not redundant, yet meaningful. // If one casts p1 to p2 (or vice versa), it is _not_ up cast, i.e., not redundant, yet meaningful.
return candidateType.isExtensionFunctionType == targetType.isExtensionFunctionType return candidateType.isExtensionFunctionType == targetType.isExtensionFunctionType
} }
@@ -144,7 +144,7 @@ internal fun checkConstantArguments(
} }
expression is FirQualifiedAccessExpression -> { expression is FirQualifiedAccessExpression -> {
val expressionType = expression.typeRef.coneType val expressionType = expression.typeRef.coneType
if (expressionType.isReflectFunctionalType(session) || expressionType.isKProperty(session) || expressionType.isKMutableProperty(session)) { if (expressionType.isReflectFunctionType(session) || expressionType.isKProperty(session) || expressionType.isKMutableProperty(session)) {
return checkConstantArguments(expression.dispatchReceiver, session) return checkConstantArguments(expression.dispatchReceiver, session)
} }
@@ -7,7 +7,7 @@ package org.jetbrains.kotlin.fir.analysis.checkers.declaration
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.StandardNames.BACKING_FIELD import org.jetbrains.kotlin.builtins.StandardNames.BACKING_FIELD
import org.jetbrains.kotlin.builtins.functions.isSuspendType import org.jetbrains.kotlin.builtins.functions.isSuspendOrKSuspendFunction
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.descriptors.EffectiveVisibility import org.jetbrains.kotlin.descriptors.EffectiveVisibility
import org.jetbrains.kotlin.descriptors.Visibilities import org.jetbrains.kotlin.descriptors.Visibilities
@@ -62,7 +62,7 @@ abstract class FirInlineDeclarationChecker : FirFunctionChecker() {
val inalienableParameters = function.valueParameters.filter { val inalienableParameters = function.valueParameters.filter {
if (it.isNoinline) return@filter false if (it.isNoinline) return@filter false
val type = it.returnTypeRef.coneType val type = it.returnTypeRef.coneType
!type.isMarkedNullable && type.isNonReflectFunctionalType(context.session) !type.isMarkedNullable && type.isNonReflectFunctionType(context.session)
}.map { it.symbol } }.map { it.symbol }
val visitor = inlineVisitor( val visitor = inlineVisitor(
@@ -234,7 +234,7 @@ abstract class FirInlineDeclarationChecker : FirFunctionChecker() {
// TODO: receivers are currently not inline (KT-5837) // TODO: receivers are currently not inline (KT-5837)
// if (targetSymbol.isInline) return true // if (targetSymbol.isInline) return true
return targetSymbol.name == OperatorNameConventions.INVOKE && return targetSymbol.name == OperatorNameConventions.INVOKE &&
targetSymbol.dispatchReceiverType?.isSomeFunctionalType(session) == true targetSymbol.dispatchReceiverType?.isSomeFunctionType(session) == true
} }
private fun checkQualifiedAccess( private fun checkQualifiedAccess(
@@ -405,22 +405,22 @@ abstract class FirInlineDeclarationChecker : FirFunctionChecker() {
) { ) {
for (param in function.valueParameters) { for (param in function.valueParameters) {
val coneType = param.returnTypeRef.coneType val coneType = param.returnTypeRef.coneType
val functionalKind = coneType.functionalTypeKind(context.session) val functionKind = coneType.functionTypeKind(context.session)
val isFunctionalType = functionalKind != null val isFunctionalType = functionKind != null
val isSuspendFunctionalType = functionalKind?.isSuspendType == true val isSuspendFunctionType = functionKind?.isSuspendOrKSuspendFunction == true
val defaultValue = param.defaultValue val defaultValue = param.defaultValue
if (!(isFunctionalType || isSuspendFunctionalType) && (param.isNoinline || param.isCrossinline)) { if (!(isFunctionalType || isSuspendFunctionType) && (param.isNoinline || param.isCrossinline)) {
reporter.reportOn(param.source, FirErrors.ILLEGAL_INLINE_PARAMETER_MODIFIER, context) reporter.reportOn(param.source, FirErrors.ILLEGAL_INLINE_PARAMETER_MODIFIER, context)
} }
if (param.isNoinline) continue if (param.isNoinline) continue
if (function.isSuspend && defaultValue != null && isSuspendFunctionalType) { if (function.isSuspend && defaultValue != null && isSuspendFunctionType) {
checkSuspendFunctionalParameterWithDefaultValue(param, context, reporter) checkSuspendFunctionalParameterWithDefaultValue(param, context, reporter)
} }
if (isSuspendFunctionalType && !param.isCrossinline) { if (isSuspendFunctionType && !param.isCrossinline) {
if (function.isSuspend) { if (function.isSuspend) {
val modifier = param.returnTypeRef.getModifier(KtTokens.SUSPEND_KEYWORD) val modifier = param.returnTypeRef.getModifier(KtTokens.SUSPEND_KEYWORD)
if (modifier != null) { if (modifier != null) {
@@ -490,7 +490,7 @@ abstract class FirInlineDeclarationChecker : FirFunctionChecker() {
function.valueParameters.any { param -> function.valueParameters.any { param ->
val type = param.returnTypeRef.coneType val type = param.returnTypeRef.coneType
!param.isNoinline && !type.isNullable !param.isNoinline && !type.isNullable
&& (type.isSimpleFunctionType(session) || type.isSuspendFunctionType(session)) && (type.isBasicFunctionType(session) || type.isSuspendOrKSuspendFunctionType(session))
} }
if (hasInlinableParameters) return if (hasInlinableParameters) return
if (function.isInlineOnly(session)) return if (function.isInlineOnly(session)) return
@@ -130,7 +130,7 @@ object FirSuspendCallChecker : FirQualifiedAccessExpressionChecker() {
private fun findEnclosingSuspendFunction(context: CheckerContext): FirFunction? { private fun findEnclosingSuspendFunction(context: CheckerContext): FirFunction? {
return context.containingDeclarations.lastOrNull { return context.containingDeclarations.lastOrNull {
when (it) { when (it) {
is FirAnonymousFunction -> it.typeRef.coneType.isSuspendFunctionType(context.session) is FirAnonymousFunction -> it.typeRef.coneType.isSuspendOrKSuspendFunctionType(context.session)
is FirSimpleFunction -> it.isSuspend is FirSimpleFunction -> it.isSuspend
else -> false else -> false
} }
@@ -218,7 +218,7 @@ object FirSuspendCallChecker : FirQualifiedAccessExpressionChecker() {
calledDeclarationSymbol: FirCallableSymbol<*> calledDeclarationSymbol: FirCallableSymbol<*>
): Triple<FirExpression?, FirExpression?, ConeKotlinType?> { ): Triple<FirExpression?, FirExpression?, ConeKotlinType?> {
if (this is FirImplicitInvokeCall && if (this is FirImplicitInvokeCall &&
dispatchReceiver != FirNoReceiverExpression && dispatchReceiver.typeRef.coneType.isSuspendFunctionType(session) dispatchReceiver != FirNoReceiverExpression && dispatchReceiver.typeRef.coneType.isSuspendOrKSuspendFunctionType(session)
) { ) {
val variableForInvoke = dispatchReceiver val variableForInvoke = dispatchReceiver
val variableForInvokeType = variableForInvoke.typeRef.coneType val variableForInvokeType = variableForInvoke.typeRef.coneType
@@ -28,7 +28,7 @@ import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
import org.jetbrains.kotlin.fir.symbols.lazyResolveToPhase import org.jetbrains.kotlin.fir.symbols.lazyResolveToPhase
import org.jetbrains.kotlin.fir.types.coneType import org.jetbrains.kotlin.fir.types.coneType
import org.jetbrains.kotlin.fir.types.isSimpleFunctionType import org.jetbrains.kotlin.fir.types.isBasicFunctionType
object UnusedChecker : AbstractFirPropertyInitializationChecker() { object UnusedChecker : AbstractFirPropertyInitializationChecker() {
override fun analyze(data: PropertyInitializationInfoData, reporter: DiagnosticReporter, context: CheckerContext) { override fun analyze(data: PropertyInitializationInfoData, reporter: DiagnosticReporter, context: CheckerContext) {
@@ -278,7 +278,7 @@ object UnusedChecker : AbstractFirPropertyInitializationChecker() {
val reference = node.fir.calleeReference.resolved ?: return dataForNode val reference = node.fir.calleeReference.resolved ?: return dataForNode
val functionSymbol = reference.resolvedSymbol as? FirFunctionSymbol<*> ?: return dataForNode val functionSymbol = reference.resolvedSymbol as? FirFunctionSymbol<*> ?: return dataForNode
val symbol = if (functionSymbol.callableId.callableName.identifier == "invoke") { val symbol = if (functionSymbol.callableId.callableName.identifier == "invoke") {
localProperties.find { it.name == reference.name && it.resolvedReturnTypeRef.coneType.isSimpleFunctionType(session) } localProperties.find { it.name == reference.name && it.resolvedReturnTypeRef.coneType.isBasicFunctionType(session) }
} else null } else null
symbol ?: return dataForNode symbol ?: return dataForNode
@@ -15,7 +15,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId
import org.jetbrains.kotlin.fir.types.FirResolvedTypeRef import org.jetbrains.kotlin.fir.types.FirResolvedTypeRef
import org.jetbrains.kotlin.fir.types.FirTypeRef import org.jetbrains.kotlin.fir.types.FirTypeRef
import org.jetbrains.kotlin.fir.types.isSomeFunctionalType import org.jetbrains.kotlin.fir.types.isSomeFunctionType
import org.jetbrains.kotlin.name.StandardClassIds import org.jetbrains.kotlin.name.StandardClassIds
object FirTypeAnnotationChecker : FirTypeRefChecker() { object FirTypeAnnotationChecker : FirTypeRefChecker() {
@@ -33,7 +33,7 @@ object FirTypeAnnotationChecker : FirTypeRefChecker() {
} }
} }
if (annotation.toAnnotationClassId(context.session) == StandardClassIds.Annotations.ExtensionFunctionType) { if (annotation.toAnnotationClassId(context.session) == StandardClassIds.Annotations.ExtensionFunctionType) {
if (!typeRef.type.isSomeFunctionalType(context.session)) { if (!typeRef.type.isSomeFunctionType(context.session)) {
if (context.languageVersionSettings.supportsFeature(LanguageFeature.ForbidExtensionFunctionTypeOnNonFunctionTypes)) { if (context.languageVersionSettings.supportsFeature(LanguageFeature.ForbidExtensionFunctionTypeOnNonFunctionTypes)) {
reporter.reportOn(annotation.source, FirErrors.WRONG_EXTENSION_FUNCTION_TYPE, context) reporter.reportOn(annotation.source, FirErrors.WRONG_EXTENSION_FUNCTION_TYPE, context)
} else { } else {
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.analysis.diagnostics package org.jetbrains.kotlin.fir.analysis.diagnostics
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.diagnostics.KtDiagnosticRenderers import org.jetbrains.kotlin.diagnostics.KtDiagnosticRenderers
import org.jetbrains.kotlin.diagnostics.WhenMissingCase import org.jetbrains.kotlin.diagnostics.WhenMissingCase
@@ -143,7 +143,7 @@ object FirDiagnosticRenderers {
} }
} }
val FUNCTIONAL_TYPE_KIND = Renderer { kind: FunctionalTypeKind -> val FUNCTIONAL_TYPE_KIND = Renderer { kind: FunctionTypeKind ->
kind.prefixForTypeRender ?: kind.classNamePrefix kind.prefixForTypeRender ?: kind.classNamePrefix
} }
@@ -61,7 +61,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_ALTERED
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_ANONYMOUS_TYPE_INFERRED import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_ANONYMOUS_TYPE_INFERRED
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_CALL_WITH_IMPLICIT_CONTEXT_RECEIVER import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_CALL_WITH_IMPLICIT_CONTEXT_RECEIVER
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_EXPECTS import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_EXPECTS
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_FUNCTIONAL_TYPE_KIND import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_FUNCTION_TYPE_KIND
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_SUPER import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.AMBIGUOUS_SUPER
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.ANNOTATION_ARGUMENT_KCLASS_LITERAL_OF_TYPE_PARAMETER_ERROR import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.ANNOTATION_ARGUMENT_KCLASS_LITERAL_OF_TYPE_PARAMETER_ERROR
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.ANNOTATION_ARGUMENT_MUST_BE_CONST import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors.ANNOTATION_ARGUMENT_MUST_BE_CONST
@@ -1078,7 +1078,7 @@ object FirErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
map.put(NEXT_MISSING, "Method ''next()'' cannot be called on ''iterator()''") map.put(NEXT_MISSING, "Method ''next()'' cannot be called on ''iterator()''")
map.put(NEXT_AMBIGUITY, "Method ''next()'' is ambiguous for this expression: {0}", SYMBOLS) map.put(NEXT_AMBIGUITY, "Method ''next()'' is ambiguous for this expression: {0}", SYMBOLS)
map.put(AMBIGUOUS_FUNCTIONAL_TYPE_KIND, "Multiple functional type conversions are not allowed for single type. Detected type conversions: {0}", FUNCTIONAL_TYPE_KINDS) map.put(AMBIGUOUS_FUNCTION_TYPE_KIND, "Multiple functional type conversions are not allowed for single type. Detected type conversions: {0}", FUNCTIONAL_TYPE_KINDS)
map.put(NEXT_NONE_APPLICABLE, "None of the ''next()'' functions is applicable for ''iterator()'' of type ''{0}''", SYMBOLS) map.put(NEXT_NONE_APPLICABLE, "None of the ''next()'' functions is applicable for ''iterator()'' of type ''{0}''", SYMBOLS)
map.put(NO_CONTEXT_RECEIVER, "No required context receiver found: {0}", RENDER_TYPE) map.put(NO_CONTEXT_RECEIVER, "No required context receiver found: {0}", RENDER_TYPE)
@@ -132,7 +132,7 @@ private fun ConeDiagnostic.toKtDiagnostic(
is ConeAmbiguouslyResolvedAnnotationFromPlugin -> { is ConeAmbiguouslyResolvedAnnotationFromPlugin -> {
FirErrors.PLUGIN_ANNOTATION_AMBIGUITY.createOn(source, typeFromCompilerPhase, typeFromTypesPhase) FirErrors.PLUGIN_ANNOTATION_AMBIGUITY.createOn(source, typeFromCompilerPhase, typeFromTypesPhase)
} }
is ConeAmbiguousFunctionalTypeKinds -> FirErrors.AMBIGUOUS_FUNCTIONAL_TYPE_KIND.createOn(source, kinds) is ConeAmbiguousFunctionTypeKinds -> FirErrors.AMBIGUOUS_FUNCTION_TYPE_KIND.createOn(source, kinds)
else -> throw IllegalArgumentException("Unsupported diagnostic type: ${this.javaClass}") else -> throw IllegalArgumentException("Unsupported diagnostic type: ${this.javaClass}")
} }
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.renderer package org.jetbrains.kotlin.fir.renderer
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
open class ConeTypeRenderer { open class ConeTypeRenderer {
@@ -15,10 +15,10 @@ open class ConeTypeRenderer {
open fun renderAsPossibleFunctionType( open fun renderAsPossibleFunctionType(
type: ConeKotlinType, type: ConeKotlinType,
functionalClassKindExtractor: (ConeKotlinType) -> FunctionalTypeKind?, functionClassKindExtractor: (ConeKotlinType) -> FunctionTypeKind?,
renderType: ConeTypeProjection.() -> Unit = { render() } renderType: ConeTypeProjection.() -> Unit = { render() }
) { ) {
val kind = functionalClassKindExtractor(type) val kind = functionClassKindExtractor(type)
if (kind?.isReflectType != false) { if (kind?.isReflectType != false) {
type.renderType() type.renderType()
return return
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.renderer package org.jetbrains.kotlin.fir.renderer
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.types.ConeKotlinType import org.jetbrains.kotlin.fir.types.ConeKotlinType
import org.jetbrains.kotlin.fir.types.ConeTypeProjection import org.jetbrains.kotlin.fir.types.ConeTypeProjection
@@ -19,11 +19,11 @@ class ConeTypeRendererForDebugging() : ConeTypeRenderer() {
override fun renderAsPossibleFunctionType( override fun renderAsPossibleFunctionType(
type: ConeKotlinType, type: ConeKotlinType,
functionalClassKindExtractor: (ConeKotlinType) -> FunctionalTypeKind?, functionClassKindExtractor: (ConeKotlinType) -> FunctionTypeKind?,
renderType: ConeTypeProjection.() -> Unit renderType: ConeTypeProjection.() -> Unit
) { ) {
builder.append("R|") builder.append("R|")
super.renderAsPossibleFunctionType(type, functionalClassKindExtractor, renderType) super.renderAsPossibleFunctionType(type, functionClassKindExtractor, renderType)
builder.append("|") builder.append("|")
} }
} }
@@ -32,7 +32,7 @@ abstract class FirExtensionRegistrar : FirExtensionRegistrarAdapter() {
FirSamConversionTransformerExtension::class, FirSamConversionTransformerExtension::class,
FirAssignExpressionAltererExtension::class, FirAssignExpressionAltererExtension::class,
FirScriptConfiguratorExtension::class, FirScriptConfiguratorExtension::class,
FirFunctionalTypeKindExtension::class, FirFunctionTypeKindExtension::class,
) )
} }
@@ -91,9 +91,9 @@ abstract class FirExtensionRegistrar : FirExtensionRegistrarAdapter() {
registerExtension(FirScriptConfiguratorExtension::class, this) registerExtension(FirScriptConfiguratorExtension::class, this)
} }
@JvmName("plusFunctionalTypeKindExtension") @JvmName("plusFunctionTypeKindExtension")
operator fun (FirFunctionalTypeKindExtension.Factory).unaryPlus() { operator fun (FirFunctionTypeKindExtension.Factory).unaryPlus() {
registerExtension(FirFunctionalTypeKindExtension::class, this) registerExtension(FirFunctionTypeKindExtension::class, this)
} }
// ------------------ reference methods ------------------ // ------------------ reference methods ------------------
@@ -148,9 +148,9 @@ abstract class FirExtensionRegistrar : FirExtensionRegistrarAdapter() {
FirScriptConfiguratorExtension.Factory { this.invoke(it) }.unaryPlus() FirScriptConfiguratorExtension.Factory { this.invoke(it) }.unaryPlus()
} }
@JvmName("plusFunctionalTypeKindExtension") @JvmName("plusFunctionTypeKindExtension")
operator fun ((FirSession) -> FirFunctionalTypeKindExtension).unaryPlus() { operator fun ((FirSession) -> FirFunctionTypeKindExtension).unaryPlus() {
FirFunctionalTypeKindExtension.Factory { this.invoke(it) }.unaryPlus() FirFunctionTypeKindExtension.Factory { this.invoke(it) }.unaryPlus()
} }
// ------------------ utilities ------------------ // ------------------ utilities ------------------
@@ -46,8 +46,8 @@ import org.jetbrains.kotlin.fir.scopes.impl.FirIntersectionOverrideStorage
import org.jetbrains.kotlin.fir.scopes.impl.FirSubstitutionOverrideStorage import org.jetbrains.kotlin.fir.scopes.impl.FirSubstitutionOverrideStorage
import org.jetbrains.kotlin.fir.symbols.FirLazyDeclarationResolver import org.jetbrains.kotlin.fir.symbols.FirLazyDeclarationResolver
import org.jetbrains.kotlin.fir.types.FirCorrespondingSupertypesCache import org.jetbrains.kotlin.fir.types.FirCorrespondingSupertypesCache
import org.jetbrains.kotlin.fir.types.FirFunctionalTypeKindService import org.jetbrains.kotlin.fir.types.FirFunctionTypeKindService
import org.jetbrains.kotlin.fir.types.FirFunctionalTypeKindServiceImpl import org.jetbrains.kotlin.fir.types.FirFunctionTypeKindServiceImpl
import org.jetbrains.kotlin.fir.types.TypeComponents import org.jetbrains.kotlin.fir.types.TypeComponents
import org.jetbrains.kotlin.incremental.components.EnumWhenTracker import org.jetbrains.kotlin.incremental.components.EnumWhenTracker
import org.jetbrains.kotlin.incremental.components.LookupTracker import org.jetbrains.kotlin.incremental.components.LookupTracker
@@ -77,7 +77,7 @@ fun FirSession.registerCommonComponents(languageVersionSettings: LanguageVersion
@OptIn(SessionConfiguration::class) @OptIn(SessionConfiguration::class)
fun FirSession.registerCommonComponentsAfterExtensionsAreConfigured() { fun FirSession.registerCommonComponentsAfterExtensionsAreConfigured() {
register(FirFunctionalTypeKindService::class, FirFunctionalTypeKindServiceImpl(this)) register(FirFunctionTypeKindService::class, FirFunctionTypeKindServiceImpl(this))
} }
@OptIn(SessionConfiguration::class) @OptIn(SessionConfiguration::class)
@@ -77,7 +77,7 @@ abstract class FirAbstractSessionFactory {
createProviders: ( createProviders: (
FirSession, FirKotlinScopeProvider, FirSymbolProvider, FirSession, FirKotlinScopeProvider, FirSymbolProvider,
FirSwitchableExtensionDeclarationsSymbolProvider?, FirSwitchableExtensionDeclarationsSymbolProvider?,
FirExtensionSyntheticFunctionalInterfaceProvider, FirExtensionSyntheticFunctionInterfaceProvider,
dependencies: List<FirSymbolProvider>, dependencies: List<FirSymbolProvider>,
) -> List<FirSymbolProvider> ) -> List<FirSymbolProvider>
): FirSession { ): FirSession {
@@ -109,14 +109,14 @@ abstract class FirAbstractSessionFactory {
val dependencyProviders = computeDependencyProviderList(moduleData) val dependencyProviders = computeDependencyProviderList(moduleData)
val generatedSymbolsProvider = FirSwitchableExtensionDeclarationsSymbolProvider.create(this) val generatedSymbolsProvider = FirSwitchableExtensionDeclarationsSymbolProvider.create(this)
val syntheticFunctionalInterfaceProvider = FirExtensionSyntheticFunctionalInterfaceProvider(this, moduleData, kotlinScopeProvider) val syntheticFunctionInterfaceProvider = FirExtensionSyntheticFunctionInterfaceProvider(this, moduleData, kotlinScopeProvider)
val providers = createProviders( val providers = createProviders(
this, this,
kotlinScopeProvider, kotlinScopeProvider,
firProvider.symbolProvider, firProvider.symbolProvider,
generatedSymbolsProvider, generatedSymbolsProvider,
syntheticFunctionalInterfaceProvider, syntheticFunctionInterfaceProvider,
dependencyProviders, dependencyProviders,
) )
@@ -44,11 +44,11 @@ object FirJsSessionFactory : FirAbstractSessionFactory() {
}, },
registerExtraCheckers = { it.registerJsCheckers() }, registerExtraCheckers = { it.registerJsCheckers() },
createKotlinScopeProvider = { FirKotlinScopeProvider { _, declaredMemberScope, _, _ -> declaredMemberScope } }, createKotlinScopeProvider = { FirKotlinScopeProvider { _, declaredMemberScope, _, _ -> declaredMemberScope } },
createProviders = { _, _, symbolProvider, generatedSymbolsProvider, syntheticFunctionalInterfaceProvider, dependencies -> createProviders = { _, _, symbolProvider, generatedSymbolsProvider, syntheticFunctionInterfaceProvider, dependencies ->
listOfNotNull( listOfNotNull(
symbolProvider, symbolProvider,
generatedSymbolsProvider, generatedSymbolsProvider,
syntheticFunctionalInterfaceProvider, syntheticFunctionInterfaceProvider,
*dependencies.toTypedArray(), *dependencies.toTypedArray(),
) )
} }
@@ -79,7 +79,7 @@ object FirJsSessionFactory : FirAbstractSessionFactory() {
// TODO: consider using "poisoning" provider for builtins to ensure that proper ones are taken from dependencies // TODO: consider using "poisoning" provider for builtins to ensure that proper ones are taken from dependencies
// NOTE: it requires precise filtering for true nuiltins, like Function* // NOTE: it requires precise filtering for true nuiltins, like Function*
FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider), FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider),
FirExtensionSyntheticFunctionalInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider), FirExtensionSyntheticFunctionInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider),
) )
} }
) )
@@ -58,7 +58,7 @@ object FirJvmSessionFactory : FirAbstractSessionFactory() {
projectEnvironment.getFirJavaFacade(session, moduleDataProvider.allModuleData.last(), scope) projectEnvironment.getFirJavaFacade(session, moduleDataProvider.allModuleData.last(), scope)
), ),
FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider), FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider),
FirExtensionSyntheticFunctionalInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider), FirExtensionSyntheticFunctionInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider),
FirCloneableSymbolProvider(session, builtinsModuleData, kotlinScopeProvider), FirCloneableSymbolProvider(session, builtinsModuleData, kotlinScopeProvider),
OptionalAnnotationClassesProvider( OptionalAnnotationClassesProvider(
session, session,
@@ -101,7 +101,7 @@ object FirJvmSessionFactory : FirAbstractSessionFactory() {
}, },
registerExtraCheckers = { it.registerJvmCheckers() }, registerExtraCheckers = { it.registerJvmCheckers() },
createKotlinScopeProvider = { FirKotlinScopeProvider(::wrapScopeWithJvmMapped) }, createKotlinScopeProvider = { FirKotlinScopeProvider(::wrapScopeWithJvmMapped) },
createProviders = { session, kotlinScopeProvider, symbolProvider, generatedSymbolsProvider, syntheticFunctionalInterfaceProvider, dependencies -> createProviders = { session, kotlinScopeProvider, symbolProvider, generatedSymbolsProvider, syntheticFunctionInterfaceProvider, dependencies ->
var symbolProviderForBinariesFromIncrementalCompilation: JvmClassFileBasedSymbolProvider? = null var symbolProviderForBinariesFromIncrementalCompilation: JvmClassFileBasedSymbolProvider? = null
var optionalAnnotationClassesProviderForBinariesFromIncrementalCompilation: OptionalAnnotationClassesProvider? = null var optionalAnnotationClassesProviderForBinariesFromIncrementalCompilation: OptionalAnnotationClassesProvider? = null
incrementalCompilationContext?.let { incrementalCompilationContext?.let {
@@ -138,7 +138,7 @@ object FirJvmSessionFactory : FirAbstractSessionFactory() {
symbolProviderForBinariesFromIncrementalCompilation, symbolProviderForBinariesFromIncrementalCompilation,
generatedSymbolsProvider, generatedSymbolsProvider,
javaSymbolProvider, javaSymbolProvider,
syntheticFunctionalInterfaceProvider, syntheticFunctionInterfaceProvider,
*dependencies.toTypedArray(), *dependencies.toTypedArray(),
optionalAnnotationClassesProviderForBinariesFromIncrementalCompilation, optionalAnnotationClassesProviderForBinariesFromIncrementalCompilation,
) )
@@ -15,7 +15,7 @@ import org.jetbrains.kotlin.fir.java.FirProjectSessionProvider
import org.jetbrains.kotlin.fir.resolve.calls.ConeCallConflictResolverFactory import org.jetbrains.kotlin.fir.resolve.calls.ConeCallConflictResolverFactory
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirBuiltinSymbolProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirBuiltinSymbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirCloneableSymbolProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirCloneableSymbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionalInterfaceProvider import org.jetbrains.kotlin.fir.resolve.providers.impl.FirExtensionSyntheticFunctionInterfaceProvider
import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider
import org.jetbrains.kotlin.fir.scopes.FirPlatformClassMapper import org.jetbrains.kotlin.fir.scopes.FirPlatformClassMapper
import org.jetbrains.kotlin.library.metadata.resolver.KotlinResolvedLibrary import org.jetbrains.kotlin.library.metadata.resolver.KotlinResolvedLibrary
@@ -41,7 +41,7 @@ object FirNativeSessionFactory : FirAbstractSessionFactory() {
listOf( listOf(
KlibBasedSymbolProvider(session, moduleDataProvider, kotlinScopeProvider, resolvedLibraries), KlibBasedSymbolProvider(session, moduleDataProvider, kotlinScopeProvider, resolvedLibraries),
FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider), FirBuiltinSymbolProvider(session, builtinsModuleData, kotlinScopeProvider),
FirExtensionSyntheticFunctionalInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider), FirExtensionSyntheticFunctionInterfaceProvider(session, builtinsModuleData, kotlinScopeProvider),
FirCloneableSymbolProvider(session, builtinsModuleData, kotlinScopeProvider), FirCloneableSymbolProvider(session, builtinsModuleData, kotlinScopeProvider),
) )
}) })
@@ -69,11 +69,11 @@ object FirNativeSessionFactory : FirAbstractSessionFactory() {
}, },
registerExtraCheckers = { it.registerNativeCheckers() }, registerExtraCheckers = { it.registerNativeCheckers() },
createKotlinScopeProvider = { FirKotlinScopeProvider { _, declaredMemberScope, _, _ -> declaredMemberScope } }, createKotlinScopeProvider = { FirKotlinScopeProvider { _, declaredMemberScope, _, _ -> declaredMemberScope } },
createProviders = { _, _, symbolProvider, generatedSymbolsProvider, syntheticFunctionalInterfaceProvider, dependencies -> createProviders = { _, _, symbolProvider, generatedSymbolsProvider, syntheticFunctionInterfaceProvider, dependencies ->
listOfNotNull( listOfNotNull(
symbolProvider, symbolProvider,
generatedSymbolsProvider, generatedSymbolsProvider,
syntheticFunctionalInterfaceProvider, syntheticFunctionInterfaceProvider,
*dependencies.toTypedArray(), *dependencies.toTypedArray(),
) )
} }
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.deserialization package org.jetbrains.kotlin.fir.deserialization
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirModuleData import org.jetbrains.kotlin.fir.FirModuleData
import org.jetbrains.kotlin.fir.computeTypeAttributes import org.jetbrains.kotlin.fir.computeTypeAttributes
import org.jetbrains.kotlin.fir.declarations.FirDeclarationOrigin import org.jetbrains.kotlin.fir.declarations.FirDeclarationOrigin
@@ -202,7 +202,7 @@ class FirTypeDeserializer(
val suspendReturnType = continuationType.typeArguments.single() as ConeKotlinTypeProjection val suspendReturnType = continuationType.typeArguments.single() as ConeKotlinTypeProjection
val valueParameters = arguments.dropLast(2) val valueParameters = arguments.dropLast(2)
val kind = FunctionalTypeKind.SuspendFunction val kind = FunctionTypeKind.SuspendFunction
return ConeClassLikeTypeImpl( return ConeClassLikeTypeImpl(
ClassId(kind.packageFqName, kind.numberedClassName(valueParameters.size)).toLookupTag(), ClassId(kind.packageFqName, kind.numberedClassName(valueParameters.size)).toLookupTag(),
(valueParameters + suspendReturnType).toTypedArray(), (valueParameters + suspendReturnType).toTypedArray(),
@@ -222,7 +222,7 @@ class FirTypeDeserializer(
1 -> { 1 -> {
val arity = arguments.size - 1 val arity = arguments.size - 1
if (arity >= 0) { if (arity >= 0) {
val kind = FunctionalTypeKind.SuspendFunction val kind = FunctionTypeKind.SuspendFunction
ConeClassLikeTypeImpl( ConeClassLikeTypeImpl(
ClassId(kind.packageFqName, kind.numberedClassName(arity)).toLookupTag(), ClassId(kind.packageFqName, kind.numberedClassName(arity)).toLookupTag(),
arguments, arguments,
@@ -40,7 +40,7 @@ open class FirBuiltinSymbolProvider(
val moduleData: FirModuleData, val moduleData: FirModuleData,
val kotlinScopeProvider: FirKotlinScopeProvider val kotlinScopeProvider: FirKotlinScopeProvider
) : FirSymbolProvider(session) { ) : FirSymbolProvider(session) {
private val syntheticFunctionalInterfaceProvider = FirBuiltinSyntheticFunctionalInterfaceProvider( private val syntheticFunctionInterfaceProvider = FirBuiltinSyntheticFunctionInterfaceProvider(
session, session,
moduleData, moduleData,
kotlinScopeProvider kotlinScopeProvider
@@ -68,7 +68,7 @@ open class FirBuiltinSymbolProvider(
override fun getClassLikeSymbolByClassId(classId: ClassId): FirRegularClassSymbol? { override fun getClassLikeSymbolByClassId(classId: ClassId): FirRegularClassSymbol? {
return allPackageFragments[classId.packageFqName]?.firstNotNullOfOrNull { return allPackageFragments[classId.packageFqName]?.firstNotNullOfOrNull {
it.getClassLikeSymbolByClassId(classId) it.getClassLikeSymbolByClassId(classId)
} ?: syntheticFunctionalInterfaceProvider.getClassLikeSymbolByClassId(classId) } ?: syntheticFunctionInterfaceProvider.getClassLikeSymbolByClassId(classId)
} }
override fun computePackageSetWithTopLevelCallables(): Set<String> = override fun computePackageSetWithTopLevelCallables(): Set<String> =
@@ -6,7 +6,7 @@
package org.jetbrains.kotlin.fir.serialization package org.jetbrains.kotlin.fir.serialization
import org.jetbrains.kotlin.builtins.StandardNames import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
@@ -682,7 +682,7 @@ class FirElementSerializer private constructor(
return lowerBound return lowerBound
} }
is ConeClassLikeType -> { is ConeClassLikeType -> {
if (type.functionalTypeKind(session) == FunctionalTypeKind.SuspendFunction) { if (type.functionTypeKind(session) == FunctionTypeKind.SuspendFunction) {
val runtimeFunctionType = type.suspendFunctionTypeToFunctionTypeWithContinuation( val runtimeFunctionType = type.suspendFunctionTypeToFunctionTypeWithContinuation(
session, StandardClassIds.Continuation session, StandardClassIds.Continuation
) )
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.serialization package org.jetbrains.kotlin.fir.serialization
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.diagnostics.ConeIntermediateDiagnostic import org.jetbrains.kotlin.fir.diagnostics.ConeIntermediateDiagnostic
import org.jetbrains.kotlin.fir.languageVersionSettings import org.jetbrains.kotlin.fir.languageVersionSettings
@@ -25,16 +25,16 @@ class TypeApproximatorForMetadataSerializer(session: FirSession) :
} }
fun ConeKotlinType.suspendFunctionTypeToFunctionTypeWithContinuation(session: FirSession, continuationClassId: ClassId): ConeClassLikeType { fun ConeKotlinType.suspendFunctionTypeToFunctionTypeWithContinuation(session: FirSession, continuationClassId: ClassId): ConeClassLikeType {
require(this.isSuspendFunctionType(session)) require(this.isSuspendOrKSuspendFunctionType(session))
val kind = val kind =
if (isReflectFunctionalType(session)) FunctionalTypeKind.KFunction if (isReflectFunctionType(session)) FunctionTypeKind.KFunction
else FunctionalTypeKind.Function else FunctionTypeKind.Function
val fullyExpandedType = type.fullyExpandedType(session) val fullyExpandedType = type.fullyExpandedType(session)
val typeArguments = fullyExpandedType.typeArguments val typeArguments = fullyExpandedType.typeArguments
val functionalTypeId = ClassId(kind.packageFqName, kind.numberedClassName(typeArguments.size)) val functionTypeId = ClassId(kind.packageFqName, kind.numberedClassName(typeArguments.size))
val lastTypeArgument = typeArguments.last() val lastTypeArgument = typeArguments.last()
return ConeClassLikeTypeImpl( return ConeClassLikeTypeImpl(
functionalTypeId.toLookupTag(), functionTypeId.toLookupTag(),
typeArguments = (typeArguments.dropLast(1) + continuationClassId.toLookupTag().constructClassType( typeArguments = (typeArguments.dropLast(1) + continuationClassId.toLookupTag().constructClassType(
arrayOf(lastTypeArgument), arrayOf(lastTypeArgument),
isNullable = false isNullable = false
@@ -233,8 +233,8 @@ class FirJvmSerializerExtension(
private fun FirFunction.needsInlineParameterNullCheckRequirement(): Boolean = private fun FirFunction.needsInlineParameterNullCheckRequirement(): Boolean =
this is FirSimpleFunction && isInline && !isSuspend && !isParamAssertionsDisabled && this is FirSimpleFunction && isInline && !isSuspend && !isParamAssertionsDisabled &&
!Visibilities.isPrivate(visibility) && !Visibilities.isPrivate(visibility) &&
(valueParameters.any { it.returnTypeRef.coneType.isSomeFunctionalType(session) } || (valueParameters.any { it.returnTypeRef.coneType.isSomeFunctionType(session) } ||
receiverParameter?.typeRef?.coneType?.isSomeFunctionalType(session) == true) receiverParameter?.typeRef?.coneType?.isSomeFunctionType(session) == true)
override fun serializeProperty( override fun serializeProperty(
property: FirProperty, property: FirProperty,
@@ -172,8 +172,8 @@ class FirJvmTypeMapper(val session: FirSession) : FirSessionComponent {
val parameters = classifier?.typeParameters.orEmpty().map { it.symbol } val parameters = classifier?.typeParameters.orEmpty().map { it.symbol }
val arguments = type.arguments val arguments = type.arguments
if ((defaultType.isSimpleFunctionType(session) && arguments.size > BuiltInFunctionArity.BIG_ARITY) if ((defaultType.isBasicFunctionType(session) && arguments.size > BuiltInFunctionArity.BIG_ARITY)
|| defaultType.isReflectFunctionalType(session) || defaultType.isReflectFunctionType(session)
) { ) {
writeGenericArguments(sw, listOf(arguments.last()), listOf(parameters.last()), mode) writeGenericArguments(sw, listOf(arguments.last()), listOf(parameters.last()), mode)
return return
@@ -264,7 +264,7 @@ class ConeTypeSystemCommonBackendContextForTypeMapping(
override fun SimpleTypeMarker.isSuspendFunction(): Boolean { override fun SimpleTypeMarker.isSuspendFunction(): Boolean {
require(this is ConeSimpleKotlinType) require(this is ConeSimpleKotlinType)
return isSuspendFunctionType(session) return isSuspendOrKSuspendFunctionType(session)
} }
override fun SimpleTypeMarker.isKClass(): Boolean { override fun SimpleTypeMarker.isKClass(): Boolean {
@@ -538,7 +538,7 @@ class Fir2IrDeclarationStorage(
?: if (isLambda) SpecialNames.ANONYMOUS else Name.special("<no name provided>") ?: if (isLambda) SpecialNames.ANONYMOUS else Name.special("<no name provided>")
val visibility = simpleFunction?.visibility ?: Visibilities.Local val visibility = simpleFunction?.visibility ?: Visibilities.Local
val isSuspend = val isSuspend =
if (isLambda) ((function as FirAnonymousFunction).typeRef as? FirResolvedTypeRef)?.type?.isSuspendFunctionType(session) == true if (isLambda) ((function as FirAnonymousFunction).typeRef as? FirResolvedTypeRef)?.type?.isSuspendOrKSuspendFunctionType(session) == true
else simpleFunction?.isSuspend == true else simpleFunction?.isSuspend == true
val created = function.convertWithOffsets { startOffset, endOffset -> val created = function.convertWithOffsets { startOffset, endOffset ->
val result = declareIrSimpleFunction(signature, simpleFunction?.containerSource) { symbol -> val result = declareIrSimpleFunction(signature, simpleFunction?.containerSource) { symbol ->
@@ -134,7 +134,7 @@ internal class AdapterGenerator(
} }
internal fun ConeKotlinType.kFunctionTypeToFunctionType(): IrSimpleType = internal fun ConeKotlinType.kFunctionTypeToFunctionType(): IrSimpleType =
reflectFunctionalTypeToNonReflectFunctionalType(session).toIrType() as IrSimpleType reflectFunctionTypeToNonReflectFunctionType(session).toIrType() as IrSimpleType
internal fun generateAdaptedCallableReference( internal fun generateAdaptedCallableReference(
callableReferenceAccess: FirCallableReferenceAccess, callableReferenceAccess: FirCallableReferenceAccess,
@@ -479,7 +479,7 @@ internal class AdapterGenerator(
} }
// If the expected type is a built-in functional type, we don't need SAM conversion. // If the expected type is a built-in functional type, we don't need SAM conversion.
val expectedType = argument.getExpectedType(parameter) val expectedType = argument.getExpectedType(parameter)
if (expectedType is ConeTypeParameterType || expectedType.isSomeFunctionalType(session)) { if (expectedType is ConeTypeParameterType || expectedType.isSomeFunctionType(session)) {
return false return false
} }
// On the other hand, the actual type should be either a functional type or a subtype of a class that has a contributed `invoke`. // On the other hand, the actual type should be either a functional type or a subtype of a class that has a contributed `invoke`.
@@ -514,10 +514,10 @@ internal class AdapterGenerator(
return this return this
} }
// Expect the expected type to be a suspend functional type. // Expect the expected type to be a suspend functional type.
if (!parameterType.isSuspendFunctionType(session)) { if (!parameterType.isSuspendOrKSuspendFunctionType(session)) {
return this return this
} }
val expectedFunctionalType = parameterType.customFunctionalTypeToSimpleFunctionalType(session) val expectedFunctionalType = parameterType.customFunctionTypeToSimpleFunctionType(session)
if (this is IrVararg) { if (this is IrVararg) {
// element-wise conversion if and only if we can build 1-to-1 mapping for elements. // element-wise conversion if and only if we can build 1-to-1 mapping for elements.
return applyConversionOnVararg(argument) { firVarargArgument -> return applyConversionOnVararg(argument) { firVarargArgument ->
@@ -546,9 +546,9 @@ internal class AdapterGenerator(
argument: FirExpression argument: FirExpression
): IrSimpleFunctionSymbol? { ): IrSimpleFunctionSymbol? {
val argumentType = argument.typeRef.coneType val argumentType = argument.typeRef.coneType
val argumentTypeWithInvoke = argumentType.findSubtypeOfSimpleFunctionalType(session, expectedFunctionalType) ?: return null val argumentTypeWithInvoke = argumentType.findSubtypeOfBasicFunctionType(session, expectedFunctionalType) ?: return null
return if (argumentTypeWithInvoke.isSomeFunctionalType(session)) { return if (argumentTypeWithInvoke.isSomeFunctionType(session)) {
(argumentTypeWithInvoke as? ConeClassLikeType)?.findBaseInvokeSymbol(session, scopeSession) (argumentTypeWithInvoke as? ConeClassLikeType)?.findBaseInvokeSymbol(session, scopeSession)
} else { } else {
argumentTypeWithInvoke.findContributedInvokeSymbol( argumentTypeWithInvoke.findContributedInvokeSymbol(
@@ -188,7 +188,7 @@ class CallAndReferenceGenerator(
// This would cause ClassCastException in case of usual type approximation, // This would cause ClassCastException in case of usual type approximation,
// because '{ X1 & ... & Xm }' would be approximated to 'Nothing'. // because '{ X1 & ... & Xm }' would be approximated to 'Nothing'.
// JVM_OLD just relies on type mapping for generic argument types in such case. // JVM_OLD just relies on type mapping for generic argument types in such case.
if (!kotlinType.isReflectFunctionalType(session)) if (!kotlinType.isReflectFunctionType(session))
return kotlinType return kotlinType
if (kotlinType !is ConeSimpleKotlinType) if (kotlinType !is ConeSimpleKotlinType)
return kotlinType return kotlinType
@@ -18,7 +18,7 @@ import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
import org.jetbrains.kotlin.fir.types.functionalTypeService import org.jetbrains.kotlin.fir.types.functionTypeService
import org.jetbrains.kotlin.name.CallableId import org.jetbrains.kotlin.name.CallableId
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.FqName
@@ -116,7 +116,7 @@ class FirCachingCompositeSymbolProvider(
} }
private fun isNameForFunctionClass(classId: ClassId): Boolean { private fun isNameForFunctionClass(classId: ClassId): Boolean {
return session.functionalTypeService.getKindByClassNamePrefix(classId.packageFqName, classId.shortClassName.asString()) != null return session.functionTypeService.getKindByClassNamePrefix(classId.packageFqName, classId.shortClassName.asString()) != null
} }
@OptIn(FirSymbolProviderInternals::class) @OptIn(FirSymbolProviderInternals::class)
@@ -5,9 +5,9 @@
package org.jetbrains.kotlin.fir.resolve.providers.impl package org.jetbrains.kotlin.fir.resolve.providers.impl
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.isBuiltin import org.jetbrains.kotlin.builtins.functions.isBuiltin
import org.jetbrains.kotlin.builtins.functions.isSuspendType import org.jetbrains.kotlin.builtins.functions.isSuspendOrKSuspendFunction
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.EffectiveVisibility import org.jetbrains.kotlin.descriptors.EffectiveVisibility
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
@@ -39,14 +39,14 @@ import org.jetbrains.kotlin.types.Variance
import org.jetbrains.kotlin.util.OperatorNameConventions import org.jetbrains.kotlin.util.OperatorNameConventions
/* /*
* Provides functional interfaces for functional kinds from compiler plugins * Provides function interfaces for function kinds from compiler plugins
*/ */
class FirExtensionSyntheticFunctionalInterfaceProvider( class FirExtensionSyntheticFunctionInterfaceProvider(
session: FirSession, session: FirSession,
moduleData: FirModuleData, moduleData: FirModuleData,
kotlinScopeProvider: FirKotlinScopeProvider kotlinScopeProvider: FirKotlinScopeProvider
) : FirSyntheticFunctionalInterfaceProviderBase(session, moduleData, kotlinScopeProvider) { ) : FirSyntheticFunctionInterfaceProviderBase(session, moduleData, kotlinScopeProvider) {
override fun FunctionalTypeKind.isAcceptable(): Boolean { override fun FunctionTypeKind.isAcceptable(): Boolean {
return !this.isBuiltin return !this.isBuiltin
} }
} }
@@ -54,17 +54,17 @@ class FirExtensionSyntheticFunctionalInterfaceProvider(
/* /*
* Provides kotlin.FunctionN, kotlin.coroutines.SuspendFunctionN, kotlin.reflect.KFunctionN and kotlin.reflect.KSuspendFunctionN * Provides kotlin.FunctionN, kotlin.coroutines.SuspendFunctionN, kotlin.reflect.KFunctionN and kotlin.reflect.KSuspendFunctionN
*/ */
class FirBuiltinSyntheticFunctionalInterfaceProvider( class FirBuiltinSyntheticFunctionInterfaceProvider(
session: FirSession, session: FirSession,
moduleData: FirModuleData, moduleData: FirModuleData,
kotlinScopeProvider: FirKotlinScopeProvider kotlinScopeProvider: FirKotlinScopeProvider
) : FirSyntheticFunctionalInterfaceProviderBase(session, moduleData, kotlinScopeProvider) { ) : FirSyntheticFunctionInterfaceProviderBase(session, moduleData, kotlinScopeProvider) {
override fun FunctionalTypeKind.isAcceptable(): Boolean { override fun FunctionTypeKind.isAcceptable(): Boolean {
return this.isBuiltin return this.isBuiltin
} }
} }
abstract class FirSyntheticFunctionalInterfaceProviderBase( abstract class FirSyntheticFunctionInterfaceProviderBase(
session: FirSession, session: FirSession,
val moduleData: FirModuleData, val moduleData: FirModuleData,
val kotlinScopeProvider: FirKotlinScopeProvider val kotlinScopeProvider: FirKotlinScopeProvider
@@ -83,7 +83,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
override fun getTopLevelPropertySymbolsTo(destination: MutableList<FirPropertySymbol>, packageFqName: FqName, name: Name) {} override fun getTopLevelPropertySymbolsTo(destination: MutableList<FirPropertySymbol>, packageFqName: FqName, name: Name) {}
override fun getPackage(fqName: FqName): FqName? { override fun getPackage(fqName: FqName): FqName? {
return fqName.takeIf { session.functionalTypeService.hasKindWithSpecificPackage(it) } return fqName.takeIf { session.functionTypeService.hasKindWithSpecificPackage(it) }
} }
override fun computePackageSetWithTopLevelCallables(): Set<String> { override fun computePackageSetWithTopLevelCallables(): Set<String> {
@@ -91,7 +91,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
} }
/** /**
* This method has no sence for synthetic functional interfaces * This method has no sense for synthetic function interfaces
*/ */
override fun knownTopLevelClassifiersInPackage(packageFqName: FqName): Set<String>? { override fun knownTopLevelClassifiersInPackage(packageFqName: FqName): Set<String>? {
return emptySet() return emptySet()
@@ -101,20 +101,20 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
return emptySet() return emptySet()
} }
private val cache = moduleData.session.firCachesFactory.createCache(::createSyntheticFunctionalInterface) private val cache = moduleData.session.firCachesFactory.createCache(::createSyntheticFunctionInterface)
protected abstract fun FunctionalTypeKind.isAcceptable(): Boolean protected abstract fun FunctionTypeKind.isAcceptable(): Boolean
private fun createSyntheticFunctionalInterface(classId: ClassId): FirRegularClassSymbol? { private fun createSyntheticFunctionInterface(classId: ClassId): FirRegularClassSymbol? {
return with(classId) { return with(classId) {
val className = relativeClassName.asString() val className = relativeClassName.asString()
val kind = session.functionalTypeService.getKindByClassNamePrefix(packageFqName, className) ?: return null val kind = session.functionTypeService.getKindByClassNamePrefix(packageFqName, className) ?: return null
if (!kind.isAcceptable()) return null if (!kind.isAcceptable()) return null
val prefix = kind.classNamePrefix val prefix = kind.classNamePrefix
val arity = className.substring(prefix.length).toIntOrNull() ?: return null val arity = className.substring(prefix.length).toIntOrNull() ?: return null
FirRegularClassSymbol(classId).apply symbol@{ FirRegularClassSymbol(classId).apply symbol@{
buildRegularClass klass@{ buildRegularClass klass@{
moduleData = this@FirSyntheticFunctionalInterfaceProviderBase.moduleData moduleData = this@FirSyntheticFunctionInterfaceProviderBase.moduleData
origin = FirDeclarationOrigin.BuiltIns origin = FirDeclarationOrigin.BuiltIns
name = relativeClassName.shortName() name = relativeClassName.shortName()
status = FirResolvedDeclarationStatusImpl( status = FirResolvedDeclarationStatusImpl(
@@ -136,7 +136,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
typeParameters.addAll( typeParameters.addAll(
(1..arity).map { (1..arity).map {
buildTypeParameter { buildTypeParameter {
moduleData = this@FirSyntheticFunctionalInterfaceProviderBase.moduleData moduleData = this@FirSyntheticFunctionInterfaceProviderBase.moduleData
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
origin = FirDeclarationOrigin.BuiltIns origin = FirDeclarationOrigin.BuiltIns
name = Name.identifier("P$it") name = Name.identifier("P$it")
@@ -150,7 +150,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
) )
typeParameters.add( typeParameters.add(
buildTypeParameter { buildTypeParameter {
moduleData = this@FirSyntheticFunctionalInterfaceProviderBase.moduleData moduleData = this@FirSyntheticFunctionInterfaceProviderBase.moduleData
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
origin = FirDeclarationOrigin.BuiltIns origin = FirDeclarationOrigin.BuiltIns
name = Name.identifier("R") name = Name.identifier("R")
@@ -175,13 +175,13 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
isInline = false isInline = false
isTailRec = false isTailRec = false
isExternal = false isExternal = false
isSuspend = kind.isSuspendType isSuspend = kind.isSuspendOrKSuspendFunction
} }
val typeArguments = typeParameters.map { val typeArguments = typeParameters.map {
ConeTypeParameterTypeImpl(it.symbol.toLookupTag(), false).toFirResolvedTypeRef() ConeTypeParameterTypeImpl(it.symbol.toLookupTag(), false).toFirResolvedTypeRef()
} }
fun createSuperType(kind: FunctionalTypeKind): FirResolvedTypeRef { fun createSuperType(kind: FunctionTypeKind): FirResolvedTypeRef {
return kind.classId(arity).toLookupTag() return kind.classId(arity).toLookupTag()
.constructClassType(typeArguments.map { it.type }.toTypedArray(), isNullable = false) .constructClassType(typeArguments.map { it.type }.toTypedArray(), isNullable = false)
.toFirResolvedTypeRef() .toFirResolvedTypeRef()
@@ -200,7 +200,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
addDeclaration( addDeclaration(
buildSimpleFunction { buildSimpleFunction {
moduleData = this@FirSyntheticFunctionalInterfaceProviderBase.moduleData moduleData = this@FirSyntheticFunctionInterfaceProviderBase.moduleData
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
origin = FirDeclarationOrigin.BuiltIns origin = FirDeclarationOrigin.BuiltIns
returnTypeRef = typeArguments.last() returnTypeRef = typeArguments.last()
@@ -213,7 +213,7 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
valueParameters += typeArguments.dropLast(1).mapIndexed { index, typeArgument -> valueParameters += typeArguments.dropLast(1).mapIndexed { index, typeArgument ->
val parameterName = Name.identifier("p${index + 1}") val parameterName = Name.identifier("p${index + 1}")
buildValueParameter { buildValueParameter {
moduleData = this@FirSyntheticFunctionalInterfaceProviderBase.moduleData moduleData = this@FirSyntheticFunctionInterfaceProviderBase.moduleData
containingFunctionSymbol = this@buildSimpleFunction.symbol containingFunctionSymbol = this@buildSimpleFunction.symbol
origin = FirDeclarationOrigin.BuiltIns origin = FirDeclarationOrigin.BuiltIns
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
@@ -242,5 +242,5 @@ abstract class FirSyntheticFunctionalInterfaceProviderBase(
} }
} }
private fun FunctionalTypeKind.classId(arity: Int) = ClassId(packageFqName, numberedClassName(arity)) private fun FunctionTypeKind.classId(arity: Int) = ClassId(packageFqName, numberedClassName(arity))
} }
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.types package org.jetbrains.kotlin.fir.types
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.fir.declarations.utils.modality import org.jetbrains.kotlin.fir.declarations.utils.modality
import org.jetbrains.kotlin.fir.diagnostics.ConeIntermediateDiagnostic import org.jetbrains.kotlin.fir.diagnostics.ConeIntermediateDiagnostic
@@ -67,7 +67,7 @@ interface ConeInferenceContext : TypeSystemInferenceExtensionContext, ConeTypeCo
): SimpleTypeMarker { ): SimpleTypeMarker {
val attributesList = attributes?.filterIsInstanceTo<ConeAttribute<*>, MutableList<ConeAttribute<*>>>(mutableListOf()) val attributesList = attributes?.filterIsInstanceTo<ConeAttribute<*>, MutableList<ConeAttribute<*>>>(mutableListOf())
val coneAttributes: ConeAttributes = if (isExtensionFunction) { val coneAttributes: ConeAttributes = if (isExtensionFunction) {
require(constructor is ConeClassLikeLookupTag && constructor.isSomeFunctionalType(session)) require(constructor is ConeClassLikeLookupTag && constructor.isSomeFunctionType(session))
// We don't want to create new instance of ConeAttributes which // We don't want to create new instance of ConeAttributes which
// contains only CompilerConeAttributes.ExtensionFunctionType // contains only CompilerConeAttributes.ExtensionFunctionType
// to avoid memory consumption // to avoid memory consumption
@@ -224,10 +224,10 @@ interface ConeInferenceContext : TypeSystemInferenceExtensionContext, ConeTypeCo
return this.typeConstructor().isUnitTypeConstructor() && !this.isNullable return this.typeConstructor().isUnitTypeConstructor() && !this.isNullable
} }
override fun KotlinTypeMarker.isBuiltinFunctionalTypeOrSubtype(): Boolean { override fun KotlinTypeMarker.isBuiltinFunctionTypeOrSubtype(): Boolean {
require(this is ConeKotlinType) require(this is ConeKotlinType)
return this.isTypeOrSubtypeOf { return this.isTypeOrSubtypeOf {
(it.lowerBoundIfFlexible() as ConeKotlinType).isSomeFunctionalType(session) (it.lowerBoundIfFlexible() as ConeKotlinType).isSomeFunctionType(session)
} }
} }
@@ -464,7 +464,7 @@ interface ConeInferenceContext : TypeSystemInferenceExtensionContext, ConeTypeCo
override fun KotlinTypeMarker.isFunctionOrKFunctionWithAnySuspendability(): Boolean { override fun KotlinTypeMarker.isFunctionOrKFunctionWithAnySuspendability(): Boolean {
require(this is ConeKotlinType) require(this is ConeKotlinType)
return this.isSomeFunctionalType(session) return this.isSomeFunctionType(session)
} }
fun ConeKotlinType.isTypeOrSubtypeOf(predicate: (ConeKotlinType) -> Boolean): Boolean { fun ConeKotlinType.isTypeOrSubtypeOf(predicate: (ConeKotlinType) -> Boolean): Boolean {
@@ -495,34 +495,35 @@ interface ConeInferenceContext : TypeSystemInferenceExtensionContext, ConeTypeCo
return (this.lowerBoundIfFlexible() as? ConeKotlinType)?.isExtensionFunctionType(session) == true return (this.lowerBoundIfFlexible() as? ConeKotlinType)?.isExtensionFunctionType(session) == true
} }
override fun KotlinTypeMarker.extractArgumentsForFunctionalTypeOrSubtype(): List<KotlinTypeMarker> { override fun KotlinTypeMarker.extractArgumentsForFunctionTypeOrSubtype(): List<KotlinTypeMarker> {
val builtInFunctionalType = getFunctionalTypeFromSupertypes() as ConeKotlinType val builtInFunctionType = getFunctionTypeFromSupertypes() as ConeKotlinType
return buildList { return buildList {
// excluding return type // excluding return type
for (index in 0 until builtInFunctionalType.argumentsCount() - 1) { for (index in 0 until builtInFunctionType.argumentsCount() - 1) {
add(builtInFunctionalType.getArgument(index).getType()) add(builtInFunctionType.getArgument(index).getType())
} }
} }
} }
override fun KotlinTypeMarker.getFunctionalTypeFromSupertypes(): KotlinTypeMarker { override fun KotlinTypeMarker.getFunctionTypeFromSupertypes(): KotlinTypeMarker {
require(this is ConeKotlinType) require(this is ConeKotlinType)
assert(this.isBuiltinFunctionalTypeOrSubtype()) { assert(this.isBuiltinFunctionTypeOrSubtype()) {
"Not a function type or subtype: ${this.renderForDebugging()}" "Not a function type or subtype: ${this.renderForDebugging()}"
} }
return fullyExpandedType(session).let { return fullyExpandedType(session).let {
val simpleType = it.lowerBoundIfFlexible() val simpleType = it.lowerBoundIfFlexible()
if ((simpleType as ConeKotlinType).isSomeFunctionalType(session)) if ((simpleType as ConeKotlinType).isSomeFunctionType(session))
this this
else { else {
var functionalSupertype: KotlinTypeMarker? = null var functionalSupertype: KotlinTypeMarker? = null
simpleType.anySuperTypeConstructor { type -> simpleType.anySuperTypeConstructor { type ->
simpleType.fastCorrespondingSupertypes(type.typeConstructor())?.any { superType -> simpleType.fastCorrespondingSupertypes(type.typeConstructor())?.any { superType ->
val isFunctional = (superType as ConeKotlinType).isSomeFunctionalType(session) val isFunction = (superType as ConeKotlinType).isSomeFunctionType(session)
if (isFunctional) if (isFunction) {
functionalSupertype = superType functionalSupertype = superType
isFunctional }
isFunction
} ?: false } ?: false
} }
functionalSupertype ?: error("Failed to find functional supertype for $simpleType") functionalSupertype ?: error("Failed to find functional supertype for $simpleType")
@@ -530,16 +531,16 @@ interface ConeInferenceContext : TypeSystemInferenceExtensionContext, ConeTypeCo
} }
} }
override fun KotlinTypeMarker.functionalTypeKind(): FunctionalTypeKind? { override fun KotlinTypeMarker.functionTypeKind(): FunctionTypeKind? {
require(this is ConeKotlinType) require(this is ConeKotlinType)
return this.functionalTypeKind(session) return this.functionTypeKind(session)
} }
override fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker { override fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker {
return kind.nonReflectKind().numberedClassId(parametersNumber).toLookupTag() return kind.nonReflectKind().numberedClassId(parametersNumber).toLookupTag()
} }
override fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker { override fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker {
return kind.reflectKind().numberedClassId(parametersNumber).toLookupTag() return kind.reflectKind().numberedClassId(parametersNumber).toLookupTag()
} }
@@ -5,30 +5,30 @@
package org.jetbrains.kotlin.fir.types package org.jetbrains.kotlin.fir.types
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKindExtractor import org.jetbrains.kotlin.builtins.functions.FunctionTypeKindExtractor
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId
import org.jetbrains.kotlin.fir.declarations.utils.isSuspend import org.jetbrains.kotlin.fir.declarations.utils.isSuspend
import org.jetbrains.kotlin.fir.extensions.FirFunctionalTypeKindExtension import org.jetbrains.kotlin.fir.extensions.FirFunctionTypeKindExtension
import org.jetbrains.kotlin.fir.extensions.extensionService import org.jetbrains.kotlin.fir.extensions.extensionService
import org.jetbrains.kotlin.fir.extensions.functionalTypeKindExtensions import org.jetbrains.kotlin.fir.extensions.functionTypeKindExtensions
import org.jetbrains.kotlin.fir.symbols.impl.FirAnonymousFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirAnonymousFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
class FirFunctionalTypeKindServiceImpl(private val session: FirSession) : FirFunctionalTypeKindService() { class FirFunctionTypeKindServiceImpl(private val session: FirSession) : FirFunctionTypeKindService() {
private val nonReflectKindsFromExtensions = mutableListOf<FunctionalTypeKind>() private val nonReflectKindsFromExtensions = mutableListOf<FunctionTypeKind>()
override val extractor: FunctionalTypeKindExtractor = run { override val extractor: FunctionTypeKindExtractor = run {
val kinds = buildList { val kinds = buildList {
add(FunctionalTypeKind.Function) add(FunctionTypeKind.Function)
add(FunctionalTypeKind.SuspendFunction) add(FunctionTypeKind.SuspendFunction)
add(FunctionalTypeKind.KFunction) add(FunctionTypeKind.KFunction)
add(FunctionalTypeKind.KSuspendFunction) add(FunctionTypeKind.KSuspendFunction)
val registrar = object : FirFunctionalTypeKindExtension.FunctionalTypeKindRegistrar { val registrar = object : FirFunctionTypeKindExtension.FunctionTypeKindRegistrar {
override fun registerKind(nonReflectKind: FunctionalTypeKind, reflectKind: FunctionalTypeKind) { override fun registerKind(nonReflectKind: FunctionTypeKind, reflectKind: FunctionTypeKind) {
require(nonReflectKind.reflectKind() == reflectKind) require(nonReflectKind.reflectKind() == reflectKind)
require(reflectKind.nonReflectKind() == nonReflectKind) require(reflectKind.nonReflectKind() == nonReflectKind)
add(nonReflectKind) add(nonReflectKind)
@@ -37,7 +37,7 @@ class FirFunctionalTypeKindServiceImpl(private val session: FirSession) : FirFun
} }
} }
for (extension in session.extensionService.functionalTypeKindExtensions) { for (extension in session.extensionService.functionTypeKindExtensions) {
with(extension) { registrar.registerKinds() } with(extension) { registrar.registerKinds() }
} }
}.also { kinds -> }.also { kinds ->
@@ -47,18 +47,18 @@ class FirFunctionalTypeKindServiceImpl(private val session: FirSession) : FirFun
} }
} }
FunctionalTypeKindExtractor(kinds) FunctionTypeKindExtractor(kinds)
} }
override fun extractSingleSpecialKindForFunction(functionSymbol: FirFunctionSymbol<*>): FunctionalTypeKind? { override fun extractSingleSpecialKindForFunction(functionSymbol: FirFunctionSymbol<*>): FunctionTypeKind? {
if (nonReflectKindsFromExtensions.isEmpty()) { if (nonReflectKindsFromExtensions.isEmpty()) {
return FunctionalTypeKind.SuspendFunction.takeIf { functionSymbol.isSuspend } return FunctionTypeKind.SuspendFunction.takeIf { functionSymbol.isSuspend }
} }
return extractAllSpecialKindsForFunction(functionSymbol).singleOrNull() return extractAllSpecialKindsForFunction(functionSymbol).singleOrNull()
} }
override fun extractAllSpecialKindsForFunction(functionSymbol: FirFunctionSymbol<*>): List<FunctionalTypeKind> { override fun extractAllSpecialKindsForFunction(functionSymbol: FirFunctionSymbol<*>): List<FunctionTypeKind> {
return extractSpecialKindsImpl( return extractSpecialKindsImpl(
functionSymbol, functionSymbol,
{ isSuspend }, { isSuspend },
@@ -71,7 +71,7 @@ class FirFunctionalTypeKindServiceImpl(private val session: FirSession) : FirFun
) )
} }
override fun extractAllSpecialKindsForFunctionalTypeRef(typeRef: FirFunctionTypeRef): List<FunctionalTypeKind> { override fun extractAllSpecialKindsForFunctionTypeRef(typeRef: FirFunctionTypeRef): List<FunctionTypeKind> {
return extractSpecialKindsImpl(typeRef, { isSuspend }, { annotations.mapNotNull { it.toAnnotationClassId(session) } }) return extractSpecialKindsImpl(typeRef, { isSuspend }, { annotations.mapNotNull { it.toAnnotationClassId(session) } })
} }
@@ -79,10 +79,10 @@ class FirFunctionalTypeKindServiceImpl(private val session: FirSession) : FirFun
source: T, source: T,
isSuspend: T.() -> Boolean, isSuspend: T.() -> Boolean,
annotations: T.() -> List<ClassId> annotations: T.() -> List<ClassId>
): List<FunctionalTypeKind> { ): List<FunctionTypeKind> {
return buildList { return buildList {
if (source.isSuspend()) { if (source.isSuspend()) {
add(FunctionalTypeKind.SuspendFunction) add(FunctionTypeKind.SuspendFunction)
} }
if (nonReflectKindsFromExtensions.isNotEmpty()) { if (nonReflectKindsFromExtensions.isNotEmpty()) {
for (annotationClassId in source.annotations()) { for (annotationClassId in source.annotations()) {
@@ -5,8 +5,8 @@
package org.jetbrains.kotlin.fir.types package org.jetbrains.kotlin.fir.types
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.isRegularFunction import org.jetbrains.kotlin.builtins.functions.isBasicFunctionOrKFunction
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirClass
import org.jetbrains.kotlin.fir.declarations.FirFunction import org.jetbrains.kotlin.fir.declarations.FirFunction
@@ -28,85 +28,80 @@ import org.jetbrains.kotlin.types.AbstractTypeChecker
import org.jetbrains.kotlin.util.OperatorNameConventions import org.jetbrains.kotlin.util.OperatorNameConventions
import org.jetbrains.kotlin.utils.addToStdlib.runUnless import org.jetbrains.kotlin.utils.addToStdlib.runUnless
// ---------------------------------------------- is type is a functional type ---------------------------------------------- // ---------------------------------------------- is type is a function type ----------------------------------------------
fun ConeKotlinType.functionalTypeKind(session: FirSession): FunctionalTypeKind? { fun ConeKotlinType.functionTypeKind(session: FirSession): FunctionTypeKind? {
if (this !is ConeClassLikeType) return null if (this !is ConeClassLikeType) return null
return fullyExpandedType(session).lookupTag.functionalTypeKind(session) return fullyExpandedType(session).lookupTag.functionTypeKind(session)
} }
private fun ConeClassLikeLookupTag.functionalTypeKind(session: FirSession): FunctionalTypeKind? { private fun ConeClassLikeLookupTag.functionTypeKind(session: FirSession): FunctionTypeKind? {
val classId = classId val classId = classId
return session.functionalTypeService.getKindByClassNamePrefix(classId.packageFqName, classId.shortClassName.asString()) return session.functionTypeService.getKindByClassNamePrefix(classId.packageFqName, classId.shortClassName.asString())
} }
private inline fun ConeKotlinType.isFunctionalTypeWithPredicate( private inline fun ConeKotlinType.isFunctionTypeWithPredicate(
session: FirSession, session: FirSession,
errorOnNotFunctionalType: Boolean = false, errorOnNotFunctionType: Boolean = false,
predicate: (FunctionalTypeKind) -> Boolean predicate: (FunctionTypeKind) -> Boolean
): Boolean { ): Boolean {
val kind = functionalTypeKind(session) val kind = functionTypeKind(session)
?: if (errorOnNotFunctionalType) error("$this is not a functional type") else return false ?: if (errorOnNotFunctionType) error("$this is not a function type") else return false
return predicate(kind) return predicate(kind)
} }
// Function // Function
fun ConeKotlinType.isSimpleFunctionType(session: FirSession): Boolean { fun ConeKotlinType.isBasicFunctionType(session: FirSession): Boolean {
return isFunctionalTypeWithPredicate(session) { it == FunctionalTypeKind.Function } return isFunctionTypeWithPredicate(session) { it == FunctionTypeKind.Function }
}
// Function, SuspendFunction, [Custom]Function
fun ConeKotlinType.isNonReflectFunctionalType(session: FirSession): Boolean {
return isFunctionalTypeWithPredicate(session) { !it.isReflectType }
} }
// SuspendFunction, KSuspendFunction // SuspendFunction, KSuspendFunction
fun ConeKotlinType.isSuspendFunctionType(session: FirSession): Boolean { fun ConeKotlinType.isSuspendOrKSuspendFunctionType(session: FirSession): Boolean {
return isFunctionalTypeWithPredicate(session) { return isFunctionTypeWithPredicate(session) {
it == FunctionalTypeKind.SuspendFunction || it == FunctionalTypeKind.KSuspendFunction it == FunctionTypeKind.SuspendFunction || it == FunctionTypeKind.KSuspendFunction
} }
} }
// KFunction, KSuspendFunction, K[Custom]Function // KFunction, KSuspendFunction, K[Custom]Function
fun ConeKotlinType.isReflectFunctionalType(session: FirSession): Boolean { fun ConeKotlinType.isReflectFunctionType(session: FirSession): Boolean {
return isFunctionalTypeWithPredicate(session) { it.isReflectType } return isFunctionTypeWithPredicate(session) { it.isReflectType }
}
// Function, SuspendFunction, [Custom]Function
fun ConeKotlinType.isNonReflectFunctionType(session: FirSession): Boolean {
return isFunctionTypeWithPredicate(session) { !it.isReflectType }
} }
// Function, SuspendFunction, [Custom]Function, KFunction, KSuspendFunction, K[Custom]Function // Function, SuspendFunction, [Custom]Function, KFunction, KSuspendFunction, K[Custom]Function
fun ConeKotlinType.isSomeFunctionalType(session: FirSession): Boolean { fun ConeKotlinType.isSomeFunctionType(session: FirSession): Boolean {
return functionalTypeKind(session) != null return functionTypeKind(session) != null
} }
// Function, SuspendFunction, [Custom]Function, KFunction, KSuspendFunction, K[Custom]Function // Function, SuspendFunction, [Custom]Function, KFunction, KSuspendFunction, K[Custom]Function
fun ConeClassLikeLookupTag.isSomeFunctionalType(session: FirSession): Boolean { fun ConeClassLikeLookupTag.isSomeFunctionType(session: FirSession): Boolean {
return functionalTypeKind(session) != null return functionTypeKind(session) != null
}
// Function, KFunction
private fun ConeKotlinType.isSimpleFunctionalType(session: FirSession, errorOnNotFunctionalType: Boolean): Boolean {
return isFunctionalTypeWithPredicate(session, errorOnNotFunctionalType) { it.isRegularFunction }
} }
// SuspendFunction, [Custom]Function, KSuspendFunction, K[Custom]Function // SuspendFunction, [Custom]Function, KSuspendFunction, K[Custom]Function
fun ConeKotlinType.isNotSimpleFunctionalType(session: FirSession): Boolean { fun ConeKotlinType.isNotBasicFunctionType(session: FirSession): Boolean {
return isFunctionalTypeWithPredicate(session, errorOnNotFunctionalType = false) { !it.isRegularFunction } return isFunctionTypeWithPredicate(session, errorOnNotFunctionType = false) { !it.isBasicFunctionOrKFunction }
} }
// ---------------------------------------------- functional type conversions ---------------------------------------------- // ---------------------------------------------- function type conversions ----------------------------------------------
/* /*
* SuspendFunction/[Custom]Function -> Function * SuspendFunction/[Custom]Function -> Function
* KSuspendFunction/K[Custom]Function -> KFunction * KSuspendFunction/K[Custom]Function -> KFunction
*/ */
fun ConeKotlinType.customFunctionalTypeToSimpleFunctionalType(session: FirSession): ConeClassLikeType { fun ConeKotlinType.customFunctionTypeToSimpleFunctionType(session: FirSession): ConeClassLikeType {
val kind = functionalTypeKind(session) val kind = functionTypeKind(session)
require(kind != null && kind != FunctionalTypeKind.Function && kind != FunctionalTypeKind.KFunction) require(kind != null && kind != FunctionTypeKind.Function && kind != FunctionTypeKind.KFunction)
val newKind = if (kind.isReflectType) { val newKind = if (kind.isReflectType) {
FunctionalTypeKind.KFunction FunctionTypeKind.KFunction
} else { } else {
FunctionalTypeKind.Function FunctionTypeKind.Function
} }
return createFunctionalTypeWithNewKind(session, newKind) return createFunctionTypeWithNewKind(session, newKind)
} }
/* /*
@@ -114,68 +109,73 @@ fun ConeKotlinType.customFunctionalTypeToSimpleFunctionalType(session: FirSessio
* KSuspendFunction -> SuspendFunction * KSuspendFunction -> SuspendFunction
* K[Custom]Function -> [Custom]Function * K[Custom]Function -> [Custom]Function
*/ */
fun ConeKotlinType.reflectFunctionalTypeToNonReflectFunctionalType(session: FirSession): ConeClassLikeType { fun ConeKotlinType.reflectFunctionTypeToNonReflectFunctionType(session: FirSession): ConeClassLikeType {
val kind = functionalTypeKind(session) val kind = functionTypeKind(session)
require(kind != null && kind.isReflectType) require(kind != null && kind.isReflectType)
return createFunctionalTypeWithNewKind(session, kind.nonReflectKind()) return createFunctionTypeWithNewKind(session, kind.nonReflectKind())
} }
private fun ConeKotlinType.createFunctionalTypeWithNewKind(session: FirSession, kind: FunctionalTypeKind): ConeClassLikeType { private fun ConeKotlinType.createFunctionTypeWithNewKind(session: FirSession, kind: FunctionTypeKind): ConeClassLikeType {
val expandedType = fullyExpandedType(session) val expandedType = fullyExpandedType(session)
val functionalTypeId = ClassId(kind.packageFqName, kind.numberedClassName(expandedType.typeArguments.size - 1)) val functionTypeId = ClassId(kind.packageFqName, kind.numberedClassName(expandedType.typeArguments.size - 1))
return functionalTypeId.toLookupTag().constructClassType( return functionTypeId.toLookupTag().constructClassType(
expandedType.typeArguments, expandedType.typeArguments,
isNullable = false, isNullable = false,
attributes = expandedType.attributes attributes = expandedType.attributes
) )
} }
// ---------------------------------------------- functional type subtyping ---------------------------------------------- // ---------------------------------------------- function type subtyping ----------------------------------------------
// expectedFunctionalType is kotlin.FunctionN or kotlin.reflect.KFunctionN // expectedfunctionType is kotlin.FunctionN or kotlin.reflect.KFunctionN
fun ConeKotlinType.findSubtypeOfSimpleFunctionalType(session: FirSession, expectedFunctionalType: ConeClassLikeType): ConeKotlinType? { fun ConeKotlinType.findSubtypeOfBasicFunctionType(session: FirSession, expectedFunctionType: ConeClassLikeType): ConeKotlinType? {
require(expectedFunctionalType.isSimpleFunctionalType(session, errorOnNotFunctionalType = true)) require(expectedFunctionType.isFunctionOrKFunctionType(session, errorOnNotFunctionType = true))
return findSubtypeOfSimpleFunctionalTypeImpl(session, expectedFunctionalType) return findSubtypeOfBasicFunctionTypeImpl(session, expectedFunctionType)
} }
private fun ConeKotlinType.findSubtypeOfSimpleFunctionalTypeImpl( // Function, KFunction
private fun ConeKotlinType.isFunctionOrKFunctionType(session: FirSession, errorOnNotFunctionType: Boolean): Boolean {
return isFunctionTypeWithPredicate(session, errorOnNotFunctionType) { it.isBasicFunctionOrKFunction }
}
private fun ConeKotlinType.findSubtypeOfBasicFunctionTypeImpl(
session: FirSession, session: FirSession,
expectedFunctionalType: ConeClassLikeType expectedFunctionType: ConeClassLikeType
): ConeKotlinType? { ): ConeKotlinType? {
return when (this) { return when (this) {
is ConeClassLikeType -> { is ConeClassLikeType -> {
when { when {
// Expect the argument type is a simple functional type. // Expect the argument type is a simple function type.
isNotSimpleFunctionalType(session) -> null isNotBasicFunctionType(session) -> null
isSubtypeOfFunctionalType(session, expectedFunctionalType) -> this isSubtypeOfFunctionType(session, expectedFunctionType) -> this
else -> null else -> null
} }
} }
is ConeIntersectionType -> { is ConeIntersectionType -> {
runUnless(intersectedTypes.any { it.isNotSimpleFunctionalType(session) }) { runUnless(intersectedTypes.any { it.isNotBasicFunctionType(session) }) {
intersectedTypes.find { it.findSubtypeOfSimpleFunctionalTypeImpl(session, expectedFunctionalType) != null } intersectedTypes.find { it.findSubtypeOfBasicFunctionTypeImpl(session, expectedFunctionType) != null }
} }
} }
is ConeTypeParameterType -> { is ConeTypeParameterType -> {
val bounds = lookupTag.typeParameterSymbol.resolvedBounds.map { it.coneType } val bounds = lookupTag.typeParameterSymbol.resolvedBounds.map { it.coneType }
runUnless(bounds.any { it.isNotSimpleFunctionalType(session) }) { runUnless(bounds.any { it.isNotBasicFunctionType(session) }) {
bounds.find { it.findSubtypeOfSimpleFunctionalTypeImpl(session, expectedFunctionalType) != null } bounds.find { it.findSubtypeOfBasicFunctionTypeImpl(session, expectedFunctionType) != null }
} }
} }
else -> null else -> null
} }
} }
private fun ConeKotlinType.isSubtypeOfFunctionalType(session: FirSession, expectedFunctionalType: ConeClassLikeType): Boolean { private fun ConeKotlinType.isSubtypeOfFunctionType(session: FirSession, expectedFunctionType: ConeClassLikeType): Boolean {
return AbstractTypeChecker.isSubtypeOf(session.typeContext, this, expectedFunctionalType.replaceArgumentsWithStarProjections()) return AbstractTypeChecker.isSubtypeOf(session.typeContext, this, expectedFunctionType.replaceArgumentsWithStarProjections())
} }
// ---------------------------------------------- functional type scope utils ---------------------------------------------- // ---------------------------------------------- function type scope utils ----------------------------------------------
fun ConeClassLikeType.findBaseInvokeSymbol(session: FirSession, scopeSession: ScopeSession): FirNamedFunctionSymbol? { fun ConeClassLikeType.findBaseInvokeSymbol(session: FirSession, scopeSession: ScopeSession): FirNamedFunctionSymbol? {
require(this.isSomeFunctionalType(session)) require(this.isSomeFunctionType(session))
val functionN = (lookupTag.toSymbol(session)?.fir as? FirClass) ?: return null val functionN = (lookupTag.toSymbol(session)?.fir as? FirClass) ?: return null
var baseInvokeSymbol: FirNamedFunctionSymbol? = null var baseInvokeSymbol: FirNamedFunctionSymbol? = null
functionN.unsubstitutedScope( functionN.unsubstitutedScope(
@@ -192,10 +192,10 @@ fun ConeClassLikeType.findBaseInvokeSymbol(session: FirSession, scopeSession: Sc
fun ConeKotlinType.findContributedInvokeSymbol( fun ConeKotlinType.findContributedInvokeSymbol(
session: FirSession, session: FirSession,
scopeSession: ScopeSession, scopeSession: ScopeSession,
expectedFunctionalType: ConeClassLikeType, expectedFunctionType: ConeClassLikeType,
shouldCalculateReturnTypesOfFakeOverrides: Boolean shouldCalculateReturnTypesOfFakeOverrides: Boolean
): FirFunctionSymbol<*>? { ): FirFunctionSymbol<*>? {
val baseInvokeSymbol = expectedFunctionalType.findBaseInvokeSymbol(session, scopeSession) ?: return null val baseInvokeSymbol = expectedFunctionType.findBaseInvokeSymbol(session, scopeSession) ?: return null
val fakeOverrideTypeCalculator = if (shouldCalculateReturnTypesOfFakeOverrides) { val fakeOverrideTypeCalculator = if (shouldCalculateReturnTypesOfFakeOverrides) {
FakeOverrideTypeCalculator.Forced FakeOverrideTypeCalculator.Forced
@@ -227,10 +227,10 @@ fun ConeKotlinType.findContributedInvokeSymbol(
return if (overriddenInvoke != null) declaredInvoke else null return if (overriddenInvoke != null) declaredInvoke else null
} }
// ---------------------------------------------- functional type type argument extraction ---------------------------------------------- // ---------------------------------------------- function type type argument extraction ----------------------------------------------
fun ConeKotlinType.receiverType(session: FirSession): ConeKotlinType? { fun ConeKotlinType.receiverType(session: FirSession): ConeKotlinType? {
if (!isSomeFunctionalType(session) || !isExtensionFunctionType(session)) return null if (!isSomeFunctionType(session) || !isExtensionFunctionType(session)) return null
return fullyExpandedType(session).let { expanded -> return fullyExpandedType(session).let { expanded ->
expanded.typeArguments[expanded.contextReceiversNumberForFunctionType].typeOrDefault(session.builtinTypes.nothingType.type) expanded.typeArguments[expanded.contextReceiversNumberForFunctionType].typeOrDefault(session.builtinTypes.nothingType.type)
} }
@@ -255,8 +255,8 @@ private fun ConeTypeProjection.typeOrDefault(default: ConeKotlinType): ConeKotli
// ----------------- TODO fir utils // ----------------- TODO fir utils
fun FirFunction.specialFunctionalTypeKind(session: FirSession): FunctionalTypeKind? { fun FirFunction.specialFunctionTypeKind(session: FirSession): FunctionTypeKind? {
return (symbol as? FirNamedFunctionSymbol)?.let { return (symbol as? FirNamedFunctionSymbol)?.let {
session.functionalTypeService.extractSingleSpecialKindForFunction(it) session.functionTypeService.extractSingleSpecialKindForFunction(it)
} }
} }
@@ -18,7 +18,7 @@ import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor
import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.FirAbstractBodyResolveTransformer import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.FirAbstractBodyResolveTransformer
import org.jetbrains.kotlin.fir.types.classId import org.jetbrains.kotlin.fir.types.classId
import org.jetbrains.kotlin.fir.types.coneType import org.jetbrains.kotlin.fir.types.coneType
import org.jetbrains.kotlin.fir.types.isSomeFunctionalType import org.jetbrains.kotlin.fir.types.isSomeFunctionType
import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintSystemCompletionMode import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintSystemCompletionMode
import org.jetbrains.kotlin.resolve.descriptorUtil.OVERLOAD_RESOLUTION_BY_LAMBDA_ANNOTATION_CLASS_ID import org.jetbrains.kotlin.resolve.descriptorUtil.OVERLOAD_RESOLUTION_BY_LAMBDA_ANNOTATION_CLASS_ID
import org.jetbrains.kotlin.utils.addToStdlib.same import org.jetbrains.kotlin.utils.addToStdlib.same
@@ -104,7 +104,7 @@ class FirOverloadByLambdaReturnTypeResolver(
.values.singleOrNull()?.toMap() ?: return null .values.singleOrNull()?.toMap() ?: return null
if (!lambdas.values.same { it.parameters.size }) return null if (!lambdas.values.same { it.parameters.size }) return null
if (!lambdas.values.all { it.expectedType?.isSomeFunctionalType(session) == true }) return null if (!lambdas.values.all { it.expectedType?.isSomeFunctionType(session) == true }) return null
val originalCalleeReference = call.calleeReference val originalCalleeReference = call.calleeReference
@@ -23,7 +23,7 @@ abstract class FirSamConversionTransformerExtension(session: FirSession) : FirEx
final override val extensionType: KClass<out FirExtension> = FirSamConversionTransformerExtension::class final override val extensionType: KClass<out FirExtension> = FirSamConversionTransformerExtension::class
abstract fun getCustomFunctionalTypeForSamConversion(function: FirSimpleFunction): ConeLookupTagBasedType? abstract fun getCustomFunctionTypeForSamConversion(function: FirSimpleFunction): ConeLookupTagBasedType?
fun interface Factory : FirExtension.Factory<FirSamConversionTransformerExtension> fun interface Factory : FirExtension.Factory<FirSamConversionTransformerExtension>
} }
@@ -7,7 +7,7 @@ package org.jetbrains.kotlin.fir.resolve
import org.jetbrains.kotlin.KtFakeSourceElementKind import org.jetbrains.kotlin.KtFakeSourceElementKind
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
@@ -88,9 +88,9 @@ fun FirAnonymousFunction.addReturnToLastStatementIfNeeded() {
} }
/** /**
* [kind] == null means that [FunctionalTypeKind.Function] will be used * [kind] == null means that [FunctionTypeKind.Function] will be used
*/ */
fun FirFunction.constructFunctionalType(kind: FunctionalTypeKind? = null): ConeLookupTagBasedType { fun FirFunction.constructFunctionType(kind: FunctionTypeKind? = null): ConeLookupTagBasedType {
val receiverTypeRef = when (this) { val receiverTypeRef = when (this) {
is FirSimpleFunction -> receiverParameter is FirSimpleFunction -> receiverParameter
is FirAnonymousFunction -> receiverParameter is FirAnonymousFunction -> receiverParameter
@@ -107,28 +107,28 @@ fun FirFunction.constructFunctionalType(kind: FunctionalTypeKind? = null): ConeL
} }
val rawReturnType = (this as FirCallableDeclaration).returnTypeRef.coneType val rawReturnType = (this as FirCallableDeclaration).returnTypeRef.coneType
return createFunctionalType( return createFunctionType(
kind ?: FunctionalTypeKind.Function, parameters, receiverTypeRef?.coneType, rawReturnType, kind ?: FunctionTypeKind.Function, parameters, receiverTypeRef?.coneType, rawReturnType,
contextReceivers = contextReceivers.map { it.typeRef.coneType } contextReceivers = contextReceivers.map { it.typeRef.coneType }
) )
} }
/** /**
* [kind] == null means that [FunctionalTypeKind.Function] will be used * [kind] == null means that [FunctionTypeKind.Function] will be used
*/ */
fun FirAnonymousFunction.constructFunctionalTypeRef(session: FirSession, kind: FunctionalTypeKind? = null): FirResolvedTypeRef { fun FirAnonymousFunction.constructFunctionTypeRef(session: FirSession, kind: FunctionTypeKind? = null): FirResolvedTypeRef {
var diagnostic: ConeDiagnostic? = null var diagnostic: ConeDiagnostic? = null
val kinds = session.functionalTypeService.extractAllSpecialKindsForFunction(symbol) val kinds = session.functionTypeService.extractAllSpecialKindsForFunction(symbol)
val kindFromDeclaration = when(kinds.size) { val kindFromDeclaration = when(kinds.size) {
0 -> null 0 -> null
1 -> kinds.single() 1 -> kinds.single()
else -> { else -> {
diagnostic = ConeAmbiguousFunctionalTypeKinds(kinds) diagnostic = ConeAmbiguousFunctionTypeKinds(kinds)
FunctionalTypeKind.Function FunctionTypeKind.Function
} }
} }
val type = constructFunctionalType(kindFromDeclaration ?: kind) val type = constructFunctionType(kindFromDeclaration ?: kind)
val source = this@constructFunctionalTypeRef.source?.fakeElement(KtFakeSourceElementKind.ImplicitTypeRef) val source = this@constructFunctionTypeRef.source?.fakeElement(KtFakeSourceElementKind.ImplicitTypeRef)
return if (diagnostic == null) { return if (diagnostic == null) {
buildResolvedTypeRef { buildResolvedTypeRef {
this.source = source this.source = source
@@ -143,8 +143,8 @@ fun FirAnonymousFunction.constructFunctionalTypeRef(session: FirSession, kind: F
} }
} }
fun createFunctionalType( fun createFunctionType(
kind: FunctionalTypeKind, kind: FunctionTypeKind,
parameters: List<ConeKotlinType>, parameters: List<ConeKotlinType>,
receiverType: ConeKotlinType?, receiverType: ConeKotlinType?,
rawReturnType: ConeKotlinType, rawReturnType: ConeKotlinType,
@@ -158,7 +158,7 @@ fun createFunctionalType(
add(rawReturnType) add(rawReturnType)
} }
val functionalTypeId = ClassId(kind.packageFqName, kind.numberedClassName(receiverAndParameterTypes.size - 1)) val functionTypeId = ClassId(kind.packageFqName, kind.numberedClassName(receiverAndParameterTypes.size - 1))
val attributes = when { val attributes = when {
contextReceivers.isNotEmpty() -> ConeAttributes.create( contextReceivers.isNotEmpty() -> ConeAttributes.create(
buildList { buildList {
@@ -172,7 +172,7 @@ fun createFunctionalType(
else -> ConeAttributes.Empty else -> ConeAttributes.Empty
} }
return ConeClassLikeTypeImpl( return ConeClassLikeTypeImpl(
functionalTypeId.toLookupTag(), functionTypeId.toLookupTag(),
receiverAndParameterTypes.toTypedArray(), receiverAndParameterTypes.toTypedArray(),
isNullable = false, isNullable = false,
attributes = attributes attributes = attributes
@@ -592,7 +592,7 @@ fun FirFunction.getAsForbiddenNamedArgumentsTarget(
result result
} }
// referenced function of a Kotlin function type // referenced function of a Kotlin function type
FirDeclarationOrigin.BuiltIns -> runIf(dispatchReceiverClassLookupTagOrNull()?.isSomeFunctionalType(session) == true) { FirDeclarationOrigin.BuiltIns -> runIf(dispatchReceiverClassLookupTagOrNull()?.isSomeFunctionType(session) == true) {
ForbiddenNamedArgumentsTarget.INVOKE_ON_FUNCTION_TYPE ForbiddenNamedArgumentsTarget.INVOKE_ON_FUNCTION_TYPE
} }
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.resolve package org.jetbrains.kotlin.fir.resolve
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.EffectiveVisibility import org.jetbrains.kotlin.descriptors.EffectiveVisibility
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
@@ -263,7 +263,7 @@ class FirSamResolver(
// TODO: val shouldConvertFirstParameterToDescriptor = samWithReceiverResolvers.any { it.shouldConvertFirstSamParameterToReceiver(abstractMethod) } // TODO: val shouldConvertFirstParameterToDescriptor = samWithReceiverResolvers.any { it.shouldConvertFirstSamParameterToReceiver(abstractMethod) }
val typeFromExtension = samConversionTransformers.firstNotNullOfOrNull { val typeFromExtension = samConversionTransformers.firstNotNullOfOrNull {
it.getCustomFunctionalTypeForSamConversion(abstractMethod) it.getCustomFunctionTypeForSamConversion(abstractMethod)
} }
SAMInfo(abstractMethod.symbol, typeFromExtension ?: abstractMethod.getFunctionTypeForAbstractMethod(session)) SAMInfo(abstractMethod.symbol, typeFromExtension ?: abstractMethod.getFunctionTypeForAbstractMethod(session))
@@ -415,8 +415,8 @@ private fun FirSimpleFunction.getFunctionTypeForAbstractMethod(session: FirSessi
val contextReceiversTypes = contextReceivers.map { val contextReceiversTypes = contextReceivers.map {
it.typeRef.coneTypeSafe<ConeKotlinType>() ?: ConeErrorType(ConeIntermediateDiagnostic("No type for context receiver $it")) it.typeRef.coneTypeSafe<ConeKotlinType>() ?: ConeErrorType(ConeIntermediateDiagnostic("No type for context receiver $it"))
} }
val kind = session.functionalTypeService.extractSingleSpecialKindForFunction(symbol) ?: FunctionalTypeKind.Function val kind = session.functionTypeService.extractSingleSpecialKindForFunction(symbol) ?: FunctionTypeKind.Function
return createFunctionalType( return createFunctionType(
kind, kind,
parameterTypes, parameterTypes,
receiverType = receiverParameter?.typeRef?.coneType, receiverType = receiverParameter?.typeRef?.coneType,
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.resolve.calls package org.jetbrains.kotlin.fir.resolve.calls
import org.jetbrains.kotlin.builtins.functions.isRegularFunction import org.jetbrains.kotlin.builtins.functions.isBasicFunctionOrKFunction
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.FirCallableDeclaration import org.jetbrains.kotlin.fir.declarations.FirCallableDeclaration
import org.jetbrains.kotlin.fir.declarations.FirValueParameter import org.jetbrains.kotlin.fir.declarations.FirValueParameter
@@ -13,7 +13,7 @@ import org.jetbrains.kotlin.fir.expressions.*
import org.jetbrains.kotlin.fir.lookupTracker import org.jetbrains.kotlin.fir.lookupTracker
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
import org.jetbrains.kotlin.fir.resolve.ScopeSession import org.jetbrains.kotlin.fir.resolve.ScopeSession
import org.jetbrains.kotlin.fir.resolve.createFunctionalType import org.jetbrains.kotlin.fir.resolve.createFunctionType
import org.jetbrains.kotlin.fir.resolve.dfa.unwrapSmartcastExpression import org.jetbrains.kotlin.fir.resolve.dfa.unwrapSmartcastExpression
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.resolve.inference.model.ConeArgumentConstraintPosition import org.jetbrains.kotlin.fir.resolve.inference.model.ConeArgumentConstraintPosition
@@ -271,7 +271,7 @@ fun Candidate.resolvePlainArgumentType(
)?.let { )?.let {
argumentTypeForApplicabilityCheck = it argumentTypeForApplicabilityCheck = it
substitutor.substituteOrSelf(argumentTypeForApplicabilityCheck) substitutor.substituteOrSelf(argumentTypeForApplicabilityCheck)
usesFunctionalConversion = true usesFunctionConversion = true
} }
} }
@@ -287,21 +287,21 @@ private fun argumentTypeWithCustomConversion(
argumentType: ConeKotlinType argumentType: ConeKotlinType
): ConeKotlinType? { ): ConeKotlinType? {
// Expect the expected type to be a not regular functional type (e.g. suspend or custom) // Expect the expected type to be a not regular functional type (e.g. suspend or custom)
val expectedTypeKind = expectedType.functionalTypeKind(session) ?: return null val expectedTypeKind = expectedType.functionTypeKind(session) ?: return null
if (expectedTypeKind.isRegularFunction) return null if (expectedTypeKind.isBasicFunctionOrKFunction) return null
// We want to check the argument type against non-suspend functional type. // We want to check the argument type against non-suspend functional type.
val expectedFunctionalType = expectedType.customFunctionalTypeToSimpleFunctionalType(session) val expectedFunctionType = expectedType.customFunctionTypeToSimpleFunctionType(session)
val argumentTypeWithInvoke = argumentType.findSubtypeOfSimpleFunctionalType(session, expectedFunctionalType) val argumentTypeWithInvoke = argumentType.findSubtypeOfBasicFunctionType(session, expectedFunctionType)
return argumentTypeWithInvoke?.findContributedInvokeSymbol( return argumentTypeWithInvoke?.findContributedInvokeSymbol(
session, session,
scopeSession, scopeSession,
expectedFunctionalType, expectedFunctionType,
shouldCalculateReturnTypesOfFakeOverrides = false shouldCalculateReturnTypesOfFakeOverrides = false
)?.let { invokeSymbol -> )?.let { invokeSymbol ->
createFunctionalType( createFunctionType(
expectedTypeKind, expectedTypeKind,
invokeSymbol.fir.valueParameters.map { it.returnTypeRef.coneType }, invokeSymbol.fir.valueParameters.map { it.returnTypeRef.coneType },
null, null,
@@ -495,7 +495,7 @@ private fun Candidate.getExpectedTypeWithSAMConversion(
candidateExpectedType: ConeKotlinType, candidateExpectedType: ConeKotlinType,
context: ResolutionContext context: ResolutionContext
): ConeKotlinType? { ): ConeKotlinType? {
if (candidateExpectedType.isSomeFunctionalType(session)) return null if (candidateExpectedType.isSomeFunctionType(session)) return null
// TODO: resolvedCall.registerArgumentWithSamConversion(argument, SamConversionDescription(convertedTypeByOriginal, convertedTypeByCandidate!!)) // TODO: resolvedCall.registerArgumentWithSamConversion(argument, SamConversionDescription(convertedTypeByOriginal, convertedTypeByCandidate!!))
@@ -518,7 +518,7 @@ fun FirExpression.isFunctional(
else -> { else -> {
// Either a functional type or a subtype of a class that has a contributed `invoke`. // Either a functional type or a subtype of a class that has a contributed `invoke`.
val coneType = typeRef.coneTypeSafe<ConeKotlinType>() ?: return false val coneType = typeRef.coneTypeSafe<ConeKotlinType>() ?: return false
if (coneType.isSomeFunctionalType(session)) { if (coneType.isSomeFunctionType(session)) {
return true return true
} }
val classLikeExpectedFunctionType = expectedFunctionType?.lowerBoundIfFlexible() as? ConeClassLikeType val classLikeExpectedFunctionType = expectedFunctionType?.lowerBoundIfFlexible() as? ConeClassLikeType
@@ -7,8 +7,8 @@ package org.jetbrains.kotlin.fir.resolve.calls
import org.jetbrains.kotlin.KtFakeSourceElementKind import org.jetbrains.kotlin.KtFakeSourceElementKind
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.isRegularFunction import org.jetbrains.kotlin.builtins.functions.isBasicFunctionOrKFunction
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.fir.* import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.declarations.*
@@ -19,7 +19,7 @@ import org.jetbrains.kotlin.fir.expressions.FirResolvedQualifier
import org.jetbrains.kotlin.fir.expressions.builder.buildNamedArgumentExpression import org.jetbrains.kotlin.fir.expressions.builder.buildNamedArgumentExpression
import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents
import org.jetbrains.kotlin.fir.resolve.DoubleColonLHS import org.jetbrains.kotlin.fir.resolve.DoubleColonLHS
import org.jetbrains.kotlin.fir.resolve.createFunctionalType import org.jetbrains.kotlin.fir.resolve.createFunctionType
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeUnsupportedCallableReferenceTarget import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeUnsupportedCallableReferenceTarget
import org.jetbrains.kotlin.fir.resolve.inference.extractInputOutputTypesFromCallableReferenceExpectedType import org.jetbrains.kotlin.fir.resolve.inference.extractInputOutputTypesFromCallableReferenceExpectedType
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
@@ -131,12 +131,12 @@ private fun buildReflectionType(
} }
val baseFunctionalTypeKind = callableReferenceAdaptation?.suspendConversionStrategy?.kind val baseFunctionTypeKind = callableReferenceAdaptation?.suspendConversionStrategy?.kind
?: fir.specialFunctionalTypeKind(context.session) ?: fir.specialFunctionTypeKind(context.session)
?: FunctionalTypeKind.Function ?: FunctionTypeKind.Function
return createFunctionalType( return createFunctionType(
baseFunctionalTypeKind.reflectKind(), baseFunctionTypeKind.reflectKind(),
parameters, parameters,
receiverType = receiverType.takeIf { fir.receiverParameter != null }, receiverType = receiverType.takeIf { fir.receiverParameter != null },
rawReturnType = returnType, rawReturnType = returnType,
@@ -255,11 +255,11 @@ private fun BodyResolveComponents.getCallableReferenceAdaptation(
else else
mappedArguments mappedArguments
val expectedTypeFunctionalKind = expectedType.functionalTypeKind(session)?.takeUnless { it.isRegularFunction } val expectedTypeFunctionKind = expectedType.functionTypeKind(session)?.takeUnless { it.isBasicFunctionOrKFunction }
val functionKind = function.specialFunctionalTypeKind(session) val functionKind = function.specialFunctionTypeKind(session)
val conversionStrategy = if (expectedTypeFunctionalKind != null && functionKind == null) { val conversionStrategy = if (expectedTypeFunctionKind != null && functionKind == null) {
CallableReferenceConversionStrategy.CustomConversion(expectedTypeFunctionalKind) CallableReferenceConversionStrategy.CustomConversion(expectedTypeFunctionKind)
} else { } else {
CallableReferenceConversionStrategy.NoConversion CallableReferenceConversionStrategy.NoConversion
} }
@@ -277,14 +277,14 @@ private fun BodyResolveComponents.getCallableReferenceAdaptation(
sealed class CallableReferenceConversionStrategy { sealed class CallableReferenceConversionStrategy {
abstract val kind: FunctionalTypeKind? abstract val kind: FunctionTypeKind?
object NoConversion : CallableReferenceConversionStrategy() { object NoConversion : CallableReferenceConversionStrategy() {
override val kind: FunctionalTypeKind? override val kind: FunctionTypeKind?
get() = null get() = null
} }
class CustomConversion(override val kind: FunctionalTypeKind) : CallableReferenceConversionStrategy() class CustomConversion(override val kind: FunctionTypeKind) : CallableReferenceConversionStrategy()
} }
private fun varargParameterTypeByExpectedParameter( private fun varargParameterTypeByExpectedParameter(
@@ -62,13 +62,13 @@ class Candidate(
internal var callableReferenceAdaptation: CallableReferenceAdaptation? = null internal var callableReferenceAdaptation: CallableReferenceAdaptation? = null
set(value) { set(value) {
field = value field = value
usesFunctionalConversion = value?.suspendConversionStrategy is CallableReferenceConversionStrategy.CustomConversion usesFunctionConversion = value?.suspendConversionStrategy is CallableReferenceConversionStrategy.CustomConversion
if (value != null) { if (value != null) {
numDefaults = value.defaults numDefaults = value.defaults
} }
} }
var usesFunctionalConversion: Boolean = false var usesFunctionConversion: Boolean = false
var argumentMapping: LinkedHashMap<FirExpression, FirValueParameter>? = null var argumentMapping: LinkedHashMap<FirExpression, FirValueParameter>? = null
var numDefaults: Int = 0 var numDefaults: Int = 0
@@ -94,7 +94,7 @@ class ConeOverloadConflictResolver(
} }
if (discriminateSuspendConversions) { if (discriminateSuspendConversions) {
val filtered = candidates.filterTo(mutableSetOf()) { !it.usesFunctionalConversion } val filtered = candidates.filterTo(mutableSetOf()) { !it.usesFunctionConversion }
when (filtered.size) { when (filtered.size) {
1 -> return filtered 1 -> return filtered
0, candidates.size -> { 0, candidates.size -> {
@@ -297,7 +297,7 @@ object CheckDslScopeViolation : ResolutionStage() {
// ``` // ```
// `useX()` is a call to `invoke` with `useX` as the dispatch receiver. In the FIR tree, extension receiver is represented as an // `useX()` is a call to `invoke` with `useX` as the dispatch receiver. In the FIR tree, extension receiver is represented as an
// implicit `this` expression passed as the first argument. // implicit `this` expression passed as the first argument.
if (candidate.dispatchReceiverValue?.type?.fullyExpandedType(context.session)?.isSomeFunctionalType(context.session) == true && if (candidate.dispatchReceiverValue?.type?.fullyExpandedType(context.session)?.isSomeFunctionType(context.session) == true &&
(candidate.symbol as? FirNamedFunctionSymbol)?.name == OperatorNameConventions.INVOKE (candidate.symbol as? FirNamedFunctionSymbol)?.name == OperatorNameConventions.INVOKE
) { ) {
val firstArg = candidate.argumentMapping?.keys?.firstOrNull() as? FirThisReceiverExpression ?: return val firstArg = candidate.argumentMapping?.keys?.firstOrNull() as? FirThisReceiverExpression ?: return
@@ -133,7 +133,7 @@ class ConstraintSystemCompleter(components: BodyResolveComponents, private val c
// Stage 4: create atoms with revised expected types if needed // Stage 4: create atoms with revised expected types if needed
for (argument in postponedArgumentsWithRevisableType) { for (argument in postponedArgumentsWithRevisableType) {
val argumentWasTransformed = transformToAtomWithNewFunctionalExpectedType( val argumentWasTransformed = transformToAtomWithNewFunctionExpectedType(
this, context, argument this, context, argument
) )
@@ -214,7 +214,7 @@ class ConstraintSystemCompleter(components: BodyResolveComponents, private val c
return variableForFixation?.hasProperConstraint == true return variableForFixation?.hasProperConstraint == true
} }
private fun transformToAtomWithNewFunctionalExpectedType( private fun transformToAtomWithNewFunctionExpectedType(
c: ConstraintSystemCompletionContext, c: ConstraintSystemCompletionContext,
resolutionContext: ResolutionContext, resolutionContext: ResolutionContext,
argument: PostponedAtomWithRevisableExpectedType, argument: PostponedAtomWithRevisableExpectedType,
@@ -14,7 +14,7 @@ import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents
import org.jetbrains.kotlin.fir.resolve.calls.Candidate import org.jetbrains.kotlin.fir.resolve.calls.Candidate
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
fun extractLambdaInfoFromFunctionalType( fun extractLambdaInfoFromFunctionType(
expectedType: ConeKotlinType?, expectedType: ConeKotlinType?,
expectedTypeRef: FirTypeRef?, expectedTypeRef: FirTypeRef?,
argument: FirAnonymousFunction, argument: FirAnonymousFunction,
@@ -26,7 +26,7 @@ fun extractLambdaInfoFromFunctionalType(
val session = components.session val session = components.session
if (expectedType == null) return null if (expectedType == null) return null
if (expectedType is ConeFlexibleType) { if (expectedType is ConeFlexibleType) {
return extractLambdaInfoFromFunctionalType( return extractLambdaInfoFromFunctionType(
expectedType.lowerBound, expectedType.lowerBound,
expectedTypeRef, expectedTypeRef,
argument, argument,
@@ -36,8 +36,8 @@ fun extractLambdaInfoFromFunctionalType(
duringCompletion duringCompletion
) )
} }
val expectedFunctionalKind = expectedType.functionalTypeKind(session) ?: return null val expectedFunctionKind = expectedType.functionTypeKind(session) ?: return null
val actualFunctionalKind = session.functionalTypeService.extractSingleSpecialKindForFunction(argument.symbol) val actualFunctionKind = session.functionTypeService.extractSingleSpecialKindForFunction(argument.symbol)
val singleStatement = argument.body?.statements?.singleOrNull() as? FirReturnExpression val singleStatement = argument.body?.statements?.singleOrNull() as? FirReturnExpression
if (argument.returnType == null && singleStatement != null && if (argument.returnType == null && singleStatement != null &&
@@ -101,7 +101,7 @@ fun extractLambdaInfoFromFunctionalType(
return ResolvedLambdaAtom( return ResolvedLambdaAtom(
argument, argument,
expectedType, expectedType,
actualFunctionalKind ?: expectedFunctionalKind, actualFunctionKind ?: expectedFunctionKind,
receiverType, receiverType,
contextReceivers, contextReceivers,
parameters, parameters,
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.resolve.inference package org.jetbrains.kotlin.fir.resolve.inference
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction
import org.jetbrains.kotlin.fir.expressions.FirAnonymousFunctionExpression import org.jetbrains.kotlin.fir.expressions.FirAnonymousFunctionExpression
@@ -14,7 +14,7 @@ import org.jetbrains.kotlin.fir.resolve.calls.ArgumentTypeMismatch
import org.jetbrains.kotlin.fir.resolve.calls.Candidate import org.jetbrains.kotlin.fir.resolve.calls.Candidate
import org.jetbrains.kotlin.fir.resolve.calls.CheckerSink import org.jetbrains.kotlin.fir.resolve.calls.CheckerSink
import org.jetbrains.kotlin.fir.resolve.calls.ResolutionContext import org.jetbrains.kotlin.fir.resolve.calls.ResolutionContext
import org.jetbrains.kotlin.fir.resolve.createFunctionalType import org.jetbrains.kotlin.fir.resolve.createFunctionType
import org.jetbrains.kotlin.fir.resolve.inference.model.ConeArgumentConstraintPosition import org.jetbrains.kotlin.fir.resolve.inference.model.ConeArgumentConstraintPosition
import org.jetbrains.kotlin.fir.resolve.inference.model.ConeExplicitTypeParameterConstraintPosition import org.jetbrains.kotlin.fir.resolve.inference.model.ConeExplicitTypeParameterConstraintPosition
import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.types.*
@@ -51,7 +51,7 @@ fun Candidate.preprocessLambdaArgument(
val anonymousFunction = argument.anonymousFunction val anonymousFunction = argument.anonymousFunction
val resolvedArgument = val resolvedArgument =
extractLambdaInfoFromFunctionalType( extractLambdaInfoFromFunctionType(
expectedType, expectedType,
expectedTypeRef, expectedTypeRef,
anonymousFunction, anonymousFunction,
@@ -63,8 +63,8 @@ fun Candidate.preprocessLambdaArgument(
if (expectedType != null) { if (expectedType != null) {
val parameters = resolvedArgument.parameters val parameters = resolvedArgument.parameters
val lambdaType = createFunctionalType( val lambdaType = createFunctionType(
resolvedArgument.expectedFunctionalTypeKind ?: FunctionalTypeKind.Function, resolvedArgument.expectedFunctionTypeKind ?: FunctionTypeKind.Function,
if (resolvedArgument.coerceFirstParameterToExtensionReceiver) parameters.drop(1) else parameters, if (resolvedArgument.coerceFirstParameterToExtensionReceiver) parameters.drop(1) else parameters,
resolvedArgument.receiver, resolvedArgument.receiver,
resolvedArgument.returnType, resolvedArgument.returnType,
@@ -107,8 +107,8 @@ private fun extractLambdaInfo(
session: FirSession, session: FirSession,
candidate: Candidate? candidate: Candidate?
): ResolvedLambdaAtom { ): ResolvedLambdaAtom {
val expectedFunctionalKind = expectedType?.lowerBoundIfFlexible()?.functionalTypeKind(session) val expectedFunctionKind = expectedType?.lowerBoundIfFlexible()?.functionTypeKind(session)
val isFunctionSupertype = expectedFunctionalKind != null val isFunctionSupertype = expectedFunctionKind != null
val typeVariable = ConeTypeVariableForLambdaReturnType(argument, "_L") val typeVariable = ConeTypeVariableForLambdaReturnType(argument, "_L")
@@ -133,7 +133,7 @@ private fun extractLambdaInfo(
return ResolvedLambdaAtom( return ResolvedLambdaAtom(
argument, argument,
expectedType, expectedType,
expectedFunctionalKind, expectedFunctionKind,
receiverType, receiverType,
contextReceivers, contextReceivers,
parameters, parameters,
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.resolve.inference package org.jetbrains.kotlin.fir.resolve.inference
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirElement import org.jetbrains.kotlin.fir.FirElement
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction
@@ -40,7 +40,7 @@ sealed class PostponedResolvedAtom : PostponedResolvedAtomMarker {
class ResolvedLambdaAtom( class ResolvedLambdaAtom(
override val atom: FirAnonymousFunction, override val atom: FirAnonymousFunction,
expectedType: ConeKotlinType?, expectedType: ConeKotlinType?,
val expectedFunctionalTypeKind: FunctionalTypeKind?, val expectedFunctionTypeKind: FunctionTypeKind?,
val receiver: ConeKotlinType?, val receiver: ConeKotlinType?,
val contextReceivers: List<ConeKotlinType>, val contextReceivers: List<ConeKotlinType>,
val parameters: List<ConeKotlinType>, val parameters: List<ConeKotlinType>,
@@ -178,7 +178,7 @@ internal fun extractInputOutputTypesFromCallableReferenceExpectedType(
if (expectedType == null) return null if (expectedType == null) return null
return when { return when {
expectedType.isSomeFunctionalType(session) -> expectedType.isSomeFunctionType(session) ->
InputOutputTypes(expectedType.valueParameterTypesIncludingReceiver(session), expectedType.returnType(session)) InputOutputTypes(expectedType.valueParameterTypesIncludingReceiver(session), expectedType.returnType(session))
// ReflectionTypes.isBaseTypeForNumberedReferenceTypes(expectedType) -> // ReflectionTypes.isBaseTypeForNumberedReferenceTypes(expectedType) ->
@@ -6,7 +6,7 @@
package org.jetbrains.kotlin.fir.resolve.providers.impl package org.jetbrains.kotlin.fir.resolve.providers.impl
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.* import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.declarations.impl.FirOuterClassTypeParameterRef import org.jetbrains.kotlin.fir.declarations.impl.FirOuterClassTypeParameterRef
@@ -19,7 +19,6 @@ import org.jetbrains.kotlin.fir.resolve.calls.AbstractCandidate
import org.jetbrains.kotlin.fir.resolve.calls.ReceiverValue import org.jetbrains.kotlin.fir.resolve.calls.ReceiverValue
import org.jetbrains.kotlin.fir.resolve.calls.ResolutionDiagnostic import org.jetbrains.kotlin.fir.resolve.calls.ResolutionDiagnostic
import org.jetbrains.kotlin.fir.resolve.diagnostics.* import org.jetbrains.kotlin.fir.resolve.diagnostics.*
import org.jetbrains.kotlin.fir.resolve.providers.symbolProvider
import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor
import org.jetbrains.kotlin.fir.resolve.transformers.ScopeClassDeclaration import org.jetbrains.kotlin.fir.resolve.transformers.ScopeClassDeclaration
import org.jetbrains.kotlin.fir.symbols.ConeTypeParameterLookupTag import org.jetbrains.kotlin.fir.symbols.ConeTypeParameterLookupTag
@@ -30,7 +29,6 @@ import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
import org.jetbrains.kotlin.fir.types.impl.ConeTypeParameterTypeImpl import org.jetbrains.kotlin.fir.types.impl.ConeTypeParameterTypeImpl
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.StandardClassIds
import org.jetbrains.kotlin.resolve.calls.inference.model.ConstraintSystemError import org.jetbrains.kotlin.resolve.calls.inference.model.ConstraintSystemError
import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind
import org.jetbrains.kotlin.resolve.calls.tower.CandidateApplicability import org.jetbrains.kotlin.resolve.calls.tower.CandidateApplicability
@@ -445,20 +443,20 @@ class FirTypeResolverImpl(private val session: FirSession) : FirTypeResolver() {
} }
} }
private fun createFunctionalType(typeRef: FirFunctionTypeRef): Pair<ConeClassLikeTypeImpl, ConeDiagnostic?> { private fun createFunctionType(typeRef: FirFunctionTypeRef): Pair<ConeClassLikeTypeImpl, ConeDiagnostic?> {
val parameters = val parameters =
typeRef.contextReceiverTypeRefs.map { it.coneType } + typeRef.contextReceiverTypeRefs.map { it.coneType } +
listOfNotNull(typeRef.receiverTypeRef?.coneType) + listOfNotNull(typeRef.receiverTypeRef?.coneType) +
typeRef.parameters.map { it.returnTypeRef.coneType.withParameterNameAnnotation(it, session) } + typeRef.parameters.map { it.returnTypeRef.coneType.withParameterNameAnnotation(it, session) } +
listOf(typeRef.returnTypeRef.coneType) listOf(typeRef.returnTypeRef.coneType)
val functionalKinds = session.functionalTypeService.extractAllSpecialKindsForFunctionalTypeRef(typeRef) val functionKinds = session.functionTypeService.extractAllSpecialKindsForFunctionTypeRef(typeRef)
var diagnostic: ConeDiagnostic? = null var diagnostic: ConeDiagnostic? = null
val kind = when (functionalKinds.size) { val kind = when (functionKinds.size) {
0 -> FunctionalTypeKind.Function 0 -> FunctionTypeKind.Function
1 -> functionalKinds.single() 1 -> functionKinds.single()
else -> { else -> {
diagnostic = ConeAmbiguousFunctionalTypeKinds(functionalKinds) diagnostic = ConeAmbiguousFunctionTypeKinds(functionKinds)
FunctionalTypeKind.Function FunctionTypeKind.Function
} }
} }
@@ -505,7 +503,7 @@ class FirTypeResolverImpl(private val session: FirSession) : FirTypeResolver() {
isOperandOfIsOperator, isOperandOfIsOperator,
) to (result as? TypeResolutionResult.Resolved)?.typeCandidate?.diagnostic ) to (result as? TypeResolutionResult.Resolved)?.typeCandidate?.diagnostic
} }
is FirFunctionTypeRef -> createFunctionalType(typeRef) is FirFunctionTypeRef -> createFunctionType(typeRef)
is FirDynamicTypeRef -> ConeDynamicType.create(session) to null is FirDynamicTypeRef -> ConeDynamicType.create(session) to null
is FirIntersectionTypeRef -> { is FirIntersectionTypeRef -> {
val leftType = typeRef.leftType.coneType val leftType = typeRef.leftType.coneType
@@ -6,7 +6,7 @@
package org.jetbrains.kotlin.fir.resolve.transformers package org.jetbrains.kotlin.fir.resolve.transformers
import org.jetbrains.kotlin.KtFakeSourceElementKind import org.jetbrains.kotlin.KtFakeSourceElementKind
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fakeElement import org.jetbrains.kotlin.fakeElement
import org.jetbrains.kotlin.fir.* import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.declarations.*
@@ -561,7 +561,7 @@ class FirCallCompletionResultsWriterTransformer(
// From the argument mapping, the expected type of this anonymous function would be: // From the argument mapping, the expected type of this anonymous function would be:
when { when {
// a built-in functional type, no-brainer // a built-in functional type, no-brainer
expectedArgumentType.isSomeFunctionalType(session) -> expectedArgumentType expectedArgumentType.isSomeFunctionType(session) -> expectedArgumentType
// fun interface (a.k.a. SAM), then unwrap it and build a functional type from that interface function // fun interface (a.k.a. SAM), then unwrap it and build a functional type from that interface function
expectedArgumentType is ConeClassLikeType -> { expectedArgumentType is ConeClassLikeType -> {
val firRegularClass = val firRegularClass =
@@ -570,8 +570,8 @@ class FirCallCompletionResultsWriterTransformer(
firRegularClass?.let answer@{ firRegularClass?.let answer@{
val functionType = samResolver.getFunctionTypeForPossibleSamType(firRegularClass.defaultType()) val functionType = samResolver.getFunctionTypeForPossibleSamType(firRegularClass.defaultType())
?: return@answer null ?: return@answer null
val kind = functionType.functionalTypeKind(session) ?: FunctionalTypeKind.Function val kind = functionType.functionTypeKind(session) ?: FunctionTypeKind.Function
createFunctionalType( createFunctionType(
kind, kind,
functionType.typeArguments.dropLast(1).map { it as ConeKotlinType }, functionType.typeArguments.dropLast(1).map { it as ConeKotlinType },
null, null,
@@ -617,9 +617,9 @@ class FirCallCompletionResultsWriterTransformer(
} }
if (needUpdateLambdaType) { if (needUpdateLambdaType) {
val kind = expectedType?.functionalTypeKind(session) val kind = expectedType?.functionTypeKind(session)
?: result.typeRef.coneTypeSafe<ConeClassLikeType>()?.functionalTypeKind(session) ?: result.typeRef.coneTypeSafe<ConeClassLikeType>()?.functionTypeKind(session)
result.replaceTypeRef(result.constructFunctionalTypeRef(session, kind)) result.replaceTypeRef(result.constructFunctionTypeRef(session, kind))
session.lookupTracker?.recordTypeResolveAsLookup(result.typeRef, result.source, context.file.source) session.lookupTracker?.recordTypeResolveAsLookup(result.typeRef, result.source, context.file.source)
} }
// Have to delay this until the type is written to avoid adding a return if the type is Unit. // Have to delay this until the type is written to avoid adding a return if the type is Unit.
@@ -123,7 +123,7 @@ class FirSpecificTypeResolverTransformer(
type = resolvedType type = resolvedType
} }
this.diagnostic = diagnostic ?: (resolvedType as? ConeErrorType)?.diagnostic this.diagnostic = diagnostic ?: (resolvedType as? ConeErrorType)?.diagnostic
?: ConeSimpleDiagnostic("Unresolved functional type: ${functionTypeRef.render()}") ?: ConeSimpleDiagnostic("Unresolved function type: ${functionTypeRef.render()}")
} }
} }
} }
@@ -19,7 +19,7 @@ import org.jetbrains.kotlin.fir.expressions.FirFunctionCall
import org.jetbrains.kotlin.fir.expressions.FirWrappedArgumentExpression import org.jetbrains.kotlin.fir.expressions.FirWrappedArgumentExpression
import org.jetbrains.kotlin.fir.resolve.calls.FirNamedReferenceWithCandidate import org.jetbrains.kotlin.fir.resolve.calls.FirNamedReferenceWithCandidate
import org.jetbrains.kotlin.fir.types.coneType import org.jetbrains.kotlin.fir.types.coneType
import org.jetbrains.kotlin.fir.types.isNonReflectFunctionalType import org.jetbrains.kotlin.fir.types.isNonReflectFunctionType
tailrec fun FirExpression.unwrapAnonymousFunctionExpression(): FirAnonymousFunction? = when (this) { tailrec fun FirExpression.unwrapAnonymousFunctionExpression(): FirAnonymousFunction? = when (this) {
is FirAnonymousFunctionExpression -> anonymousFunction is FirAnonymousFunctionExpression -> anonymousFunction
@@ -47,7 +47,7 @@ fun FirFunctionCall.replaceLambdaArgumentInvocationKinds(session: FirSession) {
val kind = byParameter[parameter] ?: EventOccurrencesRange.UNKNOWN.takeIf { val kind = byParameter[parameter] ?: EventOccurrencesRange.UNKNOWN.takeIf {
// Inline functional parameters have to be called in-place; that's the only permitted operation on them. // Inline functional parameters have to be called in-place; that's the only permitted operation on them.
isInline && !parameter.isNoinline && !parameter.isCrossinline && isInline && !parameter.isNoinline && !parameter.isCrossinline &&
parameter.returnTypeRef.coneType.isNonReflectFunctionalType(session) parameter.returnTypeRef.coneType.isNonReflectFunctionType(session)
} ?: continue } ?: continue
lambda.replaceInvocationKind(kind) lambda.replaceInvocationKind(kind)
} }
@@ -33,7 +33,7 @@ import org.jetbrains.kotlin.fir.resolve.dfa.unwrapSmartcastExpression
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeLocalVariableNoTypeOrInitializer import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeLocalVariableNoTypeOrInitializer
import org.jetbrains.kotlin.fir.resolve.inference.FirStubTypeTransformer import org.jetbrains.kotlin.fir.resolve.inference.FirStubTypeTransformer
import org.jetbrains.kotlin.fir.resolve.inference.ResolvedLambdaAtom import org.jetbrains.kotlin.fir.resolve.inference.ResolvedLambdaAtom
import org.jetbrains.kotlin.fir.resolve.inference.extractLambdaInfoFromFunctionalType import org.jetbrains.kotlin.fir.resolve.inference.extractLambdaInfoFromFunctionType
import org.jetbrains.kotlin.fir.resolve.substitution.createTypeSubstitutorByTypeConstructor import org.jetbrains.kotlin.fir.resolve.substitution.createTypeSubstitutorByTypeConstructor
import org.jetbrains.kotlin.fir.resolve.transformers.FirCallCompletionResultsWriterTransformer import org.jetbrains.kotlin.fir.resolve.transformers.FirCallCompletionResultsWriterTransformer
import org.jetbrains.kotlin.fir.resolve.transformers.FirStatusResolver import org.jetbrains.kotlin.fir.resolve.transformers.FirStatusResolver
@@ -763,7 +763,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirAbstractBodyResolve
data: ResolutionMode data: ResolutionMode
): FirAnonymousFunction { ): FirAnonymousFunction {
val resolvedLambdaAtom = (expectedTypeRef as? FirResolvedTypeRef)?.let { val resolvedLambdaAtom = (expectedTypeRef as? FirResolvedTypeRef)?.let {
extractLambdaInfoFromFunctionalType( extractLambdaInfoFromFunctionType(
it.type, it, anonymousFunction, returnTypeVariable = null, components, candidate = null, duringCompletion = false it.type, it, anonymousFunction, returnTypeVariable = null, components, candidate = null, duringCompletion = false
) )
} }
@@ -806,7 +806,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirAbstractBodyResolve
session.lookupTracker?.recordTypeResolveAsLookup(lambda.returnTypeRef, lambda.source, context.file.source) session.lookupTracker?.recordTypeResolveAsLookup(lambda.returnTypeRef, lambda.source, context.file.source)
} }
lambda.replaceTypeRef(lambda.constructFunctionalTypeRef(session, resolvedLambdaAtom?.expectedFunctionalTypeKind)) lambda.replaceTypeRef(lambda.constructFunctionTypeRef(session, resolvedLambdaAtom?.expectedFunctionTypeKind))
session.lookupTracker?.recordTypeResolveAsLookup(lambda.typeRef, lambda.source, context.file.source) session.lookupTracker?.recordTypeResolveAsLookup(lambda.typeRef, lambda.source, context.file.source)
lambda.addReturnToLastStatementIfNeeded() lambda.addReturnToLastStatementIfNeeded()
return lambda return lambda
@@ -859,7 +859,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirAbstractBodyResolve
lambda: FirAnonymousFunction lambda: FirAnonymousFunction
): List<FirValueParameter> { ): List<FirValueParameter> {
if (expectedType == null) return lambda.valueParameters if (expectedType == null) return lambda.valueParameters
if (!expectedType.isNonReflectFunctionalType(session)) return lambda.valueParameters if (!expectedType.isNonReflectFunctionType(session)) return lambda.valueParameters
val parameterTypes = expectedType.typeArguments val parameterTypes = expectedType.typeArguments
.mapTo(mutableListOf()) { it.type ?: session.builtinTypes.nullableAnyType.type } .mapTo(mutableListOf()) { it.type ?: session.builtinTypes.nullableAnyType.type }
.also { it.removeLastOrNull() } .also { it.removeLastOrNull() }
@@ -6,7 +6,7 @@
package org.jetbrains.kotlin.fir.diagnostics package org.jetbrains.kotlin.fir.diagnostics
import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.KtSourceElement
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
import org.jetbrains.kotlin.fir.types.ConeKotlinType import org.jetbrains.kotlin.fir.types.ConeKotlinType
import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.Name
@@ -52,9 +52,9 @@ object ConeDanglingModifierOnTopLevel : ConeDiagnostic {
get() = "Top level declaration expected" get() = "Top level declaration expected"
} }
class ConeAmbiguousFunctionalTypeKinds(val kinds: List<FunctionalTypeKind>) : ConeDiagnostic { class ConeAmbiguousFunctionTypeKinds(val kinds: List<FunctionTypeKind>) : ConeDiagnostic {
override val reason: String override val reason: String
get() = "There are multiple functional kinds for functional type ref" get() = "There are multiple function kinds for functional type ref"
} }
enum class DiagnosticKind { enum class DiagnosticKind {
@@ -0,0 +1,32 @@
/*
* 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.extensions
import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirSession
import kotlin.reflect.KClass
abstract class FirFunctionTypeKindExtension(session: FirSession) : FirExtension(session) {
companion object {
val NAME = FirExtensionPointName("CustomFunctionTypeKindExtension")
}
final override val name: FirExtensionPointName
get() = NAME
final override val extensionType: KClass<out FirExtension>
get() = FirFunctionTypeKindExtension::class
interface FunctionTypeKindRegistrar {
fun registerKind(nonReflectKind: FunctionTypeKind, reflectKind: FunctionTypeKind)
}
abstract fun FunctionTypeKindRegistrar.registerKinds()
fun interface Factory : FirExtension.Factory<FirFunctionTypeKindExtension>
}
val FirExtensionService.functionTypeKindExtensions: List<FirFunctionTypeKindExtension> by FirExtensionService.registeredExtensions()
@@ -1,32 +0,0 @@
/*
* 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.extensions
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind
import org.jetbrains.kotlin.fir.FirSession
import kotlin.reflect.KClass
abstract class FirFunctionalTypeKindExtension(session: FirSession) : FirExtension(session) {
companion object {
val NAME = FirExtensionPointName("CustomFunctionalTypeKindExtension")
}
final override val name: FirExtensionPointName
get() = NAME
final override val extensionType: KClass<out FirExtension>
get() = FirFunctionalTypeKindExtension::class
interface FunctionalTypeKindRegistrar {
fun registerKind(nonReflectKind: FunctionalTypeKind, reflectKind: FunctionalTypeKind)
}
abstract fun FunctionalTypeKindRegistrar.registerKinds()
fun interface Factory : FirExtension.Factory<FirFunctionalTypeKindExtension>
}
val FirExtensionService.functionalTypeKindExtensions: List<FirFunctionalTypeKindExtension> by FirExtensionService.registeredExtensions()
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.fir.renderer package org.jetbrains.kotlin.fir.renderer
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKindExtractor import org.jetbrains.kotlin.builtins.functions.FunctionTypeKindExtractor
import org.jetbrains.kotlin.builtins.functions.AllowedToUsedOnlyInK1 import org.jetbrains.kotlin.builtins.functions.AllowedToUsedOnlyInK1
import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget
import org.jetbrains.kotlin.fir.* import org.jetbrains.kotlin.fir.*
@@ -749,7 +749,7 @@ class FirRenderer(
resolvedTypeRef.type, resolvedTypeRef.type,
l@{ l@{
val classId = it.classId ?: return@l null val classId = it.classId ?: return@l null
FunctionalTypeKindExtractor.Default.getFunctionalClassKind(classId.packageFqName, classId.shortClassName.asString()) FunctionTypeKindExtractor.Default.getFunctionalClassKind(classId.packageFqName, classId.shortClassName.asString())
} }
) )
} }
@@ -5,17 +5,17 @@
package org.jetbrains.kotlin.fir.types package org.jetbrains.kotlin.fir.types
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKindExtractor import org.jetbrains.kotlin.builtins.functions.FunctionTypeKindExtractor
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.FirSessionComponent import org.jetbrains.kotlin.fir.FirSessionComponent
import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.FqName
abstract class FirFunctionalTypeKindService : FirSessionComponent { abstract class FirFunctionTypeKindService : FirSessionComponent {
protected abstract val extractor: FunctionalTypeKindExtractor protected abstract val extractor: FunctionTypeKindExtractor
fun getKindByClassNamePrefix(packageFqName: FqName, className: String): FunctionalTypeKind? { fun getKindByClassNamePrefix(packageFqName: FqName, className: String): FunctionTypeKind? {
return extractor.getFunctionalClassKindWithArity(packageFqName, className)?.kind return extractor.getFunctionalClassKindWithArity(packageFqName, className)?.kind
} }
@@ -23,9 +23,9 @@ abstract class FirFunctionalTypeKindService : FirSessionComponent {
return extractor.hasKindWithSpecificPackage(packageFqName) return extractor.hasKindWithSpecificPackage(packageFqName)
} }
abstract fun extractSingleSpecialKindForFunction(functionSymbol: FirFunctionSymbol<*>): FunctionalTypeKind? abstract fun extractSingleSpecialKindForFunction(functionSymbol: FirFunctionSymbol<*>): FunctionTypeKind?
abstract fun extractAllSpecialKindsForFunction(functionSymbol: FirFunctionSymbol<*>): List<FunctionalTypeKind> abstract fun extractAllSpecialKindsForFunction(functionSymbol: FirFunctionSymbol<*>): List<FunctionTypeKind>
abstract fun extractAllSpecialKindsForFunctionalTypeRef(typeRef: FirFunctionTypeRef): List<FunctionalTypeKind> abstract fun extractAllSpecialKindsForFunctionTypeRef(typeRef: FirFunctionTypeRef): List<FunctionTypeKind>
} }
val FirSession.functionalTypeService: FirFunctionalTypeKindService by FirSession.sessionComponentAccessor() val FirSession.functionTypeService: FirFunctionTypeKindService by FirSession.sessionComponentAccessor()
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.resolve.checkers package org.jetbrains.kotlin.resolve.checkers
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
@@ -22,14 +22,14 @@ object SuspendFunctionAsSupertypeChecker : DeclarationChecker {
val functionalSupertypes = descriptor.getAllSuperClassifiers().filterIsInstance<FunctionClassDescriptor>().toList() val functionalSupertypes = descriptor.getAllSuperClassifiers().filterIsInstance<FunctionClassDescriptor>().toList()
if (functionalSupertypes.none { if (functionalSupertypes.none {
it.functionKind == FunctionalTypeKind.SuspendFunction || it.functionKind == FunctionTypeKind.SuspendFunction ||
it.functionKind == FunctionalTypeKind.KSuspendFunction it.functionKind == FunctionTypeKind.KSuspendFunction
} }
) return ) return
if (functionalSupertypes.any { if (functionalSupertypes.any {
it.functionKind == FunctionalTypeKind.Function || it.functionKind == FunctionTypeKind.Function ||
it.functionKind == FunctionalTypeKind.KFunction it.functionKind == FunctionTypeKind.KFunction
} }
) { ) {
val reportOn = (declaration as? KtClassOrObject)?.getSuperTypeList() ?: declaration val reportOn = (declaration as? KtClassOrObject)?.getSuperTypeList() ?: declaration
@@ -5,8 +5,8 @@
package org.jetbrains.kotlin.resolve.calls.inference.components package org.jetbrains.kotlin.resolve.calls.inference.components
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.isRegularFunction import org.jetbrains.kotlin.builtins.functions.isBasicFunctionOrKFunction
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.resolve.calls.inference.model.* import org.jetbrains.kotlin.resolve.calls.inference.model.*
@@ -30,7 +30,7 @@ class PostponedArgumentInputTypesResolver(
val parametersFromConstraints: Set<List<TypeWithKind>>?, val parametersFromConstraints: Set<List<TypeWithKind>>?,
val annotations: List<AnnotationMarker>?, val annotations: List<AnnotationMarker>?,
val isExtensionFunction: Boolean, val isExtensionFunction: Boolean,
val functionalTypeKind: FunctionalTypeKind, val functionTypeKind: FunctionTypeKind,
val isNullable: Boolean val isNullable: Boolean
) )
@@ -44,7 +44,7 @@ class PostponedArgumentInputTypesResolver(
variableDependencyProvider: TypeVariableDependencyInformationProvider variableDependencyProvider: TypeVariableDependencyInformationProvider
): List<TypeWithKind> { ): List<TypeWithKind> {
fun List<Constraint>.extractFunctionalTypes() = mapNotNull { constraint -> fun List<Constraint>.extractFunctionalTypes() = mapNotNull { constraint ->
TypeWithKind(constraint.type.getFunctionalTypeFromSupertypes(), constraint.kind) TypeWithKind(constraint.type.getFunctionTypeFromSupertypes(), constraint.kind)
} }
val typeVariableTypeConstructor = variable.typeVariable.freshTypeConstructor() val typeVariableTypeConstructor = variable.typeVariable.freshTypeConstructor()
@@ -53,7 +53,7 @@ class PostponedArgumentInputTypesResolver(
return dependentVariables.flatMap { type -> return dependentVariables.flatMap { type ->
val constraints = notFixedTypeVariables[type]?.constraints ?: return@flatMap emptyList() val constraints = notFixedTypeVariables[type]?.constraints ?: return@flatMap emptyList()
val constraintsWithFunctionalType = constraints.filter { it.type.isBuiltinFunctionalTypeOrSubtype() } val constraintsWithFunctionalType = constraints.filter { it.type.isBuiltinFunctionTypeOrSubtype() }
constraintsWithFunctionalType.extractFunctionalTypes() constraintsWithFunctionalType.extractFunctionalTypes()
} }
} }
@@ -75,7 +75,7 @@ class PostponedArgumentInputTypesResolver(
if (argument is LambdaWithTypeVariableAsExpectedTypeMarker) argument.parameterTypesFromDeclaration else null if (argument is LambdaWithTypeVariableAsExpectedTypeMarker) argument.parameterTypesFromDeclaration else null
val parameterTypesFromConstraints = functionalTypesFromConstraints.mapTo(SmartSet.create()) { typeWithKind -> val parameterTypesFromConstraints = functionalTypesFromConstraints.mapTo(SmartSet.create()) { typeWithKind ->
typeWithKind.type.extractArgumentsForFunctionalTypeOrSubtype().map { typeWithKind.type.extractArgumentsForFunctionTypeOrSubtype().map {
// We should use opposite kind as lambda's parameters are contravariant // We should use opposite kind as lambda's parameters are contravariant
TypeWithKind(it, typeWithKind.direction.opposite()) TypeWithKind(it, typeWithKind.direction.opposite())
} }
@@ -96,16 +96,16 @@ class PostponedArgumentInputTypesResolver(
parameterTypesFromDeclaration, parameterTypesFromDeclaration,
) )
var functionalTypeKind: FunctionalTypeKind? = null var functionTypeKind: FunctionTypeKind? = null
var isNullable = false var isNullable = false
if (functionalTypesFromConstraints.isNotEmpty()) { if (functionalTypesFromConstraints.isNotEmpty()) {
isNullable = true isNullable = true
for (funType in functionalTypesFromConstraints) { for (funType in functionalTypesFromConstraints) {
if (functionalTypeKind == null) { if (functionTypeKind == null) {
funType.type.functionalTypeKind()?.takeUnless { it.isRegularFunction }?.let { functionalTypeKind = it } funType.type.functionTypeKind()?.takeUnless { it.isBasicFunctionOrKFunction }?.let { functionTypeKind = it }
} }
if (isNullable && !funType.type.isMarkedNullable()) isNullable = false if (isNullable && !funType.type.isMarkedNullable()) isNullable = false
if ((functionalTypeKind != null) && !isNullable) break if ((functionTypeKind != null) && !isNullable) break
} }
} }
@@ -126,7 +126,7 @@ class PostponedArgumentInputTypesResolver(
parameterTypesFromConstraints, parameterTypesFromConstraints,
annotations = annotations, annotations = annotations,
isExtensionFunction, isExtensionFunction,
functionalTypeKind ?: FunctionalTypeKind.Function, functionTypeKind ?: FunctionTypeKind.Function,
isNullable = isNullable isNullable = isNullable
) )
} }
@@ -258,7 +258,7 @@ class PostponedArgumentInputTypesResolver(
private fun Context.computeResultingFunctionalConstructor( private fun Context.computeResultingFunctionalConstructor(
argument: PostponedAtomWithRevisableExpectedType, argument: PostponedAtomWithRevisableExpectedType,
parametersNumber: Int, parametersNumber: Int,
functionalTypeKind: FunctionalTypeKind, functionTypeKind: FunctionTypeKind,
resultTypeResolver: ResultTypeResolver resultTypeResolver: ResultTypeResolver
): TypeConstructorMarker { ): TypeConstructorMarker {
val expectedType = argument.expectedType val expectedType = argument.expectedType
@@ -268,7 +268,7 @@ class PostponedArgumentInputTypesResolver(
return when (argument) { return when (argument) {
is LambdaWithTypeVariableAsExpectedTypeMarker -> is LambdaWithTypeVariableAsExpectedTypeMarker ->
getNonReflectFunctionTypeConstructor(parametersNumber, functionalTypeKind) getNonReflectFunctionTypeConstructor(parametersNumber, functionTypeKind)
is PostponedCallableReferenceMarker -> { is PostponedCallableReferenceMarker -> {
val computedResultType = resultTypeResolver.findResultType( val computedResultType = resultTypeResolver.findResultType(
this@computeResultingFunctionalConstructor, this@computeResultingFunctionalConstructor,
@@ -277,10 +277,10 @@ class PostponedArgumentInputTypesResolver(
) )
// Avoid KFunction<...>/Function<...> types // Avoid KFunction<...>/Function<...> types
if (computedResultType.isBuiltinFunctionalTypeOrSubtype() && computedResultType.argumentsCount() > 1) { if (computedResultType.isBuiltinFunctionTypeOrSubtype() && computedResultType.argumentsCount() > 1) {
computedResultType.typeConstructor() computedResultType.typeConstructor()
} else { } else {
getReflectFunctionTypeConstructor(parametersNumber, functionalTypeKind) getReflectFunctionTypeConstructor(parametersNumber, functionTypeKind)
} }
} }
else -> throw IllegalStateException("Unsupported postponed argument type of $argument") else -> throw IllegalStateException("Unsupported postponed argument type of $argument")
@@ -382,7 +382,7 @@ class PostponedArgumentInputTypesResolver(
val functionalConstructor = computeResultingFunctionalConstructor( val functionalConstructor = computeResultingFunctionalConstructor(
argument, argument,
variablesForParameterTypes.size, variablesForParameterTypes.size,
parameterTypesInfo.functionalTypeKind, parameterTypesInfo.functionTypeKind,
resultTypeResolver resultTypeResolver
) )
@@ -558,7 +558,7 @@ class PostponedArgumentInputTypesResolver(
dependencyProvider: TypeVariableDependencyInformationProvider, dependencyProvider: TypeVariableDependencyInformationProvider,
resolvedAtomByTypeVariableProvider: ResolvedAtomProvider, resolvedAtomByTypeVariableProvider: ResolvedAtomProvider,
): Boolean = with(resolutionTypeSystemContext) { ): Boolean = with(resolutionTypeSystemContext) {
val relatedVariables = type.extractArgumentsForFunctionalTypeOrSubtype() val relatedVariables = type.extractArgumentsForFunctionTypeOrSubtype()
.flatMap { getAllDeeplyRelatedTypeVariables(it, dependencyProvider) } .flatMap { getAllDeeplyRelatedTypeVariables(it, dependencyProvider) }
val variableForFixation = variableFixationFinder.findFirstVariableForFixation( val variableForFixation = variableFixationFinder.findFirstVariableForFixation(
this@fixNextReadyVariableForParameterType, this@fixNextReadyVariableForParameterType,
@@ -16,7 +16,7 @@
package org.jetbrains.kotlin.resolve.calls.tasks package org.jetbrains.kotlin.resolve.calls.tasks
import org.jetbrains.kotlin.builtins.getFunctionalClassKind import org.jetbrains.kotlin.builtins.getFunctionTypeKind
import org.jetbrains.kotlin.builtins.isBuiltinFunctionClass import org.jetbrains.kotlin.builtins.isBuiltinFunctionClass
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor
import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor
@@ -90,5 +90,5 @@ fun isSynthesizedInvoke(descriptor: DeclarationDescriptor): Boolean {
} }
return real.kind == CallableMemberDescriptor.Kind.SYNTHESIZED && return real.kind == CallableMemberDescriptor.Kind.SYNTHESIZED &&
real.containingDeclaration.getFunctionalClassKind() != null real.containingDeclaration.getFunctionTypeKind() != null
} }
@@ -339,7 +339,7 @@ class FirVisualizer(private val firFile: FirFile) : BaseRenderer() {
val projectionBuilder = StringBuilder() val projectionBuilder = StringBuilder()
ConeTypeRendererForDebugging(projectionBuilder).renderAsPossibleFunctionType( ConeTypeRendererForDebugging(projectionBuilder).renderAsPossibleFunctionType(
this, this,
{ it.functionalTypeKind(session) } { it.functionTypeKind(session) }
) { ) {
localTypeProjectionRenderer(projectionBuilder) localTypeProjectionRenderer(projectionBuilder)
} }
@@ -9,19 +9,19 @@ import org.jetbrains.kotlin.builtins.CompanionObjectMapping
import org.jetbrains.kotlin.builtins.StandardNames import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.builtins.StandardNames.FqNames import org.jetbrains.kotlin.builtins.StandardNames.FqNames
import org.jetbrains.kotlin.builtins.functions.BuiltInFunctionArity import org.jetbrains.kotlin.builtins.functions.BuiltInFunctionArity
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.name.* import org.jetbrains.kotlin.name.*
import org.jetbrains.kotlin.resolve.jvm.JvmPrimitiveType import org.jetbrains.kotlin.resolve.jvm.JvmPrimitiveType
object JavaToKotlinClassMap { object JavaToKotlinClassMap {
private val NUMBERED_FUNCTION_PREFIX: String = private val NUMBERED_FUNCTION_PREFIX: String =
FunctionalTypeKind.Function.packageFqName.toString() + "." + FunctionalTypeKind.Function.classNamePrefix FunctionTypeKind.Function.packageFqName.toString() + "." + FunctionTypeKind.Function.classNamePrefix
private val NUMBERED_K_FUNCTION_PREFIX: String = private val NUMBERED_K_FUNCTION_PREFIX: String =
FunctionalTypeKind.KFunction.packageFqName.toString() + "." + FunctionalTypeKind.KFunction.classNamePrefix FunctionTypeKind.KFunction.packageFqName.toString() + "." + FunctionTypeKind.KFunction.classNamePrefix
private val NUMBERED_SUSPEND_FUNCTION_PREFIX: String = private val NUMBERED_SUSPEND_FUNCTION_PREFIX: String =
FunctionalTypeKind.SuspendFunction.packageFqName.toString() + "." + FunctionalTypeKind.SuspendFunction.classNamePrefix FunctionTypeKind.SuspendFunction.packageFqName.toString() + "." + FunctionTypeKind.SuspendFunction.classNamePrefix
private val NUMBERED_K_SUSPEND_FUNCTION_PREFIX: String = private val NUMBERED_K_SUSPEND_FUNCTION_PREFIX: String =
FunctionalTypeKind.KSuspendFunction.packageFqName.toString() + "." + FunctionalTypeKind.KSuspendFunction.classNamePrefix FunctionTypeKind.KSuspendFunction.packageFqName.toString() + "." + FunctionTypeKind.KSuspendFunction.classNamePrefix
private val FUNCTION_N_CLASS_ID: ClassId = ClassId.topLevel(FqName("kotlin.jvm.functions.FunctionN")) private val FUNCTION_N_CLASS_ID: ClassId = ClassId.topLevel(FqName("kotlin.jvm.functions.FunctionN"))
val FUNCTION_N_FQ_NAME: FqName = FUNCTION_N_CLASS_ID.asSingleFqName() val FUNCTION_N_FQ_NAME: FqName = FUNCTION_N_CLASS_ID.asSingleFqName()
@@ -97,7 +97,7 @@ object JavaToKotlinClassMap {
addKotlinToJava(FqName(NUMBERED_K_FUNCTION_PREFIX + i), K_FUNCTION_CLASS_ID) addKotlinToJava(FqName(NUMBERED_K_FUNCTION_PREFIX + i), K_FUNCTION_CLASS_ID)
} }
for (i in 0 until BuiltInFunctionArity.BIG_ARITY - 1) { for (i in 0 until BuiltInFunctionArity.BIG_ARITY - 1) {
val kSuspendFunction = FunctionalTypeKind.KSuspendFunction val kSuspendFunction = FunctionTypeKind.KSuspendFunction
val kSuspendFun = kSuspendFunction.packageFqName.toString() + "." + kSuspendFunction.classNamePrefix val kSuspendFun = kSuspendFunction.packageFqName.toString() + "." + kSuspendFunction.classNamePrefix
addKotlinToJava(FqName(kSuspendFun + i), K_FUNCTION_CLASS_ID) addKotlinToJava(FqName(kSuspendFun + i), K_FUNCTION_CLASS_ID)
} }
@@ -6,7 +6,7 @@
package org.jetbrains.kotlin.builtins package org.jetbrains.kotlin.builtins
import org.jetbrains.kotlin.builtins.StandardNames.FqNames.reflect import org.jetbrains.kotlin.builtins.StandardNames.FqNames.reflect
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.FqNameUnsafe import org.jetbrains.kotlin.name.FqNameUnsafe
@@ -252,7 +252,7 @@ object StandardNames {
@JvmStatic @JvmStatic
fun getKFunctionFqName(parameterCount: Int): FqNameUnsafe { fun getKFunctionFqName(parameterCount: Int): FqNameUnsafe {
return reflect(FunctionalTypeKind.KFunction.classNamePrefix + parameterCount) return reflect(FunctionTypeKind.KFunction.classNamePrefix + parameterCount)
} }
@JvmStatic @JvmStatic
@@ -263,7 +263,7 @@ object StandardNames {
@JvmStatic @JvmStatic
fun getSuspendFunctionName(parameterCount: Int): String { fun getSuspendFunctionName(parameterCount: Int): String {
return FunctionalTypeKind.SuspendFunction.classNamePrefix + parameterCount return FunctionTypeKind.SuspendFunction.classNamePrefix + parameterCount
} }
@JvmStatic @JvmStatic
@@ -273,7 +273,7 @@ object StandardNames {
@JvmStatic @JvmStatic
fun getKSuspendFunctionName(parameterCount: Int): FqNameUnsafe { fun getKSuspendFunctionName(parameterCount: Int): FqNameUnsafe {
return reflect(FunctionalTypeKind.KSuspendFunction.classNamePrefix + parameterCount) return reflect(FunctionTypeKind.KSuspendFunction.classNamePrefix + parameterCount)
} }
@JvmStatic @JvmStatic
@@ -11,7 +11,7 @@ import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.Name
/** /**
* [FunctionalTypeKind] describes a family of various similar functional types (like kotlin.FunctionN) * [FunctionTypeKind] describes a family of various similar functional types (like kotlin.FunctionN)
* All types in the same family have corresponding shape of classId: [packageFqName].[classNamePrefix]N, * All types in the same family have corresponding shape of classId: [packageFqName].[classNamePrefix]N,
* where `N` is an arity of function * where `N` is an arity of function
* *
@@ -38,7 +38,7 @@ import org.jetbrains.kotlin.name.Name
* Note that if you provide some new functional type kind it's your responsibility to handle all references to it in backend * Note that if you provide some new functional type kind it's your responsibility to handle all references to it in backend
* with [IrGenerationExtension] implementation * with [IrGenerationExtension] implementation
*/ */
abstract class FunctionalTypeKind internal constructor( abstract class FunctionTypeKind internal constructor(
val packageFqName: FqName, val packageFqName: FqName,
val classNamePrefix: String, val classNamePrefix: String,
val isReflectType: Boolean, val isReflectType: Boolean,
@@ -69,7 +69,7 @@ abstract class FunctionalTypeKind internal constructor(
* *
* Should be overridden for reflect kinds * Should be overridden for reflect kinds
*/ */
open fun nonReflectKind(): FunctionalTypeKind { open fun nonReflectKind(): FunctionTypeKind {
return if (isReflectType) error("Should be overridden explicitly") else this return if (isReflectType) error("Should be overridden explicitly") else this
} }
@@ -79,7 +79,7 @@ abstract class FunctionalTypeKind internal constructor(
* *
* Should be overridden for non reflect kinds * Should be overridden for non reflect kinds
*/ */
open fun reflectKind(): FunctionalTypeKind { open fun reflectKind(): FunctionTypeKind {
return if (isReflectType) this else error("Should be overridden explicitly") return if (isReflectType) this else error("Should be overridden explicitly")
} }
@@ -93,16 +93,16 @@ abstract class FunctionalTypeKind internal constructor(
// ------------------------------------------- Builtin functional kinds ------------------------------------------- // ------------------------------------------- Builtin functional kinds -------------------------------------------
object Function : FunctionalTypeKind( object Function : FunctionTypeKind(
StandardNames.BUILT_INS_PACKAGE_FQ_NAME, StandardNames.BUILT_INS_PACKAGE_FQ_NAME,
"Function", "Function",
isReflectType = false, isReflectType = false,
annotationOnInvokeClassId = null annotationOnInvokeClassId = null
) { ) {
override fun reflectKind(): FunctionalTypeKind = KFunction override fun reflectKind(): FunctionTypeKind = KFunction
} }
object SuspendFunction : FunctionalTypeKind( object SuspendFunction : FunctionTypeKind(
StandardNames.COROUTINES_PACKAGE_FQ_NAME, StandardNames.COROUTINES_PACKAGE_FQ_NAME,
"SuspendFunction", "SuspendFunction",
isReflectType = false, isReflectType = false,
@@ -111,39 +111,39 @@ abstract class FunctionalTypeKind internal constructor(
override val prefixForTypeRender: String override val prefixForTypeRender: String
get() = "suspend" get() = "suspend"
override fun reflectKind(): FunctionalTypeKind = KSuspendFunction override fun reflectKind(): FunctionTypeKind = KSuspendFunction
} }
object KFunction : FunctionalTypeKind( object KFunction : FunctionTypeKind(
StandardNames.KOTLIN_REFLECT_FQ_NAME, StandardNames.KOTLIN_REFLECT_FQ_NAME,
"KFunction", "KFunction",
isReflectType = true, isReflectType = true,
annotationOnInvokeClassId = null annotationOnInvokeClassId = null
) { ) {
override fun nonReflectKind(): FunctionalTypeKind = Function override fun nonReflectKind(): FunctionTypeKind = Function
} }
object KSuspendFunction : FunctionalTypeKind( object KSuspendFunction : FunctionTypeKind(
StandardNames.KOTLIN_REFLECT_FQ_NAME, StandardNames.KOTLIN_REFLECT_FQ_NAME,
"KSuspendFunction", "KSuspendFunction",
isReflectType = true, isReflectType = true,
annotationOnInvokeClassId = null annotationOnInvokeClassId = null
) { ) {
override fun nonReflectKind(): FunctionalTypeKind = SuspendFunction override fun nonReflectKind(): FunctionTypeKind = SuspendFunction
} }
} }
val FunctionalTypeKind.isBuiltin: Boolean val FunctionTypeKind.isBuiltin: Boolean
get() = when (this) { get() = when (this) {
FunctionalTypeKind.Function, FunctionTypeKind.Function,
FunctionalTypeKind.SuspendFunction, FunctionTypeKind.SuspendFunction,
FunctionalTypeKind.KFunction, FunctionTypeKind.KFunction,
FunctionalTypeKind.KSuspendFunction -> true FunctionTypeKind.KSuspendFunction -> true
else -> false else -> false
} }
val FunctionalTypeKind.isSuspendType: Boolean val FunctionTypeKind.isSuspendOrKSuspendFunction: Boolean
get() = this.nonReflectKind() == FunctionalTypeKind.SuspendFunction get() = this.nonReflectKind() == FunctionTypeKind.SuspendFunction
val FunctionalTypeKind.isRegularFunction: Boolean val FunctionTypeKind.isBasicFunctionOrKFunction: Boolean
get() = this.nonReflectKind() == FunctionalTypeKind.Function get() = this.nonReflectKind() == FunctionTypeKind.Function
@@ -10,7 +10,7 @@ import org.jetbrains.kotlin.name.FqName
@RequiresOptIn @RequiresOptIn
annotation class AllowedToUsedOnlyInK1 annotation class AllowedToUsedOnlyInK1
class FunctionalTypeKindExtractor(kinds: List<FunctionalTypeKind>) { class FunctionTypeKindExtractor(kinds: List<FunctionTypeKind>) {
companion object { companion object {
/** /**
* This instance should be used only in: * This instance should be used only in:
@@ -19,19 +19,19 @@ class FunctionalTypeKindExtractor(kinds: List<FunctionalTypeKind>) {
*/ */
@JvmStatic @JvmStatic
@AllowedToUsedOnlyInK1 @AllowedToUsedOnlyInK1
val Default = FunctionalTypeKindExtractor( val Default = FunctionTypeKindExtractor(
listOf( listOf(
FunctionalTypeKind.Function, FunctionTypeKind.Function,
FunctionalTypeKind.SuspendFunction, FunctionTypeKind.SuspendFunction,
FunctionalTypeKind.KFunction, FunctionTypeKind.KFunction,
FunctionalTypeKind.KSuspendFunction, FunctionTypeKind.KSuspendFunction,
) )
) )
} }
private val knownKindsByPackageFqName = kinds.groupBy { it.packageFqName } private val knownKindsByPackageFqName = kinds.groupBy { it.packageFqName }
fun getFunctionalClassKind(packageFqName: FqName, className: String): FunctionalTypeKind? { fun getFunctionalClassKind(packageFqName: FqName, className: String): FunctionTypeKind? {
return getFunctionalClassKindWithArity(packageFqName, className)?.kind return getFunctionalClassKindWithArity(packageFqName, className)?.kind
} }
@@ -49,7 +49,7 @@ class FunctionalTypeKindExtractor(kinds: List<FunctionalTypeKind>) {
return packageFqName in knownKindsByPackageFqName return packageFqName in knownKindsByPackageFqName
} }
data class KindWithArity(val kind: FunctionalTypeKind, val arity: Int) data class KindWithArity(val kind: FunctionTypeKind, val arity: Int)
private fun toInt(s: String): Int? { private fun toInt(s: String): Int? {
if (s.isEmpty()) return null if (s.isEmpty()) return null
@@ -5,7 +5,7 @@
package org.jetbrains.kotlin.types.model package org.jetbrains.kotlin.types.model
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.resolve.checkers.EmptyIntersectionTypeChecker import org.jetbrains.kotlin.resolve.checkers.EmptyIntersectionTypeChecker
import org.jetbrains.kotlin.resolve.checkers.EmptyIntersectionTypeInfo import org.jetbrains.kotlin.resolve.checkers.EmptyIntersectionTypeInfo
import org.jetbrains.kotlin.types.* import org.jetbrains.kotlin.types.*
@@ -165,7 +165,7 @@ interface TypeSystemInferenceExtensionContext : TypeSystemContext, TypeSystemBui
fun KotlinTypeMarker.isUnit(): Boolean fun KotlinTypeMarker.isUnit(): Boolean
fun KotlinTypeMarker.isBuiltinFunctionalTypeOrSubtype(): Boolean fun KotlinTypeMarker.isBuiltinFunctionTypeOrSubtype(): Boolean
fun createCapturedType( fun createCapturedType(
constructorProjection: TypeArgumentMarker, constructorProjection: TypeArgumentMarker,
@@ -252,17 +252,17 @@ interface TypeSystemInferenceExtensionContext : TypeSystemContext, TypeSystemBui
fun KotlinTypeMarker.isFunctionOrKFunctionWithAnySuspendability(): Boolean fun KotlinTypeMarker.isFunctionOrKFunctionWithAnySuspendability(): Boolean
fun KotlinTypeMarker.functionalTypeKind(): FunctionalTypeKind? fun KotlinTypeMarker.functionTypeKind(): FunctionTypeKind?
fun KotlinTypeMarker.isExtensionFunctionType(): Boolean fun KotlinTypeMarker.isExtensionFunctionType(): Boolean
fun KotlinTypeMarker.extractArgumentsForFunctionalTypeOrSubtype(): List<KotlinTypeMarker> fun KotlinTypeMarker.extractArgumentsForFunctionTypeOrSubtype(): List<KotlinTypeMarker>
fun KotlinTypeMarker.getFunctionalTypeFromSupertypes(): KotlinTypeMarker fun KotlinTypeMarker.getFunctionTypeFromSupertypes(): KotlinTypeMarker
fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker
fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker
// ------------------------------------------------- // -------------------------------------------------
@@ -10,7 +10,7 @@ import kotlin.jvm.functions.Function1;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.builtins.functions.BuiltInFictitiousFunctionClassFactory; import org.jetbrains.kotlin.builtins.functions.BuiltInFictitiousFunctionClassFactory;
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind; import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind;
import org.jetbrains.kotlin.descriptors.*; import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.annotations.Annotations; import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.descriptors.deserialization.AdditionalClassPartsProvider; import org.jetbrains.kotlin.descriptors.deserialization.AdditionalClassPartsProvider;
@@ -315,7 +315,7 @@ public abstract class KotlinBuiltIns {
@NotNull @NotNull
public ClassDescriptor getKSuspendFunction(int parameterCount) { public ClassDescriptor getKSuspendFunction(int parameterCount) {
Name name = Name.identifier(FunctionalTypeKind.KSuspendFunction.INSTANCE.getClassNamePrefix() + parameterCount); Name name = Name.identifier(FunctionTypeKind.KSuspendFunction.INSTANCE.getClassNamePrefix() + parameterCount);
return getBuiltInClassByFqName(COROUTINES_PACKAGE_FQ_NAME.child(name)); return getBuiltInClassByFqName(COROUTINES_PACKAGE_FQ_NAME.child(name));
} }
@@ -6,8 +6,8 @@
package org.jetbrains.kotlin.builtins package org.jetbrains.kotlin.builtins
import org.jetbrains.kotlin.builtins.StandardNames.BUILT_INS_PACKAGE_NAME import org.jetbrains.kotlin.builtins.StandardNames.BUILT_INS_PACKAGE_NAME
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKindExtractor import org.jetbrains.kotlin.builtins.functions.FunctionTypeKindExtractor
import org.jetbrains.kotlin.builtins.functions.AllowedToUsedOnlyInK1 import org.jetbrains.kotlin.builtins.functions.AllowedToUsedOnlyInK1
import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
@@ -59,20 +59,20 @@ val KotlinType.isBuiltinFunctionalTypeOrSubtype: Boolean
fun KotlinType.isFunctionTypeOrSubtype(predicate: (KotlinType) -> Boolean): Boolean = fun KotlinType.isFunctionTypeOrSubtype(predicate: (KotlinType) -> Boolean): Boolean =
isTypeOrSubtypeOf { it.isFunctionType && predicate(it) } isTypeOrSubtypeOf { it.isFunctionType && predicate(it) }
val KotlinType.functionalTypeKind: FunctionalTypeKind? val KotlinType.functionTypeKind: FunctionTypeKind?
get() = constructor.declarationDescriptor?.getFunctionalClassKind() get() = constructor.declarationDescriptor?.getFunctionTypeKind()
val KotlinType.isFunctionType: Boolean val KotlinType.isFunctionType: Boolean
get() = functionalTypeKind == FunctionalTypeKind.Function get() = functionTypeKind == FunctionTypeKind.Function
val KotlinType.isKFunctionType: Boolean val KotlinType.isKFunctionType: Boolean
get() = functionalTypeKind == FunctionalTypeKind.KFunction get() = functionTypeKind == FunctionTypeKind.KFunction
val KotlinType.isSuspendFunctionType: Boolean val KotlinType.isSuspendFunctionType: Boolean
get() = functionalTypeKind == FunctionalTypeKind.SuspendFunction get() = functionTypeKind == FunctionTypeKind.SuspendFunction
val KotlinType.isKSuspendFunctionType: Boolean val KotlinType.isKSuspendFunctionType: Boolean
get() = functionalTypeKind == FunctionalTypeKind.KSuspendFunction get() = functionTypeKind == FunctionTypeKind.KSuspendFunction
val KotlinType.isFunctionOrSuspendFunctionType: Boolean val KotlinType.isFunctionOrSuspendFunctionType: Boolean
get() = isFunctionType || isSuspendFunctionType get() = isFunctionType || isSuspendFunctionType
@@ -85,17 +85,17 @@ val KotlinType.isBuiltinFunctionalType: Boolean
val DeclarationDescriptor.isBuiltinFunctionalClassDescriptor: Boolean val DeclarationDescriptor.isBuiltinFunctionalClassDescriptor: Boolean
get() { get() {
val functionalClassKind = getFunctionalClassKind() val functionalClassKind = getFunctionTypeKind()
return functionalClassKind == FunctionalTypeKind.Function || return functionalClassKind == FunctionTypeKind.Function ||
functionalClassKind == FunctionalTypeKind.SuspendFunction functionalClassKind == FunctionTypeKind.SuspendFunction
} }
fun isBuiltinFunctionClass(classId: ClassId): Boolean { fun isBuiltinFunctionClass(classId: ClassId): Boolean {
if (!classId.startsWith(StandardNames.BUILT_INS_PACKAGE_NAME)) return false if (!classId.startsWith(StandardNames.BUILT_INS_PACKAGE_NAME)) return false
val kind = classId.asSingleFqName().toUnsafe().getFunctionalClassKind() val kind = classId.asSingleFqName().toUnsafe().getFunctionTypeKind()
return kind == FunctionalTypeKind.Function || return kind == FunctionTypeKind.Function ||
kind == FunctionalTypeKind.SuspendFunction kind == FunctionTypeKind.SuspendFunction
} }
val KotlinType.isNonExtensionFunctionType: Boolean val KotlinType.isNonExtensionFunctionType: Boolean
@@ -116,21 +116,21 @@ private val KotlinType.isTypeAnnotatedWithExtensionFunctionType: Boolean
*/ */
fun isNumberedFunctionClassFqName(fqName: FqNameUnsafe): Boolean { fun isNumberedFunctionClassFqName(fqName: FqNameUnsafe): Boolean {
return fqName.startsWith(BUILT_INS_PACKAGE_NAME) && return fqName.startsWith(BUILT_INS_PACKAGE_NAME) &&
fqName.getFunctionalClassKind() == FunctionalTypeKind.Function fqName.getFunctionTypeKind() == FunctionTypeKind.Function
} }
fun DeclarationDescriptor.getFunctionalClassKind(): FunctionalTypeKind? { fun DeclarationDescriptor.getFunctionTypeKind(): FunctionTypeKind? {
if (this !is ClassDescriptor) return null if (this !is ClassDescriptor) return null
if (!KotlinBuiltIns.isUnderKotlinPackage(this)) return null if (!KotlinBuiltIns.isUnderKotlinPackage(this)) return null
return fqNameUnsafe.getFunctionalClassKind() return fqNameUnsafe.getFunctionTypeKind()
} }
@OptIn(AllowedToUsedOnlyInK1::class) @OptIn(AllowedToUsedOnlyInK1::class)
private fun FqNameUnsafe.getFunctionalClassKind(): FunctionalTypeKind? { private fun FqNameUnsafe.getFunctionTypeKind(): FunctionTypeKind? {
if (!isSafe || isRoot) return null if (!isSafe || isRoot) return null
return FunctionalTypeKindExtractor.Default.getFunctionalClassKind(toSafe().parent(), shortName().asString()) return FunctionTypeKindExtractor.Default.getFunctionalClassKind(toSafe().parent(), shortName().asString())
} }
fun KotlinType.contextFunctionTypeParamsCount(): Int { fun KotlinType.contextFunctionTypeParamsCount(): Int {
@@ -38,7 +38,7 @@ class BuiltInFictitiousFunctionClassFactory(
val string = name.asString() val string = name.asString()
return (string.startsWith("Function") || string.startsWith("KFunction") || return (string.startsWith("Function") || string.startsWith("KFunction") ||
string.startsWith("SuspendFunction") || string.startsWith("KSuspendFunction")) // an optimization string.startsWith("SuspendFunction") || string.startsWith("KSuspendFunction")) // an optimization
&& FunctionalTypeKindExtractor.Default.getFunctionalClassKindWithArity(packageFqName, string) != null && FunctionTypeKindExtractor.Default.getFunctionalClassKindWithArity(packageFqName, string) != null
} }
@OptIn(AllowedToUsedOnlyInK1::class) @OptIn(AllowedToUsedOnlyInK1::class)
@@ -49,7 +49,7 @@ class BuiltInFictitiousFunctionClassFactory(
if ("Function" !in className) return null // An optimization if ("Function" !in className) return null // An optimization
val packageFqName = classId.packageFqName val packageFqName = classId.packageFqName
val (kind, arity) = FunctionalTypeKindExtractor.Default.getFunctionalClassKindWithArity(packageFqName, className) ?: return null val (kind, arity) = FunctionTypeKindExtractor.Default.getFunctionalClassKindWithArity(packageFqName, className) ?: return null
val builtInsFragments = module.getPackage(packageFqName).fragments.filterIsInstance<BuiltInsPackageFragment>() val builtInsFragments = module.getPackage(packageFqName).fragments.filterIsInstance<BuiltInsPackageFragment>()
@@ -29,10 +29,10 @@ import org.jetbrains.kotlin.utils.addToStdlib.shouldNotBeCalled
* This allows to use both 'invoke' and reflection API on function references obtained by '::'. * This allows to use both 'invoke' and reflection API on function references obtained by '::'.
*/ */
class FunctionClassDescriptor( class FunctionClassDescriptor(
private val storageManager: StorageManager, private val storageManager: StorageManager,
private val containingDeclaration: PackageFragmentDescriptor, private val containingDeclaration: PackageFragmentDescriptor,
val functionKind: FunctionalTypeKind, val functionKind: FunctionTypeKind,
val arity: Int val arity: Int
) : AbstractClassDescriptor(storageManager, functionKind.numberedClassName(arity)) { ) : AbstractClassDescriptor(storageManager, functionKind.numberedClassName(arity)) {
private val typeConstructor = FunctionTypeConstructor() private val typeConstructor = FunctionTypeConstructor()
@@ -96,14 +96,14 @@ class FunctionClassDescriptor(
override fun computeSupertypes(): Collection<KotlinType> { override fun computeSupertypes(): Collection<KotlinType> {
// For K{Suspend}Function{n}, add corresponding numbered {Suspend}Function{n} class, e.g. {Suspend}Function2 for K{Suspend}Function2 // For K{Suspend}Function{n}, add corresponding numbered {Suspend}Function{n} class, e.g. {Suspend}Function2 for K{Suspend}Function2
val supertypes = when (functionKind) { val supertypes = when (functionKind) {
FunctionalTypeKind.Function -> // Function$N <: Function FunctionTypeKind.Function -> // Function$N <: Function
listOf(functionClassId) listOf(functionClassId)
FunctionalTypeKind.KFunction -> // KFunction$N <: KFunction FunctionTypeKind.KFunction -> // KFunction$N <: KFunction
listOf(kFunctionClassId, ClassId(BUILT_INS_PACKAGE_FQ_NAME, FunctionalTypeKind.Function.numberedClassName(arity))) listOf(kFunctionClassId, ClassId(BUILT_INS_PACKAGE_FQ_NAME, FunctionTypeKind.Function.numberedClassName(arity)))
FunctionalTypeKind.SuspendFunction -> // SuspendFunction$N<...> <: Function FunctionTypeKind.SuspendFunction -> // SuspendFunction$N<...> <: Function
listOf(functionClassId) listOf(functionClassId)
FunctionalTypeKind.KSuspendFunction -> // KSuspendFunction$N<...> <: KFunction FunctionTypeKind.KSuspendFunction -> // KSuspendFunction$N<...> <: KFunction
listOf(kFunctionClassId, ClassId(COROUTINES_PACKAGE_FQ_NAME, FunctionalTypeKind.SuspendFunction.numberedClassName(arity))) listOf(kFunctionClassId, ClassId(COROUTINES_PACKAGE_FQ_NAME, FunctionTypeKind.SuspendFunction.numberedClassName(arity)))
else -> shouldNotBeCalled() else -> shouldNotBeCalled()
} }
@@ -26,8 +26,8 @@ class FunctionClassScope(
) : GivenFunctionsMemberScope(storageManager, containingClass) { ) : GivenFunctionsMemberScope(storageManager, containingClass) {
override fun computeDeclaredFunctions(): List<FunctionDescriptor> = override fun computeDeclaredFunctions(): List<FunctionDescriptor> =
when ((containingClass as FunctionClassDescriptor).functionKind) { when ((containingClass as FunctionClassDescriptor).functionKind) {
FunctionalTypeKind.Function -> listOf(FunctionInvokeDescriptor.create(containingClass, isSuspend = false)) FunctionTypeKind.Function -> listOf(FunctionInvokeDescriptor.create(containingClass, isSuspend = false))
FunctionalTypeKind.SuspendFunction -> listOf(FunctionInvokeDescriptor.create(containingClass, isSuspend = true)) FunctionTypeKind.SuspendFunction -> listOf(FunctionInvokeDescriptor.create(containingClass, isSuspend = true))
else -> emptyList() else -> emptyList()
} }
} }
@@ -7,7 +7,7 @@ package org.jetbrains.kotlin.types.checker
import org.jetbrains.kotlin.builtins.* import org.jetbrains.kotlin.builtins.*
import org.jetbrains.kotlin.builtins.StandardNames.FqNames import org.jetbrains.kotlin.builtins.StandardNames.FqNames
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
import org.jetbrains.kotlin.descriptors.annotations.Annotations import org.jetbrains.kotlin.descriptors.annotations.Annotations
@@ -411,7 +411,7 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy
return KotlinBuiltIns.isUnit(this) return KotlinBuiltIns.isUnit(this)
} }
override fun KotlinTypeMarker.isBuiltinFunctionalTypeOrSubtype(): Boolean { override fun KotlinTypeMarker.isBuiltinFunctionTypeOrSubtype(): Boolean {
require(this is UnwrappedType, this::errorMessage) require(this is UnwrappedType, this::errorMessage)
return isBuiltinFunctionalTypeOrSubtype return isBuiltinFunctionalTypeOrSubtype
} }
@@ -855,34 +855,34 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy
return this.isBuiltinExtensionFunctionalType return this.isBuiltinExtensionFunctionalType
} }
override fun KotlinTypeMarker.extractArgumentsForFunctionalTypeOrSubtype(): List<KotlinTypeMarker> { override fun KotlinTypeMarker.extractArgumentsForFunctionTypeOrSubtype(): List<KotlinTypeMarker> {
require(this is KotlinType, this::errorMessage) require(this is KotlinType, this::errorMessage)
return this.getPureArgumentsForFunctionalTypeOrSubtype() return this.getPureArgumentsForFunctionalTypeOrSubtype()
} }
override fun KotlinTypeMarker.getFunctionalTypeFromSupertypes(): KotlinTypeMarker { override fun KotlinTypeMarker.getFunctionTypeFromSupertypes(): KotlinTypeMarker {
require(this is KotlinType) require(this is KotlinType)
return this.extractFunctionalTypeFromSupertypes() return this.extractFunctionalTypeFromSupertypes()
} }
override fun KotlinTypeMarker.functionalTypeKind(): FunctionalTypeKind? { override fun KotlinTypeMarker.functionTypeKind(): FunctionTypeKind? {
require(this is KotlinType) require(this is KotlinType)
return this.functionalTypeKind return this.functionTypeKind
} }
override fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker { override fun getNonReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker {
return getFunctionDescriptor( return getFunctionDescriptor(
builtIns, builtIns,
parametersNumber, parametersNumber,
isSuspendFunction = kind.nonReflectKind() == FunctionalTypeKind.SuspendFunction isSuspendFunction = kind.nonReflectKind() == FunctionTypeKind.SuspendFunction
).typeConstructor ).typeConstructor
} }
override fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionalTypeKind): TypeConstructorMarker { override fun getReflectFunctionTypeConstructor(parametersNumber: Int, kind: FunctionTypeKind): TypeConstructorMarker {
return getKFunctionDescriptor( return getKFunctionDescriptor(
builtIns, builtIns,
parametersNumber, parametersNumber,
isSuspendFunction = kind.reflectKind() == FunctionalTypeKind.KSuspendFunction isSuspendFunction = kind.reflectKind() == FunctionTypeKind.KSuspendFunction
).typeConstructor ).typeConstructor
} }
@@ -23,7 +23,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.builtins.KotlinBuiltIns; import org.jetbrains.kotlin.builtins.KotlinBuiltIns;
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor; import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor;
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind; import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind;
import org.jetbrains.kotlin.config.LanguageVersion; import org.jetbrains.kotlin.config.LanguageVersion;
import org.jetbrains.kotlin.descriptors.*; import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor; import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor;
@@ -338,7 +338,7 @@ public final class ExpressionVisitor extends TranslatorVisitor<JsNode> {
default: { default: {
if (descriptor instanceof FunctionClassDescriptor) { if (descriptor instanceof FunctionClassDescriptor) {
FunctionClassDescriptor functionClassDescriptor = (FunctionClassDescriptor) descriptor; FunctionClassDescriptor functionClassDescriptor = (FunctionClassDescriptor) descriptor;
if (functionClassDescriptor.getFunctionKind() == FunctionalTypeKind.Function.INSTANCE) { if (functionClassDescriptor.getFunctionKind() == FunctionTypeKind.Function.INSTANCE) {
ClassDescriptor primitivesObject = findPrimitiveClassesObject(context); ClassDescriptor primitivesObject = findPrimitiveClassesObject(context);
assert primitivesObject != null; assert primitivesObject != null;
FunctionDescriptor function = DescriptorUtils.getFunctionByName( FunctionDescriptor function = DescriptorUtils.getFunctionByName(
@@ -7,7 +7,7 @@ package org.jetbrains.kotlin.js.translate.reference
import org.jetbrains.kotlin.builtins.PrimitiveType import org.jetbrains.kotlin.builtins.PrimitiveType
import org.jetbrains.kotlin.builtins.functions.FunctionInvokeDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionInvokeDescriptor
import org.jetbrains.kotlin.builtins.getFunctionalClassKind import org.jetbrains.kotlin.builtins.getFunctionTypeKind
import org.jetbrains.kotlin.config.LanguageFeature import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.FunctionDescriptor import org.jetbrains.kotlin.descriptors.FunctionDescriptor
@@ -185,7 +185,7 @@ class CallArgumentTranslator private constructor(
val parenthisedArgumentExpression = arg.getArgumentExpression() val parenthisedArgumentExpression = arg.getArgumentExpression()
val param = argsToParameters[arg]!!.original val param = argsToParameters[arg]!!.original
val isLambda = resolvedCall.resultingDescriptor.let { it.getFunctionalClassKind() != null || it is FunctionInvokeDescriptor } val isLambda = resolvedCall.resultingDescriptor.let { it.getFunctionTypeKind() != null || it is FunctionInvokeDescriptor }
val parameterType = if (!isLambda) param.varargElementType ?: param.type else context.currentModule.builtIns.anyType val parameterType = if (!isLambda) param.varargElementType ?: param.type else context.currentModule.builtIns.anyType
var argJs = Translation.translateAsExpression(parenthisedArgumentExpression!!, argumentContext) var argJs = Translation.translateAsExpression(parenthisedArgumentExpression!!, argumentContext)
@@ -40,7 +40,6 @@ import org.jetbrains.kotlin.resolve.BindingContextUtils;
import org.jetbrains.kotlin.resolve.DescriptorUtils; import org.jetbrains.kotlin.resolve.DescriptorUtils;
import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt; import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt;
import org.jetbrains.kotlin.resolve.inline.InlineUtil; import org.jetbrains.kotlin.resolve.inline.InlineUtil;
import org.jetbrains.kotlin.resolve.source.KotlinSourceElementKt;
import org.jetbrains.kotlin.resolve.source.PsiSourceElementKt; import org.jetbrains.kotlin.resolve.source.PsiSourceElementKt;
import org.jetbrains.kotlin.types.DynamicTypesKt; import org.jetbrains.kotlin.types.DynamicTypesKt;
import org.jetbrains.kotlin.types.KotlinType; import org.jetbrains.kotlin.types.KotlinType;
@@ -434,7 +433,7 @@ public final class TranslationUtils {
public static KotlinType getReturnTypeForCoercion(@NotNull CallableDescriptor descriptor, boolean forcePrivate) { public static KotlinType getReturnTypeForCoercion(@NotNull CallableDescriptor descriptor, boolean forcePrivate) {
descriptor = descriptor.getOriginal(); descriptor = descriptor.getOriginal();
if (FunctionTypesKt.getFunctionalClassKind(descriptor) != null || descriptor instanceof AnonymousFunctionDescriptor) { if (FunctionTypesKt.getFunctionTypeKind(descriptor) != null || descriptor instanceof AnonymousFunctionDescriptor) {
return getAnyTypeFromSameModule(descriptor); return getAnyTypeFromSameModule(descriptor);
} }
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.backend.konan
import org.jetbrains.kotlin.backend.konan.descriptors.findPackage import org.jetbrains.kotlin.backend.konan.descriptors.findPackage
import org.jetbrains.kotlin.builtins.FunctionInterfacePackageFragment import org.jetbrains.kotlin.builtins.FunctionInterfacePackageFragment
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.incremental.components.NoLookupLocation import org.jetbrains.kotlin.incremental.components.NoLookupLocation
import org.jetbrains.kotlin.ir.declarations.* import org.jetbrains.kotlin.ir.declarations.*
@@ -168,7 +168,7 @@ internal class BuiltInFictitiousFunctionIrClassFactory(
val builtFunctionNClasses get() = builtClassesMap.entries.mapNotNull { (descriptor, irClass) -> val builtFunctionNClasses get() = builtClassesMap.entries.mapNotNull { (descriptor, irClass) ->
with(descriptor) { with(descriptor) {
if (functionKind == FunctionalTypeKind.Function) if (functionKind == FunctionTypeKind.Function)
FunctionalInterface(irClass, descriptor, arity) FunctionalInterface(irClass, descriptor, arity)
else null else null
} }
@@ -6,8 +6,8 @@
package org.jetbrains.kotlin.backend.konan.objcexport package org.jetbrains.kotlin.backend.konan.objcexport
import org.jetbrains.kotlin.builtins.StandardNames import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.builtins.getFunctionalClassKind import org.jetbrains.kotlin.builtins.getFunctionTypeKind
import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.FqName
@@ -16,7 +16,7 @@ import org.jetbrains.kotlin.types.KotlinType
import org.jetbrains.kotlin.types.TypeUtils import org.jetbrains.kotlin.types.TypeUtils
internal fun ClassDescriptor.isMappedFunctionClass() = internal fun ClassDescriptor.isMappedFunctionClass() =
this.getFunctionalClassKind() == FunctionalTypeKind.Function && this.getFunctionTypeKind() == FunctionTypeKind.Function &&
// Type parameters include return type. // Type parameters include return type.
declaredTypeParameters.size - 1 < CustomTypeMappers.functionTypeMappersArityLimit declaredTypeParameters.size - 1 < CustomTypeMappers.functionTypeMappersArityLimit
@@ -12,7 +12,7 @@ import org.jetbrains.kotlin.fir.extensions.FirExtensionRegistrar
import org.jetbrains.kotlin.fir.extensions.FirExtensionRegistrarAdapter import org.jetbrains.kotlin.fir.extensions.FirExtensionRegistrarAdapter
import org.jetbrains.kotlin.fir.plugin.generators.* import org.jetbrains.kotlin.fir.plugin.generators.*
import org.jetbrains.kotlin.fir.plugin.types.FirNumberSignAttributeExtension import org.jetbrains.kotlin.fir.plugin.types.FirNumberSignAttributeExtension
import org.jetbrains.kotlin.fir.plugin.types.ComposableLikeFunctionalTypeKindExtension import org.jetbrains.kotlin.fir.plugin.types.ComposableLikeFunctionTypeKindExtension
import org.jetbrains.kotlin.ir.plugin.GeneratedDeclarationsIrBodyFiller import org.jetbrains.kotlin.ir.plugin.GeneratedDeclarationsIrBodyFiller
class FirPluginPrototypeExtensionRegistrar : FirExtensionRegistrar() { class FirPluginPrototypeExtensionRegistrar : FirExtensionRegistrar() {
@@ -24,7 +24,7 @@ class FirPluginPrototypeExtensionRegistrar : FirExtensionRegistrar() {
+::PluginAdditionalCheckers +::PluginAdditionalCheckers
+::FirNumberSignAttributeExtension +::FirNumberSignAttributeExtension
+::AlgebraReceiverInjector +::AlgebraReceiverInjector
+::ComposableLikeFunctionalTypeKindExtension +::ComposableLikeFunctionTypeKindExtension
// Declaration generators // Declaration generators
+::TopLevelDeclarationsGenerator +::TopLevelDeclarationsGenerator
@@ -5,16 +5,16 @@
package org.jetbrains.kotlin.fir.plugin.types package org.jetbrains.kotlin.fir.plugin.types
import org.jetbrains.kotlin.builtins.functions.FunctionalTypeKind import org.jetbrains.kotlin.builtins.functions.FunctionTypeKind
import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.extensions.FirFunctionalTypeKindExtension import org.jetbrains.kotlin.fir.extensions.FirFunctionTypeKindExtension
import org.jetbrains.kotlin.fir.plugin.fqn import org.jetbrains.kotlin.fir.plugin.fqn
import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.Name
class ComposableLikeFunctionalTypeKindExtension(session: FirSession) : FirFunctionalTypeKindExtension(session) { class ComposableLikeFunctionTypeKindExtension(session: FirSession) : FirFunctionTypeKindExtension(session) {
override fun FunctionalTypeKindRegistrar.registerKinds() { override fun FunctionTypeKindRegistrar.registerKinds() {
registerKind(ComposableFunction, KComposableFunction) registerKind(ComposableFunction, KComposableFunction)
} }
} }
@@ -22,7 +22,7 @@ class ComposableLikeFunctionalTypeKindExtension(session: FirSession) : FirFuncti
private val COMPOSABLE_PACKAGE_FQN = FqName.topLevel(Name.identifier("some")) private val COMPOSABLE_PACKAGE_FQN = FqName.topLevel(Name.identifier("some"))
private val MY_COMPOSABLE_ANNOTATION_CLASS_ID = ClassId.topLevel("MyComposable".fqn()) private val MY_COMPOSABLE_ANNOTATION_CLASS_ID = ClassId.topLevel("MyComposable".fqn())
object ComposableFunction : FunctionalTypeKind( object ComposableFunction : FunctionTypeKind(
COMPOSABLE_PACKAGE_FQN, COMPOSABLE_PACKAGE_FQN,
"MyComposableFunction", "MyComposableFunction",
MY_COMPOSABLE_ANNOTATION_CLASS_ID, MY_COMPOSABLE_ANNOTATION_CLASS_ID,
@@ -31,14 +31,14 @@ object ComposableFunction : FunctionalTypeKind(
override val prefixForTypeRender: String override val prefixForTypeRender: String
get() = "@MyComposable" get() = "@MyComposable"
override fun reflectKind(): FunctionalTypeKind = KComposableFunction override fun reflectKind(): FunctionTypeKind = KComposableFunction
} }
object KComposableFunction : FunctionalTypeKind( object KComposableFunction : FunctionTypeKind(
COMPOSABLE_PACKAGE_FQN, COMPOSABLE_PACKAGE_FQN,
"KMyComposableFunction", "KMyComposableFunction",
MY_COMPOSABLE_ANNOTATION_CLASS_ID, MY_COMPOSABLE_ANNOTATION_CLASS_ID,
isReflectType = true isReflectType = true
) { ) {
override fun nonReflectKind(): FunctionalTypeKind = ComposableFunction override fun nonReflectKind(): FunctionTypeKind = ComposableFunction
} }
@@ -1,3 +1,3 @@
FILE: ambigousKinds.kt FILE: ambigousKinds.kt
public final fun incorrect(block: <ERROR TYPE REF: There are multiple functional kinds for functional type ref>): R|kotlin/Unit| { public final fun incorrect(block: <ERROR TYPE REF: There are multiple function kinds for functional type ref>): R|kotlin/Unit| {
} }
@@ -1,3 +1,3 @@
import org.jetbrains.kotlin.fir.plugin.MyComposable import org.jetbrains.kotlin.fir.plugin.MyComposable
fun incorrect(block: <!AMBIGUOUS_FUNCTIONAL_TYPE_KIND!>@MyComposable suspend () -> Unit<!>) {} fun incorrect(block: <!AMBIGUOUS_FUNCTION_TYPE_KIND!>@MyComposable suspend () -> Unit<!>) {}
@@ -114,7 +114,7 @@ object FirParcelizePropertyChecker : FirPropertyChecker() {
type.anySuperTypeConstructor { type.anySuperTypeConstructor {
it is ConeKotlinType && it is ConeKotlinType &&
(it.classId?.asFqNameString() in BuiltinParcelableTypes.PARCELABLE_SUPERTYPE_FQNAMES || (it.classId?.asFqNameString() in BuiltinParcelableTypes.PARCELABLE_SUPERTYPE_FQNAMES ||
it.isSomeFunctionalType(session)) it.isSomeFunctionType(session))
} }
} }
} }

Some files were not shown because too many files have changed in this diff Show More