Do not check bounds in type alias expansion if checkBounds is false

This happens when we resolve bounds for type parameters, causing wrong
UPPER_BOUND_VIOLATED to be reported on type parameter whose bounds were
not resolved yet.

 #KT-19601 Fixed Target versions 1.1.5
This commit is contained in:
Dmitry Petrov
2017-08-10 16:09:36 +03:00
parent ce37ab81ba
commit a8c82b64a1
6 changed files with 55 additions and 5 deletions
@@ -237,7 +237,7 @@ class DeclarationsChecker(
private fun checkTypeAliasExpansion(declaration: KtTypeAlias, typeAliasDescriptor: TypeAliasDescriptor) {
val typeAliasExpansion = TypeAliasExpansion.createWithFormalArguments(typeAliasDescriptor)
val reportStrategy = TypeAliasDeclarationCheckingReportStrategy(trace, typeAliasDescriptor, declaration)
TypeAliasExpander(reportStrategy).expandWithoutAbbreviation(typeAliasExpansion, Annotations.EMPTY)
TypeAliasExpander(reportStrategy, true).expandWithoutAbbreviation(typeAliasExpansion, Annotations.EMPTY)
}
private fun checkConstructorDeclaration(constructorDescriptor: ClassConstructorDescriptor, declaration: KtConstructor<*>) {
@@ -26,8 +26,10 @@ import org.jetbrains.kotlin.types.typeUtil.containsTypeAliasParameters
import org.jetbrains.kotlin.types.typeUtil.requiresTypeAliasExpansion
class TypeAliasExpander(
private val reportStrategy: TypeAliasExpansionReportStrategy
private val reportStrategy: TypeAliasExpansionReportStrategy,
private val shouldCheckBounds: Boolean
) {
fun expand(typeAliasExpansion: TypeAliasExpansion, annotations: Annotations) =
expandRecursively(typeAliasExpansion, annotations,
isNullable = false, recursionDepth = 0, withAbbreviatedType = true)
@@ -228,7 +230,9 @@ class TypeAliasExpander(
if (!substitutedArgument.isStarProjection && !substitutedArgument.type.containsTypeAliasParameters()) {
val unsubstitutedArgument = unsubstitutedType.arguments[i]
val typeParameter = unsubstitutedType.constructor.parameters[i]
DescriptorResolver.checkBoundsInTypeAlias(reportStrategy, unsubstitutedArgument.type, substitutedArgument.type, typeParameter, typeSubstitutor)
if (shouldCheckBounds) {
DescriptorResolver.checkBoundsInTypeAlias(reportStrategy, unsubstitutedArgument.type, substitutedArgument.type, typeParameter, typeSubstitutor)
}
}
}
}
@@ -242,6 +246,6 @@ class TypeAliasExpander(
}
}
val NON_REPORTING = TypeAliasExpander(TypeAliasExpansionReportStrategy.DO_NOTHING)
val NON_REPORTING = TypeAliasExpander(TypeAliasExpansionReportStrategy.DO_NOTHING, false)
}
}
@@ -544,7 +544,7 @@ class TypeResolver(
}
else {
val typeAliasExpansion = TypeAliasExpansion.create(null, descriptor, arguments)
val expandedType = TypeAliasExpander(reportStrategy).expand(typeAliasExpansion, annotations)
val expandedType = TypeAliasExpander(reportStrategy, c.checkBounds).expand(typeAliasExpansion, annotations)
type(expandedType)
}
}
@@ -0,0 +1,11 @@
interface Order<T>
typealias Ord<T> = Order<T>
class Test1<T1 : Ord<T1>>
interface Num<T : Number>
typealias N<T> = Num<T>
class Test2<T : N<<!UPPER_BOUND_VIOLATED!>String<!>>>
@@ -0,0 +1,29 @@
package
public interface Num</*0*/ T : kotlin.Number> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public interface Order</*0*/ T> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final class Test1</*0*/ T1 : Ord<T1> /* = Order<T1> */> {
public constructor Test1</*0*/ T1 : Ord<T1> /* = Order<T1> */>()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final class Test2</*0*/ T : N<kotlin.String> /* = Num<kotlin.String> */> {
public constructor Test2</*0*/ T : N<kotlin.String> /* = Num<kotlin.String> */>()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public typealias N</*0*/ T> = Num<T>
public typealias Ord</*0*/ T> = Order<T>
@@ -22849,6 +22849,12 @@ public class DiagnosticsTestGenerated extends AbstractDiagnosticsTest {
doTest(fileName);
}
@TestMetadata("kt19601.kt")
public void testKt19601() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/typealias/kt19601.kt");
doTest(fileName);
}
@TestMetadata("localTypeAlias.kt")
public void testLocalTypeAlias() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/typealias/localTypeAlias.kt");