FIR: refactor FirExpressionsResolveTransformer#transformAssignmentOperatorStatement
No logic change. This commit only rearrange stuff to make it cleaner
This commit is contained in:
committed by
TeamCityServer
parent
861f69822b
commit
c43faa2ada
+56
-43
@@ -25,15 +25,18 @@ import org.jetbrains.kotlin.fir.resolve.calls.*
|
|||||||
import org.jetbrains.kotlin.fir.resolve.diagnostics.*
|
import org.jetbrains.kotlin.fir.resolve.diagnostics.*
|
||||||
import org.jetbrains.kotlin.fir.resolve.inference.FirStubInferenceSession
|
import org.jetbrains.kotlin.fir.resolve.inference.FirStubInferenceSession
|
||||||
import org.jetbrains.kotlin.fir.resolve.inference.inferenceComponents
|
import org.jetbrains.kotlin.fir.resolve.inference.inferenceComponents
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor
|
||||||
import org.jetbrains.kotlin.fir.resolve.transformers.InvocationKindTransformer
|
import org.jetbrains.kotlin.fir.resolve.transformers.InvocationKindTransformer
|
||||||
import org.jetbrains.kotlin.fir.resolve.transformers.StoreReceiver
|
import org.jetbrains.kotlin.fir.resolve.transformers.StoreReceiver
|
||||||
import org.jetbrains.kotlin.fir.resolve.transformers.firClassLike
|
import org.jetbrains.kotlin.fir.resolve.transformers.firClassLike
|
||||||
import org.jetbrains.kotlin.name.StandardClassIds
|
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirVariableSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirVariableSymbol
|
||||||
import org.jetbrains.kotlin.fir.types.*
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
import org.jetbrains.kotlin.fir.types.builder.*
|
import org.jetbrains.kotlin.fir.types.builder.buildErrorTypeRef
|
||||||
|
import org.jetbrains.kotlin.fir.types.builder.buildResolvedTypeRef
|
||||||
import org.jetbrains.kotlin.fir.visitors.*
|
import org.jetbrains.kotlin.fir.visitors.*
|
||||||
import org.jetbrains.kotlin.name.Name
|
import org.jetbrains.kotlin.name.Name
|
||||||
|
import org.jetbrains.kotlin.name.StandardClassIds
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.inference.buildAbstractResultingSubstitutor
|
||||||
import org.jetbrains.kotlin.resolve.calls.tower.CandidateApplicability
|
import org.jetbrains.kotlin.resolve.calls.tower.CandidateApplicability
|
||||||
import org.jetbrains.kotlin.types.AbstractTypeChecker
|
import org.jetbrains.kotlin.types.AbstractTypeChecker
|
||||||
import org.jetbrains.kotlin.types.ConstantValueKind
|
import org.jetbrains.kotlin.types.ConstantValueKind
|
||||||
@@ -374,7 +377,8 @@ open class FirExpressionsResolveTransformer(transformer: FirBodyResolveTransform
|
|||||||
assignOperatorCall.transformSingle(this, ResolutionMode.ContextDependent)
|
assignOperatorCall.transformSingle(this, ResolutionMode.ContextDependent)
|
||||||
}
|
}
|
||||||
val assignCallReference = resolvedAssignCall.calleeReference as? FirNamedReferenceWithCandidate
|
val assignCallReference = resolvedAssignCall.calleeReference as? FirNamedReferenceWithCandidate
|
||||||
val assignIsError = assignCallReference?.isError ?: true
|
val assignIsResolvable = assignCallReference?.isError == false
|
||||||
|
|
||||||
// x = x + y
|
// x = x + y
|
||||||
val simpleOperatorName = FirOperationNameConventions.ASSIGNMENTS_TO_SIMPLE_OPERATOR.getValue(assignmentOperatorStatement.operation)
|
val simpleOperatorName = FirOperationNameConventions.ASSIGNMENTS_TO_SIMPLE_OPERATOR.getValue(assignmentOperatorStatement.operation)
|
||||||
val simpleOperatorCall = createFunctionCall(simpleOperatorName)
|
val simpleOperatorCall = createFunctionCall(simpleOperatorName)
|
||||||
@@ -382,57 +386,66 @@ open class FirExpressionsResolveTransformer(transformer: FirBodyResolveTransform
|
|||||||
simpleOperatorCall.transformSingle(this, ResolutionMode.ContextDependent)
|
simpleOperatorCall.transformSingle(this, ResolutionMode.ContextDependent)
|
||||||
}
|
}
|
||||||
val operatorCallReference = resolvedOperatorCall.calleeReference as? FirNamedReferenceWithCandidate
|
val operatorCallReference = resolvedOperatorCall.calleeReference as? FirNamedReferenceWithCandidate
|
||||||
val operatorIsError = operatorCallReference?.isError ?: true
|
val operatorIsResolvable = operatorCallReference?.isError == false
|
||||||
|
|
||||||
val lhsReference = leftArgument.toResolvedCallableReference()
|
val lhsReference = leftArgument.toResolvedCallableReference()
|
||||||
val lhsSymbol = lhsReference?.resolvedSymbol as? FirVariableSymbol<*>
|
val lhsSymbol = lhsReference?.resolvedSymbol as? FirVariableSymbol<*>
|
||||||
val lhsVariable = lhsSymbol?.fir
|
val lhsVariable = lhsSymbol?.fir
|
||||||
val lhsIsVar = lhsVariable?.isVar == true
|
val lhsIsVar = lhsVariable?.isVar == true
|
||||||
return when {
|
|
||||||
operatorIsError || (!lhsIsVar && !assignIsError) -> {
|
fun chooseAssign(): FirStatement {
|
||||||
callCompleter.completeCall(resolvedAssignCall, noExpectedType)
|
callCompleter.completeCall(resolvedAssignCall, noExpectedType)
|
||||||
dataFlowAnalyzer.exitFunctionCall(resolvedAssignCall, callCompleted = true)
|
dataFlowAnalyzer.exitFunctionCall(resolvedAssignCall, callCompleted = true)
|
||||||
resolvedAssignCall
|
return resolvedAssignCall
|
||||||
}
|
}
|
||||||
assignIsError -> {
|
|
||||||
callCompleter.completeCall(resolvedOperatorCall, lhsVariable?.returnTypeRef ?: noExpectedType)
|
fun chooseOperator(): FirStatement {
|
||||||
dataFlowAnalyzer.exitFunctionCall(resolvedOperatorCall, callCompleted = true)
|
callCompleter.completeCall(resolvedOperatorCall, lhsVariable?.returnTypeRef ?: noExpectedType)
|
||||||
val assignment =
|
dataFlowAnalyzer.exitFunctionCall(resolvedOperatorCall, callCompleted = true)
|
||||||
buildVariableAssignment {
|
val assignment =
|
||||||
source = assignmentOperatorStatement.source
|
buildVariableAssignment {
|
||||||
rValue = resolvedOperatorCall
|
source = assignmentOperatorStatement.source
|
||||||
calleeReference = when {
|
rValue = resolvedOperatorCall
|
||||||
lhsIsVar -> lhsReference!!
|
calleeReference = when {
|
||||||
else -> buildErrorNamedReference {
|
lhsIsVar -> lhsReference!!
|
||||||
source = when (leftArgument) {
|
else -> buildErrorNamedReference {
|
||||||
is FirFunctionCall -> leftArgument.source
|
source = when (leftArgument) {
|
||||||
is FirQualifiedAccess ->
|
is FirFunctionCall -> leftArgument.source
|
||||||
leftArgument.calleeReference.source
|
is FirQualifiedAccess ->
|
||||||
else -> leftArgument.source
|
leftArgument.calleeReference.source
|
||||||
}
|
else -> leftArgument.source
|
||||||
diagnostic = if (lhsSymbol == null) ConeVariableExpectedError() else ConeValReassignmentError(lhsSymbol)
|
|
||||||
}
|
}
|
||||||
}
|
diagnostic = if (lhsSymbol == null) ConeVariableExpectedError() else ConeValReassignmentError(lhsSymbol)
|
||||||
(leftArgument as? FirQualifiedAccess)?.let {
|
|
||||||
dispatchReceiver = it.dispatchReceiver
|
|
||||||
extensionReceiver = it.extensionReceiver
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
assignment.transform(transformer, ResolutionMode.ContextIndependent)
|
(leftArgument as? FirQualifiedAccess)?.let {
|
||||||
}
|
dispatchReceiver = it.dispatchReceiver
|
||||||
else -> {
|
extensionReceiver = it.extensionReceiver
|
||||||
val operatorCallSymbol = operatorCallReference?.candidateSymbol
|
}
|
||||||
val assignmentCallSymbol = assignCallReference?.candidateSymbol
|
|
||||||
|
|
||||||
requireNotNull(operatorCallSymbol)
|
|
||||||
requireNotNull(assignmentCallSymbol)
|
|
||||||
|
|
||||||
buildErrorExpression {
|
|
||||||
source = assignmentOperatorStatement.source
|
|
||||||
diagnostic = ConeOperatorAmbiguityError(listOf(operatorCallSymbol, assignmentCallSymbol))
|
|
||||||
}
|
}
|
||||||
|
return assignment.transform(transformer, ResolutionMode.ContextIndependent)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun reportAmbiguity(): FirStatement {
|
||||||
|
val operatorCallSymbol = operatorCallReference?.candidateSymbol
|
||||||
|
val assignmentCallSymbol = assignCallReference?.candidateSymbol
|
||||||
|
|
||||||
|
requireNotNull(operatorCallSymbol)
|
||||||
|
requireNotNull(assignmentCallSymbol)
|
||||||
|
|
||||||
|
return buildErrorExpression {
|
||||||
|
source = assignmentOperatorStatement.source
|
||||||
|
diagnostic = ConeOperatorAmbiguityError(listOf(operatorCallSymbol, assignmentCallSymbol))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return when {
|
||||||
|
assignIsResolvable && !lhsIsVar -> chooseAssign()
|
||||||
|
!assignIsResolvable && !operatorIsResolvable -> chooseAssign()
|
||||||
|
!assignIsResolvable && operatorIsResolvable -> chooseOperator()
|
||||||
|
assignIsResolvable && !operatorIsResolvable -> chooseAssign()
|
||||||
|
else -> reportAmbiguity()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun transformEqualityOperatorCall(
|
override fun transformEqualityOperatorCall(
|
||||||
|
|||||||
Reference in New Issue
Block a user