[Wasm] Add external file checker to K2
#KT-56849
This commit is contained in:
committed by
Space Team
parent
7687b86654
commit
6b6353f3b9
+3
@@ -33,6 +33,9 @@ object WASM_DIAGNOSTICS_LIST : DiagnosticList("FirWasmErrors") {
|
|||||||
parameter<String>("place")
|
parameter<String>("place")
|
||||||
parameter<ConeKotlinType>("type")
|
parameter<ConeKotlinType>("type")
|
||||||
}
|
}
|
||||||
|
val NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE by error<KtElement>(PositioningStrategy.DECLARATION_SIGNATURE_OR_DEFAULT) {
|
||||||
|
parameter<ConeKotlinType>("type")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val JS_FUN by object : DiagnosticGroup("JsFun") {
|
val JS_FUN by object : DiagnosticGroup("JsFun") {
|
||||||
|
|||||||
+1
@@ -27,6 +27,7 @@ object FirWasmErrors {
|
|||||||
val EXTERNAL_TYPE_EXTENDS_NON_EXTERNAL_TYPE by error1<KtElement, ConeKotlinType>(SourceElementPositioningStrategies.DECLARATION_SIGNATURE_OR_DEFAULT)
|
val EXTERNAL_TYPE_EXTENDS_NON_EXTERNAL_TYPE by error1<KtElement, ConeKotlinType>(SourceElementPositioningStrategies.DECLARATION_SIGNATURE_OR_DEFAULT)
|
||||||
val CALL_TO_DEFINED_EXTERNALLY_FROM_NON_EXTERNAL_DECLARATION by error0<PsiElement>()
|
val CALL_TO_DEFINED_EXTERNALLY_FROM_NON_EXTERNAL_DECLARATION by error0<PsiElement>()
|
||||||
val WRONG_JS_INTEROP_TYPE by error2<KtElement, String, ConeKotlinType>(SourceElementPositioningStrategies.DECLARATION_SIGNATURE_OR_DEFAULT)
|
val WRONG_JS_INTEROP_TYPE by error2<KtElement, String, ConeKotlinType>(SourceElementPositioningStrategies.DECLARATION_SIGNATURE_OR_DEFAULT)
|
||||||
|
val NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE by error1<KtElement, ConeKotlinType>(SourceElementPositioningStrategies.DECLARATION_SIGNATURE_OR_DEFAULT)
|
||||||
|
|
||||||
// JsFun
|
// JsFun
|
||||||
val WRONG_JS_FUN_TARGET by error0<PsiElement>()
|
val WRONG_JS_FUN_TARGET by error0<PsiElement>()
|
||||||
|
|||||||
+6
@@ -20,6 +20,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.JS_MODUL
|
|||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_JS_MODULE_PROHIBITED
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_JS_MODULE_PROHIBITED
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_WASM_EXPORT
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_WASM_EXPORT
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_WASM_IMPORT
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NESTED_WASM_IMPORT
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NON_EXTERNAL_TYPE_EXTENDS_EXTERNAL_TYPE
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.NON_EXTERNAL_TYPE_EXTENDS_EXTERNAL_TYPE
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.WASM_EXPORT_ON_EXTERNAL_DECLARATION
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.WASM_EXPORT_ON_EXTERNAL_DECLARATION
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.WASM_IMPORT_EXPORT_PARAMETER_DEFAULT_VALUE
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors.WASM_IMPORT_EXPORT_PARAMETER_DEFAULT_VALUE
|
||||||
@@ -55,6 +56,11 @@ object FirWasmErrorsDefaultMessages : BaseDiagnosticRendererFactory() {
|
|||||||
"Type ''{0}'' cannot be used in {1}. Only external, primitive, string and function types are supported in Kotlin/Wasm JS interop.",
|
"Type ''{0}'' cannot be used in {1}. Only external, primitive, string and function types are supported in Kotlin/Wasm JS interop.",
|
||||||
TO_STRING, FirDiagnosticRenderers.RENDER_TYPE,
|
TO_STRING, FirDiagnosticRenderers.RENDER_TYPE,
|
||||||
)
|
)
|
||||||
|
map.put(
|
||||||
|
NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE,
|
||||||
|
"Only external declarations are allowed in files marked with ''{0}'' annotation.",
|
||||||
|
FirDiagnosticRenderers.RENDER_TYPE
|
||||||
|
)
|
||||||
|
|
||||||
map.put(WRONG_JS_FUN_TARGET, "Only top-level external functions can be implemented using '@JsFun'.")
|
map.put(WRONG_JS_FUN_TARGET, "Only top-level external functions can be implemented using '@JsFun'.")
|
||||||
|
|
||||||
|
|||||||
+1
@@ -24,5 +24,6 @@ object WasmDeclarationCheckers : DeclarationCheckers() {
|
|||||||
FirWasmJsFunAnnotationChecker,
|
FirWasmJsFunAnnotationChecker,
|
||||||
FirJsExportAnnotationChecker,
|
FirJsExportAnnotationChecker,
|
||||||
FirWasmJsModuleChecker,
|
FirWasmJsModuleChecker,
|
||||||
|
FirWasmExternalFileChecker,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
+39
@@ -0,0 +1,39 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2023 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.fir.analysis.wasm.checkers.declaration
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.diagnostics.DiagnosticReporter
|
||||||
|
import org.jetbrains.kotlin.diagnostics.reportOn
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.declaration.FirBasicDeclarationChecker
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.checkers.isTopLevel
|
||||||
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.wasm.FirWasmErrors
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.utils.isEffectivelyExternal
|
||||||
|
import org.jetbrains.kotlin.fir.types.resolvedType
|
||||||
|
import org.jetbrains.kotlin.name.WasmStandardClassIds
|
||||||
|
|
||||||
|
object FirWasmExternalFileChecker : FirBasicDeclarationChecker() {
|
||||||
|
override fun check(declaration: FirDeclaration, context: CheckerContext, reporter: DiagnosticReporter) {
|
||||||
|
if (!context.isTopLevel || declaration.symbol.isEffectivelyExternal(context.session)) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
val targetAnnotations = context.containingFile
|
||||||
|
?.annotations
|
||||||
|
?.firstOrNull { it.toAnnotationClassId(context.session) in WasmStandardClassIds.Annotations.annotationsRequiringExternal }
|
||||||
|
|
||||||
|
if (targetAnnotations != null) {
|
||||||
|
reporter.reportOn(
|
||||||
|
declaration.source,
|
||||||
|
FirWasmErrors.NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE,
|
||||||
|
targetAnnotations.resolvedType,
|
||||||
|
context
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+10
@@ -0,0 +1,10 @@
|
|||||||
|
// FIR_IDENTICAL
|
||||||
|
@file:JsModule("lib")
|
||||||
|
|
||||||
|
class <!NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE!>A<!> {
|
||||||
|
class B
|
||||||
|
|
||||||
|
fun bar() {}
|
||||||
|
}
|
||||||
|
|
||||||
|
<!NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE!>fun foo()<!> = "OK"
|
||||||
+10
@@ -0,0 +1,10 @@
|
|||||||
|
// FIR_IDENTICAL
|
||||||
|
@file:JsQualifier("a.b")
|
||||||
|
|
||||||
|
class <!NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE!>A<!> {
|
||||||
|
class B
|
||||||
|
|
||||||
|
fun bar() {}
|
||||||
|
}
|
||||||
|
|
||||||
|
<!NON_EXTERNAL_DECLARATION_IN_INAPPROPRIATE_FILE!>fun foo()<!> = "OK"
|
||||||
@@ -7,6 +7,7 @@ project.configureJvmToolchain(JdkMajorVersion.JDK_1_8)
|
|||||||
|
|
||||||
dependencies {
|
dependencies {
|
||||||
api(project(":core:compiler.common"))
|
api(project(":core:compiler.common"))
|
||||||
|
implementation(project(":core:compiler.common.web"))
|
||||||
}
|
}
|
||||||
|
|
||||||
sourceSets {
|
sourceSets {
|
||||||
|
|||||||
@@ -6,6 +6,8 @@
|
|||||||
package org.jetbrains.kotlin.name
|
package org.jetbrains.kotlin.name
|
||||||
|
|
||||||
import org.jetbrains.kotlin.name.StandardClassIds.BASE_KOTLIN_PACKAGE
|
import org.jetbrains.kotlin.name.StandardClassIds.BASE_KOTLIN_PACKAGE
|
||||||
|
import org.jetbrains.kotlin.name.WebCommonStandardClassIds.Annotations.JsModule
|
||||||
|
import org.jetbrains.kotlin.name.WebCommonStandardClassIds.Annotations.JsQualifier
|
||||||
|
|
||||||
object WasmStandardClassIds {
|
object WasmStandardClassIds {
|
||||||
val BASE_WASM_PACKAGE = BASE_KOTLIN_PACKAGE.child(Name.identifier("wasm"))
|
val BASE_WASM_PACKAGE = BASE_KOTLIN_PACKAGE.child(Name.identifier("wasm"))
|
||||||
@@ -19,6 +21,9 @@ object WasmStandardClassIds {
|
|||||||
|
|
||||||
@JvmField
|
@JvmField
|
||||||
val JsFun = "JsFun".baseId()
|
val JsFun = "JsFun".baseId()
|
||||||
|
|
||||||
|
@JvmField
|
||||||
|
val annotationsRequiringExternal = setOf(JsModule, JsQualifier)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+22
@@ -138,6 +138,12 @@ public class DiagnosticsFirWasmTestGenerated extends AbstractDiagnosticsFirWasmT
|
|||||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/module"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/module"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("jsModuleNonExternal.kt")
|
||||||
|
public void testJsModuleNonExternal() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/wasmTests/jsInterop/module/jsModuleNonExternal.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("jsVarProhibited.kt")
|
@TestMetadata("jsVarProhibited.kt")
|
||||||
public void testJsVarProhibited() throws Exception {
|
public void testJsVarProhibited() throws Exception {
|
||||||
@@ -157,6 +163,22 @@ public class DiagnosticsFirWasmTestGenerated extends AbstractDiagnosticsFirWasmT
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Nested
|
||||||
|
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier")
|
||||||
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
public class Qualifier {
|
||||||
|
@Test
|
||||||
|
public void testAllFilesPresentInQualifier() throws Exception {
|
||||||
|
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("jsQualifierNonExternal.kt")
|
||||||
|
public void testJsQualifierNonExternal() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier/jsQualifierNonExternal.kt");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Nested
|
@Nested
|
||||||
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/rtti")
|
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/rtti")
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
|||||||
+22
@@ -138,6 +138,12 @@ public class DiagnosticsWasmTestGenerated extends AbstractDiagnosticsWasmTest {
|
|||||||
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/module"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/module"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("jsModuleNonExternal.kt")
|
||||||
|
public void testJsModuleNonExternal() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/wasmTests/jsInterop/module/jsModuleNonExternal.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("jsVarProhibited.kt")
|
@TestMetadata("jsVarProhibited.kt")
|
||||||
public void testJsVarProhibited() throws Exception {
|
public void testJsVarProhibited() throws Exception {
|
||||||
@@ -157,6 +163,22 @@ public class DiagnosticsWasmTestGenerated extends AbstractDiagnosticsWasmTest {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Nested
|
||||||
|
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier")
|
||||||
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
public class Qualifier {
|
||||||
|
@Test
|
||||||
|
public void testAllFilesPresentInQualifier() throws Exception {
|
||||||
|
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.fir\\.kts?$"), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("jsQualifierNonExternal.kt")
|
||||||
|
public void testJsQualifierNonExternal() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/wasmTests/jsInterop/qualifier/jsQualifierNonExternal.kt");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Nested
|
@Nested
|
||||||
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/rtti")
|
@TestMetadata("compiler/testData/diagnostics/wasmTests/jsInterop/rtti")
|
||||||
@TestDataPath("$PROJECT_ROOT")
|
@TestDataPath("$PROJECT_ROOT")
|
||||||
|
|||||||
Reference in New Issue
Block a user