Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
56 changes: 56 additions & 0 deletions compiler/testData/codegen/box/classLiteral/bound/primitives.kt
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
// WITH_STDLIB

import kotlin.test.assertEquals
import kotlin.test.assertNotEquals

// Circumvent constant folding —
// 21::class is always replaced with Int::class by the compiler.
fun erase(t: Any): Any = t

fun box(): String {
assertEquals(true::class, Boolean::class)
Expand All @@ -12,5 +17,56 @@ fun box(): String {
assertEquals(42L::class, Long::class)
assertEquals(42.toShort()::class, Short::class)

assertEquals(true::class.hashCode(), Boolean::class.hashCode())
assertEquals(42.toByte()::class.hashCode(), Byte::class.hashCode())
assertEquals('z'::class.hashCode(), Char::class.hashCode())
assertEquals(3.14::class.hashCode(), Double::class.hashCode())
assertEquals(2.72f::class.hashCode(), Float::class.hashCode())
assertEquals(42::class.hashCode(), Int::class.hashCode())
assertEquals(42L::class.hashCode(), Long::class.hashCode())
assertEquals(42.toShort()::class.hashCode(), Short::class.hashCode())

assertEquals(erase(true)::class, Boolean::class)
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(42.toByte())::class, Int::class)
} else {
assertEquals(erase(42.toByte())::class, Byte::class)
}
assertEquals(erase('z')::class, Char::class)
assertEquals(erase(3.14)::class, Double::class)
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(2.72f)::class, Double::class)
} else {
assertEquals(erase(2.72f)::class, Float::class)
}
assertEquals(erase(42)::class, Int::class)
assertEquals(erase(42L)::class, Long::class)
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(42.toShort())::class, Int::class)
} else {
assertEquals(erase(42.toShort())::class, Short::class)
}

assertEquals(erase(true)::class.hashCode(), Boolean::class.hashCode())
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(42.toByte())::class.hashCode(), Int::class.hashCode())
} else {
assertEquals(erase(42.toByte())::class.hashCode(), Byte::class.hashCode())
}
assertEquals(erase('z')::class.hashCode(), Char::class.hashCode())
assertEquals(erase(3.14)::class.hashCode(), Double::class.hashCode())
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(2.72f)::class.hashCode(), Double::class.hashCode())
} else {
assertEquals(erase(2.72f)::class.hashCode(), Float::class.hashCode())
}
assertEquals(erase(42)::class.hashCode(), Int::class.hashCode())
assertEquals(erase(42L)::class.hashCode(), Long::class.hashCode())
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
assertEquals(erase(42.toShort())::class.hashCode(), Int::class.hashCode())
} else {
assertEquals(erase(42.toShort())::class.hashCode(), Short::class.hashCode())
}

return "OK"
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
// IGNORE_BACKEND: JS_IR, JS_IR_ES6

// FILE: lib.kt
// boxed primitive comparisons
fun isBoolean(a: Any) = a::class == true::class
Expand All @@ -20,17 +18,35 @@ fun box(): String {
if (isBoolean(0)) return "Fail 2"
if (!isChar('c')) return "Fail 3"
if (isChar(0)) return "Fail 4"
if (!isByte(0.toByte())) return "Fail 5"
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
if (!isInt(0.toByte())) return "Fail 5"
} else {
if (!isByte(0.toByte())) return "Fail 5"
}
if (isByte(0)) return "Fail 6"
if (!isShort(0.toShort())) return "Fail 7"
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
if (!isInt(0.toShort())) return "Fail 7"
} else {
if (!isShort(0.toShort())) return "Fail 7"
}
if (isShort(0)) return "Fail 8"
if (!isInt(0)) return "Fail 9"
if (isInt("")) return "Fail 10"
if (!isLong(0L)) return "Fail 11"
if (isLong(0.0)) return "Fail 12"
if (!isFloat(10.0f)) return "Fail 13"
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
if (!isInt(10.0f)) return "Fail 13"
if (!isDouble(10.5f)) return "Fail 13"
} else {
if (!isFloat(10.0f)) return "Fail 13"
}
if (isFloat("")) return "Fail 14"
if (!isDouble(1.0)) return "Fail 15"
if (BACKEND_UNDER_TEST == "JS_IR" || BACKEND_UNDER_TEST == "JS_IR_ES6") {
if (!isInt(1.0)) return "Fail 15"
if (!isDouble(1.5)) return "Fail 15"
} else {
if (!isDouble(1.0)) return "Fail 15"
}
if (isDouble(0)) return "Fail 16"

