Support default arguments for expected declarations
#KT-21913 Fixed
This commit is contained in:
@@ -561,7 +561,6 @@ public interface Errors {
|
||||
// Multi-platform projects
|
||||
|
||||
DiagnosticFactory0<KtDeclaration> EXPECTED_DECLARATION_WITH_BODY = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<KtParameter> EXPECTED_DECLARATION_WITH_DEFAULT_PARAMETER = DiagnosticFactory0.create(ERROR);
|
||||
DiagnosticFactory0<KtConstructorDelegationCall> EXPECTED_CLASS_CONSTRUCTOR_DELEGATION_CALL = DiagnosticFactory0.create(ERROR);
|
||||
DiagnosticFactory0<KtParameter> EXPECTED_CLASS_CONSTRUCTOR_PROPERTY_PARAMETER = DiagnosticFactory0.create(ERROR);
|
||||
DiagnosticFactory0<KtConstructor<?>> EXPECTED_ENUM_CONSTRUCTOR = DiagnosticFactory0.create(ERROR);
|
||||
@@ -571,7 +570,6 @@ public interface Errors {
|
||||
DiagnosticFactory0<PsiElement> EXPECTED_LATEINIT_PROPERTY = DiagnosticFactory0.create(ERROR);
|
||||
DiagnosticFactory0<PsiElement> SUPERTYPE_INITIALIZED_IN_EXPECTED_CLASS = DiagnosticFactory0.create(ERROR);
|
||||
DiagnosticFactory0<PsiElement> EXPECTED_PRIVATE_DECLARATION = DiagnosticFactory0.create(ERROR);
|
||||
|
||||
DiagnosticFactory0<KtDelegatedSuperTypeEntry> IMPLEMENTATION_BY_DELEGATION_IN_EXPECT_CLASS = DiagnosticFactory0.create(ERROR);
|
||||
|
||||
DiagnosticFactory0<KtTypeAlias> ACTUAL_TYPE_ALIAS_NOT_TO_CLASS = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
@@ -579,6 +577,9 @@ public interface Errors {
|
||||
ACTUAL_TYPE_ALIAS_TO_CLASS_WITH_DECLARATION_SITE_VARIANCE = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<KtTypeAlias> ACTUAL_TYPE_ALIAS_WITH_USE_SITE_VARIANCE = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<KtTypeAlias> ACTUAL_TYPE_ALIAS_WITH_COMPLEX_SUBSTITUTION = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<PsiElement> ACTUAL_FUNCTION_WITH_DEFAULT_ARGUMENTS = DiagnosticFactory0.create(ERROR);
|
||||
|
||||
DiagnosticFactory0<PsiElement> EXPECTED_FUNCTION_SOURCE_WITH_DEFAULT_ARGUMENTS_NOT_FOUND = DiagnosticFactory0.create(ERROR);
|
||||
|
||||
DiagnosticFactory3<KtNamedDeclaration, MemberDescriptor, ModuleDescriptor,
|
||||
Map<Incompatible, Collection<MemberDescriptor>>> NO_ACTUAL_FOR_EXPECT =
|
||||
|
||||
@@ -157,8 +157,7 @@ object PositioningStrategies {
|
||||
callableDeclaration?.let { it.receiverTypeReference ?: it.valueParameterList }
|
||||
}
|
||||
ParameterCount, ParameterTypes, ParameterNames,
|
||||
ValueParameterHasDefault, ValueParameterVararg,
|
||||
ValueParameterNoinline, ValueParameterCrossinline -> {
|
||||
ValueParameterVararg, ValueParameterNoinline, ValueParameterCrossinline -> {
|
||||
callableDeclaration?.valueParameterList
|
||||
}
|
||||
ReturnType -> {
|
||||
|
||||
+5
-1
@@ -236,7 +236,6 @@ public class DefaultErrorMessages {
|
||||
MAP.put(FORBIDDEN_VARARG_PARAMETER_TYPE, "Forbidden vararg parameter type: {0}", RENDER_TYPE);
|
||||
|
||||
MAP.put(EXPECTED_DECLARATION_WITH_BODY, "Expected declaration must not have a body");
|
||||
MAP.put(EXPECTED_DECLARATION_WITH_DEFAULT_PARAMETER, "Expected declaration cannot have parameters with default values");
|
||||
MAP.put(EXPECTED_CLASS_CONSTRUCTOR_DELEGATION_CALL, "Explicit delegation call for constructor of an expected class is not allowed");
|
||||
MAP.put(EXPECTED_CLASS_CONSTRUCTOR_PROPERTY_PARAMETER, "Expected class constructor cannot have a property parameter");
|
||||
MAP.put(EXPECTED_ENUM_CONSTRUCTOR, "Expected enum class cannot have a constructor");
|
||||
@@ -253,6 +252,11 @@ public class DefaultErrorMessages {
|
||||
MAP.put(ACTUAL_TYPE_ALIAS_TO_CLASS_WITH_DECLARATION_SITE_VARIANCE, "Aliased class should not have type parameters with declaration-site variance");
|
||||
MAP.put(ACTUAL_TYPE_ALIAS_WITH_USE_SITE_VARIANCE, "Right-hand side of actual type alias cannot contain use-site variance or star projections");
|
||||
MAP.put(ACTUAL_TYPE_ALIAS_WITH_COMPLEX_SUBSTITUTION, "Type arguments in the right-hand side of actual type alias should be its type parameters in the same order, e.g. 'actual typealias Foo<A, B> = Bar<A, B>'");
|
||||
MAP.put(ACTUAL_FUNCTION_WITH_DEFAULT_ARGUMENTS, "Actual function cannot have default argument values, they should be declared in the expected function");
|
||||
|
||||
MAP.put(EXPECTED_FUNCTION_SOURCE_WITH_DEFAULT_ARGUMENTS_NOT_FOUND,
|
||||
"Expected function source is not found, therefore it's impossible to generate default argument values declared there. " +
|
||||
"Please add the corresponding file to compilation sources");
|
||||
|
||||
MAP.put(NO_ACTUAL_FOR_EXPECT, "Expected {0} has no actual declaration in module{1}{2}", DECLARATION_NAME_WITH_KIND,
|
||||
PLATFORM, PlatformIncompatibilityDiagnosticRenderer.TEXT);
|
||||
|
||||
@@ -37,6 +37,7 @@ import org.jetbrains.kotlin.resolve.DescriptorUtils.classCanHaveOpenMembers
|
||||
import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator
|
||||
import org.jetbrains.kotlin.resolve.checkers.PlatformDiagnosticSuppressor
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.builtIns
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.declaresOrInheritsDefaultValue
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.isEffectivelyExternal
|
||||
import org.jetbrains.kotlin.resolve.source.KotlinSourceElement
|
||||
import org.jetbrains.kotlin.types.*
|
||||
@@ -246,6 +247,10 @@ class DeclarationsChecker(
|
||||
checkVarargParameters(trace, constructorDescriptor)
|
||||
checkConstructorVisibility(constructorDescriptor, declaration)
|
||||
checkExpectedClassConstructor(constructorDescriptor, declaration)
|
||||
|
||||
if (constructorDescriptor.isActual) {
|
||||
checkActualFunction(declaration, constructorDescriptor)
|
||||
}
|
||||
}
|
||||
|
||||
private fun checkExpectedClassConstructor(constructorDescriptor: ClassConstructorDescriptor, declaration: KtConstructor<*>) {
|
||||
@@ -765,6 +770,9 @@ class DeclarationsChecker(
|
||||
if (functionDescriptor.isExpect) {
|
||||
checkExpectedFunction(function, functionDescriptor)
|
||||
}
|
||||
if (functionDescriptor.isActual) {
|
||||
checkActualFunction(function, functionDescriptor)
|
||||
}
|
||||
|
||||
shadowedExtensionChecker.checkDeclaration(function, functionDescriptor)
|
||||
}
|
||||
@@ -774,13 +782,17 @@ class DeclarationsChecker(
|
||||
trace.report(EXPECTED_DECLARATION_WITH_BODY.on(function))
|
||||
}
|
||||
|
||||
for (parameter in function.valueParameters) {
|
||||
if (parameter.hasDefaultValue()) {
|
||||
trace.report(EXPECTED_DECLARATION_WITH_DEFAULT_PARAMETER.on(parameter))
|
||||
checkPrivateExpectedDeclaration(function, functionDescriptor)
|
||||
}
|
||||
|
||||
private fun checkActualFunction(element: KtDeclaration, functionDescriptor: FunctionDescriptor) {
|
||||
for (valueParameter in functionDescriptor.valueParameters) {
|
||||
if (valueParameter.declaresDefaultValue()) {
|
||||
trace.report(
|
||||
ACTUAL_FUNCTION_WITH_DEFAULT_ARGUMENTS.on(DescriptorToSourceUtils.descriptorToDeclaration(valueParameter) ?: element)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
checkPrivateExpectedDeclaration(function, functionDescriptor)
|
||||
}
|
||||
|
||||
private fun checkImplicitCallableType(declaration: KtCallableDeclaration, descriptor: CallableDescriptor) {
|
||||
|
||||
+4
-3
@@ -27,6 +27,7 @@ import org.jetbrains.kotlin.resolve.AnalyzerExtensions
|
||||
import org.jetbrains.kotlin.resolve.BindingContext
|
||||
import org.jetbrains.kotlin.resolve.BindingTrace
|
||||
import org.jetbrains.kotlin.resolve.calls.components.hasDefaultValue
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.declaresOrInheritsDefaultValue
|
||||
|
||||
class InlineAnalyzerExtension(
|
||||
private val reasonableInlineRules: Iterable<ReasonableInlineRule>,
|
||||
@@ -95,9 +96,9 @@ class InlineAnalyzerExtension(
|
||||
if (parameter.hasDefaultValue()) {
|
||||
val ktParameter = ktParameters[parameter.index]
|
||||
//Always report unsupported error on functional parameter with inherited default (there are some problems with inlining)
|
||||
val inheritDefaultValues = !parameter.declaresDefaultValue()
|
||||
if (checkInlinableParameter(parameter, ktParameter, functionDescriptor, null) || inheritDefaultValues) {
|
||||
if (inheritDefaultValues || !languageVersionSettings.supportsFeature(LanguageFeature.InlineDefaultFunctionalParameters)) {
|
||||
val inheritsDefaultValue = !parameter.declaresDefaultValue() && parameter.declaresOrInheritsDefaultValue()
|
||||
if (checkInlinableParameter(parameter, ktParameter, functionDescriptor, null) || inheritsDefaultValue) {
|
||||
if (inheritsDefaultValue || !languageVersionSettings.supportsFeature(LanguageFeature.InlineDefaultFunctionalParameters)) {
|
||||
trace.report(
|
||||
Errors.NOT_YET_SUPPORTED_IN_INLINE.on(
|
||||
ktParameter,
|
||||
|
||||
Reference in New Issue
Block a user