Ensure the correct functions (with correct params) are being used in

ForLoopsLowering.
This commit is contained in:
Mark Punzalan
2019-11-06 15:54:13 -08:00
committed by max-kammerer
parent 21178a4f1a
commit d0c261c779
9 changed files with 74 additions and 10 deletions
@@ -63,8 +63,8 @@ internal sealed class ForLoopHeader(
/** Statement used to increment the induction variable. */
fun incrementInductionVariable(builder: DeclarationIrBuilder): IrStatement = with(builder) {
// inductionVariable = inductionVariable + step
val plusFun = inductionVariable.type.getClass()!!.functions.first {
it.name.asString() == "plus" &&
val plusFun = inductionVariable.type.getClass()!!.functions.single {
it.name == OperatorNameConventions.PLUS &&
it.valueParameters.size == 1 &&
it.valueParameters[0].type == step.type
}
@@ -23,6 +23,7 @@ import org.jetbrains.kotlin.ir.util.*
import org.jetbrains.kotlin.ir.visitors.IrElementVisitor
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.util.OperatorNameConventions
import kotlin.math.absoluteValue
/** Builds a [HeaderInfo] for progressions built using the `rangeTo` function. */
@@ -31,7 +32,7 @@ internal class RangeToHandler(private val context: CommonBackendContext, private
override val matcher = SimpleCalleeMatcher {
dispatchReceiver { it != null && it.type in progressionElementTypes }
fqName { it.pathSegments().last() == Name.identifier("rangeTo") }
fqName { it.pathSegments().last() == OperatorNameConventions.RANGE_TO }
parameterCount { it == 1 }
parameter(0) { it.type in progressionElementTypes }
}
@@ -649,7 +650,11 @@ internal class ArrayIterationHandler(context: CommonBackendContext) : IndexedGet
get() = getClass()!!.getPropertyGetter("size")!!.owner
override val IrType.getFunction
get() = getClass()!!.functions.first { it.name.asString() == "get" }
get() = getClass()!!.functions.single {
it.name == OperatorNameConventions.GET &&
it.valueParameters.size == 1 &&
it.valueParameters[0].type.isInt()
}
}
/** Builds a [HeaderInfo] for iteration over characters in a [String]. */
@@ -660,7 +665,11 @@ internal class StringIterationHandler(context: CommonBackendContext) : IndexedGe
get() = getClass()!!.getPropertyGetter("length")!!.owner
override val IrType.getFunction
get() = getClass()!!.functions.first { it.name.asString() == "get" }
get() = getClass()!!.functions.single {
it.name == OperatorNameConventions.GET &&
it.valueParameters.size == 1 &&
it.valueParameters[0].type.isInt()
}
}
/**
@@ -679,6 +688,9 @@ internal class CharSequenceIterationHandler(context: CommonBackendContext) : Ind
get() = getClass()?.getPropertyGetter("length")?.owner ?: context.ir.symbols.charSequence.getPropertyGetter("length")!!.owner
override val IrType.getFunction
get() = getClass()?.functions?.first { it.name.asString() == "get" }
?: context.ir.symbols.charSequence.getSimpleFunction("get")!!.owner
get() = getClass()?.functions?.single {
it.name == OperatorNameConventions.GET &&
it.valueParameters.size == 1 &&
it.valueParameters[0].type.isInt()
} ?: context.ir.symbols.charSequence.getSimpleFunction(OperatorNameConventions.GET.asString())!!.owner
}
@@ -25,7 +25,7 @@ internal fun IrExpression.castIfNecessary(targetType: IrType, numberCastFunction
return if (type == targetType || type.isNothing()) {
this
} else {
val castFun = type.getClass()!!.functions.first { it.name == numberCastFunctionName }
val castFun = type.getClass()!!.functions.single { it.name == numberCastFunctionName && it.valueParameters.isEmpty() }
IrCallImpl(startOffset, endOffset, castFun.returnType, castFun.symbol)
.apply { dispatchReceiver = this@castIfNecessary }
}
@@ -40,7 +40,10 @@ internal fun IrExpression.negate(): IrExpression {
// This expression's type could be Nothing from an exception throw, in which case the unary minus function will not exist.
if (type.isNothing()) return this
val unaryMinusFun = type.getClass()!!.functions.first { it.name == OperatorNameConventions.UNARY_MINUS }
val unaryMinusFun = type.getClass()!!.functions.single {
it.name == OperatorNameConventions.UNARY_MINUS &&
it.valueParameters.isEmpty()
}
IrCallImpl(startOffset, endOffset, type, unaryMinusFun.symbol, unaryMinusFun.descriptor).apply {
dispatchReceiver = this@negate
}
@@ -55,7 +58,10 @@ internal fun IrExpression.decrement(): IrExpression {
is Long -> IrConstImpl(startOffset, endOffset, type, IrConstKind.Long, thisValue - 1)
is Char -> IrConstImpl(startOffset, endOffset, type, IrConstKind.Char, thisValue - 1)
else -> {
val decFun = type.getClass()!!.functions.first { it.name == OperatorNameConventions.DEC }
val decFun = type.getClass()!!.functions.single {
it.name == OperatorNameConventions.DEC &&
it.valueParameters.isEmpty()
}
IrCallImpl(startOffset, endOffset, type, decFun.symbol, decFun.descriptor).apply {
dispatchReceiver = this@decrement
}
@@ -0,0 +1,21 @@
// KJS_WITH_FULL_RUNTIME
// WITH_RUNTIME
import kotlin.test.*
class MyCharSequence(val s: String) : CharSequence {
fun get(foo: String): Char = TODO("shouldn't be called!")
override val length = s.length
override fun subSequence(startIndex: Int, endIndex: Int) = s.subSequence(startIndex, endIndex)
override fun get(index: Int) = s.get(index)
}
fun box(): String {
val cs = MyCharSequence("1234")
val result = StringBuilder()
for (c in cs) {
result.append(c)
}
assertEquals("1234", result.toString())
return "OK"
}
@@ -19096,6 +19096,11 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceLengthIncreasedInLoopBody.kt");
}
@TestMetadata("forInCharSequenceWithMultipleGetFunctions.kt")
public void testForInCharSequenceWithMultipleGetFunctions() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceWithMultipleGetFunctions.kt");
}
@TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt")
public void testForInRangeLiteralWithMixedTypeBounds() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt");
@@ -19096,6 +19096,11 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceLengthIncreasedInLoopBody.kt");
}
@TestMetadata("forInCharSequenceWithMultipleGetFunctions.kt")
public void testForInCharSequenceWithMultipleGetFunctions() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceWithMultipleGetFunctions.kt");
}
@TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt")
public void testForInRangeLiteralWithMixedTypeBounds() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt");
@@ -17915,6 +17915,11 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceLengthIncreasedInLoopBody.kt");
}
@TestMetadata("forInCharSequenceWithMultipleGetFunctions.kt")
public void testForInCharSequenceWithMultipleGetFunctions() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceWithMultipleGetFunctions.kt");
}
@TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt")
public void testForInRangeLiteralWithMixedTypeBounds() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt");
@@ -14851,6 +14851,11 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceLengthIncreasedInLoopBody.kt");
}
@TestMetadata("forInCharSequenceWithMultipleGetFunctions.kt")
public void testForInCharSequenceWithMultipleGetFunctions() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceWithMultipleGetFunctions.kt");
}
@TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt")
public void testForInRangeLiteralWithMixedTypeBounds() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt");
@@ -16006,6 +16006,11 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceLengthIncreasedInLoopBody.kt");
}
@TestMetadata("forInCharSequenceWithMultipleGetFunctions.kt")
public void testForInCharSequenceWithMultipleGetFunctions() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInCharSequenceWithMultipleGetFunctions.kt");
}
@TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt")
public void testForInRangeLiteralWithMixedTypeBounds() throws Exception {
runTest("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt");