IR: IrPropertySymbol introduced, some code cleaned up

#KT-30304
This commit is contained in:
Dmitry Petrov
2019-02-27 13:56:13 +03:00
parent 1bc35b1b0c
commit 04fad012a0
34 changed files with 345 additions and 170 deletions
@@ -19,7 +19,6 @@ package org.jetbrains.kotlin.psi2ir.generators
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.declarations.impl.IrPropertyImpl
import org.jetbrains.kotlin.ir.descriptors.IrImplementingDelegateDescriptorImpl
import org.jetbrains.kotlin.ir.expressions.impl.*
import org.jetbrains.kotlin.ir.expressions.mapValueParameters
@@ -204,13 +203,13 @@ class ClassGenerator(
irDelegate: IrField,
delegatedDescriptor: PropertyDescriptor,
overriddenDescriptor: PropertyDescriptor
): IrPropertyImpl {
): IrProperty {
val startOffset = irDelegate.startOffset
val endOffset = irDelegate.endOffset
val irProperty = IrPropertyImpl(
val irProperty = context.symbolTable.declareProperty(
startOffset, endOffset, IrDeclarationOrigin.DELEGATED_MEMBER,
false, delegatedDescriptor
delegatedDescriptor
)
irProperty.getter = generateDelegatedFunction(irDelegate, delegatedDescriptor.getter!!, overriddenDescriptor.getter!!)
@@ -23,7 +23,6 @@ import org.jetbrains.kotlin.ir.builders.irGet
import org.jetbrains.kotlin.ir.builders.irReturn
import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.declarations.impl.IrLocalDelegatedPropertyImpl
import org.jetbrains.kotlin.ir.declarations.impl.IrPropertyImpl
import org.jetbrains.kotlin.ir.descriptors.IrLocalDelegatedPropertyDelegateDescriptor
import org.jetbrains.kotlin.ir.descriptors.IrLocalDelegatedPropertyDelegateDescriptorImpl
import org.jetbrains.kotlin.ir.descriptors.IrPropertyDelegateDescriptor
@@ -55,10 +54,10 @@ class DelegatedPropertyGenerator(declarationGenerator: DeclarationGenerator) : D
val kPropertyType = getKPropertyTypeForDelegatedProperty(propertyDescriptor)
val irProperty = IrPropertyImpl(
val irProperty = context.symbolTable.declareProperty(
ktProperty.startOffsetSkippingComments, ktProperty.endOffset, IrDeclarationOrigin.DEFINED,
isDelegated = true,
descriptor = propertyDescriptor
propertyDescriptor,
isDelegated = true
).apply {
backingField = generateDelegateFieldForProperty(propertyDescriptor, kPropertyType, ktDelegate)
}
@@ -145,14 +144,15 @@ class DelegatedPropertyGenerator(declarationGenerator: DeclarationGenerator) : D
val irDelegateInitializer = declarationGenerator.generateInitializerBody(scopeOwner, ktDelegateExpression)
val provideDelegateResolvedCall = get(BindingContext.PROVIDE_DELEGATE_RESOLVED_CALL, property)
?: return irDelegateInitializer
?: return irDelegateInitializer
val statementGenerator = createBodyGenerator(scopeOwner).createStatementGenerator()
val provideDelegateCall = statementGenerator.pregenerateCall(provideDelegateResolvedCall)
provideDelegateCall.setExplicitReceiverValue(OnceExpressionValue(irDelegateInitializer.expression))
provideDelegateCall.irValueArgumentsByIndex[1] = createCallableReference(ktDelegate, kPropertyType, property, scopeOwner)
val irProvideDelegate =
CallGenerator(statementGenerator).generateCall(ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset, provideDelegateCall)
val irProvideDelegate = CallGenerator(statementGenerator).generateCall(
ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset, provideDelegateCall
)
return IrExpressionBodyImpl(irProvideDelegate)
}
@@ -241,30 +241,30 @@ class DelegatedPropertyGenerator(declarationGenerator: DeclarationGenerator) : D
val getterDescriptor = variableDescriptor.getter!!
val delegateReceiverValue = createVariableValueForDelegate(irDelegate.symbol, ktDelegate)
irLocalDelegatedProperty.getter =
createLocalPropertyAccessor(getterDescriptor, ktDelegate) { irGetter ->
generateDelegatedPropertyGetterBody(
irGetter, ktDelegate, getterDescriptor, delegateReceiverValue,
createLocalDelegatedPropertyReference(
ktDelegate, kPropertyType,
variableDescriptor, irDelegate.symbol,
irGetter.symbol
)
createLocalPropertyAccessor(getterDescriptor, ktDelegate) { irGetter ->
generateDelegatedPropertyGetterBody(
irGetter, ktDelegate, getterDescriptor, delegateReceiverValue,
createLocalDelegatedPropertyReference(
ktDelegate, kPropertyType,
variableDescriptor, irDelegate.symbol,
irGetter.symbol
)
}
)
}
if (variableDescriptor.isVar) {
val setterDescriptor = variableDescriptor.setter!!
irLocalDelegatedProperty.setter =
createLocalPropertyAccessor(setterDescriptor, ktDelegate) { irSetter ->
generateDelegatedPropertySetterBody(
irSetter, ktDelegate, setterDescriptor, delegateReceiverValue,
createLocalDelegatedPropertyReference(
ktDelegate, kPropertyType,
variableDescriptor, irDelegate.symbol,
irSetter.symbol
)
createLocalPropertyAccessor(setterDescriptor, ktDelegate) { irSetter ->
generateDelegatedPropertySetterBody(
irSetter, ktDelegate, setterDescriptor, delegateReceiverValue,
createLocalDelegatedPropertyReference(
ktDelegate, kPropertyType,
variableDescriptor, irDelegate.symbol,
irSetter.symbol
)
}
)
}
}
return irLocalDelegatedProperty
@@ -320,14 +320,21 @@ class DelegatedPropertyGenerator(declarationGenerator: DeclarationGenerator) : D
val provideDelegateCall = statementGenerator.pregenerateCall(provideDelegateResolvedCall).apply {
setExplicitReceiverValue(OnceExpressionValue(irDelegateInitializer))
irValueArgumentsByIndex[1] =
createLocalDelegatedPropertyReference(ktDelegate, kPropertyType, variableDescriptor, delegateSymbol, scopeOwner)
createLocalDelegatedPropertyReference(ktDelegate, kPropertyType, variableDescriptor, delegateSymbol, scopeOwner)
}
return CallGenerator(statementGenerator).generateCall(ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset, provideDelegateCall)
return CallGenerator(statementGenerator).generateCall(
ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset, provideDelegateCall
)
}
private fun createVariableValueForDelegate(irDelegate: IrVariableSymbol, ktDelegate: KtPropertyDelegate) =
VariableLValue(context, ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset, irDelegate, irDelegate.descriptor.type.toIrType())
VariableLValue(
context,
ktDelegate.startOffsetSkippingComments, ktDelegate.endOffset,
irDelegate,
irDelegate.descriptor.type.toIrType()
)
private inline fun createLocalPropertyAccessor(
getterDescriptor: VariableAccessorDescriptor,
@@ -19,7 +19,6 @@ package org.jetbrains.kotlin.psi2ir.generators
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.descriptors.Visibilities
import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.declarations.impl.IrPropertyImpl
import org.jetbrains.kotlin.ir.expressions.IrExpressionBody
import org.jetbrains.kotlin.ir.expressions.IrStatementOrigin
import org.jetbrains.kotlin.ir.expressions.impl.IrExpressionBodyImpl
@@ -27,9 +26,9 @@ import org.jetbrains.kotlin.ir.expressions.impl.IrGetValueImpl
import org.jetbrains.kotlin.ir.util.declareFieldWithOverrides
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.endOffset
import org.jetbrains.kotlin.psi.psiUtil.startOffsetSkippingComments
import org.jetbrains.kotlin.psi2ir.pureEndOffsetOrUndefined
import org.jetbrains.kotlin.psi2ir.pureStartOffsetOrUndefined
import org.jetbrains.kotlin.psi.psiUtil.startOffsetSkippingComments
import org.jetbrains.kotlin.resolve.BindingContext
import org.jetbrains.kotlin.resolve.hasBackingField
@@ -47,33 +46,34 @@ class PropertyGenerator(declarationGenerator: DeclarationGenerator) : Declaratio
val propertyDescriptor = getOrFail(BindingContext.PRIMARY_CONSTRUCTOR_PARAMETER, ktParameter)
val irPropertyType = propertyDescriptor.type.toIrType()
return IrPropertyImpl(
return context.symbolTable.declareProperty(
ktParameter.startOffsetSkippingComments, ktParameter.endOffset,
IrDeclarationOrigin.DEFINED, false,
propertyDescriptor
IrDeclarationOrigin.DEFINED,
propertyDescriptor,
isDelegated = false
).also { irProperty ->
irProperty.backingField =
generatePropertyBackingField(ktParameter, propertyDescriptor) {
IrExpressionBodyImpl(
IrGetValueImpl(
ktParameter.startOffsetSkippingComments, ktParameter.endOffset,
irPropertyType,
irValueParameter.symbol,
IrStatementOrigin.INITIALIZE_PROPERTY_FROM_PARAMETER
)
generatePropertyBackingField(ktParameter, propertyDescriptor) {
IrExpressionBodyImpl(
IrGetValueImpl(
ktParameter.startOffsetSkippingComments, ktParameter.endOffset,
irPropertyType,
irValueParameter.symbol,
IrStatementOrigin.INITIALIZE_PROPERTY_FROM_PARAMETER
)
}
)
}
val getter = propertyDescriptor.getter
?: throw AssertionError("Property declared in primary constructor has no getter: $propertyDescriptor")
?: throw AssertionError("Property declared in primary constructor has no getter: $propertyDescriptor")
irProperty.getter =
FunctionGenerator(declarationGenerator).generateDefaultAccessorForPrimaryConstructorParameter(getter, ktParameter)
FunctionGenerator(declarationGenerator).generateDefaultAccessorForPrimaryConstructorParameter(getter, ktParameter)
if (propertyDescriptor.isVar) {
val setter = propertyDescriptor.setter
?: throw AssertionError("Property declared in primary constructor has no setter: $propertyDescriptor")
?: throw AssertionError("Property declared in primary constructor has no setter: $propertyDescriptor")
irProperty.setter =
FunctionGenerator(declarationGenerator).generateDefaultAccessorForPrimaryConstructorParameter(setter, ktParameter)
FunctionGenerator(declarationGenerator).generateDefaultAccessorForPrimaryConstructorParameter(setter, ktParameter)
}
}
}
@@ -101,35 +101,33 @@ class PropertyGenerator(declarationGenerator: DeclarationGenerator) : Declaratio
.generateDelegatedProperty(ktProperty, ktDelegate, propertyDescriptor)
private fun generateSimpleProperty(ktProperty: KtProperty, propertyDescriptor: PropertyDescriptor): IrProperty =
IrPropertyImpl(
context.symbolTable.declareProperty(
ktProperty.startOffsetSkippingComments, ktProperty.endOffset,
IrDeclarationOrigin.DEFINED,
false,
propertyDescriptor
propertyDescriptor,
isDelegated = false
).buildWithScope { irProperty ->
irProperty.backingField =
if (propertyDescriptor.hasBackingField(context.bindingContext))
generatePropertyBackingField(ktProperty, propertyDescriptor) { irField ->
ktProperty.initializer?.let { ktInitializer ->
val compileTimeConst = propertyDescriptor.compileTimeInitializer
if (propertyDescriptor.isConst && compileTimeConst != null)
IrExpressionBodyImpl(
context.constantValueGenerator.generateConstantValueAsExpression(
ktInitializer.startOffsetSkippingComments, ktInitializer.endOffset,
compileTimeConst
)
if (propertyDescriptor.hasBackingField(context.bindingContext))
generatePropertyBackingField(ktProperty, propertyDescriptor) { irField ->
ktProperty.initializer?.let { ktInitializer ->
val compileTimeConst = propertyDescriptor.compileTimeInitializer
if (propertyDescriptor.isConst && compileTimeConst != null)
IrExpressionBodyImpl(
context.constantValueGenerator.generateConstantValueAsExpression(
ktInitializer.startOffsetSkippingComments, ktInitializer.endOffset,
compileTimeConst
)
else
declarationGenerator.generateInitializerBody(irField.symbol, ktInitializer)
}
)
else
declarationGenerator.generateInitializerBody(irField.symbol, ktInitializer)
}
else
null
}
else
null
irProperty.getter = generateGetterIfRequired(ktProperty, propertyDescriptor)
irProperty.setter = generateSetterIfRequired(ktProperty, propertyDescriptor)
irProperty.metadata = MetadataSource.Property(propertyDescriptor)
}
fun generateFakeOverrideProperty(propertyDescriptor: PropertyDescriptor, ktElement: KtPureElement): IrProperty? {
@@ -142,21 +140,20 @@ class PropertyGenerator(declarationGenerator: DeclarationGenerator) : Declaratio
if (propertyDescriptor.hasBackingField(context.bindingContext))
context.symbolTable.declareFieldWithOverrides(
startOffset, endOffset, IrDeclarationOrigin.FAKE_OVERRIDE,
propertyDescriptor, propertyDescriptor.type.toIrType(),
{ it.hasBackingField(context.bindingContext) }
)
propertyDescriptor, propertyDescriptor.type.toIrType()
) { it.hasBackingField(context.bindingContext) }
else
null
return IrPropertyImpl(
startOffset, endOffset,
IrDeclarationOrigin.FAKE_OVERRIDE,
false,
propertyDescriptor,
backingField,
propertyDescriptor.getter?.let { FunctionGenerator(declarationGenerator).generateFakeOverrideFunction(it, ktElement) },
propertyDescriptor.setter?.let { FunctionGenerator(declarationGenerator).generateFakeOverrideFunction(it, ktElement) }
)
return context.symbolTable.declareProperty(startOffset, endOffset, IrDeclarationOrigin.FAKE_OVERRIDE, propertyDescriptor).apply {
this.backingField = backingField
this.getter = propertyDescriptor.getter?.let {
FunctionGenerator(declarationGenerator).generateFakeOverrideFunction(it, ktElement)
}
this.setter = propertyDescriptor.setter?.let {
FunctionGenerator(declarationGenerator).generateFakeOverrideFunction(it, ktElement)
}
}
}
private fun generateGetterIfRequired(ktProperty: KtProperty, property: PropertyDescriptor): IrSimpleFunction? {
@@ -172,7 +169,7 @@ class PropertyGenerator(declarationGenerator: DeclarationGenerator) : Declaratio
private fun getPropertyDescriptor(ktProperty: KtProperty): PropertyDescriptor {
val variableDescriptor = getOrFail(BindingContext.VARIABLE, ktProperty)
return variableDescriptor as? PropertyDescriptor ?: TODO("not a property?")
return variableDescriptor as? PropertyDescriptor ?: TODO("not a property: $variableDescriptor")
}
}
@@ -48,7 +48,7 @@ class ReflectionReferencesGenerator(statementGenerator: StatementGenerator) : St
} else {
val typeConstructorDeclaration = lhs.type.constructor.declarationDescriptor
val typeClass = typeConstructorDeclaration
?: throw AssertionError("Unexpected type constructor for ${lhs.type}: $typeConstructorDeclaration")
?: throw AssertionError("Unexpected type constructor for ${lhs.type}: $typeConstructorDeclaration")
IrClassReferenceImpl(
ktClassLiteral.startOffsetSkippingComments, ktClassLiteral.endOffset, resultType,
context.symbolTable.referenceClassifier(typeClass), lhs.type.toIrType()
@@ -139,17 +139,16 @@ class ReflectionReferencesGenerator(statementGenerator: StatementGenerator) : St
val getterDescriptor = propertyDescriptor.getter
val setterDescriptor = if (mutable) propertyDescriptor.setter else null
val fieldSymbol = if (getterDescriptor == null) context.symbolTable.referenceField(propertyDescriptor) else null
val getterSymbol = getterDescriptor?.let { context.symbolTable.referenceSimpleFunction(it.original) }
val setterSymbol = setterDescriptor?.let { context.symbolTable.referenceSimpleFunction(it.original) }
return IrPropertyReferenceImpl(
startOffset, endOffset, type.toIrType(),
propertyDescriptor, propertyDescriptor.typeParametersCount,
fieldSymbol, getterSymbol, setterSymbol,
context.symbolTable.referenceProperty(propertyDescriptor.original),
propertyDescriptor.typeParametersCount,
getterDescriptor?.run { context.symbolTable.referenceField(propertyDescriptor) },
getterDescriptor?.let { context.symbolTable.referenceSimpleFunction(it.original) },
setterDescriptor?.let { context.symbolTable.referenceSimpleFunction(it.original) },
origin
).apply {
putTypeArguments(typeArguments) { it.toIrType()}
putTypeArguments(typeArguments) { it.toIrType() }
}
}