WIP! Tue 3 Oct 17:51:28 CEST 2023
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 069ed79..e612899 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
@@ -5,6 +5,7 @@
package org.jetbrains.kotlin.resolve.calls.mpp
+import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.descriptors.Visibilities
@@ -29,9 +30,16 @@
actualClassLikeSymbol: ClassLikeSymbolMarker,
checkClassScopesCompatibility: Boolean,
context: ExpectActualMatchingContext<T>,
+ languageVersionSettings: LanguageVersionSettings,
): ExpectActualCompatibility<T> {
val result = with(context) {
- getClassifiersCompatibility(expectClassSymbol, actualClassLikeSymbol, parentSubstitutor = null, checkClassScopesCompatibility)
+ getClassifiersCompatibility(
+ expectClassSymbol,
+ actualClassLikeSymbol,
+ parentSubstitutor = null,
+ checkClassScopesCompatibility,
+ languageVersionSettings,
+ )
}
@Suppress("UNCHECKED_CAST")
return result as ExpectActualCompatibility<T>
@@ -44,9 +52,17 @@
expectContainingClass: RegularClassSymbolMarker?,
actualContainingClass: RegularClassSymbolMarker?,
context: ExpectActualMatchingContext<T>,
+ languageVersionSettings: LanguageVersionSettings
): ExpectActualCompatibility<T> {
val result = with(context) {
- getCallablesCompatibility(expectDeclaration, actualDeclaration, parentSubstitutor, expectContainingClass, actualContainingClass)
+ getCallablesCompatibility(
+ expectDeclaration,
+ actualDeclaration,
+ parentSubstitutor,
+ expectContainingClass,
+ actualContainingClass,
+ languageVersionSettings,
+ )
}
@Suppress("UNCHECKED_CAST")
return result as ExpectActualCompatibility<T>
@@ -56,6 +72,7 @@
expectDeclaration: DeclarationSymbolMarker,
actualDeclarations: List<DeclarationSymbolMarker>,
context: ExpectActualMatchingContext<T>,
+ languageVersionSettings: LanguageVersionSettings,
) {
with(context) {
matchSingleExpectAgainstPotentialActuals(
@@ -66,6 +83,7 @@
actualClassSymbol = null,
unfulfilled = null,
checkClassScopesCompatibility = true,
+ languageVersionSettings,
)
}
}
@@ -77,7 +95,14 @@
actualClassLikeSymbol: ClassLikeSymbolMarker,
parentSubstitutor: TypeSubstitutorMarker?,
checkClassScopes: Boolean,
- ): ExpectActualCompatibility<*> = getClassifiersIncompatibility(expectClassSymbol, actualClassLikeSymbol, parentSubstitutor, checkClassScopes)
+ languageVersionSettings: LanguageVersionSettings,
+ ): ExpectActualCompatibility<*> = getClassifiersIncompatibility(
+ expectClassSymbol,
+ actualClassLikeSymbol,
+ parentSubstitutor,
+ checkClassScopes,
+ languageVersionSettings,
+ )
?: ExpectActualCompatibility.Compatible
context(ExpectActualMatchingContext<*>)
@@ -87,6 +112,7 @@
actualClassLikeSymbol: ClassLikeSymbolMarker,
parentSubstitutor: TypeSubstitutorMarker?,
checkClassScopesCompatibility: Boolean,
+ languageVersionSettings: LanguageVersionSettings,
): ExpectActualCompatibility.Incompatible.ExpectActualCheckingIncompatible<*>? {
// Can't check FQ names here because nested expected class may be implemented via actual typealias's expansion with the other FQ name
require(expectClassSymbol.name == actualClassLikeSymbol.name) {
@@ -142,7 +168,7 @@
}
if (checkClassScopesCompatibility) {
- getClassScopesIncompatibility(expectClassSymbol, actualClass, substitutor)?.let { return it }
+ getClassScopesIncompatibility(expectClassSymbol, actualClass, substitutor, languageVersionSettings)?.let { return it }
}
return null
@@ -199,6 +225,7 @@
expectClassSymbol: RegularClassSymbolMarker,
actualClassSymbol: RegularClassSymbolMarker,
substitutor: TypeSubstitutorMarker,
+ languageVersionSettings: LanguageVersionSettings,
): Incompatible.ExpectActualCheckingIncompatible<*>? {
val unfulfilled = arrayListOf<Pair<DeclarationSymbolMarker, Map<Incompatible<*>, List<DeclarationSymbolMarker?>>>>()
@@ -220,6 +247,7 @@
actualClassSymbol,
unfulfilled,
checkClassScopesCompatibility = true,
+ languageVersionSettings,
)
}
@@ -246,6 +274,7 @@
actualClassSymbol: RegularClassSymbolMarker?,
unfulfilled: MutableList<Pair<DeclarationSymbolMarker, Map<Incompatible<*>, List<DeclarationSymbolMarker?>>>>?,
checkClassScopesCompatibility: Boolean,
+ languageVersionSettings: LanguageVersionSettings,
) {
val mapping = actualMembers.keysToMap { actualMember ->
when (expectMember) {
@@ -254,7 +283,8 @@
actualMember as CallableSymbolMarker,
substitutor,
expectClassSymbol,
- actualClassSymbol
+ actualClassSymbol,
+ languageVersionSettings
)
is RegularClassSymbolMarker -> {
@@ -264,6 +294,7 @@
actualMember as ClassLikeSymbolMarker,
parentSubstitutor,
checkClassScopesCompatibility,
+ languageVersionSettings,
)
}
else -> error("Unsupported declaration: $expectMember ($actualMembers)")
@@ -293,6 +324,7 @@
parentSubstitutor: TypeSubstitutorMarker?,
expectContainingClass: RegularClassSymbolMarker?,
actualContainingClass: RegularClassSymbolMarker?,
+ languageVersionSettings: LanguageVersionSettings,
): ExpectActualCompatibility<*> {
require(
(expectDeclaration is ConstructorSymbolMarker && actualDeclaration is ConstructorSymbolMarker) ||
@@ -321,7 +353,8 @@
actualDeclaration,
parentSubstitutor,
expectContainingClass,
- actualContainingClass
+ actualContainingClass,
+ languageVersionSettings,
)
?: ExpectActualCompatibility.Compatible
}
@@ -387,6 +420,7 @@
parentSubstitutor: TypeSubstitutorMarker?,
expectContainingClass: RegularClassSymbolMarker?,
actualContainingClass: RegularClassSymbolMarker?,
+ languageVersionSettings: LanguageVersionSettings,
): Incompatible.ExpectActualCheckingIncompatible<*>? {
val expectedTypeParameters = expectDeclaration.typeParameters
val actualTypeParameters = actualDeclaration.typeParameters
@@ -426,7 +460,7 @@
return Incompatible.Modality
}
- if (!areCompatibleCallableVisibilities(expectDeclaration.visibility, expectModality, actualDeclaration.visibility)) {
+ if (!areCompatibleCallableVisibilities(expectDeclaration.visibility, expectModality, actualDeclaration.visibility, languageVersionSettings)) {
return Incompatible.Visibility
}
@@ -467,7 +501,7 @@
getFunctionsIncompatibility(expectDeclaration, actualDeclaration)?.let { return it }
expectDeclaration is PropertySymbolMarker && actualDeclaration is PropertySymbolMarker ->
- getPropertiesIncompatibility(expectDeclaration, actualDeclaration)?.let { return it }
+ getPropertiesIncompatibility(expectDeclaration, actualDeclaration, languageVersionSettings)?.let { return it }
expectDeclaration is EnumEntrySymbolMarker && actualDeclaration is EnumEntrySymbolMarker -> {
// do nothing, entries are matched only by name
@@ -558,6 +592,7 @@
expectVisibility: Visibility,
expectModality: Modality?,
actualVisibility: Visibility,
+ languageVersionSettings: LanguageVersionSettings,
): Boolean {
val compare = Visibilities.compare(expectVisibility, actualVisibility)
return if (expectModality != Modality.FINAL) {
@@ -647,12 +682,13 @@
private fun getPropertiesIncompatibility(
expected: PropertySymbolMarker,
actual: PropertySymbolMarker,
+ languageVersionSettings: LanguageVersionSettings,
): Incompatible.ExpectActualCheckingIncompatible<*>? {
return when {
!equalBy(expected, actual) { p -> p.isVar } -> Incompatible.PropertyKind
!equalBy(expected, actual) { p -> p.isLateinit } -> Incompatible.PropertyLateinitModifier
expected.isConst && !actual.isConst -> Incompatible.PropertyConstModifier
- !arePropertySettersWithCompatibleVisibilities(expected, actual) -> Incompatible.PropertySetterVisibility
+ !arePropertySettersWithCompatibleVisibilities(expected, actual, languageVersionSettings) -> Incompatible.PropertySetterVisibility
else -> null
}
}
@@ -661,10 +697,16 @@
private fun arePropertySettersWithCompatibleVisibilities(
expected: PropertySymbolMarker,
actual: PropertySymbolMarker,
+ languageVersionSettings: LanguageVersionSettings
): Boolean {
val expectedSetter = expected.setter ?: return true
val actualSetter = actual.setter ?: return true
- return areCompatibleCallableVisibilities(expectedSetter.visibility, expectedSetter.modality, actualSetter.visibility)
+ return areCompatibleCallableVisibilities(
+ expectedSetter.visibility,
+ expectedSetter.modality,
+ actualSetter.visibility,
+ languageVersionSettings
+ )
}
// ---------------------------------------- Utils ----------------------------------------
diff --git a/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt b/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt
index c685677..cdc7465 100644
--- a/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt
+++ b/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt
@@ -7,6 +7,7 @@
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.resolve.calls.mpp.AbstractExpectActualChecker
+import org.jetbrains.kotlin.resolve.calls.mpp.AbstractExpectActualMatcher
import org.jetbrains.kotlin.resolve.descriptorUtil.classId
import org.jetbrains.kotlin.resolve.descriptorUtil.module
import org.jetbrains.kotlin.resolve.multiplatform.ExpectActualCompatibility.Compatible
@@ -29,7 +30,7 @@
// TODO: support non-source definitions (e.g. from Java)
actual.couldHaveASource
}.groupBy { actual ->
- AbstractExpectActualChecker.getCallablesCompatibility(
+ AbstractExpectActualMatcher.getCallablesCompatibility(
expected,
actual,
parentSubstitutor = null,
@@ -43,7 +44,7 @@
context.findClassifiersFromModule(expected.classId, platformModule, moduleVisibilityFilter).filter { actual ->
expected != actual && !actual.isExpect && actual.couldHaveASource
}.groupBy { actual ->
- AbstractExpectActualChecker.getClassifiersCompatibility(
+ AbstractExpectActualMatcher.getClassifiersCompatibility(
expected,
actual,
checkClassScopesCompatibility = true,