[JS IR BE] Make tests work

This commit is contained in:
Roman Artemev
2019-04-16 18:57:18 +03:00
committed by Dmitry Petrov
parent 760806a1ac
commit 6a82ffdc5e
5 changed files with 30 additions and 17 deletions
@@ -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) =
@@ -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
}
}
@@ -330,21 +330,23 @@ interface IrTypeSystemContext : TypeSystemInferenceExtensionContext {
makeTypeIntersection(types as List<IrType>)
}
fun extractTypeParameters(klass: IrTypeParametersContainer): List<IrTypeParameter> {
fun extractTypeParameters(klass: IrDeclarationParent): List<IrTypeParameter> {
val result = mutableListOf<IrTypeParameter>()
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
}
@@ -102,5 +102,5 @@ fun makeTypeProjection(type: IrType, variance: Variance): IrTypeProjection =
fun makeTypeIntersection(types: List<IrType>): 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() }
}
@@ -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 }