Refactor SAM type handling, replace non-approximated arguments with *

This commit is contained in:
Dmitry Petrov
2021-06-17 13:37:19 +03:00
committed by TeamCityServer
parent 4aeabb6b0f
commit c77884f067
23 changed files with 721 additions and 128 deletions
@@ -51,10 +51,7 @@ import org.jetbrains.kotlin.resolve.calls.components.isVararg
import org.jetbrains.kotlin.resolve.calls.model.*
import org.jetbrains.kotlin.resolve.calls.tower.NewResolvedCallImpl
import org.jetbrains.kotlin.resolve.scopes.receivers.*
import org.jetbrains.kotlin.types.KotlinType
import org.jetbrains.kotlin.types.TypeProjectionImpl
import org.jetbrains.kotlin.types.TypeSubstitutor
import org.jetbrains.kotlin.types.Variance
import org.jetbrains.kotlin.types.*
import org.jetbrains.kotlin.types.typeUtil.isUnit
import org.jetbrains.kotlin.util.OperatorNameConventions
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
@@ -567,7 +564,7 @@ fun StatementGenerator.generateSamConversionForValueArgumentsIfRequired(call: Ca
val typeSubstitutor = TypeSubstitutor.create(substitutionContext)
for (i in underlyingValueParameters.indices) {
val underlyingValueParameter = underlyingValueParameters[i]
val underlyingValueParameter: ValueParameterDescriptor = underlyingValueParameters[i]
val expectedSamConversionTypesForVararg =
if (expectSamConvertedArgumentToBeAvailableInResolvedCall && resolvedCall is NewResolvedCallImpl<*>) {
@@ -585,7 +582,7 @@ fun StatementGenerator.generateSamConversionForValueArgumentsIfRequired(call: Ca
if (!originalValueParameters[i].type.isFunctionTypeOrSubtype) continue
}
val samKotlinType = samConversion.getSamTypeForValueParameter(underlyingValueParameter, context.languageVersionSettings)
val samKotlinType = getSamTypeForValueParameter(underlyingValueParameter)
?: underlyingValueParameter.varargElementType // If we have a vararg, vararg element type will be taken
?: underlyingValueParameter.type
@@ -645,6 +642,23 @@ fun StatementGenerator.generateSamConversionForValueArgumentsIfRequired(call: Ca
}
}
private fun StatementGenerator.getSamTypeForValueParameter(valueParameter: ValueParameterDescriptor): KotlinType? {
val approximatedSamType = context.samTypeApproximator.getSamTypeForValueParameter(valueParameter)
?: return null
if (!context.extensions.samConversion.isSamType(approximatedSamType))
return null
val classDescriptor = approximatedSamType.constructor.declarationDescriptor
?: throw AssertionError("SAM type is expected to be a class type: $approximatedSamType")
return approximatedSamType.replace(
approximatedSamType.arguments.mapIndexed { index: Int, typeProjection: TypeProjection ->
if (typeProjection.type.constructor.isDenotable)
typeProjection
else
StarProjectionImpl(classDescriptor.typeConstructor.parameters[index])
}
)
}
fun StatementGenerator.pregenerateValueArgumentsUsing(
call: CallBuilder,
resolvedCall: ResolvedCall<*>,
@@ -5,6 +5,7 @@
package org.jetbrains.kotlin.psi2ir.generators
import org.jetbrains.kotlin.backend.common.SamTypeApproximator
import org.jetbrains.kotlin.builtins.ReflectionTypes
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.descriptors.CallableDescriptor
@@ -33,10 +34,12 @@ class GeneratorContext(
) : IrGeneratorContext {
internal val callToSubstitutedDescriptorMap = mutableMapOf<IrDeclarationReference, CallableDescriptor>()
// TODO: inject a correct StorageManager instance, or store NotFoundClasses inside ModuleDescriptor
val reflectionTypes = ReflectionTypes(moduleDescriptor, NotFoundClasses(LockBasedStorageManager.NO_LOCKS, moduleDescriptor))
fun IrDeclarationReference.commitSubstituted(descriptor: CallableDescriptor) {
callToSubstitutedDescriptorMap[this] = descriptor
}
// TODO: inject a correct StorageManager instance, or store NotFoundClasses inside ModuleDescriptor
val reflectionTypes = ReflectionTypes(moduleDescriptor, NotFoundClasses(LockBasedStorageManager.NO_LOCKS, moduleDescriptor))
val samTypeApproximator = SamTypeApproximator(moduleDescriptor.builtIns, languageVersionSettings)
}
@@ -8,15 +8,12 @@ package org.jetbrains.kotlin.psi2ir.generators
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.DescriptorVisibility
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.descriptors.ValueParameterDescriptor
import org.jetbrains.kotlin.ir.expressions.IrDelegatingConstructorCall
import org.jetbrains.kotlin.ir.symbols.IrScriptSymbol
import org.jetbrains.kotlin.ir.util.StubGeneratorExtensions
import org.jetbrains.kotlin.psi.KtPureClassOrObject
import org.jetbrains.kotlin.resolve.scopes.MemberScope
import org.jetbrains.kotlin.types.KotlinType
import org.jetbrains.kotlin.backend.common.SamTypeFactory
import org.jetbrains.kotlin.config.LanguageVersionSettings
open class GeneratorExtensions : StubGeneratorExtensions() {
open val samConversion: SamConversion
@@ -25,11 +22,6 @@ open class GeneratorExtensions : StubGeneratorExtensions() {
open class SamConversion {
open fun isPlatformSamType(type: KotlinType): Boolean = false
open fun getSamTypeForValueParameter(
valueParameter: ValueParameterDescriptor,
languageVersionSettings: LanguageVersionSettings
): KotlinType? = SamTypeFactory.INSTANCE.createByValueParameter(valueParameter, languageVersionSettings)?.type
companion object Instance : SamConversion()
}