Refactor SharedVariablesManager: get rid of descriptors in API

This commit is contained in:
Mikhael Bogdanov
2018-05-04 11:28:56 +02:00
parent f1c0db346a
commit 12ba1b002c
4 changed files with 75 additions and 63 deletions
@@ -16,16 +16,19 @@
package org.jetbrains.kotlin.backend.common.descriptors
import org.jetbrains.kotlin.descriptors.VariableDescriptor
import org.jetbrains.kotlin.ir.IrStatement
import org.jetbrains.kotlin.ir.declarations.IrVariable
import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.IrGetValue
import org.jetbrains.kotlin.ir.expressions.IrSetVariable
import org.jetbrains.kotlin.ir.symbols.IrVariableSymbol
interface SharedVariablesManager {
fun createSharedVariableDescriptor(variableDescriptor: VariableDescriptor): VariableDescriptor
fun defineSharedValue(sharedVariableDescriptor: VariableDescriptor, originalDeclaration: IrVariable): IrStatement
fun getSharedValue(sharedVariableDescriptor: VariableDescriptor, originalGet: IrGetValue): IrExpression
fun setSharedValue(sharedVariableDescriptor: VariableDescriptor, originalSet: IrSetVariable): IrExpression
fun declareSharedVariable(originalDeclaration: IrVariable): IrVariable
fun defineSharedValue(originalDeclaration: IrVariable, sharedVariableDeclaration: IrVariable): IrStatement
fun getSharedValue(sharedVariableSymbol: IrVariableSymbol, originalGet: IrGetValue): IrExpression
fun setSharedValue(sharedVariableSymbol: IrVariableSymbol, originalSet: IrSetVariable): IrExpression
}
@@ -18,9 +18,6 @@ package org.jetbrains.kotlin.backend.common.lower
import org.jetbrains.kotlin.backend.common.BackendContext
import org.jetbrains.kotlin.backend.common.FunctionLoweringPass
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.ValueDescriptor
import org.jetbrains.kotlin.descriptors.VariableDescriptor
import org.jetbrains.kotlin.ir.IrElement
import org.jetbrains.kotlin.ir.IrStatement
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
@@ -30,6 +27,9 @@ import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.IrGetValue
import org.jetbrains.kotlin.ir.expressions.IrSetVariable
import org.jetbrains.kotlin.ir.expressions.IrValueAccessExpression
import org.jetbrains.kotlin.ir.symbols.IrValueSymbol
import org.jetbrains.kotlin.ir.symbols.IrVariableSymbol
import org.jetbrains.kotlin.ir.util.dump
import org.jetbrains.kotlin.ir.visitors.*
import java.util.*
@@ -39,7 +39,7 @@ class SharedVariablesLowering(val context: BackendContext) : FunctionLoweringPas
}
private inner class SharedVariablesTransformer(val irFunction: IrFunction) {
val sharedVariables = HashSet<ValueDescriptor>()
private val sharedVariables = HashSet<IrVariable>()
fun lowerSharedVariables() {
collectSharedVariables()
@@ -51,10 +51,10 @@ class SharedVariablesLowering(val context: BackendContext) : FunctionLoweringPas
private fun collectSharedVariables() {
irFunction.acceptVoid(object : IrElementVisitorVoid {
val declarationsStack = ArrayDeque<IrDeclaration>()
val currentDeclaration: DeclarationDescriptor
get() = declarationsStack.peek().descriptor
val currentDeclaration: IrDeclaration
get() = declarationsStack.peek()
val relevantVars = HashSet<VariableDescriptor>()
val relevantVars = HashSet<IrVariable>()
override fun visitElement(element: IrElement) {
element.acceptChildrenVoid(this)
@@ -69,37 +69,35 @@ class SharedVariablesLowering(val context: BackendContext) : FunctionLoweringPas
override fun visitVariable(declaration: IrVariable) {
declaration.acceptChildrenVoid(this)
val variableDescriptor = declaration.descriptor
if (variableDescriptor.isVar) {
relevantVars.add(variableDescriptor)
if (declaration.isVar) {
relevantVars.add(declaration)
}
}
override fun visitVariableAccess(expression: IrValueAccessExpression) {
expression.acceptChildrenVoid(this)
val descriptor = expression.descriptor
if (descriptor in relevantVars && descriptor.containingDeclaration != currentDeclaration) {
sharedVariables.add(descriptor)
val value = expression.symbol.owner
if (value in relevantVars && (value as IrVariable).parent != currentDeclaration) {
sharedVariables.add(value)
}
}
})
}
private fun rewriteSharedVariables() {
val transformedDescriptors = HashMap<ValueDescriptor, VariableDescriptor>()
val transformedDescriptors = HashMap<IrValueSymbol, IrVariableSymbol>()
irFunction.transformChildrenVoid(object : IrElementTransformerVoid() {
override fun visitVariable(declaration: IrVariable): IrStatement {
declaration.transformChildrenVoid(this)
val oldDescriptor = declaration.descriptor
if (oldDescriptor !in sharedVariables) return declaration
if (declaration !in sharedVariables) return declaration
val newDescriptor = context.sharedVariablesManager.createSharedVariableDescriptor(oldDescriptor)
transformedDescriptors[oldDescriptor] = newDescriptor
val newDeclaration = context.sharedVariablesManager.declareSharedVariable(declaration)
transformedDescriptors[declaration.symbol] = newDeclaration.symbol
return context.sharedVariablesManager.defineSharedValue(newDescriptor, declaration)
return context.sharedVariablesManager.defineSharedValue(declaration, newDeclaration)
}
})
@@ -107,26 +105,26 @@ class SharedVariablesLowering(val context: BackendContext) : FunctionLoweringPas
override fun visitGetValue(expression: IrGetValue): IrExpression {
expression.transformChildrenVoid(this)
val newDescriptor = getTransformedDescriptor(expression.descriptor) ?: return expression
val newDeclaration = getTransformedSymbol(expression.symbol) ?: return expression
return context.sharedVariablesManager.getSharedValue(newDescriptor, expression)
return context.sharedVariablesManager.getSharedValue(newDeclaration, expression)
}
override fun visitSetVariable(expression: IrSetVariable): IrExpression {
expression.transformChildrenVoid(this)
val newDescriptor = getTransformedDescriptor(expression.descriptor) ?: return expression
val newDeclaration = getTransformedSymbol(expression.symbol) ?: return expression
return context.sharedVariablesManager.setSharedValue(newDescriptor, expression)
return context.sharedVariablesManager.setSharedValue(newDeclaration, expression)
}
private fun getTransformedDescriptor(oldDescriptor: ValueDescriptor): VariableDescriptor? =
transformedDescriptors.getOrElse(oldDescriptor) {
assert(oldDescriptor !in sharedVariables) {
"Shared variable is not transformed: $oldDescriptor"
}
null
private fun getTransformedSymbol(oldSymbol: IrValueSymbol): IrVariableSymbol? =
transformedDescriptors.getOrElse(oldSymbol) {
assert(oldSymbol.owner !in sharedVariables) {
"Shared variable is not transformed: ${oldSymbol.owner.dump()}"
}
null
}
})
}
}