From a9d0e6d3dac9bbd5b4577ea66708754b1fa705c6 Mon Sep 17 00:00:00 2001 From: Dmitry Petrov Date: Thu, 31 May 2018 15:07:53 +0300 Subject: [PATCH] IrTypes: generateAnnotationConstructorCall -> ConstantValueGenerator --- .../psi2ir/generators/ModuleGenerator.kt | 6 +- .../psi2ir/generators/StatementGenerator.kt | 2 +- .../kotlin/ir/util/AnnotationGenerator.kt | 60 +------------------ .../kotlin/ir/util/ConstantValueGenerator.kt | 57 +++++++++++++++--- .../kotlin/ir/util/TypeTranslator.kt | 4 +- 5 files changed, 57 insertions(+), 72 deletions(-) diff --git a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/ModuleGenerator.kt b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/ModuleGenerator.kt index dbf388add3b..8f87250ca69 100644 --- a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/ModuleGenerator.kt +++ b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/ModuleGenerator.kt @@ -20,15 +20,15 @@ import org.jetbrains.kotlin.ir.declarations.IrFile import org.jetbrains.kotlin.ir.declarations.IrModuleFragment import org.jetbrains.kotlin.ir.declarations.impl.IrFileImpl import org.jetbrains.kotlin.ir.declarations.impl.IrModuleFragmentImpl +import org.jetbrains.kotlin.ir.util.ConstantValueGenerator import org.jetbrains.kotlin.ir.util.ExternalDependenciesGenerator import org.jetbrains.kotlin.psi.KtFile -import org.jetbrains.kotlin.ir.util.AnnotationGenerator import org.jetbrains.kotlin.resolve.BindingContext import org.jetbrains.kotlin.resolve.lazy.descriptors.findPackageFragmentForFile class ModuleGenerator(override val context: GeneratorContext) : Generator { - private val annotationGenerator = AnnotationGenerator(context.moduleDescriptor, context.symbolTable) + private val constantValueGenerator = ConstantValueGenerator(context.moduleDescriptor, context.symbolTable, null) fun generateModuleFragment(ktFiles: Collection): IrModuleFragment = generateModuleFragmentWithoutDependencies(ktFiles).also { irModule -> @@ -60,7 +60,7 @@ class ModuleGenerator(override val context: GeneratorContext) : Generator { for (ktAnnotationEntry in ktFile.annotationEntries) { val annotationDescriptor = getOrFail(BindingContext.ANNOTATION, ktAnnotationEntry) irFile.fileAnnotations.add(annotationDescriptor) - irFile.annotations.add(annotationGenerator.generateAnnotationConstructorCall(annotationDescriptor)) + irFile.annotations.add(constantValueGenerator.generateAnnotationConstructorCall(annotationDescriptor)) } for (ktDeclaration in ktFile.declarations) { diff --git a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/StatementGenerator.kt b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/StatementGenerator.kt index 4706d332648..808a3637716 100644 --- a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/StatementGenerator.kt +++ b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/StatementGenerator.kt @@ -222,7 +222,7 @@ class StatementGenerator( ) fun generateConstantExpression(expression: KtExpression, constant: CompileTimeConstant<*>): IrExpression = - ConstantValueGenerator(context.moduleDescriptor, context.symbolTable, null, null).generateConstantValueAsExpression( + ConstantValueGenerator(context.moduleDescriptor, context.symbolTable, null).generateConstantValueAsExpression( expression.startOffset, expression.endOffset, constant.toConstantValue(getInferredTypeWithImplicitCastsOrFail(expression)) diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/AnnotationGenerator.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/AnnotationGenerator.kt index ef65572854c..d27c6a8dcf5 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/AnnotationGenerator.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/AnnotationGenerator.kt @@ -5,33 +5,24 @@ package org.jetbrains.kotlin.ir.util -import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ModuleDescriptor import org.jetbrains.kotlin.descriptors.PropertySetterDescriptor -import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget import org.jetbrains.kotlin.descriptors.annotations.AnnotationWithTarget import org.jetbrains.kotlin.ir.IrElement -import org.jetbrains.kotlin.ir.UNDEFINED_OFFSET import org.jetbrains.kotlin.ir.declarations.* -import org.jetbrains.kotlin.ir.expressions.IrCall -import org.jetbrains.kotlin.ir.expressions.impl.IrCallImpl import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid -import org.jetbrains.kotlin.psi.psiUtil.startOffset -import org.jetbrains.kotlin.resolve.DescriptorUtils -import org.jetbrains.kotlin.resolve.source.PsiSourceElement import org.jetbrains.kotlin.types.KotlinType -import org.jetbrains.kotlin.utils.addToStdlib.safeAs class AnnotationGenerator( moduleDescriptor: ModuleDescriptor, - private val symbolTable: SymbolTable + symbolTable: SymbolTable ) : IrElementVisitorVoid { private val typeTranslator = TypeTranslator(moduleDescriptor, symbolTable) private val scopedTypeParameterResolver = ScopedTypeParametersResolver() - private val constantValueGenerator = ConstantValueGenerator(moduleDescriptor, symbolTable, this, scopedTypeParameterResolver) + private val constantValueGenerator = ConstantValueGenerator(moduleDescriptor, symbolTable, scopedTypeParameterResolver) override fun visitElement(element: IrElement) { element.acceptChildrenVoid(this) @@ -73,57 +64,12 @@ class AnnotationGenerator( private fun List.generateAnnotationConstructorCalls(declaration: IrDeclaration) { mapTo(declaration.annotations) { - generateAnnotationConstructorCall(it.annotation) + constantValueGenerator.generateAnnotationConstructorCall(it.annotation) } } private fun KotlinType.toIrType() = typeTranslator.translateType(this) - fun generateAnnotationConstructorCall(annotationDescriptor: AnnotationDescriptor): IrCall { - val annotationType = annotationDescriptor.type - val annotationClassDescriptor = annotationType.constructor.declarationDescriptor as? ClassDescriptor - ?: throw AssertionError("No declaration descriptor for annotation $annotationDescriptor") - - if (annotationClassDescriptor !is ClassDescriptor) { - throw AssertionError("Annotation type descriptor is not a class: $annotationClassDescriptor") - } - - assert(DescriptorUtils.isAnnotationClass(annotationClassDescriptor)) { - "Annotation class expected: $annotationClassDescriptor" - } - - val primaryConstructorDescriptor = annotationClassDescriptor.unsubstitutedPrimaryConstructor - ?: annotationClassDescriptor.constructors.singleOrNull() - ?: throw AssertionError("No constructor for annotation class $annotationClassDescriptor") - val primaryConstructorSymbol = symbolTable.referenceConstructor(primaryConstructorDescriptor) - - val psi = annotationDescriptor.source.safeAs()?.psi - val startOffset = psi?.startOffset ?: UNDEFINED_OFFSET - val endOffset = psi?.startOffset ?: UNDEFINED_OFFSET - - val irCall = IrCallImpl( - startOffset, endOffset, - annotationType.toIrType(), - primaryConstructorSymbol, primaryConstructorDescriptor, - typeArgumentsCount = 0 - ) - - for (valueParameter in primaryConstructorDescriptor.valueParameters) { - val argumentIndex = valueParameter.index - val argumentValue = annotationDescriptor.allValueArguments[valueParameter.name] ?: continue - val irArgument = - constantValueGenerator.generateConstantValueAsExpression( - UNDEFINED_OFFSET, - UNDEFINED_OFFSET, - argumentValue, - valueParameter.varargElementType - ) - irCall.putValueArgument(argumentIndex, irArgument) - } - - return irCall - } - private fun isAnnotationTargetMatchingDeclaration(target: AnnotationUseSiteTarget?, element: IrElement): Boolean = when (element) { is IrProperty -> diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/ConstantValueGenerator.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/ConstantValueGenerator.kt index e9e9dc39fbc..56bba04d291 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/ConstantValueGenerator.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/ConstantValueGenerator.kt @@ -8,13 +8,16 @@ package org.jetbrains.kotlin.ir.util import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.descriptors.ModuleDescriptor import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor +import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor import org.jetbrains.kotlin.incremental.components.NoLookupLocation +import org.jetbrains.kotlin.ir.UNDEFINED_OFFSET +import org.jetbrains.kotlin.ir.expressions.IrCall import org.jetbrains.kotlin.ir.expressions.IrExpression -import org.jetbrains.kotlin.ir.expressions.impl.IrClassReferenceImpl -import org.jetbrains.kotlin.ir.expressions.impl.IrConstImpl -import org.jetbrains.kotlin.ir.expressions.impl.IrGetEnumValueImpl -import org.jetbrains.kotlin.ir.expressions.impl.IrVarargImpl +import org.jetbrains.kotlin.ir.expressions.impl.* +import org.jetbrains.kotlin.psi.psiUtil.startOffset +import org.jetbrains.kotlin.resolve.DescriptorUtils import org.jetbrains.kotlin.resolve.constants.* +import org.jetbrains.kotlin.resolve.source.PsiSourceElement import org.jetbrains.kotlin.types.KotlinType import org.jetbrains.kotlin.types.typeUtil.builtIns import org.jetbrains.kotlin.utils.addToStdlib.safeAs @@ -22,7 +25,6 @@ import org.jetbrains.kotlin.utils.addToStdlib.safeAs class ConstantValueGenerator( private val moduleDescriptor: ModuleDescriptor, private val symbolTable: SymbolTable, - private val annotationGenerator: AnnotationGenerator?, private val scopedTypeParameterResolver: ScopedTypeParametersResolver? ) { @@ -81,10 +83,7 @@ class ConstantValueGenerator( ) } - is AnnotationValue -> { - if (annotationGenerator == null) throw AssertionError("Unexpected AnnotationValue: $constantValue") - annotationGenerator.generateAnnotationConstructorCall(constantValue.value) - } + is AnnotationValue -> generateAnnotationConstructorCall(constantValue.value) is KClassValue -> { val classifierKtType = constantValue.value @@ -107,5 +106,45 @@ class ConstantValueGenerator( } } + fun generateAnnotationConstructorCall(annotationDescriptor: AnnotationDescriptor): IrCall { + val annotationType = annotationDescriptor.type + val annotationClassDescriptor = annotationType.constructor.declarationDescriptor as? ClassDescriptor + ?: throw AssertionError("No declaration descriptor for annotation $annotationDescriptor") + + assert(DescriptorUtils.isAnnotationClass(annotationClassDescriptor)) { + "Annotation class expected: $annotationClassDescriptor" + } + + val primaryConstructorDescriptor = annotationClassDescriptor.unsubstitutedPrimaryConstructor + ?: annotationClassDescriptor.constructors.singleOrNull() + ?: throw AssertionError("No constructor for annotation class $annotationClassDescriptor") + val primaryConstructorSymbol = symbolTable.referenceConstructor(primaryConstructorDescriptor) + + val psi = annotationDescriptor.source.safeAs()?.psi + val startOffset = psi?.startOffset ?: UNDEFINED_OFFSET + val endOffset = psi?.startOffset ?: UNDEFINED_OFFSET + + val irCall = IrCallImpl( + startOffset, endOffset, + annotationType.toIrType(), + primaryConstructorSymbol, primaryConstructorDescriptor, + typeArgumentsCount = 0 + ) + + for (valueParameter in primaryConstructorDescriptor.valueParameters) { + val argumentIndex = valueParameter.index + val argumentValue = annotationDescriptor.allValueArguments[valueParameter.name] ?: continue + val irArgument = generateConstantValueAsExpression( + UNDEFINED_OFFSET, + UNDEFINED_OFFSET, + argumentValue, + valueParameter.varargElementType + ) + irCall.putValueArgument(argumentIndex, irArgument) + } + + return irCall + } + private fun KotlinType.getArrayElementType() = builtIns.getArrayElementType(this) } \ No newline at end of file diff --git a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/TypeTranslator.kt b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/TypeTranslator.kt index de75c224a1d..4c44ba11d37 100644 --- a/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/TypeTranslator.kt +++ b/compiler/ir/ir.tree/src/org/jetbrains/kotlin/ir/util/TypeTranslator.kt @@ -25,8 +25,8 @@ class TypeTranslator( private val symbolTable: SymbolTable ) { - private val annotationGenerator = AnnotationGenerator(moduleDescriptor, symbolTable) private val typeParametersResolver = ScopedTypeParametersResolver() + private val constantValueGenerator = ConstantValueGenerator(moduleDescriptor, symbolTable, typeParametersResolver) fun enterScope(irElement: IrTypeParametersContainer) { typeParametersResolver.enterTypeParameterScope(irElement) @@ -97,7 +97,7 @@ class TypeTranslator( private fun translateTypeAnnotations(annotations: Annotations): List = annotations.getAllAnnotations().map { // TODO filter out annotation targets - annotationGenerator.generateAnnotationConstructorCall(it.annotation) + constantValueGenerator.generateAnnotationConstructorCall(it.annotation) } private fun translateTypeArguments(arguments: List) =