Make infix & operator checkers implement CallChecker
Instead of SymbolUsageValidator
This commit is contained in:
@@ -29,6 +29,7 @@ import org.jetbrains.kotlin.name.Name;
|
|||||||
import org.jetbrains.kotlin.psi.*;
|
import org.jetbrains.kotlin.psi.*;
|
||||||
import org.jetbrains.kotlin.renderer.DescriptorRenderer;
|
import org.jetbrains.kotlin.renderer.DescriptorRenderer;
|
||||||
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilKt;
|
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilKt;
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.OperatorCallChecker;
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystem;
|
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystem;
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystemCompleter;
|
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystemCompleter;
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.TypeVariableKt;
|
import org.jetbrains.kotlin.resolve.calls.inference.TypeVariableKt;
|
||||||
@@ -39,7 +40,6 @@ import org.jetbrains.kotlin.resolve.calls.smartcasts.DataFlowInfoFactory;
|
|||||||
import org.jetbrains.kotlin.resolve.scopes.LexicalScope;
|
import org.jetbrains.kotlin.resolve.scopes.LexicalScope;
|
||||||
import org.jetbrains.kotlin.resolve.scopes.ScopeUtils;
|
import org.jetbrains.kotlin.resolve.scopes.ScopeUtils;
|
||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver;
|
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver;
|
||||||
import org.jetbrains.kotlin.resolve.validation.OperatorValidator;
|
|
||||||
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator;
|
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator;
|
||||||
import org.jetbrains.kotlin.types.*;
|
import org.jetbrains.kotlin.types.*;
|
||||||
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker;
|
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker;
|
||||||
@@ -263,7 +263,7 @@ public class DelegatedPropertyResolver {
|
|||||||
PsiElement byKeyword = delegate.getByKeywordNode().getPsi();
|
PsiElement byKeyword = delegate.getByKeywordNode().getPsi();
|
||||||
|
|
||||||
if (!resultingDescriptor.isOperator()) {
|
if (!resultingDescriptor.isOperator()) {
|
||||||
OperatorValidator.Companion.report(byKeyword, resultingDescriptor, trace);
|
OperatorCallChecker.Companion.report(byKeyword, resultingDescriptor, trace);
|
||||||
}
|
}
|
||||||
|
|
||||||
symbolUsageValidator.validateCall(resultingCall, resultingCall.getResultingDescriptor(), trace, byKeyword);
|
symbolUsageValidator.validateCall(resultingCall, resultingCall.getResultingDescriptor(), trace, byKeyword);
|
||||||
|
|||||||
@@ -27,8 +27,6 @@ import org.jetbrains.kotlin.resolve.calls.checkers.*
|
|||||||
import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator
|
import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator
|
||||||
import org.jetbrains.kotlin.resolve.scopes.SyntheticScopes
|
import org.jetbrains.kotlin.resolve.scopes.SyntheticScopes
|
||||||
import org.jetbrains.kotlin.resolve.validation.DeprecatedSymbolValidator
|
import org.jetbrains.kotlin.resolve.validation.DeprecatedSymbolValidator
|
||||||
import org.jetbrains.kotlin.resolve.validation.InfixValidator
|
|
||||||
import org.jetbrains.kotlin.resolve.validation.OperatorValidator
|
|
||||||
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator
|
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator
|
||||||
import org.jetbrains.kotlin.storage.StorageManager
|
import org.jetbrains.kotlin.storage.StorageManager
|
||||||
import org.jetbrains.kotlin.types.DynamicTypesSettings
|
import org.jetbrains.kotlin.types.DynamicTypesSettings
|
||||||
@@ -66,12 +64,14 @@ private val DEFAULT_DECLARATION_CHECKERS = listOf(
|
|||||||
SuspendModifierChecker,
|
SuspendModifierChecker,
|
||||||
CoroutineModifierChecker)
|
CoroutineModifierChecker)
|
||||||
|
|
||||||
private val DEFAULT_CALL_CHECKERS = listOf(CapturingInClosureChecker(), InlineCheckerWrapper(), ReifiedTypeParameterSubstitutionChecker(),
|
private val DEFAULT_CALL_CHECKERS = listOf(
|
||||||
SafeCallChecker(), InvokeConventionChecker(), CallReturnsArrayOfNothingChecker(),
|
CapturingInClosureChecker(), InlineCheckerWrapper(), ReifiedTypeParameterSubstitutionChecker(), SafeCallChecker(),
|
||||||
ConstructorHeaderCallChecker, ProtectedConstructorCallChecker, CoroutineSuspendCallChecker,
|
InvokeConventionChecker(), CallReturnsArrayOfNothingChecker(), InfixCallChecker(), OperatorCallChecker(),
|
||||||
BuilderFunctionsCallChecker)
|
ConstructorHeaderCallChecker, ProtectedConstructorCallChecker,
|
||||||
|
CoroutineSuspendCallChecker, BuilderFunctionsCallChecker
|
||||||
|
)
|
||||||
private val DEFAULT_TYPE_CHECKERS = emptyList<AdditionalTypeChecker>()
|
private val DEFAULT_TYPE_CHECKERS = emptyList<AdditionalTypeChecker>()
|
||||||
private val DEFAULT_VALIDATORS = listOf(DeprecatedSymbolValidator(), OperatorValidator(), InfixValidator())
|
private val DEFAULT_VALIDATORS = listOf(DeprecatedSymbolValidator())
|
||||||
|
|
||||||
|
|
||||||
abstract class PlatformConfigurator(
|
abstract class PlatformConfigurator(
|
||||||
|
|||||||
@@ -30,6 +30,7 @@ import org.jetbrains.kotlin.resolve.BindingContext
|
|||||||
import org.jetbrains.kotlin.resolve.calls.CallTransformer
|
import org.jetbrains.kotlin.resolve.calls.CallTransformer
|
||||||
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
|
import org.jetbrains.kotlin.resolve.calls.callUtil.getResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.calls.callUtil.getValueArgumentForExpression
|
import org.jetbrains.kotlin.resolve.calls.callUtil.getValueArgumentForExpression
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.InfixCallChecker
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystem
|
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystem
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.constraintPosition.ConstraintPositionKind.EXPECTED_TYPE_POSITION
|
import org.jetbrains.kotlin.resolve.calls.inference.constraintPosition.ConstraintPositionKind.EXPECTED_TYPE_POSITION
|
||||||
import org.jetbrains.kotlin.resolve.calls.inference.getNestedTypeVariables
|
import org.jetbrains.kotlin.resolve.calls.inference.getNestedTypeVariables
|
||||||
@@ -41,7 +42,6 @@ import org.jetbrains.kotlin.resolve.scopes.LexicalScope
|
|||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver
|
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver
|
||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue
|
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue
|
||||||
import org.jetbrains.kotlin.resolve.scopes.utils.getImplicitReceiversHierarchy
|
import org.jetbrains.kotlin.resolve.scopes.utils.getImplicitReceiversHierarchy
|
||||||
import org.jetbrains.kotlin.resolve.validation.InfixValidator
|
|
||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
import org.jetbrains.kotlin.types.TypeUtils.DONT_CARE
|
import org.jetbrains.kotlin.types.TypeUtils.DONT_CARE
|
||||||
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker
|
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker
|
||||||
@@ -136,7 +136,7 @@ fun isConventionCall(call: Call): Boolean {
|
|||||||
return calleeExpression.getNameForConventionalOperation() != null
|
return calleeExpression.getNameForConventionalOperation() != null
|
||||||
}
|
}
|
||||||
|
|
||||||
fun isInfixCall(call: Call): Boolean = InfixValidator.isInfixCall(call.calleeExpression)
|
fun isInfixCall(call: Call): Boolean = InfixCallChecker.isInfixCall(call.calleeExpression)
|
||||||
|
|
||||||
fun getUnaryPlusOrMinusOperatorFunctionName(call: Call): Name? {
|
fun getUnaryPlusOrMinusOperatorFunctionName(call: Call): Name? {
|
||||||
if (call.callElement !is KtPrefixExpression) return null
|
if (call.callElement !is KtPrefixExpression) return null
|
||||||
|
|||||||
+11
-15
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2010-2015 JetBrains s.r.o.
|
* Copyright 2010-2016 JetBrains s.r.o.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -14,34 +14,30 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.jetbrains.kotlin.resolve.validation
|
package org.jetbrains.kotlin.resolve.calls.checkers
|
||||||
|
|
||||||
import com.intellij.psi.PsiElement
|
import com.intellij.psi.PsiElement
|
||||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
import org.jetbrains.kotlin.config.LanguageFeatureSettings
|
||||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||||
import org.jetbrains.kotlin.diagnostics.Errors
|
import org.jetbrains.kotlin.diagnostics.Errors
|
||||||
import org.jetbrains.kotlin.psi.KtBinaryExpression
|
import org.jetbrains.kotlin.psi.KtBinaryExpression
|
||||||
import org.jetbrains.kotlin.psi.KtOperationReferenceExpression
|
import org.jetbrains.kotlin.psi.KtOperationReferenceExpression
|
||||||
import org.jetbrains.kotlin.resolve.BindingTrace
|
import org.jetbrains.kotlin.resolve.calls.context.BasicCallResolutionContext
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
|
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.model.VariableAsFunctionResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.calls.tasks.isDynamic
|
import org.jetbrains.kotlin.resolve.calls.tasks.isDynamic
|
||||||
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameUnsafe
|
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameUnsafe
|
||||||
import org.jetbrains.kotlin.types.ErrorUtils
|
import org.jetbrains.kotlin.types.ErrorUtils
|
||||||
|
|
||||||
class InfixValidator : SymbolUsageValidator {
|
class InfixCallChecker : CallChecker {
|
||||||
|
override fun check(resolvedCall: ResolvedCall<*>, context: BasicCallResolutionContext, languageFeatureSettings: LanguageFeatureSettings) {
|
||||||
override fun validateCall(
|
val functionDescriptor = resolvedCall.resultingDescriptor as? FunctionDescriptor ?: return
|
||||||
resolvedCall: ResolvedCall<*>?,
|
|
||||||
targetDescriptor: CallableDescriptor,
|
|
||||||
trace: BindingTrace,
|
|
||||||
element: PsiElement
|
|
||||||
) {
|
|
||||||
val functionDescriptor = targetDescriptor as? FunctionDescriptor ?: return
|
|
||||||
if (functionDescriptor.isDynamic() || ErrorUtils.isError(functionDescriptor)) return
|
if (functionDescriptor.isDynamic() || ErrorUtils.isError(functionDescriptor)) return
|
||||||
|
val element = ((resolvedCall as? VariableAsFunctionResolvedCall)?.variableCall ?: resolvedCall).call.calleeExpression
|
||||||
if (isInfixCall(element) && !functionDescriptor.isInfix) {
|
if (isInfixCall(element) && !functionDescriptor.isInfix) {
|
||||||
val operationRefExpression = element as? KtOperationReferenceExpression ?: return
|
val operationRefExpression = element as? KtOperationReferenceExpression ?: return
|
||||||
val containingDeclarationName = functionDescriptor.containingDeclaration.fqNameUnsafe.asString()
|
val containingDeclarationName = functionDescriptor.containingDeclaration.fqNameUnsafe.asString()
|
||||||
trace.report(Errors.INFIX_MODIFIER_REQUIRED.on(operationRefExpression, functionDescriptor, containingDeclarationName))
|
context.trace.report(Errors.INFIX_MODIFIER_REQUIRED.on(operationRefExpression, functionDescriptor, containingDeclarationName))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -52,4 +48,4 @@ class InfixValidator : SymbolUsageValidator {
|
|||||||
return binaryExpression.operationReference === operationRefExpression && !operationRefExpression.isPredefinedOperator()
|
return binaryExpression.operationReference === operationRefExpression && !operationRefExpression.isPredefinedOperator()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
+22
-33
@@ -14,18 +14,17 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.jetbrains.kotlin.resolve.validation
|
package org.jetbrains.kotlin.resolve.calls.checkers
|
||||||
|
|
||||||
import com.intellij.psi.PsiElement
|
import com.intellij.psi.PsiElement
|
||||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
import org.jetbrains.kotlin.config.LanguageFeatureSettings
|
||||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||||
import org.jetbrains.kotlin.diagnostics.DiagnosticSink
|
import org.jetbrains.kotlin.diagnostics.DiagnosticSink
|
||||||
import org.jetbrains.kotlin.diagnostics.Errors
|
import org.jetbrains.kotlin.diagnostics.Errors
|
||||||
import org.jetbrains.kotlin.psi.*
|
import org.jetbrains.kotlin.psi.*
|
||||||
import org.jetbrains.kotlin.resolve.BindingContext
|
|
||||||
import org.jetbrains.kotlin.resolve.BindingTrace
|
|
||||||
import org.jetbrains.kotlin.resolve.calls.CallTransformer
|
import org.jetbrains.kotlin.resolve.calls.CallTransformer
|
||||||
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.isConventionCall
|
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.isConventionCall
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.context.BasicCallResolutionContext
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
|
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.VariableAsFunctionResolvedCall
|
import org.jetbrains.kotlin.resolve.calls.model.VariableAsFunctionResolvedCall
|
||||||
import org.jetbrains.kotlin.resolve.calls.tasks.isDynamic
|
import org.jetbrains.kotlin.resolve.calls.tasks.isDynamic
|
||||||
@@ -36,51 +35,41 @@ import org.jetbrains.kotlin.util.OperatorNameConventions.PLUS
|
|||||||
import org.jetbrains.kotlin.util.OperatorNameConventions.UNARY_MINUS
|
import org.jetbrains.kotlin.util.OperatorNameConventions.UNARY_MINUS
|
||||||
import org.jetbrains.kotlin.util.OperatorNameConventions.UNARY_PLUS
|
import org.jetbrains.kotlin.util.OperatorNameConventions.UNARY_PLUS
|
||||||
|
|
||||||
class OperatorValidator : SymbolUsageValidator {
|
class OperatorCallChecker : CallChecker {
|
||||||
|
override fun check(resolvedCall: ResolvedCall<*>, context: BasicCallResolutionContext, languageFeatureSettings: LanguageFeatureSettings) {
|
||||||
override fun validateCall(resolvedCall: ResolvedCall<*>?, targetDescriptor: CallableDescriptor, trace: BindingTrace, element: PsiElement) {
|
val functionDescriptor = resolvedCall.resultingDescriptor as? FunctionDescriptor ?: return
|
||||||
val functionDescriptor = targetDescriptor as? FunctionDescriptor ?: return
|
|
||||||
if (!checkNotErrorOrDynamic(functionDescriptor)) return
|
if (!checkNotErrorOrDynamic(functionDescriptor)) return
|
||||||
|
|
||||||
val jetElement = element as? KtElement ?: return
|
val element = resolvedCall.call.calleeExpression ?: resolvedCall.call.callElement
|
||||||
val call = resolvedCall?.call ?: trace.bindingContext[BindingContext.CALL, jetElement]
|
val call = resolvedCall.call
|
||||||
|
|
||||||
fun isInvokeCall(): Boolean {
|
fun isInvokeCall(): Boolean = call is CallTransformer.CallForImplicitInvoke
|
||||||
return call is CallTransformer.CallForImplicitInvoke
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isMultiDeclaration(): Boolean {
|
fun isMultiDeclaration(): Boolean = call.callElement is KtDestructuringDeclarationEntry
|
||||||
return (resolvedCall != null) && (call?.callElement is KtDestructuringDeclarationEntry)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isConventionOperator(): Boolean {
|
if (resolvedCall is VariableAsFunctionResolvedCall &&
|
||||||
if (jetElement !is KtOperationReferenceExpression) return false
|
call is CallTransformer.CallForImplicitInvoke && call.itIsVariableAsFunctionCall) {
|
||||||
return jetElement.getNameForConventionalOperation() != null
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isArrayAccessExpression() = jetElement is KtArrayAccessExpression
|
|
||||||
|
|
||||||
if (resolvedCall is VariableAsFunctionResolvedCall && call is CallTransformer.CallForImplicitInvoke && call.itIsVariableAsFunctionCall) {
|
|
||||||
val outerCall = call.outerCall
|
val outerCall = call.outerCall
|
||||||
if (isConventionCall(outerCall)) {
|
if (isConventionCall(outerCall)) {
|
||||||
throw AssertionError("Illegal resolved call to variable with invoke for $outerCall. Variable: ${resolvedCall.variableCall.resultingDescriptor}")
|
throw AssertionError("Illegal resolved call to variable with invoke for $outerCall. " +
|
||||||
|
"Variable: ${resolvedCall.variableCall.resultingDescriptor}")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isMultiDeclaration() || isInvokeCall()) {
|
if (isMultiDeclaration() || isInvokeCall()) {
|
||||||
if (!functionDescriptor.isOperator && call != null) {
|
if (!functionDescriptor.isOperator) {
|
||||||
report(call.callElement, functionDescriptor, trace)
|
report(call.callElement, functionDescriptor, context.trace)
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
val isConventionOperator = isConventionOperator()
|
val isConventionOperator = element is KtOperationReferenceExpression && element.getNameForConventionalOperation() != null
|
||||||
if (isConventionOperator || isArrayAccessExpression()) {
|
if (isConventionOperator || element is KtArrayAccessExpression) {
|
||||||
if (!functionDescriptor.isOperator) {
|
if (!functionDescriptor.isOperator) {
|
||||||
report(jetElement, functionDescriptor, trace)
|
report(element, functionDescriptor, context.trace)
|
||||||
}
|
}
|
||||||
if (isConventionOperator && call != null) {
|
if (isConventionOperator) {
|
||||||
checkDeprecatedUnaryConventions(call, functionDescriptor, trace)
|
checkDeprecatedUnaryConventions(call, functionDescriptor, context.trace)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -108,4 +97,4 @@ class OperatorValidator : SymbolUsageValidator {
|
|||||||
return (!functionDescriptor.isDynamic() && !ErrorUtils.isError(functionDescriptor))
|
return (!functionDescriptor.isDynamic() && !ErrorUtils.isError(functionDescriptor))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
+7
-15
@@ -869,22 +869,11 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor {
|
|||||||
* @return {@code true} iff expression can be assigned to
|
* @return {@code true} iff expression can be assigned to
|
||||||
*/
|
*/
|
||||||
public boolean checkLValue(
|
public boolean checkLValue(
|
||||||
@NotNull BindingTrace trace,
|
|
||||||
@NotNull ExpressionTypingContext context,
|
|
||||||
@NotNull KtExpression expression,
|
|
||||||
@Nullable KtExpression rightHandSide,
|
|
||||||
@NotNull KtOperationExpression operationExpression
|
|
||||||
) {
|
|
||||||
return checkLValue(trace, context, expression, rightHandSide, operationExpression, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
private boolean checkLValue(
|
|
||||||
@NotNull BindingTrace trace,
|
@NotNull BindingTrace trace,
|
||||||
@NotNull ExpressionTypingContext context,
|
@NotNull ExpressionTypingContext context,
|
||||||
@NotNull KtExpression expressionWithParenthesis,
|
@NotNull KtExpression expressionWithParenthesis,
|
||||||
@Nullable KtExpression rightHandSide,
|
@Nullable KtExpression rightHandSide,
|
||||||
@NotNull KtOperationExpression operationExpression,
|
@NotNull KtOperationExpression operationExpression
|
||||||
boolean canBeThis
|
|
||||||
) {
|
) {
|
||||||
KtExpression expression = KtPsiUtil.deparenthesize(expressionWithParenthesis);
|
KtExpression expression = KtPsiUtil.deparenthesize(expressionWithParenthesis);
|
||||||
if (expression instanceof KtArrayAccessExpression) {
|
if (expression instanceof KtArrayAccessExpression) {
|
||||||
@@ -901,17 +890,20 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor {
|
|||||||
|| operationType == KtTokens.PLUSPLUS || operationType == KtTokens.MINUSMINUS) {
|
|| operationType == KtTokens.PLUSPLUS || operationType == KtTokens.MINUSMINUS) {
|
||||||
ResolvedCall<?> resolvedCall = ignoreReportsTrace.get(INDEXED_LVALUE_SET, expression);
|
ResolvedCall<?> resolvedCall = ignoreReportsTrace.get(INDEXED_LVALUE_SET, expression);
|
||||||
if (resolvedCall != null) {
|
if (resolvedCall != null) {
|
||||||
CallableDescriptor descriptor = resolvedCall.getResultingDescriptor();
|
|
||||||
// Call must be validated with the actual, not temporary trace in order to report operator diagnostic
|
// Call must be validated with the actual, not temporary trace in order to report operator diagnostic
|
||||||
// Only unary assignment expressions (++, --) and +=/... must be checked, normal assignments have the proper trace
|
// Only unary assignment expressions (++, --) and +=/... must be checked, normal assignments have the proper trace
|
||||||
components.symbolUsageValidator.validateCall(resolvedCall, descriptor, trace, expression);
|
BasicCallResolutionContext callResolutionContext = BasicCallResolutionContext.create(
|
||||||
|
context.replaceBindingTrace(trace), resolvedCall.getCall(), CheckArgumentTypesMode.CHECK_VALUE_ARGUMENTS
|
||||||
|
);
|
||||||
|
for (CallChecker checker : components.callCheckers) {
|
||||||
|
checker.check(resolvedCall, callResolutionContext, components.languageFeatureSettings);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return info.getType() != null;
|
return info.getType() != null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (canBeThis && expression instanceof KtThisExpression) return true;
|
|
||||||
VariableDescriptor variable = BindingContextUtils.extractVariableDescriptorIfAny(trace.getBindingContext(), expression, true);
|
VariableDescriptor variable = BindingContextUtils.extractVariableDescriptorIfAny(trace.getBindingContext(), expression, true);
|
||||||
|
|
||||||
boolean result = true;
|
boolean result = true;
|
||||||
|
|||||||
+2
-2
@@ -27,11 +27,11 @@ import org.jetbrains.kotlin.diagnostics.DiagnosticSink;
|
|||||||
import org.jetbrains.kotlin.name.Name;
|
import org.jetbrains.kotlin.name.Name;
|
||||||
import org.jetbrains.kotlin.psi.Call;
|
import org.jetbrains.kotlin.psi.Call;
|
||||||
import org.jetbrains.kotlin.psi.KtExpression;
|
import org.jetbrains.kotlin.psi.KtExpression;
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.checkers.OperatorCallChecker;
|
||||||
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
|
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
|
||||||
import org.jetbrains.kotlin.resolve.calls.results.OverloadResolutionResults;
|
import org.jetbrains.kotlin.resolve.calls.results.OverloadResolutionResults;
|
||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver;
|
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver;
|
||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.TransientReceiver;
|
import org.jetbrains.kotlin.resolve.scopes.receivers.TransientReceiver;
|
||||||
import org.jetbrains.kotlin.resolve.validation.OperatorValidator;
|
|
||||||
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator;
|
import org.jetbrains.kotlin.resolve.validation.SymbolUsageValidator;
|
||||||
import org.jetbrains.kotlin.types.DynamicTypesKt;
|
import org.jetbrains.kotlin.types.DynamicTypesKt;
|
||||||
import org.jetbrains.kotlin.types.ErrorUtils;
|
import org.jetbrains.kotlin.types.ErrorUtils;
|
||||||
@@ -99,7 +99,7 @@ public class ForLoopConventionsChecker {
|
|||||||
if ((extensionReceiverParameter != null) && (DynamicTypesKt.isDynamic(extensionReceiverParameter.getType()))) return;
|
if ((extensionReceiverParameter != null) && (DynamicTypesKt.isDynamic(extensionReceiverParameter.getType()))) return;
|
||||||
|
|
||||||
if (!descriptor.isOperator()) {
|
if (!descriptor.isOperator()) {
|
||||||
OperatorValidator.Companion.report(expression, descriptor, sink);
|
OperatorCallChecker.Companion.report(expression, descriptor, sink);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user