Skip to content

Commit 3385f58

Browse files
stravantencounter
andauthored
Fix data flow analysis for multiple text sections (#220)
* Fix data flow analysis for multiple text sections * Data flow analysis results were only keyed by the symbol (function) address. That doen't work if there are multiple text sections, the result from the first function in one section will stomp the result from the first function in another because both have address zero. * Remove the ambiguity by keying off of the section address as well. * Formatting * Satisfy wasm build * Clippy * Formatting again * Thought that section was the section address not the section number. --------- Co-authored-by: Luke Street <[email protected]>
1 parent 60b227f commit 3385f58

File tree

3 files changed

+28
-7
lines changed

3 files changed

+28
-7
lines changed

objdiff-core/src/diff/display.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -189,7 +189,7 @@ pub fn display_row(
189189
let mut arg_idx = 0;
190190
let mut displayed_relocation = false;
191191
let analysis_result = if diff_config.show_data_flow {
192-
obj.flow_analysis_results.get(&resolved.symbol.address)
192+
obj.get_flow_analysis_result(resolved.symbol)
193193
} else {
194194
None
195195
};
@@ -217,7 +217,7 @@ pub fn display_row(
217217
}
218218
let data_flow_value =
219219
analysis_result.and_then(|result|
220-
result.as_ref().get_argument_value_at_address(
220+
result.get_argument_value_at_address(
221221
ins_ref.address, (arg_idx - 1) as u8));
222222
match (arg, data_flow_value, resolved.ins_ref.branch_dest) {
223223
// If we have a flow analysis result, always use that over anything else.

objdiff-core/src/obj/mod.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -338,6 +338,20 @@ impl Object {
338338
self.symbols.iter().position(|symbol| symbol.section.is_some() && symbol.name == name)
339339
}
340340

341+
pub fn get_flow_analysis_result(&self, symbol: &Symbol) -> Option<&dyn FlowAnalysisResult> {
342+
let key = symbol.section.unwrap_or_default() as u64 * 1024 * 1024 * 1024 + symbol.address;
343+
self.flow_analysis_results.get(&key).map(|result| result.as_ref())
344+
}
345+
346+
pub fn add_flow_analysis_result(
347+
&mut self,
348+
symbol: &Symbol,
349+
result: Box<dyn FlowAnalysisResult>,
350+
) {
351+
let key = symbol.section.unwrap_or_default() as u64 * 1024 * 1024 * 1024 + symbol.address;
352+
self.flow_analysis_results.insert(key, result);
353+
}
354+
341355
pub fn has_flow_analysis_result(&self) -> bool { !self.flow_analysis_results.is_empty() }
342356
}
343357

objdiff-core/src/obj/read.rs

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
use alloc::{
2+
boxed::Box,
23
collections::BTreeMap,
34
format,
45
string::{String, ToString},
@@ -13,8 +14,8 @@ use crate::{
1314
arch::{Arch, new_arch},
1415
diff::DiffObjConfig,
1516
obj::{
16-
Object, Relocation, RelocationFlags, Section, SectionData, SectionFlag, SectionKind,
17-
Symbol, SymbolFlag, SymbolKind,
17+
FlowAnalysisResult, Object, Relocation, RelocationFlags, Section, SectionData, SectionFlag,
18+
SectionKind, Symbol, SymbolFlag, SymbolKind,
1819
split_meta::{SPLITMETA_SECTION, SplitMeta},
1920
},
2021
util::{align_data_slice_to, align_u64_to, read_u16, read_u32},
@@ -439,6 +440,7 @@ fn perform_data_flow_analysis(obj: &mut Object, config: &DiffObjConfig) -> Resul
439440
}
440441

441442
let mut generated_relocations = Vec::<(usize, Vec<Relocation>)>::new();
443+
let mut generated_flow_results = Vec::<(Symbol, Box<dyn FlowAnalysisResult>)>::new();
442444
for (section_index, section) in obj.sections.iter().enumerate() {
443445
if section.kind != SectionKind::Code {
444446
continue;
@@ -474,12 +476,17 @@ fn perform_data_flow_analysis(obj: &mut Object, config: &DiffObjConfig) -> Resul
474476

475477
// Optional full data flow analysis
476478
if config.analyze_data_flow {
477-
obj.arch.data_flow_analysis(obj, symbol, code, &section.relocations).and_then(
478-
|flow_result| obj.flow_analysis_results.insert(symbol.address, flow_result),
479-
);
479+
if let Some(flow_result) =
480+
obj.arch.data_flow_analysis(obj, symbol, code, &section.relocations)
481+
{
482+
generated_flow_results.push((symbol.clone(), flow_result));
483+
}
480484
}
481485
}
482486
}
487+
for (symbol, flow_result) in generated_flow_results {
488+
obj.add_flow_analysis_result(&symbol, flow_result);
489+
}
483490
for (section_index, mut relocations) in generated_relocations {
484491
obj.sections[section_index].relocations.append(&mut relocations);
485492
}

0 commit comments

Comments
 (0)