diff --git a/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/basic/RangeUntilIntrinsic.kt b/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/basic/RangeUntilIntrinsic.kt new file mode 100644 index 00000000000..28ca1350675 --- /dev/null +++ b/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/basic/RangeUntilIntrinsic.kt @@ -0,0 +1,32 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.js.translate.intrinsic.functions.basic + +import org.jetbrains.kotlin.builtins.StandardNames +import org.jetbrains.kotlin.js.backend.ast.JsExpression +import org.jetbrains.kotlin.descriptors.FunctionDescriptor +import org.jetbrains.kotlin.incremental.components.NoLookupLocation +import org.jetbrains.kotlin.js.backend.ast.JsInvocation +import org.jetbrains.kotlin.js.translate.context.TranslationContext +import org.jetbrains.kotlin.name.Name + +class RangeUntilIntrinsic(val function: FunctionDescriptor) : FunctionIntrinsicWithReceiverComputed() { + + override fun apply(receiver: JsExpression?, arguments: List, context: TranslationContext): JsExpression { + val packageDescriptor = context.currentModule.getPackage(StandardNames.RANGES_PACKAGE_FQ_NAME) + val untilFuns = packageDescriptor.memberScope.getContributedFunctions(untilFunName, NoLookupLocation.FROM_BUILTINS) + val untilFun = untilFuns.firstOrNull { + it.extensionReceiverParameter?.type == function.dispatchReceiverParameter!!.type && + it.valueParameters.size == 1 && + it.valueParameters[0].type == function.valueParameters[0].type + } ?: error("No 'until' function found for descriptor: $function") + return JsInvocation(context.getInnerReference(untilFun), listOfNotNull(receiver) + arguments) + } + + companion object { + private val untilFunName = Name.identifier("until") + } +} \ No newline at end of file diff --git a/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/factories/PrimitiveBinaryOperationFIF.java b/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/factories/PrimitiveBinaryOperationFIF.java index 1a3c5c7e177..398790be0ba 100644 --- a/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/factories/PrimitiveBinaryOperationFIF.java +++ b/js/js.translator/src/org/jetbrains/kotlin/js/translate/intrinsic/functions/factories/PrimitiveBinaryOperationFIF.java @@ -1,17 +1,6 @@ /* - * Copyright 2010-2017 JetBrains s.r.o. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ package org.jetbrains.kotlin.js.translate.intrinsic.functions.factories; @@ -29,6 +18,7 @@ import org.jetbrains.kotlin.js.translate.context.TranslationContext; import org.jetbrains.kotlin.js.translate.intrinsic.functions.basic.FunctionIntrinsic; import org.jetbrains.kotlin.js.translate.intrinsic.functions.basic.FunctionIntrinsicWithReceiverComputed; import org.jetbrains.kotlin.js.translate.intrinsic.functions.basic.RangeToIntrinsic; +import org.jetbrains.kotlin.js.translate.intrinsic.functions.basic.RangeUntilIntrinsic; import org.jetbrains.kotlin.js.translate.operation.OperatorTable; import org.jetbrains.kotlin.js.translate.utils.JsAstUtils; import org.jetbrains.kotlin.js.translate.utils.jsAstUtils.AstUtilsKt; @@ -131,7 +121,9 @@ public enum PrimitiveBinaryOperationFIF implements FunctionIntrinsicFactory { private static final DescriptorPredicate NUMBER_REM = pattern("Byte|Short|Int.rem(Byte|Short|Int)"); private static final DescriptorPredicate CHAR_RANGE_TO = pattern("Char.rangeTo(Char)"); + private static final DescriptorPredicate CHAR_RANGE_UNTIL = pattern("Char.rangeUntil(Char)"); private static final DescriptorPredicate NUMBER_RANGE_TO = pattern("Byte|Short|Int.rangeTo(Byte|Short|Int)"); + private static final DescriptorPredicate NUMBER_RANGE_UNTIL = pattern("Byte|Short|Int|Long.rangeUntil(Byte|Short|Int|Long)"); private static final ImmutableMap BINARY_BITWISE_OPERATIONS = ImmutableMap.builder() .put("or", JsBinaryOperator.BIT_OR) @@ -151,6 +143,9 @@ public enum PrimitiveBinaryOperationFIF implements FunctionIntrinsicFactory { if (CHAR_RANGE_TO.test(descriptor)) { return new RangeToIntrinsic(descriptor); } + if (CHAR_RANGE_UNTIL.test(descriptor)) { + return new RangeUntilIntrinsic(descriptor); + } if (PRIMITIVE_INTEGRAL_NUMBERS_COMPARE_TO_INTEGRAL_OPERATIONS.test(descriptor)) { return PRIMITIVE_NUMBER_COMPARE_TO_INTRINSIC; @@ -163,6 +158,10 @@ public enum PrimitiveBinaryOperationFIF implements FunctionIntrinsicFactory { return BUILTINS_COMPARE_TO_INTRINSIC; } + if (NUMBER_RANGE_UNTIL.test(descriptor)) { // test here because Long type is rejected after that + return new RangeUntilIntrinsic(descriptor); + } + if (!PREDICATE.test(descriptor)) { return null; }