[JS IR BE] fix default arguments lowering
This commit is contained in:
@@ -171,6 +171,7 @@ fun IrValueParameter.copyTo(
|
||||
).also {
|
||||
descriptor.bind(it)
|
||||
it.parent = irFunction
|
||||
it.defaultValue = defaultValue
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+114
-94
@@ -50,7 +50,6 @@ open class DefaultArgumentStubGenerator constructor(val context: CommonBackendCo
|
||||
else
|
||||
null
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private val symbols = context.ir.symbols
|
||||
@@ -64,91 +63,91 @@ open class DefaultArgumentStubGenerator constructor(val context: CommonBackendCo
|
||||
|
||||
log { "detected ${irFunction.name.asString()} has got #${bodies.size} default expressions" }
|
||||
|
||||
if (bodies.isNotEmpty()) {
|
||||
|
||||
val newIrFunction = irFunction.generateDefaultsFunction(context)
|
||||
newIrFunction.parent = irFunction.parent
|
||||
|
||||
log { "$irFunction -> $newIrFunction" }
|
||||
val builder = context.createIrBuilder(newIrFunction.symbol)
|
||||
|
||||
newIrFunction.body = builder.irBlockBody(newIrFunction) {
|
||||
val params = mutableListOf<IrVariable>()
|
||||
val variables = mutableMapOf<IrValueDeclaration, IrValueDeclaration>()
|
||||
|
||||
irFunction.dispatchReceiverParameter?.let {
|
||||
variables[it] = newIrFunction.dispatchReceiverParameter!!
|
||||
}
|
||||
|
||||
irFunction.extensionReceiverParameter?.let {
|
||||
variables[it] = newIrFunction.extensionReceiverParameter!!
|
||||
}
|
||||
|
||||
for (valueParameter in irFunction.valueParameters) {
|
||||
val parameter = newIrFunction.valueParameters[valueParameter.index]
|
||||
|
||||
val argument = if (valueParameter.defaultValue != null) {
|
||||
val kIntAnd = symbols.intAnd.owner
|
||||
val condition = irNotEquals(irCall(kIntAnd).apply {
|
||||
dispatchReceiver = irGet(maskParameter(newIrFunction, valueParameter.index / 32))
|
||||
putValueArgument(0, irInt(1 shl (valueParameter.index % 32)))
|
||||
}, irInt(0))
|
||||
|
||||
val expressionBody = valueParameter.defaultValue!!
|
||||
|
||||
expressionBody.transformChildrenVoid(object : IrElementTransformerVoid() {
|
||||
override fun visitGetValue(expression: IrGetValue): IrExpression {
|
||||
log { "GetValue: ${expression.symbol.owner}" }
|
||||
val valueSymbol = variables[expression.symbol.owner] ?: return expression
|
||||
return irGet(valueSymbol)
|
||||
}
|
||||
})
|
||||
|
||||
irIfThenElse(
|
||||
type = parameter.type,
|
||||
condition = condition,
|
||||
thenPart = expressionBody.expression,
|
||||
elsePart = irGet(parameter)
|
||||
)
|
||||
} else {
|
||||
irGet(parameter)
|
||||
}
|
||||
|
||||
val temporaryVariable = irTemporary(argument, nameHint = parameter.name.asString())
|
||||
|
||||
params.add(temporaryVariable)
|
||||
variables[valueParameter] = temporaryVariable
|
||||
}
|
||||
|
||||
if (irFunction is IrConstructor) {
|
||||
+IrDelegatingConstructorCallImpl(
|
||||
startOffset = irFunction.startOffset,
|
||||
endOffset = irFunction.endOffset,
|
||||
type = context.irBuiltIns.unitType,
|
||||
symbol = irFunction.symbol, descriptor = irFunction.symbol.descriptor,
|
||||
typeArgumentsCount = irFunction.typeParameters.size
|
||||
).apply {
|
||||
dispatchReceiver = newIrFunction.dispatchReceiverParameter?.let { irGet(it) }
|
||||
|
||||
params.forEachIndexed { i, variable -> putValueArgument(i, irGet(variable)) }
|
||||
}
|
||||
} else {
|
||||
+irReturn(irCall(irFunction).apply {
|
||||
dispatchReceiver = newIrFunction.dispatchReceiverParameter?.let { irGet(it) }
|
||||
extensionReceiver = newIrFunction.extensionReceiverParameter?.let { irGet(it) }
|
||||
|
||||
params.forEachIndexed { i, variable -> putValueArgument(i, irGet(variable)) }
|
||||
})
|
||||
}
|
||||
}
|
||||
// Remove default argument initializers.
|
||||
irFunction.valueParameters.forEach {
|
||||
it.defaultValue = IrExpressionBodyImpl(IrErrorExpressionImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, it.type, "Default Stub"))
|
||||
}
|
||||
|
||||
if (bodies.isEmpty()) {
|
||||
// Fake override
|
||||
val newIrFunction = irFunction.generateDefaultsFunction(context, IrDeclarationOrigin.FAKE_OVERRIDE)
|
||||
return listOf(irFunction, newIrFunction)
|
||||
}
|
||||
return listOf(irFunction)
|
||||
|
||||
val newIrFunction = irFunction.generateDefaultsFunction(context, DECLARATION_ORIGIN_FUNCTION_FOR_DEFAULT_PARAMETER)
|
||||
|
||||
log { "$irFunction -> $newIrFunction" }
|
||||
val builder = context.createIrBuilder(newIrFunction.symbol)
|
||||
|
||||
newIrFunction.body = builder.irBlockBody(newIrFunction) {
|
||||
val params = mutableListOf<IrVariable>()
|
||||
val variables = mutableMapOf<IrValueDeclaration, IrValueDeclaration>()
|
||||
|
||||
irFunction.dispatchReceiverParameter?.let {
|
||||
variables[it] = newIrFunction.dispatchReceiverParameter!!
|
||||
}
|
||||
|
||||
irFunction.extensionReceiverParameter?.let {
|
||||
variables[it] = newIrFunction.extensionReceiverParameter!!
|
||||
}
|
||||
|
||||
for (valueParameter in irFunction.valueParameters) {
|
||||
val parameter = newIrFunction.valueParameters[valueParameter.index]
|
||||
|
||||
val argument = if (valueParameter.defaultValue != null) {
|
||||
val kIntAnd = symbols.intAnd.owner
|
||||
val condition = irNotEquals(irCall(kIntAnd).apply {
|
||||
dispatchReceiver = irGet(maskParameter(newIrFunction, valueParameter.index / 32))
|
||||
putValueArgument(0, irInt(1 shl (valueParameter.index % 32)))
|
||||
}, irInt(0))
|
||||
|
||||
val expressionBody = valueParameter.defaultValue!!
|
||||
|
||||
expressionBody.transformChildrenVoid(object : IrElementTransformerVoid() {
|
||||
override fun visitGetValue(expression: IrGetValue): IrExpression {
|
||||
log { "GetValue: ${expression.symbol.owner}" }
|
||||
val valueSymbol = variables[expression.symbol.owner] ?: return expression
|
||||
return irGet(valueSymbol)
|
||||
}
|
||||
})
|
||||
|
||||
irIfThenElse(
|
||||
type = parameter.type,
|
||||
condition = condition,
|
||||
thenPart = expressionBody.expression,
|
||||
elsePart = irGet(parameter)
|
||||
)
|
||||
} else {
|
||||
irGet(parameter)
|
||||
}
|
||||
|
||||
val temporaryVariable = irTemporary(argument, nameHint = parameter.name.asString())
|
||||
|
||||
params.add(temporaryVariable)
|
||||
variables[valueParameter] = temporaryVariable
|
||||
}
|
||||
|
||||
if (irFunction is IrConstructor) {
|
||||
+IrDelegatingConstructorCallImpl(
|
||||
startOffset = irFunction.startOffset,
|
||||
endOffset = irFunction.endOffset,
|
||||
type = context.irBuiltIns.unitType,
|
||||
symbol = irFunction.symbol, descriptor = irFunction.symbol.descriptor,
|
||||
typeArgumentsCount = irFunction.typeParameters.size
|
||||
).apply {
|
||||
dispatchReceiver = newIrFunction.dispatchReceiverParameter?.let { irGet(it) }
|
||||
|
||||
params.forEachIndexed { i, variable -> putValueArgument(i, irGet(variable)) }
|
||||
}
|
||||
} else {
|
||||
+irReturn(irCall(irFunction).apply {
|
||||
dispatchReceiver = newIrFunction.dispatchReceiverParameter?.let { irGet(it) }
|
||||
extensionReceiver = newIrFunction.extensionReceiverParameter?.let { irGet(it) }
|
||||
|
||||
params.forEachIndexed { i, variable -> putValueArgument(i, irGet(variable)) }
|
||||
})
|
||||
}
|
||||
}
|
||||
// Remove default argument initializers.
|
||||
irFunction.valueParameters.forEach {
|
||||
it.defaultValue = IrExpressionBodyImpl(IrErrorExpressionImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, it.type, "Default Stub"))
|
||||
}
|
||||
return listOf(irFunction, newIrFunction)
|
||||
}
|
||||
|
||||
|
||||
@@ -164,6 +163,23 @@ private fun maskParameter(function: IrFunction, number: Int) =
|
||||
private fun markerParameterDeclaration(function: IrFunction) =
|
||||
function.valueParameters.single { it.name == kConstructorMarkerName }
|
||||
|
||||
// Populates `overriddenSymbols` for the newly created functions
|
||||
class DefaultParameterFakeOverrideCleanup(val context: CommonBackendContext): DeclarationContainerLoweringPass {
|
||||
override fun lower(irDeclarationContainer: IrDeclarationContainer) {
|
||||
for (func in irDeclarationContainer.declarations) {
|
||||
if (func !is IrSimpleFunction) continue
|
||||
|
||||
val defFunc = context.ir.defaultParameterDeclarationsCache[func] as? IrSimpleFunction ?: continue
|
||||
|
||||
for (o in func.overriddenSymbols) {
|
||||
(context.ir.defaultParameterDeclarationsCache[o.owner] as? IrSimpleFunction)?.let {
|
||||
defFunc.overriddenSymbols.add(it.symbol)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
open class DefaultParameterInjector constructor(
|
||||
val context: CommonBackendContext,
|
||||
private val skipInline: Boolean = true
|
||||
@@ -264,9 +280,7 @@ open class DefaultParameterInjector constructor(
|
||||
val declaration = expression.symbol.owner
|
||||
|
||||
val keyFunction = declaration.findSuperMethodWithDefaultArguments()!!
|
||||
val realFunction = keyFunction.generateDefaultsFunction(context)
|
||||
|
||||
realFunction.parent = keyFunction.parent
|
||||
val realFunction = keyFunction.generateDefaultsFunction(context, DECLARATION_ORIGIN_FUNCTION_FOR_DEFAULT_PARAMETER)
|
||||
|
||||
log { "$declaration -> $realFunction" }
|
||||
val maskValues = Array((declaration.valueParameters.size + 31) / 32) { 0 }
|
||||
@@ -343,6 +357,7 @@ class DefaultParameterCleaner constructor(val context: CommonBackendContext) : F
|
||||
}
|
||||
}
|
||||
|
||||
// TODO this implementation is exponential
|
||||
private fun IrFunction.needsDefaultArgumentsLowering(skipInlineMethods: Boolean): Boolean {
|
||||
if (isInline && skipInlineMethods) return false
|
||||
if (valueParameters.any { it.defaultValue != null }) return true
|
||||
@@ -352,8 +367,8 @@ private fun IrFunction.needsDefaultArgumentsLowering(skipInlineMethods: Boolean)
|
||||
return overriddenSymbols.any { it.owner.needsDefaultArgumentsLowering(skipInlineMethods) }
|
||||
}
|
||||
|
||||
private fun IrFunction.generateDefaultsFunctionImpl(context: CommonBackendContext): IrFunction {
|
||||
val newFunction = buildFunctionDeclaration(this)
|
||||
private fun IrFunction.generateDefaultsFunctionImpl(context: CommonBackendContext, origin: IrDeclarationOrigin): IrFunction {
|
||||
val newFunction = buildFunctionDeclaration(this, origin)
|
||||
|
||||
val syntheticParameters = MutableList((valueParameters.size + 31) / 32) { i ->
|
||||
valueParameter(valueParameters.size + i, parameterMaskName(i), context.irBuiltIns.intType)
|
||||
@@ -375,6 +390,9 @@ private fun IrFunction.generateDefaultsFunctionImpl(context: CommonBackendContex
|
||||
|
||||
newFunction.copyTypeParametersFrom(this)
|
||||
val newValueParameters = valueParameters.map { it.copyTo(newFunction) } + syntheticParameters
|
||||
newValueParameters.forEach {
|
||||
it.defaultValue = null
|
||||
}
|
||||
|
||||
newFunction.returnType = returnType
|
||||
newFunction.dispatchReceiverParameter = dispatchReceiverParameter?.run {
|
||||
@@ -385,17 +403,19 @@ private fun IrFunction.generateDefaultsFunctionImpl(context: CommonBackendContex
|
||||
|
||||
annotations.mapTo(newFunction.annotations) { it.deepCopyWithSymbols() }
|
||||
|
||||
newFunction.parent = parent
|
||||
|
||||
return newFunction
|
||||
}
|
||||
|
||||
private fun buildFunctionDeclaration(irFunction: IrFunction): IrFunction {
|
||||
private fun buildFunctionDeclaration(irFunction: IrFunction, origin: IrDeclarationOrigin): IrFunction {
|
||||
when (irFunction) {
|
||||
is IrConstructor -> {
|
||||
val descriptor = WrappedClassConstructorDescriptor(irFunction.descriptor.annotations, irFunction.descriptor.source)
|
||||
return IrConstructorImpl(
|
||||
irFunction.startOffset,
|
||||
irFunction.endOffset,
|
||||
DECLARATION_ORIGIN_FUNCTION_FOR_DEFAULT_PARAMETER,
|
||||
origin,
|
||||
IrConstructorSymbolImpl(descriptor),
|
||||
irFunction.name,
|
||||
irFunction.visibility,
|
||||
@@ -414,7 +434,7 @@ private fun buildFunctionDeclaration(irFunction: IrFunction): IrFunction {
|
||||
return IrFunctionImpl(
|
||||
irFunction.startOffset,
|
||||
irFunction.endOffset,
|
||||
DECLARATION_ORIGIN_FUNCTION_FOR_DEFAULT_PARAMETER,
|
||||
origin,
|
||||
IrSimpleFunctionSymbolImpl(descriptor),
|
||||
name,
|
||||
irFunction.visibility,
|
||||
@@ -432,9 +452,9 @@ private fun buildFunctionDeclaration(irFunction: IrFunction): IrFunction {
|
||||
}
|
||||
}
|
||||
|
||||
private fun IrFunction.generateDefaultsFunction(context: CommonBackendContext): IrFunction =
|
||||
private fun IrFunction.generateDefaultsFunction(context: CommonBackendContext, origin: IrDeclarationOrigin): IrFunction =
|
||||
context.ir.defaultParameterDeclarationsCache.getOrPut(this) {
|
||||
generateDefaultsFunctionImpl(context)
|
||||
generateDefaultsFunctionImpl(context, origin)
|
||||
}
|
||||
|
||||
object DECLARATION_ORIGIN_FUNCTION_FOR_DEFAULT_PARAMETER :
|
||||
|
||||
@@ -107,6 +107,7 @@ private fun JsIrBackendContext.lower(moduleFragment: IrModuleFragment, dependenc
|
||||
VarargLowering(this).lower(moduleFragment)
|
||||
LateinitLowering(this, true).lower(moduleFragment)
|
||||
DefaultArgumentStubGenerator(this).runOnFilesPostfix(moduleFragment)
|
||||
DefaultParameterFakeOverrideCleanup(this).runOnFilesPostfix(moduleFragment)
|
||||
DefaultParameterInjector(this).runOnFilesPostfix(moduleFragment)
|
||||
DefaultParameterCleaner(this).runOnFilesPostfix(moduleFragment)
|
||||
SharedVariablesLowering(this).runOnFilesPostfix(moduleFragment)
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class A(val a: Int = 1) {
|
||||
FIRST(),
|
||||
SECOND(2)
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class Foo(val a: Int = 1, val b: String) {
|
||||
B(2, "b"),
|
||||
C(b = "b")
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class Foo(val a: Int = 1, val b: String = "a") {
|
||||
A(),
|
||||
B(2, "b"),
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class Foo(val a: Double = 1.0, val b: Double = 1.0) {
|
||||
A(),
|
||||
B(2.0, 2.0),
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// See KT-21968
|
||||
|
||||
interface A {
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface Foo {
|
||||
fun foo(a: Double = 1.0): Double
|
||||
}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// IGNORE_BACKEND: JVM
|
||||
// See KT-15971
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface A {
|
||||
fun visit(a:String, b:String="") : String = b + a
|
||||
}
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface Base {
|
||||
fun bar(a: String = "abc"): String = a + " from interface"
|
||||
}
|
||||
|
||||
Vendored
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface I {
|
||||
fun foo(x: Int = 23): String
|
||||
}
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface FooTrait<T> {
|
||||
fun make(size: Int = 16) : T
|
||||
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// IGNORE_BACKEND: JVM
|
||||
|
||||
var log = ""
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class Test(val str: String = "OK") {
|
||||
OK
|
||||
}
|
||||
|
||||
Vendored
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class Test(val str: String = "OK") {
|
||||
OK {
|
||||
fun foo() {}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
enum class ClassTemplate(
|
||||
// var bug: Int = 1,
|
||||
var code: Int,
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface A {
|
||||
fun bar2(arg: Int = 239) : Int
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface A {
|
||||
fun foo(x: Int, y: Int = x + 20, z: Int = y * 2) = z
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
// !LANGUAGE: +InlineClasses
|
||||
// IGNORE_BACKEND: JVM_IR, JS_IR
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
|
||||
inline class Z(val z: Int)
|
||||
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
// !LANGUAGE: +InlineClasses
|
||||
// IGNORE_BACKEND: JVM_IR, JS_IR
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// WITH_RUNTIME
|
||||
|
||||
inline class Ucn(private val i: UInt)
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
// !LANGUAGE: +MultiPlatformProjects
|
||||
// IGNORE_BACKEND: JVM_IR, JS_IR, NATIVE
|
||||
// IGNORE_BACKEND: JVM_IR, NATIVE
|
||||
// FILE: common.kt
|
||||
|
||||
expect interface I {
|
||||
|
||||
-1
@@ -1,6 +1,5 @@
|
||||
// !LANGUAGE: +MultiPlatformProjects
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// IGNORE_BACKEND: JVM
|
||||
|
||||
// FILE: lib.kt
|
||||
|
||||
Vendored
-1
@@ -1,6 +1,5 @@
|
||||
// !LANGUAGE: +MultiPlatformProjects
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
|
||||
// FILE: lib.kt
|
||||
expect interface I {
|
||||
|
||||
-1
@@ -1,6 +1,5 @@
|
||||
// !LANGUAGE: +MultiPlatformProjects
|
||||
// IGNORE_BACKEND: JVM_IR
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
|
||||
// FILE: lib.kt
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface I {
|
||||
fun foo(): String = "foo"
|
||||
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
interface I<T> {
|
||||
fun foo(x: T): String = "foo($x)"
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1294
|
||||
package foo
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1291
|
||||
package foo
|
||||
|
||||
@@ -7,9 +6,14 @@ enum class A(val a: Int = 1) {
|
||||
SECOND(2)
|
||||
}
|
||||
|
||||
class B(val a: Int = 1)
|
||||
|
||||
fun box(): String {
|
||||
if (A.FIRST.a == 1 && A.SECOND.a == 2) {
|
||||
return "OK"
|
||||
}
|
||||
|
||||
B()
|
||||
|
||||
return "fail"
|
||||
}
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1291
|
||||
package foo
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1295
|
||||
package foo
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1270
|
||||
// FILE: classes.kt
|
||||
class C : J
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1304
|
||||
interface I {
|
||||
fun foo(x: String = "default"): String = "I.foo($x)"
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1299
|
||||
package foo
|
||||
|
||||
|
||||
-1
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1282
|
||||
// MODULE: lib
|
||||
// FILE: lib.kt
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1284
|
||||
// MODULE: lib
|
||||
// FILE: lib.kt
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
// IGNORE_BACKEND: JS_IR
|
||||
// EXPECTED_REACHABLE_NODES: 1281
|
||||
// FILE: a.kt
|
||||
fun foo(n: Int): String = js("""
|
||||
|
||||
Reference in New Issue
Block a user