diff --git a/src/VM/VM.c b/src/VM/VM.c index 2753c6a..cc9d175 100644 --- a/src/VM/VM.c +++ b/src/VM/VM.c @@ -20,6 +20,7 @@ void _VM_setError(VM* vm, const char* context, const char* format, ...){ strcpy(buf, "SPRINTF FAILED"); } vm->error_message = buf; + vm->state = VMState_InternalError; } bool VM_loadProgram(VM* vm, u8* data, size_t size){ @@ -43,22 +44,26 @@ i32 VM_executeProgram(VM* vm){ return -1; } + vm->state = VMState_Executing; vm->current_pos = 0; while (vm->current_pos < vm->data_size){ u8 opcode = vm->data[vm->current_pos]; const Instruction* instr = Instruction_getFromOpcode(opcode); + // printfe("[at 0x%x] %02X %s\n", (u32)vm->current_pos, opcode, instr->name); if(instr == NULL){ VM_setError(vm, "unknown opcode %02X", opcode); return -1; } - vm->current_pos++; + i32 bytes_read = instr->implementation(vm); + // internal error occured if(bytes_read < 0) return -1; - - vm->current_pos += bytes_read; + + if(vm->state == VMState_Exited) + break; } if(vm->state != VMState_Exited){ diff --git a/src/VM/VM.h b/src/VM/VM.h index 865555b..889e1f8 100644 --- a/src/VM/VM.h +++ b/src/VM/VM.h @@ -31,6 +31,7 @@ typedef enum VMState { VMState_Initialized, VMState_Executing, VMState_Exited, + VMState_InternalError } VMState; typedef struct VM { @@ -45,7 +46,7 @@ typedef struct VM { }; VMState state; - char* NULLABLE(error_message); + char* NULLABLE(error_message); // not null on if state == VMState_InternalError u8* data; size_t data_size; diff --git a/src/instructions/impl/PUSH.c b/src/instructions/impl/PUSH.c index 91c4241..91bc539 100644 --- a/src/instructions/impl/PUSH.c +++ b/src/instructions/impl/PUSH.c @@ -10,6 +10,7 @@ i32 PUSH_impl(VM* vm){ vm->registers[dst_register_i].u32v = 0; if(!VM_dataRead(vm, &vm->registers[dst_register_i].u32v, vm->current_pos, value_size)) return -1; + vm->current_pos += value_size; return sizeof(dst_register_i) + sizeof(value_size) + value_size; } diff --git a/src/main.c b/src/main.c index 01d6411..47adf7d 100644 --- a/src/main.c +++ b/src/main.c @@ -26,37 +26,37 @@ i32 main(const i32 argc, const char** argv){ } else if(arg_is("-i") || arg_is("--image")){ if(++argi >= argc){ - printfe("ERROR: no image file specified"); + printfe("ERROR: no image file specified\n"); return 1; } filename = argv[argi]; } else { - printfe("ERROR: unknown argument '%s'", argv[argi]); + printfe("ERROR: unknown argument '%s'\n", argv[argi]); return 1; } } if(filename == NULL){ - printfe("ERROR: no arguments provided. Use --help to know more."); + printfe("ERROR: no arguments provided. Use --help to know more.\n"); return 1; } FILE* file = fopen(filename, "rb"); if(file == NULL){ - printfe("ERROR: can't open file '%s'", filename); + printfe("ERROR: can't open file '%s'\n", filename); return 1; } const size_t buffer_size = 1024*1024; - u8* buffer = malloc(buffer_size); - memset(buffer, 0, buffer_size); + u8* vm_memory = malloc(buffer_size); + memset(vm_memory, 0, buffer_size); - size_t bytes_read = fread(buffer, 1, buffer_size, file); + size_t bytes_read = fread(vm_memory, 1, buffer_size, file); fclose(file); if(bytes_read == (size_t)EOF){ - printfe("ERROR: can't read file '%s'", filename); - free(buffer); + printfe("ERROR: can't read file '%s'\n", filename); + free(vm_memory); return 1; } @@ -64,15 +64,22 @@ i32 main(const i32 argc, const char** argv){ VM_init(&vm); i32 exit_code = 1; - if(VM_loadProgram(&vm, buffer, bytes_read)){ + if(VM_loadProgram(&vm, vm_memory, bytes_read)){ exit_code = VM_executeProgram(&vm); } - if(vm.error_message != NULL){ - printfe("VM ERROR: %s", vm.error_message); - free(vm.error_message); + if(vm.state == VMState_InternalError){ + if(vm.error_message){ + printfe("VM ERROR: %s\n", vm.error_message); + free(vm.error_message); + } + else printfe("VM ERROR: unknown error (error_message is null)\n"); } - free(buffer); + if(exit_code != 0){ + printfe("program exited with code %i\n", exit_code); + } + + free(vm_memory); return exit_code; }