AbstractClosureAnnotator for IR.
This commit is contained in:
committed by
Dmitry Petrov
parent
ceeccfa1b7
commit
ec2cfd2389
Generated
+1
@@ -14,6 +14,7 @@
|
||||
<module fileurl="file://$PROJECT_DIR$/ant/ant.iml" filepath="$PROJECT_DIR$/ant/ant.iml" />
|
||||
<module fileurl="file://$PROJECT_DIR$/compiler/backend/backend.iml" filepath="$PROJECT_DIR$/compiler/backend/backend.iml" group="compiler/java" />
|
||||
<module fileurl="file://$PROJECT_DIR$/compiler/backend-common/backend-common.iml" filepath="$PROJECT_DIR$/compiler/backend-common/backend-common.iml" group="compiler" />
|
||||
<module fileurl="file://$PROJECT_DIR$/compiler/ir/backend.common/backend.common.iml" filepath="$PROJECT_DIR$/compiler/ir/backend.common/backend.common.iml" group="compiler/ir" />
|
||||
<module fileurl="file://$PROJECT_DIR$/compiler/ir/backend.jvm/backend.jvm.iml" filepath="$PROJECT_DIR$/compiler/ir/backend.jvm/backend.jvm.iml" group="compiler/ir" />
|
||||
<module fileurl="file://$PROJECT_DIR$/build-common/build-common.iml" filepath="$PROJECT_DIR$/build-common/build-common.iml" />
|
||||
<module fileurl="file://$PROJECT_DIR$/core/builtins/builtins.iml" filepath="$PROJECT_DIR$/core/builtins/builtins.iml" group="core" />
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<module type="JAVA_MODULE" version="4">
|
||||
<component name="NewModuleRootManager" inherit-compiler-output="true">
|
||||
<exclude-output />
|
||||
<content url="file://$MODULE_DIR$">
|
||||
<sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
|
||||
</content>
|
||||
<orderEntry type="inheritedJdk" />
|
||||
<orderEntry type="sourceFolder" forTests="false" />
|
||||
<orderEntry type="module" module-name="util" />
|
||||
<orderEntry type="module" module-name="ir.tree" />
|
||||
<orderEntry type="module" module-name="descriptors" />
|
||||
</component>
|
||||
</module>
|
||||
+148
@@ -0,0 +1,148 @@
|
||||
/*
|
||||
* Copyright 2010-2016 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.kotlin.xbackend.common
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.ir.IrElement
|
||||
import org.jetbrains.kotlin.ir.declarations.IrClass
|
||||
import org.jetbrains.kotlin.ir.declarations.IrGeneralFunction
|
||||
import org.jetbrains.kotlin.ir.declarations.IrLocalPropertyAccessor
|
||||
import org.jetbrains.kotlin.ir.expressions.*
|
||||
import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
|
||||
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
|
||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||
import java.util.*
|
||||
|
||||
class Closure(
|
||||
val capturedThisReferences: List<ClassDescriptor>,
|
||||
val capturedReceiverParameters: List<ReceiverParameterDescriptor>,
|
||||
val capturedVariables: List<VariableDescriptor>
|
||||
)
|
||||
|
||||
abstract class AbstractClosureAnnotator : IrElementVisitorVoid {
|
||||
protected abstract fun recordFunctionClosure(functionDescriptor: FunctionDescriptor, closure: Closure)
|
||||
protected abstract fun recordClassClosure(classDescriptor: ClassDescriptor, closure: Closure)
|
||||
|
||||
private class ClosureBuilder(val owner: DeclarationDescriptor) {
|
||||
val capturedThisReferences = mutableSetOf<ClassDescriptor>()
|
||||
val capturedReceiverParameters = mutableSetOf<ReceiverParameterDescriptor>()
|
||||
val capturedVariables = mutableSetOf<VariableDescriptor>()
|
||||
|
||||
fun buildClosure() = Closure(
|
||||
capturedThisReferences.toList(),
|
||||
capturedReceiverParameters.toList(),
|
||||
capturedVariables.toList()
|
||||
)
|
||||
|
||||
fun addNested(closure: Closure) {
|
||||
fillInCapturedThisReferences(closure)
|
||||
fillInNestedClosure(capturedReceiverParameters, closure.capturedReceiverParameters)
|
||||
fillInNestedClosure(capturedVariables, closure.capturedVariables)
|
||||
}
|
||||
|
||||
private fun fillInCapturedThisReferences(closure: Closure) {
|
||||
if (owner is ClassDescriptor) {
|
||||
closure.capturedThisReferences.filterTo(capturedThisReferences) { it != owner }
|
||||
}
|
||||
else if (owner is CallableMemberDescriptor && owner.dispatchReceiverParameter != null) {
|
||||
val ownerClass = owner.containingDeclaration as? ClassDescriptor
|
||||
closure.capturedThisReferences.filterTo(capturedThisReferences) { it != ownerClass }
|
||||
}
|
||||
}
|
||||
|
||||
private fun <T : CallableDescriptor> fillInNestedClosure(destination: MutableSet<T>, nested: List<T>) {
|
||||
nested.filterTo(destination) {
|
||||
it.containingDeclaration != owner
|
||||
}
|
||||
}
|
||||
|
||||
fun addCapturedThis(classDescriptor: ClassDescriptor) {
|
||||
if (owner is ClassDescriptor && owner != classDescriptor) {
|
||||
capturedThisReferences.add(classDescriptor)
|
||||
}
|
||||
else if (owner is CallableMemberDescriptor && owner.containingDeclaration != classDescriptor) {
|
||||
capturedThisReferences.add(classDescriptor)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private val closuresStack = ArrayDeque<ClosureBuilder>()
|
||||
|
||||
override fun visitElement(element: IrElement) {
|
||||
element.acceptChildrenVoid(this)
|
||||
}
|
||||
|
||||
override fun visitClass(declaration: IrClass) {
|
||||
val classDescriptor = declaration.descriptor
|
||||
val closureBuilder = ClosureBuilder(classDescriptor)
|
||||
|
||||
closuresStack.push(closureBuilder)
|
||||
declaration.acceptChildrenVoid(this)
|
||||
closuresStack.pop()
|
||||
|
||||
val closure = closureBuilder.buildClosure()
|
||||
|
||||
if (DescriptorUtils.isLocal(classDescriptor)) {
|
||||
recordClassClosure(classDescriptor, closure)
|
||||
}
|
||||
|
||||
closuresStack.peek()?.addNested(closure)
|
||||
}
|
||||
|
||||
override fun visitGeneralFunction(declaration: IrGeneralFunction) {
|
||||
val functionDescriptor = declaration.descriptor
|
||||
val closureBuilder = ClosureBuilder(functionDescriptor)
|
||||
|
||||
closuresStack.push(closureBuilder)
|
||||
declaration.acceptChildrenVoid(this)
|
||||
closuresStack.pop()
|
||||
|
||||
val closure = closureBuilder.buildClosure()
|
||||
|
||||
if (DescriptorUtils.isLocal(functionDescriptor)) {
|
||||
recordFunctionClosure(functionDescriptor, closure)
|
||||
}
|
||||
|
||||
closuresStack.peek()?.addNested(closure)
|
||||
}
|
||||
|
||||
override fun visitLocalPropertyAccessor(declaration: IrLocalPropertyAccessor) {
|
||||
// Local property accessors are created for delegated local properties and have no closure.
|
||||
}
|
||||
|
||||
override fun visitThisReference(expression: IrThisReference) {
|
||||
closuresStack.peek().addCapturedThis(expression.classDescriptor)
|
||||
}
|
||||
|
||||
override fun visitVariableAccess(expression: IrVariableAccessExpression) {
|
||||
val closureBuilder = closuresStack.peek()
|
||||
val variableDescriptor = expression.descriptor
|
||||
if (variableDescriptor.containingDeclaration != closureBuilder.owner) {
|
||||
closureBuilder.capturedVariables.add(variableDescriptor)
|
||||
}
|
||||
|
||||
expression.acceptChildrenVoid(this)
|
||||
}
|
||||
|
||||
override fun visitGetExtensionReceiver(expression: IrGetExtensionReceiver) {
|
||||
val closureBuilder = closuresStack.peek()
|
||||
val receiverDescriptor = expression.descriptor
|
||||
if (receiverDescriptor.containingDeclaration != closureBuilder.owner) {
|
||||
closureBuilder.capturedReceiverParameters.add(receiverDescriptor)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -15,5 +15,6 @@
|
||||
<orderEntry type="module" module-name="ir.tree" scope="TEST" />
|
||||
<orderEntry type="module" module-name="ir.psi2ir" scope="TEST" />
|
||||
<orderEntry type="library" scope="TEST" name="junit-4.12" level="project" />
|
||||
<orderEntry type="module" module-name="backend.common" scope="TEST" />
|
||||
</component>
|
||||
</module>
|
||||
+83
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright 2010-2016 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.kotlin.ir
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ConstructorDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||
import org.jetbrains.kotlin.ir.declarations.IrFile
|
||||
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
|
||||
import org.jetbrains.kotlin.test.KotlinTestUtils
|
||||
import org.jetbrains.kotlin.xbackend.common.AbstractClosureAnnotator
|
||||
import org.jetbrains.kotlin.xbackend.common.Closure
|
||||
import java.io.File
|
||||
import java.io.PrintWriter
|
||||
import java.io.StringWriter
|
||||
|
||||
abstract class AbstractClosureAnnotatorTestCase : AbstractIrGeneratorTestCase() {
|
||||
override fun doTest(wholeFile: File, testFiles: List<TestFile>) {
|
||||
val dir = wholeFile.parentFile
|
||||
val ignoreErrors = shouldIgnoreErrors(wholeFile)
|
||||
for ((testFile, irFile) in generateIrFilesAsSingleModule(testFiles, ignoreErrors)) {
|
||||
doTestIrFileAgainstExpectations(dir, testFile, irFile)
|
||||
}
|
||||
}
|
||||
|
||||
private fun doTestIrFileAgainstExpectations(dir: File, testFile: TestFile, irFile: IrFile) {
|
||||
val expectedFile = File(dir, testFile.name.replace(".kt", ".closure"))
|
||||
val actualClosures = renderClosures(irFile)
|
||||
KotlinTestUtils.assertEqualsToFile(expectedFile, actualClosures)
|
||||
}
|
||||
|
||||
private fun renderClosures(irFile: IrFile): String {
|
||||
val actualStringWriter = StringWriter()
|
||||
val actualOut = PrintWriter(actualStringWriter)
|
||||
|
||||
irFile.acceptChildrenVoid(object : AbstractClosureAnnotator() {
|
||||
override fun recordClassClosure(classDescriptor: ClassDescriptor, closure: Closure) {
|
||||
actualOut.println("Closure for class ${classDescriptor.name}:")
|
||||
printClosure(closure)
|
||||
actualOut.println()
|
||||
}
|
||||
|
||||
override fun recordFunctionClosure(functionDescriptor: FunctionDescriptor, closure: Closure) {
|
||||
if (functionDescriptor is ConstructorDescriptor) {
|
||||
actualOut.println("Closure for constructor ${functionDescriptor.containingDeclaration.name}:")
|
||||
}
|
||||
else {
|
||||
actualOut.println("Closure for function ${functionDescriptor.name}:")
|
||||
}
|
||||
printClosure(closure)
|
||||
actualOut.println()
|
||||
}
|
||||
|
||||
private fun printClosure(closure: Closure) {
|
||||
closure.capturedThisReferences.forEach {
|
||||
actualOut.println(" 'this' for ${it.name}")
|
||||
}
|
||||
closure.capturedReceiverParameters.forEach {
|
||||
actualOut.println(" receiver for ${it.containingDeclaration.name}")
|
||||
}
|
||||
closure.capturedVariables.forEach {
|
||||
actualOut.println(" variable ${it.name}")
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
return actualStringWriter.toString()
|
||||
}
|
||||
}
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.ir
|
||||
|
||||
import junit.framework.TestCase
|
||||
import org.jetbrains.kotlin.cli.jvm.compiler.EnvironmentConfigFiles
|
||||
import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment
|
||||
import org.jetbrains.kotlin.codegen.CodegenTestCase
|
||||
@@ -28,6 +29,8 @@ import org.jetbrains.kotlin.test.ConfigurationKind
|
||||
import org.jetbrains.kotlin.test.InTextDirectivesUtils
|
||||
import org.jetbrains.kotlin.test.KotlinTestUtils.getAnnotationsJar
|
||||
import java.io.File
|
||||
import java.io.FileWriter
|
||||
import java.io.PrintWriter
|
||||
import java.util.*
|
||||
|
||||
abstract class AbstractIrGeneratorTestCase : CodegenTestCase() {
|
||||
@@ -86,6 +89,24 @@ abstract class AbstractIrGeneratorTestCase : CodegenTestCase() {
|
||||
val ktFiles = testFiles.filter { it.name.endsWith(".kt") }
|
||||
return ktFiles.zip(irModule.files).toMap()
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val IGNORE_ERRORS_PATTERN = Regex("""// !IGNORE_ERRORS""")
|
||||
|
||||
internal fun shouldIgnoreErrors(wholeFile: File): Boolean =
|
||||
IGNORE_ERRORS_PATTERN.containsMatchIn(wholeFile.readText())
|
||||
|
||||
internal fun createExpectedTextFile(testFile: TestFile, dir: File, fileName: String): File {
|
||||
val textFile = File(dir, fileName)
|
||||
if (!textFile.exists()) {
|
||||
TestCase.assertTrue("Can't create an expected text containingFile: ${textFile.absolutePath}", textFile.createNewFile())
|
||||
PrintWriter(FileWriter(textFile)).use {
|
||||
it.println("$fileName: new expected text containingFile for ${testFile.name}")
|
||||
}
|
||||
}
|
||||
return textFile
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -75,10 +75,6 @@ abstract class AbstractIrTextTestCase : AbstractIrGeneratorTestCase() {
|
||||
companion object {
|
||||
private val EXPECTED_OCCURRENCES_PATTERN = Regex("""^\s*//\s*(\d+)\s*(.*)$""")
|
||||
private val IR_FILE_TXT_PATTERN = Regex("""// IR_FILE: (.*)$""")
|
||||
private val IGNORE_ERRORS_PATTERN = Regex("""// !IGNORE_ERRORS""")
|
||||
|
||||
internal fun shouldIgnoreErrors(wholeFile: File): Boolean =
|
||||
IGNORE_ERRORS_PATTERN.containsMatchIn(wholeFile.readText())
|
||||
|
||||
internal fun parseExpectations(dir: File, testFile: TestFile): Expectations {
|
||||
val regexps = ArrayList<RegexpInText>()
|
||||
@@ -102,17 +98,6 @@ abstract class AbstractIrTextTestCase : AbstractIrGeneratorTestCase() {
|
||||
|
||||
return Expectations(regexps, treeFiles)
|
||||
}
|
||||
|
||||
internal fun createExpectedTextFile(testFile: TestFile, dir: File, fileName: String): File {
|
||||
val textFile = File(dir, fileName)
|
||||
if (!textFile.exists()) {
|
||||
TestCase.assertTrue("Can't create an IR expected text containingFile: ${textFile.absolutePath}", textFile.createNewFile())
|
||||
PrintWriter(FileWriter(textFile)).use {
|
||||
it.println("$fileName: new IR expected text containingFile for ${testFile.name}")
|
||||
}
|
||||
}
|
||||
return textFile
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -60,8 +60,9 @@ interface IrElementVisitor<out R, in D> {
|
||||
fun visitSingletonReference(expression: IrGetSingletonValue, data: D) = visitDeclarationReference(expression, data)
|
||||
fun visitGetObjectValue(expression: IrGetObjectValue, data: D) = visitSingletonReference(expression, data)
|
||||
fun visitGetEnumValue(expression: IrGetEnumValue, data: D) = visitSingletonReference(expression, data)
|
||||
fun visitGetVariable(expression: IrGetVariable, data: D) = visitDeclarationReference(expression, data)
|
||||
fun visitSetVariable(expression: IrSetVariable, data: D) = visitDeclarationReference(expression, data)
|
||||
fun visitVariableAccess(expression: IrVariableAccessExpression, data: D) = visitDeclarationReference(expression, data)
|
||||
fun visitGetVariable(expression: IrGetVariable, data: D) = visitVariableAccess(expression, data)
|
||||
fun visitSetVariable(expression: IrSetVariable, data: D) = visitVariableAccess(expression, data)
|
||||
fun visitBackingFieldReference(expression: IrBackingFieldExpression, data: D) = visitDeclarationReference(expression, data)
|
||||
fun visitGetBackingField(expression: IrGetBackingField, data: D) = visitBackingFieldReference(expression, data)
|
||||
fun visitSetBackingField(expression: IrSetBackingField, data: D) = visitBackingFieldReference(expression, data)
|
||||
|
||||
@@ -123,10 +123,13 @@ interface IrElementVisitorVoid : IrElementVisitor<Unit, Nothing?> {
|
||||
fun visitGetEnumValue(expression: IrGetEnumValue) = visitSingletonReference(expression)
|
||||
override fun visitGetEnumValue(expression: IrGetEnumValue, data: Nothing?) = visitGetEnumValue(expression)
|
||||
|
||||
fun visitGetVariable(expression: IrGetVariable) = visitDeclarationReference(expression)
|
||||
fun visitVariableAccess(expression: IrVariableAccessExpression) = visitDeclarationReference(expression)
|
||||
override fun visitVariableAccess(expression: IrVariableAccessExpression, data: Nothing?) = visitVariableAccess(expression)
|
||||
|
||||
fun visitGetVariable(expression: IrGetVariable) = visitVariableAccess(expression)
|
||||
override fun visitGetVariable(expression: IrGetVariable, data: Nothing?) = visitGetVariable(expression)
|
||||
|
||||
fun visitSetVariable(expression: IrSetVariable) = visitDeclarationReference(expression)
|
||||
fun visitSetVariable(expression: IrSetVariable) = visitVariableAccess(expression)
|
||||
override fun visitSetVariable(expression: IrSetVariable, data: Nothing?) = visitSetVariable(expression)
|
||||
|
||||
fun visitBackingFieldReference(expression: IrBackingFieldExpression) = visitDeclarationReference(expression)
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
Closure for function test2:
|
||||
receiver for outer
|
||||
variable y
|
||||
|
||||
Closure for function test1:
|
||||
receiver for outer
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
fun String.outer(x: Int) {
|
||||
fun test1(x: Int, y: Int) {
|
||||
fun test2(x: Int) = this + x + y
|
||||
test2(y).length + x + y
|
||||
}
|
||||
test1(x, x * x)
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
Closure for constructor <no name provided>:
|
||||
|
||||
Closure for function test1:
|
||||
'this' for C
|
||||
|
||||
Closure for function <anonymous>:
|
||||
'this' for C
|
||||
'this' for <no name provided>
|
||||
|
||||
Closure for function test2:
|
||||
'this' for C
|
||||
|
||||
Closure for class <no name provided>:
|
||||
'this' for C
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
class C {
|
||||
fun foo() = object {
|
||||
fun test1() = this@C.toString() + this.toString()
|
||||
fun test2() = { this@C.toString() + this.toString() }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
Closure for constructor <no name provided>:
|
||||
|
||||
Closure for function test6:
|
||||
|
||||
Closure for class <no name provided>:
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
fun Int.test1(x: Int) = this + x
|
||||
|
||||
class Test2(val x: Int) {
|
||||
fun test3() = x
|
||||
fun Int.test4() = this + x
|
||||
}
|
||||
|
||||
val test5 = object {
|
||||
fun Int.test6(x: Int) = this + x
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* Copyright 2010-2016 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.kotlin.ir;
|
||||
|
||||
import com.intellij.testFramework.TestDataPath;
|
||||
import org.jetbrains.kotlin.test.JUnit3RunnerWithInners;
|
||||
import org.jetbrains.kotlin.test.KotlinTestUtils;
|
||||
import org.jetbrains.kotlin.test.TestMetadata;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/** This class is generated by {@link org.jetbrains.kotlin.generators.tests.TestsPackage}. DO NOT MODIFY MANUALLY */
|
||||
@SuppressWarnings("all")
|
||||
@TestMetadata("compiler/testData/ir/closureAnnotator")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
@RunWith(JUnit3RunnerWithInners.class)
|
||||
public class ClosureAnnotatorTestCaseGenerated extends AbstractClosureAnnotatorTestCase {
|
||||
public void testAllFilesPresentInClosureAnnotator() throws Exception {
|
||||
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/ir/closureAnnotator"), Pattern.compile("^(.+)\\.kt$"), true);
|
||||
}
|
||||
|
||||
@TestMetadata("localFunctions.kt")
|
||||
public void testLocalFunctions() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/closureAnnotator/localFunctions.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("multipleThisReferences.kt")
|
||||
public void testMultipleThisReferences() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/closureAnnotator/multipleThisReferences.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("topLevelDeclarations.kt")
|
||||
public void testTopLevelDeclarations() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/closureAnnotator/topLevelDeclarations.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
@@ -121,6 +121,7 @@ import org.jetbrains.kotlin.idea.stubs.AbstractMultiFileHighlightingTest
|
||||
import org.jetbrains.kotlin.idea.stubs.AbstractResolveByStubTest
|
||||
import org.jetbrains.kotlin.idea.stubs.AbstractStubBuilderTest
|
||||
import org.jetbrains.kotlin.integration.AbstractAntTaskTest
|
||||
import org.jetbrains.kotlin.ir.AbstractClosureAnnotatorTestCase
|
||||
import org.jetbrains.kotlin.ir.AbstractIrTextTestCase
|
||||
import org.jetbrains.kotlin.ir.AbstractPsi2IrAcceptanceTestCase
|
||||
import org.jetbrains.kotlin.j2k.AbstractJavaToKotlinConverterForWebDemoTest
|
||||
@@ -249,6 +250,10 @@ fun main(args: Array<String>) {
|
||||
model("codegen/box")
|
||||
}
|
||||
|
||||
testClass<AbstractClosureAnnotatorTestCase> {
|
||||
model("ir/closureAnnotator")
|
||||
}
|
||||
|
||||
testClass<AbstractBytecodeListingTest>() {
|
||||
model("codegen/bytecodeListing")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user