Inner type aliases.

Type alias is considered "inner" if it captures outer class type parameters (implicitly or explicitly).
This commit is contained in:
Dmitry Petrov
2016-11-09 13:14:10 +03:00
parent 63fed20249
commit 718e8ebf9e
16 changed files with 244 additions and 27 deletions
@@ -710,18 +710,25 @@ public class DescriptorResolver {
else {
typeAliasDescriptor.initialize(
typeParameterDescriptors,
storageManager.createLazyValue(new Function0<SimpleType>() {
@Override
public SimpleType invoke() {
return typeResolver.resolveAbbreviatedType(scopeWithTypeParameters, typeReference, trace);
}
}),
storageManager.createLazyValue(new Function0<SimpleType>() {
@Override
public SimpleType invoke() {
return typeResolver.resolveExpandedTypeForTypeAlias(typeAliasDescriptor);
}
}));
storageManager.createRecursionTolerantLazyValue(
new Function0<SimpleType>() {
@Override
public SimpleType invoke() {
return typeResolver.resolveAbbreviatedType(scopeWithTypeParameters, typeReference, trace);
}
},
ErrorUtils.createErrorType("Recursive type alias expansion for " + typeAliasDescriptor.getName().asString())
),
storageManager.createRecursionTolerantLazyValue(
new Function0<SimpleType>() {
@Override
public SimpleType invoke() {
return typeResolver.resolveExpandedTypeForTypeAlias(typeAliasDescriptor);
}
},
ErrorUtils.createErrorType("Recursive type alias expansion for " + typeAliasDescriptor.getName().asString())
)
);
}
trace.record(TYPE_ALIAS, typeAlias, typeAliasDescriptor);
@@ -48,7 +48,7 @@ class TypeAliasExpansion private constructor(
typeAliasDescriptor: TypeAliasDescriptor,
arguments: List<TypeProjection>
): TypeAliasExpansion {
val typeParameters = typeAliasDescriptor.typeConstructor.parameters.map { it.original as TypeParameterDescriptor }
val typeParameters = typeAliasDescriptor.typeConstructor.parameters.map { it.original }
val mappedArguments = typeParameters.zip(arguments).toMap()
return TypeAliasExpansion(parent, typeAliasDescriptor, arguments, mappedArguments)
}
@@ -22,6 +22,7 @@ import org.jetbrains.kotlin.descriptors.impl.AbstractTypeAliasDescriptor
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.BindingTrace
import org.jetbrains.kotlin.storage.NotNullLazyValue
import org.jetbrains.kotlin.storage.NullableLazyValue
import org.jetbrains.kotlin.storage.StorageManager
import org.jetbrains.kotlin.types.SimpleType
import org.jetbrains.kotlin.types.TypeSubstitutor
@@ -42,9 +43,11 @@ class LazyTypeAliasDescriptor(
private lateinit var underlyingTypeImpl: NotNullLazyValue<SimpleType>
private lateinit var expandedTypeImpl: NotNullLazyValue<SimpleType>
private lateinit var defaultTypeImpl: NotNullLazyValue<SimpleType>
private lateinit var classDescriptorImpl: NullableLazyValue<ClassDescriptor>
override val underlyingType: SimpleType get() = underlyingTypeImpl()
override val expandedType: SimpleType get() = expandedTypeImpl()
override val classDescriptor: ClassDescriptor? get() = classDescriptorImpl()
override fun getDefaultType(): SimpleType = defaultTypeImpl()
fun initialize(
@@ -56,10 +59,21 @@ class LazyTypeAliasDescriptor(
this.underlyingTypeImpl = lazyUnderlyingType
this.expandedTypeImpl = lazyExpandedType
this.defaultTypeImpl = storageManager.createLazyValue { computeDefaultType() }
this.classDescriptorImpl = storageManager.createRecursionTolerantNullableLazyValue({ computeClassDescriptor() }, null)
}
private fun computeClassDescriptor(): ClassDescriptor? {
if (underlyingType.isError) return null
val underlyingTypeDescriptor = underlyingType.constructor.declarationDescriptor
return when (underlyingTypeDescriptor) {
is ClassDescriptor -> underlyingTypeDescriptor
is TypeAliasDescriptor -> underlyingTypeDescriptor.classDescriptor
else -> null
}
}
private val lazyTypeConstructorParameters =
storageManager.createLazyValue { this.computeConstructorTypeParameters() }
storageManager.createRecursionTolerantLazyValue({ this.computeConstructorTypeParameters() }, emptyList())
fun initialize(
declaredTypeParameters: List<TypeParameterDescriptor>,