diff --git a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/model/Element.kt b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/model/Element.kt index a12f0d54afd..e3c8153c778 100644 --- a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/model/Element.kt +++ b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/model/Element.kt @@ -79,11 +79,6 @@ class Element(name: String, override val propertyName: String, kind: Kind) : Abs override val visitorParameterName: String get() = safeDecapitalizedName - var customParentInVisitor: Element? = null - - override val parentInVisitor: Element? - get() = customParentInVisitor ?: elementParents.singleOrNull()?.element?.takeIf { !it.isRootElement } - var doesNotNeedImplementation: Boolean = false val needTransformOtherChildren: Boolean get() = _needTransformOtherChildren || elementParents.any { it.element.needTransformOtherChildren } diff --git a/compiler/ir/backend.jvm/codegen/src/org/jetbrains/kotlin/backend/jvm/codegen/ExpressionCodegen.kt b/compiler/ir/backend.jvm/codegen/src/org/jetbrains/kotlin/backend/jvm/codegen/ExpressionCodegen.kt index c24d72b4f9a..e21ac735e2e 100644 --- a/compiler/ir/backend.jvm/codegen/src/org/jetbrains/kotlin/backend/jvm/codegen/ExpressionCodegen.kt +++ b/compiler/ir/backend.jvm/codegen/src/org/jetbrains/kotlin/backend/jvm/codegen/ExpressionCodegen.kt @@ -461,7 +461,7 @@ class ExpressionCodegen( } } - private fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: BlockInfo): PromisedValue { + private fun generateInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: BlockInfo): PromisedValue { val inlineCall = inlinedBlock.inlineCall val callee = inlinedBlock.inlineDeclaration as? IrFunction @@ -559,7 +559,7 @@ class ExpressionCodegen( private fun visitStatementContainer(container: IrStatementContainer, data: BlockInfo): PromisedValue { if (container is IrInlinedFunctionBlock) { - return visitInlinedFunctionBlock(container, data) + return generateInlinedFunctionBlock(container, data) } return container.statements.fold(unitValue) { prev, exp -> prev.discard() diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrInlinedFunctionBlock.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrInlinedFunctionBlock.kt index 607f3e321d5..c5e1b495ac9 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrInlinedFunctionBlock.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrInlinedFunctionBlock.kt @@ -9,6 +9,7 @@ package org.jetbrains.kotlin.ir.expressions import org.jetbrains.kotlin.ir.IrElement +import org.jetbrains.kotlin.ir.visitors.IrElementVisitor /** * A leaf IR tree element. @@ -19,4 +20,7 @@ abstract class IrInlinedFunctionBlock : IrBlock() { abstract var inlineCall: IrFunctionAccessExpression abstract var inlinedElement: IrElement + + override fun accept(visitor: IrElementVisitor, data: D): R = + visitor.visitInlinedFunctionBlock(this, data) } diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrReturnableBlock.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrReturnableBlock.kt index a76169750cc..69fd5ca80ce 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrReturnableBlock.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/expressions/IrReturnableBlock.kt @@ -11,6 +11,7 @@ package org.jetbrains.kotlin.ir.expressions import org.jetbrains.kotlin.ir.declarations.IrReturnTarget import org.jetbrains.kotlin.ir.declarations.IrSymbolOwner import org.jetbrains.kotlin.ir.symbols.IrReturnableBlockSymbol +import org.jetbrains.kotlin.ir.visitors.IrElementVisitor /** * A leaf IR tree element. @@ -19,4 +20,7 @@ import org.jetbrains.kotlin.ir.symbols.IrReturnableBlockSymbol */ abstract class IrReturnableBlock : IrBlock(), IrSymbolOwner, IrReturnTarget { abstract override val symbol: IrReturnableBlockSymbol + + override fun accept(visitor: IrElementVisitor, data: D): R = + visitor.visitReturnableBlock(this, data) } diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformer.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformer.kt index cd009b13008..5e33e471389 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformer.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformer.kt @@ -140,6 +140,12 @@ interface IrElementTransformer : IrElementVisitor { override fun visitComposite(expression: IrComposite, data: D): IrExpression = visitContainerExpression(expression, data) + override fun visitReturnableBlock(expression: IrReturnableBlock, data: D): IrExpression = + visitBlock(expression, data) + + override fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: D): IrExpression = + visitBlock(inlinedBlock, data) + override fun visitSyntheticBody(body: IrSyntheticBody, data: D): IrBody = visitBody(body, data) diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformerVoid.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformerVoid.kt index 3206dc34d7e..2043267ff49 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformerVoid.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementTransformerVoid.kt @@ -256,6 +256,18 @@ abstract class IrElementTransformerVoid : IrElementTransformer { final override fun visitComposite(expression: IrComposite, data: Nothing?): IrExpression = visitComposite(expression) + open fun visitReturnableBlock(expression: IrReturnableBlock): IrExpression = + visitBlock(expression) + + final override fun visitReturnableBlock(expression: IrReturnableBlock, data: Nothing?): IrExpression = + visitReturnableBlock(expression) + + open fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock): IrExpression = + visitBlock(inlinedBlock) + + final override fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: Nothing?): IrExpression = + visitInlinedFunctionBlock(inlinedBlock) + open fun visitSyntheticBody(body: IrSyntheticBody): IrBody = visitBody(body) diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitor.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitor.kt index 0007bf87f99..78a0f94ca38 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitor.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitor.kt @@ -124,6 +124,12 @@ interface IrElementVisitor { fun visitComposite(expression: IrComposite, data: D): R = visitContainerExpression(expression, data) + fun visitReturnableBlock(expression: IrReturnableBlock, data: D): R = + visitBlock(expression, data) + + fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: D): R = + visitBlock(inlinedBlock, data) + fun visitSyntheticBody(body: IrSyntheticBody, data: D): R = visitBody(body, data) diff --git a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitorVoid.kt b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitorVoid.kt index 95c9b2ba5e5..792e0083b82 100644 --- a/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitorVoid.kt +++ b/compiler/ir/ir.tree/gen/org/jetbrains/kotlin/ir/visitors/IrElementVisitorVoid.kt @@ -304,6 +304,22 @@ interface IrElementVisitorVoid : IrElementVisitor { visitContainerExpression(expression) } + override fun visitReturnableBlock(expression: IrReturnableBlock, data: Nothing?) { + visitReturnableBlock(expression) + } + + fun visitReturnableBlock(expression: IrReturnableBlock) { + visitBlock(expression) + } + + override fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock, data: Nothing?) { + visitInlinedFunctionBlock(inlinedBlock) + } + + fun visitInlinedFunctionBlock(inlinedBlock: IrInlinedFunctionBlock) { + visitBlock(inlinedBlock) + } + override fun visitSyntheticBody(body: IrSyntheticBody, data: Nothing?) { visitSyntheticBody(body) } diff --git a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/IrTree.kt b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/IrTree.kt index d8a6ba5e7a5..4f4f385176e 100644 --- a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/IrTree.kt +++ b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/IrTree.kt @@ -48,6 +48,9 @@ object IrTree : AbstractTreeBuilder() { private fun declarationWithLateBinding(symbol: ClassRef<*>, initializer: Element.() -> Unit) = element(Declaration) { initializer() + noAcceptMethod() + noMethodInVisitor() + fieldsToSkipInIrFactoryMethod.add("symbol") fieldsToSkipInIrFactoryMethod.add("containerSource") @@ -72,8 +75,8 @@ object IrTree : AbstractTreeBuilder() { } override val rootElement: Element by element(Other, name = "Element") { - hasAcceptMethod = true - hasTransformMethod = true + needAcceptMethod() + needTransformMethod() transformByChildren = true fun offsetField(prefix: String) = field(prefix + "Offset", int, mutable = false) { @@ -110,7 +113,6 @@ object IrTree : AbstractTreeBuilder() { typeKind = TypeKind.Class transformByChildren = true transformerReturnType = statement - parentInVisitor = rootElement nameInVisitorMethod = "Declaration" parent(declaration) @@ -194,8 +196,7 @@ object IrTree : AbstractTreeBuilder() { +field("isAssignable", boolean, mutable = false) } val valueParameter: Element by element(Declaration) { - hasTransformMethod = true - parentInVisitor = declarationBase + needTransformMethod() parent(declarationBase) parent(valueDeclaration) @@ -239,8 +240,6 @@ object IrTree : AbstractTreeBuilder() { +field("defaultValue", expressionBody, nullable = true, isChild = true) } val `class`: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(possiblyExternalDeclaration) parent(declarationWithVisibility) @@ -325,8 +324,6 @@ object IrTree : AbstractTreeBuilder() { } } val anonymousInitializer: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) +descriptor("ClassDescriptor") // TODO special descriptor for anonymous initializer blocks @@ -360,8 +357,7 @@ object IrTree : AbstractTreeBuilder() { +listField("typeParameters", typeParameter, mutability = Var, isChild = true) } val typeParameter: Element by element(Declaration) { - parentInVisitor = declarationBase - hasTransformMethod = true + needTransformMethod() parent(declarationBase) parent(declarationWithName) @@ -382,8 +378,6 @@ object IrTree : AbstractTreeBuilder() { +symbol(returnTargetSymbolType) } val function: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(possiblyExternalDeclaration) parent(declarationWithVisibility) @@ -410,8 +404,6 @@ object IrTree : AbstractTreeBuilder() { +field("body", body, nullable = true, isChild = true) } val constructor: Element by element(Declaration) { - parentInVisitor = function - parent(function) +descriptor("ClassConstructorDescriptor") @@ -419,8 +411,6 @@ object IrTree : AbstractTreeBuilder() { +field("isPrimary", boolean) } val enumEntry: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(declarationWithName) @@ -430,8 +420,6 @@ object IrTree : AbstractTreeBuilder() { +field("correspondingClass", `class`, nullable = true, isChild = true) } val errorDeclaration: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) additionalIrFactoryMethodParameters.add( @@ -454,8 +442,6 @@ object IrTree : AbstractTreeBuilder() { parent(property) } val field: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(possiblyExternalDeclaration) parent(declarationWithVisibility) @@ -473,8 +459,6 @@ object IrTree : AbstractTreeBuilder() { } } val localDelegatedProperty: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(declarationWithName) parent(symbolOwner) @@ -489,8 +473,7 @@ object IrTree : AbstractTreeBuilder() { +field("setter", simpleFunction, nullable = true, isChild = true) } val moduleFragment: Element by element(Declaration) { - parentInVisitor = rootElement - hasTransformMethod = true + needTransformMethod() transformByChildren = true generateIrFactoryMethod = false @@ -509,7 +492,6 @@ object IrTree : AbstractTreeBuilder() { } } val property: Element by element(Declaration) { - parentInVisitor = declarationBase isLeaf = true parent(declarationBase) @@ -541,7 +523,6 @@ object IrTree : AbstractTreeBuilder() { //TODO: make IrScript as IrPackageFragment, because script is used as a file, not as a class //NOTE: declarations and statements stored separately val script: Element by element(Declaration) { - parentInVisitor = declarationBase generateIrFactoryMethod = false parent(declarationBase) @@ -567,7 +548,6 @@ object IrTree : AbstractTreeBuilder() { +field("constructor", constructor, nullable = true) // K1 } val simpleFunction: Element by element(Declaration) { - parentInVisitor = function isLeaf = true parent(function) @@ -585,8 +565,6 @@ object IrTree : AbstractTreeBuilder() { } } val typeAlias: Element by element(Declaration) { - parentInVisitor = declarationBase - parent(declarationBase) parent(declarationWithName) parent(declarationWithVisibility) @@ -598,8 +576,6 @@ object IrTree : AbstractTreeBuilder() { +field("expandedType", irTypeType) } val variable: Element by element(Declaration) { - parentInVisitor = declarationBase - generateIrFactoryMethod = false parent(declarationBase) @@ -613,7 +589,6 @@ object IrTree : AbstractTreeBuilder() { +field("initializer", expression, nullable = true, isChild = true) } val packageFragment: Element by element(Declaration) { - parentInVisitor = rootElement ownsChildren = false parent(declarationContainer) @@ -643,7 +618,6 @@ object IrTree : AbstractTreeBuilder() { } } val externalPackageFragment: Element by element(Declaration) { - parentInVisitor = packageFragment transformByChildren = true generateIrFactoryMethod = false @@ -653,9 +627,8 @@ object IrTree : AbstractTreeBuilder() { +field("containerSource", type(), nullable = true, mutable = false) } val file: Element by element(Declaration) { - hasTransformMethod = true + needTransformMethod() transformByChildren = true - parentInVisitor = packageFragment generateIrFactoryMethod = false parent(packageFragment) @@ -668,8 +641,7 @@ object IrTree : AbstractTreeBuilder() { } val expression: Element by element(Expression) { - parentInVisitor = rootElement - hasTransformMethod = true + needTransformMethod() transformByChildren = true parent(statement) @@ -692,15 +664,13 @@ object IrTree : AbstractTreeBuilder() { +listField("statements", statement, mutability = List, isChild = true) } val body: Element by element(Expression) { - hasTransformMethod = true - parentInVisitor = rootElement + needTransformMethod() visitorParameterName = "body" transformByChildren = true typeKind = TypeKind.Class } val expressionBody: Element by element(Expression) { - hasTransformMethod = true - parentInVisitor = body + needTransformMethod() visitorParameterName = "body" generateIrFactoryMethod = true @@ -712,7 +682,6 @@ object IrTree : AbstractTreeBuilder() { } } val blockBody: Element by element(Expression) { - parentInVisitor = body visitorParameterName = "body" generateIrFactoryMethod = true @@ -722,15 +691,12 @@ object IrTree : AbstractTreeBuilder() { +factory } val declarationReference: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +symbol(symbolType) //diff: no accept } val memberAccessExpression: Element by element(Expression) { - parentInVisitor = declarationReference nameInVisitorMethod = "MemberAccess" transformerReturnType = rootElement val s = +param("S", symbolType) @@ -812,7 +778,6 @@ object IrTree : AbstractTreeBuilder() { } } val functionAccessExpression: Element by element(Expression) { - parentInVisitor = memberAccessExpression nameInVisitorMethod = "FunctionAccess" transformerReturnType = rootElement @@ -821,7 +786,6 @@ object IrTree : AbstractTreeBuilder() { +field("contextReceiversCount", int) } val constructorCall: Element by element(Expression) { - parentInVisitor = functionAccessExpression transformerReturnType = rootElement parent(functionAccessExpression) @@ -833,20 +797,17 @@ object IrTree : AbstractTreeBuilder() { +field("constructorTypeArgumentsCount", int) } val getSingletonValue: Element by element(Expression) { - parentInVisitor = declarationReference nameInVisitorMethod = "SingletonReference" parent(declarationReference) } val getObjectValue: Element by element(Expression) { - parentInVisitor = getSingletonValue parent(getSingletonValue) +symbol(classSymbolType, mutable = true) } val getEnumValue: Element by element(Expression) { - parentInVisitor = getSingletonValue parent(getSingletonValue) @@ -860,15 +821,12 @@ object IrTree : AbstractTreeBuilder() { * On JVM platform it represents a MethodHandle constant. */ val rawFunctionReference: Element by element(Expression) { - parentInVisitor = declarationReference parent(declarationReference) +symbol(functionSymbolType, mutable = true) } val containerExpression: Element by element(Expression) { - parentInVisitor = expression - parent(expression) parent(statementContainer) @@ -878,14 +836,11 @@ object IrTree : AbstractTreeBuilder() { } } val block: Element by element(Expression) { - parentInVisitor = containerExpression - hasAcceptMethod = true + needAcceptMethod() parent(containerExpression) } val composite: Element by element(Expression) { - parentInVisitor = containerExpression - parent(containerExpression) } val returnableBlock: Element by element(Expression) { @@ -898,11 +853,12 @@ object IrTree : AbstractTreeBuilder() { val inlinedFunctionBlock: Element by element(Expression) { parent(block) + visitorParameterName = "inlinedBlock" + +field("inlineCall", functionAccessExpression) +field("inlinedElement", rootElement) } val syntheticBody: Element by element(Expression) { - parentInVisitor = body visitorParameterName = "body" parent(body) @@ -910,7 +866,6 @@ object IrTree : AbstractTreeBuilder() { +field("kind", type(Packages.exprs, "IrSyntheticBodyKind")) } val breakContinue: Element by element(Expression) { - parentInVisitor = expression visitorParameterName = "jump" parent(expression) @@ -921,27 +876,22 @@ object IrTree : AbstractTreeBuilder() { } } val `break` by element(Expression) { - parentInVisitor = breakContinue visitorParameterName = "jump" parent(breakContinue) } val `continue` by element(Expression) { - parentInVisitor = breakContinue visitorParameterName = "jump" parent(breakContinue) } val call: Element by element(Expression) { - parentInVisitor = functionAccessExpression - parent(functionAccessExpression) +symbol(simpleFunctionSymbolType, mutable = true) +field("superQualifierSymbol", classSymbolType, nullable = true) } val callableReference: Element by element(Expression) { - parentInVisitor = memberAccessExpression val s = +param("S", symbolType) parent(memberAccessExpression.withArgs("S" to s)) @@ -949,15 +899,12 @@ object IrTree : AbstractTreeBuilder() { +symbol(s, mutable = true) } val functionReference: Element by element(Expression) { - parentInVisitor = callableReference parent(callableReference.withArgs("S" to functionSymbolType)) +field("reflectionTarget", functionSymbolType, nullable = true) } val propertyReference: Element by element(Expression) { - parentInVisitor = callableReference - parent(callableReference.withArgs("S" to propertySymbolType)) +field("field", fieldSymbolType, nullable = true) @@ -965,8 +912,6 @@ object IrTree : AbstractTreeBuilder() { +field("setter", simpleFunctionSymbolType, nullable = true) } val localDelegatedPropertyReference: Element by element(Expression) { - parentInVisitor = callableReference - parent(callableReference.withArgs("S" to localDelegatedPropertySymbolType)) +field("delegate", variableSymbolType) @@ -974,15 +919,12 @@ object IrTree : AbstractTreeBuilder() { +field("setter", simpleFunctionSymbolType, nullable = true) } val classReference: Element by element(Expression) { - parentInVisitor = declarationReference - parent(declarationReference) +symbol(classifierSymbolType, mutable = true) +field("classType", irTypeType) } val const: Element by element(Expression) { - parentInVisitor = expression val t = +param("T") parent(expression) @@ -991,7 +933,6 @@ object IrTree : AbstractTreeBuilder() { +field("value", t) } val constantValue: Element by element(Expression) { - parentInVisitor = expression transformByChildren = true parent(expression) @@ -1016,15 +957,11 @@ object IrTree : AbstractTreeBuilder() { } } val constantPrimitive: Element by element(Expression) { - parentInVisitor = constantValue - parent(constantValue) +field("value", const.withArgs("T" to TypeRef.Star), isChild = true) } val constantObject: Element by element(Expression) { - parentInVisitor = constantValue - parent(constantValue) +field("constructor", constructorSymbolType) @@ -1032,27 +969,19 @@ object IrTree : AbstractTreeBuilder() { +listField("typeArguments", irTypeType, mutability = List) } val constantArray: Element by element(Expression) { - parentInVisitor = constantValue - parent(constantValue) +listField("elements", constantValue, mutability = List, isChild = true) } val delegatingConstructorCall: Element by element(Expression) { - parentInVisitor = functionAccessExpression - parent(functionAccessExpression) +symbol(constructorSymbolType, mutable = true) } val dynamicExpression: Element by element(Expression) { - parentInVisitor = expression - parent(expression) } val dynamicOperatorExpression: Element by element(Expression) { - parentInVisitor = dynamicExpression - parent(dynamicExpression) +field("operator", type(Packages.exprs, "IrDynamicOperator")) @@ -1060,38 +989,30 @@ object IrTree : AbstractTreeBuilder() { +listField("arguments", expression, mutability = List, isChild = true) } val dynamicMemberExpression: Element by element(Expression) { - parentInVisitor = dynamicExpression - parent(dynamicExpression) +field("memberName", string) +field("receiver", expression, isChild = true) } val enumConstructorCall: Element by element(Expression) { - parentInVisitor = functionAccessExpression - parent(functionAccessExpression) +symbol(constructorSymbolType, mutable = true) } val errorExpression: Element by element(Expression) { - parentInVisitor = expression - hasAcceptMethod = true + needAcceptMethod() parent(expression) +field("description", string) } val errorCallExpression: Element by element(Expression) { - parentInVisitor = errorExpression - parent(errorExpression) +field("explicitReceiver", expression, nullable = true, isChild = true) +listField("arguments", expression, mutability = List, isChild = true) } val fieldAccessExpression: Element by element(Expression) { - parentInVisitor = declarationReference nameInVisitorMethod = "FieldAccess" ownsChildren = false @@ -1105,19 +1026,14 @@ object IrTree : AbstractTreeBuilder() { +field("origin", statementOriginType, nullable = true) } val getField: Element by element(Expression) { - parentInVisitor = fieldAccessExpression - parent(fieldAccessExpression) } val setField: Element by element(Expression) { - parentInVisitor = fieldAccessExpression - parent(fieldAccessExpression) +field("value", expression, isChild = true) } val functionExpression: Element by element(Expression) { - parentInVisitor = expression transformerReturnType = rootElement parent(expression) @@ -1126,21 +1042,16 @@ object IrTree : AbstractTreeBuilder() { +field("function", simpleFunction, isChild = true) } val getClass: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("argument", expression, isChild = true) } val instanceInitializerCall: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("classSymbol", classSymbolType) } val loop: Element by element(Expression) { - parentInVisitor = expression visitorParameterName = "loop" ownsChildren = false @@ -1156,36 +1067,28 @@ object IrTree : AbstractTreeBuilder() { } } val whileLoop: Element by element(Expression) { - parentInVisitor = loop visitorParameterName = "loop" childrenOrderOverride = listOf("condition", "body") parent(loop) } val doWhileLoop: Element by element(Expression) { - parentInVisitor = loop visitorParameterName = "loop" parent(loop) } val `return`: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("value", expression, isChild = true) +field("returnTargetSymbol", returnTargetSymbolType) } val stringConcatenation: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +listField("arguments", expression, mutability = List, isChild = true) } val suspensionPoint: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("suspensionPointIdParameter", variable, isChild = true) @@ -1193,22 +1096,17 @@ object IrTree : AbstractTreeBuilder() { +field("resumeResult", expression, isChild = true) } val suspendableExpression: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("suspensionPointId", expression, isChild = true) +field("result", expression, isChild = true) } val `throw`: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("value", expression, isChild = true) } val `try`: Element by element(Expression) { - parentInVisitor = expression visitorParameterName = "aTry" parent(expression) @@ -1218,16 +1116,14 @@ object IrTree : AbstractTreeBuilder() { +field("finallyExpression", expression, nullable = true, isChild = true) } val catch: Element by element(Expression) { - parentInVisitor = rootElement visitorParameterName = "aCatch" - hasTransformMethod = true + needTransformMethod() transformByChildren = true +field("catchParameter", variable, isChild = true) +field("result", expression, isChild = true) } val typeOperatorCall: Element by element(Expression) { - parentInVisitor = expression nameInVisitorMethod = "TypeOperator" parent(expression) @@ -1237,7 +1133,6 @@ object IrTree : AbstractTreeBuilder() { +field("typeOperand", irTypeType) } val valueAccessExpression: Element by element(Expression) { - parentInVisitor = declarationReference nameInVisitorMethod = "ValueAccess" parent(declarationReference) @@ -1246,30 +1141,23 @@ object IrTree : AbstractTreeBuilder() { +field("origin", statementOriginType, nullable = true) } val getValue: Element by element(Expression) { - parentInVisitor = valueAccessExpression - parent(valueAccessExpression) } val setValue: Element by element(Expression) { - parentInVisitor = valueAccessExpression - parent(valueAccessExpression) +field("value", expression, isChild = true) } val varargElement: Element by element(Expression) val vararg: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("varargElementType", irTypeType) +listField("elements", varargElement, mutability = List, isChild = true) } val spreadElement: Element by element(Expression) { - parentInVisitor = rootElement visitorParameterName = "spread" - hasTransformMethod = true + needTransformMethod() transformByChildren = true parent(varargElement) @@ -1277,27 +1165,23 @@ object IrTree : AbstractTreeBuilder() { +field("expression", expression, isChild = true) } val `when`: Element by element(Expression) { - parentInVisitor = expression - parent(expression) +field("origin", statementOriginType, nullable = true) +listField("branches", branch, mutability = List, isChild = true) } val branch: Element by element(Expression) { - parentInVisitor = rootElement visitorParameterName = "branch" - hasAcceptMethod = true - hasTransformMethod = true + needAcceptMethod() + needTransformMethod() transformByChildren = true +field("condition", expression, isChild = true) +field("result", expression, isChild = true) } val elseBranch: Element by element(Expression) { - parentInVisitor = branch visitorParameterName = "branch" - hasTransformMethod = true + needTransformMethod() transformByChildren = true parent(branch) diff --git a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/config/AbstractTreeBuilder.kt b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/config/AbstractTreeBuilder.kt index b10ad405a20..aca1e666e9f 100644 --- a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/config/AbstractTreeBuilder.kt +++ b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/config/AbstractTreeBuilder.kt @@ -50,6 +50,22 @@ abstract class AbstractTreeBuilder { elementParents.add(ElementRef(type.element, type.args, type.nullable)) } + protected fun Element.needAcceptMethod() { + customHasAcceptMethod = true + } + + protected fun Element.noAcceptMethod() { + customHasAcceptMethod = false + } + + protected fun Element.needTransformMethod() { + hasTransformMethod = true + } + + protected fun Element.noMethodInVisitor() { + generateVisitorMethod = false + } + protected fun param(name: String, vararg bounds: TypeRef, variance: Variance = Variance.INVARIANT): TypeVariable { return TypeVariable(name, bounds.toList(), variance) } diff --git a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Model.kt b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Model.kt index 4f1ce5dbabe..7f6facaebe9 100644 --- a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Model.kt +++ b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Model.kt @@ -8,6 +8,8 @@ package org.jetbrains.kotlin.ir.generator.model import org.jetbrains.kotlin.generators.tree.* import org.jetbrains.kotlin.generators.tree.ListField as AbstractListField import org.jetbrains.kotlin.ir.generator.BASE_PACKAGE +import org.jetbrains.kotlin.ir.generator.IrTree +import org.jetbrains.kotlin.ir.generator.elementBaseType import org.jetbrains.kotlin.utils.SmartPrinter import org.jetbrains.kotlin.utils.topologicalSort import org.jetbrains.kotlin.generators.tree.ElementOrRef as GenericElementOrRef @@ -53,7 +55,19 @@ class Element( override val args: Map get() = emptyMap() - override var parentInVisitor: Element? = null + /** + * Allows to forcibly skip generation of the method for this element in visitors. + */ + var generateVisitorMethod = true + + override val parentInVisitor: Element? + get() { + if (!generateVisitorMethod) return null + return customParentInVisitor + ?: elementParents.singleOrNull { it.typeKind == TypeKind.Class }?.element + ?: IrTree.rootElement.takeIf { elementBaseType in otherParents } + } + var typeKind: TypeKind? = null set(value) { @@ -86,7 +100,11 @@ class Element( override var visitorParameterName = category.defaultVisitorParam - override var hasAcceptMethod = false // By default, accept is generated only for leaves. + var customHasAcceptMethod: Boolean? = null + + override val hasAcceptMethod: Boolean + get() = customHasAcceptMethod ?: (isLeaf && parentInVisitor != null) + override var hasTransformMethod = false diff --git a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Transformations.kt b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Transformations.kt index 1299a3d9493..82d9d80cea7 100644 --- a/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Transformations.kt +++ b/compiler/ir/ir.tree/tree-generator/src/org/jetbrains/kotlin/ir/generator/model/Transformations.kt @@ -37,9 +37,6 @@ internal fun markLeaves(elements: List) { for (el in leaves) { el.isLeaf = true - if (el.parentInVisitor != null) { - el.hasAcceptMethod = true - } } } diff --git a/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/AbstractElement.kt b/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/AbstractElement.kt index 3b58d414cb0..852b46d980d 100644 --- a/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/AbstractElement.kt +++ b/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/AbstractElement.kt @@ -56,10 +56,16 @@ abstract class AbstractElement( */ abstract val visitorParameterName: String + /** + * @see parentInVisitor + */ + var customParentInVisitor: Element? = null + /** * The default element to visit if the method for visiting this element is not overridden. */ - abstract val parentInVisitor: Element? + open val parentInVisitor: Element? + get() = customParentInVisitor ?: elementParents.singleOrNull()?.element?.takeIf { !it.isRootElement } override val allParents: List get() = elementParents.map { it.element } @@ -92,7 +98,7 @@ abstract class AbstractElement( /** * The return type of the corresponding transformer method for this element. * - * By default, computed using [org.jetbrains.kotlin.generators.tree.detectBaseTransformerTypes], but can be customizaed via + * By default, computed using [org.jetbrains.kotlin.generators.tree.detectBaseTransformerTypes], but can be customized via * [transformerReturnType] */ val transformerClass: Element diff --git a/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/utils.kt b/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/utils.kt index 4a6bff6f583..786bb4c5103 100644 --- a/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/utils.kt +++ b/generators/tree-generator-common/src/org/jetbrains/kotlin/generators/tree/utils.kt @@ -11,7 +11,7 @@ fun > Element.traverseParents(block: (Elem } /** - * For each tree element, sets its [AbstractElement.baseTransformerType] to one of it parents if that parent type is used at least once as + * For each tree element, sets its [AbstractElement.baseTransformerType] to one of its parents if that parent type is used at least once as * a type of a field, except when that field is explicitly opted out of it via * [AbstractField.useInBaseTransformerDetection]. */