All Downloads are FREE. Search and download functionalities are using the official Maven repository.

.kotlin.kotlin-compiler.1.3.11.source-code.ManyCandidatesResolver.kt Maven / Gradle / Ivy

There is a newer version: 2.1.0-Beta1
Show newest version
/*
 * Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
 * that can be found in the license/LICENSE.txt file.
 */

package org.jetbrains.kotlin.resolve.calls.tower

import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.descriptors.CallableDescriptor
import org.jetbrains.kotlin.resolve.calls.components.*
import org.jetbrains.kotlin.resolve.calls.context.BasicCallResolutionContext
import org.jetbrains.kotlin.resolve.calls.inference.NewConstraintSystem
import org.jetbrains.kotlin.resolve.calls.inference.components.KotlinConstraintSystemCompleter
import org.jetbrains.kotlin.resolve.calls.inference.model.ConstraintStorage
import org.jetbrains.kotlin.resolve.calls.inference.model.NewConstraintSystemImpl
import org.jetbrains.kotlin.resolve.calls.inference.model.NewTypeVariable
import org.jetbrains.kotlin.resolve.calls.model.*
import org.jetbrains.kotlin.resolve.calls.results.OverloadResolutionResults
import org.jetbrains.kotlin.resolve.calls.tasks.TracingStrategy
import org.jetbrains.kotlin.types.TypeConstructor

abstract class ManyCandidatesResolver(
    private val psiCallResolver: PSICallResolver,
    private val postponedArgumentsAnalyzer: PostponedArgumentsAnalyzer,
    protected val kotlinConstraintSystemCompleter: KotlinConstraintSystemCompleter,
    protected val callComponents: KotlinCallComponents,
    val builtIns: KotlinBuiltIns
) : InferenceSession {
    private val partiallyResolvedCallsInfo = arrayListOf()
    private val errorCallsInfo = arrayListOf>()

    open fun prepareForCompletion(commonSystem: NewConstraintSystem, resolvedCallsInfo: List) {
        // do nothing
    }

    override fun shouldRunCompletion(candidate: KotlinResolutionCandidate): Boolean {
        return false
    }

    override fun addPartialCallInfo(callInfo: PartialCallInfo) {
        if (callInfo !is PSIPartialCallInfo) {
            throw AssertionError("Call info for $callInfo should be instance of PSIPartialCallInfo")
        }
        partiallyResolvedCallsInfo.add(callInfo)
    }

    override fun addCompletedCallInfo(callInfo: CompletedCallInfo) {
        // do nothing
    }

    override fun addErrorCallInfo(callInfo: ErrorCallInfo) {
        if (callInfo !is PSIErrorCallInfo<*>) {
            throw AssertionError("Error call info for $callInfo should be instance of PSIErrorCallInfo")
        }
        errorCallsInfo.add(callInfo as PSIErrorCallInfo)
    }

    override fun currentConstraintSystem(): ConstraintStorage {
        return partiallyResolvedCallsInfo.lastOrNull()?.callResolutionResult?.constraintSystem ?: ConstraintStorage.Empty
    }

    fun resolveCandidates(resolutionCallbacks: KotlinResolutionCallbacks): List> {
        val resolvedCallsInfo = partiallyResolvedCallsInfo.toList()

        val commonSystem = NewConstraintSystemImpl(callComponents.constraintInjector, builtIns).apply {
            addOtherSystem(currentConstraintSystem())
        }

        prepareForCompletion(commonSystem, resolvedCallsInfo)

        val diagnosticHolder = KotlinDiagnosticsHolder.SimpleHolder()

        kotlinConstraintSystemCompleter.runCompletion(
            commonSystem.asConstraintSystemCompleterContext(),
            KotlinConstraintSystemCompleter.ConstraintSystemCompletionMode.FULL,
            resolvedCallsInfo.map { it.callResolutionResult },
            builtIns.unitType
        ) {
            postponedArgumentsAnalyzer.analyze(
                commonSystem.asPostponedArgumentsAnalyzerContext(), resolutionCallbacks, it, diagnosticHolder
            )
        }

        val allCandidates = arrayListOf>()

        resolvedCallsInfo.mapTo(allCandidates) {
            val resolutionResult = it.asCallResolutionResult(diagnosticHolder, commonSystem)
            ResolutionResultCallInfo(
                resolutionResult, psiCallResolver.convertToOverloadResolutionResults(it.context, resolutionResult, it.tracingStrategy)
            )
        }

        errorCallsInfo.mapTo(allCandidates) { ResolutionResultCallInfo(it.callResolutionResult, it.result) }

        return allCandidates
    }

    private fun PartialCallInfo.asCallResolutionResult(
        diagnosticsHolder: KotlinDiagnosticsHolder.SimpleHolder,
        commonSystem: NewConstraintSystem
    ): CallResolutionResult {
        val diagnostics = diagnosticsHolder.getDiagnostics() + callResolutionResult.diagnostics + commonSystem.diagnostics
        return CompletedCallResolutionResult(callResolutionResult.resultCallAtom, diagnostics, commonSystem.asReadOnlyStorage())
    }
}

data class ResolutionResultCallInfo(
    val resolutionResult: CallResolutionResult,
    val overloadResolutionResults: OverloadResolutionResults
)

class PSIPartialCallInfo(
    override val callResolutionResult: PartialCallResolutionResult,
    val context: BasicCallResolutionContext,
    val tracingStrategy: TracingStrategy
) : PartialCallInfo

class PSICompletedCallInfo(
    override val callResolutionResult: CompletedCallResolutionResult,
    val context: BasicCallResolutionContext,
    val tracingStrategy: TracingStrategy
) : CompletedCallInfo

class PSIErrorCallInfo(
    override val callResolutionResult: CallResolutionResult,
    val result: OverloadResolutionResults
) : ErrorCallInfo




© 2015 - 2024 Weber Informatics LLC | Privacy Policy