[FIR] Correct resolving of sam with suspend function from another module, ^KT-51007 Fixed

Ignore fir ide test probably because of KT-50732
This commit is contained in:
Ivan Kochurkin
2022-02-01 23:45:53 +03:00
committed by teamcity
parent 17c64cf955
commit f32c355190
8 changed files with 82 additions and 16 deletions
@@ -19638,6 +19638,12 @@ public class DiagnosisCompilerTestFE10TestdataTestGenerated extends AbstractDiag
runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt"); runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt");
} }
@Test
@TestMetadata("samWithSuspendFunctionFromAnotherModule.kt")
public void testSamWithSuspendFunctionFromAnotherModule() throws Exception {
runTest("compiler/testData/diagnostics/tests/multimodule/samWithSuspendFunctionFromAnotherModule.kt");
}
@Test @Test
@TestMetadata("varargConflict.kt") @TestMetadata("varargConflict.kt")
public void testVarargConflict() throws Exception { public void testVarargConflict() throws Exception {
@@ -19638,6 +19638,12 @@ public class FirOldFrontendDiagnosticsTestGenerated extends AbstractFirDiagnosti
runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt"); runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt");
} }
@Test
@TestMetadata("samWithSuspendFunctionFromAnotherModule.kt")
public void testSamWithSuspendFunctionFromAnotherModule() throws Exception {
runTest("compiler/testData/diagnostics/tests/multimodule/samWithSuspendFunctionFromAnotherModule.kt");
}
@Test @Test
@TestMetadata("varargConflict.kt") @TestMetadata("varargConflict.kt")
public void testVarargConflict() throws Exception { public void testVarargConflict() throws Exception {
@@ -19638,6 +19638,12 @@ public class FirOldFrontendDiagnosticsWithLightTreeTestGenerated extends Abstrac
runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt"); runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt");
} }
@Test
@TestMetadata("samWithSuspendFunctionFromAnotherModule.kt")
public void testSamWithSuspendFunctionFromAnotherModule() throws Exception {
runTest("compiler/testData/diagnostics/tests/multimodule/samWithSuspendFunctionFromAnotherModule.kt");
}
@Test @Test
@TestMetadata("varargConflict.kt") @TestMetadata("varargConflict.kt")
public void testVarargConflict() throws Exception { public void testVarargConflict() throws Exception {
@@ -61,7 +61,6 @@ fun Candidate.preprocessLambdaArgument(
) ?: extractLambdaInfo(expectedType, anonymousFunction, csBuilder, context.session, this) ) ?: extractLambdaInfo(expectedType, anonymousFunction, csBuilder, context.session, this)
if (expectedType != null) { if (expectedType != null) {
// TODO: add SAM conversion processing
val parameters = resolvedArgument.parameters val parameters = resolvedArgument.parameters
val lambdaType = createFunctionalType( val lambdaType = createFunctionalType(
if (resolvedArgument.coerceFirstParameterToExtensionReceiver) parameters.drop(1) else parameters, if (resolvedArgument.coerceFirstParameterToExtensionReceiver) parameters.drop(1) else parameters,
@@ -6,14 +6,13 @@
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.descriptors.ClassKind import org.jetbrains.kotlin.builtins.functions.FunctionClassKind
import org.jetbrains.kotlin.descriptors.Visibility import org.jetbrains.kotlin.descriptors.Visibility
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.*
import org.jetbrains.kotlin.fir.declarations.utils.isInline import org.jetbrains.kotlin.fir.declarations.utils.isInline
import org.jetbrains.kotlin.fir.declarations.utils.isLocal import org.jetbrains.kotlin.fir.declarations.utils.isLocal
import org.jetbrains.kotlin.fir.declarations.utils.isSuspend
import org.jetbrains.kotlin.fir.declarations.utils.visibility import org.jetbrains.kotlin.fir.declarations.utils.visibility
import org.jetbrains.kotlin.fir.diagnostics.ConeSimpleDiagnostic import org.jetbrains.kotlin.fir.diagnostics.ConeSimpleDiagnostic
import org.jetbrains.kotlin.fir.diagnostics.DiagnosticKind import org.jetbrains.kotlin.fir.diagnostics.DiagnosticKind
@@ -23,19 +22,17 @@ import org.jetbrains.kotlin.fir.references.FirNamedReference
import org.jetbrains.kotlin.fir.references.builder.buildErrorNamedReference import org.jetbrains.kotlin.fir.references.builder.buildErrorNamedReference
import org.jetbrains.kotlin.fir.references.builder.buildResolvedCallableReference import org.jetbrains.kotlin.fir.references.builder.buildResolvedCallableReference
import org.jetbrains.kotlin.fir.references.builder.buildResolvedNamedReference import org.jetbrains.kotlin.fir.references.builder.buildResolvedNamedReference
import org.jetbrains.kotlin.fir.resolve.*
import org.jetbrains.kotlin.fir.resolve.calls.Candidate import org.jetbrains.kotlin.fir.resolve.calls.Candidate
import org.jetbrains.kotlin.fir.resolve.calls.FirErrorReferenceWithCandidate import org.jetbrains.kotlin.fir.resolve.calls.FirErrorReferenceWithCandidate
import org.jetbrains.kotlin.fir.resolve.calls.FirNamedReferenceWithCandidate import org.jetbrains.kotlin.fir.resolve.calls.FirNamedReferenceWithCandidate
import org.jetbrains.kotlin.fir.resolve.constructFunctionalTypeRef
import org.jetbrains.kotlin.fir.resolve.createFunctionalType
import org.jetbrains.kotlin.fir.resolve.dfa.FirDataFlowAnalyzer import org.jetbrains.kotlin.fir.resolve.dfa.FirDataFlowAnalyzer
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeConstraintSystemHasContradiction import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeConstraintSystemHasContradiction
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeInapplicableCandidateError import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeInapplicableCandidateError
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConePropertyAsOperator import org.jetbrains.kotlin.fir.resolve.diagnostics.ConePropertyAsOperator
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeTypeParameterInQualifiedAccess import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeTypeParameterInQualifiedAccess
import org.jetbrains.kotlin.fir.resolve.inference.* import org.jetbrains.kotlin.fir.resolve.inference.ResolvedLambdaAtom
import org.jetbrains.kotlin.fir.resolve.propagateTypeFromQualifiedAccessAfterNullCheck import org.jetbrains.kotlin.fir.resolve.providers.symbolProvider
import org.jetbrains.kotlin.fir.resolve.providers.firProvider
import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor
import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.FirArrayOfCallTransformer import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.FirArrayOfCallTransformer
import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.remapArgumentsWithVararg import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.remapArgumentsWithVararg
@@ -79,6 +76,8 @@ class FirCallCompletionResultsWriterTransformer(
private val arrayOfCallTransformer = FirArrayOfCallTransformer() private val arrayOfCallTransformer = FirArrayOfCallTransformer()
private var enableArrayOfCallTransformation = false private var enableArrayOfCallTransformation = false
private val samResolver: FirSamResolver = FirSamResolverImpl(session, ScopeSession())
enum class Mode { enum class Mode {
Normal, DelegatedPropertyCompletion Normal, DelegatedPropertyCompletion
} }
@@ -584,14 +583,22 @@ class FirCallCompletionResultsWriterTransformer(
expectedArgumentType.isBuiltinFunctionalType(session) -> expectedArgumentType expectedArgumentType.isBuiltinFunctionalType(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 sam = val firRegularClass =
(session.firProvider.getFirClassifierByFqName(expectedArgumentType.lookupTag.classId) as? FirClass) session.symbolProvider.getClassLikeSymbolByClassId(expectedArgumentType.lookupTag.classId)?.fir as? FirRegularClass
?.takeIf { it.classKind == ClassKind.INTERFACE }
?.declarations?.singleOrNull() as? FirSimpleFunction firRegularClass?.let {
sam?.let { val functionType = samResolver.getFunctionTypeForPossibleSamType(firRegularClass.defaultType())
createFunctionalType( if (functionType != null) {
sam.valueParameters.map { it.returnTypeRef.coneType }, null, sam.returnTypeRef.coneType, sam.isSuspend createFunctionalType(
) functionType.typeArguments.dropLast(1).map { it as ConeKotlinType },
null,
functionType.typeArguments.last() as ConeKotlinType,
functionType.classId?.relativeClassName?.asString()
?.startsWith(FunctionClassKind.SuspendFunction.classNamePrefix) == true
)
} else {
null
}
} }
} }
else -> null else -> null
@@ -0,0 +1,20 @@
// FIR_IDENTICAL
// FIR_IDE_IGNORE
// TODO: KT-50732
// ISSUE: KT-51007
// MODULE: lib
fun interface A {
suspend fun foo()
}
// MODULE: main(lib)
suspend fun bar() {}
fun takeA(a: A?) {}
fun test() {
takeA {
bar()
}
}
@@ -0,0 +1,16 @@
// -- Module: <lib> --
package
public fun interface A {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public abstract suspend fun foo(): kotlin.Unit
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
// -- Module: <main> --
package
public suspend fun bar(): kotlin.Unit
public fun takeA(/*0*/ a: A?): kotlin.Unit
public fun test(): kotlin.Unit
@@ -19644,6 +19644,12 @@ public class DiagnosticTestGenerated extends AbstractDiagnosticTest {
runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt"); runTest("compiler/testData/diagnostics/tests/multimodule/redundantElseInWhen.kt");
} }
@Test
@TestMetadata("samWithSuspendFunctionFromAnotherModule.kt")
public void testSamWithSuspendFunctionFromAnotherModule() throws Exception {
runTest("compiler/testData/diagnostics/tests/multimodule/samWithSuspendFunctionFromAnotherModule.kt");
}
@Test @Test
@TestMetadata("varargConflict.kt") @TestMetadata("varargConflict.kt")
public void testVarargConflict() throws Exception { public void testVarargConflict() throws Exception {