Refactoring. Removed several usages of asSimpleType
This commit is contained in:
@@ -50,6 +50,7 @@ public class CommonSupertypes {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static KotlinType commonSupertype(@NotNull Collection<KotlinType> types) {
|
public static KotlinType commonSupertype(@NotNull Collection<KotlinType> types) {
|
||||||
|
if (types.size() == 1) return types.iterator().next();
|
||||||
// Recursion should not be significantly deeper than the deepest type in question
|
// Recursion should not be significantly deeper than the deepest type in question
|
||||||
// It can be slightly deeper, though: e.g. when initial types are simple, but their supertypes are complex
|
// It can be slightly deeper, though: e.g. when initial types are simple, but their supertypes are complex
|
||||||
return findCommonSupertype(types, 0, maxDepth(types) + 3);
|
return findCommonSupertype(types, 0, maxDepth(types) + 3);
|
||||||
@@ -86,18 +87,20 @@ public class CommonSupertypes {
|
|||||||
List<SimpleType> upper = new ArrayList<SimpleType>(types.size());
|
List<SimpleType> upper = new ArrayList<SimpleType>(types.size());
|
||||||
List<SimpleType> lower = new ArrayList<SimpleType>(types.size());
|
List<SimpleType> lower = new ArrayList<SimpleType>(types.size());
|
||||||
for (KotlinType type : types) {
|
for (KotlinType type : types) {
|
||||||
if (FlexibleTypesKt.isFlexible(type)) {
|
UnwrappedType unwrappedType = type.unwrap();
|
||||||
|
if (unwrappedType instanceof FlexibleType) {
|
||||||
if (DynamicTypesKt.isDynamic(type)) {
|
if (DynamicTypesKt.isDynamic(type)) {
|
||||||
return type;
|
return type;
|
||||||
}
|
}
|
||||||
hasFlexible = true;
|
hasFlexible = true;
|
||||||
FlexibleType flexibleType = FlexibleTypesKt.asFlexibleType(type);
|
FlexibleType flexibleType = (FlexibleType) type;
|
||||||
upper.add(flexibleType.getUpperBound());
|
upper.add(flexibleType.getUpperBound());
|
||||||
lower.add(flexibleType.getLowerBound());
|
lower.add(flexibleType.getLowerBound());
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
upper.add(KotlinTypeKt.asSimpleType(type));
|
SimpleType simpleType = (SimpleType) unwrappedType;
|
||||||
lower.add(KotlinTypeKt.asSimpleType(type));
|
upper.add(simpleType);
|
||||||
|
lower.add(simpleType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -113,10 +116,6 @@ public class CommonSupertypes {
|
|||||||
assert !types.isEmpty();
|
assert !types.isEmpty();
|
||||||
Collection<SimpleType> typeSet = new HashSet<SimpleType>(types);
|
Collection<SimpleType> typeSet = new HashSet<SimpleType>(types);
|
||||||
|
|
||||||
// todo: dead code?
|
|
||||||
KotlinType bestFit = FlexibleTypesKt.singleBestRepresentative(typeSet);
|
|
||||||
if (bestFit != null) return KotlinTypeKt.asSimpleType(bestFit);
|
|
||||||
|
|
||||||
// If any of the types is nullable, the result must be nullable
|
// If any of the types is nullable, the result must be nullable
|
||||||
// This also removed Nothing and Nothing? because they are subtypes of everything else
|
// This also removed Nothing and Nothing? because they are subtypes of everything else
|
||||||
boolean nullable = false;
|
boolean nullable = false;
|
||||||
@@ -348,7 +347,7 @@ public class CommonSupertypes {
|
|||||||
if (visited.contains(supertype.getConstructor())) {
|
if (visited.contains(supertype.getConstructor())) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
result.add(KotlinTypeKt.asSimpleType(substitutor.safeSubstitute(supertype, Variance.INVARIANT)));
|
result.add(FlexibleTypesKt.lowerIfFlexible(substitutor.safeSubstitute(supertype, Variance.INVARIANT)));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|||||||
+19
-18
@@ -33,7 +33,6 @@ import org.jetbrains.kotlin.platform.JavaToKotlinClassMap
|
|||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
import org.jetbrains.kotlin.types.typeUtil.createProjection
|
import org.jetbrains.kotlin.types.typeUtil.createProjection
|
||||||
import org.jetbrains.kotlin.types.typeUtil.isTypeParameter
|
import org.jetbrains.kotlin.types.typeUtil.isTypeParameter
|
||||||
import org.jetbrains.kotlin.types.typeUtil.makeNotNullable
|
|
||||||
import org.jetbrains.kotlin.utils.addToStdlib.check
|
import org.jetbrains.kotlin.utils.addToStdlib.check
|
||||||
import org.jetbrains.kotlin.utils.toReadOnlyList
|
import org.jetbrains.kotlin.utils.toReadOnlyList
|
||||||
|
|
||||||
@@ -41,7 +40,7 @@ import org.jetbrains.kotlin.utils.toReadOnlyList
|
|||||||
// Example: for `A<B, C<D, E>>`, indices go as follows: `0 - A<...>, 1 - B, 2 - C<D, E>, 3 - D, 4 - E`,
|
// Example: for `A<B, C<D, E>>`, indices go as follows: `0 - A<...>, 1 - B, 2 - C<D, E>, 3 - D, 4 - E`,
|
||||||
// which corresponds to the left-to-right breadth-first walk of the tree representation of the type.
|
// which corresponds to the left-to-right breadth-first walk of the tree representation of the type.
|
||||||
// For flexible types, both bounds are indexed in the same way: `(A<B>..C<D>)` gives `0 - (A<B>..C<D>), 1 - B and D`.
|
// For flexible types, both bounds are indexed in the same way: `(A<B>..C<D>)` gives `0 - (A<B>..C<D>), 1 - B and D`.
|
||||||
fun KotlinType.enhance(qualifiers: (Int) -> JavaTypeQualifiers) = this.enhancePossiblyFlexible(qualifiers, 0).typeIfChanged
|
fun KotlinType.enhance(qualifiers: (Int) -> JavaTypeQualifiers) = unwrap().enhancePossiblyFlexible(qualifiers, 0).typeIfChanged
|
||||||
|
|
||||||
fun KotlinType.hasEnhancedNullability()
|
fun KotlinType.hasEnhancedNullability()
|
||||||
= annotations.findAnnotation(JvmAnnotationNames.ENHANCED_NULLABILITY_ANNOTATION) != null
|
= annotations.findAnnotation(JvmAnnotationNames.ENHANCED_NULLABILITY_ANNOTATION) != null
|
||||||
@@ -52,14 +51,16 @@ private enum class TypeComponentPosition {
|
|||||||
INFLEXIBLE
|
INFLEXIBLE
|
||||||
}
|
}
|
||||||
|
|
||||||
private data class Result(val type: KotlinType, val subtreeSize: Int, val wereChanges: Boolean) {
|
private open class Result(open val type: KotlinType, val subtreeSize: Int, val wereChanges: Boolean) {
|
||||||
val typeIfChanged: KotlinType? get() = type.check { wereChanges }
|
val typeIfChanged: KotlinType? get() = type.check { wereChanges }
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun KotlinType.enhancePossiblyFlexible(qualifiers: (Int) -> JavaTypeQualifiers, index: Int): Result {
|
private class SimpleResult(override val type: SimpleType, subtreeSize: Int, wereChanges: Boolean): Result(type, subtreeSize, wereChanges)
|
||||||
if (this.isError || unwrap() is RawTypeImpl) return Result(this, 1, false) // todo: Raw
|
|
||||||
return if (this.isFlexible()) {
|
private fun UnwrappedType.enhancePossiblyFlexible(qualifiers: (Int) -> JavaTypeQualifiers, index: Int): Result {
|
||||||
with(this.asFlexibleType()) {
|
if (isError || this is RawTypeImpl) return Result(this, 1, false) // todo: Raw
|
||||||
|
return when(this) {
|
||||||
|
is FlexibleType -> {
|
||||||
val lowerResult = lowerBound.enhanceInflexible(qualifiers, index, TypeComponentPosition.FLEXIBLE_LOWER)
|
val lowerResult = lowerBound.enhanceInflexible(qualifiers, index, TypeComponentPosition.FLEXIBLE_LOWER)
|
||||||
val upperResult = upperBound.enhanceInflexible(qualifiers, index, TypeComponentPosition.FLEXIBLE_UPPER)
|
val upperResult = upperBound.enhanceInflexible(qualifiers, index, TypeComponentPosition.FLEXIBLE_UPPER)
|
||||||
assert(lowerResult.subtreeSize == upperResult.subtreeSize) {
|
assert(lowerResult.subtreeSize == upperResult.subtreeSize) {
|
||||||
@@ -71,23 +72,23 @@ private fun KotlinType.enhancePossiblyFlexible(qualifiers: (Int) -> JavaTypeQual
|
|||||||
val wereChanges = lowerResult.wereChanges || upperResult.wereChanges
|
val wereChanges = lowerResult.wereChanges || upperResult.wereChanges
|
||||||
Result(
|
Result(
|
||||||
if (wereChanges)
|
if (wereChanges)
|
||||||
KotlinTypeFactory.flexibleType(lowerResult.type.asSimpleType(), upperResult.type.asSimpleType())
|
KotlinTypeFactory.flexibleType(lowerResult.type, upperResult.type)
|
||||||
else
|
else
|
||||||
this@enhancePossiblyFlexible,
|
this@enhancePossiblyFlexible,
|
||||||
lowerResult.subtreeSize,
|
lowerResult.subtreeSize,
|
||||||
wereChanges
|
wereChanges
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
is SimpleType -> enhanceInflexible(qualifiers, index, TypeComponentPosition.INFLEXIBLE)
|
||||||
}
|
}
|
||||||
else this.enhanceInflexible(qualifiers, index, TypeComponentPosition.INFLEXIBLE)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun KotlinType.enhanceInflexible(qualifiers: (Int) -> JavaTypeQualifiers, index: Int, position: TypeComponentPosition): Result {
|
private fun SimpleType.enhanceInflexible(qualifiers: (Int) -> JavaTypeQualifiers, index: Int, position: TypeComponentPosition): SimpleResult {
|
||||||
val shouldEnhance = position.shouldEnhance()
|
val shouldEnhance = position.shouldEnhance()
|
||||||
if (!shouldEnhance && arguments.isEmpty()) return Result(this, 1, false)
|
if (!shouldEnhance && arguments.isEmpty()) return SimpleResult(this, 1, false)
|
||||||
|
|
||||||
val originalClass = constructor.declarationDescriptor
|
val originalClass = constructor.declarationDescriptor
|
||||||
?: return Result(this, 1, false)
|
?: return SimpleResult(this, 1, false)
|
||||||
|
|
||||||
val effectiveQualifiers = qualifiers(index)
|
val effectiveQualifiers = qualifiers(index)
|
||||||
val (enhancedClassifier, enhancedMutabilityAnnotations) = originalClass.enhanceMutability(effectiveQualifiers, position)
|
val (enhancedClassifier, enhancedMutabilityAnnotations) = originalClass.enhanceMutability(effectiveQualifiers, position)
|
||||||
@@ -103,10 +104,10 @@ private fun KotlinType.enhanceInflexible(qualifiers: (Int) -> JavaTypeQualifiers
|
|||||||
TypeUtils.makeStarProjection(enhancedClassifier.typeConstructor.parameters[localArgIndex])
|
TypeUtils.makeStarProjection(enhancedClassifier.typeConstructor.parameters[localArgIndex])
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
val (enhancedType, subtreeSize, wasChangeInArgument) = arg.type.enhancePossiblyFlexible(qualifiers, globalArgIndex)
|
val enhanced = arg.type.unwrap().enhancePossiblyFlexible(qualifiers, globalArgIndex)
|
||||||
wereChanges = wereChanges || wasChangeInArgument
|
wereChanges = wereChanges || enhanced.wereChanges
|
||||||
globalArgIndex += subtreeSize
|
globalArgIndex += enhanced.subtreeSize
|
||||||
createProjection(enhancedType, arg.projectionKind, typeParameterDescriptor = typeConstructor.parameters[localArgIndex])
|
createProjection(enhanced.type, arg.projectionKind, typeParameterDescriptor = typeConstructor.parameters[localArgIndex])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -114,7 +115,7 @@ private fun KotlinType.enhanceInflexible(qualifiers: (Int) -> JavaTypeQualifiers
|
|||||||
wereChanges = wereChanges || enhancedNullabilityAnnotations != null
|
wereChanges = wereChanges || enhancedNullabilityAnnotations != null
|
||||||
|
|
||||||
val subtreeSize = globalArgIndex - index
|
val subtreeSize = globalArgIndex - index
|
||||||
if (!wereChanges) return Result(this, subtreeSize, wereChanges = false)
|
if (!wereChanges) return SimpleResult(this, subtreeSize, wereChanges = false)
|
||||||
|
|
||||||
val newAnnotations = listOf(
|
val newAnnotations = listOf(
|
||||||
annotations,
|
annotations,
|
||||||
@@ -135,7 +136,7 @@ private fun KotlinType.enhanceInflexible(qualifiers: (Int) -> JavaTypeQualifiers
|
|||||||
)
|
)
|
||||||
|
|
||||||
val result = if (effectiveQualifiers.isNotNullTypeParameter) NotNullTypeParameter(enhancedType) else enhancedType
|
val result = if (effectiveQualifiers.isNotNullTypeParameter) NotNullTypeParameter(enhancedType) else enhancedType
|
||||||
return Result(result, subtreeSize, wereChanges = true)
|
return SimpleResult(result, subtreeSize, wereChanges = true)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun List<Annotations>.compositeAnnotationsOrSingle() = when (size) {
|
private fun List<Annotations>.compositeAnnotationsOrSingle() = when (size) {
|
||||||
|
|||||||
+13
-11
@@ -22,7 +22,6 @@ import org.jetbrains.kotlin.descriptors.annotations.AnnotationsImpl
|
|||||||
import org.jetbrains.kotlin.descriptors.annotations.composeAnnotations
|
import org.jetbrains.kotlin.descriptors.annotations.composeAnnotations
|
||||||
import org.jetbrains.kotlin.descriptors.annotations.createUnsafeVarianceAnnotation
|
import org.jetbrains.kotlin.descriptors.annotations.createUnsafeVarianceAnnotation
|
||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
import org.jetbrains.kotlin.types.typeUtil.replaceAnnotations
|
|
||||||
|
|
||||||
internal class UnsafeVarianceTypeSubstitution(kotlinBuiltIns: KotlinBuiltIns) : TypeSubstitution() {
|
internal class UnsafeVarianceTypeSubstitution(kotlinBuiltIns: KotlinBuiltIns) : TypeSubstitution() {
|
||||||
private val unsafeVarianceAnnotations = AnnotationsImpl(listOf(kotlinBuiltIns.createUnsafeVarianceAnnotation()))
|
private val unsafeVarianceAnnotations = AnnotationsImpl(listOf(kotlinBuiltIns.createUnsafeVarianceAnnotation()))
|
||||||
@@ -38,19 +37,22 @@ internal class UnsafeVarianceTypeSubstitution(kotlinBuiltIns: KotlinBuiltIns) :
|
|||||||
},
|
},
|
||||||
customVariance = { null })
|
customVariance = { null })
|
||||||
|
|
||||||
return topLevelType.annotatePartsWithUnsafeVariance(unsafeVariancePaths)
|
return topLevelType.unwrap().annotatePartsWithUnsafeVariance(unsafeVariancePaths)
|
||||||
|
}
|
||||||
|
private fun UnwrappedType.annotatePartsWithUnsafeVariance(unsafeVariancePaths: Collection<List<Int>>): UnwrappedType {
|
||||||
|
if (unsafeVariancePaths.isEmpty()) return this
|
||||||
|
return when (this) {
|
||||||
|
is FlexibleType ->
|
||||||
|
KotlinTypeFactory.flexibleType(
|
||||||
|
lowerBound.annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, 0)),
|
||||||
|
upperBound.annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, 1)))
|
||||||
|
is SimpleType -> annotatePartsWithUnsafeVariance(unsafeVariancePaths)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun KotlinType.annotatePartsWithUnsafeVariance(unsafeVariancePaths: Collection<List<Int>>): KotlinType {
|
private fun SimpleType.annotatePartsWithUnsafeVariance(unsafeVariancePaths: Collection<List<Int>>): SimpleType {
|
||||||
if (unsafeVariancePaths.isEmpty()) return this
|
if (unsafeVariancePaths.isEmpty()) return this
|
||||||
|
|
||||||
if (isFlexible()) {
|
|
||||||
return KotlinTypeFactory.flexibleType(
|
|
||||||
lowerIfFlexible().annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, 0)).asSimpleType(),
|
|
||||||
upperIfFlexible().annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, 1)).asSimpleType()
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
// if root is unsafe
|
// if root is unsafe
|
||||||
if (emptyList<Int>() in unsafeVariancePaths) {
|
if (emptyList<Int>() in unsafeVariancePaths) {
|
||||||
return replaceAnnotations(composeAnnotations(annotations, unsafeVarianceAnnotations))
|
return replaceAnnotations(composeAnnotations(annotations, unsafeVarianceAnnotations))
|
||||||
@@ -61,7 +63,7 @@ internal class UnsafeVarianceTypeSubstitution(kotlinBuiltIns: KotlinBuiltIns) :
|
|||||||
if (argument.isStarProjection) return@map argument
|
if (argument.isStarProjection) return@map argument
|
||||||
TypeProjectionImpl(
|
TypeProjectionImpl(
|
||||||
argument.projectionKind,
|
argument.projectionKind,
|
||||||
argument.type.annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, index)))
|
argument.type.unwrap().annotatePartsWithUnsafeVariance(subPathsWithIndex(unsafeVariancePaths, index)))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -36,7 +36,6 @@ import org.jetbrains.kotlin.serialization.deserialization.NotFoundClasses
|
|||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
import org.jetbrains.kotlin.types.ErrorUtils.UninferredParameterTypeConstructor
|
import org.jetbrains.kotlin.types.ErrorUtils.UninferredParameterTypeConstructor
|
||||||
import org.jetbrains.kotlin.types.TypeUtils.CANT_INFER_FUNCTION_PARAM_TYPE
|
import org.jetbrains.kotlin.types.TypeUtils.CANT_INFER_FUNCTION_PARAM_TYPE
|
||||||
import org.jetbrains.kotlin.types.typeUtil.builtIns
|
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
internal class DescriptorRendererImpl(
|
internal class DescriptorRendererImpl(
|
||||||
@@ -141,10 +140,10 @@ internal class DescriptorRendererImpl(
|
|||||||
return type.toString()
|
return type.toString()
|
||||||
}
|
}
|
||||||
val unwrappedType = type.unwrap()
|
val unwrappedType = type.unwrap()
|
||||||
if (unwrappedType is FlexibleType) {
|
return when (unwrappedType) {
|
||||||
return unwrappedType.render(this, this)
|
is FlexibleType -> unwrappedType.render(this, this)
|
||||||
|
is SimpleType -> renderSimpleType(unwrappedType)
|
||||||
}
|
}
|
||||||
return renderSimpleType(unwrappedType.asSimpleType())
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun renderSimpleType(type: SimpleType): String {
|
private fun renderSimpleType(type: SimpleType): String {
|
||||||
|
|||||||
@@ -64,6 +64,7 @@ abstract class WrappedType() : KotlinType(), LazyType {
|
|||||||
override val arguments: List<TypeProjection> get() = delegate.arguments
|
override val arguments: List<TypeProjection> get() = delegate.arguments
|
||||||
override val isMarkedNullable: Boolean get() = delegate.isMarkedNullable
|
override val isMarkedNullable: Boolean get() = delegate.isMarkedNullable
|
||||||
override val memberScope: MemberScope get() = delegate.memberScope
|
override val memberScope: MemberScope get() = delegate.memberScope
|
||||||
|
override val isError: Boolean get() = delegate.isError
|
||||||
|
|
||||||
override final fun unwrap(): UnwrappedType {
|
override final fun unwrap(): UnwrappedType {
|
||||||
var result = delegate
|
var result = delegate
|
||||||
@@ -81,9 +82,6 @@ abstract class WrappedType() : KotlinType(), LazyType {
|
|||||||
return "<Not computed yet>"
|
return "<Not computed yet>"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// todo: remove this later
|
|
||||||
override val isError: Boolean get() = delegate.isError
|
|
||||||
}
|
}
|
||||||
|
|
||||||
sealed class UnwrappedType: KotlinType() {
|
sealed class UnwrappedType: KotlinType() {
|
||||||
|
|||||||
@@ -120,6 +120,21 @@ fun KotlinType.replace(
|
|||||||
): KotlinType {
|
): KotlinType {
|
||||||
if (newArguments.isEmpty() && newAnnotations === annotations) return this
|
if (newArguments.isEmpty() && newAnnotations === annotations) return this
|
||||||
|
|
||||||
|
val unwrapped = unwrap()
|
||||||
|
return when(unwrapped) {
|
||||||
|
is FlexibleType -> KotlinTypeFactory.flexibleType(unwrapped.lowerBound.replace(newArguments, newAnnotations),
|
||||||
|
unwrapped.upperBound.replace(newArguments, newAnnotations))
|
||||||
|
is SimpleType -> unwrapped.replace(newArguments, newAnnotations)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmOverloads
|
||||||
|
fun SimpleType.replace(
|
||||||
|
newArguments: List<TypeProjection> = arguments,
|
||||||
|
newAnnotations: Annotations = annotations
|
||||||
|
): SimpleType {
|
||||||
|
if (newArguments.isEmpty() && newAnnotations === annotations) return this
|
||||||
|
|
||||||
if (newArguments.isEmpty()) {
|
if (newArguments.isEmpty()) {
|
||||||
return KotlinTypeFactory.simpleType(
|
return KotlinTypeFactory.simpleType(
|
||||||
newAnnotations,
|
newAnnotations,
|
||||||
|
|||||||
@@ -171,5 +171,5 @@ private fun SimpleType.replaceArgumentsWithStarProjections(): SimpleType {
|
|||||||
|
|
||||||
val newArguments = constructor.parameters.map(::StarProjectionImpl)
|
val newArguments = constructor.parameters.map(::StarProjectionImpl)
|
||||||
|
|
||||||
return replace(newArguments).asSimpleType()
|
return replace(newArguments)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -60,14 +60,23 @@ fun Collection<TypeProjection>.singleBestRepresentative(): TypeProjection? {
|
|||||||
val projectionKinds = this.map { it.projectionKind }.toSet()
|
val projectionKinds = this.map { it.projectionKind }.toSet()
|
||||||
if (projectionKinds.size != 1) return null
|
if (projectionKinds.size != 1) return null
|
||||||
|
|
||||||
val bestType = this.map { it.type }.singleBestRepresentative()
|
val bestType = this.map { it.type }.singleBestRepresentative() ?: return null
|
||||||
if (bestType == null) return null
|
|
||||||
|
|
||||||
return TypeProjectionImpl(projectionKinds.single(), bestType)
|
return TypeProjectionImpl(projectionKinds.single(), bestType)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun KotlinType.lowerIfFlexible(): SimpleType = (if (this.isFlexible()) this.asFlexibleType().lowerBound else this).asSimpleType()
|
fun KotlinType.lowerIfFlexible(): SimpleType = with(unwrap()) {
|
||||||
fun KotlinType.upperIfFlexible(): SimpleType = (if (this.isFlexible()) this.asFlexibleType().upperBound else this).asSimpleType()
|
when (this) {
|
||||||
|
is FlexibleType -> lowerBound
|
||||||
|
is SimpleType -> this
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fun KotlinType.upperIfFlexible(): SimpleType = with(unwrap()) {
|
||||||
|
when (this) {
|
||||||
|
is FlexibleType -> upperBound
|
||||||
|
is SimpleType -> this
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
class FlexibleTypeImpl(lowerBound: SimpleType, upperBound: SimpleType) : FlexibleType(lowerBound, upperBound), CustomTypeVariable {
|
class FlexibleTypeImpl(lowerBound: SimpleType, upperBound: SimpleType) : FlexibleType(lowerBound, upperBound), CustomTypeVariable {
|
||||||
companion object {
|
companion object {
|
||||||
|
|||||||
+4
-9
@@ -20,15 +20,16 @@ import org.jetbrains.kotlin.descriptors.annotations.AnnotationWithTarget
|
|||||||
import org.jetbrains.kotlin.descriptors.annotations.Annotations
|
import org.jetbrains.kotlin.descriptors.annotations.Annotations
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedAnnotationsWithPossibleTargets
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedAnnotationsWithPossibleTargets
|
||||||
import org.jetbrains.kotlin.storage.getValue
|
import org.jetbrains.kotlin.types.AbstractLazyType
|
||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.SimpleType
|
||||||
|
import org.jetbrains.kotlin.types.withAbbreviatedType
|
||||||
import org.jetbrains.kotlin.utils.toReadOnlyList
|
import org.jetbrains.kotlin.utils.toReadOnlyList
|
||||||
|
|
||||||
class DeserializedType private constructor(
|
class DeserializedType private constructor(
|
||||||
private val c: DeserializationContext,
|
private val c: DeserializationContext,
|
||||||
private val typeProto: ProtoBuf.Type,
|
private val typeProto: ProtoBuf.Type,
|
||||||
private val additionalAnnotations: Annotations = Annotations.EMPTY
|
private val additionalAnnotations: Annotations = Annotations.EMPTY
|
||||||
) : AbstractLazyType(c.storageManager), LazyType {
|
) : AbstractLazyType(c.storageManager) {
|
||||||
override fun computeTypeConstructor() = c.typeDeserializer.typeConstructor(typeProto)
|
override fun computeTypeConstructor() = c.typeDeserializer.typeConstructor(typeProto)
|
||||||
|
|
||||||
override fun computeArguments() =
|
override fun computeArguments() =
|
||||||
@@ -48,12 +49,6 @@ class DeserializedType private constructor(
|
|||||||
|
|
||||||
override val isMarkedNullable: Boolean get() = typeProto.nullable
|
override val isMarkedNullable: Boolean get() = typeProto.nullable
|
||||||
|
|
||||||
override val isError: Boolean
|
|
||||||
get() {
|
|
||||||
val descriptor = constructor.declarationDescriptor
|
|
||||||
return descriptor != null && ErrorUtils.isError(descriptor)
|
|
||||||
}
|
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
fun create(
|
fun create(
|
||||||
c: DeserializationContext,
|
c: DeserializationContext,
|
||||||
|
|||||||
@@ -104,7 +104,7 @@ class SpecifyTypeExplicitlyIntention : SelfTargetingIntention<KtCallableDeclarat
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
KotlinTypeFactory.simpleType(it.asSimpleType(), arguments = newArguments)
|
it.replace(newArguments)
|
||||||
}
|
}
|
||||||
.ifEmpty { return null }
|
.ifEmpty { return null }
|
||||||
return object : ChooseValueExpression<KotlinType>(types, types.first()) {
|
return object : ChooseValueExpression<KotlinType>(types, types.first()) {
|
||||||
|
|||||||
+9
-8
@@ -25,6 +25,7 @@ import org.jetbrains.kotlin.serialization.deserialization.findClassAcrossModuleD
|
|||||||
import org.jetbrains.kotlin.storage.StorageManager
|
import org.jetbrains.kotlin.storage.StorageManager
|
||||||
import org.jetbrains.kotlin.types.ErrorUtils
|
import org.jetbrains.kotlin.types.ErrorUtils
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
import org.jetbrains.kotlin.types.SimpleType
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
class LazySyntheticElementResolveContext(private val module: ModuleDescriptor, storageManager: StorageManager) {
|
class LazySyntheticElementResolveContext(private val module: ModuleDescriptor, storageManager: StorageManager) {
|
||||||
@@ -53,11 +54,11 @@ class LazySyntheticElementResolveContext(private val module: ModuleDescriptor, s
|
|||||||
}
|
}
|
||||||
|
|
||||||
internal class SyntheticElementResolveContext(
|
internal class SyntheticElementResolveContext(
|
||||||
val viewType: KotlinType,
|
val viewType: SimpleType,
|
||||||
val activityType: KotlinType,
|
val activityType: SimpleType,
|
||||||
val fragmentType: KotlinType?,
|
val fragmentType: SimpleType?,
|
||||||
val supportActivityType: KotlinType?,
|
val supportActivityType: SimpleType?,
|
||||||
val supportFragmentType: KotlinType?) {
|
val supportFragmentType: SimpleType?) {
|
||||||
companion object {
|
companion object {
|
||||||
private fun errorType() = ErrorUtils.createErrorType("")
|
private fun errorType() = ErrorUtils.createErrorType("")
|
||||||
val ERROR_CONTEXT = SyntheticElementResolveContext(errorType(), errorType(), null, null, null)
|
val ERROR_CONTEXT = SyntheticElementResolveContext(errorType(), errorType(), null, null, null)
|
||||||
@@ -71,12 +72,12 @@ internal class SyntheticElementResolveContext(
|
|||||||
receivers
|
receivers
|
||||||
}
|
}
|
||||||
|
|
||||||
val fragmentTypes: List<Pair<KotlinType, KotlinType>> by lazy {
|
val fragmentTypes: List<Pair<SimpleType, SimpleType>> by lazy {
|
||||||
if (fragmentType == null) {
|
if (fragmentType == null) {
|
||||||
emptyList<Pair<KotlinType, KotlinType>>()
|
emptyList<Pair<SimpleType, SimpleType>>()
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
val types = ArrayList<Pair<KotlinType, KotlinType>>(4)
|
val types = ArrayList<Pair<SimpleType, SimpleType>>(4)
|
||||||
types += Pair(activityType, fragmentType)
|
types += Pair(activityType, fragmentType)
|
||||||
types += Pair(fragmentType, fragmentType)
|
types += Pair(fragmentType, fragmentType)
|
||||||
if (supportActivityType != null && supportFragmentType != null) {
|
if (supportActivityType != null && supportFragmentType != null) {
|
||||||
|
|||||||
+5
-6
@@ -25,16 +25,14 @@ import org.jetbrains.kotlin.descriptors.annotations.Annotations
|
|||||||
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
|
||||||
import org.jetbrains.kotlin.descriptors.impl.PropertyGetterDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.PropertyGetterDescriptorImpl
|
||||||
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl
|
||||||
import org.jetbrains.kotlin.load.java.lazy.types.LazyJavaTypeResolver
|
|
||||||
import org.jetbrains.kotlin.name.Name
|
import org.jetbrains.kotlin.name.Name
|
||||||
import org.jetbrains.kotlin.resolve.descriptorUtil.builtIns
|
import org.jetbrains.kotlin.resolve.descriptorUtil.builtIns
|
||||||
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameUnsafe
|
import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameUnsafe
|
||||||
import org.jetbrains.kotlin.resolve.source.PsiSourceElement
|
import org.jetbrains.kotlin.resolve.source.PsiSourceElement
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
import org.jetbrains.kotlin.types.KotlinTypeFactory
|
import org.jetbrains.kotlin.types.KotlinTypeFactory
|
||||||
|
import org.jetbrains.kotlin.types.SimpleType
|
||||||
import org.jetbrains.kotlin.types.StarProjectionImpl
|
import org.jetbrains.kotlin.types.StarProjectionImpl
|
||||||
import org.jetbrains.kotlin.types.asSimpleType
|
|
||||||
import org.jetbrains.kotlin.types.typeUtil.makeNullable
|
|
||||||
|
|
||||||
private class XmlSourceElement(override val psi: PsiElement) : PsiSourceElement
|
private class XmlSourceElement(override val psi: PsiElement) : PsiSourceElement
|
||||||
|
|
||||||
@@ -76,7 +74,7 @@ internal fun genPropertyForWidget(
|
|||||||
internal fun genPropertyForFragment(
|
internal fun genPropertyForFragment(
|
||||||
packageFragmentDescriptor: AndroidSyntheticPackageFragmentDescriptor,
|
packageFragmentDescriptor: AndroidSyntheticPackageFragmentDescriptor,
|
||||||
receiverType: KotlinType,
|
receiverType: KotlinType,
|
||||||
type: KotlinType,
|
type: SimpleType,
|
||||||
fragment: AndroidResource.Fragment
|
fragment: AndroidResource.Fragment
|
||||||
): PropertyDescriptor {
|
): PropertyDescriptor {
|
||||||
val sourceElement = fragment.sourceElement?.let { XmlSourceElement(it) } ?: SourceElement.NO_SOURCE
|
val sourceElement = fragment.sourceElement?.let { XmlSourceElement(it) } ?: SourceElement.NO_SOURCE
|
||||||
@@ -86,7 +84,7 @@ internal fun genPropertyForFragment(
|
|||||||
private fun genProperty(
|
private fun genProperty(
|
||||||
id: ResourceIdentifier,
|
id: ResourceIdentifier,
|
||||||
receiverType: KotlinType,
|
receiverType: KotlinType,
|
||||||
type: KotlinType,
|
type: SimpleType,
|
||||||
containingDeclaration: AndroidSyntheticPackageFragmentDescriptor,
|
containingDeclaration: AndroidSyntheticPackageFragmentDescriptor,
|
||||||
sourceElement: SourceElement,
|
sourceElement: SourceElement,
|
||||||
errorType: String?
|
errorType: String?
|
||||||
@@ -110,7 +108,8 @@ private fun genProperty(
|
|||||||
override val resourceId = id
|
override val resourceId = id
|
||||||
}
|
}
|
||||||
|
|
||||||
val flexibleType = KotlinTypeFactory.flexibleType(type.asSimpleType(), type.makeNullable().asSimpleType())
|
// todo support (Mutable)List
|
||||||
|
val flexibleType = KotlinTypeFactory.flexibleType(type, type.makeNullableAsSpecified(true))
|
||||||
property.setType(
|
property.setType(
|
||||||
flexibleType,
|
flexibleType,
|
||||||
emptyList<TypeParameterDescriptor>(),
|
emptyList<TypeParameterDescriptor>(),
|
||||||
|
|||||||
Reference in New Issue
Block a user