mirror of
https://github.com/encounter/objdiff.git
synced 2025-06-07 15:13:47 +00:00
Add initial support for x86-64 relocations
This commit is contained in:
parent
3965a035fa
commit
c6971f3f2d
@ -15,17 +15,36 @@ use crate::{
|
|||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct ArchX86 {
|
pub struct ArchX86 {
|
||||||
bits: u32,
|
arch: Architecture,
|
||||||
endianness: object::Endianness,
|
endianness: object::Endianness,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
enum Architecture {
|
||||||
|
X86,
|
||||||
|
X86_64,
|
||||||
|
}
|
||||||
|
|
||||||
impl ArchX86 {
|
impl ArchX86 {
|
||||||
pub fn new(object: &object::File) -> Result<Self> {
|
pub fn new(object: &object::File) -> Result<Self> {
|
||||||
Ok(Self { bits: if object.is_64() { 64 } else { 32 }, endianness: object.endianness() })
|
let arch = match object.architecture() {
|
||||||
|
object::Architecture::I386 => Architecture::X86,
|
||||||
|
object::Architecture::X86_64 => Architecture::X86_64,
|
||||||
|
_ => bail!("Unsupported architecture for ArchX86: {:?}", object.architecture()),
|
||||||
|
};
|
||||||
|
Ok(Self { arch, endianness: object.endianness() })
|
||||||
}
|
}
|
||||||
|
|
||||||
fn decoder<'a>(&self, code: &'a [u8], address: u64) -> Decoder<'a> {
|
fn decoder<'a>(&self, code: &'a [u8], address: u64) -> Decoder<'a> {
|
||||||
Decoder::with_ip(self.bits, code, address, DecoderOptions::NONE)
|
Decoder::with_ip(
|
||||||
|
match self.arch {
|
||||||
|
Architecture::X86 => 32,
|
||||||
|
Architecture::X86_64 => 64,
|
||||||
|
},
|
||||||
|
code,
|
||||||
|
address,
|
||||||
|
DecoderOptions::NONE,
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn formatter(&self, diff_config: &DiffObjConfig) -> Box<dyn iced_x86::Formatter> {
|
fn formatter(&self, diff_config: &DiffObjConfig) -> Box<dyn iced_x86::Formatter> {
|
||||||
@ -38,6 +57,27 @@ impl ArchX86 {
|
|||||||
formatter.options_mut().set_space_after_operand_separator(diff_config.space_between_args);
|
formatter.options_mut().set_space_after_operand_separator(diff_config.space_between_args);
|
||||||
formatter
|
formatter
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn reloc_size(&self, flags: RelocationFlags) -> Option<usize> {
|
||||||
|
match self.arch {
|
||||||
|
Architecture::X86 => match flags {
|
||||||
|
RelocationFlags::Coff(typ) => match typ {
|
||||||
|
pe::IMAGE_REL_I386_DIR16 | pe::IMAGE_REL_I386_REL16 => Some(2),
|
||||||
|
pe::IMAGE_REL_I386_DIR32 | pe::IMAGE_REL_I386_REL32 => Some(4),
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
Architecture::X86_64 => match flags {
|
||||||
|
RelocationFlags::Coff(typ) => match typ {
|
||||||
|
pe::IMAGE_REL_AMD64_ADDR32NB | pe::IMAGE_REL_AMD64_REL32 => Some(4),
|
||||||
|
pe::IMAGE_REL_AMD64_ADDR64 => Some(8),
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Arch for ArchX86 {
|
impl Arch for ArchX86 {
|
||||||
@ -88,10 +128,9 @@ impl Arch for ArchX86 {
|
|||||||
// memory operand.
|
// memory operand.
|
||||||
let mut reloc_replace = None;
|
let mut reloc_replace = None;
|
||||||
if let Some(reloc) = resolved.relocation {
|
if let Some(reloc) = resolved.relocation {
|
||||||
const PLACEHOLDER: u64 = 0x7BDE3E7D; // chosen by fair dice roll.
|
const PLACEHOLDER: u64 = 0x7BDE3E7D; // chosen by fair dice roll. guaranteed to be random.
|
||||||
// guaranteed to be random.
|
|
||||||
let reloc_offset = reloc.relocation.address - resolved.ins_ref.address;
|
let reloc_offset = reloc.relocation.address - resolved.ins_ref.address;
|
||||||
let reloc_size = reloc_size(reloc.relocation.flags).unwrap_or(usize::MAX);
|
let reloc_size = self.reloc_size(reloc.relocation.flags).unwrap_or(usize::MAX);
|
||||||
let offsets = decoder.get_constant_offsets(&instruction);
|
let offsets = decoder.get_constant_offsets(&instruction);
|
||||||
if reloc_offset == offsets.displacement_offset() as u64
|
if reloc_offset == offsets.displacement_offset() as u64
|
||||||
&& reloc_size == offsets.displacement_size()
|
&& reloc_size == offsets.displacement_size()
|
||||||
@ -148,12 +187,28 @@ impl Arch for ArchX86 {
|
|||||||
_relocation: &object::Relocation,
|
_relocation: &object::Relocation,
|
||||||
flags: RelocationFlags,
|
flags: RelocationFlags,
|
||||||
) -> Result<i64> {
|
) -> Result<i64> {
|
||||||
match flags {
|
match self.arch {
|
||||||
RelocationFlags::Coff(pe::IMAGE_REL_I386_DIR32 | pe::IMAGE_REL_I386_REL32) => {
|
Architecture::X86 => match flags {
|
||||||
let data = section.data()?[address as usize..address as usize + 4].try_into()?;
|
RelocationFlags::Coff(pe::IMAGE_REL_I386_DIR32 | pe::IMAGE_REL_I386_REL32) => {
|
||||||
Ok(self.endianness.read_i32_bytes(data) as i64)
|
let data =
|
||||||
}
|
section.data()?[address as usize..address as usize + 4].try_into()?;
|
||||||
flags => bail!("Unsupported x86 implicit relocation {flags:?}"),
|
Ok(self.endianness.read_i32_bytes(data) as i64)
|
||||||
|
}
|
||||||
|
flags => bail!("Unsupported x86 implicit relocation {flags:?}"),
|
||||||
|
},
|
||||||
|
Architecture::X86_64 => match flags {
|
||||||
|
RelocationFlags::Coff(pe::IMAGE_REL_AMD64_ADDR32NB | pe::IMAGE_REL_AMD64_REL32) => {
|
||||||
|
let data =
|
||||||
|
section.data()?[address as usize..address as usize + 4].try_into()?;
|
||||||
|
Ok(self.endianness.read_i32_bytes(data) as i64)
|
||||||
|
}
|
||||||
|
RelocationFlags::Coff(pe::IMAGE_REL_AMD64_ADDR64) => {
|
||||||
|
let data =
|
||||||
|
section.data()?[address as usize..address as usize + 8].try_into()?;
|
||||||
|
Ok(self.endianness.read_i64_bytes(data))
|
||||||
|
}
|
||||||
|
flags => bail!("Unsupported x86-64 implicit relocation {flags:?}"),
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -168,27 +223,29 @@ impl Arch for ArchX86 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn reloc_name(&self, flags: RelocationFlags) -> Option<&'static str> {
|
fn reloc_name(&self, flags: RelocationFlags) -> Option<&'static str> {
|
||||||
match flags {
|
match self.arch {
|
||||||
RelocationFlags::Coff(typ) => match typ {
|
Architecture::X86 => match flags {
|
||||||
pe::IMAGE_REL_I386_DIR32 => Some("IMAGE_REL_I386_DIR32"),
|
RelocationFlags::Coff(typ) => match typ {
|
||||||
pe::IMAGE_REL_I386_REL32 => Some("IMAGE_REL_I386_REL32"),
|
pe::IMAGE_REL_I386_DIR32 => Some("IMAGE_REL_I386_DIR32"),
|
||||||
|
pe::IMAGE_REL_I386_REL32 => Some("IMAGE_REL_I386_REL32"),
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
|
Architecture::X86_64 => match flags {
|
||||||
|
RelocationFlags::Coff(typ) => match typ {
|
||||||
|
pe::IMAGE_REL_AMD64_ADDR64 => Some("IMAGE_REL_AMD64_ADDR64"),
|
||||||
|
pe::IMAGE_REL_AMD64_ADDR32NB => Some("IMAGE_REL_AMD64_ADDR32NB"),
|
||||||
|
pe::IMAGE_REL_AMD64_REL32 => Some("IMAGE_REL_AMD64_REL32"),
|
||||||
|
_ => None,
|
||||||
|
},
|
||||||
_ => None,
|
_ => None,
|
||||||
},
|
},
|
||||||
_ => None,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn data_reloc_size(&self, flags: RelocationFlags) -> usize { reloc_size(flags).unwrap_or(1) }
|
fn data_reloc_size(&self, flags: RelocationFlags) -> usize {
|
||||||
}
|
self.reloc_size(flags).unwrap_or(1)
|
||||||
|
|
||||||
fn reloc_size(flags: RelocationFlags) -> Option<usize> {
|
|
||||||
match flags {
|
|
||||||
RelocationFlags::Coff(typ) => match typ {
|
|
||||||
pe::IMAGE_REL_I386_DIR16 | pe::IMAGE_REL_I386_REL16 => Some(2),
|
|
||||||
pe::IMAGE_REL_I386_DIR32 | pe::IMAGE_REL_I386_REL32 => Some(4),
|
|
||||||
_ => None,
|
|
||||||
},
|
|
||||||
_ => None,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -343,7 +400,7 @@ mod test {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_scan_instructions() {
|
fn test_scan_instructions() {
|
||||||
let arch = ArchX86 { bits: 32, endianness: object::Endianness::Little };
|
let arch = ArchX86 { arch: Architecture::X86, endianness: object::Endianness::Little };
|
||||||
let code = [
|
let code = [
|
||||||
0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x04, 0x85, 0x00,
|
0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x04, 0x85, 0x00,
|
||||||
0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00,
|
||||||
@ -362,7 +419,7 @@ mod test {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_process_instruction() {
|
fn test_process_instruction() {
|
||||||
let arch = ArchX86 { bits: 32, endianness: object::Endianness::Little };
|
let arch = ArchX86 { arch: Architecture::X86, endianness: object::Endianness::Little };
|
||||||
let code = [0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00];
|
let code = [0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00];
|
||||||
let opcode = iced_x86::Mnemonic::Mov as u16;
|
let opcode = iced_x86::Mnemonic::Mov as u16;
|
||||||
let mut parts = Vec::new();
|
let mut parts = Vec::new();
|
||||||
@ -398,7 +455,7 @@ mod test {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_process_instruction_with_reloc_1() {
|
fn test_process_instruction_with_reloc_1() {
|
||||||
let arch = ArchX86 { bits: 32, endianness: object::Endianness::Little };
|
let arch = ArchX86 { arch: Architecture::X86, endianness: object::Endianness::Little };
|
||||||
let code = [0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00];
|
let code = [0xc7, 0x85, 0x68, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00];
|
||||||
let opcode = iced_x86::Mnemonic::Mov as u16;
|
let opcode = iced_x86::Mnemonic::Mov as u16;
|
||||||
let mut parts = Vec::new();
|
let mut parts = Vec::new();
|
||||||
@ -443,7 +500,7 @@ mod test {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_process_instruction_with_reloc_2() {
|
fn test_process_instruction_with_reloc_2() {
|
||||||
let arch = ArchX86 { bits: 32, endianness: object::Endianness::Little };
|
let arch = ArchX86 { arch: Architecture::X86, endianness: object::Endianness::Little };
|
||||||
let code = [0x8b, 0x04, 0x85, 0x00, 0x00, 0x00, 0x00];
|
let code = [0x8b, 0x04, 0x85, 0x00, 0x00, 0x00, 0x00];
|
||||||
let opcode = iced_x86::Mnemonic::Mov as u16;
|
let opcode = iced_x86::Mnemonic::Mov as u16;
|
||||||
let mut parts = Vec::new();
|
let mut parts = Vec::new();
|
||||||
@ -486,7 +543,7 @@ mod test {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_process_instruction_with_reloc_3() {
|
fn test_process_instruction_with_reloc_3() {
|
||||||
let arch = ArchX86 { bits: 32, endianness: object::Endianness::Little };
|
let arch = ArchX86 { arch: Architecture::X86, endianness: object::Endianness::Little };
|
||||||
let code = [0xe8, 0x00, 0x00, 0x00, 0x00];
|
let code = [0xe8, 0x00, 0x00, 0x00, 0x00];
|
||||||
let opcode = iced_x86::Mnemonic::Call as u16;
|
let opcode = iced_x86::Mnemonic::Call as u16;
|
||||||
let mut parts = Vec::new();
|
let mut parts = Vec::new();
|
||||||
|
@ -26,3 +26,17 @@ fn read_x86_combine_sections() {
|
|||||||
let obj = obj::read::parse(include_object!("data/x86/rtest.obj"), &diff_config).unwrap();
|
let obj = obj::read::parse(include_object!("data/x86/rtest.obj"), &diff_config).unwrap();
|
||||||
insta::assert_debug_snapshot!(obj.sections);
|
insta::assert_debug_snapshot!(obj.sections);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "x86")]
|
||||||
|
fn read_x86_64() {
|
||||||
|
let diff_config = diff::DiffObjConfig::default();
|
||||||
|
let obj = obj::read::parse(include_object!("data/x86_64/vs2022.o"), &diff_config).unwrap();
|
||||||
|
insta::assert_debug_snapshot!(obj);
|
||||||
|
let symbol_idx =
|
||||||
|
obj.symbols.iter().position(|s| s.name == "?Dot@Vector@@QEAAMPEAU1@@Z").unwrap();
|
||||||
|
let diff = diff::code::no_diff_code(&obj, symbol_idx, &diff_config).unwrap();
|
||||||
|
insta::assert_debug_snapshot!(diff.instruction_rows);
|
||||||
|
let output = common::display_diff(&obj, &diff, symbol_idx, &diff_config);
|
||||||
|
insta::assert_snapshot!(output);
|
||||||
|
}
|
||||||
|
BIN
objdiff-core/tests/data/x86_64/vs2022.o
Normal file
BIN
objdiff-core/tests/data/x86_64/vs2022.o
Normal file
Binary file not shown.
@ -4,7 +4,7 @@ expression: obj
|
|||||||
---
|
---
|
||||||
Object {
|
Object {
|
||||||
arch: ArchX86 {
|
arch: ArchX86 {
|
||||||
bits: 32,
|
arch: X86,
|
||||||
endianness: Little,
|
endianness: Little,
|
||||||
},
|
},
|
||||||
endianness: Little,
|
endianness: Little,
|
||||||
|
279
objdiff-core/tests/snapshots/arch_x86__read_x86_64-2.snap
Normal file
279
objdiff-core/tests/snapshots/arch_x86__read_x86_64-2.snap
Normal file
@ -0,0 +1,279 @@
|
|||||||
|
---
|
||||||
|
source: objdiff-core/tests/arch_x86.rs
|
||||||
|
expression: diff.instruction_rows
|
||||||
|
---
|
||||||
|
[
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 0,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 5,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 10,
|
||||||
|
size: 1,
|
||||||
|
opcode: 640,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 11,
|
||||||
|
size: 4,
|
||||||
|
opcode: 740,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 15,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 20,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 25,
|
||||||
|
size: 4,
|
||||||
|
opcode: 448,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 29,
|
||||||
|
size: 4,
|
||||||
|
opcode: 460,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 33,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 38,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 43,
|
||||||
|
size: 5,
|
||||||
|
opcode: 448,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 48,
|
||||||
|
size: 5,
|
||||||
|
opcode: 460,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 53,
|
||||||
|
size: 4,
|
||||||
|
opcode: 11,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 57,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 62,
|
||||||
|
size: 5,
|
||||||
|
opcode: 414,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 67,
|
||||||
|
size: 5,
|
||||||
|
opcode: 448,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 72,
|
||||||
|
size: 5,
|
||||||
|
opcode: 460,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 77,
|
||||||
|
size: 4,
|
||||||
|
opcode: 11,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 81,
|
||||||
|
size: 4,
|
||||||
|
opcode: 7,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 85,
|
||||||
|
size: 1,
|
||||||
|
opcode: 590,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
InstructionDiffRow {
|
||||||
|
ins_ref: Some(
|
||||||
|
InstructionRef {
|
||||||
|
address: 86,
|
||||||
|
size: 1,
|
||||||
|
opcode: 662,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
kind: None,
|
||||||
|
branch_from: None,
|
||||||
|
branch_to: None,
|
||||||
|
arg_diff: [],
|
||||||
|
},
|
||||||
|
]
|
25
objdiff-core/tests/snapshots/arch_x86__read_x86_64-3.snap
Normal file
25
objdiff-core/tests/snapshots/arch_x86__read_x86_64-3.snap
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
---
|
||||||
|
source: objdiff-core/tests/arch_x86.rs
|
||||||
|
expression: output
|
||||||
|
---
|
||||||
|
[(Address(0), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(16)), Normal, 0), (Basic("]"), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Opaque("rdx")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(5), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(8)), Normal, 0), (Basic("]"), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Opaque("rcx")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(10), Normal, 5), (Spacing(4), Normal, 0), (Opcode("push", 640), Normal, 10), (Argument(Opaque("rdi")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(11), Normal, 5), (Spacing(4), Normal, 0), (Opcode("sub", 740), Normal, 10), (Argument(Opaque("rsp")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Unsigned(16)), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(15), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rax")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(32)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(20), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rcx")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(40)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(25), Normal, 5), (Spacing(4), Normal, 0), (Opcode("movss", 448), Normal, 10), (Argument(Opaque("xmm0")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rax")), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(29), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mulss", 460), Normal, 10), (Argument(Opaque("xmm0")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rcx")), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(33), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rax")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(32)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(38), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rcx")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(40)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(43), Normal, 5), (Spacing(4), Normal, 0), (Opcode("movss", 448), Normal, 10), (Argument(Opaque("xmm1")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rax")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(4)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(48), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mulss", 460), Normal, 10), (Argument(Opaque("xmm1")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rcx")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(4)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(53), Normal, 5), (Spacing(4), Normal, 0), (Opcode("addss", 11), Normal, 10), (Argument(Opaque("xmm0")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Opaque("xmm1")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(57), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rax")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(32)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(62), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mov", 414), Normal, 10), (Argument(Opaque("rcx")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rsp")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(40)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(67), Normal, 5), (Spacing(4), Normal, 0), (Opcode("movss", 448), Normal, 10), (Argument(Opaque("xmm1")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rax")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(8)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(72), Normal, 5), (Spacing(4), Normal, 0), (Opcode("mulss", 460), Normal, 10), (Argument(Opaque("xmm1")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Basic("["), Normal, 0), (Argument(Opaque("rcx")), Normal, 0), (Argument(Opaque("+")), Normal, 0), (Argument(Signed(8)), Normal, 0), (Basic("]"), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(77), Normal, 5), (Spacing(4), Normal, 0), (Opcode("addss", 11), Normal, 10), (Argument(Opaque("xmm0")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Opaque("xmm1")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(81), Normal, 5), (Spacing(4), Normal, 0), (Opcode("add", 7), Normal, 10), (Argument(Opaque("rsp")), Normal, 0), (Basic(","), Normal, 0), (Spacing(1), Normal, 0), (Argument(Unsigned(16)), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(85), Normal, 5), (Spacing(4), Normal, 0), (Opcode("pop", 590), Normal, 10), (Argument(Opaque("rdi")), Normal, 0), (Eol, Normal, 0)]
|
||||||
|
[(Address(86), Normal, 5), (Spacing(4), Normal, 0), (Opcode("ret", 662), Normal, 10), (Eol, Normal, 0)]
|
1505
objdiff-core/tests/snapshots/arch_x86__read_x86_64.snap
Normal file
1505
objdiff-core/tests/snapshots/arch_x86__read_x86_64.snap
Normal file
File diff suppressed because it is too large
Load Diff
Loading…
x
Reference in New Issue
Block a user