Skip to content

Commit 42d4c38

Browse files
committed
mips: Ignore .NON_MATCHING functions from INLINE_ASM macros
1 parent fa26200 commit 42d4c38

File tree

12 files changed

+539
-46
lines changed

12 files changed

+539
-46
lines changed

objdiff-cli/src/cmd/report.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,7 @@ fn report_object(
232232
if symbol.section != Some(section_idx)
233233
|| symbol.size == 0
234234
|| symbol.flags.contains(SymbolFlag::Hidden)
235+
|| symbol.flags.contains(SymbolFlag::Ignored)
235236
{
236237
continue;
237238
}

objdiff-core/src/arch/mips.rs

Lines changed: 34 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
use alloc::{collections::BTreeMap, string::ToString, vec::Vec};
1+
use alloc::{
2+
collections::{BTreeMap, BTreeSet},
3+
string::ToString,
4+
vec::Vec,
5+
};
26
use core::ops::Range;
37

48
use anyhow::{Result, bail};
@@ -15,7 +19,7 @@ use crate::{
1519
diff::{DiffObjConfig, MipsAbi, MipsInstrCategory, display::InstructionPart},
1620
obj::{
1721
InstructionArg, InstructionArgValue, InstructionRef, Relocation, RelocationFlags,
18-
ResolvedInstructionRef, ResolvedRelocation, ScannedInstruction,
22+
ResolvedInstructionRef, ResolvedRelocation, ScannedInstruction, SymbolFlag, SymbolFlagSet,
1923
},
2024
};
2125

@@ -26,6 +30,7 @@ pub struct ArchMips {
2630
pub isa_extension: Option<IsaExtension>,
2731
pub ri_gp_value: i32,
2832
pub paired_relocations: Vec<BTreeMap<u64, i64>>,
33+
pub ignored_symbols: BTreeSet<usize>,
2934
}
3035

3136
const EF_MIPS_ABI: u32 = 0x0000F000;
@@ -118,7 +123,25 @@ impl ArchMips {
118123
paired_relocations[section_index] = addends;
119124
}
120125

121-
Ok(Self { endianness, abi, isa_extension, ri_gp_value, paired_relocations })
126+
let mut ignored_symbols = BTreeSet::new();
127+
for obj_symbol in object.symbols() {
128+
let Ok(name) = obj_symbol.name() else { continue };
129+
if let Some(prefix) = name.strip_suffix(".NON_MATCHING") {
130+
ignored_symbols.insert(obj_symbol.index().0);
131+
if let Some(target_symbol) = object.symbol_by_name(prefix) {
132+
ignored_symbols.insert(target_symbol.index().0);
133+
}
134+
}
135+
}
136+
137+
Ok(Self {
138+
endianness,
139+
abi,
140+
isa_extension,
141+
ri_gp_value,
142+
paired_relocations,
143+
ignored_symbols,
144+
})
122145
}
123146

124147
fn instruction_flags(&self, diff_config: &DiffObjConfig) -> rabbitizer::InstructionFlags {
@@ -294,6 +317,14 @@ impl Arch for ArchMips {
294317
_ => 1,
295318
}
296319
}
320+
321+
fn extra_symbol_flags(&self, symbol: &object::Symbol) -> SymbolFlagSet {
322+
let mut flags = SymbolFlagSet::default();
323+
if self.ignored_symbols.contains(&symbol.index().0) {
324+
flags |= SymbolFlag::Ignored;
325+
}
326+
flags
327+
}
297328
}
298329

