[cls] write contracts information to cls stubs
^ KTIJ-24665 this information would be used to create resolved FirElements from stubs, so no ProtoBuf would be kept in memory
This commit is contained in:
+6
-1
@@ -19,6 +19,7 @@ import org.jetbrains.kotlin.resolve.DataClassResolver
|
||||
import org.jetbrains.kotlin.serialization.deserialization.AnnotatedCallableKind
|
||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoContainer
|
||||
import org.jetbrains.kotlin.serialization.deserialization.getName
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.runIf
|
||||
|
||||
fun createPackageDeclarationsStubs(
|
||||
parentStub: StubElement<out PsiElement>,
|
||||
@@ -173,6 +174,7 @@ private class FunctionClsStubBuilder(
|
||||
// Note that arguments passed to stubs here and elsewhere are based on what stabs would be generated based on decompiled code
|
||||
// As functions are never decompiled to fun f() = 1 form, hasBlockBody is always true
|
||||
// This info is anyway irrelevant for the purposes these stubs are used
|
||||
val hasContract = functionProto.hasContract()
|
||||
return KotlinFunctionStubImpl(
|
||||
parent,
|
||||
callableName.ref(),
|
||||
@@ -182,7 +184,10 @@ private class FunctionClsStubBuilder(
|
||||
hasBlockBody = true,
|
||||
hasBody = Flags.MODALITY.get(functionProto.flags) != Modality.ABSTRACT,
|
||||
hasTypeParameterListBeforeFunctionName = functionProto.typeParameterList.isNotEmpty(),
|
||||
mayHaveContract = functionProto.hasContract()
|
||||
mayHaveContract = hasContract,
|
||||
runIf(hasContract) {
|
||||
ClsContractBuilder(c, typeStubBuilder).loadContract(functionProto)
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
+55
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* 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.analysis.decompiler.stub
|
||||
|
||||
import org.jetbrains.kotlin.contracts.description.KtBooleanValueParameterReference
|
||||
import org.jetbrains.kotlin.contracts.description.KtConstantReference
|
||||
import org.jetbrains.kotlin.contracts.description.KtEffectDeclaration
|
||||
import org.jetbrains.kotlin.contracts.description.KtValueParameterReference
|
||||
import org.jetbrains.kotlin.metadata.ProtoBuf
|
||||
import org.jetbrains.kotlin.metadata.deserialization.isInstanceType
|
||||
import org.jetbrains.kotlin.name.StandardClassIds
|
||||
import org.jetbrains.kotlin.psi.stubs.impl.*
|
||||
import org.jetbrains.kotlin.psi.stubs.impl.KotlinContractEffectType.Companion.IGNORE_REFERENCE_PARAMETER_NAME
|
||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoBufContractDeserializer
|
||||
import org.jetbrains.kotlin.serialization.deserialization.getClassId
|
||||
|
||||
class ClsContractBuilder(private val c: ClsStubBuilderContext, private val typeStubBuilder: TypeClsStubBuilder) :
|
||||
ProtoBufContractDeserializer<KotlinTypeBean, Nothing?, ProtoBuf.Function>() {
|
||||
|
||||
fun loadContract(proto: ProtoBuf.Function): List<KtEffectDeclaration<KotlinTypeBean, Nothing?>>? {
|
||||
return proto.contract.effectList.map { loadPossiblyConditionalEffect(it, proto) ?: return null }
|
||||
}
|
||||
|
||||
override fun extractVariable(valueParameterIndex: Int, owner: ProtoBuf.Function): KtValueParameterReference<KotlinTypeBean, Nothing?> {
|
||||
val type = if (valueParameterIndex < 0) {
|
||||
owner.receiverType
|
||||
} else owner.valueParameterList[valueParameterIndex].type
|
||||
return if (type.hasClassName() && c.nameResolver.getClassId(type.className) == StandardClassIds.Boolean) {
|
||||
KtBooleanValueParameterReference(valueParameterIndex, name = IGNORE_REFERENCE_PARAMETER_NAME)
|
||||
} else KtValueParameterReference(valueParameterIndex, name = IGNORE_REFERENCE_PARAMETER_NAME)
|
||||
}
|
||||
|
||||
override fun extractType(proto: ProtoBuf.Expression): KotlinTypeBean? {
|
||||
return typeStubBuilder.createKotlinTypeBean(proto.isInstanceType(c.typeTable))
|
||||
}
|
||||
|
||||
override fun loadConstant(value: ProtoBuf.Expression.ConstantValue): KtConstantReference<KotlinTypeBean, Nothing?> {
|
||||
return when (value) {
|
||||
ProtoBuf.Expression.ConstantValue.TRUE -> KotlinContractConstantValues.TRUE
|
||||
ProtoBuf.Expression.ConstantValue.FALSE -> KotlinContractConstantValues.FALSE
|
||||
ProtoBuf.Expression.ConstantValue.NULL -> KotlinContractConstantValues.NULL
|
||||
}
|
||||
}
|
||||
|
||||
override fun getNotNull(): KtConstantReference<KotlinTypeBean, Nothing?> {
|
||||
return KotlinContractConstantValues.NOT_NULL
|
||||
}
|
||||
|
||||
override fun getWildcard(): KtConstantReference<KotlinTypeBean, Nothing?> {
|
||||
return KotlinContractConstantValues.WILDCARD
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -150,7 +150,7 @@ class TypeClsStubBuilder(private val c: ClsStubBuilderContext) {
|
||||
}
|
||||
}
|
||||
|
||||
private fun createKotlinTypeBean(
|
||||
fun createKotlinTypeBean(
|
||||
type: Type?
|
||||
): KotlinTypeBean? {
|
||||
if (type == null) return null
|
||||
|
||||
Reference in New Issue
Block a user