Skip to content

Commit

Permalink
Should be mostly done?
Browse files Browse the repository at this point in the history
  • Loading branch information
AngheloAlf committed Oct 20, 2024
1 parent c96c23d commit 4a2f208
Show file tree
Hide file tree
Showing 4 changed files with 101 additions and 87 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ crate-type = ["cdylib", "staticlib", "rlib"]
default = []
python_bindings = ["dep:pyo3"]
serde = ["dep:serde"]
objdiff_report = ["dep:objdiff-core"]
objdiff_report = ["dep:objdiff-core", "dep:serde"]

[dependencies]
regex = "1.10.2"
Expand Down
2 changes: 1 addition & 1 deletion src/rs/mapfile.rs
Original file line number Diff line number Diff line change
Expand Up @@ -466,7 +466,7 @@ impl MapFile {

// Calculate size of last symbol of the file
let sym = &mut file.symbols[symbols_count - 1];
if sym.size == 0{
if sym.size == 0 {
let sym_size = file.size - acummulated_size;
sym.size = sym_size;
}
Expand Down
167 changes: 94 additions & 73 deletions src/rs/report.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,43 +16,49 @@ fn do_report(mapfile: &mapfile::MapFile) -> report::Report {
for (segment_index, segment) in mapfile.segments_list.iter().enumerate() {
for section in &segment.files_list {
let section_path = section.filepath.to_string_lossy().to_string();
let mut new_report_unit = report_from_section(section);

if let Some(report_unit) = units.iter_mut().find(|x| x.name == section_path) {
report_unit.measures = measures_from_section(report_unit.measures, section);
report_unit.sections.push(report_item_from_section(section));
report_unit
.functions
.extend(gather_functions_from_section(section));
report_unit.measures =
merge_measures(report_unit.measures, new_report_unit.measures);
report_unit.sections.extend(new_report_unit.sections);
report_unit.functions.extend(new_report_unit.functions);
} else {
let report_unit = report::ReportUnit {
name: section_path.clone(),
measures: measures_from_section(None, section),
sections: vec![report_item_from_section(section)],
functions: gather_functions_from_section(section),
metadata: Some(report::ReportUnitMetadata {
complete: None,
module_name: Some(segment.name.clone()),
module_id: Some(segment_index as u32),
source_path: Some(section_path),
progress_categories: Vec::new(), // TODO
auto_generated: None, // TODO: What?
}),
};

units.push(report_unit);
new_report_unit.metadata = Some(report::ReportUnitMetadata {
complete: None,
module_name: Some(segment.name.clone()),
module_id: Some(segment_index as u32),
source_path: Some(section_path),
progress_categories: Vec::new(), // TODO
auto_generated: None, // TODO: What?
});

units.push(new_report_unit);
}
}
}

for unit in units.iter_mut() {
if let Some(measures) = &mut unit.measures {
if measures.total_code > 0 {
measures.matched_code_percent =
measures.matched_code as f32 / measures.total_code as f32 * 100.0;
}
if measures.total_data > 0 {
measures.matched_data_percent =
measures.matched_data as f32 / measures.total_data as f32 * 100.0;
}
if measures.total_functions > 0 {
measures.matched_functions_percent =
measures.matched_functions as f32 / measures.total_functions as f32 * 100.0;
}

let total = measures.total_code + measures.total_data;
if total > 0 {
measures.fuzzy_match_percent = (measures.matched_code + measures.matched_data) as f32 / total as f32 * 100.0;
measures.fuzzy_match_percent =
(measures.matched_code + measures.matched_data) as f32 / total as f32 * 100.0;
}
}

// unit.sections // .fuzzy_match_percent
}

let measures = units.iter().flat_map(|u| u.measures.into_iter()).collect();
Expand All @@ -71,56 +77,93 @@ fn do_report(mapfile: &mapfile::MapFile) -> report::Report {
report
}

fn measures_from_section(
measures_aux: Option<report::Measures>,
section: &file::File,
) -> Option<report::Measures> {
if section.size == 0 {
return None;
}
fn report_from_section(section: &file::File) -> report::ReportUnit {
let mut measures = report::Measures::default();
let mut report_item = report_item_from_section(section);
let mut functions = Vec::new();

let mut measures = measures_aux.unwrap_or_default();
let is_text = matches!(section.section_type.as_str(), ".text" | ".start");

for sym_state in section.symbol_match_state_iter(None) {
let sym_size;
match sym_state {
let mut fuzzy_match_percent = 0.0;

let sym = match sym_state {
file::SymbolDecompState::Decomped(sym) => {
sym_size = sym.size;
if is_text {
measures.matched_code += sym.size;
measures.matched_functions += 1;
fuzzy_match_percent = 100.0;
} else {
measures.matched_data += sym.size;
}
},
file::SymbolDecompState::Undecomped(sym) => {
sym_size = sym.size;
},
}
sym
}
file::SymbolDecompState::Undecomped(sym) => sym,
};

if is_text {
measures.total_code += sym_size;
measures.total_code += sym.size;
measures.total_functions += 1;

functions.push(report::ReportItem {
name: sym.name.clone(),
size: sym.size,
fuzzy_match_percent,
metadata: Some(report::ReportItemMetadata {
demangled_name: None,
virtual_address: Some(sym.vram),
}),
});
} else {
measures.total_data += sym_size;
measures.total_data += sym.size;
}
}

if measures.total_code > 0 {
measures.matched_code_percent = measures.matched_code as f32 / measures.total_code as f32 * 100.0;
}
if measures.total_data > 0 {
measures.matched_data_percent = measures.matched_data as f32 / measures.total_data as f32 * 100.0;
}
if measures.total_functions > 0 {
measures.matched_functions_percent = measures.matched_functions as f32 / measures.total_functions as f32 * 100.0;
if measures.total_code + measures.total_data > 0 {
report_item.fuzzy_match_percent = (measures.matched_code + measures.matched_data) as f32
/ (measures.total_code + measures.total_data) as f32
* 100.0;
}

// An unit always contains a singular unit, no more, no less. Right?
measures.total_units = 1;

Some(measures)
report::ReportUnit {
name: section.filepath.to_string_lossy().to_string(),
measures: Some(measures),
sections: vec![report_item],
functions,
metadata: None,
}
}

fn merge_measures(
a: Option<report::Measures>,
b: Option<report::Measures>,
) -> Option<report::Measures> {
match (a, b) {
(None, None) => None,
(None, Some(b)) => Some(b),
(Some(a), None) => Some(a),
(Some(a), Some(b)) => Some(report::Measures {
fuzzy_match_percent: 0.0,
total_code: a.total_code + b.total_code,
matched_code: a.matched_code + b.matched_code,
matched_code_percent: 0.0,
total_data: a.total_data + b.total_data,
matched_data: a.matched_data + b.matched_data,
matched_data_percent: 0.0,
total_functions: a.total_functions + b.total_functions,
matched_functions: a.matched_functions + b.matched_functions,
matched_functions_percent: 0.0,
complete_code: 0,
complete_code_percent: 0.0,
complete_data: 0,
complete_data_percent: 0.0,
total_units: 1,
complete_units: 0,
}),
}
}

fn report_item_from_section(section: &file::File) -> report::ReportItem {
Expand All @@ -134,25 +177,3 @@ fn report_item_from_section(section: &file::File) -> report::ReportItem {
}),
}
}

fn gather_functions_from_section(section: &file::File) -> Vec<report::ReportItem> {
if section.section_type != ".text" && section.section_type != ".start" {
return Vec::new();
}

let mut funcs = Vec::new();

for sym in &section.symbols {
funcs.push(report::ReportItem {
name: sym.name.clone(),
size: sym.size,
fuzzy_match_percent: 0.0, // TODO
metadata: Some(report::ReportItemMetadata {
demangled_name: None,
virtual_address: Some(sym.vram),
}),
});
}

funcs
}
17 changes: 5 additions & 12 deletions src/rs/symbol.rs
Original file line number Diff line number Diff line change
Expand Up @@ -31,13 +31,7 @@ pub struct Symbol {
}

impl Symbol {
pub fn new(
name: String,
vram: u64,
size: u64,
vrom: Option<u64>,
align: Option<u64>,
) -> Self {
pub fn new(name: String, vram: u64, size: u64, vrom: Option<u64>, align: Option<u64>) -> Self {
Self {
name,
vram,
Expand Down Expand Up @@ -227,12 +221,11 @@ pub(crate) mod python_bindings {
#[pyo3(signature=(humanReadable=true))]
fn serializeSize(&self, humanReadable: bool) -> PyObject {
Python::with_gil(|py| {
if humanReadable {
return format!("0x{:X}", self.size).to_object(py);
}
self.size.to_object(py)
if humanReadable {
return format!("0x{:X}", self.size).to_object(py);
}
)
self.size.to_object(py)
})
}

#[pyo3(signature=(humanReadable=true))]
Expand Down

0 comments on commit 4a2f208

Please sign in to comment.