ft: Implement Group 4 Instructions
This commit is contained in:
@@ -15,6 +15,7 @@ use crate::{modrmb, modrms, modrmv};
|
||||
pub enum DisasmError {
|
||||
NoFile(Option<String>),
|
||||
IoError(std::io::Error),
|
||||
OpcodeUndefined(u8),
|
||||
}
|
||||
|
||||
impl From<std::io::Error> for DisasmError {
|
||||
@@ -28,6 +29,11 @@ impl fmt::Display for DisasmError {
|
||||
match self {
|
||||
DisasmError::NoFile(msg) => write!(f, "No file error: {:?}", msg),
|
||||
DisasmError::IoError(msg) => write!(f, "{}", msg),
|
||||
DisasmError::OpcodeUndefined(opcode) => write!(
|
||||
f,
|
||||
"Instruction '{:#x} is considered undefined by the Spec",
|
||||
opcode
|
||||
),
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -327,7 +333,8 @@ impl Disassembler {
|
||||
0x0D => Mnemonic::OR_AXIv(self.parse_word()),
|
||||
|
||||
0x0E => Mnemonic::PUSH_S(SegmentRegister::CS),
|
||||
0x0F => panic!("Opcode 0x0F (POP CS) is considered undefined"),
|
||||
|
||||
0x0F => return Err(DisasmError::OpcodeUndefined(opcode)),
|
||||
|
||||
0x10 => modrmb!(self, ADC_FromReg),
|
||||
0x11 => modrmv!(self, ADC_FromReg),
|
||||
@@ -389,23 +396,23 @@ impl Disassembler {
|
||||
0x3E => Mnemonic::OVERRIDE(SegmentRegister::DS),
|
||||
0x3F => Mnemonic::AAS,
|
||||
|
||||
0x40 => Mnemonic::INC(Register::AX),
|
||||
0x41 => Mnemonic::INC(Register::CX),
|
||||
0x42 => Mnemonic::INC(Register::DX),
|
||||
0x43 => Mnemonic::INC(Register::BX),
|
||||
0x44 => Mnemonic::INC(Register::SP),
|
||||
0x45 => Mnemonic::INC(Register::BP),
|
||||
0x46 => Mnemonic::INC(Register::SI),
|
||||
0x47 => Mnemonic::INC(Register::DI),
|
||||
0x40 => Mnemonic::INC_Reg(Register::AX),
|
||||
0x41 => Mnemonic::INC_Reg(Register::CX),
|
||||
0x42 => Mnemonic::INC_Reg(Register::DX),
|
||||
0x43 => Mnemonic::INC_Reg(Register::BX),
|
||||
0x44 => Mnemonic::INC_Reg(Register::SP),
|
||||
0x45 => Mnemonic::INC_Reg(Register::BP),
|
||||
0x46 => Mnemonic::INC_Reg(Register::SI),
|
||||
0x47 => Mnemonic::INC_Reg(Register::DI),
|
||||
|
||||
0x48 => Mnemonic::DEC(Register::AX),
|
||||
0x49 => Mnemonic::DEC(Register::CX),
|
||||
0x4A => Mnemonic::DEC(Register::DX),
|
||||
0x4B => Mnemonic::DEC(Register::BX),
|
||||
0x4C => Mnemonic::DEC(Register::SP),
|
||||
0x4D => Mnemonic::DEC(Register::BP),
|
||||
0x4E => Mnemonic::DEC(Register::SI),
|
||||
0x4F => Mnemonic::DEC(Register::DI),
|
||||
0x48 => Mnemonic::DEC_Reg(Register::AX),
|
||||
0x49 => Mnemonic::DEC_Reg(Register::CX),
|
||||
0x4A => Mnemonic::DEC_Reg(Register::DX),
|
||||
0x4B => Mnemonic::DEC_Reg(Register::BX),
|
||||
0x4C => Mnemonic::DEC_Reg(Register::SP),
|
||||
0x4D => Mnemonic::DEC_Reg(Register::BP),
|
||||
0x4E => Mnemonic::DEC_Reg(Register::SI),
|
||||
0x4F => Mnemonic::DEC_Reg(Register::DI),
|
||||
|
||||
0x50 => Mnemonic::PUSH_R(Register::AX),
|
||||
0x51 => Mnemonic::PUSH_R(Register::CX),
|
||||
@@ -425,7 +432,7 @@ impl Disassembler {
|
||||
0x5E => Mnemonic::POP_R(Register::SI),
|
||||
0x5F => Mnemonic::POP_R(Register::DI),
|
||||
|
||||
0x60..=0x6F => panic!("{:#x} is considered undefined", opcode),
|
||||
0x60..=0x6F => return Err(DisasmError::OpcodeUndefined(opcode)),
|
||||
|
||||
0x70 => Mnemonic::JO(self.parse_byte()),
|
||||
0x71 => Mnemonic::JNO(self.parse_byte()),
|
||||
@@ -548,14 +555,14 @@ impl Disassembler {
|
||||
0xBE => Mnemonic::MOV_SIIv(self.parse_word()),
|
||||
0xBF => Mnemonic::MOV_DIIv(self.parse_word()),
|
||||
|
||||
0xC0..=0xC1 => panic!("{:#x} is considered in undefined", opcode),
|
||||
0xC0..=0xC1 => return Err(DisasmError::OpcodeUndefined(opcode)),
|
||||
|
||||
0xC2 => Mnemonic::RETIw(self.parse_word()),
|
||||
0xC3 => Mnemonic::RET,
|
||||
|
||||
0xC4..=0xC5 => panic!("{:#x} not yet implemented (LDS or LES)", opcode),
|
||||
0xC4..=0xC5 => todo!("LES and LDS not yet implemented"),
|
||||
|
||||
0xC8..=0xC9 => panic!("{:#x} is considered in undefined", opcode),
|
||||
0xC8..=0xC9 => return Err(DisasmError::OpcodeUndefined(opcode)),
|
||||
|
||||
0xCD => Mnemonic::INT(self.parse_byte()),
|
||||
|
||||
@@ -598,6 +605,16 @@ impl Disassembler {
|
||||
self.modrm_reg_to_grp3(reg, target, Operand::Word(0))
|
||||
}
|
||||
|
||||
0xFE => {
|
||||
let (target, reg) = self.parse_modrm_byte(Operand::Byte(0));
|
||||
match reg {
|
||||
0b0 => Mnemonic::INC_Mod(target),
|
||||
0b1 => Mnemonic::DEC_Mod(target),
|
||||
_ => panic!("Illegal Group 4 mnemonic"),
|
||||
}
|
||||
}
|
||||
0xFF => todo!("Group 5"),
|
||||
|
||||
_ => {
|
||||
eprintln!("Encountered unknown instruction '0x{:x}'", opcode);
|
||||
eprintln!("Offset might be misaligned and data is being interpreted.");
|
||||
|
||||
@@ -138,9 +138,11 @@ pub enum Mnemonic {
|
||||
CMP_ALIb(Byte),
|
||||
CMP_AXIv(Word),
|
||||
// INC
|
||||
INC(Register),
|
||||
INC_Reg(Register),
|
||||
INC_Mod(ModRmTarget),
|
||||
// DEC
|
||||
DEC(Register),
|
||||
DEC_Reg(Register),
|
||||
DEC_Mod(ModRmTarget),
|
||||
// Jumps
|
||||
JO(Byte),
|
||||
JNO(Byte),
|
||||
|
||||
Reference in New Issue
Block a user