[FIR] Use lower bound of supertype in findClassRepresentation for intersection types
This commit is contained in:
committed by
Space Team
parent
c3f3a4192c
commit
84f41b7d68
+6
@@ -19047,6 +19047,12 @@ public class FirLightTreeBlackBoxCodegenTestGenerated extends AbstractFirLightTr
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
+6
@@ -19047,6 +19047,12 @@ public class FirLightTreeBlackBoxCodegenWithIrFakeOverrideGeneratorTestGenerated
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
+6
@@ -19047,6 +19047,12 @@ public class FirPsiBlackBoxCodegenTestGenerated extends AbstractFirPsiBlackBoxCo
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
@@ -22,12 +22,10 @@ import org.jetbrains.kotlin.fir.symbols.impl.*
|
|||||||
import org.jetbrains.kotlin.fir.types.*
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
import org.jetbrains.kotlin.fir.types.builder.buildResolvedTypeRef
|
import org.jetbrains.kotlin.fir.types.builder.buildResolvedTypeRef
|
||||||
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
|
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
|
||||||
import org.jetbrains.kotlin.fir.utils.exceptions.withFirLookupTagEntry
|
|
||||||
import org.jetbrains.kotlin.name.SpecialNames
|
import org.jetbrains.kotlin.name.SpecialNames
|
||||||
import org.jetbrains.kotlin.name.StandardClassIds
|
import org.jetbrains.kotlin.name.StandardClassIds
|
||||||
import org.jetbrains.kotlin.types.ConstantValueKind
|
import org.jetbrains.kotlin.types.ConstantValueKind
|
||||||
import org.jetbrains.kotlin.util.WeakPair
|
import org.jetbrains.kotlin.util.WeakPair
|
||||||
import org.jetbrains.kotlin.utils.exceptions.errorWithAttachment
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Main operation on the [ConeClassifierLookupTag]
|
* Main operation on the [ConeClassifierLookupTag]
|
||||||
@@ -150,4 +148,10 @@ private fun ConeTypeParameterLookupTag.findClassRepresentationThatIsSubtypeOf(
|
|||||||
private fun Collection<ConeKotlinType>.findClassRepresentationThatIsSubtypeOf(
|
private fun Collection<ConeKotlinType>.findClassRepresentationThatIsSubtypeOf(
|
||||||
supertype: ConeKotlinType,
|
supertype: ConeKotlinType,
|
||||||
session: FirSession
|
session: FirSession
|
||||||
): ConeClassLikeLookupTag? = firstOrNull { it.isSubtypeOf(supertype, session) }?.findClassRepresentation(supertype, session)
|
): ConeClassLikeLookupTag? {
|
||||||
|
val supertypeLowerBound = supertype.lowerBoundIfFlexible()
|
||||||
|
val compatibleComponent = this.firstOrNull {
|
||||||
|
it.isSubtypeOf(supertypeLowerBound, session)
|
||||||
|
} ?: return null
|
||||||
|
return compatibleComponent.findClassRepresentation(supertypeLowerBound, session)
|
||||||
|
}
|
||||||
|
|||||||
+43
@@ -0,0 +1,43 @@
|
|||||||
|
// TARGET_BACKEND: JVM
|
||||||
|
// WITH_STDLIB
|
||||||
|
// MODULE: lib
|
||||||
|
// FILE: lib.kt
|
||||||
|
interface A<T1> {
|
||||||
|
fun foo()
|
||||||
|
}
|
||||||
|
|
||||||
|
interface B<T2> : A<T2>
|
||||||
|
|
||||||
|
interface C : B<String>
|
||||||
|
|
||||||
|
// FILE: FirstHolder.java
|
||||||
|
public interface FirstHolder<K1> {
|
||||||
|
K1 getValue();
|
||||||
|
}
|
||||||
|
// FILE: SecondHolder.java
|
||||||
|
public interface SecondHolder<K2 extends A> { // <--- A is raw
|
||||||
|
K2 getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
// FILE: HolderImpl.java
|
||||||
|
public interface HolderImpl extends FirstHolder<C> {}
|
||||||
|
|
||||||
|
// MODULE: main(lib)
|
||||||
|
// FILE: main.kt
|
||||||
|
fun test(s: Any) {
|
||||||
|
require(s is SecondHolder<*> && s is HolderImpl)
|
||||||
|
/*
|
||||||
|
* - Type of s.getValue() is ft<it(A<kotlin/Any?> & C), C?>
|
||||||
|
* - foo` is found in scope of it(A<kotlin/Any?> & C)
|
||||||
|
* - there are two candidates (A<Any>.foo and C.foo)
|
||||||
|
* - they have same signatures, so we chose first of them (`A<Any>.foo` in this case)
|
||||||
|
* - fir2ir needs to find correct f/o lookup tag for this call
|
||||||
|
* - `findClassRepresentation` for `ft<it(A<kotlin/Any?> & C), C?>` in this case should return `null`,
|
||||||
|
* since there is no actual representation for this type
|
||||||
|
* - if it won't then fir2ir may decide to generate f/o with `C` lookup tag, based on `A.foo` function,
|
||||||
|
* which is incorrect (there is another f/o in the hierarchy between `C` and `A`
|
||||||
|
*/
|
||||||
|
s.getValue().foo()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun box(): String = "OK"
|
||||||
+6
@@ -18135,6 +18135,12 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
|
|||||||
runTest("compiler/testData/codegen/box/fir/incorrectBytecodeWithEnhancedNullability.kt");
|
runTest("compiler/testData/codegen/box/fir/incorrectBytecodeWithEnhancedNullability.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
+6
@@ -19047,6 +19047,12 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
+6
@@ -19047,6 +19047,12 @@ public class IrBlackBoxCodegenWithIrInlinerTestGenerated extends AbstractIrBlack
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
|
|||||||
+5
@@ -15861,6 +15861,11 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
|
|||||||
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
runTest("compiler/testData/codegen/box/fir/internalPotentialOverride.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("intersectionWithCapturedTypeWithRawUpperBound.kt")
|
||||||
|
public void testIntersectionWithCapturedTypeWithRawUpperBound() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/fir/intersectionWithCapturedTypeWithRawUpperBound.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("IrBuiltIns.kt")
|
@TestMetadata("IrBuiltIns.kt")
|
||||||
public void testIrBuiltIns() throws Exception {
|
public void testIrBuiltIns() throws Exception {
|
||||||
runTest("compiler/testData/codegen/box/fir/IrBuiltIns.kt");
|
runTest("compiler/testData/codegen/box/fir/IrBuiltIns.kt");
|
||||||
|
|||||||
Reference in New Issue
Block a user