FIR2IR: don't create non-lazy fake overrides inside lazy class
This commit allows to calculate member with initial signature properly. Only lazy IR members are suitable to calculate initial signature. Before this commit we sometimes built non-lazy children for lazy class. Now we build lazy children (with an exception of private declarations).
This commit is contained in:
+69
-38
@@ -476,6 +476,11 @@ class Fir2IrDeclarationStorage(
|
|||||||
function.origin == FirDeclarationOrigin.Enhancement -> IrDeclarationOrigin.IR_EXTERNAL_JAVA_DECLARATION_STUB
|
function.origin == FirDeclarationOrigin.Enhancement -> IrDeclarationOrigin.IR_EXTERNAL_JAVA_DECLARATION_STUB
|
||||||
else -> function.computeIrOrigin(predefinedOrigin)
|
else -> function.computeIrOrigin(predefinedOrigin)
|
||||||
}
|
}
|
||||||
|
val signature = if (isLocal) null else signatureComposer.composeSignature(function, containingClass)
|
||||||
|
if (irParent is Fir2IrLazyClass && signature != null) {
|
||||||
|
// For private functions signature is null, fallback to non-lazy function
|
||||||
|
return createIrLazyFunction(function as FirSimpleFunction, signature, irParent, updatedOrigin)
|
||||||
|
}
|
||||||
classifierStorage.preCacheTypeParameters(function)
|
classifierStorage.preCacheTypeParameters(function)
|
||||||
val name = simpleFunction?.name
|
val name = simpleFunction?.name
|
||||||
?: if (isLambda) SpecialNames.ANONYMOUS else Name.special("<no name provided>")
|
?: if (isLambda) SpecialNames.ANONYMOUS else Name.special("<no name provided>")
|
||||||
@@ -483,7 +488,6 @@ class Fir2IrDeclarationStorage(
|
|||||||
val isSuspend =
|
val isSuspend =
|
||||||
if (isLambda) ((function as FirAnonymousFunction).typeRef as? FirResolvedTypeRef)?.type?.isSuspendFunctionType(session) == true
|
if (isLambda) ((function as FirAnonymousFunction).typeRef as? FirResolvedTypeRef)?.type?.isSuspendFunctionType(session) == true
|
||||||
else simpleFunction?.isSuspend == true
|
else simpleFunction?.isSuspend == true
|
||||||
val signature = if (isLocal) null else signatureComposer.composeSignature(function, containingClass)
|
|
||||||
val created = function.convertWithOffsets { startOffset, endOffset ->
|
val created = function.convertWithOffsets { startOffset, endOffset ->
|
||||||
val result = declareIrSimpleFunction(signature, simpleFunction?.containerSource) { symbol ->
|
val result = declareIrSimpleFunction(signature, simpleFunction?.containerSource) { symbol ->
|
||||||
irFactory.createFunction(
|
irFactory.createFunction(
|
||||||
@@ -792,13 +796,17 @@ class Fir2IrDeclarationStorage(
|
|||||||
containingClass: ConeClassLikeLookupTag? = null,
|
containingClass: ConeClassLikeLookupTag? = null,
|
||||||
): IrProperty = convertCatching(property) {
|
): IrProperty = convertCatching(property) {
|
||||||
val origin = property.computeIrOrigin(predefinedOrigin)
|
val origin = property.computeIrOrigin(predefinedOrigin)
|
||||||
|
val signature = if (isLocal) null else signatureComposer.composeSignature(property, containingClass)
|
||||||
|
if (irParent is Fir2IrLazyClass && signature != null) {
|
||||||
|
// For private functions signature is null, fallback to non-lazy property
|
||||||
|
return createIrLazyProperty(property, signature, irParent, origin)
|
||||||
|
}
|
||||||
classifierStorage.preCacheTypeParameters(property)
|
classifierStorage.preCacheTypeParameters(property)
|
||||||
if (property.delegate != null) {
|
if (property.delegate != null) {
|
||||||
((property.delegate as? FirQualifiedAccess)?.calleeReference?.resolvedSymbol?.fir as? FirTypeParameterRefsOwner)?.let {
|
((property.delegate as? FirQualifiedAccess)?.calleeReference?.resolvedSymbol?.fir as? FirTypeParameterRefsOwner)?.let {
|
||||||
classifierStorage.preCacheTypeParameters(it)
|
classifierStorage.preCacheTypeParameters(it)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
val signature = if (isLocal) null else signatureComposer.composeSignature(property, containingClass)
|
|
||||||
return property.convertWithOffsets { startOffset, endOffset ->
|
return property.convertWithOffsets { startOffset, endOffset ->
|
||||||
val result = declareIrProperty(signature, property.containerSource) { symbol ->
|
val result = declareIrProperty(signature, property.containerSource) { symbol ->
|
||||||
irFactory.createProperty(
|
irFactory.createProperty(
|
||||||
@@ -1181,27 +1189,11 @@ class Fir2IrDeclarationStorage(
|
|||||||
firFunctionSymbol,
|
firFunctionSymbol,
|
||||||
dispatchReceiverLookupTag,
|
dispatchReceiverLookupTag,
|
||||||
getCachedIrDeclaration = ::getCachedIrFunction,
|
getCachedIrDeclaration = ::getCachedIrFunction,
|
||||||
createIrDeclaration = { parent, origin -> createIrFunction(fir, parent, predefinedOrigin = origin) },
|
createIrDeclaration = { parent, origin ->
|
||||||
|
createIrFunction(fir, parent, predefinedOrigin = origin)
|
||||||
|
},
|
||||||
createIrLazyDeclaration = { signature, lazyParent, declarationOrigin ->
|
createIrLazyDeclaration = { signature, lazyParent, declarationOrigin ->
|
||||||
val symbol = Fir2IrSimpleFunctionSymbol(signature, fir.containerSource)
|
createIrLazyFunction(fir, signature, lazyParent, declarationOrigin)
|
||||||
val irFunction = fir.convertWithOffsets { startOffset, endOffset ->
|
|
||||||
symbolTable.declareSimpleFunction(signature, { symbol }) {
|
|
||||||
val isFakeOverride =
|
|
||||||
firFunctionSymbol is FirNamedFunctionSymbol && fir.isSubstitutionOrIntersectionOverride &&
|
|
||||||
firFunctionSymbol.dispatchReceiverClassOrNull() !=
|
|
||||||
firFunctionSymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
|
|
||||||
Fir2IrLazySimpleFunction(
|
|
||||||
components, startOffset, endOffset, declarationOrigin,
|
|
||||||
fir, lazyParent.fir, symbol, isFakeOverride
|
|
||||||
).apply {
|
|
||||||
this.parent = lazyParent
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
functionCache[fir] = irFunction
|
|
||||||
// NB: this is needed to prevent recursions in case of self bounds
|
|
||||||
(irFunction as Fir2IrLazySimpleFunction).prepareTypeParameters()
|
|
||||||
irFunction
|
|
||||||
}
|
}
|
||||||
) as IrFunctionSymbol
|
) as IrFunctionSymbol
|
||||||
if (unmatchedReceiver && dispatchReceiverLookupTag is ConeClassLookupTagWithFixedSymbol) {
|
if (unmatchedReceiver && dispatchReceiverLookupTag is ConeClassLookupTagWithFixedSymbol) {
|
||||||
@@ -1218,6 +1210,33 @@ class Fir2IrDeclarationStorage(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun createIrLazyFunction(
|
||||||
|
fir: FirSimpleFunction,
|
||||||
|
signature: IdSignature,
|
||||||
|
lazyParent: Fir2IrLazyClass,
|
||||||
|
declarationOrigin: IrDeclarationOrigin
|
||||||
|
): IrSimpleFunction {
|
||||||
|
val symbol = Fir2IrSimpleFunctionSymbol(signature, fir.containerSource)
|
||||||
|
val firFunctionSymbol = fir.symbol
|
||||||
|
val irFunction = fir.convertWithOffsets { startOffset, endOffset ->
|
||||||
|
symbolTable.declareSimpleFunction(signature, { symbol }) {
|
||||||
|
val isFakeOverride = fir.isSubstitutionOrIntersectionOverride &&
|
||||||
|
firFunctionSymbol.dispatchReceiverClassOrNull() !=
|
||||||
|
firFunctionSymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
|
||||||
|
Fir2IrLazySimpleFunction(
|
||||||
|
components, startOffset, endOffset, declarationOrigin,
|
||||||
|
fir, lazyParent.fir, symbol, isFakeOverride
|
||||||
|
).apply {
|
||||||
|
this.parent = lazyParent
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
functionCache[fir] = irFunction
|
||||||
|
// NB: this is needed to prevent recursions in case of self bounds
|
||||||
|
(irFunction as Fir2IrLazySimpleFunction).prepareTypeParameters()
|
||||||
|
return irFunction
|
||||||
|
}
|
||||||
|
|
||||||
fun getIrPropertySymbol(
|
fun getIrPropertySymbol(
|
||||||
firPropertySymbol: FirPropertySymbol,
|
firPropertySymbol: FirPropertySymbol,
|
||||||
dispatchReceiverLookupTag: ConeClassLikeLookupTag? = null
|
dispatchReceiverLookupTag: ConeClassLikeLookupTag? = null
|
||||||
@@ -1238,22 +1257,7 @@ class Fir2IrDeclarationStorage(
|
|||||||
getCachedIrDeclaration = ::getCachedIrProperty,
|
getCachedIrDeclaration = ::getCachedIrProperty,
|
||||||
createIrDeclaration = { parent, origin -> createIrProperty(fir, parent, predefinedOrigin = origin) },
|
createIrDeclaration = { parent, origin -> createIrProperty(fir, parent, predefinedOrigin = origin) },
|
||||||
createIrLazyDeclaration = { signature, lazyParent, declarationOrigin ->
|
createIrLazyDeclaration = { signature, lazyParent, declarationOrigin ->
|
||||||
val symbol = Fir2IrPropertySymbol(signature, fir.containerSource)
|
createIrLazyProperty(fir, signature, lazyParent, declarationOrigin)
|
||||||
val irProperty = fir.convertWithOffsets { startOffset, endOffset ->
|
|
||||||
symbolTable.declareProperty(signature, { symbol }) {
|
|
||||||
val isFakeOverride =
|
|
||||||
fir.isSubstitutionOrIntersectionOverride &&
|
|
||||||
firPropertySymbol.dispatchReceiverClassOrNull() !=
|
|
||||||
firPropertySymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
|
|
||||||
Fir2IrLazyProperty(
|
|
||||||
components, startOffset, endOffset, declarationOrigin, fir, lazyParent.fir, symbol, isFakeOverride
|
|
||||||
).apply {
|
|
||||||
this.parent = lazyParent
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
propertyCache[fir] = irProperty
|
|
||||||
return symbol
|
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -1284,6 +1288,33 @@ class Fir2IrDeclarationStorage(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun createIrLazyProperty(
|
||||||
|
fir: FirProperty,
|
||||||
|
signature: IdSignature,
|
||||||
|
lazyParent: Fir2IrLazyClass,
|
||||||
|
declarationOrigin: IrDeclarationOrigin
|
||||||
|
): IrProperty {
|
||||||
|
val symbol = Fir2IrPropertySymbol(signature, fir.containerSource)
|
||||||
|
val firPropertySymbol = fir.symbol
|
||||||
|
val irProperty = fir.convertWithOffsets { startOffset, endOffset ->
|
||||||
|
symbolTable.declareProperty(signature, { symbol }) {
|
||||||
|
val isFakeOverride =
|
||||||
|
fir.isSubstitutionOrIntersectionOverride &&
|
||||||
|
firPropertySymbol.dispatchReceiverClassOrNull() !=
|
||||||
|
firPropertySymbol.originalForSubstitutionOverride?.dispatchReceiverClassOrNull()
|
||||||
|
Fir2IrLazyProperty(
|
||||||
|
components, startOffset, endOffset, declarationOrigin, fir, lazyParent.fir, symbol, isFakeOverride
|
||||||
|
).apply {
|
||||||
|
this.parent = lazyParent
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
propertyCache[fir] = irProperty
|
||||||
|
// NB: this is needed to prevent recursions in case of self bounds
|
||||||
|
(irProperty as Fir2IrLazyProperty).prepareTypeParameters()
|
||||||
|
return irProperty
|
||||||
|
}
|
||||||
|
|
||||||
private inline fun <reified S : IrSymbol, reified D : IrOverridableDeclaration<S>> ConeClassLookupTagWithFixedSymbol.findIrFakeOverride(
|
private inline fun <reified S : IrSymbol, reified D : IrOverridableDeclaration<S>> ConeClassLookupTagWithFixedSymbol.findIrFakeOverride(
|
||||||
name: Name, originalDeclaration: IrOverridableDeclaration<S>
|
name: Name, originalDeclaration: IrOverridableDeclaration<S>
|
||||||
): IrSymbol? {
|
): IrSymbol? {
|
||||||
|
|||||||
+3
-1
@@ -16,6 +16,8 @@ import org.jetbrains.kotlin.fir.declarations.utils.allowsToHaveFakeOverride
|
|||||||
import org.jetbrains.kotlin.fir.declarations.utils.isExpect
|
import org.jetbrains.kotlin.fir.declarations.utils.isExpect
|
||||||
import org.jetbrains.kotlin.fir.declarations.utils.isLocal
|
import org.jetbrains.kotlin.fir.declarations.utils.isLocal
|
||||||
import org.jetbrains.kotlin.fir.declarations.utils.visibility
|
import org.jetbrains.kotlin.fir.declarations.utils.visibility
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.utils.*
|
||||||
|
import org.jetbrains.kotlin.fir.lazy.Fir2IrLazyClass
|
||||||
import org.jetbrains.kotlin.fir.resolve.defaultType
|
import org.jetbrains.kotlin.fir.resolve.defaultType
|
||||||
import org.jetbrains.kotlin.fir.resolve.toSymbol
|
import org.jetbrains.kotlin.fir.resolve.toSymbol
|
||||||
import org.jetbrains.kotlin.fir.scopes.FirTypeScope
|
import org.jetbrains.kotlin.fir.scopes.FirTypeScope
|
||||||
@@ -75,7 +77,7 @@ class FakeOverrideGenerator(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun IrClass.getFakeOverrides(klass: FirClass, realDeclarations: Collection<FirDeclaration>): List<IrDeclaration> {
|
private fun IrClass.getFakeOverrides(klass: FirClass, realDeclarations: Collection<FirDeclaration>): List<IrDeclaration> {
|
||||||
val result = mutableListOf<IrDeclaration>()
|
val result = mutableListOf<IrDeclaration>()
|
||||||
val useSiteMemberScope = klass.unsubstitutedScope(session, scopeSession, withForcedTypeCalculator = true)
|
val useSiteMemberScope = klass.unsubstitutedScope(session, scopeSession, withForcedTypeCalculator = true)
|
||||||
val superTypesCallableNames = useSiteMemberScope.getCallableNames()
|
val superTypesCallableNames = useSiteMemberScope.getCallableNames()
|
||||||
|
|||||||
Vendored
-6
@@ -3,12 +3,6 @@
|
|||||||
// SKIP_JDK6
|
// SKIP_JDK6
|
||||||
// FULL_JDK
|
// FULL_JDK
|
||||||
|
|
||||||
// IGNORE_BACKEND_FIR: JVM_IR
|
|
||||||
// FIR_STATUS: java.lang.StackOverflowError
|
|
||||||
// at Test.remove(removeAtBridgeToJavaDefault.kt:7)
|
|
||||||
// at Test.remove(removeAtBridgeToJavaDefault.kt:7)
|
|
||||||
// at Test.remove(removeAtBridgeToJavaDefault.kt:7)
|
|
||||||
|
|
||||||
// FILE: removeAtBridgeToJavaDefault.kt
|
// FILE: removeAtBridgeToJavaDefault.kt
|
||||||
class Test : IntArrayList()
|
class Test : IntArrayList()
|
||||||
|
|
||||||
|
|||||||
compiler/testData/codegen/box/builtinStubMethods/extendJavaClasses/removeAtBridgeToJavaSuperClass.kt
Vendored
-6
@@ -3,12 +3,6 @@
|
|||||||
// SKIP_JDK6
|
// SKIP_JDK6
|
||||||
// FULL_JDK
|
// FULL_JDK
|
||||||
|
|
||||||
// IGNORE_BACKEND_FIR: JVM_IR
|
|
||||||
// FIR_STATUS: java.lang.StackOverflowError
|
|
||||||
// at Test.remove(removeAtBridgeToJavaSuperClass.kt:7)
|
|
||||||
// at Test.remove(removeAtBridgeToJavaSuperClass.kt:7)
|
|
||||||
// at Test.remove(removeAtBridgeToJavaSuperClass.kt:7)
|
|
||||||
|
|
||||||
// FILE: removeAtBridgeToJavaSuperClass.kt
|
// FILE: removeAtBridgeToJavaSuperClass.kt
|
||||||
class Test : IntArrayList()
|
class Test : IntArrayList()
|
||||||
|
|
||||||
|
|||||||
-3
@@ -3,9 +3,6 @@
|
|||||||
// SKIP_JDK6
|
// SKIP_JDK6
|
||||||
// FULL_JDK
|
// FULL_JDK
|
||||||
|
|
||||||
// IGNORE_BACKEND_FIR: JVM_IR
|
|
||||||
// FIR_STATUS: java.lang.NoSuchMethodError: IntArrayList.removeAt(I)Ljava/lang/Integer;
|
|
||||||
|
|
||||||
// FILE: superCallToRemoveAtInJavaDefault.kt
|
// FILE: superCallToRemoveAtInJavaDefault.kt
|
||||||
class Test : IntArrayList() {
|
class Test : IntArrayList() {
|
||||||
override fun removeAt(index: Int): Int {
|
override fun removeAt(index: Int): Int {
|
||||||
|
|||||||
Reference in New Issue
Block a user