ft: fixed modrm target calculation

While implementing some more mnemonics and testing
them, it was clear that modrm parsing was wrong.
Now reg to reg and immediates, together with
GPR1 interpretation should work as expected.

GPR1 interpretation can currently not be merged
into the modrm function, as with the current
abstraction the REG needs to select the correct
mnemonic, for which we need to also know the second
operand, which will only be parsed afterwards.
But this will be incorporated at some point, this
just marks the first working state.
This commit is contained in:
2025-05-13 12:07:22 +09:00
parent 51b28b3bac
commit a25e0a3890
3 changed files with 450 additions and 117 deletions

View File

@@ -1,8 +1,26 @@
#[macro_export]
/// Generate an Opcode for 'normal' ModRM instructions with mem access and a reg
macro_rules! modrm {
/// Generate a byte Opcode for 'normal' ModRM instructions with mem access and a reg
macro_rules! modrmb {
($self:ident, $variant:ident) => {{
let (idx, reg) = $self.parse_modrm_byte();
Opcode::$variant(idx, Register::by_id(reg))
let (target, reg) = $self.parse_modrm_byte(OperandSize::Byte(0));
Mnemonic::$variant(target, Register::by_id(OperandSize::Byte(reg)))
}};
}
#[macro_export]
/// Generate a word Opcode for 'normal' ModRM instructions with mem access and a reg
macro_rules! modrmv {
($self:ident, $variant:ident) => {{
let (target, reg) = $self.parse_modrm_byte(OperandSize::Word(0));
Mnemonic::$variant(target, Register::by_id(OperandSize::Word(reg.into())))
}};
}
#[macro_export]
/// Generate a word Opcode for 'normal' ModRM instructions with mem access and a segment reg
macro_rules! modrms {
($self:ident, $variant:ident) => {{
let (target, reg) = $self.parse_modrm_byte(OperandSize::Word(0));
Mnemonic::$variant(target, SegmentRegister::by_id(reg))
}};
}