[IR] Support stable order in IR dump

That mode is need to test deserialization of klibs
This commit is contained in:
Roman Artemev
2021-06-07 16:12:29 +03:00
committed by teamcityserver
parent bbcd511c44
commit 2eac442705
2 changed files with 37 additions and 8 deletions
@@ -16,8 +16,8 @@
package org.jetbrains.kotlin.ir.util
import org.jetbrains.kotlin.ir.IrFileEntry
import org.jetbrains.kotlin.ir.IrElement
import org.jetbrains.kotlin.ir.IrFileEntry
import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.expressions.*
import org.jetbrains.kotlin.ir.symbols.IrSymbol
@@ -27,10 +27,10 @@ import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
import org.jetbrains.kotlin.utils.Printer
fun IrElement.dump(normalizeNames: Boolean = false): String =
fun IrElement.dump(normalizeNames: Boolean = false, stableOrder: Boolean = false): String =
try {
StringBuilder().also { sb ->
accept(DumpIrTreeVisitor(sb, normalizeNames), "")
accept(DumpIrTreeVisitor(sb, normalizeNames, stableOrder), "")
}.toString()
} catch (e: Exception) {
"(Full dump is not available: ${e.message})\n" + render()
@@ -44,13 +44,42 @@ fun IrFile.dumpTreesFromLineNumber(lineNumber: Int, normalizeNames: Boolean = fa
class DumpIrTreeVisitor(
out: Appendable,
normalizeNames: Boolean = false
normalizeNames: Boolean = false,
private val stableOrder: Boolean = false
) : IrElementVisitor<Unit, String> {
private val printer = Printer(out, " ")
private val elementRenderer = RenderIrElementVisitor(normalizeNames)
private fun IrType.render() = elementRenderer.renderType(this)
private fun List<IrDeclaration>.ordered(): List<IrDeclaration> {
if (!stableOrder) return this
val strictOrder = mutableMapOf<IrDeclaration, Int>()
var idx = 0
forEach {
if (it is IrProperty && it.backingField != null && !it.isConst) {
strictOrder[it] = idx++
}
if (it is IrAnonymousInitializer) {
strictOrder[it] = idx++
}
}
return sortedWith { a, b ->
val strictA = strictOrder[a] ?: Int.MAX_VALUE
val strictB = strictOrder[b] ?: Int.MAX_VALUE
if (strictA == strictB) {
val rA = a.render()
val rB = b.render()
rA.compareTo(rB)
} else strictA - strictB
}
}
override fun visitElement(element: IrElement, data: String) {
element.dumpLabeledElementWith(data) {
if (element is IrAnnotationContainer) {
@@ -69,7 +98,7 @@ class DumpIrTreeVisitor(
override fun visitFile(declaration: IrFile, data: String) {
declaration.dumpLabeledElementWith(data) {
dumpAnnotations(declaration)
declaration.declarations.dumpElements()
declaration.declarations.ordered().dumpElements()
}
}
@@ -78,7 +107,7 @@ class DumpIrTreeVisitor(
dumpAnnotations(declaration)
declaration.thisReceiver?.accept(this, "\$this")
declaration.typeParameters.dumpElements()
declaration.declarations.dumpElements()
declaration.declarations.ordered().dumpElements()
}
}
@@ -83,7 +83,7 @@ abstract class AbstractKlibTextTestCase : CodegenTestCase() {
val ignoreErrors = AbstractIrGeneratorTestCase.shouldIgnoreErrors(wholeFile)
val stdlib = loadKlibFromPath(listOf(runtimeKlibPath)).single()
val (irModule, bindingContext) = buildFragmentAndLinkIt(stdlib, ignoreErrors, expectActualSymbols)
val expected = irModule.dump()
val expected = irModule.dump(stableOrder = true)
val mppProject =
myEnvironment.configuration.languageVersionSettings.getFeatureSupport(LanguageFeature.MultiPlatformProjects) == LanguageFeature.State.ENABLED
val klibPath = serializeModule(irModule, bindingContext, stdlib, ignoreErrors, expectActualSymbols, !mppProject)
@@ -91,7 +91,7 @@ abstract class AbstractKlibTextTestCase : CodegenTestCase() {
val stdlib2 = libs[0]
val klib = libs[1]
val deserializedIrModule = deserializeModule(stdlib2, klib)
val actual = deserializedIrModule.dump()
val actual = deserializedIrModule.dump(stableOrder = true)
try {
TestCase.assertEquals(wholeFile.name, expected, actual)