FIR: add a resolution mode for property delegates

Like function arguments, they are context-dependent, but unlike function
arguments, callable references should be resolved eagerly as if they are
explicit receivers.
This commit is contained in:
pyos
2020-11-17 14:02:35 +01:00
committed by Mikhail Glukhikh
parent 0a5b899aab
commit 7327c20200
15 changed files with 75 additions and 32 deletions
@@ -13,6 +13,7 @@ import org.jetbrains.kotlin.fir.types.builder.buildResolvedTypeRef
sealed class ResolutionMode {
object ContextDependent : ResolutionMode()
object ContextDependentDelegate : ResolutionMode()
object ContextIndependent : ResolutionMode()
// TODO: it's better not to use WithExpectedType(FirImplicitTypeRef)
class WithExpectedType(val expectedTypeRef: FirTypeRef) : ResolutionMode()
@@ -192,7 +192,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransfor
}
private fun transformPropertyWithDelegate(property: FirProperty) {
property.transformDelegate(transformer, ResolutionMode.ContextDependent)
property.transformDelegate(transformer, ResolutionMode.ContextDependentDelegate)
val delegateExpression = property.delegate!!
@@ -230,7 +230,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransfor
): CompositeTransformResult<FirStatement> {
dataFlowAnalyzer.enterDelegateExpression()
try {
val delegateProvider = wrappedDelegateExpression.delegateProvider.transformSingle(transformer, ResolutionMode.ContextDependent)
val delegateProvider = wrappedDelegateExpression.delegateProvider.transformSingle(transformer, data)
when (val calleeReference = (delegateProvider as FirResolvable).calleeReference) {
is FirResolvedNamedReference -> return delegateProvider.compose()
is FirNamedReferenceWithCandidate -> {
@@ -243,7 +243,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransfor
(delegateProvider as? FirFunctionCall)?.let { dataFlowAnalyzer.dropSubgraphFromCall(it) }
return wrappedDelegateExpression.expression
.transformSingle(transformer, ResolutionMode.ContextDependent)
.transformSingle(transformer, data)
.approximateIfIsIntegerConst()
.compose()
} finally {
@@ -669,7 +669,7 @@ open class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransfor
context.saveContextForAnonymousFunction(anonymousFunction)
}
return when (data) {
ResolutionMode.ContextDependent -> {
is ResolutionMode.ContextDependent, is ResolutionMode.ContextDependentDelegate -> {
dataFlowAnalyzer.visitPostponedAnonymousFunction(anonymousFunction)
anonymousFunction.addReturn().compose()
}
@@ -33,7 +33,6 @@ import org.jetbrains.kotlin.fir.symbols.impl.FirVariableSymbol
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.builder.*
import org.jetbrains.kotlin.fir.visitors.*
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.calls.tower.CandidateApplicability
import org.jetbrains.kotlin.types.TypeApproximatorConfiguration
@@ -612,7 +611,7 @@ open class FirExpressionsResolveTransformer(transformer: FirBodyResolveTransform
else
callableReferenceAccess
if (data !is ResolutionMode.ContextDependent) {
if (data !is ResolutionMode.ContextDependent /* ContextDependentDelegate is Ok here */) {
val resolvedReference =
components.syntheticCallGenerator.resolveCallableReferenceWithSyntheticOuterCall(
callableReferenceAccess, data.expectedType, resolutionContext,