Write classifier and type arguments for typealiases Bug: 148581822 Change-Id: I4886c7b0004230f202378a827f47112a8330ccf0
diff --git a/src/main/java/com/android/tools/r8/kotlin/KotlinInfo.java b/src/main/java/com/android/tools/r8/kotlin/KotlinInfo.java index 3727146..967cf05 100644 --- a/src/main/java/com/android/tools/r8/kotlin/KotlinInfo.java +++ b/src/main/java/com/android/tools/r8/kotlin/KotlinInfo.java
@@ -22,11 +22,13 @@ import java.util.Map; import java.util.function.BiFunction; import java.util.function.Predicate; +import java.util.stream.Collectors; import kotlinx.metadata.KmDeclarationContainer; import kotlinx.metadata.KmFunction; import kotlinx.metadata.KmProperty; import kotlinx.metadata.KmType; import kotlinx.metadata.KmTypeAlias; +import kotlinx.metadata.KmTypeParameter; import kotlinx.metadata.jvm.KotlinClassHeader; import kotlinx.metadata.jvm.KotlinClassMetadata; @@ -276,17 +278,48 @@ private String kmTypeAliasToString(String indent, KmTypeAlias alias) { assert alias != null; StringBuilder sb = new StringBuilder(indent); - sb.append("KmAlias {"); + sb.append("KmTypeAlias {"); sb.append(StringUtils.LINE_SEPARATOR); String newIndent = indent + INDENT; appendKeyValue(newIndent, "name", alias.getName(), sb); - appendKeyValue(newIndent, "underlyingType", kmTypeToString(alias.underlyingType), sb); - appendKeyValue(newIndent, "expandedType", kmTypeToString(alias.expandedType), sb); + if (!alias.getTypeParameters().isEmpty()) { + appendKeyValue( + newIndent, + "typeParameters", + alias.getTypeParameters().stream() + .map(KmTypeParameter::getName) + .collect(Collectors.joining(",")), + sb); + } + appendType(newIndent, "underlyingType", alias.underlyingType, sb); + appendType(newIndent, "expandedType", alias.expandedType, sb); + // TODO(b/151783973): Extend with annotations. sb.append(indent); sb.append("}"); return sb.toString(); } + void appendType(String indent, String key, KmType kmType, StringBuilder sb) { + sb.append(indent); + sb.append(key); + sb.append(" {"); + sb.append(StringUtils.LINE_SEPARATOR); + String newIndent = indent + INDENT; + appendKeyValue(newIndent, "classifier", kmType.classifier.toString(), sb); + if (!kmType.getArguments().isEmpty()) { + appendKeyValue( + newIndent, + "arguments", + kmType.getArguments().stream() + .map(arg -> arg.getType().classifier.toString()) + .collect(Collectors.joining(",")), + sb); + } + sb.append(indent); + sb.append("}"); + sb.append(StringUtils.LINE_SEPARATOR); + } + void appendKeyValue(String indent, String key, String value, StringBuilder sb) { sb.append(indent); sb.append(key);
diff --git a/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib.kt b/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib.kt index 5f4de47..15771dd 100644 --- a/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib.kt +++ b/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib.kt
@@ -3,12 +3,15 @@ // BSD-style license that can be found in the LICENSE file. package com.android.tools.r8.kotlin.metadata.typealias_lib -// TypeAlias { -// name: "Jude" +// KmTypeAlias { +// name: Jude // underlyingType { -// classifier: "kotlin/Long" +// classifier: Class(name=kotlin/Long) // } -// } +// expandedType { +// classifier: Class(name=kotlin/Long) +// } +// }, typealias Jude = Long interface Itf { @@ -16,38 +19,42 @@ fun hey() : Jude } -// TypeAlias { -// name: "API" +// KmTypeAlias { +// name: API // underlyingType { -// classifier: ".../Itf" -// } -// } -typealias API = Itf - -// TypeAlias { -// typeParameters { KmTypeParameter { name = "T" ... } } -// name: "myAliasedList" -// underlyingType { -// classifier: "kotlin/Array" -// } -// expandedType == underlyingType -// } -typealias myAliasedArray<T> = Array<T> - -// TypeAlias { -// underlyingType { -// classifier: ".../myAliasedArray" -// arguments { -// KmTypeProjection { ... type = ".../API" } -// } +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Itf) // } // expandedType { -// classifier: "kotlin/Array" -// arguments { -// KmTypeProjection { ... type = ".../Itf" } -// } +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Itf) // } -// } +// }, +typealias API = Itf + +// KmTypeAlias { +// name: myAliasedArray +// typeParameters: T +// underlyingType { +// classifier: Class(name=kotlin/Array) +// arguments: TypeParameter(id=0) +// } +// expandedType { +// classifier: Class(name=kotlin/Array) +// arguments: TypeParameter(id=0) +// } +// }, +typealias myAliasedArray<T> = Array<T> + +// KmTypeAlias { +// name: APIs +// underlyingType { +// classifier: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/myAliasedArray) +// arguments: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/API) +// } +// expandedType { +// classifier: Class(name=kotlin/Array) +// arguments: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Itf) +// } +// }, typealias APIs = myAliasedArray<API> open class Impl : API {
diff --git a/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib_ext.kt b/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib_ext.kt index 397da26..ba63667 100644 --- a/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib_ext.kt +++ b/src/test/java/com/android/tools/r8/kotlin/metadata/typealias_lib/lib_ext.kt
@@ -7,19 +7,28 @@ open class LibraryClass { } -// KmAlias { -// name: Unused -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass; -// }, +// KmTypeAlias { +// name: Unused +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass) +// } +// }, typealias Unused = LibraryClass // Will give a warning, but is is not an error to have an unused argument. -// KmAlias { -// name: UnusedTypeArgument -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Unused; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass; -// }, +// KmTypeAlias { +// name: UnusedTypeArgument +// typeParameters: T +// underlyingType { +// classifier: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Unused) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/LibraryClass) +// } +// }, typealias UnusedTypeArgument<T> = Unused // Expansion to simple class @@ -28,11 +37,15 @@ val y : Int = 42; } -// KmAlias { -// name: AlphaNaming -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/SimpleClass; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/SimpleClass; -// }, +// KmTypeAlias { +// name: AlphaNaming +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/SimpleClass) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/SimpleClass) +// } +// }, typealias AlphaNaming = SimpleClass class SimpleClassTester { @@ -61,11 +74,15 @@ } } -// KmAlias { -// name: ApiAlias -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Api; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Api; -// }, +// KmTypeAlias { +// name: ApiAlias +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Api) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Api) +// } +// }, typealias ApiAlias = Api class VerticalClassMergingTester { @@ -86,18 +103,32 @@ class Arr<K>(val x : K) -// KmAlias { -// name: Arr1D -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Arr; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Arr; -// }, +// KmTypeAlias { +// name: Arr1D +// typeParameters: K +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr) +// arguments: TypeParameter(id=0) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr) +// arguments: TypeParameter(id=0) +// } +// }, typealias Arr1D<K> = Arr<K> -// KmAlias { -// name: Arr2D -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Arr; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Arr; -// }, +// KmTypeAlias { +// name: Arr2D +// typeParameters: K +// underlyingType { +// classifier: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr1D) +// arguments: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr1D) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr) +// arguments: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Arr) +// } +// }, typealias Arr2D<K> = Arr1D<Arr1D<K>> class Arr2DTester { @@ -121,25 +152,44 @@ fun f() } -// KmAlias { -// name: MyI -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/I; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/I; -// }, +// KmTypeAlias { +// name: MyI +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/I) +// arguments: Class(name=kotlin/Int) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/I) +// arguments: Class(name=kotlin/Int) +// } +// }, typealias MyI = I<Int> -// KmAlias { -// name: IntSet -// underlyingType: Lkotlin/collections/Set; -// expandedType: Lkotlin/collections/Set; -// }, +// KmTypeAlias { +// name: IntSet +// underlyingType { +// classifier: Class(name=kotlin/collections/Set) +// arguments: Class(name=kotlin/Int) +// } +// expandedType { +// classifier: Class(name=kotlin/collections/Set) +// arguments: Class(name=kotlin/Int) +// } +// }, typealias IntSet = Set<Int> -// KmAlias { -// name: MyMapToSetOfInt -// underlyingType: Lkotlin/collections/Map; -// expandedType: Lkotlin/collections/Map; -// }, +// KmTypeAlias { +// name: MyMapToSetOfInt +// typeParameters: K +// underlyingType { +// classifier: Class(name=kotlin/collections/MutableMap) +// arguments: TypeParameter(id=0),TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/IntSet) +// } +// expandedType { +// classifier: Class(name=kotlin/collections/MutableMap) +// arguments: TypeParameter(id=0),Class(name=kotlin/collections/Set) +// } +// }, typealias MyMapToSetOfInt<K> = MutableMap<K, IntSet> class InterfaceTester { @@ -166,18 +216,31 @@ // Expansion to function types -// KmAlias { -// name: MyHandler -// underlyingType: Lkotlin/Function2; -// expandedType: Lkotlin/Function2; -// }, +// KmTypeAlias { +// name: MyHandler +// underlyingType { +// classifier: Class(name=kotlin/Function2) +// arguments: Class(name=kotlin/Int),Class(name=kotlin/Any),Class(name=kotlin/Unit) +// } +// expandedType { +// classifier: Class(name=kotlin/Function2) +// arguments: Class(name=kotlin/Int),Class(name=kotlin/Any),Class(name=kotlin/Unit) +// } +// }, typealias MyHandler = (Int, Any) -> Unit -// KmAlias { -// name: MyGenericPredicate -// underlyingType: Lkotlin/Function1; -// expandedType: Lkotlin/Function1; -// }, +// KmTypeAlias { +// name: MyGenericPredicate +// typeParameters: T +// underlyingType { +// classifier: Class(name=kotlin/Function1) +// arguments: TypeParameter(id=0),Class(name=kotlin/Boolean) +// } +// expandedType { +// classifier: Class(name=kotlin/Function1) +// arguments: TypeParameter(id=0),Class(name=kotlin/Boolean) +// } +// }, typealias MyGenericPredicate<T> = (T) -> Boolean class FunctionTester { @@ -212,18 +275,26 @@ } } -// KmAlias { -// name: OuterNested -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Outer$Nested; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Outer$Nested; -// }, +// KmTypeAlias { +// name: OuterNested +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested) +// } +// }, typealias OuterNested = Outer.Nested -// KmAlias { -// name: OuterNestedInner -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Outer$Nested$Inner; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/Outer$Nested$Inner; -// }, +// KmTypeAlias { +// name: OuterNestedInner +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested.Inner) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested.Inner) +// } +// }, typealias OuterNestedInner = Outer.Nested.Inner class OuterTester { @@ -251,11 +322,15 @@ } } -// KmAlias { -// name: ClassWithCompanionC -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/ClassWithCompanion$Companion; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/ClassWithCompanion$Companion; -// }, +// KmTypeAlias { +// name: ClassWithCompanionC +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/ClassWithCompanion.Companion) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/ClassWithCompanion.Companion) +// } +// }, typealias ClassWithCompanionC = ClassWithCompanion.Companion // Expansion to constructor @@ -265,11 +340,15 @@ private constructor() : this(0) } -// KmAlias { -// name: CWithConstructor -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/C; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/C; -// }, +// KmTypeAlias { +// name: CWithConstructor +// underlyingType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/C) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/C) +// } +// }, typealias CWithConstructor = C class CWithConstructorTester { @@ -288,18 +367,28 @@ // Underlying type having type alias -// KmAlias { -// name: StillCWithConstructor -// underlyingType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/CWithConstructor; -// expandedType: Lcom/android/tools/r8/kotlin/metadata/typealias_lib/C; -// }, +// KmTypeAlias { +// name: StillCWithConstructor +// underlyingType { +// classifier: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/CWithConstructor) +// } +// expandedType { +// classifier: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/C) +// } +// }, typealias StillCWithConstructor = CWithConstructor -// KmAlias { -// name: MyAdvancedMap -// underlyingType: Lkotlin/collections/Map; -// expandedType: Lkotlin/collections/Map; -// }, +// KmTypeAlias { +// name: MyAdvancedMap +// underlyingType { +// classifier: Class(name=kotlin/collections/MutableMap) +// arguments: TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/OuterNested),TypeAlias(name=com/android/tools/r8/kotlin/metadata/typealias_lib/OuterNestedInner) +// } +// expandedType { +// classifier: Class(name=kotlin/collections/MutableMap) +// arguments: Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested),Class(name=com/android/tools/r8/kotlin/metadata/typealias_lib/Outer.Nested.Inner) +// } +// }, typealias MyAdvancedMap = MutableMap<OuterNested, OuterNestedInner> class UnderlyingTypeTest {