From 70c573864acddcebb09e9f6ac641a6f0dbf7ad68 Mon Sep 17 00:00:00 2001 From: Denis Zharkov Date: Wed, 11 Mar 2015 12:56:10 +0300 Subject: [PATCH] Prohibit DelegationBy specifier when no primary constructor Also add codegen test for case when there is primary --- .../kotlin/resolve/BodyResolver.java | 3 +++ .../delegationWithPrimary.kt | 17 +++++++++++++++ .../delegationByWithoutPrimary.kt | 6 ++++++ .../delegationByWithoutPrimary.txt | 21 +++++++++++++++++++ .../checkers/JetDiagnosticsTestGenerated.java | 6 ++++++ .../BlackBoxCodegenTestGenerated.java | 6 ++++++ 6 files changed, 59 insertions(+) create mode 100644 compiler/testData/codegen/box/secondaryConstructors/delegationWithPrimary.kt create mode 100644 compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.kt create mode 100644 compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.txt diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/BodyResolver.java b/compiler/frontend/src/org/jetbrains/kotlin/resolve/BodyResolver.java index d004c5f8d9e..9235bee7fed 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/BodyResolver.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/BodyResolver.java @@ -304,6 +304,9 @@ public class BodyResolver { JetType expectedType = supertype != null ? supertype : NO_EXPECTED_TYPE; typeInferrer.getType(scope, delegateExpression, expectedType, c.getOuterDataFlowInfo(), trace); } + if (primaryConstructor == null) { + trace.report(UNSUPPORTED.on(specifier, "Delegation without primary constructor is not supported")); + } } @Override diff --git a/compiler/testData/codegen/box/secondaryConstructors/delegationWithPrimary.kt b/compiler/testData/codegen/box/secondaryConstructors/delegationWithPrimary.kt new file mode 100644 index 00000000000..33fc62c2d16 --- /dev/null +++ b/compiler/testData/codegen/box/secondaryConstructors/delegationWithPrimary.kt @@ -0,0 +1,17 @@ +trait A { + fun foo(): String +} + +class B : A { + override fun foo() = "OK" +} + +val global = B() + +class C(x: Int) : A by global { + constructor(): this(1) {} +} + +fun box(): String { + return C().foo() +} diff --git a/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.kt b/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.kt new file mode 100644 index 00000000000..669d75112c9 --- /dev/null +++ b/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.kt @@ -0,0 +1,6 @@ +trait A +class AImpl : A + +class B : A by AImpl() { + constructor() {} +} diff --git a/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.txt b/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.txt new file mode 100644 index 00000000000..ab2496e785d --- /dev/null +++ b/compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.txt @@ -0,0 +1,21 @@ +package + +internal trait A { + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String +} + +internal final class AImpl : A { + public constructor AImpl() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String +} + +internal final class B : A { + public constructor B() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String +} diff --git a/compiler/tests/org/jetbrains/kotlin/checkers/JetDiagnosticsTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/checkers/JetDiagnosticsTestGenerated.java index fe50a184613..ce2b764c0cb 100644 --- a/compiler/tests/org/jetbrains/kotlin/checkers/JetDiagnosticsTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/checkers/JetDiagnosticsTestGenerated.java @@ -10481,6 +10481,12 @@ public class JetDiagnosticsTestGenerated extends AbstractJetDiagnosticsTest { doTest(fileName); } + @TestMetadata("delegationByWithoutPrimary.kt") + public void testDelegationByWithoutPrimary() throws Exception { + String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/secondaryConstructors/delegationByWithoutPrimary.kt"); + doTest(fileName); + } + @TestMetadata("enums.kt") public void testEnums() throws Exception { String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/secondaryConstructors/enums.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxCodegenTestGenerated.java index 95431d9d2dc..27f36d3baf0 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxCodegenTestGenerated.java @@ -6321,6 +6321,12 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest { doTest(fileName); } + @TestMetadata("delegationWithPrimary.kt") + public void testDelegationWithPrimary() throws Exception { + String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/box/secondaryConstructors/delegationWithPrimary.kt"); + doTest(fileName); + } + @TestMetadata("enums.kt") public void testEnums() throws Exception { String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/box/secondaryConstructors/enums.kt");