From 76e2ae200596d73240ea7a2c222a56e1496d9387 Mon Sep 17 00:00:00 2001 From: Andrey Breslav Date: Mon, 1 Dec 2014 15:29:15 +0300 Subject: [PATCH] Do not complain about missing bodies on native functions --- .../jet/lang/resolve/kotlin/native.kt | 61 +++++++++++++++++++ .../testsWithStdLib/native/noBody.kt | 25 ++++++++ .../testsWithStdLib/native/noBody.txt | 36 +++++++++++ ...JetDiagnosticsTestWithStdLibGenerated.java | 17 +++++- idea/src/META-INF/extensions/kotlin2jvm.xml | 2 + 5 files changed, 140 insertions(+), 1 deletion(-) create mode 100644 compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/kotlin/native.kt create mode 100644 compiler/testData/diagnostics/testsWithStdLib/native/noBody.kt create mode 100644 compiler/testData/diagnostics/testsWithStdLib/native/noBody.txt diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/kotlin/native.kt b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/kotlin/native.kt new file mode 100644 index 00000000000..7e20a45ad8f --- /dev/null +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/kotlin/native.kt @@ -0,0 +1,61 @@ +/* + * Copyright 2010-2014 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.jetbrains.jet.lang.resolve.kotlin.nativeDeclarations + +import org.jetbrains.jet.lang.resolve.DiagnosticsWithSuppression +import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor +import org.jetbrains.jet.lang.resolve.DescriptorUtils +import org.jetbrains.jet.lang.diagnostics.Errors +import org.jetbrains.jet.lang.resolve.AnnotationChecker +import org.jetbrains.jet.lang.psi.JetDeclaration +import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor +import org.jetbrains.jet.lang.diagnostics.DiagnosticSink +import org.jetbrains.jet.lang.resolve.name.FqName +import org.jetbrains.jet.lang.descriptors.CallableMemberDescriptor +import org.jetbrains.jet.lang.descriptors.Modality +import org.jetbrains.jet.lang.resolve.java.diagnostics.ErrorsJvm + +private val NATIVE_ANNOTATION_CLASS_NAME = FqName("kotlin.jvm.native") + +public fun DeclarationDescriptor.hasNativeAnnotation(): Boolean { + return getAnnotations().findAnnotation(NATIVE_ANNOTATION_CLASS_NAME) != null +} + +class SuppressNoBodyErrorsForNativeDeclarations : DiagnosticsWithSuppression.SuppressStringProvider { + override fun get(annotationDescriptor: AnnotationDescriptor): List { + val descriptor = DescriptorUtils.getClassDescriptorForType(annotationDescriptor.getType()) + if (NATIVE_ANNOTATION_CLASS_NAME.asString() == DescriptorUtils.getFqName(descriptor).asString()) { + return listOf( + Errors.NON_ABSTRACT_FUNCTION_WITH_NO_BODY.getName().toLowerCase(), + Errors.NON_MEMBER_FUNCTION_NO_BODY.getName().toLowerCase(), + Errors.FINAL_FUNCTION_WITH_NO_BODY.getName().toLowerCase() + ) + } + + return listOf() + } +} + +public class NativeFunChecker : AnnotationChecker { + override fun check(declaration: JetDeclaration, descriptor: DeclarationDescriptor, diagnosticHolder: DiagnosticSink) { + if (descriptor.hasNativeAnnotation() && + descriptor is CallableMemberDescriptor && + descriptor.getModality() == Modality.ABSTRACT) { + diagnosticHolder.report(ErrorsJvm.NATIVE_DECLARATION_CANNOT_BE_ABSTRACT.on(declaration)) + } + } +} diff --git a/compiler/testData/diagnostics/testsWithStdLib/native/noBody.kt b/compiler/testData/diagnostics/testsWithStdLib/native/noBody.kt new file mode 100644 index 00000000000..5b8c51d595b --- /dev/null +++ b/compiler/testData/diagnostics/testsWithStdLib/native/noBody.kt @@ -0,0 +1,25 @@ +import kotlin.jvm.* + +native fun foo() + +class C { + native fun foo() + + class object { + native fun foo() + } +} + +object O { + native fun foo() +} + +fun test() { + class Local { + native fun foo() + } + + object { + native fun foo() + } +} \ No newline at end of file diff --git a/compiler/testData/diagnostics/testsWithStdLib/native/noBody.txt b/compiler/testData/diagnostics/testsWithStdLib/native/noBody.txt new file mode 100644 index 00000000000..b6459d3140c --- /dev/null +++ b/compiler/testData/diagnostics/testsWithStdLib/native/noBody.txt @@ -0,0 +1,36 @@ +package + +kotlin.jvm.native() internal fun foo(): kotlin.Unit +internal fun test(): kotlin.Unit + +internal final class C { + public constructor C() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + kotlin.jvm.native() internal final fun foo(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + internal class object { + private constructor () + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + kotlin.jvm.native() internal final fun foo(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} + +internal object O { + private constructor O() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + kotlin.jvm.native() internal final fun foo(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public class object : O { + private constructor () + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + kotlin.jvm.native() internal final override /*1*/ /*fake_override*/ fun foo(): kotlin.Unit + 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/jet/checkers/JetDiagnosticsTestWithStdLibGenerated.java b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestWithStdLibGenerated.java index bb2dc8bf218..b53a325b393 100644 --- a/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestWithStdLibGenerated.java +++ b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestWithStdLibGenerated.java @@ -30,7 +30,7 @@ import java.util.regex.Pattern; @SuppressWarnings("all") @TestMetadata("compiler/testData/diagnostics/testsWithStdLib") @TestDataPath("$PROJECT_ROOT") -@InnerTestClasses({JetDiagnosticsTestWithStdLibGenerated.Annotations.class, JetDiagnosticsTestWithStdLibGenerated.CallableReference.class, JetDiagnosticsTestWithStdLibGenerated.DuplicateJvmSignature.class, JetDiagnosticsTestWithStdLibGenerated.FunctionLiterals.class, JetDiagnosticsTestWithStdLibGenerated.Inference.class, JetDiagnosticsTestWithStdLibGenerated.KotlinSignature.class, JetDiagnosticsTestWithStdLibGenerated.Reified.class, JetDiagnosticsTestWithStdLibGenerated.Resolve.class, JetDiagnosticsTestWithStdLibGenerated.Varargs.class}) +@InnerTestClasses({JetDiagnosticsTestWithStdLibGenerated.Annotations.class, JetDiagnosticsTestWithStdLibGenerated.CallableReference.class, JetDiagnosticsTestWithStdLibGenerated.DuplicateJvmSignature.class, JetDiagnosticsTestWithStdLibGenerated.FunctionLiterals.class, JetDiagnosticsTestWithStdLibGenerated.Inference.class, JetDiagnosticsTestWithStdLibGenerated.KotlinSignature.class, JetDiagnosticsTestWithStdLibGenerated.Native.class, JetDiagnosticsTestWithStdLibGenerated.Reified.class, JetDiagnosticsTestWithStdLibGenerated.Resolve.class, JetDiagnosticsTestWithStdLibGenerated.Varargs.class}) @RunWith(JUnit3RunnerWithInners.class) public class JetDiagnosticsTestWithStdLibGenerated extends AbstractJetDiagnosticsTestWithStdLib { public void testAllFilesPresentInTestsWithStdLib() throws Exception { @@ -648,6 +648,21 @@ public class JetDiagnosticsTestWithStdLibGenerated extends AbstractJetDiagnostic } } + @TestMetadata("compiler/testData/diagnostics/testsWithStdLib/native") + @TestDataPath("$PROJECT_ROOT") + @RunWith(JUnit3RunnerWithInners.class) + public static class Native extends AbstractJetDiagnosticsTestWithStdLib { + public void testAllFilesPresentInNative() throws Exception { + JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/diagnostics/testsWithStdLib/native"), Pattern.compile("^(.+)\\.kt$"), true); + } + + @TestMetadata("noBody.kt") + public void testNoBody() throws Exception { + String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/native/noBody.kt"); + doTest(fileName); + } + } + @TestMetadata("compiler/testData/diagnostics/testsWithStdLib/reified") @TestDataPath("$PROJECT_ROOT") @RunWith(JUnit3RunnerWithInners.class) diff --git a/idea/src/META-INF/extensions/kotlin2jvm.xml b/idea/src/META-INF/extensions/kotlin2jvm.xml index ecb644dc6b9..7d7eada4ad4 100644 --- a/idea/src/META-INF/extensions/kotlin2jvm.xml +++ b/idea/src/META-INF/extensions/kotlin2jvm.xml @@ -3,5 +3,7 @@ + +