FIR IDE: add KtClassInitializerSymbol

This commit is contained in:
Tianyu Geng
2021-08-25 21:07:08 -07:00
committed by Ilya Kirillov
parent 6f9712a812
commit 50166c776c
8 changed files with 138 additions and 5 deletions
@@ -38,6 +38,7 @@ import org.jetbrains.kotlin.fir.symbols.impl.FirClassifierSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.types.impl.ConeClassLikeTypeImpl
import org.jetbrains.kotlin.analysis.api.fir.symbols.KtFirClassInitializerSymbol
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.types.Variance
@@ -68,6 +69,7 @@ internal class KtSymbolByFirBuilder private constructor(
val functionLikeBuilder = FunctionLikeSymbolBuilder()
val variableLikeBuilder = VariableLikeSymbolBuilder()
val callableBuilder = CallableSymbolBuilder()
val anonymousInitializerBuilder = AnonymousInitializerBuilder()
val typeBuilder = TypeBuilder()
constructor(
@@ -337,6 +339,12 @@ internal class KtSymbolByFirBuilder private constructor(
}
}
inner class AnonymousInitializerBuilder {
fun buildClassInitializer(fir: FirAnonymousInitializer): KtClassInitializerSymbol {
return symbolsCache.cache(fir) { KtFirClassInitializerSymbol(fir, resolveState, token) }
}
}
inner class TypeBuilder {
fun buildKtType(coneType: ConeKotlinType): KtType {
return typesCache.cache(coneType) {
@@ -0,0 +1,32 @@
/*
* Copyright 2010-2021 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.analysis.api.fir.symbols
import com.intellij.psi.PsiElement
import org.jetbrains.kotlin.analysis.api.fir.findPsi
import org.jetbrains.kotlin.analysis.api.fir.utils.firRef
import org.jetbrains.kotlin.analysis.api.symbols.KtClassInitializerSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtSymbol
import org.jetbrains.kotlin.analysis.api.symbols.markers.KtSymbolKind
import org.jetbrains.kotlin.analysis.api.symbols.pointers.KtSymbolPointer
import org.jetbrains.kotlin.analysis.api.tokens.ValidityToken
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.FirModuleResolveState
import org.jetbrains.kotlin.fir.declarations.FirAnonymousInitializer
internal class KtFirClassInitializerSymbol(
fir: FirAnonymousInitializer,
resolveState: FirModuleResolveState,
override val token: ValidityToken,
) : KtClassInitializerSymbol(), KtFirSymbol<FirAnonymousInitializer> {
override val firRef = firRef(fir, resolveState)
override val psi: PsiElement? by firRef.withFirAndCache { fir -> fir.findPsi(fir.moduleData.session) }
override fun createPointer(): KtSymbolPointer<KtSymbol> {
TODO("Figure out how to create such a pointer. Should we give an index to class initializers?")
}
override val symbolKind: KtSymbolKind get() = KtSymbolKind.MEMBER
}
@@ -5,11 +5,6 @@
package org.jetbrains.kotlin.analysis.api.fir.symbols
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.renderWithType
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.*
import org.jetbrains.kotlin.analysis.api.KtAnalysisSession
import org.jetbrains.kotlin.analysis.api.ValidityTokenOwner
import org.jetbrains.kotlin.analysis.api.fir.KtSymbolByFirBuilder
@@ -17,6 +12,15 @@ import org.jetbrains.kotlin.analysis.api.fir.utils.weakRef
import org.jetbrains.kotlin.analysis.api.symbols.*
import org.jetbrains.kotlin.analysis.api.tokens.ValidityToken
import org.jetbrains.kotlin.analysis.api.withValidityAssertion
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.FirModuleResolveState
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.getOrBuildFirFile
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.getOrBuildFirOfType
import org.jetbrains.kotlin.analysis.low.level.api.fir.api.withFirDeclarationOfType
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.renderWithType
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
import org.jetbrains.kotlin.analysis.api.symbols.KtClassInitializerSymbol
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name
@@ -130,6 +134,12 @@ internal class KtFirSymbolProvider(
}
}
override fun getClassInitializerSymbol(psi: KtClassInitializer): KtClassInitializerSymbol = withValidityAssertion {
psi.withFirDeclarationOfType<FirAnonymousInitializer, KtClassInitializerSymbol>(resolveState) {
firSymbolBuilder.anonymousInitializerBuilder.buildClassInitializer(it)
}
}
override fun getClassOrObjectSymbolByClassId(classId: ClassId): KtClassOrObjectSymbol? = withValidityAssertion {
val symbol = firSymbolProvider.getClassLikeSymbolByClassId(classId) as? FirRegularClassSymbol ?: return null
firSymbolBuilder.classifierBuilder.buildNamedClassOrObjectSymbol(symbol.fir)
@@ -48,6 +48,12 @@ public class SymbolByPsiTestGenerated extends AbstractSymbolByPsiTest {
runTest("analysis/analysis-api/testData/symbols/symbolByPsi/class.kt");
}
@Test
@TestMetadata("classInitializer.kt")
public void testClassInitializer() throws Exception {
runTest("analysis/analysis-api/testData/symbols/symbolByPsi/classInitializer.kt");
}
@Test
@TestMetadata("classMembes.kt")
public void testClassMembes() throws Exception {
@@ -0,0 +1,10 @@
/*
* Copyright 2010-2021 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.analysis.api.symbols
import org.jetbrains.kotlin.analysis.api.symbols.markers.KtSymbolWithKind
public abstract class KtClassInitializerSymbol : KtSymbol, KtSymbolWithKind
@@ -27,6 +27,7 @@ public abstract class KtSymbolProvider : KtAnalysisSessionComponent() {
literalExpression?.let(::getAnonymousObjectSymbol) ?: getClassOrObjectSymbol(psi)
}
is KtPropertyAccessor -> getPropertyAccessorSymbol(psi)
is KtClassInitializer -> getClassInitializerSymbol(psi)
else -> error("Cannot build symbol for ${psi::class}")
}
@@ -44,6 +45,7 @@ public abstract class KtSymbolProvider : KtAnalysisSessionComponent() {
public abstract fun getClassOrObjectSymbol(psi: KtClassOrObject): KtClassOrObjectSymbol
public abstract fun getNamedClassOrObjectSymbol(psi: KtClassOrObject): KtNamedClassOrObjectSymbol?
public abstract fun getPropertyAccessorSymbol(psi: KtPropertyAccessor): KtPropertyAccessorSymbol
public abstract fun getClassInitializerSymbol(psi: KtClassInitializer): KtClassInitializerSymbol
public abstract fun getClassOrObjectSymbolByClassId(classId: ClassId): KtClassOrObjectSymbol?
@@ -0,0 +1,8 @@
// DO_NOT_CHECK_SYMBOL_RESTORE
class A {
val i: Int
init {
i = 1
}
}
@@ -0,0 +1,57 @@
KtFirKotlinPropertySymbol:
annotatedType: [] kotlin/Int
annotationClassIds: []
annotations: []
callableIdIfNonLocal: /A.i
dispatchType: A
getter: KtFirPropertyGetterSymbol(<getter>)
hasBackingField: true
hasGetter: true
hasSetter: false
initializer: null
isConst: false
isExtension: false
isFromPrimaryConstructor: false
isLateInit: false
isOverride: false
isStatic: false
isVal: true
modality: FINAL
name: i
origin: SOURCE
receiverType: null
setter: null
symbolKind: MEMBER
visibility: Public
deprecationStatus: null
getterDeprecationStatus: null
javaGetterName: getI
javaSetterName: null
setterDeprecationStatus: null
KtFirClassInitializerSymbol:
origin: SOURCE
symbolKind: MEMBER
deprecationStatus: null
KtFirNamedClassOrObjectSymbol:
annotationClassIds: []
annotations: []
classIdIfNonLocal: A
classKind: CLASS
companionObject: null
isData: false
isExternal: false
isFun: false
isInline: false
isInner: false
modality: FINAL
name: A
origin: SOURCE
superTypes: [
[] kotlin/Any
]
symbolKind: TOP_LEVEL
typeParameters: []
visibility: Public
deprecationStatus: null