Drop package facades: JVM BE tests passed.

This commit is contained in:
Dmitry Petrov
2015-10-14 13:13:01 +03:00
parent a59cb22bc6
commit 3502c393fc
51 changed files with 120 additions and 571 deletions
@@ -47,7 +47,7 @@ import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class AbstractLineNumberTest extends TestCaseWithTmpdir {
public abstract class AbstractLineNumberTest extends TestCaseWithTmpdir {
private static final String LINE_NUMBER_FUN = "lineNumber";
private static final Pattern TEST_LINE_NUMBER_PATTERN = Pattern.compile("^.*test." + LINE_NUMBER_FUN + "\\(\\).*$");
@@ -244,20 +244,4 @@ public class AbstractLineNumberTest extends TestCaseWithTmpdir {
}, ClassReader.SKIP_FRAMES);
return result;
}
public void testStaticDelegate() {
JetFile foo = createPsiFile(getTestDataPath() + "/staticDelegate/foo.kt").getFirst();
JetFile bar = createPsiFile(getTestDataPath() + "/staticDelegate/bar.kt").getFirst();
GenerationState state = GenerationUtils.compileManyFilesGetGenerationStateForTest(foo.getProject(), Arrays.asList(foo, bar));
OutputFile file = state.getFactory().get(PackageClassUtils.getPackageClassName(FqName.ROOT) + ".class");
assertNotNull(file);
ClassReader reader = new ClassReader(file.asByteArray());
// There must be exactly one line number attribute for each static delegate in package facade class, and it should point to the first
// line. There are two static delegates in this test, hence the [1, 1]
List<Integer> expectedLineNumbers = Arrays.asList(1, 1);
List<Integer> actualLineNumbers = readAllLineNumbers(reader);
assertSameElements(actualLineNumbers, expectedLineNumbers);
}
}
@@ -55,9 +55,6 @@ public class AnnotationGenTest extends CodegenTestCase {
public void testPropField() throws Exception {
ClassLoader loader = loadFileGetClassLoader("@[java.lang.Deprecated] var x = 0");
Class<?> packageClass = getPackageClass(loader);
assertNull(packageClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNull(packageClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
Class<?> srcClass = getPackageSrcClass(loader);
assertNull(srcClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNull(srcClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
@@ -67,9 +64,6 @@ public class AnnotationGenTest extends CodegenTestCase {
public void testPropGetter() throws Exception {
ClassLoader loader = loadFileGetClassLoader("var x = 0\n" +
"@[java.lang.Deprecated] get");
Class<?> packageClass = getPackageClass(loader);
assertNotNull(packageClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNull(packageClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
Class<?> srcClass = getPackageSrcClass(loader);
assertNotNull(srcClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNull(srcClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
@@ -79,9 +73,6 @@ public class AnnotationGenTest extends CodegenTestCase {
public void testPropSetter() throws Exception {
ClassLoader loader = loadFileGetClassLoader("var x = 0\n" +
"@[java.lang.Deprecated] set");
Class<?> packageClass = getPackageClass(loader);
assertNull(packageClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNotNull(packageClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
Class<?> scrClass = getPackageSrcClass(loader);
assertNull(scrClass.getDeclaredMethod("getX").getAnnotation(Deprecated.class));
assertNotNull(scrClass.getDeclaredMethod("setX", int.class).getAnnotation(Deprecated.class));
@@ -90,10 +81,6 @@ public class AnnotationGenTest extends CodegenTestCase {
public void testAnnotationForParamInTopLevelFunction() throws Exception {
ClassLoader loader = loadFileGetClassLoader("fun x(@[java.lang.Deprecated] i: Int) {}");
Class<?> packageClass = getPackageClass(loader);
Method packageClassMethod = packageClass.getMethod("x", int.class);
assertNotNull(packageClassMethod);
assertNotNull(getDeprecatedAnnotationFromList(packageClassMethod.getParameterAnnotations()[0]));
Class<?> srcClass = getPackageSrcClass(loader);
Method srcClassMethod = srcClass.getMethod("x", int.class);
assertNotNull(srcClassMethod);
@@ -208,11 +195,6 @@ public class AnnotationGenTest extends CodegenTestCase {
public void testMethod() throws Exception {
ClassLoader loader = loadFileGetClassLoader("@[java.lang.Deprecated] fun x () {}");
Class<?> packageClass = getPackageClass(loader);
Method packageClassMethod = packageClass.getDeclaredMethod("x");
assertNotNull(packageClassMethod.getAnnotation(Deprecated.class));
Class<?> srcClass = getPackageSrcClass(loader);
Method srcClassMethod = srcClass.getDeclaredMethod("x");
assertNotNull(srcClassMethod.getAnnotation(Deprecated.class));
@@ -107,12 +107,6 @@ public class BytecodeTextTestGenerated extends AbstractBytecodeTextTest {
doTest(fileName);
}
@TestMetadata("defaultDelegation.kt")
public void testDefaultDelegation() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/bytecodeText/defaultDelegation.kt");
doTest(fileName);
}
@TestMetadata("inlineFromOtherModule.kt")
public void testInlineFromOtherModule() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/bytecodeText/inlineFromOtherModule.kt");
@@ -54,7 +54,7 @@ public class ClassGenTest extends CodegenTestCase {
public void testDelegationToVal() throws Exception {
loadFile("classes/delegationToVal.kt");
GeneratedClassLoader loader = generateAndCreateClassLoader();
Class<?> aClass = loader.loadClass(PackageClassUtils.getPackageClassName(FqName.ROOT));
Class<?> aClass = loader.loadClass("DelegationToValKt");
assertEquals("OK", aClass.getMethod("box").invoke(null));
Class<?> test = loader.loadClass("Test");
@@ -29,6 +29,8 @@ import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment;
import org.jetbrains.kotlin.cli.jvm.config.JvmContentRootsKt;
import org.jetbrains.kotlin.codegen.forTestCompile.ForTestCompileRuntime;
import org.jetbrains.kotlin.config.CompilerConfiguration;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.fileClasses.NoResolveFileClassesProvider;
import org.jetbrains.kotlin.load.kotlin.PackagePartClassUtils;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.test.ConfigurationKind;
@@ -57,13 +59,13 @@ import java.util.List;
import java.util.Map;
import static org.jetbrains.kotlin.codegen.CodegenTestUtil.*;
import static org.jetbrains.kotlin.load.kotlin.PackageClassUtils.getPackageClassFqName;
import static org.jetbrains.kotlin.test.JetTestUtils.compilerConfigurationForTests;
import static org.jetbrains.kotlin.test.JetTestUtils.getAnnotationsJar;
public abstract class CodegenTestCase extends UsefulTestCase {
public static final String DEFAULT_TEST_FILE_NAME = "a_test";
public static final String DEFAULT_TEST_FILE_CLASS_NAME = "A_testKt";
protected KotlinCoreEnvironment myEnvironment;
protected CodegenTestFiles myFiles;
@@ -205,15 +207,15 @@ public abstract class CodegenTestCase extends UsefulTestCase {
}
@NotNull
protected Class<?> generatePackageClass() {
FqName packageFqName = myFiles.getPsiFile().getPackageFqName();
return generateClass(getPackageClassFqName(packageFqName).asString());
protected Class<?> generateFacadeClass() {
FqName facadeClassFqName = JvmFileClassUtil.getFileClassInfoNoResolve(myFiles.getPsiFile()).getFacadeClassFqName();
return generateClass(facadeClassFqName.asString());
}
@NotNull
protected Class<?> generatePackagePartClass() {
String name = PackagePartClassUtils.getPackagePartInternalName(myFiles.getPsiFile());
return generateClass(name);
protected Class<?> generateFileClass() {
FqName fileClassFqName = JvmFileClassUtil.getFileClassInfoNoResolve(myFiles.getPsiFile()).getFileClassFqName();
return generateClass(fileClassFqName.asString());
}
@NotNull
@@ -303,7 +305,7 @@ public abstract class CodegenTestCase extends UsefulTestCase {
@NotNull
protected Method generateFunction() {
Class<?> aClass = generatePackageClass();
Class<?> aClass = generateFacadeClass();
try {
return findTheOnlyMethod(aClass);
} catch (Error e) {
@@ -314,7 +316,7 @@ public abstract class CodegenTestCase extends UsefulTestCase {
@NotNull
protected Method generateFunction(@NotNull String name) {
return findDeclaredMethodByName(generatePackageClass(), name);
return findDeclaredMethodByName(generateFacadeClass(), name);
}
@NotNull
@@ -26,8 +26,8 @@ import org.jetbrains.kotlin.cli.jvm.compiler.EnvironmentConfigFiles;
import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment;
import org.jetbrains.kotlin.cli.jvm.config.JVMConfigurationKeys;
import org.jetbrains.kotlin.config.CompilerConfiguration;
import org.jetbrains.kotlin.load.kotlin.PackageClassUtils;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.psi.JetFile;
import org.jetbrains.kotlin.test.ConfigurationKind;
import org.jetbrains.kotlin.test.JetTestUtils;
import org.jetbrains.kotlin.test.TestJdkKind;
@@ -79,7 +79,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
loadFiles("notNullAssertions/noAssertionsForKotlin.kt", "notNullAssertions/noAssertionsForKotlinMain.kt");
assertNoIntrinsicsMethodIsCalled(PackageClassUtils.getPackageClassName(FqName.ROOT));
assertNoIntrinsicsMethodIsCalledInMyClasses(true);
}
public void testNoAssertionsForKotlinFromBinary() throws Exception {
@@ -92,7 +92,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
setUpEnvironment(false, true, compiledDirectory);
loadFile("notNullAssertions/noAssertionsForKotlinMain.kt");
assertNoIntrinsicsMethodIsCalled(PackageClassUtils.getPackageClassName(FqName.ROOT));
assertNoIntrinsicsMethodIsCalledInMyClasses(false);
}
public void testGenerateParamAssertions() throws Exception {
@@ -109,7 +109,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
loadFile("notNullAssertions/doNotGenerateParamAssertions.kt");
assertNoIntrinsicsMethodIsCalled("A");
assertNoIntrinsicsMethodIsCalled("A", true);
}
public void testNoParamAssertionForPrivateMethod() throws Exception {
@@ -117,7 +117,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
loadFile("notNullAssertions/noAssertionForPrivateMethod.kt");
assertNoIntrinsicsMethodIsCalled("A");
assertNoIntrinsicsMethodIsCalled("A", true);
}
public void testArrayListGet() {
@@ -154,7 +154,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
loadFile("notNullAssertions/noAssertionForNullableGenericMethod.kt");
assertNoIntrinsicsMethodIsCalled(PackageClassUtils.getPackageClassName(FqName.ROOT));
assertNoIntrinsicsMethodIsCalledInMyClasses(true);
}
public void testNoAssertionForNullableGenericMethodCall() {
@@ -162,7 +162,7 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
loadFile("notNullAssertions/noAssertionForNullableGenericMethodCall.kt");
assertNoIntrinsicsMethodIsCalled("A");
assertNoIntrinsicsMethodIsCalled("A", true);
}
public void testParamAssertionMessage() throws Exception {
@@ -184,10 +184,22 @@ public class GenerateNotNullAssertionsTest extends CodegenTestCase {
fail("Assertion should have been fired");
}
private void assertNoIntrinsicsMethodIsCalled(String className) {
private void assertNoIntrinsicsMethodIsCalledInMyClasses(boolean noClassFileIsAnError) {
for (JetFile jetFile : myFiles.getPsiFiles()) {
String fileClassName = JvmFileClassUtil.getFileClassInfoNoResolve(jetFile).getFileClassFqName().asString();
assertNoIntrinsicsMethodIsCalled(fileClassName, noClassFileIsAnError);
}
}
private void assertNoIntrinsicsMethodIsCalled(String className, boolean noClassFileIsAnError) {
OutputFileCollection classes = generateClassesInFile();
OutputFile file = classes.get(className + ".class");
assertNotNull(file);
if (noClassFileIsAnError) {
assertNotNull("File for " + className + " is absent", file);
}
else if (file == null) {
return;
}
ClassReader reader = new ClassReader(file.asByteArray());
reader.accept(new ClassVisitor(Opcodes.ASM5) {
@@ -50,7 +50,7 @@ public class JUnitUsageGenTest extends CodegenTestCase {
public void testKt1592() throws Exception {
loadFile("junit/kt1592.kt");
Class<?> packageClass = generatePackageClass();
Class<?> packageClass = generateFacadeClass();
Method method = packageClass.getMethod("foo", Method.class);
method.setAccessible(true);
Annotation annotation = method.getAnnotation(loadAnnotationClassQuietly(Test.class.getName()));
@@ -42,36 +42,6 @@ public class KotlinPackageAnnotationTest extends CodegenTestCase {
createEnvironmentWithMockJdkAndIdeaAnnotations(ConfigurationKind.JDK_ONLY);
}
public void testOldPackageKotlinInfo() throws Exception {
loadText("package " + PACKAGE_NAME + "\n" +
"\n" +
"fun foo() = 42\n" +
"val bar = 239\n" +
"\n" +
"class A\n" +
"class B\n" +
"object C\n");
Class aClass = generateClass(PackageClassUtils.getPackageClassFqName(PACKAGE_NAME).asString());
Class<? extends Annotation> annotationClass = loadAnnotationClassQuietly(JvmAnnotationNames.KOTLIN_PACKAGE.asString());
assertTrue(aClass.isAnnotationPresent(annotationClass));
Annotation kotlinPackage = aClass.getAnnotation(annotationClass);
String[] data = (String[]) CodegenTestUtil.getAnnotationAttribute(kotlinPackage, "data");
assertNotNull(data);
String[] strings = (String[]) CodegenTestUtil.getAnnotationAttribute(kotlinPackage, "strings");
assertNotNull(strings);
PackageData packageData = JvmProtoBufUtil.readPackageDataFrom(data, strings);
Set<String> callableNames = collectCallableNames(
packageData.getPackageProto().getFunctionList(),
packageData.getPackageProto().getPropertyList(),
packageData.getNameResolver()
);
assertEmpty(callableNames);
}
public void testPackagePartKotlinInfo() throws Exception {
loadText("package " + PACKAGE_NAME + "\n" +
"\n" +
@@ -81,7 +51,7 @@ public class KotlinPackageAnnotationTest extends CodegenTestCase {
"class A\n" +
"class B\n" +
"object C\n");
Class aClass = generateClass(PackagePartClassUtils.getPackagePartFqName(PACKAGE_NAME, DEFAULT_TEST_FILE_NAME).asString());
Class aClass = generateFileClass();
Class<? extends Annotation> annotationClass = loadAnnotationClassQuietly(JvmAnnotationNames.KOTLIN_FILE_FACADE.asString());
assertTrue(aClass.isAnnotationPresent(annotationClass));
@@ -159,7 +159,7 @@ public class PrimitiveTypesTest extends CodegenTestCase {
public void testCastOnStack() throws Exception {
loadText("fun foo(l: Long): Double = l.toDouble()");
Class<?> mainClass = generatePackagePartClass();
Class<?> mainClass = generateFileClass();
Method main = mainClass.getDeclaredMethod("foo", long.class);
double result = (Double) main.invoke(null, 42L);
assertTrue(Math.abs(42L - result) <= 1e-9);
@@ -73,7 +73,7 @@ public class PropertyGenTest extends CodegenTestCase {
public void testPrivatePropertyInPackage() throws Exception {
loadText("private val x = 239");
Class<?> nsClass = generatePackagePartClass();
Class<?> nsClass = generateFileClass();
Field[] fields = nsClass.getDeclaredFields();
assertEquals(1, fields.length);
Field field = fields[0];
@@ -31,17 +31,6 @@ public class SourceInfoGenTest extends CodegenTestCase {
createEnvironmentWithMockJdkAndIdeaAnnotations(ConfigurationKind.JDK_ONLY);
}
public void testSingleFilePackage() {
String producer = "foo1.kt";
loadFiles(TEST_FOLDER + producer);
assertEquals(producer, getProducerInfo("foo/FooPackage.class"));
}
public void testMultiFilePackage() {
loadFiles(TEST_FOLDER + "foo1.kt", TEST_FOLDER + "foo2.kt");
assertEquals(null, getProducerInfo("foo/FooPackage.class"));
}
public void testSingleClass() {
String producer = "singleClass.kt";
loadFiles(TEST_FOLDER + producer);
@@ -27,8 +27,10 @@ import org.jetbrains.kotlin.cli.jvm.compiler.EnvironmentConfigFiles;
import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment;
import org.jetbrains.kotlin.cli.jvm.config.JvmContentRootsKt;
import org.jetbrains.kotlin.codegen.CodegenTestCase;
import org.jetbrains.kotlin.codegen.GeneratedClassLoader;
import org.jetbrains.kotlin.codegen.GenerationUtils;
import org.jetbrains.kotlin.config.CompilerConfiguration;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.psi.JetFile;
import org.jetbrains.kotlin.cli.jvm.compiler.JvmPackagePartProvider;
import org.jetbrains.kotlin.test.ConfigurationKind;
@@ -44,7 +46,6 @@ import java.util.Collections;
import java.util.List;
import static org.jetbrains.kotlin.codegen.CodegenTestUtil.compileJava;
import static org.jetbrains.kotlin.load.kotlin.PackageClassUtils.getPackageClassFqName;
public abstract class AbstractBlackBoxCodegenTest extends CodegenTestCase {
public void doTest(@NotNull String filename) {
@@ -176,19 +177,42 @@ public abstract class AbstractBlackBoxCodegenTest extends CodegenTestCase {
}
protected void blackBox() {
// If there are many files, the first of them should contain the 'box(): String' function
JetFile firstFile = myFiles.getPsiFiles().get(0);
String fqName = getPackageClassFqName(firstFile.getPackageFqName()).asString();
Class<?> aClass = generateClass(fqName);
try {
Method method = aClass.getMethod("box");
String r = (String) method.invoke(null);
assertEquals("OK", r);
// If there are many files, the first 'box(): String' function will be executed.
GeneratedClassLoader generatedClassLoader = generateAndCreateClassLoader();
for (JetFile firstFile : myFiles.getPsiFiles()) {
String className = JvmFileClassUtil.getFileClassInfoNoResolve(firstFile).getFacadeClassFqName().asString();
Class<?> aClass = getGeneratedClass(generatedClassLoader, className);
try {
Method method = getBoxMethodOrNull(aClass);
if (method != null) {
String r = (String) method.invoke(null);
assertEquals("OK", r);
return;
}
}
catch (Throwable e) {
System.out.println(generateToText());
throw ExceptionUtilsKt.rethrow(e);
}
}
catch (Throwable e) {
System.out.println(generateToText());
throw ExceptionUtilsKt.rethrow(e);
}
private static Class<?> getGeneratedClass(GeneratedClassLoader generatedClassLoader, String className) {
try {
return generatedClassLoader.loadClass(className);
}
catch (ClassNotFoundException e) {
fail("No class file was generated for: " + className);
}
return null;
}
private static Method getBoxMethodOrNull(Class<?> aClass) {
try {
return aClass.getMethod("box");
}
catch (NoSuchMethodException e){
return null;
}
}
}
@@ -255,12 +255,6 @@ public class BlackBoxWithJavaCodegenTestGenerated extends AbstractBlackBoxCodege
doTestWithJava(fileName);
}
@TestMetadata("withPackageFacade")
public void testWithPackageFacade() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithJava/fileClasses/withPackageFacade/");
doTestWithJava(fileName);
}
}
@TestMetadata("compiler/testData/codegen/boxWithJava/interfaces")
@@ -106,18 +106,6 @@ public class BlackBoxWithStdlibCodegenTestGenerated extends AbstractBlackBoxCode
doTestWithStdlib(fileName);
}
@TestMetadata("packageFacadeIsDeprecated.kt")
public void testPackageFacadeIsDeprecated() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/annotations/packageFacadeIsDeprecated.kt");
doTestWithStdlib(fileName);
}
@TestMetadata("packageFacadeMethodsAnnotation.kt")
public void testPackageFacadeMethodsAnnotation() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/annotations/packageFacadeMethodsAnnotation.kt");
doTestWithStdlib(fileName);
}
@TestMetadata("parameterWithPrimitiveType.kt")
public void testParameterWithPrimitiveType() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/annotations/parameterWithPrimitiveType.kt");
@@ -31,7 +31,7 @@ public class ProgressionUtilTest extends UsefulTestCase {
@Override
protected void setUp() throws Exception {
super.setUp();
Class<?> progressionUtil = ForTestCompileRuntime.runtimeAndReflectJarClassLoader().loadClass("kotlin.internal.InternalPackage");
Class<?> progressionUtil = ForTestCompileRuntime.runtimeAndReflectJarClassLoader().loadClass("kotlin.internal.ProgressionUtilKt");
this.intMethod = progressionUtil.getMethod("getProgressionFinalElement", int.class, int.class, int.class);
this.longMethod = progressionUtil.getMethod("getProgressionFinalElement", long.class, long.class, long.class);
}