KT-4107 Don't generate readResolve for data objects
This commit is contained in:
committed by
Space Team
parent
ea346e3e0e
commit
f96d41e414
-16
@@ -84,22 +84,6 @@ public class FirOldDiagnosticsTestWithJvmIrBackendGenerated extends AbstractFirD
|
|||||||
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle_ir.kt");
|
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle_ir.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nested
|
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects")
|
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
|
||||||
public class DataObjects {
|
|
||||||
@Test
|
|
||||||
public void testAllFilesPresentInDataObjects() throws Exception {
|
|
||||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
@TestMetadata("customReadResolve.kt")
|
|
||||||
public void testCustomReadResolve() throws Exception {
|
|
||||||
runTest("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects/customReadResolve.kt");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Nested
|
@Nested
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
|||||||
@@ -356,7 +356,6 @@ private val jvmFilePhases = listOf(
|
|||||||
enumClassPhase,
|
enumClassPhase,
|
||||||
enumExternalEntriesPhase,
|
enumExternalEntriesPhase,
|
||||||
objectClassPhase,
|
objectClassPhase,
|
||||||
readResolveForDataObjectsPhase,
|
|
||||||
staticInitializersPhase,
|
staticInitializersPhase,
|
||||||
uniqueLoopLabelsPhase,
|
uniqueLoopLabelsPhase,
|
||||||
initializersPhase,
|
initializersPhase,
|
||||||
|
|||||||
-63
@@ -1,63 +0,0 @@
|
|||||||
/*
|
|
||||||
* 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.backend.jvm.lower
|
|
||||||
|
|
||||||
import org.jetbrains.kotlin.backend.common.ClassLoweringPass
|
|
||||||
import org.jetbrains.kotlin.backend.common.ir.addDispatchReceiver
|
|
||||||
import org.jetbrains.kotlin.backend.common.phaser.makeIrFilePhase
|
|
||||||
import org.jetbrains.kotlin.backend.jvm.JvmBackendContext
|
|
||||||
import org.jetbrains.kotlin.backend.jvm.ir.createJvmIrBuilder
|
|
||||||
import org.jetbrains.kotlin.config.LanguageFeature
|
|
||||||
import org.jetbrains.kotlin.descriptors.ClassKind
|
|
||||||
import org.jetbrains.kotlin.descriptors.DescriptorVisibilities
|
|
||||||
import org.jetbrains.kotlin.descriptors.Modality
|
|
||||||
import org.jetbrains.kotlin.ir.builders.declarations.buildFun
|
|
||||||
import org.jetbrains.kotlin.ir.builders.irExprBody
|
|
||||||
import org.jetbrains.kotlin.ir.builders.irGetField
|
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrClass
|
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrDeclarationOrigin
|
|
||||||
import org.jetbrains.kotlin.ir.util.defaultType
|
|
||||||
import org.jetbrains.kotlin.ir.util.fields
|
|
||||||
import org.jetbrains.kotlin.ir.util.getAllSuperclasses
|
|
||||||
import org.jetbrains.kotlin.ir.util.hasEqualFqName
|
|
||||||
import org.jetbrains.kotlin.load.java.JvmAbi
|
|
||||||
import org.jetbrains.kotlin.name.FqName
|
|
||||||
import org.jetbrains.kotlin.name.Name
|
|
||||||
|
|
||||||
internal val readResolveForDataObjectsPhase = makeIrFilePhase(
|
|
||||||
::ReadResolveForDataObjectsLowering,
|
|
||||||
name = "ReadResolveForDataObjectsLowering",
|
|
||||||
description = "Generate readResolve for serializable data objects"
|
|
||||||
)
|
|
||||||
|
|
||||||
private class ReadResolveForDataObjectsLowering(val context: JvmBackendContext) : ClassLoweringPass {
|
|
||||||
override fun lower(irClass: IrClass) {
|
|
||||||
if (!context.state.languageVersionSettings.supportsFeature(LanguageFeature.DataObjects)) return
|
|
||||||
|
|
||||||
if (!irClass.isData || irClass.kind != ClassKind.OBJECT || !irClass.isSerializable()) return
|
|
||||||
|
|
||||||
context.irFactory.buildFun {
|
|
||||||
name = Name.identifier("readResolve")
|
|
||||||
modality = Modality.FINAL
|
|
||||||
origin = IrDeclarationOrigin.GENERATED_DATA_CLASS_MEMBER
|
|
||||||
returnType = context.irBuiltIns.anyType
|
|
||||||
visibility = DescriptorVisibilities.PRIVATE
|
|
||||||
}.apply {
|
|
||||||
addDispatchReceiver { type = irClass.defaultType }
|
|
||||||
parent = irClass
|
|
||||||
body = context.createJvmIrBuilder(symbol).run {
|
|
||||||
val instanceField = irClass.fields.single { it.name.asString() == JvmAbi.INSTANCE_FIELD }
|
|
||||||
irExprBody(irGetField(null, instanceField))
|
|
||||||
}
|
|
||||||
irClass.declarations.add(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private val SERIALIZABLE_FQ_NAME = FqName("java.io.Serializable")
|
|
||||||
|
|
||||||
private fun IrClass.isSerializable(): Boolean =
|
|
||||||
getAllSuperclasses().any { it.hasEqualFqName(SERIALIZABLE_FQ_NAME) }
|
|
||||||
@@ -6,6 +6,7 @@
|
|||||||
// FIR_IDENTICAL
|
// FIR_IDENTICAL
|
||||||
|
|
||||||
import java.io.*
|
import java.io.*
|
||||||
|
import kotlin.test.*
|
||||||
|
|
||||||
data object NonSerializableDataObject
|
data object NonSerializableDataObject
|
||||||
|
|
||||||
@@ -14,7 +15,11 @@ data object SerializableDataObject: Serializable
|
|||||||
fun box(): String {
|
fun box(): String {
|
||||||
ByteArrayOutputStream().use { baos ->
|
ByteArrayOutputStream().use { baos ->
|
||||||
ObjectOutputStream(baos).use { oos -> oos.writeObject(SerializableDataObject) }
|
ObjectOutputStream(baos).use { oos -> oos.writeObject(SerializableDataObject) }
|
||||||
ByteArrayInputStream(baos.toByteArray()).use { bais -> assert(java.io.ObjectInputStream(bais).readObject() === SerializableDataObject) }
|
ByteArrayInputStream(baos.toByteArray()).use { bais ->
|
||||||
|
val deseialized = ObjectInputStream(bais).readObject()
|
||||||
|
assertEquals(SerializableDataObject, deseialized)
|
||||||
|
assertNotSame(deseialized, SerializableDataObject)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return "OK"
|
return "OK"
|
||||||
}
|
}
|
||||||
@@ -17,7 +17,6 @@ public final class SerializableDataObject {
|
|||||||
private method <init>(): void
|
private method <init>(): void
|
||||||
public method equals(@org.jetbrains.annotations.Nullable p0: java.lang.Object): boolean
|
public method equals(@org.jetbrains.annotations.Nullable p0: java.lang.Object): boolean
|
||||||
public method hashCode(): int
|
public method hashCode(): int
|
||||||
private final method readResolve(): java.lang.Object
|
|
||||||
public @org.jetbrains.annotations.NotNull method toString(): java.lang.String
|
public @org.jetbrains.annotations.NotNull method toString(): java.lang.String
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
-17
@@ -1,17 +0,0 @@
|
|||||||
// FIR_IDENTICAL
|
|
||||||
// !LANGUAGE: +DataObjects
|
|
||||||
// TARGET_BACKEND: JVM_IR
|
|
||||||
|
|
||||||
import java.io.Serializable
|
|
||||||
|
|
||||||
data <!CONFLICTING_JVM_DECLARATIONS!>object A<!> : Serializable {
|
|
||||||
<!CONFLICTING_JVM_DECLARATIONS!>private fun readResolve(): Any<!> = this
|
|
||||||
}
|
|
||||||
|
|
||||||
data object B : Serializable {
|
|
||||||
private fun readResolve(): B = this
|
|
||||||
}
|
|
||||||
|
|
||||||
data object C {
|
|
||||||
private fun readResolve(): Any = this
|
|
||||||
}
|
|
||||||
-26
@@ -1,26 +0,0 @@
|
|||||||
package
|
|
||||||
|
|
||||||
public data object A : java.io.Serializable {
|
|
||||||
private constructor A()
|
|
||||||
public open override /*1*/ /*synthesized*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
|
||||||
public open override /*1*/ /*synthesized*/ fun hashCode(): kotlin.Int
|
|
||||||
private final fun readResolve(): kotlin.Any
|
|
||||||
public open override /*1*/ /*synthesized*/ fun toString(): kotlin.String
|
|
||||||
}
|
|
||||||
|
|
||||||
public data object B : java.io.Serializable {
|
|
||||||
private constructor B()
|
|
||||||
public open override /*1*/ /*synthesized*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
|
||||||
public open override /*1*/ /*synthesized*/ fun hashCode(): kotlin.Int
|
|
||||||
private final fun readResolve(): B
|
|
||||||
public open override /*1*/ /*synthesized*/ fun toString(): kotlin.String
|
|
||||||
}
|
|
||||||
|
|
||||||
public data object C {
|
|
||||||
private constructor C()
|
|
||||||
public open override /*1*/ /*synthesized*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
|
||||||
public open override /*1*/ /*synthesized*/ fun hashCode(): kotlin.Int
|
|
||||||
private final fun readResolve(): kotlin.Any
|
|
||||||
public open override /*1*/ /*synthesized*/ fun toString(): kotlin.String
|
|
||||||
}
|
|
||||||
|
|
||||||
-16
@@ -61,22 +61,6 @@ public class DiagnosticsTestWithJvmIrBackendGenerated extends AbstractDiagnostic
|
|||||||
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle_ir.kt");
|
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle_ir.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nested
|
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects")
|
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
|
||||||
public class DataObjects {
|
|
||||||
@Test
|
|
||||||
public void testAllFilesPresentInDataObjects() throws Exception {
|
|
||||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects"), Pattern.compile("^(.+)\\.kts?$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), TargetBackend.JVM_IR, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
@TestMetadata("customReadResolve.kt")
|
|
||||||
public void testCustomReadResolve() throws Exception {
|
|
||||||
runTest("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects/customReadResolve.kt");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Nested
|
@Nested
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
|||||||
-10
@@ -61,16 +61,6 @@ public class DiagnosticsTestWithOldJvmBackendGenerated extends AbstractDiagnosti
|
|||||||
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle.kt");
|
runTest("compiler/testData/diagnostics/testsWithJvmBackend/suspendInlineCycle.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nested
|
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects")
|
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
|
||||||
public class DataObjects {
|
|
||||||
@Test
|
|
||||||
public void testAllFilesPresentInDataObjects() throws Exception {
|
|
||||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/testsWithJvmBackend/dataObjects"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), TargetBackend.JVM_OLD, true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Nested
|
@Nested
|
||||||
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
@TestMetadata("compiler/testData/diagnostics/testsWithJvmBackend/duplicateJvmSignature")
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
|||||||
Reference in New Issue
Block a user