if (!isReifiedInt<Int>()) return "Fail 17"
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/*
* Copyright 2010-2026 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.test.preprocessors

import org.jetbrains.kotlin.test.TargetBackend
import org.jetbrains.kotlin.test.model.TestFile
import org.jetbrains.kotlin.test.services.ReversibleSourceFilePreprocessor
import org.jetbrains.kotlin.test.services.TestServices
import org.jetbrains.kotlin.test.services.defaultsProvider
import org.jetbrains.kotlin.test.utils.ReplacingSourceTransformer

/**
* Selects the appropriate [ReplacingSourceTransformer] based on the target backend.
*/
abstract class BackendDependentSourceFilePreprocessor(testServices: TestServices) : ReversibleSourceFilePreprocessor(testServices) {
private val contentModifier: ReplacingSourceTransformer by lazy {
computeModifier(testServices.defaultsProvider.targetBackend ?: TargetBackend.ANY)
}

abstract fun computeModifier(targetBackend: TargetBackend): ReplacingSourceTransformer

override fun process(file: TestFile, content: String): String = contentModifier.invokeForTestFile(content)

override fun revert(file: TestFile, actualContent: String): String = contentModifier.revertForFile(actualContent)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/*
* Copyright 2010-2026 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.test.preprocessors

import org.jetbrains.kotlin.test.TargetBackend
import org.jetbrains.kotlin.test.services.TestServices
import org.jetbrains.kotlin.test.utils.ReplacingSourceTransformer

/**
* Replaces the magic identifier `BACKEND_UNDER_TEST` in the test source file with a string with the actual name of the backend that
* is being used to compile this test.
*
* This is useful when we want to test some behavior that _slightly_ differs between targets, so a separate test file would be an overkill.
* Instead, this magic identifier allows to write conditions like
* ```
* if (BACKEND_UNDER_TEST == "JVM") {
* // ...
* }
* ```
*/
class BackendUnderTestSourcePreprocessor(testServices: TestServices) : BackendDependentSourceFilePreprocessor(testServices) {
override fun computeModifier(targetBackend: TargetBackend): ReplacingSourceTransformer =
ReplacingSourceTransformer("BACKEND_UNDER_TEST", "\"${targetBackend.name}\"")
}

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,7 @@ package org.jetbrains.kotlin.test.preprocessors
import org.jetbrains.kotlin.test.TargetBackend
import org.jetbrains.kotlin.test.directives.ConfigurationDirectives
import org.jetbrains.kotlin.test.model.TestFile
import org.jetbrains.kotlin.test.services.ReversibleSourceFilePreprocessor
import org.jetbrains.kotlin.test.services.TestServices
import org.jetbrains.kotlin.test.services.defaultsProvider
import org.jetbrains.kotlin.test.services.moduleStructure
import org.jetbrains.kotlin.test.utils.ReplacingSourceTransformer
import org.jetbrains.kotlin.test.utils.TransformersFunctions
Expand All @@ -22,9 +20,7 @@ import org.jetbrains.kotlin.test.utils.TransformersFunctions
* - `@kotlin.jvm.JvmInline`
* - empty string
*/
class JvmInlineSourceTransformer(testServices: TestServices) : ReversibleSourceFilePreprocessor(testServices) {
private var contentModifier: ReplacingSourceTransformer? = null

class JvmInlineSourceTransformer(testServices: TestServices) : BackendDependentSourceFilePreprocessor(testServices) {
companion object {
fun computeModifier(targetBackend: TargetBackend): ReplacingSourceTransformer {
return when {
Expand All @@ -35,14 +31,15 @@ class JvmInlineSourceTransformer(testServices: TestServices) : ReversibleSourceF
}
}

override fun computeModifier(targetBackend: TargetBackend): ReplacingSourceTransformer = Companion.computeModifier(targetBackend)

override fun process(file: TestFile, content: String): String {
if (ConfigurationDirectives.WORKS_WHEN_VALUE_CLASS !in testServices.moduleStructure.allDirectives) return content
val targetBackend = testServices.defaultsProvider.targetBackend ?: TargetBackend.ANY
val contentModifier = computeModifier(targetBackend).also { this.contentModifier = it }
return contentModifier.invokeForTestFile(content)
return super.process(file, content)
}

override fun revert(file: TestFile, actualContent: String): String {
return contentModifier?.revertForFile(actualContent) ?: actualContent
if (ConfigurationDirectives.WORKS_WHEN_VALUE_CLASS !in testServices.moduleStructure.allDirectives) return actualContent
return super.revert(file, actualContent)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ package org.jetbrains.kotlin.test.runners

import com.intellij.testFramework.TestDataFile
import org.jetbrains.kotlin.codegen.forTestCompile.ForTestCompileRuntime
import org.jetbrains.kotlin.konan.test.blackbox.support.EnforcedHostTarget
import org.jetbrains.kotlin.test.Constructor
import org.jetbrains.kotlin.test.ExecutionListenerBasedDisposableProvider
import org.jetbrains.kotlin.test.NonGroupingTestRunner
Expand All @@ -19,6 +20,7 @@ import org.jetbrains.kotlin.test.directives.ConfigurationDirectives
import org.jetbrains.kotlin.test.directives.LanguageSettingsDirectives
import org.jetbrains.kotlin.test.frontend.classic.handlers.ClassicUnstableAndK2LanguageFeaturesSkipConfigurator
import org.jetbrains.kotlin.test.model.ResultingArtifact
import org.jetbrains.kotlin.test.preprocessors.BackendUnderTestSourcePreprocessor
import org.jetbrains.kotlin.test.preprocessors.JvmInlineSourceTransformer
import org.jetbrains.kotlin.test.preprocessors.MetaInfosCleanupPreprocessor
import org.jetbrains.kotlin.test.services.*
Expand All @@ -27,7 +29,6 @@ import org.jetbrains.kotlin.types.AbstractTypeChecker
import org.jetbrains.kotlin.types.FlexibleTypeImpl
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.TestInfo
import org.jetbrains.kotlin.konan.test.blackbox.support.EnforcedHostTarget
import kotlin.jvm.optionals.getOrNull

abstract class AbstractKotlinCompilerTest {
Expand All @@ -40,6 +41,7 @@ abstract class AbstractKotlinCompilerTest {
val defaultPreprocessors: List<Constructor<SourceFilePreprocessor>> = listOf(
::MetaInfosCleanupPreprocessor,
::JvmInlineSourceTransformer,
::BackendUnderTestSourcePreprocessor,
)

private fun configureDebugFlags() {
Expand Down
6 changes: 2 additions & 4 deletions libraries/stdlib/js/runtime/jsIntrinsics.kt
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,8 @@ import kotlin.js.internal.boxedLong.toStringImpl
internal annotation class JsIntrinsic

@UsedFromCompilerGeneratedCode
// @JsIntrinsic
// TODO(KT-84992): Remove the body of the intrinsic and @JsIntrinsic annotation after bootstrap
internal fun isLongCompiledToBigInt(): Boolean =
jsTypeOf(2L) === "bigint"
@JsIntrinsic
internal fun isLongCompiledToBigInt(): Boolean

@JsIntrinsic
@UsedFromCompilerGeneratedCode
Expand Down
13 changes: 3 additions & 10 deletions libraries/stdlib/js/src/kotlin/reflect/KClassImpl.kt
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

package kotlin.reflect.js.internal

import kotlin.reflect.*
import kotlin.reflect.KClass

internal abstract class KClassImpl<T : Any> : KClass<T> {
internal abstract val jClass: JsClass<T>
Expand All @@ -23,7 +23,7 @@ internal abstract class KClassImpl<T : Any> : KClass<T> {
// NothingKClassImpl doesn't provide the jClass property; therefore, process it separately.
// This can't be NothingKClassImpl because it overload equals.
is NothingKClassImpl -> false
is KClassImpl<*> -> jClass == other.jClass
is KClassImpl<*> -> jClass == other.jClass && simpleName == other.simpleName
else -> false
}
}
Expand All @@ -47,7 +47,7 @@ internal class SimpleKClassImpl<T : Any>(override val jClass: JsClass<T>) : KCla

internal class PrimitiveKClassImpl<T : Any>(
override val jClass: JsClass<T>,
private val givenSimpleName: String,
override val simpleName: String,
private val isInstanceFunction: (Any?) -> Boolean
) : KClassImpl<T>() {

Expand All @@ -56,13 +56,6 @@ internal class PrimitiveKClassImpl<T : Any>(
override val isInterface: Boolean
get() = false

override fun equals(other: Any?): Boolean {
if (other !is PrimitiveKClassImpl<*>) return false
return super.equals(other) && givenSimpleName == other.givenSimpleName
}

override val simpleName: String? get() = givenSimpleName

override fun isInstance(value: Any?): Boolean {
return isInstanceFunction(value)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,26 +5,29 @@

package org.jetbrains.kotlin.konan.test.blackbox

import org.jetbrains.kotlin.konan.test.blackbox.support.settings.ExternalSourceTransformersProvider
import org.jetbrains.kotlin.konan.test.blackbox.support.util.ExternalSourceTransformer
import org.jetbrains.kotlin.konan.test.blackbox.support.util.ExternalSourceTransformers
import org.jetbrains.kotlin.test.TargetBackend
import org.jetbrains.kotlin.test.directives.ConfigurationDirectives.WORKS_WHEN_VALUE_CLASS
import org.jetbrains.kotlin.test.preprocessors.JvmInlineSourceTransformer
import org.jetbrains.kotlin.test.utils.ReplacingSourceTransformer
import org.junit.jupiter.api.Tag
import java.io.File

@Tag("codegen")
abstract class AbstractNativeCodegenBoxTest : AbstractNativeBlackBoxTest() {
override fun getSourceTransformers(testDataFile: File): ExternalSourceTransformers? {
val needTransform = "// $WORKS_WHEN_VALUE_CLASS" in testDataFile.readText()
val transformer = object : ExternalSourceTransformer {
val jvmInlineTransformer = object : ExternalSourceTransformer {
override fun invoke(content: String): String {
if (!needTransform) return content
val contentModifier = JvmInlineSourceTransformer.computeModifier(TargetBackend.NATIVE)
return contentModifier.invoke(content)
}
}
return listOf(transformer)
return listOf(
jvmInlineTransformer,
ReplacingSourceTransformer("BACKEND_UNDER_TEST", "\"NATIVE\""),
)
}
}
Loading