Write kotlin metadata on class-files for coroutine state machines

Otherwise it breaks JPS assumptions, that leads to exceptions like:
Error:Kotlin: [Internal Error] java.lang.AssertionError: Couldn't load KotlinClass from /Users/jetbrains/IdeaProjects/KotlinPlaygroundBeta11/out/production/KotlinPlaygroundBeta11/Counter$both$1.class; it may happen because class doesn't have valid Kotlin annotations
    at org.jetbrains.kotlin.build.GeneratedJvmClass.<init>(generatedFiles.kt:36)
    at org.jetbrains.kotlin.jps.build.KotlinBuilder.getGeneratedFiles(KotlinBuilder.kt:469)
    at org.jetbrains.kotlin.jps.build.KotlinBuilder.doBuild(KotlinBuilder.kt:241)
    at org.jetbrains.kotlin.jps.build.KotlinBuilder.build(KotlinBuilder.kt:140)
...
This commit is contained in:
Denis Zharkov
2017-01-16 16:40:26 +03:00
parent 93b2c56bb4
commit 9f217de10b
9 changed files with 53 additions and 4 deletions
@@ -233,10 +233,7 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
protected void generateKotlinMetadataAnnotation() {
FunctionDescriptor freeLambdaDescriptor = createFreeLambdaDescriptor(funDescriptor);
Method method = v.getSerializationBindings().get(METHOD_FOR_FUNCTION, funDescriptor);
// Can be null for named suspend function
if (method == null) return;
assert method != null : "No method for " + funDescriptor;
v.getSerializationBindings().put(METHOD_FOR_FUNCTION, freeLambdaDescriptor, method);
final DescriptorSerializer serializer =
@@ -27,6 +27,7 @@ import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl
import org.jetbrains.kotlin.descriptors.impl.ValueParameterDescriptorImpl
import org.jetbrains.kotlin.load.kotlin.header.KotlinClassHeader
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.KtDeclarationWithBody
import org.jetbrains.kotlin.psi.KtElement
@@ -43,6 +44,7 @@ import org.jetbrains.kotlin.types.typeUtil.asTypeProjection
import org.jetbrains.kotlin.types.typeUtil.makeNullable
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
import org.jetbrains.kotlin.utils.singletonOrEmptyList
import org.jetbrains.org.objectweb.asm.AnnotationVisitor
import org.jetbrains.org.objectweb.asm.MethodVisitor
import org.jetbrains.org.objectweb.asm.Opcodes
import org.jetbrains.org.objectweb.asm.Type
@@ -301,6 +303,17 @@ class CoroutineCodegen(
)
}
override fun generateKotlinMetadataAnnotation() {
if (originalSuspendLambdaDescriptor != null) {
super.generateKotlinMetadataAnnotation()
}
else {
writeKotlinMetadata(v, state, KotlinClassHeader.Kind.SYNTHETIC_CLASS, 0) {
// Do not write method metadata for raw coroutine state machines
}
}
}
companion object {
@JvmStatic