From 48fdeeb42d004ef3a4d9b9012634ee5955906aa7 Mon Sep 17 00:00:00 2001 From: Nikita Bobko Date: Fri, 17 Nov 2023 18:34:55 +0100 Subject: [PATCH] [FIR, IR] Cleanups around allRecursivelyOverriddenDeclarationsIncludingSelf - Pass containingClass (helps to avoid calculations of the containingClass in allRecursivelyOverriddenDeclarationsIncludingSelf implementation) - Reuse allRecursivelyOverriddenDeclarationsIncludingSelf by DefaultArgumentsInExpectActualizedByFakeOverride & ActualFunctionWithDefaultParameters Review: https://jetbrains.team/p/kt/reviews/13244 --- .../mpp/FirExpectActualMatchingContextImpl.kt | 9 ++++----- .../actualizer/IrExpectActualMatchingContext.kt | 6 +++--- .../calls/mpp/AbstractExpectActualChecker.kt | 13 +++++++------ .../calls/mpp/ExpectActualMatchingContext.kt | 2 +- 4 files changed, 15 insertions(+), 15 deletions(-) diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/mpp/FirExpectActualMatchingContextImpl.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/mpp/FirExpectActualMatchingContextImpl.kt index 52722ffba9d..8c11eeaf989 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/mpp/FirExpectActualMatchingContextImpl.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/mpp/FirExpectActualMatchingContextImpl.kt @@ -259,14 +259,13 @@ class FirExpectActualMatchingContextImpl private constructor( override val CallableSymbolMarker.typeParameters: List get() = asSymbol().typeParameterSymbols - override fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(): Sequence { + override fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(containingClass: RegularClassSymbolMarker?): List { return when (val symbol = asSymbol()) { - is FirConstructorSymbol, is FirFunctionWithoutNameSymbol -> sequenceOf(this) + is FirConstructorSymbol, is FirFunctionWithoutNameSymbol -> listOf(symbol) is FirNamedFunctionSymbol -> { + if (containingClass == null) return listOf(symbol) val session = symbol.moduleData.session - val containingClass = symbol.containingClassLookupTag()?.toFirRegularClassSymbol(session) - ?: return sequenceOf(symbol) - (sequenceOf(symbol) + symbol.overriddenFunctions(containingClass, session, actualScopeSession).asSequence()) + (listOf(symbol) + symbol.overriddenFunctions(containingClass.asSymbol(), session, actualScopeSession).asSequence()) // Tests work even if you don't filter out fake-overrides. Filtering fake-overrides is needed because // the returned descriptors are compared by `equals`. And `equals` for fake-overrides is weird. // I didn't manage to invent a test that would check this condition diff --git a/compiler/ir/ir.actualization/src/main/kotlin/org/jetbrains/kotlin/backend/common/actualizer/IrExpectActualMatchingContext.kt b/compiler/ir/ir.actualization/src/main/kotlin/org/jetbrains/kotlin/backend/common/actualizer/IrExpectActualMatchingContext.kt index ed6326d138e..8a71172e993 100644 --- a/compiler/ir/ir.actualization/src/main/kotlin/org/jetbrains/kotlin/backend/common/actualizer/IrExpectActualMatchingContext.kt +++ b/compiler/ir/ir.actualization/src/main/kotlin/org/jetbrains/kotlin/backend/common/actualizer/IrExpectActualMatchingContext.kt @@ -298,10 +298,10 @@ internal abstract class IrExpectActualMatchingContext( onEnumEntry = { emptyList() } ) - override fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(): Sequence = + override fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(containingClass: RegularClassSymbolMarker?): List = when (val node = asIr()) { - is IrConstructor -> sequenceOf(this) - is IrSimpleFunction -> (sequenceOf(this) + node.overriddenSymbols) + is IrConstructor -> listOf(this) + is IrSimpleFunction -> (listOf(this) + node.overriddenSymbols) // Tests work even if you don't filter out fake-overrides. Filtering fake-overrides is needed because // the returned descriptors are compared by `equals`. And `equals` for fake-overrides is weird. // I didn't manage to invent a test that would check this condition diff --git a/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/AbstractExpectActualChecker.kt b/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/AbstractExpectActualChecker.kt index 78fc1abef5d..0e7adabd6e6 100644 --- a/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/AbstractExpectActualChecker.kt +++ b/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/AbstractExpectActualChecker.kt @@ -373,13 +373,16 @@ object AbstractExpectActualChecker { // "parameters" checks are required only for functions, because only functions can have parameters actualDeclaration is FunctionSymbolMarker && expectDeclaration is FunctionSymbolMarker ) { + val expectOverriddenDeclarations = + expectDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf(expectContainingClass).toSet() + val actualOverriddenDeclarations = + actualDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf(actualContainingClass).toSet() if (languageVersionSettings.supportsFeature(LanguageFeature.ProhibitDefaultArgumentsInExpectActualizedByFakeOverride) && (actualDeclaration.isFakeOverride(actualContainingClass) || actualDeclaration.isDelegatedMember) && // If default params came from common supertypes of actual class and expect class then it's a valid code. // Here we filter out such default params. - (expectDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf() - - actualDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf().toSet()) - .flatMap { it.valueParameters }.any { it.hasDefaultValueNonRecursive } + (expectOverriddenDeclarations - actualOverriddenDeclarations).flatMap { it.valueParameters } + .any { it.hasDefaultValueNonRecursive } ) { return ExpectActualCheckingCompatibility.DefaultArgumentsInExpectActualizedByFakeOverride } @@ -389,9 +392,7 @@ object AbstractExpectActualChecker { if (!actualDeclaration.isAnnotationConstructor() && // If default params came from common supertypes of actual class and expect class then it's a valid code. // Here we filter out such default params. - (actualDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf() - - expectDeclaration.allRecursivelyOverriddenDeclarationsIncludingSelf().toSet()) - .flatMap { it.valueParameters }.any { it.hasDefaultValue } + (actualOverriddenDeclarations - expectOverriddenDeclarations).flatMap { it.valueParameters }.any { it.hasDefaultValue } ) { return ExpectActualCheckingCompatibility.ActualFunctionWithDefaultParameters } diff --git a/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/ExpectActualMatchingContext.kt b/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/ExpectActualMatchingContext.kt index 44dc5e06754..b953916bbbe 100644 --- a/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/ExpectActualMatchingContext.kt +++ b/compiler/resolution.common/src/org/jetbrains/kotlin/resolve/calls/mpp/ExpectActualMatchingContext.kt @@ -125,7 +125,7 @@ interface ExpectActualMatchingContext : TypeSystemC /** * Returns all symbols that are overridden by [this] symbol, including self */ - fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(): Sequence + fun FunctionSymbolMarker.allRecursivelyOverriddenDeclarationsIncludingSelf(containingClass: RegularClassSymbolMarker?): List val CallableSymbolMarker.valueParameters: List get() = (this as? FunctionSymbolMarker)?.valueParameters ?: emptyList()