[NI] Add resolution applicability for resolved candidates with error
New resolution applicability is needed in cases when error is found, but candidate still should be selected. Currently there are two cases, when this behaviour is required: - unstable smartcast (choose candidate with non-nullable parameter) - unknown lambda parameter type (against non-functional expected type) KT-36264
This commit is contained in:
+2
-2
@@ -141,7 +141,7 @@ class SmartCastDiagnostic(
|
||||
class UnstableSmartCast(
|
||||
val argument: ExpressionKotlinCallArgument,
|
||||
val targetType: UnwrappedType
|
||||
) : KotlinCallDiagnostic(MAY_THROW_RUNTIME_ERROR) {
|
||||
) : KotlinCallDiagnostic(RESOLVED_WITH_ERROR) {
|
||||
override fun report(reporter: DiagnosticReporter) = reporter.onCallArgument(argument, this)
|
||||
}
|
||||
|
||||
@@ -213,7 +213,7 @@ class ResolvedToSamWithVarargDiagnostic(val argument: KotlinCallArgument) : Kotl
|
||||
class NotEnoughInformationForLambdaParameter(
|
||||
val lambdaArgument: LambdaKotlinCallArgument,
|
||||
val parameterIndex: Int
|
||||
) : KotlinCallDiagnostic(RESOLVED) {
|
||||
) : KotlinCallDiagnostic(RESOLVED_WITH_ERROR) {
|
||||
override fun report(reporter: DiagnosticReporter) {
|
||||
reporter.onCallArgument(lambdaArgument, this)
|
||||
}
|
||||
|
||||
+2
-1
@@ -74,6 +74,7 @@ fun getResultApplicability(diagnostics: Collection<KotlinCallDiagnostic>) =
|
||||
|
||||
enum class ResolutionCandidateApplicability {
|
||||
RESOLVED, // call success or has uncompleted inference or in other words possible successful candidate
|
||||
RESOLVED_WITH_ERROR, // call has error, but it is still successful from resolution perspective
|
||||
RESOLVED_LOW_PRIORITY,
|
||||
CONVENTION_ERROR, // missing infix, operator etc
|
||||
MAY_THROW_RUNTIME_ERROR, // unsafe call or unstable smart cast
|
||||
@@ -108,7 +109,7 @@ class UsedSmartCastForDispatchReceiver(val smartCastType: KotlinType) : Resoluti
|
||||
object ErrorDescriptorDiagnostic : ResolutionDiagnostic(RESOLVED) // todo discuss and change to INAPPLICABLE
|
||||
object LowPriorityDescriptorDiagnostic : ResolutionDiagnostic(RESOLVED_LOW_PRIORITY)
|
||||
object DynamicDescriptorDiagnostic : ResolutionDiagnostic(RESOLVED_LOW_PRIORITY)
|
||||
object UnstableSmartCastDiagnostic : ResolutionDiagnostic(MAY_THROW_RUNTIME_ERROR)
|
||||
object UnstableSmartCastDiagnostic : ResolutionDiagnostic(RESOLVED_WITH_ERROR)
|
||||
object HiddenExtensionRelatedToDynamicTypes : ResolutionDiagnostic(HIDDEN)
|
||||
object HiddenDescriptor : ResolutionDiagnostic(HIDDEN)
|
||||
|
||||
|
||||
@@ -311,10 +311,15 @@ class TowerResolver {
|
||||
override fun getSuccessfulCandidates(): Collection<C>? {
|
||||
if (!isSuccessful) return null
|
||||
val firstGroupWithResolved = candidateGroups.firstOrNull {
|
||||
it.any { it.resultingApplicability == ResolutionCandidateApplicability.RESOLVED }
|
||||
it.any(::isSuccessfulCandidate)
|
||||
} ?: return null
|
||||
|
||||
return firstGroupWithResolved.filter { it.resultingApplicability == ResolutionCandidateApplicability.RESOLVED }
|
||||
return firstGroupWithResolved.filter(::isSuccessfulCandidate)
|
||||
}
|
||||
|
||||
private fun isSuccessfulCandidate(candidate: C): Boolean {
|
||||
return candidate.resultingApplicability == ResolutionCandidateApplicability.RESOLVED
|
||||
|| candidate.resultingApplicability == ResolutionCandidateApplicability.RESOLVED_WITH_ERROR
|
||||
}
|
||||
|
||||
override fun pushCandidates(candidates: Collection<C>) {
|
||||
|
||||
@@ -27,7 +27,7 @@ private val INAPPLICABLE_STATUSES = setOf(
|
||||
)
|
||||
|
||||
val ResolutionCandidateApplicability.isSuccess: Boolean
|
||||
get() = this <= ResolutionCandidateApplicability.RESOLVED_LOW_PRIORITY
|
||||
get() = this <= ResolutionCandidateApplicability.RESOLVED_WITH_ERROR
|
||||
|
||||
val CallableDescriptor.isSynthesized: Boolean
|
||||
get() = (this is CallableMemberDescriptor && kind == CallableMemberDescriptor.Kind.SYNTHESIZED)
|
||||
|
||||
Reference in New Issue
Block a user