/** ****************************************************************************** * @file : vm.c * @author : simon * @brief : Interpret the bytecode from chunk * @attention : None * @date : 2023/8/17 ****************************************************************************** */ #include "common.h" #include "vm.h" #include "debug.h" #include "compiler.h" VM vm; /// \brief 重置栈 static void resetStack() { vm.stackTop = vm.stack; // 指针指向栈顶 } void initVM() { resetStack(); } static InterpretResult run() { //! reads the byte currently pointed at by ip //! and then advances the instruction pointer #define READ_BYTE() (*vm.ip++) //! reads the next byte from the bytecode //! treats the resulting number as an index #define READ_CONSTANT() (vm.chunk->constants.values[READ_BYTE()]) #define BINARY_OP(op) \ do { \ double b = pop(); \ double a = pop(); \ push(a op b); \ } while(false) for (;;) { #ifdef DEBUG_TRACE_EXECUTION //! start printf("------------------------\n|"); for (Value *slot = vm.stack; slot < vm.stackTop; slot++) { printf("[ "); printValue(*slot); printf(" ]"); } printf("\n------------------------"); printf("\n"); //! end disassembleInstruction(vm.chunk, (int) (vm.ip - vm.chunk->code)); #endif uint8_t instruction; switch (instruction = READ_BYTE()) { case OP_CONSTANT: { Value constant = READ_CONSTANT(); push(constant); break; } case OP_ADD: BINARY_OP(+); break; case OP_SUBTRACT: BINARY_OP(-); break; case OP_MULTIPLY: BINARY_OP(*); break; case OP_DIVIDE: BINARY_OP(/); break; case OP_NEGATE: push(-pop()); break; case OP_RETURN: { printValue(pop()); printf("\n"); return INTERPRET_OK; } } } #undef READ_BYTE #undef READ_CONSTANT #undef BINARY_OP } void freeVM() { } InterpretResult interpret(const char *source) { compile(source); return INTERPRET_OK; } void push(Value value) { *vm.stackTop = value; vm.stackTop++; } Value pop() { vm.stackTop--; //! NOTE: 出栈后,里面的值没有清除 return *vm.stackTop; }