void run() { while (true) { //usleep(2); //usleep(50000); //0.05 seconds /*debug_machine_print(*this); getch(true); cout << endl;*/ instr_ptr++; //cout << instr_ptr << endl; if (!mem[instr_ptr]) err("Bad instruction"); instr.uint64 = mem[instr_ptr]; Op op = Op(instr.o); OpLayout layout = op.getLayout(); OpType type = op.getType(); switch (type) { case OpType::NOP: continue; break; case OpType::HALT: return; break; case OpType::MOV: { apply(op, [&](void* a, void* b, u8 size) { memcpy(a, b, size); //*a = *b; }); break; } case OpType::PUSH: { apply(op, [&](void* val, void* unused, u8 size) { memcpy(&mem[stack_ptr++], val, size); }); break; } case OpType::POP: { apply(op, [&](void* val, void* unused, u8 size) { assert(layout == OpLayout::R); //memcpy(&r[*(u16*)val], &mem[stack_ptr--], size); memcpy(val, &mem[(stack_ptr--)-1], size); }); break; } case OpType::INT: { assert(layout == OpLayout::C); u8 cmd = instr.c; switch (cmd) { case 0: usleep(r[0]); break; case 1: cout << (char)r[0]; break; case 2: r[0] = getch(false); break; default: err("interrupt not implemented"); cout << cmd; break; } break; } case OpType::JMP: { apply(op, [&](void* val, void* unused, u8 size) { //KK TODO assert(layout == OpLayout::M); assert(layout == OpLayout::C || layout == OpLayout::R); instr_ptr = *((u16*)val); }); break; } case OpType::CMP: { apply(op, [&](void* a, void* b, u8 size) { cmp_result = asm_cmp(a, b, size); }); break; } case OpType::JE: { apply(op, [&](void* val, void* unused, u8 size) { assert(layout == OpLayout::C); if (cmp_result == 4) err("jump without previous cmp"); if (cmp_result == 0) instr_ptr = *((u16*)val); }); break; } case OpType::SUB: { assert(layout == OpLayout::RC); //temporary only for fib apply(op, [&](void* a, void* b, u8 size) { assert(size == 4); *(u64*)a =(u64) *(u32*)a - *(u32*)b; }); break; } case OpType::ADD: { assert(layout == OpLayout::RR); //temporary only for fib apply(op, [&](void* a, void* b, u8 size) { assert(size == 8); *(u64*)a =(u64) *(u64*)a + *(u64*)b; }); break; } default: op.print(); err("Command not implemented"); break; } } }
int testOp() { Op x = Op(OpType::POP, OpLayout::NONE); x.print(); Op(OpType::MOV, OpLayout::RR).print(); Op(OpType::MOV, OpLayout::NONE).print(); }