diff --git a/src/org/jetbrains/eval4j/interpreterLoop.kt b/src/org/jetbrains/eval4j/interpreterLoop.kt index 948aaf1ddc5..6b11505da2a 100644 --- a/src/org/jetbrains/eval4j/interpreterLoop.kt +++ b/src/org/jetbrains/eval4j/interpreterLoop.kt @@ -48,8 +48,8 @@ trait InterpretationEventHandler { class ThrownFromEvalException(val exception: Value): RuntimeException() fun interpreterLoop( - ownerClassInternalName: String, m: MethodNode, + initialState: Frame, eval: Eval, handler: InterpretationEventHandler = InterpretationEventHandler.NONE ): InterpreterResult { @@ -64,7 +64,7 @@ fun interpreterLoop( } val interpreter = SingleInstructionInterpreter(eval) - val frame = initFrame(ownerClassInternalName, m, interpreter) + val frame = Frame(initialState) val handlers = computeHandlers(m) class ResultException(val result: InterpreterResult): RuntimeException() @@ -193,35 +193,6 @@ fun interpreterLoop( } // Copied from org.objectweb.asm.tree.analysis.Analyzer.analyze() -fun initFrame( - owner: String, - m: MethodNode, - interpreter: Interpreter -): Frame { - val current = Frame(m.maxLocals, m.maxStack) - current.setReturn(interpreter.newValue(Type.getReturnType(m.desc))) - - var local = 0 - if ((m.access and ACC_STATIC) == 0) { - val ctype = Type.getObjectType(owner) - current.setLocal(local++, interpreter.newValue(ctype)) - } - - val args = Type.getArgumentTypes(m.desc) - for (i in 0..args.size - 1) { - current.setLocal(local++, interpreter.newValue(args[i])) - if (args[i].getSize() == 2) { - current.setLocal(local++, interpreter.newValue(null)) - } - } - - while (local < m.maxLocals) { - current.setLocal(local++, interpreter.newValue(null)) - } - - return current -} - fun computeHandlers(m: MethodNode): Array?> { val insns = m.instructions val handlers = Array?>(insns.size()) {null} diff --git a/test/org/jetbrains/eval4j/test/main.kt b/test/org/jetbrains/eval4j/test/main.kt index 89f54af4626..0ee8ee76ccc 100644 --- a/test/org/jetbrains/eval4j/test/main.kt +++ b/test/org/jetbrains/eval4j/test/main.kt @@ -13,6 +13,8 @@ import java.lang.reflect.Field import java.lang.reflect.Constructor import java.lang.reflect.InvocationTargetException import java.lang.reflect.Array as JArray +import org.objectweb.asm.tree.analysis.Interpreter +import org.objectweb.asm.tree.analysis.Frame fun suite(): TestSuite { val suite = TestSuite() @@ -72,8 +74,12 @@ fun doTest(ownerClass: Class, methodNode: MethodNode): TestCase? { override fun runTest() { val value = interpreterLoop( - ownerClass.getInternalName(), methodNode, + initFrame( + ownerClass.getInternalName(), + methodNode, + SingleInstructionInterpreter(REFLECTION_EVAL) + ), REFLECTION_EVAL ) @@ -82,6 +88,35 @@ fun doTest(ownerClass: Class, methodNode: MethodNode): TestCase? { } } +fun initFrame( + owner: String, + m: MethodNode, + interpreter: Interpreter +): Frame { + val current = Frame(m.maxLocals, m.maxStack) + current.setReturn(interpreter.newValue(Type.getReturnType(m.desc))) + + var local = 0 + if ((m.access and ACC_STATIC) == 0) { + val ctype = Type.getObjectType(owner) + current.setLocal(local++, interpreter.newValue(ctype)) + } + + val args = Type.getArgumentTypes(m.desc) + for (i in 0..args.size - 1) { + current.setLocal(local++, interpreter.newValue(args[i])) + if (args[i].getSize() == 2) { + current.setLocal(local++, interpreter.newValue(null)) + } + } + + while (local < m.maxLocals) { + current.setLocal(local++, interpreter.newValue(null)) + } + + return current +} + fun objectToValue(obj: Any?, expectedType: Type): Value { return when (expectedType.getSort()) { Type.VOID -> VOID_VALUE