JvmDefault. Support 'JvmDefaultWithCompatibility' annotation in old backend

#KT-48217
This commit is contained in:
Mikhael Bogdanov
2021-12-07 08:11:21 +01:00
committed by Space
parent 1471602c9f
commit bdeae7668e
13 changed files with 287 additions and 15 deletions
@@ -719,8 +719,14 @@ public class FunctionCodegen {
@NotNull JvmDefaultMode jvmDefaultMode
) {
return OwnerKind.DEFAULT_IMPLS == context.getContextKind() &&
jvmDefaultMode.isCompatibility() &&
JvmAnnotationUtilKt.checkIsImplementationCompiledToJvmDefault(functionDescriptor, jvmDefaultMode);
isCompiledInCompatibilityMode(jvmDefaultMode, functionDescriptor) &&
JvmAnnotationUtilKt.checkIsImplementationCompiledToJvmDefault(functionDescriptor, jvmDefaultMode);
}
private static boolean isCompiledInCompatibilityMode(JvmDefaultMode mode, CallableMemberDescriptor descriptor) {
return mode.isCompatibility() ||
(mode == JvmDefaultMode.ALL_INCOMPATIBLE &&
JvmAnnotationUtilKt.hasJvmDefaultWithCompatibilityAnnotation(descriptor.getContainingDeclaration()));
}
private static void generateLocalVariableTable(
@@ -1683,11 +1689,12 @@ public class FunctionCodegen {
// Fake overrides in interfaces should be expanded to implementation to make proper default check
if (JvmAnnotationUtilKt.checkIsImplementationCompiledToJvmDefault(memberDescriptor, mode)) {
boolean isSyntheticInCompatibilityOrJvmDefault = isSynthetic && (mode.isCompatibility() || mode == JvmDefaultMode.ENABLE);
boolean isCompatibilityMode = isCompiledInCompatibilityMode(mode, memberDescriptor);
boolean isSyntheticInCompatibilityOrJvmDefault = isSynthetic && (isCompatibilityMode || mode == JvmDefaultMode.ENABLE);
return (kind != OwnerKind.DEFAULT_IMPLS && !isSyntheticInCompatibilityOrJvmDefault) ||
(kind == OwnerKind.DEFAULT_IMPLS &&
(isSyntheticInCompatibilityOrJvmDefault ||
(mode.isCompatibility() && !JvmAnnotationUtilKt.hasJvmDefaultNoCompatibilityAnnotation(containingDeclaration))) && !DescriptorVisibilities.isPrivate(memberDescriptor.getVisibility()));
(isCompatibilityMode && !JvmAnnotationUtilKt.hasJvmDefaultNoCompatibilityAnnotation(containingDeclaration))) && !DescriptorVisibilities.isPrivate(memberDescriptor.getVisibility()));
} else {
switch (kind) {
case DEFAULT_IMPLS: return true;
@@ -25803,11 +25803,29 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/defaultArgs.kt");
}
@Test
@TestMetadata("differentCases.kt")
public void testDifferentCases() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/differentCases.kt");
}
@Test
@TestMetadata("propertyAnnotation.kt")
public void testPropertyAnnotation() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/propertyAnnotation.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/simple.kt");
}
@Test
@TestMetadata("suspend.kt")
public void testSuspend() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/suspend.kt");
}
}
}
@@ -1,9 +1,7 @@
// !JVM_DEFAULT_MODE: all
// TARGET_BACKEND: JVM
// IGNORE_BACKEND: JVM
// JVM_TARGET: 1.8
// WITH_RUNTIME
// FULL_JDK
// CHECK_BYTECODE_LISTING
@JvmDefaultWithCompatibility
@@ -0,0 +1,26 @@
// !JVM_DEFAULT_MODE: all
// TARGET_BACKEND: JVM
// JVM_TARGET: 1.8
// WITH_RUNTIME
// CHECK_BYTECODE_LISTING
@JvmDefaultWithCompatibility
interface Test {
fun test(): String = privateFun()
private fun privateFun() = "O"
val prop: String
get() = "K"
var varProp: String
get() = "K"
set(value) {}
}
class TestClass : Test
fun box(): String {
val testClass = TestClass()
return testClass.test() + testClass.varProp
}
@@ -0,0 +1,37 @@
@kotlin.Metadata
public final class DifferentCasesKt {
// source: 'differentCases.kt'
public final static @org.jetbrains.annotations.NotNull method box(): java.lang.String
}
@kotlin.Metadata
public final class Test$DefaultImpls {
// source: 'differentCases.kt'
public deprecated static @java.lang.Deprecated @org.jetbrains.annotations.NotNull method getProp(@org.jetbrains.annotations.NotNull p0: Test): java.lang.String
public deprecated static @java.lang.Deprecated @org.jetbrains.annotations.NotNull method getVarProp(@org.jetbrains.annotations.NotNull p0: Test): java.lang.String
public deprecated static @java.lang.Deprecated method setVarProp(@org.jetbrains.annotations.NotNull p0: Test, @org.jetbrains.annotations.NotNull p1: java.lang.String): void
public deprecated static @java.lang.Deprecated @org.jetbrains.annotations.NotNull method test(@org.jetbrains.annotations.NotNull p0: Test): java.lang.String
public final inner class Test$DefaultImpls
}
@kotlin.jvm.JvmDefaultWithCompatibility
@kotlin.Metadata
public interface Test {
// source: 'differentCases.kt'
public synthetic static method access$getProp$jd(p0: Test): java.lang.String
public synthetic static method access$getVarProp$jd(p0: Test): java.lang.String
public synthetic static method access$setVarProp$jd(p0: Test, p1: java.lang.String): void
public synthetic static method access$test$jd(p0: Test): java.lang.String
public @org.jetbrains.annotations.NotNull method getProp(): java.lang.String
public @org.jetbrains.annotations.NotNull method getVarProp(): java.lang.String
private method privateFun(): java.lang.String
public method setVarProp(@org.jetbrains.annotations.NotNull p0: java.lang.String): void
public @org.jetbrains.annotations.NotNull method test(): java.lang.String
public final inner class Test$DefaultImpls
}
@kotlin.Metadata
public final class TestClass {
// source: 'differentCases.kt'
public method <init>(): void
}
@@ -0,0 +1,21 @@
// !JVM_DEFAULT_MODE: all
// TARGET_BACKEND: JVM
// JVM_TARGET: 1.8
// WITH_RUNTIME
// CHECK_BYTECODE_LISTING
annotation class MyAnn
@JvmDefaultWithCompatibility
interface Test {
@MyAnn
val prop: String
get() = "OK"
}
class TestClass : Test
fun box(): String {
val testClass = TestClass()
return testClass.prop
}
@@ -0,0 +1,34 @@
@java.lang.annotation.Retention(value=RUNTIME)
@kotlin.Metadata
public annotation class MyAnn {
// source: 'propertyAnnotation.kt'
}
@kotlin.Metadata
public final class PropertyAnnotationKt {
// source: 'propertyAnnotation.kt'
public final static @org.jetbrains.annotations.NotNull method box(): java.lang.String
}
@kotlin.Metadata
public final class Test$DefaultImpls {
// source: 'propertyAnnotation.kt'
public synthetic deprecated static @MyAnn method getProp$annotations(): void
public deprecated static @java.lang.Deprecated @org.jetbrains.annotations.NotNull method getProp(@org.jetbrains.annotations.NotNull p0: Test): java.lang.String
public final inner class Test$DefaultImpls
}
@kotlin.jvm.JvmDefaultWithCompatibility
@kotlin.Metadata
public interface Test {
// source: 'propertyAnnotation.kt'
public synthetic static method access$getProp$jd(p0: Test): java.lang.String
public @org.jetbrains.annotations.NotNull method getProp(): java.lang.String
public final inner class Test$DefaultImpls
}
@kotlin.Metadata
public final class TestClass {
// source: 'propertyAnnotation.kt'
public method <init>(): void
}
@@ -1,7 +1,6 @@
// !JVM_DEFAULT_MODE: all
// TARGET_BACKEND: JVM
// JVM_TARGET: 1.8
// IGNORE_BACKEND: JVM
// WITH_RUNTIME
// FILE: Simple.java
@@ -0,0 +1,33 @@
// !JVM_DEFAULT_MODE: all
// TARGET_BACKEND: JVM
// IGNORE_BACKEND: JVM
// JVM_TARGET: 1.8
// CHECK_BYTECODE_LISTING
// WITH_COROUTINES
// WITH_STDLIB
import helpers.*
import kotlin.coroutines.*
@JvmDefaultWithCompatibility
interface Test {
suspend fun suspendFun() = privateSuspendFun()
private suspend fun privateSuspendFun() = "OK"
}
class TestClass : Test
fun builder(c: suspend () -> Unit) {
c.startCoroutine(EmptyContinuation)
}
fun box(): String {
var result = "FAIL"
builder {
val testClass = TestClass()
result = testClass.suspendFun()
}
return result
}
@@ -0,0 +1,48 @@
@kotlin.coroutines.jvm.internal.DebugMetadata
@kotlin.Metadata
final class SuspendKt$box$1 {
// source: 'suspend.kt'
enclosing method SuspendKt.box()Ljava/lang/String;
synthetic final field $result: kotlin.jvm.internal.Ref$ObjectRef
field L$0: java.lang.Object
field label: int
inner (anonymous) class SuspendKt$box$1
method <init>(p0: kotlin.jvm.internal.Ref$ObjectRef, p1: kotlin.coroutines.Continuation): void
public final @org.jetbrains.annotations.NotNull method create(@org.jetbrains.annotations.NotNull p0: kotlin.coroutines.Continuation): kotlin.coroutines.Continuation
public final @org.jetbrains.annotations.Nullable method invoke(@org.jetbrains.annotations.Nullable p0: kotlin.coroutines.Continuation): java.lang.Object
public synthetic bridge method invoke(p0: java.lang.Object): java.lang.Object
public final @org.jetbrains.annotations.Nullable method invokeSuspend(@org.jetbrains.annotations.NotNull p0: java.lang.Object): java.lang.Object
}
@kotlin.Metadata
public final class SuspendKt {
// source: 'suspend.kt'
inner (anonymous) class SuspendKt$box$1
public final static @org.jetbrains.annotations.NotNull method box(): java.lang.String
public final static method builder(@org.jetbrains.annotations.NotNull p0: kotlin.jvm.functions.Function1): void
}
@kotlin.Metadata
public final class Test$DefaultImpls {
// source: 'suspend.kt'
public deprecated static @java.lang.Deprecated @org.jetbrains.annotations.Nullable method suspendFun(@org.jetbrains.annotations.NotNull p0: Test, @org.jetbrains.annotations.NotNull p1: kotlin.coroutines.Continuation): java.lang.Object
public final inner class Test$DefaultImpls
}
@kotlin.jvm.JvmDefaultWithCompatibility
@kotlin.Metadata
public interface Test {
// source: 'suspend.kt'
public synthetic static method access$privateSuspendFun(p0: Test, p1: kotlin.coroutines.Continuation): java.lang.Object
public synthetic static method access$suspendFun$jd(p0: Test, p1: kotlin.coroutines.Continuation): java.lang.Object
private method privateSuspendFun(p0: kotlin.coroutines.Continuation): java.lang.Object
public synthetic static method suspendFun$suspendImpl(p0: Test, p1: kotlin.coroutines.Continuation): java.lang.Object
public @org.jetbrains.annotations.Nullable method suspendFun(@org.jetbrains.annotations.NotNull p0: kotlin.coroutines.Continuation): java.lang.Object
public final inner class Test$DefaultImpls
}
@kotlin.Metadata
public final class TestClass {
// source: 'suspend.kt'
public method <init>(): void
}
@@ -25425,11 +25425,29 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/defaultArgs.kt");
}
@Test
@TestMetadata("differentCases.kt")
public void testDifferentCases() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/differentCases.kt");
}
@Test
@TestMetadata("propertyAnnotation.kt")
public void testPropertyAnnotation() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/propertyAnnotation.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/simple.kt");
}
@Test
@TestMetadata("suspend.kt")
public void testSuspend() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/suspend.kt");
}
}
}
@@ -25803,11 +25803,29 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/defaultArgs.kt");
}
@Test
@TestMetadata("differentCases.kt")
public void testDifferentCases() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/differentCases.kt");
}
@Test
@TestMetadata("propertyAnnotation.kt")
public void testPropertyAnnotation() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/propertyAnnotation.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/simple.kt");
}
@Test
@TestMetadata("suspend.kt")
public void testSuspend() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/suspend.kt");
}
}
}
@@ -21438,14 +21438,9 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class WithCompatibility extends AbstractLightAnalysisModeTest {
@TestMetadata("defaultArgs.kt")
public void ignoreDefaultArgs() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/defaultArgs.kt");
}
@TestMetadata("simple.kt")
public void ignoreSimple() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/simple.kt");
@TestMetadata("suspend.kt")
public void ignoreSuspend() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/suspend.kt");
}
private void runTest(String testDataFilePath) throws Exception {
@@ -21455,6 +21450,26 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
public void testAllFilesPresentInWithCompatibility() throws Exception {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility"), Pattern.compile("^(.+)\\.kt$"), null, TargetBackend.JVM, true);
}
@TestMetadata("defaultArgs.kt")
public void testDefaultArgs() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/defaultArgs.kt");
}
@TestMetadata("differentCases.kt")
public void testDifferentCases() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/differentCases.kt");
}
@TestMetadata("propertyAnnotation.kt")
public void testPropertyAnnotation() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/propertyAnnotation.kt");
}
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/codegen/box/jvm8/defaults/noDefaultImpls/withCompatibility/simple.kt");
}
}
}