diff --git a/vm.c b/vm.c index 339ffa7..8ee8bbb 100644 --- a/vm.c +++ b/vm.c @@ -350,6 +350,7 @@ bool eval_2OPI_Int(struct lilith* vm, struct Instruction* c) { int64_t tmp1; uint64_t utmp1; + uint8_t raw0, raw1, raw2, raw3, raw4, raw5, raw6, raw7; tmp1 = (int64_t)(vm->reg[c->reg1]); utmp1 = vm->reg[c->reg1]; @@ -379,82 +380,309 @@ bool eval_2OPI_Int(struct lilith* vm, struct Instruction* c) } case 0x12: /* CMPI */ { + /* Clear bottom 3 bits of condition register */ + vm->reg[c->reg0] = vm->reg[c->reg0] & 0xFFFFFFFFFFFFFFF8; + if(tmp1 > c->raw_Immediate) + { + vm->reg[c->reg0] = vm->reg[c->reg0] | GreaterThan; + } + else if(tmp1 == c->raw_Immediate) + { + vm->reg[c->reg0] = vm->reg[c->reg0] | EQual; + } + else + { + vm->reg[c->reg0] = vm->reg[c->reg0] | LessThan; + } break; } case 0x13: /* LOAD */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + raw2 = vm->memory[utmp1 + c->raw_Immediate + 2]; + raw3 = vm->memory[utmp1 + c->raw_Immediate + 3]; + raw4 = vm->memory[utmp1 + c->raw_Immediate + 4]; + raw5 = vm->memory[utmp1 + c->raw_Immediate + 5]; + raw6 = vm->memory[utmp1 + c->raw_Immediate + 6]; + raw7 = vm->memory[utmp1 + c->raw_Immediate + 7]; + + vm->reg[c->reg0] = raw0*0x100000000000000 + + raw1*0x1000000000000 + + raw2*0x10000000000 + + raw3*0x100000000 + + raw4*0x1000000 + + raw5*0x10000 + + raw6*0x100 + + raw7; break; } case 0x14: /* LOAD8 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + int64_t tmp = raw0; + + /* Sign extend Register */ + tmp = tmp << 56; + tmp = tmp >> 56; + + vm->reg[c->reg0] = tmp; break; } case 0x15: /* LOADU8 */ { + vm->reg[c->reg0] = (uint8_t)(vm->memory[utmp1 + c->raw_Immediate]); break; } case 0x16: /* LOAD16 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + + int64_t tmp = raw0*0x100 + raw1; + + /* Sign extend Register */ + tmp = tmp << 48; + tmp = tmp >> 48; + vm->reg[c->reg0] = tmp; break; } case 0x17: /* LOADU16 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + + vm->reg[c->reg0] = raw0*0x1000000 + raw1; break; } case 0x18: /* LOAD32 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + raw2 = vm->memory[utmp1 + c->raw_Immediate + 2]; + raw3 = vm->memory[utmp1 + c->raw_Immediate + 3]; + + int64_t tmp = raw0*0x1000000 + + raw1*0x10000 + + raw2*0x100 + + raw3; + /* Sign extend Register */ + tmp = tmp << 32; + tmp = tmp >> 32; + vm->reg[c->reg0] = tmp; break; } case 0x19: /* LOADU32 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + raw2 = vm->memory[utmp1 + c->raw_Immediate + 2]; + raw3 = vm->memory[utmp1 + c->raw_Immediate + 3]; + + vm->reg[c->reg0] = raw0*0x1000000 + + raw1*0x10000 + + raw2*0x100 + + raw3; break; } case 0x1A: /* LOAD64 */ - { - break; - } case 0x1B: /* LOADU64 */ { + raw0 = vm->memory[utmp1 + c->raw_Immediate]; + raw1 = vm->memory[utmp1 + c->raw_Immediate + 1]; + raw2 = vm->memory[utmp1 + c->raw_Immediate + 2]; + raw3 = vm->memory[utmp1 + c->raw_Immediate + 3]; + raw4 = vm->memory[utmp1 + c->raw_Immediate + 4]; + raw5 = vm->memory[utmp1 + c->raw_Immediate + 5]; + raw6 = vm->memory[utmp1 + c->raw_Immediate + 6]; + raw7 = vm->memory[utmp1 + c->raw_Immediate + 7]; + + vm->reg[c->reg0] = raw0*0x100000000000000 + + raw1*0x1000000000000 + + raw2*0x10000000000 + + raw3*0x100000000 + + raw4*0x1000000 + + raw5*0x10000 + + raw6*0x100 + + raw7; break; } case 0x1F: /* CMPUI */ { + /* Clear bottom 3 bits of condition register */ + vm->reg[c->reg0] = vm->reg[c->reg0] & 0xFFFFFFFFFFFFFFF8; + if(utmp1 > (uint32_t)c->raw_Immediate) + { + vm->reg[c->reg0] = vm->reg[c->reg0] | GreaterThan; + } + else if(utmp1 == (uint32_t)c->raw_Immediate) + { + vm->reg[c->reg0] = vm->reg[c->reg0] | EQual; + } + else + { + vm->reg[c->reg0] = vm->reg[c->reg0] | LessThan; + } break; } case 0x20: /* STORE */ { + uint64_t tmp = vm->reg[c->reg0]; + raw7 = tmp%0x100; + tmp = tmp/0x100; + raw6 = tmp%0x100; + tmp = tmp/0x100; + raw5 = tmp%0x100; + tmp = tmp/0x100; + raw4 = tmp%0x100; + tmp = tmp/0x100; + raw3 = tmp%0x100; + tmp = tmp/0x100; + raw2 = tmp%0x100; + tmp = tmp/0x100; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; + vm->memory[utmp1 + c->raw_Immediate + 2] = raw2; + vm->memory[utmp1 + c->raw_Immediate + 3] = raw3; + vm->memory[utmp1 + c->raw_Immediate + 4] = raw4; + vm->memory[utmp1 + c->raw_Immediate + 5] = raw5; + vm->memory[utmp1 + c->raw_Immediate + 6] = raw6; + vm->memory[utmp1 + c->raw_Immediate + 7] = raw7; break; } case 0x21: /* STORE8 */ { + int64_t tmp = (int8_t)(vm->reg[c->reg0]); + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; break; } case 0x22: /* STOREU8 */ { + uint64_t tmp = vm->reg[c->reg0]; + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; break; } case 0x23: /* STORE16 */ { + int64_t tmp = (int16_t)(vm->reg[c->reg0]); + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; break; } case 0x24: /* STOREU16 */ { + uint64_t tmp = vm->reg[c->reg0]; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; break; } case 0x25: /* STORE32 */ { + int64_t tmp = (int64_t)(vm->reg[c->reg0]); + raw3 = tmp%0x100; + tmp = tmp/0x100; + raw2 = tmp%0x100; + tmp = tmp/0x100; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; + vm->memory[utmp1 + c->raw_Immediate + 2] = raw2; + vm->memory[utmp1 + c->raw_Immediate + 3] = raw3; break; } case 0x26: /* STOREU32 */ { + uint64_t tmp = vm->reg[c->reg0]; + raw3 = tmp%0x100; + tmp = tmp/0x100; + raw2 = tmp%0x100; + tmp = tmp/0x100; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp%0x100; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; + vm->memory[utmp1 + c->raw_Immediate + 2] = raw2; + vm->memory[utmp1 + c->raw_Immediate + 3] = raw3; + break; } case 0x27: /* STORE64 */ { + int64_t tmp = (int64_t)(vm->reg[c->reg0]); + raw7 = tmp%0x100; + tmp = tmp/0x100; + raw6 = tmp%0x100; + tmp = tmp/0x100; + raw5 = tmp%0x100; + tmp = tmp/0x100; + raw4 = tmp%0x100; + tmp = tmp/0x100; + raw3 = tmp%0x100; + tmp = tmp/0x100; + raw2 = tmp%0x100; + tmp = tmp/0x100; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; + vm->memory[utmp1 + c->raw_Immediate + 2] = raw2; + vm->memory[utmp1 + c->raw_Immediate + 3] = raw3; + vm->memory[utmp1 + c->raw_Immediate + 4] = raw4; + vm->memory[utmp1 + c->raw_Immediate + 5] = raw5; + vm->memory[utmp1 + c->raw_Immediate + 6] = raw6; + vm->memory[utmp1 + c->raw_Immediate + 7] = raw7; break; } case 0x28: /* STOREU64 */ { + uint64_t tmp = vm->reg[c->reg0]; + raw7 = tmp%0x100; + tmp = tmp/0x100; + raw6 = tmp%0x100; + tmp = tmp/0x100; + raw5 = tmp%0x100; + tmp = tmp/0x100; + raw4 = tmp%0x100; + tmp = tmp/0x100; + raw3 = tmp%0x100; + tmp = tmp/0x100; + raw2 = tmp%0x100; + tmp = tmp/0x100; + raw1 = tmp%0x100; + tmp = tmp/0x100; + raw0 = tmp; + + vm->memory[utmp1 + c->raw_Immediate] = raw0; + vm->memory[utmp1 + c->raw_Immediate + 1] = raw1; + vm->memory[utmp1 + c->raw_Immediate + 2] = raw2; + vm->memory[utmp1 + c->raw_Immediate + 3] = raw3; + vm->memory[utmp1 + c->raw_Immediate + 4] = raw4; + vm->memory[utmp1 + c->raw_Immediate + 5] = raw5; + vm->memory[utmp1 + c->raw_Immediate + 6] = raw6; + vm->memory[utmp1 + c->raw_Immediate + 7] = raw7; break; } default: return true; @@ -644,7 +872,7 @@ void eval_instruction(struct lilith* vm, struct Instruction* current) vm->ip = vm->ip + current->raw_Immediate - 4; break; } - case 0x42: + case 0x42: /* HALCODE */ { } case 0xFF: /* Deal with HALT */