Raw FIR: copy class type-parameters into constructors properly
This commit is contained in:
committed by
Mikhail Glukhikh
parent
9cef9e4056
commit
77817cb750
@@ -19,8 +19,7 @@ import org.jetbrains.kotlin.fir.labels.FirLabelImpl
|
||||
import org.jetbrains.kotlin.fir.references.*
|
||||
import org.jetbrains.kotlin.fir.symbols.CallableId
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.*
|
||||
import org.jetbrains.kotlin.fir.types.FirTypeRef
|
||||
import org.jetbrains.kotlin.fir.types.FirTypeProjection
|
||||
import org.jetbrains.kotlin.fir.types.*
|
||||
import org.jetbrains.kotlin.fir.types.impl.*
|
||||
import org.jetbrains.kotlin.lexer.KtTokens
|
||||
import org.jetbrains.kotlin.lexer.KtTokens.*
|
||||
@@ -110,7 +109,7 @@ class RawFirBuilder(val session: FirSession, val stubMode: Boolean) {
|
||||
return when (this) {
|
||||
is KtSecondaryConstructor -> toFirConstructor(
|
||||
delegatedSuperType,
|
||||
delegatedSelfType!!,
|
||||
delegatedSelfType ?: FirErrorTypeRefImpl(this@RawFirBuilder.session, this, "Constructor in object"),
|
||||
owner,
|
||||
hasPrimaryConstructor
|
||||
)
|
||||
@@ -408,7 +407,7 @@ class RawFirBuilder(val session: FirSession, val stubMode: Boolean) {
|
||||
firDelegatedCall
|
||||
)
|
||||
this?.extractAnnotationsTo(firConstructor)
|
||||
owner.extractTypeParametersTo(firConstructor)
|
||||
firConstructor.typeParameters += typeParametersFromSelfType(delegatedSelfTypeRef)
|
||||
this?.extractValueParametersTo(firConstructor)
|
||||
return firConstructor
|
||||
}
|
||||
@@ -437,16 +436,19 @@ class RawFirBuilder(val session: FirSession, val stubMode: Boolean) {
|
||||
}
|
||||
|
||||
private fun KtClassOrObject.toDelegatedSelfType(firClass: FirRegularClass): FirTypeRef {
|
||||
val typeParameters = firClass.typeParameters.map {
|
||||
FirTypeParameterImpl(session, it.psi, FirTypeParameterSymbol(), it.name, Variance.INVARIANT, false).apply {
|
||||
this.bounds += it.bounds
|
||||
}
|
||||
}
|
||||
return FirResolvedTypeRefImpl(
|
||||
session,
|
||||
this,
|
||||
ConeClassTypeImpl(
|
||||
firClass.symbol.toLookupTag(),
|
||||
firClass.typeParameters.map { ConeTypeParameterTypeImpl(it.symbol, false) }.toTypedArray(),
|
||||
typeParameters.map { ConeTypeParameterTypeImpl(it.symbol, false) }.toTypedArray(),
|
||||
false
|
||||
),
|
||||
isMarkedNullable = false,
|
||||
annotations = emptyList()
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -752,13 +754,20 @@ class RawFirBuilder(val session: FirSession, val stubMode: Boolean) {
|
||||
)
|
||||
firFunctions += firConstructor
|
||||
extractAnnotationsTo(firConstructor)
|
||||
owner.extractTypeParametersTo(firConstructor)
|
||||
firConstructor.typeParameters += typeParametersFromSelfType(delegatedSelfTypeRef)
|
||||
extractValueParametersTo(firConstructor)
|
||||
firConstructor.body = buildFirBody()
|
||||
firFunctions.removeLast()
|
||||
return firConstructor
|
||||
}
|
||||
|
||||
private fun typeParametersFromSelfType(delegatedSelfTypeRef: FirTypeRef): List<FirTypeParameter> {
|
||||
return delegatedSelfTypeRef.coneTypeSafe()
|
||||
?.typeArguments
|
||||
?.map { ((it as ConeTypeParameterType).lookupTag as FirTypeParameterSymbol).fir }
|
||||
?: emptyList()
|
||||
}
|
||||
|
||||
private fun KtConstructorDelegationCall.convert(
|
||||
delegatedSuperTypeRef: FirTypeRef?,
|
||||
delegatedSelfTypeRef: FirTypeRef,
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
FILE: complexTypes.kt
|
||||
public? final? class C<T, out S> : kotlin/Any {
|
||||
public? constructor<T, out S>(): R|a/b/C<T, S>| {
|
||||
public? constructor<T, S>(): R|a/b/C<T, S>| {
|
||||
super<kotlin/Any>()
|
||||
}
|
||||
|
||||
public? final? inner class D<R, in P> : kotlin/Any {
|
||||
public? constructor<R, in P>(): R|a/b/C.D<R, P>| {
|
||||
public? constructor<R, P>(): R|a/b/C.D<R, P>| {
|
||||
super<kotlin/Any>()
|
||||
}
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ FILE: typeParameters.kt
|
||||
public? final typealias StringList = List<out String>
|
||||
public? final typealias AnyList = List<*>
|
||||
public? abstract class AbstractList<out T : Any> : List<T> {
|
||||
public? constructor<out T : Any>(): R|AbstractList<T>| {
|
||||
public? constructor<T : Any>(): R|AbstractList<T>| {
|
||||
super<kotlin/Any>()
|
||||
}
|
||||
|
||||
|
||||
+3
-3
@@ -1,5 +1,5 @@
|
||||
open class Base<T>(val x: T)
|
||||
open class Base<T1>(val x: T1)
|
||||
|
||||
class Derived<T : Any>(x: T) : Base<T>(x)
|
||||
class Derived<T2 : Any>(x: T2) : Base<T2>(x)
|
||||
|
||||
fun <T : Any> create(x: T): Derived<T> = Derived(x)
|
||||
fun <T3 : Any> create(x: T3) /* Derived<T3> */ = Derived(x)
|
||||
+9
-9
@@ -1,19 +1,19 @@
|
||||
FILE: derivedClass.kt
|
||||
public open class Base<T> : R|kotlin/Any| {
|
||||
public constructor<T>(x: R|T|): R|Base<T>| {
|
||||
public open class Base<T1> : R|kotlin/Any| {
|
||||
public constructor<T1>(x: R|T1|): R|Base<T1>| {
|
||||
super<R|kotlin/Any|>()
|
||||
}
|
||||
|
||||
public final val x: R|T| = R|<local>/x|
|
||||
public get(): R|T|
|
||||
public final val x: R|T1| = R|<local>/x|
|
||||
public get(): R|T1|
|
||||
|
||||
}
|
||||
public final class Derived<T : R|kotlin/Any|> : R|Base<T>| {
|
||||
public constructor<T : R|kotlin/Any|>(x: R|T|): R|Derived<T>| {
|
||||
super<R|Base<T>|>(R|<local>/x|)
|
||||
public final class Derived<T2 : R|kotlin/Any|> : R|Base<T2>| {
|
||||
public constructor<T2 : R|kotlin/Any|>(x: R|T2|): R|Derived<T2>| {
|
||||
super<R|Base<T2>|>(R|<local>/x|)
|
||||
}
|
||||
|
||||
}
|
||||
public final fun <T : R|kotlin/Any|> create(x: R|T|): R|Derived<T>| {
|
||||
^create R|/Derived.Derived|(R|<local>/x|)
|
||||
public final fun <T3 : R|kotlin/Any|> create(x: R|T3|): R|Derived<T3>| {
|
||||
^create R|/Derived.Derived|<R|T3|>(R|<local>/x|)
|
||||
}
|
||||
|
||||
+1
-1
@@ -15,5 +15,5 @@ FILE: typeAliasConstructor.kt
|
||||
public final typealias BB<U> = R|B<U>|
|
||||
public final fun main(): R|kotlin/Unit| {
|
||||
lval x: R|A| = R|/A.A|(Int(1))
|
||||
lval y: <ERROR TYPE REF: Inapplicable(INAPPLICABLE): [/B.B]> = <Inapplicable(INAPPLICABLE): [/B.B]>#<R|kotlin/String|>(String(bb))
|
||||
lval y: R|B<kotlin/String>| = R|/B.B|<R|kotlin/String|>(String(bb))
|
||||
}
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
FILE: complexTypes.kt
|
||||
public final class C<T, out S> : R|kotlin/Any| {
|
||||
public constructor<T, out S>(): R|a/b/C<T, S>| {
|
||||
public constructor<T, S>(): R|a/b/C<T, S>| {
|
||||
super<R|kotlin/Any|>()
|
||||
}
|
||||
|
||||
public final inner class D<R, in P> : R|kotlin/Any| {
|
||||
public constructor<R, in P>(): R|a/b/C.D<R, P>| {
|
||||
public constructor<R, P>(): R|a/b/C.D<R, P>| {
|
||||
super<R|kotlin/Any|>()
|
||||
}
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ FILE: typeParameters.kt
|
||||
public final typealias StringList = R|List<out kotlin/String>|
|
||||
public final typealias AnyList = R|List<*>|
|
||||
public abstract class AbstractList<out T : R|kotlin/Any|> : R|List<T>| {
|
||||
public constructor<out T : R|kotlin/Any|>(): R|AbstractList<T>| {
|
||||
public constructor<T : R|kotlin/Any|>(): R|AbstractList<T>| {
|
||||
super<R|kotlin/Any|>()
|
||||
}
|
||||
|
||||
|
||||
@@ -6,10 +6,8 @@
|
||||
package org.jetbrains.kotlin.fir.declarations
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||
import org.jetbrains.kotlin.fir.FirSession
|
||||
import org.jetbrains.kotlin.fir.expressions.FirAnnotationContainer
|
||||
import org.jetbrains.kotlin.fir.expressions.FirStatement
|
||||
import org.jetbrains.kotlin.fir.scopes.FirScope
|
||||
import org.jetbrains.kotlin.fir.types.ConeClassLikeType
|
||||
import org.jetbrains.kotlin.fir.types.FirTypeRef
|
||||
import org.jetbrains.kotlin.fir.types.coneTypeSafe
|
||||
@@ -28,8 +26,15 @@ interface FirClass : FirDeclarationContainer, FirStatement, FirAnnotationContain
|
||||
for (superType in superTypeRefs) {
|
||||
superType.accept(visitor, data)
|
||||
}
|
||||
var constructorFound = false
|
||||
for (declaration in declarations) {
|
||||
declaration.accept(visitor, data)
|
||||
if (!constructorFound && declaration is FirConstructor) {
|
||||
for (typeParameter in declaration.typeParameters) {
|
||||
typeParameter.accept(visitor, data)
|
||||
}
|
||||
constructorFound = true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,11 +23,13 @@ interface FirConstructor : @VisitedSupertype FirFunction, FirCallableMemberDecla
|
||||
visitor.visitConstructor(this, data)
|
||||
|
||||
override fun <R, D> acceptChildren(visitor: FirVisitor<R, D>, data: D) {
|
||||
super<FirCallableMemberDeclaration>.acceptChildren(visitor, data)
|
||||
acceptAnnotations(visitor, data)
|
||||
status.accept(visitor, data)
|
||||
delegatedConstructor?.accept(visitor, data)
|
||||
for (parameter in valueParameters) {
|
||||
parameter.accept(visitor, data)
|
||||
}
|
||||
returnTypeRef.accept(visitor, data)
|
||||
body?.accept(visitor, data)
|
||||
}
|
||||
}
|
||||
@@ -10,6 +10,7 @@ import org.jetbrains.kotlin.descriptors.ClassKind
|
||||
import org.jetbrains.kotlin.descriptors.Modality
|
||||
import org.jetbrains.kotlin.descriptors.Visibility
|
||||
import org.jetbrains.kotlin.fir.FirSession
|
||||
import org.jetbrains.kotlin.fir.declarations.FirConstructor
|
||||
import org.jetbrains.kotlin.fir.declarations.FirDeclaration
|
||||
import org.jetbrains.kotlin.fir.declarations.FirRegularClass
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirClassSymbol
|
||||
@@ -17,6 +18,7 @@ import org.jetbrains.kotlin.fir.transformInplace
|
||||
import org.jetbrains.kotlin.fir.types.FirTypeRef
|
||||
import org.jetbrains.kotlin.fir.visitors.FirTransformer
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstanceOrNull
|
||||
|
||||
open class FirClassImpl(
|
||||
session: FirSession,
|
||||
@@ -69,6 +71,7 @@ open class FirClassImpl(
|
||||
superTypeRefs.transformInplace(transformer, data)
|
||||
val result = super<FirAbstractMemberDeclaration>.transformChildren(transformer, data) as FirRegularClass
|
||||
|
||||
declarations.firstIsInstanceOrNull<FirConstructorImpl>()?.typeParameters?.transformInplace(transformer, data)
|
||||
// Transform declarations in last turn
|
||||
declarations.transformInplace(transformer, data)
|
||||
companionObject = declarations.asSequence().filterIsInstance<FirRegularClass>().firstOrNull { it.isCompanion }
|
||||
|
||||
+4
-1
@@ -61,11 +61,14 @@ open class FirConstructorImpl : FirAbstractCallableMember, FirConstructor {
|
||||
override var body: FirBlock? = null
|
||||
|
||||
override fun <D> transformChildren(transformer: FirTransformer<D>, data: D): FirElement {
|
||||
annotations.transformInplace(transformer, data)
|
||||
valueParameters.transformInplace(transformer, data)
|
||||
returnTypeRef = returnTypeRef.transformSingle(transformer, data)
|
||||
status = status.transformSingle(transformer, data)
|
||||
delegatedConstructor?.transformSingle(transformer, data)
|
||||
body = body?.transformSingle(transformer, data)
|
||||
|
||||
return super<FirAbstractCallableMember>.transformChildren(transformer, data)
|
||||
return this
|
||||
}
|
||||
|
||||
companion object {
|
||||
|
||||
Reference in New Issue
Block a user