FIR: Get rid of usages of FirCallableSymbol::overriddenSymbol

This commit is contained in:
Denis Zharkov
2020-10-30 12:36:06 +03:00
parent 728c2a808f
commit 4282e27d73
25 changed files with 114 additions and 123 deletions
@@ -11,6 +11,7 @@ import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.expressions.FirQualifiedAccessExpression
import org.jetbrains.kotlin.fir.originalForSubstitutionOverride
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor
import org.jetbrains.kotlin.fir.resolve.substitution.substitutorByMap
@@ -113,8 +114,7 @@ object FirUpperBoundViolatedChecker : FirQualifiedAccessChecker() {
// substitution here
val protoConstructor = functionCall.calleeReference.safeAs<FirResolvedNamedReference>()
?.resolvedSymbol.safeAs<FirConstructorSymbol>()
?.overriddenSymbol
?.fir.safeAs<FirConstructor>()
?.fir?.originalForSubstitutionOverride
?: return
// holds Collection<G> bound.
@@ -9,11 +9,8 @@ import org.jetbrains.kotlin.backend.common.serialization.mangle.KotlinMangleComp
import org.jetbrains.kotlin.backend.common.serialization.mangle.MangleConstant
import org.jetbrains.kotlin.backend.common.serialization.mangle.MangleMode
import org.jetbrains.kotlin.backend.common.serialization.mangle.collectForMangler
import org.jetbrains.kotlin.fir.FirElement
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.containingClass
import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.render
import org.jetbrains.kotlin.fir.resolve.firSymbolProvider
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.resolve.toSymbol
@@ -160,12 +157,9 @@ open class FirJvmMangleComputer(
return parent
}
if (parent is FirCallableDeclaration<*>) {
val overriddenSymbol = parent.symbol.overriddenSymbol
if (overriddenSymbol != null) {
val fir = overriddenSymbol.fir
if (fir is FirTypeParametersOwner && this in fir.typeParameters) {
return parent
}
val overriddenFir = parent.originalForSubstitutionOverride
if (overriddenFir is FirTypeParametersOwner && this in overriddenFir.typeParameters) {
return parent
}
}
}
@@ -21,6 +21,7 @@ import org.jetbrains.kotlin.fir.references.FirThisReference
import org.jetbrains.kotlin.fir.references.impl.FirPropertyFromParameterResolvedNamedReference
import org.jetbrains.kotlin.fir.resolve.*
import org.jetbrains.kotlin.fir.resolve.calls.SyntheticPropertySymbol
import org.jetbrains.kotlin.fir.resolve.calls.originalConstructorIfTypeAlias
import org.jetbrains.kotlin.fir.resolve.providers.FirProvider
import org.jetbrains.kotlin.fir.scopes.ProcessorAction
import org.jetbrains.kotlin.fir.scopes.processDirectlyOverriddenFunctions
@@ -102,7 +103,7 @@ fun FirClassifierSymbol<*>.toSymbol(
}
}
fun FirReference.toSymbol(
fun FirReference.toSymbolForCall(
session: FirSession,
classifierStorage: Fir2IrClassifierStorage,
declarationStorage: Fir2IrDeclarationStorage,
@@ -113,7 +114,7 @@ fun FirReference.toSymbol(
is FirResolvedNamedReference -> {
when (val resolvedSymbol = resolvedSymbol) {
is FirCallableSymbol<*> -> {
resolvedSymbol.deepestMatchingOverriddenSymbol().toSymbol(declarationStorage, preferGetter)
resolvedSymbol.unwrapCallRepresentative().toSymbolForCall(declarationStorage, preferGetter)
}
is FirClassifierSymbol<*> -> {
resolvedSymbol.toSymbol(session, classifierStorage)
@@ -138,7 +139,7 @@ fun FirReference.toSymbol(
}
}
private fun FirCallableSymbol<*>.toSymbol(declarationStorage: Fir2IrDeclarationStorage, preferGetter: Boolean): IrSymbol? = when (this) {
private fun FirCallableSymbol<*>.toSymbolForCall(declarationStorage: Fir2IrDeclarationStorage, preferGetter: Boolean): IrSymbol? = when (this) {
is FirFunctionSymbol<*> -> declarationStorage.getIrFunctionSymbol(this)
is SyntheticPropertySymbol -> {
(fir as? FirSyntheticProperty)?.let { syntheticProperty ->
@@ -148,7 +149,7 @@ private fun FirCallableSymbol<*>.toSymbol(declarationStorage: Fir2IrDeclarationS
syntheticProperty.setter?.delegate?.symbol
?: throw AssertionError("Written synthetic property must have a setter")
}
delegateSymbol.deepestMatchingOverriddenSymbol().toSymbol(declarationStorage, preferGetter)
delegateSymbol.unwrapCallRepresentative().toSymbolForCall(declarationStorage, preferGetter)
} ?: declarationStorage.getIrPropertySymbol(this)
}
is FirPropertySymbol -> declarationStorage.getIrPropertySymbol(this)
@@ -212,17 +213,25 @@ private fun FirConstKind<*>.toIrConstKind(): IrConstKind<*> = when (this) {
FirConstKind.IntegerLiteral, FirConstKind.UnsignedIntegerLiteral -> throw IllegalArgumentException()
}
internal tailrec fun FirCallableSymbol<*>.deepestOverriddenSymbol(): FirCallableSymbol<*> {
val overriddenSymbol = overriddenSymbol ?: return this
return overriddenSymbol.deepestOverriddenSymbol()
internal tailrec fun FirCallableSymbol<*>.unwrapSubstitutionAndIntersectionOverrides(): FirCallableSymbol<*> {
val originalForSubstitutionOverride = originalForSubstitutionOverride
if (originalForSubstitutionOverride != null) return originalForSubstitutionOverride.unwrapSubstitutionAndIntersectionOverrides()
val baseForIntersectionOverride = baseForIntersectionOverride
if (baseForIntersectionOverride != null) return baseForIntersectionOverride.unwrapSubstitutionAndIntersectionOverrides()
return this
}
internal tailrec fun FirCallableSymbol<*>.deepestMatchingOverriddenSymbol(root: FirCallableSymbol<*> = this): FirCallableSymbol<*> {
internal tailrec fun FirCallableSymbol<*>.unwrapCallRepresentative(root: FirCallableSymbol<*> = this): FirCallableSymbol<*> {
if (fir.isIntersectionOverride) return this
val overriddenSymbol = overriddenSymbol?.takeIf {
val overriddenSymbol = fir.originalForSubstitutionOverride?.takeIf {
it.containingClass() == root.containingClass()
} ?: return this
return overriddenSymbol.deepestMatchingOverriddenSymbol(this)
}?.symbol ?: return this
return overriddenSymbol.unwrapCallRepresentative(this)
}
internal fun FirSimpleFunction.generateOverriddenFunctionSymbols(
@@ -239,7 +248,7 @@ internal fun FirSimpleFunction.generateOverriddenFunctionSymbols(
return@processDirectlyOverriddenFunctions ProcessorAction.NEXT
}
val overridden = declarationStorage.getIrFunctionSymbol(it.unwrapSubstitutionOverrides())
val overridden = declarationStorage.getIrFunctionSymbol(it.unwrapFakeOverrides())
overriddenSet += overridden as IrSimpleFunctionSymbol
ProcessorAction.NEXT
}
@@ -260,7 +269,7 @@ internal fun FirProperty.generateOverriddenAccessorSymbols(
if (it is FirAccessorSymbol || it.fir.visibility == Visibilities.Private) {
return@processDirectlyOverriddenProperties ProcessorAction.NEXT
}
val overriddenProperty = declarationStorage.getIrPropertySymbol(it.unwrapSubstitutionOverrides()) as IrPropertySymbol
val overriddenProperty = declarationStorage.getIrPropertySymbol(it.unwrapFakeOverrides()) as IrPropertySymbol
val overriddenAccessor = if (isGetter) overriddenProperty.owner.getter?.symbol else overriddenProperty.owner.setter?.symbol
if (overriddenAccessor != null) {
overriddenSet += overriddenAccessor
@@ -461,7 +461,7 @@ class Fir2IrDeclarationStorage(
return created
}
if (function.symbol.callableId.isKFunctionInvoke()) {
(function.symbol.overriddenSymbol as? FirNamedFunctionSymbol)?.let {
(function.symbol.originalForSubstitutionOverride as? FirNamedFunctionSymbol)?.let {
created.overriddenSymbols += getIrFunctionSymbol(it) as IrSimpleFunctionSymbol
}
}
@@ -1034,7 +1034,7 @@ class Fir2IrDeclarationStorage(
symbolTable.declareSimpleFunction(signature, { symbol }) {
val isFakeOverride =
firFunctionSymbol is FirNamedFunctionSymbol && firFunctionSymbol.fir.isSubstitutionOverride &&
firFunctionSymbol.dispatchReceiverClassOrNull() != firFunctionSymbol.overriddenSymbol?.dispatchReceiverClassOrNull()
firFunctionSymbol.dispatchReceiverClassOrNull() != firFunctionSymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
Fir2IrLazySimpleFunction(
components, startOffset, endOffset, parentOrigin, firDeclaration, irParent.fir, symbol, isFakeOverride
).apply {
@@ -1101,7 +1101,7 @@ class Fir2IrDeclarationStorage(
symbolTable.declareProperty(signature, { symbol }) {
val isFakeOverride =
firPropertySymbol.fir.isSubstitutionOverride &&
firPropertySymbol.dispatchReceiverClassOrNull() != firPropertySymbol.overriddenSymbol?.dispatchReceiverClassOrNull()
firPropertySymbol.dispatchReceiverClassOrNull() != firPropertySymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
Fir2IrLazyProperty(
components, startOffset, endOffset, declarationOrigin, fir, irParent.fir, symbol, isFakeOverride
).apply {
@@ -6,15 +6,23 @@
package org.jetbrains.kotlin.fir.backend
import org.jetbrains.kotlin.fir.FirElement
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.baseForIntersectionOverride
import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction
import org.jetbrains.kotlin.fir.declarations.FirAnonymousObject
import org.jetbrains.kotlin.fir.declarations.FirTypeAlias
import org.jetbrains.kotlin.fir.expressions.*
import org.jetbrains.kotlin.fir.expressions.impl.*
import org.jetbrains.kotlin.fir.references.*
import org.jetbrains.kotlin.fir.expressions.impl.FirStubStatement
import org.jetbrains.kotlin.fir.expressions.impl.FirUnitExpression
import org.jetbrains.kotlin.fir.references.FirReference
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
import org.jetbrains.kotlin.fir.render
import org.jetbrains.kotlin.fir.resolve.scope
import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator
import org.jetbrains.kotlin.fir.symbols.AbstractFirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.impl.*
import org.jetbrains.kotlin.fir.symbols.impl.FirAnonymousFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.visitors.FirDefaultVisitor
import org.jetbrains.kotlin.ir.IrElement
@@ -273,7 +281,7 @@ class Fir2IrImplicitCastInserter(
if (castTypeRef is FirResolvedTypeRef && originalTypeRef is FirResolvedTypeRef) {
val castType = castTypeRef.type
if (castType is ConeIntersectionType) {
val unwrappedSymbol = (referencedSymbol as? FirCallableSymbol)?.overriddenSymbol ?: referencedSymbol
val unwrappedSymbol = (referencedSymbol as? FirCallableSymbol)?.baseForIntersectionOverride ?: referencedSymbol
castType.intersectedTypes.forEach {
if (it.doesContainReferencedSymbolInScope(unwrappedSymbol, calleeReference.name)) {
return implicitCastOrExpression(value, it)
@@ -401,7 +401,7 @@ class Fir2IrVisitor(
}
}
} else if (boundSymbol is FirCallableSymbol) {
val receiverSymbol = calleeReference.toSymbol(session, classifierStorage, declarationStorage, conversionScope)
val receiverSymbol = calleeReference.toSymbolForCall(session, classifierStorage, declarationStorage, conversionScope)
val receiver = (receiverSymbol?.owner as? IrSimpleFunction)?.extensionReceiverParameter
if (receiver != null) {
return thisReceiverExpression.convertWithOffsets { startOffset, endOffset ->
@@ -55,7 +55,7 @@ class CallAndReferenceGenerator(
callableReferenceAccess: FirCallableReferenceAccess,
explicitReceiverExpression: IrExpression?
): IrExpression {
val symbol = callableReferenceAccess.calleeReference.toSymbol(session, classifierStorage, declarationStorage, conversionScope)
val symbol = callableReferenceAccess.calleeReference.toSymbolForCall(session, classifierStorage, declarationStorage, conversionScope)
val type = callableReferenceAccess.typeRef.toIrType()
fun propertyOrigin(): IrStatementOrigin? =
when (callableReferenceAccess.source?.psi?.parent) {
@@ -197,7 +197,7 @@ class CallAndReferenceGenerator(
val samConstructorCall = qualifiedAccess.tryConvertToSamConstructorCall(type)
if (samConstructorCall != null) return samConstructorCall
val symbol = qualifiedAccess.calleeReference.toSymbol(
val symbol = qualifiedAccess.calleeReference.toSymbolForCall(
session,
classifierStorage,
declarationStorage,
@@ -277,7 +277,7 @@ class CallAndReferenceGenerator(
fun convertToIrSetCall(variableAssignment: FirVariableAssignment, explicitReceiverExpression: IrExpression?): IrExpression {
val type = irBuiltIns.unitType
val calleeReference = variableAssignment.calleeReference
val symbol = calleeReference.toSymbol(session, classifierStorage, declarationStorage, conversionScope, preferGetter = false)
val symbol = calleeReference.toSymbolForCall(session, classifierStorage, declarationStorage, conversionScope, preferGetter = false)
val origin = IrStatementOrigin.EQ
return variableAssignment.convertWithOffsets { startOffset, endOffset ->
val assignedValue = visitor.convertToIrExpression(variableAssignment.rValue)
@@ -272,7 +272,7 @@ internal class ClassMemberGenerator(
startOffset, endOffset, constructedIrType, "Cannot find delegated constructor call"
)
}
val constructorSymbol = referencedSymbol.deepestMatchingOverriddenSymbol() as FirConstructorSymbol
val constructorSymbol = referencedSymbol.unwrapCallRepresentative() as FirConstructorSymbol
val firDispatchReceiver = dispatchReceiver
return convertWithOffsets { startOffset, endOffset ->
val irConstructorSymbol = declarationStorage.getIrFunctionSymbol(constructorSymbol) as IrConstructorSymbol
@@ -7,9 +7,11 @@ package org.jetbrains.kotlin.fir.backend.generators
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.fir.backend.*
import org.jetbrains.kotlin.fir.baseForIntersectionOverride
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.isIntersectionOverride
import org.jetbrains.kotlin.fir.isSubstitutionOverride
import org.jetbrains.kotlin.fir.originalForSubstitutionOverride
import org.jetbrains.kotlin.fir.scopes.*
import org.jetbrains.kotlin.fir.scopes.impl.delegatedWrapperData
import org.jetbrains.kotlin.fir.symbols.ConeClassLikeLookupTag
@@ -104,13 +106,13 @@ internal class DelegatedMemberGenerator(
return when {
wrappedSymbol.fir.isSubstitutionOverride &&
(wrappedSymbol.fir.dispatchReceiverType as? ConeClassLikeType)?.lookupTag == firSubClass.symbol.toLookupTag() ->
wrapped.symbol.overriddenSymbol!!.fir
wrapped.originalForSubstitutionOverride
else -> wrapped
}
}
private fun isJavaDefault(function: FirSimpleFunction): Boolean {
if (function.isIntersectionOverride) return isJavaDefault(function.symbol.overriddenSymbol!!.fir)
if (function.isIntersectionOverride) return isJavaDefault(function.baseForIntersectionOverride!!)
return function.origin == FirDeclarationOrigin.Enhancement && function.modality == Modality.OPEN
}
@@ -6,12 +6,9 @@
package org.jetbrains.kotlin.fir.backend.generators
import org.jetbrains.kotlin.descriptors.Visibilities
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.FirSymbolOwner
import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.backend.*
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.dispatchReceiverClassOrNull
import org.jetbrains.kotlin.fir.isSubstitutionOverride
import org.jetbrains.kotlin.fir.resolve.ScopeSession
import org.jetbrains.kotlin.fir.resolve.defaultType
import org.jetbrains.kotlin.fir.scopes.FirTypeScope
@@ -25,7 +22,6 @@ import org.jetbrains.kotlin.fir.symbols.PossiblyFirFakeOverrideSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
import org.jetbrains.kotlin.fir.symbols.impl.unwrapSubstitutionOverrides
import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.symbols.IrPropertySymbol
import org.jetbrains.kotlin.ir.symbols.IrSimpleFunctionSymbol
@@ -156,7 +152,7 @@ class FakeOverrideGenerator(
if (originalDeclaration.visibility == Visibilities.Private) return
val origin = IrDeclarationOrigin.FAKE_OVERRIDE
val baseSymbol = originalSymbol.deepestOverriddenSymbol() as S
val baseSymbol = originalSymbol.unwrapSubstitutionAndIntersectionOverrides() as S
if (originalSymbol.fir.origin.fromSupertypes && originalSymbol.dispatchReceiverClassOrNull() == classLookupTag) {
// Substitution case
@@ -204,7 +200,7 @@ class FakeOverrideGenerator(
return scope.directOverridden(symbol).map {
@Suppress("UNCHECKED_CAST")
if (it is PossiblyFirFakeOverrideSymbol<*, *> && it.fir.isSubstitutionOverride && it.dispatchReceiverClassOrNull() == containingClass)
it.overriddenSymbol!! as S
it.originalForSubstitutionOverride!!
else
it
}
@@ -234,7 +230,7 @@ class FakeOverrideGenerator(
private fun IrProperty.discardAccessorsAccordingToBaseVisibility(baseSymbols: List<FirPropertySymbol>) {
for (baseSymbol in baseSymbols) {
val unwrapped = baseSymbol.unwrapSubstitutionOverrides()
val unwrapped = baseSymbol.unwrapFakeOverrides()
// Do not create fake overrides for accessors if not allowed to do so, e.g., private lateinit var.
if (unwrapped.fir.getter?.allowsToHaveFakeOverride != true) {
getter = null
@@ -15,7 +15,6 @@ import org.jetbrains.kotlin.fir.resolve.firSymbolProvider
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.resolve.lookupSuperTypes
import org.jetbrains.kotlin.fir.symbols.AbstractFirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.PossiblyFirFakeOverrideSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
@@ -44,9 +43,9 @@ abstract class FirVisibilityChecker : FirSessionComponent {
): Boolean where T : FirMemberDeclaration, T : FirSymbolOwner<*> {
val symbol = declaration.symbol
if (symbol is PossiblyFirFakeOverrideSymbol<*, *> && symbol.overriddenSymbol != null) {
if (declaration is FirCallableDeclaration<*> && (declaration.isIntersectionOverride || declaration.isSubstitutionOverride)) {
@Suppress("UNCHECKED_CAST")
return isVisible(symbol.overriddenSymbol!!.fir as T, candidate)
return isVisible(declaration.originalIfFakeOverride() as T, candidate)
}
val callInfo = candidate.callInfo
@@ -21,12 +21,12 @@ import org.jetbrains.kotlin.fir.resolve.toSymbol
import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator
import org.jetbrains.kotlin.fir.symbols.StandardClassIds
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
import org.jetbrains.kotlin.fir.symbols.impl.unwrapSubstitutionOverrides
import org.jetbrains.kotlin.fir.typeContext
import org.jetbrains.kotlin.fir.types.ConeClassLikeType
import org.jetbrains.kotlin.fir.types.ConeKotlinType
import org.jetbrains.kotlin.fir.types.FirResolvedTypeRef
import org.jetbrains.kotlin.fir.types.FirTypeRef
import org.jetbrains.kotlin.fir.unwrapFakeOverrides
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.types.AbstractTypeChecker
import org.jetbrains.kotlin.utils.SmartList
@@ -147,5 +147,5 @@ private fun BodyResolveComponents.isConcreteMember(supertype: ConeKotlinType, me
val classSymbol =
(supertype as? ConeClassLikeType)?.lookupTag?.toSymbol(session) as? FirRegularClassSymbol ?: return true
if (classSymbol.fir.classKind != ClassKind.INTERFACE) return true
return member.symbol.unwrapSubstitutionOverrides().dispatchReceiverClassOrNull()?.classId != StandardClassIds.Any
return member.symbol.unwrapFakeOverrides().dispatchReceiverClassOrNull()?.classId != StandardClassIds.Any
}
@@ -22,6 +22,7 @@ import org.jetbrains.kotlin.fir.symbols.impl.*
import org.jetbrains.kotlin.fir.typeContext
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.ConeNullability.NOT_NULL
import org.jetbrains.kotlin.fir.unwrapFakeOverrides
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.types.AbstractTypeChecker
@@ -123,7 +124,7 @@ class FirSyntheticPropertiesScope(
private fun FirFunctionSymbol<*>.hasJavaOverridden(): Boolean {
var result = false
baseScope.processOverriddenFunctionsAndSelf(this) {
if (it.unwrapSubstitutionOverrides().fir.origin == FirDeclarationOrigin.Enhancement) {
if (it.unwrapFakeOverrides().fir.origin == FirDeclarationOrigin.Enhancement) {
result = true
ProcessorAction.STOP
} else {
@@ -9,17 +9,17 @@ import org.jetbrains.kotlin.builtins.functions.FunctionClassKind
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.FirAnonymousFunction
import org.jetbrains.kotlin.fir.declarations.FirClass
import org.jetbrains.kotlin.fir.originalForSubstitutionOverride
import org.jetbrains.kotlin.fir.resolve.*
import org.jetbrains.kotlin.fir.resolve.calls.Candidate
import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator
import org.jetbrains.kotlin.fir.scopes.ProcessorAction
import org.jetbrains.kotlin.fir.scopes.processOverriddenFunctions
import org.jetbrains.kotlin.fir.scopes.unsubstitutedScope
import org.jetbrains.kotlin.fir.symbols.StandardClassIds
import org.jetbrains.kotlin.fir.symbols.impl.ConeClassLikeLookupTagImpl
import org.jetbrains.kotlin.fir.symbols.impl.FirFunctionSymbol
import org.jetbrains.kotlin.fir.typeContext
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator
import org.jetbrains.kotlin.fir.symbols.StandardClassIds
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
import org.jetbrains.kotlin.name.ClassId
@@ -122,7 +122,7 @@ fun ConeKotlinType.findContributedInvokeSymbol(
if (declaredInvoke != null) {
// Make sure the user-contributed or type-substituted invoke we just found above is an override of base invoke.
scope.processOverriddenFunctions(declaredInvoke!!) { functionSymbol ->
if (functionSymbol == baseInvokeSymbol || functionSymbol.overriddenSymbol == baseInvokeSymbol) {
if (functionSymbol == baseInvokeSymbol || functionSymbol.originalForSubstitutionOverride == baseInvokeSymbol) {
overriddenInvoke = functionSymbol
ProcessorAction.STOP
} else {
@@ -11,6 +11,7 @@ import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.ThreadSafeMutableState
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.declarations.synthetic.FirSyntheticProperty
import org.jetbrains.kotlin.fir.originalIfFakeOverride
import org.jetbrains.kotlin.fir.resolve.providers.FirProvider
import org.jetbrains.kotlin.fir.resolve.providers.FirProviderInternals
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
@@ -30,7 +31,7 @@ class FirProviderImpl(val session: FirSession, val kotlinScopeProvider: KotlinSc
override val symbolProvider: FirSymbolProvider = SymbolProvider()
override fun getFirCallableContainerFile(symbol: FirCallableSymbol<*>): FirFile? {
symbol.overriddenSymbol?.let {
symbol.originalIfFakeOverride()?.let {
return getFirCallableContainerFile(it)
}
if (symbol is FirAccessorSymbol) {
@@ -16,7 +16,6 @@ import org.jetbrains.kotlin.fir.resolve.firProvider
import org.jetbrains.kotlin.fir.resolve.transformers.*
import org.jetbrains.kotlin.fir.resolve.transformers.contracts.runContractResolveForLocalClass
import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator
import org.jetbrains.kotlin.fir.symbols.PossiblyFirFakeOverrideSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirAccessorSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
import org.jetbrains.kotlin.fir.types.FirImplicitTypeRef
@@ -212,14 +211,13 @@ private class ReturnTypeCalculatorWithJump(
}
if (declaration.isIntersectionOverride) {
val result = tryCalculateReturnType(declaration.symbol.overriddenSymbol!!.fir)
val result = tryCalculateReturnType(declaration.symbol.baseForIntersectionOverride!!.fir)
declaration.replaceReturnTypeRef(result)
return result
}
runIf(declaration.isSubstitutionOverride) {
val possiblyFirFakeOverrideSymbol = declaration.symbol as PossiblyFirFakeOverrideSymbol<*, *>
val overriddenDeclaration = possiblyFirFakeOverrideSymbol.overriddenSymbol?.fir as FirTypedDeclaration? ?: return@runIf
val overriddenDeclaration = declaration.originalForSubstitutionOverride ?: return@runIf
tryCalculateReturnType(overriddenDeclaration)
return FakeOverrideTypeCalculator.Forced.computeReturnType(declaration)
}
@@ -58,7 +58,7 @@ class FirClassSubstitutionScope(
processDirectOverriddenCallablesWithBaseScope: FirTypeScope.(D, ((D, FirTypeScope) -> ProcessorAction)) -> ProcessorAction,
fakeOverridesMap: Map<out FirCallableSymbol<*>, FirCallableSymbol<*>>
): ProcessorAction {
val original = (callableSymbol.overriddenSymbol as? D)?.takeIf { it in fakeOverridesMap }
val original = callableSymbol.originalForSubstitutionOverride?.takeIf { it in fakeOverridesMap }
?: return useSiteMemberScope.processDirectOverriddenCallablesWithBaseScope(callableSymbol, processor)
if (!processor(original, useSiteMemberScope)) return ProcessorAction.STOP
@@ -16,7 +16,7 @@ fun FirCallableSymbol<*>.dispatchReceiverClassOrNull(): ConeClassLikeLookupTag?
fun FirCallableDeclaration<*>.dispatchReceiverClassOrNull(): ConeClassLikeLookupTag? {
if (this !is FirCallableMemberDeclaration<*>) return null
if (dispatchReceiverType is ConeIntersectionType && isIntersectionOverride) return symbol.overriddenSymbol!!.fir.dispatchReceiverClassOrNull()
if (dispatchReceiverType is ConeIntersectionType && isIntersectionOverride) return symbol.baseForIntersectionOverride!!.fir.dispatchReceiverClassOrNull()
return (dispatchReceiverType as? ConeClassLikeType)?.lookupTag
}
@@ -32,3 +32,32 @@ var FirCallableDeclaration<*>.containingClassAttr: ConeClassLikeLookupTag? by Fi
val FirCallableDeclaration<*>.isIntersectionOverride get() = origin == FirDeclarationOrigin.IntersectionOverride
val FirCallableDeclaration<*>.isSubstitutionOverride get() = origin == FirDeclarationOrigin.SubstitutionOverride
inline val <reified D : FirCallableDeclaration<*>> D.originalForSubstitutionOverride: D?
get() = if (isSubstitutionOverride) symbol.overriddenSymbol?.fir as D? else null
inline val <reified S : FirCallableSymbol<*>> S.originalForSubstitutionOverride: S?
get() = fir.originalForSubstitutionOverride?.symbol as S?
inline val <reified D : FirCallableDeclaration<*>> D.baseForIntersectionOverride: D?
get() = if (isIntersectionOverride) symbol.overriddenSymbol?.fir as D? else null
inline val <reified S : FirCallableSymbol<*>> S.baseForIntersectionOverride: S?
get() = fir.baseForIntersectionOverride?.symbol as S?
inline fun <reified D : FirCallableDeclaration<*>> D.originalIfFakeOverride(): D? =
originalForSubstitutionOverride ?: baseForIntersectionOverride
inline fun <reified S : FirCallableSymbol<*>> S.originalIfFakeOverride(): S? =
fir.originalIfFakeOverride()?.symbol as S?
inline fun <reified D : FirCallableDeclaration<*>> D.unwrapFakeOverrides(): D {
var current = this
do {
val next = current.originalIfFakeOverride() ?: return current
current = next
} while (true)
}
inline fun <reified S : FirCallableSymbol<*>> S.unwrapFakeOverrides(): S = fir.unwrapFakeOverrides().symbol as S
@@ -1008,7 +1008,7 @@ class FirRenderer(builder: StringBuilder, private val mode: RenderMode = RenderM
}
private fun AbstractFirBasedSymbol<*>.unwrapIntersectionOverrides(): AbstractFirBasedSymbol<*> {
if (this is FirCallableSymbol<*> && fir.isIntersectionOverride) return overriddenSymbol!!.unwrapIntersectionOverrides()
(this as? FirCallableSymbol<*>)?.baseForIntersectionOverride?.let { return it.unwrapIntersectionOverrides() }
return this
}
@@ -27,12 +27,3 @@ val FirCallableSymbol<*>.isExtension: Boolean
is FirProperty -> fir.receiverTypeRef != null
else -> false
}
inline fun <reified E : FirCallableSymbol<*>> E.unwrapSubstitutionOverrides(): E {
var current = this
while (current.overriddenSymbol != null) {
current = current.overriddenSymbol as E
}
return current
}
@@ -13,6 +13,7 @@ import org.jetbrains.kotlin.fir.ThreadSafeMutableState
import org.jetbrains.kotlin.fir.builder.RawFirBuilder
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.declarations.synthetic.FirSyntheticProperty
import org.jetbrains.kotlin.fir.originalForSubstitutionOverride
import org.jetbrains.kotlin.fir.resolve.providers.FirProvider
import org.jetbrains.kotlin.fir.resolve.providers.FirProviderInternals
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
@@ -79,7 +80,7 @@ internal class FirIdeProvider(
override fun getFirCallableContainerFile(symbol: FirCallableSymbol<*>): FirFile? {
symbol.overriddenSymbol?.let {
symbol.fir.originalForSubstitutionOverride?.symbol?.let {
return getFirCallableContainerFile(it)
}
if (symbol is FirAccessorSymbol) {
@@ -8,11 +8,8 @@ package org.jetbrains.kotlin.idea.fir
import com.intellij.openapi.project.Project
import com.intellij.psi.PsiElement
import com.intellij.psi.search.GlobalSearchScope
import org.jetbrains.kotlin.fir.FirElement
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.containingClass
import org.jetbrains.kotlin.fir.*
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.psi
import org.jetbrains.kotlin.idea.fir.low.level.api.sessions.FirIdeSession
import org.jetbrains.kotlin.idea.stubindex.KotlinFullClassNameIndex
import org.jetbrains.kotlin.idea.stubindex.KotlinTopLevelFunctionFqnNameIndex
@@ -53,7 +50,7 @@ object FirIdeDeserializedDeclarationSourceProvider {
.orEmpty()
}
return function.unrollFakeOverrides().chooseCorrespondingPsi(candidates)
return function.unwrapFakeOverrides().chooseCorrespondingPsi(candidates)
}
private fun provideSourceForProperty(property: FirProperty, project: Project): PsiElement? {
@@ -91,7 +88,7 @@ object FirIdeDeserializedDeclarationSourceProvider {
val containingKtClass = constructor.containingKtClass(project) ?: return null
if (constructor.isPrimary) return containingKtClass.primaryConstructor
return constructor.unrollFakeOverrides().chooseCorrespondingPsi(containingKtClass.secondaryConstructors)
return constructor.unwrapFakeOverrides().chooseCorrespondingPsi(containingKtClass.secondaryConstructors)
}
private fun FirFunction<*>.chooseCorrespondingPsi(
@@ -117,7 +114,7 @@ object FirIdeDeserializedDeclarationSourceProvider {
}
private fun FirCallableDeclaration<*>.containingKtClass(project: Project): KtClassOrObject? =
unrollFakeOverrides().containingClass()?.classId?.let { classByClassId(it, scope(project), project) }
unwrapFakeOverrides().containingClass()?.classId?.let { classByClassId(it, scope(project), project) }
private fun classByClassId(classId: ClassId, scope: GlobalSearchScope, project: Project): KtClassOrObject? {
val fqName = classId.asStringForUsingInIndexes().let { classIdMapping[it] ?: it }
@@ -5,17 +5,12 @@
package org.jetbrains.kotlin.idea.fir
import org.jetbrains.kotlin.fir.FirSymbolOwner
import org.jetbrains.kotlin.fir.declarations.FirCallableDeclaration
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
import org.jetbrains.kotlin.fir.expressions.FirFunctionCall
import org.jetbrains.kotlin.fir.expressions.FirQualifiedAccessExpression
import org.jetbrains.kotlin.fir.isIntersectionOverride
import org.jetbrains.kotlin.fir.isSubstitutionOverride
import org.jetbrains.kotlin.fir.references.FirReference
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.PossiblyFirFakeOverrideSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.idea.frontend.api.fir.KtSymbolByFirBuilder
import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbol
@@ -38,20 +33,3 @@ internal fun FirReference.getResolvedKtSymbolOfNameReference(builder: KtSymbolBy
(getResolvedSymbolOfNameReference()?.fir as? FirDeclaration)?.let { firDeclaration ->
builder.buildSymbol(firDeclaration)
}
internal inline fun <reified D> D.unrollFakeOverrides(): D where D : FirDeclaration, D : FirSymbolOwner<*> {
val symbol = symbol
if (symbol !is PossiblyFirFakeOverrideSymbol<*, *>) return this
if (!symbol.isFakeOrIntersectionOverride) return this
var current: FirBasedSymbol<*>? = symbol.overriddenSymbol
while (current is PossiblyFirFakeOverrideSymbol<*, *> && current.isFakeOrIntersectionOverride) {
current = current.overriddenSymbol
}
return current?.fir as D
}
private inline val FirBasedSymbol<*>.isFakeOrIntersectionOverride: Boolean
get() {
val declaration = fir as? FirCallableDeclaration<*> ?: return false
return declaration.isSubstitutionOverride || declaration.isIntersectionOverride
}
@@ -5,11 +5,12 @@
package org.jetbrains.kotlin.idea.frontend.api.fir.symbols
import org.jetbrains.kotlin.fir.declarations.FirCallableDeclaration
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
import org.jetbrains.kotlin.fir.declarations.FirDeclarationOrigin
import org.jetbrains.kotlin.fir.originalIfFakeOverride
import org.jetbrains.kotlin.idea.frontend.api.ValidityTokenOwner
import org.jetbrains.kotlin.idea.frontend.api.fir.utils.FirRefWithValidityCheck
import org.jetbrains.kotlin.idea.frontend.api.fir.utils.overriddenDeclaration
import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbol
import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin
@@ -27,10 +28,11 @@ private tailrec fun FirDeclaration.ktSymbolOrigin(): KtSymbolOrigin = when (orig
FirDeclarationOrigin.SamConstructor -> KtSymbolOrigin.SAM_CONSTRUCTOR
FirDeclarationOrigin.Enhancement -> KtSymbolOrigin.JAVA
else -> {
val overridden = overriddenDeclaration ?: throw InvalidFirDeclarationOriginForSymbol(origin)
val overridden =
(this as? FirCallableDeclaration<*>)?.originalIfFakeOverride() ?: throw InvalidFirDeclarationOriginForSymbol(origin)
overridden.ktSymbolOrigin()
}
}
class InvalidFirDeclarationOriginForSymbol(origin: FirDeclarationOrigin) :
IllegalStateException("Invalid FirDeclarationOrigin $origin")
IllegalStateException("Invalid FirDeclarationOrigin $origin")
@@ -1,15 +0,0 @@
/*
* Copyright 2010-2020 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.idea.frontend.api.fir.utils
import org.jetbrains.kotlin.fir.FirSymbolOwner
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
internal inline val FirDeclaration.overriddenDeclaration: FirDeclaration?
get() {
val symbol = (this as? FirSymbolOwner<*>)?.symbol ?: return null
return (symbol as? FirCallableSymbol)?.overriddenSymbol?.fir as? FirDeclaration
}