Introduce FirProperty.hasBackingField & use it in FIR2IR

This commit is contained in:
Mikhail Glukhikh
2020-08-25 17:58:25 +03:00
parent c6417696cf
commit 962059a878
2 changed files with 27 additions and 21 deletions
@@ -674,30 +674,27 @@ class Fir2IrDeclarationStorage(
val delegate = property.delegate
val getter = property.getter
val setter = property.setter
// TODO: this checks are very preliminary, FIR resolve should determine backing field presence itself
if (property.isConst || (property.modality != Modality.ABSTRACT && (irParent !is IrClass || !irParent.isInterface))) {
if (initializer != null ||
getter is FirDefaultPropertyGetter ||
property.isVar && setter is FirDefaultPropertySetter ||
property.isReferredViaField == true
) {
backingField = createBackingField(
property, IrDeclarationOrigin.PROPERTY_BACKING_FIELD, descriptor,
components.visibilityConverter.convertToOldVisibility(property.fieldVisibility),
property.name, property.isVal, initializer, type
).also { field ->
if (initializer is FirConstExpression<*>) {
// TODO: Normally we shouldn't have error type here
val constType = initializer.typeRef.toIrType().takeIf { it !is IrErrorType } ?: type
field.initializer = factory.createExpressionBody(initializer.toIrConst(constType))
if (property.hasBackingField) {
backingField = if (delegate != null) {
createBackingField(
property, IrDeclarationOrigin.PROPERTY_DELEGATE, descriptor,
components.visibilityConverter.convertToOldVisibility(property.fieldVisibility),
Name.identifier("${property.name}\$delegate"), true, delegate
)
} else {
createBackingField(
property, IrDeclarationOrigin.PROPERTY_BACKING_FIELD, descriptor,
components.visibilityConverter.convertToOldVisibility(property.fieldVisibility),
property.name, property.isVal, initializer, type
).also { field ->
if (initializer is FirConstExpression<*>) {
// TODO: Normally we shouldn't have error type here
val constType = initializer.typeRef.toIrType().takeIf { it !is IrErrorType } ?: type
field.initializer = factory.createExpressionBody(initializer.toIrConst(constType))
}
}
}
} else if (delegate != null) {
backingField = createBackingField(
property, IrDeclarationOrigin.PROPERTY_DELEGATE, descriptor,
components.visibilityConverter.convertToOldVisibility(property.fieldVisibility),
Name.identifier("${property.name}\$delegate"), true, delegate
)
}
if (irParent != null) {
backingField?.parent = irParent
@@ -9,6 +9,8 @@ import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.fir.Visibilities
import org.jetbrains.kotlin.fir.declarations.builder.FirRegularClassBuilder
import org.jetbrains.kotlin.fir.declarations.builder.FirTypeParameterBuilder
import org.jetbrains.kotlin.fir.declarations.impl.FirDefaultPropertyGetter
import org.jetbrains.kotlin.fir.declarations.impl.FirDefaultPropertySetter
import org.jetbrains.kotlin.fir.declarations.impl.FirFileImpl
import org.jetbrains.kotlin.fir.declarations.impl.FirRegularClassImpl
import org.jetbrains.kotlin.fir.symbols.impl.FirAnonymousObjectSymbol
@@ -119,6 +121,13 @@ var FirProperty.isFromVararg: Boolean? by FirDeclarationDataRegistry.data(IsFrom
private object IsReferredViaField : FirDeclarationDataKey()
var FirProperty.isReferredViaField: Boolean? by FirDeclarationDataRegistry.data(IsReferredViaField)
val FirProperty.hasBackingField: Boolean
get() = initializer != null ||
getter is FirDefaultPropertyGetter ||
isVar && setter is FirDefaultPropertySetter ||
delegate != null ||
isReferredViaField == true
inline val FirProperty.hasJvmFieldAnnotation: Boolean
get() = annotations.any {
val classId = it.annotationTypeRef.coneTypeSafe<ConeClassLikeType>()?.classId