IR: remove field fake override usage
Still a problem: Java static fields.
This commit is contained in:
+1
-1
@@ -535,7 +535,7 @@ class ExpressionCodegen(
|
||||
assert(callee.constantValue() == null) { "access of const val: ${expression.dump()}" }
|
||||
}
|
||||
|
||||
val realField = callee.resolveFakeOverride()!!
|
||||
val realField = callee
|
||||
val fieldType = typeMapper.mapType(realField.type)
|
||||
val fieldName = realField.name.asString()
|
||||
val isStatic = expression.receiver == null
|
||||
|
||||
@@ -339,7 +339,7 @@ fun IrProperty.needsAccessor(accessor: IrSimpleFunction): Boolean = when {
|
||||
// Properties in annotation classes become abstract methods named after the property.
|
||||
(parent as? IrClass)?.kind == ClassKind.ANNOTATION_CLASS -> true
|
||||
// @JvmField properties have no getters/setters
|
||||
backingField?.hasAnnotation(JvmAbi.JVM_FIELD_ANNOTATION_FQ_NAME) == true -> false
|
||||
resolveFakeOverride()?.backingField?.hasAnnotation(JvmAbi.JVM_FIELD_ANNOTATION_FQ_NAME) == true -> false
|
||||
// We do not produce default accessors for private fields
|
||||
else -> accessor.origin != IrDeclarationOrigin.DEFAULT_PROPERTY_ACCESSOR || !Visibilities.isPrivate(accessor.visibility)
|
||||
}
|
||||
|
||||
+3
-6
@@ -29,10 +29,7 @@ import org.jetbrains.kotlin.ir.expressions.impl.IrBlockBodyImpl
|
||||
import org.jetbrains.kotlin.ir.types.classifierOrFail
|
||||
import org.jetbrains.kotlin.ir.types.makeNotNull
|
||||
import org.jetbrains.kotlin.ir.types.typeWith
|
||||
import org.jetbrains.kotlin.ir.util.coerceToUnit
|
||||
import org.jetbrains.kotlin.ir.util.hasAnnotation
|
||||
import org.jetbrains.kotlin.ir.util.render
|
||||
import org.jetbrains.kotlin.ir.util.transformDeclarationsFlat
|
||||
import org.jetbrains.kotlin.ir.util.*
|
||||
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
|
||||
import org.jetbrains.kotlin.load.java.JvmAbi
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
@@ -69,10 +66,10 @@ class JvmPropertiesLowering(private val backendContext: JvmBackendContext) : IrE
|
||||
}
|
||||
|
||||
private fun IrBuilderWithScope.substituteSetter(irProperty: IrProperty, expression: IrCall): IrExpression =
|
||||
patchReceiver(irSetField(expression.dispatchReceiver, irProperty.backingField!!, expression.getValueArgument(0)!!))
|
||||
patchReceiver(irSetField(expression.dispatchReceiver, irProperty.resolveFakeOverride()!!.backingField!!, expression.getValueArgument(0)!!))
|
||||
|
||||
private fun IrBuilderWithScope.substituteGetter(irProperty: IrProperty, expression: IrCall): IrExpression {
|
||||
val backingField = irProperty.backingField!!
|
||||
val backingField = irProperty.resolveFakeOverride()!!.backingField!!
|
||||
val value = irGetField(expression.dispatchReceiver, backingField)
|
||||
return if (irProperty.isLateinit) {
|
||||
irBlock {
|
||||
|
||||
+13
-14
@@ -326,7 +326,7 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
copyAllParamsToArgs(it, accessor)
|
||||
}
|
||||
|
||||
private fun makeGetterAccessorSymbol(fieldSymbol: IrFieldSymbol, parent: IrDeclarationParent): IrSimpleFunctionSymbol =
|
||||
private fun makeGetterAccessorSymbol(fieldSymbol: IrFieldSymbol, parent: IrClass): IrSimpleFunctionSymbol =
|
||||
buildFun {
|
||||
origin = JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
name = fieldSymbol.owner.accessorNameForGetter()
|
||||
@@ -338,8 +338,9 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
pendingAccessorsToAdd.add(accessor)
|
||||
|
||||
if (!fieldSymbol.owner.isStatic) {
|
||||
// Accessors are always to one's own fields.
|
||||
accessor.addValueParameter(
|
||||
"\$this", fieldSymbol.owner.parentAsClass.defaultType, JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
"\$this", parent.defaultType, JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
)
|
||||
}
|
||||
|
||||
@@ -347,22 +348,21 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
}.symbol
|
||||
|
||||
private fun createAccessorBodyForGetter(targetField: IrField, accessor: IrSimpleFunction): IrBody {
|
||||
val resolvedTargetField = targetField.resolveFakeOverride()!!
|
||||
val maybeDispatchReceiver =
|
||||
if (resolvedTargetField.isStatic) null
|
||||
if (targetField.isStatic) null
|
||||
else IrGetValueImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, accessor.valueParameters[0].symbol)
|
||||
return IrExpressionBodyImpl(
|
||||
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
|
||||
IrGetFieldImpl(
|
||||
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
|
||||
resolvedTargetField.symbol,
|
||||
resolvedTargetField.type,
|
||||
targetField.symbol,
|
||||
targetField.type,
|
||||
maybeDispatchReceiver
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
private fun makeSetterAccessorSymbol(fieldSymbol: IrFieldSymbol, parent: IrDeclarationParent): IrSimpleFunctionSymbol =
|
||||
private fun makeSetterAccessorSymbol(fieldSymbol: IrFieldSymbol, parent: IrClass): IrSimpleFunctionSymbol =
|
||||
buildFun {
|
||||
origin = JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
name = fieldSymbol.owner.accessorNameForSetter()
|
||||
@@ -374,8 +374,9 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
pendingAccessorsToAdd.add(accessor)
|
||||
|
||||
if (!fieldSymbol.owner.isStatic) {
|
||||
// Accessors are always to one's own fields.
|
||||
accessor.addValueParameter(
|
||||
"\$this", fieldSymbol.owner.parentAsClass.defaultType, JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
"\$this", parent.defaultType, JvmLoweredDeclarationOrigin.SYNTHETIC_ACCESSOR
|
||||
)
|
||||
}
|
||||
|
||||
@@ -385,19 +386,18 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
}.symbol
|
||||
|
||||
private fun createAccessorBodyForSetter(targetField: IrField, accessor: IrSimpleFunction): IrBody {
|
||||
val resolvedTargetField = targetField.resolveFakeOverride()!!
|
||||
val maybeDispatchReceiver =
|
||||
if (resolvedTargetField.isStatic) null
|
||||
if (targetField.isStatic) null
|
||||
else IrGetValueImpl(UNDEFINED_OFFSET, UNDEFINED_OFFSET, accessor.valueParameters[0].symbol)
|
||||
val value = IrGetValueImpl(
|
||||
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
|
||||
accessor.valueParameters[if (resolvedTargetField.isStatic) 0 else 1].symbol
|
||||
accessor.valueParameters[if (targetField.isStatic) 0 else 1].symbol
|
||||
)
|
||||
return IrExpressionBodyImpl(
|
||||
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
|
||||
IrSetFieldImpl(
|
||||
UNDEFINED_OFFSET, UNDEFINED_OFFSET,
|
||||
resolvedTargetField.symbol,
|
||||
targetField.symbol,
|
||||
maybeDispatchReceiver,
|
||||
value,
|
||||
context.irBuiltIns.unitType
|
||||
@@ -574,8 +574,7 @@ internal class SyntheticAccessorLowering(val context: JvmBackendContext) : IrEle
|
||||
val symbolOwner = owner
|
||||
val declarationRaw = symbolOwner as IrDeclarationWithVisibility
|
||||
val declaration =
|
||||
(declarationRaw as? IrSimpleFunction)?.resolveFakeOverride()
|
||||
?: (declarationRaw as? IrField)?.resolveFakeOverride() ?: declarationRaw
|
||||
(declarationRaw as? IrSimpleFunction)?.resolveFakeOverride() ?: declarationRaw
|
||||
|
||||
// There is never a problem with visibility of inline functions, as those don't end up as Java entities
|
||||
if (declaration is IrFunction && declaration.isInline) return true
|
||||
|
||||
@@ -179,7 +179,7 @@ class CallGenerator(statementGenerator: StatementGenerator) : StatementGenerator
|
||||
|
||||
return if (getMethodDescriptor == null) {
|
||||
call.callReceiver.call { dispatchReceiverValue, _ ->
|
||||
val fieldSymbol = context.symbolTable.referenceField(descriptor.original)
|
||||
val fieldSymbol = context.symbolTable.referenceField(descriptor.resolveFakeOverride().original)
|
||||
IrGetFieldImpl(
|
||||
startOffset, endOffset,
|
||||
fieldSymbol,
|
||||
@@ -416,3 +416,14 @@ fun CallGenerator.generateCall(ktElement: KtElement, call: CallBuilder, origin:
|
||||
|
||||
fun CallGenerator.generateCall(irExpression: IrExpression, call: CallBuilder, origin: IrStatementOrigin? = null) =
|
||||
generateCall(irExpression.startOffset, irExpression.endOffset, call, origin)
|
||||
|
||||
// Only works for descriptors of Java fields.
|
||||
private fun PropertyDescriptor.resolveFakeOverride(): PropertyDescriptor {
|
||||
assert(getter == null)
|
||||
// Fields can only be inherited from objects, so there will be at most one overridden descriptor at each step.
|
||||
var current = this
|
||||
while (current.kind == CallableMemberDescriptor.Kind.FAKE_OVERRIDE) {
|
||||
current = current.overriddenDescriptors.single()
|
||||
}
|
||||
return current
|
||||
}
|
||||
@@ -145,17 +145,7 @@ class PropertyGenerator(declarationGenerator: DeclarationGenerator) : Declaratio
|
||||
val startOffset = ktElement.pureStartOffsetOrUndefined
|
||||
val endOffset = ktElement.pureEndOffsetOrUndefined
|
||||
|
||||
val backingField =
|
||||
if (propertyDescriptor.actuallyHasBackingField(context.bindingContext) && propertyDescriptor.fieldVisibility.admitsFakeOverride)
|
||||
context.symbolTable.declareFieldWithOverrides(
|
||||
startOffset, endOffset, IrDeclarationOrigin.FAKE_OVERRIDE,
|
||||
propertyDescriptor, propertyDescriptor.type.toIrType()
|
||||
) { it.actuallyHasBackingField(context.bindingContext) }
|
||||
else
|
||||
null
|
||||
|
||||
return context.symbolTable.declareProperty(startOffset, endOffset, IrDeclarationOrigin.FAKE_OVERRIDE, propertyDescriptor).apply {
|
||||
this.backingField = backingField
|
||||
this.getter = propertyDescriptor.getter?.let {
|
||||
FunctionGenerator(declarationGenerator).generateFakeOverrideFunction(it, ktElement)
|
||||
}
|
||||
|
||||
@@ -265,6 +265,8 @@ fun IrSimpleFunction.findInterfaceImplementation(): IrSimpleFunction? {
|
||||
return resolveFakeOverride()?.run { if (parentAsClass.isInterface) this else null }
|
||||
}
|
||||
|
||||
fun IrProperty.resolveFakeOverride(): IrProperty? = getter?.resolveFakeOverride()?.correspondingPropertySymbol?.owner
|
||||
|
||||
val IrClass.isAnnotationClass get() = kind == ClassKind.ANNOTATION_CLASS
|
||||
val IrClass.isEnumClass get() = kind == ClassKind.ENUM_CLASS
|
||||
val IrClass.isEnumEntry get() = kind == ClassKind.ENUM_ENTRY
|
||||
|
||||
@@ -24,9 +24,6 @@ FILE fqName:<root> fileName:/Derived.kt
|
||||
receiver: GET_VAR '<this>: <root>.Derived declared in <root>.Derived.setValue' type=<root>.Derived origin=null
|
||||
value: GET_VAR 'value: kotlin.Int declared in <root>.Derived.setValue' type=kotlin.Int origin=null
|
||||
PROPERTY FAKE_OVERRIDE name:value visibility:public modality:FINAL [fake_override,var]
|
||||
FIELD FAKE_OVERRIDE name:value type:kotlin.Int visibility:public [fake_override]
|
||||
overridden:
|
||||
FIELD IR_EXTERNAL_JAVA_DECLARATION_STUB name:value type:kotlin.Int visibility:public
|
||||
FUN FAKE_OVERRIDE name:equals visibility:public modality:OPEN <> ($this:kotlin.Any, other:kotlin.Any?) returnType:kotlin.Boolean [fake_override,operator]
|
||||
overridden:
|
||||
public open fun equals (other: kotlin.Any?): kotlin.Boolean [fake_override,operator] declared in <root>.Base
|
||||
|
||||
@@ -136,9 +136,6 @@ FILE fqName:<root> fileName:/kt16904.kt
|
||||
receiver: GET_VAR '<this>: <root>.Test2 declared in <root>.Test2' type=<root>.Test2 origin=null
|
||||
value: CONST Int type=kotlin.Int value=42
|
||||
PROPERTY FAKE_OVERRIDE name:field visibility:public modality:FINAL [fake_override,var]
|
||||
FIELD FAKE_OVERRIDE name:field type:kotlin.Int visibility:public [fake_override]
|
||||
overridden:
|
||||
FIELD IR_EXTERNAL_JAVA_DECLARATION_STUB name:field type:kotlin.Int visibility:public
|
||||
FUN FAKE_OVERRIDE name:equals visibility:public modality:OPEN <> ($this:kotlin.Any, other:kotlin.Any?) returnType:kotlin.Boolean [fake_override,operator]
|
||||
overridden:
|
||||
public open fun equals (other: kotlin.Any?): kotlin.Boolean [fake_override,operator] declared in <root>.J
|
||||
|
||||
@@ -19,9 +19,6 @@ FILE fqName:<root> fileName:/Derived.kt
|
||||
value: TYPE_OP type=kotlin.String origin=IMPLICIT_CAST typeOperand=kotlin.String
|
||||
GET_VAR 'v: kotlin.Any declared in <root>.Derived.setValue' type=kotlin.Any origin=null
|
||||
PROPERTY FAKE_OVERRIDE name:value visibility:public modality:FINAL [fake_override,var]
|
||||
FIELD FAKE_OVERRIDE name:value type:kotlin.String? visibility:public [fake_override]
|
||||
overridden:
|
||||
FIELD IR_EXTERNAL_JAVA_DECLARATION_STUB name:value type:kotlin.String? visibility:public
|
||||
FUN FAKE_OVERRIDE name:equals visibility:public modality:OPEN <> ($this:kotlin.Any, other:kotlin.Any?) returnType:kotlin.Boolean [fake_override,operator]
|
||||
overridden:
|
||||
public open fun equals (other: kotlin.Any?): kotlin.Boolean [fake_override,operator] declared in <root>.Base
|
||||
|
||||
@@ -18,9 +18,6 @@ FILE fqName:<root> fileName:/javaInnerClass.kt
|
||||
GET_FIELD 'FIELD PROPERTY_BACKING_FIELD name:test type:<root>.J.JInner visibility:private [final]' type=<root>.J.JInner origin=null
|
||||
receiver: GET_VAR '<this>: <root>.Test1 declared in <root>.Test1.<get-test>' type=<root>.Test1 origin=null
|
||||
PROPERTY FAKE_OVERRIDE name:x visibility:public modality:FINAL [fake_override,var]
|
||||
FIELD FAKE_OVERRIDE name:x type:kotlin.Int visibility:public [fake_override]
|
||||
overridden:
|
||||
FIELD IR_EXTERNAL_JAVA_DECLARATION_STUB name:x type:kotlin.Int visibility:public
|
||||
FUN FAKE_OVERRIDE name:bar visibility:public modality:OPEN <> ($this:<root>.J) returnType:kotlin.Unit [fake_override]
|
||||
overridden:
|
||||
public open fun bar (): kotlin.Unit declared in <root>.J
|
||||
|
||||
Reference in New Issue
Block a user