//! Example (and tool) that decodes and instruction and //! prints the corresponding encoder request. use zydis::*; struct Mode(MachineMode, StackWidth); impl Default for Mode { fn default() -> Self { Mode(MachineMode::LONG_64, StackWidth::_64) } } impl std::str::FromStr for Mode { type Err = &'static str; fn from_str(s: &str) -> std::result::Result { Ok(match s { "real" => Self(MachineMode::REAL_16, StackWidth::_16), "16" => Self(MachineMode::LONG_COMPAT_16, StackWidth::_16), "32" => Self(MachineMode::LONG_COMPAT_32, StackWidth::_32), "64" => Self(MachineMode::LONG_64, StackWidth::_64), _ => return Err("unsupported machine mode"), }) } } #[repr(transparent)] struct InsnByte(u8); impl std::str::FromStr for InsnByte { type Err = std::num::ParseIntError; fn from_str(s: &str) -> std::result::Result { u8::from_str_radix(s, 16).map(InsnByte) } } /// Decode an instruction and transform it into an encoder request. #[derive(argh::FromArgs)] struct Args { /// machine mode. 16, 32 or 64. Default is 64. #[argh(option, short = 'm', default = "Mode::default()")] mode: Mode, /// instruction bytes #[argh(positional)] bytes: Vec, } fn main() -> Result<()> { let args: Args = argh::from_env(); let dec = Decoder::new(args.mode.0, args.mode.1)?; let bytes: Vec<_> = args.bytes.into_iter().map(|x| x.0).collect(); let insn = dec .decode_first::(&bytes)? .ok_or(Status::NoMoreData)?; let req: EncoderRequest = insn.into(); assert!(req.encode().is_ok()); println!("{:#?}", req); Ok(()) }