Add configuration into IrInterpreterEnvironment
This configuration will contains all necessary setting for interpreter and will be replenished over time
This commit is contained in:
committed by
TeamCityServer
parent
b150cc9537
commit
cc56acc2c2
+1
-1
@@ -80,7 +80,7 @@ internal fun unfoldInstruction(element: IrElement?, environment: IrInterpreterEn
|
||||
}
|
||||
|
||||
private fun unfoldFunction(function: IrSimpleFunction, environment: IrInterpreterEnvironment) {
|
||||
if (environment.callStack.getStackCount() >= IrInterpreterEnvironment.MAX_STACK)
|
||||
if (environment.callStack.getStackCount() >= environment.configuration.maxStack)
|
||||
return StackOverflowError().handleUserException(environment)
|
||||
// SimpleInstruction with function is added in IrCall
|
||||
// It will serve as endpoint for all possible calls, there we drop frame and copy result to new one
|
||||
|
||||
+7
-11
@@ -39,9 +39,7 @@ internal class CustomInstruction(val evaluate: () -> Unit) : Instruction {
|
||||
get() = null
|
||||
}
|
||||
|
||||
class IrInterpreter private constructor(
|
||||
internal val bodyMap: Map<IdSignature, IrBody>, internal val environment: IrInterpreterEnvironment
|
||||
) {
|
||||
class IrInterpreter(internal val environment: IrInterpreterEnvironment, internal val bodyMap: Map<IdSignature, IrBody>) {
|
||||
val irBuiltIns: IrBuiltIns
|
||||
get() = environment.irBuiltIns
|
||||
private val callStack: CallStack
|
||||
@@ -50,16 +48,13 @@ class IrInterpreter private constructor(
|
||||
private var commandCount = 0
|
||||
|
||||
constructor(irBuiltIns: IrBuiltIns, bodyMap: Map<IdSignature, IrBody> = emptyMap()) :
|
||||
this(bodyMap, IrInterpreterEnvironment(irBuiltIns, CallStack()))
|
||||
this(IrInterpreterEnvironment(irBuiltIns), bodyMap)
|
||||
|
||||
private constructor(environment: IrInterpreterEnvironment, bodyMap: Map<IdSignature, IrBody> = emptyMap()) :
|
||||
this(bodyMap, environment)
|
||||
|
||||
constructor(irModule: IrModuleFragment) : this(emptyMap(), IrInterpreterEnvironment(irModule))
|
||||
constructor(irModule: IrModuleFragment) : this(IrInterpreterEnvironment(irModule), emptyMap())
|
||||
|
||||
private fun incrementAndCheckCommands() {
|
||||
commandCount++
|
||||
if (commandCount >= IrInterpreterEnvironment.MAX_COMMANDS) InterpreterTimeOutError().handleUserException(environment)
|
||||
if (commandCount >= environment.configuration.maxCommands) InterpreterTimeOutError().handleUserException(environment)
|
||||
}
|
||||
|
||||
private fun getUnitState(): State = environment.mapOfObjects[irBuiltIns.unitClass]!!
|
||||
@@ -395,8 +390,9 @@ class IrInterpreter private constructor(
|
||||
environment.mapOfObjects[objectClass.symbol] = state // must set object's state here to avoid cyclic evaluation
|
||||
callStack.addVariable(Variable(objectClass.thisReceiver!!.symbol, state))
|
||||
|
||||
// non compile time objects can be used in interpreter, for example, to evaluate const properties
|
||||
if (!objectClass.hasAnnotation(compileTimeAnnotation)) return@interceptGetObjectValue callStack.pushState(state)
|
||||
// non compile time objects can be used in interpreter, for example, to evaluate const properties or in tests
|
||||
if (!objectClass.hasAnnotation(compileTimeAnnotation) && !environment.configuration.createNonCompileTimeObjects)
|
||||
return@interceptGetObjectValue callStack.pushState(state)
|
||||
|
||||
val constructor = objectClass.constructors.firstOrNull() ?: return@interceptGetObjectValue callStack.pushState(state)
|
||||
val constructorCall = IrConstructorCallImpl.fromSymbolOwner(constructor.returnType, constructor.symbol)
|
||||
|
||||
+20
@@ -0,0 +1,20 @@
|
||||
/*
|
||||
* Copyright 2010-2021 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.ir.interpreter
|
||||
|
||||
/**
|
||||
* @param maxStack describes the maximum allowed call stack size
|
||||
* @param maxCommands describes the maximum allowed number of simple instructions performed
|
||||
* @param createNonCompileTimeObjects
|
||||
* 'true' - interpreter will construct object and initialize its properties despite the fact it is not marked as compile time;
|
||||
* 'false' - interpreter will create a representation of empty object, that can be used to get const properties
|
||||
*/
|
||||
// TODO maybe create some sort of builder
|
||||
class IrInterpreterConfiguration(
|
||||
val maxStack: Int = 10_000,
|
||||
val maxCommands: Int = 1_000_000,
|
||||
val createNonCompileTimeObjects: Boolean = false,
|
||||
)
|
||||
+10
-11
@@ -14,22 +14,26 @@ import org.jetbrains.kotlin.ir.interpreter.state.Complex
|
||||
import org.jetbrains.kotlin.ir.symbols.IrSymbol
|
||||
import org.jetbrains.kotlin.ir.util.isSubclassOf
|
||||
|
||||
internal class IrInterpreterEnvironment(val irBuiltIns: IrBuiltIns, val callStack: CallStack) {
|
||||
val irExceptions = mutableListOf<IrClass>()
|
||||
var mapOfEnums = mutableMapOf<IrSymbol, Complex>()
|
||||
var mapOfObjects = mutableMapOf<IrSymbol, Complex>()
|
||||
class IrInterpreterEnvironment(
|
||||
val irBuiltIns: IrBuiltIns,
|
||||
val configuration: IrInterpreterConfiguration = IrInterpreterConfiguration(),
|
||||
) {
|
||||
internal val callStack: CallStack = CallStack()
|
||||
internal val irExceptions = mutableListOf<IrClass>()
|
||||
internal var mapOfEnums = mutableMapOf<IrSymbol, Complex>()
|
||||
internal var mapOfObjects = mutableMapOf<IrSymbol, Complex>()
|
||||
|
||||
init {
|
||||
mapOfObjects[irBuiltIns.unitClass] = Common(irBuiltIns.unitClass.owner)
|
||||
}
|
||||
|
||||
private constructor(environment: IrInterpreterEnvironment) : this(environment.irBuiltIns, CallStack()) {
|
||||
private constructor(environment: IrInterpreterEnvironment) : this(environment.irBuiltIns, configuration = environment.configuration) {
|
||||
irExceptions.addAll(environment.irExceptions)
|
||||
mapOfEnums = environment.mapOfEnums
|
||||
mapOfObjects = environment.mapOfObjects
|
||||
}
|
||||
|
||||
constructor(irModule: IrModuleFragment) : this(irModule.irBuiltins, CallStack()) {
|
||||
constructor(irModule: IrModuleFragment) : this(irModule.irBuiltins) {
|
||||
irExceptions.addAll(
|
||||
irModule.files
|
||||
.flatMap { it.declarations }
|
||||
@@ -41,9 +45,4 @@ internal class IrInterpreterEnvironment(val irBuiltIns: IrBuiltIns, val callStac
|
||||
fun copyWithNewCallStack(): IrInterpreterEnvironment {
|
||||
return IrInterpreterEnvironment(this)
|
||||
}
|
||||
|
||||
companion object {
|
||||
const val MAX_STACK = 10_000
|
||||
const val MAX_COMMANDS = 1_000_000
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user