diff --git a/src/interpreter/computer.rs b/src/interpreter/computer.rs index 8c1d65b..1295033 100644 --- a/src/interpreter/computer.rs +++ b/src/interpreter/computer.rs @@ -260,6 +260,22 @@ impl Computer { } } } + + /// Write an [`ImmediateOperand`] into [`Self::memory`] or [`Self::regs`]. + pub fn write_modrm(&mut self, target: ModRmTarget, val: ImmediateOperand) { + match target { + ModRmTarget::Memory(idx) => self.memory.write(&self.regs, idx, val), + ModRmTarget::Register(reg) => self.regs.write(reg, val), + }; + } + + /// Read an [`ImmediateOperand`] from [`Self::memory`] or [`Self::regs`]. + pub fn read_modrm(&self, target: ModRmTarget) -> ImmediateOperand { + match target { + ModRmTarget::Memory(idx) => self.memory.read(&self.regs, idx), + ModRmTarget::Register(reg) => self.regs.read(reg), + } + } } impl fmt::Display for Computer { diff --git a/src/interpreter/interpreter.rs b/src/interpreter/interpreter.rs index 8cd54c4..20a69da 100644 --- a/src/interpreter/interpreter.rs +++ b/src/interpreter/interpreter.rs @@ -390,7 +390,39 @@ impl Interpreter { /* * MOV */ - Mnemonic::MOV_BXIv(word) => self.computer.regs.bx.write(word), + Mnemonic::MOV_FromReg(target, reg) => self + .computer + .write_modrm(target, self.computer.regs.read(reg)), + Mnemonic::MOV_ToReg(target, reg) => self + .computer + .regs + .write(reg, self.computer.read_modrm(target)), + Mnemonic::MOV_FromSReg(_, _) => todo!(), + Mnemonic::MOV_ToSReg(_, _) => todo!(), + Mnemonic::MOV_Ib(target, val) => self.computer.write_modrm(target, val.into()), + Mnemonic::MOV_Iv(target, val) => self.computer.write_modrm(target, val.into()), + + Mnemonic::MOV_AL0b(val) => self.computer.regs.ax.lower = val, + Mnemonic::MOV_AX0v(val) => self.computer.regs.ax.write(val), + Mnemonic::MOV_0bAL(_) => todo!(), + Mnemonic::MOV_0vAX(_) => todo!(), + + Mnemonic::MOV_ALIb(val) => self.computer.regs.ax.lower = val, + Mnemonic::MOV_CLIb(val) => self.computer.regs.cx.lower = val, + Mnemonic::MOV_DLIb(val) => self.computer.regs.dx.lower = val, + Mnemonic::MOV_BLIb(val) => self.computer.regs.bx.lower = val, + Mnemonic::MOV_AHIb(val) => self.computer.regs.ax.upper = val, + Mnemonic::MOV_CHIb(val) => self.computer.regs.ax.upper = val, + Mnemonic::MOV_DHIb(val) => self.computer.regs.ax.upper = val, + Mnemonic::MOV_BHIb(val) => self.computer.regs.ax.upper = val, + Mnemonic::MOV_AXIv(val) => self.computer.regs.ax.write(val), + Mnemonic::MOV_CXIv(val) => self.computer.regs.cx.write(val), + Mnemonic::MOV_DXIv(val) => self.computer.regs.dx.write(val), + Mnemonic::MOV_BXIv(val) => self.computer.regs.bx.write(val), + Mnemonic::MOV_SPIv(val) => self.computer.regs.sp = val, + Mnemonic::MOV_BPIv(val) => self.computer.regs.bp = val, + Mnemonic::MOV_SIIv(val) => self.computer.regs.si = val, + Mnemonic::MOV_DIIv(val) => self.computer.regs.di = val, /* * LEA diff --git a/src/interpreter/register.rs b/src/interpreter/register.rs index bbd6743..562253c 100644 --- a/src/interpreter/register.rs +++ b/src/interpreter/register.rs @@ -50,8 +50,8 @@ impl Register { } /// Write an [`ImmediateOperand`] to a [`crate::register::Register`]. - pub fn write(&mut self, reg: crate::register::Register, op: ImmediateOperand) { - match op { + pub fn write(&mut self, reg: crate::register::Register, val: ImmediateOperand) { + match val { ImmediateOperand::Byte(byte) => match reg { crate::register::Register::AX => self.ax.lower = byte, crate::register::Register::BX => self.bx.lower = byte, @@ -109,8 +109,8 @@ macro_rules! gen_regs { ($ident:ident) => { #[derive(Debug, Clone, Copy)] pub struct $ident { - upper: Byte, - lower: Byte, + pub upper: Byte, + pub lower: Byte, } impl $ident { diff --git a/src/operands.rs b/src/operands.rs index 96e8059..4b9b425 100644 --- a/src/operands.rs +++ b/src/operands.rs @@ -95,6 +95,18 @@ impl ImmediateOperand { } } +impl From for ImmediateOperand { + fn from(value: Byte) -> Self { + Self::Byte(value) + } +} + +impl From for ImmediateOperand { + fn from(value: Word) -> Self { + Self::Word(value) + } +} + impl Into for ImmediateOperand { fn into(self) -> usize { match self {