Fir2IrLazyProperty: generate overridden symbols via FirTypeScope

This commit is contained in:
Mikhail Glukhikh
2020-08-05 12:09:09 +03:00
parent 25efad2fd7
commit 02e5f140f4
3 changed files with 5 additions and 98 deletions
@@ -29,7 +29,6 @@ import org.jetbrains.kotlin.fir.scopes.processDirectlyOverriddenFunctions
import org.jetbrains.kotlin.fir.scopes.processDirectlyOverriddenProperties
import org.jetbrains.kotlin.fir.scopes.unsubstitutedScope
import org.jetbrains.kotlin.fir.symbols.AccessorSymbol
import org.jetbrains.kotlin.fir.symbols.Fir2IrClassSymbol
import org.jetbrains.kotlin.fir.symbols.impl.*
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.ir.IrElement
@@ -42,13 +41,10 @@ import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.IrStatementOrigin
import org.jetbrains.kotlin.ir.expressions.impl.*
import org.jetbrains.kotlin.ir.symbols.*
import org.jetbrains.kotlin.ir.symbols.impl.IrClassPublicSymbolImpl
import org.jetbrains.kotlin.ir.symbols.impl.IrClassSymbolImpl
import org.jetbrains.kotlin.ir.types.*
import org.jetbrains.kotlin.ir.types.impl.IrErrorTypeImpl
import org.jetbrains.kotlin.ir.util.SymbolTable
import org.jetbrains.kotlin.ir.util.functions
import org.jetbrains.kotlin.ir.util.isFakeOverride
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.psiUtil.endOffset
import org.jetbrains.kotlin.psi.psiUtil.startOffsetSkippingComments
@@ -338,85 +334,6 @@ internal fun FirProperty.generateOverriddenAccessorSymbols(
return overriddenSet.toList()
}
internal fun IrClass.findMatchingOverriddenSymbolsFromSupertypes(
irBuiltIns: IrBuiltIns,
target: IrDeclaration,
result: MutableList<IrSymbol> = mutableListOf(),
visited: MutableSet<IrClass> = mutableSetOf()
): List<IrSymbol> {
for (superType in superTypes) {
when (val superTypeClass = superType.classOrNull) {
is IrClassSymbolImpl, is IrClassPublicSymbolImpl, is Fir2IrClassSymbol -> {
superTypeClass.owner.findMatchingOverriddenSymbolsFromThisAndSupertypes(irBuiltIns, target, result, visited)
}
}
}
return result
}
private fun IrClass.findMatchingOverriddenSymbolsFromThisAndSupertypes(
irBuiltIns: IrBuiltIns,
target: IrDeclaration,
result: MutableList<IrSymbol>,
visited: MutableSet<IrClass>
): List<IrSymbol> {
if (this in visited) {
return result
}
visited += this
val targetIsPropertyAccessor = target is IrFunction && target.isPropertyAccessor
for (declaration in declarations) {
if (declaration.isFakeOverride || declaration is IrConstructor) {
continue
}
when {
declaration is IrSimpleFunction && target is IrSimpleFunction ->
if (declaration.modality != Modality.FINAL &&
!Visibilities.isPrivate(declaration.visibility) &&
isOverriding(irBuiltIns, target, declaration)
) {
result.add(declaration.symbol)
}
declaration is IrProperty && (target is IrField || targetIsPropertyAccessor) -> {
val backingField = declaration.backingField
if (target is IrField && backingField != null) {
if (!backingField.isFinal && !backingField.isStatic &&
!Visibilities.isPrivate(backingField.visibility) &&
isOverriding(irBuiltIns, target, backingField)
) {
result.add(backingField.symbol)
}
}
if (targetIsPropertyAccessor) {
val getter = declaration.getter
if (getter != null) {
if (getter.modality != Modality.FINAL &&
!Visibilities.isPrivate(getter.visibility) &&
isOverriding(irBuiltIns, target, getter)
) {
result.add(getter.symbol)
}
}
val setter = declaration.setter
if (setter != null) {
if (setter.modality != Modality.FINAL &&
!Visibilities.isPrivate(setter.visibility) &&
isOverriding(irBuiltIns, target, setter)
) {
result.add(setter.symbol)
}
}
}
}
}
}
// Stop traversing upwards if we find matching overridden symbols at this level.
if (result.isNotEmpty()) {
return result
}
return findMatchingOverriddenSymbolsFromSupertypes(irBuiltIns, target, result, visited)
}
fun isOverriding(
irBuiltIns: IrBuiltIns,
target: IrDeclaration,
@@ -521,10 +438,6 @@ fun FirClass<*>.irOrigin(firProvider: FirProvider): IrDeclarationOrigin = when {
else -> IrDeclarationOrigin.IR_EXTERNAL_DECLARATION_STUB
}
fun FirClass<*>.getSamIfAny(): FirSimpleFunction? =
declarations.filterIsInstance<FirSimpleFunction>()
.singleOrNull { it.modality == Modality.ABSTRACT && !it.isPublicInObject(checkOnlyName = true) }
val IrType.isSamType: Boolean
get() {
val irClass = classOrNull ?: return false
@@ -571,7 +571,9 @@ class Fir2IrDeclarationStorage(
parent = irParent
}
if (correspondingProperty is Fir2IrLazyProperty && !isFakeOverride && thisReceiverOwner != null) {
populateOverriddenSymbols(thisReceiverOwner)
this.overriddenSymbols = correspondingProperty.fir.generateOverriddenAccessorSymbols(
correspondingProperty.containingClass, !isSetter, session, scopeSession, declarationStorage
)
}
}
}
@@ -979,7 +981,7 @@ class Fir2IrDeclarationStorage(
firVariableSymbol is FirPropertySymbol && firVariableSymbol.isFakeOverride &&
firVariableSymbol.callableId != firVariableSymbol.overriddenSymbol?.callableId
Fir2IrLazyProperty(
components, startOffset, endOffset, parentOrigin, fir, symbol, isFakeOverride
components, startOffset, endOffset, parentOrigin, fir, irParent.fir, symbol, isFakeOverride
).apply {
parent = irParent
}
@@ -1049,15 +1051,6 @@ class Fir2IrDeclarationStorage(
}
}
private fun IrSimpleFunction.populateOverriddenSymbols(thisReceiverOwner: IrClass) {
thisReceiverOwner.findMatchingOverriddenSymbolsFromSupertypes(components.irBuiltIns, this)
.filterIsInstance<IrSimpleFunctionSymbol>().let {
if (it.isNotEmpty()) {
overriddenSymbols = it
}
}
}
private fun IrMutableAnnotationContainer.convertAnnotationsFromLibrary(firAnnotationContainer: FirAnnotationContainer) {
if ((firAnnotationContainer as? FirDeclaration)?.isFromLibrary == true) {
annotationGenerator?.generate(this, firAnnotationContainer)
@@ -31,6 +31,7 @@ class Fir2IrLazyProperty(
override val endOffset: Int,
override var origin: IrDeclarationOrigin,
override val fir: FirProperty,
internal val containingClass: FirRegularClass,
override val symbol: Fir2IrPropertySymbol,
override val isFakeOverride: Boolean
) : IrProperty(), AbstractFir2IrLazyDeclaration<FirProperty, IrProperty>, Fir2IrComponents by components {