Add "-verbose" to kotlinp tool, change type parameter name rendering
Only render the actual name of the type parameter in the verbose mode #KT-23198
This commit is contained in:
@@ -10,17 +10,17 @@ import kotlinx.metadata.jvm.KotlinClassMetadata
|
|||||||
import kotlinx.metadata.jvm.KotlinModuleMetadata
|
import kotlinx.metadata.jvm.KotlinModuleMetadata
|
||||||
import java.io.File
|
import java.io.File
|
||||||
|
|
||||||
object Kotlinp {
|
class Kotlinp(val settings: KotlinpSettings) {
|
||||||
internal fun renderClassFile(classFile: KotlinClassMetadata?): String =
|
internal fun renderClassFile(classFile: KotlinClassMetadata?): String =
|
||||||
when (classFile) {
|
when (classFile) {
|
||||||
is KotlinClassMetadata.Class -> ClassPrinter().print(classFile)
|
is KotlinClassMetadata.Class -> ClassPrinter(settings).print(classFile)
|
||||||
is KotlinClassMetadata.FileFacade -> FileFacadePrinter().print(classFile)
|
is KotlinClassMetadata.FileFacade -> FileFacadePrinter(settings).print(classFile)
|
||||||
is KotlinClassMetadata.SyntheticClass -> {
|
is KotlinClassMetadata.SyntheticClass -> {
|
||||||
if (classFile.isLambda) LambdaPrinter().print(classFile)
|
if (classFile.isLambda) LambdaPrinter(settings).print(classFile)
|
||||||
else buildString { appendln("synthetic class") }
|
else buildString { appendln("synthetic class") }
|
||||||
}
|
}
|
||||||
is KotlinClassMetadata.MultiFileClassFacade -> MultiFileClassFacadePrinter().print(classFile)
|
is KotlinClassMetadata.MultiFileClassFacade -> MultiFileClassFacadePrinter().print(classFile)
|
||||||
is KotlinClassMetadata.MultiFileClassPart -> MultiFileClassPartPrinter().print(classFile)
|
is KotlinClassMetadata.MultiFileClassPart -> MultiFileClassPartPrinter(settings).print(classFile)
|
||||||
is KotlinClassMetadata.Unknown -> buildString { appendln("unknown file (k=${classFile.header.kind})") }
|
is KotlinClassMetadata.Unknown -> buildString { appendln("unknown file (k=${classFile.header.kind})") }
|
||||||
null -> buildString { appendln("unsupported file") }
|
null -> buildString { appendln("unsupported file") }
|
||||||
}
|
}
|
||||||
@@ -41,3 +41,7 @@ object Kotlinp {
|
|||||||
internal fun readModuleFile(file: File): KotlinModuleMetadata? =
|
internal fun readModuleFile(file: File): KotlinModuleMetadata? =
|
||||||
KotlinModuleMetadata.read(file.readBytes())
|
KotlinModuleMetadata.read(file.readBytes())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
data class KotlinpSettings(
|
||||||
|
val isVerbose: Boolean
|
||||||
|
)
|
||||||
|
|||||||
@@ -11,14 +11,17 @@ import java.io.IOException
|
|||||||
object Main {
|
object Main {
|
||||||
private fun run(args: Array<String>) {
|
private fun run(args: Array<String>) {
|
||||||
val paths = arrayListOf<String>()
|
val paths = arrayListOf<String>()
|
||||||
|
var verbose = false
|
||||||
|
|
||||||
var i = 0
|
var i = 0
|
||||||
while (true) {
|
while (true) {
|
||||||
val arg = args.getOrNull(i++) ?: break
|
val arg = args.getOrNull(i++) ?: break
|
||||||
|
|
||||||
if ("-help" == arg || "-h" == arg) {
|
if (arg == "-help" || arg == "-h") {
|
||||||
printUsageAndExit()
|
printUsageAndExit()
|
||||||
} else if ("-version" == arg) {
|
} else if (arg == "-verbose") {
|
||||||
|
verbose = true
|
||||||
|
} else if (arg == "-version") {
|
||||||
printVersionAndExit()
|
printVersionAndExit()
|
||||||
} else if (arg.startsWith("-")) {
|
} else if (arg.startsWith("-")) {
|
||||||
throw KotlinpException("unsupported argument: $arg")
|
throw KotlinpException("unsupported argument: $arg")
|
||||||
@@ -27,14 +30,16 @@ object Main {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
val kotlinp = Kotlinp(KotlinpSettings(verbose))
|
||||||
|
|
||||||
for (path in paths) {
|
for (path in paths) {
|
||||||
val file = File(path)
|
val file = File(path)
|
||||||
if (!file.exists()) throw KotlinpException("file does not exist: $path")
|
if (!file.exists()) throw KotlinpException("file does not exist: $path")
|
||||||
|
|
||||||
val text = try {
|
val text = try {
|
||||||
when (file.extension) {
|
when (file.extension) {
|
||||||
"class" -> Kotlinp.renderClassFile(Kotlinp.readClassFile(file))
|
"class" -> kotlinp.renderClassFile(kotlinp.readClassFile(file))
|
||||||
"kotlin_module" -> Kotlinp.renderModuleFile(Kotlinp.readModuleFile(file))
|
"kotlin_module" -> kotlinp.renderModuleFile(kotlinp.readModuleFile(file))
|
||||||
else -> throw KotlinpException("only .class and .kotlin_module files are supported")
|
else -> throw KotlinpException("only .class and .kotlin_module files are supported")
|
||||||
}
|
}
|
||||||
} catch (e: IOException) {
|
} catch (e: IOException) {
|
||||||
@@ -65,6 +70,7 @@ object Main {
|
|||||||
|
|
||||||
Usage: kotlinp <options> <classes>
|
Usage: kotlinp <options> <classes>
|
||||||
where possible options include:
|
where possible options include:
|
||||||
|
-verbose Display information in more detail, minimizing ambiguities but worsening readability
|
||||||
-version Display Kotlin version
|
-version Display Kotlin version
|
||||||
-help (-h) Print a synopsis of options
|
-help (-h) Print a synopsis of options
|
||||||
"""
|
"""
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ private object SpecialCharacters {
|
|||||||
const val TYPE_ALIAS_MARKER = '^'
|
const val TYPE_ALIAS_MARKER = '^'
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun visitFunction(sb: StringBuilder, flags: Flags, name: String): KmFunctionVisitor =
|
private fun visitFunction(settings: KotlinpSettings, sb: StringBuilder, flags: Flags, name: String): KmFunctionVisitor =
|
||||||
object : KmFunctionVisitor() {
|
object : KmFunctionVisitor() {
|
||||||
val typeParams = mutableListOf<String>()
|
val typeParams = mutableListOf<String>()
|
||||||
val params = mutableListOf<String>()
|
val params = mutableListOf<String>()
|
||||||
@@ -27,7 +27,7 @@ private fun visitFunction(sb: StringBuilder, flags: Flags, name: String): KmFunc
|
|||||||
override fun visitTypeParameter(
|
override fun visitTypeParameter(
|
||||||
flags: Flags, name: String, id: Int, variance: KmVariance
|
flags: Flags, name: String, id: Int, variance: KmVariance
|
||||||
): KmTypeParameterVisitor? =
|
): KmTypeParameterVisitor? =
|
||||||
printTypeParameter(flags, name, id, variance) { typeParams.add(it) }
|
printTypeParameter(settings, flags, name, id, variance) { typeParams.add(it) }
|
||||||
|
|
||||||
override fun visitValueParameter(flags: Flags, name: String): KmValueParameterVisitor? =
|
override fun visitValueParameter(flags: Flags, name: String): KmValueParameterVisitor? =
|
||||||
printValueParameter(flags, name) { params.add(it) }
|
printValueParameter(flags, name) { params.add(it) }
|
||||||
@@ -74,7 +74,9 @@ private fun visitFunction(sb: StringBuilder, flags: Flags, name: String): KmFunc
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun visitProperty(sb: StringBuilder, flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags): KmPropertyVisitor =
|
private fun visitProperty(
|
||||||
|
settings: KotlinpSettings, sb: StringBuilder, flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags
|
||||||
|
): KmPropertyVisitor =
|
||||||
object : KmPropertyVisitor() {
|
object : KmPropertyVisitor() {
|
||||||
val typeParams = mutableListOf<String>()
|
val typeParams = mutableListOf<String>()
|
||||||
var receiverParameterType: String? = null
|
var receiverParameterType: String? = null
|
||||||
@@ -91,7 +93,7 @@ private fun visitProperty(sb: StringBuilder, flags: Flags, name: String, getterF
|
|||||||
printType(flags) { receiverParameterType = it }
|
printType(flags) { receiverParameterType = it }
|
||||||
|
|
||||||
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
||||||
printTypeParameter(flags, name, id, variance) { typeParams.add(it) }
|
printTypeParameter(settings, flags, name, id, variance) { typeParams.add(it) }
|
||||||
|
|
||||||
override fun visitSetterParameter(flags: Flags, name: String): KmValueParameterVisitor? =
|
override fun visitSetterParameter(flags: Flags, name: String): KmValueParameterVisitor? =
|
||||||
printValueParameter(flags, name) { setterParameter = it }
|
printValueParameter(flags, name) { setterParameter = it }
|
||||||
@@ -211,7 +213,7 @@ private fun visitConstructor(sb: StringBuilder, flags: Flags): KmConstructorVisi
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun visitTypeAlias(sb: StringBuilder, flags: Flags, name: String): KmTypeAliasVisitor =
|
private fun visitTypeAlias(settings: KotlinpSettings, sb: StringBuilder, flags: Flags, name: String): KmTypeAliasVisitor =
|
||||||
object : KmTypeAliasVisitor() {
|
object : KmTypeAliasVisitor() {
|
||||||
val annotations = mutableListOf<KmAnnotation>()
|
val annotations = mutableListOf<KmAnnotation>()
|
||||||
val typeParams = mutableListOf<String>()
|
val typeParams = mutableListOf<String>()
|
||||||
@@ -220,7 +222,7 @@ private fun visitTypeAlias(sb: StringBuilder, flags: Flags, name: String): KmTyp
|
|||||||
var versionRequirement: String? = null
|
var versionRequirement: String? = null
|
||||||
|
|
||||||
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
||||||
printTypeParameter(flags, name, id, variance) { typeParams.add(it) }
|
printTypeParameter(settings, flags, name, id, variance) { typeParams.add(it) }
|
||||||
|
|
||||||
override fun visitUnderlyingType(flags: Flags): KmTypeVisitor? =
|
override fun visitUnderlyingType(flags: Flags): KmTypeVisitor? =
|
||||||
printType(flags) { underlyingType = it }
|
printType(flags) { underlyingType = it }
|
||||||
@@ -353,7 +355,7 @@ private fun printType(flags: Flags, output: (String) -> Unit): KmTypeVisitor =
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun printTypeParameter(
|
private fun printTypeParameter(
|
||||||
flags: Flags, name: String, id: Int, variance: KmVariance, output: (String) -> Unit
|
settings: KotlinpSettings, flags: Flags, name: String, id: Int, variance: KmVariance, output: (String) -> Unit
|
||||||
): KmTypeParameterVisitor =
|
): KmTypeParameterVisitor =
|
||||||
object : KmTypeParameterVisitor() {
|
object : KmTypeParameterVisitor() {
|
||||||
val bounds = mutableListOf<String>()
|
val bounds = mutableListOf<String>()
|
||||||
@@ -380,7 +382,10 @@ private fun printTypeParameter(
|
|||||||
if (variance != KmVariance.INVARIANT) {
|
if (variance != KmVariance.INVARIANT) {
|
||||||
append(variance.name.toLowerCase()).append(" ")
|
append(variance.name.toLowerCase()).append(" ")
|
||||||
}
|
}
|
||||||
append("T#$id /* $name */")
|
append("T#$id")
|
||||||
|
if (settings.isVerbose) {
|
||||||
|
append(" /* $name */")
|
||||||
|
}
|
||||||
if (bounds.isNotEmpty()) {
|
if (bounds.isNotEmpty()) {
|
||||||
bounds.joinTo(this, separator = " & ", prefix = " : ")
|
bounds.joinTo(this, separator = " & ", prefix = " : ")
|
||||||
}
|
}
|
||||||
@@ -506,7 +511,7 @@ interface AbstractPrinter<in T : KotlinClassMetadata> {
|
|||||||
fun print(klass: T): String
|
fun print(klass: T): String
|
||||||
}
|
}
|
||||||
|
|
||||||
class ClassPrinter : KmClassVisitor(), AbstractPrinter<KotlinClassMetadata.Class> {
|
class ClassPrinter(private val settings: KotlinpSettings) : KmClassVisitor(), AbstractPrinter<KotlinClassMetadata.Class> {
|
||||||
private val sb = StringBuilder()
|
private val sb = StringBuilder()
|
||||||
private val result = StringBuilder()
|
private val result = StringBuilder()
|
||||||
|
|
||||||
@@ -540,7 +545,7 @@ class ClassPrinter : KmClassVisitor(), AbstractPrinter<KotlinClassMetadata.Class
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
override fun visitTypeParameter(flags: Flags, name: String, id: Int, variance: KmVariance): KmTypeParameterVisitor? =
|
||||||
printTypeParameter(flags, name, id, variance) { typeParams.add(it) }
|
printTypeParameter(settings, flags, name, id, variance) { typeParams.add(it) }
|
||||||
|
|
||||||
override fun visitSupertype(flags: Flags): KmTypeVisitor? =
|
override fun visitSupertype(flags: Flags): KmTypeVisitor? =
|
||||||
printType(flags) { supertypes.add(it) }
|
printType(flags) { supertypes.add(it) }
|
||||||
@@ -549,13 +554,13 @@ class ClassPrinter : KmClassVisitor(), AbstractPrinter<KotlinClassMetadata.Class
|
|||||||
visitConstructor(sb, flags)
|
visitConstructor(sb, flags)
|
||||||
|
|
||||||
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
||||||
visitFunction(sb, flags, name)
|
visitFunction(settings, sb, flags, name)
|
||||||
|
|
||||||
override fun visitProperty(flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags): KmPropertyVisitor? =
|
override fun visitProperty(flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags): KmPropertyVisitor? =
|
||||||
visitProperty(sb, flags, name, getterFlags, setterFlags)
|
visitProperty(settings, sb, flags, name, getterFlags, setterFlags)
|
||||||
|
|
||||||
override fun visitTypeAlias(flags: Flags, name: String): KmTypeAliasVisitor? =
|
override fun visitTypeAlias(flags: Flags, name: String): KmTypeAliasVisitor? =
|
||||||
visitTypeAlias(sb, flags, name)
|
visitTypeAlias(settings, sb, flags, name)
|
||||||
|
|
||||||
override fun visitCompanionObject(name: String) {
|
override fun visitCompanionObject(name: String) {
|
||||||
sb.appendln()
|
sb.appendln()
|
||||||
@@ -586,7 +591,7 @@ class ClassPrinter : KmClassVisitor(), AbstractPrinter<KotlinClassMetadata.Class
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
abstract class PackagePrinter : KmPackageVisitor() {
|
abstract class PackagePrinter(private val settings: KotlinpSettings) : KmPackageVisitor() {
|
||||||
internal val sb = StringBuilder().apply {
|
internal val sb = StringBuilder().apply {
|
||||||
appendln("package {")
|
appendln("package {")
|
||||||
}
|
}
|
||||||
@@ -596,29 +601,29 @@ abstract class PackagePrinter : KmPackageVisitor() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
||||||
visitFunction(sb, flags, name)
|
visitFunction(settings, sb, flags, name)
|
||||||
|
|
||||||
override fun visitProperty(flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags): KmPropertyVisitor? =
|
override fun visitProperty(flags: Flags, name: String, getterFlags: Flags, setterFlags: Flags): KmPropertyVisitor? =
|
||||||
visitProperty(sb, flags, name, getterFlags, setterFlags)
|
visitProperty(settings, sb, flags, name, getterFlags, setterFlags)
|
||||||
|
|
||||||
override fun visitTypeAlias(flags: Flags, name: String): KmTypeAliasVisitor? =
|
override fun visitTypeAlias(flags: Flags, name: String): KmTypeAliasVisitor? =
|
||||||
visitTypeAlias(sb, flags, name)
|
visitTypeAlias(settings, sb, flags, name)
|
||||||
}
|
}
|
||||||
|
|
||||||
class FileFacadePrinter : PackagePrinter(), AbstractPrinter<KotlinClassMetadata.FileFacade> {
|
class FileFacadePrinter(settings: KotlinpSettings) : PackagePrinter(settings), AbstractPrinter<KotlinClassMetadata.FileFacade> {
|
||||||
override fun print(klass: KotlinClassMetadata.FileFacade): String {
|
override fun print(klass: KotlinClassMetadata.FileFacade): String {
|
||||||
klass.accept(this)
|
klass.accept(this)
|
||||||
return sb.toString()
|
return sb.toString()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class LambdaPrinter : KmLambdaVisitor(), AbstractPrinter<KotlinClassMetadata.SyntheticClass> {
|
class LambdaPrinter(private val settings: KotlinpSettings) : KmLambdaVisitor(), AbstractPrinter<KotlinClassMetadata.SyntheticClass> {
|
||||||
private val sb = StringBuilder().apply {
|
private val sb = StringBuilder().apply {
|
||||||
appendln("lambda {")
|
appendln("lambda {")
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
override fun visitFunction(flags: Flags, name: String): KmFunctionVisitor? =
|
||||||
visitFunction(sb, flags, name)
|
visitFunction(settings, sb, flags, name)
|
||||||
|
|
||||||
override fun visitEnd() {
|
override fun visitEnd() {
|
||||||
sb.appendln("}")
|
sb.appendln("}")
|
||||||
@@ -630,7 +635,9 @@ class LambdaPrinter : KmLambdaVisitor(), AbstractPrinter<KotlinClassMetadata.Syn
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class MultiFileClassPartPrinter : PackagePrinter(), AbstractPrinter<KotlinClassMetadata.MultiFileClassPart> {
|
class MultiFileClassPartPrinter(
|
||||||
|
settings: KotlinpSettings
|
||||||
|
) : PackagePrinter(settings), AbstractPrinter<KotlinClassMetadata.MultiFileClassPart> {
|
||||||
override fun print(klass: KotlinClassMetadata.MultiFileClassPart): String {
|
override fun print(klass: KotlinClassMetadata.MultiFileClassPart): String {
|
||||||
sb.appendln(" // facade: ${klass.facadeClassName}")
|
sb.appendln(" // facade: ${klass.facadeClassName}")
|
||||||
klass.accept(this)
|
klass.accept(this)
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ import org.jetbrains.kotlin.cli.jvm.compiler.EnvironmentConfigFiles
|
|||||||
import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment
|
import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment
|
||||||
import org.jetbrains.kotlin.codegen.GenerationUtils
|
import org.jetbrains.kotlin.codegen.GenerationUtils
|
||||||
import org.jetbrains.kotlin.kotlinp.Kotlinp
|
import org.jetbrains.kotlin.kotlinp.Kotlinp
|
||||||
|
import org.jetbrains.kotlin.kotlinp.KotlinpSettings
|
||||||
import org.jetbrains.kotlin.test.ConfigurationKind
|
import org.jetbrains.kotlin.test.ConfigurationKind
|
||||||
import org.jetbrains.kotlin.test.KotlinTestUtils
|
import org.jetbrains.kotlin.test.KotlinTestUtils
|
||||||
import org.jetbrains.kotlin.test.TestJdkKind
|
import org.jetbrains.kotlin.test.TestJdkKind
|
||||||
@@ -24,24 +25,26 @@ fun compileAndPrintAllFiles(file: File, disposable: Disposable, tmpdir: File, co
|
|||||||
val read = StringBuilder()
|
val read = StringBuilder()
|
||||||
val readWriteRead = StringBuilder()
|
val readWriteRead = StringBuilder()
|
||||||
|
|
||||||
|
val kotlinp = Kotlinp(KotlinpSettings(isVerbose = true))
|
||||||
|
|
||||||
compile(file, disposable, tmpdir) { outputFile ->
|
compile(file, disposable, tmpdir) { outputFile ->
|
||||||
when (outputFile.extension) {
|
when (outputFile.extension) {
|
||||||
"kotlin_module" -> {
|
"kotlin_module" -> {
|
||||||
val moduleFile = Kotlinp.readModuleFile(outputFile)!!
|
val moduleFile = kotlinp.readModuleFile(outputFile)!!
|
||||||
val moduleFile2 = transformModuleFile(moduleFile)
|
val moduleFile2 = transformModuleFile(moduleFile)
|
||||||
|
|
||||||
for ((sb, moduleFileToRender) in listOf(read to moduleFile, readWriteRead to moduleFile2)) {
|
for ((sb, moduleFileToRender) in listOf(read to moduleFile, readWriteRead to moduleFile2)) {
|
||||||
sb.appendFileName(outputFile.relativeTo(tmpdir))
|
sb.appendFileName(outputFile.relativeTo(tmpdir))
|
||||||
sb.append(Kotlinp.renderModuleFile(moduleFileToRender))
|
sb.append(kotlinp.renderModuleFile(moduleFileToRender))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
"class" -> {
|
"class" -> {
|
||||||
val classFile = Kotlinp.readClassFile(outputFile)!!
|
val classFile = kotlinp.readClassFile(outputFile)!!
|
||||||
val classFile2 = transformClassFile(classFile)
|
val classFile2 = transformClassFile(classFile)
|
||||||
|
|
||||||
for ((sb, classFileToRender) in listOf(read to classFile, readWriteRead to classFile2)) {
|
for ((sb, classFileToRender) in listOf(read to classFile, readWriteRead to classFile2)) {
|
||||||
sb.appendFileName(outputFile.relativeTo(tmpdir))
|
sb.appendFileName(outputFile.relativeTo(tmpdir))
|
||||||
sb.append(Kotlinp.renderClassFile(classFileToRender))
|
sb.append(kotlinp.renderClassFile(classFileToRender))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else -> fail("Unknown file: $outputFile")
|
else -> fail("Unknown file: $outputFile")
|
||||||
|
|||||||
Reference in New Issue
Block a user