From 6a82ffdc5e1d547a40c3cd993ca541d8e1d2e50b Mon Sep 17 00:00:00 2001 From: Roman Artemev Date: Tue, 16 Apr 2019 18:57:18 +0300 Subject: [PATCH] [JS IR BE] Make tests work --- .../transformations/InsertImplicitCasts.kt | 7 +++---- .../kotlin/ir/types/IrTypeSubstitutor.kt | 8 +++++--- .../kotlin/ir/types/IrTypeSystemContext.kt | 12 +++++++----- .../kotlin/ir/types/impl/IrSimpleTypeImpl.kt | 2 +- .../org/jetbrains/kotlin/ir/util/IrUtils.kt | 18 ++++++++++++++---- 5 files changed, 30 insertions(+), 17 deletions(-) diff --git a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/transformations/InsertImplicitCasts.kt b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/transformations/InsertImplicitCasts.kt index 90a2bdce911..9d79ccdf5a8 100644 --- a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/transformations/InsertImplicitCasts.kt +++ b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/transformations/InsertImplicitCasts.kt @@ -38,6 +38,7 @@ import org.jetbrains.kotlin.psi2ir.generators.GeneratorExtensions import org.jetbrains.kotlin.types.KotlinType import org.jetbrains.kotlin.types.isDynamic import org.jetbrains.kotlin.types.isNullabilityFlexible +import org.jetbrains.kotlin.types.typeUtil.isUnit fun insertImplicitCasts(element: IrElement, context: GeneratorContext) { element.transformChildren( @@ -279,15 +280,14 @@ open class InsertImplicitCasts( val valueType = this.type val valueKotlinType = valueType.originalKotlinType!! - val expectedKotlinType = expectedType.originalKotlinType!! return when { expectedType.isUnit() -> { + expectedType.originalKotlinType?.let { require(it.isUnit()) } coerceToUnit() } valueType is IrDynamicType && expectedType !is IrDynamicType -> { - require(valueKotlinType.isDynamic() && !expectedKotlinType.isDynamic()) if (expectedType.isNullableAny()) { this } else { @@ -339,8 +339,7 @@ open class InsertImplicitCasts( } protected open fun IrExpression.coerceToUnit(): IrExpression { - val valueType = getKotlinType(this) - return coerceToUnitIfNeeded(valueType, irBuiltIns) + return coerceToUnitIfNeeded(type, irBuiltIns) } protected fun getKotlinType(irExpression: IrExpression) = diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSubstitutor.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSubstitutor.kt index c5fa768caa6..80adbfa4cc7 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSubstitutor.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSubstitutor.kt @@ -27,10 +27,12 @@ class IrTypeSubstitutor( if (substitution.isEmpty()) return type return type.typeParameterConstructor()?.let { + // check whether it's T or T? + val isNullable = type.isMarkedNullable() val typeArgument = substitution.getValue(it) when (typeArgument) { - is IrStarProjection -> irBuiltIns.anyNType - is IrTypeProjection -> typeArgument.type + is IrStarProjection -> if (isNullable) irBuiltIns.anyNType else irBuiltIns.anyType + is IrTypeProjection -> with(typeArgument.type) { if (isNullable) makeNullable() else makeNotNull() } else -> error("unknown type argument") } } ?: substituteType(type) @@ -61,7 +63,7 @@ class IrTypeSubstitutor( if (classifier is IrTypeParameterSymbol) { val newArgument = substitution.getValue(classifier) return if (newArgument is IrTypeProjection) { - makeTypeProjection(newArgument.type, TypeSubstitutor.combine(typeArgument.variance, newArgument.variance)) + makeTypeProjection(newArgument.type, typeArgument.variance) } else newArgument } } diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSystemContext.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSystemContext.kt index 9f40e3a0e6d..9e43f363b9a 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSystemContext.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/IrTypeSystemContext.kt @@ -330,21 +330,23 @@ interface IrTypeSystemContext : TypeSystemInferenceExtensionContext { makeTypeIntersection(types as List) } -fun extractTypeParameters(klass: IrTypeParametersContainer): List { +fun extractTypeParameters(klass: IrDeclarationParent): List { val result = mutableListOf() - var current: IrTypeParametersContainer? = klass + var current: IrDeclarationParent? = klass while (current != null) { - result += current.typeParameters +// result += current.typeParameters + (current as? IrTypeParametersContainer)?.let { result += it.typeParameters } current = when (current) { + is IrField -> current.parent is IrClass -> when { current.isInner -> current.parent as IrClass - current.visibility == Visibilities.LOCAL -> current.parent as? IrTypeParametersContainer + current.visibility == Visibilities.LOCAL -> current.parent else -> null } is IrConstructor -> current.parent as IrClass is IrFunction -> if (current.visibility == Visibilities.LOCAL || current.dispatchReceiverParameter != null) { - current.parent as? IrTypeParametersContainer + current.parent } else null else -> null } diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/impl/IrSimpleTypeImpl.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/impl/IrSimpleTypeImpl.kt index bc1e74f27ef..250fdec1c0f 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/impl/IrSimpleTypeImpl.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/types/impl/IrSimpleTypeImpl.kt @@ -102,5 +102,5 @@ fun makeTypeProjection(type: IrType, variance: Variance): IrTypeProjection = fun makeTypeIntersection(types: List): IrType = with(types.map { makeTypeProjection(it, Variance.INVARIANT).type }.distinct()) { if (size == 1) return single() - else first { !(it.isAny() || it.isNullableAny()) } + else firstOrNull { !(it.isAny() || it.isNullableAny()) } ?: first { it.isAny() } } \ No newline at end of file diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/IrUtils.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/IrUtils.kt index d334de0c97f..08b0b95daf9 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/IrUtils.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/IrUtils.kt @@ -15,10 +15,7 @@ import org.jetbrains.kotlin.ir.expressions.impl.IrCallImpl import org.jetbrains.kotlin.ir.expressions.impl.IrConstructorCallImpl import org.jetbrains.kotlin.ir.expressions.impl.IrTypeOperatorCallImpl import org.jetbrains.kotlin.ir.symbols.* -import org.jetbrains.kotlin.ir.types.IrSimpleType -import org.jetbrains.kotlin.ir.types.classifierOrFail -import org.jetbrains.kotlin.ir.types.isAny -import org.jetbrains.kotlin.ir.types.toKotlinType +import org.jetbrains.kotlin.ir.types.* import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.SpecialNames @@ -162,6 +159,19 @@ fun IrExpression.coerceToUnitIfNeeded(valueType: KotlinType, irBuiltIns: IrBuilt ) } +fun IrExpression.coerceToUnitIfNeeded(valueType: IrType, irBuiltIns: IrBuiltIns): IrExpression { + return if (valueType.isSubtypeOf(irBuiltIns.unitType, irBuiltIns)) + this + else + IrTypeOperatorCallImpl( + startOffset, endOffset, + irBuiltIns.unitType, + IrTypeOperator.IMPLICIT_COERCION_TO_UNIT, + irBuiltIns.unitType, irBuiltIns.unitType.classifierOrFail, + this + ) +} + fun IrMemberAccessExpression.usesDefaultArguments(): Boolean = this.descriptor.valueParameters.any { this.getValueArgument(it) == null }