Patch: Fix bus access alignment issue, modrm byte handler enhanced.
This commit is contained in:
@@ -6,41 +6,11 @@
|
||||
#include <bitset>
|
||||
#include <iostream>
|
||||
|
||||
CPUContext::CPUContext(Instruction& i, uint64_t& ip, uint64_t& flags, uint64_t* reg, std::shared_ptr<Bus>& bus) : m_Instruction(i), m_InstructionPointer(ip), m_Flags(flags), m_Registers(reg), m_Bus(bus) { }
|
||||
CPUContext::CPUContext(Instruction& i, uint32_t& ip, uint32_t& flags, uint32_t* reg, std::shared_ptr<Bus>& bus, bool& isHalted) : m_Instruction(i), m_InstructionPointer(ip), m_Flags(flags), m_Registers(reg), m_Bus(bus), m_IsHalted(isHalted) { }
|
||||
|
||||
CPUContext::~CPUContext() = default;
|
||||
|
||||
// NO SIB SUPPORT YET
|
||||
ModRM process_modrm(uint8_t modrm){
|
||||
uint8_t mod_mask = 0b11000000;
|
||||
uint8_t reg_mask = 0b00111000;
|
||||
uint8_t rm_mask = 0b00000111;
|
||||
|
||||
uint8_t mod = modrm & mod_mask;
|
||||
uint8_t reg = (modrm & reg_mask) >> 3;
|
||||
uint8_t rm = modrm & rm_mask;
|
||||
|
||||
ModRMState state = ModRMState::INVALID;
|
||||
|
||||
switch(mod) {
|
||||
case 0b00000000:
|
||||
state = ModRMState::LR;
|
||||
break;
|
||||
case 0b01000000:
|
||||
state = ModRMState::LR_DISP8;
|
||||
break;
|
||||
case 0b10000000:
|
||||
state = ModRMState::LR_DISP32;
|
||||
break;
|
||||
case 0b11000000:
|
||||
state = ModRMState::R;
|
||||
break;
|
||||
default:
|
||||
throw std::runtime_error("Mod R/M does not support non-register operands right now!");
|
||||
}
|
||||
return {.m_State = state, .m_Reg = reg, .m_Rm = rm};
|
||||
}
|
||||
|
||||
namespace executor_cases {
|
||||
void Nop(CPUContext& cc){
|
||||
std::cout << "No op" << std::endl;
|
||||
@@ -53,32 +23,33 @@ namespace executor_cases {
|
||||
|
||||
void Mov_r32_imm32(CPUContext& cc){
|
||||
cc.m_Registers[cc.m_Instruction.m_Operand1] = cc.m_Instruction.m_Operand2;
|
||||
std::cout << "Contents of " << x86::Register2Str((x86::Register)cc.m_Instruction.m_Operand1) << " changed to " << cc.m_Registers[cc.m_Instruction.m_Operand1] << std::endl;
|
||||
}
|
||||
|
||||
//NO SIB SUPPORT YET
|
||||
void Add_rm32_r32(CPUContext& cc){
|
||||
ModRM modrm = process_modrm(cc.m_Instruction.m_Operand1);
|
||||
x86::ModRM modrm = cc.m_Instruction.optional.m_ModRM;
|
||||
|
||||
switch(modrm.m_State) {
|
||||
case ModRMState::R:
|
||||
case x86::ModRMState::R:
|
||||
{
|
||||
cc.m_Registers[modrm.m_Rm] += cc.m_Registers[modrm.m_Reg];
|
||||
std::cout << "Adding " << x86::Register2Str((x86::Register)modrm.m_Reg) << " to " << x86::Register2Str((x86::Register)modrm.m_Rm) << std::endl;
|
||||
break;
|
||||
}
|
||||
case ModRMState::LR:
|
||||
case x86::ModRMState::LR:
|
||||
{
|
||||
uint32_t dstPrevValue = cc.m_Bus->AccessX<uint32_t>(cc.m_Registers[modrm.m_Rm]);
|
||||
uint32_t currRegValue = cc.m_Registers[modrm.m_Reg];
|
||||
uint32_t result = dstPrevValue + currRegValue;
|
||||
cc.m_Bus->WriteX<uint32_t>(cc.m_Registers[modrm.m_Rm], result);
|
||||
std::cout << "Memory address " << std::hex << cc.m_Registers[modrm.m_Rm] << " modified to: " << result << std::endl;
|
||||
break;
|
||||
}
|
||||
case ModRMState::LR_DISP8:
|
||||
case x86::ModRMState::LR_DISP8:
|
||||
{
|
||||
|
||||
uint32_t dstAddress = cc.m_Registers[modrm.m_Rm] + cc.m_Instruction.m_Operand2;
|
||||
uint32_t dstPrevValue = cc.m_Bus->AccessX<uint32_t>(dstAddress);
|
||||
uint32_t currRegValue = cc.m_Registers[modrm.m_Reg];
|
||||
uint32_t result = dstPrevValue + currRegValue;
|
||||
cc.m_Bus->WriteX<uint32_t>(dstAddress, result);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user