299330
fn push_args(

objdiff-core/src/diff/data.rs

Lines changed: 20 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -139,27 +139,13 @@ pub fn diff_data_section(
139139
) -> Result<(SectionDiff, SectionDiff)> {
140140
let left_section = &left_obj.sections[left_section_idx];
141141
let right_section = &right_obj.sections[right_section_idx];
142-
let left_max = left_obj
143-
.symbols
144-
.iter()
145-
.filter_map(|s| {
146-
if s.section != Some(left_section_idx) || s.kind == SymbolKind::Section {
147-
return None;
148-
}
149-
s.address.checked_sub(left_section.address).map(|a| a + s.size)
150-
})
142+
let left_max = symbols_matching_section(&left_obj.symbols, left_section_idx)
143+
.filter_map(|(_, s)| s.address.checked_sub(left_section.address).map(|a| a + s.size))
151144
.max()
152145
.unwrap_or(0)
153146
.min(left_section.size);
154-
let right_max = right_obj
155-
.symbols
156-
.iter()
157-
.filter_map(|s| {
158-
if s.section != Some(right_section_idx) || s.kind == SymbolKind::Section {
159-
return None;
160-
}
161-
s.address.checked_sub(right_section.address).map(|a| a + s.size)
162-
})
147+
let right_max = symbols_matching_section(&right_obj.symbols, right_section_idx)
148+
.filter_map(|(_, s)| s.address.checked_sub(right_section.address).map(|a| a + s.size))
163149
.max()
164150
.unwrap_or(0)
165151
.min(right_section.size);
@@ -412,21 +398,13 @@ pub fn diff_generic_section(
412398
left_section_idx: usize,
413399
_right_section_idx: usize,
414400
) -> Result<(SectionDiff, SectionDiff)> {
415-
let match_percent = if left_obj
416-
.symbols
417-
.iter()
418-
.enumerate()
419-
.filter(|(_, s)| s.section == Some(left_section_idx) && s.kind != SymbolKind::Section)
401+
let match_percent = if symbols_matching_section(&left_obj.symbols, left_section_idx)
420402
.map(|(i, _)| &left_diff.symbols[i])
421403
.all(|d| d.match_percent == Some(100.0))
422404
{
423405
100.0 // Avoid fp precision issues
424406
} else {
425-
let (matched, total) = left_obj
426-
.symbols
427-
.iter()
428-
.enumerate()
429-
.filter(|(_, s)| s.section == Some(left_section_idx) && s.kind != SymbolKind::Section)
407+
let (matched, total) = symbols_matching_section(&left_obj.symbols, left_section_idx)
430408
.map(|(i, s)| (s, &left_diff.symbols[i]))
431409
.fold((0.0, 0.0), |(matched, total), (s, d)| {
432410
(matched + d.match_percent.unwrap_or(0.0) * s.size as f32, total + s.size as f32)
@@ -449,19 +427,11 @@ pub fn diff_bss_section(
449427
right_section_idx: usize,
450428
) -> Result<(SectionDiff, SectionDiff)> {
451429
let left_section = &left_obj.sections[left_section_idx];
452-
let left_sizes = left_obj
453-
.symbols
454-
.iter()
455-
.enumerate()
456-
.filter(|(_, s)| s.section == Some(left_section_idx) && s.kind != SymbolKind::Section)
430+
let left_sizes = symbols_matching_section(&left_obj.symbols, left_section_idx)
457431
.filter_map(|(_, s)| s.address.checked_sub(left_section.address).map(|a| (a, s.size)))
458432
.collect::<Vec<_>>();
459433
let right_section = &right_obj.sections[right_section_idx];
460-
let right_sizes = right_obj
461-
.symbols
462-
.iter()
463-
.enumerate()
464-
.filter(|(_, s)| s.section == Some(right_section_idx) && s.kind != SymbolKind::Section)
434+
let right_sizes = symbols_matching_section(&right_obj.symbols, right_section_idx)
465435
.filter_map(|(_, s)| s.address.checked_sub(right_section.address).map(|a| (a, s.size)))
466436
.collect::<Vec<_>>();
467437
let ops = capture_diff_slices(Algorithm::Patience, &left_sizes, &right_sizes);
@@ -487,3 +457,15 @@ pub fn diff_bss_section(
487457
SectionDiff { match_percent: Some(match_percent), data_diff: vec![], reloc_diff: vec![] },
488458
))
489459
}
460+
461+
fn symbols_matching_section(
462+
symbols: &[Symbol],
463+
section_idx: usize,
464+
) -> impl Iterator<Item = (usize, &Symbol)> + '_ {
465+
symbols.iter().enumerate().filter(move |(_, s)| {
466+
s.section == Some(section_idx)
467+
&& s.kind != SymbolKind::Section
468+
&& s.size > 0
469+
&& !s.flags.contains(SymbolFlag::Ignored)
470+
})
471+
}

objdiff-core/src/diff/display.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -580,7 +580,11 @@ fn symbol_matches_filter(
580580
if symbol.section.is_none() && !symbol.flags.contains(SymbolFlag::Common) {
581581
return false;
582582
}
583-
if !show_hidden_symbols && (symbol.size == 0 || symbol.flags.contains(SymbolFlag::Hidden)) {
583+
if !show_hidden_symbols
584+
&& (symbol.size == 0
585+
|| symbol.flags.contains(SymbolFlag::Hidden)
586+
|| symbol.flags.contains(SymbolFlag::Ignored))
587+
{
584588
return false;
585589
}
586590
match filter {

objdiff-core/src/diff/mod.rs

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -371,7 +371,10 @@ fn generate_mapping_symbols(
371371
};
372372
let base_section_kind = symbol_section_kind(base_obj, &base_obj.symbols[base_symbol_ref]);
373373
for (target_symbol_index, target_symbol) in target_obj.symbols.iter().enumerate() {
374-
if symbol_section_kind(target_obj, target_symbol) != base_section_kind {
374+
if target_symbol.size == 0
375+
|| target_symbol.flags.contains(SymbolFlag::Ignored)
376+
|| symbol_section_kind(target_obj, target_symbol) != base_section_kind
377+
{
375378
continue;
376379
}
377380
match base_section_kind {
@@ -526,6 +529,9 @@ fn matching_symbols(
526529
)?;
527530
}
528531
for (symbol_idx, symbol) in left.symbols.iter().enumerate() {
532+
if symbol.size == 0 || symbol.flags.contains(SymbolFlag::Ignored) {
533+
continue;
534+
}
529535
let section_kind = symbol_section_kind(left, symbol);
530536
if section_kind == SectionKind::Unknown {
531537
continue;
@@ -547,6 +553,9 @@ fn matching_symbols(
547553
}
548554
if let Some(right) = right {
549555
for (symbol_idx, symbol) in right.symbols.iter().enumerate() {
556+
if symbol.size == 0 || symbol.flags.contains(SymbolFlag::Ignored) {
557+
continue;
558+
}
550559
let section_kind = symbol_section_kind(right, symbol);
551560
if section_kind == SectionKind::Unknown {
552561
continue;
@@ -572,9 +581,10 @@ fn unmatched_symbols<'obj, 'used>(
572581
where
573582
'obj: 'used,
574583
{
575-
obj.symbols.iter().enumerate().filter(move |&(symbol_idx, _)| {
576-
// Skip symbols that have already been matched
577-
!used.is_some_and(|u| u.contains(&symbol_idx))
584+
obj.symbols.iter().enumerate().filter(move |&(symbol_idx, symbol)| {
585+
!symbol.flags.contains(SymbolFlag::Ignored)
586+
// Skip symbols that have already been matched
587+
&& !used.is_some_and(|u| u.contains(&symbol_idx))
578588
})
579589
}
580590

objdiff-core/src/obj/mod.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,8 @@ flags! {
4242
HasExtra,
4343
/// Symbol size was missing and was inferred
4444
SizeInferred,
45+
/// Symbol should be ignored by any diffing
46+
Ignored,
4547
}
4648
}
4749

objdiff-core/tests/arch_mips.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,3 +37,11 @@ fn cross_endian_diff() {
3737
assert_eq!(left_diff.instruction_rows[2].kind, diff::InstructionDiffKind::None);
3838
assert_eq!(right_diff.instruction_rows[2].kind, diff::InstructionDiffKind::None);
3939
}
40+
41+
#[test]
42+
#[cfg(feature = "mips")]
43+
fn filter_non_matching() {
44+
let diff_config = diff::DiffObjConfig::default();
45+
let obj = obj::read::parse(include_object!("data/mips/vw_main.c.o"), &diff_config).unwrap();
46+
insta::assert_debug_snapshot!(obj.symbols);
47+
}
3.61 KB
Binary file not shown.

0 commit comments

Comments
 (0)